Documenting Go Github Repo
The Go language makes the documentation very accessible. The documentation serves two types of
clients - developers who work on the documented code, which consume it from the code itself, and
code users which consume the documentation from a web UI or from the go doc
command line. In Go,
the documentation is a first-class citizen of the code, and writing it properly can make code
development easier and results in a magnificent pkg.go.dev (the new
godoc.org) site for your package. Github, the code hosting service for many Go
packages, does not support Go documentation, but does support markdown readme file in the package
root directory, by rendering in the home page of the repository. This page is important since it is
the first thing that developers see when they find your project, and it is usually being used to get
information about the project. Both the Go doc and the readme file are important - the upside is
that it is possible to design them to share common content - the flipside is that constantly
maintaining both of them can be a burden… Or is it?
I would love to know what you think. Please use the comments platform on the bottom of the post for discussion.
Github Readme
From Github:
You can add a README file to your repository to tell other people why your project is useful, what they can do with your project, and how they can use it.
Once a readme file is added to the repository, Github will show it in the front page, and most Github users use it in order to introduce themselves with the unfamiliar repository. Other code hosting services, such as Bitbucket and Gitlab use the same approach.
Markdown
Even though Github supports other readme formats, markdown seems to be the most common one used to document the repository. According to its creators, Markdown allows you to write using an easy-to-read, easy-to-write plain text format, then convert it to structurally valid XHTML (or HTML). It supports headings, paragraphs, text formatting, inlining code and code blocks, bulleted and numbered lists, adding links, images, quoting, inlining some HTML tags and more. Github has its own flavor with some “extensions” to the markdown syntax such as tables and checked-list (look for “(extensions)” in the linked spec).
Godoc
We all love documenting our code. It is important for developers who are working with the source
code (or to ourselves in two weeks from the time we wrote it), or to developers who want to use the
code in their project through the go doc
command line or the pkg.go.dev
(the new godoc.org) web UI.
The go doc syntax enables a small number of formatting features: heading, paragraphs, code blocks and links. Amit Lavon made a wonderful page that explains how to use them.
goreadme
Usually, developers maintain both the Go doc and the readme file for the enumerated reasons above. Sometimes developers recognize the duplicated work and set a short readme that just refers to the Go doc page.
As an open source developer, I want attractive readme files, as well as good code documentation and
a helpful go doc sites. In the past, I found myself spending too much time on synchronizing the
readme file with the code. Now I can save time thanks to
goreadme
- a tool that converts the Go documentation to
markdown readme.
goreadme
generates a markdown readme file from a package Go documentation. It is available as a
command line tool, as Github action, or as a library.
Extending godoc syntax
When working on this project, one of the first problems I noticed was the limited syntax of Go doc. It lacks support for images, bulleted or numbered lists, or declaring a language for a code block. When writing the Go doc to also be used as a markdown file, there are two possible scenarios: Using the full markdown syntax in the Go doc, which then results in an attractive Github page but weird looking Go doc. Or limit the markdown features to the one supported by the Go doc syntax, which results in an uninviting Github page but readable Go doc.
Choosing which path to follow is actually up to the developer who writes the documentation. However,
the goreadme
converter extends the Go doc syntax in a way that it enables some more markdown
features without harming the Go doc readability, such as link titles, images and diff blocks.
Github Actions Integration
One last question is - how do we keep the documentation and the readme file synchronized. One option
is to constantly run the goreadme
command line tool and commit the modifications with the code.
The problem is that it is still a burden to remember to do this task.
Goreadme is available also with Github actions integration, in two flows:
-
Pull request flow: When a new PR is created, the pull request flow will check if this change results in any changes to the readme file, and if so - it will comment the PR with the expected readme file diff.
-
Push flow: When a new change is pushed which results in a readme change, the Github action will push a new commit with the updated readme file.
Opting into the integration is as easy as adding a single file to a repository. The parameters for
the Github actions are available here.
The integration does not require any credentials - providing the Github token parameter is only
needed to enable the diff comments option. Just put the following content in
.github/workflows/goreadme.yml
:
on:
push:
branches: [master]
pull_request:
branches: [master]
jobs:
goreadme:
runs-on: ubuntu-latest
steps:
- name: Check out repository
uses: actions/checkout@v2
- name: Update readme according to Go doc
uses: posener/goreadme@v1
with:
badge-travisci: 'true'
badge-codecov: 'true'
badge-godoc: 'true'
badge-goreadme: 'true'
# Optional: enable goreadme to comment on PRs.
github-token: '${{ secrets.GITHUB_TOKEN }}'
Wrap up
Adopting the goreadme
workflow may require some work. Usually the Go doc is not written in a way
that suits Github readme files. But this work pays off - first, by doing so you will improve
your Go doc page, which is also very important. Second, after doing it once, goreadme is doing all
the hard work for you, and all you have to do is to update your code documentation - something that
we all to do!