Skip to main content

Use GraphQL to migrate repositories from GitLab to GitHub Enterprise Cloud

You can build your own tooling to migrate repositories from GitLab to GitHub Enterprise Cloud using the GraphQL API.

Hinweis

You can also use GL2GH extension of the GitHub CLI to perform your migration. See Understand migrations from GitLab to GitHub.

Step 0: Get ready to use the GitHub GraphQL API

Um GraphQL-Abfragen zu erstellen, musst du eigene Skripts schreiben oder einen HTTP-Client wie Insomnia verwenden.

Weitere Informationen zu den ersten Schritten mit der GitHub-GraphQL-API, einschließlich der Authentifizierung, findest du unter Erstellen von Aufrufen mit GraphQL.

Du sendest alle GraphQL-Abfragen an das Ziel deiner Migration. Stelle bei der Migration zu GitHub Enterprise-Cloud mit Datenresidenz sicher, dass du Abfragen an den Endpunkt für die Unterdomäne für GHE.com sendest.

Step 1: Get the ownerId for your migration destination

Verwende als Organisationsbesitzer*in in GitHub Enterprise Cloud die Abfrage GetOrgInfo, um die ownerId (auch als Organisations-ID bezeichnet) für die Organisation zurückzugeben, der du den Besitz der migrierten Repositorys zuordnen möchtest. Du benötigst die ownerId, um das Migrationsziel anzugeben.

Abfrage GetOrgInfo

query(
  $login: String!
){
  organization (login: $login)
  {
    login
    id
    name
    databaseId
  }
}
AbfragevariableBeschreibung
loginName deiner Organisation.

Antwort von GetOrgInfo

{
  "data": {
    "organization": {
      "login": "Octo",
      "id": "MDEyOk9yZ2FuaXphdGlvbjU2MTA=",
      "name": "Octo-org",
      "databaseId": 5610
    }
  }
}

In diesem Beispiel ist MDEyOk9yZ2FuaXphdGlvbjU2MTA= die Organisations-ID oder die ownerId, die du im nächsten Schritt verwendest.

Step 2: Identify where you're migrating from

Du kannst eine Migrationsquelle mithilfe der Abfrage createMigrationSource einrichten. Du musst die ownerId oder die Organisations-ID angeben, die du mit der Abfrage GetOrgInfo abgerufen hast.

Your migration source is your GitLab instance.

createMigrationSource mutation

mutation createMigrationSource($name: String!, $url: String!, $ownerId: ID!) {
  createMigrationSource(input: {name: $name, url: $url, ownerId: $ownerId, type: GITLAB}) {
    migrationSource {
      id
      name
      url
      type
    }
  }
}

Set url to the full URL of your GitLab instance, such as https://gitlab.com or https://gitlab.example.com. Make sure to use GITLAB for type.

AbfragevariableBeschreibung
nameEin Name für deine Migrationsquelle. Dieser Name dient deiner eigenen Referenz, sodass du eine beliebige Zeichenfolge angeben kannst.
ownerIdDie Organisations-ID deiner Organisation in GitHub Enterprise Cloud.

createMigrationSource response

{
  "data": {
    "createMigrationSource": {
      "migrationSource": {
        "id": "MS_kgDaACQxYmYxOWU4Yi0wNzZmLTQ3NTMtOTdkZC1hNGUzZmYxN2U2YzA",
        "name": "GitLab Source",
        "url": "https://gitlab.com",
        "type": "GITLAB"
      }
    }
  }
}

In this example, MS_kgDaACQxYmYxOWU4Yi0wNzZmLTQ3NTMtOTdkZC1hNGUzZmYxN2U2YzA is the migration source ID, which we'll use in a later step.

Step 3: Generate and host your migration archive

Migrations from GitLab are archive-based. Instead of connecting to your GitLab instance during the migration, GitHub Enterprise Importer imports a migration archive that you generate from your GitLab project. A GitLab archive is a single file that contains both the Git source and the repository's metadata.

Before you start the migration, you must:

  1. Generate a migration archive for the GitLab project you want to migrate.
  2. Host the archive at a URL that GitHub Enterprise Cloud can access.

You'll provide this URL as the gitArchiveUrl value in the next step.

Generating a migration archive

Use the GitLab project export API to export the project you want to migrate. The token you use must have the api scope and a role with permission to export the project. For more information, see Manage access for a migration from GitLab to GitHub.

In the following requests, set the GITLAB_PAT environment variable to the token you created in Manage access for a migration from GitLab to GitHub. Replace GITLAB-SERVER with the host of your GitLab instance, such as gitlab.com, and replace GROUP%2FPROJECT with the URL-encoded path of your project. For example, the project acme-group/my-project is encoded as acme-group%2Fmy-project. For nested subgroups, include the full path, such as parent-group%2Fsubgroup%2Fmy-project.

  1. Schedule the export.

    curl --request POST \
      --header "PRIVATE-TOKEN: $GITLAB_PAT" \
      "https://GITLAB-SERVER/api/v4/projects/GROUP%2FPROJECT/export"
    
  2. Check the status of the export. Repeat this request until export_status is finished.

    curl --header "PRIVATE-TOKEN: $GITLAB_PAT" \
      "https://GITLAB-SERVER/api/v4/projects/GROUP%2FPROJECT/export"
    
  3. Download the archive.

    curl --location \
      --header "PRIVATE-TOKEN: $GITLAB_PAT" \
      --output archive.tar.gz \
      "https://GITLAB-SERVER/api/v4/projects/GROUP%2FPROJECT/export/download"
    

Hosting the archive

You must host the archive at a URL that GitHub Enterprise Cloud can access. You can either upload the archive to GitHub-owned blob storage or use an external blob storage provider. For information about external providers, see Configure blob storage.

To upload the archive to GitHub-owned blob storage, you'll need the database ID of your organization on GitHub Enterprise Cloud. Replace ORGANIZATION with the name of your organization to get this ID from the id field in the response.

curl --header "Authorization: Bearer YOUR-TOKEN" \
  "https://api.github.com/orgs/ORGANIZATION"

Hinweis

If you're migrating to GHE.com, replace https://api.github.com with the base API URL for your enterprise's subdomain, such as https://api.octocorp.ghe.com.

Upload the archive with a POST request, replacing ORGANIZATION-ID with your organization's database ID. This request works for archives up to 100 MiB. For larger archives, use an external blob storage provider.

curl --request POST \
  --header "Authorization: Bearer YOUR-TOKEN" \
  --header "Content-Type: application/octet-stream" \
  --data-binary @archive.tar.gz \
  "https://uploads.github.com/organizations/ORGANIZATION-ID/gei/archive?name=archive.tar.gz"

Hinweis

If you're migrating to GHE.com, replace uploads.github.com with the uploads host for your enterprise's subdomain, such as uploads.octocorp.ghe.com.

The response includes a uri in the format gei://archive/GUID. Use this value as the gitArchiveUrl in the next step.

{
  "guid": "ff7b1a25-aa10-41a9-8e42-f170304b1c0d",
  "node_id": "MA_kgDaACRmZjdiMWEyNS1hYTEwLTQxYTktOGU0Mi1mMTcwMzA0YjFjMGQ",
  "name": "archive.tar.gz",
  "size": 7103,
  "uri": "gei://archive/ff7b1a25-aa10-41a9-8e42-f170304b1c0d",
  "created_at": "2024-11-13T12:35:45.761-08:00"
}

Step 4: Start your repository migration

Wenn du eine Migration startest, werden ein einzelnes Repository und die zugehörigen Daten zu einem neuen GitHub-Repository migriert, das du angibst.

Wenn du mehrere Repositorys gleichzeitig aus derselben Quellorganisation verschieben möchtest, kannst du mehrere Migrationsvorgänge in die Warteschlange einreihen. Du kannst bis zu fünf Migrationsvorgänge gleichzeitig ausführen.

startRepositoryMigration mutation

mutation startRepositoryMigration (
  $sourceId: ID!,
  $ownerId: ID!,
  $sourceRepositoryUrl: URI!,
  $repositoryName: String!,
  $continueOnError: Boolean!,
  $accessToken: String!,
  $githubPat: String!,
  $gitArchiveUrl: String!,
  $targetRepoVisibility: String!
){
  startRepositoryMigration( input: {
    sourceId: $sourceId,
    ownerId: $ownerId,
    repositoryName: $repositoryName,
    continueOnError: $continueOnError,
    accessToken: $accessToken,
    githubPat: $githubPat,
    targetRepoVisibility: $targetRepoVisibility,
    gitArchiveUrl: $gitArchiveUrl,
    sourceRepositoryUrl: $sourceRepositoryUrl,
  }) {
    repositoryMigration {
      id
      migrationSource {
        id
        name
        type
      }
      sourceUrl
    }
  }
}
AbfragevariableBeschreibung
sourceIdDie id deiner Migrationsquelle, die von der createMigrationSource-Mutation zurückgegeben wurde.
ownerIdDie Organisations-ID deiner Organisation in GitHub Enterprise Cloud.
repositoryNameEin benutzerdefinierter eindeutiger Repositoryname, der derzeit von keinem deiner Repositorys im Besitz der Organisation auf GitHub Enterprise Cloud verwendet wird. Wenn die Migration abgeschlossen oder beendet wurde, wird ein Fehlerprotokollierungsproblem in diesem Repository erstellt.
continueOnErrorMigrationseinstellung, mit der die Migration fortgesetzt werden kann, wenn Fehler auftreten, die nicht dazu führen, dass die Migration fehlerhaft wird. Muss true oder false sein. Es wird dringend empfohlen continueOnError auf true festzulegen, damit die Migration fortgesetzt wird, es sei denn, der Importer kann die Git-Quelle nicht verschieben oder der Importer hat die Verbindung unterbrochen und kann die Verbindung nicht wiederherstellen, um die Migration abzuschließen.
githubPatDas personal access token für deine Zielorganisation auf GitHub Enterprise Cloud.
accessTokenDas personal access token für deine Quelle.
targetRepoVisibilityDie Sichtbarkeit des neuen Repositorys. Muss private, public oder internal sein. Wenn sie nicht festgelegt wurde, wird dein Repository als privat migriert.
gitArchiveUrlA GitHub Enterprise Cloud-accessible URL to the migration archive you generated in the previous step. GitLab migrations use a single archive that contains both the Git source and metadata, so you don't need to provide a separate metadataArchiveUrl.
sourceRepositoryUrlThe URL of your source repository on GitLab, using the format https://GITLAB-SERVER/{group}/{project}. For nested subgroups, include the full path, such as https://GITLAB-SERVER/{parent-group}/{subgroup}/{project}. GitHub Enterprise Cloud does not connect to this URL during the migration; it's recorded for reference.

Because GitLab migrations are archive-based, GitHub Enterprise Cloud does not connect to GitLab during the migration. The accessToken variable is required by the mutation but isn't used, so you can set it to any placeholder value, such as not-used.

For personal access token requirements, see Manage access for a migration from GitLab to GitHub.

Im nächsten Schritt verwendest du die von der startRepositoryMigration-Mutation zurückgegebene Migrations-ID, um den Migrationsstatus zu überprüfen.

Step 5: Check the status of your migration

Um Migrationsfehler zu erkennen und sicherzustellen, dass deine Migration funktioniert, kannst du den Migrationsstatus mithilfe der Abfrage getMigration überprüfen. Du kannst auch den Status mehrerer Migrationsvorgänge mit getMigrations überprüfen.

Die Abfrage getMigration gibt für die Migration einen der folgenden Status zurück: queued, in progress, failed oder completed. Wenn die Migration fehlerhaft war, gibt der Importer einen Grund für den Fehler an.

Abfrage getMigration

query (
  $id: ID!
){
  node( id: $id ) {
    ... on Migration {
      id
      sourceUrl
      migrationSource {
        name
      }
      state
      failureReason
    }
  }
}
AbfragevariableBeschreibung
idDie id deiner Migration, die von der startRepositoryMigration-Mutation zurückgegeben wurde.

Step 6: Validate your migration and check the error log

Um die Migration abzuschließen, solltest du das Issue „Migrationsprotokoll“ überprüfen. Dieses Problem wird in GitHub im Zielrepository erstellt.

Screenshot eines Problems mit dem Titel „Migrationsprotokoll“. Der zweite Kommentar im Issue enthält Protokolle für eine Migration.

Abschließend wird empfohlen, die Integrität deiner migrierten Repositorys zu überprüfen.

Further reading