@secux/app-btc
Advanced tools
Comparing version 3.2.1 to 3.2.2
@@ -1,1 +0,1 @@ | ||
"use strict";var t,i,e,s,r,n,o,p,a,u,c,h,f=this&&this.__classPrivateFieldSet||function(t,i,e,s,r){if("m"===s)throw new TypeError("Private method is not writable");if("a"===s&&!r)throw new TypeError("Private accessor was defined without a setter");if("function"==typeof i?t!==i||!r:!i.has(t))throw new TypeError("Cannot write private member to an object whose class did not declare it");return"a"===s?r.call(t,e):r?r.value=e:i.set(t,e),e},l=this&&this.__classPrivateFieldGet||function(t,i,e,s){if("a"===e&&!s)throw new TypeError("Private accessor was defined without a getter");if("function"==typeof i?t!==i||!s:!i.has(t))throw new TypeError("Cannot read private member from an object whose class did not declare it");return"m"===e?s:"a"===e?s.call(t):s?s.value:i.get(t)};Object.defineProperty(exports,"__esModule",{value:!0}),exports.SecuxPsbt=void 0;const d=require("./parser"),S=require("bip174/src/lib/utils"),g=require("secp256k1/elliptic"),y=require("hash.js"),P=require("./script"),w=require("@secux/utility"),T=require("./interface"),m=require("./utils"),b=require("./payment"),k=require("./transaction"),v=require("./coindef"),H=require("../../protocol-transaction/lib/protocol-transaction"),x=require("./bip340"),E=null===w.Logger||void 0===w.Logger?void 0:w.Logger.child({id:"psbt"});class W{constructor(p,a=new d.Psbtv2(new $)){t.add(this),i.set(this,void 0),e.set(this,void 0),s.set(this,void 0),r.set(this,[]),n.set(this,void 0),o.set(this,{}),f(this,i,a,"f"),f(this,e,p,"f"),f(this,s,(0,m.getPayment)(l(this,e,"f")),"f"),f(this,n,l(this,i,"f").globalMap.unsignedTx.tx,"f"),p===T.CoinType.BITCOINCASH&&(l(this,n,"f").version=1)}static FromBuffer(t,i){const e=d.Psbtv2.fromBuffer(t,(t=>new $(t)));return new W(i,e)}AddInput(t){var n;if(!(0,w.isSupportedCoin)(t.path))throw Error(`ArgumentError: unsupport bip32 path, got "${t.path}"`);const o={},p={},a=(0,m.getPublickey)(t.publickey),u=null!==(n=t.script)&&void 0!==n?n:(0,m.getDefaultScript)(t.path);switch(u){case T.ScriptType.P2PKH:o.witnessUtxo={script:l(this,s,"f").p2pkh(l(this,e,"f"),{publickey:a}).scriptPublickey,value:t.satoshis};break;case T.ScriptType.P2SH_P2PKH:const r=l(this,s,"f").p2pkh(l(this,e,"f"),{publickey:a});p.redeemScript=r.scriptPublickey,o.witnessUtxo={script:l(this,s,"f").p2sh(l(this,e,"f"),r.redeemHash).scriptPublickey,value:t.satoshis};break;case T.ScriptType.P2SH_P2WPKH:const n=l(this,s,"f").p2wpkh(l(this,e,"f"),{publickey:a});p.redeemScript=n.scriptPublickey,o.witnessUtxo={script:l(this,s,"f").p2sh(l(this,e,"f"),n.redeemHash).scriptPublickey,value:t.satoshis};break;case T.ScriptType.P2WPKH:o.witnessUtxo={script:l(this,s,"f").p2wpkh(l(this,e,"f"),{publickey:a}).scriptPublickey,value:t.satoshis};break;case T.ScriptType.P2TR:o.witnessUtxo={script:l(this,s,"f").p2tr(l(this,e,"f"),{publickey:a}).scriptPublickey,value:t.satoshis};break;default:throw Error(`ArgumentError: Invalid ScriptType of input#${l(this,i,"f").inputs.length}, got "${T.ScriptType[u]}"`)}if(t.txHex){const s=k.Transaction.fromBuffer(Buffer.from(t.txHex,"hex"));if((0,m.getSerializer)(l(this,e,"f")).getId(s)!==t.hash)throw Error(`UTXO hash for input #${l(this,i,"f").inputs.length} doesn't match the hash specified in the prevout`);const r=s.outs[t.vout];if(r.value!==t.satoshis)throw Error(`UTXO value for input #${l(this,i,"f").inputs.length} doesn't match the value specified in the prevout`);r.script.equals(o.witnessUtxo.script)||null==E||E.warn(`Input script generation error: ${r.script.toString("hex")}, got "${o.witnessUtxo.script}"`)}const c=Object.assign(Object.assign({hash:t.hash,index:t.vout},o),p);return l(this,i,"f").addInput(c),l(this,r,"f").push(t.path),this}AddInputs(t){for(const i of t)this.AddInput(i);return this}AddOutput(t){var r;let n,o,p,a=t.satoshis;if(n=(0,T.isOutuptScriptExtended)(t)){const t=(0,m.getPublickey)(n.publickey);p=n.path;const a=null!==(r=n.script)&&void 0!==r?r:(0,m.getDefaultScript)(p);let u,c;switch(a){case T.ScriptType.P2SH_P2WPKH:if(!n.path.startsWith("m/49'/"))throw Error("P2SH(...) should use m/49' path");u=l(this,s,"f").p2wpkh(l(this,e,"f"),{publickey:t}).redeemHash,c=l(this,s,"f").p2sh(l(this,e,"f"),u),o=c.scriptPublickey;break;case T.ScriptType.P2SH_P2PKH:if(!n.path.startsWith("m/49'/"))throw Error("P2SH(...) should use m/49' path");u=l(this,s,"f").p2pkh(l(this,e,"f"),{publickey:t}).redeemHash,c=l(this,s,"f").p2sh(l(this,e,"f"),u),o=c.scriptPublickey;break;case T.ScriptType.P2PKH:if(!n.path.startsWith("m/44'/"))throw Error("P2PKH should use m/44' path");o=l(this,s,"f").p2pkh(l(this,e,"f"),{publickey:t}).scriptPublickey;break;case T.ScriptType.P2WPKH:if(!n.path.startsWith("m/84'/"))throw Error("P2WPKH should use m/84' path");o=l(this,s,"f").p2wpkh(l(this,e,"f"),{publickey:t}).scriptPublickey;break;case T.ScriptType.P2TR:if(!n.path.startsWith("m/86'/"))throw Error("P2TR should use m/86' path");o=l(this,s,"f").p2tr(l(this,e,"f"),{publickey:t}).scriptPublickey;break;default:throw Error(`ArgumentError: Invalid ScriptType of output#${l(this,i,"f").outputs.length}, got "${T.ScriptType[a]}"`)}}else if(n=(0,T.isOutputAddress)(t))o=l(this,s,"f").decode(l(this,e,"f"),n.address);else{if(!(n=(0,T.isOutuptScript)(t)))throw Error("Invalid parameter of output");o=Buffer.from(n.scriptHex,"hex")}return l(this,i,"f").addOutput({script:o,value:a,path:p}),this}AddOutputs(t){for(const i of t)this.AddOutput(i);return this}PrepareSign(s){if(s){const e=l(this,t,"m",c).call(this),r=Math.round(e*s);null==E||E.info(`Estimated fee is ${r}, with ${s} fee rates.`);const o=l(this,i,"f").inputs.reduce(((t,i)=>t+i.witnessUtxo.value),0),p=l(this,n,"f").outs[0].value,a=1===l(this,i,"f").outputs.length?0:l(this,n,"f").outs[1].value,u=o-p-a;if(u<r&&(null==E||E.warn(`Estimated fee is ${r}, but got ${u}.`)),u>r||u<e)if(0!==a){const t=o-p-r;if(t<0)throw Error(`Insufficient amount, expect ${p+r}, but got ${o}.`);l(this,n,"f").outs[1].value=t,null==E||E.info(`Modify change amount from ${a} to ${t}.`)}else{const t=o-r;if(t<0)throw Error(`Insufficient amount, expect at least ${r}, but got ${o}.`);l(this,n,"f").outs[0].value=t,null==E||E.info(`Modify spend amount from ${p} to ${t}.`)}}const o=Buffer.from([l(this,i,"f").outputs.length,...(0,w.BigIntToBuffer)(l(this,n,"f").outs[0].value,8),l(this,n,"f").outs[0].script.length,...l(this,n,"f").outs[0].script,...l(this,n,"f").outs.slice(1).reduce(((t,i)=>[...t,...(0,w.BigIntToBuffer)(i.value,8),...(0,w.buildPathBuffer)(i.path).pathBuffer]),[])]),u=l(this,i,"f").inputs.map(((i,e)=>{const s=l(this,t,"m",a).call(this,e);if(null==E||E.debug(`tx data [${e}]: ${s.toString("hex")}`),s.length+25>4e3)throw Error("ArgumentError: utxo exceed maximum payload size");return s}));null==E||E.debug(`confirm data: ${o.toString("hex")}`);const h=[];let f=[],d=[],S=l(this,e,"f")!==T.CoinType.BITCOINCASH&&l(this,t,"m",p).call(this,0).type===T.ScriptType.P2PKH?Buffer.alloc(0):o;for(let i=0,s=0;i<u.length;i++){if(s+=u[i].length+25,f.push(u[i]),d.push(l(this,r,"f")[i]),s+S.length<4e3)continue;f.pop(),d.pop(),h.push(H.SecuxTransactionTool.signRawTransactionList(d,f,S)),s=u[i].length+25,f=[u[i]],d=[l(this,r,"f")[i]];const{type:n}=l(this,t,"m",p).call(this,i);S=l(this,e,"f")!==T.CoinType.BITCOINCASH&&n===T.ScriptType.P2PKH?Buffer.alloc(0):o}return f.length>0&&h.push(H.SecuxTransactionTool.signRawTransactionList(d,f,S)),{commands:h,rawTx:l(this,i,"f").toHex()}}appendSignature(s,r){var n,o;if(s.length!==r.length)throw Error(`ArgumentError: each signature is correspond to one publickey, got ${s.length} signatures and ${r.length} publickeys`);for(let u=0;u<l(this,i,"f").inputs.length;u++){const c=l(this,t,"m",a).call(this,u);if(l(this,t,"m",p).call(this,u).type!==T.ScriptType.P2TR){const t=l(this,e,"f")===T.CoinType.GROESTL?Buffer.from((0,y.sha256)().update(c).digest()):Buffer.from((0,y.sha256)().update((0,y.sha256)().update(c).digest()).digest()),o=r[u];if(!g.ecdsaVerify(s[u],t,o))throw Error(`Signature Error #${u}`);let p=null!==(n=l(this,i,"f").inputs[u].sighashType)&&void 0!==n?n:k.Transaction.SIGHASH_ALL;l(this,e,"f")===T.CoinType.BITCOINCASH&&(p|=64);const a=[{pubkey:o,signature:P.encode(s[u],p)}];l(this,i,"f").updateInput(u,{partialSig:a})}else{const t=(0,m.taggedHash)("TapSighash",c),e=(0,m.toTweakedPublickey)(r[u]),n=s[u].slice(0,64);if(!(0,x.taprootVerify)(n,t,e))throw Error(`Signature Error #${u}`);const p=null!==(o=l(this,i,"f").inputs[u].sighashType)&&void 0!==o?o:k.Transaction.SIGHASH_DEFAULT;l(this,i,"f").inputs[u].partialSig=[{pubkey:e,signature:p===k.Transaction.SIGHASH_DEFAULT?n:Buffer.from([p,...n])}]}}return this}finalizeAllInputs(){if(l(this,i,"f").inputs.length<1)throw Error("utxo input cannot be empty");return l(this,i,"f").inputs.forEach(((t,s)=>{(0,S.checkForInput)(l(this,i,"f").inputs,s);const{script:r,scriptType:n}=I(t,l(this,e,"f"));if(!r)throw new Error(`No script found for input #${s}`);if(t.sighashType&&t.partialSig){const{partialSig:i,sighashType:e}=t;for(const t of i){const{hashType:i}=P.decode(t.signature);if(i!==e)throw new Error("Signature sighash does not match input sighash type")}}const{finalScriptSig:o,finalScriptWitness:p}=function(t,i){let e,s;const{signature:r,pubkey:n}=i[0];switch(t){case T.ScriptType.P2PKH:e=P.compile([r,n]);break;case T.ScriptType.P2SH_P2PKH:e=(()=>{const t=P.compile([r,n]),i=P.decompile(t),e={output:i[i.length-1],input:P.compile(i.slice(0,-1))};return P.compile([].concat(P.decompile(e.input),e.output))})();break;case T.ScriptType.P2SH_P2WPKH:s=(0,m.witnessStackToScriptWitness)([r,n]),e=(()=>{const t=Buffer.alloc(0),i=(0,b.Hash160)(n),e=P.compile([v.OPCODES.OP_0,i]);return P.compile([].concat(P.decompile(t),e))})();break;case T.ScriptType.P2WPKH:s=(0,m.witnessStackToScriptWitness)([r,n]);break;case T.ScriptType.P2TR:s=r}return{finalScriptSig:e,finalScriptWitness:s}}(n,t.partialSig);if(o&&l(this,i,"f").updateInput(s,{finalScriptSig:o}),p&&l(this,i,"f").updateInput(s,{finalScriptWitness:p}),!o&&!p)throw new Error(`Unknown error finalizing input #${s}`)})),this}extractTransaction(){const e=l(this,n,"f").clone();l(this,i,"f").inputs.forEach(((i,s)=>l(this,t,"m",u).call(this,e,s,i)));const s=l(this,i,"f").inputs.reduce(((t,i)=>t+i.witnessUtxo.value),0)-e.outs.reduce(((t,i)=>t+i.value),0),r=e.virtualSize();if(s<r)throw Error(`Transaction fee must >= ${r}, but got ${s}.`);return e}}function I(t,i){let e,s;const r=(0,m.getPayment)(i);if(t.witnessScript)e=t.witnessScript;else if(t.redeemScript)switch(e=t.redeemScript,s=r.classify(e),s){case T.ScriptType.P2PKH:s=T.ScriptType.P2SH_P2PKH;break;case T.ScriptType.P2WPKH:s=T.ScriptType.P2SH_P2WPKH}else e=t.witnessUtxo.script,s=r.classify(e);return{script:e,scriptType:s}}exports.SecuxPsbt=W,i=new WeakMap,e=new WeakMap,s=new WeakMap,r=new WeakMap,n=new WeakMap,o=new WeakMap,t=new WeakSet,p=function(t){if(l(this,o,"f")[t])return l(this,o,"f")[t];const s=l(this,i,"f").inputs[t],r=s.witnessUtxo,n=I(s,l(this,e,"f")).scriptType,p=function(t,i,e,s){let r;switch(i){case T.ScriptType.P2SH_P2PKH:case T.ScriptType.P2SH_P2WPKH:if(!e)throw Error("scriptPubkey is P2SH but redeemScript missing");r=e;break;default:r=t}if(!r)throw Error("cannot extract script");return r}(r.script,n,s.redeemScript,s.witnessScript);null==E||E.debug(`input #${t} script type: ${T.ScriptType[n]}`),null==E||E.debug(`script: ${p.toString("hex")}`);const a={type:n,scriptPubkey:p};return l(this,o,"f")[t]=a,a},a=function(s){var r,o;const a=l(this,i,"f").inputs[s],u=l(this,n,"f");let c=null!==(r=a.sighashType)&&void 0!==r?r:k.Transaction.SIGHASH_ALL;const h=(0,m.getSerializer)(l(this,e,"f"));void 0===a.witnessUtxo&&Error("Need a Utxo input item for signing");const f=a.witnessUtxo,{type:d,scriptPubkey:S}=l(this,t,"m",p).call(this,s);let g;switch(d){case T.ScriptType.P2WPKH:case T.ScriptType.P2SH_P2WPKH:case T.ScriptType.P2SH_P2PKH:null==E||E.debug(T.ScriptType[d]);const r=(0,m.getPayment)(l(this,e,"f")).p2pkh(l(this,e,"f"),{hash:S.slice(2)}).scriptPublickey;g=h.dataForWitnessV0(u,s,r,f.value,c);break;case T.ScriptType.P2TR:null==E||E.debug("p2tr"),c=null!==(o=a.sighashType)&&void 0!==o?o:k.Transaction.SIGHASH_DEFAULT,g=h.dataForWitnessV1(u,s,l(this,i,"f").inputs.map(((i,e)=>l(this,t,"m",p).call(this,e).scriptPubkey)),l(this,i,"f").inputs.map((t=>t.witnessUtxo.value)),c);break;default:l(this,e,"f")===T.CoinType.BITCOINCASH?(null==E||E.debug("bch using bip143"),g=h.dataForWitnessV0(u,s,S,f.value,64|c)):(null==E||E.debug("non-segwit"),g=h.dataForSignature(u,s,S,c))}return g},u=function(i,e,s){if(!s.finalScriptSig&&!s.finalScriptWitness)throw Error(`input#${e} not finalized.`);s.finalScriptSig&&(i.ins[e].script=s.finalScriptSig),s.finalScriptWitness&&(l(this,t,"m",p).call(this,e).type!==T.ScriptType.P2TR?i.ins[e].witness=(0,m.scriptWitnessToWitnessStack)(s.finalScriptWitness):i.ins[e].witness=[s.finalScriptWitness])},c=function(){const e=l(this,n,"f").clone();let s=0,r=2;return l(this,i,"f").inputs.forEach(((i,e)=>{const{type:n}=l(this,t,"m",p).call(this,e);s+=(0,m.getInScriptSize)(n);const o=(0,m.getWitnessSize)(n,i.sighashType);r+=(0,m.vectorSize)(o)})),e.virtualSize()+s+r/4};class ${constructor(t=Buffer.from([2,0,0,0,0,0,0,0,0,0])){h.set(this,void 0),f(this,h,k.Transaction.fromBuffer(t),"f")}getInputOutputCounts(){return{inputCount:l(this,h,"f").ins.length,outputCount:l(this,h,"f").outs.length}}addInput(t){if(void 0===t.hash||void 0===t.index||!Buffer.isBuffer(t.hash)&&"string"!=typeof t.hash||"number"!=typeof t.index)throw new Error("Error adding input.");const i="string"==typeof t.hash?Buffer.from(Buffer.from(t.hash,"hex").reverse()):t.hash;l(this,h,"f").addInput(i,t.index,t.sequence)}addOutput(t){if(void 0===t.script||void 0===t.value||!Buffer.isBuffer(t.script)||"number"!=typeof t.value)throw new Error("Error adding output.");l(this,h,"f").addOutput(t.script,t.value,t.path)}toBuffer(){return l(this,h,"f").toBuffer()}get tx(){return l(this,h,"f")}}h=new WeakMap; | ||
"use strict";var t,i,e,s,r,n,o,p,a,u,c,h,f=this&&this.__classPrivateFieldSet||function(t,i,e,s,r){if("m"===s)throw new TypeError("Private method is not writable");if("a"===s&&!r)throw new TypeError("Private accessor was defined without a setter");if("function"==typeof i?t!==i||!r:!i.has(t))throw new TypeError("Cannot write private member to an object whose class did not declare it");return"a"===s?r.call(t,e):r?r.value=e:i.set(t,e),e},l=this&&this.__classPrivateFieldGet||function(t,i,e,s){if("a"===e&&!s)throw new TypeError("Private accessor was defined without a getter");if("function"==typeof i?t!==i||!s:!i.has(t))throw new TypeError("Cannot read private member from an object whose class did not declare it");return"m"===e?s:"a"===e?s.call(t):s?s.value:i.get(t)};Object.defineProperty(exports,"__esModule",{value:!0}),exports.SecuxPsbt=void 0;const d=require("./parser"),S=require("bip174/src/lib/utils"),g=require("secp256k1/elliptic"),y=require("hash.js"),P=require("./script"),w=require("@secux/utility"),T=require("./interface"),m=require("./utils"),b=require("./payment"),k=require("./transaction"),v=require("./coindef"),H=require("@secux/utility/lib/communication"),E=require("../../protocol-transaction/lib/protocol-transaction"),x=require("./bip340"),I=null===w.Logger||void 0===w.Logger?void 0:w.Logger.child({id:"psbt"});class W{constructor(p,a=new d.Psbtv2(new B)){t.add(this),i.set(this,void 0),e.set(this,void 0),s.set(this,void 0),r.set(this,[]),n.set(this,void 0),o.set(this,{}),f(this,i,a,"f"),f(this,e,p,"f"),f(this,s,(0,m.getPayment)(l(this,e,"f")),"f"),f(this,n,l(this,i,"f").globalMap.unsignedTx.tx,"f"),p===T.CoinType.BITCOINCASH&&(l(this,n,"f").version=1)}static FromBuffer(t,i){const e=d.Psbtv2.fromBuffer(t,(t=>new B(t)));return new W(i,e)}AddInput(t){var n;if(!(0,w.isSupportedCoin)(t.path))throw Error(`ArgumentError: unsupport bip32 path, got "${t.path}"`);const o={},p={},a=(0,m.getPublickey)(t.publickey),u=null!==(n=t.script)&&void 0!==n?n:(0,m.getDefaultScript)(t.path);switch(u){case T.ScriptType.P2PKH:o.witnessUtxo={script:l(this,s,"f").p2pkh(l(this,e,"f"),{publickey:a}).scriptPublickey,value:t.satoshis};break;case T.ScriptType.P2SH_P2PKH:const r=l(this,s,"f").p2pkh(l(this,e,"f"),{publickey:a});p.redeemScript=r.scriptPublickey,o.witnessUtxo={script:l(this,s,"f").p2sh(l(this,e,"f"),r.redeemHash).scriptPublickey,value:t.satoshis};break;case T.ScriptType.P2SH_P2WPKH:const n=l(this,s,"f").p2wpkh(l(this,e,"f"),{publickey:a});p.redeemScript=n.scriptPublickey,o.witnessUtxo={script:l(this,s,"f").p2sh(l(this,e,"f"),n.redeemHash).scriptPublickey,value:t.satoshis};break;case T.ScriptType.P2WPKH:o.witnessUtxo={script:l(this,s,"f").p2wpkh(l(this,e,"f"),{publickey:a}).scriptPublickey,value:t.satoshis};break;case T.ScriptType.P2TR:o.witnessUtxo={script:l(this,s,"f").p2tr(l(this,e,"f"),{publickey:a}).scriptPublickey,value:t.satoshis};break;default:throw Error(`ArgumentError: Invalid ScriptType of input#${l(this,i,"f").inputs.length}, got "${T.ScriptType[u]}"`)}if(t.txHex){const s=k.Transaction.fromBuffer(Buffer.from(t.txHex,"hex"));if((0,m.getSerializer)(l(this,e,"f")).getId(s)!==t.hash)throw Error(`UTXO hash for input #${l(this,i,"f").inputs.length} doesn't match the hash specified in the prevout`);const r=s.outs[t.vout];if(r.value!==t.satoshis)throw Error(`UTXO value for input #${l(this,i,"f").inputs.length} doesn't match the value specified in the prevout`);r.script.equals(o.witnessUtxo.script)||null==I||I.warn(`Input script generation error: ${r.script.toString("hex")}, got "${o.witnessUtxo.script}"`)}const c=Object.assign(Object.assign({hash:t.hash,index:t.vout},o),p);return l(this,i,"f").addInput(c),l(this,r,"f").push(t.path),this}AddInputs(t){for(const i of t)this.AddInput(i);return this}AddOutput(t){var r;let n,o,p,a=t.satoshis;if(n=(0,T.isOutuptScriptExtended)(t)){const t=(0,m.getPublickey)(n.publickey);p=n.path;const a=null!==(r=n.script)&&void 0!==r?r:(0,m.getDefaultScript)(p);let u,c;switch(a){case T.ScriptType.P2SH_P2WPKH:if(!n.path.startsWith("m/49'/"))throw Error("P2SH(...) should use m/49' path");u=l(this,s,"f").p2wpkh(l(this,e,"f"),{publickey:t}).redeemHash,c=l(this,s,"f").p2sh(l(this,e,"f"),u),o=c.scriptPublickey;break;case T.ScriptType.P2SH_P2PKH:if(!n.path.startsWith("m/49'/"))throw Error("P2SH(...) should use m/49' path");u=l(this,s,"f").p2pkh(l(this,e,"f"),{publickey:t}).redeemHash,c=l(this,s,"f").p2sh(l(this,e,"f"),u),o=c.scriptPublickey;break;case T.ScriptType.P2PKH:if(!n.path.startsWith("m/44'/"))throw Error("P2PKH should use m/44' path");o=l(this,s,"f").p2pkh(l(this,e,"f"),{publickey:t}).scriptPublickey;break;case T.ScriptType.P2WPKH:if(!n.path.startsWith("m/84'/"))throw Error("P2WPKH should use m/84' path");o=l(this,s,"f").p2wpkh(l(this,e,"f"),{publickey:t}).scriptPublickey;break;case T.ScriptType.P2TR:if(!n.path.startsWith("m/86'/"))throw Error("P2TR should use m/86' path");o=l(this,s,"f").p2tr(l(this,e,"f"),{publickey:t}).scriptPublickey;break;default:throw Error(`ArgumentError: Invalid ScriptType of output#${l(this,i,"f").outputs.length}, got "${T.ScriptType[a]}"`)}}else if(n=(0,T.isOutputAddress)(t))o=l(this,s,"f").decode(l(this,e,"f"),n.address);else{if(!(n=(0,T.isOutuptScript)(t)))throw Error("Invalid parameter of output");o=Buffer.from(n.scriptHex,"hex")}return l(this,i,"f").addOutput({script:o,value:a,path:p}),this}AddOutputs(t){for(const i of t)this.AddOutput(i);return this}PrepareSign(s){if(s){const e=l(this,t,"m",c).call(this),r=Math.round(e*s);null==I||I.info(`Estimated fee is ${r}, with ${s} fee rates.`);const o=l(this,i,"f").inputs.reduce(((t,i)=>t+i.witnessUtxo.value),0),p=l(this,n,"f").outs[0].value,a=1===l(this,i,"f").outputs.length?0:l(this,n,"f").outs[1].value,u=o-p-a;if(u<r&&(null==I||I.warn(`Estimated fee is ${r}, but got ${u}.`)),u>r||u<e)if(0!==a){const t=o-p-r;if(t<0)throw Error(`Insufficient amount, expect ${p+r}, but got ${o}.`);l(this,n,"f").outs[1].value=t,null==I||I.info(`Modify change amount from ${a} to ${t}.`)}else{const t=o-r;if(t<0)throw Error(`Insufficient amount, expect at least ${r}, but got ${o}.`);l(this,n,"f").outs[0].value=t,null==I||I.info(`Modify spend amount from ${p} to ${t}.`)}}const o=Buffer.from([l(this,i,"f").outputs.length,...(0,w.BigIntToBuffer)(l(this,n,"f").outs[0].value,8),l(this,n,"f").outs[0].script.length,...l(this,n,"f").outs[0].script,...l(this,n,"f").outs.slice(1).reduce(((t,i)=>[...t,...(0,w.BigIntToBuffer)(i.value,8),...(0,w.buildPathBuffer)(i.path).pathBuffer]),[])]),u=l(this,i,"f").inputs.map(((i,e)=>{const s=l(this,t,"m",a).call(this,e);if(null==I||I.debug(`tx data [${e}]: ${s.toString("hex")}`),s.length+H.MAX_HEAD_SIZE>H.ONESIGN_THRESHOLD)throw Error("ArgumentError: utxo exceed maximum payload size");return s}));null==I||I.debug(`confirm data: ${o.toString("hex")}`);const h=[];let f=[],d=[],S=l(this,e,"f")!==T.CoinType.BITCOINCASH&&l(this,t,"m",p).call(this,0).type===T.ScriptType.P2PKH?Buffer.alloc(0):o;for(let i=0,s=0;i<u.length;i++){if(s+=u[i].length+H.MAX_HEAD_SIZE,f.push(u[i]),d.push(l(this,r,"f")[i]),s+S.length<H.ONESIGN_THRESHOLD)continue;f.pop(),d.pop(),h.push(E.SecuxTransactionTool.signRawTransactionList(d,f,S)),s=u[i].length+25,f=[u[i]],d=[l(this,r,"f")[i]];const{type:n}=l(this,t,"m",p).call(this,i);S=l(this,e,"f")!==T.CoinType.BITCOINCASH&&n===T.ScriptType.P2PKH?Buffer.alloc(0):o}return f.length>0&&h.push(E.SecuxTransactionTool.signRawTransactionList(d,f,S)),{commands:h,rawTx:l(this,i,"f").toHex()}}appendSignature(s,r){var n,o;if(s.length!==r.length)throw Error(`ArgumentError: each signature is correspond to one publickey, got ${s.length} signatures and ${r.length} publickeys`);for(let u=0;u<l(this,i,"f").inputs.length;u++){const c=l(this,t,"m",a).call(this,u);if(l(this,t,"m",p).call(this,u).type!==T.ScriptType.P2TR){const t=l(this,e,"f")===T.CoinType.GROESTL?Buffer.from((0,y.sha256)().update(c).digest()):Buffer.from((0,y.sha256)().update((0,y.sha256)().update(c).digest()).digest()),o=r[u];if(!g.ecdsaVerify(s[u],t,o))throw Error(`Signature Error #${u}`);let p=null!==(n=l(this,i,"f").inputs[u].sighashType)&&void 0!==n?n:k.Transaction.SIGHASH_ALL;l(this,e,"f")===T.CoinType.BITCOINCASH&&(p|=64);const a=[{pubkey:o,signature:P.encode(s[u],p)}];l(this,i,"f").updateInput(u,{partialSig:a})}else{const t=(0,m.taggedHash)("TapSighash",c),e=(0,m.toTweakedPublickey)(r[u]),n=s[u].slice(0,64);if(!(0,x.taprootVerify)(n,t,e))throw Error(`Signature Error #${u}`);const p=null!==(o=l(this,i,"f").inputs[u].sighashType)&&void 0!==o?o:k.Transaction.SIGHASH_DEFAULT;l(this,i,"f").inputs[u].partialSig=[{pubkey:e,signature:p===k.Transaction.SIGHASH_DEFAULT?n:Buffer.from([p,...n])}]}}return this}finalizeAllInputs(){if(l(this,i,"f").inputs.length<1)throw Error("utxo input cannot be empty");return l(this,i,"f").inputs.forEach(((t,s)=>{(0,S.checkForInput)(l(this,i,"f").inputs,s);const{script:r,scriptType:n}=$(t,l(this,e,"f"));if(!r)throw new Error(`No script found for input #${s}`);if(t.sighashType&&t.partialSig){const{partialSig:i,sighashType:e}=t;for(const t of i){const{hashType:i}=P.decode(t.signature);if(i!==e)throw new Error("Signature sighash does not match input sighash type")}}const{finalScriptSig:o,finalScriptWitness:p}=function(t,i){let e,s;const{signature:r,pubkey:n}=i[0];switch(t){case T.ScriptType.P2PKH:e=P.compile([r,n]);break;case T.ScriptType.P2SH_P2PKH:e=(()=>{const t=P.compile([r,n]),i=P.decompile(t),e={output:i[i.length-1],input:P.compile(i.slice(0,-1))};return P.compile([].concat(P.decompile(e.input),e.output))})();break;case T.ScriptType.P2SH_P2WPKH:s=(0,m.witnessStackToScriptWitness)([r,n]),e=(()=>{const t=Buffer.alloc(0),i=(0,b.Hash160)(n),e=P.compile([v.OPCODES.OP_0,i]);return P.compile([].concat(P.decompile(t),e))})();break;case T.ScriptType.P2WPKH:s=(0,m.witnessStackToScriptWitness)([r,n]);break;case T.ScriptType.P2TR:s=r}return{finalScriptSig:e,finalScriptWitness:s}}(n,t.partialSig);if(o&&l(this,i,"f").updateInput(s,{finalScriptSig:o}),p&&l(this,i,"f").updateInput(s,{finalScriptWitness:p}),!o&&!p)throw new Error(`Unknown error finalizing input #${s}`)})),this}extractTransaction(){const e=l(this,n,"f").clone();l(this,i,"f").inputs.forEach(((i,s)=>l(this,t,"m",u).call(this,e,s,i)));const s=l(this,i,"f").inputs.reduce(((t,i)=>t+i.witnessUtxo.value),0)-e.outs.reduce(((t,i)=>t+i.value),0),r=e.virtualSize();if(s<r)throw Error(`Transaction fee must >= ${r}, but got ${s}.`);return e}}function $(t,i){let e,s;const r=(0,m.getPayment)(i);if(t.witnessScript)e=t.witnessScript;else if(t.redeemScript)switch(e=t.redeemScript,s=r.classify(e),s){case T.ScriptType.P2PKH:s=T.ScriptType.P2SH_P2PKH;break;case T.ScriptType.P2WPKH:s=T.ScriptType.P2SH_P2WPKH}else e=t.witnessUtxo.script,s=r.classify(e);return{script:e,scriptType:s}}exports.SecuxPsbt=W,i=new WeakMap,e=new WeakMap,s=new WeakMap,r=new WeakMap,n=new WeakMap,o=new WeakMap,t=new WeakSet,p=function(t){if(l(this,o,"f")[t])return l(this,o,"f")[t];const s=l(this,i,"f").inputs[t],r=s.witnessUtxo,n=$(s,l(this,e,"f")).scriptType,p=function(t,i,e,s){let r;switch(i){case T.ScriptType.P2SH_P2PKH:case T.ScriptType.P2SH_P2WPKH:if(!e)throw Error("scriptPubkey is P2SH but redeemScript missing");r=e;break;default:r=t}if(!r)throw Error("cannot extract script");return r}(r.script,n,s.redeemScript,s.witnessScript);null==I||I.debug(`input #${t} script type: ${T.ScriptType[n]}`),null==I||I.debug(`script: ${p.toString("hex")}`);const a={type:n,scriptPubkey:p};return l(this,o,"f")[t]=a,a},a=function(s){var r,o;const a=l(this,i,"f").inputs[s],u=l(this,n,"f");let c=null!==(r=a.sighashType)&&void 0!==r?r:k.Transaction.SIGHASH_ALL;const h=(0,m.getSerializer)(l(this,e,"f"));void 0===a.witnessUtxo&&Error("Need a Utxo input item for signing");const f=a.witnessUtxo,{type:d,scriptPubkey:S}=l(this,t,"m",p).call(this,s);let g;switch(d){case T.ScriptType.P2WPKH:case T.ScriptType.P2SH_P2WPKH:case T.ScriptType.P2SH_P2PKH:null==I||I.debug(T.ScriptType[d]);const r=(0,m.getPayment)(l(this,e,"f")).p2pkh(l(this,e,"f"),{hash:S.slice(2)}).scriptPublickey;g=h.dataForWitnessV0(u,s,r,f.value,c);break;case T.ScriptType.P2TR:null==I||I.debug("p2tr"),c=null!==(o=a.sighashType)&&void 0!==o?o:k.Transaction.SIGHASH_DEFAULT,g=h.dataForWitnessV1(u,s,l(this,i,"f").inputs.map(((i,e)=>l(this,t,"m",p).call(this,e).scriptPubkey)),l(this,i,"f").inputs.map((t=>t.witnessUtxo.value)),c);break;default:l(this,e,"f")===T.CoinType.BITCOINCASH?(null==I||I.debug("bch using bip143"),g=h.dataForWitnessV0(u,s,S,f.value,64|c)):(null==I||I.debug("non-segwit"),g=h.dataForSignature(u,s,S,c))}return g},u=function(i,e,s){if(!s.finalScriptSig&&!s.finalScriptWitness)throw Error(`input#${e} not finalized.`);s.finalScriptSig&&(i.ins[e].script=s.finalScriptSig),s.finalScriptWitness&&(l(this,t,"m",p).call(this,e).type!==T.ScriptType.P2TR?i.ins[e].witness=(0,m.scriptWitnessToWitnessStack)(s.finalScriptWitness):i.ins[e].witness=[s.finalScriptWitness])},c=function(){const e=l(this,n,"f").clone();let s=0,r=2;return l(this,i,"f").inputs.forEach(((i,e)=>{const{type:n}=l(this,t,"m",p).call(this,e);s+=(0,m.getInScriptSize)(n);const o=(0,m.getWitnessSize)(n,i.sighashType);r+=(0,m.vectorSize)(o)})),e.virtualSize()+s+r/4};class B{constructor(t=Buffer.from([2,0,0,0,0,0,0,0,0,0])){h.set(this,void 0),f(this,h,k.Transaction.fromBuffer(t),"f")}getInputOutputCounts(){return{inputCount:l(this,h,"f").ins.length,outputCount:l(this,h,"f").outs.length}}addInput(t){if(void 0===t.hash||void 0===t.index||!Buffer.isBuffer(t.hash)&&"string"!=typeof t.hash||"number"!=typeof t.index)throw new Error("Error adding input.");const i="string"==typeof t.hash?Buffer.from(Buffer.from(t.hash,"hex").reverse()):t.hash;l(this,h,"f").addInput(i,t.index,t.sequence)}addOutput(t){if(void 0===t.script||void 0===t.value||!Buffer.isBuffer(t.script)||"number"!=typeof t.value)throw new Error("Error adding output.");l(this,h,"f").addOutput(t.script,t.value,t.path)}toBuffer(){return l(this,h,"f").toBuffer()}get tx(){return l(this,h,"f")}}h=new WeakMap; |
{ | ||
"name": "@secux/app-btc", | ||
"version": "3.2.1", | ||
"version": "3.2.2", | ||
"description": "SecuX Hardware Wallet BTC API", | ||
@@ -39,6 +39,6 @@ "keywords": [ | ||
"@secux/protocol-transaction": "^3.0.0", | ||
"@secux/utility": "^3.0.6", | ||
"@secux/utility": "^3.0.7", | ||
"bech32": "^2.0.0", | ||
"bigi": "^1.4.2", | ||
"bip174": "^2.0.1", | ||
"bip174": "~2.0.1", | ||
"bip66": "^1.1.5", | ||
@@ -45,0 +45,0 @@ "cashaddrjs": "^0.4.4", |
@@ -132,3 +132,3 @@ [![lerna](https://img.shields.io/badge/maintained%20with-lerna-cc00ff.svg)](https://lerna.js.org/) | ||
const rspList = []; | ||
for (const cmd of obj.multi_command) { | ||
for (const cmd of commands) { | ||
const rsp = await transport.Exchange(cmd); | ||
@@ -135,0 +135,0 @@ rspList.push(rsp); |
Sorry, the diff of this file is too big to display
Sorry, the diff of this file is not supported yet
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
556999
34
+ Addedbip174@2.0.1(transitive)
- Removedbip174@2.1.1(transitive)
Updated@secux/utility@^3.0.7
Updatedbip174@~2.0.1