Running a startup is a lot of work. All manner of tasks constantly compete for the team’s attention mandating a careful dance to keep on top of everything. We haven’t nailed all the footwork to this dance yet, but we have learned that choosing the right tool for each job can drastically simplify the choreography.
We recently rewrote a large portion of Myna in the march towards version 2 of the platform. Most of the customer-facing software – the dashboard, client libraries, HTTP API, and so on – were completely new and required new documentation. Our existing help pages were in need of an overhaul, so we decided to move them out into their own project using a build system based on Grunt and Jekyll.
The new documentation is still a work-in-progress – you can watch its evolution on the Myna website and its repository on Github (yes, it’s open source – another experiment we’re trying). We’re really happy with the way it’s all working out, so we’ve published the build system as a separate project that you can use to bootstrap your own documentation. Go forth, fork, and profit!
Our old documentation was implemented as a set of templates in the Play 2 web app that runs our marketing site and original customer dashboard. Publishing the app requires a PhD in SBT, Mongo and Redis, and if you’re writing documentation on the train (as we are prone to do) it isn’t uncommon to have your plans abruptly terminated by one of SBT’s frequent unavoidable urges to download the whole internet (unadvisable in the middle of signal-free rural England).
We considered moving to a CMS such as WordPress, but our support team are all developers with their own preferred editors and IDEs. Forcing them to write documentation (painful) in a tiny WYSIWYG editor embedded into a web site seemed like torture. Also, CMSs require internet connections… it kinda goes with the territory.
Grunt and Jekyll, in contrast, run completely offline, and have a number of other advantages too. Plugins like grunt-contrib-watch provide instant previews via Livereload, and Jekyll’s syntax highlighting (provided by Pygments) can highlight any syntax you throw at it (including, to my amazement, HTTP).
Jekyll isn’t completely perfect for the job. We had to work around a few issues. Fortunately, none of them proved insurmountable:
We’ve run into versioning problems many times before, some requiring some pretty serious workarounds. In fact, versioning issues are pretty much endemic across all software development platforms. In this toolchain we’re relying on lots of components: Grunt, five Grunt plugins, Ruby, and Jekyll. Fortunately, versioning is pretty much a solved problem these days: NPM and Bower are great package managers for Node, and Bundler normalizes not only the version of Jekyll we’re using, but also the version of Ruby itself.
Static Assets (Say “NO” to Plain CSS)
One way of solving these issues would be to use Jekyll plugins – there are many candidates available on Github. However, we prefer to use Grunt for this kind of thing, running Jekyll via grunt-exec and Bundler, and using grunt-contrib-watch and grunt-contrib-connect for preview functionality.
Jekyll has built-in support for cataloguing and paginating blog posts, but it can’t natively generate navigation for a hierarchical documentation site. Fortunately, this was easy to work around with a couple of custom plugins: one to create a table of contents for the sidebar, and one to generate next and previous buttons at the bottom of each page.
If you like the idea of writing documentation in Markdown, you can get started in two minutes by cloning our Github repo and following the instructions in the README. We’d love to hear from you if you find our system useful, and we welcome pull requests with improvements.