================================= Host a Technical Blog with Docker ================================= .. figure:: /_images/image_homepagesample.png Sample screenshot from a new deployment Date: **2016-06-25** I built this repository_ for hosting my own technical blog + resume + work portfolio. It uses `docker compose`_ to deploy my nginx_ and sphinx-bootstrap_ containers and shares a mounted volume across the two containers. I use this repository for hosting: https://jaypjohnson.com Docker Hub Image(s): `jayjohnson/nginx`_ and `jayjohnson/sphinx-bootstrap`_ Container Repo(s): docker-nginx_ and docker-sphinx-bootstrap_ .. role:: bash(code) :language: bash Overview -------- I built this composition for hosting a nice-to-read blog that made it easy to generate content instead of battling formatting. Now I can write a post using `reStructuredText Markup`_ and the `python Sphinx bootstrap`_ documentation tooling converts each ``rst`` file into readable, static html which is hosted using the nginx_ container for HTTP traffic on port 80 (or 443) to the static html files. Once I containerized the sphinx-bootstrap-theme_ I added automatic integration with `Google Analytics`_ + `Google Search Console`_ for others looking to do the same thing. I like that out-of-the-box the sphinx-bootstrap-theme_ comes with support for `multiple bootswatch themes`_ and there are even more themes available from the `bootswatch repository`_ and `bootswatch website`_. Additionally it is nice to know that this blog is already mobile-ready because it is built using `bootstrap`_. Integrating with Google Analytics ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 1. Set your `Google Analytics Tracking Code`_ to the ENV_GOOGLE_ANALYTICS_CODE_ environment variable before container creation During container startup the environment variable ``ENV_GOOGLE_ANALYTICS_CODE`` will be `automatically installed into the default html layout`_ on every page across your site Integrating with Google Search Console ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 1. Automatic **sitemap.xml** creation When the container starts or you `manually rebuild the html content`_ it will `automatically build`_ a ``sitemap.xml`` from any files ending with a ``.rst`` extension in the repository's root directory. This file is stored in the environment variable ``ENV_DOC_OUTPUT_DIR`` directory. This is handy when you want to integrate your site into the `Google Search Console`_ and it should look similar to: https://jaypjohnson.com/sitemap.xml What can I use it for? ~~~~~~~~~~~~~~~~~~~~~~ After working with the `Levvel team`_ over the past year, I realized the importance of having a blog to demonstrate technical expertise. After watching wordpress lose my work, I knew there had to be a better way. Recently, my friend `Alex Smith`_ recommended I check out `Sphinx`_ because it made documentation even easier than traditional markdown. After finding the `python Sphinx bootstrap`_ repository I knew I wanted to drop this into a docker container so I could deploy content while keeping the nginx services up and running. I now use this repository as `my blog`_ for `technical posts`_, hosting my `projects and stack discussions`_, `work history`_, resume_, and `contact information`_. I find it so much easier to write an ``rst`` file and let the framework translate it into formatted, stylized html. Now I can focus on content instead of the presentation (which is nice because I am not a web developer or artist). Other interesting out-of-the-box features are: * A native ``Search`` bar on each page * Each page has a ``Source`` button in the navigation bar to quickly inspect the original ``rst`` markup data .. _docker compose: https://docs.docker.com/compose/ .. _Google Analytics: https://analytics.google.com/ .. _Google Search Console: https://www.google.com/webmasters/tools/ .. _Levvel team: http://levvel.io .. _Alex Smith: https://github.com/ajsmith .. _Sphinx: http://www.sphinx-doc.org/en/stable/ .. _reStructuredText Markup: http://docutils.sourceforge.net/docs/ref/rst/restructuredtext.html .. _python Sphinx bootstrap: https://github.com/ryan-roemer/sphinx-bootstrap-theme .. _sphinx-bootstrap-theme: https://github.com/ryan-roemer/sphinx-bootstrap-theme .. _multiple bootswatch themes: https://github.com/ryan-roemer/sphinx-bootstrap-theme/blob/bfb28af310ad5082fae01dc1ff08dab6ab3fa410/demo/source/conf.py#L146-L150 .. _bootswatch website: http://bootswatch.com/ .. _bootswatch repository: https://github.com/thomaspark/bootswatch .. _bootstrap: http://getbootstrap.com/ .. _Google Analytics Tracking Code: https://support.google.com/analytics/answer/1008080?hl=en .. _ENV_GOOGLE_ANALYTICS_CODE: https://github.com/jay-johnson/docker-nginx-sphinx-bootstrap/blob/db0f1f944918a0c8a0e1c2c6593cde6f01a173f1/docker-compose.yml#L24 .. _automatically installed into the default html layout: https://github.com/jay-johnson/docker-sphinx-bootstrap/blob/2a752b96a7bcd378dbb207da1922c2e8997dc7ae/containerfiles/start-container.sh#L13-L14 .. _manually rebuild the html content: https://github.com/jay-johnson/docker-sphinx-bootstrap/blob/2a752b96a7bcd378dbb207da1922c2e8997dc7ae/containerfiles/start-container.sh#L16-17 .. _automatically build: https://github.com/jay-johnson/docker-sphinx-bootstrap/blob/2a752b96a7bcd378dbb207da1922c2e8997dc7ae/containerfiles/start-container.sh#L21-L41 .. _my blog: https://jaypjohnson.com .. _technical posts : https://jaypjohnson.com/2016-06-24-configurable-docker-nginx.html .. _projects and stack discussions: https://jaypjohnson.com/redis.html .. _resume: https://jaypjohnson.com/_downloads/JayJohnson-Resume.pdf .. _work history : https://jaypjohnson.com/work_history.html .. _contact information: https://jaypjohnson.com/contact.html .. _repository: https://github.com/jay-johnson/docker-nginx-sphinx-bootstrap .. _nginx : https://hub.docker.com/r/jayjohnson/nginx/ .. _sphinx-bootstrap : https://hub.docker.com/r/jayjohnson/sphinx-bootstrap .. _jayjohnson/nginx : https://hub.docker.com/r/jayjohnson/nginx/ .. _jayjohnson/sphinx-bootstrap : https://hub.docker.com/r/jayjohnson/sphinx-bootstrap .. _start_container.sh: https://github.com/jay-johnson/docker-nginx/blob/master/containerfiles/start-container.sh .. _base nginx.conf : https://github.com/jay-johnson/docker-nginx/blob/master/containerfiles/base_nginx.conf .. _derived nginx.conf : https://github.com/jay-johnson/docker-nginx/blob/master/containerfiles/derived_nginx.conf .. _properties.sh : https://github.com/jay-johnson/docker-nginx/blob/master/properties.sh .. _docker-compose.yml: https://github.com/jay-johnson/docker-nginx-sphinx-bootstrap/blob/master/docker-compose.yml .. _docker-sphinx-bootstrap: https://github.com/jay-johnson/docker-sphinx-bootstrap .. _docker-nginx: https://github.com/jay-johnson/docker-nginx .. _deploy + rebuild script: https://github.com/jay-johnson/docker-sphinx-bootstrap/blob/2a752b96a7bcd378dbb207da1922c2e8997dc7ae/containerfiles/deploy-new-content.sh Install and Setup ----------------- I am running the docker containers on an Amazon EC2 t1.micro with a Route 53 dns alias record set to route ``jaypjohnson.com`` traffic to the micro. On the EC2 micro I ran these commands to setup and deploy the site: #. Create the ``/opt/blog`` directory :: $ mkdir -p /opt/blog/ && chmod 777 /opt/blog #. Clone this repo :: $ cd /opt/blog $ git clone https://github.com/jay-johnson/docker-nginx-sphinx-bootstrap.git repo $ cd repo $ #. Start the composition :: $ ./start_composition.sh Creating websphinx Creating webnginx Done $ #. Test the blog :: $ curl -s http://localhost:80 | grep Welcome | grep h2