@gearbox-protocol/sdk 16.6.0-next.3 → 16.6.0-next.5

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.
@@ -79,11 +79,7 @@ const iFaucetAbi = [
79
79
  internalType: "uint256"
80
80
  }]
81
81
  }],
82
- outputs: [{
83
- name: "",
84
- type: "bool",
85
- internalType: "bool"
86
- }],
82
+ outputs: [],
87
83
  stateMutability: "nonpayable"
88
84
  },
89
85
  {
@@ -98,11 +94,7 @@ const iFaucetAbi = [
98
94
  type: "uint256",
99
95
  internalType: "uint256"
100
96
  }],
101
- outputs: [{
102
- name: "",
103
- type: "bool",
104
- internalType: "bool"
105
- }],
97
+ outputs: [],
106
98
  stateMutability: "nonpayable"
107
99
  },
108
100
  {
@@ -113,11 +105,7 @@ const iFaucetAbi = [
113
105
  type: "address",
114
106
  internalType: "address"
115
107
  }],
116
- outputs: [{
117
- name: "",
118
- type: "bool",
119
- internalType: "bool"
120
- }],
108
+ outputs: [],
121
109
  stateMutability: "nonpayable"
122
110
  },
123
111
  {
@@ -189,6 +177,17 @@ const iFaucetAbi = [
189
177
  }],
190
178
  stateMutability: "view"
191
179
  },
180
+ {
181
+ type: "function",
182
+ name: "owner",
183
+ inputs: [],
184
+ outputs: [{
185
+ name: "",
186
+ type: "address",
187
+ internalType: "address"
188
+ }],
189
+ stateMutability: "view"
190
+ },
192
191
  {
193
192
  type: "function",
194
193
  name: "prices",
@@ -57,6 +57,7 @@ exports.getDrpcUrl = require_dev_providers.getDrpcUrl;
57
57
  exports.getErpcKey = require_dev_providers.getErpcKey;
58
58
  exports.getPublicCreate2Address = require_dev_create2.getPublicCreate2Address;
59
59
  exports.getRpcProviderUrl = require_dev_providers.getRpcProviderUrl;
60
+ exports.getSecuritizeAdmin = require_dev_kycUtils.getSecuritizeAdmin;
60
61
  exports.getThirdWebUrl = require_dev_providers.getThirdWebUrl;
61
62
  exports.greenlistMidasGateway = require_dev_kycUtils.greenlistMidasGateway;
62
63
  exports.httpTransportOptionsSchema = require_dev_transports.httpTransportOptionsSchema;
@@ -8,19 +8,49 @@ const require_abi_rwa_iDSToken = require("../abi/rwa/iDSToken.js");
8
8
  const require_dev_midasUtils = require("./midasUtils.js");
9
9
  const require_dev_withdrawalAbi = require("./withdrawalAbi.js");
10
10
  let viem = require("viem");
11
- let viem_accounts = require("viem/accounts");
12
11
  //#region src/dev/kycUtils.ts
12
+ const iMockDSTokenAdminAbi = (0, viem.parseAbi)(["function admin() view returns (address)"]);
13
13
  /**
14
- * Resolves the account that performs the DS registry writes: either the admin
15
- * private key, or the admin address impersonated on the fork
14
+ * DS trust-service master of `token`: Ownable owner at storage slot 0 of the
15
+ * trust service, same as periphery-v3 SecuritizeAttachHelper. MockDSToken
16
+ * returns itself as the trust service, so `admin()` is used instead.
17
+ */
18
+ async function getSecuritizeAdmin(anvil, token, logger) {
19
+ const trustServiceId = await anvil.readContract({
20
+ address: token,
21
+ abi: require_abi_rwa_iDSToken.iDSTokenAbi,
22
+ functionName: "TRUST_SERVICE"
23
+ });
24
+ const trustService = await anvil.readContract({
25
+ address: token,
26
+ abi: require_abi_rwa_iDSToken.iDSTokenAbi,
27
+ functionName: "getDSService",
28
+ args: [trustServiceId]
29
+ });
30
+ if ((0, viem.isAddressEqual)(trustService, token)) {
31
+ const admin = await anvil.readContract({
32
+ address: token,
33
+ abi: iMockDSTokenAdminAbi,
34
+ functionName: "admin"
35
+ });
36
+ logger?.debug(`securitize: found admin ${admin} for ${token} (token.admin)`);
37
+ return admin;
38
+ }
39
+ const word = await anvil.getStorageAt({
40
+ address: trustService,
41
+ slot: (0, viem.toHex)(0, { size: 32 })
42
+ });
43
+ if (!word) throw new Error(`securitize: empty trust-service owner slot on ${trustService}`);
44
+ const admin = (0, viem.getAddress)((0, viem.slice)(word, 12));
45
+ logger?.debug(`securitize: found admin ${admin} for ${token} (trust service ${trustService})`);
46
+ return admin;
47
+ }
48
+ /**
49
+ * Impersonates the DS trust-service admin of `token` on the fork
16
50
  */
17
51
  async function useSecuritizeAdmin(props) {
18
- const { anvil, adminPrivateKey, admin, logger } = props;
19
- if (adminPrivateKey) return {
20
- account: (0, viem_accounts.privateKeyToAccount)(adminPrivateKey),
21
- release: async () => {}
22
- };
23
- if (!admin) throw new Error("securitize: either adminPrivateKey or admin address is required");
52
+ const { anvil, token, logger } = props;
53
+ const admin = await getSecuritizeAdmin(anvil, token, logger);
24
54
  await anvil.impersonateAccount({ address: admin });
25
55
  await anvil.setBalance({
26
56
  address: admin,
@@ -295,17 +325,15 @@ async function findMidasGateway(props) {
295
325
  * result instead of aborting the whole run.
296
326
  */
297
327
  async function registerRWAInvestor(props) {
298
- const { anvil, sdk, investor, adminPrivateKey, securitizeAdmin, midasAdmin = "0xd4195CF4df289a4748C1A7B6dDBE770e27bA1227", logger } = props;
328
+ const { anvil, sdk, investor, midasAdmin = "0xd4195CF4df289a4748C1A7B6dDBE770e27bA1227", logger } = props;
299
329
  const securitizeTokens = [];
300
330
  const midasGateways = [];
301
331
  const failed = [];
302
332
  const dsTokens = new require_onchain_utils_AddressSet.AddressSet(sdk.rwa.factories.flatMap((factory) => factory.getTokens()));
303
- if (adminPrivateKey || securitizeAdmin) for (const token of dsTokens) try {
333
+ for (const token of dsTokens) try {
304
334
  await registerSecuritizeInvestor({
305
335
  anvil,
306
336
  investor,
307
- adminPrivateKey,
308
- admin: securitizeAdmin,
309
337
  token,
310
338
  logger
311
339
  });
@@ -318,7 +346,6 @@ async function registerRWAInvestor(props) {
318
346
  error: e
319
347
  });
320
348
  }
321
- else if (dsTokens.size > 0) logger?.warn(`securitize: no registry admin, skipping ${dsTokens.size} DSToken(s)`);
322
349
  const gateways = await require_dev_midasUtils.collectMidasGateways(sdk);
323
350
  for (const gateway of gateways) try {
324
351
  await greenlistMidasGateway({
@@ -345,6 +372,7 @@ async function registerRWAInvestor(props) {
345
372
  };
346
373
  }
347
374
  //#endregion
375
+ exports.getSecuritizeAdmin = getSecuritizeAdmin;
348
376
  exports.greenlistMidasGateway = greenlistMidasGateway;
349
377
  exports.registerMidasInvestor = registerMidasInvestor;
350
378
  exports.registerRWAInvestor = registerRWAInvestor;
@@ -5,7 +5,6 @@ require("../onchain/index.js");
5
5
  const require_abi_rwa_iDSToken = require("../abi/rwa/iDSToken.js");
6
6
  const require_dev_kycUtils = require("./kycUtils.js");
7
7
  let viem = require("viem");
8
- let viem_accounts = require("viem/accounts");
9
8
  //#region src/dev/securitizeUtils.ts
10
9
  /**
11
10
  * `COMPLIANCE_CONFIGURATION_SERVICE` id in the DS protocol service registry
@@ -111,7 +110,7 @@ async function issueDSTokens(props) {
111
110
  * Tokens without one (e.g. MockDSToken) are skipped
112
111
  */
113
112
  async function getComplianceConfigurationServices({ anvil, tokens, logger }) {
114
- const services = new require_onchain_utils_AddressSet.AddressSet();
113
+ const services = /* @__PURE__ */ new Map();
115
114
  for (const token of new require_onchain_utils_AddressSet.AddressSet(tokens)) try {
116
115
  const service = await anvil.readContract({
117
116
  address: token,
@@ -123,11 +122,16 @@ async function getComplianceConfigurationServices({ anvil, tokens, logger }) {
123
122
  logger?.debug(`${token} has no compliance configuration service`);
124
123
  continue;
125
124
  }
126
- services.add(service);
125
+ const checksummed = (0, viem.getAddress)(service);
126
+ if (services.has(checksummed)) continue;
127
+ services.set(checksummed, await require_dev_kycUtils.getSecuritizeAdmin(anvil, token, logger));
127
128
  } catch (e) {
128
129
  logger?.debug(`Failed to get compliance configuration service of ${token}: ${e}`);
129
130
  }
130
- return [...services];
131
+ return [...services].map(([service, admin]) => ({
132
+ service,
133
+ admin
134
+ }));
131
135
  }
132
136
  /**
133
137
  * Sets `disallowBackDating` to false on compliance configuration services of
@@ -135,18 +139,17 @@ async function getComplianceConfigurationServices({ anvil, tokens, logger }) {
135
139
  * honoured: DS protocol silently replaces it with `block.timestamp` otherwise,
136
140
  * and freshly minted tokens stay under lock-up.
137
141
  *
138
- * Must be signed by a DS admin with sufficient trust (same key as
139
- * `issueTokens` / registerInvestor); Ownable `owner()` alone is not enough.
142
+ * Impersonates the DS trust-service admin of each token. Ownable `owner()` of
143
+ * the compliance configuration service alone is not enough.
140
144
  *
141
145
  * The flag is only read while tokens are issued, so restoring it does not
142
146
  * re-lock tokens minted in the meantime.
143
147
  */
144
148
  async function enableDSTokenBackDating(props) {
145
- const { anvil, adminPrivateKey, logger } = props;
146
- const account = (0, viem_accounts.privateKeyToAccount)(adminPrivateKey);
149
+ const { anvil, logger } = props;
147
150
  const services = await getComplianceConfigurationServices(props);
148
151
  let toRestore = [];
149
- for (const service of services) {
152
+ for (const { service, admin } of services) {
150
153
  let disallowBackDating;
151
154
  try {
152
155
  disallowBackDating = await anvil.readContract({
@@ -163,32 +166,53 @@ async function enableDSTokenBackDating(props) {
163
166
  continue;
164
167
  }
165
168
  logger?.info(`Allowing back-dating on ${service}`);
166
- await anvil.writeContractSync({
167
- account,
168
- chain: anvil.chain,
169
- address: service,
170
- abi: iDSComplianceConfigurationServiceAbi,
171
- functionName: "setDisallowBackDating",
172
- args: [false],
173
- throwOnReceiptRevert: true
169
+ await anvil.impersonateAccount({ address: admin });
170
+ try {
171
+ await anvil.setBalance({
172
+ address: admin,
173
+ value: (0, viem.parseEther)("100")
174
+ });
175
+ await anvil.writeContractSync({
176
+ account: admin,
177
+ chain: anvil.chain,
178
+ address: service,
179
+ abi: iDSComplianceConfigurationServiceAbi,
180
+ functionName: "setDisallowBackDating",
181
+ args: [false],
182
+ throwOnReceiptRevert: true
183
+ });
184
+ } finally {
185
+ await anvil.stopImpersonatingAccount({ address: admin });
186
+ }
187
+ toRestore.push({
188
+ service,
189
+ admin
174
190
  });
175
- toRestore.push(service);
176
191
  }
177
192
  return async () => {
178
193
  const services = toRestore;
179
194
  toRestore = [];
180
- for (const service of services) {
195
+ for (const { service, admin } of services) {
181
196
  logger?.info(`Disallowing back-dating on ${service}`);
182
197
  try {
183
- await anvil.writeContractSync({
184
- account,
185
- chain: anvil.chain,
186
- address: service,
187
- abi: iDSComplianceConfigurationServiceAbi,
188
- functionName: "setDisallowBackDating",
189
- args: [true],
190
- throwOnReceiptRevert: true
191
- });
198
+ await anvil.impersonateAccount({ address: admin });
199
+ try {
200
+ await anvil.setBalance({
201
+ address: admin,
202
+ value: (0, viem.parseEther)("100")
203
+ });
204
+ await anvil.writeContractSync({
205
+ account: admin,
206
+ chain: anvil.chain,
207
+ address: service,
208
+ abi: iDSComplianceConfigurationServiceAbi,
209
+ functionName: "setDisallowBackDating",
210
+ args: [true],
211
+ throwOnReceiptRevert: true
212
+ });
213
+ } finally {
214
+ await anvil.stopImpersonatingAccount({ address: admin });
215
+ }
192
216
  } catch (e) {
193
217
  logger?.warn(`Failed to restore disallowBackDating on ${service}: ${e}`);
194
218
  }
@@ -196,8 +220,7 @@ async function enableDSTokenBackDating(props) {
196
220
  };
197
221
  }
198
222
  async function claimDSToken(props) {
199
- const { anvil, investor, adminPrivateKey, token, marketConfigurators, rwaFactories, usdAmount: usdAmountProp = "100000" } = props;
200
- const account = (0, viem_accounts.privateKeyToAccount)(adminPrivateKey);
223
+ const { anvil, investor, token, marketConfigurators, rwaFactories, usdAmount: usdAmountProp = "100000" } = props;
201
224
  const symbol = await anvil.readContract({
202
225
  address: token,
203
226
  abi: viem.erc20Abi,
@@ -221,18 +244,31 @@ async function claimDSToken(props) {
221
244
  if (amount === 0n) throw new Error(`No market found for token ${token}`);
222
245
  logger?.debug(`${usdAmountProp} USD === ${amount} ${symbol}`);
223
246
  await require_dev_kycUtils.registerSecuritizeInvestor({
224
- ...props,
225
- logger
226
- });
227
- logger?.debug(`Issuing ${amount} tokens to ${investor}...`);
228
- const mintHash = await issueDSTokens({
229
247
  anvil,
230
- account,
231
- token,
232
248
  investor,
233
- amount,
249
+ token,
234
250
  logger
235
251
  });
252
+ const admin = await require_dev_kycUtils.getSecuritizeAdmin(anvil, token, logger);
253
+ logger?.debug(`Issuing ${amount} tokens to ${investor}...`);
254
+ await anvil.impersonateAccount({ address: admin });
255
+ let mintHash;
256
+ try {
257
+ await anvil.setBalance({
258
+ address: admin,
259
+ value: (0, viem.parseEther)("100")
260
+ });
261
+ mintHash = await issueDSTokens({
262
+ anvil,
263
+ account: admin,
264
+ token,
265
+ investor,
266
+ amount,
267
+ logger
268
+ });
269
+ } finally {
270
+ await anvil.stopImpersonatingAccount({ address: admin });
271
+ }
236
272
  logger?.debug(`Done! tx: ${mintHash}`);
237
273
  const balance = await anvil.readContract({
238
274
  address: token,
@@ -78,11 +78,7 @@ const iFaucetAbi = [
78
78
  internalType: "uint256"
79
79
  }]
80
80
  }],
81
- outputs: [{
82
- name: "",
83
- type: "bool",
84
- internalType: "bool"
85
- }],
81
+ outputs: [],
86
82
  stateMutability: "nonpayable"
87
83
  },
88
84
  {
@@ -97,11 +93,7 @@ const iFaucetAbi = [
97
93
  type: "uint256",
98
94
  internalType: "uint256"
99
95
  }],
100
- outputs: [{
101
- name: "",
102
- type: "bool",
103
- internalType: "bool"
104
- }],
96
+ outputs: [],
105
97
  stateMutability: "nonpayable"
106
98
  },
107
99
  {
@@ -112,11 +104,7 @@ const iFaucetAbi = [
112
104
  type: "address",
113
105
  internalType: "address"
114
106
  }],
115
- outputs: [{
116
- name: "",
117
- type: "bool",
118
- internalType: "bool"
119
- }],
107
+ outputs: [],
120
108
  stateMutability: "nonpayable"
121
109
  },
122
110
  {
@@ -188,6 +176,17 @@ const iFaucetAbi = [
188
176
  }],
189
177
  stateMutability: "view"
190
178
  },
179
+ {
180
+ type: "function",
181
+ name: "owner",
182
+ inputs: [],
183
+ outputs: [{
184
+ name: "",
185
+ type: "address",
186
+ internalType: "address"
187
+ }],
188
+ stateMutability: "view"
189
+ },
191
190
  {
192
191
  type: "function",
193
192
  name: "prices",
@@ -14,7 +14,7 @@ import { isOutOfSyncError } from "./isOutOfSyncError.js";
14
14
  import { isRateLimitError } from "./isRateLimitError.js";
15
15
  import { isTransientError } from "./isTransientError.js";
16
16
  import { collectMidasGateways, collectMidasMTokens, unpauseMidasIssuanceVault } from "./midasUtils.js";
17
- import { greenlistMidasGateway, registerMidasInvestor, registerRWAInvestor, registerSecuritizeInvestor } from "./kycUtils.js";
17
+ import { getSecuritizeAdmin, greenlistMidasGateway, registerMidasInvestor, registerRWAInvestor, registerSecuritizeInvestor } from "./kycUtils.js";
18
18
  import { isRangeError, logSplitterTransport } from "./logSplitterTransport.js";
19
19
  import { setLTZero, setLTs } from "./ltUtils.js";
20
20
  import { migrateFaucet } from "./migrateFaucet.js";
@@ -25,4 +25,4 @@ import { claimDSToken, claimDSTokens, enableDSTokenBackDating } from "./securiti
25
25
  import "./types.js";
26
26
  import { ONCHAIN_EXECUTION_ID_ADDRESS, verifyTestnet } from "./verifyTestnet.js";
27
27
  import { makePendingWithdrawalsClaimable } from "./withdrawalUtils.js";
28
- export { AccountOpener, Create2Deployer, DEFAULT_CREATE2_SALT, EthCallSpy, NoAvailableTransportsError, ONCHAIN_EXECUTION_ID_ADDRESS, OpenTxRevertedError, PUBLIC_CREATE2_FACTORY, RevolverTransport, SUPPORTED_RPC_PROVIDERS, SelectionStrategy, anvilNodeInfo, calcLiquidatableLTs, claimDSToken, claimDSTokens, claimFromFaucet, collectMidasGateways, collectMidasMTokens, createAnvilClient, createMinter, deployUsingPublicCreate2, detectChain, enableDSTokenBackDating, evmMineDetailed, extendAnvilClient, getAlchemyUrl, getAnkrUrl, getDrpcUrl, getErpcKey, getPublicCreate2Address, getRpcProviderUrl, getThirdWebUrl, greenlistMidasGateway, httpTransportOptionsSchema, iDegenNftv2Abi, iFaucetAbi, iOnchainExecutionIdAbi, iOwnableAbi, iaclTraitAbi, isAnvil, isDeployedUsingPublicCreate2, isOutOfSyncError, isRangeError, isRateLimitError, isTransientError, logSplitterTransport, makePendingWithdrawalsClaimable, migrateFaucet, providerConfigSchema, registerMidasInvestor, registerRWAInvestor, registerSecuritizeInvestor, replaceStorage, resilientTransport, resilientTransportOptionsSchema, revolverTransportConfigBaseSchema, revolverTransportConfigSchema, rpcProvidersSchema, setLTZero, setLTs, unpauseMidasIssuanceVault, verifyTestnet, writeContractSync };
28
+ export { AccountOpener, Create2Deployer, DEFAULT_CREATE2_SALT, EthCallSpy, NoAvailableTransportsError, ONCHAIN_EXECUTION_ID_ADDRESS, OpenTxRevertedError, PUBLIC_CREATE2_FACTORY, RevolverTransport, SUPPORTED_RPC_PROVIDERS, SelectionStrategy, anvilNodeInfo, calcLiquidatableLTs, claimDSToken, claimDSTokens, claimFromFaucet, collectMidasGateways, collectMidasMTokens, createAnvilClient, createMinter, deployUsingPublicCreate2, detectChain, enableDSTokenBackDating, evmMineDetailed, extendAnvilClient, getAlchemyUrl, getAnkrUrl, getDrpcUrl, getErpcKey, getPublicCreate2Address, getRpcProviderUrl, getSecuritizeAdmin, getThirdWebUrl, greenlistMidasGateway, httpTransportOptionsSchema, iDegenNftv2Abi, iFaucetAbi, iOnchainExecutionIdAbi, iOwnableAbi, iaclTraitAbi, isAnvil, isDeployedUsingPublicCreate2, isOutOfSyncError, isRangeError, isRateLimitError, isTransientError, logSplitterTransport, makePendingWithdrawalsClaimable, migrateFaucet, providerConfigSchema, registerMidasInvestor, registerRWAInvestor, registerSecuritizeInvestor, replaceStorage, resilientTransport, resilientTransportOptionsSchema, revolverTransportConfigBaseSchema, revolverTransportConfigSchema, rpcProvidersSchema, setLTZero, setLTs, unpauseMidasIssuanceVault, verifyTestnet, writeContractSync };
@@ -6,20 +6,50 @@ import { iDSRegistryServiceAbi } from "../abi/rwa/iDSRegistryService.js";
6
6
  import { iDSTokenAbi } from "../abi/rwa/iDSToken.js";
7
7
  import { collectMidasGateways } from "./midasUtils.js";
8
8
  import { midasGatewayAbi } from "./withdrawalAbi.js";
9
- import { isAddressEqual, parseAbi, parseEther, zeroAddress } from "viem";
10
- import { privateKeyToAccount } from "viem/accounts";
9
+ import { getAddress, isAddressEqual, parseAbi, parseEther, slice, toHex, zeroAddress } from "viem";
11
10
  //#region src/dev/kycUtils.ts
11
+ const iMockDSTokenAdminAbi = parseAbi(["function admin() view returns (address)"]);
12
12
  /**
13
- * Resolves the account that performs the DS registry writes: either the admin
14
- * private key, or the admin address impersonated on the fork
13
+ * DS trust-service master of `token`: Ownable owner at storage slot 0 of the
14
+ * trust service, same as periphery-v3 SecuritizeAttachHelper. MockDSToken
15
+ * returns itself as the trust service, so `admin()` is used instead.
16
+ */
17
+ async function getSecuritizeAdmin(anvil, token, logger) {
18
+ const trustServiceId = await anvil.readContract({
19
+ address: token,
20
+ abi: iDSTokenAbi,
21
+ functionName: "TRUST_SERVICE"
22
+ });
23
+ const trustService = await anvil.readContract({
24
+ address: token,
25
+ abi: iDSTokenAbi,
26
+ functionName: "getDSService",
27
+ args: [trustServiceId]
28
+ });
29
+ if (isAddressEqual(trustService, token)) {
30
+ const admin = await anvil.readContract({
31
+ address: token,
32
+ abi: iMockDSTokenAdminAbi,
33
+ functionName: "admin"
34
+ });
35
+ logger?.debug(`securitize: found admin ${admin} for ${token} (token.admin)`);
36
+ return admin;
37
+ }
38
+ const word = await anvil.getStorageAt({
39
+ address: trustService,
40
+ slot: toHex(0, { size: 32 })
41
+ });
42
+ if (!word) throw new Error(`securitize: empty trust-service owner slot on ${trustService}`);
43
+ const admin = getAddress(slice(word, 12));
44
+ logger?.debug(`securitize: found admin ${admin} for ${token} (trust service ${trustService})`);
45
+ return admin;
46
+ }
47
+ /**
48
+ * Impersonates the DS trust-service admin of `token` on the fork
15
49
  */
16
50
  async function useSecuritizeAdmin(props) {
17
- const { anvil, adminPrivateKey, admin, logger } = props;
18
- if (adminPrivateKey) return {
19
- account: privateKeyToAccount(adminPrivateKey),
20
- release: async () => {}
21
- };
22
- if (!admin) throw new Error("securitize: either adminPrivateKey or admin address is required");
51
+ const { anvil, token, logger } = props;
52
+ const admin = await getSecuritizeAdmin(anvil, token, logger);
23
53
  await anvil.impersonateAccount({ address: admin });
24
54
  await anvil.setBalance({
25
55
  address: admin,
@@ -294,17 +324,15 @@ async function findMidasGateway(props) {
294
324
  * result instead of aborting the whole run.
295
325
  */
296
326
  async function registerRWAInvestor(props) {
297
- const { anvil, sdk, investor, adminPrivateKey, securitizeAdmin, midasAdmin = "0xd4195CF4df289a4748C1A7B6dDBE770e27bA1227", logger } = props;
327
+ const { anvil, sdk, investor, midasAdmin = "0xd4195CF4df289a4748C1A7B6dDBE770e27bA1227", logger } = props;
298
328
  const securitizeTokens = [];
299
329
  const midasGateways = [];
300
330
  const failed = [];
301
331
  const dsTokens = new AddressSet(sdk.rwa.factories.flatMap((factory) => factory.getTokens()));
302
- if (adminPrivateKey || securitizeAdmin) for (const token of dsTokens) try {
332
+ for (const token of dsTokens) try {
303
333
  await registerSecuritizeInvestor({
304
334
  anvil,
305
335
  investor,
306
- adminPrivateKey,
307
- admin: securitizeAdmin,
308
336
  token,
309
337
  logger
310
338
  });
@@ -317,7 +345,6 @@ async function registerRWAInvestor(props) {
317
345
  error: e
318
346
  });
319
347
  }
320
- else if (dsTokens.size > 0) logger?.warn(`securitize: no registry admin, skipping ${dsTokens.size} DSToken(s)`);
321
348
  const gateways = await collectMidasGateways(sdk);
322
349
  for (const gateway of gateways) try {
323
350
  await greenlistMidasGateway({
@@ -344,4 +371,4 @@ async function registerRWAInvestor(props) {
344
371
  };
345
372
  }
346
373
  //#endregion
347
- export { greenlistMidasGateway, registerMidasInvestor, registerRWAInvestor, registerSecuritizeInvestor };
374
+ export { getSecuritizeAdmin, greenlistMidasGateway, registerMidasInvestor, registerRWAInvestor, registerSecuritizeInvestor };
@@ -2,9 +2,8 @@ import { AddressSet } from "../onchain/utils/AddressSet.js";
2
2
  import { OnchainSDK } from "../onchain/OnchainSDK.js";
3
3
  import "../onchain/index.js";
4
4
  import { iDSTokenAbi } from "../abi/rwa/iDSToken.js";
5
- import { registerSecuritizeInvestor } from "./kycUtils.js";
6
- import { erc20Abi, isAddressEqual, parseAbi, zeroAddress } from "viem";
7
- import { privateKeyToAccount } from "viem/accounts";
5
+ import { getSecuritizeAdmin, registerSecuritizeInvestor } from "./kycUtils.js";
6
+ import { erc20Abi, getAddress, isAddressEqual, parseAbi, parseEther, zeroAddress } from "viem";
8
7
  //#region src/dev/securitizeUtils.ts
9
8
  /**
10
9
  * `COMPLIANCE_CONFIGURATION_SERVICE` id in the DS protocol service registry
@@ -110,7 +109,7 @@ async function issueDSTokens(props) {
110
109
  * Tokens without one (e.g. MockDSToken) are skipped
111
110
  */
112
111
  async function getComplianceConfigurationServices({ anvil, tokens, logger }) {
113
- const services = new AddressSet();
112
+ const services = /* @__PURE__ */ new Map();
114
113
  for (const token of new AddressSet(tokens)) try {
115
114
  const service = await anvil.readContract({
116
115
  address: token,
@@ -122,11 +121,16 @@ async function getComplianceConfigurationServices({ anvil, tokens, logger }) {
122
121
  logger?.debug(`${token} has no compliance configuration service`);
123
122
  continue;
124
123
  }
125
- services.add(service);
124
+ const checksummed = getAddress(service);
125
+ if (services.has(checksummed)) continue;
126
+ services.set(checksummed, await getSecuritizeAdmin(anvil, token, logger));
126
127
  } catch (e) {
127
128
  logger?.debug(`Failed to get compliance configuration service of ${token}: ${e}`);
128
129
  }
129
- return [...services];
130
+ return [...services].map(([service, admin]) => ({
131
+ service,
132
+ admin
133
+ }));
130
134
  }
131
135
  /**
132
136
  * Sets `disallowBackDating` to false on compliance configuration services of
@@ -134,18 +138,17 @@ async function getComplianceConfigurationServices({ anvil, tokens, logger }) {
134
138
  * honoured: DS protocol silently replaces it with `block.timestamp` otherwise,
135
139
  * and freshly minted tokens stay under lock-up.
136
140
  *
137
- * Must be signed by a DS admin with sufficient trust (same key as
138
- * `issueTokens` / registerInvestor); Ownable `owner()` alone is not enough.
141
+ * Impersonates the DS trust-service admin of each token. Ownable `owner()` of
142
+ * the compliance configuration service alone is not enough.
139
143
  *
140
144
  * The flag is only read while tokens are issued, so restoring it does not
141
145
  * re-lock tokens minted in the meantime.
142
146
  */
143
147
  async function enableDSTokenBackDating(props) {
144
- const { anvil, adminPrivateKey, logger } = props;
145
- const account = privateKeyToAccount(adminPrivateKey);
148
+ const { anvil, logger } = props;
146
149
  const services = await getComplianceConfigurationServices(props);
147
150
  let toRestore = [];
148
- for (const service of services) {
151
+ for (const { service, admin } of services) {
149
152
  let disallowBackDating;
150
153
  try {
151
154
  disallowBackDating = await anvil.readContract({
@@ -162,32 +165,53 @@ async function enableDSTokenBackDating(props) {
162
165
  continue;
163
166
  }
164
167
  logger?.info(`Allowing back-dating on ${service}`);
165
- await anvil.writeContractSync({
166
- account,
167
- chain: anvil.chain,
168
- address: service,
169
- abi: iDSComplianceConfigurationServiceAbi,
170
- functionName: "setDisallowBackDating",
171
- args: [false],
172
- throwOnReceiptRevert: true
168
+ await anvil.impersonateAccount({ address: admin });
169
+ try {
170
+ await anvil.setBalance({
171
+ address: admin,
172
+ value: parseEther("100")
173
+ });
174
+ await anvil.writeContractSync({
175
+ account: admin,
176
+ chain: anvil.chain,
177
+ address: service,
178
+ abi: iDSComplianceConfigurationServiceAbi,
179
+ functionName: "setDisallowBackDating",
180
+ args: [false],
181
+ throwOnReceiptRevert: true
182
+ });
183
+ } finally {
184
+ await anvil.stopImpersonatingAccount({ address: admin });
185
+ }
186
+ toRestore.push({
187
+ service,
188
+ admin
173
189
  });
174
- toRestore.push(service);
175
190
  }
176
191
  return async () => {
177
192
  const services = toRestore;
178
193
  toRestore = [];
179
- for (const service of services) {
194
+ for (const { service, admin } of services) {
180
195
  logger?.info(`Disallowing back-dating on ${service}`);
181
196
  try {
182
- await anvil.writeContractSync({
183
- account,
184
- chain: anvil.chain,
185
- address: service,
186
- abi: iDSComplianceConfigurationServiceAbi,
187
- functionName: "setDisallowBackDating",
188
- args: [true],
189
- throwOnReceiptRevert: true
190
- });
197
+ await anvil.impersonateAccount({ address: admin });
198
+ try {
199
+ await anvil.setBalance({
200
+ address: admin,
201
+ value: parseEther("100")
202
+ });
203
+ await anvil.writeContractSync({
204
+ account: admin,
205
+ chain: anvil.chain,
206
+ address: service,
207
+ abi: iDSComplianceConfigurationServiceAbi,
208
+ functionName: "setDisallowBackDating",
209
+ args: [true],
210
+ throwOnReceiptRevert: true
211
+ });
212
+ } finally {
213
+ await anvil.stopImpersonatingAccount({ address: admin });
214
+ }
191
215
  } catch (e) {
192
216
  logger?.warn(`Failed to restore disallowBackDating on ${service}: ${e}`);
193
217
  }
@@ -195,8 +219,7 @@ async function enableDSTokenBackDating(props) {
195
219
  };
196
220
  }
197
221
  async function claimDSToken(props) {
198
- const { anvil, investor, adminPrivateKey, token, marketConfigurators, rwaFactories, usdAmount: usdAmountProp = "100000" } = props;
199
- const account = privateKeyToAccount(adminPrivateKey);
222
+ const { anvil, investor, token, marketConfigurators, rwaFactories, usdAmount: usdAmountProp = "100000" } = props;
200
223
  const symbol = await anvil.readContract({
201
224
  address: token,
202
225
  abi: erc20Abi,
@@ -220,18 +243,31 @@ async function claimDSToken(props) {
220
243
  if (amount === 0n) throw new Error(`No market found for token ${token}`);
221
244
  logger?.debug(`${usdAmountProp} USD === ${amount} ${symbol}`);
222
245
  await registerSecuritizeInvestor({
223
- ...props,
224
- logger
225
- });
226
- logger?.debug(`Issuing ${amount} tokens to ${investor}...`);
227
- const mintHash = await issueDSTokens({
228
246
  anvil,
229
- account,
230
- token,
231
247
  investor,
232
- amount,
248
+ token,
233
249
  logger
234
250
  });
251
+ const admin = await getSecuritizeAdmin(anvil, token, logger);
252
+ logger?.debug(`Issuing ${amount} tokens to ${investor}...`);
253
+ await anvil.impersonateAccount({ address: admin });
254
+ let mintHash;
255
+ try {
256
+ await anvil.setBalance({
257
+ address: admin,
258
+ value: parseEther("100")
259
+ });
260
+ mintHash = await issueDSTokens({
261
+ anvil,
262
+ account: admin,
263
+ token,
264
+ investor,
265
+ amount,
266
+ logger
267
+ });
268
+ } finally {
269
+ await anvil.stopImpersonatingAccount({ address: admin });
270
+ }
235
271
  logger?.debug(`Done! tx: ${mintHash}`);
236
272
  const balance = await anvil.readContract({
237
273
  address: token,
@@ -55,7 +55,7 @@ var PrepareApi = class extends MultichainConstruct {
55
55
  const at = stateBlock(sdk);
56
56
  const intent = resumable(params.intent ?? params.claimable.intent);
57
57
  if (!intent) return sdkErr(noRecordedIntent());
58
- const creditAccount = await slice(sdk, position.creditAccount);
58
+ const creditAccount = await slice$1(sdk, position.creditAccount);
59
59
  if (!creditAccount) return sdkErr(creditAccountNotFound(position.creditAccount));
60
60
  return finalized(await service(sdk).finishIntent({
61
61
  intent,
@@ -404,7 +404,7 @@ var PrepareApi = class extends MultichainConstruct {
404
404
  * described, see {@link IOpportunitiesPrepare.maxWithdraw}.
405
405
  **/
406
406
  async #account(sdk, position) {
407
- const creditAccount = await slice(sdk, position.creditAccount);
407
+ const creditAccount = await slice$1(sdk, position.creditAccount);
408
408
  if (!creditAccount) throw new Error(creditAccountNotFound(position.creditAccount).message);
409
409
  return creditAccount;
410
410
  }
@@ -421,7 +421,7 @@ var PrepareApi = class extends MultichainConstruct {
421
421
  try {
422
422
  const sdk = await this.#chain(position.chainId);
423
423
  const at = stateBlock(sdk);
424
- const creditAccount = await slice(sdk, position.creditAccount);
424
+ const creditAccount = await slice$1(sdk, position.creditAccount);
425
425
  if (!creditAccount) return neitherRoute(creditAccountNotFound(position.creditAccount));
426
426
  return routed(await service(sdk).intentRoutes({
427
427
  intent,
@@ -447,7 +447,7 @@ var PrepareApi = class extends MultichainConstruct {
447
447
  try {
448
448
  const sdk = await this.#chain(position.chainId);
449
449
  const at = stateBlock(sdk);
450
- const creditAccount = await slice(sdk, position.creditAccount);
450
+ const creditAccount = await slice$1(sdk, position.creditAccount);
451
451
  if (!creditAccount) return sdkErr(creditAccountNotFound(position.creditAccount));
452
452
  return planned(await service(sdk).startIntent({
453
453
  intent,
@@ -479,7 +479,7 @@ function stateBlock(sdk) {
479
479
  * connected to hold no such account — closed since it was listed, or named on
480
480
  * the wrong chain. Read rather than thrown, so the caller gets a code for it.
481
481
  **/
482
- async function slice(sdk, creditAccount) {
482
+ async function slice$1(sdk, creditAccount) {
483
483
  const data = await sdk.accounts.getCreditAccountData(creditAccount);
484
484
  return data && toCreditAccountSlice(data);
485
485
  }
@@ -497,7 +497,7 @@ async function slice(sdk, creditAccount) {
497
497
  **/
498
498
  async function reusable(sdk, strategy, creditAccount) {
499
499
  if (!creditAccount) return;
500
- const account = await slice(sdk, creditAccount);
500
+ const account = await slice$1(sdk, creditAccount);
501
501
  if (!account || !isAddressEqual(account.creditManager, strategy.creditManager)) return sdkErr(creditAccountNotFound(creditAccount));
502
502
  if (account.totalDebt > 0n || account.tokens.some((t) => t.quota > 0n)) return sdkErr(creditAccountNotEmpty(creditAccount));
503
503
  return { account };
@@ -108,11 +108,7 @@ declare const iFaucetAbi: readonly [{
108
108
  readonly internalType: "uint256";
109
109
  }];
110
110
  }];
111
- readonly outputs: readonly [{
112
- readonly name: "";
113
- readonly type: "bool";
114
- readonly internalType: "bool";
115
- }];
111
+ readonly outputs: readonly [];
116
112
  readonly stateMutability: "nonpayable";
117
113
  }, {
118
114
  readonly type: "function";
@@ -126,11 +122,7 @@ declare const iFaucetAbi: readonly [{
126
122
  readonly type: "uint256";
127
123
  readonly internalType: "uint256";
128
124
  }];
129
- readonly outputs: readonly [{
130
- readonly name: "";
131
- readonly type: "bool";
132
- readonly internalType: "bool";
133
- }];
125
+ readonly outputs: readonly [];
134
126
  readonly stateMutability: "nonpayable";
135
127
  }, {
136
128
  readonly type: "function";
@@ -140,11 +132,7 @@ declare const iFaucetAbi: readonly [{
140
132
  readonly type: "address";
141
133
  readonly internalType: "address";
142
134
  }];
143
- readonly outputs: readonly [{
144
- readonly name: "";
145
- readonly type: "bool";
146
- readonly internalType: "bool";
147
- }];
135
+ readonly outputs: readonly [];
148
136
  readonly stateMutability: "nonpayable";
149
137
  }, {
150
138
  readonly type: "function";
@@ -207,6 +195,16 @@ declare const iFaucetAbi: readonly [{
207
195
  readonly internalType: "uint256";
208
196
  }];
209
197
  readonly stateMutability: "view";
198
+ }, {
199
+ readonly type: "function";
200
+ readonly name: "owner";
201
+ readonly inputs: readonly [];
202
+ readonly outputs: readonly [{
203
+ readonly name: "";
204
+ readonly type: "address";
205
+ readonly internalType: "address";
206
+ }];
207
+ readonly stateMutability: "view";
210
208
  }, {
211
209
  readonly type: "function";
212
210
  readonly name: "prices";
@@ -11,7 +11,7 @@ import { detectChain } from "./detectChain.js";
11
11
  import { isOutOfSyncError } from "./isOutOfSyncError.js";
12
12
  import { isRateLimitError } from "./isRateLimitError.js";
13
13
  import { isTransientError } from "./isTransientError.js";
14
- import { GreenlistMidasGatewayProps, RWAKycFailure, RegisterMidasInvestorProps, RegisterRWAInvestorProps, RegisterRWAInvestorResult, RegisterSecuritizeInvestorProps, greenlistMidasGateway, registerMidasInvestor, registerRWAInvestor, registerSecuritizeInvestor } from "./kycUtils.js";
14
+ import { GreenlistMidasGatewayProps, RWAKycFailure, RegisterMidasInvestorProps, RegisterRWAInvestorProps, RegisterRWAInvestorResult, RegisterSecuritizeInvestorProps, getSecuritizeAdmin, greenlistMidasGateway, registerMidasInvestor, registerRWAInvestor, registerSecuritizeInvestor } from "./kycUtils.js";
15
15
  import { LogSplitterTransportOptions, isRangeError, logSplitterTransport } from "./logSplitterTransport.js";
16
16
  import { setLTZero, setLTs } from "./ltUtils.js";
17
17
  import { RestoreMidasIssuanceVaultPause, UnpauseMidasIssuanceVaultProps, collectMidasGateways, collectMidasMTokens, unpauseMidasIssuanceVault } from "./midasUtils.js";
@@ -26,4 +26,4 @@ import { EnableDSTokenBackDatingProps, RestoreDSTokenBackDating, claimDSToken, c
26
26
  import { httpTransportOptionsSchema } from "./transports.js";
27
27
  import { ONCHAIN_EXECUTION_ID_ADDRESS, VerifyTestnetParams, verifyTestnet } from "./verifyTestnet.js";
28
28
  import { MakePendingWithdrawalsClaimableOptions, makePendingWithdrawalsClaimable } from "./withdrawalUtils.js";
29
- export { AccountOpener, AccountOpenerOptions, AnvilActions, AnvilClient, AnvilClientConfig, AnvilDealParameters, AnvilNodeInfo, AnvilRPCSchema, CheckMulticallFn, Create2Deployer, Create2Parameters, DEFAULT_CREATE2_SALT, DetectedCall, EnableDSTokenBackDatingProps, EnsureExistsUsingPublicCreate2ReturnType, EthCallMethod, EthCallRequest, EthCallSpy, GetCreate2AddressParameters, GreenlistMidasGatewayProps, IMinter, type LogSplitterTransportOptions, MakePendingWithdrawalsClaimableOptions, NoAvailableTransportsError, ONCHAIN_EXECUTION_ID_ADDRESS, OpenAccountHumanizedPreview, OpenAccountResult, OpenAccountsResult, OpenTxRevertedError, PUBLIC_CREATE2_FACTORY, PoolDepositResult, ProviderConfig, ProviderStatus, RWAKycFailure, RegisterMidasInvestorProps, RegisterRWAInvestorProps, RegisterRWAInvestorResult, RegisterSecuritizeInvestorProps, ReplaceStorageParams, ResilientTransportOptions, RestoreDSTokenBackDating, RestoreMidasIssuanceVaultPause, RevolverTransport, RevolverTransportConfig, RevolverTransportValue, RpcErrorResult, RpcProvider, RpcResponse, RpcSuccessResult, SUPPORTED_RPC_PROVIDERS, SelectionStrategy, TargetAccount, UnpauseMidasIssuanceVaultProps, VerifyTestnetParams, anvilNodeInfo, calcLiquidatableLTs, claimDSToken, claimDSTokens, claimFromFaucet, collectMidasGateways, collectMidasMTokens, createAnvilClient, createMinter, deployUsingPublicCreate2, detectChain, enableDSTokenBackDating, evmMineDetailed, extendAnvilClient, getAlchemyUrl, getAnkrUrl, getDrpcUrl, getErpcKey, getPublicCreate2Address, getRpcProviderUrl, getThirdWebUrl, greenlistMidasGateway, httpTransportOptionsSchema, iDegenNftv2Abi, iFaucetAbi, iOnchainExecutionIdAbi, iOwnableAbi, iaclTraitAbi, isAnvil, isDeployedUsingPublicCreate2, isOutOfSyncError, isRangeError, isRateLimitError, isTransientError, logSplitterTransport, makePendingWithdrawalsClaimable, migrateFaucet, providerConfigSchema, registerMidasInvestor, registerRWAInvestor, registerSecuritizeInvestor, replaceStorage, resilientTransport, resilientTransportOptionsSchema, revolverTransportConfigBaseSchema, revolverTransportConfigSchema, rpcProvidersSchema, setLTZero, setLTs, unpauseMidasIssuanceVault, verifyTestnet, writeContractSync };
29
+ export { AccountOpener, AccountOpenerOptions, AnvilActions, AnvilClient, AnvilClientConfig, AnvilDealParameters, AnvilNodeInfo, AnvilRPCSchema, CheckMulticallFn, Create2Deployer, Create2Parameters, DEFAULT_CREATE2_SALT, DetectedCall, EnableDSTokenBackDatingProps, EnsureExistsUsingPublicCreate2ReturnType, EthCallMethod, EthCallRequest, EthCallSpy, GetCreate2AddressParameters, GreenlistMidasGatewayProps, IMinter, type LogSplitterTransportOptions, MakePendingWithdrawalsClaimableOptions, NoAvailableTransportsError, ONCHAIN_EXECUTION_ID_ADDRESS, OpenAccountHumanizedPreview, OpenAccountResult, OpenAccountsResult, OpenTxRevertedError, PUBLIC_CREATE2_FACTORY, PoolDepositResult, ProviderConfig, ProviderStatus, RWAKycFailure, RegisterMidasInvestorProps, RegisterRWAInvestorProps, RegisterRWAInvestorResult, RegisterSecuritizeInvestorProps, ReplaceStorageParams, ResilientTransportOptions, RestoreDSTokenBackDating, RestoreMidasIssuanceVaultPause, RevolverTransport, RevolverTransportConfig, RevolverTransportValue, RpcErrorResult, RpcProvider, RpcResponse, RpcSuccessResult, SUPPORTED_RPC_PROVIDERS, SelectionStrategy, TargetAccount, UnpauseMidasIssuanceVaultProps, VerifyTestnetParams, anvilNodeInfo, calcLiquidatableLTs, claimDSToken, claimDSTokens, claimFromFaucet, collectMidasGateways, collectMidasMTokens, createAnvilClient, createMinter, deployUsingPublicCreate2, detectChain, enableDSTokenBackDating, evmMineDetailed, extendAnvilClient, getAlchemyUrl, getAnkrUrl, getDrpcUrl, getErpcKey, getPublicCreate2Address, getRpcProviderUrl, getSecuritizeAdmin, getThirdWebUrl, greenlistMidasGateway, httpTransportOptionsSchema, iDegenNftv2Abi, iFaucetAbi, iOnchainExecutionIdAbi, iOwnableAbi, iaclTraitAbi, isAnvil, isDeployedUsingPublicCreate2, isOutOfSyncError, isRangeError, isRateLimitError, isTransientError, logSplitterTransport, makePendingWithdrawalsClaimable, migrateFaucet, providerConfigSchema, registerMidasInvestor, registerRWAInvestor, registerSecuritizeInvestor, replaceStorage, resilientTransport, resilientTransportOptionsSchema, revolverTransportConfigBaseSchema, revolverTransportConfigSchema, rpcProvidersSchema, setLTZero, setLTs, unpauseMidasIssuanceVault, verifyTestnet, writeContractSync };
@@ -2,7 +2,7 @@ import { ILogger } from "../onchain/types/logger.js";
2
2
  import { OnchainSDK } from "../onchain/OnchainSDK.js";
3
3
  import "../onchain/index.js";
4
4
  import { AnvilClient } from "./createAnvilClient.js";
5
- import { Address, Hex } from "viem";
5
+ import { Address } from "viem";
6
6
  //#region src/dev/kycUtils.d.ts
7
7
  interface RegisterSecuritizeInvestorProps {
8
8
  anvil: AnvilClient;
@@ -10,20 +10,18 @@ interface RegisterSecuritizeInvestorProps {
10
10
  * Wallet to register in the Securitize DS registry
11
11
  */
12
12
  investor: Address;
13
- /**
14
- * Private key of the DS registry admin, signs the registry writes
15
- */
16
- adminPrivateKey?: Hex;
17
- /**
18
- * DS registry admin, impersonated on the fork when no private key is given
19
- */
20
- admin?: Address;
21
13
  /**
22
14
  * DSToken address
23
15
  */
24
16
  token: Address;
25
17
  logger?: ILogger;
26
18
  }
19
+ /**
20
+ * DS trust-service master of `token`: Ownable owner at storage slot 0 of the
21
+ * trust service, same as periphery-v3 SecuritizeAttachHelper. MockDSToken
22
+ * returns itself as the trust service, so `admin()` is used instead.
23
+ */
24
+ declare function getSecuritizeAdmin(anvil: AnvilClient, token: Address, logger?: ILogger): Promise<Address>;
27
25
  /**
28
26
  * Registers a wallet as a Securitize investor (fake KYC) in the DS registry
29
27
  * service of a DSToken.
@@ -92,15 +90,6 @@ interface RegisterRWAInvestorProps {
92
90
  * Wallet to pass the KYC of every RWA token
93
91
  */
94
92
  investor: Address;
95
- /**
96
- * Private key of the Securitize registry admin, DSTokens are skipped when
97
- * neither this nor `securitizeAdmin` is set
98
- */
99
- adminPrivateKey?: Hex;
100
- /**
101
- * Securitize registry admin, impersonated on the fork
102
- */
103
- securitizeAdmin?: Address;
104
93
  /**
105
94
  * Override midas access control admin address
106
95
  */
@@ -134,4 +123,4 @@ interface RegisterRWAInvestorResult {
134
123
  */
135
124
  declare function registerRWAInvestor(props: RegisterRWAInvestorProps): Promise<RegisterRWAInvestorResult>;
136
125
  //#endregion
137
- export { GreenlistMidasGatewayProps, RWAKycFailure, RegisterMidasInvestorProps, RegisterRWAInvestorProps, RegisterRWAInvestorResult, RegisterSecuritizeInvestorProps, greenlistMidasGateway, registerMidasInvestor, registerRWAInvestor, registerSecuritizeInvestor };
126
+ export { GreenlistMidasGatewayProps, RWAKycFailure, RegisterMidasInvestorProps, RegisterRWAInvestorProps, RegisterRWAInvestorResult, RegisterSecuritizeInvestorProps, getSecuritizeAdmin, greenlistMidasGateway, registerMidasInvestor, registerRWAInvestor, registerSecuritizeInvestor };
@@ -1,12 +1,11 @@
1
1
  import { ILogger } from "../onchain/types/logger.js";
2
2
  import "../onchain/index.js";
3
3
  import { AnvilClient } from "./createAnvilClient.js";
4
- import { Address, Hex } from "viem";
4
+ import { Address } from "viem";
5
5
  //#region src/dev/securitizeUtils.d.ts
6
6
  interface ClaimDSTokenProps {
7
7
  anvil: AnvilClient;
8
8
  investor: Address;
9
- adminPrivateKey: Hex;
10
9
  /**
11
10
  * DSToken addresses
12
11
  */
@@ -24,11 +23,6 @@ type ClaimDSTokensProps = Omit<ClaimDSTokenProps, "token"> & {
24
23
  };
25
24
  interface EnableDSTokenBackDatingProps {
26
25
  anvil: AnvilClient;
27
- /**
28
- * Securitize DS admin with sufficient trust to call compliance setters
29
- * (same key used for issueTokens / registerInvestor)
30
- */
31
- adminPrivateKey: Hex;
32
26
  /**
33
27
  * DSToken addresses whose compliance configuration should allow back-dating
34
28
  */
@@ -46,8 +40,8 @@ type RestoreDSTokenBackDating = () => Promise<void>;
46
40
  * honoured: DS protocol silently replaces it with `block.timestamp` otherwise,
47
41
  * and freshly minted tokens stay under lock-up.
48
42
  *
49
- * Must be signed by a DS admin with sufficient trust (same key as
50
- * `issueTokens` / registerInvestor); Ownable `owner()` alone is not enough.
43
+ * Impersonates the DS trust-service admin of each token. Ownable `owner()` of
44
+ * the compliance configuration service alone is not enough.
51
45
  *
52
46
  * The flag is only read while tokens are issued, so restoring it does not
53
47
  * re-lock tokens minted in the meantime.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@gearbox-protocol/sdk",
3
- "version": "16.6.0-next.3",
3
+ "version": "16.6.0-next.5",
4
4
  "description": "Gearbox SDK",
5
5
  "license": "MIT",
6
6
  "repository": {