Skip to main content

CI/CD pipeline

Every push to the content-portfolio repository triggers GitHub Actions workflows. This page annotates the pipelines and explains the reasoning behind each step.

Repository strategy

The portfolio uses a two-repo model. content-portfolio is a private repository that holds all source files, authoring workflows, and CI/CD pipelines. sabitarao.github.io is a public repository that holds only the compiled output. Source files never appear in the public repo. Visitors see built HTML, not markdown.

This separation means the working process, draft content, and tooling configuration stay private while the published site stays clean.

The four workflows

Four workflow files live in .github/workflows/. Each handles a different concern.

WorkflowTriggerWhat it does
vale.ymlpush and pull_request to masterRuns Vale across docs/technical-documentation/ and posts findings to the GitHub Checks tab
vale-pr.yml (WIP)push to any branch (excluding vale/*), when docs/technical-documentation/** changesAuto-applies Vale fixes where the rules support it, generates a findings report, and opens a PR with both
deploy.ymlpush and pull_request to mainLint, build (WIP), and deploy the compiled site
ai-draft.ymlmanual (workflow_dispatch)Generates a documentation stub via Claude and opens a PR. See AI draft generation for the full walkthrough

The vale.yml and vale-pr.yml workflows are meant to complement each other. vale.yml is the lightweight check that runs alongside the build. vale-pr.yml is the higher-effort workflow that auto-fixes what it can and produces a structured report for what it can't.

Vale style check (vale.yml)

push or PR to master


┌─────────┐
│ vale │ ← style check across docs/technical-documentation/
└─────────┘
- name: Vale
uses: errata-ai/vale-action@reviewdog
with:
files: docs/technical-documentation/
reporter: github-check
fail_on_error: false
vale_flags: "--config=.vale.ini --glob=*.md"

vale.yml runs only on docs/technical-documentation/. Persona pages, journey maps, and AI experiments use first-person voice and passive constructions deliberately, and the per-directory overrides in .vale.ini already account for that. Scoping CI to the instructional docs keeps the PR check focused where style consistency matters most. See Vale style guide for the full rule configuration.

reporter: github-check works on both direct pushes and pull requests. On pull requests it surfaces findings inline. The check report is always available regardless of how the change was introduced.

fail_on_error: false means findings are visible without blocking the pipeline. Style suggestions should inform the author, not stop the branch from building.

--glob=*.md skips MDX files. Vale's MDX parser fails in CI without mdx2vast, and the technical-documentation suite is markdown-only, so the flag is safe.

Vale auto-fix and report (vale-pr.yml) (WIP)

push to any branch (touching docs/technical-documentation/**)


┌────────────┐
│ vale --fix │ ← apply rule-supported fixes
└─────┬──────┘


┌──────────────────┐
│ generate report │ ← markdown summary of remaining findings
└─────┬────────────┘


┌──────────────────┐
│ open or update │ ← branch: vale/fixes-{branch}
│ pull request │
└──────────────────┘

vale-pr.yml is the heavier-weight Vale workflow. It runs on every push that touches docs/technical-documentation/**, except pushes to the vale/* branches it creates (to prevent feedback loops).

The workflow:

  1. Installs the latest Vale release.
  2. Runs vale --fix to auto-apply fixes for rules that support them.
  3. Generates vale-report.md, a markdown summary of remaining findings broken out by file with line, severity, rule, and message.
  4. Opens or updates a PR on a branch named vale/fixes-{source-branch}. The PR commits both the auto-fixes and the report.

The PR description tells the reviewer that merging applies the fixes, and that the report is for reference if it shows only warnings and suggestions. This pattern keeps master clean while making findings visible without manually running Vale locally.

Build and deploy (deploy.yml)

push or PR to main


┌─────────┐
│ lint │ ← markdown links · markdownlint · Vale (PR review mode)
└────┬────┘
│ (continue-on-error during WIP phase)

┌─────────┐
│ build │ ← npm ci · docusaurus build · upload artifact (WIP)
└────┬────┘


┌─────────┐
│ deploy │ ← disabled until ready
└─────────┘

Lint job

Three checks run in sequence. All have continue-on-error: true during the WIP phase. Failures are visible in the Actions tab but don't block the build.

Markdown link checker flags every broken internal and external link across all markdown files. Broken links erode reader trust faster than almost any other issue. Catching them automatically means they never reach production.

Markdownlint enforces markdown formatting consistency: heading hierarchy, list formatting, trailing spaces, blank lines. It keeps source files readable for contributors and prevents formatting issues from compounding over time.

Vale (PR review mode) runs the same style check as vale.yml, but with reporter: github-pr-review. On pull requests this posts inline comments directly on changed lines, so style issues appear in the same place as code review comments. This Vale step in deploy.yml runs against files: docs/ rather than just technical-documentation, because the PR review reach is broader by design.

Build job

- name: Install dependencies
run: npm ci

- name: Build site
run: npm run build

- name: Upload build artifact
uses: actions/upload-artifact@v4
with:
name: docusaurus-build
path: build/
retention-days: 1

npm ci (not npm install) ensures a clean, reproducible install from package-lock.json. The build artifact is uploaded for the deploy job to consume. The site builds once regardless of how many deployment targets exist.

What this enables

A contributor pushing to the repo gets automated feedback without needing to read the style guide first:

  • vale.yml posts style suggestions on push, visible in the Checks tab.
  • vale-pr.yml opens a PR with auto-fixes plus a structured findings report. (WIP)
  • On pull requests, Vale comments appear inline on the changed lines via deploy.yml.
  • Broken links are flagged before they reach production.
  • Markdown formatting issues are caught automatically.
  • The build verifies the site compiles cleanly before any deployment.
  • AI-generated drafts go through PR review with a mandatory checklist (see AI draft generation).