just-git 1.4.1 → 1.5.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -126,6 +126,20 @@ interface Storage {
126
126
  * The adapter uses this for compare-and-swap with symref resolution.
127
127
  */
128
128
  atomicRefUpdate<T>(repoId: string, fn: (ops: RefOps) => MaybeAsync<T>): MaybeAsync<T>;
129
+ /**
130
+ * Record a fork relationship. `targetId` becomes a fork of `sourceId`.
131
+ * The adapter layer handles ref copying and root resolution.
132
+ */
133
+ forkRepo?(sourceId: string, targetId: string): MaybeAsync<void>;
134
+ /**
135
+ * Get the parent (root) repo ID for a fork, or `null` if the repo
136
+ * is not a fork.
137
+ */
138
+ getForkParent?(repoId: string): MaybeAsync<string | null>;
139
+ /**
140
+ * List all direct fork IDs of a repo.
141
+ */
142
+ listForks?(repoId: string): MaybeAsync<string[]>;
129
143
  }
130
144
 
131
145
  /** Options for {@link gcRepo}. */
@@ -367,7 +381,7 @@ interface RefUpdateRequest {
367
381
  */
368
382
  oldHash?: string | null;
369
383
  }
370
- interface GitServer {
384
+ interface GitServer<A = Auth> {
371
385
  /** Standard fetch-API handler for HTTP: (Request) => Response */
372
386
  fetch(request: Request): Promise<Response>;
373
387
  /**
@@ -474,8 +488,24 @@ interface GitServer {
474
488
  repo(id: string): Promise<GitRepo | null>;
475
489
  /** Get a repo by ID, or throw if it doesn't exist. */
476
490
  requireRepo(id: string): Promise<GitRepo>;
477
- /** Delete a repo and all its data. */
491
+ /** Delete a repo and all its data. Throws if the repo has active forks. */
478
492
  deleteRepo(id: string): Promise<void>;
493
+ /**
494
+ * Fork an existing repo. Copies refs from the source repo to the
495
+ * target. The fork shares the source's object pool — object reads
496
+ * fall through to the root repo's partition, while writes go to
497
+ * the fork's own partition.
498
+ *
499
+ * Forking a fork resolves to the root: `forkRepo("fork-of-A", "B")`
500
+ * records B as a fork of A's root, not of the intermediate fork.
501
+ *
502
+ * Requires a storage backend that implements fork methods.
503
+ *
504
+ * @throws If the source doesn't exist, the target already exists,
505
+ * the storage backend doesn't support forks, or the server is
506
+ * shutting down.
507
+ */
508
+ forkRepo(sourceId: string, targetId: string, options?: CreateRepoOptions): Promise<GitRepo>;
479
509
  /**
480
510
  * Remove unreachable objects from a repo's storage.
481
511
  *
@@ -514,12 +544,29 @@ interface GitServer {
514
544
  * await git.exec("clone http://git/my-repo /work");
515
545
  * ```
516
546
  *
547
+ * When `auth` is provided, in-process requests bypass the server's
548
+ * `auth.http` callback entirely — hooks receive the supplied auth
549
+ * context directly. This is the recommended approach for operator-
550
+ * controlled agents where identity is known at wiring time:
551
+ *
552
+ * ```ts
553
+ * const network = server.asNetwork("http://git", {
554
+ * userId: "agent-1",
555
+ * roles: ["push"],
556
+ * });
557
+ * const git = createGit({ network });
558
+ * ```
559
+ *
560
+ * When `auth` is omitted, `auth.http` runs on every request as usual.
561
+ *
517
562
  * @param baseUrl - Base URL used in clone/push/fetch commands.
518
563
  * Only the hostname matters (for the `allowed` list). The URL
519
564
  * never hits the network — it's resolved by the server's
520
565
  * `resolve` function. Defaults to `"http://git"`.
566
+ * @param auth - Pre-resolved auth context injected into server hooks,
567
+ * bypassing `auth.http`. Must match the server's `A` type.
521
568
  */
522
- asNetwork(baseUrl?: string): NetworkPolicy;
569
+ asNetwork(baseUrl?: string, auth?: A): NetworkPolicy;
523
570
  }
524
571
  interface ServerHooks<A = Auth> {
525
572
  /**
@@ -649,7 +696,7 @@ interface RefUpdateResult {
649
696
  * server.handleSession(command, channel, { username });
650
697
  * ```
651
698
  */
652
- declare function createServer<A = Auth>(config?: GitServerConfig<A>): GitServer;
699
+ declare function createServer<A = Auth>(config?: GitServerConfig<A>): GitServer<A>;
653
700
  /**
654
701
  * Compose multiple hook sets into a single `ServerHooks` object.
655
702
  *
@@ -950,6 +997,7 @@ declare class MemoryStorage implements Storage {
950
997
  private repos;
951
998
  private objects;
952
999
  private refs;
1000
+ private forks;
953
1001
  hasRepo(repoId: string): boolean;
954
1002
  insertRepo(repoId: string): void;
955
1003
  deleteRepo(repoId: string): void;
@@ -969,6 +1017,9 @@ declare class MemoryStorage implements Storage {
969
1017
  removeRef(repoId: string, name: string): void;
970
1018
  listRefs(repoId: string, prefix?: string): RawRefEntry[];
971
1019
  atomicRefUpdate<T>(repoId: string, fn: (ops: RefOps) => T): T;
1020
+ forkRepo(sourceId: string, targetId: string): void;
1021
+ getForkParent(repoId: string): string | null;
1022
+ listForks(repoId: string): string[];
972
1023
  /** List all created repo IDs. Convenience for tests and debugging. */
973
1024
  repoIds(): string[];
974
1025
  private getObjMap;
@@ -1020,6 +1071,9 @@ declare class BunSqliteStorage implements Storage {
1020
1071
  removeRef(repoId: string, name: string): void;
1021
1072
  listRefs(repoId: string, prefix?: string): RawRefEntry[];
1022
1073
  atomicRefUpdate<T>(repoId: string, fn: (ops: RefOps) => T): T;
1074
+ forkRepo(sourceId: string, targetId: string): void;
1075
+ getForkParent(repoId: string): string | null;
1076
+ listForks(repoId: string): string[];
1023
1077
  }
1024
1078
 
1025
1079
  /** Minimal prepared statement interface matching `better-sqlite3`. */
@@ -1067,6 +1121,9 @@ declare class BetterSqlite3Storage implements Storage {
1067
1121
  removeRef(repoId: string, name: string): void;
1068
1122
  listRefs(repoId: string, prefix?: string): RawRefEntry[];
1069
1123
  atomicRefUpdate<T>(repoId: string, fn: (ops: RefOps) => T): T;
1124
+ forkRepo(sourceId: string, targetId: string): void;
1125
+ getForkParent(repoId: string): string | null;
1126
+ listForks(repoId: string): string[];
1070
1127
  }
1071
1128
 
1072
1129
  /** Minimal pool interface matching the `pg` package's `Pool` class. */
@@ -1117,6 +1174,9 @@ declare class PgStorage implements Storage {
1117
1174
  removeRef(repoId: string, name: string): Promise<void>;
1118
1175
  listRefs(repoId: string, prefix?: string): Promise<RawRefEntry[]>;
1119
1176
  atomicRefUpdate<T>(repoId: string, fn: (ops: RefOps) => Promise<T> | T): Promise<T>;
1177
+ forkRepo(sourceId: string, targetId: string): Promise<void>;
1178
+ getForkParent(repoId: string): Promise<string | null>;
1179
+ listForks(repoId: string): Promise<string[]>;
1120
1180
  }
1121
1181
 
1122
1182
  export { type AdvertiseRefsEvent, type AdvertiseResult, type ApplyReceivePackOptions, type Auth, type AuthProvider, type BetterSqlite3Database, BetterSqlite3Storage, type BunSqliteDatabase, BunSqliteStorage, type CreateRepoOptions, type GcOptions, type GcResult, GitRepo, type GitServer, type GitServerConfig, type MaybeAsync, MemoryStorage, type NodeHttpRequest, type NodeHttpResponse, type PgPool, PgStorage, type PostReceiveEvent, type PreReceiveEvent, type PushCommand, RawObject, type RawRefEntry, type ReceivePackResult, Ref, type RefAdvertisement, type RefOps, type RefResult, type RefUpdate, type RefUpdateRequest, type RefUpdateResult, Rejection, type ServerHooks, type ServerPolicy, type SshChannel, type SshSessionInfo, type Storage, type UpdateEvent, type V2CommandRequest, type V2FetchRequest, type V2FetchResponseOptions, type V2LsRefsRef, advertiseRefsWithHooks, applyCasRefUpdates, applyReceivePack, buildRefAdvertisementBytes, buildRefListBytes, buildRefListPktLines, buildV2CapabilityAdvertisement, buildV2CapabilityAdvertisementBytes, buildV2FetchResponse, buildV2LsRefsResponse, collectRefs, composeHooks, createServer, handleLsRefs, handleUploadPack, handleV2Fetch, ingestReceivePack, ingestReceivePackFromStream, parseV2CommandRequest, parseV2FetchArgs, resolveRefUpdates };