passkey-kit 0.7.3 → 0.7.5
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/cheatsheet +4 -2
- package/package.json +6 -3
- package/packages/passkey-factory-sdk/package.json +1 -1
- package/packages/passkey-factory-sdk/src/index.ts +1 -1
- package/packages/passkey-factory-sdk/types/index.d.ts +1 -1
- package/packages/passkey-kit-sdk/package.json +1 -1
- package/packages/passkey-kit-sdk/src/index.ts +1 -1
- package/packages/passkey-kit-sdk/types/index.d.ts +1 -1
- package/packages/sac-sdk/package.json +1 -1
- package/pnpm-workspace.yaml +1 -0
- package/src/kit.ts +90 -184
- package/src/server.ts +3 -2
- package/types/kit.d.ts +9 -14
- package/types/server.d.ts +2 -1
package/cheatsheet
CHANGED
|
@@ -13,8 +13,10 @@ stellar contract deploy --wasm target/wasm32-unknown-unknown/release/sample_poli
|
|
|
13
13
|
|
|
14
14
|
export JWT=???
|
|
15
15
|
mercury-cli --jwt $JWT --local false --mainnet false deploy
|
|
16
|
-
mercury-cli --jwt $JWT --local false --mainnet false catchup --project-name "smart-wallets-data-multi-signer-multi-sig" --contracts "
|
|
16
|
+
mercury-cli --jwt $JWT --local false --mainnet false catchup --project-name "smart-wallets-data-multi-signer-multi-sig" --contracts "CAGXSSDBSFBI5633C4O4KF53XPU64BMX36JMJTJNITOAWGP442XHZSHM"
|
|
17
17
|
curl -X GET https://api.mercurydata.app/catchups/4
|
|
18
18
|
curl -X POST https://api.mercurydata.app/zephyr/execute -H "Authorization: Bearer $MERCURY_JWT" -H 'Content-Type: application/json' -d '{"mode":{"Function": {"fname": "get_signers_by_address", "arguments": "{\"address\": \"CA4G3X75IGGNXNLXFIVFNYIGC6YAVLA7KSIFFDBSR7RQ7KEZMZWLXQBH\"}"}}}'
|
|
19
19
|
curl -X POST https://api.mercurydata.app/zephyr/execute -H "Authorization: Bearer $MERCURY_JWT" -H 'Content-Type: application/json' -d '{"mode":{"Function": {"fname": "get_address_by_signer", "arguments": "{\"id\": [78,127,30,69,248,174,95,168,47,59,161,168,51,120,117,135,112,133,232,92]}"}}}'
|
|
20
|
-
curl -X POST https://api.mercurydata.app/zephyr/execute -H "Authorization: Bearer $MERCURY_JWT" -H 'Content-Type: application/json' -d '{"mode":{"Function": {"fname": "get_events_by_address", "arguments": "{\"address\": \"CA4G3X75IGGNXNLXFIVFNYIGC6YAVLA7KSIFFDBSR7RQ7KEZMZWLXQBH\"}"}}}'
|
|
20
|
+
curl -X POST https://api.mercurydata.app/zephyr/execute -H "Authorization: Bearer $MERCURY_JWT" -H 'Content-Type: application/json' -d '{"mode":{"Function": {"fname": "get_events_by_address", "arguments": "{\"address\": \"CA4G3X75IGGNXNLXFIVFNYIGC6YAVLA7KSIFFDBSR7RQ7KEZMZWLXQBH\"}"}}}'
|
|
21
|
+
|
|
22
|
+
cp -R ext/js-stellar-sdk/lib/. ext/@stellar/stellar-sdk/
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "passkey-kit",
|
|
3
|
-
"version": "0.7.
|
|
3
|
+
"version": "0.7.5",
|
|
4
4
|
"description": "A helper library for creating and using passkey accounts on the Stellar blockchain.",
|
|
5
5
|
"author": "Tyler van der Hoeven",
|
|
6
6
|
"license": "MIT",
|
|
@@ -10,7 +10,7 @@
|
|
|
10
10
|
"dependencies": {
|
|
11
11
|
"@darkedges/capacitor-native-webauthn": "^0.0.4",
|
|
12
12
|
"@simplewebauthn/browser": "^10.0.0",
|
|
13
|
-
"@stellar/stellar-sdk": "
|
|
13
|
+
"@stellar/stellar-sdk": "file:./ext/js-stellar-sdk",
|
|
14
14
|
"base64url": "^3.0.1",
|
|
15
15
|
"buffer": "^6.0.3",
|
|
16
16
|
"passkey-factory-sdk": "0.3.1",
|
|
@@ -19,10 +19,13 @@
|
|
|
19
19
|
},
|
|
20
20
|
"devDependencies": {
|
|
21
21
|
"@simplewebauthn/types": "^10.0.0",
|
|
22
|
+
"@types/node": "^22.7.3",
|
|
22
23
|
"typescript": "^5.6.2"
|
|
23
24
|
},
|
|
24
25
|
"workspaces": [
|
|
25
|
-
"packages
|
|
26
|
+
"packages/passkey-factory-sdk",
|
|
27
|
+
"packages/passkey-kit-sdk",
|
|
28
|
+
"packages/sac-sdk"
|
|
26
29
|
],
|
|
27
30
|
"engine": {
|
|
28
31
|
"node": ">=20"
|
|
@@ -30,7 +30,7 @@ if (typeof window !== 'undefined') {
|
|
|
30
30
|
export const networks = {
|
|
31
31
|
testnet: {
|
|
32
32
|
networkPassphrase: "Test SDF Network ; September 2015",
|
|
33
|
-
contractId: "
|
|
33
|
+
contractId: "CBFNOEJVO4WVIHAYIBGES5AFTOWBBN274B3VD32QSD7AYJ6J4EH3K6HC",
|
|
34
34
|
}
|
|
35
35
|
} as const
|
|
36
36
|
|
|
@@ -4,7 +4,7 @@ import type { Option } from '@stellar/stellar-sdk/contract';
|
|
|
4
4
|
export declare const networks: {
|
|
5
5
|
readonly testnet: {
|
|
6
6
|
readonly networkPassphrase: "Test SDF Network ; September 2015";
|
|
7
|
-
readonly contractId: "
|
|
7
|
+
readonly contractId: "CBFNOEJVO4WVIHAYIBGES5AFTOWBBN274B3VD32QSD7AYJ6J4EH3K6HC";
|
|
8
8
|
};
|
|
9
9
|
};
|
|
10
10
|
export type SignerLimits = readonly [Map<string, Option<Array<SignerKey>>>];
|
|
@@ -30,7 +30,7 @@ if (typeof window !== 'undefined') {
|
|
|
30
30
|
export const networks = {
|
|
31
31
|
testnet: {
|
|
32
32
|
networkPassphrase: "Test SDF Network ; September 2015",
|
|
33
|
-
contractId: "
|
|
33
|
+
contractId: "CBFNOEJVO4WVIHAYIBGES5AFTOWBBN274B3VD32QSD7AYJ6J4EH3K6HC",
|
|
34
34
|
}
|
|
35
35
|
} as const
|
|
36
36
|
|
|
@@ -4,7 +4,7 @@ import type { Option } from '@stellar/stellar-sdk/contract';
|
|
|
4
4
|
export declare const networks: {
|
|
5
5
|
readonly testnet: {
|
|
6
6
|
readonly networkPassphrase: "Test SDF Network ; September 2015";
|
|
7
|
-
readonly contractId: "
|
|
7
|
+
readonly contractId: "CBFNOEJVO4WVIHAYIBGES5AFTOWBBN274B3VD32QSD7AYJ6J4EH3K6HC";
|
|
8
8
|
};
|
|
9
9
|
};
|
|
10
10
|
export declare const Errors: {
|
package/pnpm-workspace.yaml
CHANGED
package/src/kit.ts
CHANGED
|
@@ -1,12 +1,12 @@
|
|
|
1
1
|
import { Client as PasskeyClient, type Signature, type SignerKey } from 'passkey-kit-sdk'
|
|
2
2
|
import { Client as FactoryClient } from 'passkey-factory-sdk'
|
|
3
|
-
import { Address, StrKey, hash, xdr,
|
|
3
|
+
import { Address, StrKey, hash, xdr, SorobanRpc, Keypair, Transaction, Operation } from '@stellar/stellar-sdk'
|
|
4
4
|
import base64url from 'base64url'
|
|
5
5
|
import { startRegistration, startAuthentication } from "@simplewebauthn/browser"
|
|
6
6
|
import type { AuthenticatorAttestationResponseJSON, AuthenticatorSelectionCriteria } from "@simplewebauthn/types"
|
|
7
7
|
import { Buffer } from 'buffer'
|
|
8
8
|
import { PasskeyBase } from './base'
|
|
9
|
-
import { DEFAULT_TIMEOUT } from '@stellar/stellar-sdk/contract'
|
|
9
|
+
import { AssembledTransaction, DEFAULT_TIMEOUT, type Tx } from '@stellar/stellar-sdk/contract'
|
|
10
10
|
|
|
11
11
|
export class PasskeyKit extends PasskeyBase {
|
|
12
12
|
declare public rpc: SorobanRpc.Server
|
|
@@ -75,7 +75,7 @@ export class PasskeyKit extends PasskeyBase {
|
|
|
75
75
|
return {
|
|
76
76
|
keyId,
|
|
77
77
|
contractId,
|
|
78
|
-
|
|
78
|
+
built
|
|
79
79
|
}
|
|
80
80
|
}
|
|
81
81
|
|
|
@@ -185,27 +185,28 @@ export class PasskeyKit extends PasskeyBase {
|
|
|
185
185
|
rpId?: string,
|
|
186
186
|
keyId?: 'any' | string | Uint8Array
|
|
187
187
|
keypair?: Keypair,
|
|
188
|
-
|
|
188
|
+
policy?: string,
|
|
189
|
+
expiration?: number
|
|
189
190
|
}
|
|
190
191
|
) {
|
|
191
|
-
let { rpId, keyId, keypair,
|
|
192
|
+
let { rpId, keyId, keypair, policy, expiration } = options || {}
|
|
192
193
|
|
|
193
|
-
if (keyId
|
|
194
|
-
throw new Error('
|
|
194
|
+
if ([keyId, keypair, policy].filter((arg) => arg).length !== 1)
|
|
195
|
+
throw new Error('Exactly one of `options.keyId`, `options.keypair`, or `options.policy` must be provided.');
|
|
195
196
|
|
|
196
197
|
const credentials = entry.credentials().address();
|
|
197
198
|
|
|
198
|
-
if (!
|
|
199
|
-
|
|
199
|
+
if (!expiration) {
|
|
200
|
+
expiration = credentials.signatureExpirationLedger()
|
|
200
201
|
|
|
201
|
-
if (!
|
|
202
|
+
if (!expiration) {
|
|
202
203
|
const lastLedger = await this.rpc.getLatestLedger().then(({ sequence }) => sequence)
|
|
203
|
-
|
|
204
|
+
expiration = lastLedger + DEFAULT_TIMEOUT / 5;
|
|
204
205
|
}
|
|
205
206
|
}
|
|
206
207
|
|
|
207
|
-
credentials.signatureExpirationLedger(
|
|
208
|
-
|
|
208
|
+
credentials.signatureExpirationLedger(expiration)
|
|
209
|
+
|
|
209
210
|
const preimage = xdr.HashIdPreimage.envelopeTypeSorobanAuthorization(
|
|
210
211
|
new xdr.HashIdPreimageSorobanAuthorization({
|
|
211
212
|
networkId: hash(Buffer.from(this.networkPassphrase)),
|
|
@@ -214,13 +215,22 @@ export class PasskeyKit extends PasskeyBase {
|
|
|
214
215
|
invocation: entry.rootInvocation()
|
|
215
216
|
})
|
|
216
217
|
)
|
|
218
|
+
|
|
217
219
|
const payload = hash(preimage.toXDR())
|
|
218
220
|
|
|
219
221
|
let key: SignerKey
|
|
220
|
-
let val: Signature
|
|
222
|
+
let val: Signature | undefined
|
|
223
|
+
|
|
224
|
+
// Sign with a policy
|
|
225
|
+
if (policy) {
|
|
226
|
+
key = {
|
|
227
|
+
tag: "Policy",
|
|
228
|
+
values: [policy]
|
|
229
|
+
}
|
|
230
|
+
}
|
|
221
231
|
|
|
222
232
|
// Sign with the keypair as an ed25519 signer
|
|
223
|
-
if (keypair) {
|
|
233
|
+
else if (keypair) {
|
|
224
234
|
const signature = keypair.sign(payload);
|
|
225
235
|
|
|
226
236
|
key = {
|
|
@@ -288,8 +298,8 @@ export class PasskeyKit extends PasskeyBase {
|
|
|
288
298
|
const scValType = xdr.ScSpecTypeDef.scSpecTypeUdt(
|
|
289
299
|
new xdr.ScSpecTypeUdt({ name: "Signature" }),
|
|
290
300
|
);
|
|
291
|
-
const scVal = this.wallet!.spec.nativeToScVal(val, scValType);
|
|
292
301
|
const scKey = this.wallet!.spec.nativeToScVal(key, scKeyType);
|
|
302
|
+
const scVal = val ? this.wallet!.spec.nativeToScVal(val, scValType) : xdr.ScVal.scvVoid();
|
|
293
303
|
const scEntry = new xdr.ScMapEntry({
|
|
294
304
|
key: scKey,
|
|
295
305
|
val: scVal,
|
|
@@ -302,10 +312,18 @@ export class PasskeyKit extends PasskeyBase {
|
|
|
302
312
|
case 'scvMap':
|
|
303
313
|
// Add the new signature to the existing map
|
|
304
314
|
credentials.signature().map()?.push(scEntry)
|
|
315
|
+
|
|
305
316
|
// Order the map by key
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
|
|
317
|
+
// Not using Buffer.compare because Symbols are 9 bytes and unused bytes _append_ 0s vs prepending them, which is too bad
|
|
318
|
+
credentials.signature().map()?.sort((a, b) => {
|
|
319
|
+
return (
|
|
320
|
+
a.key().vec()![0].sym() +
|
|
321
|
+
a.key().vec()![1].toXDR().join('')
|
|
322
|
+
).localeCompare(
|
|
323
|
+
b.key().vec()![0].sym() +
|
|
324
|
+
b.key().vec()![1].toXDR().join('')
|
|
325
|
+
)
|
|
326
|
+
})
|
|
309
327
|
break;
|
|
310
328
|
default:
|
|
311
329
|
throw new Error('Unsupported signature')
|
|
@@ -314,181 +332,69 @@ export class PasskeyKit extends PasskeyBase {
|
|
|
314
332
|
return entry
|
|
315
333
|
}
|
|
316
334
|
|
|
317
|
-
public async signAuthEntries(
|
|
318
|
-
|
|
319
|
-
|
|
320
|
-
|
|
321
|
-
|
|
322
|
-
|
|
323
|
-
|
|
324
|
-
|
|
325
|
-
|
|
326
|
-
|
|
327
|
-
|
|
328
|
-
|
|
329
|
-
|
|
330
|
-
|
|
331
|
-
|
|
332
|
-
|
|
333
|
-
|
|
334
|
-
|
|
335
|
-
|
|
336
|
-
|
|
337
|
-
|
|
338
|
-
|
|
339
|
-
|
|
340
|
-
}
|
|
335
|
+
// public async signAuthEntries(
|
|
336
|
+
// entries: xdr.SorobanAuthorizationEntry[],
|
|
337
|
+
// options?: {
|
|
338
|
+
// rpId?: string,
|
|
339
|
+
// keyId?: 'any' | string | Uint8Array
|
|
340
|
+
// keypair?: Keypair,
|
|
341
|
+
// policy?: string,
|
|
342
|
+
// expiration?: number
|
|
343
|
+
// }
|
|
344
|
+
// ) {
|
|
345
|
+
// // TODO should there be more control over which auth entries are signed? Especially given we support multiple signers now?
|
|
346
|
+
// // As-is .sign() will always sign every smart wallet auth entry. This may be okay but likely we should have more control over which auth entry the signer is signing
|
|
347
|
+
// for (const auth of entries) {
|
|
348
|
+
// if (
|
|
349
|
+
// auth.credentials().switch().name === 'sorobanCredentialsAddress'
|
|
350
|
+
// && auth.credentials().address().address().switch().name === 'scAddressTypeContract'
|
|
351
|
+
// ) {
|
|
352
|
+
// // If auth entry matches our Smart Wallet move forward with the signature request
|
|
353
|
+
// if (Address.contract(auth.credentials().address().address().contractId()).toString() === this.wallet?.options.contractId)
|
|
354
|
+
// await this.signAuthEntry(auth, options)
|
|
355
|
+
// }
|
|
356
|
+
// }
|
|
357
|
+
// }
|
|
341
358
|
|
|
342
359
|
public async sign(
|
|
343
|
-
txn:
|
|
360
|
+
txn: AssembledTransaction<unknown>,
|
|
344
361
|
options?: {
|
|
345
362
|
rpId?: string,
|
|
346
363
|
keyId?: 'any' | string | Uint8Array
|
|
347
364
|
keypair?: Keypair,
|
|
348
|
-
|
|
349
|
-
|
|
350
|
-
) {
|
|
351
|
-
txn = this.getTxn(txn)
|
|
352
|
-
|
|
353
|
-
// Only need to sign auth for `invokeHostFunction` operations
|
|
354
|
-
if (txn.operations[0].type === 'invokeHostFunction') {
|
|
355
|
-
const entries = txn.operations[0].auth
|
|
356
|
-
|
|
357
|
-
if (entries)
|
|
358
|
-
await this.signAuthEntries(entries, options)
|
|
365
|
+
policy?: string,
|
|
366
|
+
expiration?: number
|
|
359
367
|
}
|
|
360
|
-
|
|
361
|
-
return txn.toXDR()
|
|
362
|
-
}
|
|
363
|
-
|
|
364
|
-
public async attachPolicy(
|
|
365
|
-
txn: Transaction | string,
|
|
366
|
-
index: number,
|
|
367
|
-
policy: string
|
|
368
368
|
) {
|
|
369
|
-
txn
|
|
370
|
-
|
|
371
|
-
|
|
372
|
-
|
|
373
|
-
|
|
374
|
-
|
|
375
|
-
|
|
376
|
-
throw new Error('Wallet not connected')
|
|
377
|
-
|
|
378
|
-
let context_arg: xdr.ScVal
|
|
379
|
-
|
|
380
|
-
const auth = txn.operations[0].auth?.[index]
|
|
381
|
-
const context = auth?.rootInvocation().function()
|
|
382
|
-
|
|
383
|
-
if (!auth || !context)
|
|
384
|
-
throw new Error('No context found')
|
|
385
|
-
|
|
386
|
-
switch (context.switch().name) {
|
|
387
|
-
case 'sorobanAuthorizedFunctionTypeContractFn':
|
|
388
|
-
switch (context.contractFn().contractAddress().switch().name) {
|
|
389
|
-
case 'scAddressTypeContract':
|
|
390
|
-
context_arg = xdr.ScVal.scvVec([
|
|
391
|
-
xdr.ScVal.scvSymbol("Contract"),
|
|
392
|
-
xdr.ScVal.scvMap([
|
|
393
|
-
new xdr.ScMapEntry({
|
|
394
|
-
key: xdr.ScVal.scvSymbol("args"),
|
|
395
|
-
val: xdr.ScVal.scvVec(context.contractFn().args()),
|
|
396
|
-
}),
|
|
397
|
-
new xdr.ScMapEntry({
|
|
398
|
-
key: xdr.ScVal.scvSymbol("contract"),
|
|
399
|
-
val: Address.contract(context.contractFn().contractAddress().contractId()).toScVal(),
|
|
400
|
-
}),
|
|
401
|
-
new xdr.ScMapEntry({
|
|
402
|
-
key: xdr.ScVal.scvSymbol("fn_name"),
|
|
403
|
-
val: xdr.ScVal.scvSymbol(context.contractFn().functionName()),
|
|
404
|
-
}),
|
|
405
|
-
]),
|
|
406
|
-
])
|
|
407
|
-
break;
|
|
408
|
-
default:
|
|
409
|
-
throw new Error('Unsupported contractAddress')
|
|
410
|
-
}
|
|
411
|
-
break;
|
|
412
|
-
case 'sorobanAuthorizedFunctionTypeCreateContractHostFn':
|
|
413
|
-
switch (context.createContractHostFn().contractIdPreimage().switch().name) {
|
|
414
|
-
case 'contractIdPreimageFromAddress':
|
|
415
|
-
context_arg = xdr.ScVal.scvVec([
|
|
416
|
-
xdr.ScVal.scvSymbol("CreateContractHostFn"),
|
|
417
|
-
xdr.ScVal.scvMap([
|
|
418
|
-
new xdr.ScMapEntry({
|
|
419
|
-
key: xdr.ScVal.scvSymbol("executable"),
|
|
420
|
-
val: xdr.ScVal.scvVec([
|
|
421
|
-
xdr.ScVal.scvSymbol("Wasm"),
|
|
422
|
-
xdr.ScVal.scvBytes(context.createContractHostFn().executable().wasmHash())
|
|
423
|
-
]),
|
|
424
|
-
}),
|
|
425
|
-
new xdr.ScMapEntry({
|
|
426
|
-
key: xdr.ScVal.scvSymbol("salt"),
|
|
427
|
-
val: xdr.ScVal.scvBytes(context.createContractHostFn().contractIdPreimage().fromAddress().salt()),
|
|
428
|
-
}),
|
|
429
|
-
]),
|
|
430
|
-
])
|
|
431
|
-
break;
|
|
432
|
-
default:
|
|
433
|
-
throw new Error('Unsupported contractIdPreimage')
|
|
434
|
-
}
|
|
435
|
-
break;
|
|
436
|
-
default:
|
|
437
|
-
throw new Error('Unsupported context')
|
|
438
|
-
}
|
|
439
|
-
|
|
440
|
-
const __check_auth_args = new xdr.InvokeContractArgs({
|
|
441
|
-
contractAddress: Address.fromString(this.wallet.options.contractId).toScAddress(),
|
|
442
|
-
functionName: "__check_auth",
|
|
443
|
-
args: [context_arg],
|
|
444
|
-
});
|
|
445
|
-
|
|
446
|
-
const __check_auth_invocation = new xdr.SorobanAuthorizedInvocation({
|
|
447
|
-
function:
|
|
448
|
-
xdr.SorobanAuthorizedFunction.sorobanAuthorizedFunctionTypeContractFn(
|
|
449
|
-
__check_auth_args,
|
|
450
|
-
),
|
|
451
|
-
subInvocations: [],
|
|
452
|
-
});
|
|
453
|
-
|
|
454
|
-
const __check_auth = new xdr.SorobanAuthorizationEntry({
|
|
455
|
-
credentials: xdr.SorobanCredentials.sorobanCredentialsAddress(
|
|
456
|
-
new xdr.SorobanAddressCredentials({
|
|
457
|
-
address: Address.fromString(policy).toScAddress(),
|
|
458
|
-
nonce: auth.credentials().address().nonce(),
|
|
459
|
-
signatureExpirationLedger: auth.credentials().address().signatureExpirationLedger(),
|
|
460
|
-
signature: xdr.ScVal.scvVec([]),
|
|
461
|
-
}),
|
|
462
|
-
),
|
|
463
|
-
rootInvocation: __check_auth_invocation,
|
|
464
|
-
});
|
|
465
|
-
|
|
466
|
-
txn.operations[0].auth?.push(__check_auth)
|
|
467
|
-
|
|
468
|
-
return txn.toXDR()
|
|
369
|
+
await txn.signAuthEntries({
|
|
370
|
+
address: this.wallet!.options.contractId,
|
|
371
|
+
authorizeEntry: (entry) => {
|
|
372
|
+
const clone = xdr.SorobanAuthorizationEntry.fromXDR(entry.toXDR())
|
|
373
|
+
return this.signAuthEntry(clone, options)
|
|
374
|
+
},
|
|
375
|
+
})
|
|
469
376
|
}
|
|
470
377
|
|
|
471
|
-
private
|
|
472
|
-
|
|
473
|
-
|
|
474
|
-
|
|
475
|
-
|
|
476
|
-
|
|
477
|
-
|
|
478
|
-
|
|
479
|
-
|
|
480
|
-
|
|
481
|
-
|
|
482
|
-
|
|
483
|
-
|
|
484
|
-
|
|
485
|
-
|
|
486
|
-
|
|
487
|
-
|
|
488
|
-
|
|
489
|
-
|
|
490
|
-
|
|
491
|
-
}
|
|
378
|
+
// private getAuthEntries(txn: Transaction) {
|
|
379
|
+
// if (txn.operations.length !== 1)
|
|
380
|
+
// throw new Error('Must include only one Soroban operation')
|
|
381
|
+
|
|
382
|
+
// for (const op of txn.operations) {
|
|
383
|
+
// if (
|
|
384
|
+
// op.type !== 'invokeHostFunction'
|
|
385
|
+
// && op.type !== 'extendFootprintTtl'
|
|
386
|
+
// && op.type !== 'restoreFootprint'
|
|
387
|
+
// ) throw new Error('Must include only one operation of type `invokeHostFunction` or `extendFootprintTtl` or `restoreFootprint`')
|
|
388
|
+
// }
|
|
389
|
+
|
|
390
|
+
// // Only need to sign auth for `invokeHostFunction` operations
|
|
391
|
+
// if (txn.operations[0].type === 'invokeHostFunction') {
|
|
392
|
+
// const entries = txn.operations[0].auth
|
|
393
|
+
|
|
394
|
+
// if (entries && entries.length)
|
|
395
|
+
// return entries
|
|
396
|
+
// }
|
|
397
|
+
// }
|
|
492
398
|
|
|
493
399
|
/* LATER
|
|
494
400
|
- Add a getKeyInfo action to get info about a specific passkey
|
package/src/server.ts
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import { SorobanRpc, xdr } from "@stellar/stellar-sdk"
|
|
2
2
|
import { PasskeyBase } from "./base"
|
|
3
3
|
import base64url from "base64url"
|
|
4
|
+
import type { Tx } from "@stellar/stellar-sdk/contract"
|
|
4
5
|
|
|
5
6
|
export class PasskeyServer extends PasskeyBase {
|
|
6
7
|
public launchtubeUrl: string | undefined
|
|
@@ -123,13 +124,13 @@ export class PasskeyServer extends PasskeyBase {
|
|
|
123
124
|
- Add a method for getting a paginated or filtered list of all a wallet's events
|
|
124
125
|
*/
|
|
125
126
|
|
|
126
|
-
public async send(
|
|
127
|
+
public async send(txn: Tx, fee?: number) {
|
|
127
128
|
if (!this.launchtubeUrl || !this.launchtubeJwt)
|
|
128
129
|
throw new Error('Launchtube service not configured')
|
|
129
130
|
|
|
130
131
|
const data = new FormData();
|
|
131
132
|
|
|
132
|
-
data.set('xdr',
|
|
133
|
+
data.set('xdr', txn.toXDR());
|
|
133
134
|
|
|
134
135
|
if (fee)
|
|
135
136
|
data.set('fee', fee.toString());
|
package/types/kit.d.ts
CHANGED
|
@@ -1,10 +1,11 @@
|
|
|
1
1
|
import { Client as PasskeyClient } from 'passkey-kit-sdk';
|
|
2
2
|
import { Client as FactoryClient } from 'passkey-factory-sdk';
|
|
3
|
-
import { xdr,
|
|
3
|
+
import { xdr, SorobanRpc, Keypair } from '@stellar/stellar-sdk';
|
|
4
4
|
import { startRegistration, startAuthentication } from "@simplewebauthn/browser";
|
|
5
5
|
import type { AuthenticatorSelectionCriteria } from "@simplewebauthn/types";
|
|
6
6
|
import { Buffer } from 'buffer';
|
|
7
7
|
import { PasskeyBase } from './base';
|
|
8
|
+
import { AssembledTransaction, type Tx } from '@stellar/stellar-sdk/contract';
|
|
8
9
|
export declare class PasskeyKit extends PasskeyBase {
|
|
9
10
|
rpc: SorobanRpc.Server;
|
|
10
11
|
rpcUrl: string;
|
|
@@ -28,7 +29,7 @@ export declare class PasskeyKit extends PasskeyBase {
|
|
|
28
29
|
createWallet(app: string, user: string): Promise<{
|
|
29
30
|
keyId: Buffer;
|
|
30
31
|
contractId: string;
|
|
31
|
-
|
|
32
|
+
built: Tx;
|
|
32
33
|
}>;
|
|
33
34
|
createKey(app: string, user: string, settings?: {
|
|
34
35
|
rpId?: string;
|
|
@@ -49,22 +50,16 @@ export declare class PasskeyKit extends PasskeyBase {
|
|
|
49
50
|
rpId?: string;
|
|
50
51
|
keyId?: 'any' | string | Uint8Array;
|
|
51
52
|
keypair?: Keypair;
|
|
52
|
-
|
|
53
|
+
policy?: string;
|
|
54
|
+
expiration?: number;
|
|
53
55
|
}): Promise<xdr.SorobanAuthorizationEntry>;
|
|
54
|
-
|
|
56
|
+
sign(txn: AssembledTransaction<unknown>, options?: {
|
|
55
57
|
rpId?: string;
|
|
56
58
|
keyId?: 'any' | string | Uint8Array;
|
|
57
59
|
keypair?: Keypair;
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
rpId?: string;
|
|
62
|
-
keyId?: 'any' | string | Uint8Array;
|
|
63
|
-
keypair?: Keypair;
|
|
64
|
-
validUntilLedgerSeq?: number;
|
|
65
|
-
}): Promise<string>;
|
|
66
|
-
attachPolicy(txn: Transaction | string, index: number, policy: string): Promise<string>;
|
|
67
|
-
private getTxn;
|
|
60
|
+
policy?: string;
|
|
61
|
+
expiration?: number;
|
|
62
|
+
}): Promise<void>;
|
|
68
63
|
private getPublicKey;
|
|
69
64
|
private compactSignature;
|
|
70
65
|
}
|
package/types/server.d.ts
CHANGED
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import { PasskeyBase } from "./base";
|
|
2
|
+
import type { Tx } from "@stellar/stellar-sdk/contract";
|
|
2
3
|
export declare class PasskeyServer extends PasskeyBase {
|
|
3
4
|
launchtubeUrl: string | undefined;
|
|
4
5
|
launchtubeJwt: string | undefined;
|
|
@@ -19,5 +20,5 @@ export declare class PasskeyServer extends PasskeyBase {
|
|
|
19
20
|
expired?: boolean;
|
|
20
21
|
}[]>;
|
|
21
22
|
getContractId(keyId: string): Promise<any>;
|
|
22
|
-
send(
|
|
23
|
+
send(txn: Tx, fee?: number): Promise<any>;
|
|
23
24
|
}
|