Files
gbr-games/.gitea/workflows/validate.yml
T
gregandClaude Opus 5.5 c75190d8c4
Validate game templates / validate (push) Successful in 19s
Validate game templates / boot-test (push) Skipped
Validate game templates / publish (push) Skipped
feat(builder): research, build and a worker for the AI builder
- research: searches SearXNG, reads the best pages through the reader, has the
  model list the server's variants, then checks every Docker image and Steam
  app it named for real before an admin sees it.
- build: first boot of the variant's images (skipping ones that need root),
  a draft by the model, then the draft deployed with the node-agent's
  BootTest like CI does; crashes, error lines and saves outside /server go
  back to the model, three boots at most.
- worker: polls the panel's builder queue (outbound only), runs research or
  build in a fresh clone, streams the output as the job log, and opens the
  result as a pull request from the bot account.
- Dockerfile.builder, a workflow publishing gbr-builder:latest, and
  BUILDER.md. Everything about where it runs comes from environment
  variables; deployment files live outside this public repo.

draft now keeps its conversation in a drafter, so build can send boot
failures back to the same model session. The boot-test runner comment no
longer names its VM.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-25 12:51:29 -04:00

123 lines
4.6 KiB
YAML

name: Validate game templates
# Push-only on purpose: this repo is public, and a pull_request trigger would run a fork's
# version of this workflow on our self-hosted runners. PRs from branches in this repo are
# still checked through their push.
on:
push:
workflow_dispatch:
inputs:
games:
description: "Games to boot-test: comma-separated ids, or 'all'"
required: true
default: all
env:
PANEL_WEBHOOK_URL: https://api.gbrhosting.com/api/v1/webhooks/gitea
jobs:
validate:
runs-on: ubuntu-latest
outputs:
games: ${{ steps.changed.outputs.games }}
steps:
- name: Checkout Code
uses: actions/checkout@v4
with:
fetch-depth: 0
- name: Set up Go
uses: actions/setup-go@v5
with:
go-version-file: go.mod
# Three small modules aren't worth caching, and the runners' cache server is unreachable
# from job containers: each restore/save attempt timed out after ~4.7 minutes.
cache: false
- name: Validate
run: |
go test ./...
go run ./cmd/gbrgames validate
# main: games changed since the previous main commit. Branches: games changed against main,
# so results show up before merging. Manual runs pick their own.
- name: Find changed games
id: changed
run: |
if [ "${{ github.event_name }}" = "workflow_dispatch" ]; then
games=$(scripts/changed-games.sh "${{ inputs.games }}")
elif [ "${{ github.ref }}" = "refs/heads/main" ]; then
before="${{ github.event.before }}"
if [ -z "$before" ] || ! git cat-file -e "$before" 2>/dev/null; then
games=$(scripts/changed-games.sh all)
else
games=$(scripts/changed-games.sh "$before" "${{ github.sha }}")
fi
else
games=$(scripts/changed-games.sh "$(git merge-base origin/main HEAD)" HEAD)
fi
echo "Games to boot-test: ${games:-none}"
echo "games=$(echo $games)" >> "$GITHUB_OUTPUT"
boot-test:
needs: validate
if: needs.validate.outputs.games != ''
# A dedicated runner whose game containers can reach the internet but not private networks
runs-on: game-test
steps:
- name: Checkout Code
uses: actions/checkout@v4
- name: Set up Go
uses: actions/setup-go@v5
with:
go-version-file: go.mod
# Three small modules aren't worth caching, and the runners' cache server is unreachable
# from job containers: each restore/save attempt timed out after ~4.7 minutes.
cache: false
# Secrets named in a game's test.yaml must be listed here to reach the boot test
- name: Boot test changed games
env:
DRAGONWILDS_OWNER_ID: ${{ secrets.DRAGONWILDS_OWNER_ID }}
run: scripts/boot-test.sh ${{ needs.validate.outputs.games }}
# main is the source of truth: send every template to the panel, which saves the changed ones
# (new games arrive disabled). Runs only if the changed games booted, or none changed.
publish:
needs: [validate, boot-test]
if: >-
always() && github.ref == 'refs/heads/main' && github.event_name == 'push'
&& needs.validate.result == 'success'
&& (needs.boot-test.result == 'success' || needs.boot-test.result == 'skipped')
runs-on: ubuntu-latest
steps:
- name: Checkout Code
uses: actions/checkout@v4
- name: Set up Go
uses: actions/setup-go@v5
with:
go-version-file: go.mod
# Three small modules aren't worth caching, and the runners' cache server is unreachable
# from job containers: each restore/save attempt timed out after ~4.7 minutes.
cache: false
# Unlike the node-agent notify, a failure here fails the run, because the panel would
# otherwise keep serving the previous templates silently.
- name: Publish to Control Panel
env:
PANEL_WEBHOOK_SECRET: ${{ secrets.PANEL_WEBHOOK_SECRET }}
run: |
if [ -z "$PANEL_WEBHOOK_SECRET" ]; then
echo "::error::PANEL_WEBHOOK_SECRET is not set; templates were not published"
exit 1
fi
go run ./cmd/gbrgames export -repo "${{ github.repository }}" -commit "${{ github.sha }}" -out payload.json
curl -sS --fail-with-body --max-time 30 --retry 3 --retry-delay 10 \
-X POST "${{ env.PANEL_WEBHOOK_URL }}" \
-H "Content-Type: application/json" \
-H "X-Gitea-Token: $PANEL_WEBHOOK_SECRET" \
-H "X-GBR-Event: games_published" \
--data-binary @payload.json