@algorandfoundation/algokit-utils 10.0.0-alpha.24 → 10.0.0-alpha.25

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.
Files changed (39) hide show
  1. package/package.json +1 -1
  2. package/packages/transact/src/logicsig.d.ts +36 -22
  3. package/packages/transact/src/logicsig.js +69 -52
  4. package/packages/transact/src/logicsig.js.map +1 -1
  5. package/packages/transact/src/logicsig.mjs +70 -54
  6. package/packages/transact/src/logicsig.mjs.map +1 -1
  7. package/packages/transact/src/multisig.d.ts +4 -1
  8. package/packages/transact/src/multisig.js +17 -0
  9. package/packages/transact/src/multisig.js.map +1 -1
  10. package/packages/transact/src/multisig.mjs +17 -0
  11. package/packages/transact/src/multisig.mjs.map +1 -1
  12. package/packages/transact/src/signer.js +4 -1
  13. package/packages/transact/src/signer.js.map +1 -1
  14. package/packages/transact/src/signer.mjs +4 -1
  15. package/packages/transact/src/signer.mjs.map +1 -1
  16. package/packages/transact/src/transactions/signed-transaction-meta.js +6 -6
  17. package/packages/transact/src/transactions/signed-transaction-meta.js.map +1 -1
  18. package/packages/transact/src/transactions/signed-transaction-meta.mjs +6 -6
  19. package/packages/transact/src/transactions/signed-transaction-meta.mjs.map +1 -1
  20. package/packages/transact/src/transactions/signed-transaction.d.ts +4 -4
  21. package/packages/transact/src/transactions/signed-transaction.js.map +1 -1
  22. package/packages/transact/src/transactions/signed-transaction.mjs.map +1 -1
  23. package/testing/account.js +4 -2
  24. package/testing/account.js.map +1 -1
  25. package/testing/account.mjs +4 -2
  26. package/testing/account.mjs.map +1 -1
  27. package/transact/index.d.ts +3 -3
  28. package/transact/index.js +2 -1
  29. package/transact/index.mjs +2 -2
  30. package/types/account-manager.d.ts +6 -8
  31. package/types/account-manager.js +13 -3
  32. package/types/account-manager.js.map +1 -1
  33. package/types/account-manager.mjs +13 -3
  34. package/types/account-manager.mjs.map +1 -1
  35. package/types/algorand-client-transaction-creator.d.ts +26 -26
  36. package/types/algorand-client-transaction-sender.d.ts +26 -26
  37. package/types/app-client.d.ts +74 -74
  38. package/types/app-factory.d.ts +30 -30
  39. package/types/testing.d.ts +2 -2
package/package.json CHANGED
@@ -6,7 +6,7 @@
6
6
  "**"
7
7
  ],
8
8
  "name": "@algorandfoundation/algokit-utils",
9
- "version": "10.0.0-alpha.24",
9
+ "version": "10.0.0-alpha.25",
10
10
  "private": false,
11
11
  "description": "A set of core Algorand utilities written in TypeScript and released via npm that make it easier to build solutions on Algorand.",
12
12
  "author": "Algorand Foundation",
@@ -1,35 +1,49 @@
1
- import { Address } from "../../common/src/address.js";
2
- import { LogicSignature, MultisigSignature } from "./transactions/signed-transaction.js";
1
+ import { Address, Addressable } from "../../common/src/address.js";
2
+ import { LogicSigSignature, MultisigSignature } from "./transactions/signed-transaction.js";
3
3
  import { MultisigAccount } from "./multisig.js";
4
- import { TransactionSigner } from "./signer.js";
4
+ import { AddressWithDelegatedLsigSigner, TransactionSigner } from "./signer.js";
5
5
 
6
6
  //#region packages/transact/src/logicsig.d.ts
7
- /** Function for signing logic signatures for delegation */
8
- type DelegatedLsigSigner = (lsig: LogicSigAccount, msig?: MultisigAccount) => Promise<Uint8Array>;
7
+
8
+ /** Function for signing logic signatures for delegation
9
+ * @param lsig - The logic signature that is being signed for delegation
10
+ * @param msig - Optional multisig account that should be set when a public key is signing as a subsigner of a multisig
11
+ * @returns The address of the delegator
12
+ * */
13
+ type DelegatedLsigSigner = (lsig: LogicSigAccount, msig?: MultisigAccount) => Promise<{
14
+ addr: Address;
15
+ } & ({
16
+ sig?: Uint8Array;
17
+ } | {
18
+ lmsig?: MultisigSignature;
19
+ })>;
9
20
  /** Function for signing program data for a logic signature */
10
- type ProgramDataSigner = (data: Uint8Array, lsig: LogicSigAccount) => Promise<Uint8Array>;
11
- declare class LogicSigAccount {
21
+ type ProgramDataSigner = (data: Uint8Array, lsig: LogicSig) => Promise<Uint8Array>;
22
+ declare class LogicSig implements Addressable {
12
23
  logic: Uint8Array;
13
24
  args: Uint8Array[];
14
- sig?: Uint8Array;
15
- msig?: MultisigSignature;
16
- lmsig?: MultisigSignature;
17
- static fromSignature(signature: LogicSignature): LogicSigAccount;
18
- static fromBytes(encodedLsig: Uint8Array): LogicSigAccount;
19
- constructor(program: Uint8Array, programArgs?: Array<Uint8Array> | null);
20
- get signer(): TransactionSigner;
21
- get addr(): Address;
22
- /**
23
- * Compute hash of the logic sig program (that is the same as escrow account address) as string address
24
- * @returns String representation of the address
25
- */
25
+ protected _addr: Address;
26
+ constructor(program: Uint8Array, programArgs?: Array<Uint8Array>);
27
+ static fromSignature(signature: LogicSigSignature): LogicSig;
28
+ static fromBytes(encodedLsig: Uint8Array): LogicSig;
26
29
  address(): Address;
27
- delegate(signer: DelegatedLsigSigner): Promise<void>;
28
- delegateMultisig(msig: MultisigAccount): Promise<void>;
30
+ get addr(): Address;
29
31
  bytesToSignForDelegation(msig?: MultisigAccount): Uint8Array;
30
32
  signProgramData(data: Uint8Array, signer: ProgramDataSigner): Promise<Uint8Array>;
31
33
  programDataToSign(data: Uint8Array): Uint8Array;
34
+ account(): LogicSigAccount;
35
+ delegatedAccount(delegator: Address): LogicSigAccount;
36
+ }
37
+ declare class LogicSigAccount extends LogicSig {
38
+ sig?: Uint8Array;
39
+ msig?: MultisigSignature;
40
+ lmsig?: MultisigSignature;
41
+ static fromSignature(signature: LogicSigSignature, delegator?: Address): LogicSigAccount;
42
+ static fromBytes(encodedLsig: Uint8Array, delegator?: Address): LogicSigAccount;
43
+ constructor(program: Uint8Array, programArgs?: Array<Uint8Array> | null, delegator?: Address);
44
+ get signer(): TransactionSigner;
45
+ signForDelegation(delegator: AddressWithDelegatedLsigSigner): Promise<void>;
32
46
  }
33
47
  //#endregion
34
- export { DelegatedLsigSigner, LogicSigAccount, ProgramDataSigner };
48
+ export { DelegatedLsigSigner, LogicSig, LogicSigAccount, ProgramDataSigner };
35
49
  //# sourceMappingURL=logicsig.d.ts.map
@@ -4,35 +4,81 @@ const require_crypto = require('../../common/src/crypto.js');
4
4
  const require_msgpack = require('../../common/src/msgpack.js');
5
5
  const require_signed_transaction_meta = require('./transactions/signed-transaction-meta.js');
6
6
  const require_signed_transaction = require('./transactions/signed-transaction.js');
7
+ const require_multisig = require('./multisig.js');
7
8
 
8
9
  //#region packages/transact/src/logicsig.ts
9
10
  const PROGRAM_TAG = new TextEncoder().encode("Program");
10
11
  const MSIG_PROGRAM_TAG = new TextEncoder().encode("MsigProgram");
11
12
  const SIGN_PROGRAM_DATA_PREFIX = new TextEncoder().encode("ProgData");
12
- var LogicSigAccount = class LogicSigAccount {
13
+ var LogicSig = class LogicSig {
13
14
  logic;
14
15
  args;
16
+ _addr;
17
+ constructor(program, programArgs) {
18
+ this.logic = program;
19
+ this.args = programArgs ?? [];
20
+ this._addr = new require_address.Address(require_crypto.hash(require_array.concatArrays(PROGRAM_TAG, this.logic)));
21
+ }
22
+ static fromSignature(signature) {
23
+ return new LogicSig(signature.logic, signature.args || []);
24
+ }
25
+ static fromBytes(encodedLsig) {
26
+ const decoded = require_msgpack.decodeMsgpack(encodedLsig);
27
+ const lsigSignature = require_signed_transaction_meta.logicSigSignatureCodec.decode(decoded, "msgpack");
28
+ return LogicSig.fromSignature(lsigSignature);
29
+ }
30
+ address() {
31
+ return this._addr;
32
+ }
33
+ get addr() {
34
+ return this._addr;
35
+ }
36
+ bytesToSignForDelegation(msig) {
37
+ if (msig) return require_array.concatArrays(MSIG_PROGRAM_TAG, msig.addr.publicKey, this.logic);
38
+ else return require_array.concatArrays(PROGRAM_TAG, this.logic);
39
+ }
40
+ signProgramData(data, signer) {
41
+ return signer(data, this);
42
+ }
43
+ programDataToSign(data) {
44
+ return require_array.concatArrays(SIGN_PROGRAM_DATA_PREFIX, this.address().publicKey, data);
45
+ }
46
+ account() {
47
+ return new LogicSigAccount(this.logic, this.args);
48
+ }
49
+ delegatedAccount(delegator) {
50
+ return new LogicSigAccount(this.logic, this.args, delegator);
51
+ }
52
+ };
53
+ var LogicSigAccount = class LogicSigAccount extends LogicSig {
15
54
  sig;
16
55
  msig;
17
56
  lmsig;
18
- static fromSignature(signature) {
19
- const lsigAccount = new LogicSigAccount(signature.logic, signature.args || []);
20
- lsigAccount.sig = signature.sig;
21
- lsigAccount.msig = signature.msig;
22
- lsigAccount.lmsig = signature.lmsig;
57
+ static fromSignature(signature, delegator) {
58
+ if (signature.lmsig || signature.msig) {
59
+ const msigAddr = require_multisig.MultisigAccount.fromSignature(signature.lmsig || signature.msig).addr;
60
+ if (delegator && !msigAddr.equals(delegator)) throw new Error("Provided delegator address does not match multisig address");
61
+ const lsig = new LogicSigAccount(signature.logic, signature.args || [], msigAddr);
62
+ lsig.lmsig = signature.lmsig;
63
+ lsig.msig = signature.msig;
64
+ return lsig;
65
+ }
66
+ const lsigAccount = new LogicSigAccount(signature.logic, signature.args || [], delegator);
67
+ if (signature.sig && delegator === void 0) throw new Error("Delegated address must be provided when logic sig has a signature");
68
+ if (signature.sig) {
69
+ lsigAccount.sig = signature.sig;
70
+ return lsigAccount;
71
+ }
23
72
  return lsigAccount;
24
73
  }
25
- static fromBytes(encodedLsig) {
74
+ static fromBytes(encodedLsig, delegator) {
26
75
  const decoded = require_msgpack.decodeMsgpack(encodedLsig);
27
- const lsigSignature = require_signed_transaction_meta.logicSignatureCodec.decode(decoded, "msgpack");
28
- return LogicSigAccount.fromSignature(lsigSignature);
76
+ const lsigSignature = require_signed_transaction_meta.logicSigSignatureCodec.decode(decoded, "msgpack");
77
+ return LogicSigAccount.fromSignature(lsigSignature, delegator);
29
78
  }
30
- constructor(program, programArgs) {
31
- if (programArgs && (!Array.isArray(programArgs) || !programArgs.every((arg) => arg.constructor === Uint8Array))) throw new TypeError("Invalid arguments");
32
- let args = [];
33
- if (programArgs != null) args = programArgs.map((arg) => new Uint8Array(arg));
34
- this.logic = program;
35
- this.args = args;
79
+ constructor(program, programArgs, delegator) {
80
+ super(program, programArgs ?? void 0);
81
+ this._addr = delegator ?? this._addr;
36
82
  }
37
83
  get signer() {
38
84
  return async (txns, indexes) => {
@@ -48,51 +94,22 @@ var LogicSigAccount = class LogicSigAccount {
48
94
  sig: this.sig
49
95
  }
50
96
  };
97
+ if (!stxn.txn.sender.equals(this.addr)) stxn.authAddress = this.addr;
51
98
  signedTxns.push(require_signed_transaction.encodeSignedTransaction(stxn));
52
99
  }
53
100
  return signedTxns;
54
101
  };
55
102
  }
56
- get addr() {
57
- return this.address();
58
- }
59
- /**
60
- * Compute hash of the logic sig program (that is the same as escrow account address) as string address
61
- * @returns String representation of the address
62
- */
63
- address() {
64
- return new require_address.Address(require_crypto.hash(require_array.concatArrays(PROGRAM_TAG, this.logic)));
65
- }
66
- async delegate(signer) {
67
- this.sig = await signer(this);
68
- }
69
- async delegateMultisig(msig) {
70
- if (this.lmsig == void 0) this.lmsig = {
71
- subsigs: [],
72
- version: msig.params.version,
73
- threshold: msig.params.threshold
74
- };
75
- for (const addrWithSigner of msig.subSigners) {
76
- const { lsigSigner, addr } = addrWithSigner;
77
- const signature = await lsigSigner(this, msig);
78
- this.lmsig.subsigs.push({
79
- publicKey: addr.publicKey,
80
- sig: signature
81
- });
82
- }
83
- }
84
- bytesToSignForDelegation(msig) {
85
- if (msig) return require_array.concatArrays(MSIG_PROGRAM_TAG, msig.addr.publicKey, this.logic);
86
- else return require_array.concatArrays(PROGRAM_TAG, this.logic);
87
- }
88
- signProgramData(data, signer) {
89
- return signer(data, this);
90
- }
91
- programDataToSign(data) {
92
- return require_array.concatArrays(SIGN_PROGRAM_DATA_PREFIX, this.address().publicKey, data);
103
+ async signForDelegation(delegator) {
104
+ const result = await delegator.lsigSigner(this);
105
+ if (!result.addr.equals(this._addr)) throw new Error(`Delegator address from signer does not match expected delegator address. Expected: ${this._addr.toString()}, got: ${result.addr.toString()}`);
106
+ if ("sig" in result && result.sig) this.sig = result.sig;
107
+ else if ("lmsig" in result && result.lmsig) this.lmsig = result.lmsig;
108
+ else throw new Error("Delegated lsig signer must return either a sig or lmsig");
93
109
  }
94
110
  };
95
111
 
96
112
  //#endregion
113
+ exports.LogicSig = LogicSig;
97
114
  exports.LogicSigAccount = LogicSigAccount;
98
115
  //# sourceMappingURL=logicsig.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"logicsig.js","names":["decodeMsgpack","logicSignatureCodec","args: Uint8Array[]","signedTxns: Uint8Array[]","stxn: SignedTransaction","encodeSignedTransaction","Address","hash","concatArrays"],"sources":["../../../../packages/transact/src/logicsig.ts"],"sourcesContent":["import { Address, concatArrays, decodeMsgpack, hash } from '@algorandfoundation/algokit-common'\nimport { MultisigAccount } from './multisig'\nimport { TransactionSigner } from './signer'\nimport { LogicSignature, MultisigSignature, SignedTransaction, encodeSignedTransaction } from './transactions/signed-transaction'\nimport { Transaction } from './transactions/transaction'\nimport { logicSignatureCodec } from './transactions/signed-transaction-meta'\n\nconst PROGRAM_TAG = new TextEncoder().encode('Program')\nconst MSIG_PROGRAM_TAG = new TextEncoder().encode('MsigProgram')\nconst SIGN_PROGRAM_DATA_PREFIX = new TextEncoder().encode('ProgData')\n\n/** Function for signing logic signatures for delegation */\nexport type DelegatedLsigSigner = (lsig: LogicSigAccount, msig?: MultisigAccount) => Promise<Uint8Array>\n\n/** Function for signing program data for a logic signature */\nexport type ProgramDataSigner = (data: Uint8Array, lsig: LogicSigAccount) => Promise<Uint8Array>\n\nexport class LogicSigAccount {\n logic: Uint8Array\n args: Uint8Array[]\n sig?: Uint8Array\n msig?: MultisigSignature\n lmsig?: MultisigSignature\n\n static fromSignature(signature: LogicSignature): LogicSigAccount {\n const lsigAccount = new LogicSigAccount(signature.logic, signature.args || [])\n lsigAccount.sig = signature.sig\n lsigAccount.msig = signature.msig\n lsigAccount.lmsig = signature.lmsig\n return lsigAccount\n }\n\n static fromBytes(encodedLsig: Uint8Array): LogicSigAccount {\n const decoded = decodeMsgpack(encodedLsig)\n const lsigSignature = logicSignatureCodec.decode(decoded, 'msgpack')\n return LogicSigAccount.fromSignature(lsigSignature)\n }\n\n constructor(program: Uint8Array, programArgs?: Array<Uint8Array> | null) {\n if (programArgs && (!Array.isArray(programArgs) || !programArgs.every((arg) => arg.constructor === Uint8Array))) {\n throw new TypeError('Invalid arguments')\n }\n\n let args: Uint8Array[] = []\n if (programArgs != null) args = programArgs.map((arg) => new Uint8Array(arg))\n\n this.logic = program\n this.args = args\n }\n\n get signer(): TransactionSigner {\n return async (txns: Transaction[], indexes: number[]) => {\n const signedTxns: Uint8Array[] = []\n for (const index of indexes) {\n const txn = txns[index]\n\n const stxn: SignedTransaction = {\n txn,\n lsig: { logic: this.logic, args: this.args, msig: this.msig, lmsig: this.lmsig, sig: this.sig },\n }\n\n signedTxns.push(encodeSignedTransaction(stxn))\n }\n\n return signedTxns\n }\n }\n\n get addr(): Address {\n return this.address()\n }\n\n /**\n * Compute hash of the logic sig program (that is the same as escrow account address) as string address\n * @returns String representation of the address\n */\n address(): Address {\n const toBeSigned = concatArrays(PROGRAM_TAG, this.logic)\n const h = hash(toBeSigned)\n return new Address(h)\n }\n\n async delegate(signer: DelegatedLsigSigner) {\n this.sig = await signer(this)\n }\n\n async delegateMultisig(msig: MultisigAccount) {\n if (this.lmsig == undefined) {\n this.lmsig = {\n subsigs: [],\n version: msig.params.version,\n threshold: msig.params.threshold,\n }\n }\n for (const addrWithSigner of msig.subSigners) {\n const { lsigSigner, addr } = addrWithSigner\n const signature = await lsigSigner(this, msig)\n\n this.lmsig.subsigs.push({ publicKey: addr.publicKey, sig: signature })\n }\n }\n\n bytesToSignForDelegation(msig?: MultisigAccount): Uint8Array {\n if (msig) {\n return concatArrays(MSIG_PROGRAM_TAG, msig.addr.publicKey, this.logic)\n } else {\n return concatArrays(PROGRAM_TAG, this.logic)\n }\n }\n\n signProgramData(data: Uint8Array, signer: ProgramDataSigner): Promise<Uint8Array> {\n return signer(data, this)\n }\n\n programDataToSign(data: Uint8Array): Uint8Array {\n return concatArrays(SIGN_PROGRAM_DATA_PREFIX, this.address().publicKey, data)\n }\n}\n"],"mappings":";;;;;;;;AAOA,MAAM,cAAc,IAAI,aAAa,CAAC,OAAO,UAAU;AACvD,MAAM,mBAAmB,IAAI,aAAa,CAAC,OAAO,cAAc;AAChE,MAAM,2BAA2B,IAAI,aAAa,CAAC,OAAO,WAAW;AAQrE,IAAa,kBAAb,MAAa,gBAAgB;CAC3B;CACA;CACA;CACA;CACA;CAEA,OAAO,cAAc,WAA4C;EAC/D,MAAM,cAAc,IAAI,gBAAgB,UAAU,OAAO,UAAU,QAAQ,EAAE,CAAC;AAC9E,cAAY,MAAM,UAAU;AAC5B,cAAY,OAAO,UAAU;AAC7B,cAAY,QAAQ,UAAU;AAC9B,SAAO;;CAGT,OAAO,UAAU,aAA0C;EACzD,MAAM,UAAUA,8BAAc,YAAY;EAC1C,MAAM,gBAAgBC,oDAAoB,OAAO,SAAS,UAAU;AACpE,SAAO,gBAAgB,cAAc,cAAc;;CAGrD,YAAY,SAAqB,aAAwC;AACvE,MAAI,gBAAgB,CAAC,MAAM,QAAQ,YAAY,IAAI,CAAC,YAAY,OAAO,QAAQ,IAAI,gBAAgB,WAAW,EAC5G,OAAM,IAAI,UAAU,oBAAoB;EAG1C,IAAIC,OAAqB,EAAE;AAC3B,MAAI,eAAe,KAAM,QAAO,YAAY,KAAK,QAAQ,IAAI,WAAW,IAAI,CAAC;AAE7E,OAAK,QAAQ;AACb,OAAK,OAAO;;CAGd,IAAI,SAA4B;AAC9B,SAAO,OAAO,MAAqB,YAAsB;GACvD,MAAMC,aAA2B,EAAE;AACnC,QAAK,MAAM,SAAS,SAAS;IAG3B,MAAMC,OAA0B;KAC9B,KAHU,KAAK;KAIf,MAAM;MAAE,OAAO,KAAK;MAAO,MAAM,KAAK;MAAM,MAAM,KAAK;MAAM,OAAO,KAAK;MAAO,KAAK,KAAK;MAAK;KAChG;AAED,eAAW,KAAKC,mDAAwB,KAAK,CAAC;;AAGhD,UAAO;;;CAIX,IAAI,OAAgB;AAClB,SAAO,KAAK,SAAS;;;;;;CAOvB,UAAmB;AAGjB,SAAO,IAAIC,wBADDC,oBADSC,2BAAa,aAAa,KAAK,MAAM,CAC9B,CACL;;CAGvB,MAAM,SAAS,QAA6B;AAC1C,OAAK,MAAM,MAAM,OAAO,KAAK;;CAG/B,MAAM,iBAAiB,MAAuB;AAC5C,MAAI,KAAK,SAAS,OAChB,MAAK,QAAQ;GACX,SAAS,EAAE;GACX,SAAS,KAAK,OAAO;GACrB,WAAW,KAAK,OAAO;GACxB;AAEH,OAAK,MAAM,kBAAkB,KAAK,YAAY;GAC5C,MAAM,EAAE,YAAY,SAAS;GAC7B,MAAM,YAAY,MAAM,WAAW,MAAM,KAAK;AAE9C,QAAK,MAAM,QAAQ,KAAK;IAAE,WAAW,KAAK;IAAW,KAAK;IAAW,CAAC;;;CAI1E,yBAAyB,MAAoC;AAC3D,MAAI,KACF,QAAOA,2BAAa,kBAAkB,KAAK,KAAK,WAAW,KAAK,MAAM;MAEtE,QAAOA,2BAAa,aAAa,KAAK,MAAM;;CAIhD,gBAAgB,MAAkB,QAAgD;AAChF,SAAO,OAAO,MAAM,KAAK;;CAG3B,kBAAkB,MAA8B;AAC9C,SAAOA,2BAAa,0BAA0B,KAAK,SAAS,CAAC,WAAW,KAAK"}
1
+ {"version":3,"file":"logicsig.js","names":["Address","hash","concatArrays","decodeMsgpack","logicSigSignatureCodec","MultisigAccount","signedTxns: Uint8Array[]","stxn: SignedTransaction","encodeSignedTransaction"],"sources":["../../../../packages/transact/src/logicsig.ts"],"sourcesContent":["import { Address, Addressable, concatArrays, decodeMsgpack, hash } from '@algorandfoundation/algokit-common'\nimport { MultisigAccount } from './multisig'\nimport { AddressWithDelegatedLsigSigner, TransactionSigner } from './signer'\nimport { LogicSigSignature, MultisigSignature, SignedTransaction, encodeSignedTransaction } from './transactions/signed-transaction'\nimport { logicSigSignatureCodec } from './transactions/signed-transaction-meta'\nimport { Transaction } from './transactions/transaction'\n\nconst PROGRAM_TAG = new TextEncoder().encode('Program')\nconst MSIG_PROGRAM_TAG = new TextEncoder().encode('MsigProgram')\nconst SIGN_PROGRAM_DATA_PREFIX = new TextEncoder().encode('ProgData')\n\n/** Function for signing logic signatures for delegation\n * @param lsig - The logic signature that is being signed for delegation\n * @param msig - Optional multisig account that should be set when a public key is signing as a subsigner of a multisig\n * @returns The address of the delegator\n * */\nexport type DelegatedLsigSigner = (\n lsig: LogicSigAccount,\n msig?: MultisigAccount,\n) => Promise<{ addr: Address } & ({ sig?: Uint8Array } | { lmsig?: MultisigSignature })>\n\n/** Function for signing program data for a logic signature */\nexport type ProgramDataSigner = (data: Uint8Array, lsig: LogicSig) => Promise<Uint8Array>\n\nexport class LogicSig implements Addressable {\n logic: Uint8Array\n args: Uint8Array[]\n protected _addr: Address\n\n constructor(program: Uint8Array, programArgs?: Array<Uint8Array>) {\n this.logic = program\n this.args = programArgs ?? []\n const toBeSigned = concatArrays(PROGRAM_TAG, this.logic)\n const h = hash(toBeSigned)\n this._addr = new Address(h)\n }\n\n static fromSignature(signature: LogicSigSignature): LogicSig {\n return new LogicSig(signature.logic, signature.args || [])\n }\n\n static fromBytes(encodedLsig: Uint8Array): LogicSig {\n const decoded = decodeMsgpack(encodedLsig)\n const lsigSignature = logicSigSignatureCodec.decode(decoded, 'msgpack')\n return LogicSig.fromSignature(lsigSignature)\n }\n\n address(): Address {\n return this._addr\n }\n\n get addr(): Address {\n return this._addr\n }\n\n bytesToSignForDelegation(msig?: MultisigAccount): Uint8Array {\n if (msig) {\n return concatArrays(MSIG_PROGRAM_TAG, msig.addr.publicKey, this.logic)\n } else {\n return concatArrays(PROGRAM_TAG, this.logic)\n }\n }\n\n signProgramData(data: Uint8Array, signer: ProgramDataSigner): Promise<Uint8Array> {\n return signer(data, this)\n }\n\n programDataToSign(data: Uint8Array): Uint8Array {\n return concatArrays(SIGN_PROGRAM_DATA_PREFIX, this.address().publicKey, data)\n }\n\n account(): LogicSigAccount {\n return new LogicSigAccount(this.logic, this.args)\n }\n\n delegatedAccount(delegator: Address): LogicSigAccount {\n return new LogicSigAccount(this.logic, this.args, delegator)\n }\n}\n\nexport class LogicSigAccount extends LogicSig {\n sig?: Uint8Array\n msig?: MultisigSignature\n lmsig?: MultisigSignature\n\n static fromSignature(signature: LogicSigSignature, delegator?: Address): LogicSigAccount {\n if (signature.lmsig || signature.msig) {\n const msigAddr = MultisigAccount.fromSignature((signature.lmsig || signature.msig)!).addr\n\n if (delegator && !msigAddr.equals(delegator)) {\n throw new Error('Provided delegator address does not match multisig address')\n }\n\n const lsig = new LogicSigAccount(signature.logic, signature.args || [], msigAddr)\n lsig.lmsig = signature.lmsig\n lsig.msig = signature.msig\n return lsig\n }\n\n const lsigAccount = new LogicSigAccount(signature.logic, signature.args || [], delegator)\n\n if (signature.sig && delegator === undefined) {\n throw new Error('Delegated address must be provided when logic sig has a signature')\n }\n\n if (signature.sig) {\n lsigAccount.sig = signature.sig\n return lsigAccount\n }\n\n return lsigAccount\n }\n\n static fromBytes(encodedLsig: Uint8Array, delegator?: Address): LogicSigAccount {\n const decoded = decodeMsgpack(encodedLsig)\n const lsigSignature = logicSigSignatureCodec.decode(decoded, 'msgpack')\n return LogicSigAccount.fromSignature(lsigSignature, delegator)\n }\n\n constructor(program: Uint8Array, programArgs?: Array<Uint8Array> | null, delegator?: Address) {\n super(program, programArgs ?? undefined)\n this._addr = delegator ?? this._addr\n }\n\n get signer(): TransactionSigner {\n return async (txns: Transaction[], indexes: number[]) => {\n const signedTxns: Uint8Array[] = []\n for (const index of indexes) {\n const txn = txns[index]\n\n const stxn: SignedTransaction = {\n txn,\n lsig: { logic: this.logic, args: this.args, msig: this.msig, lmsig: this.lmsig, sig: this.sig },\n }\n\n if (!stxn.txn.sender.equals(this.addr)) {\n stxn.authAddress = this.addr\n }\n\n signedTxns.push(encodeSignedTransaction(stxn))\n }\n\n return signedTxns\n }\n }\n\n async signForDelegation(delegator: AddressWithDelegatedLsigSigner) {\n const result = await delegator.lsigSigner(this)\n\n if (!result.addr.equals(this._addr)) {\n throw new Error(\n `Delegator address from signer does not match expected delegator address. Expected: ${this._addr.toString()}, got: ${result.addr.toString()}`,\n )\n }\n\n if ('sig' in result && result.sig) {\n this.sig = result.sig\n } else if ('lmsig' in result && result.lmsig) {\n this.lmsig = result.lmsig\n } else {\n throw new Error('Delegated lsig signer must return either a sig or lmsig')\n }\n }\n}\n"],"mappings":";;;;;;;;;AAOA,MAAM,cAAc,IAAI,aAAa,CAAC,OAAO,UAAU;AACvD,MAAM,mBAAmB,IAAI,aAAa,CAAC,OAAO,cAAc;AAChE,MAAM,2BAA2B,IAAI,aAAa,CAAC,OAAO,WAAW;AAerE,IAAa,WAAb,MAAa,SAAgC;CAC3C;CACA;CACA,AAAU;CAEV,YAAY,SAAqB,aAAiC;AAChE,OAAK,QAAQ;AACb,OAAK,OAAO,eAAe,EAAE;AAG7B,OAAK,QAAQ,IAAIA,wBADPC,oBADSC,2BAAa,aAAa,KAAK,MAAM,CAC9B,CACC;;CAG7B,OAAO,cAAc,WAAwC;AAC3D,SAAO,IAAI,SAAS,UAAU,OAAO,UAAU,QAAQ,EAAE,CAAC;;CAG5D,OAAO,UAAU,aAAmC;EAClD,MAAM,UAAUC,8BAAc,YAAY;EAC1C,MAAM,gBAAgBC,uDAAuB,OAAO,SAAS,UAAU;AACvE,SAAO,SAAS,cAAc,cAAc;;CAG9C,UAAmB;AACjB,SAAO,KAAK;;CAGd,IAAI,OAAgB;AAClB,SAAO,KAAK;;CAGd,yBAAyB,MAAoC;AAC3D,MAAI,KACF,QAAOF,2BAAa,kBAAkB,KAAK,KAAK,WAAW,KAAK,MAAM;MAEtE,QAAOA,2BAAa,aAAa,KAAK,MAAM;;CAIhD,gBAAgB,MAAkB,QAAgD;AAChF,SAAO,OAAO,MAAM,KAAK;;CAG3B,kBAAkB,MAA8B;AAC9C,SAAOA,2BAAa,0BAA0B,KAAK,SAAS,CAAC,WAAW,KAAK;;CAG/E,UAA2B;AACzB,SAAO,IAAI,gBAAgB,KAAK,OAAO,KAAK,KAAK;;CAGnD,iBAAiB,WAAqC;AACpD,SAAO,IAAI,gBAAgB,KAAK,OAAO,KAAK,MAAM,UAAU;;;AAIhE,IAAa,kBAAb,MAAa,wBAAwB,SAAS;CAC5C;CACA;CACA;CAEA,OAAO,cAAc,WAA8B,WAAsC;AACvF,MAAI,UAAU,SAAS,UAAU,MAAM;GACrC,MAAM,WAAWG,iCAAgB,cAAe,UAAU,SAAS,UAAU,KAAO,CAAC;AAErF,OAAI,aAAa,CAAC,SAAS,OAAO,UAAU,CAC1C,OAAM,IAAI,MAAM,6DAA6D;GAG/E,MAAM,OAAO,IAAI,gBAAgB,UAAU,OAAO,UAAU,QAAQ,EAAE,EAAE,SAAS;AACjF,QAAK,QAAQ,UAAU;AACvB,QAAK,OAAO,UAAU;AACtB,UAAO;;EAGT,MAAM,cAAc,IAAI,gBAAgB,UAAU,OAAO,UAAU,QAAQ,EAAE,EAAE,UAAU;AAEzF,MAAI,UAAU,OAAO,cAAc,OACjC,OAAM,IAAI,MAAM,oEAAoE;AAGtF,MAAI,UAAU,KAAK;AACjB,eAAY,MAAM,UAAU;AAC5B,UAAO;;AAGT,SAAO;;CAGT,OAAO,UAAU,aAAyB,WAAsC;EAC9E,MAAM,UAAUF,8BAAc,YAAY;EAC1C,MAAM,gBAAgBC,uDAAuB,OAAO,SAAS,UAAU;AACvE,SAAO,gBAAgB,cAAc,eAAe,UAAU;;CAGhE,YAAY,SAAqB,aAAwC,WAAqB;AAC5F,QAAM,SAAS,eAAe,OAAU;AACxC,OAAK,QAAQ,aAAa,KAAK;;CAGjC,IAAI,SAA4B;AAC9B,SAAO,OAAO,MAAqB,YAAsB;GACvD,MAAME,aAA2B,EAAE;AACnC,QAAK,MAAM,SAAS,SAAS;IAG3B,MAAMC,OAA0B;KAC9B,KAHU,KAAK;KAIf,MAAM;MAAE,OAAO,KAAK;MAAO,MAAM,KAAK;MAAM,MAAM,KAAK;MAAM,OAAO,KAAK;MAAO,KAAK,KAAK;MAAK;KAChG;AAED,QAAI,CAAC,KAAK,IAAI,OAAO,OAAO,KAAK,KAAK,CACpC,MAAK,cAAc,KAAK;AAG1B,eAAW,KAAKC,mDAAwB,KAAK,CAAC;;AAGhD,UAAO;;;CAIX,MAAM,kBAAkB,WAA2C;EACjE,MAAM,SAAS,MAAM,UAAU,WAAW,KAAK;AAE/C,MAAI,CAAC,OAAO,KAAK,OAAO,KAAK,MAAM,CACjC,OAAM,IAAI,MACR,sFAAsF,KAAK,MAAM,UAAU,CAAC,SAAS,OAAO,KAAK,UAAU,GAC5I;AAGH,MAAI,SAAS,UAAU,OAAO,IAC5B,MAAK,MAAM,OAAO;WACT,WAAW,UAAU,OAAO,MACrC,MAAK,QAAQ,OAAO;MAEpB,OAAM,IAAI,MAAM,0DAA0D"}
@@ -2,37 +2,83 @@ import { concatArrays } from "../../common/src/array.mjs";
2
2
  import { Address } from "../../common/src/address.mjs";
3
3
  import { hash } from "../../common/src/crypto.mjs";
4
4
  import { decodeMsgpack } from "../../common/src/msgpack.mjs";
5
- import { logicSignatureCodec } from "./transactions/signed-transaction-meta.mjs";
5
+ import { logicSigSignatureCodec } from "./transactions/signed-transaction-meta.mjs";
6
6
  import { encodeSignedTransaction } from "./transactions/signed-transaction.mjs";
7
+ import { MultisigAccount } from "./multisig.mjs";
7
8
 
8
9
  //#region packages/transact/src/logicsig.ts
9
10
  const PROGRAM_TAG = new TextEncoder().encode("Program");
10
11
  const MSIG_PROGRAM_TAG = new TextEncoder().encode("MsigProgram");
11
12
  const SIGN_PROGRAM_DATA_PREFIX = new TextEncoder().encode("ProgData");
12
- var LogicSigAccount = class LogicSigAccount {
13
+ var LogicSig = class LogicSig {
13
14
  logic;
14
15
  args;
16
+ _addr;
17
+ constructor(program, programArgs) {
18
+ this.logic = program;
19
+ this.args = programArgs ?? [];
20
+ this._addr = new Address(hash(concatArrays(PROGRAM_TAG, this.logic)));
21
+ }
22
+ static fromSignature(signature) {
23
+ return new LogicSig(signature.logic, signature.args || []);
24
+ }
25
+ static fromBytes(encodedLsig) {
26
+ const decoded = decodeMsgpack(encodedLsig);
27
+ const lsigSignature = logicSigSignatureCodec.decode(decoded, "msgpack");
28
+ return LogicSig.fromSignature(lsigSignature);
29
+ }
30
+ address() {
31
+ return this._addr;
32
+ }
33
+ get addr() {
34
+ return this._addr;
35
+ }
36
+ bytesToSignForDelegation(msig) {
37
+ if (msig) return concatArrays(MSIG_PROGRAM_TAG, msig.addr.publicKey, this.logic);
38
+ else return concatArrays(PROGRAM_TAG, this.logic);
39
+ }
40
+ signProgramData(data, signer) {
41
+ return signer(data, this);
42
+ }
43
+ programDataToSign(data) {
44
+ return concatArrays(SIGN_PROGRAM_DATA_PREFIX, this.address().publicKey, data);
45
+ }
46
+ account() {
47
+ return new LogicSigAccount(this.logic, this.args);
48
+ }
49
+ delegatedAccount(delegator) {
50
+ return new LogicSigAccount(this.logic, this.args, delegator);
51
+ }
52
+ };
53
+ var LogicSigAccount = class LogicSigAccount extends LogicSig {
15
54
  sig;
16
55
  msig;
17
56
  lmsig;
18
- static fromSignature(signature) {
19
- const lsigAccount = new LogicSigAccount(signature.logic, signature.args || []);
20
- lsigAccount.sig = signature.sig;
21
- lsigAccount.msig = signature.msig;
22
- lsigAccount.lmsig = signature.lmsig;
57
+ static fromSignature(signature, delegator) {
58
+ if (signature.lmsig || signature.msig) {
59
+ const msigAddr = MultisigAccount.fromSignature(signature.lmsig || signature.msig).addr;
60
+ if (delegator && !msigAddr.equals(delegator)) throw new Error("Provided delegator address does not match multisig address");
61
+ const lsig = new LogicSigAccount(signature.logic, signature.args || [], msigAddr);
62
+ lsig.lmsig = signature.lmsig;
63
+ lsig.msig = signature.msig;
64
+ return lsig;
65
+ }
66
+ const lsigAccount = new LogicSigAccount(signature.logic, signature.args || [], delegator);
67
+ if (signature.sig && delegator === void 0) throw new Error("Delegated address must be provided when logic sig has a signature");
68
+ if (signature.sig) {
69
+ lsigAccount.sig = signature.sig;
70
+ return lsigAccount;
71
+ }
23
72
  return lsigAccount;
24
73
  }
25
- static fromBytes(encodedLsig) {
74
+ static fromBytes(encodedLsig, delegator) {
26
75
  const decoded = decodeMsgpack(encodedLsig);
27
- const lsigSignature = logicSignatureCodec.decode(decoded, "msgpack");
28
- return LogicSigAccount.fromSignature(lsigSignature);
76
+ const lsigSignature = logicSigSignatureCodec.decode(decoded, "msgpack");
77
+ return LogicSigAccount.fromSignature(lsigSignature, delegator);
29
78
  }
30
- constructor(program, programArgs) {
31
- if (programArgs && (!Array.isArray(programArgs) || !programArgs.every((arg) => arg.constructor === Uint8Array))) throw new TypeError("Invalid arguments");
32
- let args = [];
33
- if (programArgs != null) args = programArgs.map((arg) => new Uint8Array(arg));
34
- this.logic = program;
35
- this.args = args;
79
+ constructor(program, programArgs, delegator) {
80
+ super(program, programArgs ?? void 0);
81
+ this._addr = delegator ?? this._addr;
36
82
  }
37
83
  get signer() {
38
84
  return async (txns, indexes) => {
@@ -48,51 +94,21 @@ var LogicSigAccount = class LogicSigAccount {
48
94
  sig: this.sig
49
95
  }
50
96
  };
97
+ if (!stxn.txn.sender.equals(this.addr)) stxn.authAddress = this.addr;
51
98
  signedTxns.push(encodeSignedTransaction(stxn));
52
99
  }
53
100
  return signedTxns;
54
101
  };
55
102
  }
56
- get addr() {
57
- return this.address();
58
- }
59
- /**
60
- * Compute hash of the logic sig program (that is the same as escrow account address) as string address
61
- * @returns String representation of the address
62
- */
63
- address() {
64
- return new Address(hash(concatArrays(PROGRAM_TAG, this.logic)));
65
- }
66
- async delegate(signer) {
67
- this.sig = await signer(this);
68
- }
69
- async delegateMultisig(msig) {
70
- if (this.lmsig == void 0) this.lmsig = {
71
- subsigs: [],
72
- version: msig.params.version,
73
- threshold: msig.params.threshold
74
- };
75
- for (const addrWithSigner of msig.subSigners) {
76
- const { lsigSigner, addr } = addrWithSigner;
77
- const signature = await lsigSigner(this, msig);
78
- this.lmsig.subsigs.push({
79
- publicKey: addr.publicKey,
80
- sig: signature
81
- });
82
- }
83
- }
84
- bytesToSignForDelegation(msig) {
85
- if (msig) return concatArrays(MSIG_PROGRAM_TAG, msig.addr.publicKey, this.logic);
86
- else return concatArrays(PROGRAM_TAG, this.logic);
87
- }
88
- signProgramData(data, signer) {
89
- return signer(data, this);
90
- }
91
- programDataToSign(data) {
92
- return concatArrays(SIGN_PROGRAM_DATA_PREFIX, this.address().publicKey, data);
103
+ async signForDelegation(delegator) {
104
+ const result = await delegator.lsigSigner(this);
105
+ if (!result.addr.equals(this._addr)) throw new Error(`Delegator address from signer does not match expected delegator address. Expected: ${this._addr.toString()}, got: ${result.addr.toString()}`);
106
+ if ("sig" in result && result.sig) this.sig = result.sig;
107
+ else if ("lmsig" in result && result.lmsig) this.lmsig = result.lmsig;
108
+ else throw new Error("Delegated lsig signer must return either a sig or lmsig");
93
109
  }
94
110
  };
95
111
 
96
112
  //#endregion
97
- export { LogicSigAccount };
113
+ export { LogicSig, LogicSigAccount };
98
114
  //# sourceMappingURL=logicsig.mjs.map
@@ -1 +1 @@
1
- {"version":3,"file":"logicsig.mjs","names":["args: Uint8Array[]","signedTxns: Uint8Array[]","stxn: SignedTransaction"],"sources":["../../../../packages/transact/src/logicsig.ts"],"sourcesContent":["import { Address, concatArrays, decodeMsgpack, hash } from '@algorandfoundation/algokit-common'\nimport { MultisigAccount } from './multisig'\nimport { TransactionSigner } from './signer'\nimport { LogicSignature, MultisigSignature, SignedTransaction, encodeSignedTransaction } from './transactions/signed-transaction'\nimport { Transaction } from './transactions/transaction'\nimport { logicSignatureCodec } from './transactions/signed-transaction-meta'\n\nconst PROGRAM_TAG = new TextEncoder().encode('Program')\nconst MSIG_PROGRAM_TAG = new TextEncoder().encode('MsigProgram')\nconst SIGN_PROGRAM_DATA_PREFIX = new TextEncoder().encode('ProgData')\n\n/** Function for signing logic signatures for delegation */\nexport type DelegatedLsigSigner = (lsig: LogicSigAccount, msig?: MultisigAccount) => Promise<Uint8Array>\n\n/** Function for signing program data for a logic signature */\nexport type ProgramDataSigner = (data: Uint8Array, lsig: LogicSigAccount) => Promise<Uint8Array>\n\nexport class LogicSigAccount {\n logic: Uint8Array\n args: Uint8Array[]\n sig?: Uint8Array\n msig?: MultisigSignature\n lmsig?: MultisigSignature\n\n static fromSignature(signature: LogicSignature): LogicSigAccount {\n const lsigAccount = new LogicSigAccount(signature.logic, signature.args || [])\n lsigAccount.sig = signature.sig\n lsigAccount.msig = signature.msig\n lsigAccount.lmsig = signature.lmsig\n return lsigAccount\n }\n\n static fromBytes(encodedLsig: Uint8Array): LogicSigAccount {\n const decoded = decodeMsgpack(encodedLsig)\n const lsigSignature = logicSignatureCodec.decode(decoded, 'msgpack')\n return LogicSigAccount.fromSignature(lsigSignature)\n }\n\n constructor(program: Uint8Array, programArgs?: Array<Uint8Array> | null) {\n if (programArgs && (!Array.isArray(programArgs) || !programArgs.every((arg) => arg.constructor === Uint8Array))) {\n throw new TypeError('Invalid arguments')\n }\n\n let args: Uint8Array[] = []\n if (programArgs != null) args = programArgs.map((arg) => new Uint8Array(arg))\n\n this.logic = program\n this.args = args\n }\n\n get signer(): TransactionSigner {\n return async (txns: Transaction[], indexes: number[]) => {\n const signedTxns: Uint8Array[] = []\n for (const index of indexes) {\n const txn = txns[index]\n\n const stxn: SignedTransaction = {\n txn,\n lsig: { logic: this.logic, args: this.args, msig: this.msig, lmsig: this.lmsig, sig: this.sig },\n }\n\n signedTxns.push(encodeSignedTransaction(stxn))\n }\n\n return signedTxns\n }\n }\n\n get addr(): Address {\n return this.address()\n }\n\n /**\n * Compute hash of the logic sig program (that is the same as escrow account address) as string address\n * @returns String representation of the address\n */\n address(): Address {\n const toBeSigned = concatArrays(PROGRAM_TAG, this.logic)\n const h = hash(toBeSigned)\n return new Address(h)\n }\n\n async delegate(signer: DelegatedLsigSigner) {\n this.sig = await signer(this)\n }\n\n async delegateMultisig(msig: MultisigAccount) {\n if (this.lmsig == undefined) {\n this.lmsig = {\n subsigs: [],\n version: msig.params.version,\n threshold: msig.params.threshold,\n }\n }\n for (const addrWithSigner of msig.subSigners) {\n const { lsigSigner, addr } = addrWithSigner\n const signature = await lsigSigner(this, msig)\n\n this.lmsig.subsigs.push({ publicKey: addr.publicKey, sig: signature })\n }\n }\n\n bytesToSignForDelegation(msig?: MultisigAccount): Uint8Array {\n if (msig) {\n return concatArrays(MSIG_PROGRAM_TAG, msig.addr.publicKey, this.logic)\n } else {\n return concatArrays(PROGRAM_TAG, this.logic)\n }\n }\n\n signProgramData(data: Uint8Array, signer: ProgramDataSigner): Promise<Uint8Array> {\n return signer(data, this)\n }\n\n programDataToSign(data: Uint8Array): Uint8Array {\n return concatArrays(SIGN_PROGRAM_DATA_PREFIX, this.address().publicKey, data)\n }\n}\n"],"mappings":";;;;;;;;AAOA,MAAM,cAAc,IAAI,aAAa,CAAC,OAAO,UAAU;AACvD,MAAM,mBAAmB,IAAI,aAAa,CAAC,OAAO,cAAc;AAChE,MAAM,2BAA2B,IAAI,aAAa,CAAC,OAAO,WAAW;AAQrE,IAAa,kBAAb,MAAa,gBAAgB;CAC3B;CACA;CACA;CACA;CACA;CAEA,OAAO,cAAc,WAA4C;EAC/D,MAAM,cAAc,IAAI,gBAAgB,UAAU,OAAO,UAAU,QAAQ,EAAE,CAAC;AAC9E,cAAY,MAAM,UAAU;AAC5B,cAAY,OAAO,UAAU;AAC7B,cAAY,QAAQ,UAAU;AAC9B,SAAO;;CAGT,OAAO,UAAU,aAA0C;EACzD,MAAM,UAAU,cAAc,YAAY;EAC1C,MAAM,gBAAgB,oBAAoB,OAAO,SAAS,UAAU;AACpE,SAAO,gBAAgB,cAAc,cAAc;;CAGrD,YAAY,SAAqB,aAAwC;AACvE,MAAI,gBAAgB,CAAC,MAAM,QAAQ,YAAY,IAAI,CAAC,YAAY,OAAO,QAAQ,IAAI,gBAAgB,WAAW,EAC5G,OAAM,IAAI,UAAU,oBAAoB;EAG1C,IAAIA,OAAqB,EAAE;AAC3B,MAAI,eAAe,KAAM,QAAO,YAAY,KAAK,QAAQ,IAAI,WAAW,IAAI,CAAC;AAE7E,OAAK,QAAQ;AACb,OAAK,OAAO;;CAGd,IAAI,SAA4B;AAC9B,SAAO,OAAO,MAAqB,YAAsB;GACvD,MAAMC,aAA2B,EAAE;AACnC,QAAK,MAAM,SAAS,SAAS;IAG3B,MAAMC,OAA0B;KAC9B,KAHU,KAAK;KAIf,MAAM;MAAE,OAAO,KAAK;MAAO,MAAM,KAAK;MAAM,MAAM,KAAK;MAAM,OAAO,KAAK;MAAO,KAAK,KAAK;MAAK;KAChG;AAED,eAAW,KAAK,wBAAwB,KAAK,CAAC;;AAGhD,UAAO;;;CAIX,IAAI,OAAgB;AAClB,SAAO,KAAK,SAAS;;;;;;CAOvB,UAAmB;AAGjB,SAAO,IAAI,QADD,KADS,aAAa,aAAa,KAAK,MAAM,CAC9B,CACL;;CAGvB,MAAM,SAAS,QAA6B;AAC1C,OAAK,MAAM,MAAM,OAAO,KAAK;;CAG/B,MAAM,iBAAiB,MAAuB;AAC5C,MAAI,KAAK,SAAS,OAChB,MAAK,QAAQ;GACX,SAAS,EAAE;GACX,SAAS,KAAK,OAAO;GACrB,WAAW,KAAK,OAAO;GACxB;AAEH,OAAK,MAAM,kBAAkB,KAAK,YAAY;GAC5C,MAAM,EAAE,YAAY,SAAS;GAC7B,MAAM,YAAY,MAAM,WAAW,MAAM,KAAK;AAE9C,QAAK,MAAM,QAAQ,KAAK;IAAE,WAAW,KAAK;IAAW,KAAK;IAAW,CAAC;;;CAI1E,yBAAyB,MAAoC;AAC3D,MAAI,KACF,QAAO,aAAa,kBAAkB,KAAK,KAAK,WAAW,KAAK,MAAM;MAEtE,QAAO,aAAa,aAAa,KAAK,MAAM;;CAIhD,gBAAgB,MAAkB,QAAgD;AAChF,SAAO,OAAO,MAAM,KAAK;;CAG3B,kBAAkB,MAA8B;AAC9C,SAAO,aAAa,0BAA0B,KAAK,SAAS,CAAC,WAAW,KAAK"}
1
+ {"version":3,"file":"logicsig.mjs","names":["signedTxns: Uint8Array[]","stxn: SignedTransaction"],"sources":["../../../../packages/transact/src/logicsig.ts"],"sourcesContent":["import { Address, Addressable, concatArrays, decodeMsgpack, hash } from '@algorandfoundation/algokit-common'\nimport { MultisigAccount } from './multisig'\nimport { AddressWithDelegatedLsigSigner, TransactionSigner } from './signer'\nimport { LogicSigSignature, MultisigSignature, SignedTransaction, encodeSignedTransaction } from './transactions/signed-transaction'\nimport { logicSigSignatureCodec } from './transactions/signed-transaction-meta'\nimport { Transaction } from './transactions/transaction'\n\nconst PROGRAM_TAG = new TextEncoder().encode('Program')\nconst MSIG_PROGRAM_TAG = new TextEncoder().encode('MsigProgram')\nconst SIGN_PROGRAM_DATA_PREFIX = new TextEncoder().encode('ProgData')\n\n/** Function for signing logic signatures for delegation\n * @param lsig - The logic signature that is being signed for delegation\n * @param msig - Optional multisig account that should be set when a public key is signing as a subsigner of a multisig\n * @returns The address of the delegator\n * */\nexport type DelegatedLsigSigner = (\n lsig: LogicSigAccount,\n msig?: MultisigAccount,\n) => Promise<{ addr: Address } & ({ sig?: Uint8Array } | { lmsig?: MultisigSignature })>\n\n/** Function for signing program data for a logic signature */\nexport type ProgramDataSigner = (data: Uint8Array, lsig: LogicSig) => Promise<Uint8Array>\n\nexport class LogicSig implements Addressable {\n logic: Uint8Array\n args: Uint8Array[]\n protected _addr: Address\n\n constructor(program: Uint8Array, programArgs?: Array<Uint8Array>) {\n this.logic = program\n this.args = programArgs ?? []\n const toBeSigned = concatArrays(PROGRAM_TAG, this.logic)\n const h = hash(toBeSigned)\n this._addr = new Address(h)\n }\n\n static fromSignature(signature: LogicSigSignature): LogicSig {\n return new LogicSig(signature.logic, signature.args || [])\n }\n\n static fromBytes(encodedLsig: Uint8Array): LogicSig {\n const decoded = decodeMsgpack(encodedLsig)\n const lsigSignature = logicSigSignatureCodec.decode(decoded, 'msgpack')\n return LogicSig.fromSignature(lsigSignature)\n }\n\n address(): Address {\n return this._addr\n }\n\n get addr(): Address {\n return this._addr\n }\n\n bytesToSignForDelegation(msig?: MultisigAccount): Uint8Array {\n if (msig) {\n return concatArrays(MSIG_PROGRAM_TAG, msig.addr.publicKey, this.logic)\n } else {\n return concatArrays(PROGRAM_TAG, this.logic)\n }\n }\n\n signProgramData(data: Uint8Array, signer: ProgramDataSigner): Promise<Uint8Array> {\n return signer(data, this)\n }\n\n programDataToSign(data: Uint8Array): Uint8Array {\n return concatArrays(SIGN_PROGRAM_DATA_PREFIX, this.address().publicKey, data)\n }\n\n account(): LogicSigAccount {\n return new LogicSigAccount(this.logic, this.args)\n }\n\n delegatedAccount(delegator: Address): LogicSigAccount {\n return new LogicSigAccount(this.logic, this.args, delegator)\n }\n}\n\nexport class LogicSigAccount extends LogicSig {\n sig?: Uint8Array\n msig?: MultisigSignature\n lmsig?: MultisigSignature\n\n static fromSignature(signature: LogicSigSignature, delegator?: Address): LogicSigAccount {\n if (signature.lmsig || signature.msig) {\n const msigAddr = MultisigAccount.fromSignature((signature.lmsig || signature.msig)!).addr\n\n if (delegator && !msigAddr.equals(delegator)) {\n throw new Error('Provided delegator address does not match multisig address')\n }\n\n const lsig = new LogicSigAccount(signature.logic, signature.args || [], msigAddr)\n lsig.lmsig = signature.lmsig\n lsig.msig = signature.msig\n return lsig\n }\n\n const lsigAccount = new LogicSigAccount(signature.logic, signature.args || [], delegator)\n\n if (signature.sig && delegator === undefined) {\n throw new Error('Delegated address must be provided when logic sig has a signature')\n }\n\n if (signature.sig) {\n lsigAccount.sig = signature.sig\n return lsigAccount\n }\n\n return lsigAccount\n }\n\n static fromBytes(encodedLsig: Uint8Array, delegator?: Address): LogicSigAccount {\n const decoded = decodeMsgpack(encodedLsig)\n const lsigSignature = logicSigSignatureCodec.decode(decoded, 'msgpack')\n return LogicSigAccount.fromSignature(lsigSignature, delegator)\n }\n\n constructor(program: Uint8Array, programArgs?: Array<Uint8Array> | null, delegator?: Address) {\n super(program, programArgs ?? undefined)\n this._addr = delegator ?? this._addr\n }\n\n get signer(): TransactionSigner {\n return async (txns: Transaction[], indexes: number[]) => {\n const signedTxns: Uint8Array[] = []\n for (const index of indexes) {\n const txn = txns[index]\n\n const stxn: SignedTransaction = {\n txn,\n lsig: { logic: this.logic, args: this.args, msig: this.msig, lmsig: this.lmsig, sig: this.sig },\n }\n\n if (!stxn.txn.sender.equals(this.addr)) {\n stxn.authAddress = this.addr\n }\n\n signedTxns.push(encodeSignedTransaction(stxn))\n }\n\n return signedTxns\n }\n }\n\n async signForDelegation(delegator: AddressWithDelegatedLsigSigner) {\n const result = await delegator.lsigSigner(this)\n\n if (!result.addr.equals(this._addr)) {\n throw new Error(\n `Delegator address from signer does not match expected delegator address. Expected: ${this._addr.toString()}, got: ${result.addr.toString()}`,\n )\n }\n\n if ('sig' in result && result.sig) {\n this.sig = result.sig\n } else if ('lmsig' in result && result.lmsig) {\n this.lmsig = result.lmsig\n } else {\n throw new Error('Delegated lsig signer must return either a sig or lmsig')\n }\n }\n}\n"],"mappings":"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"}
@@ -1,6 +1,7 @@
1
1
  import { Address } from "../../common/src/address.js";
2
2
  import { Transaction } from "./transactions/transaction.js";
3
3
  import { MultisigSignature, SignedTransaction } from "./transactions/signed-transaction.js";
4
+ import { DelegatedLsigSigner } from "./logicsig.js";
4
5
  import { AddressWithDelegatedLsigSigner, AddressWithTransactionSigner, TransactionSigner } from "./signer.js";
5
6
 
6
7
  //#region packages/transact/src/multisig.d.ts
@@ -20,11 +21,12 @@ interface MultisigMetadata {
20
21
  addrs: Array<Address>;
21
22
  }
22
23
  /** Account wrapper that supports partial or full multisig signing. */
23
- declare class MultisigAccount implements AddressWithTransactionSigner {
24
+ declare class MultisigAccount implements AddressWithTransactionSigner, AddressWithDelegatedLsigSigner {
24
25
  _params: MultisigMetadata;
25
26
  _subSigners: (AddressWithTransactionSigner & AddressWithDelegatedLsigSigner)[];
26
27
  _addr: Address;
27
28
  _signer: TransactionSigner;
29
+ _lsigSigner: DelegatedLsigSigner;
28
30
  /** The parameters for the multisig account */
29
31
  get params(): Readonly<MultisigMetadata>;
30
32
  /** The list of accounts that are present to sign transactions or lsigs */
@@ -33,6 +35,7 @@ declare class MultisigAccount implements AddressWithTransactionSigner {
33
35
  get addr(): Readonly<Address>;
34
36
  /** The transaction signer for the multisig account */
35
37
  get signer(): TransactionSigner;
38
+ get lsigSigner(): DelegatedLsigSigner;
36
39
  static fromSignature(signature: MultisigSignature): MultisigAccount;
37
40
  constructor(multisigParams: MultisigMetadata, subSigners: (AddressWithTransactionSigner & AddressWithDelegatedLsigSigner)[]);
38
41
  createMultisigTransaction(txn: Transaction): SignedTransaction;
@@ -254,6 +254,7 @@ var MultisigAccount = class MultisigAccount {
254
254
  _subSigners;
255
255
  _addr;
256
256
  _signer;
257
+ _lsigSigner;
257
258
  /** The parameters for the multisig account */
258
259
  get params() {
259
260
  return this._params;
@@ -270,6 +271,9 @@ var MultisigAccount = class MultisigAccount {
270
271
  get signer() {
271
272
  return this._signer;
272
273
  }
274
+ get lsigSigner() {
275
+ return this._lsigSigner;
276
+ }
273
277
  static fromSignature(signature) {
274
278
  return new MultisigAccount({
275
279
  version: signature.version,
@@ -296,6 +300,19 @@ var MultisigAccount = class MultisigAccount {
296
300
  }
297
301
  return signedMsigTxns.map(require_signed_transaction.encodeSignedTransaction);
298
302
  };
303
+ this._lsigSigner = async (lsig, _) => {
304
+ let lmsig = lsig.lmsig ?? this.createMultisigSignature();
305
+ for (const addrWithSigner of this.subSigners) {
306
+ const { lsigSigner, addr } = addrWithSigner;
307
+ const result = await lsigSigner(lsig, this);
308
+ if (!("sig" in result) || !result.sig) throw new Error(`Signer for address ${addr.toString()} did not produce a valid signature when signing logic sig for multisig account ${this._addr.toString()}`);
309
+ lmsig = this.applySignature(lmsig, addr.publicKey, result.sig);
310
+ }
311
+ return {
312
+ addr: this.addr,
313
+ lmsig
314
+ };
315
+ };
299
316
  }
300
317
  createMultisigTransaction(txn) {
301
318
  return createMultisigTransaction(txn, this._params);