passkey-kit 0.12.0 → 0.13.1
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 +399 -227
- package/{types → dist}/base.d.ts +2 -1
- package/dist/base.d.ts.map +1 -0
- package/{src/base.ts → dist/base.js} +8 -10
- package/dist/base.js.map +1 -0
- package/dist/base64url.d.ts +18 -0
- package/dist/base64url.d.ts.map +1 -0
- package/dist/base64url.js +18 -0
- package/dist/base64url.js.map +1 -0
- package/dist/constants.d.ts +87 -0
- package/dist/constants.d.ts.map +1 -0
- package/dist/constants.js +111 -0
- package/dist/constants.js.map +1 -0
- package/dist/contract-errors.d.ts +69 -0
- package/dist/contract-errors.d.ts.map +1 -0
- package/dist/contract-errors.js +129 -0
- package/dist/contract-errors.js.map +1 -0
- package/dist/errors.d.ts +163 -0
- package/dist/errors.d.ts.map +1 -0
- package/dist/errors.js +244 -0
- package/dist/errors.js.map +1 -0
- package/dist/events.d.ts +94 -0
- package/dist/events.d.ts.map +1 -0
- package/dist/events.js +92 -0
- package/dist/events.js.map +1 -0
- package/dist/index.d.ts +22 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +36 -0
- package/dist/index.js.map +1 -0
- package/dist/indexer/codec.d.ts +18 -0
- package/dist/indexer/codec.d.ts.map +1 -0
- package/dist/indexer/codec.js +32 -0
- package/dist/indexer/codec.js.map +1 -0
- package/dist/indexer/index.d.ts +25 -0
- package/dist/indexer/index.d.ts.map +1 -0
- package/dist/indexer/index.js +34 -0
- package/dist/indexer/index.js.map +1 -0
- package/dist/indexer/mercury.d.ts +88 -0
- package/dist/indexer/mercury.d.ts.map +1 -0
- package/dist/indexer/mercury.js +237 -0
- package/dist/indexer/mercury.js.map +1 -0
- package/dist/indexer/stellar-indexer.d.ts +115 -0
- package/dist/indexer/stellar-indexer.d.ts.map +1 -0
- package/dist/indexer/stellar-indexer.js +279 -0
- package/dist/indexer/stellar-indexer.js.map +1 -0
- package/dist/indexer/types.d.ts +73 -0
- package/dist/indexer/types.d.ts.map +1 -0
- package/dist/indexer/types.js +9 -0
- package/dist/indexer/types.js.map +1 -0
- package/dist/kit/auth-payload.d.ts +89 -0
- package/dist/kit/auth-payload.d.ts.map +1 -0
- package/dist/kit/auth-payload.js +203 -0
- package/dist/kit/auth-payload.js.map +1 -0
- package/dist/kit/deploy-ops.d.ts +45 -0
- package/dist/kit/deploy-ops.d.ts.map +1 -0
- package/dist/kit/deploy-ops.js +69 -0
- package/dist/kit/deploy-ops.js.map +1 -0
- package/dist/kit/tx-ops.d.ts +92 -0
- package/dist/kit/tx-ops.d.ts.map +1 -0
- package/dist/kit/tx-ops.js +113 -0
- package/dist/kit/tx-ops.js.map +1 -0
- package/dist/kit/wallet-ops.d.ts +59 -0
- package/dist/kit/wallet-ops.d.ts.map +1 -0
- package/dist/kit/wallet-ops.js +122 -0
- package/dist/kit/wallet-ops.js.map +1 -0
- package/dist/kit/webauthn-ops.d.ts +55 -0
- package/dist/kit/webauthn-ops.d.ts.map +1 -0
- package/dist/kit/webauthn-ops.js +79 -0
- package/dist/kit/webauthn-ops.js.map +1 -0
- package/dist/kit.d.ts +128 -0
- package/dist/kit.d.ts.map +1 -0
- package/dist/kit.js +276 -0
- package/dist/kit.js.map +1 -0
- package/dist/managers/credential-manager.d.ts +39 -0
- package/dist/managers/credential-manager.d.ts.map +1 -0
- package/dist/managers/credential-manager.js +47 -0
- package/dist/managers/credential-manager.js.map +1 -0
- package/dist/managers/index.d.ts +7 -0
- package/dist/managers/index.d.ts.map +1 -0
- package/dist/managers/index.js +7 -0
- package/dist/managers/index.js.map +1 -0
- package/dist/managers/signer-manager.d.ts +51 -0
- package/dist/managers/signer-manager.d.ts.map +1 -0
- package/dist/managers/signer-manager.js +92 -0
- package/dist/managers/signer-manager.js.map +1 -0
- package/dist/managers/submission-manager.d.ts +52 -0
- package/dist/managers/submission-manager.d.ts.map +1 -0
- package/dist/managers/submission-manager.js +77 -0
- package/dist/managers/submission-manager.js.map +1 -0
- package/dist/relayer.d.ts +61 -0
- package/dist/relayer.d.ts.map +1 -0
- package/dist/relayer.js +119 -0
- package/dist/relayer.js.map +1 -0
- package/dist/rpc-data.d.ts +35 -0
- package/dist/rpc-data.d.ts.map +1 -0
- package/dist/rpc-data.js +49 -0
- package/dist/rpc-data.js.map +1 -0
- package/dist/sac.d.ts +31 -0
- package/dist/sac.d.ts.map +1 -0
- package/dist/sac.js +47 -0
- package/dist/sac.js.map +1 -0
- package/dist/server.d.ts +79 -0
- package/dist/server.d.ts.map +1 -0
- package/dist/server.js +152 -0
- package/dist/server.js.map +1 -0
- package/dist/signers.d.ts +83 -0
- package/dist/signers.d.ts.map +1 -0
- package/dist/signers.js +124 -0
- package/dist/signers.js.map +1 -0
- package/dist/storage/index.d.ts +13 -0
- package/dist/storage/index.d.ts.map +1 -0
- package/dist/storage/index.js +12 -0
- package/dist/storage/index.js.map +1 -0
- package/dist/storage/indexeddb.d.ts +26 -0
- package/dist/storage/indexeddb.d.ts.map +1 -0
- package/dist/storage/indexeddb.js +100 -0
- package/dist/storage/indexeddb.js.map +1 -0
- package/dist/storage/localStorage.d.ts +22 -0
- package/dist/storage/localStorage.d.ts.map +1 -0
- package/dist/storage/localStorage.js +86 -0
- package/dist/storage/localStorage.js.map +1 -0
- package/dist/storage/memory.d.ts +18 -0
- package/dist/storage/memory.d.ts.map +1 -0
- package/dist/storage/memory.js +41 -0
- package/dist/storage/memory.js.map +1 -0
- package/dist/types.d.ts +136 -0
- package/dist/types.d.ts.map +1 -0
- package/dist/types.js +39 -0
- package/dist/types.js.map +1 -0
- package/dist/utils.d.ts +52 -0
- package/dist/utils.d.ts.map +1 -0
- package/dist/utils.js +153 -0
- package/dist/utils.js.map +1 -0
- package/dist/validation.d.ts +40 -0
- package/dist/validation.d.ts.map +1 -0
- package/dist/validation.js +73 -0
- package/dist/validation.js.map +1 -0
- package/dist/version.d.ts +7 -0
- package/dist/version.d.ts.map +1 -0
- package/dist/version.js +9 -0
- package/dist/version.js.map +1 -0
- package/package.json +48 -20
- package/.claude/settings.local.json +0 -20
- package/.cursorrules +0 -170
- package/.gitattributes +0 -2
- package/.github/workflows/release.yml +0 -21
- package/.vscode/settings.json +0 -6
- package/PROPOSAL.md +0 -397
- package/cheatsheet.txt +0 -18
- package/clone-js-sdk.sh +0 -21
- package/packages/passkey-kit-sdk/README.md +0 -54
- package/packages/passkey-kit-sdk/package.json +0 -18
- package/packages/passkey-kit-sdk/src/index.ts +0 -171
- package/packages/passkey-kit-sdk/tsconfig.json +0 -98
- package/packages/passkey-kit-sdk/types/index.d.ts +0 -190
- package/packages/sac-sdk/README.md +0 -54
- package/packages/sac-sdk/package.json +0 -18
- package/packages/sac-sdk/src/index.ts +0 -586
- package/packages/sac-sdk/tsconfig.json +0 -98
- package/packages/sac-sdk/types/index.d.ts +0 -532
- package/pnpm-workspace.yaml +0 -2
- package/src/index.ts +0 -5
- package/src/kit.ts +0 -698
- package/src/sac.ts +0 -29
- package/src/server.ts +0 -179
- package/src/types.ts +0 -32
- package/tsconfig.json +0 -28
- package/types/index.d.ts +0 -5
- package/types/kit.d.ts +0 -89
- package/types/sac.d.ts +0 -13
- package/types/server.d.ts +0 -29
- package/types/types.d.ts +0 -22
|
@@ -0,0 +1,203 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Soroban authorization-entry payload helpers + the flat `Signatures` map codec.
|
|
3
|
+
*
|
|
4
|
+
* These are thin wrappers over the stellar-sdk's native Protocol-27 auth
|
|
5
|
+
* primitives (`buildAuthorizationEntryPreimage`). The old kit hand-rolled a
|
|
6
|
+
* stack of "does this SDK support P27?" probe shims; on stellar-sdk >= 16 those
|
|
7
|
+
* are all dead, so this module simply uses the SDK.
|
|
8
|
+
*
|
|
9
|
+
* The smart wallet's `__check_auth` reads a `Signatures` value — a single
|
|
10
|
+
* `Map<SignerKey, Signature>` — from the address credentials. Each signer
|
|
11
|
+
* contributes one entry keyed by its on-chain `SignerKey`. The host rejects an
|
|
12
|
+
* `ScMap` whose keys are not in the host's canonical sort order, so the map is
|
|
13
|
+
* sorted with {@link compareScVal} (NOT a byte/`localeCompare` sort — see below).
|
|
14
|
+
*
|
|
15
|
+
* @packageDocumentation
|
|
16
|
+
*/
|
|
17
|
+
import { buildAuthorizationEntryPreimage, hash, xdr, } from "@stellar/stellar-sdk";
|
|
18
|
+
import { SigningError, PasskeyKitErrorCode } from "../errors.js";
|
|
19
|
+
// ============================================================================
|
|
20
|
+
// Address credentials + signature payload
|
|
21
|
+
// ============================================================================
|
|
22
|
+
/**
|
|
23
|
+
* Extract the {@link xdr.SorobanAddressCredentials} from a credentials union,
|
|
24
|
+
* for the address / addressV2 / addressWithDelegates variants.
|
|
25
|
+
*
|
|
26
|
+
* @throws {SigningError} If the credentials are not address-based.
|
|
27
|
+
*/
|
|
28
|
+
export function getAddressCredentials(credentials) {
|
|
29
|
+
switch (credentials.switch().name) {
|
|
30
|
+
case "sorobanCredentialsAddress":
|
|
31
|
+
return credentials.address();
|
|
32
|
+
case "sorobanCredentialsAddressV2":
|
|
33
|
+
return credentials.addressV2();
|
|
34
|
+
case "sorobanCredentialsAddressWithDelegates":
|
|
35
|
+
return credentials.addressWithDelegates().addressCredentials();
|
|
36
|
+
default:
|
|
37
|
+
throw new SigningError(`Soroban credentials do not contain address credentials: ${credentials.switch().name}`, PasskeyKitErrorCode.UNSUPPORTED_CREDENTIALS);
|
|
38
|
+
}
|
|
39
|
+
}
|
|
40
|
+
/**
|
|
41
|
+
* Whether a credentials union uses an address-bound signature payload (the P27
|
|
42
|
+
* V2 / with-delegates variants), whose preimage binds the invoker address.
|
|
43
|
+
*/
|
|
44
|
+
export function usesAddressBoundPayload(credentials) {
|
|
45
|
+
const name = credentials.switch().name;
|
|
46
|
+
return (name === "sorobanCredentialsAddressV2" ||
|
|
47
|
+
name === "sorobanCredentialsAddressWithDelegates");
|
|
48
|
+
}
|
|
49
|
+
/**
|
|
50
|
+
* Assert that a signature-expiration ledger is a valid `u32`.
|
|
51
|
+
*
|
|
52
|
+
* @throws {SigningError} If not a `u32` integer.
|
|
53
|
+
*/
|
|
54
|
+
export function assertSignatureExpirationLedger(expiration) {
|
|
55
|
+
if (!Number.isInteger(expiration) ||
|
|
56
|
+
expiration < 0 ||
|
|
57
|
+
expiration > 0xffffffff) {
|
|
58
|
+
throw new SigningError("Soroban signature expiration ledger must be a uint32 integer", PasskeyKitErrorCode.INVALID_SIGNATURE_EXPIRATION, { expiration });
|
|
59
|
+
}
|
|
60
|
+
}
|
|
61
|
+
/**
|
|
62
|
+
* Build the signature payload (the 32-byte hash a signer signs) for an
|
|
63
|
+
* authorization entry at a given expiration ledger.
|
|
64
|
+
*
|
|
65
|
+
* Sets the expiration on the entry's address credentials, then hashes the SDK's
|
|
66
|
+
* canonical authorization-entry preimage. Works for the address, addressV2, and
|
|
67
|
+
* addressWithDelegates credential variants.
|
|
68
|
+
*
|
|
69
|
+
* @throws {SigningError} If `expiration` is not a valid `u32`.
|
|
70
|
+
*/
|
|
71
|
+
export function buildSignaturePayload(networkPassphrase, entry, expiration) {
|
|
72
|
+
assertSignatureExpirationLedger(expiration);
|
|
73
|
+
const credentials = getAddressCredentials(entry.credentials());
|
|
74
|
+
credentials.signatureExpirationLedger(expiration);
|
|
75
|
+
return hash(buildAuthorizationEntryPreimage(entry, expiration, networkPassphrase).toXDR());
|
|
76
|
+
}
|
|
77
|
+
// ============================================================================
|
|
78
|
+
// Host-order ScVal comparison
|
|
79
|
+
// ============================================================================
|
|
80
|
+
/**
|
|
81
|
+
* Compare two ScVals in the order the Soroban host uses when it validates that
|
|
82
|
+
* an ScMap is sorted by key (host `metered_map::from_map`, which rejects an
|
|
83
|
+
* unsorted map with `InvalidInput`).
|
|
84
|
+
*
|
|
85
|
+
* This is deliberately NOT a comparison of the XDR byte encodings. XDR prefixes
|
|
86
|
+
* every variable-length payload (Bytes, Symbol, String, Vec) with a 4-byte
|
|
87
|
+
* length, so `toXDR("hex")` sorting is length-major; the host instead compares
|
|
88
|
+
* those payloads element-wise by content (Rust slice `Ord`), where a shorter
|
|
89
|
+
* value that is a prefix of a longer one sorts first. The old kit's
|
|
90
|
+
* `localeCompare` on a symbol+hex string approximated this and could diverge
|
|
91
|
+
* from the host, producing a map the wallet rejects at `__check_auth`.
|
|
92
|
+
*
|
|
93
|
+
* Only the shapes that appear as `SignerKey` map keys are handled precisely
|
|
94
|
+
* (Vec, Symbol, String, Bytes, Address). All other shapes are same-type here
|
|
95
|
+
* (the discriminant is compared first), so their fixed-width XDR encodings sort
|
|
96
|
+
* order-equivalently to the host.
|
|
97
|
+
*/
|
|
98
|
+
export function compareScVal(a, b) {
|
|
99
|
+
const aType = a.switch().value;
|
|
100
|
+
const bType = b.switch().value;
|
|
101
|
+
if (aType !== bType) {
|
|
102
|
+
return aType < bType ? -1 : 1;
|
|
103
|
+
}
|
|
104
|
+
switch (a.switch().name) {
|
|
105
|
+
case "scvVec": {
|
|
106
|
+
const av = a.vec() ?? [];
|
|
107
|
+
const bv = b.vec() ?? [];
|
|
108
|
+
const len = Math.min(av.length, bv.length);
|
|
109
|
+
for (let i = 0; i < len; i += 1) {
|
|
110
|
+
const cmp = compareScVal(av[i], bv[i]);
|
|
111
|
+
if (cmp !== 0)
|
|
112
|
+
return cmp;
|
|
113
|
+
}
|
|
114
|
+
return av.length - bv.length;
|
|
115
|
+
}
|
|
116
|
+
case "scvMap": {
|
|
117
|
+
const am = a.map() ?? [];
|
|
118
|
+
const bm = b.map() ?? [];
|
|
119
|
+
const len = Math.min(am.length, bm.length);
|
|
120
|
+
for (let i = 0; i < len; i += 1) {
|
|
121
|
+
const keyCmp = compareScVal(am[i].key(), bm[i].key());
|
|
122
|
+
if (keyCmp !== 0)
|
|
123
|
+
return keyCmp;
|
|
124
|
+
const valCmp = compareScVal(am[i].val(), bm[i].val());
|
|
125
|
+
if (valCmp !== 0)
|
|
126
|
+
return valCmp;
|
|
127
|
+
}
|
|
128
|
+
return am.length - bm.length;
|
|
129
|
+
}
|
|
130
|
+
case "scvSymbol":
|
|
131
|
+
return Buffer.compare(Buffer.from(a.sym().toString(), "utf8"), Buffer.from(b.sym().toString(), "utf8"));
|
|
132
|
+
case "scvString":
|
|
133
|
+
return Buffer.compare(Buffer.from(a.str().toString(), "utf8"), Buffer.from(b.str().toString(), "utf8"));
|
|
134
|
+
case "scvBytes":
|
|
135
|
+
return Buffer.compare(Buffer.from(a.bytes()), Buffer.from(b.bytes()));
|
|
136
|
+
case "scvAddress":
|
|
137
|
+
// ScAddress is a type discriminant plus a fixed-width key, so a byte
|
|
138
|
+
// comparison of the encoding matches the host's (type, key) ordering.
|
|
139
|
+
return Buffer.compare(a.address().toXDR(), b.address().toXDR());
|
|
140
|
+
default:
|
|
141
|
+
// Same-type scalar (or any unhandled shape): its XDR encoding is
|
|
142
|
+
// fixed-width for a given type, so a byte comparison is order-equivalent.
|
|
143
|
+
return Buffer.compare(a.toXDR(), b.toXDR());
|
|
144
|
+
}
|
|
145
|
+
}
|
|
146
|
+
// ============================================================================
|
|
147
|
+
// SignerKey / Signature encoding + the flat Signatures map
|
|
148
|
+
// ============================================================================
|
|
149
|
+
const SIGNER_KEY_UDT = xdr.ScSpecTypeDef.scSpecTypeUdt(new xdr.ScSpecTypeUdt({ name: "SignerKey" }));
|
|
150
|
+
const SIGNATURE_UDT = xdr.ScSpecTypeDef.scSpecTypeUdt(new xdr.ScSpecTypeUdt({ name: "Signature" }));
|
|
151
|
+
/** The `SignerVal` UDT type def, for decoding a stored signer entry's value. */
|
|
152
|
+
export const SIGNER_VAL_UDT = xdr.ScSpecTypeDef.scSpecTypeUdt(new xdr.ScSpecTypeUdt({ name: "SignerVal" }));
|
|
153
|
+
/** Encode a native `SignerKey` union into its contract ScVal via the spec. */
|
|
154
|
+
export function signerKeyToScVal(spec, key) {
|
|
155
|
+
return spec.nativeToScVal(key, SIGNER_KEY_UDT);
|
|
156
|
+
}
|
|
157
|
+
/**
|
|
158
|
+
* Encode a native `Signature` union into its contract ScVal via the spec, or
|
|
159
|
+
* `scvVoid` when there is no signature value (policy signers).
|
|
160
|
+
*/
|
|
161
|
+
export function signatureToScVal(spec, val) {
|
|
162
|
+
return val ? spec.nativeToScVal(val, SIGNATURE_UDT) : xdr.ScVal.scvVoid();
|
|
163
|
+
}
|
|
164
|
+
/**
|
|
165
|
+
* Upsert a `(SignerKey, Signature)` pair into the entry's `Signatures` value,
|
|
166
|
+
* which is encoded as `scvVec([ scvMap([...]) ])`.
|
|
167
|
+
*
|
|
168
|
+
* A signer key already present in the map is replaced (co-signing is idempotent
|
|
169
|
+
* per signer). The map is re-sorted by key in host order after every insert, so
|
|
170
|
+
* the wallet's `__check_auth` accepts it.
|
|
171
|
+
*
|
|
172
|
+
* @throws {SigningError} If the existing signature is neither void nor a
|
|
173
|
+
* Signatures vec.
|
|
174
|
+
*/
|
|
175
|
+
export function upsertSignatureEntry(credentials, scKey, scVal) {
|
|
176
|
+
const newEntry = new xdr.ScMapEntry({ key: scKey, val: scVal });
|
|
177
|
+
switch (credentials.signature().switch().name) {
|
|
178
|
+
case "scvVoid": {
|
|
179
|
+
credentials.signature(xdr.ScVal.scvVec([xdr.ScVal.scvMap([newEntry])]));
|
|
180
|
+
break;
|
|
181
|
+
}
|
|
182
|
+
case "scvVec": {
|
|
183
|
+
const map = credentials.signature().vec()?.[0]?.map();
|
|
184
|
+
if (!map) {
|
|
185
|
+
throw new SigningError("Malformed Signatures value: expected a map inside the signatures vector", PasskeyKitErrorCode.SIGNING_FAILED);
|
|
186
|
+
}
|
|
187
|
+
const existingIndex = map.findIndex((entry) => compareScVal(entry.key(), scKey) === 0);
|
|
188
|
+
if (existingIndex >= 0) {
|
|
189
|
+
map[existingIndex] = newEntry;
|
|
190
|
+
}
|
|
191
|
+
else {
|
|
192
|
+
map.push(newEntry);
|
|
193
|
+
}
|
|
194
|
+
// Host order: the wallet converts this map to a host object and rejects
|
|
195
|
+
// it if the keys are not in host-sort order.
|
|
196
|
+
map.sort((x, y) => compareScVal(x.key(), y.key()));
|
|
197
|
+
break;
|
|
198
|
+
}
|
|
199
|
+
default:
|
|
200
|
+
throw new SigningError(`Unsupported existing signature value: ${credentials.signature().switch().name}`, PasskeyKitErrorCode.SIGNING_FAILED);
|
|
201
|
+
}
|
|
202
|
+
}
|
|
203
|
+
//# sourceMappingURL=auth-payload.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"auth-payload.js","sourceRoot":"","sources":["../../src/kit/auth-payload.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Smart-wallet deployment operations.
|
|
3
|
+
*
|
|
4
|
+
* The deployer keypair is now configurable (`config.deploySource`) instead of a
|
|
5
|
+
* hard-coded `Keypair.fromRawEd25519Seed(hash("kalepail"))`. The default still
|
|
6
|
+
* derives from {@link DEFAULT_DEPLOYER_SEED} = `"kalepail"` so contract-id
|
|
7
|
+
* determinism (and indexer reverse-lookup) is preserved out of the box.
|
|
8
|
+
*
|
|
9
|
+
* @packageDocumentation
|
|
10
|
+
*/
|
|
11
|
+
import { Keypair } from "@stellar/stellar-sdk";
|
|
12
|
+
import type { AssembledTransaction } from "@stellar/stellar-sdk/contract";
|
|
13
|
+
import { Client as PasskeyClient } from "passkey-kit-sdk";
|
|
14
|
+
/**
|
|
15
|
+
* Resolve the fee-paying deployer keypair from an optional secret.
|
|
16
|
+
*
|
|
17
|
+
* With no secret, derives the canonical deterministic deployer from
|
|
18
|
+
* {@link DEFAULT_DEPLOYER_SEED}. The deployer only pays fees and salts the
|
|
19
|
+
* deploy; it never controls the wallet. Supplying a different `deploySource`
|
|
20
|
+
* changes the derived contract addresses (and breaks keyId → contract
|
|
21
|
+
* discovery), so this is documented as an advanced option.
|
|
22
|
+
*
|
|
23
|
+
* @throws {ConfigurationError} If `deploySource` is not a valid secret key.
|
|
24
|
+
*/
|
|
25
|
+
export declare function resolveDeployer(deploySource?: string): Keypair;
|
|
26
|
+
/** Deterministically derive a smart-wallet address for a passkey credential. */
|
|
27
|
+
export declare function deriveWalletAddress(deps: {
|
|
28
|
+
networkPassphrase: string;
|
|
29
|
+
deployerPublicKey: string;
|
|
30
|
+
}, keyId: Buffer): string;
|
|
31
|
+
/**
|
|
32
|
+
* Build the smart-wallet deploy transaction, initializing it with the passkey as
|
|
33
|
+
* the first (unlimited, persistent) Secp256r1 signer via `__constructor`.
|
|
34
|
+
*
|
|
35
|
+
* The returned {@link AssembledTransaction} still needs to be signed by the
|
|
36
|
+
* deployer keypair (the fee source) before submission.
|
|
37
|
+
*/
|
|
38
|
+
export declare function buildDeployTransaction(deps: {
|
|
39
|
+
rpcUrl: string;
|
|
40
|
+
networkPassphrase: string;
|
|
41
|
+
walletWasmHash: string;
|
|
42
|
+
deployerPublicKey: string;
|
|
43
|
+
timeoutInSeconds: number;
|
|
44
|
+
}, keyId: Buffer, publicKey: Uint8Array): Promise<AssembledTransaction<PasskeyClient>>;
|
|
45
|
+
//# sourceMappingURL=deploy-ops.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"deploy-ops.d.ts","sourceRoot":"","sources":["../../src/kit/deploy-ops.ts"],"names":[],"mappings":"AAAA;;;;;;;;;GASG;AAEH,OAAO,EAAE,OAAO,EAAQ,MAAM,sBAAsB,CAAC;AACrD,OAAO,KAAK,EAAE,oBAAoB,EAAE,MAAM,+BAA+B,CAAC;AAC1E,OAAO,EACL,MAAM,IAAI,aAAa,EAExB,MAAM,iBAAiB,CAAC;AAKzB;;;;;;;;;;GAUG;AACH,wBAAgB,eAAe,CAAC,YAAY,CAAC,EAAE,MAAM,GAAG,OAAO,CAY9D;AAED,gFAAgF;AAChF,wBAAgB,mBAAmB,CACjC,IAAI,EAAE;IAAE,iBAAiB,EAAE,MAAM,CAAC;IAAC,iBAAiB,EAAE,MAAM,CAAA;CAAE,EAC9D,KAAK,EAAE,MAAM,GACZ,MAAM,CAER;AAED;;;;;;GAMG;AACH,wBAAsB,sBAAsB,CAC1C,IAAI,EAAE;IACJ,MAAM,EAAE,MAAM,CAAC;IACf,iBAAiB,EAAE,MAAM,CAAC;IAC1B,cAAc,EAAE,MAAM,CAAC;IACvB,iBAAiB,EAAE,MAAM,CAAC;IAC1B,gBAAgB,EAAE,MAAM,CAAC;CAC1B,EACD,KAAK,EAAE,MAAM,EACb,SAAS,EAAE,UAAU,GACpB,OAAO,CAAC,oBAAoB,CAAC,aAAa,CAAC,CAAC,CAuB9C"}
|
|
@@ -0,0 +1,69 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Smart-wallet deployment operations.
|
|
3
|
+
*
|
|
4
|
+
* The deployer keypair is now configurable (`config.deploySource`) instead of a
|
|
5
|
+
* hard-coded `Keypair.fromRawEd25519Seed(hash("kalepail"))`. The default still
|
|
6
|
+
* derives from {@link DEFAULT_DEPLOYER_SEED} = `"kalepail"` so contract-id
|
|
7
|
+
* determinism (and indexer reverse-lookup) is preserved out of the box.
|
|
8
|
+
*
|
|
9
|
+
* @packageDocumentation
|
|
10
|
+
*/
|
|
11
|
+
import { Keypair, hash } from "@stellar/stellar-sdk";
|
|
12
|
+
import { Client as PasskeyClient, } from "passkey-kit-sdk";
|
|
13
|
+
import { DEFAULT_DEPLOYER_SEED } from "../constants.js";
|
|
14
|
+
import { deriveContractAddress } from "../utils.js";
|
|
15
|
+
import { ConfigurationError, PasskeyKitErrorCode } from "../errors.js";
|
|
16
|
+
/**
|
|
17
|
+
* Resolve the fee-paying deployer keypair from an optional secret.
|
|
18
|
+
*
|
|
19
|
+
* With no secret, derives the canonical deterministic deployer from
|
|
20
|
+
* {@link DEFAULT_DEPLOYER_SEED}. The deployer only pays fees and salts the
|
|
21
|
+
* deploy; it never controls the wallet. Supplying a different `deploySource`
|
|
22
|
+
* changes the derived contract addresses (and breaks keyId → contract
|
|
23
|
+
* discovery), so this is documented as an advanced option.
|
|
24
|
+
*
|
|
25
|
+
* @throws {ConfigurationError} If `deploySource` is not a valid secret key.
|
|
26
|
+
*/
|
|
27
|
+
export function resolveDeployer(deploySource) {
|
|
28
|
+
if (deploySource) {
|
|
29
|
+
try {
|
|
30
|
+
return Keypair.fromSecret(deploySource);
|
|
31
|
+
}
|
|
32
|
+
catch {
|
|
33
|
+
throw new ConfigurationError("deploySource must be a valid Stellar secret key (S…)", PasskeyKitErrorCode.INVALID_CONFIG);
|
|
34
|
+
}
|
|
35
|
+
}
|
|
36
|
+
return Keypair.fromRawEd25519Seed(hash(Buffer.from(DEFAULT_DEPLOYER_SEED)));
|
|
37
|
+
}
|
|
38
|
+
/** Deterministically derive a smart-wallet address for a passkey credential. */
|
|
39
|
+
export function deriveWalletAddress(deps, keyId) {
|
|
40
|
+
return deriveContractAddress(keyId, deps.deployerPublicKey, deps.networkPassphrase);
|
|
41
|
+
}
|
|
42
|
+
/**
|
|
43
|
+
* Build the smart-wallet deploy transaction, initializing it with the passkey as
|
|
44
|
+
* the first (unlimited, persistent) Secp256r1 signer via `__constructor`.
|
|
45
|
+
*
|
|
46
|
+
* The returned {@link AssembledTransaction} still needs to be signed by the
|
|
47
|
+
* deployer keypair (the fee source) before submission.
|
|
48
|
+
*/
|
|
49
|
+
export async function buildDeployTransaction(deps, keyId, publicKey) {
|
|
50
|
+
const signer = {
|
|
51
|
+
tag: "Secp256r1",
|
|
52
|
+
values: [
|
|
53
|
+
Buffer.from(keyId),
|
|
54
|
+
Buffer.from(publicKey),
|
|
55
|
+
[undefined], // SignerExpiration: none
|
|
56
|
+
[undefined], // SignerLimits: unlimited
|
|
57
|
+
{ tag: "Persistent", values: undefined },
|
|
58
|
+
],
|
|
59
|
+
};
|
|
60
|
+
return PasskeyClient.deploy({ signer }, {
|
|
61
|
+
rpcUrl: deps.rpcUrl,
|
|
62
|
+
wasmHash: deps.walletWasmHash,
|
|
63
|
+
networkPassphrase: deps.networkPassphrase,
|
|
64
|
+
publicKey: deps.deployerPublicKey,
|
|
65
|
+
salt: hash(keyId),
|
|
66
|
+
timeoutInSeconds: deps.timeoutInSeconds,
|
|
67
|
+
});
|
|
68
|
+
}
|
|
69
|
+
//# sourceMappingURL=deploy-ops.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"deploy-ops.js","sourceRoot":"","sources":["../../src/kit/deploy-ops.ts"],"names":[],"mappings":"AAAA;;;;;;;;;GASG;AAEH,OAAO,EAAE,OAAO,EAAE,IAAI,EAAE,MAAM,sBAAsB,CAAC;AAErD,OAAO,EACL,MAAM,IAAI,aAAa,GAExB,MAAM,iBAAiB,CAAC;AACzB,OAAO,EAAE,qBAAqB,EAAE,MAAM,iBAAiB,CAAC;AACxD,OAAO,EAAE,qBAAqB,EAAE,MAAM,aAAa,CAAC;AACpD,OAAO,EAAE,kBAAkB,EAAE,mBAAmB,EAAE,MAAM,cAAc,CAAC;AAEvE;;;;;;;;;;GAUG;AACH,MAAM,UAAU,eAAe,CAAC,YAAqB;IACnD,IAAI,YAAY,EAAE,CAAC;QACjB,IAAI,CAAC;YACH,OAAO,OAAO,CAAC,UAAU,CAAC,YAAY,CAAC,CAAC;QAC1C,CAAC;QAAC,MAAM,CAAC;YACP,MAAM,IAAI,kBAAkB,CAC1B,sDAAsD,EACtD,mBAAmB,CAAC,cAAc,CACnC,CAAC;QACJ,CAAC;IACH,CAAC;IACD,OAAO,OAAO,CAAC,kBAAkB,CAAC,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,qBAAqB,CAAC,CAAC,CAAC,CAAC;AAC9E,CAAC;AAED,gFAAgF;AAChF,MAAM,UAAU,mBAAmB,CACjC,IAA8D,EAC9D,KAAa;IAEb,OAAO,qBAAqB,CAAC,KAAK,EAAE,IAAI,CAAC,iBAAiB,EAAE,IAAI,CAAC,iBAAiB,CAAC,CAAC;AACtF,CAAC;AAED;;;;;;GAMG;AACH,MAAM,CAAC,KAAK,UAAU,sBAAsB,CAC1C,IAMC,EACD,KAAa,EACb,SAAqB;IAErB,MAAM,MAAM,GAAc;QACxB,GAAG,EAAE,WAAW;QAChB,MAAM,EAAE;YACN,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC;YAClB,MAAM,CAAC,IAAI,CAAC,SAAS,CAAC;YACtB,CAAC,SAAS,CAAC,EAAE,yBAAyB;YACtC,CAAC,SAAS,CAAC,EAAE,0BAA0B;YACvC,EAAE,GAAG,EAAE,YAAY,EAAE,MAAM,EAAE,SAAS,EAAE;SACzC;KACF,CAAC;IAEF,OAAO,aAAa,CAAC,MAAM,CACzB,EAAE,MAAM,EAAE,EACV;QACE,MAAM,EAAE,IAAI,CAAC,MAAM;QACnB,QAAQ,EAAE,IAAI,CAAC,cAAc;QAC7B,iBAAiB,EAAE,IAAI,CAAC,iBAAiB;QACzC,SAAS,EAAE,IAAI,CAAC,iBAAiB;QACjC,IAAI,EAAE,IAAI,CAAC,KAAK,CAAC;QACjB,gBAAgB,EAAE,IAAI,CAAC,gBAAgB;KACxC,CACF,CAAC;AACJ,CAAC"}
|
|
@@ -0,0 +1,92 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Transaction-signing operations: the auth-entry signing pipeline and the
|
|
3
|
+
* `AssembledTransaction` signing entrypoint.
|
|
4
|
+
*
|
|
5
|
+
* Two deliberate changes from the old kit:
|
|
6
|
+
* - `sign` takes a single explicit `AssembledTransaction<T>` instead of the
|
|
7
|
+
* lossy `AssembledTransaction | Tx | string` tri-input that silently dropped
|
|
8
|
+
* memo/fee/operations on its fallback path (#599 §6). Callers holding XDR use
|
|
9
|
+
* `AssembledTransaction.fromXDR` first.
|
|
10
|
+
* - The `Signatures` map is sorted with the host-order `compareScVal`, not the
|
|
11
|
+
* old `localeCompare` string approximation.
|
|
12
|
+
*
|
|
13
|
+
* @packageDocumentation
|
|
14
|
+
*/
|
|
15
|
+
import { xdr } from "@stellar/stellar-sdk";
|
|
16
|
+
import type { Keypair } from "@stellar/stellar-sdk";
|
|
17
|
+
import type { Server } from "@stellar/stellar-sdk/rpc";
|
|
18
|
+
import type { AssembledTransaction, Spec as ContractSpec } from "@stellar/stellar-sdk/contract";
|
|
19
|
+
import type { Signer, SignerContext } from "../signers.js";
|
|
20
|
+
/** Deps for computing a default signature-expiration ledger. */
|
|
21
|
+
export interface ExpirationDeps {
|
|
22
|
+
rpc: Server;
|
|
23
|
+
timeoutInSeconds: number;
|
|
24
|
+
}
|
|
25
|
+
/**
|
|
26
|
+
* Compute a default signature-expiration ledger: the latest ledger plus the
|
|
27
|
+
* timeout window (assuming ~5s ledgers), rounded up.
|
|
28
|
+
*/
|
|
29
|
+
export declare function calculateExpiration(deps: ExpirationDeps): Promise<number>;
|
|
30
|
+
/** Deps for signing a single auth entry. */
|
|
31
|
+
export interface SignAuthEntryDeps {
|
|
32
|
+
networkPassphrase: string;
|
|
33
|
+
spec: ContractSpec;
|
|
34
|
+
signerContext: SignerContext;
|
|
35
|
+
calculateExpiration: () => Promise<number>;
|
|
36
|
+
}
|
|
37
|
+
/** Per-call signing options. */
|
|
38
|
+
export interface SignOptions {
|
|
39
|
+
/** Signature expiration ledger (defaults to the configured window). */
|
|
40
|
+
expiration?: number;
|
|
41
|
+
}
|
|
42
|
+
/**
|
|
43
|
+
* Sign a single Soroban authorization entry with a {@link Signer}, merging the
|
|
44
|
+
* resulting `(SignerKey, Signature)` pair into the entry's flat `Signatures`
|
|
45
|
+
* map (host-ordered).
|
|
46
|
+
*
|
|
47
|
+
* Mutates and returns the passed entry.
|
|
48
|
+
*/
|
|
49
|
+
export declare function signAuthEntry(deps: SignAuthEntryDeps, entry: xdr.SorobanAuthorizationEntry, signer: Signer, options?: SignOptions): Promise<xdr.SorobanAuthorizationEntry>;
|
|
50
|
+
/** Deps for signing an assembled transaction's auth entries. */
|
|
51
|
+
export interface SignTxDeps extends SignAuthEntryDeps {
|
|
52
|
+
getContractId: () => string | undefined;
|
|
53
|
+
}
|
|
54
|
+
/**
|
|
55
|
+
* Sign every auth entry of an {@link AssembledTransaction} that is authorized by
|
|
56
|
+
* the connected wallet, using `signer`. Returns the same transaction with its
|
|
57
|
+
* auth entries signed.
|
|
58
|
+
*
|
|
59
|
+
* @throws {SigningError} If no wallet is connected.
|
|
60
|
+
*/
|
|
61
|
+
export declare function sign<T>(deps: SignTxDeps, txn: AssembledTransaction<T>, signer: Signer, options?: SignOptions): Promise<AssembledTransaction<T>>;
|
|
62
|
+
/**
|
|
63
|
+
* The `restorePreamble` shape Soroban simulation returns when a transaction
|
|
64
|
+
* touches archived entries (a subset of the SDK's `SimulateTransactionResponse`).
|
|
65
|
+
*/
|
|
66
|
+
export interface RestorePreamble {
|
|
67
|
+
minResourceFee: string;
|
|
68
|
+
transactionData: {
|
|
69
|
+
build(): xdr.SorobanTransactionData;
|
|
70
|
+
};
|
|
71
|
+
}
|
|
72
|
+
/**
|
|
73
|
+
* Restore an archived contract-data footprint reported by simulation, paying
|
|
74
|
+
* with the deployer keypair.
|
|
75
|
+
*
|
|
76
|
+
* Soroban simulation returns a `restorePreamble` when the transaction touches
|
|
77
|
+
* archived entries; the footprint must be restored (a separate, fee-bearing
|
|
78
|
+
* transaction) before the real transaction can succeed. The deployer keypair
|
|
79
|
+
* pays because it is the on-chain fee source the kit already controls.
|
|
80
|
+
*
|
|
81
|
+
* Returns the restore transaction hash. This path is exercised live in F2 (it
|
|
82
|
+
* requires archived on-chain state to trigger).
|
|
83
|
+
*
|
|
84
|
+
* @throws {SigningError} On submission/confirmation failure.
|
|
85
|
+
*/
|
|
86
|
+
export declare function restoreFootprint(deps: {
|
|
87
|
+
rpc: Server;
|
|
88
|
+
networkPassphrase: string;
|
|
89
|
+
deployerKeypair: Keypair;
|
|
90
|
+
timeoutInSeconds: number;
|
|
91
|
+
}, restorePreamble: RestorePreamble): Promise<string>;
|
|
92
|
+
//# sourceMappingURL=tx-ops.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"tx-ops.d.ts","sourceRoot":"","sources":["../../src/kit/tx-ops.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;GAaG;AAEH,OAAO,EAAiC,GAAG,EAAE,MAAM,sBAAsB,CAAC;AAC1E,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,sBAAsB,CAAC;AACpD,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,0BAA0B,CAAC;AACvD,OAAO,KAAK,EACV,oBAAoB,EACpB,IAAI,IAAI,YAAY,EACrB,MAAM,+BAA+B,CAAC;AACvC,OAAO,KAAK,EAAE,MAAM,EAAE,aAAa,EAAE,MAAM,eAAe,CAAC;AAU3D,gEAAgE;AAChE,MAAM,WAAW,cAAc;IAC7B,GAAG,EAAE,MAAM,CAAC;IACZ,gBAAgB,EAAE,MAAM,CAAC;CAC1B;AAED;;;GAGG;AACH,wBAAsB,mBAAmB,CAAC,IAAI,EAAE,cAAc,GAAG,OAAO,CAAC,MAAM,CAAC,CAG/E;AAED,4CAA4C;AAC5C,MAAM,WAAW,iBAAiB;IAChC,iBAAiB,EAAE,MAAM,CAAC;IAC1B,IAAI,EAAE,YAAY,CAAC;IACnB,aAAa,EAAE,aAAa,CAAC;IAC7B,mBAAmB,EAAE,MAAM,OAAO,CAAC,MAAM,CAAC,CAAC;CAC5C;AAED,gCAAgC;AAChC,MAAM,WAAW,WAAW;IAC1B,uEAAuE;IACvE,UAAU,CAAC,EAAE,MAAM,CAAC;CACrB;AAED;;;;;;GAMG;AACH,wBAAsB,aAAa,CACjC,IAAI,EAAE,iBAAiB,EACvB,KAAK,EAAE,GAAG,CAAC,yBAAyB,EACpC,MAAM,EAAE,MAAM,EACd,OAAO,CAAC,EAAE,WAAW,GACpB,OAAO,CAAC,GAAG,CAAC,yBAAyB,CAAC,CAgCxC;AAED,gEAAgE;AAChE,MAAM,WAAW,UAAW,SAAQ,iBAAiB;IACnD,aAAa,EAAE,MAAM,MAAM,GAAG,SAAS,CAAC;CACzC;AAED;;;;;;GAMG;AACH,wBAAsB,IAAI,CAAC,CAAC,EAC1B,IAAI,EAAE,UAAU,EAChB,GAAG,EAAE,oBAAoB,CAAC,CAAC,CAAC,EAC5B,MAAM,EAAE,MAAM,EACd,OAAO,CAAC,EAAE,WAAW,GACpB,OAAO,CAAC,oBAAoB,CAAC,CAAC,CAAC,CAAC,CAkBlC;AAED;;;GAGG;AACH,MAAM,WAAW,eAAe;IAC9B,cAAc,EAAE,MAAM,CAAC;IACvB,eAAe,EAAE;QAAE,KAAK,IAAI,GAAG,CAAC,sBAAsB,CAAA;KAAE,CAAC;CAC1D;AAED;;;;;;;;;;;;;GAaG;AACH,wBAAsB,gBAAgB,CACpC,IAAI,EAAE;IACJ,GAAG,EAAE,MAAM,CAAC;IACZ,iBAAiB,EAAE,MAAM,CAAC;IAC1B,eAAe,EAAE,OAAO,CAAC;IACzB,gBAAgB,EAAE,MAAM,CAAC;CAC1B,EACD,eAAe,EAAE,eAAe,GAC/B,OAAO,CAAC,MAAM,CAAC,CAkCjB"}
|
|
@@ -0,0 +1,113 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Transaction-signing operations: the auth-entry signing pipeline and the
|
|
3
|
+
* `AssembledTransaction` signing entrypoint.
|
|
4
|
+
*
|
|
5
|
+
* Two deliberate changes from the old kit:
|
|
6
|
+
* - `sign` takes a single explicit `AssembledTransaction<T>` instead of the
|
|
7
|
+
* lossy `AssembledTransaction | Tx | string` tri-input that silently dropped
|
|
8
|
+
* memo/fee/operations on its fallback path (#599 §6). Callers holding XDR use
|
|
9
|
+
* `AssembledTransaction.fromXDR` first.
|
|
10
|
+
* - The `Signatures` map is sorted with the host-order `compareScVal`, not the
|
|
11
|
+
* old `localeCompare` string approximation.
|
|
12
|
+
*
|
|
13
|
+
* @packageDocumentation
|
|
14
|
+
*/
|
|
15
|
+
import { Operation, TransactionBuilder, xdr } from "@stellar/stellar-sdk";
|
|
16
|
+
import { buildSignaturePayload, getAddressCredentials, signatureToScVal, signerKeyToScVal, upsertSignatureEntry, } from "./auth-payload.js";
|
|
17
|
+
import { SigningError, PasskeyKitError, PasskeyKitErrorCode } from "../errors.js";
|
|
18
|
+
/**
|
|
19
|
+
* Compute a default signature-expiration ledger: the latest ledger plus the
|
|
20
|
+
* timeout window (assuming ~5s ledgers), rounded up.
|
|
21
|
+
*/
|
|
22
|
+
export async function calculateExpiration(deps) {
|
|
23
|
+
const { sequence } = await deps.rpc.getLatestLedger();
|
|
24
|
+
return Math.ceil(sequence + deps.timeoutInSeconds / 5);
|
|
25
|
+
}
|
|
26
|
+
/**
|
|
27
|
+
* Sign a single Soroban authorization entry with a {@link Signer}, merging the
|
|
28
|
+
* resulting `(SignerKey, Signature)` pair into the entry's flat `Signatures`
|
|
29
|
+
* map (host-ordered).
|
|
30
|
+
*
|
|
31
|
+
* Mutates and returns the passed entry.
|
|
32
|
+
*/
|
|
33
|
+
export async function signAuthEntry(deps, entry, signer, options) {
|
|
34
|
+
if (entry.credentials().switch().name === "sorobanCredentialsAddressWithDelegates") {
|
|
35
|
+
throw new SigningError("ADDRESS_WITH_DELEGATES auth entries are not supported by passkey signing", PasskeyKitErrorCode.UNSUPPORTED_CREDENTIALS);
|
|
36
|
+
}
|
|
37
|
+
const credentials = getAddressCredentials(entry.credentials());
|
|
38
|
+
// `== null`, not `!expiration`: an explicit `expiration: 0` is a caller-chosen
|
|
39
|
+
// value, not "unset" — only undefined/null falls through to the entry's
|
|
40
|
+
// existing ledger or a freshly computed default.
|
|
41
|
+
let expiration = options?.expiration;
|
|
42
|
+
if (expiration == null) {
|
|
43
|
+
expiration = credentials.signatureExpirationLedger();
|
|
44
|
+
if (!expiration) {
|
|
45
|
+
expiration = await deps.calculateExpiration();
|
|
46
|
+
}
|
|
47
|
+
}
|
|
48
|
+
// Sets credentials.signatureExpirationLedger(expiration) as a side effect.
|
|
49
|
+
const payload = buildSignaturePayload(deps.networkPassphrase, entry, expiration);
|
|
50
|
+
const prepared = await signer.sign(payload, deps.signerContext);
|
|
51
|
+
const scKey = signerKeyToScVal(deps.spec, prepared.key);
|
|
52
|
+
const scVal = signatureToScVal(deps.spec, prepared.value);
|
|
53
|
+
upsertSignatureEntry(credentials, scKey, scVal);
|
|
54
|
+
return entry;
|
|
55
|
+
}
|
|
56
|
+
/**
|
|
57
|
+
* Sign every auth entry of an {@link AssembledTransaction} that is authorized by
|
|
58
|
+
* the connected wallet, using `signer`. Returns the same transaction with its
|
|
59
|
+
* auth entries signed.
|
|
60
|
+
*
|
|
61
|
+
* @throws {SigningError} If no wallet is connected.
|
|
62
|
+
*/
|
|
63
|
+
export async function sign(deps, txn, signer, options) {
|
|
64
|
+
const contractId = deps.getContractId();
|
|
65
|
+
if (!contractId) {
|
|
66
|
+
throw new SigningError("A wallet must be connected to sign a transaction", PasskeyKitErrorCode.SIGNING_FAILED);
|
|
67
|
+
}
|
|
68
|
+
await txn.signAuthEntries({
|
|
69
|
+
address: contractId,
|
|
70
|
+
authorizeEntry: async (entry) => {
|
|
71
|
+
const clone = xdr.SorobanAuthorizationEntry.fromXDR(entry.toXDR());
|
|
72
|
+
return signAuthEntry(deps, clone, signer, options);
|
|
73
|
+
},
|
|
74
|
+
});
|
|
75
|
+
return txn;
|
|
76
|
+
}
|
|
77
|
+
/**
|
|
78
|
+
* Restore an archived contract-data footprint reported by simulation, paying
|
|
79
|
+
* with the deployer keypair.
|
|
80
|
+
*
|
|
81
|
+
* Soroban simulation returns a `restorePreamble` when the transaction touches
|
|
82
|
+
* archived entries; the footprint must be restored (a separate, fee-bearing
|
|
83
|
+
* transaction) before the real transaction can succeed. The deployer keypair
|
|
84
|
+
* pays because it is the on-chain fee source the kit already controls.
|
|
85
|
+
*
|
|
86
|
+
* Returns the restore transaction hash. This path is exercised live in F2 (it
|
|
87
|
+
* requires archived on-chain state to trigger).
|
|
88
|
+
*
|
|
89
|
+
* @throws {SigningError} On submission/confirmation failure.
|
|
90
|
+
*/
|
|
91
|
+
export async function restoreFootprint(deps, restorePreamble) {
|
|
92
|
+
const account = await deps.rpc.getAccount(deps.deployerKeypair.publicKey());
|
|
93
|
+
const fee = (Number(restorePreamble.minResourceFee) + 100_000).toString();
|
|
94
|
+
const restoreTx = new TransactionBuilder(account, {
|
|
95
|
+
fee,
|
|
96
|
+
networkPassphrase: deps.networkPassphrase,
|
|
97
|
+
})
|
|
98
|
+
.addOperation(Operation.restoreFootprint({}))
|
|
99
|
+
.setSorobanData(restorePreamble.transactionData.build())
|
|
100
|
+
.setTimeout(deps.timeoutInSeconds)
|
|
101
|
+
.build();
|
|
102
|
+
restoreTx.sign(deps.deployerKeypair);
|
|
103
|
+
const sendResult = await deps.rpc.sendTransaction(restoreTx);
|
|
104
|
+
if (sendResult.status === "ERROR") {
|
|
105
|
+
throw new PasskeyKitError(`Footprint restore submission failed: ${sendResult.errorResult?.toXDR("base64") ?? "unknown"}`, PasskeyKitErrorCode.RESTORE_REQUIRED, { context: { hash: sendResult.hash } });
|
|
106
|
+
}
|
|
107
|
+
const result = await deps.rpc.pollTransaction(sendResult.hash, { attempts: 10 });
|
|
108
|
+
if (result.status !== "SUCCESS") {
|
|
109
|
+
throw new PasskeyKitError(`Footprint restore did not confirm (status ${result.status})`, PasskeyKitErrorCode.RESTORE_REQUIRED, { context: { hash: sendResult.hash } });
|
|
110
|
+
}
|
|
111
|
+
return sendResult.hash;
|
|
112
|
+
}
|
|
113
|
+
//# sourceMappingURL=tx-ops.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"tx-ops.js","sourceRoot":"","sources":["../../src/kit/tx-ops.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,59 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Wallet signer operations: build add/update/remove signer transactions, encode
|
|
3
|
+
* the SDK-side {@link SignerKey}/{@link SignerLimits} helpers into the contract's
|
|
4
|
+
* union types, and read a signer entry back from the ledger.
|
|
5
|
+
*
|
|
6
|
+
* `getSigner` reads the flat top-level `SignerKey → SignerVal` entry directly via
|
|
7
|
+
* RPC (temporary durability before persistent, per the contract's lookup
|
|
8
|
+
* invariant). This doubles as `connectWallet`'s ownership check (#601 F7): a
|
|
9
|
+
* keyId that resolves to a live signer entry proves the wallet actually knows
|
|
10
|
+
* that passkey. When the contract's `get_signer` view lands (A3) this can move
|
|
11
|
+
* onto the view; the ledger read is equivalent and works today.
|
|
12
|
+
*
|
|
13
|
+
* @packageDocumentation
|
|
14
|
+
*/
|
|
15
|
+
import { type Server } from "@stellar/stellar-sdk/rpc";
|
|
16
|
+
import type { AssembledTransaction, Result, Spec as ContractSpec } from "@stellar/stellar-sdk/contract";
|
|
17
|
+
import { Client as PasskeyClient, type SignerKey as SDKSignerKey, type SignerLimits as SDKSignerLimits, type SignerVal } from "passkey-kit-sdk";
|
|
18
|
+
import { SignerStore, type SignerKey, type SignerLimits } from "../types.js";
|
|
19
|
+
/**
|
|
20
|
+
* The result of a signer-write / upgrade transaction. The reworked contract's
|
|
21
|
+
* admin functions are typed `Result<void>` (they return `Ok(())` or a typed
|
|
22
|
+
* contract error), so the AssembledTransaction is generic over that.
|
|
23
|
+
*/
|
|
24
|
+
export type WalletTx = AssembledTransaction<Result<void>>;
|
|
25
|
+
/** Which write the builder targets. */
|
|
26
|
+
type SignerFn = "add_signer" | "update_signer";
|
|
27
|
+
/** Encode a SDK-side {@link SignerKey} helper into the contract's union. */
|
|
28
|
+
export declare function toContractSignerKey({ key, value }: SignerKey): SDKSignerKey;
|
|
29
|
+
/** Encode SDK-side {@link SignerLimits} into the contract's `SignerLimits`. */
|
|
30
|
+
export declare function toContractSignerLimits(limits: SignerLimits): SDKSignerLimits;
|
|
31
|
+
/** Shared deps for building signer-write transactions. */
|
|
32
|
+
export interface WalletWriteDeps {
|
|
33
|
+
wallet: PasskeyClient;
|
|
34
|
+
timeoutInSeconds: number;
|
|
35
|
+
}
|
|
36
|
+
export declare function buildSecp256r1SignerTx(deps: WalletWriteDeps, fn: SignerFn, keyId: string | Uint8Array, publicKey: string | Uint8Array, limits: SignerLimits, store: SignerStore, expiration?: number): Promise<WalletTx>;
|
|
37
|
+
export declare function buildEd25519SignerTx(deps: WalletWriteDeps, fn: SignerFn, publicKey: string, limits: SignerLimits, store: SignerStore, expiration?: number): Promise<WalletTx>;
|
|
38
|
+
export declare function buildPolicySignerTx(deps: WalletWriteDeps, fn: SignerFn, policy: string, limits: SignerLimits, store: SignerStore, expiration?: number): Promise<WalletTx>;
|
|
39
|
+
export declare function buildRemoveSignerTx(deps: WalletWriteDeps, signerKey: SignerKey): Promise<WalletTx>;
|
|
40
|
+
/** Build an `upgrade(new_wasm_hash)` transaction (renamed from update_contract_code). */
|
|
41
|
+
export declare function buildUpgradeTx(deps: WalletWriteDeps, newWasmHash: Buffer | Uint8Array): Promise<WalletTx>;
|
|
42
|
+
/**
|
|
43
|
+
* Read a signer entry from the ledger, or `null` if absent.
|
|
44
|
+
*
|
|
45
|
+
* Checks temporary durability before persistent (the contract's lookup order).
|
|
46
|
+
* A non-null result proves the wallet holds this signer — the basis of
|
|
47
|
+
* `connectWallet`'s ownership verification.
|
|
48
|
+
*
|
|
49
|
+
* `null` means a genuine not-found in BOTH durabilities. A transport error
|
|
50
|
+
* (RPC 429/5xx/timeout) is NOT swallowed — it propagates, so `connectWallet`
|
|
51
|
+
* never mistakes a flaky RPC for "the passkey is not a signer" and throws a
|
|
52
|
+
* misleading `WalletOwnershipError` for a valid credential.
|
|
53
|
+
*/
|
|
54
|
+
export declare function getSigner(deps: {
|
|
55
|
+
rpc: Server;
|
|
56
|
+
spec: ContractSpec;
|
|
57
|
+
}, contractId: string, signerKey: SignerKey): Promise<SignerVal | null>;
|
|
58
|
+
export {};
|
|
59
|
+
//# sourceMappingURL=wallet-ops.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"wallet-ops.d.ts","sourceRoot":"","sources":["../../src/kit/wallet-ops.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;GAaG;AAGH,OAAO,EAAc,KAAK,MAAM,EAAE,MAAM,0BAA0B,CAAC;AACnE,OAAO,KAAK,EACV,oBAAoB,EACpB,MAAM,EACN,IAAI,IAAI,YAAY,EACrB,MAAM,+BAA+B,CAAC;AACvC,OAAO,EACL,MAAM,IAAI,aAAa,EAGvB,KAAK,SAAS,IAAI,YAAY,EAC9B,KAAK,YAAY,IAAI,eAAe,EACpC,KAAK,SAAS,EACf,MAAM,iBAAiB,CAAC;AAEzB,OAAO,EAAE,WAAW,EAAE,KAAK,SAAS,EAAE,KAAK,YAAY,EAAE,MAAM,aAAa,CAAC;AAI7E;;;;GAIG;AACH,MAAM,MAAM,QAAQ,GAAG,oBAAoB,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC,CAAC;AAO1D,uCAAuC;AACvC,KAAK,QAAQ,GAAG,YAAY,GAAG,eAAe,CAAC;AAE/C,4EAA4E;AAC5E,wBAAgB,mBAAmB,CAAC,EAAE,GAAG,EAAE,KAAK,EAAE,EAAE,SAAS,GAAG,YAAY,CAS3E;AAED,+EAA+E;AAC/E,wBAAgB,sBAAsB,CAAC,MAAM,EAAE,YAAY,GAAG,eAAe,CAa5E;AA6DD,0DAA0D;AAC1D,MAAM,WAAW,eAAe;IAC9B,MAAM,EAAE,aAAa,CAAC;IACtB,gBAAgB,EAAE,MAAM,CAAC;CAC1B;AAED,wBAAgB,sBAAsB,CACpC,IAAI,EAAE,eAAe,EACrB,EAAE,EAAE,QAAQ,EACZ,KAAK,EAAE,MAAM,GAAG,UAAU,EAC1B,SAAS,EAAE,MAAM,GAAG,UAAU,EAC9B,MAAM,EAAE,YAAY,EACpB,KAAK,EAAE,WAAW,EAClB,UAAU,CAAC,EAAE,MAAM,GAClB,OAAO,CAAC,QAAQ,CAAC,CAKnB;AAED,wBAAgB,oBAAoB,CAClC,IAAI,EAAE,eAAe,EACrB,EAAE,EAAE,QAAQ,EACZ,SAAS,EAAE,MAAM,EACjB,MAAM,EAAE,YAAY,EACpB,KAAK,EAAE,WAAW,EAClB,UAAU,CAAC,EAAE,MAAM,GAClB,OAAO,CAAC,QAAQ,CAAC,CAKnB;AAED,wBAAgB,mBAAmB,CACjC,IAAI,EAAE,eAAe,EACrB,EAAE,EAAE,QAAQ,EACZ,MAAM,EAAE,MAAM,EACd,MAAM,EAAE,YAAY,EACpB,KAAK,EAAE,WAAW,EAClB,UAAU,CAAC,EAAE,MAAM,GAClB,OAAO,CAAC,QAAQ,CAAC,CAKnB;AAED,wBAAgB,mBAAmB,CACjC,IAAI,EAAE,eAAe,EACrB,SAAS,EAAE,SAAS,GACnB,OAAO,CAAC,QAAQ,CAAC,CAKnB;AAED,yFAAyF;AACzF,wBAAgB,cAAc,CAC5B,IAAI,EAAE,eAAe,EACrB,WAAW,EAAE,MAAM,GAAG,UAAU,GAC/B,OAAO,CAAC,QAAQ,CAAC,CAKnB;AAED;;;;;;;;;;;GAWG;AACH,wBAAsB,SAAS,CAC7B,IAAI,EAAE;IAAE,GAAG,EAAE,MAAM,CAAC;IAAC,IAAI,EAAE,YAAY,CAAA;CAAE,EACzC,UAAU,EAAE,MAAM,EAClB,SAAS,EAAE,SAAS,GACnB,OAAO,CAAC,SAAS,GAAG,IAAI,CAAC,CAW3B"}
|