嗨!我的名字是Nathan,我是Linode的技术写作团队的成员。我们的主要工作之一是贡献和维护https://www.linode.com/docs 的指南和教程库,其中发布了1400多篇文章。为了维护内容的质量,并鼓励在写作过程中的合作,我们在编写工作流程中采用了docs as code的方法。
文档即代码是一种方法论,你用于编写文档的工具与用于编写软件的工具相同。这包括
- 使用版本控制软件
- 编写纯文本文档文件
- 运行自动化测试
- 实行持续集成和持续交付
Linode的技术写作团队也通过负责托管我们的文档网站的云基础设施来扩展这一方法。
为什么要把文件当作代码?
遵循这些做法会带来一系列的好处。
- 与这些技术合作有助于在技术写作团队和 Linode 的开发和工程团队之间形成更紧密的联系。
- Linode的其他团队可以为我们的流程的各个方面作出贡献。例如:前端团队可以使用他们已经使用的工具帮助更新文档网站的主题/演示,而工程团队的成员可能会为文档库编写新的自动化测试。
- 我们的团队经常撰写关于我们流程中使用的技术的指南和教程。自己实施这些,使我们对它们有更好的理解,从而提高我们解释它们的能力。
- 我们还需要准确地记录Linode的产品,这可能涉及审查Linode的代码库。熟练掌握这些项目的语言和工具可以帮助我们更好地理解它们。
我们的实施
由于这种方法的实施在不同的组织之间可能有所不同,我想提供一个我们的过程的详细概要。
- 编写。我们的技术撰稿人用Markdown编写新指南。Markdown被用来在纯文本文件中表示丰富的文本,它可以被一系列工具编译成HTML。Markdown在软件开发中几乎被普遍采用;例如,GitHub的README文件就是用Markdown编写的。用Markdown写作也意味着你可以使用任何你喜欢的纯文本编辑器,从现代桌面编辑器如Visual Studio Code,到Emacs和Vim。我们知道,人们对自己喜欢的文本编辑器有强烈的意见,这种灵活性有助于更多的人对我们的库做出贡献。
- 本地网站预览。 我们库中的Markdown文件被编译成最终的HTML表现形式,并以一个 静态网站生成器.静态网站是预先建立的页面的集合,当它们被请求时不依赖于数据库来呈现(像WordPress这样的CMS那样)。正因为如此,静态网站的加载速度非常快。静态网站生成器通过将你的内容文件(如Markdown)与你指定的主题相结合来渲染一个静态网站。
Linode的文档网站使用 雨果,这是一个 最受欢迎的静态网站生成器: - 协作。文档库存储在GitHub上的一个公共Git仓库中,每个作者都维护这个仓库的分叉。当作者完成了指南的起草工作,他们会提交他们的修改,将修改推送到他们的分叉库,然后针对主库打开一个拉动请求。
我们的写作过程中有两个独立的团队成员对任何新指南或指南更新进行技术编辑和复制编辑。这些团队成员会下载拉动请求的分支,做出并提交他们的修改,然后把它们推送到GitHub上的分支。Git是另一个几乎通用的开发工具,使用它可以让我们利用一些标准的最佳协作实践,比如gitflow工作流。
此外,GitHub的普及意味着它有大量有用的集成。特别是,我们使用Netlify来为每个拉动请求生成自动的、可公开访问的预览。我们经常需要征求不同部门的Linodian的反馈,他们可以查看这些可共享的Netlify链接,而不必克隆我们的文档库并在他们的笔记本电脑上安装Hugo。
最后,托管在一个公共资源库中,使我们的图书馆向外部贡献者开放,我们对此表示欢迎。 - 测试。 每当提交或更新一个拉动请求,就会对PR的内容进行一系列的测试。这些测试是通过 Travis CI,它是一个持续集成服务,也提供GitHub集成。如果这些测试中有任何一项失败,那么该拉动请求就会暂时被阻止合并。
- 指南内容的拼写和风格(例如,技术术语的正确大写)都要进行检查。我们使用Vale来执行这些任务,它是一个开源的linter,专门用于散文。当我们第一次整合Vale时,它在我们的图书馆中报告了超过50万个拼写错误。虽然有点尴尬,但知道了这个数字,然后能够根据它采取行动,使我们对我们的内容和我们的新出版系统的信心大增。
- 我们通过使用Scrapy检查指南之间潜在的断裂链接,Scrapy是一个开源的Python 框架,可以从网站上刮取内容。这个测试是与Linode工程团队的一名成员合作编写的。在第一次实施Scrapy时,我们同样发现了一些可以纠正的断裂链接。
- 另一个Python 脚本检查指南的正面元数据是否有效,是否有语法错误。在建立网站时,一个破碎的前事项部分可能会导致问题,所以有这个验证意味着我们可以确保网站在更新生产网络服务器时能够呈现。
- 指南内容的拼写和风格(例如,技术术语的正确大写)都要进行检查。我们使用Vale来执行这些任务,它是一个开源的linter,专门用于散文。当我们第一次整合Vale时,它在我们的图书馆中报告了超过50万个拼写错误。虽然有点尴尬,但知道了这个数字,然后能够根据它采取行动,使我们对我们的内容和我们的新出版系统的信心大增。
- 出版和托管。 更新文档网站是由一组脚本自动处理的,这些脚本是由GitHub上的某些事件触发的。
- 每当内容被合并到主文档库的主分支时,一个webhook通知就会被发送到一个暂存的Web服务器,也就是Linode。这台中转网站服务器会从 GitHub 调取主分支,然后用 Hugo 构建网站,并将网站服务器的文档根作为渲染网站的目标。我们查看这个暂存网站,并确认内容与预期一致。
暂存服务器最初并不是我们工作流程的一部分;它是在一次生产网站更新过程中临时破坏了我们的CSS/styling之后建立的。简而言之,Netlify已经正确地渲染了新网站的预览,但它没有发现一个风格问题。这是因为它使用了我们的 "开发 "构建管道,而不是我们的 "生产 "构建管道(它将我们的CSS和其他资产最小化)。新的暂存服务器的配置与我们的生产服务器相同,所以它也使用生产构建管道,它将捕捉到这样的错误。 - 为了更新生产网站,我们在GitHub上创建一个新的发布标签。这将触发另一个webhook通知,并发送给生产网站服务器。这个服务器运行一个类似于暂存服务器的脚本,但它从新的发布标签中提取内容。
- 让我们的发布功能自动发生,最大限度地减少了如果我们手动执行这一过程可能出现的任何人为错误。中转服务器和生产服务器都是通过公式进行配置管理的。 SaltSalt 也被Linode的其他基础设施项目所使用,因此我们的文档网络服务器可以和其他部分一起被管理。
- 每当内容被合并到主文档库的主分支时,一个webhook通知就会被发送到一个暂存的Web服务器,也就是Linode。这台中转网站服务器会从 GitHub 调取主分支,然后用 Hugo 构建网站,并将网站服务器的文档根作为渲染网站的目标。我们查看这个暂存网站,并确认内容与预期一致。
采用这种方法帮助我们大大简化了我们的工作流程,但我们一直在努力迭代和改进它。如果你有任何关于我们可以进行更新的建议,请告诉我们!我在Write the Docs Slack上的名字是nmelehan,其他几个团队成员也是如此。如果你想阅读更多关于文档即代码的内容,我推荐Eric Holscher在Write the Docs网站的指南。
评论 (3)
What engine do you use for allowing users to search through your documents from the https://www.linode.com/docs/ page?
Hi Ken –
We use Algolia. We update our index in Algolia from the scripts that we run in step 5 (publishing and hosting). To update that index, we first have Hugo output a list of our guides to a JSON file (see Hugo – Custom Output Formats), and then we ship that data to Algolia’s API.
Excellent write-up, Nathan. We’re using a similar Docs as Code approach for our documentation for Tugboat at https://docs.tugboat.qa. Our GitHub repository is at https://github.com/TugboatQA/docs. Instead of Netlify, we’re using Tugboat itself to build the previews of the site. That way, anyone can create a pull request with a fix and preview that change right away.
We’re huge fans of Linode (our hosting provider since day 1!), so it’s nice to see you all validating our approach as well!
Thanks for sharing all the detail into your approach. Very helpful.