docs(guides): add a migration guide for GitHub and GitLab #185

Sammanfogat
supernaut sammanfogade 2 incheckningar från docs/migration-guide in i main 2026-08-03 07:36:07 +00:00
Ägare

Nothing on the site told a visitor how to move an existing repository here, or what comes across
when they do. It is the first question anyone already settled on another host asks, and answering it
removes a real switching cost.

One guide covers both origins rather than two near-identical ones: the import path and most of the
content are shared, and a single page is the one a search lands on.

What the guide leads with

The choice that cannot be undone. A repository can be created as a mirror or as a one-off
import, and a repository that already exists here cannot be converted into a mirror afterwards. That
belongs at the top, not in a footnote, because it is the only decision in the whole process that a
reader cannot correct later.

The longer list is what does not come across. Workflows do not run unchanged — runs-on: ubuntu-latest has to become ci — secrets never transfer, and branch protection, webhooks, stars
and watchers are not part of an import. None of it is visible while the import runs; all of it is
visible afterwards. A migration guide that omits what is lost is worse than no guide, because the
loss is then discovered after the switch.

Existing guides are renumbered so this one sits second, after getting-started, without an order
tie.

Verified, not assumed — and where the line falls

The transfer claims were checked in two different ways, and the PR is explicit about which is which
rather than implying uniform confidence.

Confirmed by a real import — sindresorhus/slash into a scratch repository on the instance,
since deleted:

Claim Evidence
The GitHub import path works for a public repository with no token The import ran and created the repository
The repository description transfers Convert Windows backslash paths to slash paths arrived
Releases transfer 5 at source (v3.0.0, v4.0.0, v5.0.0, v5.0.1, v5.1.0), 5 imported, blank titles preserved
An unauthenticated import crawls rather than failing Two runs, both stalled on issue and pull request pagination

That last finding is not in the issue and is now the guide's most practically useful paragraph:
GitHub allows roughly 60 unauthenticated API requests per hour, and an import that hits the limit
does not error — it slows to a crawl, which a reader would reasonably misread as a hung migration.
The guide therefore tells them to use a token when importing issue history, not only for private
repositories.

Sourced from the migration form at the pinned Forgejo version, not from an observed import: the
item list itself — issues, pull requests, labels, milestones, releases and wiki — read from
templates/repo/migrate/github.tmpl at v16.0, plus the mirror behaviour and the
cannot-convert-afterwards constraint from the repository mirror documentation.

Swedish terminology was taken from Forgejo's own sv-SE locale as the style guide requires, not
invented: spegling, utgåvor, milstolpar, grenar, taggar.

pnpm lang-check clean over 78 files, pnpm lint clean, pnpm check 0 errors and 0 warnings,
pnpm test 296 passing, pnpm build clean, and both new slugs present in sitemap-0.xml.

What is deliberately left open

The issue's definition of done asked for every claim to be checked against a real import. The
rate limit above stopped that: the scratch repository never began serving git data, so branches,
tags, history, issues, pull requests, labels, milestones and wiki are unconfirmed. Both attempts
were also interrupted by killing the client while the server-side task continued, so the 500 the
repository returned on git ls-remote is not presented as a Forgejo defect — it may be an
artefact of that interruption.

Rather than overstate the guide's provenance, that gap is filed as gitborg/gitborg-web#184, which
records what is already confirmed, what is not, and that a GitHub token makes the remaining check a
minutes-long job.

A note on scope: LFS is offered as a migratable item by the API (--include lfs) but does not appear
as a checkbox in the GitHub migration form template. Since the guide's table describes the form, no
LFS row was added — an unverified row is exactly the kind of claim this guide exists to avoid.

Closes #182. Part of gitborg/gitborg-docs#28.

Nothing on the site told a visitor how to move an existing repository here, or what comes across when they do. It is the first question anyone already settled on another host asks, and answering it removes a real switching cost. One guide covers both origins rather than two near-identical ones: the import path and most of the content are shared, and a single page is the one a search lands on. ### What the guide leads with **The choice that cannot be undone.** A repository can be created as a mirror or as a one-off import, and a repository that already exists here cannot be converted into a mirror afterwards. That belongs at the top, not in a footnote, because it is the only decision in the whole process that a reader cannot correct later. **The longer list is what does *not* come across.** Workflows do not run unchanged — `runs-on: ubuntu-latest` has to become `ci` — secrets never transfer, and branch protection, webhooks, stars and watchers are not part of an import. None of it is visible while the import runs; all of it is visible afterwards. A migration guide that omits what is lost is worse than no guide, because the loss is then discovered after the switch. Existing guides are renumbered so this one sits second, after `getting-started`, without an `order` tie. ### Verified, not assumed — and where the line falls The transfer claims were checked in two different ways, and the PR is explicit about which is which rather than implying uniform confidence. **Confirmed by a real import** — `sindresorhus/slash` into a scratch repository on the instance, since deleted: | Claim | Evidence | | ----- | -------- | | The GitHub import path works for a public repository with no token | The import ran and created the repository | | The repository description transfers | `Convert Windows backslash paths to slash paths` arrived | | Releases transfer | 5 at source (`v3.0.0`, `v4.0.0`, `v5.0.0`, `v5.0.1`, `v5.1.0`), 5 imported, blank titles preserved | | An unauthenticated import crawls rather than failing | Two runs, both stalled on issue and pull request pagination | That last finding is not in the issue and is now the guide's most practically useful paragraph: GitHub allows roughly 60 unauthenticated API requests per hour, and an import that hits the limit does not error — it slows to a crawl, which a reader would reasonably misread as a hung migration. The guide therefore tells them to use a token when importing issue history, not only for private repositories. **Sourced from the migration form at the pinned Forgejo version**, not from an observed import: the item list itself — issues, pull requests, labels, milestones, releases and wiki — read from `templates/repo/migrate/github.tmpl` at `v16.0`, plus the mirror behaviour and the cannot-convert-afterwards constraint from the repository mirror documentation. **Swedish terminology** was taken from Forgejo's own `sv-SE` locale as the style guide requires, not invented: *spegling*, *utgåvor*, *milstolpar*, *grenar*, *taggar*. `pnpm lang-check` clean over 78 files, `pnpm lint` clean, `pnpm check` 0 errors and 0 warnings, `pnpm test` 296 passing, `pnpm build` clean, and both new slugs present in `sitemap-0.xml`. ### What is deliberately left open The issue's definition of done asked for **every** claim to be checked against a real import. The rate limit above stopped that: the scratch repository never began serving git data, so branches, tags, history, issues, pull requests, labels, milestones and wiki are unconfirmed. Both attempts were also interrupted by killing the client while the server-side task continued, so the 500 the repository returned on `git ls-remote` is **not** presented as a Forgejo defect — it may be an artefact of that interruption. Rather than overstate the guide's provenance, that gap is filed as gitborg/gitborg-web#184, which records what is already confirmed, what is not, and that a GitHub token makes the remaining check a minutes-long job. A note on scope: LFS is offered as a migratable item by the API (`--include lfs`) but does not appear as a checkbox in the GitHub migration form template. Since the guide's table describes the form, no LFS row was added — an unverified row is exactly the kind of claim this guide exists to avoid. Closes #182. Part of gitborg/gitborg-docs#28.
supernaut lade till 2 incheckningar 2026-08-02 23:32:59 +00:00
Nothing on the site told a visitor how to move an existing repository here, or what
comes across when they do. It is the first question anyone already settled on another
host asks.

One guide covers both origins: the import path and most of the content are shared, and a
single page is the one a search lands on.

The item list is read from the migration form at the pinned Forgejo version rather than
from memory, and the guide leads with the choice that cannot be undone — a repository
that already exists here cannot be turned into a mirror afterwards.

The longer of the two lists is what does NOT come across, because none of it is visible
during the import and all of it is visible afterwards.

Existing guides are renumbered so the new one sits second without an order tie.
docs(guides): tell readers to use a token when importing issue history
Alla kontroller lyckades
ci / ci (pull_request) Successful in 1m20s
4137daac3b
Found by running a real import: an unauthenticated GitHub import does not fail on the
API rate limit, it crawls. The code arrives quickly; the issue and pull request history
is what waits, which is exactly the failure a reader would misread as a hung migration.
supernaut sammanfogade incheckning b269f9ee0c till main 2026-08-03 07:36:07 +00:00
supernaut tog bort grenen docs/migration-guide 2026-08-03 07:36:07 +00:00
Logga in för att delta i denna konversation.
Inga granskare
Ingen milstolpe
Inget projekt
Inga tilldelade
1 deltagare
Notiser
Förfallodatum
Förfallodatumet är ogiltigt eller utanför gränserna. Använd formatet "åååå-mm-dd".

Inget förfallodatum satt.

Beroenden

Inga beroenden satta

Referens
bitborg/bitborg-web!185
Ingen beskrivning angiven.