diff --git a/docs/forgejo-production-decisions.md b/docs/forgejo-production-decisions.md index 7fa651e..3e55f0c 100644 --- a/docs/forgejo-production-decisions.md +++ b/docs/forgejo-production-decisions.md @@ -49,8 +49,11 @@ remains canonical for git remotes until migration drills pass. CI `IMAGE_REPOSITORY` variables. - State Hub / sweep checkouts on railiance01 (T05) should clone from `forgejo.coulomb.social` once cutover completes. -- Runners and image-build CI are proven; remaining blockers for production - cutover: SMTP, backup, cutover mode, and repo migration (`RAIL-HO-WP-0005-T11`). +- Runners and image-build CI are proven; first repo migration pilot + (`glas-harness`) documents git/SSH/CI routing in + `docs/forgejo-repo-migration-pilot-glas-harness.md`. +- Remaining blockers for production cutover: SMTP, backup, cutover mode, operator + SSH identity on Forgejo, and production repo migration (`RAIL-HO-WP-0005-T11`). ## Open decisions (need operator input) diff --git a/docs/forgejo-repo-migration-pilot-glas-harness.md b/docs/forgejo-repo-migration-pilot-glas-harness.md new file mode 100644 index 0000000..111c006 --- /dev/null +++ b/docs/forgejo-repo-migration-pilot-glas-harness.md @@ -0,0 +1,111 @@ +# Forgejo Repo Migration Pilot — glas-harness + +Date: 2026-07-03 +Workplan: `CUST-WP-0054-T04`, `RAIL-HO-WP-0005` +Pilot repo: `coulomb/glas-harness` (non-production tooling; safe routing drill) + +## Why this repo + +| Criterion | glas-harness | +| --- | --- | +| Production dependency | None — harness meta-framework, not deployed | +| Size / complexity | 3 commits, no container image, no submodules | +| Blast radius | Low — wrong remote or CI failure does not break triage, State Hub, or emission | +| State Hub registration | Not in active production sweep set | + +Use lessons here before migrating `state-hub` (high value, high risk). + +## Pilot outcome (2026-07-03) + +| Step | Result | Notes | +| --- | --- | --- | +| Create repo on Forgejo | **pass** | `POST /api/v1/orgs/coulomb/repos` | +| Mirror git history (HTTPS) | **pass** | `main` @ `e35e287` pushed with admin token | +| SSH `forgejo-remote` push | **pass** | After adding `id_gitea.pub` to `forgejo_admin`; NodePort `92.205.62.239:30022` | +| `origin` → Forgejo, `gitea` legacy remote | **pass** | `origin=forgejo-remote:…`, `gitea=gitea-remote:…` | +| Actions `ci-smoke` (host + container) | **pass** | `host-smoke` (`self-hosted`) + `container-smoke` (`ubuntu-latest`) both `success` | +| Gitea left intact | **pass** | No delete; Gitea still at `e35e287` until mirror sync policy defined | + +## Routing that works + +### Git remotes (workstation) + +Add to `~/.ssh/config` (see `FORGEJO-REMOTE` block): + +```ssh +Host forgejo-remote + HostName 92.205.62.239 + Port 30022 + User git + IdentityFile ~/.ssh/id_gitea + StrictHostKeyChecking accept-new +``` + +Per-repo layout after cutover: + +```bash +git remote rename origin gitea # if still on Gitea +git remote add origin forgejo-remote:coulomb/.git +git push -u origin main +``` + +Canonical URL: `https://forgejo.coulomb.social/coulomb/.git` + +### HTTPS fallback (automation / first push) + +Admin or user token with `write:repository`: + +```bash +git push "https://:@forgejo.coulomb.social/coulomb/.git" main +``` + +### CI runner labels (railiance01-build-01) + +| Label | Works for | Evidence | +| --- | --- | --- | +| `self-hosted` | Host runner smoke | glas-harness `host-smoke` | +| `ubuntu-latest` | Container step jobs | glas-harness `container-smoke` | +| `container-build` | Docker build/push jobs | forgejo-actions-probe `image-build` | + +### Registry / image CI (from prior probe) + +- Org secrets `REGISTRY_USER` / `REGISTRY_TOKEN` via `PUT /api/v1/orgs/coulomb/actions/secrets/{name}` with plaintext `data` (HTTPS API). +- Host runner has **no** `docker` CLI and **cannot** `apk add` (non-root). Use **static docker binary** in the job step. +- `actions/checkout@v4` **fails** on host runner — use `git clone` in the job until resolved. + +## Routing that does not work yet + +| Gap | Impact | Mitigation for next repos | +| --- | --- | --- | +| `tegwick` Gitea user not on Forgejo | SSH as `git@92.205.130.254` (Gitea) ≠ `git@92.205.62.239` (Forgejo); keys are per-forge | Register operator keys on Forgejo users before cutover; or use `forgejo_admin` interim | +| No automated Gitea→Forgejo mirror | Gitea copy drifts after Forgejo becomes canonical | Staged cutover: freeze Gitea pushes, one-way mirror, or retire Gitea remote after verification | +| `actions/checkout@v4` on host runner | Breaks multi-step workflows that depend on checkout | `git clone` in `run:` step (see image-build probe) | +| Issues/wiki/releases/LFS | Not exercised in pilot | Classify per repo in migration inventory before production repos | +| State Hub `remote_url` field | Still points at `gitea-remote:…` for most repos | Update registration when repo is promoted (separate step; not done for glas-harness) | + +## Repeatable procedure (non-production repo) + +1. Confirm repo is **not** in a production drain wave or has explicit operator approval. +2. Create empty repo on Forgejo (`auto_init: false` if mirroring existing history). +3. Push all branches/tags from workstation clone (HTTPS or SSH). +4. Add `forgejo-remote` remote; rename Gitea remote to `gitea`; set `origin` to Forgejo. +5. Add `.forgejo/workflows/` smoke (and image workflow if applicable). +6. Verify Actions green on Forgejo runner. +7. Leave Gitea repo read-only; do not delete (safety contract). +8. Record results in this doc or a per-repo row in the migration inventory. + +## Not ready for state-hub yet + +Before `state-hub`, the pilot still needs: + +- [ ] Operator/user SSH identity on Forgejo (not only `forgejo_admin`) +- [ ] Reusable workflow template with `hub-core` build context and `git clone` checkout pattern +- [ ] State Hub `remote_url` + sweep checkout path update playbook +- [ ] Gitea read-only mirror or push-disable policy for repos after cutover + +## References + +- `docs/forgejo-production-decisions.md` +- `railiance-forge/docs/forgejo-actions-runner-substrate.md` +- `railiance-apps/docs/forgejo-on-railiance01.md` +- Forgejo repo: https://forgejo.coulomb.social/coulomb/glas-harness \ No newline at end of file diff --git a/workplans/CUST-WP-0054-workstation-independence-and-fleet-realignment.md b/workplans/CUST-WP-0054-workstation-independence-and-fleet-realignment.md index c8a7ac8..106670f 100644 --- a/workplans/CUST-WP-0054-workstation-independence-and-fleet-realignment.md +++ b/workplans/CUST-WP-0054-workstation-independence-and-fleet-realignment.md @@ -181,9 +181,11 @@ DinD) replaces interim coulombcore host runner. Interim coulombcore host runner disabled. Org Actions secrets (`REGISTRY_USER`, `REGISTRY_TOKEN`) set. `coulomb/forgejo-actions-probe` `image-build` workflow builds and pushes to `forgejo.coulomb.social/coulomb/forgejo-actions-probe` (static docker-cli + -DinD; `actions/checkout@v4` not used — git clone in job). Remaining: migrate -production repos (state-hub, core-hub, issue-core, activity-core) and cut over -git remotes; release with workstation off. +DinD; `actions/checkout@v4` not used — git clone in job). **Pilot (2026-07-03):** +`coulomb/glas-harness` migrated to Forgejo (`origin=forgejo-remote`); CI smoke +host+container green — see `docs/forgejo-repo-migration-pilot-glas-harness.md`. +Remaining: promote more repos using pilot routing; then production set +(state-hub, core-hub, issue-core, activity-core); release with workstation off. ## Task: State Hub production home on railiance01