{"version":3,"sources":["../src/base/index.ts","../src/browser/index.ts","../src/node/index.ts","../src/wallet-factory.ts"],"names":["WalletError","SignatureImpl","TransactionBuilder","cryptoProvider","isValidAddress","hexEncode","encryptToKeystore","mnemonicToKey"],"mappings":"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","file":"index.mjs","sourcesContent":["import { WalletError, isValidAddress } from '@klever/connect-core'\nimport type { KleverAddress } from '@klever/connect-core'\nimport type {\n  TransactionSubmitResult,\n  IProvider,\n  TransferRequest,\n  ContractRequestData,\n} from '@klever/connect-provider'\nimport type { Transaction } from '@klever/connect-transactions'\nimport { TransactionBuilder } from '@klever/connect-transactions'\nimport { verifySignature, SignatureImpl } from '@klever/connect-crypto'\nimport type { Signature } from '@klever/connect-crypto'\nimport { hexDecode } from '@klever/connect-encoding'\n\nimport type { Wallet, WalletEvent, WalletEventHandler } from '../types'\nimport type { TransactionHash } from '@klever/connect-core'\n\n/**\n * Abstract base wallet implementation providing common functionality\n *\n * BaseWallet implements the core wallet interface and provides shared functionality\n * for all wallet types. It handles:\n * - Provider management\n * - Event system (connect, disconnect, accountChanged)\n * - Balance and nonce queries\n * - Transaction broadcasting\n * - Message verification\n *\n * **Design Pattern:**\n * This class follows the Template Method pattern, where concrete implementations\n * (NodeWallet, BrowserWallet) provide specific implementations for:\n * - connect() - How to establish wallet connection\n * - disconnect() - How to clean up connection\n * - signMessage() - How to sign arbitrary messages\n * - signTransaction() - How to sign blockchain transactions\n *\n * **Common Functionality:**\n * All wallets inherit these capabilities:\n * - getBalance() - Query wallet balance\n * - getNonce() - Get transaction nonce\n * - verifyMessage() - Verify message signatures\n * - broadcastTransaction() - Send signed transactions to blockchain\n * - Event handling (on/off/emit)\n *\n * **Do Not Instantiate Directly:**\n * This is an abstract class. Use concrete implementations:\n * - NodeWallet for server-side Node.js applications\n * - BrowserWallet for browser/dApp applications\n *\n * @example\n * ```typescript\n * // Don't do this (abstract class):\n * // const wallet = new BaseWallet(provider) // ❌ Error\n *\n * // Do this instead:\n * import { NodeWallet } from '@klever/connect-wallet'\n * const wallet = new NodeWallet(provider, privateKey) // ✅ Correct\n * ```\n */\nexport abstract class BaseWallet implements Wallet {\n  protected _provider: IProvider\n  protected _address: string = ''\n  protected _publicKey: string = ''\n  protected _connected: boolean = false\n  protected _events: Map<WalletEvent, Set<WalletEventHandler>> = new Map()\n\n  constructor(provider: IProvider) {\n    this._provider = provider\n  }\n\n  /** Wallet address (bech32 format) */\n  get address(): string {\n    return this._address\n  }\n\n  /** Public key (hex format) */\n  get publicKey(): string {\n    return this._publicKey\n  }\n\n  /** Provider instance for blockchain queries */\n  get provider(): IProvider {\n    return this._provider\n  }\n\n  /** Connect to the wallet */\n  abstract connect(): Promise<void>\n\n  /** Disconnect from the wallet */\n  abstract disconnect(clearPrivateKey?: boolean): Promise<void>\n\n  /** Sign a message with the wallet's private key */\n  abstract signMessage(message: string | Uint8Array): Promise<Signature>\n\n  /** Sign a transaction with the wallet's private key */\n  abstract signTransaction(unsignedTx: Transaction): Promise<Transaction>\n\n  /**\n   * Verify a message signature\n   * @param message - The message that was signed (string or bytes)\n   * @param signature - The signature to verify (Signature object, hex string, or base64 string)\n   * @returns true if signature is valid, false otherwise\n   *\n   * @example\n   * ```typescript\n   * const message = \"Hello, Klever!\"\n   * const signature = await wallet.signMessage(message)\n   *\n   * // Verify with Signature object\n   * const isValid = await wallet.verifyMessage(message, signature)\n   *\n   * // Or verify with hex string\n   * const isValidHex = await wallet.verifyMessage(message, signature.toHex())\n   *\n   * // Or verify with base64 string\n   * const isValidBase64 = await wallet.verifyMessage(message, signature.toBase64())\n   * console.log('Signature valid:', isValid)\n   * ```\n   */\n  async verifyMessage(\n    message: string | Uint8Array,\n    signature: Signature | string,\n  ): Promise<boolean> {\n    if (!this._publicKey) {\n      throw new WalletError('Wallet not connected or public key not available')\n    }\n\n    try {\n      const messageBytes = typeof message === 'string' ? new TextEncoder().encode(message) : message\n\n      // Handle Signature object or string (hex/base64)\n      let signatureBytes: Uint8Array\n      if (typeof signature === 'string') {\n        // Try hex first, fallback to base64\n        try {\n          signatureBytes = hexDecode(signature)\n        } catch {\n          // If hex fails, try base64\n          signatureBytes = SignatureImpl.fromBase64(signature).bytes\n        }\n      } else {\n        signatureBytes = signature.bytes\n      }\n\n      const publicKeyBytes = hexDecode(this._publicKey)\n\n      return await verifySignature(messageBytes, signatureBytes, publicKeyBytes)\n    } catch {\n      // If there's any error (invalid format, etc.), return false\n      return false\n    }\n  }\n\n  /**\n   * Check if wallet is connected\n   * @returns true if connected, false otherwise\n   */\n  isConnected(): boolean {\n    return this._connected\n  }\n\n  /**\n   * Get wallet balance\n   * @returns Balance in smallest units (KLV has 6 decimals)\n   */\n  async getBalance(): Promise<bigint> {\n    if (!this._connected || !this._address) {\n      throw new WalletError('Wallet not connected')\n    }\n\n    if (!isValidAddress(this._address)) {\n      throw new WalletError('Invalid wallet address')\n    }\n\n    const account = await this._provider.getAccount(this._address as KleverAddress)\n    return account.balance\n  }\n\n  /**\n   * Get current nonce for the wallet\n   * Used for transaction ordering\n   * @returns Current nonce value\n   */\n  async getNonce(): Promise<number> {\n    if (!this._connected || !this._address) {\n      throw new WalletError('Wallet not connected')\n    }\n\n    if (!isValidAddress(this._address)) {\n      throw new WalletError('Invalid wallet address')\n    }\n\n    const account = await this._provider.getAccount(this._address as KleverAddress)\n    return account.nonce\n  }\n\n  /**\n   * Broadcast a single signed transaction to the network\n   * Default implementation uses the provider's sendRawTransaction method\n   * Can be overridden by child classes for custom behavior (e.g., extension broadcasting)\n   */\n  async broadcastTransaction(tx: Transaction): Promise<TransactionHash> {\n    if (!this._connected) {\n      throw new WalletError('Wallet not connected')\n    }\n\n    if (!tx.isSigned()) {\n      throw new WalletError('Transaction must be signed before broadcasting')\n    }\n\n    return this._provider.sendRawTransaction(tx.toJSON())\n  }\n\n  /**\n   * Broadcast multiple signed transactions to the network in a single batch\n   * Default implementation uses the provider's sendRawTransactions method\n   * Can be overridden by child classes for custom behavior (e.g., extension broadcasting)\n   */\n  async broadcastTransactions(txs: Transaction[]): Promise<TransactionHash[]> {\n    if (!this._connected) {\n      throw new WalletError('Wallet not connected')\n    }\n\n    const submit = txs.map((tx) => {\n      if (!tx.isSigned()) {\n        throw new WalletError('All transactions must be signed before broadcasting')\n      }\n      return tx.toJSON()\n    })\n\n    return this._provider.sendRawTransactions(submit)\n  }\n\n  /**\n   * Send a transaction with any contract type\n   * Builds, signs, and broadcasts the transaction\n   * Can be overridden by child classes (e.g., BrowserWallet uses extension)\n   */\n  async sendTransaction(contract: ContractRequestData): Promise<TransactionSubmitResult> {\n    if (!this._connected) {\n      throw new WalletError('Wallet not connected')\n    }\n\n    try {\n      // Build transaction using TransactionBuilder\n      const builder = new TransactionBuilder(this._provider)\n      builder.addContract(contract).sender(this._address)\n\n      const unsignedTx = await builder.build()\n\n      // Sign transaction\n      const signedTx = await this.signTransaction(unsignedTx)\n\n      // Broadcast transaction\n      const hash = await this.broadcastTransaction(signedTx)\n\n      // Return standardized result\n      return {\n        hash,\n        status: 'pending',\n      }\n    } catch (error) {\n      throw new WalletError(\n        `Failed to send transaction: ${error instanceof Error ? error.message : 'Unknown error'}`,\n      )\n    }\n  }\n\n  /**\n   * Transfer tokens to another address\n   * Convenience method that uses sendTransaction internally\n   */\n  async transfer(params: TransferRequest): Promise<TransactionSubmitResult> {\n    if (!this._connected) {\n      throw new WalletError('Wallet not connected')\n    }\n\n    try {\n      // Build transaction using TransactionBuilder\n      const builder = new TransactionBuilder(this._provider)\n      builder.transfer(params).sender(this._address)\n\n      const unsignedTx = await builder.build()\n\n      // Sign transaction\n      const signedTx = await this.signTransaction(unsignedTx)\n\n      // Broadcast transaction\n      const hash = await this.broadcastTransaction(signedTx)\n\n      // Return standardized result\n      return {\n        hash,\n        status: 'pending',\n      }\n    } catch (error) {\n      throw new WalletError(\n        `Failed to transfer: ${error instanceof Error ? error.message : 'Unknown error'}`,\n      )\n    }\n  }\n\n  /**\n   * Register an event handler\n   * @param event - Event name ('connect', 'disconnect', 'accountChanged')\n   * @param handler - Event handler function\n   */\n  on(event: WalletEvent, handler: WalletEventHandler): void {\n    const handlers = this._events.get(event) ?? new Set()\n    handlers.add(handler)\n    this._events.set(event, handlers)\n  }\n\n  /**\n   * Unregister an event handler\n   * @param event - Event name\n   * @param handler - Event handler function to remove\n   */\n  off(event: WalletEvent, handler: WalletEventHandler): void {\n    const handlers = this._events.get(event)\n    if (handlers) {\n      handlers.delete(handler)\n    }\n  }\n\n  /**\n   * Remove all event listeners for a specific event or all events\n   * @param event - Optional event name. If not provided, removes all listeners for all events\n   */\n  removeAllListeners(event?: WalletEvent): void {\n    if (event) {\n      this._events.delete(event)\n    } else {\n      this._events.clear()\n    }\n  }\n\n  protected emit(event: WalletEvent, data?: unknown): void {\n    const handlers = this._events.get(event)\n    if (handlers) {\n      handlers.forEach((handler) => handler(data))\n    }\n  }\n}\n","import { isBrowser, TXType, WalletError } from '@klever/connect-core'\nimport type { KleverAddress, TransactionHash } from '@klever/connect-core'\nimport type {\n  ContractRequestData,\n  TransferRequest,\n  TransactionSubmitResult,\n  IProvider,\n  NetworkURI,\n} from '@klever/connect-provider'\nimport { Transaction } from '@klever/connect-transactions'\nimport type { PrivateKey, Signature } from '@klever/connect-crypto'\nimport {\n  cryptoProvider,\n  SignatureImpl,\n  encryptToKeystore,\n  type EncryptOptions,\n  type Keystore,\n} from '@klever/connect-crypto'\nimport { hexEncode, base64Encode } from '@klever/connect-encoding'\nimport type { KleverWeb, KleverHub, IContractRequest } from '../types/browser-types'\nimport type { WalletConfig } from '../types/wallet'\nimport { BaseWallet } from '../base'\n\n// Ensure window is typed (browser environment only - this file should only run in browser)\ndeclare const window: Window & typeof globalThis\n\n/**\n * Wallet implementation for browser environments\n *\n * BrowserWallet supports two modes of operation:\n *\n * **1. Extension Mode (Default):**\n * - Integrates with the Klever Browser Extension\n * - Users sign transactions through the extension UI\n * - Most secure for dApps - private keys never leave the extension\n * - Supports account switching and network changes\n * - Requires Klever Extension to be installed\n *\n * **2. Private Key Mode:**\n * - Direct signing using a private key (like NodeWallet)\n * - Useful for testing or non-extension wallets\n * - Can also use PEM files with optional password protection\n * - Less secure - private keys are in browser memory\n *\n * **Security Considerations:**\n * - Extension mode is recommended for production dApps\n * - Private key mode should only be used for testing or trusted environments\n * - Never expose private keys in production code\n * - Always validate transaction details before signing\n *\n * **Event Handling:**\n * - Emits 'accountChanged' when user switches accounts in extension\n * - Emits 'disconnect' when user switches to a different blockchain\n * - Events are debounced to prevent rapid firing\n *\n * @example\n * ```typescript\n * // Extension mode (recommended for dApps)\n * import { BrowserWallet } from '@klever/connect-wallet'\n * import { KleverProvider } from '@klever/connect-provider'\n *\n * const provider = new KleverProvider({ network: 'mainnet' })\n * const wallet = new BrowserWallet(provider)\n *\n * try {\n *   await wallet.connect()\n *   console.log('Connected:', wallet.address)\n *\n *   // Listen for account changes\n *   wallet.on('accountChanged', ({ address }) => {\n *     console.log('Account changed to:', address)\n *   })\n *\n *   // Send a transaction (extension will prompt user)\n *   const result = await wallet.transfer({\n *     receiver: 'klv1...',\n *     amount: 1000000,\n *   })\n *   console.log('Transaction hash:', result.hash)\n * } catch (error) {\n *   if (error.message.includes('Extension not found')) {\n *     console.log('Please install Klever Extension')\n *   }\n * }\n * ```\n *\n * @example\n * ```typescript\n * // Private key mode (testing only)\n * const wallet = new BrowserWallet(provider, {\n *   privateKey: '0x123...',\n * })\n * await wallet.connect() // No extension needed\n * ```\n *\n * @example\n * ```typescript\n * // PEM file mode with password\n * const pemContent = '-----BEGIN PRIVATE KEY-----...'\n * const wallet = new BrowserWallet(provider, {\n *   pemContent,\n *   pemPassword: 'my-secure-password',\n * })\n * await wallet.connect()\n * ```\n */\nexport class BrowserWallet extends BaseWallet {\n  private _kleverWeb?: KleverWeb\n  private _kleverHub?: KleverHub\n  private _privateKey?: PrivateKey | undefined\n  private _mode: 'extension' | 'privateKey' = 'extension'\n  private _useExtensionBroadcast: boolean = true\n  private _lastEmittedAddress?: string | undefined\n  private _accountChangeDebounceTimer?: NodeJS.Timeout | undefined\n\n  /**\n   * Create a new BrowserWallet instance\n   *\n   * @param provider - Provider instance for blockchain communication\n   * @param config - Optional wallet configuration\n   * @param config.privateKey - Private key for private key mode (hex string)\n   * @param config.pemContent - PEM file content for PEM mode\n   * @param config.pemPassword - Optional password for encrypted PEM files\n   *\n   * @throws {WalletError} If used in non-browser environment\n   *\n   * @example\n   * ```typescript\n   * // Extension mode (default)\n   * const wallet = new BrowserWallet(provider)\n   *\n   * // Private key mode\n   * const wallet = new BrowserWallet(provider, {\n   *   privateKey: '0x123...',\n   * })\n   *\n   * // PEM mode\n   * const wallet = new BrowserWallet(provider, {\n   *   pemContent: pemFileContent,\n   *   pemPassword: 'optional-password',\n   * })\n   * ```\n   */\n  constructor(provider: IProvider, config?: WalletConfig) {\n    super(provider)\n\n    if (!isBrowser()) {\n      throw new WalletError('BrowserWallet can only be used in browser environment')\n    }\n\n    // Initialize private key mode if provided\n    if (config?.privateKey) {\n      this._mode = 'privateKey'\n      this._privateKey = cryptoProvider.importPrivateKey(config.privateKey)\n    } else if (config?.pemContent) {\n      this._mode = 'privateKey'\n      // Import PEM using crypto package's loader (async, will be done in connect())\n      // Store pemContent temporarily for loading in connect()\n      if (config.pemPassword !== undefined) {\n        this._pendingPemLoad = {\n          content: config.pemContent,\n          password: config.pemPassword,\n        }\n      } else {\n        this._pendingPemLoad = {\n          content: config.pemContent,\n        }\n      }\n    }\n  }\n\n  private _pendingPemLoad?:\n    | {\n        content: string\n        password?: string\n      }\n    | undefined\n\n  /**\n   * Connect to the wallet\n   *\n   * **Extension Mode:**\n   * - Checks for Klever Extension installation\n   * - Retrieves the current wallet address from extension\n   * - Sets up event listeners for account changes\n   * - Prompts user if no wallet is connected in extension\n   *\n   * **Private Key Mode:**\n   * - Derives address from the provided private key or PEM file\n   * - No user interaction required\n   *\n   * @throws {WalletError} In extension mode: If extension is not installed or no wallet is connected\n   * @throws {WalletError} In private key mode: If key is invalid or PEM decryption fails\n   *\n   * @fires connect - Emits when successfully connected with { address: string }\n   *\n   * @example\n   * ```typescript\n   * // Extension mode - user must have extension installed\n   * const wallet = new BrowserWallet(provider)\n   * try {\n   *   await wallet.connect()\n   *   console.log('Connected to:', wallet.address)\n   * } catch (error) {\n   *   console.error('Extension not found or no wallet connected')\n   * }\n   * ```\n   *\n   * @example\n   * ```typescript\n   * // Private key mode - instant connection\n   * const wallet = new BrowserWallet(provider, { privateKey: '0x123...' })\n   * await wallet.connect() // No extension needed\n   * ```\n   */\n  async connect(): Promise<void> {\n    if (this._connected) {\n      return\n    }\n\n    // Private key mode - direct connection without extension\n    if (this._mode === 'privateKey') {\n      try {\n        // Load PEM if pending\n        if (this._pendingPemLoad && !this._privateKey) {\n          const pemResult = await cryptoProvider.importPrivateKeyFromPem(\n            this._pendingPemLoad.content,\n            this._pendingPemLoad.password ? { password: this._pendingPemLoad.password } : undefined,\n          )\n          this._privateKey = pemResult\n          // PEM loader returns PrivateKey with validated address\n          // Get address from public key\n          const publicKey = await cryptoProvider.getPublicKey(pemResult)\n          this._address = publicKey.toAddress()\n          this._pendingPemLoad = undefined // Clear after loading\n        }\n\n        if (!this._privateKey) {\n          throw new WalletError('No private key provided')\n        }\n\n        // Generate address from private key (if not already set from PEM)\n        if (!this._address) {\n          const publicKey = await cryptoProvider.getPublicKey(this._privateKey)\n          this._publicKey = publicKey.toHex()\n          this._address = publicKey.toAddress()\n        } else {\n          // PEM mode - still get public key\n          const publicKey = await cryptoProvider.getPublicKey(this._privateKey)\n          this._publicKey = publicKey.toHex()\n        }\n\n        this._connected = true\n        this.emit('connect', { address: this._address })\n        return\n      } catch (error) {\n        throw new WalletError(\n          `Failed to connect with private key: ${error instanceof Error ? error.message : 'Unknown error'}`,\n        )\n      }\n    }\n\n    // Extension mode - check for Klever Extension\n    if (typeof window === 'undefined') {\n      throw new WalletError('Klever Extension is only available in browser environments')\n    }\n\n    if (!window.kleverWeb) {\n      throw new WalletError(\n        'Klever Extension not found. Please install it from https://klever.io/extension, or provide a private key.',\n      )\n    }\n\n    this._kleverWeb = window.kleverWeb\n    if (window.kleverHub) {\n      this._kleverHub = window.kleverHub\n    }\n\n    try {\n      // Initialize KleverHub if available\n      if (this._kleverHub) {\n        await this._kleverHub.initialize()\n\n        // Set up account change listener with debouncing\n        this._kleverHub.onAccountChanged((event) => {\n          // Clear any pending debounce timer\n          if (this._accountChangeDebounceTimer) {\n            clearTimeout(this._accountChangeDebounceTimer)\n          }\n\n          // Debounce the event to prevent rapid firing\n          this._accountChangeDebounceTimer = setTimeout(() => {\n            // Check if it's a KLV chain (chain === 'KLV' or chain === 1)\n            if (event.chain === 'KLV' || event.chain === 1) {\n              // Only emit if address actually changed\n              if (event.address !== this._lastEmittedAddress) {\n                this._address = event.address\n                this._lastEmittedAddress = event.address\n                this.emit('accountChanged', { address: event.address, chain: event.chain })\n              }\n            } else {\n              // Different chain selected, treat as disconnect\n              this._connected = false\n              this._address = ''\n              this._lastEmittedAddress = undefined\n              this.emit('disconnect')\n            }\n          }, 100) // 100ms debounce delay\n        })\n      }\n\n      // Get the wallet address from the extension\n      const address = this._kleverWeb.getWalletAddress()\n\n      if (!address) {\n        throw new WalletError(\n          'No wallet address set in Klever Extension. Please connect your wallet in the extension.',\n        )\n      }\n\n      this._address = address\n      this._connected = true\n\n      this.emit('connect', { address: this._address })\n    } catch (error) {\n      throw new WalletError(\n        `Failed to connect to Klever Extension: ${error instanceof Error ? error.message : 'Unknown error'}`,\n      )\n    }\n  }\n\n  /**\n   * Disconnect from the wallet\n   *\n   * **Extension Mode:**\n   * - Disconnects from KleverHub\n   * - Removes event listeners\n   * - Clears connection state\n   *\n   * **Private Key Mode:**\n   * - Clears connection state\n   * - Optionally removes private key from memory (clearPrivateKey=true)\n   *\n   * @param clearPrivateKey - In private key mode, whether to clear the private key from memory (default: false)\n   *                          - false: Keep key in memory for quick reconnection\n   *                          - true: Remove key from memory (recommended for security)\n   *\n   * @fires disconnect - Emits when disconnected\n   *\n   * @example\n   * ```typescript\n   * // Extension mode\n   * await wallet.disconnect()\n   *\n   * // Private key mode - clear key for security\n   * await wallet.disconnect(true)\n   * ```\n   */\n  async disconnect(clearPrivateKey: boolean = false): Promise<void> {\n    if (!this._connected) {\n      return\n    }\n\n    try {\n      // Clear any pending debounce timer\n      if (this._accountChangeDebounceTimer) {\n        clearTimeout(this._accountChangeDebounceTimer)\n        this._accountChangeDebounceTimer = undefined\n      }\n\n      // Extension mode - disconnect from hub\n      if (this._mode === 'extension' && this._kleverHub) {\n        await this._kleverHub.disconnect()\n      }\n\n      // Clear connection state\n      this._connected = false\n      this._address = ''\n      this._publicKey = ''\n      this._lastEmittedAddress = undefined\n\n      // Private key mode: Optionally clear private key for security\n      if (clearPrivateKey && this._mode === 'privateKey') {\n        this._privateKey = undefined\n        this._pendingPemLoad = undefined\n      }\n\n      this.emit('disconnect')\n    } catch (error) {\n      throw new WalletError(\n        `Failed to disconnect: ${error instanceof Error ? error.message : 'Unknown error'}`,\n      )\n    }\n  }\n\n  /**\n   * Sign a message with the wallet's private key\n   *\n   * **SECURITY WARNING:**\n   * - Only sign messages from trusted sources\n   * - Verify message content before signing\n   * - Extension mode will show a confirmation dialog to the user\n   * - Malicious messages could trick users into authorizing unintended actions\n   *\n   * **Extension Mode:**\n   * - Prompts user to confirm signing in extension UI\n   * - User can review message before approving\n   * - More secure as private key never leaves extension\n   *\n   * **Private Key Mode:**\n   * - Signs immediately without user confirmation\n   * - Use only in trusted environments\n   *\n   * @param message - Message to sign (string or bytes)\n   * @returns Signature object with .toHex() and .toBase64() methods\n   *\n   * @throws {WalletError} If wallet is not connected\n   * @throws {WalletError} If user rejects signing in extension mode\n   *\n   * @example\n   * ```typescript\n   * // Extension mode - user will see confirmation dialog\n   * const message = \"Sign in to My dApp\"\n   * const signature = await wallet.signMessage(message)\n   * console.log('Signature:', signature.toHex())\n   * ```\n   *\n   * @example\n   * ```typescript\n   * // Private key mode - immediate signing\n   * const signature = await wallet.signMessage(\"Hello, Klever!\")\n   * const isValid = await wallet.verifyMessage(\"Hello, Klever!\", signature)\n   * ```\n   */\n  async signMessage(message: string | Uint8Array): Promise<Signature> {\n    if (!this._connected) {\n      throw new WalletError('Wallet not connected')\n    }\n\n    // Private key mode - sign locally\n    if (this._mode === 'privateKey') {\n      if (!this._privateKey) {\n        throw new WalletError('No private key available')\n      }\n\n      try {\n        const messageBytes =\n          typeof message === 'string' ? new TextEncoder().encode(message) : message\n        const signature = await cryptoProvider.signMessage(messageBytes, this._privateKey)\n        return signature\n      } catch (error) {\n        throw new WalletError(\n          `Failed to sign message: ${error instanceof Error ? error.message : 'Unknown error'}`,\n        )\n      }\n    }\n\n    // Extension mode - use KleverWeb (returns string signature)\n    if (!this._kleverWeb) {\n      throw new WalletError('Extension not available')\n    }\n\n    try {\n      const messageStr = typeof message === 'string' ? message : hexEncode(message)\n\n      const signatureStr = await this._kleverWeb.signMessage(messageStr)\n      // Extension returns hex or base64 - try both\n      try {\n        return SignatureImpl.fromHex(signatureStr)\n      } catch {\n        return SignatureImpl.fromBase64(signatureStr)\n      }\n    } catch (error) {\n      throw new WalletError(\n        `Failed to sign message: ${error instanceof Error ? error.message : 'Unknown error'}`,\n      )\n    }\n  }\n\n  /**\n   * Sign a transaction with the wallet's private key\n   *\n   * **SECURITY WARNING:**\n   * - Always verify transaction details before signing\n   * - Check recipient address, amount, and contract type\n   * - Extension mode shows transaction details to user for review\n   * - Signed transactions authorize blockchain state changes\n   *\n   * **Extension Mode:**\n   * - Displays transaction in extension UI for user approval\n   * - User can review all details before signing\n   * - Most secure - private key never exposed\n   *\n   * **Private Key Mode:**\n   * - Signs immediately without user confirmation\n   * - Validate transaction parameters before calling\n   *\n   * @param unsignedTx - Unsigned transaction to sign\n   * @returns Signed transaction ready for broadcast\n   *\n   * @throws {WalletError} If wallet is not connected\n   * @throws {WalletError} If user rejects signing in extension mode\n   *\n   * @example\n   * ```typescript\n   * // Build a transaction\n   * const unsignedTx = await wallet.buildTransaction([\n   *   {\n   *     contractType: TXType.Transfer,\n   *     receiver: 'klv1...',\n   *     amount: '1000000',\n   *   }\n   * ])\n   *\n   * // Sign it (extension will prompt user)\n   * const signedTx = await wallet.signTransaction(unsignedTx)\n   *\n   * // Broadcast\n   * const hash = await wallet.broadcastTransaction(signedTx)\n   * ```\n   */\n  async signTransaction(unsignedTx: Transaction): Promise<Transaction> {\n    if (!this._connected) {\n      throw new WalletError('Wallet not connected')\n    }\n\n    // Private key mode - sign locally using Transaction.sign()\n    if (this._mode === 'privateKey') {\n      if (!this._privateKey) {\n        throw new WalletError('No private key available')\n      }\n\n      try {\n        await unsignedTx.sign(this._privateKey)\n        return unsignedTx\n      } catch (error) {\n        throw new WalletError(\n          `Failed to sign transaction: ${error instanceof Error ? error.message : 'Unknown error'}`,\n        )\n      }\n    }\n\n    // Extension mode - use KleverWeb\n    if (!this._kleverWeb) {\n      throw new WalletError('Extension not available')\n    }\n\n    try {\n      // Sign transaction via extension\n      const result = await this._kleverWeb.signTransaction(unsignedTx.toJSON())\n      return Transaction.fromTransaction(result)\n    } catch (error) {\n      throw new WalletError(\n        `Failed to sign transaction: ${error instanceof Error ? error.message : 'Unknown error'}`,\n      )\n    }\n  }\n\n  /**\n   * Build an unsigned transaction\n   *\n   * Creates a transaction with the specified contracts and parameters.\n   * The transaction is built but not signed.\n   *\n   * **Extension Mode:**\n   * - Uses KleverWeb extension's transaction builder\n   * - Automatically fetches nonce and other parameters\n   *\n   * **Private Key Mode:**\n   * - Uses TransactionBuilder with provider\n   * - Fetches account data for proper transaction construction\n   *\n   * @param contracts - Array of contract requests to include in the transaction\n   * @param txData - Optional transaction data (for smart contracts or metadata)\n   * @param options - Optional transaction options\n   * @param options.nonce - Manual nonce override (auto-fetched if not provided)\n   * @param options.kdaFee - Asset ID to pay fees with (defaults to KLV)\n   *\n   * @returns Unsigned transaction ready to be signed\n   *\n   * @throws {WalletError} If wallet is not connected\n   * @throws {WalletError} If transaction building fails\n   *\n   * @example\n   * ```typescript\n   * // Build a simple transfer\n   * const tx = await wallet.buildTransaction([\n   *   {\n   *     contractType: TXType.Transfer,\n   *     receiver: 'klv1...',\n   *     amount: '1000000',\n   *   }\n   * ])\n   *\n   * // Sign and broadcast\n   * const signedTx = await wallet.signTransaction(tx)\n   * const hash = await wallet.broadcastTransaction(signedTx)\n   * ```\n   *\n   * @example\n   * ```typescript\n   * // Build multi-contract transaction\n   * const tx = await wallet.buildTransaction([\n   *   { contractType: TXType.Transfer, receiver: 'klv1...', amount: '1000000' },\n   *   { contractType: TXType.Claim, claimType: 0 },\n   * ])\n   * ```\n   *\n   * @example\n   * ```typescript\n   * // Build with custom nonce and KDA fee\n   * const tx = await wallet.buildTransaction(\n   *   [{ contractType: TXType.Transfer, receiver: 'klv1...', amount: '1000000' }],\n   *   undefined,\n   *   { nonce: 42, kdaFee: 'KFI' }\n   * )\n   * ```\n   */\n  async buildTransaction(\n    contracts: ContractRequestData[],\n    txData?: string[],\n    options?: { nonce?: number; kdaFee?: string },\n  ): Promise<Transaction> {\n    if (!this._connected) {\n      throw new WalletError('Wallet not connected')\n    }\n\n    // Private key mode - use TransactionBuilder\n    if (this._mode === 'privateKey') {\n      try {\n        const { TransactionBuilder } = await import('@klever/connect-transactions')\n        const builder = new TransactionBuilder(this._provider)\n\n        // Add all contracts\n        for (const contract of contracts) {\n          builder.addContract(contract)\n        }\n\n        // Set sender\n        builder.sender(this._address)\n\n        // Set nonce if provided, otherwise auto-fetch\n        if (options?.nonce !== undefined) {\n          builder.nonce(options.nonce)\n        }\n\n        // Build the transaction\n        return await builder.build()\n      } catch (error) {\n        throw new WalletError(\n          `Failed to build transaction: ${error instanceof Error ? error.message : 'Unknown error'}`,\n        )\n      }\n    }\n\n    // Extension mode - use KleverWeb\n    if (!this._kleverWeb) {\n      throw new WalletError('Extension not available')\n    }\n\n    try {\n      // KleverWeb accepts contracts with 'type' field and deconstructs payload internally\n      // Since it converts { type, payload } back to { ...payload, contractType: type },\n      // we can pass ContractRequestData directly by aliasing contractType as type\n      const extensionContracts = contracts.map((contract) => ({\n        type: contract.contractType,\n        payload: contract,\n      })) as IContractRequest[]\n\n      return await this._kleverWeb.buildTransaction(extensionContracts, txData, options)\n    } catch (error) {\n      throw new WalletError(\n        `Failed to build transaction: ${error instanceof Error ? error.message : 'Unknown error'}`,\n      )\n    }\n  }\n\n  /**\n   * Broadcast multiple signed transactions to the network in a single batch\n   * In extension mode: Uses KleverWeb extension\n   * In private key mode: Uses provider.sendRawTransactions\n   * @param signedTxs Array of signed transactions\n   * @returns Array of transaction hashes\n   */\n  override async broadcastTransactions(signedTxs: Transaction[]): Promise<TransactionHash[]> {\n    if (!this._connected) {\n      throw new WalletError('Wallet not connected')\n    }\n\n    // Private key mode - use provider\n    if (this._mode === 'privateKey') {\n      // Use the base class implementation which calls provider.sendRawTransactions\n      return super.broadcastTransactions(signedTxs)\n    }\n\n    // Extension mode - use KleverWeb\n    if (!this._kleverWeb) {\n      throw new WalletError('Extension not available')\n    }\n\n    try {\n      const response = await this._kleverWeb.broadcastTransactions(signedTxs)\n\n      // Extract hashes from extension response\n      if (response.error) {\n        throw new WalletError(response.error)\n      }\n\n      if (response.data?.txsHashes) {\n        return response.data.txsHashes as TransactionHash[]\n      }\n\n      // Fallback: compute hashes locally if extension didn't return them\n      return signedTxs.map((tx) => tx.getHash() as TransactionHash)\n    } catch (error) {\n      throw new WalletError(\n        `Failed to broadcast transactions: ${error instanceof Error ? error.message : 'Unknown error'}`,\n      )\n    }\n  }\n\n  /**\n   * Build and sign a transfer transaction\n   *\n   * Convenience method that combines building and signing a transfer in one call.\n   *\n   * **Extension Mode:**\n   * - Uses KleverWeb extension\n   * - User confirms the transfer in extension UI\n   *\n   * **Private Key Mode:**\n   * - Uses TransactionBuilder + local signing\n   * - Signs immediately without confirmation\n   *\n   * @param to - Recipient address (bech32 format)\n   * @param amount - Amount to transfer in smallest units (KLV has 6 decimals)\n   * @param token - Optional token ID (defaults to 'KLV')\n   *\n   * @returns Signed transaction ready to broadcast\n   *\n   * @throws {WalletError} If wallet is not connected\n   * @throws {WalletError} If user rejects in extension mode\n   *\n   * @example\n   * ```typescript\n   * // Transfer 1 KLV (1000000 smallest units)\n   * const signedTx = await wallet.buildTransfer(\n   *   'klv1...',\n   *   1000000\n   * )\n   * const hash = await wallet.broadcastTransaction(signedTx)\n   * ```\n   *\n   * @example\n   * ```typescript\n   * // Transfer custom token\n   * const signedTx = await wallet.buildTransfer(\n   *   'klv1...',\n   *   5000000,\n   *   'KFI-ABC' // Custom token ID\n   * )\n   * ```\n   */\n  async buildTransfer(to: string, amount: string | number, token?: string): Promise<Transaction> {\n    const contract: ContractRequestData = {\n      contractType: TXType.Transfer,\n      toAddress: to,\n      receiver: to,\n      amount: amount.toString(),\n      ...(token && {\n        kda: token,\n        assetId: token, // Include both for compatibility\n      }),\n    } as ContractRequestData\n\n    const unsignedTx = await this.buildTransaction([contract])\n\n    // Private key mode - sign locally\n    if (this._mode === 'privateKey') {\n      return await this.signTransaction(unsignedTx)\n    }\n\n    // Extension mode - sign with extension\n    if (!this._kleverWeb) {\n      throw new WalletError('KleverWeb not available')\n    }\n    return await this._kleverWeb.signTransaction(unsignedTx)\n  }\n\n  /**\n   * Get the extension's current provider configuration\n   * @returns Network URI configuration from the extension\n   */\n  getExtensionProvider(): NetworkURI {\n    return this._kleverWeb?.getProvider() ?? {}\n  }\n\n  /**\n   * Update the provider for network switching\n   *\n   * This method updates both the extension's provider configuration (NetworkURI)\n   * and the wallet's internal provider (IProvider) to ensure consistency during\n   * network switches.\n   *\n   * @param provider - Can be either:\n   *   - NetworkURI: Updates only the extension's provider configuration\n   *   - IProvider: Updates the wallet's internal provider for blockchain operations\n   *\n   * @remarks\n   * When switching networks, call this method twice:\n   * 1. First with NetworkURI (network config) to update the extension\n   * 2. Then with IProvider to update the wallet's internal provider\n   *\n   * @example\n   * ```typescript\n   * // Switch to mainnet\n   * const networkConfig = getNetworkConfig('mainnet')\n   * const newProvider = new KleverProvider({ network: 'mainnet' })\n   *\n   * // Update both extension config and internal provider\n   * wallet.updateProvider(networkConfig)  // Extension config\n   * wallet.updateProvider(newProvider)     // Internal provider\n   * ```\n   */\n  /**\n   * Type guard to check if provider is an IProvider interface\n   */\n  private isIProvider(provider: NetworkURI | IProvider): provider is IProvider {\n    return (\n      typeof provider === 'object' &&\n      provider !== null &&\n      'getAccount' in provider &&\n      'sendRawTransaction' in provider &&\n      typeof provider.getAccount === 'function' &&\n      typeof provider.sendRawTransaction === 'function'\n    )\n  }\n\n  /**\n   * Type guard to check if provider is a NetworkURI\n   */\n  private isNetworkURI(provider: NetworkURI | IProvider): provider is NetworkURI {\n    return (\n      typeof provider === 'object' && provider !== null && ('api' in provider || 'node' in provider)\n    )\n  }\n\n  updateProvider(provider: NetworkURI | IProvider): void {\n    // Update extension's provider configuration if it's a NetworkURI\n    if (this.isNetworkURI(provider)) {\n      if (!this._kleverWeb) {\n        // return early if extension is not available\n        return\n      }\n      // NetworkURI - update extension configuration\n      this._kleverWeb.provider = provider\n    }\n\n    // Update wallet's internal provider if it's an IProvider\n    if (this.isIProvider(provider)) {\n      // IProvider - update internal provider used by wallet methods\n      this._provider = provider\n    }\n  }\n\n  /**\n   * Create a new account using the extension\n   * Extension mode only\n   * @returns PEM response with private key and address\n   */\n  async createAccount(): Promise<{ privateKey: string; address: string }> {\n    if (!this._kleverWeb) {\n      throw new WalletError('KleverWeb extension not available')\n    }\n\n    try {\n      return await this._kleverWeb.createAccount()\n    } catch (error) {\n      throw new WalletError(\n        `Failed to create account: ${error instanceof Error ? error.message : 'Unknown error'}`,\n      )\n    }\n  }\n\n  /**\n   * Get account information\n   * In extension mode: Uses KleverWeb extension\n   * In private key mode: Uses provider\n   * @param address - Optional address to query (defaults to current wallet address)\n   * @returns Account information\n   */\n  async getAccount(address?: string): Promise<{\n    address: string\n    balance?: number\n    nonce?: number\n    allowance?: number\n    permissions?: string[]\n    rootHash?: string\n    txCount?: number\n  }> {\n    const queryAddress = address || this._address\n\n    if (!queryAddress) {\n      throw new WalletError('No address available')\n    }\n\n    // Private key mode - use provider\n    if (this._mode === 'privateKey') {\n      try {\n        const account = await this._provider.getAccount(queryAddress as KleverAddress)\n        return {\n          address: account.address,\n          balance: Number(account.balance),\n          nonce: account.nonce,\n          // Provider may not return all these fields\n        }\n      } catch (error) {\n        throw new WalletError(\n          `Failed to get account: ${error instanceof Error ? error.message : 'Unknown error'}`,\n        )\n      }\n    }\n\n    // Extension mode - use KleverWeb\n    if (!this._kleverWeb) {\n      throw new WalletError('KleverWeb extension not available')\n    }\n\n    try {\n      return await this._kleverWeb.getAccount(address)\n    } catch (error) {\n      throw new WalletError(\n        `Failed to get account: ${error instanceof Error ? error.message : 'Unknown error'}`,\n      )\n    }\n  }\n\n  /**\n   * Parse PEM file data using the extension\n   * Extension mode only\n   * @param pemData - PEM file content\n   * @returns Private key and address from PEM\n   */\n  async parsePemFileData(pemData: string): Promise<{ privateKey: string; address: string }> {\n    if (!this._kleverWeb) {\n      throw new WalletError('KleverWeb extension not available')\n    }\n\n    try {\n      return await this._kleverWeb.parsePemFileData(pemData)\n    } catch (error) {\n      throw new WalletError(\n        `Failed to parse PEM data: ${error instanceof Error ? error.message : 'Unknown error'}`,\n      )\n    }\n  }\n\n  /**\n   * Set the wallet address in the extension\n   * Extension mode only\n   * @param address - Address to set\n   */\n  async setWalletAddress(address: string): Promise<void> {\n    if (!this._kleverWeb) {\n      throw new WalletError('KleverWeb extension not available')\n    }\n\n    try {\n      await this._kleverWeb.setWalletAddress(address)\n      this._address = address\n    } catch (error) {\n      throw new WalletError(\n        `Failed to set wallet address: ${error instanceof Error ? error.message : 'Unknown error'}`,\n      )\n    }\n  }\n\n  /**\n   * Set a private key in the extension\n   * Extension mode only\n   * @param privateKey - Private key to set\n   */\n  async setPrivateKey(privateKey: string): Promise<void> {\n    if (!this._kleverWeb) {\n      throw new WalletError('KleverWeb extension not available')\n    }\n\n    try {\n      await this._kleverWeb.setPrivateKey(privateKey)\n    } catch (error) {\n      throw new WalletError(\n        `Failed to set private key: ${error instanceof Error ? error.message : 'Unknown error'}`,\n      )\n    }\n  }\n\n  /**\n   * Validate a signature using the extension\n   * Extension mode only\n   * @param message - The original message that was signed\n   * @param signature - The signature to validate\n   * @param address - The address of the expected signer\n   * @returns Validation result with signer information\n   */\n  async validateSignature(\n    message: string,\n    signature: string,\n    address: string,\n  ): Promise<{ isValid: boolean; signer?: string }> {\n    if (!this._kleverWeb) {\n      throw new WalletError('KleverWeb extension not available')\n    }\n\n    try {\n      return await this._kleverWeb.validateSignature(message, signature, address)\n    } catch (error) {\n      throw new WalletError(\n        `Failed to validate signature: ${error instanceof Error ? error.message : 'Unknown error'}`,\n      )\n    }\n  }\n\n  /**\n   * Extract transaction data from contract payload\n   * Handles smart contract calls and regular transaction data\n   */\n  private extractTxData(\n    contractType: number,\n    payload: Record<string, unknown>,\n  ): string[] | undefined {\n    if (contractType === 63) {\n      // SmartContract type - build call input\n      const func = payload['function']\n      const args = payload['args']\n      if (func && args && Array.isArray(args)) {\n        const funcStr = typeof func === 'string' ? func : JSON.stringify(func)\n        const dataString = args.length > 0 ? `${funcStr}@${args.join('@')}` : funcStr\n        // Use base64Encode for consistent cross-platform encoding\n        const callInput = base64Encode(new TextEncoder().encode(dataString))\n        return [callInput]\n      }\n    } else {\n      // Regular transaction data\n      const data = payload['data']\n      if (data) {\n        return Array.isArray(data) ? (data as string[]) : [data as string]\n      }\n    }\n    return undefined\n  }\n\n  /**\n   * Build standard payload from contract data\n   * Filters out non-standard fields like function/args/data\n   */\n  private buildStandardPayload(payload: Record<string, unknown>): Record<string, unknown> {\n    const standardFields = [\n      'toAddress',\n      'amount',\n      'kda',\n      'kdaId',\n      'assetId',\n      'ticker',\n      'ownerAddress',\n      'precision',\n      'initialSupply',\n      'maxSupply',\n      'blsPublicKey',\n      'canDelegate',\n      'commission',\n      'rewardAddress',\n      'bucketId',\n      'address',\n      'callValue',\n      'scType',\n      'marketplaceId',\n      'currencyId',\n      'price',\n      'orderType',\n      'message',\n      'receiver',\n    ]\n\n    const standardPayload: Record<string, unknown> = {}\n    for (const field of standardFields) {\n      if (field in payload) {\n        const value = payload[field]\n        if (value !== undefined) {\n          standardPayload[field] = value\n        }\n      }\n    }\n    return standardPayload\n  }\n\n  /**\n   * Send a generic transaction\n   * In extension mode: Uses KleverWeb extension for building and broadcasting\n   * In private key mode: Uses base implementation (local signing + provider broadcast)\n   */\n  override async sendTransaction(contract: ContractRequestData): Promise<TransactionSubmitResult> {\n    if (!this._connected) {\n      throw new WalletError('Wallet not connected')\n    }\n\n    // Private key mode - use base implementation (local signing)\n    if (this._mode === 'privateKey') {\n      return super.sendTransaction(contract)\n    }\n\n    // Extension mode - use KleverWeb\n    if (!this._kleverWeb) {\n      throw new WalletError('Extension not available')\n    }\n\n    try {\n      const { contractType, ...payload } = contract\n      const txPayload = payload as Record<string, unknown>\n\n      // Extract transaction data\n      const txData = this.extractTxData(contractType, txPayload)\n\n      // Build standard payload\n      const standardPayload = this.buildStandardPayload(txPayload)\n\n      // Build transaction using extension\n      const unsignedTx = await this.buildTransaction(\n        [{ contractType, ...standardPayload } as ContractRequestData],\n        txData,\n      )\n\n      // Sign transaction\n      const signedTx = await this._kleverWeb.signTransaction(unsignedTx)\n\n      // Broadcast transaction\n      const hashes = await this.broadcastTransactions([signedTx])\n\n      if (!hashes || hashes.length === 0) {\n        throw new WalletError('Failed to broadcast transaction')\n      }\n\n      const hash = hashes[0]\n      if (!hash) {\n        throw new WalletError('Invalid transaction hash')\n      }\n\n      return {\n        hash,\n        status: 'pending',\n      }\n    } catch (error) {\n      throw new WalletError(\n        `Failed to send transaction: ${error instanceof Error ? error.message : 'Unknown error'}`,\n      )\n    }\n  }\n\n  /**\n   * Transfer tokens to another address\n   * In extension mode: Uses KleverWeb extension\n   * In private key mode: Uses base implementation\n   */\n  override async transfer(params: TransferRequest): Promise<TransactionSubmitResult> {\n    // Private key mode - use base implementation\n    if (this._mode === 'privateKey') {\n      return super.transfer(params)\n    }\n\n    // Extension mode with broadcast support\n    if (this._useExtensionBroadcast && this._kleverWeb) {\n      try {\n        // buildTransfer already builds and signs the transaction\n        const signedTx = await this.buildTransfer(\n          params.receiver,\n          params.amount.toString(),\n          params.kda,\n        )\n        const hashes = await this.broadcastTransactions([signedTx])\n\n        if (!hashes || hashes.length === 0) {\n          throw new WalletError('Failed to broadcast transaction')\n        }\n\n        const hash = hashes[0]\n        if (!hash) {\n          throw new WalletError('Invalid transaction hash')\n        }\n\n        return {\n          hash,\n          status: 'pending',\n        }\n      } catch (error) {\n        // Fallback to regular provider broadcast\n        console.warn('Extension broadcast failed, falling back to provider:', error)\n      }\n    }\n\n    // Use the default implementation\n    return super.transfer(params)\n  }\n\n  /**\n   * Encrypts the wallet's private key to a keystore format\n   *\n   * **Only available in private key mode** - extension mode wallets cannot be encrypted\n   * as the private key is stored in the browser extension.\n   *\n   * Creates an encrypted keystore (Web3 Secret Storage format) that can be\n   * saved and later decrypted using `WalletFactory.fromEncryptedJson()`.\n   *\n   * **Security Notes:**\n   * - Use a strong password with mixed characters, numbers, and symbols\n   * - The scryptN parameter controls encryption strength vs speed\n   * - Higher scryptN = more secure but slower (default: 262144)\n   * - Never store the password with the keystore\n   *\n   * @param password - The password to encrypt the keystore\n   * @param options - Optional scrypt parameters for encryption strength\n   * @param options.scryptN - Work factor (default: 262144, min: 4096)\n   * @returns A promise that resolves to the encrypted keystore object\n   *\n   * @throws {WalletError} If wallet is not connected or in extension mode\n   *\n   * @example\n   * ```typescript\n   * // Private key mode only\n   * const wallet = new BrowserWallet(provider, { privateKey: '0x123...' })\n   * await wallet.connect()\n   *\n   * // Encrypt with default parameters\n   * const keystore = await wallet.encrypt('my-secure-password')\n   *\n   * // Save to localStorage or download as file\n   * localStorage.setItem('wallet', JSON.stringify(keystore))\n   * ```\n   *\n   * @example\n   * ```typescript\n   * // Encrypt with custom parameters (faster, for testing)\n   * const testKeystore = await wallet.encrypt('password', {\n   *   scryptN: 4096  // Faster but less secure\n   * })\n   * ```\n   */\n  async encrypt(password: string, options?: EncryptOptions): Promise<Keystore> {\n    if (this._mode === 'extension') {\n      throw new WalletError(\n        'Cannot encrypt extension wallet - private key is stored in the browser extension',\n      )\n    }\n\n    if (!this.isConnected() || !this._privateKey) {\n      throw new WalletError('Wallet must be connected to encrypt')\n    }\n\n    return encryptToKeystore(this._privateKey, password, this._address, options)\n  }\n}\n","import { WalletError, isNode, isValidAddress } from '@klever/connect-core'\nimport type { PrivateKey, Signature } from '@klever/connect-crypto'\nimport {\n  cryptoProvider,\n  encryptToKeystore,\n  type EncryptOptions,\n  type Keystore,\n} from '@klever/connect-crypto'\nimport { hexEncode } from '@klever/connect-encoding'\nimport type { IProvider } from '@klever/connect-provider'\nimport type { Transaction } from '@klever/connect-transactions'\n\nimport { BaseWallet } from '../base'\n\n/**\n * Wallet implementation for Node.js environments\n *\n * NodeWallet provides secure wallet operations in server-side Node.js applications.\n * It uses private key-based signing and is designed for backend services, CLI tools,\n * and automated systems.\n *\n * **Security Considerations:**\n * - Private keys are stored in memory and should be handled with care\n * - Use environment variables or secure key management systems for production\n * - Never expose private keys in logs, error messages, or client-side code\n * - Consider using the `disconnect(true)` option to clear keys from memory when done\n *\n * **Environment:**\n * - Node.js only - will throw error if used in browser environments\n * - Use BrowserWallet for browser/dApp applications\n *\n * @example\n * ```typescript\n * import { KleverProvider } from '@klever/connect-provider'\n * import { NodeWallet } from '@klever/connect-wallet'\n *\n * // Create wallet with private key\n * const provider = new KleverProvider({ network: 'mainnet' })\n * const wallet = new NodeWallet(provider, process.env.PRIVATE_KEY)\n *\n * // Connect and use\n * await wallet.connect()\n * console.log('Address:', wallet.address)\n *\n * // Send a transaction\n * const result = await wallet.transfer({\n *   receiver: 'klv1...',\n *   amount: 1000000, // 1 KLV (6 decimals)\n * })\n * console.log('Transaction hash:', result.hash)\n *\n * // Disconnect and clear private key from memory (recommended for security)\n * await wallet.disconnect(true)\n * ```\n *\n * @example\n * ```typescript\n * // Generate a new random wallet\n * const newWallet = await NodeWallet.generate(provider)\n * await newWallet.connect()\n * console.log('New address:', newWallet.address)\n * ```\n */\nexport class NodeWallet extends BaseWallet {\n  private _privateKey?: PrivateKey | undefined\n\n  /**\n   * Create a new NodeWallet instance\n   *\n   * @param provider - Provider instance for blockchain communication\n   * @param privateKey - Optional private key as hex string. Can be set later with setPrivateKey()\n   *\n   * @throws {WalletError} If used in non-Node.js environment\n   * @throws {WalletError} If private key format is invalid\n   */\n  constructor(provider: IProvider, privateKey?: string) {\n    super(provider)\n\n    if (!isNode()) {\n      throw new WalletError('NodeWallet can only be used in Node.js environment')\n    }\n\n    if (privateKey) {\n      this.importPrivateKey(privateKey)\n    }\n  }\n\n  private importPrivateKey(privateKey: string): void {\n    try {\n      this._privateKey = cryptoProvider.importPrivateKey(privateKey)\n    } catch (error) {\n      throw new WalletError(\n        `Invalid private key: ${error instanceof Error ? error.message : 'Unknown error'}`,\n      )\n    }\n  }\n\n  /**\n   * Connect the wallet\n   *\n   * Derives the public key and address from the private key and marks the wallet as connected.\n   * This operation is performed locally without any network calls.\n   *\n   * @throws {WalletError} If no private key was provided during construction or via setPrivateKey()\n   * @throws {WalletError} If the generated address is invalid\n   *\n   * @fires connect - Emits when successfully connected with { address: string }\n   *\n   * @example\n   * ```typescript\n   * const wallet = new NodeWallet(provider, privateKey)\n   * await wallet.connect()\n   * console.log('Connected:', wallet.address)\n   * ```\n   */\n  async connect(): Promise<void> {\n    if (this._connected) {\n      return\n    }\n\n    if (!this._privateKey) {\n      throw new WalletError('No private key provided')\n    }\n\n    try {\n      // Get public key and address from private key\n      const publicKey = await cryptoProvider.getPublicKey(this._privateKey)\n      this._publicKey = publicKey.toHex()\n      this._address = publicKey.toAddress()\n\n      if (!isValidAddress(this._address)) {\n        throw new WalletError('Generated address is invalid')\n      }\n\n      this._connected = true\n      this.emit('connect', { address: this._address })\n    } catch (error) {\n      throw new WalletError(\n        `Failed to connect: ${error instanceof Error ? error.message : 'Unknown error'}`,\n      )\n    }\n  }\n\n  /**\n   * Disconnect from the wallet\n   *\n   * Clears the connection state and optionally removes the private key from memory.\n   *\n   * **Security Note:**\n   * - By default (clearPrivateKey=false), the private key remains in memory for quick reconnection\n   * - For enhanced security, set clearPrivateKey=true to completely remove the key from memory\n   * - After clearing the private key, you must create a new wallet instance to reconnect\n   *\n   * @param clearPrivateKey - Whether to clear the private key from memory (default: false)\n   *                          - false: Keep key in memory, can reconnect with connect()\n   *                          - true: Remove key from memory, requires new wallet instance\n   *\n   * @fires disconnect - Emits when disconnected\n   *\n   * @example\n   * ```typescript\n   * // Disconnect but keep key for reconnection\n   * await wallet.disconnect()\n   * await wallet.connect() // Works - key still in memory\n   *\n   * // Disconnect and clear key (recommended for security)\n   * await wallet.disconnect(true)\n   * await wallet.connect() // Throws error - key cleared\n   * ```\n   */\n  async disconnect(clearPrivateKey: boolean = false): Promise<void> {\n    if (!this._connected) {\n      return\n    }\n\n    this._connected = false\n    this._address = ''\n    this._publicKey = ''\n\n    // Optionally clear private key for security\n    if (clearPrivateKey) {\n      this._privateKey = undefined\n    }\n    // Note: We keep the private key in memory for potential reconnection\n\n    this.emit('disconnect')\n  }\n\n  /**\n   * Sign a message with the wallet's private key\n   *\n   * **SECURITY WARNING:**\n   * - Only sign messages from trusted sources\n   * - Signing malicious messages can lead to phishing attacks\n   * - Never sign messages that look like transactions or authorization requests\n   * - Verify the message content before signing\n   *\n   * The message is signed using the Ed25519 signature scheme. The resulting signature\n   * can be verified using the wallet's public key.\n   *\n   * @param message - Message to sign (string or raw bytes)\n   * @returns Signature object with .toHex() and .toBase64() methods\n   *\n   * @throws {WalletError} If wallet is not connected or private key not available\n   *\n   * @example\n   * ```typescript\n   * const message = \"Hello, Klever!\"\n   * const signature = await wallet.signMessage(message)\n   *\n   * // Get signature in different formats\n   * console.log('Hex:', signature.toHex())\n   * console.log('Base64:', signature.toBase64())\n   *\n   * // Verify the signature\n   * const isValid = await wallet.verifyMessage(message, signature)\n   * console.log('Valid:', isValid) // true\n   * ```\n   *\n   * @example\n   * ```typescript\n   * // Sign raw bytes\n   * const data = new Uint8Array([1, 2, 3, 4])\n   * const signature = await wallet.signMessage(data)\n   * ```\n   */\n  async signMessage(message: string | Uint8Array): Promise<Signature> {\n    if (!this._connected || !this._privateKey) {\n      throw new WalletError('Wallet not connected')\n    }\n\n    try {\n      const messageBytes = typeof message === 'string' ? new TextEncoder().encode(message) : message\n\n      const signature = await cryptoProvider.signMessage(messageBytes, this._privateKey)\n      // Return Signature object - developers can choose .toHex() or .toBase64()\n      return signature\n    } catch (error) {\n      throw new WalletError(\n        `Failed to sign message: ${error instanceof Error ? error.message : 'Unknown error'}`,\n      )\n    }\n  }\n\n  /**\n   * Sign a transaction with the wallet's private key\n   *\n   * **SECURITY WARNING:**\n   * - Always verify transaction details before signing\n   * - Check recipient address, amount, and contract type\n   * - Signing a transaction authorizes it to be broadcasted to the blockchain\n   * - Signed transactions cannot be reversed once broadcasted\n   *\n   * The transaction is signed in-place, modifying the original transaction object\n   * with the signature. The same transaction object is returned for convenience.\n   *\n   * @param tx - Unsigned transaction to sign\n   * @returns The same transaction object, now signed\n   *\n   * @throws {WalletError} If wallet is not connected or private key not available\n   *\n   * @example\n   * ```typescript\n   * import { TransactionBuilder } from '@klever/connect-transactions'\n   *\n   * // Build a transaction\n   * const builder = new TransactionBuilder(provider)\n   * const unsignedTx = await builder\n   *   .transfer({ receiver: 'klv1...', amount: 1000000 })\n   *   .sender(wallet.address)\n   *   .build()\n   *\n   * // Sign it\n   * const signedTx = await wallet.signTransaction(unsignedTx)\n   *\n   * // Broadcast\n   * const hash = await wallet.broadcastTransaction(signedTx)\n   * console.log('Transaction hash:', hash)\n   * ```\n   */\n  async signTransaction(tx: Transaction): Promise<Transaction> {\n    if (!this._connected || !this._privateKey) {\n      throw new WalletError('Wallet not connected')\n    }\n\n    try {\n      // Sign the transaction using the Transaction class method\n      await tx.sign(this._privateKey)\n      return tx\n    } catch (error) {\n      throw new WalletError(\n        `Failed to sign transaction: ${error instanceof Error ? error.message : 'Unknown error'}`,\n      )\n    }\n  }\n\n  /**\n   * Get the private key for internal use by child classes\n   *\n   * @returns The private key instance or undefined if not set\n   * @internal\n   */\n  protected getPrivateKey(): Uint8Array | undefined {\n    return this._privateKey ? new Uint8Array(this._privateKey.bytes) : undefined\n  }\n\n  /**\n   * Set or change the private key\n   *\n   * **Security Note:**\n   * Can only be called when wallet is disconnected to prevent accidental key changes\n   * during active operations.\n   *\n   * @param privateKey - Private key as hex string\n   *\n   * @throws {WalletError} If wallet is currently connected\n   * @throws {WalletError} If private key format is invalid\n   *\n   * @example\n   * ```typescript\n   * const wallet = new NodeWallet(provider) // No key yet\n   * wallet.setPrivateKey(process.env.PRIVATE_KEY)\n   * await wallet.connect()\n   * ```\n   */\n  setPrivateKey(privateKey: string): void {\n    if (this._connected) {\n      throw new WalletError('Cannot change private key while connected')\n    }\n\n    this.importPrivateKey(privateKey)\n  }\n\n  /**\n   * Generate a new wallet with a random private key\n   *\n   * Creates a new wallet instance with a cryptographically secure random private key.\n   * The wallet is ready to connect and use immediately.\n   *\n   * **Important:**\n   * - Save the private key securely - it cannot be recovered if lost\n   * - Never share the private key with anyone\n   * - Use environment variables or secure key management in production\n   *\n   * @param provider - Provider instance for blockchain communication\n   * @returns New NodeWallet instance with generated key pair\n   *\n   * @example\n   * ```typescript\n   * import { KleverProvider } from '@klever/connect-provider'\n   * import { NodeWallet } from '@klever/connect-wallet'\n   *\n   * const provider = new KleverProvider({ network: 'testnet' })\n   * const wallet = await NodeWallet.generate(provider)\n   *\n   * await wallet.connect()\n   * console.log('New wallet address:', wallet.address)\n   *\n   * // IMPORTANT: Save the private key securely!\n   * // You can extract it before connecting if needed for backup\n   * ```\n   *\n   * @example\n   * ```typescript\n   * // Generate multiple wallets for testing\n   * const wallets = await Promise.all([\n   *   NodeWallet.generate(provider),\n   *   NodeWallet.generate(provider),\n   *   NodeWallet.generate(provider),\n   * ])\n   *\n   * for (const wallet of wallets) {\n   *   await wallet.connect()\n   *   console.log('Generated address:', wallet.address)\n   * }\n   * ```\n   */\n  static async generate(provider: IProvider): Promise<NodeWallet> {\n    const keyPair = await cryptoProvider.generateKeyPair()\n    const privateKeyHex = hexEncode(keyPair.privateKey.bytes)\n    return new NodeWallet(provider, privateKeyHex)\n  }\n\n  /**\n   * Encrypts the wallet's private key to a keystore format\n   *\n   * Creates an encrypted keystore (Web3 Secret Storage format) that can be\n   * saved to disk and later decrypted using `WalletFactory.fromEncryptedJson()`.\n   *\n   * **Security Notes:**\n   * - Use a strong password with mixed characters, numbers, and symbols\n   * - The scryptN parameter controls encryption strength vs speed\n   * - Higher scryptN = more secure but slower (default: 262144)\n   * - Never store the password with the keystore file\n   *\n   * @param password - The password to encrypt the keystore\n   * @param options - Optional scrypt parameters for encryption strength\n   * @param options.scryptN - Work factor (default: 262144, min: 4096)\n   * @returns A promise that resolves to the encrypted keystore object\n   *\n   * @throws {WalletError} If wallet is not connected\n   *\n   * @example\n   * ```typescript\n   * const wallet = await NodeWallet.generate(provider)\n   * await wallet.connect()\n   *\n   * // Encrypt with default parameters (most secure)\n   * const keystore = await wallet.encrypt('my-secure-password')\n   *\n   * // Save to file\n   * await fs.writeFile('keystore.json', JSON.stringify(keystore, null, 2))\n   * ```\n   *\n   * @example\n   * ```typescript\n   * // Encrypt with custom parameters (faster, for testing)\n   * const testKeystore = await wallet.encrypt('password', {\n   *   scryptN: 4096  // Faster but less secure\n   * })\n   * ```\n   */\n  async encrypt(password: string, options?: EncryptOptions): Promise<Keystore> {\n    if (!this.isConnected() || !this._privateKey) {\n      throw new WalletError('Wallet must be connected to encrypt')\n    }\n\n    return encryptToKeystore(this._privateKey, password, this._address, options)\n  }\n}\n","import { detectEnvironment } from '@klever/connect-core'\nimport type { IProvider } from '@klever/connect-provider'\nimport { KleverProvider } from '@klever/connect-provider'\nimport {\n  cryptoProvider,\n  mnemonicToPrivateKey as mnemonicToKey,\n  decryptKeystore,\n  type MnemonicToKeyOptions,\n  type Keystore,\n} from '@klever/connect-crypto'\nimport { hexEncode } from '@klever/connect-encoding'\n\nimport { BrowserWallet } from './browser'\nimport { NodeWallet } from './node'\nimport type { Wallet, WalletConfig, WalletFactory as IWalletFactory } from './types'\n\n/**\n * Factory for creating environment-appropriate wallet instances\n *\n * WalletFactory automatically detects the runtime environment (Node.js, Browser, React Native)\n * and creates the appropriate wallet implementation. This provides a unified API for\n * wallet creation across different platforms.\n *\n * **Automatic Environment Detection:**\n * - Node.js → Creates NodeWallet\n * - Browser → Creates BrowserWallet\n * - React Native → (Future support)\n *\n * **Benefits:**\n * - Write once, run anywhere - same code works in Node.js and browser\n * - Simplifies multi-platform dApp development\n * - Handles environment-specific wallet initialization\n * - Type-safe configuration\n *\n * @example\n * ```typescript\n * import { WalletFactory } from '@klever/connect-wallet'\n * import { KleverProvider } from '@klever/connect-provider'\n *\n * const provider = new KleverProvider({ network: 'mainnet' })\n * const factory = new WalletFactory(provider)\n *\n * // In Node.js, this creates a NodeWallet\n * // In Browser, this creates a BrowserWallet\n * const wallet = await factory.createWallet({\n *   privateKey: process.env.PRIVATE_KEY, // Optional in browser (uses extension)\n *   network: 'mainnet',\n * })\n *\n * await wallet.connect()\n * console.log('Wallet address:', wallet.address)\n * ```\n *\n * @example\n * ```typescript\n * // Browser-specific configuration\n * const wallet = await factory.createWallet({\n *   // No privateKey = uses extension in browser\n *   // With privateKey = uses private key mode\n *   privateKey: '0x123...', // Optional\n * })\n * ```\n *\n * @example\n * ```typescript\n * // Use the convenience function for simpler code\n * import { createWallet } from '@klever/connect-wallet'\n *\n * const wallet = await createWallet({\n *   network: 'testnet',\n *   privateKey: process.env.PRIVATE_KEY,\n * })\n * ```\n */\nexport class WalletFactory implements IWalletFactory {\n  private provider: IProvider\n\n  /**\n   * Create a new WalletFactory instance\n   *\n   * @param provider - Optional provider instance. If not provided, creates a default KleverProvider\n   */\n  constructor(provider?: IProvider) {\n    this.provider = provider || new KleverProvider()\n  }\n\n  /**\n   * Create a wallet instance appropriate for the current environment\n   *\n   * Detects the runtime environment and creates:\n   * - NodeWallet in Node.js (requires privateKey)\n   * - BrowserWallet in browsers (optional privateKey, defaults to extension mode)\n   * - Throws error for React Native (not yet implemented)\n   *\n   * @param config - Optional wallet configuration\n   * @param config.privateKey - Private key for wallet initialization (required for Node.js)\n   * @param config.pemContent - PEM file content (alternative to privateKey)\n   * @param config.pemPassword - Password for encrypted PEM files\n   * @param config.network - Network to connect to ('mainnet', 'testnet', etc.)\n   * @param config.provider - Override the factory's provider\n   *\n   * @returns Wallet instance ready to connect\n   *\n   * @throws {Error} If environment is React Native (not yet supported)\n   * @throws {Error} If privateKey is not provided in Node.js environment\n   *\n   * @example\n   * ```typescript\n   * // Node.js environment\n   * const wallet = await factory.createWallet({\n   *   privateKey: process.env.PRIVATE_KEY, // Required\n   *   network: 'mainnet',\n   * })\n   * ```\n   *\n   * @example\n   * ```typescript\n   * // Browser environment - Extension mode\n   * const wallet = await factory.createWallet({\n   *   // No privateKey = uses Klever Extension\n   * })\n   * ```\n   *\n   * @example\n   * ```typescript\n   * // Browser environment - Private key mode\n   * const wallet = await factory.createWallet({\n   *   privateKey: '0x123...', // Uses private key instead of extension\n   * })\n   * ```\n   */\n  async createWallet(config?: WalletConfig): Promise<Wallet> {\n    const environment = detectEnvironment()\n\n    // Allow overriding the provider\n    if (config?.provider) {\n      this.provider = config.provider\n    } else if (config?.network) {\n      this.provider = new KleverProvider({\n        network: config.network,\n      })\n    }\n\n    switch (environment) {\n      case 'browser':\n        return this.createBrowserWallet(config)\n\n      case 'node':\n        return this.createNodeWallet(config?.privateKey)\n\n      case 'react-native':\n        // TODO: Implement React Native wallet\n        throw new Error('React Native wallet not implemented yet')\n\n      default:\n        throw new Error(`Unsupported environment: ${environment}`)\n    }\n  }\n\n  private createBrowserWallet(config?: WalletConfig): BrowserWallet {\n    return new BrowserWallet(this.provider, config)\n  }\n\n  private createNodeWallet(privateKey?: string): NodeWallet {\n    if (!privateKey) {\n      throw new Error('Private key is required for Node.js environment')\n    }\n    return new NodeWallet(this.provider, privateKey)\n  }\n\n  /**\n   * Create a new wallet with a randomly generated private key\n   *\n   * Creates a wallet appropriate for the current environment:\n   * - Node.js → NodeWallet with random key\n   * - Browser → BrowserWallet in private key mode with random key\n   *\n   * **Important:**\n   * - Save the private key securely - it cannot be recovered if lost\n   * - Never share the private key with anyone\n   * - Use environment variables or secure key management in production\n   *\n   * @param provider - Optional custom provider (defaults to factory's provider)\n   * @returns A promise that resolves to a new Wallet instance\n   *\n   * @example\n   * ```typescript\n   * const factory = new WalletFactory()\n   * const wallet = await factory.createRandom()\n   * await wallet.connect()\n   * console.log('New address:', wallet.address)\n   * ```\n   *\n   * @example\n   * ```typescript\n   * // With custom provider\n   * const testProvider = new KleverProvider({ network: 'testnet' })\n   * const wallet = await factory.createRandom(testProvider)\n   * ```\n   */\n  async createRandom(provider?: IProvider): Promise<Wallet> {\n    const walletProvider = provider || this.provider\n    const keyPair = await cryptoProvider.generateKeyPair()\n    const privateKeyHex = hexEncode(keyPair.privateKey.bytes)\n\n    const environment = detectEnvironment()\n\n    switch (environment) {\n      case 'browser':\n        return new BrowserWallet(walletProvider, { privateKey: privateKeyHex })\n\n      case 'node':\n        return new NodeWallet(walletProvider, privateKeyHex)\n\n      case 'react-native':\n        throw new Error('React Native wallet not implemented yet')\n\n      default:\n        throw new Error(`Unsupported environment: ${environment}`)\n    }\n  }\n\n  /**\n   * Converts a BIP39 mnemonic phrase to a private key (hex string)\n   *\n   * This is a utility method that derives a private key from a mnemonic without\n   * creating a wallet instance. Useful when you only need the private key.\n   *\n   * @param mnemonic - The BIP39 mnemonic phrase (12-24 words)\n   * @param options - Optional derivation path and passphrase\n   * @returns The private key as a hexadecimal string\n   *\n   * @example\n   * ```typescript\n   * const factory = new WalletFactory()\n   * const privateKey = factory.mnemonicToPrivateKey('abandon abandon abandon...')\n   * console.log('Private key:', privateKey)\n   * ```\n   *\n   * @example\n   * ```typescript\n   * // With custom derivation path\n   * const privateKey = factory.mnemonicToPrivateKey('abandon abandon abandon...', {\n   *   path: \"m/44'/690'/0'/0'/1'\"\n   * })\n   * ```\n   */\n  mnemonicToPrivateKey(mnemonic: string, options?: MnemonicToKeyOptions): string {\n    const privateKey = mnemonicToKey(mnemonic, options)\n    return hexEncode(privateKey.bytes)\n  }\n\n  /**\n   * Create a wallet from a BIP39 mnemonic phrase\n   *\n   * Creates a wallet appropriate for the current environment:\n   * - Node.js → NodeWallet with derived key\n   * - Browser → BrowserWallet in private key mode with derived key\n   *\n   * @param mnemonic - The BIP39 mnemonic phrase (12-24 words)\n   * @param provider - Optional custom provider (defaults to factory's provider)\n   * @param options - Optional derivation path and passphrase\n   * @returns A promise that resolves to a new Wallet instance\n   *\n   * @example\n   * ```typescript\n   * const factory = new WalletFactory()\n   * const wallet = await factory.fromMnemonic('abandon abandon abandon...')\n   * await wallet.connect()\n   * console.log('Address:', wallet.address)\n   * ```\n   *\n   * @example\n   * ```typescript\n   * // With custom derivation path\n   * const wallet = await factory.fromMnemonic('abandon abandon abandon...', undefined, {\n   *   path: \"m/44'/690'/0'/0'/1'\"\n   * })\n   * ```\n   *\n   * @example\n   * ```typescript\n   * // With passphrase\n   * const wallet = await factory.fromMnemonic('abandon abandon abandon...', undefined, {\n   *   passphrase: 'my-secret-passphrase'\n   * })\n   * ```\n   */\n  async fromMnemonic(\n    mnemonic: string,\n    provider?: IProvider,\n    options?: MnemonicToKeyOptions,\n  ): Promise<Wallet> {\n    const walletProvider = provider || this.provider\n    const privateKeyHex = this.mnemonicToPrivateKey(mnemonic, options)\n\n    const environment = detectEnvironment()\n\n    switch (environment) {\n      case 'browser':\n        return new BrowserWallet(walletProvider, { privateKey: privateKeyHex })\n\n      case 'node':\n        return new NodeWallet(walletProvider, privateKeyHex)\n\n      case 'react-native':\n        throw new Error('React Native wallet not implemented yet')\n\n      default:\n        throw new Error(`Unsupported environment: ${environment}`)\n    }\n  }\n\n  /**\n   * Create a wallet from an encrypted keystore (Web3 Secret Storage)\n   *\n   * Creates a wallet appropriate for the current environment:\n   * - Node.js → NodeWallet with decrypted key\n   * - Browser → BrowserWallet in private key mode with decrypted key\n   *\n   * @param json - The keystore object or JSON string\n   * @param password - The password to decrypt the keystore\n   * @param provider - Optional custom provider (defaults to factory's provider)\n   * @returns A promise that resolves to a new Wallet instance\n   *\n   * @throws Error if password is incorrect or keystore is invalid\n   *\n   * @example\n   * ```typescript\n   * const factory = new WalletFactory()\n   * const wallet = await factory.fromEncryptedJson(keystore, 'my-password')\n   * await wallet.connect()\n   * console.log('Loaded wallet address:', wallet.address)\n   * ```\n   *\n   * @example\n   * ```typescript\n   * // From JSON string\n   * const keystoreJson = await fs.readFile('keystore.json', 'utf-8')\n   * const wallet = await factory.fromEncryptedJson(keystoreJson, 'my-password')\n   * ```\n   */\n  async fromEncryptedJson(\n    json: Keystore | string,\n    password: string,\n    provider?: IProvider,\n  ): Promise<Wallet> {\n    const walletProvider = provider || this.provider\n    const privateKey = await decryptKeystore(json, password)\n    const privateKeyHex = hexEncode(privateKey.bytes)\n\n    const environment = detectEnvironment()\n\n    switch (environment) {\n      case 'browser':\n        return new BrowserWallet(walletProvider, { privateKey: privateKeyHex })\n\n      case 'node':\n        return new NodeWallet(walletProvider, privateKeyHex)\n\n      case 'react-native':\n        throw new Error('React Native wallet not implemented yet')\n\n      default:\n        throw new Error(`Unsupported environment: ${environment}`)\n    }\n  }\n}\n\n/**\n * Convenience function for creating environment-appropriate wallets\n *\n * This is a simplified wrapper around WalletFactory for quick wallet creation.\n * It automatically detects the environment and creates the appropriate wallet type.\n *\n * **When to use:**\n * - Quick prototyping and testing\n * - Simple applications with one wallet instance\n * - Default provider configuration is acceptable\n *\n * **When to use WalletFactory instead:**\n * - Need to reuse the same provider for multiple wallets\n * - Custom provider configuration required\n * - Creating multiple wallet instances\n *\n * @param config - Optional wallet configuration\n * @param config.privateKey - Private key (required in Node.js, optional in browser)\n * @param config.pemContent - PEM file content (alternative to privateKey)\n * @param config.pemPassword - Password for encrypted PEM files\n * @param config.network - Network to connect to\n * @param config.provider - Custom provider instance\n *\n * @returns Wallet instance appropriate for the current environment\n *\n * @example\n * ```typescript\n * // Simple usage with defaults\n * const wallet = await createWallet({\n *   privateKey: process.env.PRIVATE_KEY,\n * })\n * await wallet.connect()\n * ```\n *\n * @example\n * ```typescript\n * // Browser extension mode\n * const wallet = await createWallet() // No config needed\n * await wallet.connect() // Uses Klever Extension\n * ```\n *\n * @example\n * ```typescript\n * // Custom network\n * const wallet = await createWallet({\n *   network: 'testnet',\n *   privateKey: process.env.TEST_PRIVATE_KEY,\n * })\n * ```\n */\nexport async function createWallet(config?: WalletConfig): Promise<Wallet> {\n  const factory = new WalletFactory()\n  return factory.createWallet(config)\n}\n\n// Export specific wallet types for advanced users\nexport { BrowserWallet, NodeWallet }\n"]}