@proveanything/smartlinks 1.16.6 → 1.17.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/dist/api/attestations.d.ts +39 -10
- package/dist/api/attestations.js +42 -9
- package/dist/api/index.d.ts +2 -0
- package/dist/api/index.js +2 -0
- package/dist/api/integrations.d.ts +28 -0
- package/dist/api/integrations.js +82 -0
- package/dist/api/proof.js +3 -0
- package/dist/api/secrets.d.ts +15 -0
- package/dist/api/secrets.js +52 -0
- package/dist/docs/API_SUMMARY.md +284 -3
- package/dist/docs/attestations.md +19 -0
- package/dist/docs/integrations.md +141 -0
- package/dist/docs/proof-share-grants.md +78 -5
- package/dist/openapi.yaml +352 -1
- package/dist/types/attestations.d.ts +51 -4
- package/dist/types/index.d.ts +1 -0
- package/dist/types/index.js +1 -0
- package/dist/types/integrations.d.ts +136 -0
- package/dist/types/integrations.js +10 -0
- package/dist/types/proof.d.ts +22 -2
- package/docs/API_SUMMARY.md +284 -3
- package/docs/attestations.md +19 -0
- package/docs/integrations.md +141 -0
- package/docs/proof-share-grants.md +78 -5
- package/openapi.yaml +352 -1
- package/package.json +2 -2
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import type { Attestation, CreateAttestationInput, ListAttestationsParams, ListAttestationsResponse, AttestationSummaryParams, AttestationSummaryResponse, PublicAttestationSummaryResponse, AttestationLatestParams, AttestationLatestResponse, PublicAttestationLatestResponse, AttestationVerifyParams, ChainVerifyResult, AttestationTreeSummaryParams, AttestationTreeSummaryResponse, PublicAttestationTreeSummaryResponse, AttestationTreeLatestParams, AttestationTreeLatestResponse, PublicAttestationTreeLatestResponse, PublicListAttestationsResponse, OwnerAttestationInput, CreateOwnerAttestationResponse } from "../types/attestations";
|
|
1
|
+
import type { Attestation, CreateAttestationInput, ListAttestationsParams, ListAttestationsResponse, AttestationSummaryParams, AttestationSummaryResponse, PublicAttestationSummaryResponse, AttestationLatestParams, AttestationLatestResponse, PublicAttestationLatestResponse, AttestationVerifyParams, ChainVerifyResult, AttestationTreeSummaryParams, AttestationTreeSummaryResponse, PublicAttestationTreeSummaryResponse, AttestationTreeLatestParams, AttestationTreeLatestResponse, PublicAttestationTreeLatestResponse, PublicListAttestationsResponse, OwnerAttestationInput, CreateOwnerAttestationResponse, ModerateAttestationInput, ModerateAttestationResponse } from "../types/attestations";
|
|
2
2
|
/**
|
|
3
3
|
* Postgres-backed Attestations API (v2).
|
|
4
4
|
*
|
|
@@ -13,9 +13,11 @@ import type { Attestation, CreateAttestationInput, ListAttestationsParams, ListA
|
|
|
13
13
|
* admin session or bearer token. All three data zones are returned, and the
|
|
14
14
|
* business can write any zone/visibility ({@link create}).
|
|
15
15
|
* - **Public** endpoints (`/public/collection/:id/attestations`) are read-only,
|
|
16
|
-
* EXCEPT {@link publicCreate}
|
|
17
|
-
*
|
|
18
|
-
* zone)
|
|
16
|
+
* EXCEPT {@link publicCreate} (the proof OWNER, or a `contribute`-grant holder,
|
|
17
|
+
* authors an attestation — value + ownerData, visibility public|owner, never the
|
|
18
|
+
* admin zone) and {@link moderate} (owner/admin approves or rejects a contributed
|
|
19
|
+
* record). Owner elevation is via `Authorization: Bearer <Firebase ID token>`;
|
|
20
|
+
* contributor access via a grant token set with `setGrantToken`.
|
|
19
21
|
*
|
|
20
22
|
* @see docs/attestations.md
|
|
21
23
|
*/
|
|
@@ -211,22 +213,49 @@ export declare namespace attestations {
|
|
|
211
213
|
*/
|
|
212
214
|
function publicList(collectionId: string, params: ListAttestationsParams): Promise<PublicListAttestationsResponse>;
|
|
213
215
|
/**
|
|
214
|
-
* Create
|
|
215
|
-
*
|
|
216
|
-
* (identity,
|
|
217
|
-
*
|
|
218
|
-
*
|
|
219
|
-
*
|
|
216
|
+
* Create a public attestation — the counterpart to the admin {@link create}.
|
|
217
|
+
* Authorised two ways, same call (the server decides from the request):
|
|
218
|
+
* 1. the proof OWNER (identity, via `Authorization: Bearer <Firebase ID token>`)
|
|
219
|
+
* adds an attestation to their own item; or
|
|
220
|
+
* 2. a holder of a `contribute`-scope grant adds one — call
|
|
221
|
+
* {@link setGrantToken} with the grant token first; for a public-link
|
|
222
|
+
* (anonymous) grant, pass `guestName` for attribution.
|
|
223
|
+
*
|
|
224
|
+
* Guardrails (server-enforced): `value` + `ownerData` only (`adminData` dropped),
|
|
225
|
+
* `visibility` clamped to `'public' | 'owner'`, `authorId`/`grantId` server-stamped.
|
|
226
|
+
* If the contribute grant was issued with `moderate: true`, the returned record
|
|
227
|
+
* has `moderationStatus: 'pending'` — held to the owner until {@link moderate}.
|
|
228
|
+
* The record joins the same tamper-evident hash chain.
|
|
220
229
|
* POST /public/collection/:collectionId/attestations
|
|
221
230
|
* ```ts
|
|
231
|
+
* // Owner:
|
|
222
232
|
* await attestations.publicCreate('coll_123', {
|
|
223
233
|
* subjectType: 'proof', subjectId: 'proof_1',
|
|
224
234
|
* attestationType: 'condition-report',
|
|
225
235
|
* value: { grade: 'excellent' }, visibility: 'public',
|
|
226
236
|
* })
|
|
237
|
+
* // Contributor on a shared link:
|
|
238
|
+
* setGrantToken(shareToken)
|
|
239
|
+
* await attestations.publicCreate('coll_123', {
|
|
240
|
+
* subjectType: 'proof', subjectId: 'proof_1',
|
|
241
|
+
* attestationType: 'photo', value: { url }, visibility: 'public',
|
|
242
|
+
* guestName: 'Sam',
|
|
243
|
+
* })
|
|
227
244
|
* ```
|
|
228
245
|
*/
|
|
229
246
|
function publicCreate(collectionId: string, data: OwnerAttestationInput): Promise<CreateOwnerAttestationResponse>;
|
|
247
|
+
/**
|
|
248
|
+
* Moderate a contributed attestation (proof OWNER by identity, or collection
|
|
249
|
+
* admin). `'approve'` releases it to its declared visibility; `'reject'` keeps
|
|
250
|
+
* it author + admin only. Only the `moderationStatus` changes — the hashed fact
|
|
251
|
+
* and its chain are untouched. Find pending items with
|
|
252
|
+
* {@link publicList} + `moderationStatus: 'pending'`.
|
|
253
|
+
* POST /public/collection/:collectionId/attestations/:attestationId/moderate
|
|
254
|
+
* ```ts
|
|
255
|
+
* await attestations.moderate('coll_123', 'att_uuid', { decision: 'approve' })
|
|
256
|
+
* ```
|
|
257
|
+
*/
|
|
258
|
+
function moderate(collectionId: string, attestationId: string, input: ModerateAttestationInput): Promise<ModerateAttestationResponse>;
|
|
230
259
|
/**
|
|
231
260
|
* Time-series summary (public).
|
|
232
261
|
*
|
package/dist/api/attestations.js
CHANGED
|
@@ -26,9 +26,11 @@ function buildAttestationQuery(params) {
|
|
|
26
26
|
* admin session or bearer token. All three data zones are returned, and the
|
|
27
27
|
* business can write any zone/visibility ({@link create}).
|
|
28
28
|
* - **Public** endpoints (`/public/collection/:id/attestations`) are read-only,
|
|
29
|
-
* EXCEPT {@link publicCreate}
|
|
30
|
-
*
|
|
31
|
-
* zone)
|
|
29
|
+
* EXCEPT {@link publicCreate} (the proof OWNER, or a `contribute`-grant holder,
|
|
30
|
+
* authors an attestation — value + ownerData, visibility public|owner, never the
|
|
31
|
+
* admin zone) and {@link moderate} (owner/admin approves or rejects a contributed
|
|
32
|
+
* record). Owner elevation is via `Authorization: Bearer <Firebase ID token>`;
|
|
33
|
+
* contributor access via a grant token set with `setGrantToken`.
|
|
32
34
|
*
|
|
33
35
|
* @see docs/attestations.md
|
|
34
36
|
*/
|
|
@@ -277,19 +279,34 @@ export var attestations;
|
|
|
277
279
|
}
|
|
278
280
|
attestations.publicList = publicList;
|
|
279
281
|
/**
|
|
280
|
-
* Create
|
|
281
|
-
*
|
|
282
|
-
* (identity,
|
|
283
|
-
*
|
|
284
|
-
*
|
|
285
|
-
*
|
|
282
|
+
* Create a public attestation — the counterpart to the admin {@link create}.
|
|
283
|
+
* Authorised two ways, same call (the server decides from the request):
|
|
284
|
+
* 1. the proof OWNER (identity, via `Authorization: Bearer <Firebase ID token>`)
|
|
285
|
+
* adds an attestation to their own item; or
|
|
286
|
+
* 2. a holder of a `contribute`-scope grant adds one — call
|
|
287
|
+
* {@link setGrantToken} with the grant token first; for a public-link
|
|
288
|
+
* (anonymous) grant, pass `guestName` for attribution.
|
|
289
|
+
*
|
|
290
|
+
* Guardrails (server-enforced): `value` + `ownerData` only (`adminData` dropped),
|
|
291
|
+
* `visibility` clamped to `'public' | 'owner'`, `authorId`/`grantId` server-stamped.
|
|
292
|
+
* If the contribute grant was issued with `moderate: true`, the returned record
|
|
293
|
+
* has `moderationStatus: 'pending'` — held to the owner until {@link moderate}.
|
|
294
|
+
* The record joins the same tamper-evident hash chain.
|
|
286
295
|
* POST /public/collection/:collectionId/attestations
|
|
287
296
|
* ```ts
|
|
297
|
+
* // Owner:
|
|
288
298
|
* await attestations.publicCreate('coll_123', {
|
|
289
299
|
* subjectType: 'proof', subjectId: 'proof_1',
|
|
290
300
|
* attestationType: 'condition-report',
|
|
291
301
|
* value: { grade: 'excellent' }, visibility: 'public',
|
|
292
302
|
* })
|
|
303
|
+
* // Contributor on a shared link:
|
|
304
|
+
* setGrantToken(shareToken)
|
|
305
|
+
* await attestations.publicCreate('coll_123', {
|
|
306
|
+
* subjectType: 'proof', subjectId: 'proof_1',
|
|
307
|
+
* attestationType: 'photo', value: { url }, visibility: 'public',
|
|
308
|
+
* guestName: 'Sam',
|
|
309
|
+
* })
|
|
293
310
|
* ```
|
|
294
311
|
*/
|
|
295
312
|
async function publicCreate(collectionId, data) {
|
|
@@ -297,6 +314,22 @@ export var attestations;
|
|
|
297
314
|
return post(path, data);
|
|
298
315
|
}
|
|
299
316
|
attestations.publicCreate = publicCreate;
|
|
317
|
+
/**
|
|
318
|
+
* Moderate a contributed attestation (proof OWNER by identity, or collection
|
|
319
|
+
* admin). `'approve'` releases it to its declared visibility; `'reject'` keeps
|
|
320
|
+
* it author + admin only. Only the `moderationStatus` changes — the hashed fact
|
|
321
|
+
* and its chain are untouched. Find pending items with
|
|
322
|
+
* {@link publicList} + `moderationStatus: 'pending'`.
|
|
323
|
+
* POST /public/collection/:collectionId/attestations/:attestationId/moderate
|
|
324
|
+
* ```ts
|
|
325
|
+
* await attestations.moderate('coll_123', 'att_uuid', { decision: 'approve' })
|
|
326
|
+
* ```
|
|
327
|
+
*/
|
|
328
|
+
async function moderate(collectionId, attestationId, input) {
|
|
329
|
+
const path = `/public/collection/${encodeURIComponent(collectionId)}/attestations/${encodeURIComponent(attestationId)}/moderate`;
|
|
330
|
+
return post(path, input);
|
|
331
|
+
}
|
|
332
|
+
attestations.moderate = moderate;
|
|
300
333
|
/**
|
|
301
334
|
* Time-series summary (public).
|
|
302
335
|
*
|
package/dist/api/index.d.ts
CHANGED
|
@@ -37,6 +37,8 @@ export { containers } from "./containers";
|
|
|
37
37
|
export { lots } from "./lots";
|
|
38
38
|
export { loyalty } from "./loyalty";
|
|
39
39
|
export { translations } from "./translations";
|
|
40
|
+
export { integrations } from "./integrations";
|
|
41
|
+
export { secrets } from "./secrets";
|
|
40
42
|
export { config } from "./config";
|
|
41
43
|
export { http } from "./http";
|
|
42
44
|
export { navigation } from "./navigation";
|
package/dist/api/index.js
CHANGED
|
@@ -40,6 +40,8 @@ export { containers } from "./containers";
|
|
|
40
40
|
export { lots } from "./lots";
|
|
41
41
|
export { loyalty } from "./loyalty";
|
|
42
42
|
export { translations } from "./translations";
|
|
43
|
+
export { integrations } from "./integrations";
|
|
44
|
+
export { secrets } from "./secrets";
|
|
43
45
|
export { config } from "./config";
|
|
44
46
|
export { http } from "./http";
|
|
45
47
|
export { navigation } from "./navigation";
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
import type { IntegrationFlow, CreateFlowInput, UpdateFlowInput, ListFlowsQuery, FlowList, RunFlowInput, RunFlowResult, RunFlowSummary, RunFlowEnqueued } from "../types/integrations";
|
|
2
|
+
export declare namespace integrations {
|
|
3
|
+
/** List flows in a collection. GET /integrations/flows */
|
|
4
|
+
function listFlows(collectionId: string, query?: ListFlowsQuery): Promise<FlowList>;
|
|
5
|
+
/** Create a flow. POST /integrations/flows */
|
|
6
|
+
function createFlow(collectionId: string, input: CreateFlowInput): Promise<IntegrationFlow>;
|
|
7
|
+
/** Get one flow. GET /integrations/flows/:id */
|
|
8
|
+
function getFlow(collectionId: string, id: string): Promise<IntegrationFlow>;
|
|
9
|
+
/** Update whitelisted fields. PUT /integrations/flows/:id */
|
|
10
|
+
function updateFlow(collectionId: string, id: string, input: UpdateFlowInput): Promise<IntegrationFlow>;
|
|
11
|
+
/** Soft-delete a flow. DELETE /integrations/flows/:id */
|
|
12
|
+
function deleteFlow(collectionId: string, id: string): Promise<{
|
|
13
|
+
deleted: boolean;
|
|
14
|
+
}>;
|
|
15
|
+
/**
|
|
16
|
+
* Run a flow now. POST /integrations/flows/:id/run
|
|
17
|
+
* - inline (default): resolves and returns the run summary.
|
|
18
|
+
* - options.async: enqueue on the worker, returns { enqueued: true }.
|
|
19
|
+
* Pass options.entityId to run for a single source entity.
|
|
20
|
+
*/
|
|
21
|
+
function runFlow(collectionId: string, id: string, options?: RunFlowInput & {
|
|
22
|
+
async?: boolean;
|
|
23
|
+
}): Promise<RunFlowResult>;
|
|
24
|
+
/** Type guard: the run executed inline and returned a summary. */
|
|
25
|
+
function isRunSummary(r: RunFlowResult): r is RunFlowSummary;
|
|
26
|
+
/** Type guard: the run was enqueued (async). */
|
|
27
|
+
function isRunEnqueued(r: RunFlowResult): r is RunFlowEnqueued;
|
|
28
|
+
}
|
|
@@ -0,0 +1,82 @@
|
|
|
1
|
+
// src/api/integrations.ts
|
|
2
|
+
//
|
|
3
|
+
// Integration flow management + execution. Flows model input/output pipelines
|
|
4
|
+
// (inbound: fetch external -> write entity; outbound: read entity -> transform ->
|
|
5
|
+
// send). Credentials live in the secret store (see the `secrets` namespace); a flow
|
|
6
|
+
// only carries an opaque credentialRef in config.connection.auth.
|
|
7
|
+
//
|
|
8
|
+
// Endpoints: /admin/collection/:collectionId/integrations/flows
|
|
9
|
+
var __rest = (this && this.__rest) || function (s, e) {
|
|
10
|
+
var t = {};
|
|
11
|
+
for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p) && e.indexOf(p) < 0)
|
|
12
|
+
t[p] = s[p];
|
|
13
|
+
if (s != null && typeof Object.getOwnPropertySymbols === "function")
|
|
14
|
+
for (var i = 0, p = Object.getOwnPropertySymbols(s); i < p.length; i++) {
|
|
15
|
+
if (e.indexOf(p[i]) < 0 && Object.prototype.propertyIsEnumerable.call(s, p[i]))
|
|
16
|
+
t[p[i]] = s[p[i]];
|
|
17
|
+
}
|
|
18
|
+
return t;
|
|
19
|
+
};
|
|
20
|
+
import { request, post, put, del } from "../http";
|
|
21
|
+
function enc(v) { return encodeURIComponent(v); }
|
|
22
|
+
function encodeQuery(params = {}) {
|
|
23
|
+
const search = new URLSearchParams();
|
|
24
|
+
for (const [key, value] of Object.entries(params)) {
|
|
25
|
+
if (value === undefined || value === null || value === "")
|
|
26
|
+
continue;
|
|
27
|
+
search.set(key, typeof value === "boolean" ? (value ? "true" : "false") : String(value));
|
|
28
|
+
}
|
|
29
|
+
const qs = search.toString();
|
|
30
|
+
return qs ? `?${qs}` : "";
|
|
31
|
+
}
|
|
32
|
+
export var integrations;
|
|
33
|
+
(function (integrations) {
|
|
34
|
+
const base = (collectionId) => `/admin/collection/${enc(collectionId)}/integrations/flows`;
|
|
35
|
+
/** List flows in a collection. GET /integrations/flows */
|
|
36
|
+
async function listFlows(collectionId, query = {}) {
|
|
37
|
+
return request(`${base(collectionId)}${encodeQuery(query)}`);
|
|
38
|
+
}
|
|
39
|
+
integrations.listFlows = listFlows;
|
|
40
|
+
/** Create a flow. POST /integrations/flows */
|
|
41
|
+
async function createFlow(collectionId, input) {
|
|
42
|
+
return post(base(collectionId), input);
|
|
43
|
+
}
|
|
44
|
+
integrations.createFlow = createFlow;
|
|
45
|
+
/** Get one flow. GET /integrations/flows/:id */
|
|
46
|
+
async function getFlow(collectionId, id) {
|
|
47
|
+
return request(`${base(collectionId)}/${enc(id)}`);
|
|
48
|
+
}
|
|
49
|
+
integrations.getFlow = getFlow;
|
|
50
|
+
/** Update whitelisted fields. PUT /integrations/flows/:id */
|
|
51
|
+
async function updateFlow(collectionId, id, input) {
|
|
52
|
+
return put(`${base(collectionId)}/${enc(id)}`, input);
|
|
53
|
+
}
|
|
54
|
+
integrations.updateFlow = updateFlow;
|
|
55
|
+
/** Soft-delete a flow. DELETE /integrations/flows/:id */
|
|
56
|
+
async function deleteFlow(collectionId, id) {
|
|
57
|
+
return del(`${base(collectionId)}/${enc(id)}`);
|
|
58
|
+
}
|
|
59
|
+
integrations.deleteFlow = deleteFlow;
|
|
60
|
+
/**
|
|
61
|
+
* Run a flow now. POST /integrations/flows/:id/run
|
|
62
|
+
* - inline (default): resolves and returns the run summary.
|
|
63
|
+
* - options.async: enqueue on the worker, returns { enqueued: true }.
|
|
64
|
+
* Pass options.entityId to run for a single source entity.
|
|
65
|
+
*/
|
|
66
|
+
async function runFlow(collectionId, id, options = {}) {
|
|
67
|
+
const { async: runAsync } = options, body = __rest(options, ["async"]);
|
|
68
|
+
const qs = runAsync ? "?async=true" : "";
|
|
69
|
+
return post(`${base(collectionId)}/${enc(id)}/run${qs}`, body);
|
|
70
|
+
}
|
|
71
|
+
integrations.runFlow = runFlow;
|
|
72
|
+
/** Type guard: the run executed inline and returned a summary. */
|
|
73
|
+
function isRunSummary(r) {
|
|
74
|
+
return r.status !== undefined;
|
|
75
|
+
}
|
|
76
|
+
integrations.isRunSummary = isRunSummary;
|
|
77
|
+
/** Type guard: the run was enqueued (async). */
|
|
78
|
+
function isRunEnqueued(r) {
|
|
79
|
+
return r.enqueued === true;
|
|
80
|
+
}
|
|
81
|
+
integrations.isRunEnqueued = isRunEnqueued;
|
|
82
|
+
})(integrations || (integrations = {}));
|
package/dist/api/proof.js
CHANGED
|
@@ -222,6 +222,9 @@ export var proof;
|
|
|
222
222
|
body.audience = options.audience;
|
|
223
223
|
if (options.expiresAt)
|
|
224
224
|
body.expiresAt = options.expiresAt instanceof Date ? options.expiresAt.toISOString() : options.expiresAt;
|
|
225
|
+
// Only applied server-side when scope includes 'contribute'.
|
|
226
|
+
if (options.moderate !== undefined)
|
|
227
|
+
body.moderate = options.moderate;
|
|
225
228
|
return post(grantBase(collectionId, productId, proofId), body);
|
|
226
229
|
}
|
|
227
230
|
proof.createGrant = createGrant;
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import type { SecretMeta, SecretList, SetSecretInput, SetSecretResult, ListSecretsQuery } from "../types/integrations";
|
|
2
|
+
export declare namespace secrets {
|
|
3
|
+
/** List secrets as refs + masked hints + metadata (never values). GET /secrets */
|
|
4
|
+
function list(collectionId: string, query?: ListSecretsQuery): Promise<SecretList>;
|
|
5
|
+
/** Create a secret. POST /secrets → { ref, hint }. Store the ref on a flow. */
|
|
6
|
+
function set(collectionId: string, input: SetSecretInput): Promise<SetSecretResult>;
|
|
7
|
+
/** Metadata for one secret (never the value). GET /secrets/:ref */
|
|
8
|
+
function get(collectionId: string, ref: string): Promise<SecretMeta>;
|
|
9
|
+
/** Rotate/update a secret's value (and optionally name/purpose). PUT /secrets/:ref → { ref, hint } */
|
|
10
|
+
function rotate(collectionId: string, ref: string, input: SetSecretInput): Promise<SetSecretResult>;
|
|
11
|
+
/** Soft-delete a secret. DELETE /secrets/:ref */
|
|
12
|
+
function remove(collectionId: string, ref: string): Promise<{
|
|
13
|
+
deleted: boolean;
|
|
14
|
+
}>;
|
|
15
|
+
}
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
// src/api/secrets.ts
|
|
2
|
+
//
|
|
3
|
+
// Sealed-secret store — the credentials that back integration flows and other
|
|
4
|
+
// server-side handlers. WRITE-ONLY from the client: you can set, rotate, list
|
|
5
|
+
// (refs + masked hints + metadata) and delete, but a value NEVER comes back over the
|
|
6
|
+
// API. It is sealed at rest and resolved server-side only, at execution time.
|
|
7
|
+
//
|
|
8
|
+
// Typical use: `set` a credential, take the returned `ref`, and put it on a flow's
|
|
9
|
+
// config.connection.auth.credentialRef.
|
|
10
|
+
//
|
|
11
|
+
// Endpoints: /admin/collection/:collectionId/secrets
|
|
12
|
+
import { request, post, put, del } from "../http";
|
|
13
|
+
function enc(v) { return encodeURIComponent(v); }
|
|
14
|
+
function encodeQuery(params = {}) {
|
|
15
|
+
const search = new URLSearchParams();
|
|
16
|
+
for (const [key, value] of Object.entries(params)) {
|
|
17
|
+
if (value === undefined || value === null || value === "")
|
|
18
|
+
continue;
|
|
19
|
+
search.set(key, String(value));
|
|
20
|
+
}
|
|
21
|
+
const qs = search.toString();
|
|
22
|
+
return qs ? `?${qs}` : "";
|
|
23
|
+
}
|
|
24
|
+
export var secrets;
|
|
25
|
+
(function (secrets) {
|
|
26
|
+
const base = (collectionId) => `/admin/collection/${enc(collectionId)}/secrets`;
|
|
27
|
+
/** List secrets as refs + masked hints + metadata (never values). GET /secrets */
|
|
28
|
+
async function list(collectionId, query = {}) {
|
|
29
|
+
return request(`${base(collectionId)}${encodeQuery(query)}`);
|
|
30
|
+
}
|
|
31
|
+
secrets.list = list;
|
|
32
|
+
/** Create a secret. POST /secrets → { ref, hint }. Store the ref on a flow. */
|
|
33
|
+
async function set(collectionId, input) {
|
|
34
|
+
return post(base(collectionId), input);
|
|
35
|
+
}
|
|
36
|
+
secrets.set = set;
|
|
37
|
+
/** Metadata for one secret (never the value). GET /secrets/:ref */
|
|
38
|
+
async function get(collectionId, ref) {
|
|
39
|
+
return request(`${base(collectionId)}/${enc(ref)}`);
|
|
40
|
+
}
|
|
41
|
+
secrets.get = get;
|
|
42
|
+
/** Rotate/update a secret's value (and optionally name/purpose). PUT /secrets/:ref → { ref, hint } */
|
|
43
|
+
async function rotate(collectionId, ref, input) {
|
|
44
|
+
return put(`${base(collectionId)}/${enc(ref)}`, input);
|
|
45
|
+
}
|
|
46
|
+
secrets.rotate = rotate;
|
|
47
|
+
/** Soft-delete a secret. DELETE /secrets/:ref */
|
|
48
|
+
async function remove(collectionId, ref) {
|
|
49
|
+
return del(`${base(collectionId)}/${enc(ref)}`);
|
|
50
|
+
}
|
|
51
|
+
secrets.remove = remove;
|
|
52
|
+
})(secrets || (secrets = {}));
|