@sparkvault/sdk-mobile 6.0.2 → 7.0.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/README.md +5 -5
- package/dist/account.d.ts +4 -3
- package/dist/account.js +16 -11
- package/dist/account.js.map +1 -1
- package/dist/app-sdk/email-address.d.ts +37 -0
- package/dist/app-sdk/email-address.js +91 -0
- package/dist/app-sdk/email-address.js.map +1 -0
- package/dist/app-sdk/encoding.d.ts +64 -0
- package/dist/app-sdk/encoding.js +245 -0
- package/dist/app-sdk/encoding.js.map +1 -0
- package/dist/app-sdk/entropy-contract.d.ts +33 -0
- package/dist/app-sdk/entropy-contract.js +51 -0
- package/dist/app-sdk/entropy-contract.js.map +1 -0
- package/dist/app-sdk/filename.d.ts +93 -0
- package/dist/app-sdk/filename.js +161 -0
- package/dist/app-sdk/filename.js.map +1 -0
- package/dist/app-sdk/forge-url.d.ts +107 -0
- package/dist/app-sdk/forge-url.js +222 -0
- package/dist/app-sdk/forge-url.js.map +1 -0
- package/dist/app-sdk/ids.d.ts +48 -0
- package/dist/app-sdk/ids.js +65 -0
- package/dist/app-sdk/ids.js.map +1 -0
- package/dist/app-sdk/ingot-access-log.d.ts +29 -0
- package/dist/app-sdk/ingot-access-log.js +49 -0
- package/dist/app-sdk/ingot-access-log.js.map +1 -0
- package/dist/app-sdk/phone.d.ts +37 -0
- package/dist/app-sdk/phone.js +134 -0
- package/dist/app-sdk/phone.js.map +1 -0
- package/dist/app-sdk/platform-domains.d.ts +41 -0
- package/dist/app-sdk/platform-domains.js +82 -0
- package/dist/app-sdk/platform-domains.js.map +1 -0
- package/dist/app-sdk/request-path.d.ts +49 -0
- package/dist/app-sdk/request-path.js +81 -0
- package/dist/app-sdk/request-path.js.map +1 -0
- package/dist/app-sdk/transient.d.ts +23 -0
- package/dist/app-sdk/transient.js +29 -0
- package/dist/app-sdk/transient.js.map +1 -0
- package/dist/app-sdk/vat-refusal.d.ts +66 -0
- package/dist/app-sdk/vat-refusal.js +69 -0
- package/dist/app-sdk/vat-refusal.js.map +1 -0
- package/dist/billing.d.ts +9 -17
- package/dist/billing.js +14 -17
- package/dist/billing.js.map +1 -1
- package/dist/config.d.ts +7 -1
- package/dist/config.js +10 -17
- package/dist/config.js.map +1 -1
- package/dist/encoding.d.ts +30 -4
- package/dist/encoding.js +89 -83
- package/dist/encoding.js.map +1 -1
- package/dist/entropy.d.ts +25 -4
- package/dist/entropy.js +62 -15
- package/dist/entropy.js.map +1 -1
- package/dist/entropy.test-d.d.ts +40 -0
- package/dist/entropy.test-d.js +12 -0
- package/dist/entropy.test-d.js.map +1 -0
- package/dist/errors.d.ts +67 -17
- package/dist/errors.js +70 -27
- package/dist/errors.js.map +1 -1
- package/dist/folders.js +8 -7
- package/dist/folders.js.map +1 -1
- package/dist/http.d.ts +57 -15
- package/dist/http.js +125 -138
- package/dist/http.js.map +1 -1
- package/dist/identity-dialog.js +4 -30
- package/dist/identity-dialog.js.map +1 -1
- package/dist/identity-input.d.ts +39 -0
- package/dist/identity-input.js +59 -0
- package/dist/identity-input.js.map +1 -0
- package/dist/index.d.ts +6 -5
- package/dist/index.js +4 -3
- package/dist/index.js.map +1 -1
- package/dist/ingots.d.ts +51 -18
- package/dist/ingots.js +132 -122
- package/dist/ingots.js.map +1 -1
- package/dist/mutex.d.ts +1 -2
- package/dist/mutex.js +0 -6
- package/dist/mutex.js.map +1 -1
- package/dist/notify.d.ts +7 -2
- package/dist/notify.js +12 -15
- package/dist/notify.js.map +1 -1
- package/dist/notify.test-d.d.ts +3 -2
- package/dist/notify.test-d.js +1 -1
- package/dist/products/identity.d.ts +5 -0
- package/dist/products/identity.js +40 -35
- package/dist/products/identity.js.map +1 -1
- package/dist/request-path.d.ts +32 -0
- package/dist/request-path.js +35 -0
- package/dist/request-path.js.map +1 -0
- package/dist/sparks.js +16 -15
- package/dist/sparks.js.map +1 -1
- package/dist/tus.d.ts +19 -2
- package/dist/tus.js +86 -35
- package/dist/tus.js.map +1 -1
- package/dist/types.d.ts +167 -15
- package/dist/users.d.ts +12 -5
- package/dist/users.js +27 -19
- package/dist/users.js.map +1 -1
- package/dist/validation.d.ts +20 -5
- package/dist/validation.js +29 -27
- package/dist/validation.js.map +1 -1
- package/dist/vaults.d.ts +34 -83
- package/dist/vaults.js +64 -44
- package/dist/vaults.js.map +1 -1
- package/dist/vaults.test-d.d.ts +22 -0
- package/dist/vaults.test-d.js +14 -0
- package/dist/vaults.test-d.js.map +1 -0
- package/package.json +4 -2
- package/src/account.ts +16 -11
- package/src/app-sdk/email-address.js +94 -0
- package/src/app-sdk/encoding.js +250 -0
- package/src/app-sdk/entropy-contract.js +56 -0
- package/src/app-sdk/filename.js +174 -0
- package/src/app-sdk/forge-url.js +224 -0
- package/src/app-sdk/ids.js +71 -0
- package/src/app-sdk/ingot-access-log.js +51 -0
- package/src/app-sdk/phone.js +139 -0
- package/src/app-sdk/platform-domains.js +99 -0
- package/src/app-sdk/request-path.js +81 -0
- package/src/app-sdk/transient.js +30 -0
- package/src/app-sdk/vat-refusal.js +74 -0
- package/src/billing.ts +16 -25
- package/src/config.ts +16 -23
- package/src/encoding.ts +91 -103
- package/src/entropy.test-d.ts +47 -0
- package/src/entropy.ts +86 -20
- package/src/errors.ts +93 -33
- package/src/folders.ts +8 -7
- package/src/http.ts +145 -150
- package/src/identity-dialog.tsx +4 -37
- package/src/identity-input.ts +70 -0
- package/src/index.ts +11 -3
- package/src/ingots.ts +173 -159
- package/src/mutex.ts +1 -8
- package/src/notify.test-d.ts +3 -1
- package/src/notify.ts +19 -17
- package/src/products/identity.ts +45 -39
- package/src/request-path.ts +45 -0
- package/src/sparks.ts +16 -13
- package/src/tus.ts +90 -37
- package/src/types.ts +165 -15
- package/src/users.ts +27 -17
- package/src/validation.ts +30 -24
- package/src/vaults.test-d.ts +29 -0
- package/src/vaults.ts +87 -153
- package/dist/platform-domains.generated.d.ts +0 -2
- package/dist/platform-domains.generated.js +0 -16
- package/dist/platform-domains.generated.js.map +0 -1
- package/src/platform-domains.generated.ts +0 -17
package/dist/users.js
CHANGED
|
@@ -1,11 +1,13 @@
|
|
|
1
|
+
import { apiPath } from './request-path.js';
|
|
2
|
+
import { validateResourceId } from './validation.js';
|
|
1
3
|
/**
|
|
2
4
|
* Organization team client (member admins only — the API gates these on the
|
|
3
5
|
* admin role and returns 403 otherwise).
|
|
4
6
|
*
|
|
5
|
-
* Licensing is a billing action (
|
|
6
|
-
*
|
|
7
|
-
* operation exposed here is `invite`, which defaults new members
|
|
8
|
-
* `unlicensed` and never charges. Assigning or changing a paid license is
|
|
7
|
+
* Licensing is a billing action (licenses are prepaid: assigning or upgrading
|
|
8
|
+
* one charges the rest of the current billing period at once), so the only
|
|
9
|
+
* seat-affecting operation exposed here is `invite`, which defaults new members
|
|
10
|
+
* to `unlicensed` and never charges. Assigning or changing a paid license is
|
|
9
11
|
* intentionally absent — clients route that to the web dashboard so native
|
|
10
12
|
* apps never initiate an out-of-band purchase.
|
|
11
13
|
*/
|
|
@@ -15,32 +17,38 @@ export class MobileUsersClient {
|
|
|
15
17
|
}
|
|
16
18
|
/** List organization members (active and invited), with optional search/filter. */
|
|
17
19
|
async list(options = {}) {
|
|
18
|
-
const
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
params.set('cursor', options.cursor);
|
|
27
|
-
const query = params.toString();
|
|
28
|
-
const response = await this.http.get(query ? `/users?${query}` : '/users');
|
|
20
|
+
const response = await this.http.get(apiPath `/users`, {
|
|
21
|
+
query: {
|
|
22
|
+
search: options.search,
|
|
23
|
+
status: options.status,
|
|
24
|
+
limit: typeof options.limit === 'number' ? options.limit : undefined,
|
|
25
|
+
cursor: options.cursor,
|
|
26
|
+
},
|
|
27
|
+
});
|
|
29
28
|
return response.data;
|
|
30
29
|
}
|
|
31
30
|
/** Invite a coworker by email. Defaults to an unlicensed seat (no charge). */
|
|
32
31
|
async invite(request) {
|
|
33
|
-
const response = await this.http.post(
|
|
32
|
+
const response = await this.http.post(apiPath `/users/invite`, request);
|
|
34
33
|
return response.data;
|
|
35
34
|
}
|
|
36
|
-
/**
|
|
35
|
+
/**
|
|
36
|
+
* Remove a member and revoke their DVAKs. Access ends immediately. A license
|
|
37
|
+
* they held stays paid until the end of the billing period — nothing is
|
|
38
|
+
* refunded — and is not renewed; until then it can be given to someone else
|
|
39
|
+
* at no charge. `wind_down` is true when this removal ends the
|
|
40
|
+
* subscription — theirs was the last license it renews, and it was not
|
|
41
|
+
* already set to end: it ends at the period end.
|
|
42
|
+
*/
|
|
37
43
|
async remove(userId) {
|
|
38
|
-
|
|
44
|
+
validateResourceId(userId, 'user ID', 'userId');
|
|
45
|
+
const response = await this.http.delete(apiPath `/users/${userId}`);
|
|
39
46
|
return response.data;
|
|
40
47
|
}
|
|
41
48
|
/** Resend a pending invitation email (resets the 7-day expiry). */
|
|
42
49
|
async resendInvite(userId) {
|
|
43
|
-
|
|
50
|
+
validateResourceId(userId, 'user ID', 'userId');
|
|
51
|
+
const response = await this.http.post(apiPath `/users/${userId}/resend-invite`);
|
|
44
52
|
return response.data;
|
|
45
53
|
}
|
|
46
54
|
}
|
package/dist/users.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"users.js","sourceRoot":"","sources":["../src/users.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"users.js","sourceRoot":"","sources":["../src/users.ts"],"names":[],"mappings":"AASA,OAAO,EAAE,OAAO,EAAE,MAAM,mBAAmB,CAAC;AAC5C,OAAO,EAAE,kBAAkB,EAAE,MAAM,iBAAiB,CAAC;AAErD;;;;;;;;;;GAUG;AACH,MAAM,OAAO,iBAAiB;IAG5B,YAAY,IAAsB;QAChC,IAAI,CAAC,IAAI,GAAG,IAAI,CAAC;IACnB,CAAC;IAED,mFAAmF;IACnF,KAAK,CAAC,IAAI,CAAC,UAA8B,EAAE;QACzC,MAAM,QAAQ,GAAG,MAAM,IAAI,CAAC,IAAI,CAAC,GAAG,CAAsB,OAAO,CAAA,QAAQ,EAAE;YACzE,KAAK,EAAE;gBACL,MAAM,EAAE,OAAO,CAAC,MAAM;gBACtB,MAAM,EAAE,OAAO,CAAC,MAAM;gBACtB,KAAK,EAAE,OAAO,OAAO,CAAC,KAAK,KAAK,QAAQ,CAAC,CAAC,CAAC,OAAO,CAAC,KAAK,CAAC,CAAC,CAAC,SAAS;gBACpE,MAAM,EAAE,OAAO,CAAC,MAAM;aACvB;SACF,CAAC,CAAC;QACH,OAAO,QAAQ,CAAC,IAAI,CAAC;IACvB,CAAC;IAED,8EAA8E;IAC9E,KAAK,CAAC,MAAM,CAAC,OAA4B;QACvC,MAAM,QAAQ,GAAG,MAAM,IAAI,CAAC,IAAI,CAAC,IAAI,CAAuB,OAAO,CAAA,eAAe,EAAE,OAAO,CAAC,CAAC;QAC7F,OAAO,QAAQ,CAAC,IAAI,CAAC;IACvB,CAAC;IAED;;;;;;;OAOG;IACH,KAAK,CAAC,MAAM,CAAC,MAAc;QACzB,kBAAkB,CAAC,MAAM,EAAE,SAAS,EAAE,QAAQ,CAAC,CAAC;QAChD,MAAM,QAAQ,GAAG,MAAM,IAAI,CAAC,IAAI,CAAC,MAAM,CAAuB,OAAO,CAAA,UAAU,MAAM,EAAE,CAAC,CAAC;QACzF,OAAO,QAAQ,CAAC,IAAI,CAAC;IACvB,CAAC;IAED,mEAAmE;IACnE,KAAK,CAAC,YAAY,CAAC,MAAc;QAC/B,kBAAkB,CAAC,MAAM,EAAE,SAAS,EAAE,QAAQ,CAAC,CAAC;QAChD,MAAM,QAAQ,GAAG,MAAM,IAAI,CAAC,IAAI,CAAC,IAAI,CAAuB,OAAO,CAAA,UAAU,MAAM,gBAAgB,CAAC,CAAC;QACrG,OAAO,QAAQ,CAAC,IAAI,CAAC;IACvB,CAAC;CACF"}
|
package/dist/validation.d.ts
CHANGED
|
@@ -1,11 +1,26 @@
|
|
|
1
|
-
|
|
1
|
+
import { isResourceId } from './app-sdk/ids.js';
|
|
2
|
+
/** Whether a value is a well-formed SparkVault resource id (the platform's one rule). */
|
|
3
|
+
export { isResourceId as isSafeId };
|
|
4
|
+
/**
|
|
5
|
+
* Refuse a value that is not a SparkVault resource id before it names a route.
|
|
6
|
+
*
|
|
7
|
+
* @param label - How the message names the id, e.g. 'spark ID'.
|
|
8
|
+
* @param field - The argument's name, reported in the error details.
|
|
9
|
+
*/
|
|
10
|
+
export declare function validateResourceId(value: unknown, label: string, field: string): void;
|
|
2
11
|
export declare function validateVaultId(vaultId: string): void;
|
|
3
12
|
export declare function validateIngotId(ingotId: string): void;
|
|
4
13
|
export declare function validateFolderId(folderId: string): void;
|
|
5
14
|
/**
|
|
6
|
-
*
|
|
7
|
-
*
|
|
8
|
-
*
|
|
9
|
-
*
|
|
15
|
+
* The file name to store or save text under, by the platform's one file-name
|
|
16
|
+
* rule (@sparkvault/app-sdk/filename, mirrored into ./app-sdk/filename.js):
|
|
17
|
+
* path separators, control characters and the bidi controls that disguise an
|
|
18
|
+
* extension (`invoice<U+202E>fdp.exe` shows as `invoiceexe.pdf`) become `_`,
|
|
19
|
+
* and so do the characters SparkVault refuses in a name (: * ? " < > |), so a
|
|
20
|
+
* name derived from a note's title uploads. With every separator gone no name
|
|
21
|
+
* can climb a directory, so a `..` inside a name is kept. On top of the rule,
|
|
22
|
+
* for the device's file system: leading dots are stripped (a hidden file) and
|
|
23
|
+
* Windows reserved names are prefixed. Falls back to the platform's one
|
|
24
|
+
* fallback name (SAVED_FILENAME_FALLBACK) when nothing remains.
|
|
10
25
|
*/
|
|
11
26
|
export declare function sanitizeFilename(filename: string): string;
|
package/dist/validation.js
CHANGED
|
@@ -1,27 +1,27 @@
|
|
|
1
|
+
import { isResourceId } from './app-sdk/ids.js';
|
|
1
2
|
import { SparkVaultValidationError } from './errors.js';
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
3
|
+
import { SAVED_FILENAME_FALLBACK, toStorableFilename } from './app-sdk/filename.js';
|
|
4
|
+
/** Whether a value is a well-formed SparkVault resource id (the platform's one rule). */
|
|
5
|
+
export { isResourceId as isSafeId };
|
|
6
|
+
/**
|
|
7
|
+
* Refuse a value that is not a SparkVault resource id before it names a route.
|
|
8
|
+
*
|
|
9
|
+
* @param label - How the message names the id, e.g. 'spark ID'.
|
|
10
|
+
* @param field - The argument's name, reported in the error details.
|
|
11
|
+
*/
|
|
12
|
+
export function validateResourceId(value, label, field) {
|
|
13
|
+
if (!isResourceId(value)) {
|
|
14
|
+
throw new SparkVaultValidationError(`Invalid ${label} format`, { [field]: value });
|
|
15
|
+
}
|
|
10
16
|
}
|
|
11
17
|
export function validateVaultId(vaultId) {
|
|
12
|
-
|
|
13
|
-
throw new SparkVaultValidationError('Invalid vault ID format', { vaultId });
|
|
14
|
-
}
|
|
18
|
+
validateResourceId(vaultId, 'vault ID', 'vaultId');
|
|
15
19
|
}
|
|
16
20
|
export function validateIngotId(ingotId) {
|
|
17
|
-
|
|
18
|
-
throw new SparkVaultValidationError('Invalid ingot ID format', { ingotId });
|
|
19
|
-
}
|
|
21
|
+
validateResourceId(ingotId, 'ingot ID', 'ingotId');
|
|
20
22
|
}
|
|
21
23
|
export function validateFolderId(folderId) {
|
|
22
|
-
|
|
23
|
-
throw new SparkVaultValidationError('Invalid folder ID format', { folderId });
|
|
24
|
-
}
|
|
24
|
+
validateResourceId(folderId, 'folder ID', 'folderId');
|
|
25
25
|
}
|
|
26
26
|
/** Windows reserved filenames that cannot be used. */
|
|
27
27
|
const WINDOWS_RESERVED_NAMES = new Set([
|
|
@@ -30,23 +30,25 @@ const WINDOWS_RESERVED_NAMES = new Set([
|
|
|
30
30
|
'LPT1', 'LPT2', 'LPT3', 'LPT4', 'LPT5', 'LPT6', 'LPT7', 'LPT8', 'LPT9',
|
|
31
31
|
]);
|
|
32
32
|
/**
|
|
33
|
-
*
|
|
34
|
-
*
|
|
35
|
-
*
|
|
36
|
-
*
|
|
33
|
+
* The file name to store or save text under, by the platform's one file-name
|
|
34
|
+
* rule (@sparkvault/app-sdk/filename, mirrored into ./app-sdk/filename.js):
|
|
35
|
+
* path separators, control characters and the bidi controls that disguise an
|
|
36
|
+
* extension (`invoice<U+202E>fdp.exe` shows as `invoiceexe.pdf`) become `_`,
|
|
37
|
+
* and so do the characters SparkVault refuses in a name (: * ? " < > |), so a
|
|
38
|
+
* name derived from a note's title uploads. With every separator gone no name
|
|
39
|
+
* can climb a directory, so a `..` inside a name is kept. On top of the rule,
|
|
40
|
+
* for the device's file system: leading dots are stripped (a hidden file) and
|
|
41
|
+
* Windows reserved names are prefixed. Falls back to the platform's one
|
|
42
|
+
* fallback name (SAVED_FILENAME_FALLBACK) when nothing remains.
|
|
37
43
|
*/
|
|
38
44
|
export function sanitizeFilename(filename) {
|
|
39
|
-
let sanitized = filename
|
|
40
|
-
.replace(/\0/g, '')
|
|
41
|
-
.replace(/[\x00-\x1f\x7f]/g, '')
|
|
42
|
-
.replace(/\.\./g, '')
|
|
43
|
-
.replace(/[\/\\]/g, '_')
|
|
45
|
+
let sanitized = toStorableFilename(filename)
|
|
44
46
|
.replace(/^\.+/, '')
|
|
45
47
|
.trim();
|
|
46
48
|
const baseName = sanitized.split('.')[0].toUpperCase();
|
|
47
49
|
if (WINDOWS_RESERVED_NAMES.has(baseName)) {
|
|
48
50
|
sanitized = `_${sanitized}`;
|
|
49
51
|
}
|
|
50
|
-
return sanitized ||
|
|
52
|
+
return sanitized || SAVED_FILENAME_FALLBACK;
|
|
51
53
|
}
|
|
52
54
|
//# sourceMappingURL=validation.js.map
|
package/dist/validation.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"validation.js","sourceRoot":"","sources":["../src/validation.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,
|
|
1
|
+
{"version":3,"file":"validation.js","sourceRoot":"","sources":["../src/validation.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAE,MAAM,kBAAkB,CAAC;AAChD,OAAO,EAAE,yBAAyB,EAAE,MAAM,aAAa,CAAC;AACxD,OAAO,EAAE,uBAAuB,EAAE,kBAAkB,EAAE,MAAM,uBAAuB,CAAC;AAEpF,yFAAyF;AACzF,OAAO,EAAE,YAAY,IAAI,QAAQ,EAAE,CAAC;AAEpC;;;;;GAKG;AACH,MAAM,UAAU,kBAAkB,CAAC,KAAc,EAAE,KAAa,EAAE,KAAa;IAC7E,IAAI,CAAC,YAAY,CAAC,KAAK,CAAC,EAAE,CAAC;QACzB,MAAM,IAAI,yBAAyB,CAAC,WAAW,KAAK,SAAS,EAAE,EAAE,CAAC,KAAK,CAAC,EAAE,KAAK,EAAE,CAAC,CAAC;IACrF,CAAC;AACH,CAAC;AAED,MAAM,UAAU,eAAe,CAAC,OAAe;IAC7C,kBAAkB,CAAC,OAAO,EAAE,UAAU,EAAE,SAAS,CAAC,CAAC;AACrD,CAAC;AAED,MAAM,UAAU,eAAe,CAAC,OAAe;IAC7C,kBAAkB,CAAC,OAAO,EAAE,UAAU,EAAE,SAAS,CAAC,CAAC;AACrD,CAAC;AAED,MAAM,UAAU,gBAAgB,CAAC,QAAgB;IAC/C,kBAAkB,CAAC,QAAQ,EAAE,WAAW,EAAE,UAAU,CAAC,CAAC;AACxD,CAAC;AAED,sDAAsD;AACtD,MAAM,sBAAsB,GAAG,IAAI,GAAG,CAAC;IACrC,KAAK,EAAE,KAAK,EAAE,KAAK,EAAE,KAAK;IAC1B,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM;IACtE,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM;CACvE,CAAC,CAAC;AAEH;;;;;;;;;;;GAWG;AACH,MAAM,UAAU,gBAAgB,CAAC,QAAgB;IAC/C,IAAI,SAAS,GAAG,kBAAkB,CAAC,QAAQ,CAAC;SACzC,OAAO,CAAC,MAAM,EAAE,EAAE,CAAC;SACnB,IAAI,EAAE,CAAC;IAEV,MAAM,QAAQ,GAAG,SAAS,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC,WAAW,EAAE,CAAC;IACvD,IAAI,sBAAsB,CAAC,GAAG,CAAC,QAAQ,CAAC,EAAE,CAAC;QACzC,SAAS,GAAG,IAAI,SAAS,EAAE,CAAC;IAC9B,CAAC;IAED,OAAO,SAAS,IAAI,uBAAuB,CAAC;AAC9C,CAAC"}
|
package/dist/vaults.d.ts
CHANGED
|
@@ -1,49 +1,5 @@
|
|
|
1
1
|
import type { MobileHttpClient } from './http.js';
|
|
2
|
-
import type { CreateVaultRequest, CreateVaultResponse, ListVaultsResponse, UnsealVaultRequest, UnsealVaultResponse, UpdateVaultRequest, UpdateVaultResponse, Vault } from './types.js';
|
|
3
|
-
export interface SharingConfig {
|
|
4
|
-
vault_id: string;
|
|
5
|
-
public_sharing_enabled: boolean;
|
|
6
|
-
all_ingots_public: boolean;
|
|
7
|
-
session_length_seconds: number | null;
|
|
8
|
-
enabled_at: number | null;
|
|
9
|
-
}
|
|
10
|
-
export interface UploadConfig {
|
|
11
|
-
vault_id: string;
|
|
12
|
-
upload_portal_enabled: boolean;
|
|
13
|
-
upload_portal_enabled_at: number | null;
|
|
14
|
-
upload_widget_enabled: boolean;
|
|
15
|
-
upload_widget_enabled_at: number | null;
|
|
16
|
-
max_size_bytes: number | null;
|
|
17
|
-
notification_email: string | null;
|
|
18
|
-
portal_url?: string;
|
|
19
|
-
}
|
|
20
|
-
export interface UploadPortalEnabled {
|
|
21
|
-
vault_id: string;
|
|
22
|
-
upload_portal_enabled: true;
|
|
23
|
-
enabled_at: number;
|
|
24
|
-
portal_url: string;
|
|
25
|
-
}
|
|
26
|
-
export interface UploadWidgetEnabled {
|
|
27
|
-
vault_id: string;
|
|
28
|
-
upload_widget_enabled: true;
|
|
29
|
-
enabled_at: number;
|
|
30
|
-
}
|
|
31
|
-
export interface UploadPortalDisabled {
|
|
32
|
-
vault_id: string;
|
|
33
|
-
upload_portal_enabled: false;
|
|
34
|
-
disabled_at: number;
|
|
35
|
-
}
|
|
36
|
-
export interface UploadWidgetDisabled {
|
|
37
|
-
vault_id: string;
|
|
38
|
-
upload_widget_enabled: false;
|
|
39
|
-
disabled_at: number;
|
|
40
|
-
}
|
|
41
|
-
export interface UploadConfigUpdate {
|
|
42
|
-
vault_id: string;
|
|
43
|
-
max_size_bytes: number;
|
|
44
|
-
notification_email: string | null;
|
|
45
|
-
updated_at: number;
|
|
46
|
-
}
|
|
2
|
+
import type { AccessLogRetention, CreateVaultRequest, CreateVaultResponse, DisableVaultSharingResponse, EnableVaultSharingResponse, ListVaultsResponse, UnsealVaultRequest, UnsealVaultResponse, UpdateAccessLogRetentionResponse, UpdateVaultRequest, UpdateVaultResponse, UpdateVaultSharingResponse, UploadConfig, UploadConfigUpdate, UploadPortalDisabled, UploadPortalEnabled, UploadWidgetDisabled, UploadWidgetEnabled, Vault, VaultSharingConfig, VaultSharingOptions } from './types.js';
|
|
47
3
|
export declare class MobileVaultsClient {
|
|
48
4
|
private readonly http;
|
|
49
5
|
constructor(http: MobileHttpClient);
|
|
@@ -53,6 +9,15 @@ export declare class MobileVaultsClient {
|
|
|
53
9
|
limit?: number;
|
|
54
10
|
cursor?: string;
|
|
55
11
|
}): Promise<ListVaultsResponse>;
|
|
12
|
+
/**
|
|
13
|
+
* Every vault on the account, newest first. Follows next_cursor at the
|
|
14
|
+
* largest page size until the server reports no more — a page the server
|
|
15
|
+
* filtered down to nothing still carries a cursor. A failed page fails the
|
|
16
|
+
* listing: a vault picker must never show a silently partial account.
|
|
17
|
+
*/
|
|
18
|
+
listAll(options?: {
|
|
19
|
+
status?: 'sealed' | 'unsealed';
|
|
20
|
+
}): Promise<Vault[]>;
|
|
56
21
|
get(vaultId: string): Promise<Vault>;
|
|
57
22
|
update(vaultId: string, request: UpdateVaultRequest): Promise<UpdateVaultResponse>;
|
|
58
23
|
/**
|
|
@@ -62,48 +27,34 @@ export declare class MobileVaultsClient {
|
|
|
62
27
|
* The name is sent base64(UTF-8) as `X-Confirm-Name-B64` so that vaults named
|
|
63
28
|
* with any Unicode (emoji, CJK, the U+202F in macOS-style names) are
|
|
64
29
|
* deletable — a raw header value throws before the request is sent for
|
|
65
|
-
* non-latin1 characters.
|
|
66
|
-
* is latin1-safe, for older API servers.
|
|
30
|
+
* non-latin1 characters.
|
|
67
31
|
*/
|
|
68
32
|
delete(vaultId: string, name: string): Promise<void>;
|
|
69
33
|
unseal(vaultId: string, request: UnsealVaultRequest): Promise<UnsealVaultResponse>;
|
|
34
|
+
/**
|
|
35
|
+
* Seal the vault: end every session of it, so every VAT minted for it stops
|
|
36
|
+
* working, whoever holds it. To end only the caller's own session, use
|
|
37
|
+
* `endSession`.
|
|
38
|
+
*/
|
|
70
39
|
seal(vaultId: string): Promise<void>;
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
all_ingots_public?: boolean;
|
|
90
|
-
session_length_seconds?: number;
|
|
91
|
-
}): Promise<{
|
|
92
|
-
vault_id: string;
|
|
93
|
-
public_sharing_enabled: boolean;
|
|
94
|
-
all_ingots_public: boolean;
|
|
95
|
-
session_length_seconds: number;
|
|
96
|
-
updated_at: number;
|
|
97
|
-
}>;
|
|
98
|
-
getAccessLogRetention(vaultId: string): Promise<{
|
|
99
|
-
vault_id: string;
|
|
100
|
-
access_log_retention_seconds: number;
|
|
101
|
-
}>;
|
|
102
|
-
updateAccessLogRetention(vaultId: string, retentionSeconds: number): Promise<{
|
|
103
|
-
vault_id: string;
|
|
104
|
-
access_log_retention_seconds: number;
|
|
105
|
-
updated_at: number;
|
|
106
|
-
}>;
|
|
40
|
+
/**
|
|
41
|
+
* End the session `vat` names, and no other session of the vault: every
|
|
42
|
+
* other holder keeps theirs. A VAT the server already refuses (an
|
|
43
|
+
* `isVatExpiredError` or a `vatRefusalReason` of VAT_INVALID) names a
|
|
44
|
+
* session that is already over.
|
|
45
|
+
*/
|
|
46
|
+
endSession(vaultId: string, vat: string): Promise<void>;
|
|
47
|
+
getSharingConfig(vaultId: string): Promise<VaultSharingConfig>;
|
|
48
|
+
enableSharing(vaultId: string, vmk: string, options?: VaultSharingOptions): Promise<EnableVaultSharingResponse>;
|
|
49
|
+
disableSharing(vaultId: string): Promise<DisableVaultSharingResponse>;
|
|
50
|
+
/**
|
|
51
|
+
* Update the vault's sharing policy. Making every ingot public publishes
|
|
52
|
+
* each file to anyone holding its URL, so the API accepts
|
|
53
|
+
* `all_ingots_public: true` only with a read-write VAT for this vault.
|
|
54
|
+
*/
|
|
55
|
+
updateSharingConfig(vaultId: string, config: VaultSharingOptions, vat?: string): Promise<UpdateVaultSharingResponse>;
|
|
56
|
+
getAccessLogRetention(vaultId: string): Promise<AccessLogRetention>;
|
|
57
|
+
updateAccessLogRetention(vaultId: string, retentionSeconds: number): Promise<UpdateAccessLogRetentionResponse>;
|
|
107
58
|
getUploadConfig(vaultId: string): Promise<UploadConfig>;
|
|
108
59
|
enableUploadPortal(vaultId: string, vmk: string): Promise<UploadPortalEnabled>;
|
|
109
60
|
disableUploadPortal(vaultId: string): Promise<UploadPortalDisabled>;
|
package/dist/vaults.js
CHANGED
|
@@ -1,41 +1,46 @@
|
|
|
1
1
|
import { validateVaultId } from './validation.js';
|
|
2
2
|
import { base64EncodeUtf8 } from './encoding.js';
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
if (value.charCodeAt(i) > 0xff)
|
|
7
|
-
return false;
|
|
8
|
-
}
|
|
9
|
-
return true;
|
|
10
|
-
}
|
|
3
|
+
import { apiPath } from './request-path.js';
|
|
4
|
+
/** GET /v1/vaults' largest page (apps/api vaults/list.js maxLimit). */
|
|
5
|
+
const VAULT_LIST_PAGE_LIMIT = 500;
|
|
11
6
|
export class MobileVaultsClient {
|
|
12
7
|
constructor(http) {
|
|
13
8
|
this.http = http;
|
|
14
9
|
}
|
|
15
10
|
async create(request) {
|
|
16
|
-
const response = await this.http.post(
|
|
11
|
+
const response = await this.http.post(apiPath `/vaults`, request);
|
|
17
12
|
return response.data;
|
|
18
13
|
}
|
|
19
14
|
async list(options) {
|
|
20
|
-
const
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
if (options?.limit)
|
|
24
|
-
params.append('limit', options.limit.toString());
|
|
25
|
-
if (options?.cursor)
|
|
26
|
-
params.append('cursor', options.cursor);
|
|
27
|
-
const query = params.toString();
|
|
28
|
-
const response = await this.http.get(query ? `/vaults?${query}` : '/vaults');
|
|
15
|
+
const response = await this.http.get(apiPath `/vaults`, {
|
|
16
|
+
query: { status: options?.status, limit: options?.limit || undefined, cursor: options?.cursor },
|
|
17
|
+
});
|
|
29
18
|
return response.data;
|
|
30
19
|
}
|
|
20
|
+
/**
|
|
21
|
+
* Every vault on the account, newest first. Follows next_cursor at the
|
|
22
|
+
* largest page size until the server reports no more — a page the server
|
|
23
|
+
* filtered down to nothing still carries a cursor. A failed page fails the
|
|
24
|
+
* listing: a vault picker must never show a silently partial account.
|
|
25
|
+
*/
|
|
26
|
+
async listAll(options) {
|
|
27
|
+
const vaults = [];
|
|
28
|
+
let cursor;
|
|
29
|
+
do {
|
|
30
|
+
const page = await this.list({ ...options, limit: VAULT_LIST_PAGE_LIMIT, cursor });
|
|
31
|
+
vaults.push(...page.vaults);
|
|
32
|
+
cursor = page.has_more ? page.next_cursor : undefined;
|
|
33
|
+
} while (cursor);
|
|
34
|
+
return vaults;
|
|
35
|
+
}
|
|
31
36
|
async get(vaultId) {
|
|
32
37
|
validateVaultId(vaultId);
|
|
33
|
-
const response = await this.http.get(`/vaults/${vaultId}`);
|
|
38
|
+
const response = await this.http.get(apiPath `/vaults/${vaultId}`);
|
|
34
39
|
return response.data;
|
|
35
40
|
}
|
|
36
41
|
async update(vaultId, request) {
|
|
37
42
|
validateVaultId(vaultId);
|
|
38
|
-
const response = await this.http.put(`/vaults/${vaultId}`, request);
|
|
43
|
+
const response = await this.http.put(apiPath `/vaults/${vaultId}`, request);
|
|
39
44
|
return response.data;
|
|
40
45
|
}
|
|
41
46
|
/**
|
|
@@ -45,39 +50,49 @@ export class MobileVaultsClient {
|
|
|
45
50
|
* The name is sent base64(UTF-8) as `X-Confirm-Name-B64` so that vaults named
|
|
46
51
|
* with any Unicode (emoji, CJK, the U+202F in macOS-style names) are
|
|
47
52
|
* deletable — a raw header value throws before the request is sent for
|
|
48
|
-
* non-latin1 characters.
|
|
49
|
-
* is latin1-safe, for older API servers.
|
|
53
|
+
* non-latin1 characters.
|
|
50
54
|
*/
|
|
51
55
|
async delete(vaultId, name) {
|
|
52
56
|
validateVaultId(vaultId);
|
|
53
57
|
if (!name) {
|
|
54
58
|
throw new Error('Vault name is required to confirm deletion');
|
|
55
59
|
}
|
|
56
|
-
|
|
57
|
-
'X-Confirm-Name-B64': base64EncodeUtf8(name),
|
|
58
|
-
};
|
|
59
|
-
if (isLatin1(name)) {
|
|
60
|
-
headers['X-Confirm-Name'] = name;
|
|
61
|
-
}
|
|
62
|
-
await this.http.delete(`/vaults/${vaultId}`, { headers });
|
|
60
|
+
await this.http.delete(apiPath `/vaults/${vaultId}`, {
|
|
61
|
+
headers: { 'X-Confirm-Name-B64': base64EncodeUtf8(name) },
|
|
62
|
+
});
|
|
63
63
|
}
|
|
64
64
|
async unseal(vaultId, request) {
|
|
65
65
|
validateVaultId(vaultId);
|
|
66
|
-
const response = await this.http.post(`/vaults/${vaultId}/unseal`, request);
|
|
66
|
+
const response = await this.http.post(apiPath `/vaults/${vaultId}/unseal`, request);
|
|
67
67
|
return response.data;
|
|
68
68
|
}
|
|
69
|
+
/**
|
|
70
|
+
* Seal the vault: end every session of it, so every VAT minted for it stops
|
|
71
|
+
* working, whoever holds it. To end only the caller's own session, use
|
|
72
|
+
* `endSession`.
|
|
73
|
+
*/
|
|
69
74
|
async seal(vaultId) {
|
|
70
75
|
validateVaultId(vaultId);
|
|
71
|
-
await this.http.post(`/vaults/${vaultId}/seal`);
|
|
76
|
+
await this.http.post(apiPath `/vaults/${vaultId}/seal`);
|
|
77
|
+
}
|
|
78
|
+
/**
|
|
79
|
+
* End the session `vat` names, and no other session of the vault: every
|
|
80
|
+
* other holder keeps theirs. A VAT the server already refuses (an
|
|
81
|
+
* `isVatExpiredError` or a `vatRefusalReason` of VAT_INVALID) names a
|
|
82
|
+
* session that is already over.
|
|
83
|
+
*/
|
|
84
|
+
async endSession(vaultId, vat) {
|
|
85
|
+
validateVaultId(vaultId);
|
|
86
|
+
await this.http.delete(apiPath `/vaults/${vaultId}/session`, { vat });
|
|
72
87
|
}
|
|
73
88
|
async getSharingConfig(vaultId) {
|
|
74
89
|
validateVaultId(vaultId);
|
|
75
|
-
const response = await this.http.get(`/vaults/${vaultId}/sharing`);
|
|
90
|
+
const response = await this.http.get(apiPath `/vaults/${vaultId}/sharing`);
|
|
76
91
|
return response.data;
|
|
77
92
|
}
|
|
78
93
|
async enableSharing(vaultId, vmk, options) {
|
|
79
94
|
validateVaultId(vaultId);
|
|
80
|
-
const response = await this.http.post(`/vaults/${vaultId}/sharing/enable`, {
|
|
95
|
+
const response = await this.http.post(apiPath `/vaults/${vaultId}/sharing/enable`, {
|
|
81
96
|
vmk,
|
|
82
97
|
all_ingots_public: options?.all_ingots_public,
|
|
83
98
|
session_length_seconds: options?.session_length_seconds,
|
|
@@ -86,58 +101,63 @@ export class MobileVaultsClient {
|
|
|
86
101
|
}
|
|
87
102
|
async disableSharing(vaultId) {
|
|
88
103
|
validateVaultId(vaultId);
|
|
89
|
-
const response = await this.http.post(`/vaults/${vaultId}/sharing/disable`);
|
|
104
|
+
const response = await this.http.post(apiPath `/vaults/${vaultId}/sharing/disable`);
|
|
90
105
|
return response.data;
|
|
91
106
|
}
|
|
92
|
-
|
|
107
|
+
/**
|
|
108
|
+
* Update the vault's sharing policy. Making every ingot public publishes
|
|
109
|
+
* each file to anyone holding its URL, so the API accepts
|
|
110
|
+
* `all_ingots_public: true` only with a read-write VAT for this vault.
|
|
111
|
+
*/
|
|
112
|
+
async updateSharingConfig(vaultId, config, vat) {
|
|
93
113
|
validateVaultId(vaultId);
|
|
94
|
-
const response = await this.http.put(`/vaults/${vaultId}/sharing`, config);
|
|
114
|
+
const response = await this.http.put(apiPath `/vaults/${vaultId}/sharing`, config, { vat });
|
|
95
115
|
return response.data;
|
|
96
116
|
}
|
|
97
117
|
async getAccessLogRetention(vaultId) {
|
|
98
118
|
validateVaultId(vaultId);
|
|
99
|
-
const response = await this.http.get(`/vaults/${vaultId}/access-log-retention`);
|
|
119
|
+
const response = await this.http.get(apiPath `/vaults/${vaultId}/access-log-retention`);
|
|
100
120
|
return response.data;
|
|
101
121
|
}
|
|
102
122
|
async updateAccessLogRetention(vaultId, retentionSeconds) {
|
|
103
123
|
validateVaultId(vaultId);
|
|
104
|
-
const response = await this.http.put(`/vaults/${vaultId}/access-log-retention`, {
|
|
124
|
+
const response = await this.http.put(apiPath `/vaults/${vaultId}/access-log-retention`, {
|
|
105
125
|
access_log_retention_seconds: retentionSeconds,
|
|
106
126
|
});
|
|
107
127
|
return response.data;
|
|
108
128
|
}
|
|
109
129
|
async getUploadConfig(vaultId) {
|
|
110
130
|
validateVaultId(vaultId);
|
|
111
|
-
const response = await this.http.get(`/vaults/${vaultId}/upload`);
|
|
131
|
+
const response = await this.http.get(apiPath `/vaults/${vaultId}/upload`);
|
|
112
132
|
return response.data;
|
|
113
133
|
}
|
|
114
134
|
async enableUploadPortal(vaultId, vmk) {
|
|
115
135
|
validateVaultId(vaultId);
|
|
116
|
-
const response = await this.http.post(`/vaults/${vaultId}/upload/portal/enable`, {
|
|
136
|
+
const response = await this.http.post(apiPath `/vaults/${vaultId}/upload/portal/enable`, {
|
|
117
137
|
vmk,
|
|
118
138
|
});
|
|
119
139
|
return response.data;
|
|
120
140
|
}
|
|
121
141
|
async disableUploadPortal(vaultId) {
|
|
122
142
|
validateVaultId(vaultId);
|
|
123
|
-
const response = await this.http.post(`/vaults/${vaultId}/upload/portal/disable`);
|
|
143
|
+
const response = await this.http.post(apiPath `/vaults/${vaultId}/upload/portal/disable`);
|
|
124
144
|
return response.data;
|
|
125
145
|
}
|
|
126
146
|
async enableUploadWidget(vaultId, vmk) {
|
|
127
147
|
validateVaultId(vaultId);
|
|
128
|
-
const response = await this.http.post(`/vaults/${vaultId}/upload/widget/enable`, {
|
|
148
|
+
const response = await this.http.post(apiPath `/vaults/${vaultId}/upload/widget/enable`, {
|
|
129
149
|
vmk,
|
|
130
150
|
});
|
|
131
151
|
return response.data;
|
|
132
152
|
}
|
|
133
153
|
async disableUploadWidget(vaultId) {
|
|
134
154
|
validateVaultId(vaultId);
|
|
135
|
-
const response = await this.http.post(`/vaults/${vaultId}/upload/widget/disable`);
|
|
155
|
+
const response = await this.http.post(apiPath `/vaults/${vaultId}/upload/widget/disable`);
|
|
136
156
|
return response.data;
|
|
137
157
|
}
|
|
138
158
|
async updateUploadConfig(vaultId, config) {
|
|
139
159
|
validateVaultId(vaultId);
|
|
140
|
-
const response = await this.http.put(`/vaults/${vaultId}/upload`, config);
|
|
160
|
+
const response = await this.http.put(apiPath `/vaults/${vaultId}/upload`, config);
|
|
141
161
|
return response.data;
|
|
142
162
|
}
|
|
143
163
|
}
|
package/dist/vaults.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"vaults.js","sourceRoot":"","sources":["../src/vaults.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"vaults.js","sourceRoot":"","sources":["../src/vaults.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Vault and folder wire-contract assertions — COMPILE-TIME ONLY.
|
|
3
|
+
*
|
|
4
|
+
* These types have no runtime, so a unit test can never catch them drifting from
|
|
5
|
+
* the server: the transpiler strips them and every assertion passes. `tsc
|
|
6
|
+
* --noEmit` (`pnpm typecheck`) is the gate instead. It is deliberately NOT a
|
|
7
|
+
* `*.test.ts`, which tsconfig excludes.
|
|
8
|
+
*
|
|
9
|
+
* Mirrored server sources: apps/api/src/folders/list.js (listFolders answers
|
|
10
|
+
* `{ folders }`, the whole list and nothing else) and apps/api/src/vaults/list.js
|
|
11
|
+
* (one page: `{ vaults, count, has_more, next_cursor? }`).
|
|
12
|
+
*/
|
|
13
|
+
import type { ListFoldersResponse, ListVaultsResponse } from './types.js';
|
|
14
|
+
/** Fails to compile unless `T` resolves to exactly `true`. */
|
|
15
|
+
type Assert<T extends true> = T;
|
|
16
|
+
/** Invariant type equality: the SAME type, not merely mutually assignable. */
|
|
17
|
+
type Equals<A, B> = (<T>() => T extends A ? 1 : 2) extends <T>() => T extends B ? 1 : 2 ? true : false;
|
|
18
|
+
export type VaultsWireContract = [
|
|
19
|
+
Assert<Equals<keyof ListFoldersResponse, 'folders'>>,
|
|
20
|
+
Assert<Equals<keyof ListVaultsResponse, 'vaults' | 'count' | 'has_more' | 'next_cursor'>>
|
|
21
|
+
];
|
|
22
|
+
export {};
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Vault and folder wire-contract assertions — COMPILE-TIME ONLY.
|
|
3
|
+
*
|
|
4
|
+
* These types have no runtime, so a unit test can never catch them drifting from
|
|
5
|
+
* the server: the transpiler strips them and every assertion passes. `tsc
|
|
6
|
+
* --noEmit` (`pnpm typecheck`) is the gate instead. It is deliberately NOT a
|
|
7
|
+
* `*.test.ts`, which tsconfig excludes.
|
|
8
|
+
*
|
|
9
|
+
* Mirrored server sources: apps/api/src/folders/list.js (listFolders answers
|
|
10
|
+
* `{ folders }`, the whole list and nothing else) and apps/api/src/vaults/list.js
|
|
11
|
+
* (one page: `{ vaults, count, has_more, next_cursor? }`).
|
|
12
|
+
*/
|
|
13
|
+
export {};
|
|
14
|
+
//# sourceMappingURL=vaults.test-d.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"vaults.test-d.js","sourceRoot":"","sources":["../src/vaults.test-d.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;GAWG"}
|