---
title: "Case study: Switching tools to docs-as-code"
date: 2026-09-28
description: "Download PDF Changing any documentation tooling at a company can be a massive undertaking. Depending on the amount of legacy content to convert, the number of..."
canonical_url: https://idratherbewriting.com/learnapidoc/pubapis_switching_to_docs_as_code
---
# Case study: Switching tools to docs-as-code
[Download PDF](https://www.buymeacoffee.com/learnapidoc/e/146076)

Changing any documentation tooling at a company can be a massive undertaking. Depending on the amount of legacy content to convert, the number of writers to train, the restrictions and processes you have to work against in your corporate environment and more, it can require an immense amount of time and effort to switch tools from the status quo to docs-as-code.

Additionally, you will likely need to make this change outside your regular documentation work, and you’ll probably need to develop the new system *while still updating and publishing content in the old system*. Essentially, this means you’ll be laying down a new highway while simultaneously driving down it.

For an overview of the docs-as-code approach, see [Docs-as-code tools](pubapis_docs_as_code.html). In this article, I describe the challenges we faced in implementing a docs-as-code approach within a tech writing group at a large company.

 - [Creative solutions for theme distribution across repos](#creative-solutions-for-theme-distribution-across-repos)

 - [Ensuring everyone builds with the same version of Jekyll](#ensuring-everyone-builds-with-the-same-version-of-jekyll)

 - [Figuring out translation workflows](#figuring-out-translation-workflows)

 - [Other challenges](#other-challenges) 

 [Moving content out of the legacy CMS](#moving-content-out-of-the-legacy-cms)

 - [Implementing new processes while still supporting the old](#implementing-new-processes-while-still-supporting-the-old)

 - [Constantly changing the processes for documentation](#constantly-changing-the-processes-for-documentation)

 - [Styling the tech docs within a larger site](#styling-the-tech-docs-within-a-larger-site)

 - [Transitioning to a Git-based workflow](#transitioning-to-a-git-based-workflow)

 - [Striking a balance between simplicity and robustness in doc tooling](#striking-a-balance-between-simplicity-and-robustness-in-doc-tooling)

 - [Building a system that scales](#building-a-system-that-scales)

 - [Conclusion](#conclusion)

 - [Slides and links to republished content](#slides-and-links-to-republished-content)

## Previous processes

Previously, our team published content through a content management system called [Hippo](https://www.bloomreach.com/) (by Bloomreach). Hippo is similar to WordPress or Drupal but is Java-based rather than PHP-based (which made it attractive to a Java-centric enterprise that restricted PHP but still needed a CMS solution for publishing).

To publish a page of documentation, tech writers had to create a new page in the Hippo CMS and then paste in the HTML for the page (or try to use the WYSIWYG editor in the Hippo CMS). If you had 50 pages of documentation to publish, you would need to paste the HTML into each CMS page one by one. Originally, many writers would use tools such as [Pandoc](https://pandoc.org/) to convert their content to HTML and then paste it into the Hippo CMS. This copy-and-paste approach was tedious, prone to error, and primitive.

When I started, I championed using Jekyll to generate and manage the HTML, and I started storing the Jekyll projects in internal Git repositories. I also created a layout in Jekyll that was explicitly designed for Hippo publishing. The layout included a documentation-specific sidebar (previously absent in Hippo on a granular level) to navigate all the content in a particular set of documentation. This Jekyll layout included several styles and scripts to override settings in the CMS.

Despite this innovation, our publishing process still involved pasting the generated HTML (after building Jekyll) page by page into the CMS. Thus, we were only partially using docs-as-code and still had a long way to go. One of the tenets of docs-as-code is to build your output directly from the server (called “continuous deployment”). In other words, you incorporate the publishing logic on the server rather than running the publishing process from your local computer.

This last step, publishing directly from the server, was difficult because another engineering group was responsible for the website and server, and we couldn’t just rip Hippo out and start uploading the Jekyll-generated files onto a web server ourselves. It would take another year or more before the engineering team had the bandwidth for the project. Once it started, the project was a wild ride of mismatched expectations and assumptions. But in the end, we succeeded.

Most of the lessons learned here are about this process, specifically how we transitioned to building Jekyll directly from an internal Git repo, the decisions we made and the reasoning behind those decisions, the compromises and other changes of direction, and so on. My purpose here is to share lessons learned so that other writers embarking on similar endeavors can benefit from understanding what might be on the road ahead.

## Advantages of integrating into a larger system

Why did we want to move to docs as code in the first place? At most large companies, there are plenty of robust, internally developed tools that tech writers can take advantage of. The docs-as-code approach would allow us to integrate into this robust enterprise infrastructure that developers had already created.

Documentation tools are often independent, standalone tools that offer complete functionality (such as version control, search, and deployment) within their own system. But these systems are often a black box, meaning, you can’t really open them up and integrate them into another process or system. With the docs-as-code approach, we had the flexibility to adapt our process to fully integrate within the company’s infrastructure and website deployment process. Some of this infrastructure we wanted to hook into included the following:

 - Internal test environments (a gamma environment separate from production)

 - Authentication for specific pages based on account profiles

 - Search and indexing

 - Website templating (primarily a complex header and footer)

 - Robust analytics

 - Secure servers to satisfy Information Security policies with the corporate domain

 - Media CDN for distributing images

 - Git repositories and GUI for managing code

 - Build pipelines and a build management system

All we really needed to do was to generate out the body HTML along with the sidebar and make it available for the existing infrastructure to consume. The engineering team that supported the website already had a process in place for managing and deploying content on the site. We wanted to use similar processes rather than coming up with an entirely different approach.

## End solution

In the end, here’s the solution we implemented. We stored our Jekyll project in an internal Git repository — the same farm of Git repositories other engineers used for nearly every software project, and which connected into a build management system. After we pushed our Jekyll doc content to the master branch of the Git repository, a build pipeline would kick off and build the Jekyll project directly from the server (similar to [GitHub Pages](https://pages.github.com/)).

Our Jekyll layout omitted any header or footer in the theme. The built HTML pages were then pulled into an S3 bucket in AWS through an ingestion tool (which would check for titles, descriptions, and unique permalinks in the HTML). This bucket acted as a flat-file database for storing content. Our website would make calls to the content in S3 based on permalink values in the HTML to pull the content into another website template that included the header and footer.

The build process from the Git repo to the deployed website took about 10 minutes, but tech writers didn’t need to do anything during that time. After you typed a few commands in your terminal (merging with the `gamma` or `production` branch locally and then pushing out the update to origin), the deployment process kicked off and ran all by itself.

The first day in launching our new system, a team had to publish 40 new pages of documentation. Had we still been in Hippo, this would have taken several hours to publish. Even more painful, their release timeframe was an early morning, pre-dawn hour, so the team would have had to publish 40 pages in Hippo CMS at around 4 am to 6 am, copying and pasting the HTML frantically to meet the release push and hoping they didn’t screw anything up.

Instead, with the new process, the writer just merged her `development` branch into the `production` branch and pushed the update to the repo. Ten minutes later, all 40 pages were live on the site. She was floored! We knew this was the beginning of a new chapter in the team’s processes. We all felt like a considerable publishing burden had been lifted off our shoulders.

## Challenges we faced

I’ve summarized the success and overall approach, but there were a lot of questions and hurdles in developing the process. I’ll detail these main challenges in the following sections.

### Inability to do it ourselves

The biggest challenge, ironically, was probably with myself — dealing with my own perfectionist, controlling tendencies to do everything on my own, just how I wanted. (This is probably both my biggest weakness and strength as a technical writer.) It’s hard for me to relinquish control and have another team do the work. We had to wait *about a year* for the overworked engineering team’s schedule to clear up so they would have the bandwidth to do the project.

During this wait time, we refined our Jekyll theme and process, ramped up on our Git skills, and migrated all of the content out of the old CMS into [kramdown Markdown](https://kramdown.gettalong.org/). Even so, as project timelines kept getting delayed and pushed out, we weren’t sure if the engineering team’s bandwidth would ever lighten up. I wanted to jump ship and just deploy everything myself through the [S3_website plugin](https://github.com/laurilehmijoki/s3_website) on [AWS S3](https://aws.amazon.com/s3/).

But as I researched domain policies, server requirements, and other corporate standards and workflows, I realized that a do-it-myself approach wouldn’t work (unless I possessed a lot more engineering knowledge than I currently did). Given our corporate domain, security policies required us to host the content on an internal tier 1 server, which had to pass security requirements and other standards. It became clear that this would involve a lot more engineering and server knowledge and time than I had, as well as maintenance time if I managed the server post-release. So we had to wait.

We wanted to get this right because we probably wouldn’t get bandwidth from the engineering team again for a few years. In the end, waiting turned out to be the right approach.

### Understanding each other

When we did finally begin the project and start working with the engineering team, another challenge was in understanding each other. The engineering team (the ones implementing the server build pipeline and workflow) didn’t understand our Jekyll authoring process and needs.

Conversely, we didn’t understand the engineer’s world well either. To me, it seemed all they needed to do was upload HTML files to a web server, which seemed a simple task. I felt they were overcomplicating the process with unnecessary workflows and layouts. And what was the deal with storing content in S3 and doing dynamic lookups based on matching permalinks? But they already had a process for publishing content to the existing site, so they were more or less following the same build flow.

Despite the common goal, we lived in seemingly different worlds, and we had to continually communicate about what each other needed. It didn’t help that we were located in different states and had to interact virtually, often through chat and email.

### Figuring out repo size

Probably the primary challenge was to figure out the correct size for the documentation repos. Across our teams, we had 30 different products, each with their doc navigation and content. Was it better to store each product in its own repo, or to store all products in one giant repo? I flipped my thinking on this several times.

Storing content in multiple repos led to quick build times, reduced visual clutter, resulted in fewer merge conflicts, didn’t introduce warnings about repo sizes, and had other benefits with autonomy.

On the other hand, storing all content in one repo simplified content re-use, made link management and validation easier, reduced maintenance efforts, and more. Most of all, it made it easier to update the theme in a single place rather than duplicating theme file updates across multiple repos.

Originally, our team started out storing content in separate repos. When I had updates to the Jekyll theme, I thought I could simply explain what files needed to be modified, and each tech writer would make the update to their theme’s files. This turned out not to work — tech writers didn’t like making updates to theme files. The Jekyll projects became out of date, and then when someone experienced an issue, I had no idea what version of the theme they were on.

I then championed consolidating all content in the same repo. We migrated all of these separate, autonomous repos into one master repo. This worked well for making theme updates. But soon the long build times (1-2 minutes for each build) became painful. We also ran into size warnings in our repo (images and other binary files such as Word docs were included in the repos). Sometimes merge conflicts happened.

The long build times were so annoying, we decided to switch back to individual repos. There’s nothing worse than waiting 2 minutes for your project to build, and I didn’t want the other tech writers to hate Jekyll like they did Hippo. The lightning-fast auto-regenerating build time with Jekyll is part of its magic.

## Creative solutions for theme distribution across repos

I came up with several creative ways to push the theme files out to multiple small repos in a semi-automated way. My first solution was to distribute the theme through [RubyGems](https://rubygems.org/), which is Jekyll’s official [solution for theming](https://jekyllrb.com/docs/themes/). I created a theme gem, open-sourced it and the theme (see [Jekyll Doc Project](https://github.com/amzn/jekyll-doc-project)), and practiced the workflow to push out updates to the theme gem and pull them into each repo.