Skip to content

What handing a takeover back would do, ref by ref, in plan.refs: each with base (where it was when the takeover began), ours, theirs and action: push (only g1t moved), fetch (only the remote moved), pull_request (the remote protects the branch: g1t's commits go to g1t/handback/<branch> there as a pull request, and g1t follows the remote's branch) or diverged (both moved: it needs a decision).

GET/repos/{owner}/{name}/mirror/hand-back

plan.reachable is false while the remote does not answer; plan.ready once it answers and every diverged ref has a decision. Asks the remote, so it takes a moment. Needs the Admin role.

Refs that did not move on either side are left out. ready stays false until docs/readme has a decision.

  • Authentication: Required. Send an access token as Authorization: Bearer.
  • MCP tool: repository with action mirror_hand_back_plan, and the same inputs
  • Scope: An access token needs repo:admin.
Name Type Required Description
owner string Yes The workspace that owns the repository.
name string Yes The repository’s name.
curl https://api.g1t.sh/repos/acme/web/mirror/hand-back \
-H "Authorization: Bearer $G1T_TOKEN"

A successful request answers 200 with:

{
"remotes": [
{
"id": "rmt_01kp4a2b3c4d5e6f7g8h9j0k1m",
"repo_id": "rep_01kp49z8y7x6w5v4t3s2r1q0pn",
"repo": "acme/web",
"provider": "github",
"role": "leader",
"name": "github.com/acme/web",
"url": "https://github.com/acme/web",
"state": "takeover",
"state_since": "2026-10-08T13:58:00.000Z",
"state_by": "syntaqx",
"reachable": true,
"unreachable_since": null,
"synced_at": "2026-10-08T13:57:42.000Z",
"last_error": null,
"settings": {
"notify": "banner",
"take_over_after": null,
"hand_back": "when_clean",
"keep_ci_warm": false,
"github_workflows": true,
"hold_deploys": true,
"remote_pushes": "adopt"
},
"created_at": "2026-10-05T10:00:00.000Z"
}
],
"plan": {
"refs": [
{
"ref": "refs/heads/fix/login-timeout",
"base": "9d0e1aa4c8f2b7e6d5a4c3b2a1f0e9d8c7b6a5f4",
"ours": "c47f2b8e1d0c9b8a7f6e5d4c3b2a1f0e9d8c7b6a",
"theirs": "9d0e1aa4c8f2b7e6d5a4c3b2a1f0e9d8c7b6a5f4",
"action": "push",
"decision": null
},
{
"ref": "refs/heads/main",
"base": "41c9e02b7a6f5e4d3c2b1a0f9e8d7c6b5a4f3e2d",
"ours": "e01d9a37f6e5d4c3b2a1f0e9d8c7b6a5f4e3d2c1",
"theirs": "41c9e02b7a6f5e4d3c2b1a0f9e8d7c6b5a4f3e2d",
"action": "pull_request",
"decision": null
},
{
"ref": "refs/heads/docs/readme",
"base": "7f3a1c2d4e5f6a7b8c9d0e1f2a3b4c5d6e7f8a9b",
"ours": "5b6c7d8e9f0a1b2c3d4e5f6a7b8c9d0e1f2a3b4c",
"theirs": "a1b2c3d4e5f6a7b8c9d0e1f2a3b4c5d6e7f8a9b0",
"action": "diverged",
"decision": null
}
],
"reachable": true,
"ready": false
},
"can_manage": true
}

A failed request answers with one of these statuses and a body like {"error": {"code": "not_found", "message": "Repository not found."}}. See errors.

Status Code When
401 unauthenticated A token is required, or the one sent is not valid.
403 forbidden The token is valid but not allowed to do this, such as a member-only change or an agent token outside its repository.
404 not_found It does not exist, or you cannot see it.
422 invalid The input is not valid. message says which field and why.