markdown · 2394 bytes Raw Blame History

Forks

Manage a repo's fork network. Mirrors GitHub's /repos/{owner}/{repo}/forks shape.

Scopes: repo:read on GET, repo:write on POST. Policy gates are ActionRepoRead and ActionForkCreate. See common API conventions for envelopes and headers.

List forks

GET /api/v1/repos/{owner}/{repo}/forks[?page=&per_page=]

Paginated, recency-sorted, soft-deleted rows excluded. Per-row visibility filter applies — a private fork of a public repo only surfaces to viewers who can see the fork.

[
  {
    "id":         101,
    "name":       "demo",
    "owner_login":         "bob",
    "owner_display_name":  "Bob",
    "description":         "",
    "visibility":          "public",
    "star_count":          0,
    "fork_count":          0,
    "init_status":         "initialized",
    "created_at":          "2026-05-12T15:00:00Z"
  }
]

init_status is one of init_pending / initialized / init_failed — clients can poll the single-repo endpoint to watch a fresh fork transition out of init_pending.

Create a fork

POST /api/v1/repos/alice/demo/forks
Authorization: Bearer <pat>
Content-Type: application/json

{
  "name":       "demo-fork",
  "visibility": "private"
}

All fields are optional:

  • name — repo name on the caller's account. Defaults to the source repo's name. Forking your own repo into the same name is refused (409); pass a different name.
  • visibility — must be ≤ source visibility. A public source can fork to private; a private source is pinned to private.

Targets the authenticated user's namespace only today. Org targets land in a follow-up.

Returns 201 Created with the persisted row immediately. The on-disk git clone --bare --shared runs in the background worker (repo:fork_clone kind), so the response carries init_status: "init_pending" and the fork's URL resolves right away.

{
  "id":             101,
  "name":           "demo-fork",
  "owner_login":    "bob",
  "visibility":     "public",
  "init_status":    "init_pending",
  "source_repo_id": 42,
  "default_branch": "trunk",
  "created_at":     "2026-05-12T15:00:00Z"
}

Errors

  • 404 — source repo not visible.
  • 409 — self-fork with no name override, target name collides with an existing repo, or source archived.
  • 422visibility exceeds source visibility.
View source
1 # Forks
2
3 Manage a repo's fork network. Mirrors GitHub's
4 `/repos/{owner}/{repo}/forks` shape.
5
6 Scopes: `repo:read` on GET, `repo:write` on POST. Policy gates
7 are `ActionRepoRead` and `ActionForkCreate`. See
8 [common API conventions](overview.md) for envelopes and headers.
9
10 ## List forks
11
12 ```
13 GET /api/v1/repos/{owner}/{repo}/forks[?page=&per_page=]
14 ```
15
16 Paginated, recency-sorted, soft-deleted rows excluded. Per-row
17 visibility filter applies — a private fork of a public repo
18 only surfaces to viewers who can see the fork.
19
20 ```json
21 [
22 {
23 "id": 101,
24 "name": "demo",
25 "owner_login": "bob",
26 "owner_display_name": "Bob",
27 "description": "",
28 "visibility": "public",
29 "star_count": 0,
30 "fork_count": 0,
31 "init_status": "initialized",
32 "created_at": "2026-05-12T15:00:00Z"
33 }
34 ]
35 ```
36
37 `init_status` is one of `init_pending` / `initialized` /
38 `init_failed` — clients can poll the single-repo endpoint to
39 watch a fresh fork transition out of `init_pending`.
40
41 ## Create a fork
42
43 ```http
44 POST /api/v1/repos/alice/demo/forks
45 Authorization: Bearer <pat>
46 Content-Type: application/json
47
48 {
49 "name": "demo-fork",
50 "visibility": "private"
51 }
52 ```
53
54 All fields are optional:
55
56 - `name` — repo name on the caller's account. Defaults to the
57 source repo's name. Forking your own repo into the same name
58 is refused (409); pass a different `name`.
59 - `visibility` — must be ≤ source visibility. A public source
60 can fork to private; a private source is pinned to private.
61
62 Targets the **authenticated user's namespace only** today. Org
63 targets land in a follow-up.
64
65 Returns `201 Created` with the persisted row immediately. The
66 on-disk `git clone --bare --shared` runs in the background
67 worker (`repo:fork_clone` kind), so the response carries
68 `init_status: "init_pending"` and the fork's URL resolves right
69 away.
70
71 ```json
72 {
73 "id": 101,
74 "name": "demo-fork",
75 "owner_login": "bob",
76 "visibility": "public",
77 "init_status": "init_pending",
78 "source_repo_id": 42,
79 "default_branch": "trunk",
80 "created_at": "2026-05-12T15:00:00Z"
81 }
82 ```
83
84 ## Errors
85
86 - `404` — source repo not visible.
87 - `409` — self-fork with no `name` override, target name
88 collides with an existing repo, or source archived.
89 - `422``visibility` exceeds source visibility.