@indigo-labs/indigo-sdk 0.1.28 → 0.2.0

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 (135) hide show
  1. package/.github/workflows/ci.yml +8 -3
  2. package/dist/index.d.mts +1300 -671
  3. package/dist/index.d.ts +1300 -671
  4. package/dist/index.js +4663 -2220
  5. package/dist/index.mjs +4594 -2190
  6. package/eslint.config.mjs +7 -1
  7. package/package.json +9 -4
  8. package/src/contracts/cdp/helpers.ts +167 -0
  9. package/src/contracts/cdp/scripts.ts +33 -0
  10. package/src/contracts/cdp/transactions.ts +1310 -0
  11. package/src/contracts/cdp/types.ts +161 -0
  12. package/src/contracts/cdp-creator/scripts.ts +39 -0
  13. package/src/{types/indigo/cdp-creator.ts → contracts/cdp-creator/types.ts} +6 -4
  14. package/src/contracts/collector/scripts.ts +32 -0
  15. package/src/contracts/collector/transactions.ts +44 -0
  16. package/src/contracts/execute/scripts.ts +48 -0
  17. package/src/contracts/execute/types.ts +57 -0
  18. package/src/contracts/gov/helpers.ts +157 -0
  19. package/src/contracts/gov/scripts.ts +34 -0
  20. package/src/contracts/gov/transactions.ts +1224 -0
  21. package/src/contracts/gov/types-new.ts +115 -0
  22. package/src/contracts/gov/types.ts +89 -0
  23. package/src/{helpers/interest-oracle.ts → contracts/interest-oracle/helpers.ts} +37 -9
  24. package/src/contracts/interest-oracle/scripts.ts +18 -0
  25. package/src/contracts/interest-oracle/transactions.ts +149 -0
  26. package/src/{types/indigo/interest-oracle.ts → contracts/interest-oracle/types.ts} +1 -1
  27. package/src/contracts/lrp/scripts.ts +27 -0
  28. package/src/contracts/{lrp.ts → lrp/transactions.ts} +14 -14
  29. package/src/{types/indigo/lrp.ts → contracts/lrp/types.ts} +2 -2
  30. package/src/{scripts/one-shot-policy.ts → contracts/one-shot/scripts.ts} +1 -1
  31. package/src/contracts/{one-shot.ts → one-shot/transactions.ts} +3 -3
  32. package/src/contracts/poll/helpers.ts +55 -0
  33. package/src/contracts/poll/scripts.ts +72 -0
  34. package/src/contracts/poll/types-poll-manager.ts +38 -0
  35. package/src/contracts/poll/types-poll-shard.ts +38 -0
  36. package/src/contracts/poll/types-poll.ts +88 -0
  37. package/src/{scripts/price-oracle-validator.ts → contracts/price-oracle/scripts.ts} +1 -4
  38. package/src/contracts/price-oracle/transactions.ts +112 -0
  39. package/src/{types/indigo/price-oracle.ts → contracts/price-oracle/types.ts} +16 -4
  40. package/src/{helpers/stability-pool-helpers.ts → contracts/stability-pool/helpers.ts} +110 -6
  41. package/src/contracts/stability-pool/scripts.ts +46 -0
  42. package/src/contracts/stability-pool/transactions.ts +676 -0
  43. package/src/contracts/stability-pool/types-new.ts +208 -0
  44. package/src/contracts/stability-pool/types.ts +42 -0
  45. package/src/contracts/staking/helpers.ts +116 -0
  46. package/src/contracts/staking/scripts.ts +41 -0
  47. package/src/contracts/staking/transactions.ts +268 -0
  48. package/src/contracts/staking/types-new.ts +81 -0
  49. package/src/contracts/staking/types.ts +41 -0
  50. package/src/contracts/treasury/scripts.ts +37 -0
  51. package/src/contracts/treasury/transactions.ts +44 -0
  52. package/src/contracts/treasury/types.ts +55 -0
  53. package/src/contracts/version-registry/scripts.ts +29 -0
  54. package/src/contracts/version-registry/types-new.ts +19 -0
  55. package/src/{types/indigo/version-record.ts → contracts/version-registry/types.ts} +1 -1
  56. package/src/contracts/vesting/helpers.ts +267 -0
  57. package/src/index.ts +39 -33
  58. package/src/types/evolution-schema-options.ts +16 -0
  59. package/src/types/generic.ts +78 -60
  60. package/src/types/on-chain-decimal.ts +22 -0
  61. package/src/types/system-params.ts +22 -11
  62. package/src/utils/bigint-utils.ts +7 -0
  63. package/src/{helpers → utils}/helper-txs.ts +1 -0
  64. package/src/utils/time-helpers.ts +4 -0
  65. package/src/{helpers/helpers.ts → utils/utils.ts} +0 -10
  66. package/src/{helpers → utils}/value-helpers.ts +10 -0
  67. package/src/{scripts → validators}/cdp-creator-validator.ts +4 -50
  68. package/src/{scripts → validators}/cdp-validator.ts +3 -5
  69. package/src/{scripts → validators}/collector-validator.ts +2 -3
  70. package/src/{scripts/version-registry.ts → validators/execute-validator.ts} +3 -11
  71. package/src/{scripts/gov-validator.ts → validators/governance-validator.ts} +3 -40
  72. package/src/{scripts → validators}/interest-oracle-validator.ts +4 -20
  73. package/src/validators/lrp-validator.ts +7 -0
  74. package/src/validators/poll-manager-validator.ts +7 -0
  75. package/src/{scripts → validators}/poll-shard-validator.ts +3 -43
  76. package/src/{scripts → validators}/stability-pool-validator.ts +4 -57
  77. package/src/{scripts → validators}/staking-validator.ts +2 -3
  78. package/src/{scripts → validators}/treasury-validator.ts +2 -3
  79. package/src/{scripts → validators}/version-record-policy.ts +4 -23
  80. package/src/validators/version-registry-validator.ts +7 -0
  81. package/tests/cdp.test.ts +1565 -0
  82. package/tests/datums.test.ts +125 -108
  83. package/tests/endpoints/initialize.ts +240 -338
  84. package/tests/gov.test.ts +1874 -0
  85. package/tests/hash-checks.test.ts +26 -21
  86. package/tests/indigo-test-helpers.ts +1 -55
  87. package/tests/initialize.test.ts +10 -5
  88. package/tests/interest-calculations.test.ts +18 -18
  89. package/tests/interest-oracle.test.ts +20 -18
  90. package/tests/lrp.test.ts +191 -65
  91. package/tests/mock/assets-mock.ts +59 -0
  92. package/tests/queries/cdp-queries.ts +144 -0
  93. package/tests/queries/collector-queries.ts +26 -0
  94. package/tests/queries/execute-queries.ts +46 -0
  95. package/tests/queries/governance-queries.ts +19 -16
  96. package/tests/queries/iasset-queries.ts +46 -23
  97. package/tests/queries/interest-oracle-queries.ts +3 -6
  98. package/tests/queries/lrp-queries.ts +2 -2
  99. package/tests/queries/poll-queries.ts +97 -0
  100. package/tests/queries/price-oracle-queries.ts +5 -22
  101. package/tests/queries/stability-pool-queries.ts +10 -8
  102. package/tests/queries/staking-queries.ts +28 -19
  103. package/tests/queries/treasury-queries.ts +19 -0
  104. package/tests/stability-pool.test.ts +186 -71
  105. package/tests/staking.test.ts +30 -23
  106. package/tests/test-helpers.ts +11 -2
  107. package/tests/utils/asserts.ts +13 -0
  108. package/tests/utils/index.ts +50 -0
  109. package/tsconfig.json +3 -1
  110. package/vitest.config.ts +1 -1
  111. package/.github/workflows/test.yml +0 -44
  112. package/src/contracts/cdp.ts +0 -752
  113. package/src/contracts/collector.ts +0 -98
  114. package/src/contracts/gov.ts +0 -1
  115. package/src/contracts/interest-oracle.ts +0 -149
  116. package/src/contracts/stability-pool.ts +0 -690
  117. package/src/contracts/staking.ts +0 -348
  118. package/src/contracts/treasury.ts +0 -112
  119. package/src/helpers/asset-helpers.ts +0 -62
  120. package/src/helpers/staking-helpers.ts +0 -94
  121. package/src/helpers/time-helpers.ts +0 -4
  122. package/src/scripts/execute-validator.ts +0 -52
  123. package/src/scripts/lrp-validator.ts +0 -40
  124. package/src/scripts/poll-manager-validator.ts +0 -52
  125. package/src/types/indigo/cdp.ts +0 -88
  126. package/src/types/indigo/execute.ts +0 -21
  127. package/src/types/indigo/gov.ts +0 -51
  128. package/src/types/indigo/poll-manager.ts +0 -21
  129. package/src/types/indigo/poll-shard.ts +0 -16
  130. package/src/types/indigo/stability-pool.ts +0 -233
  131. package/src/types/indigo/staking.ts +0 -99
  132. /package/src/{types/one-shot.ts → contracts/one-shot/types.ts} +0 -0
  133. /package/src/{helpers/price-oracle-helpers.ts → contracts/price-oracle/helpers.ts} +0 -0
  134. /package/src/{helpers → utils}/indigo-helpers.ts +0 -0
  135. /package/src/{helpers → utils}/lucid-utils.ts +0 -0
@@ -1,752 +0,0 @@
1
- import {
2
- applyParamsToScript,
3
- Assets,
4
- Constr,
5
- Credential,
6
- credentialToAddress,
7
- Data,
8
- fromText,
9
- LucidEvolution,
10
- OutRef,
11
- slotToUnixTime,
12
- SpendingValidator,
13
- TxBuilder,
14
- UTxO,
15
- validatorToAddress,
16
- validatorToScriptHash,
17
- } from '@lucid-evolution/lucid';
18
- import {
19
- CdpParams,
20
- ScriptReferences,
21
- SystemParams,
22
- } from '../types/system-params';
23
- import { IAssetHelpers, IAssetOutput } from '../helpers/asset-helpers';
24
- import { CollectorContract } from './collector';
25
- import { TreasuryContract } from './treasury';
26
- import { addrDetails, scriptRef } from '../helpers/lucid-utils';
27
- import {
28
- calculateFeeFromPercentage,
29
- getRandomElement,
30
- } from '../helpers/helpers';
31
- import {
32
- CDPContent,
33
- parseCDPDatum,
34
- serialiseCDPDatum,
35
- } from '../types/indigo/cdp';
36
- import { _cdpValidator } from '../scripts/cdp-validator';
37
- import { parsePriceOracleDatum } from '../types/indigo/price-oracle';
38
- import { parseInterestOracleDatum } from '../types/indigo/interest-oracle';
39
- import { castCDPCreatorRedeemer } from '../types/indigo/cdp-creator';
40
- import { parseGovDatum } from '../types/indigo/gov';
41
- import {
42
- calculateAccruedInterest,
43
- calculateUnitaryInterestSinceOracleLastUpdated,
44
- } from '../helpers/interest-oracle';
45
- import { oracleExpirationAwareValidity } from '../helpers/price-oracle-helpers';
46
-
47
- export class CDPContract {
48
- static async openPosition(
49
- asset: string,
50
- collateralAmount: bigint,
51
- mintedAmount: bigint,
52
- params: SystemParams,
53
- lucid: LucidEvolution,
54
- currentSlot: number,
55
- assetRef?: OutRef,
56
- priceOracleRef?: OutRef,
57
- interestOracleRef?: OutRef,
58
- cdpCreatorRef?: OutRef,
59
- collectorRef?: OutRef,
60
- ): Promise<TxBuilder> {
61
- const network = lucid.config().network;
62
- const currentTime = BigInt(slotToUnixTime(network, currentSlot));
63
-
64
- const [pkh, skh] = await addrDetails(lucid);
65
- const assetOut: IAssetOutput = await (assetRef
66
- ? IAssetHelpers.findIAssetByRef(assetRef, lucid)
67
- : IAssetHelpers.findIAssetByName(asset, params, lucid));
68
- if (!assetOut || !assetOut.datum) throw new Error('Unable to find IAsset');
69
- // Fail if delisted asset
70
- if ('Delisted' in assetOut.datum.price)
71
- return Promise.reject(
72
- new Error('Trying to open CDP against delisted asset'),
73
- );
74
-
75
- const oracleAsset = assetOut.datum.price.Oracle.oracleNft.asset;
76
- const oracleOut = priceOracleRef
77
- ? (await lucid.utxosByOutRef([priceOracleRef]))[0]
78
- : await lucid.utxoByUnit(
79
- oracleAsset.currencySymbol + oracleAsset.tokenName,
80
- );
81
- if (!oracleOut.datum)
82
- return Promise.reject(new Error('Price Oracle datum not found'));
83
- const oracleDatum = parsePriceOracleDatum(oracleOut.datum);
84
-
85
- const interestOracleAsset = assetOut.datum.interestOracleNft;
86
- const interestOracleOut = interestOracleRef
87
- ? (await lucid.utxosByOutRef([interestOracleRef]))[0]
88
- : await lucid.utxoByUnit(
89
- interestOracleAsset.currencySymbol + interestOracleAsset.tokenName,
90
- );
91
- if (!interestOracleOut.datum)
92
- return Promise.reject(new Error('Interest Oracle datum not found'));
93
- const interestOracleDatum = parseInterestOracleDatum(
94
- interestOracleOut.datum,
95
- );
96
-
97
- const cdpCreatorOut = getRandomElement(
98
- cdpCreatorRef
99
- ? await lucid.utxosByOutRef([cdpCreatorRef])
100
- : await lucid.utxosAtWithUnit(
101
- credentialToAddress(network, {
102
- type: 'Script',
103
- hash: params.validatorHashes.cdpCreatorHash,
104
- }),
105
- params.cdpCreatorParams.cdpCreatorNft[0].unCurrencySymbol +
106
- fromText(params.cdpCreatorParams.cdpCreatorNft[1].unTokenName),
107
- ),
108
- );
109
-
110
- const cdpCreatorRedeemer = castCDPCreatorRedeemer({
111
- CreateCDP: {
112
- cdpOwner: pkh.hash,
113
- minted: mintedAmount,
114
- collateral: collateralAmount,
115
- currentTime: currentTime,
116
- },
117
- });
118
-
119
- const cdpCreatorScriptRefUtxo = await scriptRef(
120
- params.scriptReferences.cdpCreatorValidatorRef,
121
- lucid,
122
- );
123
-
124
- const cdpAddress = CDPContract.address(params.cdpParams, lucid, skh);
125
- const cdpToken =
126
- params.cdpParams.cdpAuthToken[0].unCurrencySymbol +
127
- fromText(params.cdpParams.cdpAuthToken[1].unTokenName);
128
-
129
- const cdpValue: Assets = {
130
- lovelace: collateralAmount,
131
- };
132
- cdpValue[cdpToken] = 1n;
133
- const newSnapshot =
134
- calculateUnitaryInterestSinceOracleLastUpdated(
135
- currentTime,
136
- interestOracleDatum,
137
- ) + interestOracleDatum.unitaryInterest;
138
- const cdpDatum: CDPContent = {
139
- cdpOwner: pkh.hash,
140
- iasset: fromText(asset),
141
- mintedAmt: mintedAmount,
142
- cdpFees: {
143
- ActiveCDPInterestTracking: {
144
- lastSettled: currentTime,
145
- unitaryInterestSnapshot: newSnapshot,
146
- },
147
- },
148
- };
149
-
150
- const assetToken =
151
- params.cdpParams.cdpAssetSymbol.unCurrencySymbol + fromText(asset);
152
- const cdpTokenMintValue: Assets = {};
153
- cdpTokenMintValue[cdpToken] = 1n;
154
- const iassetTokenMintValue: Assets = {};
155
- iassetTokenMintValue[assetToken] = BigInt(mintedAmount);
156
-
157
- const cdpAuthTokenScriptRefUtxo = await CDPContract.cdpAuthTokenRef(
158
- params.scriptReferences,
159
- lucid,
160
- );
161
- const iAssetTokenScriptRefUtxo = await CDPContract.assetTokenRef(
162
- params.scriptReferences,
163
- lucid,
164
- );
165
-
166
- const debtMintingFee = calculateFeeFromPercentage(
167
- BigInt(assetOut.datum.debtMintingFeePercentage.getOnChainInt),
168
- (mintedAmount * oracleDatum.price.getOnChainInt) / 1_000_000n,
169
- );
170
-
171
- const txValidity = oracleExpirationAwareValidity(
172
- currentSlot,
173
- Number(params.cdpCreatorParams.biasTime),
174
- Number(oracleDatum.expiration),
175
- network,
176
- );
177
-
178
- const tx = lucid
179
- .newTx()
180
- .collectFrom([cdpCreatorOut], Data.to(cdpCreatorRedeemer))
181
- .readFrom([cdpCreatorScriptRefUtxo])
182
- .pay.ToContract(
183
- cdpAddress,
184
- { kind: 'inline', value: serialiseCDPDatum(cdpDatum) },
185
- cdpValue,
186
- )
187
- .pay.ToContract(
188
- cdpCreatorOut.address,
189
- { kind: 'inline', value: cdpCreatorOut.datum },
190
- cdpCreatorOut.assets,
191
- )
192
- .readFrom([oracleOut, interestOracleOut, assetOut.utxo])
193
- .mintAssets(cdpTokenMintValue, Data.to(new Constr(0, [])))
194
- .readFrom([cdpAuthTokenScriptRefUtxo])
195
- .mintAssets(iassetTokenMintValue, Data.to(new Constr(0, [])))
196
- .readFrom([iAssetTokenScriptRefUtxo])
197
- .addSignerKey(pkh.hash)
198
- .validFrom(txValidity.validFrom)
199
- .validTo(txValidity.validTo);
200
-
201
- if (debtMintingFee > 0) {
202
- await CollectorContract.feeTx(
203
- debtMintingFee,
204
- lucid,
205
- params,
206
- tx,
207
- collectorRef,
208
- );
209
- }
210
- return tx;
211
- }
212
-
213
- static async deposit(
214
- cdpRef: OutRef,
215
- amount: bigint,
216
- params: SystemParams,
217
- lucid: LucidEvolution,
218
- currentSlot: number,
219
- assetRef?: OutRef,
220
- priceOracleRef?: OutRef,
221
- interestOracleRef?: OutRef,
222
- collectorRef?: OutRef,
223
- govRef?: OutRef,
224
- treasuryRef?: OutRef,
225
- ): Promise<TxBuilder> {
226
- return CDPContract.adjust(
227
- cdpRef,
228
- amount,
229
- 0n,
230
- params,
231
- lucid,
232
- currentSlot,
233
- assetRef,
234
- priceOracleRef,
235
- interestOracleRef,
236
- collectorRef,
237
- govRef,
238
- treasuryRef,
239
- );
240
- }
241
-
242
- static async withdraw(
243
- cdpRef: OutRef,
244
- amount: bigint,
245
- params: SystemParams,
246
- lucid: LucidEvolution,
247
- currentSlot: number,
248
- assetRef?: OutRef,
249
- priceOracleRef?: OutRef,
250
- interestOracleRef?: OutRef,
251
- collectorRef?: OutRef,
252
- govRef?: OutRef,
253
- treasuryRef?: OutRef,
254
- ): Promise<TxBuilder> {
255
- return CDPContract.adjust(
256
- cdpRef,
257
- -amount,
258
- 0n,
259
- params,
260
- lucid,
261
- currentSlot,
262
- assetRef,
263
- priceOracleRef,
264
- interestOracleRef,
265
- collectorRef,
266
- govRef,
267
- treasuryRef,
268
- );
269
- }
270
-
271
- static async mint(
272
- cdpRef: OutRef,
273
- amount: bigint,
274
- params: SystemParams,
275
- lucid: LucidEvolution,
276
- currentSlot: number,
277
- assetRef?: OutRef,
278
- priceOracleRef?: OutRef,
279
- interestOracleRef?: OutRef,
280
- collectorRef?: OutRef,
281
- govRef?: OutRef,
282
- treasuryRef?: OutRef,
283
- ): Promise<TxBuilder> {
284
- return CDPContract.adjust(
285
- cdpRef,
286
- 0n,
287
- amount,
288
- params,
289
- lucid,
290
- currentSlot,
291
- assetRef,
292
- priceOracleRef,
293
- interestOracleRef,
294
- collectorRef,
295
- govRef,
296
- treasuryRef,
297
- );
298
- }
299
-
300
- static async burn(
301
- cdpRef: OutRef,
302
- amount: bigint,
303
- params: SystemParams,
304
- lucid: LucidEvolution,
305
- currentSlot: number,
306
- assetRef?: OutRef,
307
- priceOracleRef?: OutRef,
308
- interestOracleRef?: OutRef,
309
- collectorRef?: OutRef,
310
- govRef?: OutRef,
311
- treasuryRef?: OutRef,
312
- ): Promise<TxBuilder> {
313
- return CDPContract.adjust(
314
- cdpRef,
315
- 0n,
316
- -amount,
317
- params,
318
- lucid,
319
- currentSlot,
320
- assetRef,
321
- priceOracleRef,
322
- interestOracleRef,
323
- collectorRef,
324
- govRef,
325
- treasuryRef,
326
- );
327
- }
328
-
329
- static async adjust(
330
- cdpRef: OutRef,
331
- collateralAmount: bigint,
332
- mintAmount: bigint,
333
- params: SystemParams,
334
- lucid: LucidEvolution,
335
- currentSlot: number,
336
- assetRef?: OutRef,
337
- priceOracleRef?: OutRef,
338
- interestOracleRef?: OutRef,
339
- collectorRef?: OutRef,
340
- govRef?: OutRef,
341
- treasuryRef?: OutRef,
342
- ): Promise<TxBuilder> {
343
- const network = lucid.config().network;
344
- // Find Pkh, Skh
345
- const currentTime = BigInt(slotToUnixTime(network, currentSlot));
346
-
347
- // Find Outputs: iAsset Output, CDP Output, Gov Output
348
- const cdp = (await lucid.utxosByOutRef([cdpRef]))[0];
349
- if (!cdp.datum) throw new Error('Unable to find CDP Datum');
350
- const cdpDatum = parseCDPDatum(cdp.datum);
351
- console.log('cdpDatum.iasset', cdpDatum.iasset);
352
- const iAsset = await (assetRef
353
- ? IAssetHelpers.findIAssetByRef(assetRef, lucid)
354
- : IAssetHelpers.findIAssetByName(cdpDatum.iasset, params, lucid));
355
- console.log('iasset output', iAsset.utxo.txHash, iAsset.utxo.outputIndex);
356
-
357
- const gov = govRef
358
- ? (await lucid.utxosByOutRef([govRef]))[0]
359
- : await lucid.utxoByUnit(
360
- params.govParams.govNFT[0].unCurrencySymbol +
361
- fromText(params.govParams.govNFT[1].unTokenName),
362
- );
363
- if (!gov.datum) throw new Error('Unable to find Gov Datum');
364
-
365
- console.log('gov output', gov.txHash, gov.outputIndex);
366
- const govData = parseGovDatum(gov.datum);
367
- const cdpScriptRefUtxo = await CDPContract.scriptRef(
368
- params.scriptReferences,
369
- lucid,
370
- );
371
- const cdpAssets = Object.assign({}, cdp.assets);
372
- cdpAssets['lovelace'] = cdp.assets['lovelace'] + collateralAmount;
373
-
374
- const interestOracleAsset = iAsset.datum.interestOracleNft;
375
- console.log('interestOracleAsset', interestOracleAsset.currencySymbol + interestOracleAsset.tokenName);
376
- const interestOracleOut = interestOracleRef
377
- ? (await lucid.utxosByOutRef([interestOracleRef]))[0]
378
- : await lucid.utxoByUnit(
379
- interestOracleAsset.currencySymbol + interestOracleAsset.tokenName,
380
- );
381
- if (!interestOracleOut.datum)
382
- return Promise.reject(new Error('Interest Oracle datum not found'));
383
- const interestOracleDatum = parseInterestOracleDatum(
384
- interestOracleOut.datum,
385
- );
386
-
387
- const tx = lucid
388
- .newTx()
389
- .collectFrom(
390
- [cdp],
391
- Data.to(new Constr(0, [currentTime, mintAmount, collateralAmount])),
392
- )
393
- .readFrom([iAsset.utxo, gov, cdpScriptRefUtxo])
394
- .addSignerKey(cdpDatum.cdpOwner);
395
- if (!cdp.datum) throw new Error('Unable to find CDP Datum');
396
- const cdpD = parseCDPDatum(cdp.datum);
397
-
398
- if (!('ActiveCDPInterestTracking' in cdpD.cdpFees))
399
- throw new Error('Invalid CDP Fees');
400
-
401
- const newSnapshot =
402
- calculateUnitaryInterestSinceOracleLastUpdated(
403
- currentTime,
404
- interestOracleDatum,
405
- ) + interestOracleDatum.unitaryInterest;
406
-
407
- const cdpD_: CDPContent = {
408
- ...cdpD,
409
- mintedAmt: cdpD.mintedAmt + mintAmount,
410
- cdpFees: {
411
- ActiveCDPInterestTracking: {
412
- lastSettled: currentTime,
413
- unitaryInterestSnapshot: newSnapshot,
414
- },
415
- },
416
- };
417
-
418
- tx.pay.ToContract(
419
- cdp.address,
420
- {
421
- kind: 'inline',
422
- value: serialiseCDPDatum(cdpD_),
423
- },
424
- cdpAssets,
425
- );
426
-
427
- // Find Oracle Ref Input
428
- const oracleAsset = iAsset.datum.price;
429
- if (!('Oracle' in oracleAsset)) throw new Error('Invalid oracle asset');
430
- const oracleRefInput = priceOracleRef
431
- ? (await lucid.utxosByOutRef([priceOracleRef]))[0]
432
- : await lucid.utxoByUnit(
433
- oracleAsset.Oracle.oracleNft.asset.currencySymbol + oracleAsset.Oracle.oracleNft.asset.tokenName,
434
- );
435
-
436
- console.log('oracleRefInput', oracleRefInput.txHash, oracleRefInput.outputIndex);
437
- // Fail if delisted asset
438
- if (!oracleRefInput.datum)
439
- return Promise.reject(new Error('Invalid oracle input'));
440
- const od = parsePriceOracleDatum(oracleRefInput.datum);
441
- if (!od) return Promise.reject(new Error('Invalid oracle input'));
442
-
443
- const txValidity = oracleExpirationAwareValidity(
444
- currentSlot,
445
- Number(params.cdpCreatorParams.biasTime),
446
- Number(od.expiration),
447
- network,
448
- );
449
- tx.readFrom([oracleRefInput])
450
- .validFrom(txValidity.validFrom)
451
- .validTo(txValidity.validTo);
452
-
453
- let fee = 0n;
454
- if (collateralAmount < 0) {
455
- fee += calculateFeeFromPercentage(
456
- govData.protocolParams.collateralFeePercentage.getOnChainInt,
457
- collateralAmount,
458
- );
459
- }
460
-
461
- if (mintAmount > 0) {
462
- fee += calculateFeeFromPercentage(
463
- iAsset.datum.debtMintingFeePercentage.getOnChainInt,
464
- (mintAmount * od.price.getOnChainInt) / 1_000_000n,
465
- );
466
- }
467
-
468
- // Interest payment
469
-
470
- const interestPaymentAsset = calculateAccruedInterest(
471
- currentTime,
472
- cdpD.cdpFees.ActiveCDPInterestTracking.unitaryInterestSnapshot,
473
- cdpD.mintedAmt,
474
- cdpD.cdpFees.ActiveCDPInterestTracking.lastSettled,
475
- interestOracleDatum,
476
- );
477
- const interestPayment =
478
- (interestPaymentAsset * od.price.getOnChainInt) / 1_000_000n;
479
- const interestCollectorPayment = calculateFeeFromPercentage(
480
- iAsset.datum.interestCollectorPortionPercentage.getOnChainInt,
481
- interestPayment,
482
- );
483
- const interestTreasuryPayment = interestPayment - interestCollectorPayment;
484
-
485
- if (interestTreasuryPayment > 0) {
486
- await TreasuryContract.feeTx(
487
- interestTreasuryPayment,
488
- lucid,
489
- params,
490
- tx,
491
- treasuryRef,
492
- );
493
- }
494
-
495
- fee += interestCollectorPayment;
496
- tx.readFrom([interestOracleOut]);
497
-
498
- if (mintAmount !== 0n) {
499
- const iAssetTokenScriptRefUtxo = await CDPContract.assetTokenRef(
500
- params.scriptReferences,
501
- lucid,
502
- );
503
- const iassetToken =
504
- params.cdpParams.cdpAssetSymbol.unCurrencySymbol + cdpD.iasset;
505
- const mintValue = {} as Assets;
506
- mintValue[iassetToken] = mintAmount;
507
-
508
- tx.readFrom([iAssetTokenScriptRefUtxo]).mintAssets(
509
- mintValue,
510
- Data.to(new Constr(0, [])),
511
- );
512
- }
513
-
514
- if (fee > 0n) {
515
- await CollectorContract.feeTx(fee, lucid, params, tx, collectorRef);
516
- }
517
-
518
- return tx;
519
- }
520
-
521
- static async close(
522
- cdpRef: OutRef,
523
- params: SystemParams,
524
- lucid: LucidEvolution,
525
- currentSlot: number,
526
- assetRef?: OutRef,
527
- priceOracleRef?: OutRef,
528
- interestOracleRef?: OutRef,
529
- collectorRef?: OutRef,
530
- govRef?: OutRef,
531
- treasuryRef?: OutRef,
532
- ): Promise<TxBuilder> {
533
- const network = lucid.config().network;
534
- // Find Pkh, Skh
535
- const currentTime = BigInt(slotToUnixTime(network, currentSlot));
536
-
537
- // Find Outputs: iAsset Output, CDP Output, Gov Output
538
- const cdp = (await lucid.utxosByOutRef([cdpRef]))[0];
539
- if (!cdp.datum) throw new Error('Unable to find CDP Datum');
540
- const cdpDatum = parseCDPDatum(cdp.datum);
541
- const iAsset = await (assetRef
542
- ? IAssetHelpers.findIAssetByRef(assetRef, lucid)
543
- : IAssetHelpers.findIAssetByName(cdpDatum.iasset, params, lucid));
544
-
545
- const gov = govRef
546
- ? (await lucid.utxosByOutRef([govRef]))[0]
547
- : await lucid.utxoByUnit(
548
- params.govParams.govNFT[0].unCurrencySymbol +
549
- fromText(params.govParams.govNFT[1].unTokenName),
550
- );
551
-
552
- if (!gov.datum) throw new Error('Unable to find Gov Datum');
553
- const cdpScriptRefUtxo = await CDPContract.scriptRef(
554
- params.scriptReferences,
555
- lucid,
556
- );
557
-
558
- const interestOracleAsset = iAsset.datum.interestOracleNft;
559
- console.log('interestOracleAsset', interestOracleAsset.currencySymbol + interestOracleAsset.tokenName);
560
- const interestOracleOut = interestOracleRef
561
- ? (await lucid.utxosByOutRef([interestOracleRef]))[0]
562
- : await lucid.utxoByUnit(
563
- interestOracleAsset.currencySymbol + interestOracleAsset.tokenName,
564
- );
565
- if (!interestOracleOut.datum)
566
- return Promise.reject(new Error('Interest Oracle datum not found'));
567
- const interestOracleDatum = parseInterestOracleDatum(
568
- interestOracleOut.datum,
569
- );
570
-
571
- const tx = lucid
572
- .newTx()
573
- .collectFrom([cdp], Data.to(new Constr(1, [currentTime])))
574
- .readFrom([iAsset.utxo, gov, cdpScriptRefUtxo])
575
- .addSignerKey(cdpDatum.cdpOwner);
576
- if (!cdp.datum) throw new Error('Unable to find CDP Datum');
577
- const cdpD = parseCDPDatum(cdp.datum);
578
- if (!('ActiveCDPInterestTracking' in cdpD.cdpFees))
579
- throw new Error('Invalid CDP Fees');
580
-
581
- // Find Oracle Ref Input
582
- if (!('Oracle' in iAsset.datum.price))
583
- throw new Error('iAsset is delisted');
584
- const oracleAsset = iAsset.datum.price.Oracle.oracleNft.asset;
585
- const oracleRefInput = priceOracleRef
586
- ? (await lucid.utxosByOutRef([priceOracleRef]))[0]
587
- : await lucid.utxoByUnit(
588
- oracleAsset.currencySymbol + oracleAsset.tokenName,
589
- );
590
-
591
- console.log('oracleRefInput', oracleRefInput.txHash, oracleRefInput.outputIndex);
592
-
593
- // Fail if delisted asset
594
- if (!oracleRefInput.datum)
595
- return Promise.reject(new Error('Invalid oracle input'));
596
- const od = parsePriceOracleDatum(oracleRefInput.datum);
597
-
598
- const txValidity = oracleExpirationAwareValidity(
599
- currentSlot,
600
- Number(params.cdpCreatorParams.biasTime),
601
- Number(od.expiration),
602
- network,
603
- );
604
- tx.readFrom([oracleRefInput])
605
- .validFrom(txValidity.validFrom)
606
- .validTo(txValidity.validTo);
607
-
608
- let fee = 0n;
609
-
610
- // Interest payment
611
- const interestPaymentAsset = calculateAccruedInterest(
612
- currentTime,
613
- cdpD.cdpFees.ActiveCDPInterestTracking.unitaryInterestSnapshot,
614
- cdpD.mintedAmt,
615
- cdpD.cdpFees.ActiveCDPInterestTracking.lastSettled,
616
- interestOracleDatum,
617
- );
618
- const interestPayment =
619
- (interestPaymentAsset * od.price.getOnChainInt) / 1_000_000n;
620
- const interestCollectorPayment = calculateFeeFromPercentage(
621
- iAsset.datum.interestCollectorPortionPercentage.getOnChainInt,
622
- interestPayment,
623
- );
624
- const interestTreasuryPayment = interestPayment - interestCollectorPayment;
625
-
626
- if (interestTreasuryPayment > 0) {
627
- await TreasuryContract.feeTx(
628
- interestTreasuryPayment,
629
- lucid,
630
- params,
631
- tx,
632
- treasuryRef,
633
- );
634
- }
635
-
636
- fee += interestCollectorPayment;
637
- tx.readFrom([interestOracleOut]);
638
-
639
- const iAssetTokenScriptRefUtxo = await CDPContract.assetTokenRef(
640
- params.scriptReferences,
641
- lucid,
642
- );
643
- const iassetToken =
644
- params.cdpParams.cdpAssetSymbol.unCurrencySymbol + cdpD.iasset;
645
- const assetBurnValue = {} as Assets;
646
- assetBurnValue[iassetToken] = -BigInt(cdpD.mintedAmt);
647
- const cdpTokenBurnValue = {} as Assets;
648
- cdpTokenBurnValue[
649
- params.cdpParams.cdpAuthToken[0].unCurrencySymbol +
650
- fromText(params.cdpParams.cdpAuthToken[1].unTokenName)
651
- ] = -1n;
652
- const cdpAuthTokenScriptRefUtxo = await CDPContract.cdpAuthTokenRef(
653
- params.scriptReferences,
654
- lucid,
655
- );
656
- tx.readFrom([iAssetTokenScriptRefUtxo])
657
- .mintAssets(assetBurnValue, Data.to(new Constr(0, [])))
658
- .readFrom([cdpAuthTokenScriptRefUtxo])
659
- .mintAssets(cdpTokenBurnValue, Data.to(new Constr(0, [])));
660
-
661
- if (fee > 0n) {
662
- await CollectorContract.feeTx(fee, lucid, params, tx, collectorRef);
663
- }
664
-
665
- return tx;
666
- }
667
-
668
- static validator(params: CdpParams): SpendingValidator {
669
- return {
670
- type: _cdpValidator.type,
671
- script: applyParamsToScript(_cdpValidator.cborHex, [
672
- new Constr(0, [
673
- new Constr(0, [
674
- params.cdpAuthToken[0].unCurrencySymbol,
675
- fromText(params.cdpAuthToken[1].unTokenName),
676
- ]),
677
- params.cdpAssetSymbol.unCurrencySymbol,
678
- new Constr(0, [
679
- params.iAssetAuthToken[0].unCurrencySymbol,
680
- fromText(params.iAssetAuthToken[1].unTokenName),
681
- ]),
682
- new Constr(0, [
683
- params.stabilityPoolAuthToken[0].unCurrencySymbol,
684
- fromText(params.stabilityPoolAuthToken[1].unTokenName),
685
- ]),
686
- new Constr(0, [
687
- params.versionRecordToken[0].unCurrencySymbol,
688
- fromText(params.versionRecordToken[1].unTokenName),
689
- ]),
690
- new Constr(0, [
691
- params.upgradeToken[0].unCurrencySymbol,
692
- fromText(params.upgradeToken[1].unTokenName),
693
- ]),
694
- params.collectorValHash,
695
- params.spValHash,
696
- new Constr(0, [
697
- params.govNFT[0].unCurrencySymbol,
698
- fromText(params.govNFT[1].unTokenName),
699
- ]),
700
- BigInt(params.minCollateralInLovelace),
701
- BigInt(params.partialRedemptionExtraFeeLovelace),
702
- BigInt(params.biasTime),
703
- params.treasuryValHash,
704
- ]),
705
- ]),
706
- };
707
- }
708
-
709
- static validatorHash(params: CdpParams): string {
710
- return validatorToScriptHash(CDPContract.validator(params));
711
- }
712
-
713
- static address(
714
- cdpParams: CdpParams,
715
- lucid: LucidEvolution,
716
- skh?: Credential,
717
- ) {
718
- const network = lucid.config().network;
719
- if (!network) {
720
- throw new Error('Network configuration is undefined');
721
- }
722
- return validatorToAddress(network, CDPContract.validator(cdpParams), skh);
723
- }
724
-
725
- static scriptRef(
726
- params: ScriptReferences,
727
- lucid: LucidEvolution,
728
- ): Promise<UTxO> {
729
- return scriptRef(params.cdpValidatorRef, lucid);
730
- }
731
-
732
- static cdpAuthTokenRef(
733
- params: ScriptReferences,
734
- lucid: LucidEvolution,
735
- ): Promise<UTxO> {
736
- return scriptRef(params.authTokenPolicies.cdpAuthTokenRef, lucid);
737
- }
738
-
739
- static assetTokenRef(
740
- params: ScriptReferences,
741
- lucid: LucidEvolution,
742
- ): Promise<UTxO> {
743
- return scriptRef(params.iAssetTokenPolicyRef, lucid);
744
- }
745
-
746
- static assetAuthTokenRef(
747
- params: ScriptReferences,
748
- lucid: LucidEvolution,
749
- ): Promise<UTxO> {
750
- return scriptRef(params.authTokenPolicies.iAssetTokenRef, lucid);
751
- }
752
- }