Skip to content

Commit

Permalink
Add ci docs gen and github pages pub (#73)
Browse files Browse the repository at this point in the history
Add documentation geneartion and publishing CI.

Following, all paths are assumed in <repo>/docs/
Basics logic is as in build-docs.sh for non-CI case:

1. compose the docs/ dir for mkdocs (mkdocs-material, specifically)
2. mkdocs build generate non-versioned site/
3. copy site/ to generated/<version_name>
4. patch generated/ by creating generated/index.html for non version URL redirection and generate versions.json for the version drop down list

In CI, 1,2 are in docs build stage and the stage driven by as matrix what version we want to publish to the site
3,4 is publish stage. Two stages are linked together by artifacts upload and download.
  • Loading branch information
cloudhan authored Mar 23, 2023
1 parent e7bf878 commit a62c35f
Show file tree
Hide file tree
Showing 9 changed files with 247 additions and 36 deletions.
32 changes: 0 additions & 32 deletions .github/workflows/docs-tests.yaml

This file was deleted.

79 changes: 79 additions & 0 deletions .github/workflows/github-pages.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,79 @@
name: Generate docs

on:
pull_request:
branches:
- main
push:
branches:
- main

jobs:
pages:
runs-on: ubuntu-latest
strategy:
matrix:
docs:
# { ref: <branch/tag name>, name: <docs drop down entry> }
- { ref: main, name: latest }
steps:
- uses: actions/checkout@v3
if: ${{ matrix.docs.ref == 'main' }}
- uses: actions/checkout@v3
with:
ref: ${{ matrix.docs.ref }}
if: ${{ matrix.docs.ref != 'main' }}

- uses: bazelbuild/setup-bazelisk@v2
- name: Mount bazel cache
uses: actions/cache@v3
with:
path: ~/.cache/bazel
key: bazel-gen-docs-${{ matrix.docs.ref }}

- uses: actions/setup-python@v4
with:
python-version: "3.10"
cache: pip

- name: Generate docs
run: bash ./build-docs.sh
env:
CI: 1
working-directory: ${{ github.workspace }}/docs

- run: bazelisk shutdown

- uses: actions/upload-artifact@v3
with:
name: "${{ matrix.docs.name }}"
path: ${{ github.workspace }}/docs/site/
if-no-files-found: error
if: ${{ github.event_name != 'pull_request' }}

publish:
needs: pages
if: ${{ github.event_name != 'pull_request' }}
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v3

- uses: actions/download-artifact@v3
with:
path: ${{ github.workspace }}/docs/generated
- name: Inspect docs site directory structure
run: find ${{ github.workspace }}/docs/generated -maxdepth 2

- uses: actions/setup-python@v4
with:
python-version: "3.10"
- run: |
pip install packaging==23.*
python versioning.py generated/
working-directory: ${{ github.workspace }}/docs
- uses: peaceiris/actions-gh-pages@v3
with:
github_token: ${{ secrets.GITHUB_TOKEN }}
publish_dir: ./docs/generated
force_orphan: true
3 changes: 3 additions & 0 deletions docs/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
docs/
generated/
site/
19 changes: 15 additions & 4 deletions docs/BUILD.bazel
Original file line number Diff line number Diff line change
@@ -1,29 +1,40 @@
load("@io_bazel_stardoc//stardoc:stardoc.bzl", "stardoc")

# NOTE: when the `out` is changed, the `nav` part of `mkdocs.yaml` must be also be changed correspondingly.
stardoc(
name = "user_docs",
out = "user_docs.md",
out = "user/user_docs.md",
input = "user_docs.bzl",
deps = ["@rules_cuda//:bzl_srcs"],
)

stardoc(
name = "toolchain_config_docs",
out = "toolchain_config_docs.md",
out = "user/toolchain_config_docs.md",
input = "toolchain_config_docs.bzl",
deps = ["@rules_cuda//:bzl_srcs"],
)

stardoc(
name = "providers_docs",
out = "providers_docs.md",
out = "developer/providers_docs.md",
input = "providers_docs.bzl",
deps = ["@rules_cuda//:bzl_srcs"],
)

stardoc(
name = "developer_docs",
out = "developer_docs.md",
out = "developer/developer_docs.md",
input = "developer_docs.bzl",
deps = ["@rules_cuda//:bzl_srcs"],
)

filegroup(
name = "all_docs",
srcs = [
":developer_docs",
":providers_docs",
":toolchain_config_docs",
":user_docs",
],
)
44 changes: 44 additions & 0 deletions docs/build-docs.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
#!/bin/bash

function prepare-env {
pip install -r requirements.txt
}

function compose-docs {
rm -rf docs site
mkdir -p docs
cp ../README.md docs/index.md
bazel build :all_docs
rsync -a --prune-empty-dirs --include '*/' mkdocs/stylesheets docs/
rsync -a --prune-empty-dirs --include '*/' --include '*.md' --exclude '*' bazel-bin/ docs/
}

function compose-versioned-site {
mkdir -p generated
rsync -a --prune-empty-dirs --include '*/' site/ generated/$1/
python versioning.py generated/ --force

printf "\nRun following command to update version list then serve locally:\n\n"
printf "\tpython -m http.server -d generate/\n\n"
}


CI=${CI:-0} # 1 for CI only logic

if [ $CI == "1" ]; then
set -ex
prepare-env
compose-docs
mkdocs build
else
if [[ $# -ne 1 ]]; then
printf "Usage: $0 <version>\n"
exit -1
fi
version=$1

# env should be prepared manually
compose-docs
mkdocs build
compose-versioned-site $version
fi
30 changes: 30 additions & 0 deletions docs/mkdocs.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
site_name: "rules_cuda: Starlark implementation of bazel rules for CUDA"
repo_url: https://github.com/bazel-contrib/rules_cuda
docs_dir: docs

theme:
name: material
palette:
- media: "(prefers-color-scheme: light)"
scheme: default
primary: green
locale: en
features:
- navigation.tabs
extra_css:
- stylesheets/extra.css

extra:
version:
# we are not actually using mike
# just for `versions.json` to be functional
provider: mike

nav:
- Home: index.md
- User:
- Using the rules: user/user_docs.md
- Configure the toolchain: user/toolchain_config_docs.md
- Developer:
- Providers: developer/providers_docs.md
- Rule Authoring: developer/developer_docs.md
3 changes: 3 additions & 0 deletions docs/mkdocs/stylesheets/extra.css
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
.md-header {
background: #44a147
}
1 change: 1 addition & 0 deletions docs/requirements.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
mkdocs-material==9.1.3
72 changes: 72 additions & 0 deletions docs/versioning.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,72 @@
import argparse
import json
import os
from packaging.version import parse as parse_version

TEMPLATE = """<!-- Generated, don't modify! -->
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Redirecting</title>
<noscript>
<meta http-equiv="refresh" content="1; url={version}/" />
</noscript>
<script>
window.location.replace("{version}/" + window.location.hash);
</script>
</head>
<body>
Redirecting to <a href="{version}/">{version}/</a>...
</body>
</html>
"""


def collect_versions(work_dir):
versioned_dirs = [item.name for item in os.scandir(work_dir) if item.is_dir()]
names = []
versions = []
for v in versioned_dirs:
try:
parse_version(v)
versions.append(v)
except:
names.append(v)

versions.sort(key=lambda v: parse_version(v), reverse=True)
names.sort()
return versions + names


def generate_redirect_page(work_dir, version, *, force=False):
output = os.path.join(work_dir, "index.html")
assert force or not os.path.exists(output)
with open(output, "w") as f:
f.write(TEMPLATE.format(version=version))


def generate_version_json(work_dir, versions, *, force=False):
output = os.path.join(work_dir, "versions.json")
assert force or not os.path.exists(output)
with open(output, "w") as f:
json.dump([{"version": v, "title": v, "aliases": []} for v in versions], f)


def process(work_dir, default_version=None, *, force=False):
versions = collect_versions(work_dir)
if default_version is None:
default_version = versions[0]
generate_redirect_page(work_dir, default_version, force=force)
generate_version_json(work_dir, versions, force=force)


if __name__ == "__main__":
parser = argparse.ArgumentParser()
parser.add_argument("work_dir")
parser.add_argument("--default_version", "-d", default=None)
parser.add_argument("--force", "-f", action="store_true")
args = parser.parse_args()

process(args.work_dir, args.default_version, force=args.force)

0 comments on commit a62c35f

Please sign in to comment.