@calimero-network/mero-js 26.11.0 → 27.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 +73 -288
- package/dist/cloud-v2/attestation.d.ts +91 -0
- package/dist/cloud-v2/attestation.js +135 -0
- package/dist/cloud-v2/capabilities.d.ts +30 -0
- package/dist/cloud-v2/capabilities.js +31 -0
- package/dist/cloud-v2/client.d.ts +426 -0
- package/dist/cloud-v2/client.js +646 -0
- package/dist/cloud-v2/errors.d.ts +98 -0
- package/dist/cloud-v2/errors.js +165 -0
- package/dist/cloud-v2/index.d.ts +10 -0
- package/dist/cloud-v2/index.js +5 -0
- package/dist/cloud-v2/passkey.d.ts +27 -0
- package/dist/cloud-v2/passkey.js +73 -0
- package/dist/crypto/internal.d.ts +3 -37
- package/dist/crypto/internal.js +3 -72
- package/dist/index.browser.mjs +4 -2
- package/dist/index.browser.mjs.map +4 -4
- package/dist/index.cjs +1750 -12772
- package/dist/index.cjs.map +4 -4
- package/dist/index.d.ts +3 -56
- package/dist/index.js +14 -75
- package/dist/index.mjs +1750 -12772
- package/dist/index.mjs.map +4 -4
- package/dist/sealed/index.d.ts +4 -4
- package/dist/sealed/index.js +2 -2
- package/dist/sealed/release.d.ts +21 -76
- package/dist/sealed/release.js +24 -108
- package/dist/sealed/sealed.d.ts +8 -56
- package/dist/sealed/sealed.js +11 -89
- package/dist/sealed/verify.d.ts +7 -13
- package/dist/sealed/verify.js +3 -7
- package/package.json +8 -13
- package/dist/account/account-admin.d.ts +0 -80
- package/dist/account/account-admin.js +0 -346
- package/dist/account/account.d.ts +0 -196
- package/dist/account/account.js +0 -269
- package/dist/account/application-id.d.ts +0 -50
- package/dist/account/application-id.js +0 -83
- package/dist/account/bootstrap-from-invitation.d.ts +0 -110
- package/dist/account/bootstrap-from-invitation.js +0 -80
- package/dist/account/create-context.d.ts +0 -103
- package/dist/account/create-context.js +0 -267
- package/dist/account/govern.d.ts +0 -24
- package/dist/account/govern.js +0 -50
- package/dist/account/index.d.ts +0 -26
- package/dist/account/index.js +0 -15
- package/dist/account/join-as-account.d.ts +0 -23
- package/dist/account/join-as-account.js +0 -34
- package/dist/account/join-with-node.d.ts +0 -115
- package/dist/account/join-with-node.js +0 -161
- package/dist/account/node-admin.d.ts +0 -20
- package/dist/account/node-admin.js +0 -33
- package/dist/account/relay-from-invitation.d.ts +0 -137
- package/dist/account/relay-from-invitation.js +0 -180
- package/dist/account/relay-login-error.d.ts +0 -32
- package/dist/account/relay-login-error.js +0 -34
- package/dist/account/session.d.ts +0 -266
- package/dist/account/session.js +0 -915
- package/dist/account/wordlist.d.ts +0 -16
- package/dist/account/wordlist.js +0 -273
- package/dist/admin-api/admin-client.d.ts +0 -688
- package/dist/admin-api/admin-client.js +0 -1230
- package/dist/admin-api/admin-factory.d.ts +0 -14
- package/dist/admin-api/admin-factory.js +0 -22
- package/dist/admin-api/admin-types.d.ts +0 -2046
- package/dist/admin-api/admin-types.js +0 -12
- package/dist/admin-api/index.d.ts +0 -4
- package/dist/admin-api/index.js +0 -5
- package/dist/admin-api/redeem-invitation.d.ts +0 -101
- package/dist/admin-api/redeem-invitation.js +0 -200
- package/dist/auth/index.d.ts +0 -34
- package/dist/auth/index.js +0 -67
- package/dist/auth-api/auth-client.d.ts +0 -31
- package/dist/auth-api/auth-client.js +0 -117
- package/dist/auth-api/auth-factory.d.ts +0 -7
- package/dist/auth-api/auth-factory.js +0 -41
- package/dist/auth-api/auth-types.d.ts +0 -130
- package/dist/auth-api/auth-types.js +0 -2
- package/dist/auth-api/index.d.ts +0 -3
- package/dist/auth-api/index.js +0 -4
- package/dist/capabilities.d.ts +0 -84
- package/dist/capabilities.js +0 -117
- package/dist/cloud/account-ownership.d.ts +0 -63
- package/dist/cloud/account-ownership.js +0 -87
- package/dist/cloud/cloud-client.d.ts +0 -949
- package/dist/cloud/cloud-client.js +0 -1068
- package/dist/cloud/connect.d.ts +0 -213
- package/dist/cloud/connect.js +0 -260
- package/dist/cloud/enrol-redirect.d.ts +0 -181
- package/dist/cloud/enrol-redirect.js +0 -244
- package/dist/cloud/index.d.ts +0 -12
- package/dist/cloud/index.js +0 -10
- package/dist/cloud/link-redirect.d.ts +0 -95
- package/dist/cloud/link-redirect.js +0 -121
- package/dist/cloud/link-state.d.ts +0 -36
- package/dist/cloud/link-state.js +0 -104
- package/dist/cloud/routing-proof.d.ts +0 -113
- package/dist/cloud/routing-proof.js +0 -96
- package/dist/device-cert/device-cert.d.ts +0 -189
- package/dist/device-cert/device-cert.js +0 -239
- package/dist/device-cert/device-scope.d.ts +0 -58
- package/dist/device-cert/device-scope.js +0 -76
- package/dist/device-cert/index.d.ts +0 -4
- package/dist/device-cert/index.js +0 -3
- package/dist/ephemeral/codec.d.ts +0 -4
- package/dist/ephemeral/codec.js +0 -12
- package/dist/ephemeral/index.d.ts +0 -57
- package/dist/ephemeral/index.js +0 -101
- package/dist/ephemeral/types.d.ts +0 -27
- package/dist/ephemeral/types.js +0 -1
- package/dist/errors/classify.d.ts +0 -65
- package/dist/errors/classify.js +0 -117
- package/dist/errors/index.d.ts +0 -2
- package/dist/errors/index.js +0 -1
- package/dist/events/group.d.ts +0 -95
- package/dist/events/group.js +0 -10
- package/dist/events/index.d.ts +0 -5
- package/dist/events/index.js +0 -2
- package/dist/events/sse.d.ts +0 -127
- package/dist/events/sse.js +0 -469
- package/dist/events/ws.d.ts +0 -57
- package/dist/events/ws.js +0 -212
- package/dist/http-client/api-response.d.ts +0 -15
- package/dist/http-client/api-response.js +0 -1
- package/dist/http-client/http-factory.d.ts +0 -71
- package/dist/http-client/http-factory.js +0 -68
- package/dist/http-client/http-types.d.ts +0 -87
- package/dist/http-client/http-types.js +0 -1
- package/dist/http-client/index.d.ts +0 -7
- package/dist/http-client/index.js +0 -11
- package/dist/http-client/path-segment.d.ts +0 -1
- package/dist/http-client/path-segment.js +0 -8
- package/dist/http-client/retry.d.ts +0 -5
- package/dist/http-client/retry.js +0 -82
- package/dist/http-client/signal-utils.d.ts +0 -2
- package/dist/http-client/signal-utils.js +0 -41
- package/dist/http-client/web-client.d.ts +0 -80
- package/dist/http-client/web-client.js +0 -557
- package/dist/invitation/index.d.ts +0 -2
- package/dist/invitation/index.js +0 -2
- package/dist/invitation/invitation.d.ts +0 -106
- package/dist/invitation/invitation.js +0 -104
- package/dist/login/index.d.ts +0 -4
- package/dist/login/index.js +0 -3
- package/dist/login/login.d.ts +0 -111
- package/dist/login/login.js +0 -110
- package/dist/login/session.d.ts +0 -124
- package/dist/login/session.js +0 -141
- package/dist/mero-js.d.ts +0 -231
- package/dist/mero-js.js +0 -469
- package/dist/namespace-op/index.d.ts +0 -2
- package/dist/namespace-op/index.js +0 -3
- package/dist/namespace-op/namespace-op.d.ts +0 -150
- package/dist/namespace-op/namespace-op.js +0 -191
- package/dist/nodeDiscovery.d.ts +0 -47
- package/dist/nodeDiscovery.js +0 -101
- package/dist/owner-op/index.d.ts +0 -2
- package/dist/owner-op/index.js +0 -3
- package/dist/owner-op/owner-op.d.ts +0 -119
- package/dist/owner-op/owner-op.js +0 -214
- package/dist/presence/relay-presence.d.ts +0 -56
- package/dist/presence/relay-presence.js +0 -107
- package/dist/presence/statement.d.ts +0 -12
- package/dist/presence/statement.js +0 -17
- package/dist/relay/index.d.ts +0 -4
- package/dist/relay/index.js +0 -2
- package/dist/relay/nonce-source.d.ts +0 -72
- package/dist/relay/nonce-source.js +0 -111
- package/dist/relay/relay-client.d.ts +0 -472
- package/dist/relay/relay-client.js +0 -518
- package/dist/relay-attestation/attest-node-key.d.ts +0 -66
- package/dist/relay-attestation/attest-node-key.js +0 -110
- package/dist/relay-attestation/index.d.ts +0 -1
- package/dist/relay-attestation/index.js +0 -1
- package/dist/request/caller-proof.d.ts +0 -43
- package/dist/request/caller-proof.js +0 -36
- package/dist/request/index.d.ts +0 -3
- package/dist/request/index.js +0 -3
- package/dist/request/proof-signer.d.ts +0 -49
- package/dist/request/proof-signer.js +0 -59
- package/dist/request/request-sig.d.ts +0 -99
- package/dist/request/request-sig.js +0 -95
- package/dist/request-proof/authorizer.d.ts +0 -41
- package/dist/request-proof/authorizer.js +0 -60
- package/dist/request-proof/index.d.ts +0 -4
- package/dist/request-proof/index.js +0 -2
- package/dist/request-proof/request-proof.d.ts +0 -53
- package/dist/request-proof/request-proof.js +0 -95
- package/dist/rpc/index.d.ts +0 -64
- package/dist/rpc/index.js +0 -78
- package/dist/signer/index.d.ts +0 -2
- package/dist/signer/index.js +0 -3
- package/dist/signer/signer.d.ts +0 -92
- package/dist/signer/signer.js +0 -147
- package/dist/token-store/index.d.ts +0 -27
- package/dist/token-store/index.js +0 -62
- package/dist/transport/index.d.ts +0 -6
- package/dist/transport/index.js +0 -3
- package/dist/transport/mero-client.d.ts +0 -294
- package/dist/transport/mero-client.js +0 -386
- package/dist/transport/relay-observer.d.ts +0 -152
- package/dist/transport/relay-observer.js +0 -173
- package/dist/transport/relay-transport.d.ts +0 -73
- package/dist/transport/relay-transport.js +0 -94
- package/dist/transport/types.d.ts +0 -100
- package/dist/transport/types.js +0 -32
- package/dist/types/api-response.d.ts +0 -15
- package/dist/types/api-response.js +0 -1
- package/dist/types/index.d.ts +0 -1
- package/dist/types/index.js +0 -1
- package/dist/warrant/creation-warrant.d.ts +0 -163
- package/dist/warrant/creation-warrant.js +0 -194
- package/dist/warrant/governance-op.d.ts +0 -202
- package/dist/warrant/governance-op.js +0 -355
- package/dist/warrant/governance-warrant.d.ts +0 -124
- package/dist/warrant/governance-warrant.js +0 -164
- package/dist/warrant/index.d.ts +0 -8
- package/dist/warrant/index.js +0 -5
- package/dist/warrant/warrant.d.ts +0 -188
- package/dist/warrant/warrant.js +0 -202
|
@@ -1,53 +0,0 @@
|
|
|
1
|
-
import type { Signer } from '../signer/index.js';
|
|
2
|
-
/** The header a signed request carries. */
|
|
3
|
-
export declare const REQUEST_PROOF_HEADER = "X-Calimero-Proof";
|
|
4
|
-
export interface RequestProofInput {
|
|
5
|
-
/**
|
|
6
|
-
* The HTTP method, exactly as it will be sent.
|
|
7
|
-
*
|
|
8
|
-
* Not folded. `HEAD` and `GET` are the same *permission* and the node's
|
|
9
|
-
* permission table treats them so, but they are different *requests*: folding
|
|
10
|
-
* them here would let a proof minted for one be presented as the other.
|
|
11
|
-
*/
|
|
12
|
-
method: string;
|
|
13
|
-
/**
|
|
14
|
-
* The path and query, exactly as on the request line, with no re-encoding or
|
|
15
|
-
* reordering. Use `signedPath` to take it from a URL.
|
|
16
|
-
*/
|
|
17
|
-
path: string;
|
|
18
|
-
/**
|
|
19
|
-
* The body, exactly as it will be sent. Omit when there is none.
|
|
20
|
-
*
|
|
21
|
-
* There is no "absent body" case: an omitted body commits to the hash of no
|
|
22
|
-
* bytes, so a signer and a verifier cannot disagree about which encoding a
|
|
23
|
-
* bodyless request used.
|
|
24
|
-
*/
|
|
25
|
-
body?: string | Uint8Array;
|
|
26
|
-
/** The `AccountProof<DeviceCert>` from `signDeviceCert`, hex. */
|
|
27
|
-
credential: string;
|
|
28
|
-
/** The certified device's ed25519 secret, hex. Or pass `signer`. */
|
|
29
|
-
deviceSecret?: string;
|
|
30
|
-
/** A signer, for a key that cannot be exported to hex. */
|
|
31
|
-
signer?: Signer;
|
|
32
|
-
/** Seconds the signature stays valid. Defaults to 300. */
|
|
33
|
-
validForSeconds?: number;
|
|
34
|
-
/** Override the clock, for tests. Unix seconds. */
|
|
35
|
-
now?: number;
|
|
36
|
-
}
|
|
37
|
-
/**
|
|
38
|
-
* Sign one request and return the `X-Calimero-Proof` value, hex.
|
|
39
|
-
*
|
|
40
|
-
* The encoding is borsh, and it is assembled rather than re-derived: the
|
|
41
|
-
* account proof is the **first** field of `CallerProof`, so the credential hex
|
|
42
|
-
* a caller already holds is exactly its own prefix. Concatenating avoids a
|
|
43
|
-
* second implementation of a structure the node deserializes — the class of bug
|
|
44
|
-
* that surfaces far away, as a node refusing a credential nothing can explain.
|
|
45
|
-
*
|
|
46
|
-
* CallerProof = <account_proof bytes> || 0x00 (no session) || RequestSig
|
|
47
|
-
* RequestSig = u32le(len method) || method
|
|
48
|
-
* || u32le(len path) || path (with its query)
|
|
49
|
-
* || body_hash[32]
|
|
50
|
-
* || u64le(issued_at) || u64le(expires_at)
|
|
51
|
-
* || signature[64]
|
|
52
|
-
*/
|
|
53
|
-
export declare function signRequestProof(input: RequestProofInput): Promise<string>;
|
|
@@ -1,95 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Signing one request, so a caller's identity travels with it.
|
|
3
|
-
*
|
|
4
|
-
* This is the credential a keyholder presents when it has no session: the device
|
|
5
|
-
* key signs the request itself, and the certificate its account signed says whose
|
|
6
|
-
* key that is. The node verifies both with no store read and no prior
|
|
7
|
-
* relationship — `crates/server/src/proof_auth.rs` — which is what lets a hosted
|
|
8
|
-
* relay serve a caller it has never seen and holds no auth provider for.
|
|
9
|
-
*
|
|
10
|
-
* ## Why this exists alongside `login()`
|
|
11
|
-
*
|
|
12
|
-
* A session is a second link in the same chain, not an alternative to it. It
|
|
13
|
-
* earns its place where the device key sits behind a boundary worth crossing
|
|
14
|
-
* once — a hardware key, an extension — so a per-call signature becomes a
|
|
15
|
-
* per-session one. A CLI, a server job, or a browser holding its device secret
|
|
16
|
-
* in memory gains nothing from it, and `login()` additionally needs the node's
|
|
17
|
-
* signing key learned out of band. This path needs neither.
|
|
18
|
-
*
|
|
19
|
-
* Measured against a node built from core `aecba573b`: a two-link proof is
|
|
20
|
-
* served `200` on `/admin-api/namespaces`, `/contexts`, `/contexts/{id}`,
|
|
21
|
-
* `/groups/{id}`, `/groups/{id}/contexts`, `/contexts/{id}/identities` and
|
|
22
|
-
* `/storage`, and the listings are **filtered** — an account in one of a node's
|
|
23
|
-
* two namespaces is shown one. `POST /admin-api/namespaces` is refused `403`, so
|
|
24
|
-
* this authenticates a caller without granting operator actions.
|
|
25
|
-
*/
|
|
26
|
-
import { concat, domainHash, fromHex, hex, importSigningKey, u32le, u64le, } from '../crypto/internal.js';
|
|
27
|
-
import { requestBodyHash, SIGN_DOMAIN } from '../request/request-sig.js';
|
|
28
|
-
const utf8 = (text) => new TextEncoder().encode(text);
|
|
29
|
-
/** The header a signed request carries. */
|
|
30
|
-
export const REQUEST_PROOF_HEADER = 'X-Calimero-Proof';
|
|
31
|
-
/** Seconds a signature stays honourable. Short, because it bounds replay. */
|
|
32
|
-
const DEFAULT_VALID_FOR = 300;
|
|
33
|
-
/**
|
|
34
|
-
* Sign one request and return the `X-Calimero-Proof` value, hex.
|
|
35
|
-
*
|
|
36
|
-
* The encoding is borsh, and it is assembled rather than re-derived: the
|
|
37
|
-
* account proof is the **first** field of `CallerProof`, so the credential hex
|
|
38
|
-
* a caller already holds is exactly its own prefix. Concatenating avoids a
|
|
39
|
-
* second implementation of a structure the node deserializes — the class of bug
|
|
40
|
-
* that surfaces far away, as a node refusing a credential nothing can explain.
|
|
41
|
-
*
|
|
42
|
-
* CallerProof = <account_proof bytes> || 0x00 (no session) || RequestSig
|
|
43
|
-
* RequestSig = u32le(len method) || method
|
|
44
|
-
* || u32le(len path) || path (with its query)
|
|
45
|
-
* || body_hash[32]
|
|
46
|
-
* || u64le(issued_at) || u64le(expires_at)
|
|
47
|
-
* || signature[64]
|
|
48
|
-
*/
|
|
49
|
-
export async function signRequestProof(input) {
|
|
50
|
-
const { method, path, credential } = input;
|
|
51
|
-
if (!method)
|
|
52
|
-
throw new Error('signRequestProof needs the method the request will use');
|
|
53
|
-
if (!path.startsWith('/')) {
|
|
54
|
-
throw new Error(`signRequestProof needs a path, got ${JSON.stringify(path)}`);
|
|
55
|
-
}
|
|
56
|
-
const bodyHash = await requestBodyHash(input.body);
|
|
57
|
-
const issuedAt = Math.floor(input.now ?? Date.now() / 1000);
|
|
58
|
-
const expiresAt = issuedAt + (input.validForSeconds ?? DEFAULT_VALID_FOR);
|
|
59
|
-
const payload = await domainHash(SIGN_DOMAIN, [
|
|
60
|
-
utf8(method),
|
|
61
|
-
utf8(path),
|
|
62
|
-
bodyHash,
|
|
63
|
-
u64le(issuedAt),
|
|
64
|
-
u64le(expiresAt),
|
|
65
|
-
]);
|
|
66
|
-
const signature = await signPayload(payload, input);
|
|
67
|
-
if (signature.length !== 64) {
|
|
68
|
-
throw new Error(`the signer returned ${signature.length} bytes, not a 64-byte signature`);
|
|
69
|
-
}
|
|
70
|
-
const requestSig = concat(u32le(utf8(method).length), utf8(method), u32le(utf8(path).length), utf8(path), bodyHash, u64le(issuedAt), u64le(expiresAt), signature);
|
|
71
|
-
// The credential IS the account-proof prefix. Length is not asserted: it varies
|
|
72
|
-
// with the handoff chain, and a wrong one fails as a refused proof rather than
|
|
73
|
-
// silently as something else.
|
|
74
|
-
const accountProof = hexToBytes(credential, 'credential');
|
|
75
|
-
// 0x00: borsh's `None`. The device key signed the request, so there is no
|
|
76
|
-
// session link — a different encoding, not a shorter one.
|
|
77
|
-
return hex(concat(accountProof, new Uint8Array([0]), requestSig));
|
|
78
|
-
}
|
|
79
|
-
async function signPayload(payload, input) {
|
|
80
|
-
if (input.signer)
|
|
81
|
-
return input.signer.sign(payload);
|
|
82
|
-
if (!input.deviceSecret) {
|
|
83
|
-
throw new Error('signRequestProof needs either `deviceSecret` or `signer`');
|
|
84
|
-
}
|
|
85
|
-
const key = await importSigningKey(input.deviceSecret);
|
|
86
|
-
return new Uint8Array(await crypto.subtle.sign({ name: 'Ed25519' }, key, payload));
|
|
87
|
-
}
|
|
88
|
-
/** Hex of unknown length — `fromHex` requires a fixed byte count. */
|
|
89
|
-
function hexToBytes(value, label) {
|
|
90
|
-
const clean = value.trim();
|
|
91
|
-
if (!/^[0-9a-fA-F]*$/.test(clean) || clean.length % 2 !== 0) {
|
|
92
|
-
throw new Error(`${label} is not an even-length hex string`);
|
|
93
|
-
}
|
|
94
|
-
return fromHex(clean, label, clean.length / 2);
|
|
95
|
-
}
|
package/dist/rpc/index.d.ts
DELETED
|
@@ -1,64 +0,0 @@
|
|
|
1
|
-
import type { HttpClient } from '../http-client/index.js';
|
|
2
|
-
/** Result of the owner-driven `migrate_my_entries` convert (counts are u32). */
|
|
3
|
-
export interface MigrateMyEntriesSummary {
|
|
4
|
-
converted: number;
|
|
5
|
-
remaining: number;
|
|
6
|
-
}
|
|
7
|
-
export interface ExecuteParams {
|
|
8
|
-
contextId: string;
|
|
9
|
-
method: string;
|
|
10
|
-
argsJson?: Record<string, unknown>;
|
|
11
|
-
/** @deprecated No longer used by the server. Ignored if provided. */
|
|
12
|
-
executorPublicKey?: string;
|
|
13
|
-
}
|
|
14
|
-
export declare class RpcError extends Error {
|
|
15
|
-
code: number;
|
|
16
|
-
type?: string;
|
|
17
|
-
data?: unknown;
|
|
18
|
-
constructor(code: number, message: string, data?: unknown, type?: string);
|
|
19
|
-
}
|
|
20
|
-
/**
|
|
21
|
-
* POST a JSON-RPC call and unwrap `result`, converting an `error` payload into
|
|
22
|
-
* an `RpcError`. The node returns `{ type, data }` (not always `{ code,
|
|
23
|
-
* message }`), so this is the one place that normalization lives — every
|
|
24
|
-
* JSON-RPC caller in this SDK shares it rather than re-deriving a bare
|
|
25
|
-
* `Error(message)` and dropping the typed detail.
|
|
26
|
-
*/
|
|
27
|
-
export declare function jsonRpcCall<T>(httpClient: HttpClient, method: string, params: unknown): Promise<T>;
|
|
28
|
-
export declare class RpcClient {
|
|
29
|
-
private httpClient;
|
|
30
|
-
/**
|
|
31
|
-
* Which write path this is. Present so `RpcClient` satisfies
|
|
32
|
-
* `ExecuteTransport` as-is — the transport abstraction adopted *this* class's
|
|
33
|
-
* `execute` shape as the canonical one, so the node side is the interface
|
|
34
|
-
* rather than an adapter onto it.
|
|
35
|
-
*/
|
|
36
|
-
readonly kind: "node";
|
|
37
|
-
/** A node serves `/sse` and `/ws` to the credential it issued. */
|
|
38
|
-
readonly canSubscribe = true;
|
|
39
|
-
constructor(opts: {
|
|
40
|
-
httpClient: HttpClient;
|
|
41
|
-
});
|
|
42
|
-
execute<T = unknown>(params: ExecuteParams): Promise<T>;
|
|
43
|
-
/**
|
|
44
|
-
* The same call, in the shape the transport abstraction shares with the
|
|
45
|
-
* relay.
|
|
46
|
-
*
|
|
47
|
-
* `rootHash` is left absent rather than synthesized: JSON-RPC `execute` does
|
|
48
|
-
* not report the context's scope root, and inventing a value — or a `''` —
|
|
49
|
-
* would make "the node does not tell us" indistinguishable from an answer.
|
|
50
|
-
*/
|
|
51
|
-
executeWithMetadata<T = unknown>(params: ExecuteParams): Promise<{
|
|
52
|
-
returns: T;
|
|
53
|
-
transport: 'node';
|
|
54
|
-
}>;
|
|
55
|
-
/**
|
|
56
|
-
* One-tap owner-driven convert: re-signs the caller's identity-gated entries
|
|
57
|
-
* to the current schema. The export converts all of the caller's
|
|
58
|
-
* below-target entries in a single sweep, so this issues one call and returns
|
|
59
|
-
* the resulting summary — it does not loop.
|
|
60
|
-
*/
|
|
61
|
-
migrateMyEntries(contextId: string): Promise<MigrateMyEntriesSummary>;
|
|
62
|
-
/** Read-only count of the caller's entries still below the target schema. */
|
|
63
|
-
countMyPending(contextId: string): Promise<number>;
|
|
64
|
-
}
|
package/dist/rpc/index.js
DELETED
|
@@ -1,78 +0,0 @@
|
|
|
1
|
-
export class RpcError extends Error {
|
|
2
|
-
constructor(code, message, data, type) {
|
|
3
|
-
super(message);
|
|
4
|
-
this.name = 'RpcError';
|
|
5
|
-
this.code = code;
|
|
6
|
-
this.data = data;
|
|
7
|
-
this.type = type;
|
|
8
|
-
}
|
|
9
|
-
}
|
|
10
|
-
/**
|
|
11
|
-
* POST a JSON-RPC call and unwrap `result`, converting an `error` payload into
|
|
12
|
-
* an `RpcError`. The node returns `{ type, data }` (not always `{ code,
|
|
13
|
-
* message }`), so this is the one place that normalization lives — every
|
|
14
|
-
* JSON-RPC caller in this SDK shares it rather than re-deriving a bare
|
|
15
|
-
* `Error(message)` and dropping the typed detail.
|
|
16
|
-
*/
|
|
17
|
-
export async function jsonRpcCall(httpClient, method, params) {
|
|
18
|
-
const response = await httpClient.post('/jsonrpc', {
|
|
19
|
-
jsonrpc: '2.0',
|
|
20
|
-
id: 1,
|
|
21
|
-
method,
|
|
22
|
-
params,
|
|
23
|
-
});
|
|
24
|
-
if (response.error) {
|
|
25
|
-
const err = response.error;
|
|
26
|
-
throw new RpcError(err.code ?? -1, err.message ?? err.type ?? 'RPC error', err.data, err.type);
|
|
27
|
-
}
|
|
28
|
-
return response.result;
|
|
29
|
-
}
|
|
30
|
-
export class RpcClient {
|
|
31
|
-
constructor(opts) {
|
|
32
|
-
/**
|
|
33
|
-
* Which write path this is. Present so `RpcClient` satisfies
|
|
34
|
-
* `ExecuteTransport` as-is — the transport abstraction adopted *this* class's
|
|
35
|
-
* `execute` shape as the canonical one, so the node side is the interface
|
|
36
|
-
* rather than an adapter onto it.
|
|
37
|
-
*/
|
|
38
|
-
this.kind = 'node';
|
|
39
|
-
/** A node serves `/sse` and `/ws` to the credential it issued. */
|
|
40
|
-
this.canSubscribe = true;
|
|
41
|
-
this.httpClient = opts.httpClient;
|
|
42
|
-
}
|
|
43
|
-
async execute(params) {
|
|
44
|
-
const result = await jsonRpcCall(this.httpClient, 'execute', {
|
|
45
|
-
contextId: params.contextId,
|
|
46
|
-
method: params.method,
|
|
47
|
-
argsJson: params.argsJson ?? {},
|
|
48
|
-
});
|
|
49
|
-
if (result && 'output' in result) {
|
|
50
|
-
return result.output;
|
|
51
|
-
}
|
|
52
|
-
return result;
|
|
53
|
-
}
|
|
54
|
-
/**
|
|
55
|
-
* The same call, in the shape the transport abstraction shares with the
|
|
56
|
-
* relay.
|
|
57
|
-
*
|
|
58
|
-
* `rootHash` is left absent rather than synthesized: JSON-RPC `execute` does
|
|
59
|
-
* not report the context's scope root, and inventing a value — or a `''` —
|
|
60
|
-
* would make "the node does not tell us" indistinguishable from an answer.
|
|
61
|
-
*/
|
|
62
|
-
async executeWithMetadata(params) {
|
|
63
|
-
return { returns: await this.execute(params), transport: 'node' };
|
|
64
|
-
}
|
|
65
|
-
/**
|
|
66
|
-
* One-tap owner-driven convert: re-signs the caller's identity-gated entries
|
|
67
|
-
* to the current schema. The export converts all of the caller's
|
|
68
|
-
* below-target entries in a single sweep, so this issues one call and returns
|
|
69
|
-
* the resulting summary — it does not loop.
|
|
70
|
-
*/
|
|
71
|
-
async migrateMyEntries(contextId) {
|
|
72
|
-
return this.execute({ contextId, method: 'migrate_my_entries' });
|
|
73
|
-
}
|
|
74
|
-
/** Read-only count of the caller's entries still below the target schema. */
|
|
75
|
-
async countMyPending(contextId) {
|
|
76
|
-
return this.execute({ contextId, method: 'count_my_pending' });
|
|
77
|
-
}
|
|
78
|
-
}
|
package/dist/signer/index.d.ts
DELETED
package/dist/signer/index.js
DELETED
package/dist/signer/signer.d.ts
DELETED
|
@@ -1,92 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Who signs, separated from what is signed.
|
|
3
|
-
*
|
|
4
|
-
* Every signing entry point in this package used to take 32 hex bytes. That is
|
|
5
|
-
* fine for a CLI or a server holding a key file, and it is the one thing a
|
|
6
|
-
* browser must not do: a secret that exists as a string can be read by anything
|
|
7
|
-
* running on the origin, and a stolen account key is the account — permanently,
|
|
8
|
-
* because unlike a device key there is nothing above it to revoke it with.
|
|
9
|
-
*
|
|
10
|
-
* WebCrypto can hold an Ed25519 key that **signs but cannot be exported**
|
|
11
|
-
* (`generateKey(..., extractable: false, ...)`). Such a key has no hex
|
|
12
|
-
* representation to pass, so it could not be used with this package at all —
|
|
13
|
-
* which pushed consumers into reimplementing core's wire formats around their
|
|
14
|
-
* own key. That is the failure `crates/account/src/tests/sdk_credential_fixture.rs`
|
|
15
|
-
* exists to document: a second implementation of a byte contract agreed with
|
|
16
|
-
* itself for a full release while core rejected every credential it produced.
|
|
17
|
-
*
|
|
18
|
-
* So the interface is the key's *capability*, not its material:
|
|
19
|
-
*
|
|
20
|
-
* ```ts
|
|
21
|
-
* const signer = await signerFromSecret(deviceSecret); // as before
|
|
22
|
-
* const signer = await signerFromCryptoKey(privateKey, pubKey); // unexportable
|
|
23
|
-
* await signWarrant({ ...terms, signer });
|
|
24
|
-
* ```
|
|
25
|
-
*
|
|
26
|
-
* `deviceSecret` and `rootSecret` keep working everywhere they did. They are
|
|
27
|
-
* now one way of producing a `Signer` rather than the only way, and callers
|
|
28
|
-
* that pass a secret get a signer built for them.
|
|
29
|
-
*/
|
|
30
|
-
/**
|
|
31
|
-
* Something that can produce Ed25519 signatures and name the key they verify
|
|
32
|
-
* against.
|
|
33
|
-
*
|
|
34
|
-
* Deliberately the smallest surface that works: a signature and the public key
|
|
35
|
-
* it belongs to. Anything larger would start describing *how* the key is held,
|
|
36
|
-
* which is the detail this exists to hide — a hex seed, a non-extractable
|
|
37
|
-
* `CryptoKey`, a hardware token behind an async prompt, and a remote signing
|
|
38
|
-
* service all satisfy it.
|
|
39
|
-
*/
|
|
40
|
-
export interface Signer {
|
|
41
|
-
/**
|
|
42
|
-
* The public half, 64 hex characters.
|
|
43
|
-
*
|
|
44
|
-
* Carried rather than derived on demand because a non-extractable private key
|
|
45
|
-
* cannot produce it: the public half has to be captured when the key is
|
|
46
|
-
* generated. A signer that could not name its key would force every caller to
|
|
47
|
-
* pass the public key alongside it, and the two could then disagree.
|
|
48
|
-
*/
|
|
49
|
-
readonly publicKey: string;
|
|
50
|
-
/**
|
|
51
|
-
* Sign `payload` — the exact bytes, with no hashing or framing added.
|
|
52
|
-
*
|
|
53
|
-
* Every caller in this package passes a 32-byte domain-separated digest it
|
|
54
|
-
* has already computed, and an implementation that hashed again would produce
|
|
55
|
-
* signatures that verify nowhere.
|
|
56
|
-
*/
|
|
57
|
-
sign(payload: Uint8Array): Promise<Uint8Array>;
|
|
58
|
-
}
|
|
59
|
-
/**
|
|
60
|
-
* A signer over a raw 32-byte Ed25519 seed, hex.
|
|
61
|
-
*
|
|
62
|
-
* The public half is derived from the seed rather than accepted alongside it,
|
|
63
|
-
* for the reason core does the same: a caller able to name a key it does not
|
|
64
|
-
* hold could produce a statement it cannot sign, and the field would stop
|
|
65
|
-
* meaning "who authorised this".
|
|
66
|
-
*
|
|
67
|
-
* @param secret the seed, 64 hex characters
|
|
68
|
-
* @param label what to call it in an error — `deviceSecret`, `rootSecret`
|
|
69
|
-
*/
|
|
70
|
-
export declare function signerFromSecret(secret: string, label?: string): Promise<Signer>;
|
|
71
|
-
/**
|
|
72
|
-
* A signer over a `CryptoKey` this process may use and cannot read.
|
|
73
|
-
*
|
|
74
|
-
* The point of the whole interface. Generate the key with
|
|
75
|
-
* `generateKey({ name: 'Ed25519' }, false, ['sign', 'verify'])`, keep the pair's
|
|
76
|
-
* private half (structured-clone it into IndexedDB if it must survive a reload),
|
|
77
|
-
* and pass it here with its public half.
|
|
78
|
-
*
|
|
79
|
-
* @param privateKey the signing key — extractable or not, it is never exported
|
|
80
|
-
* @param publicKey its public half: 64 hex, or the pair's `publicKey` (which
|
|
81
|
-
* WebCrypto leaves exportable even when the private half is not)
|
|
82
|
-
*/
|
|
83
|
-
export declare function signerFromCryptoKey(privateKey: CryptoKey, publicKey: string | CryptoKey): Promise<Signer>;
|
|
84
|
-
/**
|
|
85
|
-
* Resolve the signer an input describes, accepting either form.
|
|
86
|
-
*
|
|
87
|
-
* Internal. Every signing entry point takes an optional secret *and* an
|
|
88
|
-
* optional signer, and exactly one must be present — passing both is refused
|
|
89
|
-
* rather than silently preferring one, because the two could name different
|
|
90
|
-
* keys and the caller would have no way to tell which signed.
|
|
91
|
-
*/
|
|
92
|
-
export declare function resolveSigner(secret: string | undefined, signer: Signer | undefined, label: string): Promise<Signer>;
|
package/dist/signer/signer.js
DELETED
|
@@ -1,147 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Who signs, separated from what is signed.
|
|
3
|
-
*
|
|
4
|
-
* Every signing entry point in this package used to take 32 hex bytes. That is
|
|
5
|
-
* fine for a CLI or a server holding a key file, and it is the one thing a
|
|
6
|
-
* browser must not do: a secret that exists as a string can be read by anything
|
|
7
|
-
* running on the origin, and a stolen account key is the account — permanently,
|
|
8
|
-
* because unlike a device key there is nothing above it to revoke it with.
|
|
9
|
-
*
|
|
10
|
-
* WebCrypto can hold an Ed25519 key that **signs but cannot be exported**
|
|
11
|
-
* (`generateKey(..., extractable: false, ...)`). Such a key has no hex
|
|
12
|
-
* representation to pass, so it could not be used with this package at all —
|
|
13
|
-
* which pushed consumers into reimplementing core's wire formats around their
|
|
14
|
-
* own key. That is the failure `crates/account/src/tests/sdk_credential_fixture.rs`
|
|
15
|
-
* exists to document: a second implementation of a byte contract agreed with
|
|
16
|
-
* itself for a full release while core rejected every credential it produced.
|
|
17
|
-
*
|
|
18
|
-
* So the interface is the key's *capability*, not its material:
|
|
19
|
-
*
|
|
20
|
-
* ```ts
|
|
21
|
-
* const signer = await signerFromSecret(deviceSecret); // as before
|
|
22
|
-
* const signer = await signerFromCryptoKey(privateKey, pubKey); // unexportable
|
|
23
|
-
* await signWarrant({ ...terms, signer });
|
|
24
|
-
* ```
|
|
25
|
-
*
|
|
26
|
-
* `deviceSecret` and `rootSecret` keep working everywhere they did. They are
|
|
27
|
-
* now one way of producing a `Signer` rather than the only way, and callers
|
|
28
|
-
* that pass a secret get a signer built for them.
|
|
29
|
-
*/
|
|
30
|
-
import { concat, fromHex, hex } from '../crypto/internal.js';
|
|
31
|
-
/** Ed25519 PKCS#8 prefix, so a raw 32-byte seed can be imported by WebCrypto. */
|
|
32
|
-
const PKCS8_ED25519_PREFIX = new Uint8Array([
|
|
33
|
-
0x30, 0x2e, 0x02, 0x01, 0x00, 0x30, 0x05, 0x06, 0x03, 0x2b, 0x65, 0x70, 0x04,
|
|
34
|
-
0x22, 0x04, 0x20,
|
|
35
|
-
]);
|
|
36
|
-
/** Turn WebCrypto's bare `NotSupportedError` into something actionable. */
|
|
37
|
-
function unsupported(cause) {
|
|
38
|
-
// The original is folded into the message rather than passed as `cause`:
|
|
39
|
-
// this package targets ES2020, where `Error` has no `cause` option.
|
|
40
|
-
const detail = cause instanceof Error ? `: ${cause.message}` : '';
|
|
41
|
-
return new Error('this runtime has no WebCrypto Ed25519, so nothing can be signed here. ' +
|
|
42
|
-
'Node 18.4+, Safari 17+, Firefox 129+ and Chrome 137+ have it' +
|
|
43
|
-
detail);
|
|
44
|
-
}
|
|
45
|
-
/**
|
|
46
|
-
* A signer over a raw 32-byte Ed25519 seed, hex.
|
|
47
|
-
*
|
|
48
|
-
* The public half is derived from the seed rather than accepted alongside it,
|
|
49
|
-
* for the reason core does the same: a caller able to name a key it does not
|
|
50
|
-
* hold could produce a statement it cannot sign, and the field would stop
|
|
51
|
-
* meaning "who authorised this".
|
|
52
|
-
*
|
|
53
|
-
* @param secret the seed, 64 hex characters
|
|
54
|
-
* @param label what to call it in an error — `deviceSecret`, `rootSecret`
|
|
55
|
-
*/
|
|
56
|
-
export async function signerFromSecret(secret, label = 'secret') {
|
|
57
|
-
const seed = fromHex(secret, label, 32);
|
|
58
|
-
const pkcs8 = concat(PKCS8_ED25519_PREFIX, seed);
|
|
59
|
-
let privateKey;
|
|
60
|
-
let publicKey;
|
|
61
|
-
try {
|
|
62
|
-
// Imported twice on purpose: `extractable: true` is needed to read the
|
|
63
|
-
// public half out of a JWK, and the signing key is then re-imported
|
|
64
|
-
// unexportable so a `Signer` built from a secret is no more powerful than
|
|
65
|
-
// one built from a `CryptoKey`.
|
|
66
|
-
const exportable = await crypto.subtle.importKey('pkcs8', pkcs8, { name: 'Ed25519' }, true, ['sign']);
|
|
67
|
-
const jwk = (await crypto.subtle.exportKey('jwk', exportable));
|
|
68
|
-
publicKey = hex(Uint8Array.from(atob(jwk.x.replace(/-/g, '+').replace(/_/g, '/')), (c) => c.charCodeAt(0)));
|
|
69
|
-
privateKey = await crypto.subtle.importKey('pkcs8', pkcs8, { name: 'Ed25519' }, false, ['sign']);
|
|
70
|
-
}
|
|
71
|
-
catch (cause) {
|
|
72
|
-
throw unsupported(cause);
|
|
73
|
-
}
|
|
74
|
-
return fromKeyAndPublic(privateKey, publicKey);
|
|
75
|
-
}
|
|
76
|
-
/**
|
|
77
|
-
* A signer over a `CryptoKey` this process may use and cannot read.
|
|
78
|
-
*
|
|
79
|
-
* The point of the whole interface. Generate the key with
|
|
80
|
-
* `generateKey({ name: 'Ed25519' }, false, ['sign', 'verify'])`, keep the pair's
|
|
81
|
-
* private half (structured-clone it into IndexedDB if it must survive a reload),
|
|
82
|
-
* and pass it here with its public half.
|
|
83
|
-
*
|
|
84
|
-
* @param privateKey the signing key — extractable or not, it is never exported
|
|
85
|
-
* @param publicKey its public half: 64 hex, or the pair's `publicKey` (which
|
|
86
|
-
* WebCrypto leaves exportable even when the private half is not)
|
|
87
|
-
*/
|
|
88
|
-
export async function signerFromCryptoKey(privateKey, publicKey) {
|
|
89
|
-
if (privateKey.type !== 'private') {
|
|
90
|
-
throw new Error(`signerFromCryptoKey needs the private half of the pair, got a ${privateKey.type} key`);
|
|
91
|
-
}
|
|
92
|
-
if (!privateKey.usages.includes('sign')) {
|
|
93
|
-
throw new Error("this CryptoKey cannot sign: generate it with usages ['sign', 'verify']");
|
|
94
|
-
}
|
|
95
|
-
let publicHex;
|
|
96
|
-
if (typeof publicKey === 'string') {
|
|
97
|
-
// Validated rather than trusted: a wrong public key produces signatures
|
|
98
|
-
// that verify nowhere, and the refusal arrives at a relay as a 403 —
|
|
99
|
-
// nowhere near this call.
|
|
100
|
-
fromHex(publicKey, 'publicKey', 32);
|
|
101
|
-
publicHex = publicKey.trim().toLowerCase();
|
|
102
|
-
}
|
|
103
|
-
else {
|
|
104
|
-
try {
|
|
105
|
-
publicHex = hex(new Uint8Array(await crypto.subtle.exportKey('raw', publicKey)));
|
|
106
|
-
}
|
|
107
|
-
catch (cause) {
|
|
108
|
-
const detail = cause instanceof Error ? `: ${cause.message}` : '';
|
|
109
|
-
throw new Error('could not read the public half of this key pair; pass the public key ' +
|
|
110
|
-
'as 64 hex instead' +
|
|
111
|
-
detail);
|
|
112
|
-
}
|
|
113
|
-
}
|
|
114
|
-
return fromKeyAndPublic(privateKey, publicHex);
|
|
115
|
-
}
|
|
116
|
-
/** The shared tail of both constructors. */
|
|
117
|
-
function fromKeyAndPublic(privateKey, publicKey) {
|
|
118
|
-
return {
|
|
119
|
-
publicKey,
|
|
120
|
-
async sign(payload) {
|
|
121
|
-
try {
|
|
122
|
-
return new Uint8Array(await crypto.subtle.sign({ name: 'Ed25519' }, privateKey, payload));
|
|
123
|
-
}
|
|
124
|
-
catch (cause) {
|
|
125
|
-
throw unsupported(cause);
|
|
126
|
-
}
|
|
127
|
-
},
|
|
128
|
-
};
|
|
129
|
-
}
|
|
130
|
-
/**
|
|
131
|
-
* Resolve the signer an input describes, accepting either form.
|
|
132
|
-
*
|
|
133
|
-
* Internal. Every signing entry point takes an optional secret *and* an
|
|
134
|
-
* optional signer, and exactly one must be present — passing both is refused
|
|
135
|
-
* rather than silently preferring one, because the two could name different
|
|
136
|
-
* keys and the caller would have no way to tell which signed.
|
|
137
|
-
*/
|
|
138
|
-
export async function resolveSigner(secret, signer, label) {
|
|
139
|
-
if (signer && secret !== undefined) {
|
|
140
|
-
throw new Error(`pass either ${label} or signer, not both — they may name different keys`);
|
|
141
|
-
}
|
|
142
|
-
if (signer)
|
|
143
|
-
return signer;
|
|
144
|
-
if (secret !== undefined)
|
|
145
|
-
return signerFromSecret(secret, label);
|
|
146
|
-
throw new Error(`${label} or signer is required`);
|
|
147
|
-
}
|
|
@@ -1,27 +0,0 @@
|
|
|
1
|
-
import type { TokenData } from '../mero-js.js';
|
|
2
|
-
export interface TokenStore {
|
|
3
|
-
getTokens(): TokenData | null;
|
|
4
|
-
setTokens(data: TokenData): void;
|
|
5
|
-
clear(): void;
|
|
6
|
-
/**
|
|
7
|
-
* Run `fn` holding a lock that every process sharing this store respects.
|
|
8
|
-
* MeroJs holds it around a token refresh, so two processes on one store never
|
|
9
|
-
* spend the same single-use refresh token. Web Locks cover tabs of one
|
|
10
|
-
* browser; a store shared across processes (a file read by several CLIs, say)
|
|
11
|
-
* needs its own lock, and implements this. Takes precedence over Web Locks.
|
|
12
|
-
*/
|
|
13
|
-
withLock?<T>(fn: () => Promise<T>): Promise<T>;
|
|
14
|
-
}
|
|
15
|
-
export declare class MemoryTokenStore implements TokenStore {
|
|
16
|
-
private tokens;
|
|
17
|
-
getTokens(): TokenData | null;
|
|
18
|
-
setTokens(data: TokenData): void;
|
|
19
|
-
clear(): void;
|
|
20
|
-
}
|
|
21
|
-
export declare class LocalStorageTokenStore implements TokenStore {
|
|
22
|
-
private readonly key;
|
|
23
|
-
constructor(key?: string);
|
|
24
|
-
getTokens(): TokenData | null;
|
|
25
|
-
setTokens(data: TokenData): void;
|
|
26
|
-
clear(): void;
|
|
27
|
-
}
|
|
@@ -1,62 +0,0 @@
|
|
|
1
|
-
export class MemoryTokenStore {
|
|
2
|
-
constructor() {
|
|
3
|
-
this.tokens = null;
|
|
4
|
-
}
|
|
5
|
-
getTokens() {
|
|
6
|
-
return this.tokens;
|
|
7
|
-
}
|
|
8
|
-
setTokens(data) {
|
|
9
|
-
this.tokens = data;
|
|
10
|
-
}
|
|
11
|
-
clear() {
|
|
12
|
-
this.tokens = null;
|
|
13
|
-
}
|
|
14
|
-
}
|
|
15
|
-
const STORAGE_KEY = 'mero-tokens';
|
|
16
|
-
export class LocalStorageTokenStore {
|
|
17
|
-
constructor(key = STORAGE_KEY) {
|
|
18
|
-
this.key = key;
|
|
19
|
-
}
|
|
20
|
-
getTokens() {
|
|
21
|
-
try {
|
|
22
|
-
if (typeof localStorage === 'undefined')
|
|
23
|
-
return null;
|
|
24
|
-
const raw = localStorage.getItem(this.key);
|
|
25
|
-
if (!raw)
|
|
26
|
-
return null;
|
|
27
|
-
const parsed = JSON.parse(raw);
|
|
28
|
-
if (parsed && parsed.access_token && parsed.refresh_token) {
|
|
29
|
-
return {
|
|
30
|
-
access_token: parsed.access_token,
|
|
31
|
-
refresh_token: parsed.refresh_token,
|
|
32
|
-
expires_at: typeof parsed.expires_at === 'number' ? parsed.expires_at : Date.now() + 3600000,
|
|
33
|
-
...(typeof parsed.node_origin === 'string' && { node_origin: parsed.node_origin }),
|
|
34
|
-
};
|
|
35
|
-
}
|
|
36
|
-
return null;
|
|
37
|
-
}
|
|
38
|
-
catch {
|
|
39
|
-
return null;
|
|
40
|
-
}
|
|
41
|
-
}
|
|
42
|
-
setTokens(data) {
|
|
43
|
-
try {
|
|
44
|
-
if (typeof localStorage === 'undefined')
|
|
45
|
-
return;
|
|
46
|
-
localStorage.setItem(this.key, JSON.stringify(data));
|
|
47
|
-
}
|
|
48
|
-
catch {
|
|
49
|
-
// Storage unavailable
|
|
50
|
-
}
|
|
51
|
-
}
|
|
52
|
-
clear() {
|
|
53
|
-
try {
|
|
54
|
-
if (typeof localStorage === 'undefined')
|
|
55
|
-
return;
|
|
56
|
-
localStorage.removeItem(this.key);
|
|
57
|
-
}
|
|
58
|
-
catch {
|
|
59
|
-
// Storage unavailable
|
|
60
|
-
}
|
|
61
|
-
}
|
|
62
|
-
}
|
|
@@ -1,6 +0,0 @@
|
|
|
1
|
-
export { MeroClient, createMeroClient } from './mero-client.js';
|
|
2
|
-
export type { MeroClientConfig, NodeTransportConfig, RelayTransportConfig, } from './mero-client.js';
|
|
3
|
-
export { RelayTransport } from './relay-transport.js';
|
|
4
|
-
export { RelayObserver, defaultAudience } from './relay-observer.js';
|
|
5
|
-
export type { RelayObserveConfig } from './relay-observer.js';
|
|
6
|
-
export type { ExecuteTransport, ExecuteResult, TransportKind } from './types.js';
|
package/dist/transport/index.js
DELETED