w3pk 0.9.1 → 0.9.2

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 CHANGED
@@ -11,6 +11,8 @@ Passwordless Web3 authentication SDK with encrypted wallets and privacy features
11
11
  ## Install
12
12
  ```bash
13
13
  npm install w3pk ethers
14
+ # or
15
+ npm install w3pk viem
14
16
  ```
15
17
 
16
18
  ## Quick Start
@@ -34,9 +36,6 @@ const tx = await w3pk.sendTransaction({ to: '0x...', value: 1n * 10n**18n, chain
34
36
  // EIP-1193 provider (ethers, viem, wagmi, RainbowKit)
35
37
  const eip1193 = w3pk.getEIP1193Provider({ chainId: 1 })
36
38
 
37
- // Derive wallets (STANDARD/STRICT/YOLO modes)
38
- const wallet = await w3pk.deriveWallet('STANDARD', 'GAMING')
39
-
40
39
  // Get RPC endpoints
41
40
  const endpoints = await w3pk.getEndpoints(1)
42
41
  ```
@@ -85,17 +84,28 @@ await w3pk.logout()
85
84
 
86
85
  ### Wallet Derivation
87
86
 
87
+ w3pk supports multiple security modes for deriving wallets with different privacy and security trade-offs:
88
+
88
89
  ```typescript
89
- // STANDARD mode - address only (no private key)
90
+ // PRIMARY mode - WebAuthn P-256 passkey (EIP-7951)
91
+ // Uses hardware-backed passkey directly, no seed phrase involved
92
+ const primaryWallet = await w3pk.deriveWallet('PRIMARY')
93
+ // Returns: { address, publicKey, origin, mode: 'PRIMARY', tag: 'MAIN' }
94
+
95
+ // STANDARD mode - Default balanced security (recommended)
96
+ // Returns address only, private key stays in SDK for signing
90
97
  const mainWallet = await w3pk.deriveWallet('STANDARD')
91
- // Returns: { address, index, origin, tag: 'MAIN' }
98
+ // Returns: { address, index, origin, mode: 'STANDARD', tag: 'MAIN' }
92
99
 
93
- // YOLO mode - includes private key for app-specific use
100
+ // YOLO mode - Private key exposed to app
101
+ // Use only when app needs direct key access (advanced use cases)
94
102
  const gamingWallet = await w3pk.deriveWallet('YOLO', 'GAMING')
95
- // Returns: { address, privateKey, index, origin, tag: 'GAMING' }
103
+ // Returns: { address, privateKey, index, origin, mode: 'YOLO', tag: 'GAMING' }
96
104
 
97
- // STRICT mode - address only, no persistent sessions allowed
105
+ // STRICT mode - Maximum security, re-auth required every time
106
+ // Requires biometric/PIN for each call - impractical for most apps
98
107
  const strictWallet = await w3pk.deriveWallet('STRICT', 'SECURE')
108
+ // Returns: { address, privateKey, index, origin, mode: 'STRICT', tag: 'SECURE' }
99
109
 
100
110
  // Different tags generate different addresses
101
111
  console.log(mainWallet.address !== gamingWallet.address) // true
@@ -421,6 +431,8 @@ console.log(result.report)
421
431
  await inspectNow() // Logs report directly to console
422
432
  ```
423
433
 
434
+ **Note:** Inspection API calls are sponsored by the [W3HC (Web3 Hackers Collective)](https://w3hc.org).
435
+
424
436
  **Node.js (analyze local files):**
425
437
  ```typescript
426
438
  import { inspect, gatherCode } from 'w3pk/inspect/node'
@@ -464,6 +476,7 @@ Host applications should verify their installed W3PK build against this registry
464
476
  - [Security Inspection](./docs/INSPECTION.md)
465
477
  - [EIP-7951](./docs/EIP-7951.md)
466
478
  - [Security Architecture](./docs/SECURITY.md)
479
+ - [Post-Quantum Cryptography](./docs/POST_QUANTUM.md) - Quantum-safe migration roadmap
467
480
  - [Recovery & Backup System](./docs/RECOVERY.md)
468
481
  - [Portability Guide](./docs/PORTABILITY.md)
469
482
  - [ZK Proofs](./docs/ZK.md)
package/dist/index.js CHANGED
@@ -954,7 +954,7 @@ ${e}`)}`:r!=null?`${r.split(`
954
954
  ${e}`)}`:t!=null?`${t}`:`${n.toString()}`}function bg(n){return n instanceof AggregateError||n?.name==="AggregateError"&&Array.isArray(n.errors)}function Xu(n,e=""){if(bg(n)){let t=Ju(n,e);return n.errors.length>0?(e=`${e} `,t+=`
955
955
  ${e}${n.errors.map(r=>`${Xu(r,`${e}`)}`).join(`
956
956
  ${e}`)}`):t+=`
957
- ${e}[Error list was empty]`,t.trim()}return Ju(n,e)}function Sg(n){let e=()=>{};return e.enabled=!1,e.color="",e.diff=0,e.log=()=>{},e.namespace=n,e.destroy=()=>!0,e.extend=()=>e,e}function Do(n,e){let t=Sg(`${n}:trace`);return X.enabled(`${n}:trace`)&&X.names.map(r=>r.toString()).find(r=>r.includes(":trace"))!=null&&(t=X(`${n}:trace`,e)),Object.assign(X(n,e),{error:X(`${n}:error`,e),trace:t,newScope:r=>Do(`${n}:${r}`,e)})}function Qu(n){if(n!=null&&(n=n.trim(),n.length!==0))return n}var Zu=w(()=>{"use strict";Er();Hn();Xi();ju();X.formatters.b=n=>n==null?"undefined":de.baseEncode(n);X.formatters.t=n=>n==null?"undefined":J.baseEncode(n);X.formatters.m=n=>n==null?"undefined":Ji.baseEncode(n);X.formatters.p=n=>n==null?"undefined":n.toString();X.formatters.c=n=>n==null?"undefined":n.toString();X.formatters.k=n=>n==null?"undefined":n.toString();X.formatters.a=n=>n==null?"undefined":n.toString();X.formatters.e=n=>n==null?"undefined":Xu(n)});function xg(n){let[e,t]=n[Symbol.asyncIterator]!=null?[n[Symbol.asyncIterator](),Symbol.asyncIterator]:[n[Symbol.iterator](),Symbol.iterator],r=[];return{peek:()=>e.next(),push:s=>{r.push(s)},next:()=>r.length>0?{done:!1,value:r.shift()}:e.next(),[t](){return this}}}var ed,td=w(()=>{"use strict";ed=xg});function vg(n){return n[Symbol.asyncIterator]!=null}function Ag(n,e){let t=0;if(vg(n))return(async function*(){for await(let a of n)await e(a,t++)&&(yield a)})();let r=ed(n),{value:s,done:i}=r.next();if(i===!0)return(function*(){})();let o=e(s,t++);if(typeof o.then=="function")return(async function*(){await o&&(yield s);for(let a of r)await e(a,t++)&&(yield a)})();let c=e;return(function*(){o===!0&&(yield s);for(let a of r)c(a,t++)&&(yield a)})()}var rd,nd=w(()=>{"use strict";td();rd=Ag});function Qt(){let n={};return n.promise=new Promise((e,t)=>{n.resolve=e,n.reject=t}),n}var sd=w(()=>{"use strict"});async function id(n,e,t){if(e==null)return n;if(e.aborted)return n.catch(()=>{}),Promise.reject(new ps(t?.errorMessage,t?.errorCode,t?.errorName));let r,s=new ps(t?.errorMessage,t?.errorCode,t?.errorName);try{return await Promise.race([n,new Promise((i,o)=>{r=()=>{o(s)},e.addEventListener("abort",r)})])}finally{r!=null&&e.removeEventListener("abort",r)}}var ps,od=w(()=>{"use strict";ps=class extends Error{constructor(t,r,s){super(t??"The operation was aborted");p(this,"type");p(this,"code");this.type="aborted",this.name=s??"AbortError",this.code=r??"ABORT_ERR"}}});function ad(){return new Ro}var Ro,cd=w(()=>{"use strict";sd();od();Ro=class{constructor(){p(this,"readNext");p(this,"haveNext");p(this,"ended");p(this,"nextResult");p(this,"error");this.ended=!1,this.readNext=Qt(),this.haveNext=Qt()}[Symbol.asyncIterator](){return this}async next(){if(this.nextResult==null&&await this.haveNext.promise,this.nextResult==null)throw new Error("HaveNext promise resolved but nextResult was undefined");let e=this.nextResult;return this.nextResult=void 0,this.readNext.resolve(),this.readNext=Qt(),e}async throw(e){return this.ended=!0,this.error=e,e!=null&&(this.haveNext.promise.catch(()=>{}),this.haveNext.reject(e)),{done:!0,value:void 0}}async return(){let e={done:!0,value:void 0};return this.ended=!0,this.nextResult=e,this.haveNext.resolve(),e}async push(e,t){await this._push(e,t)}async end(e,t){e!=null?await this.throw(e):await this._push(void 0,t)}async _push(e,t){if(e!=null&&this.ended)throw this.error??new Error("Cannot push value onto an ended pushable");for(;this.nextResult!=null;)await this.readNext.promise;e!=null?this.nextResult={done:!1,value:e}:(this.ended=!0,this.nextResult={done:!0,value:void 0}),this.haveNext.resolve(),this.haveNext=Qt(),await id(this.readNext.promise,t?.signal,t)}}});function kg(n){return n[Symbol.asyncIterator]!=null}async function Eg(n,e,t){try{await Promise.all(n.map(async r=>{for await(let s of r)await e.push(s,{signal:t}),t.throwIfAborted()})),await e.end(void 0,{signal:t})}catch(r){await e.end(r,{signal:t}).catch(()=>{})}}async function*Cg(n){let e=new AbortController,t=ad();Eg(n,t,e.signal).catch(()=>{});try{yield*t}finally{e.abort()}}function*Pg(n){for(let e of n)yield*e}function Ig(...n){let e=[];for(let t of n)kg(t)||e.push(t);return e.length===n.length?Pg(e):Cg(n)}var ld,ud=w(()=>{"use strict";cd();ld=Ig});var Bg,gs,dd=w(()=>{"use strict";Zu();ls();nd();ud();qr();Bg=Do("blockstore:core:tiered"),gs=class extends Ee{constructor(t){super();p(this,"stores");this.stores=t.slice()}async put(t,r,s){return await Promise.all(this.stores.map(async i=>{await i.put(t,r,s)})),t}async*get(t,r){let s;for(let i of this.stores)try{yield*i.get(t,r);return}catch(o){s=o,Bg.error(o)}throw s??new He}async has(t,r){for(let s of this.stores)if(await s.has(t,r))return!0;return!1}async delete(t,r){await Promise.all(this.stores.map(async s=>{await s.delete(t,r)}))}async*putMany(t,r={}){for await(let s of t)await this.put(s.cid,s.bytes,r),yield s.cid}async*deleteMany(t,r={}){for await(let s of t)await this.delete(s,r),yield s}async*getAll(t){let r=new Set;yield*rd(ld(...this.stores.map(s=>s.getAll(t))),s=>{let i=s.cid.toString();return r.has(i)?!1:(r.add(i),!0)})}}});var hd={};B(hd,{BaseBlockstore:()=>Ee,BlackHoleBlockstore:()=>ds,MemoryBlockstore:()=>us,TieredBlockstore:()=>gs});var fd=w(()=>{"use strict";qr();qu();Hu();dd()});var pd=D((zS,Dg)=>{Dg.exports={name:"w3pk",version:"0.9.1",description:"WebAuthn SDK for passwordless authentication, encrypted wallets, ERC-5564 stealth addresses, and zero-knowledge proofs",author:"Julien B\xE9ranger",license:"GPL-3.0",repository:{type:"git",url:"https://github.com/w3hc/w3pk.git"},bugs:{url:"https://github.com/w3hc/w3pk/issues"},homepage:"https://github.com/w3hc/w3pk#readme",keywords:["webauthn","passkey","authentication","passwordless","fido2","biometric","ethereum","web3","encryption","zero-knowledge","zk-proofs","zk-snarks","privacy","stealth-address","erc-5564","erc-6538","unlinkable","anonymous-transactions","privacy-preserving","ecdh","secp256k1","view-tags","circom","groth16","merkle-tree","commitment-scheme"],main:"./dist/index.js",module:"./dist/index.mjs",types:"./dist/index.d.ts",exports:{".":{types:"./dist/index.d.ts",import:"./dist/index.mjs",require:"./dist/index.js"},"./zk":{types:"./dist/zk/index.d.ts",import:"./dist/zk/index.mjs",require:"./dist/zk/index.js"},"./zk/utils":{types:"./dist/zk/utils.d.ts",import:"./dist/zk/utils.mjs",require:"./dist/zk/utils.js"},"./chainlist":{types:"./dist/chainlist/index.d.ts",import:"./dist/chainlist/index.mjs",require:"./dist/chainlist/index.js"},"./inspect":{types:"./dist/inspect/index.d.ts",import:"./dist/inspect/index.mjs",require:"./dist/inspect/index.js"},"./inspect/node":{types:"./dist/inspect/node.d.ts",import:"./dist/inspect/node.mjs",require:"./dist/inspect/node.js"}},sideEffects:!1,files:["dist","README.md","LICENSE","docs/","scripts/compute-build-hash.mjs"],scripts:{build:"tsup","build:zk":"npm run build && npm run compile:circuits","compile:circuits":"node scripts/compile-circuits.js",dev:"tsup --watch",test:"tsx test/test.ts && tsx test/comprehensive.test.ts && tsx test/backup.test.ts && tsx test/social-recovery.test.ts && tsx test/recovery-education.test.ts && tsx test/zk/zk.test.ts && tsx test/nft-ownership.test.ts && tsx test/chainlist.test.ts && tsx test/eip7702.test.ts && tsx test/external-wallet.test.ts && tsx test/erc5564.test.ts && tsx test/zk/key-stretching.test.ts && tsx test/username-encoding.test.ts && tsx test/username-validation.test.ts && tsx test/origin-derivation.test.ts && tsx test/build-hash.test.ts && tsx test/credential-checking.test.ts && tsx test/webauthn-native.test.ts && tsx test/persistent-session.test.ts && tsx test/sign-message.test.ts && tsx test/siwe.test.ts && tsx test/requirereauth.test.ts && tsx test/eip7951.test.ts && tsx test/send-transaction.test.ts && tsx test/eip1193-provider.test.ts","test:basic":"tsx test/test.ts","test:comprehensive":"tsx test/comprehensive.test.ts","test:backup":"tsx test/backup.test.ts","test:social-recovery":"tsx test/social-recovery.test.ts","test:education":"tsx test/recovery-education.test.ts","test:username":"tsx test/username-encoding.test.ts && tsx test/username-validation.test.ts","test:recovery":"tsx test/backup.test.ts && tsx test/social-recovery.test.ts && tsx test/recovery-education.test.ts","test:zk":"tsx test/zk/zk.test.ts","test:nft":"tsx test/nft-ownership.test.ts","test:chainlist":"tsx test/chainlist.test.ts","test:eip7702":"tsx test/eip7702.test.ts","test:external-wallet":"tsx test/external-wallet.test.ts","test:eip7951":"tsx test/eip7951.test.ts","test:erc5564":"tsx test/erc5564.test.ts","test:sign-message":"tsx test/sign-message.test.ts","test:siwe":"tsx test/siwe.test.ts",prepublishOnly:"pnpm build","build:hash":"node scripts/compute-build-hash.mjs","release:notes":"node scripts/generate-release-notes.mjs",html:"lsof -ti:3000 | xargs kill -9 2>/dev/null || true && tsup && npx serve . -l 3000 & sleep 5 && open http://localhost:3000/standalone/checker.html"},packageManager:"pnpm@10.6.4",devDependencies:{"@types/node":"^24.9.0","@types/qrcode":"^1.5.5",circomlib:"^2.0.5",tsup:"^8.5.1",tsx:"^4.21.0",typescript:"^5.9.3"},peerDependencies:{ethers:"^6.0.0"},optionalDependencies:{"@ipld/car":"^5.4.2","blockstore-core":"^6.1.1",circomlibjs:"^0.1.7","ipfs-unixfs-importer":"^16.0.1",qrcode:"^1.5.4",snarkjs:"^0.7.5"}}});var Ug={};B(Ug,{ApiError:()=>Hr,AuthenticationError:()=>O,CryptoError:()=>N,DEFAULT_MODE:()=>fe,DEFAULT_TAG:()=>pe,RecoverySimulator:()=>kt,RegistrationError:()=>ht,StealthAddressModule:()=>yt,StorageError:()=>R,WalletError:()=>S,Web3Passkey:()=>Et,Web3PasskeyError:()=>$,arrayBufferToBase64Url:()=>Se,assertEthereumAddress:()=>Vr,assertMnemonic:()=>Lo,assertUsername:()=>Gr,authenticateWithPasskey:()=>li,base64ToArrayBuffer:()=>Ss,base64UrlDecode:()=>vs,base64UrlToArrayBuffer:()=>L,canControlStealthAddress:()=>Ho,checkStealthAddress:()=>nr,clearCache:()=>Zo,computeStealthPrivateKey:()=>sr,createSiweMessage:()=>yd,createWalletFromMnemonic:()=>Es,createWeb3Passkey:()=>xd,default:()=>Ng,deriveAddressFromP256PublicKey:()=>Ps,deriveIndexFromOriginModeAndTag:()=>Zr,deriveStealthKeys:()=>mt,deriveWalletFromMnemonic:()=>tr,detectWalletProvider:()=>dn,encodeEIP7702AuthorizationMessage:()=>or,extractRS:()=>Fs,generateBIP39Wallet:()=>er,generateSiweNonce:()=>md,generateStealthAddress:()=>tn,getAllChains:()=>Qo,getAllTopics:()=>hi,getChainById:()=>Xo,getCurrentBuildHash:()=>Mo,getCurrentOrigin:()=>Me,getDefaultProvider:()=>un,getEndpoints:()=>on,getExplainer:()=>di,getOriginSpecificAddress:()=>Fe,getPackageVersion:()=>Fo,getW3pkBuildHash:()=>To,hashEIP7702AuthorizationMessage:()=>ar,inspect:()=>No,inspectNow:()=>Sd,isStrongPassword:()=>_o,normalizeOrigin:()=>rr,parseSiweMessage:()=>ms,promptPasskeySelection:()=>ci,requestExternalWalletAuthorization:()=>ln,safeAtob:()=>Ve,safeBtoa:()=>xs,searchExplainers:()=>fi,supportsEIP7702Authorization:()=>hn,validateEthereumAddress:()=>ys,validateMnemonic:()=>bs,validateSiweMessage:()=>wd,validateUsername:()=>ws,verifyBuildHash:()=>gd,verifyEIP7702Authorization:()=>an,verifySiweSignature:()=>bd});module.exports=Bd(Ug);Y();function ys(n){return/^0x[a-fA-F0-9]{40}$/.test(n)}function ws(n){return n.length<3||n.length>50?!1:/^[a-zA-Z0-9]([a-zA-Z0-9_-]*[a-zA-Z0-9])?$/.test(n)}function bs(n){let e=n.trim().split(/\s+/);return e.length===12||e.length===24}function Vr(n){if(!ys(n))throw new Error("Invalid Ethereum address format")}function Gr(n){if(!ws(n))throw new Error("Username must be 3-50 characters long and contain only letters, numbers, underscores, and hyphens. Must start and end with a letter or number.")}function Lo(n){if(!bs(n))throw new Error("Invalid mnemonic: must be 12 or 24 words")}function _o(n){if(n.length<12)return!1;let e=/[A-Z]/.test(n),t=/[a-z]/.test(n),r=/[0-9]/.test(n),s=/[!@#$%^&*()_+\-=\[\]{};':"\\|,.<>\/?]/.test(n);return!(!e||!t||!r||!s||["password","12345678","qwerty","abc123","password123","admin","letmein"].some(o=>n.toLowerCase().includes(o)))}Te();xe();q();async function Rd(n){try{let e=new Uint8Array(n),t=Td(e);if(t===-1)return null;let r=e.slice(t);if(!((r[32]&64)!==0))return null;let o=37;o+=16;let c=r[o]<<8|r[o+1];o+=2,o+=c;let a=r.slice(o),u=await Fd(a);return Se(u)}catch(e){return console.error("Failed to extract public key:",e),null}}function Td(n){let e=new Uint8Array([104,97,117,116,104,68,97,116,97]);for(let t=0;t<n.length-e.length;t++){let r=!0;for(let s=0;s<e.length;s++)if(n[t+s]!==e[s]){r=!1;break}if(r){let s=n[t+e.length],i=t+e.length+1;if(s>=88&&s<=91){let o=s-87;i+=o}return i}}return-1}async function Fd(n){let e=Ko(n,-2),t=Ko(n,-3);if(!e||!t)throw new Error("Failed to extract EC coordinates from COSE key");let r=new Uint8Array(65);r[0]=4,r.set(e,1),r.set(t,33);let s=new Uint8Array([48,89,48,19,6,7,42,134,72,206,61,2,1,6,8,42,134,72,206,61,3,1,7,3,66,0]),i=new Uint8Array(s.length+r.length);return i.set(s,0),i.set(r,s.length),i.buffer}function Ko(n,e){let t=e<0?32+(-1-e):e;for(let r=0;r<n.length-33;r++)if(n[r]===t&&(n[r+1]===88&&n[r+2]===32||n[r+1]===88&&n[r+2]===32))return n.slice(r+3,r+35);return null}async function zo(n){try{let{username:e,ethereumAddress:t}=n;Gr(e),Vr(t);let r=new F;if(await r.userExists(e))throw new Error("Username already registered");let s=De(),o=new TextEncoder().encode(e),c=Se(o),a=L(s),u=L(c),l={challenge:a,rp:{name:"w3pk",id:window.location.hostname},user:{id:u,name:e,displayName:e},pubKeyCredParams:[{type:"public-key",alg:-7},{type:"public-key",alg:-257}],authenticatorSelection:{authenticatorAttachment:"platform",userVerification:"required",residentKey:"required",requireResidentKey:!0},timeout:6e4,attestation:"none"},h=await navigator.credentials.create({publicKey:l});if(!h)throw new Error("Failed to create credential");let g=await Rd(h.response.attestationObject);if(!g)throw new Error("Public key not returned from authenticator");return await r.saveCredential({id:h.id,publicKey:g,username:e,ethereumAddress:t,createdAt:new Date().toISOString(),lastUsed:new Date().toISOString(),signCount:0}),{signature:h.response.attestationObject}}catch(e){throw new ht(e instanceof Error?e.message:"Registration failed",e)}}Y();Te();xe();q();async function Qr(){try{let n=new F,e=De(),t=[];try{let a=await n.getAllCredentials();a.length>0&&(t=a.map(u=>({id:u.id,type:"public-key",transports:["internal","hybrid","usb","nfc","ble"]})))}catch{}let s={challenge:L(e),rpId:window.location.hostname,userVerification:"required",timeout:6e4};t.length>0&&(s.allowCredentials=t.map(a=>({id:L(a.id),type:a.type,transports:a.transports})));let i;try{let a=await navigator.credentials.get({publicKey:s});if(!a)throw new Error("Authentication failed - no credential returned");i=a}catch(a){throw a?.name==="NotAllowedError"||a?.message?.toLowerCase().includes("no credentials available")||a?.message?.toLowerCase().includes("no access key")?(await n.getAllCredentials()).length>0?new O("Your passkey is not available on this device. You may need to restore your wallet from a backup, or login on the device where you registered."):new O("No passkey found. Please register first or restore from a backup."):a}let o=await n.getCredentialById(i.id);if(!o)throw new O("Passkey authenticated but wallet data not found on this device. To sync your account: 1) Select your passkey when prompted, then 2) Provide your backup file. This allows you to use the same passkey on multiple devices.");if(!await Md(i,o,n))throw new Error("Signature verification failed");return{verified:!0,user:{username:o.username,ethereumAddress:o.ethereumAddress,credentialId:o.id},signature:i.response.signature}}catch(n){throw new O(n instanceof Error?n.message:"Authentication failed",n)}}async function Md(n,e,t){try{let r=n.response.authenticatorData,s=new DataView(r),o=new Uint8Array(r).slice(0,32),c=window.location.hostname,a=new Uint8Array(await crypto.subtle.digest("SHA-256",new TextEncoder().encode(c)));if(!Nd(o,a))return console.error("RP ID hash mismatch - possible phishing attack"),!1;let u=s.getUint32(33,!1);if(u>0||e.signCount&&e.signCount>0){let b=e.signCount||0;if(u<=b)return console.error(`Authenticator cloning detected! Counter did not increase: stored=${b}, received=${u}`),!1}let l=L(e.publicKey),h=await crypto.subtle.importKey("spki",l,{name:"ECDSA",namedCurve:"P-256"},!1,["verify"]),g=n.response.clientDataJSON,d=await crypto.subtle.digest("SHA-256",g),f=new Uint8Array(r.byteLength+d.byteLength);f.set(new Uint8Array(r),0),f.set(new Uint8Array(d),r.byteLength);let y=n.response.signature,k=Ud(new Uint8Array(y));return await crypto.subtle.verify({name:"ECDSA",hash:"SHA-256"},h,k,f)?(await t.updateSignatureCounter(e.id,u),!0):!1}catch(r){return console.error("Signature verification error:",r),!1}}function Nd(n,e){if(n.length!==e.length)return!1;for(let t=0;t<n.length;t++)if(n[t]!==e[t])return!1;return!0}function Ud(n){let e=2;e++;let t=n[e++];t>32&&(e++,t--);let r=n.slice(e,e+t);e+=t,e++;let s=n[e++];s>32&&(e++,s--);let i=n.slice(e,e+s),o=new Uint8Array(64);return o.set(r,32-r.length),o.set(i,64-i.length),o.buffer}Y();var Ld="Web3PasskeyWallet",_d=1,ve="wallets",Xr=class{constructor(){this.db=null}async init(){return new Promise((e,t)=>{let r=indexedDB.open(Ld,_d);r.onerror=()=>t(new R("Failed to open database",r.error)),r.onsuccess=()=>{this.db=r.result,e()},r.onupgradeneeded=()=>{let s=r.result;s.objectStoreNames.contains(ve)||s.createObjectStore(ve,{keyPath:"ethereumAddress"})}})}async store(e){return this.db||await this.init(),new Promise((t,r)=>{let o=this.db.transaction([ve],"readwrite").objectStore(ve).put(e);o.onerror=()=>r(new R("Failed to store wallet data",o.error)),o.onsuccess=()=>t()})}async retrieve(e){return this.db||await this.init(),new Promise((t,r)=>{let o=this.db.transaction([ve],"readonly").objectStore(ve).get(e);o.onerror=()=>r(new R("Failed to retrieve wallet data",o.error)),o.onsuccess=()=>t(o.result||null)})}async delete(e){return this.db||await this.init(),new Promise((t,r)=>{let o=this.db.transaction([ve],"readwrite").objectStore(ve).delete(e);o.onerror=()=>r(new R("Failed to delete wallet data",o.error)),o.onsuccess=()=>t()})}async clear(){return this.db||await this.init(),new Promise((e,t)=>{let i=this.db.transaction([ve],"readwrite").objectStore(ve).clear();i.onerror=()=>t(new R("Failed to clear wallet data",i.error)),i.onsuccess=()=>e()})}};pt();gt();q();Y();var H=require("ethers");Y();function mt(n){try{let e=H.ethers.HDNodeWallet.fromPhrase(n,void 0,"m/44'/60'/1'/0/0"),t=H.ethers.HDNodeWallet.fromPhrase(n,void 0,"m/44'/60'/1'/0/1"),r=t.signingKey.compressedPublicKey,s=e.signingKey.compressedPublicKey;return{stealthMetaAddress:r+s.slice(2),spendingPubKey:r,viewingPubKey:s,viewingKey:e.privateKey,spendingKey:t.privateKey}}catch(e){throw new N("Failed to derive stealth keys",e)}}function tn(n){try{let e="0x"+n.slice(2,68),t="0x"+n.slice(68),r=H.ethers.Wallet.createRandom(),s=r.signingKey.compressedPublicKey,i=Is(r.privateKey,t),o=H.ethers.keccak256(i),c="0x"+o.slice(2,4),a=Go(e,Vo(o));return{stealthAddress:Yo(a),ephemeralPubKey:s,viewTag:c}}catch(e){throw new N("Failed to generate stealth address",e)}}function nr(n,e,t,r,s){try{let i=Is(n,t),o=H.ethers.keccak256(i);if(s&&("0x"+o.slice(2,4)).toLowerCase()!==s.toLowerCase())return{isForUser:!1};let c=Go(e,Vo(o)),a=Yo(c);return a.toLowerCase()!==r.toLowerCase()?{isForUser:!1}:{isForUser:!0,stealthAddress:a}}catch{return{isForUser:!1}}}function sr(n,e,t){try{let r=Is(n,t),s=H.ethers.keccak256(r);return Kd(e,s)}catch(r){throw new N("Failed to compute stealth private key",r)}}function Ho(n,e,t,r,s,i){try{if(!nr(n,t,r,s,i).isForUser)return!1;let c=sr(n,e,r);return new H.ethers.Wallet(c).address.toLowerCase()===s.toLowerCase()}catch{return!1}}function Is(n,e){try{return new H.ethers.Wallet(n).signingKey.computeSharedSecret(e)}catch(t){throw new N("Failed to compute shared secret",t)}}function Vo(n){try{return new H.ethers.Wallet(n).signingKey.compressedPublicKey}catch(e){throw new N("Failed to multiply generator by scalar",e)}}function Go(n,e){try{let t=H.ethers.SigningKey.computePublicKey(n,!1),r=H.ethers.SigningKey.computePublicKey(e,!1),s=BigInt("0x"+t.slice(4,68)),i=BigInt("0x"+t.slice(68)),o=BigInt("0x"+r.slice(4,68)),c=BigInt("0x"+r.slice(68)),a=BigInt("0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEFFFFFC2F");if(s===o&&i===c){let f=3n*s*s%a,y=2n*i%a,k=f*qo(y,a)%a,m=(k*k-2n*s)%a,b=(k*(s-m)-i)%a;return $o((m+a)%a,(b+a)%a)}let u=((c-i)%a+a)%a,l=((o-s)%a+a)%a,h=u*qo(l,a)%a,g=(h*h-s-o)%a,d=(h*(s-g)-i)%a;return $o((g+a)%a,(d+a)%a)}catch(t){throw new N("Failed to add public keys",t)}}function Kd(n,e){try{let t=BigInt("0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEBAAEDCE6AF48A03BBFD25E8CD0364141"),r=BigInt(n),s=BigInt(e);return"0x"+((r+s)%t).toString(16).padStart(64,"0")}catch(t){throw new N("Failed to add private keys",t)}}function $o(n,e){return"0x"+(e%2n===0n?"02":"03")+n.toString(16).padStart(64,"0")}function qo(n,e){n=(n%e+e)%e;let[t,r]=[n,e],[s,i]=[1n,0n];for(;r!==0n;){let o=t/r;[t,r]=[r,t-o*r],[s,i]=[i,s-o*i]}return(s%e+e)%e}function Yo(n){try{let e=H.ethers.SigningKey.computePublicKey(n,!1),t=H.ethers.keccak256("0x"+e.slice(4));return H.ethers.getAddress("0x"+t.slice(-40))}catch(e){throw new N("Failed to derive address from public key",e)}}var yt=class{constructor(e,t){this.getMnemonic=t}async generateStealthAddress(e){try{let t=await this.getMnemonic(e?.requireAuth),r=mt(t),s=tn(r.stealthMetaAddress);return{stealthAddress:s.stealthAddress,ephemeralPublicKey:s.ephemeralPubKey,viewTag:s.viewTag}}catch(t){throw new $("Failed to generate stealth address","STEALTH_GENERATION_ERROR",t)}}async parseAnnouncement(e,t){try{let r=await this.getMnemonic(t?.requireAuth),s=mt(r),i=nr(s.viewingKey,s.spendingPubKey,e.ephemeralPublicKey,e.stealthAddress,e.viewTag);if(!i.isForUser)return{isForUser:!1};let o=sr(s.viewingKey,s.spendingKey,e.ephemeralPublicKey);return{isForUser:!0,stealthAddress:i.stealthAddress,stealthPrivateKey:o}}catch(r){throw new $("Failed to parse announcement","ANNOUNCEMENT_PARSE_ERROR",r)}}async scanAnnouncements(e,t){let r=[];for(let s of e){let i=await this.parseAnnouncement(s,t);i.isForUser&&r.push(i)}return r}async getKeys(e){try{let t=await this.getMnemonic(e?.requireAuth);return mt(t)}catch(t){throw new $("Failed to get stealth keys","STEALTH_KEYS_ERROR",t)}}async getStealthMetaAddress(e){try{return(await this.getKeys(e)).stealthMetaAddress}catch(t){throw new $("Failed to get stealth meta-address","STEALTH_META_ADDRESS_ERROR",t)}}get isAvailable(){return!0}};Y();q();var zd="Web3PasskeyPersistentSessions",Wd=2,ae="sessions",rn=class{constructor(){this.db=null;this.initPromise=null}async init(){return this.initPromise?this.initPromise:this.db?Promise.resolve():(this.initPromise=new Promise((e,t)=>{let r=indexedDB.open(zd,Wd);r.onupgradeneeded=s=>{let i=s.target.result;i.objectStoreNames.contains(ae)||i.createObjectStore(ae,{keyPath:"ethereumAddress"}).createIndex("expiresAt","expiresAt",{unique:!1})},r.onsuccess=()=>{this.db=r.result,this.initPromise=null,e()},r.onerror=()=>{this.initPromise=null,t(new R("Failed to open persistent session database",r.error))}}),this.initPromise)}async store(e){if(e.securityMode==="STRICT")throw new R("Cannot persist STRICT mode sessions");return this.db||await this.init(),new Promise((t,r)=>{let o=this.db.transaction([ae],"readwrite").objectStore(ae).put(e);o.onerror=()=>r(new R("Failed to store persistent session",o.error)),o.onsuccess=()=>t()})}async retrieve(e){return this.db||await this.init(),new Promise((t,r)=>{let o=this.db.transaction([ae],"readonly").objectStore(ae).get(e);o.onerror=()=>r(new R("Failed to retrieve persistent session",o.error)),o.onsuccess=()=>{let c=o.result||null;if(c&&Date.now()>c.expiresAt){this.delete(e).catch(console.error),t(null);return}t(c)}})}async delete(e){return this.db||await this.init(),new Promise((t,r)=>{let o=this.db.transaction([ae],"readwrite").objectStore(ae).delete(e);o.onerror=()=>r(new R("Failed to delete persistent session",o.error)),o.onsuccess=()=>t()})}async clear(){return this.db||await this.init(),new Promise((e,t)=>{let i=this.db.transaction([ae],"readwrite").objectStore(ae).clear();i.onerror=()=>t(new R("Failed to clear persistent sessions",i.error)),i.onsuccess=()=>e()})}async cleanupExpired(){return this.db||await this.init(),new Promise((e,t)=>{let i=this.db.transaction([ae],"readwrite").objectStore(ae).index("expiresAt"),o=Date.now(),c=IDBKeyRange.upperBound(o),a=i.openCursor(c);a.onsuccess=u=>{let l=u.target.result;l?(l.delete(),l.continue()):e()},a.onerror=()=>t(new R("Failed to cleanup expired sessions",a.error))})}};async function jo(n,e,t){try{let r=await j(e,t);return await ie(n,r)}catch(r){throw new N("Failed to encrypt mnemonic for persistence",r)}}async function Bs(n,e,t){try{let r=await j(e,t);return await oe(n,r)}catch(r){throw new N("Failed to decrypt mnemonic from persistence",r)}}var nn=class{constructor(e=1,t){this.session=null;this.sessionDuration=e*60*60*1e3,this.persistentConfig={enabled:t?.enabled??!1,duration:t?.duration??168,requireReauth:t?.requireReauth??!0},this.persistentStorage=new rn}async startSession(e,t,r,s,i){let o=new Date(Date.now()+this.sessionDuration).toISOString();if(this.session={mnemonic:e,expiresAt:o,credentialId:t},this.persistentConfig.enabled&&i!=="STRICT"&&r&&s)try{let c=await jo(e,t,s),a=Date.now()+this.persistentConfig.duration*60*60*1e3;await this.persistentStorage.store({encryptedMnemonic:c,expiresAt:a,credentialId:t,ethereumAddress:r,securityMode:i||"STANDARD",createdAt:Date.now()})}catch(c){console.warn("[w3pk] Failed to persist session:",c)}}getMnemonic(){return this.session?new Date>new Date(this.session.expiresAt)?(this.clearSession(),null):this.session.mnemonic:null}getCredentialId(){return this.session?new Date>new Date(this.session.expiresAt)?(this.clearSession(),null):this.session.credentialId:null}isActive(){return this.getMnemonic()!==null}getRemainingTime(){return this.session?new Date>new Date(this.session.expiresAt)?(this.clearSession(),0):Math.floor((new Date(this.session.expiresAt).getTime()-Date.now())/1e3):0}extendSession(){if(!this.session)throw new Error("No active session to extend");if(new Date>new Date(this.session.expiresAt))throw this.clearSession(),new Error("Session expired, cannot extend");this.session.expiresAt=new Date(Date.now()+this.sessionDuration).toISOString()}async restoreFromPersistentStorage(e,t,r){if(!this.persistentConfig.enabled)return null;try{let s=await this.persistentStorage.retrieve(e);if(!s)return null;if(s.credentialId!==t)return console.warn("[w3pk] Credential ID mismatch, clearing persistent session"),await this.persistentStorage.delete(e),null;let i=await Bs(s.encryptedMnemonic,t,r),o=new Date(Date.now()+this.sessionDuration).toISOString();return this.session={mnemonic:i,expiresAt:o,credentialId:t},i}catch(s){console.warn("[w3pk] Failed to restore persistent session:",s);try{await this.persistentStorage.delete(e)}catch{}return null}}async attemptSilentRestore(){if(!this.persistentConfig.enabled||this.persistentConfig.requireReauth)return null;try{let{CredentialStorage:e}=await Promise.resolve().then(()=>(Te(),Jr)),r=await new e().getAllCredentials();if(r.length===0)return null;for(let s of r){let i=await this.persistentStorage.retrieve(s.ethereumAddress);if(!i)continue;if(i.credentialId!==s.id){console.warn("[w3pk] Credential ID mismatch, skipping this session");continue}let o=await Bs(i.encryptedMnemonic,s.id,s.publicKey),c=new Date(Date.now()+this.sessionDuration).toISOString();return this.session={mnemonic:o,expiresAt:c,credentialId:s.id},{mnemonic:o,ethereumAddress:s.ethereumAddress,credentialId:s.id,publicKey:s.publicKey}}return null}catch(e){return console.warn("[w3pk] Failed to attempt silent restore:",e),null}}async clearSession(){if(this.session&&(this.session.mnemonic="0".repeat(this.session.mnemonic.length)),this.session=null,this.persistentConfig.enabled)try{await this.persistentStorage.clear()}catch(e){console.warn("[w3pk] Failed to clear persistent sessions:",e)}}setSessionDuration(e){this.sessionDuration=e*60*60*1e3}};Te();var sn={debug:!1,sessionDuration:1,persistentSession:{enabled:!1,duration:168,requireReauth:!0},onError:n=>{sn.debug&&console.error("[w3pk]",n)}};Y();var Jo="https://chainid.network/chains.json";var ir=null,$d=[/\$\{[\w_]+\}/i,/\{[\w_]+\}/i,/<[\w_]+>/i,/YOUR[-_]?API[-_]?KEY/i,/INSERT[-_]?API[-_]?KEY/i,/API[-_]?KEY[-_]?HERE/i];function qd(n){return $d.some(e=>e.test(n))}async function Hd(n=Jo){let e=await fetch(n);if(!e.ok)throw new Error(`Failed to fetch chains data: ${e.status} ${e.statusText}`);return await e.json()}async function Ds(n){let e=n?.chainsJsonUrl??Jo,t=n?.cacheDuration??36e5,r=Date.now();if(ir&&r-ir.timestamp<t)return ir.data;let s=await Hd(e);return ir={data:s,timestamp:r},s}async function on(n,e){let r=(await Ds(e)).find(s=>s.chainId===n);return r?r.rpc.filter(s=>!qd(s)&&!s.startsWith("wss://")&&!s.startsWith("ws://")):[]}async function Qo(n){return Ds(n)}async function Xo(n,e){return(await Ds(e)).find(r=>r.chainId===n)}function Zo(){ir=null}Ts();cn();var Vd=new Set([1,10,8453,42161,57073,100,42220,137,42,15,40,41,44,46,47,50,51,56,61,71,82,83,95,97,112,123,130,146,151,153,171,180,183,185,195,215,228,247,248,252,261,267,291,293,311,332,336,395,401,416,466,480,488,510,545,634,647,648,747,831,919,938,945,957,964,970,980,995,997,1001,1003,1024,1030,1114,1125,1135,1149,1188,1284,1285,1287,1300,1301,1315,1337,1338,1339,1424,1514,1687,1727,1729,1740,1750,1829,1868,1946,1961,1962,1969,1989,1995,2017,2020,2031,2043,2109,2241,2340,2345,2440,2522,2559,2649,3068,3109,3338,3502,3799,3888,3889,4e3,4048,4078,4162,4201,4202,4460,4488,4661,4689,4690,4888,5e3,5003,5124,5234,5330,5424,5522,6283,6342,6398,6678,6806,6934,6942,6969,7117,7171,7200,7208,7368,7518,7668,7672,7744,7771,7869,7897,8008,8118,8217,8408,8700,8726,8727,8844,8880,8881,8882,8889,9372,9496,9700,9745,9746,9899,9990,9996,10011,10085,10143,10200,11221,11501,11504,11891,13370,14853,16602,16661,17e3,18880,18881,19991,21e3,21816,21912,25327,32323,33401,34443,41923,42170,43111,44787,47805,48898,48900,49049,49088,5e4,50312,53302,53456,53457,55244,56288,59141,60808,60850,62320,62850,64002,71402,72080,73114,73115,75338,78281,80002,80008,80069,80094,80451,80931,84532,88899,91342,92278,94524,96970,97476,97477,98985,100021,100501,101010,102030,102031,102032,112358,120893,121212,121213,121214,121215,129399,161803,175188,192940,193939,198989,212013,222222,240241,325e3,355110,355113,421614,555777,560048,656476,713715,743111,747474,763373,763375,777777,806582,808813,810180,839999,888991,2019775,2222222,4278608,5734951,6666689,6985385,7080969,7777777,9999999,11142220,11155111,11155420,11155931,16969696,19850818,20180427,20250825,28122024,34949059,37084624,52164803,61022448,79479957,96969696,420420421,420420422,888888888,974399131,999999999,1020352220,1273227453,1313161560,1350216234,1380996178,1417429182,1444673419,1482601649,1564830818,2046399126,11297108099,11297108109,88153591557,123420000220,123420001114]);async function Gd(n,e=1e4){try{let t=new AbortController,r=setTimeout(()=>t.abort(),e),s=await fetch(n,{method:"POST",headers:{"Content-Type":"application/json"},signal:t.signal,body:JSON.stringify({jsonrpc:"2.0",method:"eth_estimateGas",params:[{from:"0xdeadbeef00000000000000000000000000000000",to:"0xdeadbeef00000000000000000000000000000000",data:"0x0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000",value:"0x0"},"latest",{"0xdeadbeef00000000000000000000000000000000":{code:"0xef01000000000000000000000000000000000000000001"}}],id:1})});if(clearTimeout(r),!s.ok)return!1;let i=await s.json();if(i.error){let o=(i.error.message||"").toLowerCase();return!["unsupported","not supported","unknown","invalid","unrecognized","does not support","not implemented"].some(a=>o.includes(a))}return i.result!==void 0}catch{return!1}}async function ta(n,e,t){if(Vd.has(n))return!0;let r=t?.maxEndpoints||3,s=t?.timeout||1e4;try{let i=await e(n);if(i.length===0)return!1;let o=i.slice(0,r);for(let c of o)if(await Gd(c,s))return!0;return!1}catch{return!1}}function wc(n){return typeof n=="string"&&/^0x[0-9a-fA-F]*$/.test(n)}function bc(n){let e=n.startsWith("0x")?n.slice(2):n,t=new Uint8Array(e.match(/.{1,2}/g).map(r=>parseInt(r,16)));return new TextDecoder().decode(t)}var Et=class{constructor(e={}){this.currentUser=null;this.currentWallet=null;this.config={...sn,...e},this.walletStorage=new Xr;let t={...sn.persistentSession,...e.persistentSession};this.sessionManager=new nn(e.sessionDuration||1,t),e.stealthAddresses!==void 0&&(this.stealth=new yt(e.stealthAddresses,r=>this.getMnemonicFromSession(r)))}async loadZKModule(){if(this.zkModule)return this.zkModule;try{let e=new Function("path","return import(path)"),{ZKProofModule:t}=await e("w3pk/zk"),r=this.config.zkProofs||{};return this.zkModule=new t(r),this.zkModule}catch{throw new Error("ZK module not available. Install dependencies: npm install snarkjs circomlibjs")}}async getMnemonicFromSession(e=!1,t="STANDARD"){let r=t;if(!e){let h=this.sessionManager.getMnemonic();if(h)return h}if(!this.currentUser)throw new S("Must be authenticated. Call login() first.");let s=await this.walletStorage.retrieve(this.currentUser.ethereumAddress);if(!s)throw new S("No wallet found. Generate a wallet first.");if(!(await Qr()).user)throw new S("Authentication failed");let a=(await new F().getCredentialById(s.credentialId))?.publicKey,u=await j(s.credentialId,a),l=await oe(s.encryptedMnemonic,u);return await this.sessionManager.startSession(l,s.credentialId,this.currentUser.ethereumAddress,a,r),l}async register(e){try{this.currentWallet?.address||await this.generateWallet();let t=this.currentWallet.address,r=this.currentWallet.mnemonic;await zo({username:e.username,ethereumAddress:t});let i=await new F().getCredentialByAddress(t);if(this.currentUser={username:e.username,ethereumAddress:t,credentialId:i?.id||""},!i)throw new S("Credential not found after registration");let o=i.id,c=i.publicKey,a=await j(o,c),u=await ie(r,a);return await this.walletStorage.store({ethereumAddress:this.currentUser.ethereumAddress,encryptedMnemonic:u,credentialId:o,createdAt:new Date().toISOString()}),await this.sessionManager.startSession(r,o,t,c,"STANDARD"),this.currentWallet={address:t,mnemonic:r},this.config.onAuthStateChanged?.(!0,this.currentUser),{address:t,username:e.username}}catch(t){throw this.config.onError?.(t),t}}async login(){try{let e=await this.sessionManager.attemptSilentRestore();if(e){let l=await new F().getCredentialById(e.credentialId);return this.currentUser={username:l?.username||e.ethereumAddress,ethereumAddress:e.ethereumAddress,credentialId:e.credentialId},await this.walletStorage.retrieve(this.currentUser.ethereumAddress)?(this.config.onAuthStateChanged?.(!0,this.currentUser),this.currentUser):(await this.sessionManager.clearSession(),this.login())}let t=await Qr();if(!t.verified||!t.user)throw new O("Login failed");this.currentUser={username:t.user.username,ethereumAddress:t.user.ethereumAddress,credentialId:t.user.credentialId};let r=await this.walletStorage.retrieve(this.currentUser.ethereumAddress);if(!r)return this.config.onAuthStateChanged?.(!0,this.currentUser),this.currentUser;let o=(await new F().getCredentialById(r.credentialId))?.publicKey,c=await this.sessionManager.restoreFromPersistentStorage(this.currentUser.ethereumAddress,r.credentialId,o||""),a;if(c)a=c;else{let u=await j(r.credentialId,o);a=await oe(r.encryptedMnemonic,u),await this.sessionManager.startSession(a,r.credentialId,this.currentUser.ethereumAddress,o,"STANDARD")}return this.config.onAuthStateChanged?.(!0,this.currentUser),this.currentUser}catch(e){throw this.config.onError?.(e),e}}async logout(){this.currentUser=null,this.currentWallet=null,await this.sessionManager.clearSession(),this.config.onAuthStateChanged?.(!1,void 0)}get isAuthenticated(){return this.currentUser!==null}get user(){return this.currentUser}async listExistingCredentials(){try{return(await new F().getAllCredentials()).map(r=>({username:r.username,ethereumAddress:r.ethereumAddress,createdAt:r.createdAt,lastUsed:r.lastUsed}))}catch{return[]}}async hasExistingCredential(){return(await this.listExistingCredentials()).length>0}async getExistingCredentialCount(){return(await this.listExistingCredentials()).length}async generateWallet(){try{let e=er();return this.currentWallet={address:e.address,mnemonic:e.mnemonic},{address:e.address,mnemonic:e.mnemonic}}catch(e){throw this.config.onError?.(e),new S("Failed to generate wallet",e)}}async deriveWallet(e,t,r){try{if(!this.currentUser)throw new S("Must be authenticated to derive wallet");let s=e||fe,i=t||pe,o=r?.origin||Me();if(s==="PRIMARY"){let{CredentialStorage:l}=await Promise.resolve().then(()=>(Te(),Jr)),{deriveAddressFromP256PublicKey:h}=await Promise.resolve().then(()=>(gt(),en)),d=await new l().getCredentialById(this.currentUser.credentialId);if(!d||!d.publicKey)throw new S("No WebAuthn credential found for PRIMARY mode");return{address:await h(d.publicKey),origin:o,mode:s,tag:i,publicKey:d.publicKey}}let c=s==="STRICT"?!0:r?.requireAuth||!1,a=await this.getMnemonicFromSession(c,s),u=await Fe(a,o,s,i);return{address:u.address,privateKey:u.privateKey,index:u.index,origin:u.origin,mode:u.mode,tag:u.tag}}catch(s){throw this.config.onError?.(s),new S("Failed to derive wallet",s)}}async getAddress(e,t,r){try{if(!this.currentUser)throw new S("Must be authenticated to get address");let s=e||fe,i=t||pe,o=r?.origin||Me();if(s==="PRIMARY"){let{deriveAddressFromP256PublicKey:l}=await Promise.resolve().then(()=>(gt(),en)),g=await new F().getCredentialById(this.currentUser.credentialId);if(!g||!g.publicKey)throw new S("No WebAuthn credential found for PRIMARY mode");return await l(g.publicKey)}let c=s==="STRICT",a=await this.getMnemonicFromSession(c,s);return(await Fe(a,o,s,i)).address}catch(s){throw this.config.onError?.(s),new S("Failed to get address",s)}}async importMnemonic(e){try{if(!this.currentUser)throw new S("Must be authenticated to import mnemonic");if(!e||e.trim().split(/\s+/).length<12)throw new S("Invalid mnemonic: must be at least 12 words");let t=await Qr();if(!t.user)throw new S("Authentication failed");let r=t.user.credentialId,o=(await new F().getCredentialById(r))?.publicKey,c=await j(r,o),a=await ie(e.trim(),c);await this.walletStorage.store({ethereumAddress:this.currentUser.ethereumAddress,encryptedMnemonic:a,credentialId:r,createdAt:new Date().toISOString()}),this.currentWallet={address:this.currentUser.ethereumAddress,mnemonic:e.trim()},await this.sessionManager.startSession(e.trim(),r,this.currentUser.ethereumAddress,o,"STANDARD")}catch(t){throw this.config.onError?.(t),new S("Failed to import mnemonic",t)}}async signMessage(e,t){try{if(!this.currentUser)throw new S("Must be authenticated to sign message");let r=t?.mode||fe,s=t?.tag||pe,i=t?.origin||Me(),o=t?.signingMethod||"EIP191",c=r==="STRICT"?!0:t?.requireAuth||!1,a=await this.getMnemonicFromSession(c,r),u=await Fe(a,i,r,s),{Wallet:l}=await import("ethers"),h;if(u.privateKey)h=new l(u.privateKey);else{let{deriveWalletFromMnemonic:d}=await Promise.resolve().then(()=>(pt(),Cs)),{privateKey:f}=d(a,u.index);h=new l(f)}let g;switch(o){case"EIP191":case"SIWE":g=await h.signMessage(e);break;case"EIP712":if(!t?.eip712Domain||!t?.eip712Types||!t?.eip712PrimaryType)throw new S("EIP712 signing requires eip712Domain, eip712Types, and eip712PrimaryType in options");let d;try{d=typeof e=="string"?JSON.parse(e):e}catch{throw new S("EIP712 message must be valid JSON or an object")}g=await h.signTypedData(t.eip712Domain,t.eip712Types,d);break;case"rawHash":let{SigningKey:f}=await import("ethers"),y=e;if(y.startsWith("0x")&&(y=y.slice(2)),y.length!==64)throw new S("rawHash signing method requires a 32-byte hash (64 hex characters)");g=new f(h.privateKey).sign("0x"+y).serialized;break;default:throw new S(`Unsupported signing method: ${o}`)}return{signature:g,address:u.address,mode:u.mode,tag:u.tag,origin:u.origin}}catch(r){throw this.config.onError?.(r),new S("Failed to sign message",r)}}async signMessageWithPasskey(e){try{if(!this.currentUser)throw new S("Must be authenticated to sign message");let{extractRS:t}=await Promise.resolve().then(()=>(Ms(),ra)),{base64UrlDecode:r}=await Promise.resolve().then(()=>(xe(),As)),s=await crypto.subtle.digest("SHA-256",new TextEncoder().encode(e)),i="0x"+Buffer.from(s).toString("hex"),o=new Uint8Array(Buffer.from(i.slice(2),"hex")),c=this.currentUser.credentialId;if(!c)throw new S("Credential ID not found in user object");let a={challenge:o,rpId:window.location.hostname,allowCredentials:[{id:r(c),type:"public-key",transports:["internal","hybrid","usb","nfc","ble"]}],userVerification:"required",timeout:6e4},u=await navigator.credentials.get({publicKey:a});if(!u||!u.response)throw new S("WebAuthn signature failed");let l=u.response,h=new Uint8Array(l.authenticatorData),g=new Uint8Array(l.clientDataJSON),d=await crypto.subtle.digest("SHA-256",g),f=new Uint8Array(h.length+d.byteLength);f.set(h,0),f.set(new Uint8Array(d),h.length);let y=await crypto.subtle.digest("SHA-256",f.buffer),k="0x"+Buffer.from(y).toString("hex"),m=new Uint8Array(l.signature),{r:b,s:v}=t(m),{CredentialStorage:A}=await Promise.resolve().then(()=>(Te(),Jr)),C=await new A().getCredentialById(c);if(!C||!C.publicKey)throw new S("No WebAuthn credential found for PRIMARY mode");let{base64UrlToArrayBuffer:x}=await Promise.resolve().then(()=>(xe(),As)),P=x(C.publicKey),G=await crypto.subtle.importKey("spki",P,{name:"ECDSA",namedCurve:"P-256"},!0,["verify"]),he=await crypto.subtle.exportKey("jwk",G);if(!he.x||!he.y)throw new S("Invalid P-256 public key: missing x or y coordinates");let ut="0x"+Buffer.from(x(he.x)).toString("hex"),dt="0x"+Buffer.from(x(he.y)).toString("hex"),{deriveAddressFromP256PublicKey:I}=await Promise.resolve().then(()=>(gt(),en)),vd=await I(C.publicKey);return{signature:{r:b,s:v},messageHash:i,signedHash:k,address:vd,publicKey:{qx:ut,qy:dt}}}catch(t){throw this.config.onError?.(t),new S("Failed to sign message with passkey",t)}}async sendTransaction(e,t){try{if(!this.currentUser)throw new S("Must be authenticated to send transaction");let r=t?.mode||fe,s=t?.tag||pe,i=t?.origin||Me();if(r==="PRIMARY")throw t?.rpcUrl?new S("PRIMARY mode sendTransaction is not yet supported. Use signMessageWithPasskey() to obtain a P-256 signature and submit via a bundler manually."):new S("PRIMARY mode requires options.rpcUrl pointing to a bundler or sponsoring relayer. The P-256 address cannot pay gas directly without a deployed P-256-verifier contract via EIP-7702.");let o=r==="STRICT"?!0:t?.requireAuth||!1,c=await this.getMnemonicFromSession(o,r),a=await Fe(c,i,r,s),{Wallet:u,JsonRpcProvider:l}=await import("ethers"),h;if(a.privateKey)h=new u(a.privateKey);else{let{deriveWalletFromMnemonic:k}=await Promise.resolve().then(()=>(pt(),Cs)),{privateKey:m}=k(c,a.index);h=new u(m)}let g=t?.rpcUrl??(await this.getEndpoints(e.chainId))[0];if(!g)throw new S(`No RPC endpoint found for chainId ${e.chainId}. Pass options.rpcUrl.`);let d=new l(g);return{hash:(await h.connect(d).sendTransaction({to:e.to,value:e.value,data:e.data??"0x",chainId:e.chainId,gasLimit:e.gasLimit,maxFeePerGas:e.maxFeePerGas,maxPriorityFeePerGas:e.maxPriorityFeePerGas,nonce:e.nonce})).hash,from:a.address,chainId:e.chainId,mode:a.mode,tag:a.tag,origin:a.origin}}catch(r){throw this.config.onError?.(r),new S("Failed to send transaction",r)}}async signAuthorization(e,t){try{if(!this.currentUser)throw new S("Must be authenticated to sign authorization");let{Wallet:r,Signature:s}=await import("ethers"),{hashEIP7702AuthorizationMessage:i,verifyEIP7702Authorization:o}=await Promise.resolve().then(()=>(cn(),Rs)),c;if(e.privateKey)c=new r(e.privateKey);else{let y=await this.getMnemonicFromSession(t?.requireAuth);c=r.fromPhrase(y)}let a=BigInt(e.chainId||1),u=e.nonce||0n,l=i(a,e.contractAddress,u),h=c.signingKey.sign(l),g=s.from(h),d={chainId:a,address:e.contractAddress.toLowerCase(),nonce:u,yParity:g.yParity,r:g.r,s:g.s};if(!o(a,e.contractAddress,u,d,c.address))throw new S("Signature verification failed - this should not happen");return d}catch(r){throw this.config.onError?.(r),new S("Failed to sign authorization",r)}}async getEndpoints(e){return on(e)}async supportsEIP7702(e,t){return ta(e,this.getEndpoints.bind(this),t)}getEIP1193Provider(e){let t=e?.chainId??1,r=this,s={},i=(c,...a)=>{(s[c]??[]).forEach(u=>u(...a))};return{async request({method:c,params:a}){switch(c){case"eth_accounts":case"eth_requestAccounts":return[await r.getAddress(e?.mode??"STANDARD",e?.tag??"MAIN")];case"eth_chainId":return"0x"+t.toString(16);case"eth_sendTransaction":{let u=(a??[])[0]??{};if(!u.chainId&&!t)throw new S("eth_sendTransaction: chainId is required");let l=u.chainId?parseInt(u.chainId,16):t;return(await r.sendTransaction({to:u.to,value:u.value!==void 0?BigInt(u.value):void 0,data:u.data??"0x",chainId:l,gasLimit:u.gas!==void 0?BigInt(u.gas):void 0,maxFeePerGas:u.maxFeePerGas!==void 0?BigInt(u.maxFeePerGas):void 0,maxPriorityFeePerGas:u.maxPriorityFeePerGas!==void 0?BigInt(u.maxPriorityFeePerGas):void 0,nonce:u.nonce!==void 0?parseInt(u.nonce,16):void 0},{mode:e?.mode,tag:e?.tag,rpcUrl:e?.rpcUrl})).hash}case"personal_sign":{let[u]=a??[],l=wc(u)?bc(u):u;return(await r.signMessage(l,{mode:e?.mode,tag:e?.tag,signingMethod:"EIP191"})).signature}case"eth_sign":{let[,u]=a??[],l=wc(u)?bc(u):u;return(await r.signMessage(l,{mode:e?.mode,tag:e?.tag,signingMethod:"EIP191"})).signature}case"eth_signTypedData_v4":{let[,u]=a??[],l=typeof u=="string"?JSON.parse(u):u,{domain:h,types:g,message:d,primaryType:f}=l,y={...g};return delete y.EIP712Domain,(await r.signMessage(JSON.stringify(d),{mode:e?.mode,tag:e?.tag,signingMethod:"EIP712",eip712Domain:h,eip712Types:y,eip712PrimaryType:f})).signature}case"wallet_switchEthereumChain":{let u=parseInt((a??[])[0]?.chainId??"0x1",16);return t=u,i("chainChanged","0x"+u.toString(16)),null}default:throw new S(`w3pk EIP-1193: unsupported method "${c}"`)}},on(c,a){s[c]||(s[c]=[]),s[c].push(a)},removeListener(c,a){s[c]&&(s[c]=s[c].filter(u=>u!==a))}}}async requestExternalWalletDelegation(e){if(!this.currentUser)throw new S("Must be authenticated to get w3pk delegation address. Call login() or register() first.");let{requestExternalWalletAuthorization:t,getDefaultProvider:r}=await Promise.resolve().then(()=>(Ts(),ea)),s=e?.provider||r();if(!s)throw new S("No external wallet provider found. Please install MetaMask, Rabby, or similar wallet.");let i=this.currentUser.ethereumAddress;return t(s,{delegateToAddress:i,chainId:e?.chainId,nonce:e?.nonce,accountIndex:e?.accountIndex})}get zk(){return new Proxy({},{get:(e,t)=>async(...r)=>(await this.loadZKModule())[t](...r)})}async getBackupStatus(){if(!this.currentUser)throw new S("Must be authenticated to check backup status");let{BackupManager:e}=await Promise.resolve().then(()=>(tt(),et));return new e().getBackupStatus(this.currentUser.ethereumAddress)}async createBackupFile(e="password",t){if(!this.currentUser)throw new S("Must be authenticated to create backup");let r=await this.getMnemonicFromSession(!0),{BackupFileManager:s}=await Promise.resolve().then(()=>(le(),ge)),{BackupStorage:i}=await Promise.resolve().then(()=>(fn(),na)),o=new s,c=new i,a,u;if(e==="password"){if(!t)throw new S("Password required for password-based backup");u=(await o.createPasswordBackup(r,this.currentUser.ethereumAddress,t)).backupFile,a=o.createDownloadableBackup(u)}else if(e==="passkey"){let l=await this.walletStorage.retrieve(this.currentUser.ethereumAddress);if(!l)throw new S("No wallet data found");let g=await new F().getCredentialById(l.credentialId);if(!g)throw new S("Credential not found");u=(await o.createPasskeyBackup(r,this.currentUser.ethereumAddress,g.id,g.publicKey)).backupFile,a=o.createDownloadableBackup(u)}else if(e==="hybrid"){if(!t)throw new S("Password required for hybrid backup");let l=await this.walletStorage.retrieve(this.currentUser.ethereumAddress);if(!l)throw new S("No wallet data found");let g=await new F().getCredentialById(l.credentialId);if(!g)throw new S("Credential not found");u=(await o.createHybridBackup(r,this.currentUser.ethereumAddress,t,g.id,g.publicKey)).backupFile,a=o.createDownloadableBackup(u)}else throw new S(`Unknown encryption type: ${e}`);return await c.storeBackupMetadata({id:crypto.randomUUID(),ethereumAddress:this.currentUser.ethereumAddress,method:"file",createdAt:new Date().toISOString(),addressChecksum:u.addressChecksum}),a}async setupSocialRecovery(e,t,r){if(!this.currentUser)throw new S("Must be authenticated to set up social recovery");let s=await this.getMnemonicFromSession(!0),{BackupFileManager:i}=await Promise.resolve().then(()=>(le(),ge)),o=new i,c;if(r)c=(await o.createPasswordBackup(s,this.currentUser.ethereumAddress,r)).backupFile;else{let h=await this.walletStorage.retrieve(this.currentUser.ethereumAddress);if(!h)throw new S("No wallet data found");let d=await new F().getCredentialById(h.credentialId);if(!d)throw new S("Credential not found");c=(await o.createPasskeyBackup(s,this.currentUser.ethereumAddress,d.id,d.publicKey)).backupFile}let{SocialRecovery:a}=await Promise.resolve().then(()=>(Un(),Nn));return{guardianShares:(await new a().splitAmongGuardians(c,e,t)).guardianShares,setupComplete:!0}}async generateGuardianInvite(e,t){let{SocialRecovery:r}=await Promise.resolve().then(()=>(Un(),Nn)),s=new r,i=await s.createGuardianInvitation(e,t),o=s.createShareDownload(e);return{qrCodeDataURL:i.qrCodeDataURL,shareDocument:i.shareDocument,downloadBlob:o.blob,filename:o.filename}}async recoverFromGuardians(e,t){let{SocialRecovery:r}=await Promise.resolve().then(()=>(Un(),Nn)),{BackupFileManager:s}=await Promise.resolve().then(()=>(le(),ge)),{BackupManager:i}=await Promise.resolve().then(()=>(tt(),et)),o=new r,c=new s,a=new i,u=e.map(g=>typeof g=="string"?o.parseGuardianShare(g):g),l=await o.recoverFromShares(u),h;if(l.encryptionMethod==="password"){if(!t)throw new S("Password required to decrypt password-protected backup");h=await c.restoreWithPassword(l,t)}else throw new S("Passkey-encrypted backups not supported for guardian recovery. Use password-protected backups.");return a.markBackupVerified(h.ethereumAddress),h}async restoreFromBackupFile(e,t){let{BackupFileManager:r}=await Promise.resolve().then(()=>(le(),ge)),{BackupManager:s}=await Promise.resolve().then(()=>(tt(),et)),i=new r,o=new s,c=await i.parseBackupFile(e),a,u;if(c.encryptionMethod==="password"){if(!t)throw new S("Password required to restore password-encrypted backup");let l=await i.restoreWithPassword(c,t);a=l.mnemonic,u=l.ethereumAddress}else if(c.encryptionMethod==="passkey"){if(!this.currentUser)throw new S("Must be logged in with passkey to restore passkey-encrypted backup. Call login() first.");let g=(await new F().getAllCredentials()).find(f=>f.ethereumAddress.toLowerCase()===this.currentUser.ethereumAddress.toLowerCase());if(!g)throw new S("Credential not found for current user");let d=await i.restoreWithExistingPasskey(c,g.id,g.publicKey);a=d.mnemonic,u=d.ethereumAddress}else if(c.encryptionMethod==="hybrid"){if(!t)throw new S("Password required to restore hybrid backup");if(!this.currentUser)throw new S("Must be logged in with passkey to restore hybrid backup. Call login() first.");let g=(await new F().getAllCredentials()).find(f=>f.ethereumAddress.toLowerCase()===this.currentUser.ethereumAddress.toLowerCase());if(!g)throw new S("Credential not found for current user");let d=await i.restoreWithHybrid(c,t,g.id,g.publicKey);a=d.mnemonic,u=d.ethereumAddress}else throw new S(`Unknown encryption method: ${c.encryptionMethod}`);if(o.markBackupVerified(u),this.currentWallet={address:u,mnemonic:a},this.currentUser){let l=new F,g=(await l.getAllCredentials()).find(d=>d.ethereumAddress.toLowerCase()===this.currentUser.ethereumAddress.toLowerCase());if(g){let d=this.currentUser.ethereumAddress;d.toLowerCase()!==u.toLowerCase()&&await this.walletStorage.delete(d),await l.updateCredentialAddress(g.id,u);let f=await(await Promise.resolve().then(()=>(q(),Re))).deriveEncryptionKeyFromWebAuthn(g.id,g.publicKey),y=await(await Promise.resolve().then(()=>(q(),Re))).encryptData(a,f);await this.walletStorage.store({ethereumAddress:u,encryptedMnemonic:y,credentialId:g.id,createdAt:new Date().toISOString()}),this.currentUser={...this.currentUser,ethereumAddress:u},await this.sessionManager.startSession(a,g.id,u,g.publicKey,"STANDARD"),this.config.onAuthStateChanged?.(!0,this.currentUser)}}return{mnemonic:a,ethereumAddress:u}}async syncWalletWithPasskey(e,t){let{BackupFileManager:r}=await Promise.resolve().then(()=>(le(),ge)),{BackupManager:s}=await Promise.resolve().then(()=>(tt(),et)),{promptPasskeySelection:i}=await Promise.resolve().then(()=>(ui(),lc)),o=new r,c=new s,a=await i(),u=await o.parseBackupFile(e),l,h;if(u.encryptionMethod==="password"){if(!t)throw new S("Password required to restore password-encrypted backup");let f=await o.restoreWithPassword(u,t);l=f.mnemonic,h=f.ethereumAddress}else if(u.encryptionMethod==="passkey"){if(!a.publicKey)throw new S("Passkey public key not found. The passkey may not be registered on this device yet.");let f=await o.restoreWithExistingPasskey(u,a.credentialId,a.publicKey);l=f.mnemonic,h=f.ethereumAddress}else if(u.encryptionMethod==="hybrid"){if(!t)throw new S("Password required to restore hybrid backup");if(!a.publicKey)throw new S("Passkey public key not found. The passkey may not be registered on this device yet.");let f=await o.restoreWithHybrid(u,t,a.credentialId,a.publicKey);l=f.mnemonic,h=f.ethereumAddress}else throw new S(`Unknown encryption method: ${u.encryptionMethod}`);c.markBackupVerified(h);let d=await new F().getCredentialById(a.credentialId);if(d){let{deriveEncryptionKeyFromWebAuthn:f,encryptData:y}=await Promise.resolve().then(()=>(q(),Re)),k=await f(d.id,d.publicKey),m=await y(l,k);await this.walletStorage.store({ethereumAddress:h,encryptedMnemonic:m,credentialId:d.id,createdAt:new Date().toISOString()}),this.currentUser={username:d.username,ethereumAddress:h,credentialId:d.id},await this.sessionManager.startSession(l,d.id,h,d.publicKey,"STANDARD"),this.config.onAuthStateChanged?.(!0,this.currentUser)}return{mnemonic:l,ethereumAddress:h}}async registerWithBackupFile(e,t,r){let{BackupFileManager:s}=await Promise.resolve().then(()=>(le(),ge)),{BackupManager:i}=await Promise.resolve().then(()=>(tt(),et)),o=new s,c=new i,a=await o.parseBackupFile(e);if(a.encryptionMethod!=="password")throw new S("Can only register with password-encrypted backups. Use restoreFromBackupFile() for passkey-encrypted backups.");let{mnemonic:u,ethereumAddress:l}=await o.restoreWithPassword(a,t),{Wallet:h}=await import("ethers");if(h.fromPhrase(u).address.toLowerCase()!==l.toLowerCase())throw new S("Backup verification failed: address mismatch");return c.markBackupVerified(l),this.currentWallet={address:l,mnemonic:u},this.register({username:r})}async getSyncStatus(){let{DeviceSyncManager:e}=await Promise.resolve().then(()=>(xr(),Ln));return new e().getSyncInfo()}async exportForSync(){if(!this.currentUser)throw new S("Must be authenticated to export for sync");let e=await this.getMnemonicFromSession(!0),t=await this.walletStorage.retrieve(this.currentUser.ethereumAddress);if(!t)throw new S("No wallet data found");let s=await new F().getCredentialById(t.credentialId);if(!s)throw new S("Credential not found");let{DeviceSyncManager:i}=await Promise.resolve().then(()=>(xr(),Ln)),o=new i,{backupFile:c,blob:a}=await o.exportForSync(e,this.currentUser.ethereumAddress,s.id,s.publicKey),u=`w3pk-sync-${this.currentUser.ethereumAddress.substring(0,8)}.json`,l;try{l=await o.generateSyncQR(c)}catch(h){console.warn("QR code generation failed:",h)}return{blob:a,filename:u,qrCode:l}}async importFromSync(e){if(!this.currentUser)throw new S("Must be logged in to import from sync. Call login() first.");let{DeviceSyncManager:t}=await Promise.resolve().then(()=>(xr(),Ln)),{BackupFileManager:r}=await Promise.resolve().then(()=>(le(),ge)),{BackupManager:s}=await Promise.resolve().then(()=>(tt(),et)),i=new r,o=new t,c=new s,a=await i.parseBackupFile(e),u=await this.walletStorage.retrieve(this.currentUser.ethereumAddress);if(!u)throw new S("No wallet data found for current user");let h=await new F().getCredentialById(u.credentialId);if(!h)throw new S("Credential not found");let{mnemonic:g,ethereumAddress:d}=await o.importFromSync(a,h.id,h.publicKey);c.markBackupVerified(d);let f=await(await Promise.resolve().then(()=>(q(),Re))).deriveEncryptionKeyFromWebAuthn(h.id,h.publicKey),y=await(await Promise.resolve().then(()=>(q(),Re))).encryptData(g,f);return await this.walletStorage.store({ethereumAddress:d,encryptedMnemonic:y,credentialId:h.id,createdAt:new Date().toISOString()}),{ethereumAddress:d,success:!0}}async detectSyncCapabilities(){let{PlatformDetector:e}=await Promise.resolve().then(()=>(gc(),pc));return new e().detectSyncCapabilities()}async simulateRecoveryScenario(e){if(!this.currentUser)throw new S("Must be authenticated to run recovery simulation");let t=await this.getBackupStatus(),{RecoverySimulator:r}=await Promise.resolve().then(()=>(vr(),Wn));return new r().simulateScenario(e,t)}async runRecoveryTest(){if(!this.currentUser)throw new S("Must be authenticated to run recovery test");let e=await this.getBackupStatus(),{RecoverySimulator:t}=await Promise.resolve().then(()=>(vr(),Wn));return new t().runInteractiveTest(e)}async getEducation(e){let{getExplainer:t}=await Promise.resolve().then(()=>(vr(),Wn)),r=t(e);if(!r)throw new S(`Unknown education topic: ${e}`);return r}hasActiveSession(){return this.sessionManager.isActive()}getSessionRemainingTime(){return this.sessionManager.getRemainingTime()}extendSession(){try{this.sessionManager.extendSession()}catch(e){throw new S("Cannot extend session",e)}}async clearSession(){await this.sessionManager.clearSession()}setSessionDuration(e){this.sessionManager.setSessionDuration(e)}};Y();ui();gt();vr();async function Rg(n,e="build"){let{importer:t}=await Promise.resolve().then(()=>(Wu(),zu)),{MemoryBlockstore:r}=await Promise.resolve().then(()=>(fd(),hd)),s=new r,o=t(async function*(){yield{path:e,content:n}}(),s,{cidVersion:1,rawLeaves:!0,wrapWithDirectory:!1});for await(let c of o)return c.cid.toString();throw new Error("Failed to generate CID")}async function Tg(n){let e=["index.js","index.mjs","index.d.ts"],t=[],r=0;for(let o of e){let c=`${n}/${o}`,a=await fetch(c);if(!a.ok)throw new Error(`Failed to fetch ${o}: ${a.statusText}`);let u=await a.arrayBuffer(),l=new Uint8Array(u);t.push(l),r+=l.length}let s=new Uint8Array(r),i=0;for(let o of t)s.set(o,i),i+=o.length;return s}async function To(n){let e=await Tg(n);return Rg(e)}function Fo(){try{return pd().version}catch{throw new Error("Failed to read package version")}}async function Mo(){let n=Fo();return To(`https://unpkg.com/w3pk@${n}/dist`)}async function gd(n){return await Mo()===n}xe();Ms();pt();function md(n=11){let e="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789",t=new Uint8Array(n);return crypto.getRandomValues(t),Array.from(t).map(r=>e[r%e.length]).join("")}function yd(n){if(!n.domain||!n.address||!n.uri||!n.version||n.chainId===void 0||!n.nonce||!n.issuedAt)throw new Error("Missing required SIWE message fields");if(n.version!=="1")throw new Error('SIWE version must be "1"');if(n.nonce.length<8||!/^[a-zA-Z0-9]+$/.test(n.nonce))throw new Error("Nonce must be at least 8 alphanumeric characters");if(n.statement&&n.statement.includes(`
957
+ ${e}[Error list was empty]`,t.trim()}return Ju(n,e)}function Sg(n){let e=()=>{};return e.enabled=!1,e.color="",e.diff=0,e.log=()=>{},e.namespace=n,e.destroy=()=>!0,e.extend=()=>e,e}function Do(n,e){let t=Sg(`${n}:trace`);return X.enabled(`${n}:trace`)&&X.names.map(r=>r.toString()).find(r=>r.includes(":trace"))!=null&&(t=X(`${n}:trace`,e)),Object.assign(X(n,e),{error:X(`${n}:error`,e),trace:t,newScope:r=>Do(`${n}:${r}`,e)})}function Qu(n){if(n!=null&&(n=n.trim(),n.length!==0))return n}var Zu=w(()=>{"use strict";Er();Hn();Xi();ju();X.formatters.b=n=>n==null?"undefined":de.baseEncode(n);X.formatters.t=n=>n==null?"undefined":J.baseEncode(n);X.formatters.m=n=>n==null?"undefined":Ji.baseEncode(n);X.formatters.p=n=>n==null?"undefined":n.toString();X.formatters.c=n=>n==null?"undefined":n.toString();X.formatters.k=n=>n==null?"undefined":n.toString();X.formatters.a=n=>n==null?"undefined":n.toString();X.formatters.e=n=>n==null?"undefined":Xu(n)});function xg(n){let[e,t]=n[Symbol.asyncIterator]!=null?[n[Symbol.asyncIterator](),Symbol.asyncIterator]:[n[Symbol.iterator](),Symbol.iterator],r=[];return{peek:()=>e.next(),push:s=>{r.push(s)},next:()=>r.length>0?{done:!1,value:r.shift()}:e.next(),[t](){return this}}}var ed,td=w(()=>{"use strict";ed=xg});function vg(n){return n[Symbol.asyncIterator]!=null}function Ag(n,e){let t=0;if(vg(n))return(async function*(){for await(let a of n)await e(a,t++)&&(yield a)})();let r=ed(n),{value:s,done:i}=r.next();if(i===!0)return(function*(){})();let o=e(s,t++);if(typeof o.then=="function")return(async function*(){await o&&(yield s);for(let a of r)await e(a,t++)&&(yield a)})();let c=e;return(function*(){o===!0&&(yield s);for(let a of r)c(a,t++)&&(yield a)})()}var rd,nd=w(()=>{"use strict";td();rd=Ag});function Qt(){let n={};return n.promise=new Promise((e,t)=>{n.resolve=e,n.reject=t}),n}var sd=w(()=>{"use strict"});async function id(n,e,t){if(e==null)return n;if(e.aborted)return n.catch(()=>{}),Promise.reject(new ps(t?.errorMessage,t?.errorCode,t?.errorName));let r,s=new ps(t?.errorMessage,t?.errorCode,t?.errorName);try{return await Promise.race([n,new Promise((i,o)=>{r=()=>{o(s)},e.addEventListener("abort",r)})])}finally{r!=null&&e.removeEventListener("abort",r)}}var ps,od=w(()=>{"use strict";ps=class extends Error{constructor(t,r,s){super(t??"The operation was aborted");p(this,"type");p(this,"code");this.type="aborted",this.name=s??"AbortError",this.code=r??"ABORT_ERR"}}});function ad(){return new Ro}var Ro,cd=w(()=>{"use strict";sd();od();Ro=class{constructor(){p(this,"readNext");p(this,"haveNext");p(this,"ended");p(this,"nextResult");p(this,"error");this.ended=!1,this.readNext=Qt(),this.haveNext=Qt()}[Symbol.asyncIterator](){return this}async next(){if(this.nextResult==null&&await this.haveNext.promise,this.nextResult==null)throw new Error("HaveNext promise resolved but nextResult was undefined");let e=this.nextResult;return this.nextResult=void 0,this.readNext.resolve(),this.readNext=Qt(),e}async throw(e){return this.ended=!0,this.error=e,e!=null&&(this.haveNext.promise.catch(()=>{}),this.haveNext.reject(e)),{done:!0,value:void 0}}async return(){let e={done:!0,value:void 0};return this.ended=!0,this.nextResult=e,this.haveNext.resolve(),e}async push(e,t){await this._push(e,t)}async end(e,t){e!=null?await this.throw(e):await this._push(void 0,t)}async _push(e,t){if(e!=null&&this.ended)throw this.error??new Error("Cannot push value onto an ended pushable");for(;this.nextResult!=null;)await this.readNext.promise;e!=null?this.nextResult={done:!1,value:e}:(this.ended=!0,this.nextResult={done:!0,value:void 0}),this.haveNext.resolve(),this.haveNext=Qt(),await id(this.readNext.promise,t?.signal,t)}}});function kg(n){return n[Symbol.asyncIterator]!=null}async function Eg(n,e,t){try{await Promise.all(n.map(async r=>{for await(let s of r)await e.push(s,{signal:t}),t.throwIfAborted()})),await e.end(void 0,{signal:t})}catch(r){await e.end(r,{signal:t}).catch(()=>{})}}async function*Cg(n){let e=new AbortController,t=ad();Eg(n,t,e.signal).catch(()=>{});try{yield*t}finally{e.abort()}}function*Pg(n){for(let e of n)yield*e}function Ig(...n){let e=[];for(let t of n)kg(t)||e.push(t);return e.length===n.length?Pg(e):Cg(n)}var ld,ud=w(()=>{"use strict";cd();ld=Ig});var Bg,gs,dd=w(()=>{"use strict";Zu();ls();nd();ud();qr();Bg=Do("blockstore:core:tiered"),gs=class extends Ee{constructor(t){super();p(this,"stores");this.stores=t.slice()}async put(t,r,s){return await Promise.all(this.stores.map(async i=>{await i.put(t,r,s)})),t}async*get(t,r){let s;for(let i of this.stores)try{yield*i.get(t,r);return}catch(o){s=o,Bg.error(o)}throw s??new He}async has(t,r){for(let s of this.stores)if(await s.has(t,r))return!0;return!1}async delete(t,r){await Promise.all(this.stores.map(async s=>{await s.delete(t,r)}))}async*putMany(t,r={}){for await(let s of t)await this.put(s.cid,s.bytes,r),yield s.cid}async*deleteMany(t,r={}){for await(let s of t)await this.delete(s,r),yield s}async*getAll(t){let r=new Set;yield*rd(ld(...this.stores.map(s=>s.getAll(t))),s=>{let i=s.cid.toString();return r.has(i)?!1:(r.add(i),!0)})}}});var hd={};B(hd,{BaseBlockstore:()=>Ee,BlackHoleBlockstore:()=>ds,MemoryBlockstore:()=>us,TieredBlockstore:()=>gs});var fd=w(()=>{"use strict";qr();qu();Hu();dd()});var pd=D((zS,Dg)=>{Dg.exports={name:"w3pk",version:"0.9.2",description:"WebAuthn SDK for passwordless authentication, encrypted wallets, ERC-5564 stealth addresses, and zero-knowledge proofs",author:"Julien B\xE9ranger",license:"GPL-3.0",repository:{type:"git",url:"https://github.com/w3hc/w3pk.git"},bugs:{url:"https://github.com/w3hc/w3pk/issues"},homepage:"https://github.com/w3hc/w3pk#readme",keywords:["webauthn","passkey","authentication","passwordless","fido2","biometric","ethereum","web3","encryption","zero-knowledge","zk-proofs","zk-snarks","privacy","stealth-address","erc-5564","erc-6538","unlinkable","anonymous-transactions","privacy-preserving","ecdh","secp256k1","view-tags","circom","groth16","merkle-tree","commitment-scheme"],main:"./dist/index.js",module:"./dist/index.mjs",types:"./dist/index.d.ts",exports:{".":{types:"./dist/index.d.ts",import:"./dist/index.mjs",require:"./dist/index.js"},"./zk":{types:"./dist/zk/index.d.ts",import:"./dist/zk/index.mjs",require:"./dist/zk/index.js"},"./zk/utils":{types:"./dist/zk/utils.d.ts",import:"./dist/zk/utils.mjs",require:"./dist/zk/utils.js"},"./chainlist":{types:"./dist/chainlist/index.d.ts",import:"./dist/chainlist/index.mjs",require:"./dist/chainlist/index.js"},"./inspect":{types:"./dist/inspect/index.d.ts",import:"./dist/inspect/index.mjs",require:"./dist/inspect/index.js"},"./inspect/node":{types:"./dist/inspect/node.d.ts",import:"./dist/inspect/node.mjs",require:"./dist/inspect/node.js"}},sideEffects:!1,files:["dist","README.md","LICENSE","docs/","scripts/compute-build-hash.mjs"],scripts:{build:"tsup","build:zk":"npm run build && npm run compile:circuits","compile:circuits":"node scripts/compile-circuits.js",dev:"tsup --watch",test:"tsx test/test.ts && tsx test/comprehensive.test.ts && tsx test/backup.test.ts && tsx test/social-recovery.test.ts && tsx test/recovery-education.test.ts && tsx test/zk/zk.test.ts && tsx test/nft-ownership.test.ts && tsx test/chainlist.test.ts && tsx test/eip7702.test.ts && tsx test/external-wallet.test.ts && tsx test/erc5564.test.ts && tsx test/zk/key-stretching.test.ts && tsx test/username-encoding.test.ts && tsx test/username-validation.test.ts && tsx test/origin-derivation.test.ts && tsx test/build-hash.test.ts && tsx test/credential-checking.test.ts && tsx test/webauthn-native.test.ts && tsx test/persistent-session.test.ts && tsx test/sign-message.test.ts && tsx test/siwe.test.ts && tsx test/requirereauth.test.ts && tsx test/eip7951.test.ts && tsx test/send-transaction.test.ts && tsx test/eip1193-provider.test.ts","test:basic":"tsx test/test.ts","test:comprehensive":"tsx test/comprehensive.test.ts","test:backup":"tsx test/backup.test.ts","test:social-recovery":"tsx test/social-recovery.test.ts","test:education":"tsx test/recovery-education.test.ts","test:username":"tsx test/username-encoding.test.ts && tsx test/username-validation.test.ts","test:recovery":"tsx test/backup.test.ts && tsx test/social-recovery.test.ts && tsx test/recovery-education.test.ts","test:zk":"tsx test/zk/zk.test.ts","test:nft":"tsx test/nft-ownership.test.ts","test:chainlist":"tsx test/chainlist.test.ts","test:eip7702":"tsx test/eip7702.test.ts","test:external-wallet":"tsx test/external-wallet.test.ts","test:eip7951":"tsx test/eip7951.test.ts","test:erc5564":"tsx test/erc5564.test.ts","test:sign-message":"tsx test/sign-message.test.ts","test:siwe":"tsx test/siwe.test.ts",prepublishOnly:"pnpm build","build:hash":"node scripts/compute-build-hash.mjs","release:notes":"node scripts/generate-release-notes.mjs",html:"lsof -ti:3000 | xargs kill -9 2>/dev/null || true && tsup && npx serve . -l 3000 & sleep 5 && open http://localhost:3000/standalone/checker.html"},packageManager:"pnpm@10.6.4",devDependencies:{"@types/node":"^24.9.0","@types/qrcode":"^1.5.5",circomlib:"^2.0.5",tsup:"^8.5.1",tsx:"^4.21.0",typescript:"^5.9.3"},peerDependencies:{ethers:"^6.0.0"},optionalDependencies:{"@ipld/car":"^5.4.2","blockstore-core":"^6.1.1",circomlibjs:"^0.1.7","ipfs-unixfs-importer":"^16.0.1",qrcode:"^1.5.4",snarkjs:"^0.7.5"}}});var Ug={};B(Ug,{ApiError:()=>Hr,AuthenticationError:()=>O,CryptoError:()=>N,DEFAULT_MODE:()=>fe,DEFAULT_TAG:()=>pe,RecoverySimulator:()=>kt,RegistrationError:()=>ht,StealthAddressModule:()=>yt,StorageError:()=>R,WalletError:()=>S,Web3Passkey:()=>Et,Web3PasskeyError:()=>$,arrayBufferToBase64Url:()=>Se,assertEthereumAddress:()=>Vr,assertMnemonic:()=>Lo,assertUsername:()=>Gr,authenticateWithPasskey:()=>li,base64ToArrayBuffer:()=>Ss,base64UrlDecode:()=>vs,base64UrlToArrayBuffer:()=>L,canControlStealthAddress:()=>Ho,checkStealthAddress:()=>nr,clearCache:()=>Zo,computeStealthPrivateKey:()=>sr,createSiweMessage:()=>yd,createWalletFromMnemonic:()=>Es,createWeb3Passkey:()=>xd,default:()=>Ng,deriveAddressFromP256PublicKey:()=>Ps,deriveIndexFromOriginModeAndTag:()=>Zr,deriveStealthKeys:()=>mt,deriveWalletFromMnemonic:()=>tr,detectWalletProvider:()=>dn,encodeEIP7702AuthorizationMessage:()=>or,extractRS:()=>Fs,generateBIP39Wallet:()=>er,generateSiweNonce:()=>md,generateStealthAddress:()=>tn,getAllChains:()=>Qo,getAllTopics:()=>hi,getChainById:()=>Xo,getCurrentBuildHash:()=>Mo,getCurrentOrigin:()=>Me,getDefaultProvider:()=>un,getEndpoints:()=>on,getExplainer:()=>di,getOriginSpecificAddress:()=>Fe,getPackageVersion:()=>Fo,getW3pkBuildHash:()=>To,hashEIP7702AuthorizationMessage:()=>ar,inspect:()=>No,inspectNow:()=>Sd,isStrongPassword:()=>_o,normalizeOrigin:()=>rr,parseSiweMessage:()=>ms,promptPasskeySelection:()=>ci,requestExternalWalletAuthorization:()=>ln,safeAtob:()=>Ve,safeBtoa:()=>xs,searchExplainers:()=>fi,supportsEIP7702Authorization:()=>hn,validateEthereumAddress:()=>ys,validateMnemonic:()=>bs,validateSiweMessage:()=>wd,validateUsername:()=>ws,verifyBuildHash:()=>gd,verifyEIP7702Authorization:()=>an,verifySiweSignature:()=>bd});module.exports=Bd(Ug);Y();function ys(n){return/^0x[a-fA-F0-9]{40}$/.test(n)}function ws(n){return n.length<3||n.length>50?!1:/^[a-zA-Z0-9]([a-zA-Z0-9_-]*[a-zA-Z0-9])?$/.test(n)}function bs(n){let e=n.trim().split(/\s+/);return e.length===12||e.length===24}function Vr(n){if(!ys(n))throw new Error("Invalid Ethereum address format")}function Gr(n){if(!ws(n))throw new Error("Username must be 3-50 characters long and contain only letters, numbers, underscores, and hyphens. Must start and end with a letter or number.")}function Lo(n){if(!bs(n))throw new Error("Invalid mnemonic: must be 12 or 24 words")}function _o(n){if(n.length<12)return!1;let e=/[A-Z]/.test(n),t=/[a-z]/.test(n),r=/[0-9]/.test(n),s=/[!@#$%^&*()_+\-=\[\]{};':"\\|,.<>\/?]/.test(n);return!(!e||!t||!r||!s||["password","12345678","qwerty","abc123","password123","admin","letmein"].some(o=>n.toLowerCase().includes(o)))}Te();xe();q();async function Rd(n){try{let e=new Uint8Array(n),t=Td(e);if(t===-1)return null;let r=e.slice(t);if(!((r[32]&64)!==0))return null;let o=37;o+=16;let c=r[o]<<8|r[o+1];o+=2,o+=c;let a=r.slice(o),u=await Fd(a);return Se(u)}catch(e){return console.error("Failed to extract public key:",e),null}}function Td(n){let e=new Uint8Array([104,97,117,116,104,68,97,116,97]);for(let t=0;t<n.length-e.length;t++){let r=!0;for(let s=0;s<e.length;s++)if(n[t+s]!==e[s]){r=!1;break}if(r){let s=n[t+e.length],i=t+e.length+1;if(s>=88&&s<=91){let o=s-87;i+=o}return i}}return-1}async function Fd(n){let e=Ko(n,-2),t=Ko(n,-3);if(!e||!t)throw new Error("Failed to extract EC coordinates from COSE key");let r=new Uint8Array(65);r[0]=4,r.set(e,1),r.set(t,33);let s=new Uint8Array([48,89,48,19,6,7,42,134,72,206,61,2,1,6,8,42,134,72,206,61,3,1,7,3,66,0]),i=new Uint8Array(s.length+r.length);return i.set(s,0),i.set(r,s.length),i.buffer}function Ko(n,e){let t=e<0?32+(-1-e):e;for(let r=0;r<n.length-33;r++)if(n[r]===t&&(n[r+1]===88&&n[r+2]===32||n[r+1]===88&&n[r+2]===32))return n.slice(r+3,r+35);return null}async function zo(n){try{let{username:e,ethereumAddress:t}=n;Gr(e),Vr(t);let r=new F;if(await r.userExists(e))throw new Error("Username already registered");let s=De(),o=new TextEncoder().encode(e),c=Se(o),a=L(s),u=L(c),l={challenge:a,rp:{name:"w3pk",id:window.location.hostname},user:{id:u,name:e,displayName:e},pubKeyCredParams:[{type:"public-key",alg:-7},{type:"public-key",alg:-257}],authenticatorSelection:{authenticatorAttachment:"platform",userVerification:"required",residentKey:"required",requireResidentKey:!0},timeout:6e4,attestation:"none"},h=await navigator.credentials.create({publicKey:l});if(!h)throw new Error("Failed to create credential");let g=await Rd(h.response.attestationObject);if(!g)throw new Error("Public key not returned from authenticator");return await r.saveCredential({id:h.id,publicKey:g,username:e,ethereumAddress:t,createdAt:new Date().toISOString(),lastUsed:new Date().toISOString(),signCount:0}),{signature:h.response.attestationObject}}catch(e){throw new ht(e instanceof Error?e.message:"Registration failed",e)}}Y();Te();xe();q();async function Qr(){try{let n=new F,e=De(),t=[];try{let a=await n.getAllCredentials();a.length>0&&(t=a.map(u=>({id:u.id,type:"public-key",transports:["internal","hybrid","usb","nfc","ble"]})))}catch{}let s={challenge:L(e),rpId:window.location.hostname,userVerification:"required",timeout:6e4};t.length>0&&(s.allowCredentials=t.map(a=>({id:L(a.id),type:a.type,transports:a.transports})));let i;try{let a=await navigator.credentials.get({publicKey:s});if(!a)throw new Error("Authentication failed - no credential returned");i=a}catch(a){throw a?.name==="NotAllowedError"||a?.message?.toLowerCase().includes("no credentials available")||a?.message?.toLowerCase().includes("no access key")?(await n.getAllCredentials()).length>0?new O("Your passkey is not available on this device. You may need to restore your wallet from a backup, or login on the device where you registered."):new O("No passkey found. Please register first or restore from a backup."):a}let o=await n.getCredentialById(i.id);if(!o)throw new O("Passkey authenticated but wallet data not found on this device. To sync your account: 1) Select your passkey when prompted, then 2) Provide your backup file. This allows you to use the same passkey on multiple devices.");if(!await Md(i,o,n))throw new Error("Signature verification failed");return{verified:!0,user:{username:o.username,ethereumAddress:o.ethereumAddress,credentialId:o.id},signature:i.response.signature}}catch(n){throw new O(n instanceof Error?n.message:"Authentication failed",n)}}async function Md(n,e,t){try{let r=n.response.authenticatorData,s=new DataView(r),o=new Uint8Array(r).slice(0,32),c=window.location.hostname,a=new Uint8Array(await crypto.subtle.digest("SHA-256",new TextEncoder().encode(c)));if(!Nd(o,a))return console.error("RP ID hash mismatch - possible phishing attack"),!1;let u=s.getUint32(33,!1);if(u>0||e.signCount&&e.signCount>0){let b=e.signCount||0;if(u<=b)return console.error(`Authenticator cloning detected! Counter did not increase: stored=${b}, received=${u}`),!1}let l=L(e.publicKey),h=await crypto.subtle.importKey("spki",l,{name:"ECDSA",namedCurve:"P-256"},!1,["verify"]),g=n.response.clientDataJSON,d=await crypto.subtle.digest("SHA-256",g),f=new Uint8Array(r.byteLength+d.byteLength);f.set(new Uint8Array(r),0),f.set(new Uint8Array(d),r.byteLength);let y=n.response.signature,k=Ud(new Uint8Array(y));return await crypto.subtle.verify({name:"ECDSA",hash:"SHA-256"},h,k,f)?(await t.updateSignatureCounter(e.id,u),!0):!1}catch(r){return console.error("Signature verification error:",r),!1}}function Nd(n,e){if(n.length!==e.length)return!1;for(let t=0;t<n.length;t++)if(n[t]!==e[t])return!1;return!0}function Ud(n){let e=2;e++;let t=n[e++];t>32&&(e++,t--);let r=n.slice(e,e+t);e+=t,e++;let s=n[e++];s>32&&(e++,s--);let i=n.slice(e,e+s),o=new Uint8Array(64);return o.set(r,32-r.length),o.set(i,64-i.length),o.buffer}Y();var Ld="Web3PasskeyWallet",_d=1,ve="wallets",Xr=class{constructor(){this.db=null}async init(){return new Promise((e,t)=>{let r=indexedDB.open(Ld,_d);r.onerror=()=>t(new R("Failed to open database",r.error)),r.onsuccess=()=>{this.db=r.result,e()},r.onupgradeneeded=()=>{let s=r.result;s.objectStoreNames.contains(ve)||s.createObjectStore(ve,{keyPath:"ethereumAddress"})}})}async store(e){return this.db||await this.init(),new Promise((t,r)=>{let o=this.db.transaction([ve],"readwrite").objectStore(ve).put(e);o.onerror=()=>r(new R("Failed to store wallet data",o.error)),o.onsuccess=()=>t()})}async retrieve(e){return this.db||await this.init(),new Promise((t,r)=>{let o=this.db.transaction([ve],"readonly").objectStore(ve).get(e);o.onerror=()=>r(new R("Failed to retrieve wallet data",o.error)),o.onsuccess=()=>t(o.result||null)})}async delete(e){return this.db||await this.init(),new Promise((t,r)=>{let o=this.db.transaction([ve],"readwrite").objectStore(ve).delete(e);o.onerror=()=>r(new R("Failed to delete wallet data",o.error)),o.onsuccess=()=>t()})}async clear(){return this.db||await this.init(),new Promise((e,t)=>{let i=this.db.transaction([ve],"readwrite").objectStore(ve).clear();i.onerror=()=>t(new R("Failed to clear wallet data",i.error)),i.onsuccess=()=>e()})}};pt();gt();q();Y();var H=require("ethers");Y();function mt(n){try{let e=H.ethers.HDNodeWallet.fromPhrase(n,void 0,"m/44'/60'/1'/0/0"),t=H.ethers.HDNodeWallet.fromPhrase(n,void 0,"m/44'/60'/1'/0/1"),r=t.signingKey.compressedPublicKey,s=e.signingKey.compressedPublicKey;return{stealthMetaAddress:r+s.slice(2),spendingPubKey:r,viewingPubKey:s,viewingKey:e.privateKey,spendingKey:t.privateKey}}catch(e){throw new N("Failed to derive stealth keys",e)}}function tn(n){try{let e="0x"+n.slice(2,68),t="0x"+n.slice(68),r=H.ethers.Wallet.createRandom(),s=r.signingKey.compressedPublicKey,i=Is(r.privateKey,t),o=H.ethers.keccak256(i),c="0x"+o.slice(2,4),a=Go(e,Vo(o));return{stealthAddress:Yo(a),ephemeralPubKey:s,viewTag:c}}catch(e){throw new N("Failed to generate stealth address",e)}}function nr(n,e,t,r,s){try{let i=Is(n,t),o=H.ethers.keccak256(i);if(s&&("0x"+o.slice(2,4)).toLowerCase()!==s.toLowerCase())return{isForUser:!1};let c=Go(e,Vo(o)),a=Yo(c);return a.toLowerCase()!==r.toLowerCase()?{isForUser:!1}:{isForUser:!0,stealthAddress:a}}catch{return{isForUser:!1}}}function sr(n,e,t){try{let r=Is(n,t),s=H.ethers.keccak256(r);return Kd(e,s)}catch(r){throw new N("Failed to compute stealth private key",r)}}function Ho(n,e,t,r,s,i){try{if(!nr(n,t,r,s,i).isForUser)return!1;let c=sr(n,e,r);return new H.ethers.Wallet(c).address.toLowerCase()===s.toLowerCase()}catch{return!1}}function Is(n,e){try{return new H.ethers.Wallet(n).signingKey.computeSharedSecret(e)}catch(t){throw new N("Failed to compute shared secret",t)}}function Vo(n){try{return new H.ethers.Wallet(n).signingKey.compressedPublicKey}catch(e){throw new N("Failed to multiply generator by scalar",e)}}function Go(n,e){try{let t=H.ethers.SigningKey.computePublicKey(n,!1),r=H.ethers.SigningKey.computePublicKey(e,!1),s=BigInt("0x"+t.slice(4,68)),i=BigInt("0x"+t.slice(68)),o=BigInt("0x"+r.slice(4,68)),c=BigInt("0x"+r.slice(68)),a=BigInt("0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEFFFFFC2F");if(s===o&&i===c){let f=3n*s*s%a,y=2n*i%a,k=f*qo(y,a)%a,m=(k*k-2n*s)%a,b=(k*(s-m)-i)%a;return $o((m+a)%a,(b+a)%a)}let u=((c-i)%a+a)%a,l=((o-s)%a+a)%a,h=u*qo(l,a)%a,g=(h*h-s-o)%a,d=(h*(s-g)-i)%a;return $o((g+a)%a,(d+a)%a)}catch(t){throw new N("Failed to add public keys",t)}}function Kd(n,e){try{let t=BigInt("0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEBAAEDCE6AF48A03BBFD25E8CD0364141"),r=BigInt(n),s=BigInt(e);return"0x"+((r+s)%t).toString(16).padStart(64,"0")}catch(t){throw new N("Failed to add private keys",t)}}function $o(n,e){return"0x"+(e%2n===0n?"02":"03")+n.toString(16).padStart(64,"0")}function qo(n,e){n=(n%e+e)%e;let[t,r]=[n,e],[s,i]=[1n,0n];for(;r!==0n;){let o=t/r;[t,r]=[r,t-o*r],[s,i]=[i,s-o*i]}return(s%e+e)%e}function Yo(n){try{let e=H.ethers.SigningKey.computePublicKey(n,!1),t=H.ethers.keccak256("0x"+e.slice(4));return H.ethers.getAddress("0x"+t.slice(-40))}catch(e){throw new N("Failed to derive address from public key",e)}}var yt=class{constructor(e,t){this.getMnemonic=t}async generateStealthAddress(e){try{let t=await this.getMnemonic(e?.requireAuth),r=mt(t),s=tn(r.stealthMetaAddress);return{stealthAddress:s.stealthAddress,ephemeralPublicKey:s.ephemeralPubKey,viewTag:s.viewTag}}catch(t){throw new $("Failed to generate stealth address","STEALTH_GENERATION_ERROR",t)}}async parseAnnouncement(e,t){try{let r=await this.getMnemonic(t?.requireAuth),s=mt(r),i=nr(s.viewingKey,s.spendingPubKey,e.ephemeralPublicKey,e.stealthAddress,e.viewTag);if(!i.isForUser)return{isForUser:!1};let o=sr(s.viewingKey,s.spendingKey,e.ephemeralPublicKey);return{isForUser:!0,stealthAddress:i.stealthAddress,stealthPrivateKey:o}}catch(r){throw new $("Failed to parse announcement","ANNOUNCEMENT_PARSE_ERROR",r)}}async scanAnnouncements(e,t){let r=[];for(let s of e){let i=await this.parseAnnouncement(s,t);i.isForUser&&r.push(i)}return r}async getKeys(e){try{let t=await this.getMnemonic(e?.requireAuth);return mt(t)}catch(t){throw new $("Failed to get stealth keys","STEALTH_KEYS_ERROR",t)}}async getStealthMetaAddress(e){try{return(await this.getKeys(e)).stealthMetaAddress}catch(t){throw new $("Failed to get stealth meta-address","STEALTH_META_ADDRESS_ERROR",t)}}get isAvailable(){return!0}};Y();q();var zd="Web3PasskeyPersistentSessions",Wd=2,ae="sessions",rn=class{constructor(){this.db=null;this.initPromise=null}async init(){return this.initPromise?this.initPromise:this.db?Promise.resolve():(this.initPromise=new Promise((e,t)=>{let r=indexedDB.open(zd,Wd);r.onupgradeneeded=s=>{let i=s.target.result;i.objectStoreNames.contains(ae)||i.createObjectStore(ae,{keyPath:"ethereumAddress"}).createIndex("expiresAt","expiresAt",{unique:!1})},r.onsuccess=()=>{this.db=r.result,this.initPromise=null,e()},r.onerror=()=>{this.initPromise=null,t(new R("Failed to open persistent session database",r.error))}}),this.initPromise)}async store(e){if(e.securityMode==="STRICT")throw new R("Cannot persist STRICT mode sessions");return this.db||await this.init(),new Promise((t,r)=>{let o=this.db.transaction([ae],"readwrite").objectStore(ae).put(e);o.onerror=()=>r(new R("Failed to store persistent session",o.error)),o.onsuccess=()=>t()})}async retrieve(e){return this.db||await this.init(),new Promise((t,r)=>{let o=this.db.transaction([ae],"readonly").objectStore(ae).get(e);o.onerror=()=>r(new R("Failed to retrieve persistent session",o.error)),o.onsuccess=()=>{let c=o.result||null;if(c&&Date.now()>c.expiresAt){this.delete(e).catch(console.error),t(null);return}t(c)}})}async delete(e){return this.db||await this.init(),new Promise((t,r)=>{let o=this.db.transaction([ae],"readwrite").objectStore(ae).delete(e);o.onerror=()=>r(new R("Failed to delete persistent session",o.error)),o.onsuccess=()=>t()})}async clear(){return this.db||await this.init(),new Promise((e,t)=>{let i=this.db.transaction([ae],"readwrite").objectStore(ae).clear();i.onerror=()=>t(new R("Failed to clear persistent sessions",i.error)),i.onsuccess=()=>e()})}async cleanupExpired(){return this.db||await this.init(),new Promise((e,t)=>{let i=this.db.transaction([ae],"readwrite").objectStore(ae).index("expiresAt"),o=Date.now(),c=IDBKeyRange.upperBound(o),a=i.openCursor(c);a.onsuccess=u=>{let l=u.target.result;l?(l.delete(),l.continue()):e()},a.onerror=()=>t(new R("Failed to cleanup expired sessions",a.error))})}};async function jo(n,e,t){try{let r=await j(e,t);return await ie(n,r)}catch(r){throw new N("Failed to encrypt mnemonic for persistence",r)}}async function Bs(n,e,t){try{let r=await j(e,t);return await oe(n,r)}catch(r){throw new N("Failed to decrypt mnemonic from persistence",r)}}var nn=class{constructor(e=1,t){this.session=null;this.sessionDuration=e*60*60*1e3,this.persistentConfig={enabled:t?.enabled??!1,duration:t?.duration??168,requireReauth:t?.requireReauth??!0},this.persistentStorage=new rn}async startSession(e,t,r,s,i){let o=new Date(Date.now()+this.sessionDuration).toISOString();if(this.session={mnemonic:e,expiresAt:o,credentialId:t},this.persistentConfig.enabled&&i!=="STRICT"&&r&&s)try{let c=await jo(e,t,s),a=Date.now()+this.persistentConfig.duration*60*60*1e3;await this.persistentStorage.store({encryptedMnemonic:c,expiresAt:a,credentialId:t,ethereumAddress:r,securityMode:i||"STANDARD",createdAt:Date.now()})}catch(c){console.warn("[w3pk] Failed to persist session:",c)}}getMnemonic(){return this.session?new Date>new Date(this.session.expiresAt)?(this.clearSession(),null):this.session.mnemonic:null}getCredentialId(){return this.session?new Date>new Date(this.session.expiresAt)?(this.clearSession(),null):this.session.credentialId:null}isActive(){return this.getMnemonic()!==null}getRemainingTime(){return this.session?new Date>new Date(this.session.expiresAt)?(this.clearSession(),0):Math.floor((new Date(this.session.expiresAt).getTime()-Date.now())/1e3):0}extendSession(){if(!this.session)throw new Error("No active session to extend");if(new Date>new Date(this.session.expiresAt))throw this.clearSession(),new Error("Session expired, cannot extend");this.session.expiresAt=new Date(Date.now()+this.sessionDuration).toISOString()}async restoreFromPersistentStorage(e,t,r){if(!this.persistentConfig.enabled)return null;try{let s=await this.persistentStorage.retrieve(e);if(!s)return null;if(s.credentialId!==t)return console.warn("[w3pk] Credential ID mismatch, clearing persistent session"),await this.persistentStorage.delete(e),null;let i=await Bs(s.encryptedMnemonic,t,r),o=new Date(Date.now()+this.sessionDuration).toISOString();return this.session={mnemonic:i,expiresAt:o,credentialId:t},i}catch(s){console.warn("[w3pk] Failed to restore persistent session:",s);try{await this.persistentStorage.delete(e)}catch{}return null}}async attemptSilentRestore(){if(!this.persistentConfig.enabled||this.persistentConfig.requireReauth)return null;try{let{CredentialStorage:e}=await Promise.resolve().then(()=>(Te(),Jr)),r=await new e().getAllCredentials();if(r.length===0)return null;for(let s of r){let i=await this.persistentStorage.retrieve(s.ethereumAddress);if(!i)continue;if(i.credentialId!==s.id){console.warn("[w3pk] Credential ID mismatch, skipping this session");continue}let o=await Bs(i.encryptedMnemonic,s.id,s.publicKey),c=new Date(Date.now()+this.sessionDuration).toISOString();return this.session={mnemonic:o,expiresAt:c,credentialId:s.id},{mnemonic:o,ethereumAddress:s.ethereumAddress,credentialId:s.id,publicKey:s.publicKey}}return null}catch(e){return console.warn("[w3pk] Failed to attempt silent restore:",e),null}}async clearSession(){if(this.session&&(this.session.mnemonic="0".repeat(this.session.mnemonic.length)),this.session=null,this.persistentConfig.enabled)try{await this.persistentStorage.clear()}catch(e){console.warn("[w3pk] Failed to clear persistent sessions:",e)}}setSessionDuration(e){this.sessionDuration=e*60*60*1e3}};Te();var sn={debug:!1,sessionDuration:1,persistentSession:{enabled:!1,duration:168,requireReauth:!0},onError:n=>{sn.debug&&console.error("[w3pk]",n)}};Y();var Jo="https://chainid.network/chains.json";var ir=null,$d=[/\$\{[\w_]+\}/i,/\{[\w_]+\}/i,/<[\w_]+>/i,/YOUR[-_]?API[-_]?KEY/i,/INSERT[-_]?API[-_]?KEY/i,/API[-_]?KEY[-_]?HERE/i];function qd(n){return $d.some(e=>e.test(n))}async function Hd(n=Jo){let e=await fetch(n);if(!e.ok)throw new Error(`Failed to fetch chains data: ${e.status} ${e.statusText}`);return await e.json()}async function Ds(n){let e=n?.chainsJsonUrl??Jo,t=n?.cacheDuration??36e5,r=Date.now();if(ir&&r-ir.timestamp<t)return ir.data;let s=await Hd(e);return ir={data:s,timestamp:r},s}async function on(n,e){let r=(await Ds(e)).find(s=>s.chainId===n);return r?r.rpc.filter(s=>!qd(s)&&!s.startsWith("wss://")&&!s.startsWith("ws://")):[]}async function Qo(n){return Ds(n)}async function Xo(n,e){return(await Ds(e)).find(r=>r.chainId===n)}function Zo(){ir=null}Ts();cn();var Vd=new Set([1,10,8453,42161,57073,100,42220,137,42,15,40,41,44,46,47,50,51,56,61,71,82,83,95,97,112,123,130,146,151,153,171,180,183,185,195,215,228,247,248,252,261,267,291,293,311,332,336,395,401,416,466,480,488,510,545,634,647,648,747,831,919,938,945,957,964,970,980,995,997,1001,1003,1024,1030,1114,1125,1135,1149,1188,1284,1285,1287,1300,1301,1315,1337,1338,1339,1424,1514,1687,1727,1729,1740,1750,1829,1868,1946,1961,1962,1969,1989,1995,2017,2020,2031,2043,2109,2241,2340,2345,2440,2522,2559,2649,3068,3109,3338,3502,3799,3888,3889,4e3,4048,4078,4162,4201,4202,4460,4488,4661,4689,4690,4888,5e3,5003,5124,5234,5330,5424,5522,6283,6342,6398,6678,6806,6934,6942,6969,7117,7171,7200,7208,7368,7518,7668,7672,7744,7771,7869,7897,8008,8118,8217,8408,8700,8726,8727,8844,8880,8881,8882,8889,9372,9496,9700,9745,9746,9899,9990,9996,10011,10085,10143,10200,11221,11501,11504,11891,13370,14853,16602,16661,17e3,18880,18881,19991,21e3,21816,21912,25327,32323,33401,34443,41923,42170,43111,44787,47805,48898,48900,49049,49088,5e4,50312,53302,53456,53457,55244,56288,59141,60808,60850,62320,62850,64002,71402,72080,73114,73115,75338,78281,80002,80008,80069,80094,80451,80931,84532,88899,91342,92278,94524,96970,97476,97477,98985,100021,100501,101010,102030,102031,102032,112358,120893,121212,121213,121214,121215,129399,161803,175188,192940,193939,198989,212013,222222,240241,325e3,355110,355113,421614,555777,560048,656476,713715,743111,747474,763373,763375,777777,806582,808813,810180,839999,888991,2019775,2222222,4278608,5734951,6666689,6985385,7080969,7777777,9999999,11142220,11155111,11155420,11155931,16969696,19850818,20180427,20250825,28122024,34949059,37084624,52164803,61022448,79479957,96969696,420420421,420420422,888888888,974399131,999999999,1020352220,1273227453,1313161560,1350216234,1380996178,1417429182,1444673419,1482601649,1564830818,2046399126,11297108099,11297108109,88153591557,123420000220,123420001114]);async function Gd(n,e=1e4){try{let t=new AbortController,r=setTimeout(()=>t.abort(),e),s=await fetch(n,{method:"POST",headers:{"Content-Type":"application/json"},signal:t.signal,body:JSON.stringify({jsonrpc:"2.0",method:"eth_estimateGas",params:[{from:"0xdeadbeef00000000000000000000000000000000",to:"0xdeadbeef00000000000000000000000000000000",data:"0x0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000",value:"0x0"},"latest",{"0xdeadbeef00000000000000000000000000000000":{code:"0xef01000000000000000000000000000000000000000001"}}],id:1})});if(clearTimeout(r),!s.ok)return!1;let i=await s.json();if(i.error){let o=(i.error.message||"").toLowerCase();return!["unsupported","not supported","unknown","invalid","unrecognized","does not support","not implemented"].some(a=>o.includes(a))}return i.result!==void 0}catch{return!1}}async function ta(n,e,t){if(Vd.has(n))return!0;let r=t?.maxEndpoints||3,s=t?.timeout||1e4;try{let i=await e(n);if(i.length===0)return!1;let o=i.slice(0,r);for(let c of o)if(await Gd(c,s))return!0;return!1}catch{return!1}}function wc(n){return typeof n=="string"&&/^0x[0-9a-fA-F]*$/.test(n)}function bc(n){let e=n.startsWith("0x")?n.slice(2):n,t=new Uint8Array(e.match(/.{1,2}/g).map(r=>parseInt(r,16)));return new TextDecoder().decode(t)}var Et=class{constructor(e={}){this.currentUser=null;this.currentWallet=null;this.config={...sn,...e},this.walletStorage=new Xr;let t={...sn.persistentSession,...e.persistentSession};this.sessionManager=new nn(e.sessionDuration||1,t),e.stealthAddresses!==void 0&&(this.stealth=new yt(e.stealthAddresses,r=>this.getMnemonicFromSession(r)))}async loadZKModule(){if(this.zkModule)return this.zkModule;try{let e=new Function("path","return import(path)"),{ZKProofModule:t}=await e("w3pk/zk"),r=this.config.zkProofs||{};return this.zkModule=new t(r),this.zkModule}catch{throw new Error("ZK module not available. Install dependencies: npm install snarkjs circomlibjs")}}async getMnemonicFromSession(e=!1,t="STANDARD"){let r=t;if(!e){let h=this.sessionManager.getMnemonic();if(h)return h}if(!this.currentUser)throw new S("Must be authenticated. Call login() first.");let s=await this.walletStorage.retrieve(this.currentUser.ethereumAddress);if(!s)throw new S("No wallet found. Generate a wallet first.");if(!(await Qr()).user)throw new S("Authentication failed");let a=(await new F().getCredentialById(s.credentialId))?.publicKey,u=await j(s.credentialId,a),l=await oe(s.encryptedMnemonic,u);return await this.sessionManager.startSession(l,s.credentialId,this.currentUser.ethereumAddress,a,r),l}async register(e){try{this.currentWallet?.address||await this.generateWallet();let t=this.currentWallet.address,r=this.currentWallet.mnemonic;await zo({username:e.username,ethereumAddress:t});let i=await new F().getCredentialByAddress(t);if(this.currentUser={username:e.username,ethereumAddress:t,credentialId:i?.id||""},!i)throw new S("Credential not found after registration");let o=i.id,c=i.publicKey,a=await j(o,c),u=await ie(r,a);return await this.walletStorage.store({ethereumAddress:this.currentUser.ethereumAddress,encryptedMnemonic:u,credentialId:o,createdAt:new Date().toISOString()}),await this.sessionManager.startSession(r,o,t,c,"STANDARD"),this.currentWallet={address:t,mnemonic:r},this.config.onAuthStateChanged?.(!0,this.currentUser),{address:t,username:e.username}}catch(t){throw this.config.onError?.(t),t}}async login(){try{let e=await this.sessionManager.attemptSilentRestore();if(e){let l=await new F().getCredentialById(e.credentialId);return this.currentUser={username:l?.username||e.ethereumAddress,ethereumAddress:e.ethereumAddress,credentialId:e.credentialId},await this.walletStorage.retrieve(this.currentUser.ethereumAddress)?(this.config.onAuthStateChanged?.(!0,this.currentUser),this.currentUser):(await this.sessionManager.clearSession(),this.login())}let t=await Qr();if(!t.verified||!t.user)throw new O("Login failed");this.currentUser={username:t.user.username,ethereumAddress:t.user.ethereumAddress,credentialId:t.user.credentialId};let r=await this.walletStorage.retrieve(this.currentUser.ethereumAddress);if(!r)return this.config.onAuthStateChanged?.(!0,this.currentUser),this.currentUser;let o=(await new F().getCredentialById(r.credentialId))?.publicKey,c=await this.sessionManager.restoreFromPersistentStorage(this.currentUser.ethereumAddress,r.credentialId,o||""),a;if(c)a=c;else{let u=await j(r.credentialId,o);a=await oe(r.encryptedMnemonic,u),await this.sessionManager.startSession(a,r.credentialId,this.currentUser.ethereumAddress,o,"STANDARD")}return this.config.onAuthStateChanged?.(!0,this.currentUser),this.currentUser}catch(e){throw this.config.onError?.(e),e}}async logout(){this.currentUser=null,this.currentWallet=null,await this.sessionManager.clearSession(),this.config.onAuthStateChanged?.(!1,void 0)}get isAuthenticated(){return this.currentUser!==null}get user(){return this.currentUser}async listExistingCredentials(){try{return(await new F().getAllCredentials()).map(r=>({username:r.username,ethereumAddress:r.ethereumAddress,createdAt:r.createdAt,lastUsed:r.lastUsed}))}catch{return[]}}async hasExistingCredential(){return(await this.listExistingCredentials()).length>0}async getExistingCredentialCount(){return(await this.listExistingCredentials()).length}async generateWallet(){try{let e=er();return this.currentWallet={address:e.address,mnemonic:e.mnemonic},{address:e.address,mnemonic:e.mnemonic}}catch(e){throw this.config.onError?.(e),new S("Failed to generate wallet",e)}}async deriveWallet(e,t,r){try{if(!this.currentUser)throw new S("Must be authenticated to derive wallet");let s=e||fe,i=t||pe,o=r?.origin||Me();if(s==="PRIMARY"){let{CredentialStorage:l}=await Promise.resolve().then(()=>(Te(),Jr)),{deriveAddressFromP256PublicKey:h}=await Promise.resolve().then(()=>(gt(),en)),d=await new l().getCredentialById(this.currentUser.credentialId);if(!d||!d.publicKey)throw new S("No WebAuthn credential found for PRIMARY mode");return{address:await h(d.publicKey),origin:o,mode:s,tag:i,publicKey:d.publicKey}}let c=s==="STRICT"?!0:r?.requireAuth||!1,a=await this.getMnemonicFromSession(c,s),u=await Fe(a,o,s,i);return{address:u.address,privateKey:u.privateKey,index:u.index,origin:u.origin,mode:u.mode,tag:u.tag}}catch(s){throw this.config.onError?.(s),new S("Failed to derive wallet",s)}}async getAddress(e,t,r){try{if(!this.currentUser)throw new S("Must be authenticated to get address");let s=e||fe,i=t||pe,o=r?.origin||Me();if(s==="PRIMARY"){let{deriveAddressFromP256PublicKey:l}=await Promise.resolve().then(()=>(gt(),en)),g=await new F().getCredentialById(this.currentUser.credentialId);if(!g||!g.publicKey)throw new S("No WebAuthn credential found for PRIMARY mode");return await l(g.publicKey)}let c=s==="STRICT",a=await this.getMnemonicFromSession(c,s);return(await Fe(a,o,s,i)).address}catch(s){throw this.config.onError?.(s),new S("Failed to get address",s)}}async importMnemonic(e){try{if(!this.currentUser)throw new S("Must be authenticated to import mnemonic");if(!e||e.trim().split(/\s+/).length<12)throw new S("Invalid mnemonic: must be at least 12 words");let t=await Qr();if(!t.user)throw new S("Authentication failed");let r=t.user.credentialId,o=(await new F().getCredentialById(r))?.publicKey,c=await j(r,o),a=await ie(e.trim(),c);await this.walletStorage.store({ethereumAddress:this.currentUser.ethereumAddress,encryptedMnemonic:a,credentialId:r,createdAt:new Date().toISOString()}),this.currentWallet={address:this.currentUser.ethereumAddress,mnemonic:e.trim()},await this.sessionManager.startSession(e.trim(),r,this.currentUser.ethereumAddress,o,"STANDARD")}catch(t){throw this.config.onError?.(t),new S("Failed to import mnemonic",t)}}async signMessage(e,t){try{if(!this.currentUser)throw new S("Must be authenticated to sign message");let r=t?.mode||fe,s=t?.tag||pe,i=t?.origin||Me(),o=t?.signingMethod||"EIP191",c=r==="STRICT"?!0:t?.requireAuth||!1,a=await this.getMnemonicFromSession(c,r),u=await Fe(a,i,r,s),{Wallet:l}=await import("ethers"),h;if(u.privateKey)h=new l(u.privateKey);else{let{deriveWalletFromMnemonic:d}=await Promise.resolve().then(()=>(pt(),Cs)),{privateKey:f}=d(a,u.index);h=new l(f)}let g;switch(o){case"EIP191":case"SIWE":g=await h.signMessage(e);break;case"EIP712":if(!t?.eip712Domain||!t?.eip712Types||!t?.eip712PrimaryType)throw new S("EIP712 signing requires eip712Domain, eip712Types, and eip712PrimaryType in options");let d;try{d=typeof e=="string"?JSON.parse(e):e}catch{throw new S("EIP712 message must be valid JSON or an object")}g=await h.signTypedData(t.eip712Domain,t.eip712Types,d);break;case"rawHash":let{SigningKey:f}=await import("ethers"),y=e;if(y.startsWith("0x")&&(y=y.slice(2)),y.length!==64)throw new S("rawHash signing method requires a 32-byte hash (64 hex characters)");g=new f(h.privateKey).sign("0x"+y).serialized;break;default:throw new S(`Unsupported signing method: ${o}`)}return{signature:g,address:u.address,mode:u.mode,tag:u.tag,origin:u.origin}}catch(r){throw this.config.onError?.(r),new S("Failed to sign message",r)}}async signMessageWithPasskey(e){try{if(!this.currentUser)throw new S("Must be authenticated to sign message");let{extractRS:t}=await Promise.resolve().then(()=>(Ms(),ra)),{base64UrlDecode:r}=await Promise.resolve().then(()=>(xe(),As)),s=await crypto.subtle.digest("SHA-256",new TextEncoder().encode(e)),i="0x"+Buffer.from(s).toString("hex"),o=new Uint8Array(Buffer.from(i.slice(2),"hex")),c=this.currentUser.credentialId;if(!c)throw new S("Credential ID not found in user object");let a={challenge:o,rpId:window.location.hostname,allowCredentials:[{id:r(c),type:"public-key",transports:["internal","hybrid","usb","nfc","ble"]}],userVerification:"required",timeout:6e4},u=await navigator.credentials.get({publicKey:a});if(!u||!u.response)throw new S("WebAuthn signature failed");let l=u.response,h=new Uint8Array(l.authenticatorData),g=new Uint8Array(l.clientDataJSON),d=await crypto.subtle.digest("SHA-256",g),f=new Uint8Array(h.length+d.byteLength);f.set(h,0),f.set(new Uint8Array(d),h.length);let y=await crypto.subtle.digest("SHA-256",f.buffer),k="0x"+Buffer.from(y).toString("hex"),m=new Uint8Array(l.signature),{r:b,s:v}=t(m),{CredentialStorage:A}=await Promise.resolve().then(()=>(Te(),Jr)),C=await new A().getCredentialById(c);if(!C||!C.publicKey)throw new S("No WebAuthn credential found for PRIMARY mode");let{base64UrlToArrayBuffer:x}=await Promise.resolve().then(()=>(xe(),As)),P=x(C.publicKey),G=await crypto.subtle.importKey("spki",P,{name:"ECDSA",namedCurve:"P-256"},!0,["verify"]),he=await crypto.subtle.exportKey("jwk",G);if(!he.x||!he.y)throw new S("Invalid P-256 public key: missing x or y coordinates");let ut="0x"+Buffer.from(x(he.x)).toString("hex"),dt="0x"+Buffer.from(x(he.y)).toString("hex"),{deriveAddressFromP256PublicKey:I}=await Promise.resolve().then(()=>(gt(),en)),vd=await I(C.publicKey);return{signature:{r:b,s:v},messageHash:i,signedHash:k,address:vd,publicKey:{qx:ut,qy:dt}}}catch(t){throw this.config.onError?.(t),new S("Failed to sign message with passkey",t)}}async sendTransaction(e,t){try{if(!this.currentUser)throw new S("Must be authenticated to send transaction");let r=t?.mode||fe,s=t?.tag||pe,i=t?.origin||Me();if(r==="PRIMARY")throw t?.rpcUrl?new S("PRIMARY mode sendTransaction is not yet supported. Use signMessageWithPasskey() to obtain a P-256 signature and submit via a bundler manually."):new S("PRIMARY mode requires options.rpcUrl pointing to a bundler or sponsoring relayer. The P-256 address cannot pay gas directly without a deployed P-256-verifier contract via EIP-7702.");let o=r==="STRICT"?!0:t?.requireAuth||!1,c=await this.getMnemonicFromSession(o,r),a=await Fe(c,i,r,s),{Wallet:u,JsonRpcProvider:l}=await import("ethers"),h;if(a.privateKey)h=new u(a.privateKey);else{let{deriveWalletFromMnemonic:k}=await Promise.resolve().then(()=>(pt(),Cs)),{privateKey:m}=k(c,a.index);h=new u(m)}let g=t?.rpcUrl??(await this.getEndpoints(e.chainId))[0];if(!g)throw new S(`No RPC endpoint found for chainId ${e.chainId}. Pass options.rpcUrl.`);let d=new l(g);return{hash:(await h.connect(d).sendTransaction({to:e.to,value:e.value,data:e.data??"0x",chainId:e.chainId,gasLimit:e.gasLimit,maxFeePerGas:e.maxFeePerGas,maxPriorityFeePerGas:e.maxPriorityFeePerGas,nonce:e.nonce})).hash,from:a.address,chainId:e.chainId,mode:a.mode,tag:a.tag,origin:a.origin}}catch(r){throw this.config.onError?.(r),new S("Failed to send transaction",r)}}async signAuthorization(e,t){try{if(!this.currentUser)throw new S("Must be authenticated to sign authorization");let{Wallet:r,Signature:s}=await import("ethers"),{hashEIP7702AuthorizationMessage:i,verifyEIP7702Authorization:o}=await Promise.resolve().then(()=>(cn(),Rs)),c;if(e.privateKey)c=new r(e.privateKey);else{let y=await this.getMnemonicFromSession(t?.requireAuth);c=r.fromPhrase(y)}let a=BigInt(e.chainId||1),u=e.nonce||0n,l=i(a,e.contractAddress,u),h=c.signingKey.sign(l),g=s.from(h),d={chainId:a,address:e.contractAddress.toLowerCase(),nonce:u,yParity:g.yParity,r:g.r,s:g.s};if(!o(a,e.contractAddress,u,d,c.address))throw new S("Signature verification failed - this should not happen");return d}catch(r){throw this.config.onError?.(r),new S("Failed to sign authorization",r)}}async getEndpoints(e){return on(e)}async supportsEIP7702(e,t){return ta(e,this.getEndpoints.bind(this),t)}getEIP1193Provider(e){let t=e?.chainId??1,r=this,s={},i=(c,...a)=>{(s[c]??[]).forEach(u=>u(...a))};return{async request({method:c,params:a}){switch(c){case"eth_accounts":case"eth_requestAccounts":return[await r.getAddress(e?.mode??"STANDARD",e?.tag??"MAIN")];case"eth_chainId":return"0x"+t.toString(16);case"eth_sendTransaction":{let u=(a??[])[0]??{};if(!u.chainId&&!t)throw new S("eth_sendTransaction: chainId is required");let l=u.chainId?parseInt(u.chainId,16):t;return(await r.sendTransaction({to:u.to,value:u.value!==void 0?BigInt(u.value):void 0,data:u.data??"0x",chainId:l,gasLimit:u.gas!==void 0?BigInt(u.gas):void 0,maxFeePerGas:u.maxFeePerGas!==void 0?BigInt(u.maxFeePerGas):void 0,maxPriorityFeePerGas:u.maxPriorityFeePerGas!==void 0?BigInt(u.maxPriorityFeePerGas):void 0,nonce:u.nonce!==void 0?parseInt(u.nonce,16):void 0},{mode:e?.mode,tag:e?.tag,rpcUrl:e?.rpcUrl})).hash}case"personal_sign":{let[u]=a??[],l=wc(u)?bc(u):u;return(await r.signMessage(l,{mode:e?.mode,tag:e?.tag,signingMethod:"EIP191"})).signature}case"eth_sign":{let[,u]=a??[],l=wc(u)?bc(u):u;return(await r.signMessage(l,{mode:e?.mode,tag:e?.tag,signingMethod:"EIP191"})).signature}case"eth_signTypedData_v4":{let[,u]=a??[],l=typeof u=="string"?JSON.parse(u):u,{domain:h,types:g,message:d,primaryType:f}=l,y={...g};return delete y.EIP712Domain,(await r.signMessage(JSON.stringify(d),{mode:e?.mode,tag:e?.tag,signingMethod:"EIP712",eip712Domain:h,eip712Types:y,eip712PrimaryType:f})).signature}case"wallet_switchEthereumChain":{let u=parseInt((a??[])[0]?.chainId??"0x1",16);return t=u,i("chainChanged","0x"+u.toString(16)),null}default:throw new S(`w3pk EIP-1193: unsupported method "${c}"`)}},on(c,a){s[c]||(s[c]=[]),s[c].push(a)},removeListener(c,a){s[c]&&(s[c]=s[c].filter(u=>u!==a))}}}async requestExternalWalletDelegation(e){if(!this.currentUser)throw new S("Must be authenticated to get w3pk delegation address. Call login() or register() first.");let{requestExternalWalletAuthorization:t,getDefaultProvider:r}=await Promise.resolve().then(()=>(Ts(),ea)),s=e?.provider||r();if(!s)throw new S("No external wallet provider found. Please install MetaMask, Rabby, or similar wallet.");let i=this.currentUser.ethereumAddress;return t(s,{delegateToAddress:i,chainId:e?.chainId,nonce:e?.nonce,accountIndex:e?.accountIndex})}get zk(){return new Proxy({},{get:(e,t)=>async(...r)=>(await this.loadZKModule())[t](...r)})}async getBackupStatus(){if(!this.currentUser)throw new S("Must be authenticated to check backup status");let{BackupManager:e}=await Promise.resolve().then(()=>(tt(),et));return new e().getBackupStatus(this.currentUser.ethereumAddress)}async createBackupFile(e="password",t){if(!this.currentUser)throw new S("Must be authenticated to create backup");let r=await this.getMnemonicFromSession(!0),{BackupFileManager:s}=await Promise.resolve().then(()=>(le(),ge)),{BackupStorage:i}=await Promise.resolve().then(()=>(fn(),na)),o=new s,c=new i,a,u;if(e==="password"){if(!t)throw new S("Password required for password-based backup");u=(await o.createPasswordBackup(r,this.currentUser.ethereumAddress,t)).backupFile,a=o.createDownloadableBackup(u)}else if(e==="passkey"){let l=await this.walletStorage.retrieve(this.currentUser.ethereumAddress);if(!l)throw new S("No wallet data found");let g=await new F().getCredentialById(l.credentialId);if(!g)throw new S("Credential not found");u=(await o.createPasskeyBackup(r,this.currentUser.ethereumAddress,g.id,g.publicKey)).backupFile,a=o.createDownloadableBackup(u)}else if(e==="hybrid"){if(!t)throw new S("Password required for hybrid backup");let l=await this.walletStorage.retrieve(this.currentUser.ethereumAddress);if(!l)throw new S("No wallet data found");let g=await new F().getCredentialById(l.credentialId);if(!g)throw new S("Credential not found");u=(await o.createHybridBackup(r,this.currentUser.ethereumAddress,t,g.id,g.publicKey)).backupFile,a=o.createDownloadableBackup(u)}else throw new S(`Unknown encryption type: ${e}`);return await c.storeBackupMetadata({id:crypto.randomUUID(),ethereumAddress:this.currentUser.ethereumAddress,method:"file",createdAt:new Date().toISOString(),addressChecksum:u.addressChecksum}),a}async setupSocialRecovery(e,t,r){if(!this.currentUser)throw new S("Must be authenticated to set up social recovery");let s=await this.getMnemonicFromSession(!0),{BackupFileManager:i}=await Promise.resolve().then(()=>(le(),ge)),o=new i,c;if(r)c=(await o.createPasswordBackup(s,this.currentUser.ethereumAddress,r)).backupFile;else{let h=await this.walletStorage.retrieve(this.currentUser.ethereumAddress);if(!h)throw new S("No wallet data found");let d=await new F().getCredentialById(h.credentialId);if(!d)throw new S("Credential not found");c=(await o.createPasskeyBackup(s,this.currentUser.ethereumAddress,d.id,d.publicKey)).backupFile}let{SocialRecovery:a}=await Promise.resolve().then(()=>(Un(),Nn));return{guardianShares:(await new a().splitAmongGuardians(c,e,t)).guardianShares,setupComplete:!0}}async generateGuardianInvite(e,t){let{SocialRecovery:r}=await Promise.resolve().then(()=>(Un(),Nn)),s=new r,i=await s.createGuardianInvitation(e,t),o=s.createShareDownload(e);return{qrCodeDataURL:i.qrCodeDataURL,shareDocument:i.shareDocument,downloadBlob:o.blob,filename:o.filename}}async recoverFromGuardians(e,t){let{SocialRecovery:r}=await Promise.resolve().then(()=>(Un(),Nn)),{BackupFileManager:s}=await Promise.resolve().then(()=>(le(),ge)),{BackupManager:i}=await Promise.resolve().then(()=>(tt(),et)),o=new r,c=new s,a=new i,u=e.map(g=>typeof g=="string"?o.parseGuardianShare(g):g),l=await o.recoverFromShares(u),h;if(l.encryptionMethod==="password"){if(!t)throw new S("Password required to decrypt password-protected backup");h=await c.restoreWithPassword(l,t)}else throw new S("Passkey-encrypted backups not supported for guardian recovery. Use password-protected backups.");return a.markBackupVerified(h.ethereumAddress),h}async restoreFromBackupFile(e,t){let{BackupFileManager:r}=await Promise.resolve().then(()=>(le(),ge)),{BackupManager:s}=await Promise.resolve().then(()=>(tt(),et)),i=new r,o=new s,c=await i.parseBackupFile(e),a,u;if(c.encryptionMethod==="password"){if(!t)throw new S("Password required to restore password-encrypted backup");let l=await i.restoreWithPassword(c,t);a=l.mnemonic,u=l.ethereumAddress}else if(c.encryptionMethod==="passkey"){if(!this.currentUser)throw new S("Must be logged in with passkey to restore passkey-encrypted backup. Call login() first.");let g=(await new F().getAllCredentials()).find(f=>f.ethereumAddress.toLowerCase()===this.currentUser.ethereumAddress.toLowerCase());if(!g)throw new S("Credential not found for current user");let d=await i.restoreWithExistingPasskey(c,g.id,g.publicKey);a=d.mnemonic,u=d.ethereumAddress}else if(c.encryptionMethod==="hybrid"){if(!t)throw new S("Password required to restore hybrid backup");if(!this.currentUser)throw new S("Must be logged in with passkey to restore hybrid backup. Call login() first.");let g=(await new F().getAllCredentials()).find(f=>f.ethereumAddress.toLowerCase()===this.currentUser.ethereumAddress.toLowerCase());if(!g)throw new S("Credential not found for current user");let d=await i.restoreWithHybrid(c,t,g.id,g.publicKey);a=d.mnemonic,u=d.ethereumAddress}else throw new S(`Unknown encryption method: ${c.encryptionMethod}`);if(o.markBackupVerified(u),this.currentWallet={address:u,mnemonic:a},this.currentUser){let l=new F,g=(await l.getAllCredentials()).find(d=>d.ethereumAddress.toLowerCase()===this.currentUser.ethereumAddress.toLowerCase());if(g){let d=this.currentUser.ethereumAddress;d.toLowerCase()!==u.toLowerCase()&&await this.walletStorage.delete(d),await l.updateCredentialAddress(g.id,u);let f=await(await Promise.resolve().then(()=>(q(),Re))).deriveEncryptionKeyFromWebAuthn(g.id,g.publicKey),y=await(await Promise.resolve().then(()=>(q(),Re))).encryptData(a,f);await this.walletStorage.store({ethereumAddress:u,encryptedMnemonic:y,credentialId:g.id,createdAt:new Date().toISOString()}),this.currentUser={...this.currentUser,ethereumAddress:u},await this.sessionManager.startSession(a,g.id,u,g.publicKey,"STANDARD"),this.config.onAuthStateChanged?.(!0,this.currentUser)}}return{mnemonic:a,ethereumAddress:u}}async syncWalletWithPasskey(e,t){let{BackupFileManager:r}=await Promise.resolve().then(()=>(le(),ge)),{BackupManager:s}=await Promise.resolve().then(()=>(tt(),et)),{promptPasskeySelection:i}=await Promise.resolve().then(()=>(ui(),lc)),o=new r,c=new s,a=await i(),u=await o.parseBackupFile(e),l,h;if(u.encryptionMethod==="password"){if(!t)throw new S("Password required to restore password-encrypted backup");let f=await o.restoreWithPassword(u,t);l=f.mnemonic,h=f.ethereumAddress}else if(u.encryptionMethod==="passkey"){if(!a.publicKey)throw new S("Passkey public key not found. The passkey may not be registered on this device yet.");let f=await o.restoreWithExistingPasskey(u,a.credentialId,a.publicKey);l=f.mnemonic,h=f.ethereumAddress}else if(u.encryptionMethod==="hybrid"){if(!t)throw new S("Password required to restore hybrid backup");if(!a.publicKey)throw new S("Passkey public key not found. The passkey may not be registered on this device yet.");let f=await o.restoreWithHybrid(u,t,a.credentialId,a.publicKey);l=f.mnemonic,h=f.ethereumAddress}else throw new S(`Unknown encryption method: ${u.encryptionMethod}`);c.markBackupVerified(h);let d=await new F().getCredentialById(a.credentialId);if(d){let{deriveEncryptionKeyFromWebAuthn:f,encryptData:y}=await Promise.resolve().then(()=>(q(),Re)),k=await f(d.id,d.publicKey),m=await y(l,k);await this.walletStorage.store({ethereumAddress:h,encryptedMnemonic:m,credentialId:d.id,createdAt:new Date().toISOString()}),this.currentUser={username:d.username,ethereumAddress:h,credentialId:d.id},await this.sessionManager.startSession(l,d.id,h,d.publicKey,"STANDARD"),this.config.onAuthStateChanged?.(!0,this.currentUser)}return{mnemonic:l,ethereumAddress:h}}async registerWithBackupFile(e,t,r){let{BackupFileManager:s}=await Promise.resolve().then(()=>(le(),ge)),{BackupManager:i}=await Promise.resolve().then(()=>(tt(),et)),o=new s,c=new i,a=await o.parseBackupFile(e);if(a.encryptionMethod!=="password")throw new S("Can only register with password-encrypted backups. Use restoreFromBackupFile() for passkey-encrypted backups.");let{mnemonic:u,ethereumAddress:l}=await o.restoreWithPassword(a,t),{Wallet:h}=await import("ethers");if(h.fromPhrase(u).address.toLowerCase()!==l.toLowerCase())throw new S("Backup verification failed: address mismatch");return c.markBackupVerified(l),this.currentWallet={address:l,mnemonic:u},this.register({username:r})}async getSyncStatus(){let{DeviceSyncManager:e}=await Promise.resolve().then(()=>(xr(),Ln));return new e().getSyncInfo()}async exportForSync(){if(!this.currentUser)throw new S("Must be authenticated to export for sync");let e=await this.getMnemonicFromSession(!0),t=await this.walletStorage.retrieve(this.currentUser.ethereumAddress);if(!t)throw new S("No wallet data found");let s=await new F().getCredentialById(t.credentialId);if(!s)throw new S("Credential not found");let{DeviceSyncManager:i}=await Promise.resolve().then(()=>(xr(),Ln)),o=new i,{backupFile:c,blob:a}=await o.exportForSync(e,this.currentUser.ethereumAddress,s.id,s.publicKey),u=`w3pk-sync-${this.currentUser.ethereumAddress.substring(0,8)}.json`,l;try{l=await o.generateSyncQR(c)}catch(h){console.warn("QR code generation failed:",h)}return{blob:a,filename:u,qrCode:l}}async importFromSync(e){if(!this.currentUser)throw new S("Must be logged in to import from sync. Call login() first.");let{DeviceSyncManager:t}=await Promise.resolve().then(()=>(xr(),Ln)),{BackupFileManager:r}=await Promise.resolve().then(()=>(le(),ge)),{BackupManager:s}=await Promise.resolve().then(()=>(tt(),et)),i=new r,o=new t,c=new s,a=await i.parseBackupFile(e),u=await this.walletStorage.retrieve(this.currentUser.ethereumAddress);if(!u)throw new S("No wallet data found for current user");let h=await new F().getCredentialById(u.credentialId);if(!h)throw new S("Credential not found");let{mnemonic:g,ethereumAddress:d}=await o.importFromSync(a,h.id,h.publicKey);c.markBackupVerified(d);let f=await(await Promise.resolve().then(()=>(q(),Re))).deriveEncryptionKeyFromWebAuthn(h.id,h.publicKey),y=await(await Promise.resolve().then(()=>(q(),Re))).encryptData(g,f);return await this.walletStorage.store({ethereumAddress:d,encryptedMnemonic:y,credentialId:h.id,createdAt:new Date().toISOString()}),{ethereumAddress:d,success:!0}}async detectSyncCapabilities(){let{PlatformDetector:e}=await Promise.resolve().then(()=>(gc(),pc));return new e().detectSyncCapabilities()}async simulateRecoveryScenario(e){if(!this.currentUser)throw new S("Must be authenticated to run recovery simulation");let t=await this.getBackupStatus(),{RecoverySimulator:r}=await Promise.resolve().then(()=>(vr(),Wn));return new r().simulateScenario(e,t)}async runRecoveryTest(){if(!this.currentUser)throw new S("Must be authenticated to run recovery test");let e=await this.getBackupStatus(),{RecoverySimulator:t}=await Promise.resolve().then(()=>(vr(),Wn));return new t().runInteractiveTest(e)}async getEducation(e){let{getExplainer:t}=await Promise.resolve().then(()=>(vr(),Wn)),r=t(e);if(!r)throw new S(`Unknown education topic: ${e}`);return r}hasActiveSession(){return this.sessionManager.isActive()}getSessionRemainingTime(){return this.sessionManager.getRemainingTime()}extendSession(){try{this.sessionManager.extendSession()}catch(e){throw new S("Cannot extend session",e)}}async clearSession(){await this.sessionManager.clearSession()}setSessionDuration(e){this.sessionManager.setSessionDuration(e)}};Y();ui();gt();vr();async function Rg(n,e="build"){let{importer:t}=await Promise.resolve().then(()=>(Wu(),zu)),{MemoryBlockstore:r}=await Promise.resolve().then(()=>(fd(),hd)),s=new r,o=t(async function*(){yield{path:e,content:n}}(),s,{cidVersion:1,rawLeaves:!0,wrapWithDirectory:!1});for await(let c of o)return c.cid.toString();throw new Error("Failed to generate CID")}async function Tg(n){let e=["index.js","index.mjs","index.d.ts"],t=[],r=0;for(let o of e){let c=`${n}/${o}`,a=await fetch(c);if(!a.ok)throw new Error(`Failed to fetch ${o}: ${a.statusText}`);let u=await a.arrayBuffer(),l=new Uint8Array(u);t.push(l),r+=l.length}let s=new Uint8Array(r),i=0;for(let o of t)s.set(o,i),i+=o.length;return s}async function To(n){let e=await Tg(n);return Rg(e)}function Fo(){try{return pd().version}catch{throw new Error("Failed to read package version")}}async function Mo(){let n=Fo();return To(`https://unpkg.com/w3pk@${n}/dist`)}async function gd(n){return await Mo()===n}xe();Ms();pt();function md(n=11){let e="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789",t=new Uint8Array(n);return crypto.getRandomValues(t),Array.from(t).map(r=>e[r%e.length]).join("")}function yd(n){if(!n.domain||!n.address||!n.uri||!n.version||n.chainId===void 0||!n.nonce||!n.issuedAt)throw new Error("Missing required SIWE message fields");if(n.version!=="1")throw new Error('SIWE version must be "1"');if(n.nonce.length<8||!/^[a-zA-Z0-9]+$/.test(n.nonce))throw new Error("Nonce must be at least 8 alphanumeric characters");if(n.statement&&n.statement.includes(`
958
958
  `))throw new Error("Statement cannot contain newlines");let e=`${n.domain} wants you to sign in with your Ethereum account:
959
959
  `;if(e+=`${n.address}
960
960
  `,e+=`