@metalabel/dfos-protocol 0.0.3 → 0.2.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.
package/REGISTRY-API.md DELETED
@@ -1,242 +0,0 @@
1
- # DFOS Registry API
2
-
3
- Minimal HTTP API for chain storage, retrieval, and resolution. Any server implementing these endpoints with these semantics is a compatible DFOS registry.
4
-
5
- The protocol is transport-agnostic — chains can be exchanged through any mechanism. This API defines one standard transport binding: a REST interface for submitting chains, resolving identities and content, and retrieving operations and documents.
6
-
7
- [Protocol Specification](https://protocol.dfos.com/spec) · [OpenAPI Spec](https://github.com/metalabel/dfos/blob/main/packages/dfos-protocol/openapi.yaml) · [Reference Implementation](https://github.com/metalabel/dfos/blob/main/packages/dfos-protocol/src/registry/server.ts)
8
-
9
- ---
10
-
11
- ## Overview
12
-
13
- The registry stores verified chains and serves resolved state. It enforces **linear chain integrity** — it accepts chains that are the same length or longer than what's stored, and rejects forks (two different operations at the same chain position).
14
-
15
- Six endpoints, two concerns:
16
-
17
- | Concern | Endpoints |
18
- | ------------------- | ----------------------------------------------- |
19
- | **Identity chains** | Submit chain, resolve identity, list operations |
20
- | **Content chains** | Submit chain, resolve content, list operations |
21
- | **Lookup** | Resolve operation by CID |
22
-
23
- All request and response bodies are JSON (`application/json`).
24
-
25
- ---
26
-
27
- ## Identity Endpoints
28
-
29
- ### `POST /identities` — Submit or extend an identity chain
30
-
31
- Submit an ordered array of JWS tokens (genesis-first). The registry verifies the chain, derives the DID from the genesis CID, and stores it.
32
-
33
- **Request:**
34
-
35
- ```json
36
- {
37
- "chain": ["eyJhbGciOiJFZERTQSI...", "eyJhbGciOiJFZERTQSI..."]
38
- }
39
- ```
40
-
41
- | Field | Type | Description |
42
- | ------- | -------- | ---------------------------------------------------------- |
43
- | `chain` | string[] | Ordered JWS compact tokens, genesis-first. Minimum 1 item. |
44
-
45
- **Responses:**
46
-
47
- | Status | Meaning |
48
- | ------ | ---------------------------------------------------------- |
49
- | `201` | Chain accepted (new or extended) — returns `IdentityState` |
50
- | `200` | Chain already stored, no change — returns `IdentityState` |
51
- | `400` | Invalid chain (verification failed) |
52
- | `409` | Fork conflict with stored chain |
53
-
54
- ---
55
-
56
- ### `GET /identities/{did}` — Resolve current identity state
57
-
58
- Returns the current key state for a DID.
59
-
60
- **Parameters:**
61
-
62
- | Name | In | Pattern | Example |
63
- | ----- | ---- | ------------------------------------ | --------------------------------- |
64
- | `did` | path | `did:dfos:[2346789acdefhknrtvz]{22}` | `did:dfos:e3vvtck42d4eacdnzvtrn6` |
65
-
66
- **Response (`IdentityState`):**
67
-
68
- ```json
69
- {
70
- "did": "did:dfos:e3vvtck42d4eacdnzvtrn6",
71
- "isDeleted": false,
72
- "authKeys": [{ "id": "key_...", "type": "Multikey", "publicKeyMultibase": "z6Mk..." }],
73
- "assertKeys": [{ "id": "key_...", "type": "Multikey", "publicKeyMultibase": "z6Mk..." }],
74
- "controllerKeys": [{ "id": "key_...", "type": "Multikey", "publicKeyMultibase": "z6Mk..." }]
75
- }
76
- ```
77
-
78
- ---
79
-
80
- ### `GET /identities/{did}/operations` — List identity chain operations
81
-
82
- Returns operations newest-first, paginated.
83
-
84
- **Parameters:**
85
-
86
- | Name | In | Description |
87
- | -------- | ----- | ------------------------------------------------------------ |
88
- | `did` | path | The DID to list operations for |
89
- | `cursor` | query | Opaque pagination cursor (CID of last item on previous page) |
90
- | `limit` | query | Page size, 1–100, default 25 |
91
-
92
- **Response (`PaginatedOperations`):**
93
-
94
- ```json
95
- {
96
- "operations": [
97
- { "cid": "bafyrei...", "jwsToken": "eyJ...", "createdAt": "2026-03-07T00:01:00.000Z" },
98
- { "cid": "bafyrei...", "jwsToken": "eyJ...", "createdAt": "2026-03-07T00:00:00.000Z" }
99
- ],
100
- "nextCursor": null
101
- }
102
- ```
103
-
104
- ---
105
-
106
- ## Content Endpoints
107
-
108
- ### `POST /content` — Submit or extend a content chain
109
-
110
- Same mechanics as identity submission. The registry verifies the chain (resolving signing keys from stored identity chains), derives the content ID from the genesis CID, and stores it.
111
-
112
- **Request:** Same `{ "chain": [...] }` format as identity submission.
113
-
114
- **Responses:** Same status code semantics — `201` accepted, `200` noop, `400` invalid, `409` fork.
115
-
116
- ---
117
-
118
- ### `GET /content/{contentId}` — Resolve current content state
119
-
120
- Returns the current state for a content chain.
121
-
122
- **Parameters:**
123
-
124
- | Name | In | Pattern | Example |
125
- | ----------- | ---- | --------------------------- | ------------------------ |
126
- | `contentId` | path | `[2346789acdefhknrtvz]{22}` | `67t27rzc83v7c22n9t6z7c` |
127
-
128
- **Response (`ContentState`):**
129
-
130
- ```json
131
- {
132
- "contentId": "67t27rzc83v7c22n9t6z7c",
133
- "isDeleted": false,
134
- "currentDocumentCID": "bafyrei...",
135
- "genesisCID": "bafyrei...",
136
- "headCID": "bafyrei..."
137
- }
138
- ```
139
-
140
- | Field | Description |
141
- | -------------------- | --------------------------------------------------- |
142
- | `currentDocumentCID` | CID of current document, null if cleared or deleted |
143
- | `genesisCID` | CID of the genesis operation |
144
- | `headCID` | CID of the most recent operation |
145
-
146
- ---
147
-
148
- ### `GET /content/{contentId}/operations` — List content chain operations
149
-
150
- Same pagination mechanics as identity operations.
151
-
152
- ---
153
-
154
- ## Lookup Endpoints
155
-
156
- ### `GET /operations/{cid}` — Resolve a single operation by CID
157
-
158
- Returns the JWS token for any operation (identity or content) by its CID.
159
-
160
- **Response:**
161
-
162
- ```json
163
- {
164
- "cid": "bafyrei...",
165
- "jwsToken": "eyJ..."
166
- }
167
- ```
168
-
169
- ---
170
-
171
- ## Errors
172
-
173
- All error responses follow a standard shape:
174
-
175
- ```json
176
- {
177
- "error": "BAD_REQUEST",
178
- "message": "Human-readable description"
179
- }
180
- ```
181
-
182
- | Error Code | Used By |
183
- | ------------- | ---------------------------------------------------------- |
184
- | `BAD_REQUEST` | Invalid chain, malformed request |
185
- | `NOT_FOUND` | Identity, content, or operation not found |
186
- | `CONFLICT` | Fork detected — submitted chain diverges from stored chain |
187
-
188
- ---
189
-
190
- ## Chain Submission Semantics
191
-
192
- The registry enforces **linear chain extension**:
193
-
194
- - **New chain** — genesis operation not seen before → store and return `201`
195
- - **Extension** — submitted chain is longer than stored, shares the same prefix → replace stored chain, return `201`
196
- - **Noop** — submitted chain is identical to stored → return `200`
197
- - **Fork** — submitted chain diverges from stored chain at some operation → reject with `409`
198
-
199
- This means a registry is **eventually consistent with the longest valid chain** it receives. It does not implement consensus — if two registries receive different valid extensions, they may diverge. Fork detection is the caller's responsibility.
200
-
201
- ---
202
-
203
- ## Authentication
204
-
205
- Registry endpoints that require authentication use **EdDSA JWTs** signed with the same Ed25519 keys from identity chains. The JWT convention is not part of the chain protocol — it's an application-layer auth mechanism for services.
206
-
207
- ```json
208
- {
209
- "alg": "EdDSA",
210
- "typ": "JWT",
211
- "kid": "key_ez9a874tckr3dv933d3ckd"
212
- }
213
- ```
214
-
215
- ```json
216
- {
217
- "iss": "dfos",
218
- "sub": "did:dfos:e3vvtck42d4eacdnzvtrn6",
219
- "aud": "dfos-api",
220
- "exp": 1772902800,
221
- "iat": 1772899200,
222
- "jti": "session_ref_example_01"
223
- }
224
- ```
225
-
226
- | Field | Description |
227
- | ----- | ------------------------------------------------------------- |
228
- | `kid` | Bare key ID (not a DID URL — the `sub` claim carries the DID) |
229
- | `sub` | The DID of the authenticating identity |
230
- | `aud` | Target audience (e.g., `"dfos-api"`) |
231
-
232
- The signing mechanics are identical to operation JWS — `ed25519.sign(UTF8(base64url(header) + "." + base64url(payload)), privateKey)`. The key is resolved from the identity chain via `kid` + `sub`.
233
-
234
- ---
235
-
236
- ## Reference Implementation
237
-
238
- A complete reference server is available in the protocol package:
239
-
240
- - [`registry/server.ts`](https://github.com/metalabel/dfos/blob/main/packages/dfos-protocol/src/registry/server.ts) — Hono-based HTTP server implementing all endpoints
241
- - [`registry/store.ts`](https://github.com/metalabel/dfos/blob/main/packages/dfos-protocol/src/registry/store.ts) — In-memory chain store with linear enforcement
242
- - [`openapi.yaml`](https://github.com/metalabel/dfos/blob/main/packages/dfos-protocol/openapi.yaml) — OpenAPI 3.1 machine-readable specification
@@ -1,311 +0,0 @@
1
- import {
2
- MultikeyPublicKey,
3
- decodeMultikey,
4
- verifyContentChain,
5
- verifyIdentityChain
6
- } from "./chunk-VEBMLR37.js";
7
- import {
8
- dagCborCanonicalEncode,
9
- decodeJwsUnsafe
10
- } from "./chunk-ZXXP5W5N.js";
11
-
12
- // src/registry/schemas.ts
13
- import { z } from "zod";
14
- var OperationEntry = z.strictObject({
15
- cid: z.string(),
16
- jwsToken: z.string(),
17
- createdAt: z.string()
18
- });
19
- var PaginatedOperations = z.strictObject({
20
- operations: z.array(OperationEntry),
21
- nextCursor: z.string().nullable()
22
- });
23
- var PaginationParams = z.object({
24
- cursor: z.string().optional(),
25
- limit: z.coerce.number().int().min(1).max(100).default(25)
26
- });
27
- var SubmitIdentityChainRequest = z.strictObject({
28
- chain: z.array(z.string()).min(1)
29
- });
30
- var SubmitIdentityChainResponse = z.strictObject({
31
- did: z.string(),
32
- isDeleted: z.boolean(),
33
- authKeys: z.array(MultikeyPublicKey),
34
- assertKeys: z.array(MultikeyPublicKey),
35
- controllerKeys: z.array(MultikeyPublicKey)
36
- });
37
- var ResolveIdentityResponse = SubmitIdentityChainResponse;
38
- var IdentityOperationsParams = PaginationParams;
39
- var IdentityOperationsResponse = PaginatedOperations;
40
- var SubmitContentChainRequest = z.strictObject({
41
- chain: z.array(z.string()).min(1)
42
- });
43
- var SubmitContentChainResponse = z.strictObject({
44
- contentId: z.string(),
45
- isDeleted: z.boolean(),
46
- currentDocumentCID: z.string().nullable(),
47
- genesisCID: z.string(),
48
- headCID: z.string()
49
- });
50
- var ResolveContentResponse = SubmitContentChainResponse;
51
- var ContentOperationsParams = PaginationParams;
52
- var ContentOperationsResponse = PaginatedOperations;
53
- var ResolveOperationResponse = z.strictObject({
54
- cid: z.string(),
55
- jwsToken: z.string()
56
- });
57
- var RegistryError = z.strictObject({
58
- error: z.string(),
59
- message: z.string()
60
- });
61
-
62
- // src/registry/server.ts
63
- import { Hono } from "hono";
64
-
65
- // src/registry/store.ts
66
- var ChainStore = class {
67
- identityChains = /* @__PURE__ */ new Map();
68
- contentChains = /* @__PURE__ */ new Map();
69
- // --- identityChains ---
70
- getIdentityChain(did) {
71
- return this.identityChains.get(did);
72
- }
73
- /**
74
- * Submit an identity chain. Returns 'accepted' | 'noop' | 'conflict'.
75
- * - accepted: chain was stored or extended
76
- * - noop: submitted chain is same as or prefix of stored chain
77
- * - conflict: submitted chain diverges from stored chain (fork)
78
- */
79
- submitIdentityChain(did, operations) {
80
- return this.submitChain(this.identityChains, did, operations);
81
- }
82
- // --- contentChains ---
83
- getContentChain(contentId) {
84
- return this.contentChains.get(contentId);
85
- }
86
- submitContentChain(contentId, operations) {
87
- return this.submitChain(this.contentChains, contentId, operations);
88
- }
89
- // --- operations (lookup across all chains) ---
90
- getOperation(cid) {
91
- for (const chain of this.identityChains.values()) {
92
- const op = chain.operations.find((o) => o.cid === cid);
93
- if (op) return op;
94
- }
95
- for (const chain of this.contentChains.values()) {
96
- const op = chain.operations.find((o) => o.cid === cid);
97
- if (op) return op;
98
- }
99
- return void 0;
100
- }
101
- // --- shared chain submission logic ---
102
- submitChain(store, id, operations) {
103
- const existing = store.get(id);
104
- if (!existing) {
105
- store.set(id, { operations });
106
- return "accepted";
107
- }
108
- if (operations.length <= existing.operations.length) {
109
- for (let i = 0; i < operations.length; i++) {
110
- if (operations[i].cid !== existing.operations[i].cid) {
111
- return "conflict";
112
- }
113
- }
114
- return "noop";
115
- }
116
- for (let i = 0; i < existing.operations.length; i++) {
117
- if (operations[i].cid !== existing.operations[i].cid) {
118
- return "conflict";
119
- }
120
- }
121
- store.set(id, { operations });
122
- return "accepted";
123
- }
124
- };
125
-
126
- // src/registry/server.ts
127
- var err = (code, message) => ({
128
- error: code,
129
- message
130
- });
131
- var extractOperationEntries = async (chain) => {
132
- const entries = [];
133
- for (const jwsToken of chain) {
134
- const decoded = decodeJwsUnsafe(jwsToken);
135
- if (!decoded) throw new Error("invalid JWS token");
136
- const payload = decoded.payload;
137
- const encoded = await dagCborCanonicalEncode(payload);
138
- entries.push({
139
- cid: encoded.cid.toString(),
140
- jwsToken,
141
- createdAt: payload.createdAt ?? ""
142
- });
143
- }
144
- return entries;
145
- };
146
- var paginate = (operations, cursor, limit) => {
147
- const reversed = [...operations].reverse();
148
- let startIdx = 0;
149
- if (cursor) {
150
- const cursorIdx = reversed.findIndex((op) => op.cid === cursor);
151
- if (cursorIdx >= 0) startIdx = cursorIdx + 1;
152
- }
153
- const page = reversed.slice(startIdx, startIdx + limit);
154
- const hasMore = startIdx + limit < reversed.length;
155
- return {
156
- operations: page,
157
- nextCursor: hasMore ? page[page.length - 1].cid : null
158
- };
159
- };
160
- var paginationParams = (c) => ({
161
- cursor: c.query("cursor"),
162
- limit: Math.min(Math.max(parseInt(c.query("limit") ?? "25"), 1), 100)
163
- });
164
- var createKeyResolver = (store) => async (kid) => {
165
- const hashIdx = kid.indexOf("#");
166
- if (hashIdx < 0) throw new Error(`invalid kid format: ${kid}`);
167
- const did = kid.substring(0, hashIdx);
168
- const keyId = kid.substring(hashIdx + 1);
169
- const identityChain = store.getIdentityChain(did);
170
- if (!identityChain) throw new Error(`identity not found: ${did}`);
171
- const identity = await verifyIdentityChain({
172
- didPrefix: "did:dfos",
173
- log: identityChain.operations.map((o) => o.jwsToken)
174
- });
175
- const allKeys = [...identity.authKeys, ...identity.assertKeys, ...identity.controllerKeys];
176
- const key = allKeys.find((k) => k.id === keyId);
177
- if (!key) throw new Error(`key not found: ${keyId}`);
178
- return decodeMultikey(key.publicKeyMultibase).keyBytes;
179
- };
180
- var createRegistryServer = (store = new ChainStore()) => {
181
- const app = new Hono();
182
- const resolveKey = createKeyResolver(store);
183
- app.post("/identities", async (c) => {
184
- const body = await c.req.json();
185
- if (!body.chain || !Array.isArray(body.chain) || body.chain.length === 0) {
186
- return c.json(err("BAD_REQUEST", "chain must be a non-empty array of JWS tokens"), 400);
187
- }
188
- let verified;
189
- try {
190
- verified = await verifyIdentityChain({
191
- didPrefix: "did:dfos",
192
- log: body.chain
193
- });
194
- } catch (e) {
195
- return c.json(err("BAD_REQUEST", `chain verification failed: ${e.message}`), 400);
196
- }
197
- const operations = await extractOperationEntries(body.chain);
198
- const result = store.submitIdentityChain(verified.did, operations);
199
- if (result === "conflict") {
200
- return c.json(err("CONFLICT", "submitted chain conflicts with stored chain"), 409);
201
- }
202
- return c.json(
203
- {
204
- did: verified.did,
205
- isDeleted: verified.isDeleted,
206
- authKeys: verified.authKeys,
207
- assertKeys: verified.assertKeys,
208
- controllerKeys: verified.controllerKeys
209
- },
210
- result === "accepted" ? 201 : 200
211
- );
212
- });
213
- app.get("/identities/:did", async (c) => {
214
- const did = c.req.param("did");
215
- const chain = store.getIdentityChain(did);
216
- if (!chain) return c.json(err("NOT_FOUND", "identity not found"), 404);
217
- const verified = await verifyIdentityChain({
218
- didPrefix: "did:dfos",
219
- log: chain.operations.map((o) => o.jwsToken)
220
- });
221
- return c.json({
222
- did: verified.did,
223
- isDeleted: verified.isDeleted,
224
- authKeys: verified.authKeys,
225
- assertKeys: verified.assertKeys,
226
- controllerKeys: verified.controllerKeys
227
- });
228
- });
229
- app.get("/identities/:did/operations", (c) => {
230
- const did = c.req.param("did");
231
- const chain = store.getIdentityChain(did);
232
- if (!chain) return c.json(err("NOT_FOUND", "identity not found"), 404);
233
- const { cursor, limit } = paginationParams(c.req);
234
- return c.json(paginate(chain.operations, cursor, limit));
235
- });
236
- app.post("/content", async (c) => {
237
- const body = await c.req.json();
238
- if (!body.chain || !Array.isArray(body.chain) || body.chain.length === 0) {
239
- return c.json(err("BAD_REQUEST", "chain must be a non-empty array of JWS tokens"), 400);
240
- }
241
- const operations = await extractOperationEntries(body.chain);
242
- let verified;
243
- try {
244
- verified = await verifyContentChain({ log: body.chain, resolveKey });
245
- } catch (e) {
246
- return c.json(err("BAD_REQUEST", `chain verification failed: ${e.message}`), 400);
247
- }
248
- const result = store.submitContentChain(verified.contentId, operations);
249
- if (result === "conflict") {
250
- return c.json(err("CONFLICT", "submitted chain conflicts with stored chain"), 409);
251
- }
252
- return c.json(
253
- {
254
- contentId: verified.contentId,
255
- isDeleted: verified.isDeleted,
256
- currentDocumentCID: verified.currentDocumentCID,
257
- genesisCID: verified.genesisCID,
258
- headCID: verified.headCID
259
- },
260
- result === "accepted" ? 201 : 200
261
- );
262
- });
263
- app.get("/content/:contentId", (c) => {
264
- const contentId = c.req.param("contentId");
265
- const chain = store.getContentChain(contentId);
266
- if (!chain) return c.json(err("NOT_FOUND", "content not found"), 404);
267
- const genesis = chain.operations[0];
268
- const head = chain.operations[chain.operations.length - 1];
269
- const headDecoded = decodeJwsUnsafe(head.jwsToken);
270
- const headPayload = headDecoded?.payload;
271
- const headType = headPayload?.type;
272
- return c.json({
273
- contentId,
274
- isDeleted: headType === "delete",
275
- currentDocumentCID: headType === "delete" ? null : headPayload?.documentCID ?? null,
276
- genesisCID: genesis.cid,
277
- headCID: head.cid
278
- });
279
- });
280
- app.get("/content/:contentId/operations", (c) => {
281
- const contentId = c.req.param("contentId");
282
- const chain = store.getContentChain(contentId);
283
- if (!chain) return c.json(err("NOT_FOUND", "content not found"), 404);
284
- const { cursor, limit } = paginationParams(c.req);
285
- return c.json(paginate(chain.operations, cursor, limit));
286
- });
287
- app.get("/operations/:cid", (c) => {
288
- const cid = c.req.param("cid");
289
- const op = store.getOperation(cid);
290
- if (!op) return c.json(err("NOT_FOUND", "operation not found"), 404);
291
- return c.json({ cid: op.cid, jwsToken: op.jwsToken });
292
- });
293
- return { app, store };
294
- };
295
-
296
- export {
297
- SubmitIdentityChainRequest,
298
- SubmitIdentityChainResponse,
299
- ResolveIdentityResponse,
300
- IdentityOperationsParams,
301
- IdentityOperationsResponse,
302
- SubmitContentChainRequest,
303
- SubmitContentChainResponse,
304
- ResolveContentResponse,
305
- ContentOperationsParams,
306
- ContentOperationsResponse,
307
- ResolveOperationResponse,
308
- RegistryError,
309
- ChainStore,
310
- createRegistryServer
311
- };
@@ -1,143 +0,0 @@
1
- import { z } from 'zod';
2
- import * as hono_types from 'hono/types';
3
- import { Hono } from 'hono';
4
-
5
- declare const OperationEntry: z.ZodObject<{
6
- cid: z.ZodString;
7
- jwsToken: z.ZodString;
8
- createdAt: z.ZodString;
9
- }, z.core.$strict>;
10
- type OperationEntry = z.infer<typeof OperationEntry>;
11
- declare const PaginationParams: z.ZodObject<{
12
- cursor: z.ZodOptional<z.ZodString>;
13
- limit: z.ZodDefault<z.ZodCoercedNumber<unknown>>;
14
- }, z.core.$strip>;
15
- type PaginationParams = z.infer<typeof PaginationParams>;
16
- declare const SubmitIdentityChainRequest: z.ZodObject<{
17
- chain: z.ZodArray<z.ZodString>;
18
- }, z.core.$strict>;
19
- type SubmitIdentityChainRequest = z.infer<typeof SubmitIdentityChainRequest>;
20
- declare const SubmitIdentityChainResponse: z.ZodObject<{
21
- did: z.ZodString;
22
- isDeleted: z.ZodBoolean;
23
- authKeys: z.ZodArray<z.ZodObject<{
24
- id: z.ZodString;
25
- type: z.ZodLiteral<"Multikey">;
26
- publicKeyMultibase: z.ZodString;
27
- }, z.core.$strict>>;
28
- assertKeys: z.ZodArray<z.ZodObject<{
29
- id: z.ZodString;
30
- type: z.ZodLiteral<"Multikey">;
31
- publicKeyMultibase: z.ZodString;
32
- }, z.core.$strict>>;
33
- controllerKeys: z.ZodArray<z.ZodObject<{
34
- id: z.ZodString;
35
- type: z.ZodLiteral<"Multikey">;
36
- publicKeyMultibase: z.ZodString;
37
- }, z.core.$strict>>;
38
- }, z.core.$strict>;
39
- type SubmitIdentityChainResponse = z.infer<typeof SubmitIdentityChainResponse>;
40
- declare const ResolveIdentityResponse: z.ZodObject<{
41
- did: z.ZodString;
42
- isDeleted: z.ZodBoolean;
43
- authKeys: z.ZodArray<z.ZodObject<{
44
- id: z.ZodString;
45
- type: z.ZodLiteral<"Multikey">;
46
- publicKeyMultibase: z.ZodString;
47
- }, z.core.$strict>>;
48
- assertKeys: z.ZodArray<z.ZodObject<{
49
- id: z.ZodString;
50
- type: z.ZodLiteral<"Multikey">;
51
- publicKeyMultibase: z.ZodString;
52
- }, z.core.$strict>>;
53
- controllerKeys: z.ZodArray<z.ZodObject<{
54
- id: z.ZodString;
55
- type: z.ZodLiteral<"Multikey">;
56
- publicKeyMultibase: z.ZodString;
57
- }, z.core.$strict>>;
58
- }, z.core.$strict>;
59
- type ResolveIdentityResponse = SubmitIdentityChainResponse;
60
- declare const IdentityOperationsParams: z.ZodObject<{
61
- cursor: z.ZodOptional<z.ZodString>;
62
- limit: z.ZodDefault<z.ZodCoercedNumber<unknown>>;
63
- }, z.core.$strip>;
64
- declare const IdentityOperationsResponse: z.ZodObject<{
65
- operations: z.ZodArray<z.ZodObject<{
66
- cid: z.ZodString;
67
- jwsToken: z.ZodString;
68
- createdAt: z.ZodString;
69
- }, z.core.$strict>>;
70
- nextCursor: z.ZodNullable<z.ZodString>;
71
- }, z.core.$strict>;
72
- type IdentityOperationsResponse = z.infer<typeof IdentityOperationsResponse>;
73
- declare const SubmitContentChainRequest: z.ZodObject<{
74
- chain: z.ZodArray<z.ZodString>;
75
- }, z.core.$strict>;
76
- type SubmitContentChainRequest = z.infer<typeof SubmitContentChainRequest>;
77
- declare const SubmitContentChainResponse: z.ZodObject<{
78
- contentId: z.ZodString;
79
- isDeleted: z.ZodBoolean;
80
- currentDocumentCID: z.ZodNullable<z.ZodString>;
81
- genesisCID: z.ZodString;
82
- headCID: z.ZodString;
83
- }, z.core.$strict>;
84
- type SubmitContentChainResponse = z.infer<typeof SubmitContentChainResponse>;
85
- declare const ResolveContentResponse: z.ZodObject<{
86
- contentId: z.ZodString;
87
- isDeleted: z.ZodBoolean;
88
- currentDocumentCID: z.ZodNullable<z.ZodString>;
89
- genesisCID: z.ZodString;
90
- headCID: z.ZodString;
91
- }, z.core.$strict>;
92
- type ResolveContentResponse = SubmitContentChainResponse;
93
- declare const ContentOperationsParams: z.ZodObject<{
94
- cursor: z.ZodOptional<z.ZodString>;
95
- limit: z.ZodDefault<z.ZodCoercedNumber<unknown>>;
96
- }, z.core.$strip>;
97
- declare const ContentOperationsResponse: z.ZodObject<{
98
- operations: z.ZodArray<z.ZodObject<{
99
- cid: z.ZodString;
100
- jwsToken: z.ZodString;
101
- createdAt: z.ZodString;
102
- }, z.core.$strict>>;
103
- nextCursor: z.ZodNullable<z.ZodString>;
104
- }, z.core.$strict>;
105
- type ContentOperationsResponse = z.infer<typeof ContentOperationsResponse>;
106
- declare const ResolveOperationResponse: z.ZodObject<{
107
- cid: z.ZodString;
108
- jwsToken: z.ZodString;
109
- }, z.core.$strict>;
110
- type ResolveOperationResponse = z.infer<typeof ResolveOperationResponse>;
111
- declare const RegistryError: z.ZodObject<{
112
- error: z.ZodString;
113
- message: z.ZodString;
114
- }, z.core.$strict>;
115
- type RegistryError = z.infer<typeof RegistryError>;
116
-
117
- interface StoredChain {
118
- /** Ordered array of operations, genesis first */
119
- operations: OperationEntry[];
120
- }
121
- declare class ChainStore {
122
- private identityChains;
123
- private contentChains;
124
- getIdentityChain(did: string): StoredChain | undefined;
125
- /**
126
- * Submit an identity chain. Returns 'accepted' | 'noop' | 'conflict'.
127
- * - accepted: chain was stored or extended
128
- * - noop: submitted chain is same as or prefix of stored chain
129
- * - conflict: submitted chain diverges from stored chain (fork)
130
- */
131
- submitIdentityChain(did: string, operations: OperationEntry[]): 'accepted' | 'noop' | 'conflict';
132
- getContentChain(contentId: string): StoredChain | undefined;
133
- submitContentChain(contentId: string, operations: OperationEntry[]): 'accepted' | 'noop' | 'conflict';
134
- getOperation(cid: string): OperationEntry | undefined;
135
- private submitChain;
136
- }
137
-
138
- declare const createRegistryServer: (store?: ChainStore) => {
139
- app: Hono<hono_types.BlankEnv, hono_types.BlankSchema, "/">;
140
- store: ChainStore;
141
- };
142
-
143
- export { ChainStore, ContentOperationsParams, ContentOperationsResponse, IdentityOperationsParams, IdentityOperationsResponse, OperationEntry, PaginationParams, RegistryError, ResolveContentResponse, ResolveIdentityResponse, ResolveOperationResponse, type StoredChain, SubmitContentChainRequest, SubmitContentChainResponse, SubmitIdentityChainRequest, SubmitIdentityChainResponse, createRegistryServer };