@gvnrdao/dh-lit-ops 0.0.108 ā 0.0.183
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/dist/interfaces/chunks/config.d.ts +0 -6
- package/dist/interfaces/chunks/config.d.ts.map +1 -1
- package/dist/interfaces/chunks/lit-action-execution.d.ts +11 -0
- package/dist/interfaces/chunks/lit-action-execution.d.ts.map +1 -1
- package/dist/modules/action-executor.module.d.ts.map +1 -1
- package/dist/modules/action-executor.module.js +23 -103
- package/dist/modules/action-executor.module.js.map +1 -1
- package/dist/modules/auth-manager.module.d.ts.map +1 -1
- package/dist/modules/auth-manager.module.js +34 -148
- package/dist/modules/auth-manager.module.js.map +1 -1
- package/dist/modules/client-manager.module.d.ts.map +1 -1
- package/dist/modules/client-manager.module.js.map +1 -1
- package/dist/modules/lit-ops.module.d.ts +14 -118
- package/dist/modules/lit-ops.module.d.ts.map +1 -1
- package/dist/modules/lit-ops.module.js +109 -827
- package/dist/modules/lit-ops.module.js.map +1 -1
- package/dist/modules/pkp-minter.module.d.ts +0 -1
- package/dist/modules/pkp-minter.module.d.ts.map +1 -1
- package/dist/modules/pkp-minter.module.js +98 -106
- package/dist/modules/pkp-minter.module.js.map +1 -1
- package/dist/modules/session-signature-manager.module.d.ts.map +1 -1
- package/dist/modules/session-signature-manager.module.js +31 -67
- package/dist/modules/session-signature-manager.module.js.map +1 -1
- package/package.json +3 -4
|
@@ -415,29 +415,6 @@ class LitOps {
|
|
|
415
415
|
};
|
|
416
416
|
return this.actionExecutor.executeAction(request, litClient);
|
|
417
417
|
}
|
|
418
|
-
/**
|
|
419
|
-
* TEST-ONLY: Execute arbitrary local LIT Action code for debugging PKP authorization.
|
|
420
|
-
*
|
|
421
|
-
* This helper is intended for Jest / integration tests to run a minimal action
|
|
422
|
-
* (e.g. sign-only) with either wildcard or CID-scoped session signatures.
|
|
423
|
-
*/
|
|
424
|
-
async runLocalLitActionCodeForTest(options) {
|
|
425
|
-
const { code, pkpPublicKey, params, pkpTokenId, cid } = options;
|
|
426
|
-
const litClient = await this.clientManager.getClient({
|
|
427
|
-
litNetwork: this.config.network,
|
|
428
|
-
debug: this.config.debug,
|
|
429
|
-
});
|
|
430
|
-
const request = {
|
|
431
|
-
code,
|
|
432
|
-
cid, // Optional CID: when provided, session sigs are scoped to this action
|
|
433
|
-
pkpPublicKey,
|
|
434
|
-
params,
|
|
435
|
-
signer: this.config.signer,
|
|
436
|
-
pkpTokenId,
|
|
437
|
-
};
|
|
438
|
-
const result = await this.actionExecutor.executeAction(request, litClient);
|
|
439
|
-
return result.response;
|
|
440
|
-
}
|
|
441
418
|
/**
|
|
442
419
|
* Execute a LIT Action from IPFS
|
|
443
420
|
*/
|
|
@@ -653,7 +630,7 @@ class LitOps {
|
|
|
653
630
|
* @param signer - The wallet to use for session signatures
|
|
654
631
|
* @returns PKP validation result with signature verification
|
|
655
632
|
*/
|
|
656
|
-
async validatePKPSecurity(targetPkpTokenId, expectedCid, signerPkp, signer
|
|
633
|
+
async validatePKPSecurity(targetPkpTokenId, expectedCid, signerPkp, signer) {
|
|
657
634
|
console.log(`š LIT-OPS TRACE: validatePKPSecurity ENTRY`);
|
|
658
635
|
console.log(` - targetPkpTokenId: "${targetPkpTokenId}"`);
|
|
659
636
|
console.log(` - targetPkpTokenId type: ${typeof targetPkpTokenId}`);
|
|
@@ -675,54 +652,25 @@ class LitOps {
|
|
|
675
652
|
: (() => {
|
|
676
653
|
throw new Error("Unsupported LIT network");
|
|
677
654
|
})()).pkpValidator.cid;
|
|
678
|
-
// Convert validator CID to hex format for signature message
|
|
679
|
-
// The contract expects the validator's CID in the signature, not the PKP's CID
|
|
680
|
-
// Use registry CID (same as cr-lit branch) - this is the source of truth
|
|
681
|
-
const validatorCidHex = (0, dh_lit_actions_1.cidToHex)(pkpValidatorCid);
|
|
682
655
|
if (this.config.debug) {
|
|
683
|
-
console.log(` PKP Validator CID
|
|
684
|
-
console.log(` Validator CID (hex): ${validatorCidHex}`);
|
|
685
|
-
console.log(` PKP's expected CID (hex): ${expectedCid}`);
|
|
656
|
+
console.log(` PKP Validator CID: ${pkpValidatorCid}`);
|
|
686
657
|
}
|
|
687
658
|
// Execute PKP Validator LIT Action
|
|
688
|
-
// NOTE:
|
|
689
|
-
//
|
|
690
|
-
//
|
|
691
|
-
//
|
|
692
|
-
// Normalize signer PKP token ID to hex format for session scoping
|
|
693
|
-
// NOTE: signerPkp IS the validator PKP (passed from call site)
|
|
694
|
-
let sessionScopedSignerTokenId = signerPkp.tokenId;
|
|
695
|
-
try {
|
|
696
|
-
const normalizedHex = BigInt(signerPkp.tokenId)
|
|
697
|
-
.toString(16)
|
|
698
|
-
.padStart(64, "0");
|
|
699
|
-
sessionScopedSignerTokenId = `0x${normalizedHex}`;
|
|
700
|
-
}
|
|
701
|
-
catch (tokenErr) {
|
|
702
|
-
console.warn("ā ļø Failed to normalize signer PKP tokenId to hex, using raw value", tokenErr);
|
|
703
|
-
}
|
|
704
|
-
if (this.config.debug) {
|
|
705
|
-
console.log(` Signer PKP (validator) Public Key: ${signerPkp.publicKey.substring(0, 20)}...`);
|
|
706
|
-
console.log(` Signer PKP (validator) Token ID: ${signerPkp.tokenId}`);
|
|
707
|
-
console.log(` Signer PKP (validator) ETH Address: ${signerPkp.ethAddress}`);
|
|
708
|
-
}
|
|
659
|
+
// NOTE: We do NOT pass the validator PKP token ID here because the validator
|
|
660
|
+
// performs READ-ONLY operations (no signing). Passing undefined for pkpTokenId
|
|
661
|
+
// will skip adding LitPKPResource to the session signature, which is correct
|
|
662
|
+
// for burned/immutable validator PKPs that can't sign via session signatures.
|
|
709
663
|
console.log(`\nš LIT-OPS TRACE: About to call executeActionFromCID with jsParams:`);
|
|
710
664
|
console.log(` - targetPkpTokenId: "${targetPkpTokenId}"`);
|
|
711
665
|
console.log(` - expectedCid: "${expectedCid}"`);
|
|
712
|
-
|
|
713
|
-
console.log(` - signerPkp.publicKey: "${signerPkp.publicKey.substring(0, 20)}..."`);
|
|
714
|
-
// Use signerPkp directly (which IS the validator PKP from call site, matching cr-lit)
|
|
715
|
-
// The LIT Action will use globalThis.publicKey which is set from pkpPublicKey parameter
|
|
716
|
-
const litResult = await this.executeActionFromCID(pkpValidatorCid, signerPkp.publicKey, // ā
Use signerPkp.publicKey (validator PKP, matching cr-lit)
|
|
717
|
-
{
|
|
666
|
+
const litResult = await this.executeActionFromCID(pkpValidatorCid, signerPkp.publicKey, {
|
|
718
667
|
targetPkpTokenId,
|
|
719
|
-
expectedCid, //
|
|
720
|
-
certificationCid: validatorCidHex, // Validator's CID (for signature message) - from registry
|
|
668
|
+
expectedCid, // Expected to be in hex format
|
|
721
669
|
message: `PKP validation: ${Date.now()}`,
|
|
722
670
|
// Ensure the LIT Action knows which network (datil vs datil-test)
|
|
723
671
|
network: this.config.network,
|
|
724
|
-
}, signer
|
|
725
|
-
|
|
672
|
+
}, signer
|
|
673
|
+
// Intentionally NOT passing signerPkp.tokenId - validator is read-only
|
|
726
674
|
);
|
|
727
675
|
if (this.config.debug) {
|
|
728
676
|
console.log(` LIT Action Success: ${litResult.success}`);
|
|
@@ -781,7 +729,7 @@ class LitOps {
|
|
|
781
729
|
console.log(" š Verifying signature authenticity...");
|
|
782
730
|
}
|
|
783
731
|
try {
|
|
784
|
-
// Compute
|
|
732
|
+
// Compute PKP address from public key (publicKey already includes 0x prefix)
|
|
785
733
|
const cleanPublicKey = signerPkp.publicKey.startsWith("0x")
|
|
786
734
|
? signerPkp.publicKey
|
|
787
735
|
: `0x${signerPkp.publicKey}`;
|
|
@@ -929,24 +877,10 @@ class LitOps {
|
|
|
929
877
|
litActionCids: litActionCids,
|
|
930
878
|
}),
|
|
931
879
|
}, timeoutMs);
|
|
932
|
-
// Read response body first (whether success or error)
|
|
933
|
-
const responseText = await response.text();
|
|
934
|
-
let result;
|
|
935
|
-
try {
|
|
936
|
-
result = JSON.parse(responseText);
|
|
937
|
-
}
|
|
938
|
-
catch {
|
|
939
|
-
// If response is not JSON, treat as plain text error
|
|
940
|
-
if (!response.ok) {
|
|
941
|
-
throw new Error(`Service request failed: ${response.status} ${response.statusText} - ${responseText}`);
|
|
942
|
-
}
|
|
943
|
-
throw new Error(`Invalid JSON response from service: ${responseText}`);
|
|
944
|
-
}
|
|
945
880
|
if (!response.ok) {
|
|
946
|
-
|
|
947
|
-
const errorDetails = result.error || result.message || response.statusText;
|
|
948
|
-
throw new Error(`Service request failed: ${response.status} ${errorDetails}`);
|
|
881
|
+
throw new Error(`Service request failed: ${response.status} ${response.statusText}`);
|
|
949
882
|
}
|
|
883
|
+
const result = (await response.json());
|
|
950
884
|
const duration = Date.now() - startTime;
|
|
951
885
|
// The service may wrap the LitOps result as { success, data }
|
|
952
886
|
// Unwrap if needed to maintain a stable SDK return shape
|
|
@@ -1138,16 +1072,8 @@ class LitOps {
|
|
|
1138
1072
|
console.log(` - pkpTokenId startsWith '0x': ${pkpData.tokenId.startsWith("0x")}`);
|
|
1139
1073
|
console.log(` - litActionCidHex (expectedCid): "${litActionCidHex}"`);
|
|
1140
1074
|
console.log(` - validatorPkp: "${validatorPkp}"`);
|
|
1141
|
-
// Get validator version and contract info from config
|
|
1142
|
-
const validatorVersion = this.config.validatorVersion;
|
|
1143
|
-
const ethRpcUrl = this.config.ethRpcUrl;
|
|
1144
|
-
const pkpValidationRegistry = this.config.pkpValidationRegistry;
|
|
1145
1075
|
validationResult = await this.validatePKPSecurity(pkpData.tokenId, litActionCidHex, // Pass hex format CID
|
|
1146
|
-
validatorPkp, signer
|
|
1147
|
-
validatorVersion,
|
|
1148
|
-
ethRpcUrl,
|
|
1149
|
-
pkpValidationRegistry,
|
|
1150
|
-
});
|
|
1076
|
+
validatorPkp, signer);
|
|
1151
1077
|
// If validation succeeds, break out of retry loop
|
|
1152
1078
|
if (validationResult.success) {
|
|
1153
1079
|
if (this.config.debug && attempt > 1) {
|
|
@@ -1569,19 +1495,10 @@ class LitOps {
|
|
|
1569
1495
|
if (!litActionInfo || !litActionInfo.cid || !litActionInfo.pkp) {
|
|
1570
1496
|
throw new Error("UCD mint validator LIT Action not found in registry");
|
|
1571
1497
|
}
|
|
1572
|
-
// CRITICAL: Use validator PKP details from registry (not loan PKP)
|
|
1573
|
-
// The validator PKP is the one that signs mint authorization messages
|
|
1574
|
-
const validatorPkpTokenId = litActionInfo.pkp.tokenId;
|
|
1575
|
-
const validatorCid = litActionInfo.cid;
|
|
1576
|
-
const validatorPkpPublicKey = litActionInfo.pkp.publicKey;
|
|
1577
|
-
const validatorPkpEthAddress = litActionInfo.pkp.ethAddress;
|
|
1578
1498
|
if (this.config.debug) {
|
|
1579
1499
|
console.log("š” Calling UCD Mint Validator LIT Action:");
|
|
1580
1500
|
console.log(" Network:", this.config.network);
|
|
1581
|
-
console.log("
|
|
1582
|
-
console.log(" Validator PKP Token ID:", validatorPkpTokenId);
|
|
1583
|
-
console.log(" Validator PKP Public Key:", validatorPkpPublicKey);
|
|
1584
|
-
console.log(" Validator PKP ETH Address:", validatorPkpEthAddress);
|
|
1501
|
+
console.log(" CID:", litActionInfo.cid);
|
|
1585
1502
|
console.log(" Position:", request.authMessage.positionId);
|
|
1586
1503
|
console.log(" Amount:", request.authMessage.amount);
|
|
1587
1504
|
console.log(" Timestamp:", request.authMessage.timestamp);
|
|
@@ -1604,7 +1521,7 @@ class LitOps {
|
|
|
1604
1521
|
chain = "sepolia";
|
|
1605
1522
|
bitcoinProviderUrl =
|
|
1606
1523
|
process.env.BITCOIN_PROVIDER_URL ||
|
|
1607
|
-
"https://diamond-hands-btc-faucet-
|
|
1524
|
+
"https://diamond-hands-btc-faucet-jw-b86e9451a147.herokuapp.com/api";
|
|
1608
1525
|
break;
|
|
1609
1526
|
case 1337: // Hardhat local testnet (actual deployment chainId)
|
|
1610
1527
|
case 31337: // Hardhat local testnet (standard default)
|
|
@@ -1638,14 +1555,10 @@ class LitOps {
|
|
|
1638
1555
|
mode: request.authMessage.mode,
|
|
1639
1556
|
},
|
|
1640
1557
|
amount: request.authMessage.amount,
|
|
1641
|
-
//
|
|
1558
|
+
// Contracts must be at top level to become globalThis.contractAddresses in LIT Action
|
|
1642
1559
|
...(request.authMessage.contractAddresses && {
|
|
1643
1560
|
contractAddresses: request.authMessage.contractAddresses,
|
|
1644
1561
|
}),
|
|
1645
|
-
// Price providers with API keys for faster price fetching
|
|
1646
|
-
...(request.priceProviders && {
|
|
1647
|
-
priceProviders: request.priceProviders,
|
|
1648
|
-
}),
|
|
1649
1562
|
};
|
|
1650
1563
|
// Add custom RPC URL for local development (ngrok tunnels)
|
|
1651
1564
|
if (request.customRpcUrl) {
|
|
@@ -1654,115 +1567,15 @@ class LitOps {
|
|
|
1654
1567
|
console.log(" Custom RPC URL:", request.customRpcUrl);
|
|
1655
1568
|
}
|
|
1656
1569
|
}
|
|
1657
|
-
//
|
|
1658
|
-
|
|
1659
|
-
|
|
1660
|
-
|
|
1661
|
-
|
|
1662
|
-
|
|
1663
|
-
|
|
1664
|
-
|
|
1665
|
-
debug: this.config.debug,
|
|
1666
|
-
signer: this.config.signer,
|
|
1667
|
-
network: this.config.network, // Pass LIT network (e.g., 'datil') for PKP authorization check
|
|
1668
|
-
});
|
|
1669
|
-
const isPermitted = await pkpAuthorizer.isActionPermitted(validatorPkpTokenId, validatorCid);
|
|
1670
|
-
console.log("[LitOps] PKP Authorization Status:", isPermitted ? "ā
AUTHORIZED" : "ā NOT AUTHORIZED");
|
|
1671
|
-
if (!isPermitted) {
|
|
1672
|
-
console.warn("[LitOps] ā ļø PKP is not authorized for this Lit Action CID");
|
|
1673
|
-
console.warn("[LitOps] This may cause signing to fail or timeout");
|
|
1674
|
-
console.warn("[LitOps] Session signatures may use wildcard authorization instead");
|
|
1675
|
-
}
|
|
1676
|
-
// Get comprehensive permission check for debugging
|
|
1677
|
-
const permissionCheck = await pkpAuthorizer.checkPermissions(validatorPkpTokenId, validatorCid);
|
|
1678
|
-
console.log("[LitOps] Permitted Actions Count:", permissionCheck.permittedActions.length);
|
|
1679
|
-
console.log("[LitOps] CID in Permitted List:", permissionCheck.isPermitted);
|
|
1680
|
-
if (permissionCheck.permittedActions.length > 0) {
|
|
1681
|
-
console.log("[LitOps] Sample Permitted Actions:", permissionCheck.permittedActions.slice(0, 3));
|
|
1682
|
-
}
|
|
1683
|
-
}
|
|
1684
|
-
catch (authError) {
|
|
1685
|
-
console.warn("[LitOps] ā ļø Failed to check PKP authorization:", authError instanceof Error ? authError.message : String(authError));
|
|
1686
|
-
console.warn("[LitOps] Continuing with execution - may use wildcard authorization");
|
|
1687
|
-
}
|
|
1688
|
-
console.log("[LitOps] ================================");
|
|
1689
|
-
}
|
|
1690
|
-
else {
|
|
1691
|
-
console.log("[LitOps] ā ļø Skipping PKP authorization check (CID or tokenId missing)");
|
|
1692
|
-
if (!validatorCid) {
|
|
1693
|
-
console.log("[LitOps] Validator CID:", validatorCid);
|
|
1694
|
-
}
|
|
1695
|
-
if (!validatorPkpTokenId) {
|
|
1696
|
-
console.log("[LitOps] Validator PKP Token ID:", validatorPkpTokenId);
|
|
1697
|
-
}
|
|
1698
|
-
}
|
|
1699
|
-
// CRITICAL: Use validator PKP token ID (not loan PKP)
|
|
1700
|
-
// Session signatures must authorize the validator PKP to sign, not the loan PKP
|
|
1701
|
-
// PKP token ID should already be in decimal format from the registry
|
|
1702
|
-
// Don't normalize it - session-signature-manager will handle the conversion to hex
|
|
1703
|
-
// The registry stores token IDs as decimal strings, and session-signature-manager
|
|
1704
|
-
// expects decimal input which it then converts to hex for LitPKPResource
|
|
1705
|
-
const normalizedPkpTokenId = validatorPkpTokenId;
|
|
1706
|
-
// Check if we should use local code execution
|
|
1707
|
-
// CRITICAL: If we have a registry CID, always use IPFS mode
|
|
1708
|
-
// Never use local code when we have a deployed registry CID
|
|
1709
|
-
const useLocalCode = this.config.litActionExecution === 'local' && !validatorCid;
|
|
1710
|
-
if (this.config.debug) {
|
|
1711
|
-
console.log("š [DEBUG] litActionExecution config:", this.config.litActionExecution);
|
|
1712
|
-
console.log("š [DEBUG] Validator CID available:", validatorCid);
|
|
1713
|
-
console.log("š [DEBUG] useLocalCode:", useLocalCode, "(ignored if registry CID exists)");
|
|
1714
|
-
}
|
|
1715
|
-
let result;
|
|
1716
|
-
if (useLocalCode) {
|
|
1717
|
-
// Only use local code if NO registry CID is available (shouldn't happen in production)
|
|
1718
|
-
// Read code from local dist file
|
|
1719
|
-
const fs = require('fs');
|
|
1720
|
-
const path = require('path');
|
|
1721
|
-
// Try multiple possible paths
|
|
1722
|
-
const possiblePaths = [
|
|
1723
|
-
path.join(__dirname, '../../lit-actions/dist/ucd-mint-validator.action.js'),
|
|
1724
|
-
path.join(process.cwd(), 'lit-actions/dist/ucd-mint-validator.action.js'),
|
|
1725
|
-
path.join(process.cwd(), '../lit-actions/dist/ucd-mint-validator.action.js'),
|
|
1726
|
-
];
|
|
1727
|
-
let codePath;
|
|
1728
|
-
for (const p of possiblePaths) {
|
|
1729
|
-
if (fs.existsSync(p)) {
|
|
1730
|
-
codePath = p;
|
|
1731
|
-
break;
|
|
1732
|
-
}
|
|
1733
|
-
}
|
|
1734
|
-
if (!codePath) {
|
|
1735
|
-
throw new Error(`Local LIT action code not found. Tried: ${possiblePaths.join(', ')}. Please build lit-actions first.`);
|
|
1736
|
-
}
|
|
1737
|
-
const code = fs.readFileSync(codePath, 'utf8');
|
|
1738
|
-
if (this.config.debug) {
|
|
1739
|
-
console.log("š¦ Using LOCAL LIT Action code (not IPFS)");
|
|
1740
|
-
console.log(" Code path:", codePath);
|
|
1741
|
-
console.log(" Code size:", code.length, "bytes");
|
|
1742
|
-
}
|
|
1743
|
-
result = await this.executeActionFromCode(code, validatorPkpPublicKey, // Use validator PKP public key
|
|
1744
|
-
litActionParams, this.config.signer, normalizedPkpTokenId, // Validator PKP token ID
|
|
1745
|
-
validatorCid // Validator CID for authorization validation
|
|
1746
|
-
);
|
|
1747
|
-
}
|
|
1748
|
-
else {
|
|
1749
|
-
// Always use IPFS mode when we have a registry CID
|
|
1750
|
-
// This ensures the Lit SDK uses the correct CID from the registry for authorization
|
|
1751
|
-
// Execute LIT Action (single attempt - retry logic is in SDK layer)
|
|
1752
|
-
// CRITICAL: Pass validator PKP token ID for session signature PKP scoping (fixes signEcdsa timeout)
|
|
1753
|
-
// Use normalized decimal format for consistent conversion in session-signature-manager
|
|
1754
|
-
result = await this.actionExecutor.executeAction({
|
|
1755
|
-
cid: validatorCid, // Use validator CID from registry
|
|
1756
|
-
pkpPublicKey: validatorPkpPublicKey, // Use validator PKP public key
|
|
1757
|
-
params: litActionParams,
|
|
1758
|
-
signer: this.config.signer,
|
|
1759
|
-
pkpTokenId: normalizedPkpTokenId, // Validator PKP token ID (decimal string)
|
|
1760
|
-
pkpEthAddress: validatorPkpEthAddress, // Validator PKP ETH address for capacity credit delegation
|
|
1761
|
-
}, litClient);
|
|
1762
|
-
}
|
|
1570
|
+
// Execute LIT Action (single attempt - retry logic is in SDK layer)
|
|
1571
|
+
const result = await this.actionExecutor.executeAction({
|
|
1572
|
+
cid: litActionInfo.cid,
|
|
1573
|
+
pkpPublicKey: litActionInfo.pkp.publicKey,
|
|
1574
|
+
params: litActionParams,
|
|
1575
|
+
signer: this.config.signer,
|
|
1576
|
+
priceProviders: request.priceProviders, // Pass price provider API keys (standalone mode)
|
|
1577
|
+
}, litClient);
|
|
1763
1578
|
if (this.config.debug) {
|
|
1764
|
-
console.log("š [DEBUG] litActionParams passed to LIT Action:", JSON.stringify(litActionParams, null, 2));
|
|
1765
|
-
console.log("š [DEBUG] contractAddresses in litActionParams:", litActionParams.contractAddresses);
|
|
1766
1579
|
console.log("š„ LIT Action response:", {
|
|
1767
1580
|
success: result.success,
|
|
1768
1581
|
hasSignature: !!result.signatures,
|
|
@@ -1802,8 +1615,6 @@ class LitOps {
|
|
|
1802
1615
|
newCollateral: responseData?.newCollateral,
|
|
1803
1616
|
btcPrice: responseData?.btcPrice,
|
|
1804
1617
|
authorizedSpendsHash: responseData?.authorizedSpendsHash,
|
|
1805
|
-
ucdDebtHash: responseData?.ucdDebtHash,
|
|
1806
|
-
contractBundleHash: responseData?.contractBundleHash,
|
|
1807
1618
|
timestamp: responseData?.timestamp,
|
|
1808
1619
|
reason: responseData?.reason,
|
|
1809
1620
|
failedStep: responseData?.failedStep,
|
|
@@ -1816,298 +1627,6 @@ class LitOps {
|
|
|
1816
1627
|
}
|
|
1817
1628
|
return returnValue;
|
|
1818
1629
|
}
|
|
1819
|
-
/**
|
|
1820
|
-
* Request extend position authorization from Extend Position Validator LIT Action
|
|
1821
|
-
*
|
|
1822
|
-
* In SERVICE mode: Delegates to lit-ops-server
|
|
1823
|
-
* In STANDALONE mode: Executes LIT action locally
|
|
1824
|
-
*
|
|
1825
|
-
* @param request - Authorization request with authMessage and userSignature
|
|
1826
|
-
* @returns Extend authorization response from LIT Action
|
|
1827
|
-
*/
|
|
1828
|
-
async requestExtendAuthorization(request) {
|
|
1829
|
-
// In SERVICE mode, delegate to lit-ops-server
|
|
1830
|
-
if (this.config.mode === "service") {
|
|
1831
|
-
return this.requestExtendAuthorizationViaService(request);
|
|
1832
|
-
}
|
|
1833
|
-
return this.requestExtendAuthorizationStandalone(request);
|
|
1834
|
-
}
|
|
1835
|
-
/**
|
|
1836
|
-
* Request extend authorization via lit-ops-server (SERVICE mode)
|
|
1837
|
-
*/
|
|
1838
|
-
async requestExtendAuthorizationViaService(request) {
|
|
1839
|
-
if (!this.config.serviceEndpoint) {
|
|
1840
|
-
throw new Error("Service endpoint not configured for service mode");
|
|
1841
|
-
}
|
|
1842
|
-
const url = `${this.config.serviceEndpoint}/api/lit/extend/authorize`;
|
|
1843
|
-
if (this.config.debug) {
|
|
1844
|
-
console.log("š Requesting extend authorization via service:", url);
|
|
1845
|
-
console.log(" Position ID:", request.authMessage.positionId);
|
|
1846
|
-
console.log(" New Term:", request.authMessage.newTerm);
|
|
1847
|
-
}
|
|
1848
|
-
try {
|
|
1849
|
-
const response = await fetch(url, {
|
|
1850
|
-
method: "POST",
|
|
1851
|
-
headers: {
|
|
1852
|
-
"Content-Type": "application/json",
|
|
1853
|
-
},
|
|
1854
|
-
body: JSON.stringify({
|
|
1855
|
-
authMessage: request.authMessage,
|
|
1856
|
-
userSignature: request.userSignature,
|
|
1857
|
-
customRpcUrl: request.customRpcUrl,
|
|
1858
|
-
customBitcoinRpcUrl: request.customBitcoinRpcUrl,
|
|
1859
|
-
}),
|
|
1860
|
-
});
|
|
1861
|
-
if (!response.ok) {
|
|
1862
|
-
const errorText = await response.text();
|
|
1863
|
-
throw new Error(`Service error (${response.status}): ${errorText}`);
|
|
1864
|
-
}
|
|
1865
|
-
const envelope = await response.json();
|
|
1866
|
-
if (envelope.success && envelope.data) {
|
|
1867
|
-
return envelope.data;
|
|
1868
|
-
}
|
|
1869
|
-
else if (!envelope.success && envelope.error) {
|
|
1870
|
-
return {
|
|
1871
|
-
approved: false,
|
|
1872
|
-
error: envelope.error,
|
|
1873
|
-
reason: "Service returned error",
|
|
1874
|
-
};
|
|
1875
|
-
}
|
|
1876
|
-
return envelope;
|
|
1877
|
-
}
|
|
1878
|
-
catch (error) {
|
|
1879
|
-
if (this.config.debug) {
|
|
1880
|
-
console.error("ā Service extend authorization failed:", error);
|
|
1881
|
-
}
|
|
1882
|
-
return {
|
|
1883
|
-
approved: false,
|
|
1884
|
-
error: error instanceof Error ? error.message : String(error),
|
|
1885
|
-
reason: "Service request failed",
|
|
1886
|
-
};
|
|
1887
|
-
}
|
|
1888
|
-
}
|
|
1889
|
-
/**
|
|
1890
|
-
* Request extend authorization locally (STANDALONE mode)
|
|
1891
|
-
*/
|
|
1892
|
-
async requestExtendAuthorizationStandalone(request) {
|
|
1893
|
-
// Get LIT Action info from registry
|
|
1894
|
-
const litActions = this.config.network === "datil"
|
|
1895
|
-
? dh_lit_actions_1.DH_LIT_ACTIONS_DATIL
|
|
1896
|
-
: (() => {
|
|
1897
|
-
throw new Error("Unsupported LIT network");
|
|
1898
|
-
})();
|
|
1899
|
-
// Note: extendPositionValidator needs to be added to registry
|
|
1900
|
-
// For now, we'll throw an error if not found
|
|
1901
|
-
const litActionInfo = litActions.extendPositionValidator;
|
|
1902
|
-
if (!litActionInfo || !litActionInfo.cid || !litActionInfo.pkp) {
|
|
1903
|
-
throw new Error("Extend position validator LIT Action not found in registry");
|
|
1904
|
-
}
|
|
1905
|
-
if (this.config.debug) {
|
|
1906
|
-
console.log("š” Calling Extend Position Validator LIT Action:");
|
|
1907
|
-
console.log(" Network:", this.config.network);
|
|
1908
|
-
console.log(" CID:", litActionInfo.cid);
|
|
1909
|
-
console.log(" Position:", request.authMessage.positionId);
|
|
1910
|
-
console.log(" New Term:", request.authMessage.newTerm);
|
|
1911
|
-
}
|
|
1912
|
-
// Verify PKP authorization before executing LIT Action
|
|
1913
|
-
if (litActionInfo.cid && litActionInfo.pkp.tokenId) {
|
|
1914
|
-
console.log("[LitOps] ======= PKP Authorization Check =======");
|
|
1915
|
-
console.log("[LitOps] PKP Token ID:", litActionInfo.pkp.tokenId);
|
|
1916
|
-
console.log("[LitOps] Lit Action CID:", litActionInfo.cid);
|
|
1917
|
-
try {
|
|
1918
|
-
const pkpAuthorizer = new pkp_authorizer_module_1.PKPAuthorizer({
|
|
1919
|
-
debug: this.config.debug,
|
|
1920
|
-
signer: this.config.signer,
|
|
1921
|
-
network: this.config.network, // Pass LIT network (e.g., 'datil') for PKP authorization check
|
|
1922
|
-
});
|
|
1923
|
-
const isPermitted = await pkpAuthorizer.isActionPermitted(litActionInfo.pkp.tokenId, litActionInfo.cid);
|
|
1924
|
-
console.log("[LitOps] PKP Authorization Status:", isPermitted ? "ā
AUTHORIZED" : "ā NOT AUTHORIZED");
|
|
1925
|
-
if (!isPermitted) {
|
|
1926
|
-
console.warn("[LitOps] ā ļø PKP is not authorized for this Lit Action CID");
|
|
1927
|
-
console.warn("[LitOps] This may cause signing to fail or timeout");
|
|
1928
|
-
console.warn("[LitOps] Session signatures may use wildcard authorization instead");
|
|
1929
|
-
}
|
|
1930
|
-
// Get comprehensive permission check for debugging
|
|
1931
|
-
const permissionCheck = await pkpAuthorizer.checkPermissions(litActionInfo.pkp.tokenId, litActionInfo.cid);
|
|
1932
|
-
console.log("[LitOps] Permitted Actions Count:", permissionCheck.permittedActions.length);
|
|
1933
|
-
console.log("[LitOps] CID in Permitted List:", permissionCheck.isPermitted);
|
|
1934
|
-
if (permissionCheck.permittedActions.length > 0) {
|
|
1935
|
-
console.log("[LitOps] Sample Permitted Actions:", permissionCheck.permittedActions.slice(0, 3));
|
|
1936
|
-
}
|
|
1937
|
-
}
|
|
1938
|
-
catch (authError) {
|
|
1939
|
-
console.warn("[LitOps] ā ļø Failed to check PKP authorization:", authError instanceof Error ? authError.message : String(authError));
|
|
1940
|
-
console.warn("[LitOps] Continuing with execution - may use wildcard authorization");
|
|
1941
|
-
}
|
|
1942
|
-
console.log("[LitOps] ================================");
|
|
1943
|
-
}
|
|
1944
|
-
else {
|
|
1945
|
-
console.log("[LitOps] ā ļø Skipping PKP authorization check (CID or tokenId missing)");
|
|
1946
|
-
if (!litActionInfo.cid) {
|
|
1947
|
-
console.log("[LitOps] CID:", litActionInfo.cid);
|
|
1948
|
-
}
|
|
1949
|
-
if (!litActionInfo.pkp.tokenId) {
|
|
1950
|
-
console.log("[LitOps] PKP Token ID:", litActionInfo.pkp.tokenId);
|
|
1951
|
-
}
|
|
1952
|
-
}
|
|
1953
|
-
// Get LIT client for execution
|
|
1954
|
-
const litClient = await this.clientManager.getClient({
|
|
1955
|
-
litNetwork: this.config.network,
|
|
1956
|
-
debug: this.config.debug,
|
|
1957
|
-
});
|
|
1958
|
-
// Determine chain and Bitcoin provider from chainId
|
|
1959
|
-
let chain;
|
|
1960
|
-
let bitcoinProviderUrl;
|
|
1961
|
-
switch (request.authMessage.chainId) {
|
|
1962
|
-
case 1: // Ethereum mainnet
|
|
1963
|
-
chain = "ethereum";
|
|
1964
|
-
bitcoinProviderUrl =
|
|
1965
|
-
process.env.BITCOIN_PROVIDER_URL || "https://mempool.space/api";
|
|
1966
|
-
break;
|
|
1967
|
-
case 11155111: // Sepolia testnet
|
|
1968
|
-
chain = "sepolia";
|
|
1969
|
-
bitcoinProviderUrl =
|
|
1970
|
-
process.env.BITCOIN_PROVIDER_URL ||
|
|
1971
|
-
"https://diamond-hands-btc-faucet-6b39a1072059.herokuapp.com/api/esplora";
|
|
1972
|
-
break;
|
|
1973
|
-
case 1337: // Hardhat local testnet (actual deployment chainId)
|
|
1974
|
-
case 31337: // Hardhat local testnet (standard default)
|
|
1975
|
-
chain = "hardhat";
|
|
1976
|
-
bitcoinProviderUrl =
|
|
1977
|
-
process.env.BITCOIN_PROVIDER_URL || "http://127.0.0.1:18443";
|
|
1978
|
-
break;
|
|
1979
|
-
default:
|
|
1980
|
-
throw new Error(`Unsupported chainId: ${request.authMessage.chainId}`);
|
|
1981
|
-
}
|
|
1982
|
-
if (request.customBitcoinRpcUrl) {
|
|
1983
|
-
bitcoinProviderUrl = request.customBitcoinRpcUrl;
|
|
1984
|
-
if (this.config.debug) {
|
|
1985
|
-
console.log(" Custom Bitcoin RPC URL:", request.customBitcoinRpcUrl);
|
|
1986
|
-
}
|
|
1987
|
-
}
|
|
1988
|
-
const litActionParams = {
|
|
1989
|
-
chain,
|
|
1990
|
-
bitcoinProviderUrl,
|
|
1991
|
-
auth: {
|
|
1992
|
-
positionId: request.authMessage.positionId,
|
|
1993
|
-
timestamp: request.authMessage.timestamp,
|
|
1994
|
-
chainId: request.authMessage.chainId,
|
|
1995
|
-
newTerm: request.authMessage.newTerm,
|
|
1996
|
-
action: request.authMessage.action,
|
|
1997
|
-
signature: request.userSignature,
|
|
1998
|
-
mode: request.authMessage.mode,
|
|
1999
|
-
},
|
|
2000
|
-
selectedTerm: request.authMessage.newTerm,
|
|
2001
|
-
// Contract addresses must be at top level to become globalThis.contractAddresses in LIT Action
|
|
2002
|
-
...(request.authMessage.contractAddresses && {
|
|
2003
|
-
contractAddresses: request.authMessage.contractAddresses,
|
|
2004
|
-
}),
|
|
2005
|
-
// Price providers with API keys for faster price fetching
|
|
2006
|
-
...(request.priceProviders && {
|
|
2007
|
-
priceProviders: request.priceProviders,
|
|
2008
|
-
}),
|
|
2009
|
-
};
|
|
2010
|
-
// Debug: Log priceProviders to verify they're being passed
|
|
2011
|
-
if (this.config.debug) {
|
|
2012
|
-
console.log(" Price Providers:", request.priceProviders);
|
|
2013
|
-
console.log(" Price Providers in litActionParams:", litActionParams.priceProviders);
|
|
2014
|
-
}
|
|
2015
|
-
if (request.customRpcUrl) {
|
|
2016
|
-
litActionParams.customRpcUrl = request.customRpcUrl;
|
|
2017
|
-
}
|
|
2018
|
-
// PKP token ID should already be in decimal format from the registry
|
|
2019
|
-
// Don't normalize it - session-signature-manager will handle the conversion to hex
|
|
2020
|
-
// The registry stores token IDs as decimal strings, and session-signature-manager
|
|
2021
|
-
// expects decimal input which it then converts to hex for LitPKPResource
|
|
2022
|
-
const normalizedPkpTokenId = litActionInfo.pkp.tokenId;
|
|
2023
|
-
// Check if we should use local code execution
|
|
2024
|
-
// CRITICAL: If we have a registry CID, always use IPFS mode
|
|
2025
|
-
// Never use local code when we have a deployed registry CID
|
|
2026
|
-
const useLocalCode = this.config.litActionExecution === 'local' && !litActionInfo.cid;
|
|
2027
|
-
if (this.config.debug) {
|
|
2028
|
-
console.log("š [DEBUG] litActionExecution config:", this.config.litActionExecution);
|
|
2029
|
-
console.log("š [DEBUG] Registry CID available:", litActionInfo.cid);
|
|
2030
|
-
console.log("š [DEBUG] useLocalCode:", useLocalCode, "(ignored if registry CID exists)");
|
|
2031
|
-
}
|
|
2032
|
-
let result;
|
|
2033
|
-
if (useLocalCode) {
|
|
2034
|
-
// Only use local code if NO registry CID is available (shouldn't happen in production)
|
|
2035
|
-
// Read code from local dist file
|
|
2036
|
-
const fs = require('fs');
|
|
2037
|
-
const path = require('path');
|
|
2038
|
-
// Try multiple possible paths
|
|
2039
|
-
const possiblePaths = [
|
|
2040
|
-
path.join(__dirname, '../../lit-actions/dist/extend-position-validator.action.js'),
|
|
2041
|
-
path.join(process.cwd(), 'lit-actions/dist/extend-position-validator.action.js'),
|
|
2042
|
-
path.join(process.cwd(), '../lit-actions/dist/extend-position-validator.action.js'),
|
|
2043
|
-
];
|
|
2044
|
-
let codePath;
|
|
2045
|
-
for (const p of possiblePaths) {
|
|
2046
|
-
if (fs.existsSync(p)) {
|
|
2047
|
-
codePath = p;
|
|
2048
|
-
break;
|
|
2049
|
-
}
|
|
2050
|
-
}
|
|
2051
|
-
if (!codePath) {
|
|
2052
|
-
throw new Error(`Local LIT action code not found. Tried: ${possiblePaths.join(', ')}. Please build lit-actions first.`);
|
|
2053
|
-
}
|
|
2054
|
-
const code = fs.readFileSync(codePath, 'utf8');
|
|
2055
|
-
if (this.config.debug) {
|
|
2056
|
-
console.log("š¦ Using LOCAL LIT Action code (not IPFS)");
|
|
2057
|
-
console.log(" Code path:", codePath);
|
|
2058
|
-
console.log(" Code size:", code.length, "bytes");
|
|
2059
|
-
}
|
|
2060
|
-
result = await this.executeActionFromCode(code, litActionInfo.pkp.publicKey, litActionParams, this.config.signer, normalizedPkpTokenId, // Normalized to decimal string for consistent handling
|
|
2061
|
-
litActionInfo.cid // Still provide CID for authorization validation
|
|
2062
|
-
);
|
|
2063
|
-
}
|
|
2064
|
-
else {
|
|
2065
|
-
// Always use IPFS mode when we have a registry CID
|
|
2066
|
-
// This ensures the Lit SDK uses the correct CID from the registry for authorization
|
|
2067
|
-
// Execute LIT Action (single attempt - retry logic is in SDK layer)
|
|
2068
|
-
// CRITICAL: Pass pkpTokenId for session signature PKP scoping (fixes signEcdsa timeout)
|
|
2069
|
-
// Use normalized decimal format for consistent conversion in session-signature-manager
|
|
2070
|
-
result = await this.actionExecutor.executeAction({
|
|
2071
|
-
cid: litActionInfo.cid, // Use registry CID
|
|
2072
|
-
pkpPublicKey: litActionInfo.pkp.publicKey,
|
|
2073
|
-
params: litActionParams,
|
|
2074
|
-
signer: this.config.signer,
|
|
2075
|
-
pkpTokenId: normalizedPkpTokenId, // Normalized to decimal string for consistent handling
|
|
2076
|
-
pkpEthAddress: litActionInfo.pkp.ethAddress, // Required for capacity credit delegation
|
|
2077
|
-
}, litClient);
|
|
2078
|
-
}
|
|
2079
|
-
let responseData = result.response;
|
|
2080
|
-
if (typeof result.response === "string") {
|
|
2081
|
-
try {
|
|
2082
|
-
responseData = JSON.parse(result.response);
|
|
2083
|
-
}
|
|
2084
|
-
catch (e) {
|
|
2085
|
-
// Ignore parse errors
|
|
2086
|
-
}
|
|
2087
|
-
}
|
|
2088
|
-
// Handle signature: prefer LIT SDK format (result.signatures), fall back to responseData.signature
|
|
2089
|
-
let signature;
|
|
2090
|
-
if (result.signatures) {
|
|
2091
|
-
signature = JSON.stringify(result.signatures);
|
|
2092
|
-
}
|
|
2093
|
-
else if (responseData?.signature) {
|
|
2094
|
-
signature = responseData.signature;
|
|
2095
|
-
}
|
|
2096
|
-
return {
|
|
2097
|
-
approved: responseData?.approved ?? false,
|
|
2098
|
-
signature,
|
|
2099
|
-
btcPrice: responseData?.btcPrice,
|
|
2100
|
-
availableBTCBalance: responseData?.availableBTCBalance,
|
|
2101
|
-
extensionFee: responseData?.extensionFee,
|
|
2102
|
-
newTotalDebt: responseData?.newTotalDebt,
|
|
2103
|
-
newCollateralRatioBps: responseData?.newCollateralRatioBps,
|
|
2104
|
-
quantumTimestamp: responseData?.quantumTimestamp,
|
|
2105
|
-
timestamp: responseData?.timestamp,
|
|
2106
|
-
reason: responseData?.reason,
|
|
2107
|
-
failedStep: responseData?.failedStep,
|
|
2108
|
-
error: result.error,
|
|
2109
|
-
};
|
|
2110
|
-
}
|
|
2111
1630
|
/**
|
|
2112
1631
|
* Request BTC withdrawal authorization (dual-mode)
|
|
2113
1632
|
*
|
|
@@ -2135,7 +1654,7 @@ class LitOps {
|
|
|
2135
1654
|
if (!this.config.serviceEndpoint) {
|
|
2136
1655
|
throw new Error("Service endpoint not configured for service mode");
|
|
2137
1656
|
}
|
|
2138
|
-
const url = `${this.config.serviceEndpoint}/api/lit/
|
|
1657
|
+
const url = `${this.config.serviceEndpoint}/api/lit/withdraw-btc/authorize`;
|
|
2139
1658
|
if (this.config.debug) {
|
|
2140
1659
|
console.log("š Requesting withdrawal authorization via service:", url);
|
|
2141
1660
|
console.log(" Position ID:", request.authMessage.positionId);
|
|
@@ -2143,13 +1662,20 @@ class LitOps {
|
|
|
2143
1662
|
console.log(" Address:", request.authMessage.withdrawalAddress);
|
|
2144
1663
|
}
|
|
2145
1664
|
try {
|
|
1665
|
+
// Transform authMessage: SDK uses withdrawalAddress, server expects destinationAddress
|
|
1666
|
+
const transformedAuthMessage = {
|
|
1667
|
+
...request.authMessage,
|
|
1668
|
+
destinationAddress: request.authMessage.withdrawalAddress,
|
|
1669
|
+
};
|
|
1670
|
+
// Remove withdrawalAddress from the transformed message
|
|
1671
|
+
delete transformedAuthMessage.withdrawalAddress;
|
|
2146
1672
|
const response = await fetch(url, {
|
|
2147
1673
|
method: "POST",
|
|
2148
1674
|
headers: {
|
|
2149
1675
|
"Content-Type": "application/json",
|
|
2150
1676
|
},
|
|
2151
1677
|
body: JSON.stringify({
|
|
2152
|
-
authMessage:
|
|
1678
|
+
authMessage: transformedAuthMessage,
|
|
2153
1679
|
userSignature: request.userSignature,
|
|
2154
1680
|
customRpcUrl: request.customRpcUrl,
|
|
2155
1681
|
customBitcoinRpcUrl: request.customBitcoinRpcUrl,
|
|
@@ -2163,19 +1689,28 @@ class LitOps {
|
|
|
2163
1689
|
if (this.config.debug) {
|
|
2164
1690
|
console.log("š„ Service response:", envelope);
|
|
2165
1691
|
}
|
|
1692
|
+
// Extract data from envelope (server wraps in { success, data } structure)
|
|
1693
|
+
const result = envelope.data || envelope;
|
|
2166
1694
|
// Return the result from service
|
|
2167
1695
|
return {
|
|
2168
|
-
approved:
|
|
2169
|
-
signature:
|
|
2170
|
-
|
|
2171
|
-
|
|
2172
|
-
|
|
2173
|
-
|
|
2174
|
-
|
|
2175
|
-
|
|
2176
|
-
|
|
2177
|
-
|
|
2178
|
-
|
|
1696
|
+
approved: result.approved ?? false,
|
|
1697
|
+
signature: result.signature,
|
|
1698
|
+
actionHash: result.actionHash,
|
|
1699
|
+
authorizedSpendsHash: result.authorizedSpendsHash,
|
|
1700
|
+
ucdDebtHash: result.ucdDebtHash,
|
|
1701
|
+
contractBundleHash: result.contractBundleHash,
|
|
1702
|
+
totalDeduction: result.totalDeduction,
|
|
1703
|
+
remainingCollateral: result.remainingCollateral,
|
|
1704
|
+
newCollateralRatioBps: result.newCollateralRatioBps,
|
|
1705
|
+
destinationAddress: result.destinationAddress,
|
|
1706
|
+
btcPrice: result.btcPrice,
|
|
1707
|
+
timestamp: result.timestamp,
|
|
1708
|
+
utxoTxid: result.utxoTxid,
|
|
1709
|
+
utxoVout: result.utxoVout,
|
|
1710
|
+
utxoSatoshis: result.utxoSatoshis,
|
|
1711
|
+
reason: result.reason,
|
|
1712
|
+
failedStep: result.failedStep,
|
|
1713
|
+
error: result.error,
|
|
2179
1714
|
};
|
|
2180
1715
|
}
|
|
2181
1716
|
catch (error) {
|
|
@@ -2228,7 +1763,7 @@ class LitOps {
|
|
|
2228
1763
|
chain = "sepolia";
|
|
2229
1764
|
bitcoinProviderUrl =
|
|
2230
1765
|
process.env.BITCOIN_PROVIDER_URL ||
|
|
2231
|
-
"https://diamond-hands-btc-faucet-
|
|
1766
|
+
"https://diamond-hands-btc-faucet-jw-b86e9451a147.herokuapp.com/api";
|
|
2232
1767
|
break;
|
|
2233
1768
|
case 1337: // Hardhat local testnet (actual deployment chainId)
|
|
2234
1769
|
case 31337: // Hardhat local testnet (standard default)
|
|
@@ -2262,6 +1797,7 @@ class LitOps {
|
|
|
2262
1797
|
},
|
|
2263
1798
|
// Always pass contractAddresses (undefined in prod mode)
|
|
2264
1799
|
contractAddresses: request.authMessage.contractAddresses,
|
|
1800
|
+
priceProviders: request.priceProviders, // Pass price provider API keys (standalone mode)
|
|
2265
1801
|
};
|
|
2266
1802
|
// Add custom RPC URL for local development
|
|
2267
1803
|
if (request.customRpcUrl) {
|
|
@@ -2270,21 +1806,12 @@ class LitOps {
|
|
|
2270
1806
|
console.log(" Custom RPC URL:", request.customRpcUrl);
|
|
2271
1807
|
}
|
|
2272
1808
|
}
|
|
2273
|
-
// PKP token ID should already be in decimal format from the registry
|
|
2274
|
-
// Don't normalize it - session-signature-manager will handle the conversion to hex
|
|
2275
|
-
// The registry stores token IDs as decimal strings, and session-signature-manager
|
|
2276
|
-
// expects decimal input which it then converts to hex for LitPKPResource
|
|
2277
|
-
const normalizedPkpTokenId = litActionInfo.pkp.tokenId;
|
|
2278
1809
|
// Execute LIT Action
|
|
2279
|
-
// CRITICAL: Pass pkpTokenId for session signature PKP scoping (fixes signEcdsa timeout)
|
|
2280
|
-
// Use normalized decimal format for consistent conversion in session-signature-manager
|
|
2281
1810
|
const result = await this.actionExecutor.executeAction({
|
|
2282
1811
|
cid: litActionInfo.cid,
|
|
2283
1812
|
pkpPublicKey: litActionInfo.pkp.publicKey,
|
|
2284
1813
|
params: litActionParams,
|
|
2285
1814
|
signer: this.config.signer,
|
|
2286
|
-
pkpTokenId: normalizedPkpTokenId, // Normalized to decimal string for consistent handling
|
|
2287
|
-
pkpEthAddress: litActionInfo.pkp.ethAddress, // Required for capacity credit delegation
|
|
2288
1815
|
}, litClient);
|
|
2289
1816
|
if (this.config.debug) {
|
|
2290
1817
|
console.log("š„ LIT Action response:", {
|
|
@@ -2318,6 +1845,7 @@ class LitOps {
|
|
|
2318
1845
|
actionHash: responseData?.actionHash,
|
|
2319
1846
|
authorizedSpendsHash: responseData?.authorizedSpendsHash,
|
|
2320
1847
|
ucdDebtHash: responseData?.ucdDebtHash,
|
|
1848
|
+
contractBundleHash: responseData?.contractBundleHash, // Binds to specific contract deployment
|
|
2321
1849
|
totalDeduction: responseData?.totalDeduction,
|
|
2322
1850
|
remainingCollateral: responseData?.remainingCollateral,
|
|
2323
1851
|
newCollateralRatioBps: responseData?.newCollateralRatioBps,
|
|
@@ -2336,82 +1864,6 @@ class LitOps {
|
|
|
2336
1864
|
}
|
|
2337
1865
|
return returnValue;
|
|
2338
1866
|
}
|
|
2339
|
-
/**
|
|
2340
|
-
* Request payment authorization from Process Payment Validator LIT Action
|
|
2341
|
-
*
|
|
2342
|
-
* In SERVICE mode: Delegates to lit-ops-server
|
|
2343
|
-
* In STANDALONE mode: Executes LIT action locally
|
|
2344
|
-
*
|
|
2345
|
-
* @param request - Payment authorization request
|
|
2346
|
-
* @returns Payment authorization response from LIT Action
|
|
2347
|
-
*/
|
|
2348
|
-
async requestPaymentAuthorization(request) {
|
|
2349
|
-
// In SERVICE mode, delegate to lit-ops-server
|
|
2350
|
-
if (this.config.mode === "service") {
|
|
2351
|
-
return this.requestPaymentAuthorizationViaService(request);
|
|
2352
|
-
}
|
|
2353
|
-
return this.requestPaymentAuthorizationStandalone(request);
|
|
2354
|
-
}
|
|
2355
|
-
/**
|
|
2356
|
-
* Request payment authorization via lit-ops-server (SERVICE mode)
|
|
2357
|
-
*/
|
|
2358
|
-
async requestPaymentAuthorizationViaService(request) {
|
|
2359
|
-
if (!this.config.serviceEndpoint) {
|
|
2360
|
-
throw new Error("Service endpoint not configured for service mode");
|
|
2361
|
-
}
|
|
2362
|
-
const url = `${this.config.serviceEndpoint}/api/lit/payment/authorize`;
|
|
2363
|
-
if (this.config.debug) {
|
|
2364
|
-
console.log("š Requesting payment authorization via service:", url);
|
|
2365
|
-
console.log(" Position ID:", request.positionId);
|
|
2366
|
-
console.log(" Payment Amount:", request.paymentAmount);
|
|
2367
|
-
console.log(" Price Providers:", request.priceProviders);
|
|
2368
|
-
}
|
|
2369
|
-
const requestBody = {
|
|
2370
|
-
positionId: request.positionId,
|
|
2371
|
-
paymentAmount: request.paymentAmount,
|
|
2372
|
-
chainId: request.chainId,
|
|
2373
|
-
mode: request.mode,
|
|
2374
|
-
contractAddresses: request.contractAddresses,
|
|
2375
|
-
customRpcUrl: request.customRpcUrl,
|
|
2376
|
-
customBitcoinRpcUrl: request.customBitcoinRpcUrl,
|
|
2377
|
-
priceProviders: request.priceProviders,
|
|
2378
|
-
};
|
|
2379
|
-
try {
|
|
2380
|
-
const response = await fetch(url, {
|
|
2381
|
-
method: "POST",
|
|
2382
|
-
headers: {
|
|
2383
|
-
"Content-Type": "application/json",
|
|
2384
|
-
},
|
|
2385
|
-
body: JSON.stringify(requestBody),
|
|
2386
|
-
});
|
|
2387
|
-
if (!response.ok) {
|
|
2388
|
-
const errorText = await response.text();
|
|
2389
|
-
throw new Error(`Service error (${response.status}): ${errorText}`);
|
|
2390
|
-
}
|
|
2391
|
-
const envelope = await response.json();
|
|
2392
|
-
if (envelope.success && envelope.data) {
|
|
2393
|
-
return envelope.data;
|
|
2394
|
-
}
|
|
2395
|
-
else if (!envelope.success && envelope.error) {
|
|
2396
|
-
return {
|
|
2397
|
-
approved: false,
|
|
2398
|
-
error: envelope.error,
|
|
2399
|
-
reason: "Service returned error",
|
|
2400
|
-
};
|
|
2401
|
-
}
|
|
2402
|
-
return envelope;
|
|
2403
|
-
}
|
|
2404
|
-
catch (error) {
|
|
2405
|
-
if (this.config.debug) {
|
|
2406
|
-
console.error("ā Service payment authorization failed:", error);
|
|
2407
|
-
}
|
|
2408
|
-
return {
|
|
2409
|
-
approved: false,
|
|
2410
|
-
error: error instanceof Error ? error.message : String(error),
|
|
2411
|
-
reason: "Service request failed",
|
|
2412
|
-
};
|
|
2413
|
-
}
|
|
2414
|
-
}
|
|
2415
1867
|
/**
|
|
2416
1868
|
* Sign Bitcoin transaction for BTC withdrawal execution (Phase 2)
|
|
2417
1869
|
*
|
|
@@ -2461,23 +1913,25 @@ class LitOps {
|
|
|
2461
1913
|
if (this.config.debug) {
|
|
2462
1914
|
console.log("š„ Service response:", envelope);
|
|
2463
1915
|
}
|
|
1916
|
+
// Extract data from envelope (server wraps in { success, data } structure)
|
|
1917
|
+
const result = envelope.data || envelope;
|
|
2464
1918
|
return {
|
|
2465
|
-
success:
|
|
2466
|
-
unsignedTxHex:
|
|
2467
|
-
sigHash:
|
|
2468
|
-
signature:
|
|
2469
|
-
pkpPublicKey:
|
|
2470
|
-
pkpBtcAddress:
|
|
2471
|
-
destination:
|
|
2472
|
-
userReceivesAmount:
|
|
2473
|
-
networkFee:
|
|
2474
|
-
changeAmount:
|
|
2475
|
-
utxo:
|
|
2476
|
-
authorization:
|
|
2477
|
-
timestamp:
|
|
2478
|
-
action:
|
|
2479
|
-
error:
|
|
2480
|
-
failedStep:
|
|
1919
|
+
success: result.success ?? false,
|
|
1920
|
+
unsignedTxHex: result.unsignedTxHex,
|
|
1921
|
+
sigHash: result.sigHash,
|
|
1922
|
+
signature: result.signature,
|
|
1923
|
+
pkpPublicKey: result.pkpPublicKey,
|
|
1924
|
+
pkpBtcAddress: result.pkpBtcAddress,
|
|
1925
|
+
destination: result.destination,
|
|
1926
|
+
userReceivesAmount: result.userReceivesAmount,
|
|
1927
|
+
networkFee: result.networkFee,
|
|
1928
|
+
changeAmount: result.changeAmount,
|
|
1929
|
+
utxo: result.utxo,
|
|
1930
|
+
authorization: result.authorization,
|
|
1931
|
+
timestamp: result.timestamp,
|
|
1932
|
+
action: result.action,
|
|
1933
|
+
error: result.error,
|
|
1934
|
+
failedStep: result.failedStep,
|
|
2481
1935
|
};
|
|
2482
1936
|
}
|
|
2483
1937
|
catch (error) {
|
|
@@ -2488,206 +1942,6 @@ class LitOps {
|
|
|
2488
1942
|
};
|
|
2489
1943
|
}
|
|
2490
1944
|
}
|
|
2491
|
-
/**
|
|
2492
|
-
* Request payment authorization locally (STANDALONE mode)
|
|
2493
|
-
*/
|
|
2494
|
-
async requestPaymentAuthorizationStandalone(request) {
|
|
2495
|
-
// Get LIT Action info from registry
|
|
2496
|
-
const litActions = this.config.network === "datil"
|
|
2497
|
-
? dh_lit_actions_1.DH_LIT_ACTIONS_DATIL
|
|
2498
|
-
: (() => {
|
|
2499
|
-
throw new Error("Unsupported LIT network");
|
|
2500
|
-
})();
|
|
2501
|
-
const litActionInfo = litActions.processPaymentValidator;
|
|
2502
|
-
if (!litActionInfo || !litActionInfo.cid || !litActionInfo.pkp) {
|
|
2503
|
-
throw new Error("Process payment validator LIT Action not found in registry");
|
|
2504
|
-
}
|
|
2505
|
-
if (this.config.debug) {
|
|
2506
|
-
console.log("š” Calling Process Payment Validator LIT Action:");
|
|
2507
|
-
console.log(" Network:", this.config.network);
|
|
2508
|
-
console.log(" CID:", litActionInfo.cid);
|
|
2509
|
-
console.log(" Position:", request.positionId);
|
|
2510
|
-
console.log(" Payment Amount:", request.paymentAmount);
|
|
2511
|
-
}
|
|
2512
|
-
// Verify PKP authorization before executing LIT Action
|
|
2513
|
-
if (litActionInfo.cid && litActionInfo.pkp.tokenId) {
|
|
2514
|
-
console.log("[LitOps] ======= PKP Authorization Check =======");
|
|
2515
|
-
console.log("[LitOps] PKP Token ID:", litActionInfo.pkp.tokenId);
|
|
2516
|
-
console.log("[LitOps] Lit Action CID:", litActionInfo.cid);
|
|
2517
|
-
try {
|
|
2518
|
-
const pkpAuthorizer = new pkp_authorizer_module_1.PKPAuthorizer({
|
|
2519
|
-
debug: this.config.debug,
|
|
2520
|
-
signer: this.config.signer,
|
|
2521
|
-
network: this.config.network, // Pass LIT network (e.g., 'datil') for PKP authorization check
|
|
2522
|
-
});
|
|
2523
|
-
const isPermitted = await pkpAuthorizer.isActionPermitted(litActionInfo.pkp.tokenId, litActionInfo.cid);
|
|
2524
|
-
console.log("[LitOps] PKP Authorization Status:", isPermitted ? "ā
AUTHORIZED" : "ā NOT AUTHORIZED");
|
|
2525
|
-
if (!isPermitted) {
|
|
2526
|
-
console.warn("[LitOps] ā ļø PKP is not authorized for this Lit Action CID");
|
|
2527
|
-
console.warn("[LitOps] This may cause signing to fail or timeout");
|
|
2528
|
-
console.warn("[LitOps] Session signatures may use wildcard authorization instead");
|
|
2529
|
-
}
|
|
2530
|
-
// Get comprehensive permission check for debugging
|
|
2531
|
-
const permissionCheck = await pkpAuthorizer.checkPermissions(litActionInfo.pkp.tokenId, litActionInfo.cid);
|
|
2532
|
-
console.log("[LitOps] Permitted Actions Count:", permissionCheck.permittedActions.length);
|
|
2533
|
-
console.log("[LitOps] CID in Permitted List:", permissionCheck.isPermitted);
|
|
2534
|
-
if (permissionCheck.permittedActions.length > 0) {
|
|
2535
|
-
console.log("[LitOps] Sample Permitted Actions:", permissionCheck.permittedActions.slice(0, 3));
|
|
2536
|
-
}
|
|
2537
|
-
}
|
|
2538
|
-
catch (authError) {
|
|
2539
|
-
console.warn("[LitOps] ā ļø Failed to check PKP authorization:", authError instanceof Error ? authError.message : String(authError));
|
|
2540
|
-
console.warn("[LitOps] Continuing with execution - may use wildcard authorization");
|
|
2541
|
-
}
|
|
2542
|
-
console.log("[LitOps] ================================");
|
|
2543
|
-
}
|
|
2544
|
-
else {
|
|
2545
|
-
console.log("[LitOps] ā ļø Skipping PKP authorization check (CID or tokenId missing)");
|
|
2546
|
-
if (!litActionInfo.cid) {
|
|
2547
|
-
console.log("[LitOps] CID:", litActionInfo.cid);
|
|
2548
|
-
}
|
|
2549
|
-
if (!litActionInfo.pkp.tokenId) {
|
|
2550
|
-
console.log("[LitOps] PKP Token ID:", litActionInfo.pkp.tokenId);
|
|
2551
|
-
}
|
|
2552
|
-
}
|
|
2553
|
-
// PKP token ID should already be in decimal format from the registry
|
|
2554
|
-
// Don't normalize it - session-signature-manager will handle the conversion to hex
|
|
2555
|
-
// The registry stores token IDs as decimal strings, and session-signature-manager
|
|
2556
|
-
// expects decimal input which it then converts to hex for LitPKPResource
|
|
2557
|
-
const normalizedPkpTokenId = litActionInfo.pkp.tokenId;
|
|
2558
|
-
// Get LIT client for execution
|
|
2559
|
-
const litClient = await this.clientManager.getClient({
|
|
2560
|
-
litNetwork: this.config.network,
|
|
2561
|
-
debug: this.config.debug,
|
|
2562
|
-
});
|
|
2563
|
-
// Determine chain and Bitcoin provider from chainId
|
|
2564
|
-
let chain;
|
|
2565
|
-
let bitcoinProviderUrl;
|
|
2566
|
-
switch (request.chainId) {
|
|
2567
|
-
case 1:
|
|
2568
|
-
chain = "ethereum";
|
|
2569
|
-
bitcoinProviderUrl =
|
|
2570
|
-
process.env.BITCOIN_PROVIDER_URL || "https://mempool.space/api";
|
|
2571
|
-
break;
|
|
2572
|
-
case 11155111:
|
|
2573
|
-
chain = "sepolia";
|
|
2574
|
-
bitcoinProviderUrl =
|
|
2575
|
-
process.env.BITCOIN_PROVIDER_URL ||
|
|
2576
|
-
"https://diamond-hands-btc-faucet-6b39a1072059.herokuapp.com/api/esplora";
|
|
2577
|
-
break;
|
|
2578
|
-
case 1337:
|
|
2579
|
-
case 31337:
|
|
2580
|
-
chain = "hardhat";
|
|
2581
|
-
bitcoinProviderUrl =
|
|
2582
|
-
process.env.BITCOIN_PROVIDER_URL || "http://127.0.0.1:18443";
|
|
2583
|
-
break;
|
|
2584
|
-
default:
|
|
2585
|
-
throw new Error(`Unsupported chainId: ${request.chainId}`);
|
|
2586
|
-
}
|
|
2587
|
-
if (request.customBitcoinRpcUrl) {
|
|
2588
|
-
bitcoinProviderUrl = request.customBitcoinRpcUrl;
|
|
2589
|
-
}
|
|
2590
|
-
// Support both legacy `contracts` (standalone) and newer `contractAddresses`
|
|
2591
|
-
const contractAddresses = request.contractAddresses ?? request.contracts;
|
|
2592
|
-
const litActionParams = {
|
|
2593
|
-
chain,
|
|
2594
|
-
bitcoinProviderUrl,
|
|
2595
|
-
positionId: request.positionId,
|
|
2596
|
-
paymentAmount: request.paymentAmount,
|
|
2597
|
-
...(contractAddresses && {
|
|
2598
|
-
contractAddresses,
|
|
2599
|
-
}),
|
|
2600
|
-
...(request.priceProviders && {
|
|
2601
|
-
priceProviders: request.priceProviders,
|
|
2602
|
-
}),
|
|
2603
|
-
};
|
|
2604
|
-
if (request.customRpcUrl) {
|
|
2605
|
-
litActionParams.customRpcUrl = request.customRpcUrl;
|
|
2606
|
-
}
|
|
2607
|
-
// Check if we should use local code execution
|
|
2608
|
-
// CRITICAL: If we have a registry CID, always use IPFS mode
|
|
2609
|
-
// Never use local code when we have a deployed registry CID
|
|
2610
|
-
const useLocalCode = this.config.litActionExecution === 'local' && !litActionInfo.cid;
|
|
2611
|
-
if (this.config.debug) {
|
|
2612
|
-
console.log("š [DEBUG] litActionExecution config:", this.config.litActionExecution);
|
|
2613
|
-
console.log("š [DEBUG] Registry CID available:", litActionInfo.cid);
|
|
2614
|
-
console.log("š [DEBUG] useLocalCode:", useLocalCode, "(ignored if registry CID exists)");
|
|
2615
|
-
}
|
|
2616
|
-
let result;
|
|
2617
|
-
if (useLocalCode) {
|
|
2618
|
-
// Only use local code if NO registry CID is available (shouldn't happen in production)
|
|
2619
|
-
// Read code from local dist file
|
|
2620
|
-
const fs = require('fs');
|
|
2621
|
-
const path = require('path');
|
|
2622
|
-
// Try multiple possible paths
|
|
2623
|
-
const possiblePaths = [
|
|
2624
|
-
path.join(__dirname, '../../lit-actions/dist/process-payment-validator.action.js'),
|
|
2625
|
-
path.join(process.cwd(), 'lit-actions/dist/process-payment-validator.action.js'),
|
|
2626
|
-
path.join(process.cwd(), '../lit-actions/dist/process-payment-validator.action.js'),
|
|
2627
|
-
];
|
|
2628
|
-
let codePath;
|
|
2629
|
-
for (const p of possiblePaths) {
|
|
2630
|
-
if (fs.existsSync(p)) {
|
|
2631
|
-
codePath = p;
|
|
2632
|
-
break;
|
|
2633
|
-
}
|
|
2634
|
-
}
|
|
2635
|
-
if (!codePath) {
|
|
2636
|
-
throw new Error(`Local LIT action code not found. Tried: ${possiblePaths.join(', ')}. Please build lit-actions first.`);
|
|
2637
|
-
}
|
|
2638
|
-
const code = fs.readFileSync(codePath, 'utf8');
|
|
2639
|
-
if (this.config.debug) {
|
|
2640
|
-
console.log("š¦ Using LOCAL LIT Action code (not IPFS)");
|
|
2641
|
-
console.log(" Code path:", codePath);
|
|
2642
|
-
console.log(" Code size:", code.length, "bytes");
|
|
2643
|
-
}
|
|
2644
|
-
result = await this.executeActionFromCode(code, litActionInfo.pkp.publicKey, litActionParams, this.config.signer, normalizedPkpTokenId, // Normalized to decimal string for consistent handling
|
|
2645
|
-
litActionInfo.cid // Still provide CID for authorization validation
|
|
2646
|
-
);
|
|
2647
|
-
}
|
|
2648
|
-
else {
|
|
2649
|
-
// Always use IPFS mode when we have a registry CID
|
|
2650
|
-
// This ensures the Lit SDK uses the correct CID from the registry for authorization
|
|
2651
|
-
// Execute LIT Action (single attempt - retry logic is in SDK layer)
|
|
2652
|
-
// CRITICAL: Pass pkpTokenId for session signature PKP scoping (fixes signEcdsa timeout)
|
|
2653
|
-
// Use normalized decimal format for consistent conversion in session-signature-manager
|
|
2654
|
-
result = await this.actionExecutor.executeAction({
|
|
2655
|
-
cid: litActionInfo.cid, // Use registry CID
|
|
2656
|
-
pkpPublicKey: litActionInfo.pkp.publicKey,
|
|
2657
|
-
params: litActionParams,
|
|
2658
|
-
signer: this.config.signer,
|
|
2659
|
-
pkpTokenId: normalizedPkpTokenId, // Normalized to decimal string for consistent handling
|
|
2660
|
-
pkpEthAddress: litActionInfo.pkp.ethAddress, // Required for capacity credit delegation
|
|
2661
|
-
}, litClient);
|
|
2662
|
-
}
|
|
2663
|
-
let responseData = result.response;
|
|
2664
|
-
if (typeof result.response === "string") {
|
|
2665
|
-
try {
|
|
2666
|
-
responseData = JSON.parse(result.response);
|
|
2667
|
-
}
|
|
2668
|
-
catch (e) {
|
|
2669
|
-
// Ignore parse errors
|
|
2670
|
-
}
|
|
2671
|
-
}
|
|
2672
|
-
// Handle signature: prefer LIT SDK format (result.signatures), fall back to responseData.signature
|
|
2673
|
-
let signature;
|
|
2674
|
-
if (result.signatures) {
|
|
2675
|
-
signature = JSON.stringify(result.signatures);
|
|
2676
|
-
}
|
|
2677
|
-
else if (responseData?.signature) {
|
|
2678
|
-
signature = responseData.signature;
|
|
2679
|
-
}
|
|
2680
|
-
return {
|
|
2681
|
-
approved: responseData?.approved ?? false,
|
|
2682
|
-
signature,
|
|
2683
|
-
btcPrice: responseData?.btcPrice,
|
|
2684
|
-
paymentAmount: responseData?.paymentAmount,
|
|
2685
|
-
timestamp: responseData?.timestamp,
|
|
2686
|
-
reason: responseData?.reason,
|
|
2687
|
-
failedStep: responseData?.failedStep,
|
|
2688
|
-
error: result.error,
|
|
2689
|
-
};
|
|
2690
|
-
}
|
|
2691
1945
|
/**
|
|
2692
1946
|
* Sign Bitcoin transaction locally (STANDALONE mode)
|
|
2693
1947
|
*/
|
|
@@ -2721,14 +1975,18 @@ class LitOps {
|
|
|
2721
1975
|
const chainId = request.auth.chainId;
|
|
2722
1976
|
switch (chainId) {
|
|
2723
1977
|
case 1: // Ethereum mainnet
|
|
2724
|
-
bitcoinProviderUrl =
|
|
1978
|
+
bitcoinProviderUrl =
|
|
1979
|
+
process.env.BITCOIN_PROVIDER_URL || "https://mempool.space/api";
|
|
2725
1980
|
break;
|
|
2726
1981
|
case 11155111: // Sepolia testnet
|
|
2727
|
-
bitcoinProviderUrl =
|
|
1982
|
+
bitcoinProviderUrl =
|
|
1983
|
+
process.env.BITCOIN_PROVIDER_URL ||
|
|
1984
|
+
"https://diamond-hands-btc-faucet-jw-b86e9451a147.herokuapp.com/api";
|
|
2728
1985
|
break;
|
|
2729
1986
|
case 1337: // Hardhat local testnet (actual deployment chainId)
|
|
2730
1987
|
case 31337: // Hardhat local testnet (standard default)
|
|
2731
|
-
bitcoinProviderUrl =
|
|
1988
|
+
bitcoinProviderUrl =
|
|
1989
|
+
process.env.BITCOIN_PROVIDER_URL || "http://127.0.0.1:18443";
|
|
2732
1990
|
break;
|
|
2733
1991
|
default:
|
|
2734
1992
|
throw new Error(`Unsupported chainId: ${chainId}`);
|
|
@@ -2746,7 +2004,7 @@ class LitOps {
|
|
|
2746
2004
|
bitcoinProviderUrl, // For Bitcoin UTXO queries
|
|
2747
2005
|
auth: request.auth,
|
|
2748
2006
|
publicKey: request.publicKey,
|
|
2749
|
-
|
|
2007
|
+
contractAddresses: request.contractAddresses,
|
|
2750
2008
|
};
|
|
2751
2009
|
// Add custom EVM RPC URL for local development (Hardhat)
|
|
2752
2010
|
if (request.customRpcUrl) {
|
|
@@ -2771,6 +2029,30 @@ class LitOps {
|
|
|
2771
2029
|
hasSignature: !!result.signatures,
|
|
2772
2030
|
error: result.error,
|
|
2773
2031
|
});
|
|
2032
|
+
// Log per-node debug information if available
|
|
2033
|
+
if (result.debug) {
|
|
2034
|
+
console.log("\nš PER-NODE DEBUG INFORMATION:");
|
|
2035
|
+
console.log("=====================================");
|
|
2036
|
+
const debugInfo = result.debug;
|
|
2037
|
+
if (debugInfo.allNodeResponses) {
|
|
2038
|
+
console.log("\nš All Node Responses:");
|
|
2039
|
+
console.log(JSON.stringify(debugInfo.allNodeResponses, null, 2));
|
|
2040
|
+
}
|
|
2041
|
+
if (debugInfo.allNodeLogs) {
|
|
2042
|
+
console.log("\nš All Node Logs:");
|
|
2043
|
+
debugInfo.allNodeLogs.forEach((nodeLog, index) => {
|
|
2044
|
+
console.log(`\n--- Node ${index + 1} ---`);
|
|
2045
|
+
console.log(JSON.stringify(nodeLog, null, 2));
|
|
2046
|
+
});
|
|
2047
|
+
}
|
|
2048
|
+
if (debugInfo.rawNodeHTTPResponses) {
|
|
2049
|
+
console.log("\nš Raw Node HTTP Responses:");
|
|
2050
|
+
console.log(JSON.stringify(debugInfo.rawNodeHTTPResponses, null, 2));
|
|
2051
|
+
}
|
|
2052
|
+
}
|
|
2053
|
+
else {
|
|
2054
|
+
console.log("ā ļø No per-node debug information available in result");
|
|
2055
|
+
}
|
|
2774
2056
|
}
|
|
2775
2057
|
// Parse response if it's a string
|
|
2776
2058
|
let responseData = result.response;
|
|
@@ -2790,7 +2072,7 @@ class LitOps {
|
|
|
2790
2072
|
// Extract combined signature from LIT SDK result
|
|
2791
2073
|
// LIT SDK returns signatures in result.signatures.btcTxSig after combination
|
|
2792
2074
|
let combinedSignature;
|
|
2793
|
-
if (result.signatures && typeof result.signatures ===
|
|
2075
|
+
if (result.signatures && typeof result.signatures === "object") {
|
|
2794
2076
|
const btcTxSig = result.signatures.btcTxSig;
|
|
2795
2077
|
if (btcTxSig && btcTxSig.signature) {
|
|
2796
2078
|
// LIT SDK combined signature
|
|
@@ -2798,7 +2080,7 @@ class LitOps {
|
|
|
2798
2080
|
if (this.config.debug && combinedSignature) {
|
|
2799
2081
|
console.log("ā
Extracted combined signature from LIT SDK:", {
|
|
2800
2082
|
signatureLength: combinedSignature.length,
|
|
2801
|
-
signatureStart: combinedSignature.substring(0, 20) + "..."
|
|
2083
|
+
signatureStart: combinedSignature.substring(0, 20) + "...",
|
|
2802
2084
|
});
|
|
2803
2085
|
}
|
|
2804
2086
|
}
|