GitHub Pages Staging Deployment Workflow

Milestone

This workflow documents the successful setup of a full-site GitHub Pages staging deployment for the DataInsideData / Builder Showcase layer.

The goal was to create a public staging environment where the full Minimal Mistakes site can be tested before production deployment.

Final staging architecture:

private source repo
        ↓
GitHub Actions staging workflow
        ↓
full Jekyll staging build
        ↓
public staging repo gh-pages branch
        ↓
GitHub Pages staging site

Expected staging URL pattern:

https://dataeden.github.io/did-builder-showcase-staging/

Builder Showcase form URL pattern:

https://dataeden.github.io/did-builder-showcase-staging/projects/submit-a-builder-project/

1. Create the public staging repository

Create a new public repository:

dataeden/did-builder-showcase-staging

Purpose:

Public GitHub Pages staging layer for full-site preview and Builder Showcase testing.

This repo receives the built static site from the private source repo.


2. Configure GitHub Pages in the staging repo

In the public staging repo:

Settings
→ Pages

Initial state may be:

Deploy from branch
Branch: main
Folder: / root

This is okay before the first deploy.

After the first successful workflow run creates the gh-pages branch, update Pages to:

Deploy from branch
Branch: gh-pages
Folder: / root

The gh-pages branch may not be selectable until the workflow creates it.


3. Create a staging deploy token

Create a fine-grained personal access token for staging deployment.

Suggested token name:

did-builder-showcase-staging-deploy

Recommended scope:

Repository access:
Only selected repositories

Selected repository:
dataeden/did-builder-showcase-staging

Repository permissions:
Contents: Read and write
Metadata: Read-only

Purpose:

Allow GitHub Actions in the private source repo to push the built staging site into the public staging repo.

4. Add the staging token to private repo secrets

In the private source repo:

Settings
→ Secrets and variables
→ Actions
→ New repository secret

Add:

DID_STAGING_PAT

Secret value:

the fine-grained token value

Do not commit this token to the repo.


5. Add staging config

Create or update:

_config_staging.yml

For a GitHub Project Pages staging site:

url: "https://dataeden.github.io"
baseurl: "/did-builder-showcase-staging"

title: "DataInsideData Staging"
description: "Staging preview for DataInsideData and Builder Showcase testing."

environment: staging

Why this matters:

GitHub Project Pages serves the site from a subpath:
https://dataeden.github.io/did-builder-showcase-staging/

So links and assets need the correct baseurl.


6. Use relative URLs for staging-safe assets

Root-relative links like this can break on project Pages:

![raw readme image](/docs/imgs/raw_readme_url_hint.png)

Use Jekyll’s relative_url filter instead:

![raw readme image](/docs/imgs/raw_readme_url_hint.png)

This works across both:

https://datainsidedata.com
https://dataeden.github.io/did-builder-showcase-staging/

7. Add generated build folders to .gitignore

Add or confirm:

# Jekyll build output
_site/
_site_staging/
_site_staging_full/
.jekyll-cache/
.sass-cache/

# Local environment secrets
.env
.env.*
!.env.example

These folders/files should not be committed.

_site_staging_full/ is generated during local test builds or GitHub Actions builds.


8. Add the staging deploy workflow

Create:

.github/workflows/deploy-staging.yml

Workflow:

name: Deploy DID Full Staging Site

on:
  workflow_dispatch:
  push:
    branches:
      - builder-showcase-staging

jobs:
  build-and-deploy-staging:
    runs-on: ubuntu-latest

    steps:
      - name: Checkout private source repo
        uses: actions/checkout@v4

      - name: Set up Ruby
        uses: ruby/setup-ruby@v1
        with:
          ruby-version: "3.2"
          bundler-cache: true

      - name: Build full Jekyll staging site
        run: |
          bundle exec jekyll build \
            --config _config.yml,_config_staging.yml \
            --destination _site_staging_full

      - name: Add nojekyll
        run: |
          touch _site_staging_full/.nojekyll

      - name: Deploy full staging site
        uses: peaceiris/actions-gh-pages@v4
        with:
          personal_token: $
          external_repository: dataeden/did-builder-showcase-staging
          publish_branch: gh-pages
          publish_dir: ./_site_staging_full

9. Make the workflow visible to GitHub Actions

Important lesson:

For manual workflow_dispatch runs, GitHub must be able to see the workflow file on the default branch.

If deploy-staging.yml only exists on a feature branch, this command may fail:

gh workflow run deploy-staging.yml --ref feat/community-projects

Possible error:

HTTP 404: workflow deploy-staging.yml not found on the default branch

Fix:

Commit deploy-staging.yml to the default branch first.

Only the workflow/config support files need to be added to the default branch:

.github/workflows/deploy-staging.yml
_config_staging.yml
.gitignore

The actual site changes can remain on the feature branch.


10. Run the workflow from the feature branch

Once the workflow exists on the default branch, run it against the branch you want to deploy:

gh workflow run deploy-staging.yml --ref feat/community-projects

GitHub CLI response:

✓ Created workflow_dispatch event for deploy-staging.yml at feat/community-projects

To see runs for this workflow, try:
gh run list --workflow="deploy-staging.yml"

Rule:

deploy-staging.yml must exist on the default branch
--ref points to the branch that should be built and deployed

11. Check workflow run status

List recent runs:

gh run list --workflow="deploy-staging.yml" --limit 5

View a specific run:

gh run view <RUN_ID>

View failed logs:

gh run view <RUN_ID> --log-failed

Watch the current/latest run:

gh run watch

View job details:

gh run view --job=<JOB_ID>

12. First failure: Bundler platform mismatch

The first workflow attempt failed during Ruby setup.

Error summary:

The process '/opt/hostedtoolcache/Ruby/3.2.11/x64/bin/bundle' failed with exit code 16

Detailed cause:

Your bundle only supports platforms ["x64-mingw-ucrt"] but your local platform is x86_64-linux.
Add the current platform to the lockfile with:
bundle lock --add-platform x86_64-linux

Why it happened:

Gemfile.lock was generated on Windows.
GitHub Actions runs on Linux.
The lockfile needed the Linux platform added.

13. Fix Bundler platform support

On the feature branch:

git checkout feat/community-projects

Add Linux platform:

bundle lock --add-platform x86_64-linux

Optional but helpful:

bundle lock --add-platform ruby

A deprecation warning may appear about Windows platform names. That warning does not block the fix.

Confirm the lockfile changed:

git diff Gemfile.lock

Expected platform section includes:

PLATFORMS
  ruby
  x64-mingw-ucrt
  x86_64-linux

Commit and push:

git add Gemfile.lock
git commit -m "Add Linux platform to Gemfile lock"
git push origin feat/community-projects

14. Rerun the staging deploy

Run the workflow again:

gh workflow run deploy-staging.yml --ref feat/community-projects

Check status:

gh run list --workflow="deploy-staging.yml" --limit 5

View the run:

gh run view <RUN_ID>

Successful result:

✓ feat/community-projects Deploy DID Full Staging Site
Triggered via workflow_dispatch

JOBS
✓ build-and-deploy-staging

Example successful milestone:

✓ feat/community-projects Deploy DID Full Staging Site · 27240924480
Triggered via workflow_dispatch

JOBS
✓ build-and-deploy-staging in 45s

15. After successful deploy

Go to the public staging repo:

dataeden/did-builder-showcase-staging

Confirm:

gh-pages branch exists
index.html exists
assets/ exists
.nojekyll exists

Then in the staging repo:

Settings
→ Pages
→ Deploy from branch
→ gh-pages
→ / root
→ Save

After GitHub Pages publishes, test:

https://dataeden.github.io/did-builder-showcase-staging/

And:

https://dataeden.github.io/did-builder-showcase-staging/projects/submit-a-builder-project/

16. Edge Function CORS note

Because the staging site is served from GitHub Pages, the browser origin is:

https://dataeden.github.io

If the Builder Showcase form posts to a Supabase Edge Function, the Edge Function CORS allowlist should include:

"https://dataeden.github.io"

The full page path is not the origin.

Correct origin:

https://dataeden.github.io

Not:

https://dataeden.github.io/did-builder-showcase-staging/

17. Final working flow

feat/community-projects branch
        ↓
gh workflow run deploy-staging.yml --ref feat/community-projects
        ↓
GitHub Actions checks out feature branch
        ↓
Ruby + Bundler setup
        ↓
Jekyll builds full site with _config_staging.yml
        ↓
_site_staging_full generated
        ↓
.nojekyll added
        ↓
peaceiris/actions-gh-pages pushes output to staging repo gh-pages
        ↓
GitHub Pages serves staging site

18. Useful commands reference

Check current branch:

git branch --show-current

Push feature branch:

git push origin feat/community-projects

Run staging deploy:

gh workflow run deploy-staging.yml --ref feat/community-projects

List workflow runs:

gh run list --workflow="deploy-staging.yml" --limit 5

View run:

gh run view <RUN_ID>

View failed logs:

gh run view <RUN_ID> --log-failed

Watch run:

gh run watch

Add Linux platform to lockfile:

bundle lock --add-platform x86_64-linux

Add generic Ruby platform:

bundle lock --add-platform ruby

Commit lockfile fix:

git add Gemfile.lock
git commit -m "Add Linux platform to Gemfile lock"
git push origin feat/community-projects

19. Milestone summary

This milestone created a working full-site staging deployment path for DataInsideData and Builder Showcase.

It enables:

full-site preview testing
Builder Showcase form testing
navigation/style testing
GitHub Pages staging before production
safe participant submission testing
future feature QA before live deployment

This supports the broader Builder Showcase workflow by creating a safe public testing layer before promoting changes to the production DataInsideData site.