From 0767f72848fdaf17deae4f939e52b693391e37b1 Mon Sep 17 00:00:00 2001 From: anilhelvaci Date: Tue, 5 Nov 2024 18:34:21 +0300 Subject: [PATCH 01/56] chore(pp-upgrade): create and set a new bridgeHandler in the proposal Refs: https://github.com/Agoric/agoric-sdk/issues/10395 --- golang/cosmos/app/upgrade.go | 6 +++ .../upgrade-provisionPool-proposal.js | 44 ++++++++++++++++++- 2 files changed, 48 insertions(+), 2 deletions(-) diff --git a/golang/cosmos/app/upgrade.go b/golang/cosmos/app/upgrade.go index 8770675d792..9f81d6bb0ca 100644 --- a/golang/cosmos/app/upgrade.go +++ b/golang/cosmos/app/upgrade.go @@ -212,6 +212,12 @@ func unreleasedUpgradeHandler(app *GaiaApp, targetUpgrade string) func(sdk.Conte // Upgrade to include a cleanup from https://github.com/Agoric/agoric-sdk/pull/10319 "@agoric/builders/scripts/smart-wallet/build-wallet-factory2-upgrade.js", ), + vm.CoreProposalStepForModules( + "@agoric/builders/scripts/vats/upgrade-provisionPool.js", + ), + vm.CoreProposalStepForModules( + "@agoric/builders/scripts/vats/upgrade-bank.js", + ), ) // // CoreProposals for Upgrade 19. These should not be introduced diff --git a/packages/vats/src/proposals/upgrade-provisionPool-proposal.js b/packages/vats/src/proposals/upgrade-provisionPool-proposal.js index 9d31c752607..4dd74af9c69 100644 --- a/packages/vats/src/proposals/upgrade-provisionPool-proposal.js +++ b/packages/vats/src/proposals/upgrade-provisionPool-proposal.js @@ -16,6 +16,10 @@ export const upgradeProvisionPool = async ( economicCommitteeCreatorFacet: electorateCreatorFacet, instancePrivateArgs: instancePrivateArgsP, provisionPoolStartResult: provisionPoolStartResultP, + bankManager, + namesByAddressAdmin: namesByAddressAdminP, + walletFactoryStartResult: walletFactoryStartResultP, + provisionWalletBridgeManager: provisionWalletBridgeManagerP, }, }, options, @@ -25,11 +29,25 @@ export const upgradeProvisionPool = async ( assert(provisionPoolRef.bundleID); console.log(`PROVISION POOL BUNDLE ID: `, provisionPoolRef.bundleID); - const [provisionPoolStartResult, instancePrivateArgs] = await Promise.all([ + const [ + provisionPoolStartResult, + instancePrivateArgs, + namesByAddressAdmin, + walletFactoryStartResult, + provisionWalletBridgeManager, + ] = await Promise.all([ provisionPoolStartResultP, instancePrivateArgsP, + namesByAddressAdminP, + walletFactoryStartResultP, + provisionWalletBridgeManagerP, ]); - const { adminFacet, instance } = provisionPoolStartResult; + const { + adminFacet, + instance, + creatorFacet: ppCreatorFacet, + } = provisionPoolStartResult; + const { creatorFacet: wfCreatorFacet } = walletFactoryStartResult; const [originalPrivateArgs, poserInvitation] = await Promise.all([ // eslint-disable-next-line @typescript-eslint/ban-ts-comment @@ -49,6 +67,24 @@ export const upgradeProvisionPool = async ( ); console.log('ProvisionPool upgraded: ', upgradeResult); + + const references = { + bankManager, + namesByAddressAdmin, + walletFactory: wfCreatorFacet, + }; + + console.log('Calling setReferences with: ', references); + await E(ppCreatorFacet).setReferences(references); + + console.log('Creating bridgeHandler...'); + const bridgeHandler = await E(ppCreatorFacet).makeHandler(); + + console.log('Setting new bridgeHandler...'); + // @ts-expect-error casting + await E(provisionWalletBridgeManager).setHandler(bridgeHandler); + + console.log('Done.'); }; export const getManifestForUpgradingProvisionPool = ( @@ -61,6 +97,10 @@ export const getManifestForUpgradingProvisionPool = ( economicCommitteeCreatorFacet: true, instancePrivateArgs: true, provisionPoolStartResult: true, + bankManager: true, + namesByAddressAdmin: true, + walletFactoryStartResult: true, + provisionWalletBridgeManager: true, }, produce: {}, }, From c8916b25289540ccd92c81a11fb4ae8c2efb9bac Mon Sep 17 00:00:00 2001 From: anilhelvaci Date: Wed, 6 Nov 2024 16:43:15 +0300 Subject: [PATCH 02/56] chore(pp-upgrade): create helper core-evals Refs: https://github.com/Agoric/agoric-sdk/issues/10395 --- .../deposit-usd-lemons-permit.json | 8 +++ .../depositUSD-LEMONS/deposit-usd-lemons.js | 49 +++++++++++++++++++ .../scripts/testing/add-USD-LEMONS.js | 19 +++++++ 3 files changed, 76 insertions(+) create mode 100644 a3p-integration/proposals/p:upgrade-19/depositUSD-LEMONS/deposit-usd-lemons-permit.json create mode 100644 a3p-integration/proposals/p:upgrade-19/depositUSD-LEMONS/deposit-usd-lemons.js create mode 100644 packages/builders/scripts/testing/add-USD-LEMONS.js diff --git a/a3p-integration/proposals/p:upgrade-19/depositUSD-LEMONS/deposit-usd-lemons-permit.json b/a3p-integration/proposals/p:upgrade-19/depositUSD-LEMONS/deposit-usd-lemons-permit.json new file mode 100644 index 00000000000..0a580519276 --- /dev/null +++ b/a3p-integration/proposals/p:upgrade-19/depositUSD-LEMONS/deposit-usd-lemons-permit.json @@ -0,0 +1,8 @@ +{ + "consume": { + "contractKits": true, + "namesByAddressAdmin": true, + "agoricNames": true + } +} + diff --git a/a3p-integration/proposals/p:upgrade-19/depositUSD-LEMONS/deposit-usd-lemons.js b/a3p-integration/proposals/p:upgrade-19/depositUSD-LEMONS/deposit-usd-lemons.js new file mode 100644 index 00000000000..2d9a6f0650f --- /dev/null +++ b/a3p-integration/proposals/p:upgrade-19/depositUSD-LEMONS/deposit-usd-lemons.js @@ -0,0 +1,49 @@ +const PROVISIONING_POOL_ADDR = 'agoric1megzytg65cyrgzs6fvzxgrcqvwwl7ugpt62346'; + +const depositUsdLemons = async powers => { + const { + consume: { contractKits: contractKitsP, namesByAddressAdmin: namesByAddressAdminP , agoricNames }, + // instance: { consume: { ['psm-IST-USD_LEMONS']: usdLemonsPsmInstanceP }} + } = powers; + + const namesByAddressAdmin = await namesByAddressAdminP; + + const getDepositFacet = async address => { + const admin = await E(namesByAddressAdmin).lookupAdmin(address); + console.log('ADMIN', admin) + + const nameHub = await E(admin).readonly(); + console.log('NAME_HUB', nameHub); + const hub = E(E(namesByAddressAdmin).lookupAdmin(address)).readonly(); + return E(hub).lookup('depositFacet'); + }; + + const [contractKits, usdLemonsIssuer, usdLemonsBrand, ppDepositFacet] = await Promise.all([ + contractKitsP, + E(agoricNames).lookup('issuer', 'USD_LEMONS'), + E(agoricNames).lookup('brand', 'USD_LEMONS'), + getDepositFacet(PROVISIONING_POOL_ADDR), + ]); + + console.log('[CONTRACT_KITS]', contractKits); + console.log('[ISSUER]', usdLemonsIssuer); + + let usdLemonsMint; + for (const { publicFacet, creatorFacet: mint } of contractKits.values()) { + if (publicFacet === usdLemonsIssuer) { + usdLemonsMint = mint; + console.log('BINGO', mint) + break; + } + } + + console.log('Minting USD_LEMONS'); + const helloPayment = await E(usdLemonsMint).mintPayment(harden({ brand: usdLemonsBrand, value: 500000n })); + + console.log('Funding provision pool...'); + await E(ppDepositFacet).receive(helloPayment); + + console.log('Done.'); +}; + +depositUsdLemons; diff --git a/packages/builders/scripts/testing/add-USD-LEMONS.js b/packages/builders/scripts/testing/add-USD-LEMONS.js new file mode 100644 index 00000000000..89afc1279cb --- /dev/null +++ b/packages/builders/scripts/testing/add-USD-LEMONS.js @@ -0,0 +1,19 @@ +import { makeHelpers } from '@agoric/deploy-script-support'; +import { psmProposalBuilder } from '../inter-protocol/add-collateral-core.js'; + +const addUsdLemonsProposalBuilder = async powers => { + return psmProposalBuilder(powers, { + anchorOptions: { + denom: 'ibc/000C0AAAEECAFE000', + keyword: 'USD_LEMONS', + decimalPlaces: 6, + proposedName: 'USD_LEMONS', + } + }); +}; + +/** @type {import('@agoric/deploy-script-support/src/externalTypes.js').DeployScriptFunction} */ +export default async (homeP, endowments) => { + const { writeCoreEval } = await makeHelpers(homeP, endowments); + await writeCoreEval('add-LEMONS-PSM', addUsdLemonsProposalBuilder); + }; \ No newline at end of file From bf6c1ffa75885fc1d2a7901b2f36977544aaf476 Mon Sep 17 00:00:00 2001 From: anilhelvaci Date: Thu, 7 Nov 2024 11:29:24 +0300 Subject: [PATCH 03/56] chore(pp-upgrade): test functionality after provisionPool and bank upgrade Refs: https://github.com/Agoric/agoric-sdk/issues/10395 fix: format fixes --- .../proposals/p:upgrade-19/.gitignore | 1 + .../depositUSD-LEMONS/deposit-usd-lemons.js | 32 ++- .../proposals/p:upgrade-19/package.json | 1 + .../p:upgrade-19/provisionPool.test.js | 129 +++++++++ .../proposals/p:upgrade-19/test-lib/errors.js | 20 ++ .../p:upgrade-19/test-lib/sync-tools.js | 272 ++++++++++++++++++ .../proposals/p:upgrade-19/test.sh | 2 + golang/cosmos/app/upgrade.go | 38 +-- .../scripts/testing/add-USD-LEMONS.js | 22 +- 9 files changed, 472 insertions(+), 45 deletions(-) create mode 100644 a3p-integration/proposals/p:upgrade-19/provisionPool.test.js create mode 100644 a3p-integration/proposals/p:upgrade-19/test-lib/errors.js create mode 100644 a3p-integration/proposals/p:upgrade-19/test-lib/sync-tools.js diff --git a/a3p-integration/proposals/p:upgrade-19/.gitignore b/a3p-integration/proposals/p:upgrade-19/.gitignore index 17bb7d663e2..d348dadf7d9 100644 --- a/a3p-integration/proposals/p:upgrade-19/.gitignore +++ b/a3p-integration/proposals/p:upgrade-19/.gitignore @@ -1,2 +1,3 @@ replaceFeeDistributor/ testUpgradedBoard/ +addUsdLemons/ diff --git a/a3p-integration/proposals/p:upgrade-19/depositUSD-LEMONS/deposit-usd-lemons.js b/a3p-integration/proposals/p:upgrade-19/depositUSD-LEMONS/deposit-usd-lemons.js index 2d9a6f0650f..4a4a3c0313c 100644 --- a/a3p-integration/proposals/p:upgrade-19/depositUSD-LEMONS/deposit-usd-lemons.js +++ b/a3p-integration/proposals/p:upgrade-19/depositUSD-LEMONS/deposit-usd-lemons.js @@ -1,29 +1,29 @@ +/* eslint-disable no-undef */ const PROVISIONING_POOL_ADDR = 'agoric1megzytg65cyrgzs6fvzxgrcqvwwl7ugpt62346'; const depositUsdLemons = async powers => { const { - consume: { contractKits: contractKitsP, namesByAddressAdmin: namesByAddressAdminP , agoricNames }, - // instance: { consume: { ['psm-IST-USD_LEMONS']: usdLemonsPsmInstanceP }} + consume: { + contractKits: contractKitsP, + namesByAddressAdmin: namesByAddressAdminP, + agoricNames, + }, } = powers; const namesByAddressAdmin = await namesByAddressAdminP; const getDepositFacet = async address => { - const admin = await E(namesByAddressAdmin).lookupAdmin(address); - console.log('ADMIN', admin) - - const nameHub = await E(admin).readonly(); - console.log('NAME_HUB', nameHub); const hub = E(E(namesByAddressAdmin).lookupAdmin(address)).readonly(); return E(hub).lookup('depositFacet'); }; - const [contractKits, usdLemonsIssuer, usdLemonsBrand, ppDepositFacet] = await Promise.all([ - contractKitsP, - E(agoricNames).lookup('issuer', 'USD_LEMONS'), - E(agoricNames).lookup('brand', 'USD_LEMONS'), - getDepositFacet(PROVISIONING_POOL_ADDR), - ]); + const [contractKits, usdLemonsIssuer, usdLemonsBrand, ppDepositFacet] = + await Promise.all([ + contractKitsP, + E(agoricNames).lookup('issuer', 'USD_LEMONS'), + E(agoricNames).lookup('brand', 'USD_LEMONS'), + getDepositFacet(PROVISIONING_POOL_ADDR), + ]); console.log('[CONTRACT_KITS]', contractKits); console.log('[ISSUER]', usdLemonsIssuer); @@ -32,13 +32,15 @@ const depositUsdLemons = async powers => { for (const { publicFacet, creatorFacet: mint } of contractKits.values()) { if (publicFacet === usdLemonsIssuer) { usdLemonsMint = mint; - console.log('BINGO', mint) + console.log('BINGO', mint); break; } } console.log('Minting USD_LEMONS'); - const helloPayment = await E(usdLemonsMint).mintPayment(harden({ brand: usdLemonsBrand, value: 500000n })); + const helloPayment = await E(usdLemonsMint).mintPayment( + harden({ brand: usdLemonsBrand, value: 500000n }), + ); console.log('Funding provision pool...'); await E(ppDepositFacet).receive(helloPayment); diff --git a/a3p-integration/proposals/p:upgrade-19/package.json b/a3p-integration/proposals/p:upgrade-19/package.json index f3b062f3c76..9a18e4f658c 100644 --- a/a3p-integration/proposals/p:upgrade-19/package.json +++ b/a3p-integration/proposals/p:upgrade-19/package.json @@ -3,6 +3,7 @@ "type": "/agoric.swingset.CoreEvalProposal", "sdk-generate": [ "testing/replace-feeDistributor-short.js replaceFeeDistributor", + "testing/add-USD-LEMONS.js addUsdLemons", "vats/upgrade-paRegistry.js", "vats/upgrade-board.js", "testing/test-upgraded-board.js testUpgradedBoard" diff --git a/a3p-integration/proposals/p:upgrade-19/provisionPool.test.js b/a3p-integration/proposals/p:upgrade-19/provisionPool.test.js new file mode 100644 index 00000000000..df8511305d9 --- /dev/null +++ b/a3p-integration/proposals/p:upgrade-19/provisionPool.test.js @@ -0,0 +1,129 @@ +/* eslint-env node */ +/** + * @file The goal of this file is to make sure v28-provisionPool and v14-bank can be successfully + * upgraded. These vats are related because of the issues below; + * - https://github.com/Agoric/agoric-sdk/issues/8722 + * - https://github.com/Agoric/agoric-sdk/issues/8724 + * + * The test scenario is as follows; + * - Prerequisite: provisionPool and bank are already upgraded. See `upgrade.go` + * 1. Add a new account and successfully provision it + * - Observe new account's address under `published.wallet.${address}` + * 2. Send some USDC_axl to provisionPoolAddress and observe its IST balances increases accordingly + * 3. Introduce a new asset to the chain and start a PSM instance for the new asset + * 3a. Deposit some of that asset to provisionPoolAddress + * 3b. Observe provisionPoolAddress' IST balance increase by the amount deposited in step 3a + */ + +import '@endo/init'; +import test from 'ava'; +import { execFileSync } from 'node:child_process'; +import { + addUser, + makeAgd, + evalBundles, + agd as agdAmbient, + agoric, + bankSend, + getISTBalance, +} from '@agoric/synthetic-chain'; +import { NonNullish } from './test-lib/errors.js'; +import { + retryUntilCondition, + waitUntilAccountFunded, + waitUntilContractDeployed, +} from './test-lib/sync-tools.js'; + +const PROVISIONING_POOL_ADDR = 'agoric1megzytg65cyrgzs6fvzxgrcqvwwl7ugpt62346'; + +const ADD_PSM_DIR = 'addUsdLemons'; +const DEPOSIT_USD_LEMONS_DIR = 'depositUSD-LEMONS'; + +const USDC_DENOM = NonNullish(process.env.USDC_DENOM); + +const agd = makeAgd({ execFileSync }).withOpts({ keyringBackend: 'test' }); + +const ambientAuthority = { + query: agdAmbient.query, + follow: agoric.follow, + setTimeout, +}; + +const provision = (name, address) => + agd.tx(['swingset', 'provision-one', name, address, 'SMART_WALLET'], { + chainId: 'agoriclocal', + from: 'validator', + yes: true, + }); + +const introduceAndProvision = async name => { + const address = await addUser(name); + console.log('ADDR', name, address); + + const provisionP = provision(name, address); + + return { provisionP, address }; +}; + +const getProvisionedAddresses = async () => { + const { children } = await agd.query([ + 'vstorage', + 'children', + 'published.wallet', + ]); + return children; +}; + +const checkUserProvisioned = addr => + retryUntilCondition( + getProvisionedAddresses, + children => children.includes(addr), + 'Account not provisioned', + { maxRetries: 5, retryIntervalMs: 1000, log: console.log, setTimeout }, + ); + +test(`upgrade provision pool`, async t => { + // Introduce new user then provision + const { address } = await introduceAndProvision('provisionTester'); + await checkUserProvisioned(address); + + // Send USDC_axl to pp + const istBalanceBefore = await getISTBalance(PROVISIONING_POOL_ADDR); + await bankSend(PROVISIONING_POOL_ADDR, `500000${USDC_DENOM}`); + + // Check IST balance + await waitUntilAccountFunded( + PROVISIONING_POOL_ADDR, + ambientAuthority, + { denom: 'uist', value: istBalanceBefore + 500000 }, + { errorMessage: 'Provision pool not able to swap USDC_axl for IST.' }, + ); + + // Introduce USD_LEMONS + await evalBundles(ADD_PSM_DIR); + await waitUntilContractDeployed('psm-IST-USD_LEMONS', ambientAuthority, { + errorMessage: 'psm-IST-USD_LEMONS instance not observed.', + }); + + // Provision the provisionPoolAddress. This is a workaround of provisionPoolAddress + // not having a depositFacet published to namesByAddress. Shouldn't be a problem since + // vat-bank keeps track of virtual purses per address basis. We need there to be + // depositFacet for provisionPoolAddress since we'll fund it with USD_LEMONS + await provision('provisionPoolAddress', PROVISIONING_POOL_ADDR); + await checkUserProvisioned(PROVISIONING_POOL_ADDR); + + // Send USD_LEMONS to provisionPoolAddress + const istBalanceBeforeLemonsSent = await getISTBalance( + PROVISIONING_POOL_ADDR, + ); + await evalBundles(DEPOSIT_USD_LEMONS_DIR); + + // Check balance again + await waitUntilAccountFunded( + PROVISIONING_POOL_ADDR, + ambientAuthority, + { denom: 'uist', value: istBalanceBeforeLemonsSent + 500000 }, + { errorMessage: 'Provision pool not bale swap USDC_axl for IST.' }, + ); + t.pass(); +}); diff --git a/a3p-integration/proposals/p:upgrade-19/test-lib/errors.js b/a3p-integration/proposals/p:upgrade-19/test-lib/errors.js new file mode 100644 index 00000000000..57dc771e6a5 --- /dev/null +++ b/a3p-integration/proposals/p:upgrade-19/test-lib/errors.js @@ -0,0 +1,20 @@ +/** + * @file Copied from "@agoric/internal" + */ + +import { q } from '@endo/errors'; + +/** + * @template T + * @param {T | null | undefined} val + * @param {string} [optDetails] + * @returns {T} + */ +export const NonNullish = (val, optDetails = `unexpected ${q(val)}`) => { + if (val != null) { + // This `!= null` idiom checks that `val` is neither `null` nor `undefined`. + return val; + } + assert.fail(optDetails); +}; +harden(NonNullish); diff --git a/a3p-integration/proposals/p:upgrade-19/test-lib/sync-tools.js b/a3p-integration/proposals/p:upgrade-19/test-lib/sync-tools.js new file mode 100644 index 00000000000..dac2ba7e04f --- /dev/null +++ b/a3p-integration/proposals/p:upgrade-19/test-lib/sync-tools.js @@ -0,0 +1,272 @@ +/* eslint-env node */ + +/** + * @file The purpose of this file is to bring together a set of tools that + * developers can use to synchronize operations they carry out in their tests. + * + * These operations include; + * - Making sure a core-eval resulted in successfully deploying a contract + * - Making sure a core-eval successfully sent zoe invitations to committee members for governance + * - Making sure an account is successfully funded with vbank assets like IST, BLD etc. + * - operation: query dest account's balance + * - condition: dest account has a balance >= sent token + * - Making sure an offer resulted successfully + * + */ + +/** + * @typedef {object} RetryOptions + * @property {number} [maxRetries] + * @property {number} [retryIntervalMs] + * @property {(...arg0: string[]) => void} [log] + * @property {(callback: Function, delay: number) => void} [setTimeout] + * + * @typedef {RetryOptions & {errorMessage: string}} WaitUntilOptions + * + * @typedef {object} CosmosBalanceThreshold + * @property {string} denom + * @property {number} value + */ + +const ambientSetTimeout = global.setTimeout; + +/** + * From https://github.com/Agoric/agoric-sdk/blob/442f07c8f0af03281b52b90e90c27131eef6f331/multichain-testing/tools/sleep.ts#L10 + * + * @param {number} ms + * @param {*} sleepOptions + */ +export const sleep = (ms, { log = () => {}, setTimeout = ambientSetTimeout }) => + new Promise(resolve => { + log(`Sleeping for ${ms}ms...`); + setTimeout(resolve, ms); + }); + +/** + * From https://github.com/Agoric/agoric-sdk/blob/442f07c8f0af03281b52b90e90c27131eef6f331/multichain-testing/tools/sleep.ts#L24 + * + * @param {() => Promise} operation + * @param {(result: any) => boolean} condition + * @param {string} message + * @param {RetryOptions} options + */ +export const retryUntilCondition = async ( + operation, + condition, + message, + { maxRetries = 6, retryIntervalMs = 3500, log = console.log, setTimeout }, +) => { + console.log({ maxRetries, retryIntervalMs, message }); + let retries = 0; + + while (retries < maxRetries) { + try { + const result = await operation(); + log('RESULT', result); + if (condition(result)) { + return result; + } + } catch (error) { + if (error instanceof Error) { + log(`Error: ${error.message}`); + } else { + log(`Unknown error: ${String(error)}`); + } + } + + retries += 1; + console.log( + `Retry ${retries}/${maxRetries} - Waiting for ${retryIntervalMs}ms for ${message}...`, + ); + await sleep(retryIntervalMs, { log, setTimeout }); + } + + throw Error(`${message} condition failed after ${maxRetries} retries.`); +}; + +/** + * @param {WaitUntilOptions} options + */ +const overrideDefaultOptions = options => { + const defaultValues = { + maxRetries: 6, + retryIntervalMs: 3500, + log: console.log, + errorMessage: 'Error', + }; + + return { ...defaultValues, ...options }; +}; + +/// ////////// Making sure a core-eval resulted successfully deploying a contract ///////////// + +const makeGetInstances = follow => async () => { + const instanceEntries = await follow( + '-lF', + `:published.agoricNames.instance`, + ); + + return Object.fromEntries(instanceEntries); +}; + +/** + * + * @param {string} contractName + * @param {{follow: () => object, setTimeout: (object) => void}} ambientAuthority + * @param {WaitUntilOptions} options + */ +export const waitUntilContractDeployed = ( + contractName, + ambientAuthority, + options, +) => { + const { follow, setTimeout } = ambientAuthority; + const getInstances = makeGetInstances(follow); + const { maxRetries, retryIntervalMs, errorMessage, log } = + overrideDefaultOptions(options); + + return retryUntilCondition( + getInstances, + instanceObject => Object.keys(instanceObject).includes(contractName), + errorMessage, + { maxRetries, retryIntervalMs, log, setTimeout }, + ); +}; + +/// ////////// Making sure an account is successfully funded with vbank assets like IST, BLD etc. /////////////// + +const makeQueryCosmosBalance = queryCb => async dest => { + const coins = await queryCb('bank', 'balances', dest); + return coins.balances; +}; + +/** + * + * @param {Array} balances + * @param {CosmosBalanceThreshold} threshold + * @returns {boolean} + */ +const checkCosmosBalance = (balances, threshold) => { + const balance = [...balances].find(({ denom }) => denom === threshold.denom); + return Number(balance.amount) >= threshold.value; +}; + +/** + * @param {string} destAcct + * @param {{query: () => Promise, setTimeout: (object) => void}} ambientAuthority + * @param {{denom: string, value: number}} threshold + * @param {WaitUntilOptions} options + */ +export const waitUntilAccountFunded = ( + destAcct, + ambientAuthority, + threshold, + options, +) => { + const { query, setTimeout } = ambientAuthority; + const queryCosmosBalance = makeQueryCosmosBalance(query); + const { maxRetries, retryIntervalMs, errorMessage, log } = + overrideDefaultOptions(options); + + return retryUntilCondition( + async () => queryCosmosBalance(destAcct), + balances => checkCosmosBalance(balances, threshold), + errorMessage, + { maxRetries, retryIntervalMs, log, setTimeout }, + ); +}; + +/// ////////// Making sure an offers get results ///////////// + +const makeQueryWallet = follow => async (/** @type {string} */ addr) => { + const update = await follow('-lF', `:published.wallet.${addr}`); + + return update; +}; + +/** + * + * @param {object} offerStatus + * @param {boolean} waitForPayouts + * @param {string} offerId + */ +const checkOfferState = (offerStatus, waitForPayouts, offerId) => { + const { updated, status } = offerStatus; + + if (updated !== 'offerStatus') return false; + if (!status) return false; + if (status.id !== offerId) return false; + if (!status.numWantsSatisfied || status.numWantsSatisfied !== 1) return false; + if (waitForPayouts && status.payouts) return true; + if (!waitForPayouts && status.result) return true; + + return false; +}; + +/** + * + * @param {string} addr + * @param {string} offerId + * @param {boolean} waitForPayouts + * @param {{follow: () => object, setTimeout: (callback: Function, delay: number) => void}} ambientAuthority + * @param {WaitUntilOptions} options + */ +export const waitUntilOfferResult = ( + addr, + offerId, + waitForPayouts, + ambientAuthority, + options, +) => { + const { follow, setTimeout } = ambientAuthority; + const queryWallet = makeQueryWallet(follow); + const { maxRetries, retryIntervalMs, errorMessage, log } = + overrideDefaultOptions(options); + + return retryUntilCondition( + async () => queryWallet(addr), + status => checkOfferState(status, waitForPayouts, offerId), + errorMessage, + { maxRetries, retryIntervalMs, log, setTimeout }, + ); +}; + +/// ////////// Making sure a core-eval successfully sent zoe invitations to committee members for governance ///////////// + +/** + * + * @param {{ updated: string, currentAmount: any }} update + * @returns {boolean} + */ +const checkForInvitation = update => { + const { updated, currentAmount } = update; + + if (updated !== 'balance') return false; + if (!currentAmount || !currentAmount.brand) return false; + + return currentAmount.brand.includes('Invitation'); +}; + +/** + * + * @param {string} addr + * @param {{follow: () => object, setTimeout: (object) => void}} ambientAuthority + * @param {WaitUntilOptions} options + */ +export const waitUntilInvitationReceived = ( + addr, + ambientAuthority, + options, +) => { + const { follow, setTimeout } = ambientAuthority; + const queryWallet = makeQueryWallet(follow); + const { maxRetries, retryIntervalMs, errorMessage, log } = + overrideDefaultOptions(options); + + return retryUntilCondition( + async () => queryWallet(addr), + checkForInvitation, + errorMessage, + { maxRetries, retryIntervalMs, log, setTimeout }, + ); +}; diff --git a/a3p-integration/proposals/p:upgrade-19/test.sh b/a3p-integration/proposals/p:upgrade-19/test.sh index 056fe6836ac..055727518f8 100644 --- a/a3p-integration/proposals/p:upgrade-19/test.sh +++ b/a3p-integration/proposals/p:upgrade-19/test.sh @@ -2,3 +2,5 @@ yarn ava replaceFeeDistributor.test.js yarn ava upgradedBoard.test.js + +yarn ava provisionPool.test.js diff --git a/golang/cosmos/app/upgrade.go b/golang/cosmos/app/upgrade.go index 9f81d6bb0ca..2858370cf05 100644 --- a/golang/cosmos/app/upgrade.go +++ b/golang/cosmos/app/upgrade.go @@ -212,27 +212,27 @@ func unreleasedUpgradeHandler(app *GaiaApp, targetUpgrade string) func(sdk.Conte // Upgrade to include a cleanup from https://github.com/Agoric/agoric-sdk/pull/10319 "@agoric/builders/scripts/smart-wallet/build-wallet-factory2-upgrade.js", ), - vm.CoreProposalStepForModules( - "@agoric/builders/scripts/vats/upgrade-provisionPool.js", - ), - vm.CoreProposalStepForModules( - "@agoric/builders/scripts/vats/upgrade-bank.js", - ), ) - // // CoreProposals for Upgrade 19. These should not be introduced - // // before upgrade 18 is done because they would be run in n:upgrade-next - // CoreProposalSteps = append(CoreProposalSteps, - // vm.CoreProposalStepForModules( - // "@agoric/builders/scripts/inter-protocol/replace-feeDistributor.js", - // ), - // vm.CoreProposalStepForModules( - // "@agoric/builders/scripts/vats/upgrade-paRegistry.js", - // ), - // vm.CoreProposalStepForModules( - // "@agoric/builders/scripts/vats/upgrade-board.js", - // ), - // ) + // CoreProposals for Upgrade 19. These should not be introduced + // before upgrade 18 is done because they would be run in n:upgrade-next + // CoreProposalSteps = append(CoreProposalSteps, + // vm.CoreProposalStepForModules( + // "@agoric/builders/scripts/inter-protocol/replace-feeDistributor.js", + // ), + // vm.CoreProposalStepForModules( + // "@agoric/builders/scripts/vats/upgrade-paRegistry.js", + // ), + // vm.CoreProposalStepForModules( + // "@agoric/builders/scripts/vats/upgrade-board.js", + // ), + // vm.CoreProposalStepForModules( + // "@agoric/builders/scripts/vats/upgrade-provisionPool.js", + // ), + // vm.CoreProposalStepForModules( + // "@agoric/builders/scripts/vats/upgrade-bank.js", + // ), + // ) } app.upgradeDetails = &upgradeDetails{ diff --git a/packages/builders/scripts/testing/add-USD-LEMONS.js b/packages/builders/scripts/testing/add-USD-LEMONS.js index 89afc1279cb..ed548b5561c 100644 --- a/packages/builders/scripts/testing/add-USD-LEMONS.js +++ b/packages/builders/scripts/testing/add-USD-LEMONS.js @@ -2,18 +2,18 @@ import { makeHelpers } from '@agoric/deploy-script-support'; import { psmProposalBuilder } from '../inter-protocol/add-collateral-core.js'; const addUsdLemonsProposalBuilder = async powers => { - return psmProposalBuilder(powers, { - anchorOptions: { - denom: 'ibc/000C0AAAEECAFE000', - keyword: 'USD_LEMONS', - decimalPlaces: 6, - proposedName: 'USD_LEMONS', - } - }); + return psmProposalBuilder(powers, { + anchorOptions: { + denom: 'ibc/000C0AAAEECAFE000', + keyword: 'USD_LEMONS', + decimalPlaces: 6, + proposedName: 'USD_LEMONS', + }, + }); }; /** @type {import('@agoric/deploy-script-support/src/externalTypes.js').DeployScriptFunction} */ export default async (homeP, endowments) => { - const { writeCoreEval } = await makeHelpers(homeP, endowments); - await writeCoreEval('add-LEMONS-PSM', addUsdLemonsProposalBuilder); - }; \ No newline at end of file + const { writeCoreEval } = await makeHelpers(homeP, endowments); + await writeCoreEval('add-LEMONS-PSM', addUsdLemonsProposalBuilder); +}; From 164151ecf34ae08b217817e970da1c8d64f763cb Mon Sep 17 00:00:00 2001 From: anilhelvaci Date: Mon, 25 Nov 2024 23:31:46 +0300 Subject: [PATCH 04/56] chore: make provisionBridgeHandler durable Make sure the handler returned from E(creatorFacet).makeHandler() is durable and provisionPool is upgradable multiple times. Refs: #10425 Refs: #10564 fix: remove unnecessary comment chore: get rid of ephemera, address change requests Refs: #10395 Refs: #10425 fix: drop trace chore: address change requests fix: rebase fixes fix: yarn.lock fix fix: bring back missing upgrade-paRegistry proposal --- .../proposals/p:upgrade-19/.gitignore | 1 + .../depositUSD-LEMONS/deposit-usd-lemons.js | 1 + .../nullUpgradePP/null-upgrade-pp-permit.json | 7 + .../nullUpgradePP/null-upgrade-pp.js | 38 +++ .../proposals/p:upgrade-19/package.json | 2 + .../p:upgrade-19/provisionPool.test.js | 215 +++++++++----- .../proposals/p:upgrade-19/test-lib/errors.js | 20 -- .../test-lib/provision-helpers.js | 56 ++++ .../p:upgrade-19/test-lib/sync-tools.js | 272 ------------------ .../proposals/p:upgrade-19/tsconfig.json | 7 +- .../proposals/p:upgrade-19/yarn.lock | 53 +++- .../proposals/z:acceptance/yarn.lock | 1 + packages/inter-protocol/package.json | 2 +- packages/inter-protocol/src/provisionPool.js | 12 +- .../inter-protocol/src/provisionPoolKit.js | 134 +++++---- .../inter-protocol/test/provisionPool.test.js | 16 +- .../upgrade-provisionPool-proposal.js | 15 +- 17 files changed, 398 insertions(+), 454 deletions(-) create mode 100644 a3p-integration/proposals/p:upgrade-19/nullUpgradePP/null-upgrade-pp-permit.json create mode 100644 a3p-integration/proposals/p:upgrade-19/nullUpgradePP/null-upgrade-pp.js delete mode 100644 a3p-integration/proposals/p:upgrade-19/test-lib/errors.js create mode 100644 a3p-integration/proposals/p:upgrade-19/test-lib/provision-helpers.js delete mode 100644 a3p-integration/proposals/p:upgrade-19/test-lib/sync-tools.js diff --git a/a3p-integration/proposals/p:upgrade-19/.gitignore b/a3p-integration/proposals/p:upgrade-19/.gitignore index d348dadf7d9..80f57c98cb2 100644 --- a/a3p-integration/proposals/p:upgrade-19/.gitignore +++ b/a3p-integration/proposals/p:upgrade-19/.gitignore @@ -1,3 +1,4 @@ replaceFeeDistributor/ testUpgradedBoard/ addUsdLemons/ +upgradeProvisionPool/ diff --git a/a3p-integration/proposals/p:upgrade-19/depositUSD-LEMONS/deposit-usd-lemons.js b/a3p-integration/proposals/p:upgrade-19/depositUSD-LEMONS/deposit-usd-lemons.js index 4a4a3c0313c..c7ee0db948f 100644 --- a/a3p-integration/proposals/p:upgrade-19/depositUSD-LEMONS/deposit-usd-lemons.js +++ b/a3p-integration/proposals/p:upgrade-19/depositUSD-LEMONS/deposit-usd-lemons.js @@ -1,3 +1,4 @@ +// @ts-nocheck /* eslint-disable no-undef */ const PROVISIONING_POOL_ADDR = 'agoric1megzytg65cyrgzs6fvzxgrcqvwwl7ugpt62346'; diff --git a/a3p-integration/proposals/p:upgrade-19/nullUpgradePP/null-upgrade-pp-permit.json b/a3p-integration/proposals/p:upgrade-19/nullUpgradePP/null-upgrade-pp-permit.json new file mode 100644 index 00000000000..668a9c7f0d5 --- /dev/null +++ b/a3p-integration/proposals/p:upgrade-19/nullUpgradePP/null-upgrade-pp-permit.json @@ -0,0 +1,7 @@ +{ + "consume": { + "provisionPoolStartResult": true, + "instancePrivateArgs": true, + "economicCommitteeCreatorFacet": true + } +} diff --git a/a3p-integration/proposals/p:upgrade-19/nullUpgradePP/null-upgrade-pp.js b/a3p-integration/proposals/p:upgrade-19/nullUpgradePP/null-upgrade-pp.js new file mode 100644 index 00000000000..be3fdc96b3d --- /dev/null +++ b/a3p-integration/proposals/p:upgrade-19/nullUpgradePP/null-upgrade-pp.js @@ -0,0 +1,38 @@ +// @ts-nocheck +/* eslint-disable no-undef */ +const nullUpgradePP = async powers => { + const { + consume: { + provisionPoolStartResult: provisionPoolStartResultP, + instancePrivateArgs: instancePrivateArgsP, + economicCommitteeCreatorFacet, + }, + } = powers; + + console.log('awaiting powers'); + const { adminFacet, instance } = await provisionPoolStartResultP; + const instancePrivateArgs = await instancePrivateArgsP; + + console.log('get privateArgs'); + const privateArgs = instancePrivateArgs.get(instance); + const [poolBank, poserInvitation] = await Promise.all([ + privateArgs.poolBank, + E(economicCommitteeCreatorFacet).getPoserInvitation(), + ]); + + console.log('DEBUG', { + adminFacet, + instance, + privateArgs, + poserInvitation, + }); + + await E(adminFacet).restartContract({ + ...privateArgs, + poolBank, + initialPoserInvitation: poserInvitation, + }); + console.log('Done'); +}; + +nullUpgradePP; diff --git a/a3p-integration/proposals/p:upgrade-19/package.json b/a3p-integration/proposals/p:upgrade-19/package.json index 9a18e4f658c..6848af6d060 100644 --- a/a3p-integration/proposals/p:upgrade-19/package.json +++ b/a3p-integration/proposals/p:upgrade-19/package.json @@ -4,6 +4,7 @@ "sdk-generate": [ "testing/replace-feeDistributor-short.js replaceFeeDistributor", "testing/add-USD-LEMONS.js addUsdLemons", + "vats/upgrade-provisionPool.js upgradeProvisionPool", "vats/upgrade-paRegistry.js", "vats/upgrade-board.js", "testing/test-upgraded-board.js testUpgradedBoard" @@ -14,6 +15,7 @@ "dependencies": { "@agoric/client-utils": "0.1.1-dev-02c06c4.0", "@agoric/ertp": "dev", + "@agoric/internal": "dev", "@agoric/synthetic-chain": "^0.4.3", "@agoric/zoe": "dev", "@endo/errors": "1.2.7", diff --git a/a3p-integration/proposals/p:upgrade-19/provisionPool.test.js b/a3p-integration/proposals/p:upgrade-19/provisionPool.test.js index df8511305d9..12934603921 100644 --- a/a3p-integration/proposals/p:upgrade-19/provisionPool.test.js +++ b/a3p-integration/proposals/p:upgrade-19/provisionPool.test.js @@ -6,124 +6,181 @@ * - https://github.com/Agoric/agoric-sdk/issues/8724 * * The test scenario is as follows; - * - Prerequisite: provisionPool and bank are already upgraded. See `upgrade.go` - * 1. Add a new account and successfully provision it - * - Observe new account's address under `published.wallet.${address}` - * 2. Send some USDC_axl to provisionPoolAddress and observe its IST balances increases accordingly - * 3. Introduce a new asset to the chain and start a PSM instance for the new asset - * 3a. Deposit some of that asset to provisionPoolAddress - * 3b. Observe provisionPoolAddress' IST balance increase by the amount deposited in step 3a + * 1. Upgrade provisionPool. This upgrade overrides provisionWalletBridgerManager with a durable one + * 2. Add a new account and successfully provision it + * - Observe new account's address under `published.wallet.${address}` + * 3. Send some USDC_axl to provisionPoolAddress and observe its IST balances increases accordingly + * 4. Introduce a new asset to the chain and start a PSM instance for the new asset + * 4a. Deposit some of that asset to provisionPoolAddress + * 4b. Observe provisionPoolAddress' IST balance increase by the amount deposited in step 4a + * 5. Perform a null upgrade for provisionPool. This upgrade does NOT override provisionWalletBridgerManager + * - The goal here is to allow testing the bridgeHandler from the first upgrade is in fact durable + * 6. Auto provision + * 6a. Introduce a new account + * 6b. Fund it with IST and ATOM to be able to open a vault + * 6c. Try to open a vault WITHOUT provisioning the newly introduced account + * 6d. Observe the new account's address under `published.wallet` + * 7. Same as step 2. Checks manual provision works after null upgrade */ import '@endo/init'; import test from 'ava'; -import { execFileSync } from 'node:child_process'; import { addUser, - makeAgd, evalBundles, agd as agdAmbient, agoric, - bankSend, getISTBalance, + getDetailsMatchingVats, + GOV1ADDR, + openVault, + ATOM_DENOM, } from '@agoric/synthetic-chain'; -import { NonNullish } from './test-lib/errors.js'; import { - retryUntilCondition, + makeVstorageKit, waitUntilAccountFunded, waitUntilContractDeployed, -} from './test-lib/sync-tools.js'; +} from '@agoric/client-utils'; +import { NonNullish } from '@agoric/internal'; +import { + bankSend, + checkUserProvisioned, + introduceAndProvision, + provision, +} from './test-lib/provision-helpers.js'; const PROVISIONING_POOL_ADDR = 'agoric1megzytg65cyrgzs6fvzxgrcqvwwl7ugpt62346'; const ADD_PSM_DIR = 'addUsdLemons'; const DEPOSIT_USD_LEMONS_DIR = 'depositUSD-LEMONS'; +const UPGRADE_PP_DIR = 'upgradeProvisionPool'; +const NULL_UPGRADE_PP_DIR = 'nullUpgradePP'; const USDC_DENOM = NonNullish(process.env.USDC_DENOM); -const agd = makeAgd({ execFileSync }).withOpts({ keyringBackend: 'test' }); - const ambientAuthority = { query: agdAmbient.query, follow: agoric.follow, setTimeout, + log: console.log, }; -const provision = (name, address) => - agd.tx(['swingset', 'provision-one', name, address, 'SMART_WALLET'], { - chainId: 'agoriclocal', - from: 'validator', - yes: true, - }); +test.before(async t => { + const vstorageKit = await makeVstorageKit( + { fetch }, + { rpcAddrs: ['http://localhost:26657'], chainName: 'agoriclocal' }, + ); -const introduceAndProvision = async name => { - const address = await addUser(name); - console.log('ADDR', name, address); + t.context = { + vstorageKit, + }; +}); - const provisionP = provision(name, address); +test.serial('upgrade provisionPool', async t => { + await evalBundles(UPGRADE_PP_DIR); - return { provisionP, address }; -}; + const vatDetailsAfter = await getDetailsMatchingVats('provisionPool'); + const { incarnation } = vatDetailsAfter.find(vat => + vat.vatName.endsWith('provisionPool'), + ); -const getProvisionedAddresses = async () => { - const { children } = await agd.query([ - 'vstorage', - 'children', - 'published.wallet', - ]); - return children; -}; + t.log(vatDetailsAfter); + t.is(incarnation, 1, 'incorrect incarnation'); + t.pass(); +}); -const checkUserProvisioned = addr => - retryUntilCondition( - getProvisionedAddresses, - children => children.includes(addr), - 'Account not provisioned', - { maxRetries: 5, retryIntervalMs: 1000, log: console.log, setTimeout }, - ); +test.serial( + `check provisionPool can recover purse and asset subscribers after upgrade`, + async t => { + // @ts-expect-error casting + const { vstorageKit } = t.context; + + // Introduce new user then provision + const { address } = await introduceAndProvision('provisionTester'); + await checkUserProvisioned(address, vstorageKit); + + // Send USDC_axl to pp + const istBalanceBefore = await getISTBalance(PROVISIONING_POOL_ADDR); + await bankSend(PROVISIONING_POOL_ADDR, `500000${USDC_DENOM}`); + + // Check IST balance + await waitUntilAccountFunded( + PROVISIONING_POOL_ADDR, + ambientAuthority, + { denom: 'uist', value: istBalanceBefore + 500000 }, + { errorMessage: 'Provision pool not able to swap USDC_axl for IST.' }, + ); + + // Introduce USD_LEMONS + await evalBundles(ADD_PSM_DIR); + await waitUntilContractDeployed('psm-IST-USD_LEMONS', ambientAuthority, { + errorMessage: 'psm-IST-USD_LEMONS instance not observed.', + }); + + // Provision the provisionPoolAddress. This is a workaround of provisionPoolAddress + // not having a depositFacet published to namesByAddress. Shouldn't be a problem since + // vat-bank keeps track of virtual purses per address basis. We need there to be + // depositFacet for provisionPoolAddress since we'll fund it with USD_LEMONS + await provision('provisionPoolAddress', PROVISIONING_POOL_ADDR); + await checkUserProvisioned(PROVISIONING_POOL_ADDR, vstorageKit); + + // Send USD_LEMONS to provisionPoolAddress + const istBalanceBeforeLemonsSent = await getISTBalance( + PROVISIONING_POOL_ADDR, + ); + await evalBundles(DEPOSIT_USD_LEMONS_DIR); + + // Check balance again + await waitUntilAccountFunded( + PROVISIONING_POOL_ADDR, + ambientAuthority, + { denom: 'uist', value: istBalanceBeforeLemonsSent + 500000 }, + { errorMessage: 'Provision pool not able to swap USDC_axl for IST.' }, + ); + t.pass(); + }, +); + +test.serial('null upgrade', async t => { + await evalBundles(NULL_UPGRADE_PP_DIR); + + const vatDetailsAfter = await getDetailsMatchingVats('provisionPool'); + const { incarnation } = vatDetailsAfter.find(vat => vat.vatID === 'v28'); // provisionPool is v28 + + t.log(vatDetailsAfter); + t.is(incarnation, 2, 'incorrect incarnation'); + t.pass(); +}); -test(`upgrade provision pool`, async t => { - // Introduce new user then provision - const { address } = await introduceAndProvision('provisionTester'); - await checkUserProvisioned(address); +test.serial('auto provision', async t => { + // @ts-expect-error casting + const { vstorageKit } = t.context; - // Send USDC_axl to pp - const istBalanceBefore = await getISTBalance(PROVISIONING_POOL_ADDR); - await bankSend(PROVISIONING_POOL_ADDR, `500000${USDC_DENOM}`); + const address = await addUser('automaticallyProvisioned'); + console.log('ADDR', 'automaticallyProvisioned', address); - // Check IST balance + await bankSend(address, `50000000${ATOM_DENOM}`); + // some ist is needed for opening a new vault + await bankSend(address, `10000000uist`, GOV1ADDR); await waitUntilAccountFunded( - PROVISIONING_POOL_ADDR, - ambientAuthority, - { denom: 'uist', value: istBalanceBefore + 500000 }, - { errorMessage: 'Provision pool not able to swap USDC_axl for IST.' }, + address, + // TODO: drop agd.query and switch to vstorgeKit + { log: console.log, setTimeout, query: agdAmbient.query }, + { denom: ATOM_DENOM, value: 50_000_000 }, + { errorMessage: `not able to fund ${address}` }, ); - // Introduce USD_LEMONS - await evalBundles(ADD_PSM_DIR); - await waitUntilContractDeployed('psm-IST-USD_LEMONS', ambientAuthority, { - errorMessage: 'psm-IST-USD_LEMONS instance not observed.', - }); - - // Provision the provisionPoolAddress. This is a workaround of provisionPoolAddress - // not having a depositFacet published to namesByAddress. Shouldn't be a problem since - // vat-bank keeps track of virtual purses per address basis. We need there to be - // depositFacet for provisionPoolAddress since we'll fund it with USD_LEMONS - await provision('provisionPoolAddress', PROVISIONING_POOL_ADDR); - await checkUserProvisioned(PROVISIONING_POOL_ADDR); - - // Send USD_LEMONS to provisionPoolAddress - const istBalanceBeforeLemonsSent = await getISTBalance( - PROVISIONING_POOL_ADDR, - ); - await evalBundles(DEPOSIT_USD_LEMONS_DIR); + await openVault(address, '10.0', '20.0'); + await checkUserProvisioned(address, vstorageKit); + t.pass(); +}); - // Check balance again - await waitUntilAccountFunded( - PROVISIONING_POOL_ADDR, - ambientAuthority, - { denom: 'uist', value: istBalanceBeforeLemonsSent + 500000 }, - { errorMessage: 'Provision pool not bale swap USDC_axl for IST.' }, - ); +test.serial('manual provision', async t => { + // @ts-expect-error casting + const { vstorageKit } = t.context; + + const { address } = await introduceAndProvision('manuallyProvisioned'); + await checkUserProvisioned(address, vstorageKit); + t.log('manuallyProvisioned address:', address); t.pass(); }); diff --git a/a3p-integration/proposals/p:upgrade-19/test-lib/errors.js b/a3p-integration/proposals/p:upgrade-19/test-lib/errors.js deleted file mode 100644 index 57dc771e6a5..00000000000 --- a/a3p-integration/proposals/p:upgrade-19/test-lib/errors.js +++ /dev/null @@ -1,20 +0,0 @@ -/** - * @file Copied from "@agoric/internal" - */ - -import { q } from '@endo/errors'; - -/** - * @template T - * @param {T | null | undefined} val - * @param {string} [optDetails] - * @returns {T} - */ -export const NonNullish = (val, optDetails = `unexpected ${q(val)}`) => { - if (val != null) { - // This `!= null` idiom checks that `val` is neither `null` nor `undefined`. - return val; - } - assert.fail(optDetails); -}; -harden(NonNullish); diff --git a/a3p-integration/proposals/p:upgrade-19/test-lib/provision-helpers.js b/a3p-integration/proposals/p:upgrade-19/test-lib/provision-helpers.js new file mode 100644 index 00000000000..1a8eabee12c --- /dev/null +++ b/a3p-integration/proposals/p:upgrade-19/test-lib/provision-helpers.js @@ -0,0 +1,56 @@ +/* eslint-env node */ +import { retryUntilCondition } from '@agoric/client-utils'; +import { + addUser, + CHAINID, + makeAgd, + VALIDATORADDR, +} from '@agoric/synthetic-chain'; +import { execFileSync } from 'node:child_process'; + +const agd = makeAgd({ execFileSync }).withOpts({ keyringBackend: 'test' }); + +/** + * @param {string} addr + * @param {string} wanted + * @param {string} [from] + */ +export const bankSend = (addr, wanted, from = VALIDATORADDR) => { + return agd.tx(['bank', 'send', from, addr, wanted], { + chainId: CHAINID, + from, + yes: true, + }); +}; + +export const provision = (name, address) => + agd.tx(['swingset', 'provision-one', name, address, 'SMART_WALLET'], { + chainId: 'agoriclocal', + from: 'validator', + yes: true, + }); + +export const introduceAndProvision = async name => { + const address = await addUser(name); + console.log('ADDR', name, address); + + const provisionP = provision(name, address); + + return { provisionP, address }; +}; + +/** + * @param {import('@agoric/client-utils').VstorageKit} vstorageKit + */ +export const getProvisionedAddresses = async vstorageKit => { + const children = await vstorageKit.vstorage.keys('published.wallet'); + return children; +}; + +export const checkUserProvisioned = (addr, vstorageKit) => + retryUntilCondition( + () => getProvisionedAddresses(vstorageKit), + children => children.includes(addr), + 'Account not provisioned', + { maxRetries: 5, retryIntervalMs: 1000, log: console.log, setTimeout }, + ); diff --git a/a3p-integration/proposals/p:upgrade-19/test-lib/sync-tools.js b/a3p-integration/proposals/p:upgrade-19/test-lib/sync-tools.js deleted file mode 100644 index dac2ba7e04f..00000000000 --- a/a3p-integration/proposals/p:upgrade-19/test-lib/sync-tools.js +++ /dev/null @@ -1,272 +0,0 @@ -/* eslint-env node */ - -/** - * @file The purpose of this file is to bring together a set of tools that - * developers can use to synchronize operations they carry out in their tests. - * - * These operations include; - * - Making sure a core-eval resulted in successfully deploying a contract - * - Making sure a core-eval successfully sent zoe invitations to committee members for governance - * - Making sure an account is successfully funded with vbank assets like IST, BLD etc. - * - operation: query dest account's balance - * - condition: dest account has a balance >= sent token - * - Making sure an offer resulted successfully - * - */ - -/** - * @typedef {object} RetryOptions - * @property {number} [maxRetries] - * @property {number} [retryIntervalMs] - * @property {(...arg0: string[]) => void} [log] - * @property {(callback: Function, delay: number) => void} [setTimeout] - * - * @typedef {RetryOptions & {errorMessage: string}} WaitUntilOptions - * - * @typedef {object} CosmosBalanceThreshold - * @property {string} denom - * @property {number} value - */ - -const ambientSetTimeout = global.setTimeout; - -/** - * From https://github.com/Agoric/agoric-sdk/blob/442f07c8f0af03281b52b90e90c27131eef6f331/multichain-testing/tools/sleep.ts#L10 - * - * @param {number} ms - * @param {*} sleepOptions - */ -export const sleep = (ms, { log = () => {}, setTimeout = ambientSetTimeout }) => - new Promise(resolve => { - log(`Sleeping for ${ms}ms...`); - setTimeout(resolve, ms); - }); - -/** - * From https://github.com/Agoric/agoric-sdk/blob/442f07c8f0af03281b52b90e90c27131eef6f331/multichain-testing/tools/sleep.ts#L24 - * - * @param {() => Promise} operation - * @param {(result: any) => boolean} condition - * @param {string} message - * @param {RetryOptions} options - */ -export const retryUntilCondition = async ( - operation, - condition, - message, - { maxRetries = 6, retryIntervalMs = 3500, log = console.log, setTimeout }, -) => { - console.log({ maxRetries, retryIntervalMs, message }); - let retries = 0; - - while (retries < maxRetries) { - try { - const result = await operation(); - log('RESULT', result); - if (condition(result)) { - return result; - } - } catch (error) { - if (error instanceof Error) { - log(`Error: ${error.message}`); - } else { - log(`Unknown error: ${String(error)}`); - } - } - - retries += 1; - console.log( - `Retry ${retries}/${maxRetries} - Waiting for ${retryIntervalMs}ms for ${message}...`, - ); - await sleep(retryIntervalMs, { log, setTimeout }); - } - - throw Error(`${message} condition failed after ${maxRetries} retries.`); -}; - -/** - * @param {WaitUntilOptions} options - */ -const overrideDefaultOptions = options => { - const defaultValues = { - maxRetries: 6, - retryIntervalMs: 3500, - log: console.log, - errorMessage: 'Error', - }; - - return { ...defaultValues, ...options }; -}; - -/// ////////// Making sure a core-eval resulted successfully deploying a contract ///////////// - -const makeGetInstances = follow => async () => { - const instanceEntries = await follow( - '-lF', - `:published.agoricNames.instance`, - ); - - return Object.fromEntries(instanceEntries); -}; - -/** - * - * @param {string} contractName - * @param {{follow: () => object, setTimeout: (object) => void}} ambientAuthority - * @param {WaitUntilOptions} options - */ -export const waitUntilContractDeployed = ( - contractName, - ambientAuthority, - options, -) => { - const { follow, setTimeout } = ambientAuthority; - const getInstances = makeGetInstances(follow); - const { maxRetries, retryIntervalMs, errorMessage, log } = - overrideDefaultOptions(options); - - return retryUntilCondition( - getInstances, - instanceObject => Object.keys(instanceObject).includes(contractName), - errorMessage, - { maxRetries, retryIntervalMs, log, setTimeout }, - ); -}; - -/// ////////// Making sure an account is successfully funded with vbank assets like IST, BLD etc. /////////////// - -const makeQueryCosmosBalance = queryCb => async dest => { - const coins = await queryCb('bank', 'balances', dest); - return coins.balances; -}; - -/** - * - * @param {Array} balances - * @param {CosmosBalanceThreshold} threshold - * @returns {boolean} - */ -const checkCosmosBalance = (balances, threshold) => { - const balance = [...balances].find(({ denom }) => denom === threshold.denom); - return Number(balance.amount) >= threshold.value; -}; - -/** - * @param {string} destAcct - * @param {{query: () => Promise, setTimeout: (object) => void}} ambientAuthority - * @param {{denom: string, value: number}} threshold - * @param {WaitUntilOptions} options - */ -export const waitUntilAccountFunded = ( - destAcct, - ambientAuthority, - threshold, - options, -) => { - const { query, setTimeout } = ambientAuthority; - const queryCosmosBalance = makeQueryCosmosBalance(query); - const { maxRetries, retryIntervalMs, errorMessage, log } = - overrideDefaultOptions(options); - - return retryUntilCondition( - async () => queryCosmosBalance(destAcct), - balances => checkCosmosBalance(balances, threshold), - errorMessage, - { maxRetries, retryIntervalMs, log, setTimeout }, - ); -}; - -/// ////////// Making sure an offers get results ///////////// - -const makeQueryWallet = follow => async (/** @type {string} */ addr) => { - const update = await follow('-lF', `:published.wallet.${addr}`); - - return update; -}; - -/** - * - * @param {object} offerStatus - * @param {boolean} waitForPayouts - * @param {string} offerId - */ -const checkOfferState = (offerStatus, waitForPayouts, offerId) => { - const { updated, status } = offerStatus; - - if (updated !== 'offerStatus') return false; - if (!status) return false; - if (status.id !== offerId) return false; - if (!status.numWantsSatisfied || status.numWantsSatisfied !== 1) return false; - if (waitForPayouts && status.payouts) return true; - if (!waitForPayouts && status.result) return true; - - return false; -}; - -/** - * - * @param {string} addr - * @param {string} offerId - * @param {boolean} waitForPayouts - * @param {{follow: () => object, setTimeout: (callback: Function, delay: number) => void}} ambientAuthority - * @param {WaitUntilOptions} options - */ -export const waitUntilOfferResult = ( - addr, - offerId, - waitForPayouts, - ambientAuthority, - options, -) => { - const { follow, setTimeout } = ambientAuthority; - const queryWallet = makeQueryWallet(follow); - const { maxRetries, retryIntervalMs, errorMessage, log } = - overrideDefaultOptions(options); - - return retryUntilCondition( - async () => queryWallet(addr), - status => checkOfferState(status, waitForPayouts, offerId), - errorMessage, - { maxRetries, retryIntervalMs, log, setTimeout }, - ); -}; - -/// ////////// Making sure a core-eval successfully sent zoe invitations to committee members for governance ///////////// - -/** - * - * @param {{ updated: string, currentAmount: any }} update - * @returns {boolean} - */ -const checkForInvitation = update => { - const { updated, currentAmount } = update; - - if (updated !== 'balance') return false; - if (!currentAmount || !currentAmount.brand) return false; - - return currentAmount.brand.includes('Invitation'); -}; - -/** - * - * @param {string} addr - * @param {{follow: () => object, setTimeout: (object) => void}} ambientAuthority - * @param {WaitUntilOptions} options - */ -export const waitUntilInvitationReceived = ( - addr, - ambientAuthority, - options, -) => { - const { follow, setTimeout } = ambientAuthority; - const queryWallet = makeQueryWallet(follow); - const { maxRetries, retryIntervalMs, errorMessage, log } = - overrideDefaultOptions(options); - - return retryUntilCondition( - async () => queryWallet(addr), - checkForInvitation, - errorMessage, - { maxRetries, retryIntervalMs, log, setTimeout }, - ); -}; diff --git a/a3p-integration/proposals/p:upgrade-19/tsconfig.json b/a3p-integration/proposals/p:upgrade-19/tsconfig.json index 960c1f4587a..23a6b14091b 100644 --- a/a3p-integration/proposals/p:upgrade-19/tsconfig.json +++ b/a3p-integration/proposals/p:upgrade-19/tsconfig.json @@ -11,5 +11,10 @@ "noImplicitThis": true, // XXX synthetic-chain has some errors "skipLibCheck": true - } + }, + "exclude": [ + "addUsdLemons/", + "replaceFeeDistributor/", + "upgradeProvisionPool/" + ] } diff --git a/a3p-integration/proposals/p:upgrade-19/yarn.lock b/a3p-integration/proposals/p:upgrade-19/yarn.lock index f74d4368e0e..e795ff2f376 100644 --- a/a3p-integration/proposals/p:upgrade-19/yarn.lock +++ b/a3p-integration/proposals/p:upgrade-19/yarn.lock @@ -31,6 +31,21 @@ __metadata: languageName: node linkType: hard +"@agoric/base-zone@npm:0.1.1-dev-1dd4589.0+1dd4589": + version: 0.1.1-dev-1dd4589.0 + resolution: "@agoric/base-zone@npm:0.1.1-dev-1dd4589.0" + dependencies: + "@agoric/store": "npm:0.9.3-dev-1dd4589.0+1dd4589" + "@endo/common": "npm:^1.2.8" + "@endo/errors": "npm:^1.2.8" + "@endo/exo": "npm:^1.5.7" + "@endo/far": "npm:^1.1.9" + "@endo/pass-style": "npm:^1.4.7" + "@endo/patterns": "npm:^1.4.7" + checksum: 10c0/d0c214a7e69b427df1632d1ac10bc97f977823d723e4696ad8cf92a0eb9dd6297142ce4b98ae211c994547c43380c9a6487959a1719f7ee90fb128a00e5ff669 + languageName: node + linkType: hard + "@agoric/base-zone@npm:0.1.1-dev-3b799b8.0+3b799b8": version: 0.1.1-dev-3b799b8.0 resolution: "@agoric/base-zone@npm:0.1.1-dev-3b799b8.0" @@ -200,6 +215,26 @@ __metadata: languageName: node linkType: hard +"@agoric/internal@npm:dev": + version: 0.3.3-dev-1dd4589.0 + resolution: "@agoric/internal@npm:0.3.3-dev-1dd4589.0" + dependencies: + "@agoric/base-zone": "npm:0.1.1-dev-1dd4589.0+1dd4589" + "@endo/common": "npm:^1.2.8" + "@endo/errors": "npm:^1.2.8" + "@endo/far": "npm:^1.1.9" + "@endo/init": "npm:^1.1.7" + "@endo/marshal": "npm:^1.6.2" + "@endo/pass-style": "npm:^1.4.7" + "@endo/patterns": "npm:^1.4.7" + "@endo/promise-kit": "npm:^1.1.8" + "@endo/stream": "npm:^1.2.8" + anylogger: "npm:^0.21.0" + jessie.js: "npm:^0.3.4" + checksum: 10c0/eb261f7bde265f168698c9da04af7458e2747fd54e945cdef82b822af5749e8a9443bb827bbace959269a04ae58d33c4ea465c31b580bf8d07b15fa87cb80ca3 + languageName: node + linkType: hard + "@agoric/kmarshal@npm:0.1.1-dev-02c06c4.0+02c06c4": version: 0.1.1-dev-02c06c4.0 resolution: "@agoric/kmarshal@npm:0.1.1-dev-02c06c4.0" @@ -305,6 +340,19 @@ __metadata: languageName: node linkType: hard +"@agoric/store@npm:0.9.3-dev-1dd4589.0+1dd4589": + version: 0.9.3-dev-1dd4589.0 + resolution: "@agoric/store@npm:0.9.3-dev-1dd4589.0" + dependencies: + "@endo/errors": "npm:^1.2.8" + "@endo/exo": "npm:^1.5.7" + "@endo/marshal": "npm:^1.6.2" + "@endo/pass-style": "npm:^1.4.7" + "@endo/patterns": "npm:^1.4.7" + checksum: 10c0/72d2c3ff3cb0d8b48f06146e4deb0967273e10a86ec7c01e7bc176c5e1ab31d016b909bde1230c8f031ba60552c31ee7d0eccb5791985fc12330fdb6dcda5edb + languageName: node + linkType: hard + "@agoric/store@npm:0.9.3-dev-3b799b8.0+3b799b8": version: 0.9.3-dev-3b799b8.0 resolution: "@agoric/store@npm:0.9.3-dev-3b799b8.0" @@ -1096,7 +1144,7 @@ __metadata: languageName: node linkType: hard -"@endo/exo@npm:^1.5.6": +"@endo/exo@npm:^1.5.6, @endo/exo@npm:^1.5.7": version: 1.5.7 resolution: "@endo/exo@npm:1.5.7" dependencies: @@ -1238,7 +1286,7 @@ __metadata: languageName: node linkType: hard -"@endo/stream@npm:^1.2.7": +"@endo/stream@npm:^1.2.7, @endo/stream@npm:^1.2.8": version: 1.2.8 resolution: "@endo/stream@npm:1.2.8" dependencies: @@ -5203,6 +5251,7 @@ __metadata: dependencies: "@agoric/client-utils": "npm:0.1.1-dev-02c06c4.0" "@agoric/ertp": "npm:dev" + "@agoric/internal": "npm:dev" "@agoric/synthetic-chain": "npm:^0.4.3" "@agoric/zoe": "npm:dev" "@endo/errors": "npm:1.2.7" diff --git a/a3p-integration/proposals/z:acceptance/yarn.lock b/a3p-integration/proposals/z:acceptance/yarn.lock index 92dc8a54bfe..d76e6d95485 100644 --- a/a3p-integration/proposals/z:acceptance/yarn.lock +++ b/a3p-integration/proposals/z:acceptance/yarn.lock @@ -156,6 +156,7 @@ __metadata: "@agoric/vat-data": "npm:^0.5.2" "@agoric/vats": "npm:^0.15.1" "@agoric/zoe": "npm:^0.26.2" + "@agoric/zone": "npm:^0.2.2" "@endo/captp": "npm:^4.4.3" "@endo/errors": "npm:^1.2.8" "@endo/eventual-send": "npm:^1.2.8" diff --git a/packages/inter-protocol/package.json b/packages/inter-protocol/package.json index 76f545f1e35..46f5336f45a 100644 --- a/packages/inter-protocol/package.json +++ b/packages/inter-protocol/package.json @@ -41,6 +41,7 @@ "@agoric/vat-data": "^0.5.2", "@agoric/vats": "^0.15.1", "@agoric/zoe": "^0.26.2", + "@agoric/zone": "^0.2.2", "@endo/captp": "^4.4.3", "@endo/eventual-send": "^1.2.8", "@endo/far": "^1.1.9", @@ -53,7 +54,6 @@ "@agoric/smart-wallet": "^0.5.3", "@agoric/swingset-liveslots": "^0.10.2", "@agoric/swingset-vat": "^0.32.2", - "@agoric/zone": "^0.2.2", "@endo/bundle-source": "^3.5.0", "@endo/init": "^1.1.7", "@endo/promise-kit": "^1.1.8", diff --git a/packages/inter-protocol/src/provisionPool.js b/packages/inter-protocol/src/provisionPool.js index 7eb37c61dd1..de96cfabaab 100644 --- a/packages/inter-protocol/src/provisionPool.js +++ b/packages/inter-protocol/src/provisionPool.js @@ -12,7 +12,11 @@ import { prepareExo } from '@agoric/vat-data'; import { provideSingleton } from '@agoric/zoe/src/contractSupport/durability.js'; import { prepareRecorderKitMakers } from '@agoric/zoe/src/contractSupport/recorder.js'; import { TopicsRecordShape } from '@agoric/zoe/src/contractSupport/topics.js'; -import { prepareProvisionPoolKit } from './provisionPoolKit.js'; +import { makeDurableZone } from '@agoric/zone/durable.js'; +import { + prepareBridgeProvisionTool, + prepareProvisionPoolKit, +} from './provisionPoolKit.js'; /** @import {Marshal} from '@endo/marshal'; */ @@ -72,11 +76,15 @@ export const start = async (zcf, privateArgs, baggage) => { privateArgs.marshaller, ); - const makeProvisionPoolKit = prepareProvisionPoolKit(baggage, { + const zone = makeDurableZone(baggage); + + const makeBridgeProvisionTool = prepareBridgeProvisionTool(zone); + const makeProvisionPoolKit = prepareProvisionPoolKit(zone, { makeRecorderKit, params, poolBank, zcf, + makeBridgeProvisionTool, }); const provisionPoolKit = await provideSingleton( diff --git a/packages/inter-protocol/src/provisionPoolKit.js b/packages/inter-protocol/src/provisionPoolKit.js index ee05ea5cc06..6c3694e6097 100644 --- a/packages/inter-protocol/src/provisionPoolKit.js +++ b/packages/inter-protocol/src/provisionPoolKit.js @@ -1,7 +1,6 @@ // @ts-check import { X, q, Fail } from '@endo/errors'; import { E } from '@endo/far'; -import { Far } from '@endo/marshal'; import { AmountMath, BrandShape } from '@agoric/ertp'; import { deeplyFulfilledObject, makeTracer } from '@agoric/internal'; @@ -15,7 +14,6 @@ import { M, makeScalarBigMapStore, makeScalarBigSetStore, - prepareExoClassKit, } from '@agoric/vat-data'; import { PowerFlags } from '@agoric/vats/src/walletFlags.js'; import { @@ -75,18 +73,22 @@ const FIRST_LOWER_NEAR_KEYWORD = /^[a-z][a-zA-Z0-9_$]*$/; * Given attenuated access to the funding purse, handle requests to provision * smart wallets. * - * @param {(depositBank: ERef) => Promise} sendInitialPayment - * @param {() => void} onProvisioned + * @param {import('@agoric/zone').Zone} zone */ -export const makeBridgeProvisionTool = (sendInitialPayment, onProvisioned) => { - /** @param {ProvisionPoolKitReferences} refs */ - const makeBridgeHandler = ({ - bankManager, - namesByAddressAdmin, - walletFactory, - }) => - Far('provisioningHandler', { - fromBridge: async obj => { +export const prepareBridgeProvisionTool = zone => + zone.exoClass( + 'smartWalletProvisioningHandler', + M.interface('ProvisionBridgeHandlerMaker', { + fromBridge: M.callWhen(M.record()).returns(), + }), + (bankManager, walletFactory, namesByAddressAdmin, forHandler) => ({ + bankManager, + walletFactory, + namesByAddressAdmin, + forHandler, + }), + { + async fromBridge(obj) { obj.type === 'PLEASE_PROVISION' || Fail`Unrecognized request ${obj.type}`; trace('PLEASE_PROVISION', obj); @@ -94,9 +96,12 @@ export const makeBridgeProvisionTool = (sendInitialPayment, onProvisioned) => { powerFlags.includes(PowerFlags.SMART_WALLET) || Fail`missing SMART_WALLET in powerFlags`; + const { bankManager, walletFactory, namesByAddressAdmin, forHandler } = + this.state; + const bank = E(bankManager).getBankForAddress(address); // only proceed if we can provide funds - await sendInitialPayment(bank); + await forHandler.sendInitialPayment(bank); const [_, created] = await E(walletFactory).provideSmartWallet( address, @@ -104,31 +109,30 @@ export const makeBridgeProvisionTool = (sendInitialPayment, onProvisioned) => { namesByAddressAdmin, ); if (created) { - onProvisioned(); + forHandler.onProvisioned(); } trace(created ? 'provisioned' : 're-provisioned', address); }, - }); - return makeBridgeHandler; -}; + }, + ); /** - * @param {import('@agoric/vat-data').Baggage} baggage + * @param {import('@agoric/zone').Zone} zone * @param {{ * makeRecorderKit: import('@agoric/zoe/src/contractSupport/recorder.js').MakeRecorderKit; * params: any; * poolBank: import('@endo/far').ERef; * zcf: ZCF; + * makeBridgeProvisionTool: ReturnType; * }} powers */ export const prepareProvisionPoolKit = ( - baggage, - { makeRecorderKit, params, poolBank, zcf }, + zone, + { makeRecorderKit, params, poolBank, zcf, makeBridgeProvisionTool }, ) => { const zoe = zcf.getZoeService(); - const makeProvisionPoolKitInternal = prepareExoClassKit( - baggage, + const makeProvisionPoolKitInternal = zone.exoClassKit( 'ProvisionPoolKit', { machine: M.interface('ProvisionPoolKit machine', { @@ -151,6 +155,7 @@ export const prepareProvisionPoolKit = ( ackWallet: M.call(M.string()).returns(M.boolean()), }), helper: UnguardedHelperI, + forHandler: UnguardedHelperI, public: M.interface('ProvisionPoolKit public', { getPublicTopics: M.call().returns({ metrics: PublicTopicShape }), }), @@ -217,23 +222,24 @@ export const prepareProvisionPoolKit = ( const refs = await deeplyFulfilledObject(obj); Object.assign(this.state, refs); }, + /** @returns {import('@agoric/vats').BridgeHandler} */ makeHandler() { const { bankManager, namesByAddressAdmin, walletFactory } = this.state; if (!bankManager || !namesByAddressAdmin || !walletFactory) { throw Fail`must set references before handling requests`; } - const { helper } = this.facets; - // a bit obtuse but leave for backwards compatibility with tests - const innerMaker = makeBridgeProvisionTool( - bank => helper.sendInitialPayment(bank), - () => helper.onProvisioned(), - ); - return innerMaker({ + + const { forHandler } = this.facets; + + const provisionHandler = makeBridgeProvisionTool( bankManager, - namesByAddressAdmin, walletFactory, - }); + namesByAddressAdmin, + forHandler, + ); + + return provisionHandler; }, /** * @param {Brand} brand @@ -311,37 +317,6 @@ export const prepareProvisionPoolKit = ( ); facets.helper.publishMetrics(); }, - onProvisioned() { - const { state, facets } = this; - state.walletsProvisioned += 1n; - facets.helper.publishMetrics(); - }, - /** @param {ERef} destBank */ - async sendInitialPayment(destBank) { - const { - facets: { helper }, - state: { fundPurse, poolBrand }, - } = this; - const perAccountInitialAmount = /** @type {Amount<'nat'>} */ ( - params.getPerAccountInitialAmount() - ); - const initialPmt = await E(fundPurse).withdraw( - perAccountInitialAmount, - ); - - const destPurse = E(destBank).getPurse(poolBrand); - return E(destPurse) - .deposit(initialPmt) - .then(amt => { - helper.onSendFunds(perAccountInitialAmount); - trace('provisionPool sent', amt); - }) - .catch(reason => { - console.error(X`initial deposit failed: ${q(reason)}`); - void E(fundPurse).deposit(initialPmt); - throw reason; - }); - }, /** * @param {ERef} exchangePurse * @param {ERef} brand @@ -491,6 +466,39 @@ export const prepareProvisionPoolKit = ( return rxd; }, }, + forHandler: { + onProvisioned() { + const { state, facets } = this; + state.walletsProvisioned += 1n; + facets.helper.publishMetrics(); + }, + /** @param {ERef} destBank */ + async sendInitialPayment(destBank) { + const { + facets: { helper }, + state: { fundPurse, poolBrand }, + } = this; + const perAccountInitialAmount = /** @type {Amount<'nat'>} */ ( + params.getPerAccountInitialAmount() + ); + const initialPmt = await E(fundPurse).withdraw( + perAccountInitialAmount, + ); + + const destPurse = E(destBank).getPurse(poolBrand); + return E(destPurse) + .deposit(initialPmt) + .then(amt => { + helper.onSendFunds(perAccountInitialAmount); + trace('provisionPool sent', amt); + }) + .catch(reason => { + console.error(X`initial deposit failed: ${q(reason)}`); + void E(fundPurse).deposit(initialPmt); + throw reason; + }); + }, + }, public: { getPublicTopics() { return { diff --git a/packages/inter-protocol/test/provisionPool.test.js b/packages/inter-protocol/test/provisionPool.test.js index 48ea08f7312..e591643a927 100644 --- a/packages/inter-protocol/test/provisionPool.test.js +++ b/packages/inter-protocol/test/provisionPool.test.js @@ -19,7 +19,8 @@ import { makeFakeBoard } from '@agoric/vats/tools/board-utils.js'; import { makeRatio } from '@agoric/zoe/src/contractSupport/ratio.js'; import { E, Far } from '@endo/far'; import path from 'path'; -import { makeBridgeProvisionTool } from '../src/provisionPoolKit.js'; +import { makeHeapZone } from '@agoric/zone'; +import { prepareBridgeProvisionTool } from '../src/provisionPoolKit.js'; import { makeMockChainStorageRoot, setUpZoeForTest, @@ -364,15 +365,14 @@ test('makeBridgeProvisionTool handles duplicate requests', async t => { const { nameHub: namesByAddress, nameAdmin: namesByAddressAdmin } = makeNameHubKit(); const publishMetrics = () => {}; - const makeHandler = makeBridgeProvisionTool( - sendInitialPayment, - publishMetrics, - ); - const handler = makeHandler({ + const zone = makeHeapZone(); + const makeBridgeProvisionTool = prepareBridgeProvisionTool(zone); + const handler = makeBridgeProvisionTool( bankManager, - namesByAddressAdmin, walletFactory, - }); + namesByAddressAdmin, + Far('helpers', { sendInitialPayment, onProvisioned: publishMetrics }), + ); t.log('1st request to provision a SMART_WALLET for', address); await handler.fromBridge({ diff --git a/packages/vats/src/proposals/upgrade-provisionPool-proposal.js b/packages/vats/src/proposals/upgrade-provisionPool-proposal.js index 4dd74af9c69..a94fd6ef418 100644 --- a/packages/vats/src/proposals/upgrade-provisionPool-proposal.js +++ b/packages/vats/src/proposals/upgrade-provisionPool-proposal.js @@ -1,5 +1,8 @@ import { E } from '@endo/far'; import { deeplyFulfilled } from '@endo/marshal'; +import { makeTracer } from '@agoric/internal'; + +const tracer = makeTracer('UpgradeProvisionPool'); /** * @param {BootstrapPowers & { @@ -27,7 +30,7 @@ export const upgradeProvisionPool = async ( const { provisionPoolRef } = options.options; assert(provisionPoolRef.bundleID); - console.log(`PROVISION POOL BUNDLE ID: `, provisionPoolRef.bundleID); + tracer(`PROVISION POOL BUNDLE ID: `, provisionPoolRef); const [ provisionPoolStartResult, @@ -66,7 +69,7 @@ export const upgradeProvisionPool = async ( newPrivateArgs, ); - console.log('ProvisionPool upgraded: ', upgradeResult); + tracer('ProvisionPool upgraded: ', upgradeResult); const references = { bankManager, @@ -74,17 +77,17 @@ export const upgradeProvisionPool = async ( walletFactory: wfCreatorFacet, }; - console.log('Calling setReferences with: ', references); + tracer('Calling setReferences with: ', references); await E(ppCreatorFacet).setReferences(references); - console.log('Creating bridgeHandler...'); + tracer('Creating bridgeHandler...'); const bridgeHandler = await E(ppCreatorFacet).makeHandler(); - console.log('Setting new bridgeHandler...'); + tracer('Setting new bridgeHandler...'); // @ts-expect-error casting await E(provisionWalletBridgeManager).setHandler(bridgeHandler); - console.log('Done.'); + tracer('Done.'); }; export const getManifestForUpgradingProvisionPool = ( From 51e7a9c3e3fb2cde44db2ffce817f353a17e76a3 Mon Sep 17 00:00:00 2001 From: 0xPatrick Date: Fri, 29 Nov 2024 16:38:20 -0500 Subject: [PATCH 05/56] feat: assetInfo as array of entries - to facililate registering the same denom across multiple chains in `ChainHub` - denoms are unique to a chain, but not all chains --- .../scripts/fast-usdc/init-fast-usdc.js | 28 ++++++++++------- packages/fast-usdc/src/fast-usdc.contract.js | 5 ++-- packages/fast-usdc/src/fast-usdc.start.js | 10 +++++-- packages/fast-usdc/test/supports.ts | 12 ++++---- .../src/examples/send-anywhere.contract.js | 2 +- .../src/proposals/start-send-anywhere.js | 2 +- .../src/utils/chain-hub-helper.js | 9 ++++-- .../orchestration/test/exos/chain-hub.test.ts | 30 +++++++++++-------- 8 files changed, 58 insertions(+), 40 deletions(-) diff --git a/packages/builders/scripts/fast-usdc/init-fast-usdc.js b/packages/builders/scripts/fast-usdc/init-fast-usdc.js index 783ce078f43..f5d38ebee82 100644 --- a/packages/builders/scripts/fast-usdc/init-fast-usdc.js +++ b/packages/builders/scripts/fast-usdc/init-fast-usdc.js @@ -20,31 +20,39 @@ import { parseArgs } from 'node:util'; * @import {ParseArgsConfig} from 'node:util' * @import {FastUSDCConfig} from '@agoric/fast-usdc/src/fast-usdc.start.js' * @import {Passable} from '@endo/marshal'; - * @import {CosmosChainInfo} from '@agoric/orchestration'; + * @import {CosmosChainInfo, Denom, DenomDetail} from '@agoric/orchestration'; */ const { keys } = Object; -const defaultAssetInfo = { - uusdc: { - baseName: 'noble', - chainName: 'noble', - baseDenom: 'uusdc', - }, - [`ibc/${denomHash({ denom: 'uusdc', channelId: fetchedChainInfo.agoric.connections['noble-1'].transferChannel.channelId })}`]: +/** @type {[Denom, DenomDetail & { brandKey?: string}][]} */ +const defaultAssetInfo = [ + [ + 'uusdc', + { + baseName: 'noble', + chainName: 'noble', + baseDenom: 'uusdc', + }, + ], + [ + `ibc/${denomHash({ denom: 'uusdc', channelId: fetchedChainInfo.agoric.connections['noble-1'].transferChannel.channelId })}`, { baseName: 'noble', chainName: 'agoric', baseDenom: 'uusdc', brandKey: 'USDC', }, - [`ibc/${denomHash({ denom: 'uusdc', channelId: fetchedChainInfo.osmosis.connections['noble-1'].transferChannel.channelId })}`]: + ], + [ + `ibc/${denomHash({ denom: 'uusdc', channelId: fetchedChainInfo.osmosis.connections['noble-1'].transferChannel.channelId })}`, { baseName: 'noble', chainName: 'osmosis', baseDenom: 'uusdc', }, -}; + ], +]; /** * @type {Record>} diff --git a/packages/fast-usdc/src/fast-usdc.contract.js b/packages/fast-usdc/src/fast-usdc.contract.js index 45bf9cc82d5..aa799e101d2 100644 --- a/packages/fast-usdc/src/fast-usdc.contract.js +++ b/packages/fast-usdc/src/fast-usdc.contract.js @@ -4,6 +4,7 @@ import { observeIteration, subscribeEach } from '@agoric/notifier'; import { CosmosChainInfoShape, DenomDetailShape, + DenomShape, OrchestrationPowersShape, registerChainsAndAssets, withOrchestration, @@ -55,7 +56,7 @@ export const meta = { feeConfig: FeeConfigShape, marshaller: M.remotable(), chainInfo: M.recordOf(M.string(), CosmosChainInfoShape), - assetInfo: M.recordOf(M.string(), DenomDetailShape), + assetInfo: M.arrayOf([DenomShape, DenomDetailShape]), }, }; harden(meta); @@ -77,7 +78,7 @@ const publishFeeConfig = async (node, marshaller, feeConfig) => { * marshaller: Marshaller; * feeConfig: FeeConfig; * chainInfo: Record; - * assetInfo: Record; + * assetInfo: [Denom, DenomDetail & { brandKey?: string}][]; * }} privateArgs * @param {Zone} zone * @param {OrchestrationTools} tools diff --git a/packages/fast-usdc/src/fast-usdc.start.js b/packages/fast-usdc/src/fast-usdc.start.js index 0dce7f375e2..237af828f30 100644 --- a/packages/fast-usdc/src/fast-usdc.start.js +++ b/packages/fast-usdc/src/fast-usdc.start.js @@ -1,5 +1,9 @@ import { deeplyFulfilledObject, makeTracer, objectMap } from '@agoric/internal'; -import { CosmosChainInfoShape, DenomDetailShape } from '@agoric/orchestration'; +import { + CosmosChainInfoShape, + DenomDetailShape, + DenomShape, +} from '@agoric/orchestration'; import { Fail } from '@endo/errors'; import { E } from '@endo/far'; import { makeMarshal } from '@endo/marshal'; @@ -36,7 +40,7 @@ const contractName = 'fastUsdc'; * feeConfig: FeeConfig; * feedPolicy: FeedPolicy & Passable; * chainInfo: Record; - * assetInfo: Record; + * assetInfo: [Denom, DenomDetail & {brandKey?: string}][]; * }} FastUSDCConfig */ /** @type {TypedPattern} */ @@ -46,7 +50,7 @@ export const FastUSDCConfigShape = M.splitRecord({ feeConfig: FeeConfigShape, feedPolicy: FeedPolicyShape, chainInfo: M.recordOf(M.string(), CosmosChainInfoShape), - assetInfo: M.recordOf(M.string(), DenomDetailShape), + assetInfo: M.arrayOf([DenomShape, DenomDetailShape]), }); /** diff --git a/packages/fast-usdc/test/supports.ts b/packages/fast-usdc/test/supports.ts index 174a28ceed9..2c9154ab227 100644 --- a/packages/fast-usdc/test/supports.ts +++ b/packages/fast-usdc/test/supports.ts @@ -200,13 +200,11 @@ export const commonSetup = async (t: ExecutionContext) => { return { agoric, osmosis, noble }; })(); - const assetInfo = harden( - Object.fromEntries([ - assetOn('uusdc', 'noble'), - [uusdcOnAgoric, agUSDCDetail], - assetOn('uusdc', 'noble', 'osmosis', fetchedChainInfo), - ]), - ); + const assetInfo: [Denom, DenomDetail & { brandKey?: string }][] = harden([ + assetOn('uusdc', 'noble'), + [uusdcOnAgoric, agUSDCDetail], + assetOn('uusdc', 'noble', 'osmosis', fetchedChainInfo), + ]); return { bootstrap: { diff --git a/packages/orchestration/src/examples/send-anywhere.contract.js b/packages/orchestration/src/examples/send-anywhere.contract.js index 3d2065de836..b277d5733ad 100644 --- a/packages/orchestration/src/examples/send-anywhere.contract.js +++ b/packages/orchestration/src/examples/send-anywhere.contract.js @@ -30,7 +30,7 @@ harden(SingleNatAmountRecord); * @param {OrchestrationPowers & { * marshaller: Marshaller; * chainInfo?: Record; - * assetInfo?: Record; + * assetInfo?: [Denom, DenomDetail & { brandKey?: string }][]; * }} privateArgs * @param {Zone} zone * @param {OrchestrationTools} tools diff --git a/packages/orchestration/src/proposals/start-send-anywhere.js b/packages/orchestration/src/proposals/start-send-anywhere.js index a50d87f3f7f..6d1c6932bc1 100644 --- a/packages/orchestration/src/proposals/start-send-anywhere.js +++ b/packages/orchestration/src/proposals/start-send-anywhere.js @@ -28,7 +28,7 @@ const trace = makeTracer('StartSA', true); * @param {{ * options: { * chainInfo: Record; - * assetInfo: Record; + * assetInfo: [Denom, DenomDetail & { brandKey?: string }][]; * }; * }} config */ diff --git a/packages/orchestration/src/utils/chain-hub-helper.js b/packages/orchestration/src/utils/chain-hub-helper.js index 306a5ecef56..829d0b58a7e 100644 --- a/packages/orchestration/src/utils/chain-hub-helper.js +++ b/packages/orchestration/src/utils/chain-hub-helper.js @@ -12,7 +12,7 @@ * @param {ChainHub} chainHub * @param {Record>} brands * @param {Record | undefined} chainInfo - * @param {Record | undefined} assetInfo + * @param {[Denom, DenomDetail & { brandKey?: string }][] | undefined} assetInfo */ export const registerChainsAndAssets = ( chainHub, @@ -43,11 +43,14 @@ export const registerChainsAndAssets = ( } console.log('chainHub: registered connections', [...registeredPairs].sort()); - console.log('chainHub: registering assets', Object.keys(assetInfo || {})); + console.log( + 'chainHub: registering assets', + assetInfo?.map(([denom, { chainName }]) => `${chainName}: ${denom}`), + ); if (!assetInfo) { return; } - for (const [denom, info] of Object.entries(assetInfo)) { + for (const [denom, info] of assetInfo) { const { brandKey, ...rest } = info; const infoWithBrand = brandKey ? { ...rest, brand: brands[brandKey] } diff --git a/packages/orchestration/test/exos/chain-hub.test.ts b/packages/orchestration/test/exos/chain-hub.test.ts index b93e4e34464..53a12302491 100644 --- a/packages/orchestration/test/exos/chain-hub.test.ts +++ b/packages/orchestration/test/exos/chain-hub.test.ts @@ -216,7 +216,10 @@ test('makeTransferRoute - to issuing chain', async t => { chainHub, {}, withChainCapabilities(knownChains), // adds pfmEnabled - harden({ [uusdcOnAgoric]: agDetail, [uusdcOnOsmosis]: osDetail }), + harden([ + [uusdcOnAgoric, agDetail], + [uusdcOnOsmosis, osDetail], + ]), ); const dest: ChainAddress = chainHub.makeChainAddress('noble1234'); @@ -257,12 +260,7 @@ test('makeTransferRoute - from issuing chain', async t => { chainHub, {}, withChainCapabilities(knownChains), // adds pfmEnabled - harden( - Object.fromEntries([ - assetOn('uist', 'agoric'), - assetOn('uosmo', 'osmosis'), - ]), - ), + harden([assetOn('uist', 'agoric'), assetOn('uosmo', 'osmosis')]), ); const dest: ChainAddress = chainHub.makeChainAddress('noble1234'); @@ -301,7 +299,7 @@ test('makeTransferRoute - through issuing chain', async t => { chainHub, {}, withChainCapabilities(knownChains), // adds pfmEnabled - harden({ [uusdcOnAgoric]: agDetail }), + harden([[uusdcOnAgoric, agDetail]]), ); const dest: ChainAddress = chainHub.makeChainAddress('osmo1234'); @@ -359,7 +357,7 @@ test('makeTransferRoute - takes forwardOpts', t => { chainHub, {}, withChainCapabilities(knownChains), // adds pfmEnabled - harden({ [uusdcOnOsmosis]: osDetail }), + harden([[uusdcOnOsmosis, osDetail]]), ); const dest: ChainAddress = chainHub.makeChainAddress('agoric1234'); @@ -464,7 +462,10 @@ test('makeTransferRoute - no connection info single hop', t => { chainHub, {}, knownChainsSansConns, // omit connections - harden({ [uusdcOnAgoric]: agDetail }), + harden([ + [uusdcOnAgoric, agDetail], + [uusdcOnOsmosis, osDetail], + ]), ); t.throws( @@ -487,7 +488,10 @@ test('makeTransferRoute - no connection info multi hop', t => { chainHub, {}, harden(chainInfo), - harden({ [uusdcOnAgoric]: agDetail, [uusdcOnOsmosis]: osDetail }), + harden([ + [uusdcOnAgoric, agDetail], + [uusdcOnOsmosis, osDetail], + ]), ); const osmoDest = chainHub.makeChainAddress('osmo1234'); @@ -522,7 +526,7 @@ test('makeTransferRoute - asset not on holding chain', t => { chainHub, {}, withChainCapabilities(knownChains), - harden({ [uusdcOnAgoric]: agDetail }), + harden([[uusdcOnAgoric, agDetail]]), ); // transfer USDC on agoric from osmosis to noble (impossible) @@ -547,7 +551,7 @@ test('makeTransferRoute - no PFM path', t => { chainHub, {}, knownChains, // intentionally omit pfmEnabled - harden({ [uusdcOnAgoric]: agDetail }), + harden([[uusdcOnAgoric, agDetail]]), ); // transfer USDC on agoric to osmosis From fc802adc06082eb0618f4a2d58d91ac380512352 Mon Sep 17 00:00:00 2001 From: 0xPatrick Date: Fri, 29 Nov 2024 14:47:23 -0500 Subject: [PATCH 06/56] feat!: `getAsset` and `getDenomInfo` require `srcChainName` param - since denoms are only unique to a chain and all chains, require `srcChainName` parameter for asset info lookups --- .../snapshots/fast-usdc.contract.test.ts.md | 14 ++--- .../snapshots/fast-usdc.contract.test.ts.snap | Bin 5637 -> 5637 bytes packages/orchestration/src/exos/chain-hub.js | 54 ++++++++++++------ .../src/exos/local-orchestration-account.js | 2 +- .../orchestration/src/exos/orchestrator.js | 6 +- .../orchestration/src/orchestration-api.ts | 1 + .../snapshots/staking-combinations.test.ts.md | 2 +- .../staking-combinations.test.ts.snap | Bin 2743 -> 2749 bytes .../orchestration/test/exos/chain-hub.test.ts | 21 +++---- .../test/facade-durability.test.ts | 26 ++++++--- packages/orchestration/test/supports.ts | 2 +- packages/orchestration/test/types.test-d.ts | 2 +- 12 files changed, 79 insertions(+), 51 deletions(-) diff --git a/packages/fast-usdc/test/snapshots/fast-usdc.contract.test.ts.md b/packages/fast-usdc/test/snapshots/fast-usdc.contract.test.ts.md index 62804cfa992..ece2a6e83cd 100644 --- a/packages/fast-usdc/test/snapshots/fast-usdc.contract.test.ts.md +++ b/packages/fast-usdc/test/snapshots/fast-usdc.contract.test.ts.md @@ -536,22 +536,22 @@ Generated by [AVA](https://avajs.dev). }, }, denom: { - 'ibc/498A0751C798A0D9A389AA3691123DADA57DAA4FE165D5C75894505B876BA6E4': { - baseDenom: 'uusdc', - baseName: 'noble', - chainName: 'osmosis', - }, - 'ibc/FE98AAD68F02F03565E9FA39A5E627946699B2B07115889ED812D8BA639576A9': { + 'agoric:ibc/FE98AAD68F02F03565E9FA39A5E627946699B2B07115889ED812D8BA639576A9': { baseDenom: 'uusdc', baseName: 'noble', brand: Object @Alleged: USDC brand {}, chainName: 'agoric', }, - uusdc: { + 'noble:uusdc': { baseDenom: 'uusdc', baseName: 'noble', chainName: 'noble', }, + 'osmosis:ibc/498A0751C798A0D9A389AA3691123DADA57DAA4FE165D5C75894505B876BA6E4': { + baseDenom: 'uusdc', + baseName: 'noble', + chainName: 'osmosis', + }, }, lookupChainInfo_kindHandle: 'Alleged: kind', lookupChainsAndConnection_kindHandle: 'Alleged: kind', diff --git a/packages/fast-usdc/test/snapshots/fast-usdc.contract.test.ts.snap b/packages/fast-usdc/test/snapshots/fast-usdc.contract.test.ts.snap index 084687b3bab0cbb2441b180c061d6ebbda934d4e..b4f6db225e5d35f97fc59405cd299d04a75b129f 100644 GIT binary patch literal 5637 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 literal 5637 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 diff --git a/packages/orchestration/src/exos/chain-hub.js b/packages/orchestration/src/exos/chain-hub.js index f74d9eda964..6a300fade5a 100644 --- a/packages/orchestration/src/exos/chain-hub.js +++ b/packages/orchestration/src/exos/chain-hub.js @@ -205,7 +205,9 @@ const ChainHubI = M.interface('ChainHub', { getConnectionInfo: M.call(ChainIdArgShape, ChainIdArgShape).returns(VowShape), getChainsAndConnection: M.call(M.string(), M.string()).returns(VowShape), registerAsset: M.call(M.string(), DenomDetailShape).returns(), - getAsset: M.call(M.string()).returns(M.or(DenomDetailShape, M.undefined())), + getAsset: M.call(M.string(), M.string()).returns( + M.or(DenomDetailShape, M.undefined()), + ), getDenom: M.call(BrandShape).returns(M.or(M.string(), M.undefined())), makeChainAddress: M.call(M.string()).returns(ChainAddressShape), makeTransferRoute: M.call(ChainAddressShape, DenomAmountShape, M.string()) @@ -256,6 +258,12 @@ export const makeChainHub = (zone, agoricNames, vowTools) => { valueShape: M.string(), }); + /** + * @param {Denom} denom - from perspective of the src/holding chain + * @param {DenomDetail['chainName']} srcChainName + */ + const makeDenomKey = (denom, srcChainName) => `${srcChainName}:${denom}`; + const lookupChainInfo = vowTools.retryable( zone, 'lookupChainInfo', @@ -440,8 +448,14 @@ export const makeChainHub = (zone, agoricNames, vowTools) => { Fail`must register chain ${q(chainName)} first`; chainInfos.has(baseName) || Fail`must register chain ${q(baseName)} first`; - denomDetails.init(denom, detail); + + const denomKey = makeDenomKey(denom, detail.chainName); + denomDetails.has(denomKey) && + Fail`already registered ${q(denom)} on ${q(chainName)}`; + denomDetails.init(denomKey, detail); if (detail.brand) { + chainName === 'agoric' || + Fail`brands only registerable for agoric-held assets`; brandDenoms.init(detail.brand, denom); } }, @@ -449,11 +463,13 @@ export const makeChainHub = (zone, agoricNames, vowTools) => { * Retrieve holding, issuing chain names etc. for a denom. * * @param {Denom} denom + * @param {string} srcChainName - the chainName the denom is held on * @returns {DenomDetail | undefined} */ - getAsset(denom) { - if (denomDetails.has(denom)) { - return denomDetails.get(denom); + getAsset(denom, srcChainName) { + const denomKey = makeDenomKey(denom, srcChainName); + if (denomDetails.has(denomKey)) { + return denomDetails.get(denomKey); } return undefined; }, @@ -491,26 +507,31 @@ export const makeChainHub = (zone, agoricNames, vowTools) => { * Determine the transfer route for a destination and amount given the * current holding chain. * + * Does not account for routes with more than 1 intermediary hop - that is, + * it can't unwrap denoms that were incorrectly routed. + * * XXX consider accepting AmountArg #10449 * * @param {ChainAddress} destination * @param {DenomAmount} denomAmount - * @param {string} holdingChainName + * @param {string} srcChainName * @param {Pick} [forwardOpts] * @returns {TransferRoute} single hop, multi hop * @throws {Error} if unable to determine route */ - makeTransferRoute(destination, denomAmount, holdingChainName, forwardOpts) { - chainInfos.has(holdingChainName) || - Fail`chain info not found for holding chain: ${q(holdingChainName)}`; + makeTransferRoute(destination, denomAmount, srcChainName, forwardOpts) { + chainInfos.has(srcChainName) || + Fail`chain info not found for holding chain: ${q(srcChainName)}`; - const denomDetail = chainHub.getAsset(denomAmount.denom); + const denomDetail = chainHub.getAsset(denomAmount.denom, srcChainName); denomDetail || - Fail`no denom detail for: ${q(denomAmount.denom)}. ensure it is registered in chainHub.`; + Fail`no denom detail for: ${q(denomAmount.denom)} on ${q(srcChainName)}. ensure it is registered in chainHub.`; const { baseName, chainName } = /** @type {DenomDetail} */ (denomDetail); - chainName === holdingChainName || - Fail`cannot transfer asset ${q(denomAmount.denom)}. held on ${q(chainName)} not ${q(holdingChainName)}.`; + + // currently unreachable since assets are registered with holdingChainName + chainName === srcChainName || + Fail`cannot transfer asset ${q(denomAmount.denom)}. held on ${q(chainName)} not ${q(srcChainName)}.`; // currently unreachable since we can't register an asset before a chain chainInfos.has(baseName) || @@ -518,13 +539,10 @@ export const makeChainHub = (zone, agoricNames, vowTools) => { const { chainId: baseChainId, pfmEnabled } = chainInfos.get(baseName); - const holdingChainId = chainInfos.get(holdingChainName).chainId; + const holdingChainId = chainInfos.get(srcChainName).chainId; // asset is transferring to or from the issuing chain, return direct route - if ( - baseChainId === destination.chainId || - baseName === holdingChainName - ) { + if (baseChainId === destination.chainId || baseName === srcChainName) { // TODO use getConnectionInfo once its sync const connKey = connectionKey(holdingChainId, destination.chainId); connectionInfos.has(connKey) || diff --git a/packages/orchestration/src/exos/local-orchestration-account.js b/packages/orchestration/src/exos/local-orchestration-account.js index bc5e1f2a48a..7ab823a0719 100644 --- a/packages/orchestration/src/exos/local-orchestration-account.js +++ b/packages/orchestration/src/exos/local-orchestration-account.js @@ -511,7 +511,7 @@ export const prepareLocalOrchestrationAccountKit = ( return asVow(() => { const [brand, denom] = typeof denomArg === 'string' - ? [chainHub.getAsset(denomArg)?.brand, denomArg] + ? [chainHub.getAsset(denomArg, 'agoric')?.brand, denomArg] : [denomArg, chainHub.getDenom(denomArg)]; if (!denom) { diff --git a/packages/orchestration/src/exos/orchestrator.js b/packages/orchestration/src/exos/orchestrator.js index 70e02ee60e7..0d5dae350b8 100644 --- a/packages/orchestration/src/exos/orchestrator.js +++ b/packages/orchestration/src/exos/orchestrator.js @@ -34,7 +34,7 @@ const trace = makeTracer('Orchestrator'); /** @see {Orchestrator} */ export const OrchestratorI = M.interface('Orchestrator', { getChain: M.call(M.string()).returns(Vow$(ChainInfoShape)), - getDenomInfo: M.call(DenomShape).returns(DenomInfoShape), + getDenomInfo: M.call(DenomShape, M.string()).returns(DenomInfoShape), asAmount: M.call(DenomAmountShape).returns(AmountShape), }); @@ -138,8 +138,8 @@ const prepareOrchestratorKit = ( }); }, /** @type {HostOf} */ - getDenomInfo(denom) { - const denomDetail = chainHub.getAsset(denom); + getDenomInfo(denom, holdingChainName) { + const denomDetail = chainHub.getAsset(denom, holdingChainName); if (!denomDetail) throw Fail`No denom detail for ${q(denom)}`; const { chainName, baseName, baseDenom, brand } = denomDetail; chainByName.has(chainName) || diff --git a/packages/orchestration/src/orchestration-api.ts b/packages/orchestration/src/orchestration-api.ts index 50830862c05..2294f376dce 100644 --- a/packages/orchestration/src/orchestration-api.ts +++ b/packages/orchestration/src/orchestration-api.ts @@ -146,6 +146,7 @@ export interface Orchestrator { IssuingChain extends keyof KnownChains, >( denom: Denom, + srcChainName: HoldingChain, ) => DenomInfo; /** diff --git a/packages/orchestration/test/examples/snapshots/staking-combinations.test.ts.md b/packages/orchestration/test/examples/snapshots/staking-combinations.test.ts.md index bbf2ad9192b..378cdaddaf7 100644 --- a/packages/orchestration/test/examples/snapshots/staking-combinations.test.ts.md +++ b/packages/orchestration/test/examples/snapshots/staking-combinations.test.ts.md @@ -98,7 +98,7 @@ Generated by [AVA](https://avajs.dev). }, }, denom: { - ubld: { + 'agoric:ubld': { baseDenom: 'ubld', baseName: 'agoric', brand: Object @Alleged: BLD brand {}, diff --git a/packages/orchestration/test/examples/snapshots/staking-combinations.test.ts.snap b/packages/orchestration/test/examples/snapshots/staking-combinations.test.ts.snap index 01a323d924f17902e88e58d2a0c44d1e0f98fc89..89494e9934d40e5f508d23d3c19b809d99d905d1 100644 GIT binary patch literal 2749 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 diff --git a/packages/orchestration/test/exos/chain-hub.test.ts b/packages/orchestration/test/exos/chain-hub.test.ts index 53a12302491..1a8efc8e762 100644 --- a/packages/orchestration/test/exos/chain-hub.test.ts +++ b/packages/orchestration/test/exos/chain-hub.test.ts @@ -86,28 +86,28 @@ test('denom info support via getAsset and getDenom', async t => { const denom = 'utok1'; const info1: CosmosChainInfo = { bech32Prefix: 'chain', - chainId: 'chain1', + chainId: 'agoric', stakingTokens: [{ denom }], }; const tok1 = withAmountUtils(makeIssuerKit('Tok1')); - chainHub.registerChain('chain1', info1); + chainHub.registerChain('agoric', info1); const info = { - chainName: 'chain1', - baseName: 'chain1', + chainName: 'agoric', + baseName: 'agoric', baseDenom: denom, brand: tok1.brand, }; chainHub.registerAsset('utok1', info); t.deepEqual( - chainHub.getAsset('utok1'), + chainHub.getAsset('utok1', 'agoric'), info, 'getAsset(denom) returns denom info', ); t.is( - chainHub.getAsset('utok404'), + chainHub.getAsset('utok404', 'agoric'), undefined, 'getAsset returns undefined when denom not registered', ); @@ -145,7 +145,7 @@ test('toward asset info in agoricNames (#9572)', async t => { registerAssets(chainHub, 'cosmoshub', details); { - const actual = chainHub.getAsset('uatom'); + const actual = chainHub.getAsset('uatom', 'cosmoshub'); t.deepEqual(actual, { chainName: 'cosmoshub', baseName: 'cosmoshub', @@ -156,6 +156,7 @@ test('toward asset info in agoricNames (#9572)', async t => { { const actual = chainHub.getAsset( 'ibc/F04D72CF9B5D9C849BB278B691CDFA2241813327430EC9CDC83F8F4CA4CDC2B0', + 'cosmoshub', ); t.deepEqual(actual, { chainName: 'cosmoshub', @@ -432,7 +433,7 @@ test('makeTransferRoute - no asset info', t => { ), { message: - 'no denom detail for: "uist". ensure it is registered in chainHub.', + 'no denom detail for: "uist" on "agoric". ensure it is registered in chainHub.', }, ); @@ -445,7 +446,7 @@ test('makeTransferRoute - no asset info', t => { ), { message: - 'no denom detail for: "ibc/FE98AAD68F02F03565E9FA39A5E627946699B2B07115889ED812D8BA639576A9". ensure it is registered in chainHub.', + 'no denom detail for: "ibc/FE98AAD68F02F03565E9FA39A5E627946699B2B07115889ED812D8BA639576A9" on "agoric". ensure it is registered in chainHub.', }, ); }); @@ -539,7 +540,7 @@ test('makeTransferRoute - asset not on holding chain', t => { ), { message: - 'cannot transfer asset "ibc/FE98AAD68F02F03565E9FA39A5E627946699B2B07115889ED812D8BA639576A9". held on "agoric" not "osmosis".', + 'no denom detail for: "ibc/FE98AAD68F02F03565E9FA39A5E627946699B2B07115889ED812D8BA639576A9" on "osmosis". ensure it is registered in chainHub.', }, ); }); diff --git a/packages/orchestration/test/facade-durability.test.ts b/packages/orchestration/test/facade-durability.test.ts index e6c3a4fe9ac..dff35064c26 100644 --- a/packages/orchestration/test/facade-durability.test.ts +++ b/packages/orchestration/test/facade-durability.test.ts @@ -184,7 +184,7 @@ test('asset / denom info', async t => { const { chainHub, orchestrate } = orchKit; chainHub.registerChain('agoric', fetchedChainInfo.agoric); - chainHub.registerChain(mockChainInfo.chainId, mockChainInfo); + chainHub.registerChain('mock', mockChainInfo); chainHub.registerConnection( 'agoric-3', mockChainInfo.chainId, @@ -192,8 +192,8 @@ test('asset / denom info', async t => { ); chainHub.registerAsset('utoken1', { - chainName: mockChainInfo.chainId, - baseName: mockChainInfo.chainId, + chainName: 'mock', + baseName: 'mock', baseDenom: 'utoken1', }); @@ -203,7 +203,7 @@ test('asset / denom info', async t => { t.log(`utoken1 over ${channelId}: ${agDenom}`); chainHub.registerAsset(agDenom, { chainName: 'agoric', - baseName: mockChainInfo.chainId, + baseName: 'mock', baseDenom: 'utoken1', brand, }); @@ -213,10 +213,14 @@ test('asset / denom info', async t => { { brand }, // eslint-disable-next-line no-shadow async (orc, { brand }) => { - const c1 = await orc.getChain(mockChainInfo.chainId); + const c1 = await orc.getChain('mock'); { - const actual = orc.getDenomInfo('utoken1'); + const actual = orc.getDenomInfo( + 'utoken1', + // @ts-expect-error 'mock' not a KnownChain + 'mock', + ); console.log('actual', actual); const info = await actual.chain.getChainInfo(); t.deepEqual(info, mockChainInfo); @@ -230,12 +234,12 @@ test('asset / denom info', async t => { } const agP = orc.getChain('agoric'); - t.throws(() => orc.getDenomInfo(agDenom), { + t.throws(() => orc.getDenomInfo(agDenom, 'agoric'), { message: /^wait until getChain\("agoric"\) completes/, }); const ag = await agP; { - const actual = orc.getDenomInfo(agDenom); + const actual = orc.getDenomInfo(agDenom, 'agoric'); t.deepEqual(actual, { chain: ag, @@ -258,7 +262,11 @@ test('asset / denom info', async t => { }); const missingGetChain = orchestrate('missing getChain', {}, async orc => { - const actual = orc.getDenomInfo('utoken2'); + const actual = orc.getDenomInfo( + 'utoken2', + // @ts-expect-error 'mock' not a KnownChain + 'anotherChain', + ); }); await t.throwsAsync(vt.when(missingGetChain()), { diff --git a/packages/orchestration/test/supports.ts b/packages/orchestration/test/supports.ts index dbf539c0919..6486a7ffbaa 100644 --- a/packages/orchestration/test/supports.ts +++ b/packages/orchestration/test/supports.ts @@ -174,7 +174,7 @@ export const commonSetup = async (t: ExecutionContext) => { * ChainHub. Use `ChainHubAdmin` instead. */ const registerAgoricBld = () => { - if (!chainHub.getAsset('ubld')) { + if (!chainHub.getAsset('ubld', 'agoric')) { chainHub.registerChain('agoric', fetchedChainInfo.agoric); chainHub.registerAsset('ubld', { chainName: 'agoric', diff --git a/packages/orchestration/test/types.test-d.ts b/packages/orchestration/test/types.test-d.ts index a889ca536e6..0b13a42fc19 100644 --- a/packages/orchestration/test/types.test-d.ts +++ b/packages/orchestration/test/types.test-d.ts @@ -110,7 +110,7 @@ expectNotType(chainAddr); expectNotType<() => Promise>(vowFn); const getDenomInfo: HostOf = null as any; - const chainHostOf = getDenomInfo('uatom').chain; + const chainHostOf = getDenomInfo('uatom', 'cosmoshub').chain; expectType>(chainHostOf.getChainInfo()); } From 50b36bad0ae62cbd9205532ebf5bb637bc06beed Mon Sep 17 00:00:00 2001 From: 0xPatrick Date: Fri, 29 Nov 2024 16:49:53 -0500 Subject: [PATCH 07/56] feat: multichain-testing `makeAssetInfo` helper --- multichain-testing/test/send-anywhere.test.ts | 35 +--- multichain-testing/test/support.ts | 7 + .../test/tools/asset-info.test.ts | 167 ++++++++++++++++++ multichain-testing/tools/asset-info.ts | 76 ++++++++ 4 files changed, 254 insertions(+), 31 deletions(-) create mode 100644 multichain-testing/test/tools/asset-info.test.ts create mode 100644 multichain-testing/tools/asset-info.ts diff --git a/multichain-testing/test/send-anywhere.test.ts b/multichain-testing/test/send-anywhere.test.ts index 376853600f0..ba74b23338a 100644 --- a/multichain-testing/test/send-anywhere.test.ts +++ b/multichain-testing/test/send-anywhere.test.ts @@ -10,8 +10,6 @@ import { createWallet } from '../tools/wallet.js'; import { AmountMath } from '@agoric/ertp'; import { makeQueryClient } from '../tools/query.js'; import type { Amount } from '@agoric/ertp/src/types.js'; -import chainInfo from '../starship-chain-info.js'; -import { denomHash, withChainCapabilities } from '@agoric/orchestration'; const test = anyTest as TestFn; @@ -22,39 +20,14 @@ const contractBuilder = '../packages/builders/scripts/testing/init-send-anywhere.js'; test.before(async t => { - const { deleteTestKeys, setupTestKeys, ...rest } = await commonSetup(t); + const { setupTestKeys, ...common } = await commonSetup(t); + const { assetInfo, chainInfo, deleteTestKeys, startContract } = common; deleteTestKeys(accounts).catch(); const wallets = await setupTestKeys(accounts); - t.context = { ...rest, wallets, deleteTestKeys }; - const { startContract } = rest; - - const assetInfo = { - uosmo: { - baseName: 'osmosis', - chainName: 'osmosis', - baseDenom: 'uosmo', - }, - [`ibc/${denomHash({ denom: 'uosmo', channelId: chainInfo.agoric.connections['osmosislocal'].transferChannel.channelId })}`]: - { - baseName: 'osmosis', - chainName: 'agoric', - baseDenom: 'uosmo', - }, - uatom: { - baseName: 'cosmoshub', - chainName: 'cosmoshub', - baseDenom: 'uatom', - }, - [`ibc/${denomHash({ denom: 'uatom', channelId: chainInfo.agoric.connections['gaialocal'].transferChannel.channelId })}`]: - { - baseName: 'cosmoshub', - chainName: 'agoric', - baseDenom: 'uatom', - }, - }; + t.context = { ...common, wallets }; await startContract(contractName, contractBuilder, { - chainInfo: JSON.stringify(withChainCapabilities(chainInfo)), + chainInfo: JSON.stringify(chainInfo), assetInfo: JSON.stringify(assetInfo), }); }); diff --git a/multichain-testing/test/support.ts b/multichain-testing/test/support.ts index f98b5a13f08..aef2bfab173 100644 --- a/multichain-testing/test/support.ts +++ b/multichain-testing/test/support.ts @@ -3,6 +3,7 @@ import { dirname, join } from 'path'; import { execa } from 'execa'; import fse from 'fs-extra'; import childProcess from 'node:child_process'; +import { withChainCapabilities } from '@agoric/orchestration'; import { makeAgdTools } from '../tools/agd-tools.js'; import { type E2ETools } from '../tools/e2e-tools.js'; import { @@ -15,6 +16,8 @@ import { makeRetryUntilCondition } from '../tools/sleep.js'; import { makeDeployBuilder } from '../tools/deploy.js'; import { makeHermes } from '../tools/hermes-tools.js'; import { makeNobleTools } from '../tools/noble-tools.js'; +import { makeAssetInfo } from '../tools/asset-info.js'; +import starshipChainInfo from '../starship-chain-info.js'; export const FAUCET_POUR = 10_000n * 1_000_000n; @@ -78,6 +81,8 @@ export const commonSetup = async (t: ExecutionContext) => { }); const hermes = makeHermes(childProcess); const nobleTools = makeNobleTools(childProcess); + const assetInfo = makeAssetInfo(starshipChainInfo); + const chainInfo = withChainCapabilities(starshipChainInfo); /** * Starts a contract if instance not found. Takes care of installing @@ -116,6 +121,8 @@ export const commonSetup = async (t: ExecutionContext) => { hermes, nobleTools, startContract, + assetInfo, + chainInfo, }; }; diff --git a/multichain-testing/test/tools/asset-info.test.ts b/multichain-testing/test/tools/asset-info.test.ts new file mode 100644 index 00000000000..f12748de7fd --- /dev/null +++ b/multichain-testing/test/tools/asset-info.test.ts @@ -0,0 +1,167 @@ +import test from '@endo/ses-ava/prepare-endo.js'; +import type { Denom, DenomDetail } from '@agoric/orchestration'; +import { makeAssetInfo } from '../../tools/asset-info.js'; + +const minChainInfo = { + agoric: { + chainId: 'agoriclocal', + connections: { + gaialocal: { + transferChannel: { + channelId: 'channel-1', + }, + }, + osmosislocal: { + transferChannel: { + channelId: 'channel-0', + }, + }, + }, + }, + cosmoshub: { + chainId: 'gaialocal', + connections: { + agoriclocal: { + transferChannel: { + channelId: 'channel-1', + }, + }, + osmosislocal: { + transferChannel: { + channelId: 'channel-0', + }, + }, + }, + }, + osmosis: { + chainId: 'osmosislocal', + connections: { + agoriclocal: { + transferChannel: { + channelId: 'channel-1', + }, + }, + gaialocal: { + transferChannel: { + channelId: 'channel-0', + }, + }, + }, + }, +}; + +const minTokenMap = { + agoric: ['ubld', 'uist'], + cosmoshub: ['uatom'], + osmosis: ['uosmo'], +}; + +test('makeAssetInfo', async t => { + const byDenom = (assetInfo: [Denom, DenomDetail][]) => + assetInfo.sort(([a], [b]) => a.localeCompare(b) * -1); + + const assetInfo = makeAssetInfo( + /** @ts-expect-error minified mock */ + minChainInfo, + minTokenMap, + ); + + t.deepEqual(byDenom([...assetInfo]), [ + [ + 'uosmo', + { + baseDenom: 'uosmo', + baseName: 'osmosis', + chainName: 'osmosis', + }, + ], + [ + 'uist', + { + baseDenom: 'uist', + baseName: 'agoric', + chainName: 'agoric', + }, + ], + [ + 'ubld', + { + baseDenom: 'ubld', + baseName: 'agoric', + chainName: 'agoric', + }, + ], + [ + 'uatom', + { + baseDenom: 'uatom', + baseName: 'cosmoshub', + chainName: 'cosmoshub', + }, + ], + [ + 'ibc/ED07A3391A112B175915CD8FAF43A2DA8E4790EDE12566649D0C2F97716B8518', + { + baseDenom: 'uosmo', + baseName: 'osmosis', + chainName: 'agoric', + }, + ], + [ + 'ibc/ED07A3391A112B175915CD8FAF43A2DA8E4790EDE12566649D0C2F97716B8518', + { + baseDenom: 'uosmo', + baseName: 'osmosis', + chainName: 'cosmoshub', + }, + ], + [ + 'ibc/E7827844CB818EE9C4DB2C159F1543FF62B26213B44CE8029D5CEFE52F0EE596', + { + baseDenom: 'ubld', + baseName: 'agoric', + chainName: 'cosmoshub', + }, + ], + [ + 'ibc/E7827844CB818EE9C4DB2C159F1543FF62B26213B44CE8029D5CEFE52F0EE596', + { + baseDenom: 'ubld', + baseName: 'agoric', + chainName: 'osmosis', + }, + ], + [ + 'ibc/C4CFF46FD6DE35CA4CF4CE031E643C8FDC9BA4B99AE598E9B0ED98FE3A2319F9', + { + baseDenom: 'uatom', + baseName: 'cosmoshub', + chainName: 'agoric', + }, + ], + [ + 'ibc/27394FB092D2ECCD56123C74F36E4C1F926001CEADA9CA97EA622B25F41E5EB2', + { + baseDenom: 'uatom', + baseName: 'cosmoshub', + chainName: 'osmosis', + }, + ], + [ + 'ibc/16CD81E12F05F5397CA2D580B4BA786A12A8F48B6FB3823D82EBE95D80B5287B', + { + baseDenom: 'uist', + baseName: 'agoric', + chainName: 'cosmoshub', + }, + ], + [ + 'ibc/16CD81E12F05F5397CA2D580B4BA786A12A8F48B6FB3823D82EBE95D80B5287B', + { + baseDenom: 'uist', + baseName: 'agoric', + chainName: 'osmosis', + }, + ], + ]); +}); diff --git a/multichain-testing/tools/asset-info.ts b/multichain-testing/tools/asset-info.ts new file mode 100644 index 00000000000..34c7d536b8c --- /dev/null +++ b/multichain-testing/tools/asset-info.ts @@ -0,0 +1,76 @@ +import { + denomHash, + type CosmosChainInfo, + type Denom, + type DenomDetail, +} from '@agoric/orchestration'; +import type { IBCChannelID } from '@agoric/vats'; + +/** make asset info for current env */ +export const makeAssetInfo = ( + chainInfo: Record, + tokenMap: Record = { + agoric: ['ubld', 'uist'], + cosmoshub: ['uatom'], + noble: ['uusdc'], + osmosis: ['uosmo', 'uion'], + }, +): [Denom, DenomDetail][] => { + const getChannelId = ( + issuingChainId: string, + holdingChainName: string, + ): IBCChannelID | undefined => + chainInfo[holdingChainName]?.connections?.[issuingChainId]?.transferChannel + .channelId; + + const toDenomHash = ( + denom: Denom, + issuingChainId: string, + holdingChainName: string, + ): Denom => { + const channelId = getChannelId(issuingChainId, holdingChainName); + if (!channelId) { + throw new Error( + `No channel found for ${issuingChainId} -> ${holdingChainName}`, + ); + } + return `ibc/${denomHash({ denom, channelId })}`; + }; + + // only include chains present in `chainInfo` + const tokens = Object.entries(tokenMap) + .filter(([chain]) => chain in chainInfo) + .flatMap(([chain, denoms]) => denoms.map(denom => ({ denom, chain }))); + + const assetInfo: [Denom, DenomDetail][] = []; + for (const { denom, chain } of tokens) { + const baseDetails = { + baseName: chain, + baseDenom: denom, + }; + + // Add native token entry + assetInfo.push([ + denom, + { + ...baseDetails, + chainName: chain, + }, + ]); + + // Add IBC entries for non-issuing chains + const issuingChainId = chainInfo[chain].chainId; + for (const holdingChain of Object.keys(chainInfo)) { + if (holdingChain === chain) continue; + assetInfo.push([ + toDenomHash(denom, issuingChainId, holdingChain), + { + ...baseDetails, + chainName: holdingChain, + }, + ]); + } + } + + return harden(assetInfo); +}; From 5912769ceca9bf97cc0fbf9f83c8e8290f1a4a61 Mon Sep 17 00:00:00 2001 From: 0xPatrick Date: Mon, 2 Dec 2024 16:09:56 -0500 Subject: [PATCH 08/56] chore(z:acceptance): skip "user can open a vault under debt limit" - filed #10599 after observing multiple flakes from unrelated changes --- a3p-integration/proposals/z:acceptance/vaults.test.js | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/a3p-integration/proposals/z:acceptance/vaults.test.js b/a3p-integration/proposals/z:acceptance/vaults.test.js index 7f3b818549d..bb8d9a40cb5 100644 --- a/a3p-integration/proposals/z:acceptance/vaults.test.js +++ b/a3p-integration/proposals/z:acceptance/vaults.test.js @@ -226,7 +226,8 @@ test.serial('user cannot open a vault above debt limit', async t => { ); }); -test.serial('user can open a vault under debt limit', async t => { +// TODO #10599. marked as `skip` since several flakes were observed +test.skip('user can open a vault under debt limit', async t => { const istBalanceBefore = await getISTBalance(GOV1ADDR); const activeVaultsBefore = await listVaults(GOV1ADDR, walletUtils); From 9df7f9bd0665facb84a40f3506cf565f8d7d4607 Mon Sep 17 00:00:00 2001 From: Turadg Aleahmad Date: Mon, 2 Dec 2024 13:05:48 -0800 Subject: [PATCH 09/56] chore: rm spurious option --- packages/orchestration/scripts/fetch-chain-info.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/orchestration/scripts/fetch-chain-info.ts b/packages/orchestration/scripts/fetch-chain-info.ts index e304d6993d9..90ffb0627be 100755 --- a/packages/orchestration/scripts/fetch-chain-info.ts +++ b/packages/orchestration/scripts/fetch-chain-info.ts @@ -1,4 +1,4 @@ -#!/usr/bin/env TS_BLANK_SPACE_EMIT=false node --import ts-blank-space/register +#!/usr/bin/env node --import ts-blank-space/register /** @file Fetch canonical chain info to generate the minimum needed for agoricNames */ import { ChainRegistryClient } from '@chain-registry/client'; import fsp from 'node:fs/promises'; From 9872ca55a3605a8e9a5a2fcf125794d7c4faa45d Mon Sep 17 00:00:00 2001 From: Turadg Aleahmad Date: Mon, 2 Dec 2024 13:13:57 -0800 Subject: [PATCH 10/56] build: use .ts for compat with ts-blank-space --- .../proposals/z:acceptance/lib/{vaults.mts => vaults.ts} | 0 .../scripts/{test-vaults.mts => test-vaults.ts} | 2 +- a3p-integration/proposals/z:acceptance/test.sh | 3 +-- a3p-integration/proposals/z:acceptance/tsconfig.json | 7 ++++++- scripts/{report-globals.mts => report-globals.ts} | 1 + 5 files changed, 9 insertions(+), 4 deletions(-) rename a3p-integration/proposals/z:acceptance/lib/{vaults.mts => vaults.ts} (100%) rename a3p-integration/proposals/z:acceptance/scripts/{test-vaults.mts => test-vaults.ts} (98%) rename scripts/{report-globals.mts => report-globals.ts} (98%) diff --git a/a3p-integration/proposals/z:acceptance/lib/vaults.mts b/a3p-integration/proposals/z:acceptance/lib/vaults.ts similarity index 100% rename from a3p-integration/proposals/z:acceptance/lib/vaults.mts rename to a3p-integration/proposals/z:acceptance/lib/vaults.ts diff --git a/a3p-integration/proposals/z:acceptance/scripts/test-vaults.mts b/a3p-integration/proposals/z:acceptance/scripts/test-vaults.ts similarity index 98% rename from a3p-integration/proposals/z:acceptance/scripts/test-vaults.mts rename to a3p-integration/proposals/z:acceptance/scripts/test-vaults.ts index 7fdbcef510a..2a5cbb51124 100755 --- a/a3p-integration/proposals/z:acceptance/scripts/test-vaults.mts +++ b/a3p-integration/proposals/z:acceptance/scripts/test-vaults.ts @@ -13,7 +13,7 @@ import { ISTunit, provisionWallet, setDebtLimit, -} from '../lib/vaults.mjs'; +} from '../lib/vaults.ts'; const START_FREQUENCY = 600; // StartFrequency: 600s (auction runs every 10m) const CLOCK_STEP = 20; // ClockStep: 20s (ensures auction completes in time) diff --git a/a3p-integration/proposals/z:acceptance/test.sh b/a3p-integration/proposals/z:acceptance/test.sh index 906bb57262e..a029b8d6e8a 100755 --- a/a3p-integration/proposals/z:acceptance/test.sh +++ b/a3p-integration/proposals/z:acceptance/test.sh @@ -10,8 +10,7 @@ yarn ava initial.test.js # XXX some of these tests have path dependencies so no globs yarn ava core-eval.test.js -npm install -g tsx -scripts/test-vaults.mts +scripts/test-vaults.ts echo ACCEPTANCE TESTING kread yarn ava kread.test.js diff --git a/a3p-integration/proposals/z:acceptance/tsconfig.json b/a3p-integration/proposals/z:acceptance/tsconfig.json index fb5b67a7598..064d7a860d4 100644 --- a/a3p-integration/proposals/z:acceptance/tsconfig.json +++ b/a3p-integration/proposals/z:acceptance/tsconfig.json @@ -6,11 +6,16 @@ "moduleResolution": "bundler", "allowJs": true, "checkJs": true, + "allowImportingTsExtensions": true, "strict": false, "strictNullChecks": true, "noImplicitThis": true, // XXX synthetic-chain has some errors "skipLibCheck": true }, - "exclude": ["restart-valueVow", "start-valueVow", "localchaintest-submission"] + "exclude": [ + "restart-valueVow", + "start-valueVow", + "localchaintest-submission" + ] } diff --git a/scripts/report-globals.mts b/scripts/report-globals.ts similarity index 98% rename from scripts/report-globals.mts rename to scripts/report-globals.ts index 50fa82cb7b8..b09cadcc930 100755 --- a/scripts/report-globals.mts +++ b/scripts/report-globals.ts @@ -79,6 +79,7 @@ const report = () => { console.log(counts); }; +console.log('Gathering globals...'); // Feel free to disable this while debugging runEslint(); report(); From 51cb26feb051a8d57d4c15b6a3038d48495a6abb Mon Sep 17 00:00:00 2001 From: Turadg Aleahmad Date: Mon, 2 Dec 2024 13:07:37 -0800 Subject: [PATCH 11/56] build: run with ts-blank-space/register --- a3p-integration/proposals/z:acceptance/scripts/test-vaults.ts | 2 +- multichain-testing/scripts/deploy-cli.ts | 2 +- multichain-testing/scripts/fetch-starship-chain-info.ts | 2 +- scripts/report-globals.ts | 2 +- 4 files changed, 4 insertions(+), 4 deletions(-) mode change 100644 => 100755 multichain-testing/scripts/deploy-cli.ts diff --git a/a3p-integration/proposals/z:acceptance/scripts/test-vaults.ts b/a3p-integration/proposals/z:acceptance/scripts/test-vaults.ts index 2a5cbb51124..7a5c2fa1aec 100755 --- a/a3p-integration/proposals/z:acceptance/scripts/test-vaults.ts +++ b/a3p-integration/proposals/z:acceptance/scripts/test-vaults.ts @@ -1,4 +1,4 @@ -#!/usr/bin/env tsx +#!/usr/bin/env node --import ts-blank-space/register /* eslint-disable @jessie.js/safe-await-separator */ import { diff --git a/multichain-testing/scripts/deploy-cli.ts b/multichain-testing/scripts/deploy-cli.ts old mode 100644 new mode 100755 index 7f032606e23..47cb70e1153 --- a/multichain-testing/scripts/deploy-cli.ts +++ b/multichain-testing/scripts/deploy-cli.ts @@ -1,4 +1,4 @@ -#!/usr/bin/env tsx +#!/usr/bin/env node --import ts-blank-space/register import '@endo/init/debug.js'; import { execa } from 'execa'; diff --git a/multichain-testing/scripts/fetch-starship-chain-info.ts b/multichain-testing/scripts/fetch-starship-chain-info.ts index e660039cad2..fa4ec834687 100755 --- a/multichain-testing/scripts/fetch-starship-chain-info.ts +++ b/multichain-testing/scripts/fetch-starship-chain-info.ts @@ -1,4 +1,4 @@ -#!/usr/bin/env tsx +#!/usr/bin/env node --import ts-blank-space/register /* eslint-env node */ import fsp from 'node:fs/promises'; diff --git a/scripts/report-globals.ts b/scripts/report-globals.ts index b09cadcc930..ff5fe426dc5 100755 --- a/scripts/report-globals.ts +++ b/scripts/report-globals.ts @@ -1,4 +1,4 @@ -#!/usr/bin/env tsx +#!/usr/bin/env node --import ts-blank-space/register /* eslint-disable -- hacky script for irregular reports */ /** From 1805d3813414591a4cc96e388e8b9088fd990108 Mon Sep 17 00:00:00 2001 From: Turadg Aleahmad Date: Mon, 2 Dec 2024 13:07:49 -0800 Subject: [PATCH 12/56] chore(deps): remove tsx --- .../proposals/z:acceptance/package.json | 3 +- .../proposals/z:acceptance/yarn.lock | 288 +----- multichain-testing/package.json | 1 - multichain-testing/yarn.lock | 854 +----------------- 4 files changed, 11 insertions(+), 1135 deletions(-) diff --git a/a3p-integration/proposals/z:acceptance/package.json b/a3p-integration/proposals/z:acceptance/package.json index e95b55a26a5..8a906d701b8 100644 --- a/a3p-integration/proposals/z:acceptance/package.json +++ b/a3p-integration/proposals/z:acceptance/package.json @@ -23,8 +23,7 @@ "@endo/marshal": "^1.6.1", "agoric": "dev", "ava": "^6.1.2", - "execa": "9.1.0", - "tsx": "^4.17.0" + "execa": "9.1.0" }, "$comment": "UNTIL https://github.com/Agoric/agoric-sdk/issues/10259", "resolutions": { diff --git a/a3p-integration/proposals/z:acceptance/yarn.lock b/a3p-integration/proposals/z:acceptance/yarn.lock index d76e6d95485..c4f420e2cde 100644 --- a/a3p-integration/proposals/z:acceptance/yarn.lock +++ b/a3p-integration/proposals/z:acceptance/yarn.lock @@ -1084,174 +1084,6 @@ __metadata: languageName: node linkType: hard -"@esbuild/aix-ppc64@npm:0.23.1": - version: 0.23.1 - resolution: "@esbuild/aix-ppc64@npm:0.23.1" - conditions: os=aix & cpu=ppc64 - languageName: node - linkType: hard - -"@esbuild/android-arm64@npm:0.23.1": - version: 0.23.1 - resolution: "@esbuild/android-arm64@npm:0.23.1" - conditions: os=android & cpu=arm64 - languageName: node - linkType: hard - -"@esbuild/android-arm@npm:0.23.1": - version: 0.23.1 - resolution: "@esbuild/android-arm@npm:0.23.1" - conditions: os=android & cpu=arm - languageName: node - linkType: hard - -"@esbuild/android-x64@npm:0.23.1": - version: 0.23.1 - resolution: "@esbuild/android-x64@npm:0.23.1" - conditions: os=android & cpu=x64 - languageName: node - linkType: hard - -"@esbuild/darwin-arm64@npm:0.23.1": - version: 0.23.1 - resolution: "@esbuild/darwin-arm64@npm:0.23.1" - conditions: os=darwin & cpu=arm64 - languageName: node - linkType: hard - -"@esbuild/darwin-x64@npm:0.23.1": - version: 0.23.1 - resolution: "@esbuild/darwin-x64@npm:0.23.1" - conditions: os=darwin & cpu=x64 - languageName: node - linkType: hard - -"@esbuild/freebsd-arm64@npm:0.23.1": - version: 0.23.1 - resolution: "@esbuild/freebsd-arm64@npm:0.23.1" - conditions: os=freebsd & cpu=arm64 - languageName: node - linkType: hard - -"@esbuild/freebsd-x64@npm:0.23.1": - version: 0.23.1 - resolution: "@esbuild/freebsd-x64@npm:0.23.1" - conditions: os=freebsd & cpu=x64 - languageName: node - linkType: hard - -"@esbuild/linux-arm64@npm:0.23.1": - version: 0.23.1 - resolution: "@esbuild/linux-arm64@npm:0.23.1" - conditions: os=linux & cpu=arm64 - languageName: node - linkType: hard - -"@esbuild/linux-arm@npm:0.23.1": - version: 0.23.1 - resolution: "@esbuild/linux-arm@npm:0.23.1" - conditions: os=linux & cpu=arm - languageName: node - linkType: hard - -"@esbuild/linux-ia32@npm:0.23.1": - version: 0.23.1 - resolution: "@esbuild/linux-ia32@npm:0.23.1" - conditions: os=linux & cpu=ia32 - languageName: node - linkType: hard - -"@esbuild/linux-loong64@npm:0.23.1": - version: 0.23.1 - resolution: "@esbuild/linux-loong64@npm:0.23.1" - conditions: os=linux & cpu=loong64 - languageName: node - linkType: hard - -"@esbuild/linux-mips64el@npm:0.23.1": - version: 0.23.1 - resolution: "@esbuild/linux-mips64el@npm:0.23.1" - conditions: os=linux & cpu=mips64el - languageName: node - linkType: hard - -"@esbuild/linux-ppc64@npm:0.23.1": - version: 0.23.1 - resolution: "@esbuild/linux-ppc64@npm:0.23.1" - conditions: os=linux & cpu=ppc64 - languageName: node - linkType: hard - -"@esbuild/linux-riscv64@npm:0.23.1": - version: 0.23.1 - resolution: "@esbuild/linux-riscv64@npm:0.23.1" - conditions: os=linux & cpu=riscv64 - languageName: node - linkType: hard - -"@esbuild/linux-s390x@npm:0.23.1": - version: 0.23.1 - resolution: "@esbuild/linux-s390x@npm:0.23.1" - conditions: os=linux & cpu=s390x - languageName: node - linkType: hard - -"@esbuild/linux-x64@npm:0.23.1": - version: 0.23.1 - resolution: "@esbuild/linux-x64@npm:0.23.1" - conditions: os=linux & cpu=x64 - languageName: node - linkType: hard - -"@esbuild/netbsd-x64@npm:0.23.1": - version: 0.23.1 - resolution: "@esbuild/netbsd-x64@npm:0.23.1" - conditions: os=netbsd & cpu=x64 - languageName: node - linkType: hard - -"@esbuild/openbsd-arm64@npm:0.23.1": - version: 0.23.1 - resolution: "@esbuild/openbsd-arm64@npm:0.23.1" - conditions: os=openbsd & cpu=arm64 - languageName: node - linkType: hard - -"@esbuild/openbsd-x64@npm:0.23.1": - version: 0.23.1 - resolution: "@esbuild/openbsd-x64@npm:0.23.1" - conditions: os=openbsd & cpu=x64 - languageName: node - linkType: hard - -"@esbuild/sunos-x64@npm:0.23.1": - version: 0.23.1 - resolution: "@esbuild/sunos-x64@npm:0.23.1" - conditions: os=sunos & cpu=x64 - languageName: node - linkType: hard - -"@esbuild/win32-arm64@npm:0.23.1": - version: 0.23.1 - resolution: "@esbuild/win32-arm64@npm:0.23.1" - conditions: os=win32 & cpu=arm64 - languageName: node - linkType: hard - -"@esbuild/win32-ia32@npm:0.23.1": - version: 0.23.1 - resolution: "@esbuild/win32-ia32@npm:0.23.1" - conditions: os=win32 & cpu=ia32 - languageName: node - linkType: hard - -"@esbuild/win32-x64@npm:0.23.1": - version: 0.23.1 - resolution: "@esbuild/win32-x64@npm:0.23.1" - conditions: os=win32 & cpu=x64 - languageName: node - linkType: hard - "@eslint-community/eslint-utils@npm:^4.2.0": version: 4.4.1 resolution: "@eslint-community/eslint-utils@npm:4.4.1" @@ -3010,89 +2842,6 @@ __metadata: languageName: node linkType: hard -"esbuild@npm:~0.23.0": - version: 0.23.1 - resolution: "esbuild@npm:0.23.1" - dependencies: - "@esbuild/aix-ppc64": "npm:0.23.1" - "@esbuild/android-arm": "npm:0.23.1" - "@esbuild/android-arm64": "npm:0.23.1" - "@esbuild/android-x64": "npm:0.23.1" - "@esbuild/darwin-arm64": "npm:0.23.1" - "@esbuild/darwin-x64": "npm:0.23.1" - "@esbuild/freebsd-arm64": "npm:0.23.1" - "@esbuild/freebsd-x64": "npm:0.23.1" - "@esbuild/linux-arm": "npm:0.23.1" - "@esbuild/linux-arm64": "npm:0.23.1" - "@esbuild/linux-ia32": "npm:0.23.1" - "@esbuild/linux-loong64": "npm:0.23.1" - "@esbuild/linux-mips64el": "npm:0.23.1" - "@esbuild/linux-ppc64": "npm:0.23.1" - "@esbuild/linux-riscv64": "npm:0.23.1" - "@esbuild/linux-s390x": "npm:0.23.1" - "@esbuild/linux-x64": "npm:0.23.1" - "@esbuild/netbsd-x64": "npm:0.23.1" - "@esbuild/openbsd-arm64": "npm:0.23.1" - "@esbuild/openbsd-x64": "npm:0.23.1" - "@esbuild/sunos-x64": "npm:0.23.1" - "@esbuild/win32-arm64": "npm:0.23.1" - "@esbuild/win32-ia32": "npm:0.23.1" - "@esbuild/win32-x64": "npm:0.23.1" - dependenciesMeta: - "@esbuild/aix-ppc64": - optional: true - "@esbuild/android-arm": - optional: true - "@esbuild/android-arm64": - optional: true - "@esbuild/android-x64": - optional: true - "@esbuild/darwin-arm64": - optional: true - "@esbuild/darwin-x64": - optional: true - "@esbuild/freebsd-arm64": - optional: true - "@esbuild/freebsd-x64": - optional: true - "@esbuild/linux-arm": - optional: true - "@esbuild/linux-arm64": - optional: true - "@esbuild/linux-ia32": - optional: true - "@esbuild/linux-loong64": - optional: true - "@esbuild/linux-mips64el": - optional: true - "@esbuild/linux-ppc64": - optional: true - "@esbuild/linux-riscv64": - optional: true - "@esbuild/linux-s390x": - optional: true - "@esbuild/linux-x64": - optional: true - "@esbuild/netbsd-x64": - optional: true - "@esbuild/openbsd-arm64": - optional: true - "@esbuild/openbsd-x64": - optional: true - "@esbuild/sunos-x64": - optional: true - "@esbuild/win32-arm64": - optional: true - "@esbuild/win32-ia32": - optional: true - "@esbuild/win32-x64": - optional: true - bin: - esbuild: bin/esbuild - checksum: 10c0/08c2ed1105cc3c5e3a24a771e35532fe6089dd24a39c10097899072cef4a99f20860e41e9294e000d86380f353b04d8c50af482483d7f69f5208481cce61eec7 - languageName: node - linkType: hard - "escalade@npm:^3.1.1": version: 3.2.0 resolution: "escalade@npm:3.2.0" @@ -3569,7 +3318,7 @@ __metadata: languageName: node linkType: hard -"fsevents@npm:~2.3.2, fsevents@npm:~2.3.3": +"fsevents@npm:~2.3.2": version: 2.3.3 resolution: "fsevents@npm:2.3.3" dependencies: @@ -3579,7 +3328,7 @@ __metadata: languageName: node linkType: hard -"fsevents@patch:fsevents@npm%3A~2.3.2#optional!builtin, fsevents@patch:fsevents@npm%3A~2.3.3#optional!builtin": +"fsevents@patch:fsevents@npm%3A~2.3.2#optional!builtin": version: 2.3.3 resolution: "fsevents@patch:fsevents@npm%3A2.3.3#optional!builtin::version=2.3.3&hash=df0bf1" dependencies: @@ -3679,15 +3428,6 @@ __metadata: languageName: node linkType: hard -"get-tsconfig@npm:^4.7.5": - version: 4.8.1 - resolution: "get-tsconfig@npm:4.8.1" - dependencies: - resolve-pkg-maps: "npm:^1.0.0" - checksum: 10c0/536ee85d202f604f4b5fb6be81bcd6e6d9a96846811e83e9acc6de4a04fb49506edea0e1b8cf1d5ee7af33e469916ec2809d4c5445ab8ae015a7a51fbd1572f9 - languageName: node - linkType: hard - "github-from-package@npm:0.0.0": version: 0.0.0 resolution: "github-from-package@npm:0.0.0" @@ -5716,13 +5456,6 @@ __metadata: languageName: node linkType: hard -"resolve-pkg-maps@npm:^1.0.0": - version: 1.0.0 - resolution: "resolve-pkg-maps@npm:1.0.0" - checksum: 10c0/fb8f7bbe2ca281a73b7ef423a1cbc786fb244bd7a95cbe5c3fba25b27d327150beca8ba02f622baea65919a57e061eb5005204daa5f93ed590d9b77463a567ab - languageName: node - linkType: hard - "resolve@npm:^1.10.0, resolve@npm:^1.17.0, resolve@npm:^1.19.0": version: 1.22.8 resolution: "resolve@npm:1.22.8" @@ -5818,7 +5551,6 @@ __metadata: eslint: "npm:^8.57.0" execa: "npm:9.1.0" npm-run-all: "npm:^4.1.5" - tsx: "npm:^4.17.0" typescript: "npm:^5.6.3" languageName: unknown linkType: soft @@ -6548,22 +6280,6 @@ __metadata: languageName: node linkType: hard -"tsx@npm:^4.17.0": - version: 4.19.2 - resolution: "tsx@npm:4.19.2" - dependencies: - esbuild: "npm:~0.23.0" - fsevents: "npm:~2.3.3" - get-tsconfig: "npm:^4.7.5" - dependenciesMeta: - fsevents: - optional: true - bin: - tsx: dist/cli.mjs - checksum: 10c0/63164b889b1d170403e4d8753a6755dec371f220f5ce29a8e88f1f4d6085a784a12d8dc2ee669116611f2c72757ac9beaa3eea5c452796f541bdd2dc11753721 - languageName: node - linkType: hard - "tunnel-agent@npm:^0.6.0": version: 0.6.0 resolution: "tunnel-agent@npm:0.6.0" diff --git a/multichain-testing/package.json b/multichain-testing/package.json index 4d00409e179..8d204854818 100644 --- a/multichain-testing/package.json +++ b/multichain-testing/package.json @@ -38,7 +38,6 @@ "patch-package": "^8.0.0", "starshipjs": "2.4.1", "ts-blank-space": "^0.4.4", - "tsx": "^4.15.6", "typescript": "~5.6.2" }, "resolutions": { diff --git a/multichain-testing/yarn.lock b/multichain-testing/yarn.lock index 56b70b10a67..f6abb8ce779 100644 --- a/multichain-testing/yarn.lock +++ b/multichain-testing/yarn.lock @@ -436,167 +436,6 @@ __metadata: languageName: node linkType: hard -"@esbuild/aix-ppc64@npm:0.21.5": - version: 0.21.5 - resolution: "@esbuild/aix-ppc64@npm:0.21.5" - conditions: os=aix & cpu=ppc64 - languageName: node - linkType: hard - -"@esbuild/android-arm64@npm:0.21.5": - version: 0.21.5 - resolution: "@esbuild/android-arm64@npm:0.21.5" - conditions: os=android & cpu=arm64 - languageName: node - linkType: hard - -"@esbuild/android-arm@npm:0.21.5": - version: 0.21.5 - resolution: "@esbuild/android-arm@npm:0.21.5" - conditions: os=android & cpu=arm - languageName: node - linkType: hard - -"@esbuild/android-x64@npm:0.21.5": - version: 0.21.5 - resolution: "@esbuild/android-x64@npm:0.21.5" - conditions: os=android & cpu=x64 - languageName: node - linkType: hard - -"@esbuild/darwin-arm64@npm:0.21.5": - version: 0.21.5 - resolution: "@esbuild/darwin-arm64@npm:0.21.5" - conditions: os=darwin & cpu=arm64 - languageName: node - linkType: hard - -"@esbuild/darwin-x64@npm:0.21.5": - version: 0.21.5 - resolution: "@esbuild/darwin-x64@npm:0.21.5" - conditions: os=darwin & cpu=x64 - languageName: node - linkType: hard - -"@esbuild/freebsd-arm64@npm:0.21.5": - version: 0.21.5 - resolution: "@esbuild/freebsd-arm64@npm:0.21.5" - conditions: os=freebsd & cpu=arm64 - languageName: node - linkType: hard - -"@esbuild/freebsd-x64@npm:0.21.5": - version: 0.21.5 - resolution: "@esbuild/freebsd-x64@npm:0.21.5" - conditions: os=freebsd & cpu=x64 - languageName: node - linkType: hard - -"@esbuild/linux-arm64@npm:0.21.5": - version: 0.21.5 - resolution: "@esbuild/linux-arm64@npm:0.21.5" - conditions: os=linux & cpu=arm64 - languageName: node - linkType: hard - -"@esbuild/linux-arm@npm:0.21.5": - version: 0.21.5 - resolution: "@esbuild/linux-arm@npm:0.21.5" - conditions: os=linux & cpu=arm - languageName: node - linkType: hard - -"@esbuild/linux-ia32@npm:0.21.5": - version: 0.21.5 - resolution: "@esbuild/linux-ia32@npm:0.21.5" - conditions: os=linux & cpu=ia32 - languageName: node - linkType: hard - -"@esbuild/linux-loong64@npm:0.21.5": - version: 0.21.5 - resolution: "@esbuild/linux-loong64@npm:0.21.5" - conditions: os=linux & cpu=loong64 - languageName: node - linkType: hard - -"@esbuild/linux-mips64el@npm:0.21.5": - version: 0.21.5 - resolution: "@esbuild/linux-mips64el@npm:0.21.5" - conditions: os=linux & cpu=mips64el - languageName: node - linkType: hard - -"@esbuild/linux-ppc64@npm:0.21.5": - version: 0.21.5 - resolution: "@esbuild/linux-ppc64@npm:0.21.5" - conditions: os=linux & cpu=ppc64 - languageName: node - linkType: hard - -"@esbuild/linux-riscv64@npm:0.21.5": - version: 0.21.5 - resolution: "@esbuild/linux-riscv64@npm:0.21.5" - conditions: os=linux & cpu=riscv64 - languageName: node - linkType: hard - -"@esbuild/linux-s390x@npm:0.21.5": - version: 0.21.5 - resolution: "@esbuild/linux-s390x@npm:0.21.5" - conditions: os=linux & cpu=s390x - languageName: node - linkType: hard - -"@esbuild/linux-x64@npm:0.21.5": - version: 0.21.5 - resolution: "@esbuild/linux-x64@npm:0.21.5" - conditions: os=linux & cpu=x64 - languageName: node - linkType: hard - -"@esbuild/netbsd-x64@npm:0.21.5": - version: 0.21.5 - resolution: "@esbuild/netbsd-x64@npm:0.21.5" - conditions: os=netbsd & cpu=x64 - languageName: node - linkType: hard - -"@esbuild/openbsd-x64@npm:0.21.5": - version: 0.21.5 - resolution: "@esbuild/openbsd-x64@npm:0.21.5" - conditions: os=openbsd & cpu=x64 - languageName: node - linkType: hard - -"@esbuild/sunos-x64@npm:0.21.5": - version: 0.21.5 - resolution: "@esbuild/sunos-x64@npm:0.21.5" - conditions: os=sunos & cpu=x64 - languageName: node - linkType: hard - -"@esbuild/win32-arm64@npm:0.21.5": - version: 0.21.5 - resolution: "@esbuild/win32-arm64@npm:0.21.5" - conditions: os=win32 & cpu=arm64 - languageName: node - linkType: hard - -"@esbuild/win32-ia32@npm:0.21.5": - version: 0.21.5 - resolution: "@esbuild/win32-ia32@npm:0.21.5" - conditions: os=win32 & cpu=ia32 - languageName: node - linkType: hard - -"@esbuild/win32-x64@npm:0.21.5": - version: 0.21.5 - resolution: "@esbuild/win32-x64@npm:0.21.5" - conditions: os=win32 & cpu=x64 - languageName: node - linkType: hard - "@eslint-community/eslint-utils@npm:^4.2.0, @eslint-community/eslint-utils@npm:^4.4.0": version: 4.4.0 resolution: "@eslint-community/eslint-utils@npm:4.4.0" @@ -675,20 +514,6 @@ __metadata: languageName: node linkType: hard -"@isaacs/cliui@npm:^8.0.2": - version: 8.0.2 - resolution: "@isaacs/cliui@npm:8.0.2" - dependencies: - string-width: "npm:^5.1.2" - string-width-cjs: "npm:string-width@^4.2.0" - strip-ansi: "npm:^7.0.1" - strip-ansi-cjs: "npm:strip-ansi@^6.0.1" - wrap-ansi: "npm:^8.1.0" - wrap-ansi-cjs: "npm:wrap-ansi@^7.0.0" - checksum: 10c0/b1bf42535d49f11dc137f18d5e4e63a28c5569de438a221c369483731e9dac9fb797af554e8bf02b6192d1e5eba6e6402cf93900c3d0ac86391d00d04876789e - languageName: node - linkType: hard - "@mapbox/node-pre-gyp@npm:^1.0.11": version: 1.0.11 resolution: "@mapbox/node-pre-gyp@npm:1.0.11" @@ -742,35 +567,6 @@ __metadata: languageName: node linkType: hard -"@npmcli/agent@npm:^2.0.0": - version: 2.2.2 - resolution: "@npmcli/agent@npm:2.2.2" - dependencies: - agent-base: "npm:^7.1.0" - http-proxy-agent: "npm:^7.0.0" - https-proxy-agent: "npm:^7.0.1" - lru-cache: "npm:^10.0.1" - socks-proxy-agent: "npm:^8.0.3" - checksum: 10c0/325e0db7b287d4154ecd164c0815c08007abfb07653cc57bceded17bb7fd240998a3cbdbe87d700e30bef494885eccc725ab73b668020811d56623d145b524ae - languageName: node - linkType: hard - -"@npmcli/fs@npm:^3.1.0": - version: 3.1.1 - resolution: "@npmcli/fs@npm:3.1.1" - dependencies: - semver: "npm:^7.3.5" - checksum: 10c0/c37a5b4842bfdece3d14dfdb054f73fe15ed2d3da61b34ff76629fb5b1731647c49166fd2a8bf8b56fcfa51200382385ea8909a3cbecdad612310c114d3f6c99 - languageName: node - linkType: hard - -"@pkgjs/parseargs@npm:^0.11.0": - version: 0.11.0 - resolution: "@pkgjs/parseargs@npm:0.11.0" - checksum: 10c0/5bd7576bb1b38a47a7fc7b51ac9f38748e772beebc56200450c4a817d712232b8f1d3ef70532c80840243c657d491cf6a6be1e3a214cff907645819fdc34aadd - languageName: node - linkType: hard - "@protobufjs/aspromise@npm:^1.1.1, @protobufjs/aspromise@npm:^1.1.2": version: 1.1.2 resolution: "@protobufjs/aspromise@npm:1.1.2" @@ -1129,13 +925,6 @@ __metadata: languageName: node linkType: hard -"abbrev@npm:^2.0.0": - version: 2.0.0 - resolution: "abbrev@npm:2.0.0" - checksum: 10c0/f742a5a107473946f426c691c08daba61a1d15942616f300b5d32fd735be88fef5cba24201757b6c407fd564555fb48c751cfa33519b2605c8a7aadd22baf372 - languageName: node - linkType: hard - "acorn-import-attributes@npm:^1.9.5": version: 1.9.5 resolution: "acorn-import-attributes@npm:1.9.5" @@ -1190,25 +979,6 @@ __metadata: languageName: node linkType: hard -"agent-base@npm:^7.0.2, agent-base@npm:^7.1.0, agent-base@npm:^7.1.1": - version: 7.1.1 - resolution: "agent-base@npm:7.1.1" - dependencies: - debug: "npm:^4.3.4" - checksum: 10c0/e59ce7bed9c63bf071a30cc471f2933862044c97fd9958967bfe22521d7a0f601ce4ed5a8c011799d0c726ca70312142ae193bbebb60f576b52be19d4a363b50 - languageName: node - linkType: hard - -"aggregate-error@npm:^3.0.0": - version: 3.1.0 - resolution: "aggregate-error@npm:3.1.0" - dependencies: - clean-stack: "npm:^2.0.0" - indent-string: "npm:^4.0.0" - checksum: 10c0/a42f67faa79e3e6687a4923050e7c9807db3848a037076f791d10e092677d65c1d2d863b7848560699f40fc0502c19f40963fb1cd1fb3d338a7423df8e45e039 - languageName: node - linkType: hard - "ajv@npm:^6.12.4": version: 6.12.6 resolution: "ajv@npm:6.12.6" @@ -1244,7 +1014,7 @@ __metadata: languageName: node linkType: hard -"ansi-styles@npm:^6.0.0, ansi-styles@npm:^6.1.0, ansi-styles@npm:^6.2.1": +"ansi-styles@npm:^6.0.0, ansi-styles@npm:^6.2.1": version: 6.2.1 resolution: "ansi-styles@npm:6.2.1" checksum: 10c0/5d1ec38c123984bcedd996eac680d548f31828bd679a66db2bdf11844634dde55fec3efa9c6bb1d89056a5e79c1ac540c4c784d592ea1d25028a92227d2f2d5c @@ -1508,26 +1278,6 @@ __metadata: languageName: node linkType: hard -"cacache@npm:^18.0.0": - version: 18.0.3 - resolution: "cacache@npm:18.0.3" - dependencies: - "@npmcli/fs": "npm:^3.1.0" - fs-minipass: "npm:^3.0.0" - glob: "npm:^10.2.2" - lru-cache: "npm:^10.0.1" - minipass: "npm:^7.0.3" - minipass-collect: "npm:^2.0.1" - minipass-flush: "npm:^1.0.5" - minipass-pipeline: "npm:^1.2.4" - p-map: "npm:^4.0.0" - ssri: "npm:^10.0.0" - tar: "npm:^6.1.11" - unique-filename: "npm:^3.0.0" - checksum: 10c0/dfda92840bb371fb66b88c087c61a74544363b37a265023223a99965b16a16bbb87661fe4948718d79df6e0cc04e85e62784fbcf1832b2a5e54ff4c46fbb45b7 - languageName: node - linkType: hard - "call-bind@npm:^1.0.5": version: 1.0.7 resolution: "call-bind@npm:1.0.7" @@ -1616,13 +1366,6 @@ __metadata: languageName: node linkType: hard -"clean-stack@npm:^2.0.0": - version: 2.2.0 - resolution: "clean-stack@npm:2.2.0" - checksum: 10c0/1f90262d5f6230a17e27d0c190b09d47ebe7efdd76a03b5a1127863f7b3c9aec4c3e6c8bb3a7bbf81d553d56a1fd35728f5a8ef4c63f867ac8d690109742a8c1 - languageName: node - linkType: hard - "cli-truncate@npm:^4.0.0": version: 4.0.0 resolution: "cli-truncate@npm:4.0.0" @@ -1747,7 +1490,7 @@ __metadata: languageName: node linkType: hard -"cross-spawn@npm:^7.0.0, cross-spawn@npm:^7.0.2, cross-spawn@npm:^7.0.3": +"cross-spawn@npm:^7.0.2, cross-spawn@npm:^7.0.3": version: 7.0.3 resolution: "cross-spawn@npm:7.0.3" dependencies: @@ -1868,13 +1611,6 @@ __metadata: languageName: node linkType: hard -"eastasianwidth@npm:^0.2.0": - version: 0.2.0 - resolution: "eastasianwidth@npm:0.2.0" - checksum: 10c0/26f364ebcdb6395f95124fda411f63137a4bfb5d3a06453f7f23dfe52502905bd84e0488172e0f9ec295fdc45f05c23d5d91baf16bd26f0fe9acd777a188dc39 - languageName: node - linkType: hard - "elliptic@npm:^6.5.4": version: 6.5.7 resolution: "elliptic@npm:6.5.7" @@ -1911,36 +1647,6 @@ __metadata: languageName: node linkType: hard -"emoji-regex@npm:^9.2.2": - version: 9.2.2 - resolution: "emoji-regex@npm:9.2.2" - checksum: 10c0/af014e759a72064cf66e6e694a7fc6b0ed3d8db680427b021a89727689671cefe9d04151b2cad51dbaf85d5ba790d061cd167f1cf32eb7b281f6368b3c181639 - languageName: node - linkType: hard - -"encoding@npm:^0.1.13": - version: 0.1.13 - resolution: "encoding@npm:0.1.13" - dependencies: - iconv-lite: "npm:^0.6.2" - checksum: 10c0/36d938712ff00fe1f4bac88b43bcffb5930c1efa57bbcdca9d67e1d9d6c57cfb1200fb01efe0f3109b2ce99b231f90779532814a81370a1bd3274a0f58585039 - languageName: node - linkType: hard - -"env-paths@npm:^2.2.0": - version: 2.2.1 - resolution: "env-paths@npm:2.2.1" - checksum: 10c0/285325677bf00e30845e330eec32894f5105529db97496ee3f598478e50f008c5352a41a30e5e72ec9de8a542b5a570b85699cd63bd2bc646dbcb9f311d83bc4 - languageName: node - linkType: hard - -"err-code@npm:^2.0.2": - version: 2.0.3 - resolution: "err-code@npm:2.0.3" - checksum: 10c0/b642f7b4dd4a376e954947550a3065a9ece6733ab8e51ad80db727aaae0817c2e99b02a97a3d6cecc648a97848305e728289cf312d09af395403a90c9d4d8a66 - languageName: node - linkType: hard - "es-define-property@npm:^1.0.0": version: 1.0.0 resolution: "es-define-property@npm:1.0.0" @@ -1957,86 +1663,6 @@ __metadata: languageName: node linkType: hard -"esbuild@npm:~0.21.4": - version: 0.21.5 - resolution: "esbuild@npm:0.21.5" - dependencies: - "@esbuild/aix-ppc64": "npm:0.21.5" - "@esbuild/android-arm": "npm:0.21.5" - "@esbuild/android-arm64": "npm:0.21.5" - "@esbuild/android-x64": "npm:0.21.5" - "@esbuild/darwin-arm64": "npm:0.21.5" - "@esbuild/darwin-x64": "npm:0.21.5" - "@esbuild/freebsd-arm64": "npm:0.21.5" - "@esbuild/freebsd-x64": "npm:0.21.5" - "@esbuild/linux-arm": "npm:0.21.5" - "@esbuild/linux-arm64": "npm:0.21.5" - "@esbuild/linux-ia32": "npm:0.21.5" - "@esbuild/linux-loong64": "npm:0.21.5" - "@esbuild/linux-mips64el": "npm:0.21.5" - "@esbuild/linux-ppc64": "npm:0.21.5" - "@esbuild/linux-riscv64": "npm:0.21.5" - "@esbuild/linux-s390x": "npm:0.21.5" - "@esbuild/linux-x64": "npm:0.21.5" - "@esbuild/netbsd-x64": "npm:0.21.5" - "@esbuild/openbsd-x64": "npm:0.21.5" - "@esbuild/sunos-x64": "npm:0.21.5" - "@esbuild/win32-arm64": "npm:0.21.5" - "@esbuild/win32-ia32": "npm:0.21.5" - "@esbuild/win32-x64": "npm:0.21.5" - dependenciesMeta: - "@esbuild/aix-ppc64": - optional: true - "@esbuild/android-arm": - optional: true - "@esbuild/android-arm64": - optional: true - "@esbuild/android-x64": - optional: true - "@esbuild/darwin-arm64": - optional: true - "@esbuild/darwin-x64": - optional: true - "@esbuild/freebsd-arm64": - optional: true - "@esbuild/freebsd-x64": - optional: true - "@esbuild/linux-arm": - optional: true - "@esbuild/linux-arm64": - optional: true - "@esbuild/linux-ia32": - optional: true - "@esbuild/linux-loong64": - optional: true - "@esbuild/linux-mips64el": - optional: true - "@esbuild/linux-ppc64": - optional: true - "@esbuild/linux-riscv64": - optional: true - "@esbuild/linux-s390x": - optional: true - "@esbuild/linux-x64": - optional: true - "@esbuild/netbsd-x64": - optional: true - "@esbuild/openbsd-x64": - optional: true - "@esbuild/sunos-x64": - optional: true - "@esbuild/win32-arm64": - optional: true - "@esbuild/win32-ia32": - optional: true - "@esbuild/win32-x64": - optional: true - bin: - esbuild: bin/esbuild - checksum: 10c0/fa08508adf683c3f399e8a014a6382a6b65542213431e26206c0720e536b31c09b50798747c2a105a4bbba1d9767b8d3615a74c2f7bf1ddf6d836cd11eb672de - languageName: node - linkType: hard - "escalade@npm:^3.1.1": version: 3.1.2 resolution: "escalade@npm:3.1.2" @@ -2221,13 +1847,6 @@ __metadata: languageName: node linkType: hard -"exponential-backoff@npm:^3.1.1": - version: 3.1.1 - resolution: "exponential-backoff@npm:3.1.1" - checksum: 10c0/160456d2d647e6019640bd07111634d8c353038d9fa40176afb7cd49b0548bdae83b56d05e907c2cce2300b81cae35d800ef92fefb9d0208e190fa3b7d6bb579 - languageName: node - linkType: hard - "fast-check@npm:^3.0.0": version: 3.19.0 resolution: "fast-check@npm:3.19.0" @@ -2375,16 +1994,6 @@ __metadata: languageName: node linkType: hard -"foreground-child@npm:^3.1.0": - version: 3.1.1 - resolution: "foreground-child@npm:3.1.1" - dependencies: - cross-spawn: "npm:^7.0.0" - signal-exit: "npm:^4.0.1" - checksum: 10c0/9700a0285628abaeb37007c9a4d92bd49f67210f09067638774338e146c8e9c825c5c877f072b2f75f41dc6a2d0be8664f79ffc03f6576649f54a84fb9b47de0 - languageName: node - linkType: hard - "form-data@npm:^4.0.0": version: 4.0.0 resolution: "form-data@npm:4.0.0" @@ -2428,15 +2037,6 @@ __metadata: languageName: node linkType: hard -"fs-minipass@npm:^3.0.0": - version: 3.0.3 - resolution: "fs-minipass@npm:3.0.3" - dependencies: - minipass: "npm:^7.0.3" - checksum: 10c0/63e80da2ff9b621e2cb1596abcb9207f1cf82b968b116ccd7b959e3323144cce7fb141462200971c38bbf2ecca51695069db45265705bed09a7cd93ae5b89f94 - languageName: node - linkType: hard - "fs.realpath@npm:^1.0.0": version: 1.0.0 resolution: "fs.realpath@npm:1.0.0" @@ -2444,25 +2044,6 @@ __metadata: languageName: node linkType: hard -"fsevents@npm:~2.3.3": - version: 2.3.3 - resolution: "fsevents@npm:2.3.3" - dependencies: - node-gyp: "npm:latest" - checksum: 10c0/a1f0c44595123ed717febbc478aa952e47adfc28e2092be66b8ab1635147254ca6cfe1df792a8997f22716d4cbafc73309899ff7bfac2ac3ad8cf2e4ecc3ec60 - conditions: os=darwin - languageName: node - linkType: hard - -"fsevents@patch:fsevents@npm%3A~2.3.3#optional!builtin": - version: 2.3.3 - resolution: "fsevents@patch:fsevents@npm%3A2.3.3#optional!builtin::version=2.3.3&hash=df0bf1" - dependencies: - node-gyp: "npm:latest" - conditions: os=darwin - languageName: node - linkType: hard - "function-bind@npm:^1.1.2": version: 1.1.2 resolution: "function-bind@npm:1.1.2" @@ -2524,15 +2105,6 @@ __metadata: languageName: node linkType: hard -"get-tsconfig@npm:^4.7.5": - version: 4.7.5 - resolution: "get-tsconfig@npm:4.7.5" - dependencies: - resolve-pkg-maps: "npm:^1.0.0" - checksum: 10c0/a917dff2ba9ee187c41945736bf9bbab65de31ce5bc1effd76267be483a7340915cff232199406379f26517d2d0a4edcdbcda8cca599c2480a0f2cf1e1de3efa - languageName: node - linkType: hard - "glob-parent@npm:^5.1.2": version: 5.1.2 resolution: "glob-parent@npm:5.1.2" @@ -2551,21 +2123,6 @@ __metadata: languageName: node linkType: hard -"glob@npm:^10.2.2, glob@npm:^10.3.10": - version: 10.4.1 - resolution: "glob@npm:10.4.1" - dependencies: - foreground-child: "npm:^3.1.0" - jackspeak: "npm:^3.1.2" - minimatch: "npm:^9.0.4" - minipass: "npm:^7.1.2" - path-scurry: "npm:^1.11.1" - bin: - glob: dist/esm/bin.mjs - checksum: 10c0/77f2900ed98b9cc2a0e1901ee5e476d664dae3cd0f1b662b8bfd4ccf00d0edc31a11595807706a274ca10e1e251411bbf2e8e976c82bed0d879a9b89343ed379 - languageName: node - linkType: hard - "glob@npm:^7.1.3": version: 7.2.3 resolution: "glob@npm:7.2.3" @@ -2636,7 +2193,7 @@ __metadata: languageName: node linkType: hard -"graceful-fs@npm:^4.1.11, graceful-fs@npm:^4.1.6, graceful-fs@npm:^4.2.0, graceful-fs@npm:^4.2.6, graceful-fs@npm:^4.2.9": +"graceful-fs@npm:^4.1.11, graceful-fs@npm:^4.1.6, graceful-fs@npm:^4.2.0, graceful-fs@npm:^4.2.9": version: 4.2.11 resolution: "graceful-fs@npm:4.2.11" checksum: 10c0/386d011a553e02bc594ac2ca0bd6d9e4c22d7fa8cfbfc448a6d148c59ea881b092db9dbe3547ae4b88e55f1b01f7c4a2ecc53b310c042793e63aa44cf6c257f2 @@ -2717,23 +2274,6 @@ __metadata: languageName: node linkType: hard -"http-cache-semantics@npm:^4.1.1": - version: 4.1.1 - resolution: "http-cache-semantics@npm:4.1.1" - checksum: 10c0/ce1319b8a382eb3cbb4a37c19f6bfe14e5bb5be3d09079e885e8c513ab2d3cd9214902f8a31c9dc4e37022633ceabfc2d697405deeaf1b8f3552bb4ed996fdfc - languageName: node - linkType: hard - -"http-proxy-agent@npm:^7.0.0": - version: 7.0.2 - resolution: "http-proxy-agent@npm:7.0.2" - dependencies: - agent-base: "npm:^7.1.0" - debug: "npm:^4.3.4" - checksum: 10c0/4207b06a4580fb85dd6dff521f0abf6db517489e70863dca1a0291daa7f2d3d2d6015a57bd702af068ea5cf9f1f6ff72314f5f5b4228d299c0904135d2aef921 - languageName: node - linkType: hard - "https-proxy-agent@npm:^5.0.0": version: 5.0.1 resolution: "https-proxy-agent@npm:5.0.1" @@ -2744,16 +2284,6 @@ __metadata: languageName: node linkType: hard -"https-proxy-agent@npm:^7.0.1": - version: 7.0.4 - resolution: "https-proxy-agent@npm:7.0.4" - dependencies: - agent-base: "npm:^7.0.2" - debug: "npm:4" - checksum: 10c0/bc4f7c38da32a5fc622450b6cb49a24ff596f9bd48dcedb52d2da3fa1c1a80e100fb506bd59b326c012f21c863c69b275c23de1a01d0b84db396822fdf25e52b - languageName: node - linkType: hard - "human-signals@npm:^7.0.0": version: 7.0.0 resolution: "human-signals@npm:7.0.0" @@ -2761,15 +2291,6 @@ __metadata: languageName: node linkType: hard -"iconv-lite@npm:^0.6.2": - version: 0.6.3 - resolution: "iconv-lite@npm:0.6.3" - dependencies: - safer-buffer: "npm:>= 2.1.2 < 3.0.0" - checksum: 10c0/98102bc66b33fcf5ac044099d1257ba0b7ad5e3ccd3221f34dd508ab4070edff183276221684e1e0555b145fce0850c9f7d2b60a9fcac50fbb4ea0d6e845a3b1 - languageName: node - linkType: hard - "ignore-by-default@npm:^2.1.0": version: 2.1.0 resolution: "ignore-by-default@npm:2.1.0" @@ -2801,13 +2322,6 @@ __metadata: languageName: node linkType: hard -"indent-string@npm:^4.0.0": - version: 4.0.0 - resolution: "indent-string@npm:4.0.0" - checksum: 10c0/1e1904ddb0cb3d6cce7cd09e27a90184908b7a5d5c21b92e232c93579d314f0b83c246ffb035493d0504b1e9147ba2c9b21df0030f48673fba0496ecd698161f - languageName: node - linkType: hard - "indent-string@npm:^5.0.0": version: 5.0.0 resolution: "indent-string@npm:5.0.0" @@ -2832,16 +2346,6 @@ __metadata: languageName: node linkType: hard -"ip-address@npm:^9.0.5": - version: 9.0.5 - resolution: "ip-address@npm:9.0.5" - dependencies: - jsbn: "npm:1.1.0" - sprintf-js: "npm:^1.1.3" - checksum: 10c0/331cd07fafcb3b24100613e4b53e1a2b4feab11e671e655d46dc09ee233da5011284d09ca40c4ecbdfe1d0004f462958675c224a804259f2f78d2465a87824bc - languageName: node - linkType: hard - "irregular-plurals@npm:^3.3.0": version: 3.5.0 resolution: "irregular-plurals@npm:3.5.0" @@ -2888,13 +2392,6 @@ __metadata: languageName: node linkType: hard -"is-lambda@npm:^1.0.1": - version: 1.0.1 - resolution: "is-lambda@npm:1.0.1" - checksum: 10c0/85fee098ae62ba6f1e24cf22678805473c7afd0fb3978a3aa260e354cb7bcb3a5806cf0a98403188465efedec41ab4348e8e4e79305d409601323855b3839d4d - languageName: node - linkType: hard - "is-number@npm:^7.0.0": version: 7.0.0 resolution: "is-number@npm:7.0.0" @@ -2967,13 +2464,6 @@ __metadata: languageName: node linkType: hard -"isexe@npm:^3.1.1": - version: 3.1.1 - resolution: "isexe@npm:3.1.1" - checksum: 10c0/9ec257654093443eb0a528a9c8cbba9c0ca7616ccb40abd6dde7202734d96bb86e4ac0d764f0f8cd965856aacbff2f4ce23e730dc19dfb41e3b0d865ca6fdcc7 - languageName: node - linkType: hard - "isomorphic-ws@npm:^4.0.1": version: 4.0.1 resolution: "isomorphic-ws@npm:4.0.1" @@ -2983,19 +2473,6 @@ __metadata: languageName: node linkType: hard -"jackspeak@npm:^3.1.2": - version: 3.4.0 - resolution: "jackspeak@npm:3.4.0" - dependencies: - "@isaacs/cliui": "npm:^8.0.2" - "@pkgjs/parseargs": "npm:^0.11.0" - dependenciesMeta: - "@pkgjs/parseargs": - optional: true - checksum: 10c0/7e42d1ea411b4d57d43ea8a6afbca9224382804359cb72626d0fc45bb8db1de5ad0248283c3db45fe73e77210750d4fcc7c2b4fe5d24fda94aaa24d658295c5f - languageName: node - linkType: hard - "js-string-escape@npm:^1.0.1": version: 1.0.1 resolution: "js-string-escape@npm:1.0.1" @@ -3026,13 +2503,6 @@ __metadata: languageName: node linkType: hard -"jsbn@npm:1.1.0": - version: 1.1.0 - resolution: "jsbn@npm:1.1.0" - checksum: 10c0/4f907fb78d7b712e11dea8c165fe0921f81a657d3443dde75359ed52eb2b5d33ce6773d97985a089f09a65edd80b11cb75c767b57ba47391fee4c969f7215c96 - languageName: node - linkType: hard - "json-buffer@npm:3.0.1": version: 3.0.1 resolution: "json-buffer@npm:3.0.1" @@ -3167,13 +2637,6 @@ __metadata: languageName: node linkType: hard -"lru-cache@npm:^10.0.1, lru-cache@npm:^10.2.0": - version: 10.2.2 - resolution: "lru-cache@npm:10.2.2" - checksum: 10c0/402d31094335851220d0b00985084288136136992979d0e015f0f1697e15d1c86052d7d53ae86b614e5b058425606efffc6969a31a091085d7a2b80a8a1e26d6 - languageName: node - linkType: hard - "make-dir@npm:^3.1.0": version: 3.1.0 resolution: "make-dir@npm:3.1.0" @@ -3183,26 +2646,6 @@ __metadata: languageName: node linkType: hard -"make-fetch-happen@npm:^13.0.0": - version: 13.0.1 - resolution: "make-fetch-happen@npm:13.0.1" - dependencies: - "@npmcli/agent": "npm:^2.0.0" - cacache: "npm:^18.0.0" - http-cache-semantics: "npm:^4.1.1" - is-lambda: "npm:^1.0.1" - minipass: "npm:^7.0.2" - minipass-fetch: "npm:^3.0.0" - minipass-flush: "npm:^1.0.5" - minipass-pipeline: "npm:^1.2.4" - negotiator: "npm:^0.6.3" - proc-log: "npm:^4.2.0" - promise-retry: "npm:^2.0.1" - ssri: "npm:^10.0.0" - checksum: 10c0/df5f4dbb6d98153b751bccf4dc4cc500de85a96a9331db9805596c46aa9f99d9555983954e6c1266d9f981ae37a9e4647f42b9a4bb5466f867f4012e582c9e7e - languageName: node - linkType: hard - "matcher@npm:^5.0.0": version: 5.0.0 resolution: "matcher@npm:5.0.0" @@ -3312,15 +2755,6 @@ __metadata: languageName: node linkType: hard -"minimatch@npm:^9.0.4": - version: 9.0.4 - resolution: "minimatch@npm:9.0.4" - dependencies: - brace-expansion: "npm:^2.0.1" - checksum: 10c0/2c16f21f50e64922864e560ff97c587d15fd491f65d92a677a344e970fe62aafdbeafe648965fa96d33c061b4d0eabfe0213466203dd793367e7f28658cf6414 - languageName: node - linkType: hard - "minimist@npm:^1.2.6": version: 1.2.8 resolution: "minimist@npm:1.2.8" @@ -3328,57 +2762,6 @@ __metadata: languageName: node linkType: hard -"minipass-collect@npm:^2.0.1": - version: 2.0.1 - resolution: "minipass-collect@npm:2.0.1" - dependencies: - minipass: "npm:^7.0.3" - checksum: 10c0/5167e73f62bb74cc5019594709c77e6a742051a647fe9499abf03c71dca75515b7959d67a764bdc4f8b361cf897fbf25e2d9869ee039203ed45240f48b9aa06e - languageName: node - linkType: hard - -"minipass-fetch@npm:^3.0.0": - version: 3.0.5 - resolution: "minipass-fetch@npm:3.0.5" - dependencies: - encoding: "npm:^0.1.13" - minipass: "npm:^7.0.3" - minipass-sized: "npm:^1.0.3" - minizlib: "npm:^2.1.2" - dependenciesMeta: - encoding: - optional: true - checksum: 10c0/9d702d57f556274286fdd97e406fc38a2f5c8d15e158b498d7393b1105974b21249289ec571fa2b51e038a4872bfc82710111cf75fae98c662f3d6f95e72152b - languageName: node - linkType: hard - -"minipass-flush@npm:^1.0.5": - version: 1.0.5 - resolution: "minipass-flush@npm:1.0.5" - dependencies: - minipass: "npm:^3.0.0" - checksum: 10c0/2a51b63feb799d2bb34669205eee7c0eaf9dce01883261a5b77410c9408aa447e478efd191b4de6fc1101e796ff5892f8443ef20d9544385819093dbb32d36bd - languageName: node - linkType: hard - -"minipass-pipeline@npm:^1.2.4": - version: 1.2.4 - resolution: "minipass-pipeline@npm:1.2.4" - dependencies: - minipass: "npm:^3.0.0" - checksum: 10c0/cbda57cea20b140b797505dc2cac71581a70b3247b84480c1fed5ca5ba46c25ecc25f68bfc9e6dcb1a6e9017dab5c7ada5eab73ad4f0a49d84e35093e0c643f2 - languageName: node - linkType: hard - -"minipass-sized@npm:^1.0.3": - version: 1.0.3 - resolution: "minipass-sized@npm:1.0.3" - dependencies: - minipass: "npm:^3.0.0" - checksum: 10c0/298f124753efdc745cfe0f2bdfdd81ba25b9f4e753ca4a2066eb17c821f25d48acea607dfc997633ee5bf7b6dfffb4eee4f2051eb168663f0b99fad2fa4829cb - languageName: node - linkType: hard - "minipass@npm:^3.0.0": version: 3.3.6 resolution: "minipass@npm:3.3.6" @@ -3395,14 +2778,7 @@ __metadata: languageName: node linkType: hard -"minipass@npm:^5.0.0 || ^6.0.2 || ^7.0.0, minipass@npm:^7.0.2, minipass@npm:^7.0.3, minipass@npm:^7.1.2": - version: 7.1.2 - resolution: "minipass@npm:7.1.2" - checksum: 10c0/b0fd20bb9fb56e5fa9a8bfac539e8915ae07430a619e4b86ff71f5fc757ef3924b23b2c4230393af1eda647ed3d75739e4e0acb250a6b1eb277cf7f8fe449557 - languageName: node - linkType: hard - -"minizlib@npm:^2.1.1, minizlib@npm:^2.1.2": +"minizlib@npm:^2.1.1": version: 2.1.2 resolution: "minizlib@npm:2.1.2" dependencies: @@ -3442,13 +2818,6 @@ __metadata: languageName: node linkType: hard -"negotiator@npm:^0.6.3": - version: 0.6.3 - resolution: "negotiator@npm:0.6.3" - checksum: 10c0/3ec9fd413e7bf071c937ae60d572bc67155262068ed522cf4b3be5edbe6ddf67d095ec03a3a14ebf8fc8e95f8e1d61be4869db0dbb0de696f6b837358bd43fc2 - languageName: node - linkType: hard - "node-fetch@npm:^2.6.12, node-fetch@npm:^2.6.7, node-fetch@npm:^2.6.9": version: 2.7.0 resolution: "node-fetch@npm:2.7.0" @@ -3474,26 +2843,6 @@ __metadata: languageName: node linkType: hard -"node-gyp@npm:latest": - version: 10.1.0 - resolution: "node-gyp@npm:10.1.0" - dependencies: - env-paths: "npm:^2.2.0" - exponential-backoff: "npm:^3.1.1" - glob: "npm:^10.3.10" - graceful-fs: "npm:^4.2.6" - make-fetch-happen: "npm:^13.0.0" - nopt: "npm:^7.0.0" - proc-log: "npm:^3.0.0" - semver: "npm:^7.3.5" - tar: "npm:^6.1.2" - which: "npm:^4.0.0" - bin: - node-gyp: bin/node-gyp.js - checksum: 10c0/9cc821111ca244a01fb7f054db7523ab0a0cd837f665267eb962eb87695d71fb1e681f9e21464cc2fd7c05530dc4c81b810bca1a88f7d7186909b74477491a3c - languageName: node - linkType: hard - "nofilter@npm:^3.1.0": version: 3.1.0 resolution: "nofilter@npm:3.1.0" @@ -3512,17 +2861,6 @@ __metadata: languageName: node linkType: hard -"nopt@npm:^7.0.0": - version: 7.2.1 - resolution: "nopt@npm:7.2.1" - dependencies: - abbrev: "npm:^2.0.0" - bin: - nopt: bin/nopt.js - checksum: 10c0/a069c7c736767121242037a22a788863accfa932ab285a1eb569eb8cd534b09d17206f68c37f096ae785647435e0c5a5a0a67b42ec743e481a455e5ae6a6df81 - languageName: node - linkType: hard - "npm-run-path@npm:^5.2.0": version: 5.3.0 resolution: "npm-run-path@npm:5.3.0" @@ -3616,15 +2954,6 @@ __metadata: languageName: node linkType: hard -"p-map@npm:^4.0.0": - version: 4.0.0 - resolution: "p-map@npm:4.0.0" - dependencies: - aggregate-error: "npm:^3.0.0" - checksum: 10c0/592c05bd6262c466ce269ff172bb8de7c6975afca9b50c975135b974e9bdaafbfe80e61aaaf5be6d1200ba08b30ead04b88cfa7e25ff1e3b93ab28c9f62a2c75 - languageName: node - linkType: hard - "p-map@npm:^7.0.2": version: 7.0.2 resolution: "p-map@npm:7.0.2" @@ -3711,16 +3040,6 @@ __metadata: languageName: node linkType: hard -"path-scurry@npm:^1.11.1": - version: 1.11.1 - resolution: "path-scurry@npm:1.11.1" - dependencies: - lru-cache: "npm:^10.2.0" - minipass: "npm:^5.0.0 || ^6.0.2 || ^7.0.0" - checksum: 10c0/32a13711a2a505616ae1cc1b5076801e453e7aae6ac40ab55b388bb91b9d0547a52f5aaceff710ea400205f18691120d4431e520afbe4266b836fadede15872d - languageName: node - linkType: hard - "path-type@npm:^4.0.0": version: 4.0.0 resolution: "path-type@npm:4.0.0" @@ -3783,30 +3102,6 @@ __metadata: languageName: node linkType: hard -"proc-log@npm:^3.0.0": - version: 3.0.0 - resolution: "proc-log@npm:3.0.0" - checksum: 10c0/f66430e4ff947dbb996058f6fd22de2c66612ae1a89b097744e17fb18a4e8e7a86db99eda52ccf15e53f00b63f4ec0b0911581ff2aac0355b625c8eac509b0dc - languageName: node - linkType: hard - -"proc-log@npm:^4.2.0": - version: 4.2.0 - resolution: "proc-log@npm:4.2.0" - checksum: 10c0/17db4757c2a5c44c1e545170e6c70a26f7de58feb985091fb1763f5081cab3d01b181fb2dd240c9f4a4255a1d9227d163d5771b7e69c9e49a561692db865efb9 - languageName: node - linkType: hard - -"promise-retry@npm:^2.0.1": - version: 2.0.1 - resolution: "promise-retry@npm:2.0.1" - dependencies: - err-code: "npm:^2.0.2" - retry: "npm:^0.12.0" - checksum: 10c0/9c7045a1a2928094b5b9b15336dcd2a7b1c052f674550df63cc3f36cd44028e5080448175b6f6ca32b642de81150f5e7b1a98b728f15cb069f2dd60ac2616b96 - languageName: node - linkType: hard - "protobufjs@npm:^6.8.8": version: 6.11.4 resolution: "protobufjs@npm:6.11.4" @@ -3914,20 +3209,6 @@ __metadata: languageName: node linkType: hard -"resolve-pkg-maps@npm:^1.0.0": - version: 1.0.0 - resolution: "resolve-pkg-maps@npm:1.0.0" - checksum: 10c0/fb8f7bbe2ca281a73b7ef423a1cbc786fb244bd7a95cbe5c3fba25b27d327150beca8ba02f622baea65919a57e061eb5005204daa5f93ed590d9b77463a567ab - languageName: node - linkType: hard - -"retry@npm:^0.12.0": - version: 0.12.0 - resolution: "retry@npm:0.12.0" - checksum: 10c0/59933e8501727ba13ad73ef4a04d5280b3717fd650408460c987392efe9d7be2040778ed8ebe933c5cbd63da3dcc37919c141ef8af0a54a6e4fca5a2af177bfe - languageName: node - linkType: hard - "reusify@npm:^1.0.4": version: 1.0.4 resolution: "reusify@npm:1.0.4" @@ -3982,7 +3263,6 @@ __metadata: patch-package: "npm:^8.0.0" starshipjs: "npm:2.4.1" ts-blank-space: "npm:^0.4.4" - tsx: "npm:^4.15.6" typescript: "npm:~5.6.2" languageName: unknown linkType: soft @@ -4003,13 +3283,6 @@ __metadata: languageName: node linkType: hard -"safer-buffer@npm:>= 2.1.2 < 3.0.0": - version: 2.1.2 - resolution: "safer-buffer@npm:2.1.2" - checksum: 10c0/7e3c8b2e88a1841c9671094bbaeebd94448111dd90a81a1f606f3f67708a6ec57763b3b47f06da09fc6054193e0e6709e77325415dc8422b04497a8070fa02d4 - languageName: node - linkType: hard - "semver@npm:^6.0.0": version: 6.3.1 resolution: "semver@npm:6.3.1" @@ -4149,41 +3422,6 @@ __metadata: languageName: node linkType: hard -"smart-buffer@npm:^4.2.0": - version: 4.2.0 - resolution: "smart-buffer@npm:4.2.0" - checksum: 10c0/a16775323e1404dd43fabafe7460be13a471e021637bc7889468eb45ce6a6b207261f454e4e530a19500cc962c4cc5348583520843b363f4193cee5c00e1e539 - languageName: node - linkType: hard - -"socks-proxy-agent@npm:^8.0.3": - version: 8.0.3 - resolution: "socks-proxy-agent@npm:8.0.3" - dependencies: - agent-base: "npm:^7.1.1" - debug: "npm:^4.3.4" - socks: "npm:^2.7.1" - checksum: 10c0/4950529affd8ccd6951575e21c1b7be8531b24d924aa4df3ee32df506af34b618c4e50d261f4cc603f1bfd8d426915b7d629966c8ce45b05fb5ad8c8b9a6459d - languageName: node - linkType: hard - -"socks@npm:^2.7.1": - version: 2.8.3 - resolution: "socks@npm:2.8.3" - dependencies: - ip-address: "npm:^9.0.5" - smart-buffer: "npm:^4.2.0" - checksum: 10c0/d54a52bf9325165770b674a67241143a3d8b4e4c8884560c4e0e078aace2a728dffc7f70150660f51b85797c4e1a3b82f9b7aa25e0a0ceae1a243365da5c51a7 - languageName: node - linkType: hard - -"sprintf-js@npm:^1.1.3": - version: 1.1.3 - resolution: "sprintf-js@npm:1.1.3" - checksum: 10c0/09270dc4f30d479e666aee820eacd9e464215cdff53848b443964202bf4051490538e5dd1b42e1a65cf7296916ca17640aebf63dae9812749c7542ee5f288dec - languageName: node - linkType: hard - "sprintf-js@npm:~1.0.2": version: 1.0.3 resolution: "sprintf-js@npm:1.0.3" @@ -4191,15 +3429,6 @@ __metadata: languageName: node linkType: hard -"ssri@npm:^10.0.0": - version: 10.0.6 - resolution: "ssri@npm:10.0.6" - dependencies: - minipass: "npm:^7.0.3" - checksum: 10c0/e5a1e23a4057a86a97971465418f22ea89bd439ac36ade88812dd920e4e61873e8abd6a9b72a03a67ef50faa00a2daf1ab745c5a15b46d03e0544a0296354227 - languageName: node - linkType: hard - "stack-utils@npm:^2.0.6": version: 2.0.6 resolution: "stack-utils@npm:2.0.6" @@ -4221,7 +3450,7 @@ __metadata: languageName: node linkType: hard -"string-width-cjs@npm:string-width@^4.2.0, string-width@npm:^1.0.2 || 2 || 3 || 4, string-width@npm:^4.1.0, string-width@npm:^4.2.0, string-width@npm:^4.2.3": +"string-width@npm:^1.0.2 || 2 || 3 || 4, string-width@npm:^4.1.0, string-width@npm:^4.2.0, string-width@npm:^4.2.3": version: 4.2.3 resolution: "string-width@npm:4.2.3" dependencies: @@ -4232,17 +3461,6 @@ __metadata: languageName: node linkType: hard -"string-width@npm:^5.0.1, string-width@npm:^5.1.2": - version: 5.1.2 - resolution: "string-width@npm:5.1.2" - dependencies: - eastasianwidth: "npm:^0.2.0" - emoji-regex: "npm:^9.2.2" - strip-ansi: "npm:^7.0.1" - checksum: 10c0/ab9c4264443d35b8b923cbdd513a089a60de339216d3b0ed3be3ba57d6880e1a192b70ae17225f764d7adbf5994e9bb8df253a944736c15a0240eff553c678ca - languageName: node - linkType: hard - "string-width@npm:^7.0.0": version: 7.1.0 resolution: "string-width@npm:7.1.0" @@ -4263,7 +3481,7 @@ __metadata: languageName: node linkType: hard -"strip-ansi-cjs@npm:strip-ansi@^6.0.1, strip-ansi@npm:^6.0.0, strip-ansi@npm:^6.0.1": +"strip-ansi@npm:^6.0.0, strip-ansi@npm:^6.0.1": version: 6.0.1 resolution: "strip-ansi@npm:6.0.1" dependencies: @@ -4323,7 +3541,7 @@ __metadata: languageName: node linkType: hard -"tar@npm:^6.1.11, tar@npm:^6.1.2": +"tar@npm:^6.1.11": version: 6.2.1 resolution: "tar@npm:6.2.1" dependencies: @@ -4401,22 +3619,6 @@ __metadata: languageName: node linkType: hard -"tsx@npm:^4.15.6": - version: 4.15.6 - resolution: "tsx@npm:4.15.6" - dependencies: - esbuild: "npm:~0.21.4" - fsevents: "npm:~2.3.3" - get-tsconfig: "npm:^4.7.5" - dependenciesMeta: - fsevents: - optional: true - bin: - tsx: dist/cli.mjs - checksum: 10c0/c44e489d35b8b4795d68164572eb9e322a707290aa0786c2aac0f5c7782a884dfec38d557d74471b981a8314b2c7f6612078451d0429db028a23cb54a37e83a0 - languageName: node - linkType: hard - "type-check@npm:^0.4.0, type-check@npm:~0.4.0": version: 0.4.0 resolution: "type-check@npm:0.4.0" @@ -4501,24 +3703,6 @@ __metadata: languageName: node linkType: hard -"unique-filename@npm:^3.0.0": - version: 3.0.0 - resolution: "unique-filename@npm:3.0.0" - dependencies: - unique-slug: "npm:^4.0.0" - checksum: 10c0/6363e40b2fa758eb5ec5e21b3c7fb83e5da8dcfbd866cc0c199d5534c42f03b9ea9ab069769cc388e1d7ab93b4eeef28ef506ab5f18d910ef29617715101884f - languageName: node - linkType: hard - -"unique-slug@npm:^4.0.0": - version: 4.0.0 - resolution: "unique-slug@npm:4.0.0" - dependencies: - imurmurhash: "npm:^0.1.4" - checksum: 10c0/cb811d9d54eb5821b81b18205750be84cb015c20a4a44280794e915f5a0a70223ce39066781a354e872df3572e8155c228f43ff0cce94c7cbf4da2cc7cbdd635 - languageName: node - linkType: hard - "universalify@npm:^2.0.0": version: 2.0.1 resolution: "universalify@npm:2.0.1" @@ -4577,17 +3761,6 @@ __metadata: languageName: node linkType: hard -"which@npm:^4.0.0": - version: 4.0.0 - resolution: "which@npm:4.0.0" - dependencies: - isexe: "npm:^3.1.1" - bin: - node-which: bin/which.js - checksum: 10c0/449fa5c44ed120ccecfe18c433296a4978a7583bf2391c50abce13f76878d2476defde04d0f79db8165bdf432853c1f8389d0485ca6e8ebce3bbcded513d5e6a - languageName: node - linkType: hard - "wide-align@npm:^1.1.2": version: 1.1.5 resolution: "wide-align@npm:1.1.5" @@ -4604,7 +3777,7 @@ __metadata: languageName: node linkType: hard -"wrap-ansi-cjs@npm:wrap-ansi@^7.0.0, wrap-ansi@npm:^7.0.0": +"wrap-ansi@npm:^7.0.0": version: 7.0.0 resolution: "wrap-ansi@npm:7.0.0" dependencies: @@ -4615,17 +3788,6 @@ __metadata: languageName: node linkType: hard -"wrap-ansi@npm:^8.1.0": - version: 8.1.0 - resolution: "wrap-ansi@npm:8.1.0" - dependencies: - ansi-styles: "npm:^6.1.0" - string-width: "npm:^5.0.1" - strip-ansi: "npm:^7.0.1" - checksum: 10c0/138ff58a41d2f877eae87e3282c0630fc2789012fc1af4d6bd626eeb9a2f9a65ca92005e6e69a75c7b85a68479fe7443c7dbe1eb8fbaa681a4491364b7c55c60 - languageName: node - linkType: hard - "wrappy@npm:1": version: 1.0.2 resolution: "wrappy@npm:1.0.2" From 13b32687a39d81263ee821a68347a11c4f93e1d6 Mon Sep 17 00:00:00 2001 From: Turadg Aleahmad Date: Mon, 2 Dec 2024 14:26:37 -0800 Subject: [PATCH 13/56] build: run scripts with shebang --- multichain-testing/Makefile | 12 ++++++------ multichain-testing/scripts/dev-setup.sh | 0 multichain-testing/scripts/install.sh | 0 multichain-testing/scripts/pod-readiness.ts | 1 + multichain-testing/scripts/port-forward.sh | 0 multichain-testing/scripts/update-config.sh | 0 6 files changed, 7 insertions(+), 6 deletions(-) mode change 100644 => 100755 multichain-testing/scripts/dev-setup.sh mode change 100644 => 100755 multichain-testing/scripts/install.sh mode change 100644 => 100755 multichain-testing/scripts/pod-readiness.ts mode change 100644 => 100755 multichain-testing/scripts/port-forward.sh mode change 100644 => 100755 multichain-testing/scripts/update-config.sh diff --git a/multichain-testing/Makefile b/multichain-testing/Makefile index 9fd5b926b18..5301808e631 100644 --- a/multichain-testing/Makefile +++ b/multichain-testing/Makefile @@ -26,14 +26,14 @@ clean: stop clean-kind .PHONY: check setup-deps: - bash $(CURDIR)/scripts/dev-setup.sh + $(CURDIR)/scripts/dev-setup.sh ############################################################################### ### Helm Charts ### ############################################################################### install: - bash $(CURDIR)/scripts/install.sh --config $(FILE) --name $(NAME) --version $(HELM_VERSION) + $(CURDIR)/scripts/install.sh --config $(FILE) --name $(NAME) --version $(HELM_VERSION) delete: -helm delete $(NAME) @@ -44,7 +44,7 @@ delete: .PHONY: port-forward port-forward: - bash $(CURDIR)/scripts/port-forward.sh --config=$(FILE) + $(CURDIR)/scripts/port-forward.sh --config=$(FILE) .PHONY: stop-forward stop-forward: @@ -76,8 +76,8 @@ fund-provision-pool: kubectl exec -i agoriclocal-genesis-0 -c validator -- agd tx bank send faucet $(PROVISION_POOL_ADDR) 1000000000uist -y -b block override-chain-registry: - node_modules/.bin/tsx scripts/fetch-starship-chain-info.ts && \ - node_modules/.bin/tsx scripts/deploy-cli.ts src/revise-chain-info.builder.js + scripts/fetch-starship-chain-info.ts && \ + scripts/deploy-cli.ts src/revise-chain-info.builder.js ADDR=agoric1ldmtatp24qlllgxmrsjzcpe20fvlkp448zcuce COIN=1000000000uist @@ -98,7 +98,7 @@ tail-slog: .PHONY: wait-for-pods wait-for-pods: - node_modules/.bin/tsx scripts/pod-readiness.ts + scripts/pod-readiness.ts .PHONY: start start: install wait-for-pods port-forward fund-provision-pool override-chain-registry diff --git a/multichain-testing/scripts/dev-setup.sh b/multichain-testing/scripts/dev-setup.sh old mode 100644 new mode 100755 diff --git a/multichain-testing/scripts/install.sh b/multichain-testing/scripts/install.sh old mode 100644 new mode 100755 diff --git a/multichain-testing/scripts/pod-readiness.ts b/multichain-testing/scripts/pod-readiness.ts old mode 100644 new mode 100755 index 315980e0ffc..4218c3ec175 --- a/multichain-testing/scripts/pod-readiness.ts +++ b/multichain-testing/scripts/pod-readiness.ts @@ -1,3 +1,4 @@ +#!/usr/bin/env node --import ts-blank-space/register import { execa } from 'execa'; import { sleep } from '../tools/sleep.js'; diff --git a/multichain-testing/scripts/port-forward.sh b/multichain-testing/scripts/port-forward.sh old mode 100644 new mode 100755 diff --git a/multichain-testing/scripts/update-config.sh b/multichain-testing/scripts/update-config.sh old mode 100644 new mode 100755 From df36ae6823beeab209c1afd81d18a486b522f8c9 Mon Sep 17 00:00:00 2001 From: Turadg Aleahmad Date: Mon, 2 Dec 2024 15:33:33 -0800 Subject: [PATCH 14/56] build: Linux compatible shebang --- a3p-integration/proposals/z:acceptance/scripts/test-vaults.ts | 2 +- multichain-testing/scripts/deploy-cli.ts | 2 +- multichain-testing/scripts/fetch-starship-chain-info.ts | 2 +- multichain-testing/scripts/pod-readiness.ts | 2 +- packages/orchestration/scripts/fetch-chain-info.ts | 2 +- scripts/report-globals.ts | 2 +- 6 files changed, 6 insertions(+), 6 deletions(-) diff --git a/a3p-integration/proposals/z:acceptance/scripts/test-vaults.ts b/a3p-integration/proposals/z:acceptance/scripts/test-vaults.ts index 7a5c2fa1aec..48a216fe8e8 100755 --- a/a3p-integration/proposals/z:acceptance/scripts/test-vaults.ts +++ b/a3p-integration/proposals/z:acceptance/scripts/test-vaults.ts @@ -1,4 +1,4 @@ -#!/usr/bin/env node --import ts-blank-space/register +#!/usr/bin/env -S node --import ts-blank-space/register /* eslint-disable @jessie.js/safe-await-separator */ import { diff --git a/multichain-testing/scripts/deploy-cli.ts b/multichain-testing/scripts/deploy-cli.ts index 47cb70e1153..2dfd7b94d06 100755 --- a/multichain-testing/scripts/deploy-cli.ts +++ b/multichain-testing/scripts/deploy-cli.ts @@ -1,4 +1,4 @@ -#!/usr/bin/env node --import ts-blank-space/register +#!/usr/bin/env -S node --import ts-blank-space/register import '@endo/init/debug.js'; import { execa } from 'execa'; diff --git a/multichain-testing/scripts/fetch-starship-chain-info.ts b/multichain-testing/scripts/fetch-starship-chain-info.ts index fa4ec834687..b51da77c566 100755 --- a/multichain-testing/scripts/fetch-starship-chain-info.ts +++ b/multichain-testing/scripts/fetch-starship-chain-info.ts @@ -1,4 +1,4 @@ -#!/usr/bin/env node --import ts-blank-space/register +#!/usr/bin/env -S node --import ts-blank-space/register /* eslint-env node */ import fsp from 'node:fs/promises'; diff --git a/multichain-testing/scripts/pod-readiness.ts b/multichain-testing/scripts/pod-readiness.ts index 4218c3ec175..087fd5bb040 100755 --- a/multichain-testing/scripts/pod-readiness.ts +++ b/multichain-testing/scripts/pod-readiness.ts @@ -1,4 +1,4 @@ -#!/usr/bin/env node --import ts-blank-space/register +#!/usr/bin/env -S node --import ts-blank-space/register import { execa } from 'execa'; import { sleep } from '../tools/sleep.js'; diff --git a/packages/orchestration/scripts/fetch-chain-info.ts b/packages/orchestration/scripts/fetch-chain-info.ts index 90ffb0627be..75ee144555e 100755 --- a/packages/orchestration/scripts/fetch-chain-info.ts +++ b/packages/orchestration/scripts/fetch-chain-info.ts @@ -1,4 +1,4 @@ -#!/usr/bin/env node --import ts-blank-space/register +#!/usr/bin/env -S node --import ts-blank-space/register /** @file Fetch canonical chain info to generate the minimum needed for agoricNames */ import { ChainRegistryClient } from '@chain-registry/client'; import fsp from 'node:fs/promises'; diff --git a/scripts/report-globals.ts b/scripts/report-globals.ts index ff5fe426dc5..2661d134e6d 100755 --- a/scripts/report-globals.ts +++ b/scripts/report-globals.ts @@ -1,4 +1,4 @@ -#!/usr/bin/env node --import ts-blank-space/register +#!/usr/bin/env -S node --import ts-blank-space/register /* eslint-disable -- hacky script for irregular reports */ /** From ecd89390aacf72582ff519c797f2f2e2ba439c58 Mon Sep 17 00:00:00 2001 From: Turadg Aleahmad Date: Tue, 3 Dec 2024 09:22:28 -0800 Subject: [PATCH 15/56] chore(deps): bump typescript deps --- multichain-testing/package.json | 6 +- multichain-testing/yarn.lock | 283 ++++++++++++++------------------ 2 files changed, 123 insertions(+), 166 deletions(-) diff --git a/multichain-testing/package.json b/multichain-testing/package.json index 8d204854818..e6bf20b73ea 100644 --- a/multichain-testing/package.json +++ b/multichain-testing/package.json @@ -28,8 +28,8 @@ "@types/eslint": "^8", "@types/fs-extra": "^11", "@types/node": "^22.0.0", - "@typescript-eslint/eslint-plugin": "^6.20.0", - "@typescript-eslint/parser": "^6.20.0", + "@typescript-eslint/eslint-plugin": "^8.17.0", + "@typescript-eslint/parser": "^8.17.0", "ava": "^6.2.0", "eslint": "^8.56.0", "eslint-config-prettier": "^9.1.0", @@ -38,7 +38,7 @@ "patch-package": "^8.0.0", "starshipjs": "2.4.1", "ts-blank-space": "^0.4.4", - "typescript": "~5.6.2" + "typescript": "~5.7.2" }, "resolutions": { "axios": "1.6.7" diff --git a/multichain-testing/yarn.lock b/multichain-testing/yarn.lock index f6abb8ce779..ae4d0d64393 100644 --- a/multichain-testing/yarn.lock +++ b/multichain-testing/yarn.lock @@ -447,7 +447,14 @@ __metadata: languageName: node linkType: hard -"@eslint-community/regexpp@npm:^4.5.1, @eslint-community/regexpp@npm:^4.6.1": +"@eslint-community/regexpp@npm:^4.10.0": + version: 4.12.1 + resolution: "@eslint-community/regexpp@npm:4.12.1" + checksum: 10c0/a03d98c246bcb9109aec2c08e4d10c8d010256538dcb3f56610191607214523d4fb1b00aa81df830b6dffb74c5fa0be03642513a289c567949d3e550ca11cdf6 + languageName: node + linkType: hard + +"@eslint-community/regexpp@npm:^4.6.1": version: 4.10.1 resolution: "@eslint-community/regexpp@npm:4.10.1" checksum: 10c0/f59376025d0c91dd9fdf18d33941df499292a3ecba3e9889c360f3f6590197d30755604588786cdca0f9030be315a26b206014af4b65c0ff85b4ec49043de780 @@ -711,7 +718,7 @@ __metadata: languageName: node linkType: hard -"@types/json-schema@npm:*, @types/json-schema@npm:^7.0.12": +"@types/json-schema@npm:*": version: 7.0.15 resolution: "@types/json-schema@npm:7.0.15" checksum: 10c0/a996a745e6c5d60292f36731dd41341339d4eeed8180bb09226e5c8d23759067692b1d88e5d91d72ee83dfc00d3aca8e7bd43ea120516c17922cbcb7c3e252db @@ -752,133 +759,124 @@ __metadata: languageName: node linkType: hard -"@types/semver@npm:^7.5.0": - version: 7.5.8 - resolution: "@types/semver@npm:7.5.8" - checksum: 10c0/8663ff927234d1c5fcc04b33062cb2b9fcfbe0f5f351ed26c4d1e1581657deebd506b41ff7fdf89e787e3d33ce05854bc01686379b89e9c49b564c4cfa988efa - languageName: node - linkType: hard - -"@typescript-eslint/eslint-plugin@npm:^6.20.0": - version: 6.21.0 - resolution: "@typescript-eslint/eslint-plugin@npm:6.21.0" +"@typescript-eslint/eslint-plugin@npm:^8.17.0": + version: 8.17.0 + resolution: "@typescript-eslint/eslint-plugin@npm:8.17.0" dependencies: - "@eslint-community/regexpp": "npm:^4.5.1" - "@typescript-eslint/scope-manager": "npm:6.21.0" - "@typescript-eslint/type-utils": "npm:6.21.0" - "@typescript-eslint/utils": "npm:6.21.0" - "@typescript-eslint/visitor-keys": "npm:6.21.0" - debug: "npm:^4.3.4" + "@eslint-community/regexpp": "npm:^4.10.0" + "@typescript-eslint/scope-manager": "npm:8.17.0" + "@typescript-eslint/type-utils": "npm:8.17.0" + "@typescript-eslint/utils": "npm:8.17.0" + "@typescript-eslint/visitor-keys": "npm:8.17.0" graphemer: "npm:^1.4.0" - ignore: "npm:^5.2.4" + ignore: "npm:^5.3.1" natural-compare: "npm:^1.4.0" - semver: "npm:^7.5.4" - ts-api-utils: "npm:^1.0.1" + ts-api-utils: "npm:^1.3.0" peerDependencies: - "@typescript-eslint/parser": ^6.0.0 || ^6.0.0-alpha - eslint: ^7.0.0 || ^8.0.0 + "@typescript-eslint/parser": ^8.0.0 || ^8.0.0-alpha.0 + eslint: ^8.57.0 || ^9.0.0 peerDependenciesMeta: typescript: optional: true - checksum: 10c0/f911a79ee64d642f814a3b6cdb0d324b5f45d9ef955c5033e78903f626b7239b4aa773e464a38c3e667519066169d983538f2bf8e5d00228af587c9d438fb344 + checksum: 10c0/d78778173571a9a1370345bc2aa3e850235a489d16b8a8b5ba3086b988bbef7549bdae38e509d7a679ba3179c688cc5a408376b158be402770836e94ffc9602d languageName: node linkType: hard -"@typescript-eslint/parser@npm:^6.20.0": - version: 6.21.0 - resolution: "@typescript-eslint/parser@npm:6.21.0" +"@typescript-eslint/parser@npm:^8.17.0": + version: 8.17.0 + resolution: "@typescript-eslint/parser@npm:8.17.0" dependencies: - "@typescript-eslint/scope-manager": "npm:6.21.0" - "@typescript-eslint/types": "npm:6.21.0" - "@typescript-eslint/typescript-estree": "npm:6.21.0" - "@typescript-eslint/visitor-keys": "npm:6.21.0" + "@typescript-eslint/scope-manager": "npm:8.17.0" + "@typescript-eslint/types": "npm:8.17.0" + "@typescript-eslint/typescript-estree": "npm:8.17.0" + "@typescript-eslint/visitor-keys": "npm:8.17.0" debug: "npm:^4.3.4" peerDependencies: - eslint: ^7.0.0 || ^8.0.0 + eslint: ^8.57.0 || ^9.0.0 peerDependenciesMeta: typescript: optional: true - checksum: 10c0/a8f99820679decd0d115c0af61903fb1de3b1b5bec412dc72b67670bf636de77ab07f2a68ee65d6da7976039bbf636907f9d5ca546db3f0b98a31ffbc225bc7d + checksum: 10c0/2543deadf01302a92d3b6f58a4c14f98d8936c4d976e7da05e3bb65608f19d8de93b25282e343c304eca3e3f37f2ac23e97fa9c11c6edff36dd2d4f6b601a630 languageName: node linkType: hard -"@typescript-eslint/scope-manager@npm:6.21.0": - version: 6.21.0 - resolution: "@typescript-eslint/scope-manager@npm:6.21.0" +"@typescript-eslint/scope-manager@npm:8.17.0": + version: 8.17.0 + resolution: "@typescript-eslint/scope-manager@npm:8.17.0" dependencies: - "@typescript-eslint/types": "npm:6.21.0" - "@typescript-eslint/visitor-keys": "npm:6.21.0" - checksum: 10c0/eaf868938d811cbbea33e97e44ba7050d2b6892202cea6a9622c486b85ab1cf801979edf78036179a8ba4ac26f1dfdf7fcc83a68c1ff66be0b3a8e9a9989b526 + "@typescript-eslint/types": "npm:8.17.0" + "@typescript-eslint/visitor-keys": "npm:8.17.0" + checksum: 10c0/0c08d14240bad4b3f6874f08ba80b29db1a6657437089a6f109db458c544d835bcdc06ba9140bb4f835233ba4326d9a86e6cf6bdb5209960d2f7025aa3191f4f languageName: node linkType: hard -"@typescript-eslint/type-utils@npm:6.21.0": - version: 6.21.0 - resolution: "@typescript-eslint/type-utils@npm:6.21.0" +"@typescript-eslint/type-utils@npm:8.17.0": + version: 8.17.0 + resolution: "@typescript-eslint/type-utils@npm:8.17.0" dependencies: - "@typescript-eslint/typescript-estree": "npm:6.21.0" - "@typescript-eslint/utils": "npm:6.21.0" + "@typescript-eslint/typescript-estree": "npm:8.17.0" + "@typescript-eslint/utils": "npm:8.17.0" debug: "npm:^4.3.4" - ts-api-utils: "npm:^1.0.1" + ts-api-utils: "npm:^1.3.0" peerDependencies: - eslint: ^7.0.0 || ^8.0.0 + eslint: ^8.57.0 || ^9.0.0 peerDependenciesMeta: typescript: optional: true - checksum: 10c0/7409c97d1c4a4386b488962739c4f1b5b04dc60cf51f8cd88e6b12541f84d84c6b8b67e491a147a2c95f9ec486539bf4519fb9d418411aef6537b9c156468117 + checksum: 10c0/6138ec71b5692d4b5e0bf3d7f66a6fa4e91ddea7031907b0ac45a7693df0a2f4cc5bca7218311e0639620d636ceb7efec83a137dfcd5938304d873b774fcc8bd languageName: node linkType: hard -"@typescript-eslint/types@npm:6.21.0": - version: 6.21.0 - resolution: "@typescript-eslint/types@npm:6.21.0" - checksum: 10c0/020631d3223bbcff8a0da3efbdf058220a8f48a3de221563996ad1dcc30d6c08dadc3f7608cc08830d21c0d565efd2db19b557b9528921c78aabb605eef2d74d +"@typescript-eslint/types@npm:8.17.0": + version: 8.17.0 + resolution: "@typescript-eslint/types@npm:8.17.0" + checksum: 10c0/26b1bf9dfc3ee783c85c6f354b84c28706d5689d777f3ff2de2cb496e45f9d0189c0d561c03ccbc8b24712438be17cf63dd0871ff3ca2083e7f48749770d1893 languageName: node linkType: hard -"@typescript-eslint/typescript-estree@npm:6.21.0": - version: 6.21.0 - resolution: "@typescript-eslint/typescript-estree@npm:6.21.0" +"@typescript-eslint/typescript-estree@npm:8.17.0": + version: 8.17.0 + resolution: "@typescript-eslint/typescript-estree@npm:8.17.0" dependencies: - "@typescript-eslint/types": "npm:6.21.0" - "@typescript-eslint/visitor-keys": "npm:6.21.0" + "@typescript-eslint/types": "npm:8.17.0" + "@typescript-eslint/visitor-keys": "npm:8.17.0" debug: "npm:^4.3.4" - globby: "npm:^11.1.0" + fast-glob: "npm:^3.3.2" is-glob: "npm:^4.0.3" - minimatch: "npm:9.0.3" - semver: "npm:^7.5.4" - ts-api-utils: "npm:^1.0.1" + minimatch: "npm:^9.0.4" + semver: "npm:^7.6.0" + ts-api-utils: "npm:^1.3.0" peerDependenciesMeta: typescript: optional: true - checksum: 10c0/af1438c60f080045ebb330155a8c9bb90db345d5069cdd5d01b67de502abb7449d6c75500519df829f913a6b3f490ade3e8215279b6bdc63d0fb0ae61034df5f + checksum: 10c0/523013f9b5cf2c58c566868e4c3b0b9ac1b4807223a6d64e2a7c58e01e53b6587ba61f1a8241eade361f3f426d6057657515473176141ef8aebb352bc0d223ce languageName: node linkType: hard -"@typescript-eslint/utils@npm:6.21.0": - version: 6.21.0 - resolution: "@typescript-eslint/utils@npm:6.21.0" +"@typescript-eslint/utils@npm:8.17.0": + version: 8.17.0 + resolution: "@typescript-eslint/utils@npm:8.17.0" dependencies: "@eslint-community/eslint-utils": "npm:^4.4.0" - "@types/json-schema": "npm:^7.0.12" - "@types/semver": "npm:^7.5.0" - "@typescript-eslint/scope-manager": "npm:6.21.0" - "@typescript-eslint/types": "npm:6.21.0" - "@typescript-eslint/typescript-estree": "npm:6.21.0" - semver: "npm:^7.5.4" + "@typescript-eslint/scope-manager": "npm:8.17.0" + "@typescript-eslint/types": "npm:8.17.0" + "@typescript-eslint/typescript-estree": "npm:8.17.0" peerDependencies: - eslint: ^7.0.0 || ^8.0.0 - checksum: 10c0/ab2df3833b2582d4e5467a484d08942b4f2f7208f8e09d67de510008eb8001a9b7460f2f9ba11c12086fd3cdcac0c626761c7995c2c6b5657d5fa6b82030a32d + eslint: ^8.57.0 || ^9.0.0 + peerDependenciesMeta: + typescript: + optional: true + checksum: 10c0/a9785ae5f7e7b51d521dc3f48b15093948e4fcd03352c0b60f39bae366cbc935947d215f91e2ae3182d52fa6affb5ccbb50feff487bd1209011f3e0da02cdf07 languageName: node linkType: hard -"@typescript-eslint/visitor-keys@npm:6.21.0": - version: 6.21.0 - resolution: "@typescript-eslint/visitor-keys@npm:6.21.0" +"@typescript-eslint/visitor-keys@npm:8.17.0": + version: 8.17.0 + resolution: "@typescript-eslint/visitor-keys@npm:8.17.0" dependencies: - "@typescript-eslint/types": "npm:6.21.0" - eslint-visitor-keys: "npm:^3.4.1" - checksum: 10c0/7395f69739cfa1cb83c1fb2fad30afa2a814756367302fb4facd5893eff66abc807e8d8f63eba94ed3b0fe0c1c996ac9a1680bcbf0f83717acedc3f2bb724fbf + "@typescript-eslint/types": "npm:8.17.0" + eslint-visitor-keys: "npm:^4.2.0" + checksum: 10c0/9144c4e4a63034fb2031a0ee1fc77e80594f30cab3faafa9a1f7f83782695774dd32fac8986f260698b4e150b4dd52444f2611c07e4c101501f08353eb47c82c languageName: node linkType: hard @@ -1061,13 +1059,6 @@ __metadata: languageName: node linkType: hard -"array-union@npm:^2.1.0": - version: 2.1.0 - resolution: "array-union@npm:2.1.0" - checksum: 10c0/429897e68110374f39b771ec47a7161fc6a8fc33e196857c0a396dc75df0b5f65e4d046674db764330b6bb66b39ef48dd7c53b6a2ee75cfb0681e0c1a7033962 - languageName: node - linkType: hard - "arrgv@npm:^1.0.2": version: 1.0.2 resolution: "arrgv@npm:1.0.2" @@ -1593,15 +1584,6 @@ __metadata: languageName: node linkType: hard -"dir-glob@npm:^3.0.1": - version: 3.0.1 - resolution: "dir-glob@npm:3.0.1" - dependencies: - path-type: "npm:^4.0.0" - checksum: 10c0/dcac00920a4d503e38bb64001acb19df4efc14536ada475725e12f52c16777afdee4db827f55f13a908ee7efc0cb282e2e3dbaeeb98c0993dd93d1802d3bf00c - languageName: node - linkType: hard - "doctrine@npm:^3.0.0": version: 3.0.0 resolution: "doctrine@npm:3.0.0" @@ -1719,6 +1701,13 @@ __metadata: languageName: node linkType: hard +"eslint-visitor-keys@npm:^4.2.0": + version: 4.2.0 + resolution: "eslint-visitor-keys@npm:4.2.0" + checksum: 10c0/2ed81c663b147ca6f578312919483eb040295bbab759e5a371953456c636c5b49a559883e2677112453728d66293c0a4c90ab11cab3428cf02a0236d2e738269 + languageName: node + linkType: hard + "eslint@npm:^8.56.0": version: 8.57.0 resolution: "eslint@npm:8.57.0" @@ -1870,7 +1859,7 @@ __metadata: languageName: node linkType: hard -"fast-glob@npm:^3.2.9, fast-glob@npm:^3.3.2": +"fast-glob@npm:^3.3.2": version: 3.3.2 resolution: "fast-glob@npm:3.3.2" dependencies: @@ -2156,20 +2145,6 @@ __metadata: languageName: node linkType: hard -"globby@npm:^11.1.0": - version: 11.1.0 - resolution: "globby@npm:11.1.0" - dependencies: - array-union: "npm:^2.1.0" - dir-glob: "npm:^3.0.1" - fast-glob: "npm:^3.2.9" - ignore: "npm:^5.2.0" - merge2: "npm:^1.4.1" - slash: "npm:^3.0.0" - checksum: 10c0/b39511b4afe4bd8a7aead3a27c4ade2b9968649abab0a6c28b1a90141b96ca68ca5db1302f7c7bd29eab66bf51e13916b8e0a3d0ac08f75e1e84a39b35691189 - languageName: node - linkType: hard - "globby@npm:^14.0.2": version: 14.0.2 resolution: "globby@npm:14.0.2" @@ -2305,6 +2280,13 @@ __metadata: languageName: node linkType: hard +"ignore@npm:^5.3.1": + version: 5.3.2 + resolution: "ignore@npm:5.3.2" + checksum: 10c0/f9f652c957983634ded1e7f02da3b559a0d4cc210fca3792cb67f1b153623c9c42efdc1c4121af171e295444459fc4a9201101fb041b1104a3c000bccb188337 + languageName: node + linkType: hard + "import-fresh@npm:^3.2.1": version: 3.3.0 resolution: "import-fresh@npm:3.3.0" @@ -2673,7 +2655,7 @@ __metadata: languageName: node linkType: hard -"merge2@npm:^1.3.0, merge2@npm:^1.4.1": +"merge2@npm:^1.3.0": version: 1.4.1 resolution: "merge2@npm:1.4.1" checksum: 10c0/254a8a4605b58f450308fc474c82ac9a094848081bf4c06778200207820e5193726dc563a0d2c16468810516a5c97d9d3ea0ca6585d23c58ccfff2403e8dbbeb @@ -2737,15 +2719,6 @@ __metadata: languageName: node linkType: hard -"minimatch@npm:9.0.3": - version: 9.0.3 - resolution: "minimatch@npm:9.0.3" - dependencies: - brace-expansion: "npm:^2.0.1" - checksum: 10c0/85f407dcd38ac3e180f425e86553911d101455ca3ad5544d6a7cec16286657e4f8a9aa6695803025c55e31e35a91a2252b5dc8e7d527211278b8b65b4dbd5eac - languageName: node - linkType: hard - "minimatch@npm:^3.0.5, minimatch@npm:^3.1.1, minimatch@npm:^3.1.2": version: 3.1.2 resolution: "minimatch@npm:3.1.2" @@ -2755,6 +2728,15 @@ __metadata: languageName: node linkType: hard +"minimatch@npm:^9.0.4": + version: 9.0.5 + resolution: "minimatch@npm:9.0.5" + dependencies: + brace-expansion: "npm:^2.0.1" + checksum: 10c0/de96cf5e35bdf0eab3e2c853522f98ffbe9a36c37797778d2665231ec1f20a9447a7e567cb640901f89e4daaa95ae5d70c65a9e8aa2bb0019b6facbc3c0575ed + languageName: node + linkType: hard + "minimist@npm:^1.2.6": version: 1.2.8 resolution: "minimist@npm:1.2.8" @@ -3040,13 +3022,6 @@ __metadata: languageName: node linkType: hard -"path-type@npm:^4.0.0": - version: 4.0.0 - resolution: "path-type@npm:4.0.0" - checksum: 10c0/666f6973f332f27581371efaf303fd6c272cc43c2057b37aa99e3643158c7e4b2626549555d88626e99ea9e046f82f32e41bbde5f1508547e9a11b149b52387c - languageName: node - linkType: hard - "path-type@npm:^5.0.0": version: 5.0.0 resolution: "path-type@npm:5.0.0" @@ -3253,8 +3228,8 @@ __metadata: "@types/eslint": "npm:^8" "@types/fs-extra": "npm:^11" "@types/node": "npm:^22.0.0" - "@typescript-eslint/eslint-plugin": "npm:^6.20.0" - "@typescript-eslint/parser": "npm:^6.20.0" + "@typescript-eslint/eslint-plugin": "npm:^8.17.0" + "@typescript-eslint/parser": "npm:^8.17.0" ava: "npm:^6.2.0" eslint: "npm:^8.56.0" eslint-config-prettier: "npm:^9.1.0" @@ -3263,7 +3238,7 @@ __metadata: patch-package: "npm:^8.0.0" starshipjs: "npm:2.4.1" ts-blank-space: "npm:^0.4.4" - typescript: "npm:~5.6.2" + typescript: "npm:~5.7.2" languageName: unknown linkType: soft @@ -3292,7 +3267,7 @@ __metadata: languageName: node linkType: hard -"semver@npm:^7.3.2, semver@npm:^7.3.5, semver@npm:^7.5.3, semver@npm:^7.5.4": +"semver@npm:^7.3.2, semver@npm:^7.3.5, semver@npm:^7.5.3": version: 7.6.2 resolution: "semver@npm:7.6.2" bin: @@ -3301,6 +3276,15 @@ __metadata: languageName: node linkType: hard +"semver@npm:^7.6.0": + version: 7.6.3 + resolution: "semver@npm:7.6.3" + bin: + semver: bin/semver.js + checksum: 10c0/88f33e148b210c153873cb08cfe1e281d518aaa9a666d4d148add6560db5cd3c582f3a08ccb91f38d5f379ead256da9931234ed122057f40bb5766e65e58adaf + languageName: node + linkType: hard + "serialize-error@npm:^7.0.1": version: 7.0.1 resolution: "serialize-error@npm:7.0.1" @@ -3398,13 +3382,6 @@ __metadata: languageName: node linkType: hard -"slash@npm:^3.0.0": - version: 3.0.0 - resolution: "slash@npm:3.0.0" - checksum: 10c0/e18488c6a42bdfd4ac5be85b2ced3ccd0224773baae6ad42cfbb9ec74fc07f9fa8396bd35ee638084ead7a2a0818eb5e7151111544d4731ce843019dab4be47b - languageName: node - linkType: hard - "slash@npm:^5.1.0": version: 5.1.0 resolution: "slash@npm:5.1.0" @@ -3601,12 +3578,12 @@ __metadata: languageName: node linkType: hard -"ts-api-utils@npm:^1.0.1": - version: 1.3.0 - resolution: "ts-api-utils@npm:1.3.0" +"ts-api-utils@npm:^1.3.0": + version: 1.4.3 + resolution: "ts-api-utils@npm:1.4.3" peerDependencies: typescript: ">=4.2.0" - checksum: 10c0/f54a0ba9ed56ce66baea90a3fa087a484002e807f28a8ccb2d070c75e76bde64bd0f6dce98b3802834156306050871b67eec325cb4e918015a360a3f0868c77c + checksum: 10c0/e65dc6e7e8141140c23e1dc94984bf995d4f6801919c71d6dc27cf0cd51b100a91ffcfe5217626193e5bea9d46831e8586febdc7e172df3f1091a7384299e23a languageName: node linkType: hard @@ -3642,7 +3619,7 @@ __metadata: languageName: node linkType: hard -"typescript@npm:5.1.6 - 5.7.x": +"typescript@npm:5.1.6 - 5.7.x, typescript@npm:~5.7.2": version: 5.7.2 resolution: "typescript@npm:5.7.2" bin: @@ -3652,17 +3629,7 @@ __metadata: languageName: node linkType: hard -"typescript@npm:~5.6.2": - version: 5.6.3 - resolution: "typescript@npm:5.6.3" - bin: - tsc: bin/tsc - tsserver: bin/tsserver - checksum: 10c0/44f61d3fb15c35359bc60399cb8127c30bae554cd555b8e2b46d68fa79d680354b83320ad419ff1b81a0bdf324197b29affe6cc28988cd6a74d4ac60c94f9799 - languageName: node - linkType: hard - -"typescript@patch:typescript@npm%3A5.1.6 - 5.7.x#optional!builtin": +"typescript@patch:typescript@npm%3A5.1.6 - 5.7.x#optional!builtin, typescript@patch:typescript@npm%3A~5.7.2#optional!builtin": version: 5.7.2 resolution: "typescript@patch:typescript@npm%3A5.7.2#optional!builtin::version=5.7.2&hash=5786d5" bin: @@ -3672,16 +3639,6 @@ __metadata: languageName: node linkType: hard -"typescript@patch:typescript@npm%3A~5.6.2#optional!builtin": - version: 5.6.3 - resolution: "typescript@patch:typescript@npm%3A5.6.3#optional!builtin::version=5.6.3&hash=8c6c40" - bin: - tsc: bin/tsc - tsserver: bin/tsserver - checksum: 10c0/7c9d2e07c81226d60435939618c91ec2ff0b75fbfa106eec3430f0fcf93a584bc6c73176676f532d78c3594fe28a54b36eb40b3d75593071a7ec91301533ace7 - languageName: node - linkType: hard - "undici-types@npm:~5.26.4": version: 5.26.5 resolution: "undici-types@npm:5.26.5" From c6ae87332c2952932b5ca1629d77c7fed4411367 Mon Sep 17 00:00:00 2001 From: Richard Gibson Date: Mon, 2 Dec 2024 15:35:20 -0500 Subject: [PATCH 16/56] refactor: Cleanup #10348 https://github.com/Agoric/agoric-sdk/pull/10348#discussion_r1855150615 --- packages/boot/tools/supports.ts | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/packages/boot/tools/supports.ts b/packages/boot/tools/supports.ts index 967fe12d257..603b8f54cd0 100644 --- a/packages/boot/tools/supports.ts +++ b/packages/boot/tools/supports.ts @@ -681,19 +681,19 @@ export const makeRunPolicyProvider = () => { /** @type {ReturnType | undefined} */ let policy; - let counting = false; + let policyEnabled = false; const meter = harden({ provideRunPolicy: () => { - if (counting && !policy) { + if (policyEnabled && !policy) { policy = computronCounter({ beansPerUnit }); } return policy; }, - /** @param {boolean} x */ - usePolicy: x => { - counting = x; - if (!counting) { + /** @param {boolean} forceEnabled */ + usePolicy: forceEnabled => { + policyEnabled = forceEnabled; + if (!policyEnabled) { policy = undefined; } }, From 50fda75f54adb4558cadb97aec76d2b1c85a67e3 Mon Sep 17 00:00:00 2001 From: Richard Gibson Date: Mon, 2 Dec 2024 15:35:20 -0500 Subject: [PATCH 17/56] refactor: Cleanup #10348 https://github.com/Agoric/agoric-sdk/pull/10348#discussion_r1855204572 --- packages/cosmic-swingset/src/computron-counter.js | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/packages/cosmic-swingset/src/computron-counter.js b/packages/cosmic-swingset/src/computron-counter.js index 4db024ca7a0..c21f4150be1 100644 --- a/packages/cosmic-swingset/src/computron-counter.js +++ b/packages/cosmic-swingset/src/computron-counter.js @@ -50,10 +50,7 @@ export function computronCounter( const defaultCleanupBudget = remainingCleanups.default; let cleanupStarted = false; let cleanupDone = false; - const cleanupPossible = - Object.values(remainingCleanups).length > 0 - ? Object.values(remainingCleanups).some(n => n > 0) - : defaultCleanupBudget > 0; + const cleanupPossible = Object.values(remainingCleanups).some(n => n > 0); if (!cleanupPossible) cleanupDone = true; /** @type {() => (false | import('@agoric/swingset-vat').CleanupBudget)} */ const allowCleanup = () => From a0798d295a66753944ff98ba9d570caf4aa47454 Mon Sep 17 00:00:00 2001 From: Richard Gibson Date: Mon, 2 Dec 2024 15:35:20 -0500 Subject: [PATCH 18/56] refactor: Cleanup #10348 Rename types/functions/parameters as suggested at: * https://github.com/Agoric/agoric-sdk/pull/10348#discussion_r1855147470 * https://github.com/Agoric/agoric-sdk/pull/10348#discussion_r1855150764 --- packages/SwingSet/tools/run-utils.js | 8 +++---- .../test/bootstrapTests/orchestration.test.ts | 22 +++++++++--------- .../bootstrapTests/price-feed-replace.test.ts | 8 +++---- packages/boot/tools/liquidation.ts | 10 ++++---- packages/boot/tools/supports.ts | 23 +++++++++++-------- 5 files changed, 38 insertions(+), 33 deletions(-) diff --git a/packages/SwingSet/tools/run-utils.js b/packages/SwingSet/tools/run-utils.js index d2676f1055b..bdb1a435390 100644 --- a/packages/SwingSet/tools/run-utils.js +++ b/packages/SwingSet/tools/run-utils.js @@ -7,13 +7,13 @@ import { makeQueue } from '@endo/stream'; * @import { RunPolicy } from '../src/types-external.js' */ -/** @typedef {{ provideRunPolicy: () => RunPolicy | undefined }} RunPolicyMaker */ +/** @typedef {{ provideRunPolicy: () => RunPolicy | undefined }} RunHarness */ /** * @param {import('../src/controller/controller.js').SwingsetController} controller - * @param {RunPolicyMaker} [perfTool] + * @param {RunHarness} [harness] */ -export const makeRunUtils = (controller, perfTool) => { +export const makeRunUtils = (controller, harness) => { const mutex = makeQueue(); const logRunFailure = reason => console.log('controller.run() failure', reason); @@ -31,7 +31,7 @@ export const makeRunUtils = (controller, perfTool) => { const queueAndRun = async (deliveryThunk, voidResult = false) => { await mutex.get(); const kpid = await deliveryThunk(); - const runPolicy = perfTool && perfTool.provideRunPolicy(); + const runPolicy = harness && harness.provideRunPolicy(); const runResultP = controller.run(runPolicy); mutex.put(runResultP.catch(logRunFailure)); await runResultP; diff --git a/packages/boot/test/bootstrapTests/orchestration.test.ts b/packages/boot/test/bootstrapTests/orchestration.test.ts index ec95a0c95ef..b51f13e6568 100644 --- a/packages/boot/test/bootstrapTests/orchestration.test.ts +++ b/packages/boot/test/bootstrapTests/orchestration.test.ts @@ -16,12 +16,12 @@ import { } from './walletFactory.js'; import { insistManagerType, - makeRunPolicyProvider, + makeSwingsetHarness, } from '../../tools/supports.js'; const test: TestFn< WalletFactoryTestContext & { - perfTool?: ReturnType; + harness?: ReturnType; } > = anyTest; @@ -40,14 +40,14 @@ const { test.before(async t => { insistManagerType(defaultManagerType); - const perfTool = - defaultManagerType === 'xsnap' ? makeRunPolicyProvider() : undefined; + const harness = + defaultManagerType === 'xsnap' ? makeSwingsetHarness() : undefined; const ctx = await makeWalletFactoryContext( t, '@agoric/vm-config/decentral-itest-orchestration-config.json', - { slogFile, defaultManagerType, perfTool }, + { slogFile, defaultManagerType, harness }, ); - t.context = { ...ctx, perfTool }; + t.context = { ...ctx, harness }; }); test.after.always(t => t.context.shutdown?.()); @@ -123,7 +123,7 @@ test.skip('stakeOsmo - queries', async t => { buildProposal, evalProposal, runUtils: { EV }, - perfTool, + harness, } = t.context; await evalProposal( buildProposal('@agoric/builders/scripts/orchestration/init-stakeOsmo.js'), @@ -162,7 +162,7 @@ test.serial('stakeAtom - smart wallet', async t => { agoricNamesRemotes, bridgeUtils: { flushInboundQueue }, readPublished, - perfTool, + harness, } = t.context; await evalProposal( @@ -173,7 +173,7 @@ test.serial('stakeAtom - smart wallet', async t => { 'agoric1testStakAtom', ); - perfTool?.usePolicy(true); + harness?.useRunPolicy(true); await wd.sendOffer({ id: 'request-account', invitationSpec: { @@ -183,8 +183,8 @@ test.serial('stakeAtom - smart wallet', async t => { }, proposal: {}, }); - perfTool && t.log('makeAccount computrons', perfTool.totalCount()); - perfTool?.usePolicy(false); + harness && t.log('makeAccount computrons', harness.totalComputronCount()); + harness?.useRunPolicy(false); await flushInboundQueue(); t.like(wd.getCurrentWalletRecord(), { diff --git a/packages/boot/test/bootstrapTests/price-feed-replace.test.ts b/packages/boot/test/bootstrapTests/price-feed-replace.test.ts index 3e7876b694c..c9a6178f0fd 100644 --- a/packages/boot/test/bootstrapTests/price-feed-replace.test.ts +++ b/packages/boot/test/bootstrapTests/price-feed-replace.test.ts @@ -64,7 +64,7 @@ test.serial('setupVaults; run updatePriceFeeds proposals', async t => { setupVaults, governanceDriver: gd, readPublished, - perfTool, + harness, } = t.context; await setupVaults(collateralBrandKey, managerIndex, setup); @@ -75,10 +75,10 @@ test.serial('setupVaults; run updatePriceFeeds proposals', async t => { roundId: 1n, }); - perfTool && perfTool.usePolicy(true); + harness && harness.useRunPolicy(true); await priceFeedDrivers[collateralBrandKey].setPrice(15.99); - perfTool && t.log('setPrice computrons', perfTool.totalCount()); - perfTool && perfTool.usePolicy(false); + harness && t.log('setPrice computrons', harness.totalComputronCount()); + harness && harness.useRunPolicy(false); t.like(readPublished('priceFeed.ATOM-USD_price_feed.latestRound'), { roundId: 2n, diff --git a/packages/boot/tools/liquidation.ts b/packages/boot/tools/liquidation.ts index 04fbe9e6499..6b386535ef0 100644 --- a/packages/boot/tools/liquidation.ts +++ b/packages/boot/tools/liquidation.ts @@ -9,7 +9,7 @@ import { } from '@agoric/vats/tools/board-utils.js'; import { Offers } from '@agoric/inter-protocol/src/clientSupport.js'; import type { ExecutionContext } from 'ava'; -import { insistManagerType, makeRunPolicyProvider } from './supports.js'; +import { insistManagerType, makeSwingsetHarness } from './supports.js'; import { type SwingsetTestKit, makeSwingsetTestKit } from './supports.js'; import { type GovernanceDriver, @@ -322,12 +322,12 @@ export const makeLiquidationTestContext = async ( SWINGSET_WORKER_TYPE: defaultManagerType = 'local', } = env; assertManagerType(defaultManagerType); - const perfTool = - defaultManagerType === 'xsnap' ? makeRunPolicyProvider() : undefined; + const harness = + defaultManagerType === 'xsnap' ? makeSwingsetHarness() : undefined; const swingsetTestKit = await makeSwingsetTestKit(t.log, undefined, { slogFile, defaultManagerType, - perfTool, + harness, }); console.time('DefaultTestContext'); @@ -385,7 +385,7 @@ export const makeLiquidationTestContext = async ( refreshAgoricNamesRemotes, walletFactoryDriver, governanceDriver, - perfTool, + harness, }; }; diff --git a/packages/boot/tools/supports.ts b/packages/boot/tools/supports.ts index 603b8f54cd0..0be39b19fa0 100644 --- a/packages/boot/tools/supports.ts +++ b/packages/boot/tools/supports.ts @@ -32,7 +32,7 @@ import { Fail } from '@endo/errors'; import { makeRunUtils, type RunUtils, - type RunPolicyMaker, + type RunHarness, } from '@agoric/swingset-vat/tools/run-utils.js'; import { boardSlottingMarshaller, @@ -83,7 +83,7 @@ type BootstrapEV = EProxy & { const makeBootstrapRunUtils = makeRunUtils as ( controller: SwingsetController, - perfTool?: RunPolicyMaker, + harness?: RunHarness, ) => Omit & { EV: BootstrapEV }; const keysToObject = ( @@ -315,7 +315,7 @@ export const matchIter = (t: AvaT, iter, valueRef) => { * @param [options.profileVats] * @param [options.debugVats] * @param [options.defaultManagerType] - * @param [options.perfTool] + * @param [options.harness] */ export const makeSwingsetTestKit = async ( log: (..._: any[]) => void, @@ -329,7 +329,7 @@ export const makeSwingsetTestKit = async ( profileVats = [] as string[], debugVats = [] as string[], defaultManagerType = 'local' as ManagerType, - perfTool = undefined as RunPolicyMaker | undefined, + harness = undefined as RunHarness | undefined, } = {}, ) => { console.time('makeBaseSwingsetTestKit'); @@ -547,7 +547,7 @@ export const makeSwingsetTestKit = async ( console.timeLog('makeBaseSwingsetTestKit', 'buildSwingset'); - const runUtils = makeBootstrapRunUtils(controller, perfTool); + const runUtils = makeBootstrapRunUtils(controller, harness); const buildProposal = makeProposalExtractor({ childProcess: childProcessAmbient, @@ -670,7 +670,12 @@ export const makeSwingsetTestKit = async ( }; export type SwingsetTestKit = Awaited>; -export const makeRunPolicyProvider = () => { +/** + * Return a harness that can be dynamically configured to provide a computron- + * counting run policy (and queried for the count of computrons recorded since + * the last reset). + */ +export const makeSwingsetHarness = () => { const c2b = defaultBeansPerXsnapComputron; const beansPerUnit = { // see https://cosgov.org/agoric?msgType=parameterChangeProposal&network=main @@ -691,14 +696,14 @@ export const makeRunPolicyProvider = () => { return policy; }, /** @param {boolean} forceEnabled */ - usePolicy: forceEnabled => { + useRunPolicy: forceEnabled => { policyEnabled = forceEnabled; if (!policyEnabled) { policy = undefined; } }, - totalCount: () => (policy?.totalBeans() || 0n) / c2b, - resetPolicy: () => (policy = undefined), + totalComputronCount: () => (policy?.totalBeans() || 0n) / c2b, + resetRunPolicy: () => (policy = undefined), }); return meter; }; From 50b1717c1e40ed67a5e69810961ad8d0144c5f9e Mon Sep 17 00:00:00 2001 From: 0xPatrick Date: Wed, 27 Nov 2024 18:27:44 -0500 Subject: [PATCH 19/56] feat: `ForwardOptsShape` - shape used for pfm ForwardInfo options --- .../orchestration-imports.test.js.md | 28 +++++++++++ .../orchestration-imports.test.js.snap | Bin 3987 -> 4095 bytes packages/orchestration/src/cosmos-api.ts | 4 ++ packages/orchestration/src/exos/chain-hub.js | 10 ++-- packages/orchestration/src/typeGuards.js | 46 ++++++++++++------ .../orchestration/test/exos/chain-hub.test.ts | 16 +++++- .../test/snapshots/exports.test.ts.md | 1 + .../test/snapshots/exports.test.ts.snap | Bin 689 -> 698 bytes 8 files changed, 83 insertions(+), 22 deletions(-) diff --git a/packages/builders/test/snapshots/orchestration-imports.test.js.md b/packages/builders/test/snapshots/orchestration-imports.test.js.md index 879f4029b18..247866d9e3b 100644 --- a/packages/builders/test/snapshots/orchestration-imports.test.js.md +++ b/packages/builders/test/snapshots/orchestration-imports.test.js.md @@ -318,6 +318,20 @@ Generated by [AVA](https://avajs.dev). ], }, }, + ForwardOptsShape: Object @match:splitRecord { + payload: [ + {}, + { + retries: Object @match:kind { + payload: 'number', + }, + timeout: Object @match:string { + payload: [], + }, + }, + {}, + ], + }, IBCChannelIDShape: Object @match:string { payload: [], }, @@ -405,6 +419,20 @@ Generated by [AVA](https://avajs.dev). payload: [ {}, { + forwardOpts: Object @match:splitRecord { + payload: [ + {}, + { + retries: Object @match:kind { + payload: 'number', + }, + timeout: Object @match:string { + payload: [], + }, + }, + {}, + ], + }, memo: Object @match:string { payload: [], }, diff --git a/packages/builders/test/snapshots/orchestration-imports.test.js.snap b/packages/builders/test/snapshots/orchestration-imports.test.js.snap index dba58251741462f8c1e1c312743d2c4078823f05..f1588bc482db490addff528f0ac9c8d3562dabc9 100644 GIT binary patch literal 4095 zcmV8%RzV?im-8Sa5C55&L zr!}-V6sM%7ht@l@JNwNyyJN~ZJtzKSkM{n4zwdtc_1*8@yFNKRl~NP?^dqMvLpD;< z!Pe`<8C8=LgQ}L8m2^WB4Ovw>q=Ok%Gjv&3#Ed?x8v2ow$)sqAyH~CEqYAlyLQv@b zCV=k%I1Au?0E+}*wE)~C0CNKHumHRu06!Lh3Lmh{2W;{I2_JCJ~5lrypnz0BZuko&az-06Y``eh>iO3jm8NfUyc7CREl6LR6^S zq9(H`slL7*LIgq=gjzvJRseCq51}F|)Q+XqtYVC5GdIkN8Og-&BY1R7ncpfJ7OO~k zfKXzTqJLIOs9Mq_ou+oiXGK{VOC~i**Nb-kjk;n|CY5Qmh__W1@#=9^R*KLhf#Tz; zo>uiSU6%}}fkSRqiE5r8th)75N}4f8zDRhJ5bD=Uikjv<@|KISUNS^ERb(uzB5gGp zPA4`KyvD?f*mi=|Z&bAdqLy^350qeR%NV4uzd;z$$#vu7v!bF%smb+4%C`w6MktP& z{)v#{Ig+X_78#-XmsQk5s5W(n!oU%(8}z8D;&>Q15eEJ+4E$9X_*br8 zo#9mwb%{xz+O(<8x`U+Sy4+~Bj?ur zw3v`K<-QiC^1)i*j#}Wixp0=-_kXJvc(N9FnNww#D?h0P-sZF~di9dO4ydkU3e9T~ zcGUqrb-+fh$~xU?LM#_mic!=g2RCLFb9e9^1^Gr5C4(yy-(608g_z6C+*8g>xlqjX zUoNLF9if@}-g0Vp;AYBWE@cFQU~T}3y5a^fj1b_Oy^UREd;DdsR=QaZ+NXB+(59n9|U=erd zsTlBF4EQrf?Bv9=G2pcr@Q;kRoD<)P0q@0t4;gWY5q*_$ARK2K-lw8MowZGBQd%{{ zsr>DL-Kr&Vpr5Ng%`@$w;9DODHgn?IGUkJVFA)c1&cDuM*ACnj2ad&o`{TePac65c z^49)-9QYO^UC&9+#DV7-X&dk0m*T*yao}$m@di%(@#Pksj|1;B;umtRAzW?{VnwZK!&Y1=%5RXpv`x+~o}) z_J+S+60R}xppYP(T~u)E-Mm{NL1=1%>9*YkS2sDkWUk5CB~LUJti0UB+WnCY^)9CE zuFGYB+%Y@1umeFMWpmIYNoiWlrVMk)b+fc8!a4SFB)2gaN}I~w-k6=Wb1~U%$h6W) zgYH~hXwV~z*~~d>L3ZDNu-J2G2AWI3LBT)W45XTYqs?rY1YBpPK)Ex_3p;N2D=)Cw$X1;$&MtlQOpQ?0;kD{z=oSGXK` zs1-QLX#<=V_~TaKg;wAnT7eHZeb{BSp$%Bn#%Loh+F%>7iqo!kHRtnfz%6aSY@0I* ze}+e4y$zV>_I}A_@8LG!R2%R(vp43n=QOj)W#;KN;B*`C8n1DJQJv@{Hx#_k2K=lI zsBZ_ZZU=5^2eR$JeeJ;4+L`fRc1@Dg?ZBV518=kg|J@GMcL2*em~6YJPdmBMiir+j zYX`8e131zFoZtpO=jx9aI)IltfHyexCKvT$2XLtaXy|0rJuYf*CotFvOmM2`*`k!I zMYnbW)1APvPTrs zS5w%&k+4skYYALDkdKqnkm=^$tRm-c()Uw~NmOM))$vCzyDSh$MP0Fk1#FU&A4OJuU?WKgI^}LrSST{(6l;FGzSw)~= z4%%Ai{XM%8os+N?r!VO-QAeEV-;t(mX&<)YB2I~lI&77p^=EIUb{4;01OUP~A8A1z97awx1n=S$d(o)*G zI(dzhM)E^7A;~kd*7^{Zk*DE2Y(H3%sZd3Df!q%q%+d%g&4|V%0T~?}do+hQuimHrj zvLPqL)P_wW!S$&K!>A8cc|()b+ArACdz4ypmv~ zsA@VUrp5|ZN}rCxnxq>Aj!nspTo0K^nq*`(#pDoguj%=P@pe~PZ-avG<{lu?!*Yv? z@^?*N>H+TJ{Ho%CM=YKMdVrIhS(7_5TDMY0F5(n!RjSO~?AadR`#r#!9%mw5=aooD z%U{t11>dOI9h&m@8|{Y=KO2Q^B?I2zRLM)+)WG$m9O*yf87hb z(+kx10eyYIcpsClbEV9C`hY1;8+Q$PyXU|i>;vxLMz$2EVnR%bnsW|p;YR!q_W`H+ zfYaR2jxrO_GO^kG+&~Qd=yH?(xexI5GebAJ4DBk@ENi}W^#eWJ$duP5;aESgi7O;8 z#jX9oG*>7d>nAAq?(7Hd;hIc2jorqeW6dArhw(@Ifv<6^^Y$Pb;>?Vcq(?VP?z;>8 zsbQXMIj8$Q&l^AShOxZNy`hyIwk$7Xhh59rb!JaVr44WKfITk-tEN;nC5iL_an8G{ zhrHnzKB*_wStTh=%Zfy|#q-o!qL89F>;!T-r@ccK(mCreL)1Y{N=Wit9{CxyOOx#n zDL|8Lt98N(ddQOw8dq*wZdbKat{$Ri>Fof4BE{pJ3ETRWgjB0Zb8;?kA{nMw3g4Pd zPf7F`HnYNW2p{!^&w0a_yy5nN()Y8zi2-2i09&t>EWkUKe6Z9upT|O_-wUlDrR^U8 z4h%SRhGzbzbYuXycL4ZxMqI)J&BFu0DMsq$q{jzDs=|4FIom+Uk${sO0-- z00;~+`FhWUr*#nM=8|1@n4FSlWQFc8L7{TZAh2!_xOosbItV;A2)xQoBwY7R?+gO( z4FcgIU}OmR!Vqx#5R*;2y5#r}aAL^Wy(;hCZw>+9VWj&w% zD#ZVfbI8-fS3EVH{snUP-Lmf5qknPO`QmqJm`t2-t`^&Z|3>wI$-#&v**NJX>mk`$vEWM}Si!z!M|R z<(A~3*{r+bnGxXm5#Xf};BQ8NH<)augp7U$1>gA*-~xC5P}vT$7e#RNljJPZU8~A~)vR{=b>bh!=-7001hJ{jvZ6 literal 3987 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 diff --git a/packages/orchestration/src/cosmos-api.ts b/packages/orchestration/src/cosmos-api.ts index cbbe4658760..c0fc2cf196d 100644 --- a/packages/orchestration/src/cosmos-api.ts +++ b/packages/orchestration/src/cosmos-api.ts @@ -333,6 +333,10 @@ export interface IBCMsgTransferOptions { timeoutHeight?: MsgTransfer['timeoutHeight']; timeoutTimestamp?: MsgTransfer['timeoutTimestamp']; memo?: string; + forwardOpts?: { + timeout?: ForwardInfo['forward']['timeout']; + retries?: ForwardInfo['forward']['retries']; + }; } /** diff --git a/packages/orchestration/src/exos/chain-hub.js b/packages/orchestration/src/exos/chain-hub.js index 6a300fade5a..ce01844bb00 100644 --- a/packages/orchestration/src/exos/chain-hub.js +++ b/packages/orchestration/src/exos/chain-hub.js @@ -11,6 +11,7 @@ import { DenomAmountShape, DenomDetailShape, ForwardInfoShape, + ForwardOptsShape, IBCChannelIDShape, IBCConnectionInfoShape, } from '../typeGuards.js'; @@ -20,7 +21,7 @@ import { getBech32Prefix } from '../utils/address.js'; * @import {NameHub} from '@agoric/vats'; * @import {Vow, VowTools} from '@agoric/vow'; * @import {Zone} from '@agoric/zone'; - * @import {CosmosAssetInfo, CosmosChainInfo, ForwardInfo, IBCConnectionInfo, TransferRoute} from '../cosmos-api.js'; + * @import {CosmosAssetInfo, CosmosChainInfo, ForwardInfo, IBCConnectionInfo, IBCMsgTransferOptions, TransferRoute} from '../cosmos-api.js'; * @import {ChainInfo, KnownChains} from '../chain-info.js'; * @import {ChainAddress, Denom, DenomAmount} from '../orchestration-api.js'; * @import {Remote, TypedPattern} from '@agoric/internal'; @@ -211,10 +212,7 @@ const ChainHubI = M.interface('ChainHub', { getDenom: M.call(BrandShape).returns(M.or(M.string(), M.undefined())), makeChainAddress: M.call(M.string()).returns(ChainAddressShape), makeTransferRoute: M.call(ChainAddressShape, DenomAmountShape, M.string()) - .optional({ - timeout: M.string(), - retries: M.number(), - }) + .optional(ForwardOptsShape) .returns(M.or(M.undefined(), TransferRouteShape)), }); @@ -515,7 +513,7 @@ export const makeChainHub = (zone, agoricNames, vowTools) => { * @param {ChainAddress} destination * @param {DenomAmount} denomAmount * @param {string} srcChainName - * @param {Pick} [forwardOpts] + * @param {IBCMsgTransferOptions['forwardOpts']} [forwardOpts] * @returns {TransferRoute} single hop, multi hop * @throws {Error} if unable to determine route */ diff --git a/packages/orchestration/src/typeGuards.js b/packages/orchestration/src/typeGuards.js index f97f2bb24c0..4496e245643 100644 --- a/packages/orchestration/src/typeGuards.js +++ b/packages/orchestration/src/typeGuards.js @@ -4,7 +4,7 @@ import { M } from '@endo/patterns'; /** * @import {TypedPattern} from '@agoric/internal'; - * @import {ChainAddress, CosmosAssetInfo, Chain, ChainInfo, CosmosChainInfo, DenomAmount, DenomInfo, AmountArg, CosmosValidatorAddress, OrchestrationPowers, ForwardInfo} from './types.js'; + * @import {ChainAddress, CosmosAssetInfo, Chain, ChainInfo, CosmosChainInfo, DenomAmount, DenomInfo, AmountArg, CosmosValidatorAddress, OrchestrationPowers, ForwardInfo, IBCMsgTransferOptions} from './types.js'; * @import {Any as Proto3Msg} from '@agoric/cosmic-proto/google/protobuf/any.js'; * @import {TxBody} from '@agoric/cosmic-proto/cosmos/tx/v1beta1/tx.js'; * @import {Coin} from '@agoric/cosmic-proto/cosmos/base/v1beta1/coin.js'; @@ -39,19 +39,6 @@ harden(ChainAddressShape); export const Proto3Shape = { typeUrl: M.string(), value: M.string() }; harden(ChainAddressShape); -/** @internal */ -export const IBCTransferOptionsShape = M.splitRecord( - {}, - { - timeoutTimestamp: M.bigint(), - timeoutHeight: { - revisionHeight: M.bigint(), - revisionNumber: M.bigint(), - }, - memo: M.string(), - }, -); - /** @internal */ export const IBCChannelIDShape = M.string(); @@ -247,3 +234,34 @@ export const ForwardInfoShape = { }), }; harden(ForwardInfoShape); + +/** + * Caller configurable values of {@link ForwardInfo} + * + * @type {TypedPattern} + */ +export const ForwardOptsShape = M.splitRecord( + {}, + { + timeout: M.string(), + retries: M.number(), + }, + {}, +); + +/** + * @type {TypedPattern} + * @internal + */ +export const IBCTransferOptionsShape = M.splitRecord( + {}, + { + timeoutTimestamp: M.bigint(), + timeoutHeight: { + revisionHeight: M.bigint(), + revisionNumber: M.bigint(), + }, + memo: M.string(), + forwardOpts: ForwardOptsShape, + }, +); diff --git a/packages/orchestration/test/exos/chain-hub.test.ts b/packages/orchestration/test/exos/chain-hub.test.ts index 1a8efc8e762..4148f5a1bf5 100644 --- a/packages/orchestration/test/exos/chain-hub.test.ts +++ b/packages/orchestration/test/exos/chain-hub.test.ts @@ -329,7 +329,7 @@ test('makeTransferRoute - through issuing chain', async t => { }); // use TransferRoute to build a MsgTransfer - if (!route || !('forwardInfo' in route)) { + if (!('forwardInfo' in route)) { throw new Error('forwardInfo not returned'); // appease tsc... } @@ -383,6 +383,18 @@ test('makeTransferRoute - takes forwardOpts', t => { }, }); + t.like( + chainHub.makeTransferRoute(dest, amt, 'osmosis', { timeout: '99min' }), + { + forwardInfo: { + forward: { + timeout: '99min', + }, + }, + }, + 'each field is optional', + ); + // test that typeGuard works t.throws( () => @@ -395,7 +407,7 @@ test('makeTransferRoute - takes forwardOpts', t => { forward: JSON.stringify('stringified nested forward data'), }), ), - { message: /Must not have unexpected properties/ }, + { message: /In "makeTransferRoute" method of/ }, ); }); diff --git a/packages/orchestration/test/snapshots/exports.test.ts.md b/packages/orchestration/test/snapshots/exports.test.ts.md index f4a36635d08..22bf7e69d2d 100644 --- a/packages/orchestration/test/snapshots/exports.test.ts.md +++ b/packages/orchestration/test/snapshots/exports.test.ts.md @@ -23,6 +23,7 @@ Generated by [AVA](https://avajs.dev). 'DenomInfoShape', 'DenomShape', 'ForwardInfoShape', + 'ForwardOptsShape', 'IBCChannelIDShape', 'IBCChannelInfoShape', 'IBCConnectionIDShape', diff --git a/packages/orchestration/test/snapshots/exports.test.ts.snap b/packages/orchestration/test/snapshots/exports.test.ts.snap index 3d9da073d5a8c310ae5fb16b5b2bbbcd5cc14d37..613327cd832180a10fb5f963ed843f8bd908c744 100644 GIT binary patch literal 698 zcmV;r0!95nRzVZiGTZ z*zd+qryq+500000000ARlf7;eK@^40?5^|U1RTftBak1UrQ-!yuNB3J;6U8aG4@Wf zqu4X6nK6k)l>!Oz6oi@rQSb;*QqfZL00<$`fEQ-S*x71V=i77d+V}169 z8E$%vagnl9t_96?CXGHjPg82>lM)XxjnPA9$nAFkJ^=Uv;3t3$0^B3OQvy6Ez&Qav z5#SpE$^mdE03HND767mQe7_BV&jIi~0Mxx@Pvz{aw6@vAe4G&pxYrTMsSE{;^ zjvy%n>yG9%X0>Rk6`vY+t66TfSx?%E3Vp~_D<83b`%4y_YbKBOv>(}JE3UOvH)GnU zVu$bj<~; zeOj04aAGOzE)?xy&eHpOEO^(gzStclcZYUq%J!JaWU4K5!(Ebe6r5eEGb?SlUFC}9 zRIwueyMs=g_PMasrlmG5Ros=PFiaI?514w!yRNA%w=>0#xHe1`wmKGRaSL5%+ZJ3t g;U+7fgyyuvd)#p5u$wNKBh1_2Z_@$-@skAr07~9Rs(J6FWPCfp5S^=mHbuz@|=nlcnc(&-?m)ADz<>a62=JKz zKL{`p0Jj665dbUzUIoDW0QeFB=K-)40{26p69TV8;8O^E4}o7Huvr4`mVjp^;AIJT zTLQk8fS-TPJ7u6oCaRM~Q7s?>SLkEuzeUu@a}3w17J?}~}c_(Yu>nr0p`>+V_* zmztQf`b?pF+BN6CC)I!|cIoeVH|*wa94Ax=o;B+pQgKVWfQ=b_qj-nCt9@1(ye@NeU>YIqjrb XYEtg79hb}z=56pd&!i?GZ3O@T#M(L% From c35fac7e82e6b66d2ffdc62ded1ba29a7d7388ff Mon Sep 17 00:00:00 2001 From: 0xPatrick Date: Wed, 27 Nov 2024 19:21:01 -0500 Subject: [PATCH 20/56] feat(local-orchestration-account): support multi-hop pfm transfers --- packages/orchestration/src/cosmos-api.ts | 1 + packages/orchestration/src/exos/chain-hub.js | 6 +- .../src/exos/local-orchestration-account.js | 70 +++++++------- .../orchestration/src/orchestration-api.ts | 4 +- .../orchestration/test/exos/chain-hub.test.ts | 6 +- .../local-orchestration-account-kit.test.ts | 96 ++++++++++++++++--- 6 files changed, 127 insertions(+), 56 deletions(-) diff --git a/packages/orchestration/src/cosmos-api.ts b/packages/orchestration/src/cosmos-api.ts index c0fc2cf196d..661d92a23d5 100644 --- a/packages/orchestration/src/cosmos-api.ts +++ b/packages/orchestration/src/cosmos-api.ts @@ -401,5 +401,6 @@ export type TransferRoute = { } | { receiver: string; + forwardInfo?: never; } ); diff --git a/packages/orchestration/src/exos/chain-hub.js b/packages/orchestration/src/exos/chain-hub.js index ce01844bb00..1477ca91de8 100644 --- a/packages/orchestration/src/exos/chain-hub.js +++ b/packages/orchestration/src/exos/chain-hub.js @@ -544,7 +544,7 @@ export const makeChainHub = (zone, agoricNames, vowTools) => { // TODO use getConnectionInfo once its sync const connKey = connectionKey(holdingChainId, destination.chainId); connectionInfos.has(connKey) || - Fail`no connection info found for ${q(connKey)}`; + Fail`no connection info found for ${holdingChainId}<->${destination.chainId}`; const { transferChannel } = denormalizeConnectionInfo( holdingChainId, // from chain (primary) @@ -568,11 +568,11 @@ export const makeChainHub = (zone, agoricNames, vowTools) => { // TODO use getConnectionInfo once its sync const currToIssuerKey = connectionKey(holdingChainId, baseChainId); connectionInfos.has(currToIssuerKey) || - Fail`no connection info found for ${q(currToIssuerKey)}`; + Fail`no connection info found for ${holdingChainId}<->${baseChainId}`; const issuerToDestKey = connectionKey(baseChainId, destination.chainId); connectionInfos.has(issuerToDestKey) || - Fail`no connection info found for ${q(issuerToDestKey)}`; + Fail`no connection info found for ${baseChainId}<->${destination.chainId}`; const currToIssuer = denormalizeConnectionInfo( holdingChainId, diff --git a/packages/orchestration/src/exos/local-orchestration-account.js b/packages/orchestration/src/exos/local-orchestration-account.js index 7ab823a0719..153b86ecd69 100644 --- a/packages/orchestration/src/exos/local-orchestration-account.js +++ b/packages/orchestration/src/exos/local-orchestration-account.js @@ -11,7 +11,6 @@ import { Fail, q } from '@endo/errors'; import { AmountArgShape, AnyNatAmountsRecord, - ChainAddressShape, DenomAmountShape, DenomShape, IBCTransferOptionsShape, @@ -24,11 +23,12 @@ import { makeTimestampHelper } from '../utils/time.js'; import { preparePacketTools } from './packet-tools.js'; import { prepareIBCTools } from './ibc-packet.js'; import { coerceCoin, coerceDenomAmount } from '../utils/amounts.js'; +import { TransferRouteShape } from './chain-hub.js'; /** * @import {HostOf} from '@agoric/async-flow'; * @import {LocalChain, LocalChainAccount} from '@agoric/vats/src/localchain.js'; - * @import {AmountArg, ChainAddress, DenomAmount, IBCMsgTransferOptions, IBCConnectionInfo, OrchestrationAccountI, LocalAccountMethods} from '@agoric/orchestration'; + * @import {AmountArg, ChainAddress, DenomAmount, IBCMsgTransferOptions, IBCConnectionInfo, OrchestrationAccountI, LocalAccountMethods, TransferRoute} from '@agoric/orchestration'; * @import {RecorderKit, MakeRecorderKit} from '@agoric/zoe/src/contractSupport/recorder.js'. * @import {Zone} from '@agoric/zone'; * @import {Remote} from '@agoric/internal'; @@ -107,7 +107,7 @@ export const prepareLocalOrchestrationAccountKit = ( zoeTools, }, ) => { - const { watch, allVows, asVow, when } = vowTools; + const { watch, asVow, when } = vowTools; const { makeIBCTransferSender } = prepareIBCTools( zone.subZone('ibcTools'), vowTools, @@ -134,11 +134,10 @@ export const prepareLocalOrchestrationAccountKit = ( .returns(VowShape), }), transferWatcher: M.interface('transferWatcher', { - onFulfilled: M.call([M.record(), M.nat()]) + onFulfilled: M.call(M.nat()) .optional({ - destination: ChainAddressShape, opts: M.or(M.undefined(), IBCTransferOptionsShape), - amount: DenomAmountShape, + route: TransferRouteShape, }) .returns(Vow$(M.record())), }), @@ -345,37 +344,34 @@ export const prepareLocalOrchestrationAccountKit = ( }, transferWatcher: { /** - * @param {[ - * { transferChannel: IBCConnectionInfo['transferChannel'] }, - * bigint, - * ]} results + * @param {bigint} timeoutTimestamp * @param {{ - * destination: ChainAddress; - * opts?: IBCMsgTransferOptions; - * amount: DenomAmount; + * opts?: Omit; + * route: TransferRoute; * }} ctx */ - onFulfilled( - [{ transferChannel }, timeoutTimestamp], - { opts, amount, destination }, - ) { + onFulfilled(timeoutTimestamp, { opts, route }) { + const { forwardInfo, ...transferDetails } = route; + /** @type {string | undefined} */ + let memo; + if (opts && 'memo' in opts) { + memo = opts.memo; + } + if (forwardInfo) { + // forward memo takes precedence + memo = JSON.stringify(forwardInfo); + } const transferMsg = typedJson( '/ibc.applications.transfer.v1.MsgTransfer', { - sourcePort: transferChannel.portId, - sourceChannel: transferChannel.channelId, - token: { - amount: String(amount.value), - denom: amount.denom, - }, + ...transferDetails, sender: this.state.address.value, - receiver: destination.value, timeoutHeight: opts?.timeoutHeight ?? { revisionHeight: 0n, revisionNumber: 0n, }, timeoutTimestamp, - memo: opts?.memo ?? '', + memo: memo ?? '', }, ); @@ -682,16 +678,23 @@ export const prepareLocalOrchestrationAccountKit = ( * timeoutTimestamp are not supplied, a default timeoutTimestamp will * be set for 5 minutes in the future * @returns {Vow} + * @throws {Error} if route is not determinable, asset is not + * recognized, or the transfer is rejected (insufficient funds, + * timeout) */ transfer(destination, amount, opts) { return asVow(() => { trace('Transferring funds from LCA over IBC'); + const denomAmount = coerceDenomAmount(chainHub, amount); - const connectionInfoV = watch( - chainHub.getConnectionInfo( - this.state.address.chainId, - destination.chainId, - ), + const { forwardOpts, ...rest } = opts ?? {}; + + // throws if route is not determinable + const route = chainHub.makeTransferRoute( + destination, + denomAmount, + 'agoric', + forwardOpts, ); // set a `timeoutTimestamp` if caller does not supply either `timeoutHeight` or `timeoutTimestamp` @@ -705,12 +708,11 @@ export const prepareLocalOrchestrationAccountKit = ( // don't resolve the vow until the transfer is confirmed on remote // and reject vow if the transfer fails for any reason const resultV = watch( - allVows([connectionInfoV, timeoutTimestampVowOrValue]), + timeoutTimestampVowOrValue, this.facets.transferWatcher, { - opts, - amount: coerceDenomAmount(chainHub, amount), - destination, + opts: rest, + route, }, ); return resultV; diff --git a/packages/orchestration/src/orchestration-api.ts b/packages/orchestration/src/orchestration-api.ts index 2294f376dce..cb97cadcc56 100644 --- a/packages/orchestration/src/orchestration-api.ts +++ b/packages/orchestration/src/orchestration-api.ts @@ -195,8 +195,8 @@ export interface OrchestrationAccountI { * @param destination - the account to transfer the amount to. * @param [opts] - an optional memo to include with the transfer, which could drive custom PFM behavior, and timeout parameters * @returns void - * - * TODO document the mapping from the address to the destination chain. + * @throws {Error} if route is not determinable, asset is not recognized, or + * the transfer is rejected (insufficient funds, timeout) */ transfer: ( destination: ChainAddress, diff --git a/packages/orchestration/test/exos/chain-hub.test.ts b/packages/orchestration/test/exos/chain-hub.test.ts index 4148f5a1bf5..c8ba5c32a2c 100644 --- a/packages/orchestration/test/exos/chain-hub.test.ts +++ b/packages/orchestration/test/exos/chain-hub.test.ts @@ -488,7 +488,7 @@ test('makeTransferRoute - no connection info single hop', t => { harden({ denom: uusdcOnAgoric, value: 100n }), 'agoric', ), - { message: 'no connection info found for "agoric-3_noble-1"' }, + { message: 'no connection info found for "agoric-3"<->"noble-1"' }, ); }); @@ -517,7 +517,7 @@ test('makeTransferRoute - no connection info multi hop', t => { harden({ denom: uusdcOnAgoric, value: 100n }), 'agoric', ), - { message: 'no connection info found for "noble-1_osmosis-1"' }, + { message: 'no connection info found for "noble-1"<->"osmosis-1"' }, ); // transfer USDC on osmosis to agoric @@ -528,7 +528,7 @@ test('makeTransferRoute - no connection info multi hop', t => { harden({ denom: uusdcOnOsmosis, value: 100n }), 'osmosis', ), - { message: 'no connection info found for "noble-1_osmosis-1"' }, + { message: 'no connection info found for "osmosis-1"<->"noble-1"' }, ); }); diff --git a/packages/orchestration/test/exos/local-orchestration-account-kit.test.ts b/packages/orchestration/test/exos/local-orchestration-account-kit.test.ts index c1eed2f6730..8fe222f00aa 100644 --- a/packages/orchestration/test/exos/local-orchestration-account-kit.test.ts +++ b/packages/orchestration/test/exos/local-orchestration-account-kit.test.ts @@ -9,13 +9,22 @@ import { } from '@agoric/vats/tools/fake-bridge.js'; import { heapVowE as VE } from '@agoric/vow/vat.js'; import { withAmountUtils } from '@agoric/zoe/tools/test-utils.js'; -import type { ChainAddress, AmountArg } from '../../src/orchestration-api.js'; +import type { IBCChannelID } from '@agoric/vats'; +import type { + ChainAddress, + AmountArg, + DenomAmount, +} from '../../src/orchestration-api.js'; import { maxClockSkew } from '../../src/utils/cosmos.js'; import { NANOSECONDS_PER_SECOND } from '../../src/utils/time.js'; import { buildVTransferEvent } from '../../tools/ibc-mocks.js'; import { UNBOND_PERIOD_SECONDS } from '../ibc-mocks.js'; import { commonSetup } from '../supports.js'; import { prepareMakeTestLOAKit } from './make-test-loa-kit.js'; +import fetchedChainInfo from '../../src/fetched-chain-info.js'; +import type { IBCMsgTransferOptions } from '../../src/cosmos-api.js'; +import { PFM_RECEIVER } from '../../src/exos/chain-hub.js'; +import { assetOn } from '../../src/utils/asset.js'; test('deposit, withdraw', async t => { const common = await commonSetup(t); @@ -108,12 +117,12 @@ test('transfer', async t => { const { brands: { bld: stake }, mocks: { transferBridge }, - utils, + utils: { inspectLocalBridge, pourPayment }, } = common; t.truthy(account, 'account is returned'); - const oneHundredStakePmt = await utils.pourPayment(stake.units(100)); + const oneHundredStakePmt = await pourPayment(stake.units(100)); t.log('deposit 100 bld to account'); await VE(account).deposit(oneHundredStakePmt); @@ -127,7 +136,6 @@ test('transfer', async t => { value: 'cosmos1pleab', encoding: 'bech32', }; - const sourceChannel = 'channel-5'; // observed in toBridge VLOCALCHAIN_EXECUTE_TX sourceChannel, confirmed via fetched-chain-info.js /** The running tally of transfer messages that were sent over the bridge */ let lastSequence = 0n; @@ -142,7 +150,7 @@ test('transfer', async t => { const startTransfer = async ( amount: AmountArg, dest: ChainAddress, - opts = {}, + opts: IBCMsgTransferOptions = {}, ) => { const transferP = VE(account).transfer(dest, amount, opts); lastSequence += 1n; @@ -163,16 +171,15 @@ test('transfer', async t => { buildVTransferEvent({ receiver: destination.value, sender, - sourceChannel, + sourceChannel: + fetchedChainInfo.agoric.connections[destination.chainId].transferChannel + .channelId, sequence: lastSequence, }), ); const transferRes = await transferP; - t.true( - transferRes === undefined, - 'Successful transfer returns Promise.', - ); + t.true(transferRes === undefined, 'Successful transfer returns Vow.'); await t.throwsAsync( ( @@ -194,7 +201,7 @@ test('transfer', async t => { // XXX dev has to know not to startTransfer here await t.throwsAsync( VE(account).transfer(unknownDestination, { denom: 'ubld', value: 1n }), - { message: /connection not found: agoric-3<->fakenet/ }, + { message: 'no connection info found for "agoric-3"<->"fakenet"' }, 'cannot create transfer msg with unknown chainId', ); @@ -203,11 +210,13 @@ test('transfer', async t => { * @param amount * @param dest * @param opts + * @param sourceChannel */ const doTransfer = async ( amount: AmountArg, dest: ChainAddress, - opts = {}, + opts: IBCMsgTransferOptions = {}, + sourceChannel?: IBCChannelID, ) => { const { transferP: promise } = await startTransfer(amount, dest, opts); // simulate incoming message so that promise resolves @@ -215,20 +224,33 @@ test('transfer', async t => { buildVTransferEvent({ receiver: dest.value, sender, - sourceChannel, + sourceChannel: + sourceChannel || + fetchedChainInfo.agoric.connections[dest.chainId].transferChannel + .channelId, sequence: lastSequence, }), ); return promise; }; + const lastestTxMsg = () => { + const tx = inspectLocalBridge().at(-1); + if (tx.type !== 'VLOCALCHAIN_EXECUTE_TX') { + throw new Error('last message was not VLOCALCHAIN_EXECUTE_TX'); + } + return tx.messages[0]; + }; + await t.notThrowsAsync( doTransfer({ denom: 'ubld', value: 10n }, destination, { memo: 'hello', }), 'can create transfer msg with memo', ); - // TODO, intercept/spy the bridge message to see that it has a memo + t.like(lastestTxMsg(), { + memo: 'hello', + }); await t.notThrowsAsync( doTransfer({ denom: 'ubld', value: 10n }, destination, { @@ -244,6 +266,52 @@ test('transfer', async t => { }), 'accepts custom timeoutHeight', ); + + const [uusdcOnAgoric] = assetOn('uusdc', 'noble', 'agoric', fetchedChainInfo); + const dydxDest: ChainAddress = { + chainId: 'dydx-mainnet-1', + encoding: 'bech32', + value: 'dydx1test', + }; + const aDenomAmount: DenomAmount = { + denom: uusdcOnAgoric, + value: 100n, + }; + + t.log('Transfer handles multi-hop transfers'); + await t.notThrowsAsync( + doTransfer( + aDenomAmount, + dydxDest, + {}, + fetchedChainInfo.agoric.connections['noble-1'].transferChannel.channelId, + ), + ); + + t.like(lastestTxMsg(), { + receiver: PFM_RECEIVER, + memo: '{"forward":{"receiver":"dydx1test","port":"transfer","channel":"channel-33","retries":3,"timeout":"10min"}}', + }); + + t.log('accepts pfm `forwardOpts`'); + await t.notThrowsAsync( + doTransfer( + aDenomAmount, + dydxDest, + { + forwardOpts: { + timeout: '999min', + }, + }, + fetchedChainInfo.agoric.connections['noble-1'].transferChannel.channelId, + ), + ); + + t.like(JSON.parse(lastestTxMsg().memo), { + forward: { + timeout: '999min', + }, + }); }); test('monitor transfers', async t => { From 05aa139f4dd850e5f6ad3018e500c7d6f3f6b22b Mon Sep 17 00:00:00 2001 From: 0xPatrick Date: Wed, 27 Nov 2024 20:46:52 -0500 Subject: [PATCH 21/56] test: `chainHub` test support - provide `chainInfo` and `assetInfo` in commonPrivateArgs for contracts to use - register common assets used in testing - provide `populateChainHub` function for use in exo unit testing in favor of `registerAgoricBld` --- packages/orchestration/src/utils/asset.js | 17 ++++--- .../orchestration/test/exos/chain-hub.test.ts | 2 + .../exos/cosmos-orchestration-account.test.ts | 6 ++- .../local-orchestration-account-kit.test.ts | 15 ++++++- .../test/exos/make-test-coa-kit.ts | 4 -- .../test/exos/make-test-loa-kit.ts | 3 -- .../test/exos/portfolio-holder-kit.test.ts | 1 + packages/orchestration/test/supports.ts | 45 ++++++++++++------- 8 files changed, 59 insertions(+), 34 deletions(-) diff --git a/packages/orchestration/src/utils/asset.js b/packages/orchestration/src/utils/asset.js index 3a39da7135b..2f4efccd998 100644 --- a/packages/orchestration/src/utils/asset.js +++ b/packages/orchestration/src/utils/asset.js @@ -8,19 +8,18 @@ import { denomHash } from './denomHash.js'; * Helper function for creating {@link DenomDetail} data for {@link ChainHub} * asset registration. * - * TODO #10580 remove 'brandKey' in favor of `LegibleCapData` - * * @param {Denom} baseDenom * @param {string} baseName + * @param {Brand<'nat'>} [brand] * @param {string} [chainName] * @param {Record} [infoOf] - * @param {string} [brandKey] - * @returns {[string, DenomDetail & { brandKey?: string }]} + * @returns {[string, DenomDetail]} */ -export const assetOn = (baseDenom, baseName, chainName, infoOf, brandKey) => { - if (!chainName) { - return [baseDenom, { baseName, chainName: baseName, baseDenom }]; - } +export const assetOn = (baseDenom, baseName, brand, chainName, infoOf) => { + const baseDetail = { baseName, chainName: chainName || baseName, baseDenom }; + const detail = brand ? { ...baseDetail, brand } : baseDetail; + if (!chainName) return harden([baseDenom, detail]); + if (!infoOf) throw Error(`must provide infoOf`); const issuerInfo = infoOf[baseName]; const holdingInfo = infoOf[chainName]; @@ -30,5 +29,5 @@ export const assetOn = (baseDenom, baseName, chainName, infoOf, brandKey) => { const { channelId } = holdingInfo.connections[issuerInfo.chainId].transferChannel; const denom = `ibc/${denomHash({ denom: baseDenom, channelId })}`; - return [denom, { baseName, chainName, baseDenom, brandKey }]; + return harden([denom, detail]); }; diff --git a/packages/orchestration/test/exos/chain-hub.test.ts b/packages/orchestration/test/exos/chain-hub.test.ts index c8ba5c32a2c..02505f41778 100644 --- a/packages/orchestration/test/exos/chain-hub.test.ts +++ b/packages/orchestration/test/exos/chain-hub.test.ts @@ -201,12 +201,14 @@ test('makeChainAddress', async t => { const [uusdcOnAgoric, agDetail] = assetOn( 'uusdc', 'noble', + undefined, 'agoric', knownChains, ); const [uusdcOnOsmosis, osDetail] = assetOn( 'uusdc', 'noble', + undefined, 'osmosis', knownChains, ); diff --git a/packages/orchestration/test/exos/cosmos-orchestration-account.test.ts b/packages/orchestration/test/exos/cosmos-orchestration-account.test.ts index d3454066473..f88664fad1d 100644 --- a/packages/orchestration/test/exos/cosmos-orchestration-account.test.ts +++ b/packages/orchestration/test/exos/cosmos-orchestration-account.test.ts @@ -67,8 +67,9 @@ test.beforeEach(async t => { test('send (to addr on same chain)', async t => { const { brands: { ist }, - utils: { inspectDibcBridge }, + utils: { inspectDibcBridge, populateChainHub }, } = t.context; + populateChainHub(); const makeTestCOAKit = prepareMakeTestCOAKit(t, t.context); const account = await makeTestCOAKit(); t.assert(account, 'account is returned'); @@ -122,9 +123,10 @@ test('transfer', async t => { const { brands: { ist }, facadeServices: { chainHub }, - utils: { inspectDibcBridge }, + utils: { inspectDibcBridge, populateChainHub }, mocks: { ibcBridge }, } = t.context; + populateChainHub(); const mockIbcTransfer = { sourcePort: 'transfer', diff --git a/packages/orchestration/test/exos/local-orchestration-account-kit.test.ts b/packages/orchestration/test/exos/local-orchestration-account-kit.test.ts index 8fe222f00aa..afec573e19c 100644 --- a/packages/orchestration/test/exos/local-orchestration-account-kit.test.ts +++ b/packages/orchestration/test/exos/local-orchestration-account-kit.test.ts @@ -28,6 +28,7 @@ import { assetOn } from '../../src/utils/asset.js'; test('deposit, withdraw', async t => { const common = await commonSetup(t); + common.utils.populateChainHub(); const makeTestLOAKit = prepareMakeTestLOAKit(t, common); const account = await makeTestLOAKit(); @@ -73,6 +74,7 @@ test('deposit, withdraw', async t => { test('delegate, undelegate', async t => { const common = await commonSetup(t); + common.utils.populateChainHub(); const makeTestLOAKit = prepareMakeTestLOAKit(t, common); const account = await makeTestLOAKit(); @@ -109,6 +111,7 @@ test('delegate, undelegate', async t => { test('transfer', async t => { const common = await commonSetup(t); + common.utils.populateChainHub(); const makeTestLOAKit = prepareMakeTestLOAKit(t, common); const account = await makeTestLOAKit(); @@ -267,7 +270,13 @@ test('transfer', async t => { 'accepts custom timeoutHeight', ); - const [uusdcOnAgoric] = assetOn('uusdc', 'noble', 'agoric', fetchedChainInfo); + const [uusdcOnAgoric] = assetOn( + 'uusdc', + 'noble', + undefined, + 'agoric', + fetchedChainInfo, + ); const dydxDest: ChainAddress = { chainId: 'dydx-mainnet-1', encoding: 'bech32', @@ -316,6 +325,7 @@ test('transfer', async t => { test('monitor transfers', async t => { const common = await commonSetup(t); + common.utils.populateChainHub(); const makeTestLOAKit = prepareMakeTestLOAKit(t, common); const account = await makeTestLOAKit(); const { @@ -360,6 +370,7 @@ test('monitor transfers', async t => { test('send', async t => { const common = await commonSetup(t); + common.utils.populateChainHub(); const makeTestLOAKit = prepareMakeTestLOAKit(t, common); const account = await makeTestLOAKit(); t.truthy(account, 'account is returned'); @@ -420,6 +431,7 @@ test('send', async t => { test('getBalance', async t => { const common = await commonSetup(t); + common.utils.populateChainHub(); const makeTestLOAKit = prepareMakeTestLOAKit(t, common); const account = await makeTestLOAKit(); t.truthy(account, 'account is returned'); @@ -474,6 +486,7 @@ test('getBalance', async t => { test('getBalances', async t => { const common = await commonSetup(t); + common.utils.populateChainHub(); const makeTestLOAKit = prepareMakeTestLOAKit(t, common); const account = await makeTestLOAKit(); t.truthy(account, 'account is returned'); diff --git a/packages/orchestration/test/exos/make-test-coa-kit.ts b/packages/orchestration/test/exos/make-test-coa-kit.ts index 6042091b31a..f1b63c50550 100644 --- a/packages/orchestration/test/exos/make-test-coa-kit.ts +++ b/packages/orchestration/test/exos/make-test-coa-kit.ts @@ -83,10 +83,6 @@ export const prepareMakeTestCOAKit = ( timer, }, ); - - t.log('register Agoric chain and BLD in ChainHub'); - utils.registerAgoricBld(); - return holder; }; }; diff --git a/packages/orchestration/test/exos/make-test-loa-kit.ts b/packages/orchestration/test/exos/make-test-loa-kit.ts index ee718c5a997..8bb57055d0b 100644 --- a/packages/orchestration/test/exos/make-test-loa-kit.ts +++ b/packages/orchestration/test/exos/make-test-loa-kit.ts @@ -63,9 +63,6 @@ export const prepareMakeTestLOAKit = ( }), storageNode: storageNode.makeChildNode(address), }); - - t.log('register Agoric chain and BLD in ChainHub'); - utils.registerAgoricBld(); return account; }; }; diff --git a/packages/orchestration/test/exos/portfolio-holder-kit.test.ts b/packages/orchestration/test/exos/portfolio-holder-kit.test.ts index a498b9b0c2c..b456399b57c 100644 --- a/packages/orchestration/test/exos/portfolio-holder-kit.test.ts +++ b/packages/orchestration/test/exos/portfolio-holder-kit.test.ts @@ -8,6 +8,7 @@ import { prepareMakeTestCOAKit } from './make-test-coa-kit.js'; test('portfolio holder kit behaviors', async t => { const common = await commonSetup(t); + common.utils.populateChainHub(); const { rootZone, storage, vowTools } = common.bootstrap; const storageNode = storage.rootNode.makeChildNode('accounts'); diff --git a/packages/orchestration/test/supports.ts b/packages/orchestration/test/supports.ts index 6486a7ffbaa..0454f493eb3 100644 --- a/packages/orchestration/test/supports.ts +++ b/packages/orchestration/test/supports.ts @@ -26,6 +26,9 @@ import { prepareCosmosInterchainService } from '../src/exos/cosmos-interchain-se import fetchedChainInfo from '../src/fetched-chain-info.js'; import { buildVTransferEvent } from '../tools/ibc-mocks.js'; import { setupFakeNetwork } from './network-fakes.js'; +import { withChainCapabilities } from '../src/chain-capabilities.js'; +import { registerChainsAndAssets } from '../src/utils/chain-hub-helper.js'; +import { assetOn } from '../src/utils/asset.js'; export { makeFakeLocalchainBridge, @@ -168,22 +171,32 @@ export const commonSetup = async (t: ExecutionContext) => { vowTools, ); + /** add `pfmEnabled` to chainInfo */ + const chainInfoWithCaps = withChainCapabilities(fetchedChainInfo); + + /** for registration with `ChainHub` */ + const commonAssetInfo = harden([ + assetOn('ubld', 'agoric', bldSansMint.brand), + assetOn('uist', 'agoric', istSansMint.brand), + assetOn('uusdc', 'noble', undefined, 'agoric', chainInfoWithCaps), + assetOn('uatom', 'cosmoshub', undefined, 'agoric', chainInfoWithCaps), + assetOn('uusdc', 'noble', undefined, 'dydx', chainInfoWithCaps), + ]); + /** - * Register BLD if it's not already registered. - * Does not work with `withOrchestration` contracts, as these have their own - * ChainHub. Use `ChainHubAdmin` instead. + * Register known chains an assets into the test context's `ChainHub`. + * + * For contract tests with contracts that use `withOrchestration`, access + * `chainInfo` and `assetInfo` from `commonPrivateArgs` and register in the + * contract's ChainHub with `registerChainsAndAssets`. */ - const registerAgoricBld = () => { - if (!chainHub.getAsset('ubld', 'agoric')) { - chainHub.registerChain('agoric', fetchedChainInfo.agoric); - chainHub.registerAsset('ubld', { - chainName: 'agoric', - baseName: 'agoric', - baseDenom: 'ubld', - brand: bld.brand, - }); - } - }; + const populateChainHub = () => + registerChainsAndAssets( + chainHub, + harden({ BLD: bldSansMint.brand, IST: istSansMint.brand }), + chainInfoWithCaps, + commonAssetInfo, + ); return { bootstrap: { @@ -214,6 +227,8 @@ export const commonSetup = async (t: ExecutionContext) => { storageNode: storage.rootNode, marshaller, timerService: timer, + chainInfo: withChainCapabilities(fetchedChainInfo), + assetInfo: harden(commonAssetInfo), }, facadeServices: { agoricNames, @@ -227,7 +242,7 @@ export const commonSetup = async (t: ExecutionContext) => { inspectLocalBridge: () => harden([...localBridgeMessages]), inspectDibcBridge: () => E(ibcBridge).inspectDibcBridge(), inspectBankBridge: () => harden([...bankBridgeMessages]), - registerAgoricBld, + populateChainHub, transmitTransferAck, }, }; From e8b37a8ae6685b0528054c4c78d3d09a1cecee71 Mon Sep 17 00:00:00 2001 From: Ikenna Omekam Date: Fri, 1 Nov 2024 10:48:21 -0500 Subject: [PATCH 22/56] timestamp durable --- .../src/exos/local-orchestration-account.js | 14 ++++---------- 1 file changed, 4 insertions(+), 10 deletions(-) diff --git a/packages/orchestration/src/exos/local-orchestration-account.js b/packages/orchestration/src/exos/local-orchestration-account.js index 153b86ecd69..20285c1c9b2 100644 --- a/packages/orchestration/src/exos/local-orchestration-account.js +++ b/packages/orchestration/src/exos/local-orchestration-account.js @@ -391,9 +391,7 @@ export const prepareLocalOrchestrationAccountKit = ( * first result */ extractFirstResultWatcher: { - /** - * @param {Record[]} results - */ + /** @param {Record[]} results */ onFulfilled(results) { results.length === 1 || Fail`expected exactly one result; got ${results}`; @@ -500,9 +498,7 @@ export const prepareLocalOrchestrationAccountKit = ( }); }); }, - /** - * @type {HostOf} - */ + /** @type {HostOf} */ getBalance(denomArg) { return asVow(() => { const [brand, denom] = @@ -545,9 +541,7 @@ export const prepareLocalOrchestrationAccountKit = ( ); }, - /** - * @type {HostOf} - */ + /** @type {HostOf} */ getPublicTopics() { // getStoragePath resolves promptly (same run), so we don't need a watcher // eslint-disable-next-line no-restricted-syntax @@ -703,7 +697,7 @@ export const prepareLocalOrchestrationAccountKit = ( opts?.timeoutTimestamp ?? (opts?.timeoutHeight ? 0n - : E(timestampHelper).getTimeoutTimestampNS()); + : asVow(() => E(timestampHelper).getTimeoutTimestampNS())); // don't resolve the vow until the transfer is confirmed on remote // and reject vow if the transfer fails for any reason From 5e048af2af3cb1c86f6e42229600251a3cd1dbc5 Mon Sep 17 00:00:00 2001 From: 0xPatrick Date: Mon, 25 Nov 2024 21:55:10 -0500 Subject: [PATCH 23/56] refactor: cosmos-orchestration-account-kit.test.ts this test can no longer rely on the IST brand being available, so we - added checks to ensure brands are accepted for `.transfer` and `.send`. marked as failing for now - filed #10449 since this surfaced a bug in `amountToCoin` - use Moolah issuer for "no denom for brand" failure path tests --- .../test/bootstrapTests/orchestration.test.ts | 4 +- .../examples/staking-combinations.contract.js | 1 + .../examples/staking-combinations.flows.js | 13 ++- .../src/exos/cosmos-orchestration-account.js | 2 + .../exos/cosmos-orchestration-account.test.ts | 104 +++++++++++++++--- packages/orchestration/test/supports.ts | 1 + 6 files changed, 106 insertions(+), 19 deletions(-) diff --git a/packages/boot/test/bootstrapTests/orchestration.test.ts b/packages/boot/test/bootstrapTests/orchestration.test.ts index b51f13e6568..fa976fd7dac 100644 --- a/packages/boot/test/bootstrapTests/orchestration.test.ts +++ b/packages/boot/test/bootstrapTests/orchestration.test.ts @@ -266,7 +266,9 @@ test.serial('stakeAtom - smart wallet', async t => { proposal: {}, }), { - message: 'No denom for brand [object Alleged: ATOM brand]', + // TODO #10449 + message: + "'amountToCoin' not working for \"[Alleged: ATOM brand]\" until #10449; use 'DenomAmount' for now", }, ); }); diff --git a/packages/orchestration/src/examples/staking-combinations.contract.js b/packages/orchestration/src/examples/staking-combinations.contract.js index b38da6633d6..209fe7dc787 100644 --- a/packages/orchestration/src/examples/staking-combinations.contract.js +++ b/packages/orchestration/src/examples/staking-combinations.contract.js @@ -131,6 +131,7 @@ const contract = async ( ); const orchFns = orchestrateAll(flows, { + chainHub, sharedLocalAccountP, makeCombineInvitationMakers, makeExtraInvitationMaker, diff --git a/packages/orchestration/src/examples/staking-combinations.flows.js b/packages/orchestration/src/examples/staking-combinations.flows.js index 23b1583ce58..794d13099f8 100644 --- a/packages/orchestration/src/examples/staking-combinations.flows.js +++ b/packages/orchestration/src/examples/staking-combinations.flows.js @@ -1,6 +1,6 @@ /** * @import {GuestInterface} from '@agoric/async-flow'; - * @import {Orchestrator, OrchestrationFlow, AmountArg, CosmosValidatorAddress, ChainAddress, LocalAccountMethods, OrchestrationAccountI} from '../types.js' + * @import {Orchestrator, OrchestrationFlow, AmountArg, CosmosValidatorAddress, ChainAddress, LocalAccountMethods, OrchestrationAccountI, ChainHub} from '../types.js' * @import {ContinuingOfferResult, InvitationMakers} from '@agoric/smart-wallet/src/types.js'; * @import {LocalOrchestrationAccountKit} from '../exos/local-orchestration-account.js'; * @import {MakeCombineInvitationMakers} from '../exos/combine-invitation-makers.js'; @@ -9,7 +9,7 @@ */ import { mustMatch } from '@endo/patterns'; -import { makeError, q } from '@endo/errors'; +import { Fail, makeError, q } from '@endo/errors'; import { makeTracer } from '@agoric/internal'; import { ChainAddressShape } from '../typeGuards.js'; @@ -48,6 +48,7 @@ harden(makeAccount); * @satisfies {OrchestrationFlow} * @param {Orchestrator} orch * @param {object} ctx + * @param {GuestInterface} ctx.chainHub * @param {Promise>} ctx.sharedLocalAccountP * @param {GuestInterface} ctx.zoeTools * @param {GuestInterface} account @@ -57,7 +58,7 @@ harden(makeAccount); */ export const depositAndDelegate = async ( orch, - { sharedLocalAccountP, zoeTools }, + { chainHub, sharedLocalAccountP, zoeTools }, account, seat, validator, @@ -84,7 +85,11 @@ export const depositAndDelegate = async ( throw errMsg; } seat.exit(); - await account.delegate(validator, give.Stake); + const denom = chainHub.getDenom(give.Stake.brand); + if (!denom) throw Fail`unknown brand ${q(give.Stake.brand)}`; + // TODO #10449 amountToCoin accepts brands + const denomAmount = harden({ denom, value: give.Stake.value }); + await account.delegate(validator, denomAmount); }; harden(depositAndDelegate); diff --git a/packages/orchestration/src/exos/cosmos-orchestration-account.js b/packages/orchestration/src/exos/cosmos-orchestration-account.js index cc33d39c448..843bb10fbb5 100644 --- a/packages/orchestration/src/exos/cosmos-orchestration-account.js +++ b/packages/orchestration/src/exos/cosmos-orchestration-account.js @@ -340,6 +340,8 @@ export const prepareCosmosOrchestrationAccountKit = ( * @returns {Coin} */ amountToCoin(amount) { + !('brand' in amount) || + Fail`'amountToCoin' not working for ${q(amount.brand)} until #10449; use 'DenomAmount' for now`; return coerceCoin(chainHub, amount); }, }, diff --git a/packages/orchestration/test/exos/cosmos-orchestration-account.test.ts b/packages/orchestration/test/exos/cosmos-orchestration-account.test.ts index f88664fad1d..1cfb26d7a2f 100644 --- a/packages/orchestration/test/exos/cosmos-orchestration-account.test.ts +++ b/packages/orchestration/test/exos/cosmos-orchestration-account.test.ts @@ -14,6 +14,10 @@ import { QueryBalanceRequest, QueryBalanceResponse, } from '@agoric/cosmic-proto/cosmos/bank/v1beta1/query.js'; +import { + MsgSend, + MsgSendResponse, +} from '@agoric/cosmic-proto/cosmos/bank/v1beta1/tx.js'; import { Coin } from '@agoric/cosmic-proto/cosmos/base/v1beta1/coin.js'; import { QueryDelegationRequest, @@ -38,6 +42,8 @@ import { MsgDelegate, MsgDelegateResponse, } from '@agoric/cosmic-proto/cosmos/staking/v1beta1/tx.js'; +import { withAmountUtils } from '@agoric/zoe/tools/test-utils.js'; +import { makeIssuerKit } from '@agoric/ertp'; import { decodeBase64 } from '@endo/base64'; import { commonSetup } from '../supports.js'; import type { @@ -55,6 +61,8 @@ import { } from '../../tools/ibc-mocks.js'; import type { CosmosValidatorAddress } from '../../src/cosmos-api.js'; import { protoMsgMocks } from '../ibc-mocks.js'; +import fetchedChainInfo from '../../src/fetched-chain-info.js'; +import { assetOn } from '../../src/utils/asset.js'; type TestContext = Awaited>; @@ -64,9 +72,18 @@ test.beforeEach(async t => { t.context = await commonSetup(t); }); +const [uistOnCosmos] = assetOn( + 'uist', + 'agoric', + undefined, + 'cosmoshub', + fetchedChainInfo, +); + test('send (to addr on same chain)', async t => { const { brands: { ist }, + mocks: { ibcBridge }, utils: { inspectDibcBridge, populateChainHub }, } = t.context; populateChainHub(); @@ -89,6 +106,42 @@ test('send (to addr on same chain)', async t => { undefined, ); + // register handler for ist bank send + ibcBridge.addMockAck( + buildTxPacketString([ + MsgSend.toProtoMsg({ + fromAddress: 'cosmos1test', + toAddress: 'cosmos99test', + amount: [ + { + denom: uistOnCosmos, + // denom: 'ibc/uisthash', + amount: '10', + }, + ], + }), + ]), + buildMsgResponseString(MsgSendResponse, {}), + ); + + t.is( + await E(account).send(toAddress, { + denom: uistOnCosmos, + value: 10n, + } as AmountArg), + undefined, + 'send accepts Amount', + ); + + await t.throwsAsync( + () => E(account).send(toAddress, ist.make(10n) as AmountArg), + { + message: + "'amountToCoin' not working for \"[Alleged: IST brand]\" until #10449; use 'DenomAmount' for now", + }, + 'TODO #10449 amountToCoin for CosmosOrchestrationAccount', + ); + // simulate timeout error await t.throwsAsync( E(account).send(toAddress, { value: 504n, denom: 'uatom' } as AmountArg), @@ -96,10 +149,17 @@ test('send (to addr on same chain)', async t => { { message: 'ABCI code: 5: error handling packet: see events for details' }, ); - // IST not registered - await t.throwsAsync(E(account).send(toAddress, ist.make(10n) as AmountArg), { - message: 'No denom for brand [object Alleged: IST brand]', - }); + // MOO brand not registered + const moolah = withAmountUtils(makeIssuerKit('MOO')); + await t.throwsAsync( + E(account).send(toAddress, moolah.make(10n) as AmountArg), + { + // TODO #10449 + // message: 'No denom for brand [object Alleged: MOO brand]', + message: + "'amountToCoin' not working for \"[Alleged: MOO brand]\" until #10449; use 'DenomAmount' for now", + }, + ); // multi-send (sendAll) t.is( @@ -111,11 +171,10 @@ test('send (to addr on same chain)', async t => { ); const { bridgeDowncalls } = await inspectDibcBridge(); - t.is( bridgeDowncalls.filter(d => d.method === 'sendPacket').length, - 3, - 'sent 2 successful txs and 1 failed. 1 rejected before sending', + 4, + 'sent 3 successful txs and 1 failed. 1 rejected before sending', ); }); @@ -186,6 +245,14 @@ test('transfer', async t => { }, }); + const umooTransfer = toTransferTxPacket({ + ...mockIbcTransfer, + token: { + denom: 'umoo', + amount: '10', + }, + }); + return { [defaultTransfer]: transferResp, [customTimeoutHeight]: transferResp, @@ -193,6 +260,7 @@ test('transfer', async t => { [customTimeout]: transferResp, [customMemo]: transferResp, [uistTransfer]: transferResp, + [umooTransfer]: transferResp, }; }; ibcBridge.setMockAck(buildMocks()); @@ -309,18 +377,26 @@ test('transfer', async t => { }, ); + const moolah = withAmountUtils(makeIssuerKit('MOO')); t.log('transfer throws if asset is not in its chainHub'); - await t.throwsAsync(E(account).transfer(mockDestination, ist.make(10n)), { - message: 'No denom for brand [object Alleged: IST brand]', + await t.throwsAsync(E(account).transfer(mockDestination, moolah.make(10n)), { + // TODO #10449 + // message: 'No denom for brand [object Alleged: MOO brand]', + message: + "'amountToCoin' not working for \"[Alleged: MOO brand]\" until #10449; use 'DenomAmount' for now", }); - chainHub.registerAsset('uist', { - baseDenom: 'uist', + chainHub.registerAsset('umoo', { + baseDenom: 'umoo', baseName: 'agoric', - brand: ist.brand, + brand: moolah.brand, chainName: 'agoric', }); - // uses uistTransfer mock above - await E(account).transfer(mockDestination, ist.make(10n)); + // uses umooTransfer mock above + await E(account).transfer( + mockDestination, + // moolah.make(10n), // TODO #10449 restore + { denom: 'umoo', value: 10n }, + ); t.log('transfer timeout error recieved and handled from the bridge'); await t.throwsAsync( diff --git a/packages/orchestration/test/supports.ts b/packages/orchestration/test/supports.ts index 0454f493eb3..2d8a85cb056 100644 --- a/packages/orchestration/test/supports.ts +++ b/packages/orchestration/test/supports.ts @@ -178,6 +178,7 @@ export const commonSetup = async (t: ExecutionContext) => { const commonAssetInfo = harden([ assetOn('ubld', 'agoric', bldSansMint.brand), assetOn('uist', 'agoric', istSansMint.brand), + assetOn('uist', 'agoric', undefined, 'cosmoshub', chainInfoWithCaps), assetOn('uusdc', 'noble', undefined, 'agoric', chainInfoWithCaps), assetOn('uatom', 'cosmoshub', undefined, 'agoric', chainInfoWithCaps), assetOn('uusdc', 'noble', undefined, 'dydx', chainInfoWithCaps), From 20cf6d4db81dadc0c80af7d936bcb18cb7b7740a Mon Sep 17 00:00:00 2001 From: 0xPatrick Date: Mon, 25 Nov 2024 22:57:41 -0500 Subject: [PATCH 24/56] chore: send-anywhere includes IST and BLD brands - enables sending offers with brands --- .../src/proposals/start-send-anywhere.js | 28 +++++++++++++------ 1 file changed, 20 insertions(+), 8 deletions(-) diff --git a/packages/orchestration/src/proposals/start-send-anywhere.js b/packages/orchestration/src/proposals/start-send-anywhere.js index 6d1c6932bc1..b0db84c3f32 100644 --- a/packages/orchestration/src/proposals/start-send-anywhere.js +++ b/packages/orchestration/src/proposals/start-send-anywhere.js @@ -6,17 +6,15 @@ import { import { E } from '@endo/far'; /// + /** * @import {Installation} from '@agoric/zoe/src/zoeService/utils.js'; * @import {CosmosChainInfo, Denom, DenomDetail} from '@agoric/orchestration'; + * @import {start as StartFn} from '@agoric/orchestration/src/examples/send-anywhere.contract.js'; */ const trace = makeTracer('StartSA', true); -/** - * @import {start as StartFn} from '@agoric/orchestration/src/examples/send-anywhere.contract.js'; - */ - /** * @param {BootstrapPowers & { * installation: { @@ -24,6 +22,18 @@ const trace = makeTracer('StartSA', true); * sendAnywhere: Installation; * }; * }; + * instance: { + * produce: { + * sendAnywhere: Producer; + * }; + * }; + * issuer: { + * consume: { + * BLD: Issuer<'nat'>; + * IST: Issuer<'nat'>; + * USDC: Issuer<'nat'>; + * }; + * }; * }} powers * @param {{ * options: { @@ -47,11 +57,10 @@ export const startSendAnywhere = async ( consume: { sendAnywhere }, }, instance: { - // @ts-expect-error unknown instance produce: { sendAnywhere: produceInstance }, }, issuer: { - consume: { IST }, + consume: { BLD, IST }, }, }, { options: { chainInfo, assetInfo } }, @@ -78,7 +87,10 @@ export const startSendAnywhere = async ( const { instance } = await E(startUpgradable)({ label: 'send-anywhere', installation: sendAnywhere, - issuerKeywordRecord: { Stable: await IST }, + issuerKeywordRecord: { + Stable: await IST, + Stake: await BLD, + }, privateArgs, }); produceInstance.resolve(instance); @@ -107,7 +119,7 @@ export const getManifest = ({ restoreRef }, { installationRef, options }) => { produce: { sendAnywhere: true }, }, issuer: { - consume: { IST: true }, + consume: { BLD: true, IST: true }, }, }, }, From 09a3a923e4c72f7a7deae44dbc2bbe18b2d37e4c Mon Sep 17 00:00:00 2001 From: 0xPatrick Date: Mon, 25 Nov 2024 23:00:10 -0500 Subject: [PATCH 25/56] chore: update send-anywhere baggage snapshot --- .../snapshots/send-anywhere.test.ts.md | 1101 ++++++++++++++++- .../snapshots/send-anywhere.test.ts.snap | Bin 1702 -> 9152 bytes 2 files changed, 1098 insertions(+), 3 deletions(-) diff --git a/packages/orchestration/test/examples/snapshots/send-anywhere.test.ts.md b/packages/orchestration/test/examples/snapshots/send-anywhere.test.ts.md index cb7e77f4a24..df818b1eba8 100644 --- a/packages/orchestration/test/examples/snapshots/send-anywhere.test.ts.md +++ b/packages/orchestration/test/examples/snapshots/send-anywhere.test.ts.md @@ -36,22 +36,1117 @@ Generated by [AVA](https://avajs.dev). ChainHub_singleton: 'Alleged: ChainHub', bech32PrefixToChainName: { agoric: 'agoric', + celestia: 'celestia', + cosmos: 'cosmoshub', + dydx: 'dydx', + juno: 'juno', + neutron: 'neutron', + noble: 'noble', + omniflix: 'omniflixhub', + osmo: 'osmosis', + secret: 'secretnetwork', + stars: 'stargaze', + stride: 'stride', + umee: 'umee', + }, + brandDenom: { + 'Alleged: BLD brand': 'ubld', + 'Alleged: IST brand': 'uist', }, - brandDenom: {}, chainInfos: { agoric: { bech32Prefix: 'agoric', chainId: 'agoric-3', icqEnabled: false, + pfmEnabled: true, stakingTokens: [ { denom: 'ubld', }, ], }, + celestia: { + bech32Prefix: 'celestia', + chainId: 'celestia', + icqEnabled: false, + pfmEnabled: true, + stakingTokens: [ + { + denom: 'utia', + }, + ], + }, + cosmoshub: { + bech32Prefix: 'cosmos', + chainId: 'cosmoshub-4', + icqEnabled: false, + pfmEnabled: true, + stakingTokens: [ + { + denom: 'uatom', + }, + ], + }, + dydx: { + bech32Prefix: 'dydx', + chainId: 'dydx-mainnet-1', + icqEnabled: false, + pfmEnabled: false, + stakingTokens: [ + { + denom: 'adydx', + }, + ], + }, + juno: { + bech32Prefix: 'juno', + chainId: 'juno-1', + icqEnabled: false, + pfmEnabled: true, + stakingTokens: [ + { + denom: 'ujuno', + }, + ], + }, + neutron: { + bech32Prefix: 'neutron', + chainId: 'neutron-1', + icqEnabled: false, + pfmEnabled: true, + stakingTokens: [ + { + denom: 'untrn', + }, + ], + }, + noble: { + bech32Prefix: 'noble', + chainId: 'noble-1', + icqEnabled: false, + pfmEnabled: true, + }, + omniflixhub: { + bech32Prefix: 'omniflix', + chainId: 'omniflixhub-1', + icqEnabled: true, + pfmEnabled: true, + stakingTokens: [ + { + denom: 'uflix', + }, + ], + }, + osmosis: { + bech32Prefix: 'osmo', + chainId: 'osmosis-1', + icqEnabled: true, + pfmEnabled: true, + stakingTokens: [ + { + denom: 'uosmo', + }, + ], + }, + secretnetwork: { + bech32Prefix: 'secret', + chainId: 'secret-4', + icqEnabled: false, + pfmEnabled: true, + stakingTokens: [ + { + denom: 'uscrt', + }, + ], + }, + stargaze: { + bech32Prefix: 'stars', + chainId: 'stargaze-1', + icqEnabled: false, + pfmEnabled: true, + stakingTokens: [ + { + denom: 'ustars', + }, + ], + }, + stride: { + bech32Prefix: 'stride', + chainId: 'stride-1', + icqEnabled: false, + pfmEnabled: true, + stakingTokens: [ + { + denom: 'ustrd', + }, + ], + }, + umee: { + bech32Prefix: 'umee', + chainId: 'umee-1', + icqEnabled: false, + pfmEnabled: true, + stakingTokens: [ + { + denom: 'uumee', + }, + ], + }, + }, + connectionInfos: { + 'agoric-3_cosmoshub-4': { + client_id: '07-tendermint-6', + counterparty: { + client_id: '07-tendermint-927', + connection_id: 'connection-649', + }, + id: 'connection-8', + state: 3, + transferChannel: { + channelId: 'channel-5', + counterPartyChannelId: 'channel-405', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'agoric-3_noble-1': { + client_id: '07-tendermint-77', + counterparty: { + client_id: '07-tendermint-32', + connection_id: 'connection-40', + }, + id: 'connection-72', + state: 3, + transferChannel: { + channelId: 'channel-62', + counterPartyChannelId: 'channel-21', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'agoric-3_omniflixhub-1': { + client_id: '07-tendermint-73', + counterparty: { + client_id: '07-tendermint-47', + connection_id: 'connection-40', + }, + id: 'connection-67', + state: 3, + transferChannel: { + channelId: 'channel-58', + counterPartyChannelId: 'channel-30', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'agoric-3_osmosis-1': { + client_id: '07-tendermint-1', + counterparty: { + client_id: '07-tendermint-2109', + connection_id: 'connection-1649', + }, + id: 'connection-1', + state: 3, + transferChannel: { + channelId: 'channel-1', + counterPartyChannelId: 'channel-320', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'agoric-3_secret-4': { + client_id: '07-tendermint-17', + counterparty: { + client_id: '07-tendermint-111', + connection_id: 'connection-80', + }, + id: 'connection-17', + state: 3, + transferChannel: { + channelId: 'channel-10', + counterPartyChannelId: 'channel-51', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'agoric-3_stride-1': { + client_id: '07-tendermint-74', + counterparty: { + client_id: '07-tendermint-129', + connection_id: 'connection-118', + }, + id: 'connection-68', + state: 3, + transferChannel: { + channelId: 'channel-59', + counterPartyChannelId: 'channel-148', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'agoric-3_umee-1': { + client_id: '07-tendermint-18', + counterparty: { + client_id: '07-tendermint-152', + connection_id: 'connection-101', + }, + id: 'connection-18', + state: 3, + transferChannel: { + channelId: 'channel-11', + counterPartyChannelId: 'channel-42', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'celestia_neutron-1': { + client_id: '07-tendermint-29', + counterparty: { + client_id: '07-tendermint-48', + connection_id: 'connection-36', + }, + id: 'connection-7', + state: 3, + transferChannel: { + channelId: 'channel-8', + counterPartyChannelId: 'channel-35', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'celestia_osmosis-1': { + client_id: '07-tendermint-10', + counterparty: { + client_id: '07-tendermint-3012', + connection_id: 'connection-2503', + }, + id: 'connection-2', + state: 3, + transferChannel: { + channelId: 'channel-2', + counterPartyChannelId: 'channel-6994', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'celestia_secret-4': { + client_id: '07-tendermint-52', + counterparty: { + client_id: '07-tendermint-174', + connection_id: 'connection-131', + }, + id: 'connection-15', + state: 3, + transferChannel: { + channelId: 'channel-14', + counterPartyChannelId: 'channel-91', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'celestia_stargaze-1': { + client_id: '07-tendermint-86', + counterparty: { + client_id: '07-tendermint-359', + connection_id: 'connection-296', + }, + id: 'connection-56', + state: 3, + transferChannel: { + channelId: 'channel-33', + counterPartyChannelId: 'channel-291', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'celestia_stride-1': { + client_id: '07-tendermint-0', + counterparty: { + client_id: '07-tendermint-137', + connection_id: 'connection-125', + }, + id: 'connection-4', + state: 3, + transferChannel: { + channelId: 'channel-4', + counterPartyChannelId: 'channel-162', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'cosmoshub-4_juno-1': { + client_id: '07-tendermint-439', + counterparty: { + client_id: '07-tendermint-3', + connection_id: 'connection-2', + }, + id: 'connection-372', + state: 3, + transferChannel: { + channelId: 'channel-207', + counterPartyChannelId: 'channel-1', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'cosmoshub-4_neutron-1': { + client_id: '07-tendermint-1119', + counterparty: { + client_id: '07-tendermint-0', + connection_id: 'connection-0', + }, + id: 'connection-809', + state: 3, + transferChannel: { + channelId: 'channel-569', + counterPartyChannelId: 'channel-1', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'cosmoshub-4_noble-1': { + client_id: '07-tendermint-1116', + counterparty: { + client_id: '07-tendermint-4', + connection_id: 'connection-12', + }, + id: 'connection-790', + state: 3, + transferChannel: { + channelId: 'channel-536', + counterPartyChannelId: 'channel-4', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'cosmoshub-4_omniflixhub-1': { + client_id: '07-tendermint-656', + counterparty: { + client_id: '07-tendermint-23', + connection_id: 'connection-19', + }, + id: 'connection-501', + state: 3, + transferChannel: { + channelId: 'channel-306', + counterPartyChannelId: 'channel-12', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'cosmoshub-4_osmosis-1': { + client_id: '07-tendermint-259', + counterparty: { + client_id: '07-tendermint-1', + connection_id: 'connection-1', + }, + id: 'connection-257', + state: 3, + transferChannel: { + channelId: 'channel-141', + counterPartyChannelId: 'channel-0', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'cosmoshub-4_secret-4': { + client_id: '07-tendermint-492', + counterparty: { + client_id: '07-tendermint-1', + connection_id: 'connection-0', + }, + id: 'connection-401', + state: 3, + transferChannel: { + channelId: 'channel-235', + counterPartyChannelId: 'channel-0', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'cosmoshub-4_stargaze-1': { + client_id: '07-tendermint-1188', + counterparty: { + client_id: '07-tendermint-320', + connection_id: 'connection-256', + }, + id: 'connection-918', + state: 3, + transferChannel: { + channelId: 'channel-730', + counterPartyChannelId: 'channel-239', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'cosmoshub-4_stride-1': { + client_id: '07-tendermint-913', + counterparty: { + client_id: '07-tendermint-0', + connection_id: 'connection-0', + }, + id: 'connection-635', + state: 3, + transferChannel: { + channelId: 'channel-391', + counterPartyChannelId: 'channel-0', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'dydx-mainnet-1_neutron-1': { + client_id: '07-tendermint-11', + counterparty: { + client_id: '07-tendermint-72', + connection_id: 'connection-51', + }, + id: 'connection-17', + state: 3, + transferChannel: { + channelId: 'channel-11', + counterPartyChannelId: 'channel-48', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'dydx-mainnet-1_noble-1': { + client_id: '07-tendermint-0', + counterparty: { + client_id: '07-tendermint-59', + connection_id: 'connection-57', + }, + id: 'connection-0', + state: 3, + transferChannel: { + channelId: 'channel-0', + counterPartyChannelId: 'channel-33', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'dydx-mainnet-1_osmosis-1': { + client_id: '07-tendermint-3', + counterparty: { + client_id: '07-tendermint-3009', + connection_id: 'connection-2500', + }, + id: 'connection-7', + state: 3, + transferChannel: { + channelId: 'channel-3', + counterPartyChannelId: 'channel-6787', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'dydx-mainnet-1_stride-1': { + client_id: '07-tendermint-1', + counterparty: { + client_id: '07-tendermint-133', + connection_id: 'connection-123', + }, + id: 'connection-1', + state: 3, + transferChannel: { + channelId: 'channel-1', + counterPartyChannelId: 'channel-160', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'dydx-mainnet-1_umee-1': { + client_id: '07-tendermint-8', + counterparty: { + client_id: '07-tendermint-244', + connection_id: 'connection-208', + }, + id: 'connection-13', + state: 3, + transferChannel: { + channelId: 'channel-8', + counterPartyChannelId: 'channel-118', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'juno-1_neutron-1': { + client_id: '07-tendermint-557', + counterparty: { + client_id: '07-tendermint-97', + connection_id: 'connection-71', + }, + id: 'connection-524', + state: 3, + transferChannel: { + channelId: 'channel-548', + counterPartyChannelId: 'channel-4328', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'juno-1_noble-1': { + client_id: '07-tendermint-334', + counterparty: { + client_id: '07-tendermint-3', + connection_id: 'connection-8', + }, + id: 'connection-322', + state: 3, + transferChannel: { + channelId: 'channel-224', + counterPartyChannelId: 'channel-3', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'juno-1_osmosis-1': { + client_id: '07-tendermint-0', + counterparty: { + client_id: '07-tendermint-1457', + connection_id: 'connection-1142', + }, + id: 'connection-0', + state: 3, + transferChannel: { + channelId: 'channel-0', + counterPartyChannelId: 'channel-42', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'juno-1_secret-4': { + client_id: '07-tendermint-108', + counterparty: { + client_id: '07-tendermint-23', + connection_id: 'connection-9', + }, + id: 'connection-68', + state: 3, + transferChannel: { + channelId: 'channel-48', + counterPartyChannelId: 'channel-8', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'juno-1_stargaze-1': { + client_id: '07-tendermint-44', + counterparty: { + client_id: '07-tendermint-13', + connection_id: 'connection-11', + }, + id: 'connection-30', + state: 3, + transferChannel: { + channelId: 'channel-20', + counterPartyChannelId: 'channel-5', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'juno-1_stride-1': { + client_id: '07-tendermint-263', + counterparty: { + client_id: '07-tendermint-31', + connection_id: 'connection-19', + }, + id: 'connection-205', + state: 3, + transferChannel: { + channelId: 'channel-139', + counterPartyChannelId: 'channel-24', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'neutron-1_noble-1': { + client_id: '07-tendermint-40', + counterparty: { + client_id: '07-tendermint-25', + connection_id: 'connection-34', + }, + id: 'connection-31', + state: 3, + transferChannel: { + channelId: 'channel-30', + counterPartyChannelId: 'channel-18', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'neutron-1_osmosis-1': { + client_id: '07-tendermint-19', + counterparty: { + client_id: '07-tendermint-2823', + connection_id: 'connection-2338', + }, + id: 'connection-18', + state: 3, + transferChannel: { + channelId: 'channel-10', + counterPartyChannelId: 'channel-874', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'neutron-1_secret-4': { + client_id: '07-tendermint-85', + counterparty: { + client_id: '07-tendermint-199', + connection_id: 'connection-192', + }, + id: 'connection-63', + state: 3, + transferChannel: { + channelId: 'channel-1551', + counterPartyChannelId: 'channel-144', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'neutron-1_stargaze-1': { + client_id: '07-tendermint-31', + counterparty: { + client_id: '07-tendermint-283', + connection_id: 'connection-211', + }, + id: 'connection-23', + state: 3, + transferChannel: { + channelId: 'channel-18', + counterPartyChannelId: 'channel-191', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'neutron-1_stride-1': { + client_id: '07-tendermint-18', + counterparty: { + client_id: '07-tendermint-125', + connection_id: 'connection-113', + }, + id: 'connection-15', + state: 3, + transferChannel: { + channelId: 'channel-8', + counterPartyChannelId: 'channel-123', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'noble-1_omniflixhub-1': { + client_id: '07-tendermint-68', + counterparty: { + client_id: '07-tendermint-51', + connection_id: 'connection-49', + }, + id: 'connection-65', + state: 3, + transferChannel: { + channelId: 'channel-44', + counterPartyChannelId: 'channel-38', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'noble-1_osmosis-1': { + client_id: '07-tendermint-0', + counterparty: { + client_id: '07-tendermint-2704', + connection_id: 'connection-2241', + }, + id: 'connection-2', + state: 3, + transferChannel: { + channelId: 'channel-1', + counterPartyChannelId: 'channel-750', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'noble-1_secret-4': { + client_id: '07-tendermint-24', + counterparty: { + client_id: '07-tendermint-170', + connection_id: 'connection-127', + }, + id: 'connection-33', + state: 3, + transferChannel: { + channelId: 'channel-17', + counterPartyChannelId: 'channel-88', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'noble-1_stargaze-1': { + client_id: '07-tendermint-16', + counterparty: { + client_id: '07-tendermint-287', + connection_id: 'connection-214', + }, + id: 'connection-25', + state: 3, + transferChannel: { + channelId: 'channel-11', + counterPartyChannelId: 'channel-204', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'noble-1_umee-1': { + client_id: '07-tendermint-73', + counterparty: { + client_id: '07-tendermint-248', + connection_id: 'connection-210', + }, + id: 'connection-74', + state: 3, + transferChannel: { + channelId: 'channel-51', + counterPartyChannelId: 'channel-120', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'omniflixhub-1_osmosis-1': { + client_id: '07-tendermint-8', + counterparty: { + client_id: '07-tendermint-1829', + connection_id: 'connection-1431', + }, + id: 'connection-8', + state: 3, + transferChannel: { + channelId: 'channel-1', + counterPartyChannelId: 'channel-199', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'osmosis-1_secret-4': { + client_id: '07-tendermint-1588', + counterparty: { + client_id: '07-tendermint-2', + connection_id: 'connection-1', + }, + id: 'connection-1244', + state: 3, + transferChannel: { + channelId: 'channel-88', + counterPartyChannelId: 'channel-1', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'osmosis-1_stargaze-1': { + client_id: '07-tendermint-1562', + counterparty: { + client_id: '07-tendermint-0', + connection_id: 'connection-0', + }, + id: 'connection-1223', + state: 3, + transferChannel: { + channelId: 'channel-75', + counterPartyChannelId: 'channel-0', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'osmosis-1_stride-1': { + client_id: '07-tendermint-2119', + counterparty: { + client_id: '07-tendermint-1', + connection_id: 'connection-2', + }, + id: 'connection-1657', + state: 3, + transferChannel: { + channelId: 'channel-326', + counterPartyChannelId: 'channel-5', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'osmosis-1_umee-1': { + client_id: '07-tendermint-1805', + counterparty: { + client_id: '07-tendermint-6', + connection_id: 'connection-0', + }, + id: 'connection-1410', + state: 3, + transferChannel: { + channelId: 'channel-184', + counterPartyChannelId: 'channel-0', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'secret-4_stargaze-1': { + client_id: '07-tendermint-43', + counterparty: { + client_id: '07-tendermint-177', + connection_id: 'connection-110', + }, + id: 'connection-25', + state: 3, + transferChannel: { + channelId: 'channel-19', + counterPartyChannelId: 'channel-48', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'secret-4_stride-1': { + client_id: '07-tendermint-75', + counterparty: { + client_id: '07-tendermint-37', + connection_id: 'connection-25', + }, + id: 'connection-40', + state: 3, + transferChannel: { + channelId: 'channel-37', + counterPartyChannelId: 'channel-40', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'secret-4_umee-1': { + client_id: '07-tendermint-193', + counterparty: { + client_id: '07-tendermint-249', + connection_id: 'connection-213', + }, + id: 'connection-188', + state: 3, + transferChannel: { + channelId: 'channel-126', + counterPartyChannelId: 'channel-123', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'stargaze-1_stride-1': { + client_id: '07-tendermint-195', + counterparty: { + client_id: '07-tendermint-30', + connection_id: 'connection-18', + }, + id: 'connection-128', + state: 3, + transferChannel: { + channelId: 'channel-106', + counterPartyChannelId: 'channel-19', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + 'stride-1_umee-1': { + client_id: '07-tendermint-32', + counterparty: { + client_id: '07-tendermint-64', + connection_id: 'connection-45', + }, + id: 'connection-20', + state: 3, + transferChannel: { + channelId: 'channel-29', + counterPartyChannelId: 'channel-34', + counterPartyPortId: 'transfer', + ordering: 0, + portId: 'transfer', + state: 3, + version: 'ics20-1', + }, + }, + }, + denom: { + 'agoric:ibc/BA313C4A19DFBF943586C0387E6B11286F9E416B4DD27574E6909CABE0E342FA': { + baseDenom: 'uatom', + baseName: 'cosmoshub', + chainName: 'agoric', + }, + 'agoric:ibc/FE98AAD68F02F03565E9FA39A5E627946699B2B07115889ED812D8BA639576A9': { + baseDenom: 'uusdc', + baseName: 'noble', + chainName: 'agoric', + }, + 'agoric:ubld': { + baseDenom: 'ubld', + baseName: 'agoric', + brand: Object @Alleged: BLD brand {}, + chainName: 'agoric', + }, + 'agoric:uist': { + baseDenom: 'uist', + baseName: 'agoric', + brand: Object @Alleged: IST brand {}, + chainName: 'agoric', + }, + 'cosmoshub:ibc/9EA9BCC30570DC3198317BB6B5561AB41DDC17AFC342087022C128C57EFE19BA': { + baseDenom: 'uist', + baseName: 'agoric', + chainName: 'cosmoshub', + }, + 'dydx:ibc/8E27BA2D5493AF5636760E354E46004562C46AB7EC0CC4C1CA14E9E20E2545B5': { + baseDenom: 'uusdc', + baseName: 'noble', + chainName: 'dydx', + }, }, - connectionInfos: {}, - denom: {}, lookupChainInfo_kindHandle: 'Alleged: kind', lookupChainsAndConnection_kindHandle: 'Alleged: kind', lookupConnectionInfo_kindHandle: 'Alleged: kind', diff --git a/packages/orchestration/test/examples/snapshots/send-anywhere.test.ts.snap b/packages/orchestration/test/examples/snapshots/send-anywhere.test.ts.snap index 019aa9a9d1af05779e75d69327a22ac5f66f262f..3cf1a7c6eca84a3e8d241754528dd71dc9e77105 100644 GIT binary patch literal 9152 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 KjVI2Z&j0`bc-VXZ literal 1702 zcmV;X23h$*RzVOD=gCC0s00000000A>SWAc;MHv2S-ZQ)No=x_ZWD+GpFcJ+R;z8JKvLv`MYqHr8 z5VWSdcD6G;RbzKgCJ{UYPl5*ziugd1;3FtOL^OxsMK1>Nfnx9=A`-;M!IK~g!A$qe zY<2Z!v%P!S-TA-&tE#`g|50;cv1SUbVV}Fm9K$hLy+-SGT4#pMY0F*`j(zT;u2YAe z9Qh!MB)UH&MN%^WW&yka;2MA%0B!;pCBR++lu4pU5=UyMnC1{N__I(bfMh|EAbFHY zq(Y(~@gmv0zirW)$*ObhnrYZe)kh5HiH5=TgOuwg>%+2Brpf9|f2i8EDIDdaOcR#Q ztTj012suoEzBx_pvs{}oMaMOrmrN;bi5mQ1yXIQ{^jQRVEUG!KWqV}Vk``4H#3E=qza6O?=rBtfqL=xDV1fEO+mu~(3 zISGuXfPE>&wWzwLX$q*PfU7BBC=JY}f#=e|7ir+vG=PjkF&bEXQwF#z11x5Mk2ApE z8DP&4&>B))s{wTlE6Ny~(whdK>fdo#VT~&8w!!Nra|G`LHV(Y~NQI}e&*<*b5IpP- zCTH5*bv({H7HzfGq;Vg^M35nHjPU_M0PJe`^`T`A7iLBMm?JE9m^rjtAJk;*+rw^j z?3hCx7UrBeLOzprR`GJV&9wux&a4x(!7STF{U)J`1Jn#P%(lfmNMcxmESjP-BdjBB zM-xr95V+5D+uh}1+UkEYGT2&&(Z*rgazo&1GNT4)x>r}i2Bh>BH8kq;M`OB zGT@2?i0dAw?@;5W5RGo zDTVC5X<;{oT|FWrt3C4SL1C_~`f{s!zrt4TR$iKbz*6V%a`!YgNdL39prhgqDO_Bxa@;;wt#F-&`Hm-LJj z?{P~$n9`b3B=TAoxR6!Gqo_JrMLx{}pZ8($Da)c~Nv!`@KA-RAppPOEp!hZm{GhIs z48XSMfO~TaEUm!&)=Yrpu^ezhB^g?kB)_V)pe_*=IiQ^bURIYW1$Og(4){ogjj6EM zmpS0O959*(PUaQ(<^bzkdEh-2wq?~*Yz>UPMA2HN&N%amoBL7s0g-WGLxlX1cb{@A zxNRPYP|&PvuolQ!6_ z)L>kME&JPy>xUeP{f*nON7d$kXy5d_MY+AmtZr*#)_R(OQPYkxyKOq_tuXmH@oNR(>jLm^0oYaqri+T4hXbmw6@eucRt{w6#UgO2 z2>hZ#D*@=uA`mM9+e!*_JdiChb!d?%VppHp?2<86VT9}I>5X2+Ji<4 zt{V52qyflwXv5(3dC_3pUh(oOG{nQzOPTfi=LmUR+FpinU38j^JNAm)$rj_f!Ry}f z@~;20l7IAcuQk0>0xp;QJtyn$IV5tW1bm|2+(G6 z4dvynkzJDEfMiIv=vh-x-CfHp16EmCD;FsDFP4E<%fMG<02KwkA#j563Q$#HlXooW z-qUIDHB!4~>MNG9oGI#Ii%z!d6R0!80~b@&J@Hng$?$2xmWMwtlBXnl+-(?cbvR!E z-mU;QD!`5rz!*_Zzj4)Ox9N^;>2_&7>b^z#MLqOf?)MJFXM+?U38 Date: Mon, 25 Nov 2024 23:00:48 -0500 Subject: [PATCH 26/56] chore: auto-stake-it provides its own chain, connection, asset info --- multichain-testing/test/auto-stake-it.test.ts | 7 ++----- .../src/examples/auto-stake-it.contract.js | 15 +++++++++++++-- 2 files changed, 15 insertions(+), 7 deletions(-) diff --git a/multichain-testing/test/auto-stake-it.test.ts b/multichain-testing/test/auto-stake-it.test.ts index f7b3ff9ba7c..27861de5af7 100644 --- a/multichain-testing/test/auto-stake-it.test.ts +++ b/multichain-testing/test/auto-stake-it.test.ts @@ -1,7 +1,6 @@ -import type { CosmosChainInfo } from '@agoric/orchestration'; import anyTest from '@endo/ses-ava/prepare-endo.js'; import type { ExecutionContext, TestFn } from 'ava'; -import chainInfo from '../starship-chain-info.js'; +import starshipChainInfo from '../starship-chain-info.js'; import { makeDoOffer } from '../tools/e2e-tools.js'; import { createFundedWalletAndClient, @@ -96,9 +95,7 @@ const autoStakeItScenario = test.macro({ const fundAndTransfer = makeFundAndTransfer(t); // 2. Find 'stakingDenom' denom on agoric - const remoteChainInfo = (chainInfo as Record)[ - chainName - ]; + const remoteChainInfo = starshipChainInfo[chainName]; const stakingDenom = remoteChainInfo?.stakingTokens?.[0].denom; if (!stakingDenom) throw Error(`staking denom found for ${chainName}`); diff --git a/packages/orchestration/src/examples/auto-stake-it.contract.js b/packages/orchestration/src/examples/auto-stake-it.contract.js index d08781e47ff..4db3c55adcb 100644 --- a/packages/orchestration/src/examples/auto-stake-it.contract.js +++ b/packages/orchestration/src/examples/auto-stake-it.contract.js @@ -8,10 +8,12 @@ import { preparePortfolioHolder } from '../exos/portfolio-holder-kit.js'; import { withOrchestration } from '../utils/start-helper.js'; import { prepareStakingTap } from './auto-stake-it-tap-kit.js'; import * as flows from './auto-stake-it.flows.js'; +import { registerChainsAndAssets } from '../utils/chain-hub-helper.js'; /** * @import {Zone} from '@agoric/zone'; * @import {OrchestrationPowers, OrchestrationTools} from '../utils/start-helper.js'; + * @import {CosmosChainInfo, Denom, DenomDetail} from '../types.js'; */ /** @@ -23,13 +25,15 @@ import * as flows from './auto-stake-it.flows.js'; * @param {ZCF} zcf * @param {OrchestrationPowers & { * marshaller: Marshaller; - * }} _privateArgs + * chainInfo?: Record; + * assetInfo?: [Denom, DenomDetail & { brandKey?: string }][]; + * }} privateArgs * @param {Zone} zone * @param {OrchestrationTools} tools */ const contract = async ( zcf, - _privateArgs, + privateArgs, zone, { chainHub, orchestrateAll, vowTools }, ) => { @@ -67,6 +71,13 @@ const contract = async ( const creatorFacet = prepareChainHubAdmin(zone, chainHub); + registerChainsAndAssets( + chainHub, + zcf.getTerms().brands, + privateArgs.chainInfo, + privateArgs.assetInfo, + ); + return { publicFacet, creatorFacet }; }; From cf514845c27b44c86ff14d9fcfef588b15b7652e Mon Sep 17 00:00:00 2001 From: 0xPatrick Date: Fri, 29 Nov 2024 17:04:40 -0500 Subject: [PATCH 27/56] chore: swap.contract.js allows `chainInfo` and `assetInfo` - chainInfo and assetInfo are provided as `commonPrivateArgs`. include them in `ContractMeta` --- packages/orchestration/src/examples/swap.contract.js | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/packages/orchestration/src/examples/swap.contract.js b/packages/orchestration/src/examples/swap.contract.js index e726d371cf1..400eae50b92 100644 --- a/packages/orchestration/src/examples/swap.contract.js +++ b/packages/orchestration/src/examples/swap.contract.js @@ -3,6 +3,7 @@ import { TimerServiceShape } from '@agoric/time'; import { M } from '@endo/patterns'; import { withOrchestration } from '../utils/start-helper.js'; import * as flows from './swap.flows.js'; +import { CosmosChainInfoShape, DenomDetailShape } from '../typeGuards.js'; /** * @import {TimerService} from '@agoric/time'; @@ -12,6 +13,7 @@ import * as flows from './swap.flows.js'; * @import {NameHub} from '@agoric/vats'; * @import {Zone} from '@agoric/zone'; * @import {OrchestrationTools} from '../utils/start-helper.js'; + * @import {CosmosChainInfo, Denom, DenomDetail} from '@agoric/orchestration'; */ /** @type {ContractMeta} */ @@ -23,6 +25,8 @@ export const meta = { storageNode: StorageNodeShape, marshaller: M.remotable('marshaller'), timerService: M.or(TimerServiceShape, null), + chainInfo: M.recordOf(M.string(), CosmosChainInfoShape), + assetInfo: M.arrayOf([M.string(), DenomDetailShape]), }, upgradability: 'canUpgrade', }; @@ -49,6 +53,8 @@ harden(makeNatAmountShape); * storageNode: Remote; * timerService: Remote; * marshaller: Marshaller; + * chainInfo: Record; + * assetInfo: [Denom, DenomDetail & { brandKey?: string }][]; * }} privateArgs * @param {Zone} zone * @param {OrchestrationTools} tools From 68c568a7f10ef1f2409485d99e3267d1d20c362b Mon Sep 17 00:00:00 2001 From: 0xPatrick Date: Fri, 29 Nov 2024 17:08:20 -0500 Subject: [PATCH 28/56] test(boot): restart send-anywhere includes asset info --- .../orchestration/restart-contracts.test.ts | 22 +++++++++++++++++-- 1 file changed, 20 insertions(+), 2 deletions(-) diff --git a/packages/boot/test/orchestration/restart-contracts.test.ts b/packages/boot/test/orchestration/restart-contracts.test.ts index 790f58e5d44..8cae71baa2e 100644 --- a/packages/boot/test/orchestration/restart-contracts.test.ts +++ b/packages/boot/test/orchestration/restart-contracts.test.ts @@ -3,9 +3,13 @@ import { test as anyTest } from '@agoric/zoe/tools/prepare-test-env-ava.js'; import type { TestFn } from 'ava'; import { BridgeId } from '@agoric/internal'; -import type { CosmosValidatorAddress } from '@agoric/orchestration'; +import { + withChainCapabilities, + type CosmosValidatorAddress, +} from '@agoric/orchestration'; import { buildVTransferEvent } from '@agoric/orchestration/tools/ibc-mocks.js'; import type { UpdateRecord } from '@agoric/smart-wallet/src/smartWallet.js'; +import fetchedChainInfo from '@agoric/orchestration/src/fetched-chain-info.js'; import { makeWalletFactoryContext, type WalletFactoryTestContext, @@ -32,7 +36,21 @@ test.serial('send-anywhere', async t => { t.log('start send-anywhere'); await evalProposal( - buildProposal('@agoric/builders/scripts/testing/init-send-anywhere.js'), + buildProposal('@agoric/builders/scripts/testing/init-send-anywhere.js', [ + '--chainInfo', + JSON.stringify(withChainCapabilities(fetchedChainInfo)), + '--assetInfo', + JSON.stringify([ + [ + 'uist', + { + baseDenom: 'uist', + baseName: 'agoric', + chainName: 'agoric', + }, + ], + ]), + ]), ); t.log('making offer'); From 56164bd85f66b828ec436da25217ed4b520f64e6 Mon Sep 17 00:00:00 2001 From: 0xPatrick Date: Tue, 26 Nov 2024 00:28:52 -0500 Subject: [PATCH 29/56] chore: auto-stake-it.contract.js inits `chainHub` - auto-stake-it initializes `chainHub` with data so existing tests that use `.transfer()` pass --- multichain-testing/test/auto-stake-it.test.ts | 14 ++-- .../test/bootstrapTests/orchestration.test.ts | 2 +- .../scripts/testing/init-auto-stake-it.js | 73 +++++++++++++++++ .../src/proposals}/start-auto-stake-it.js | 82 +++++++------------ 4 files changed, 114 insertions(+), 57 deletions(-) create mode 100644 packages/builders/scripts/testing/init-auto-stake-it.js rename packages/{builders/scripts/testing => orchestration/src/proposals}/start-auto-stake-it.js (55%) diff --git a/multichain-testing/test/auto-stake-it.test.ts b/multichain-testing/test/auto-stake-it.test.ts index 27861de5af7..1c185c588b7 100644 --- a/multichain-testing/test/auto-stake-it.test.ts +++ b/multichain-testing/test/auto-stake-it.test.ts @@ -17,15 +17,19 @@ const accounts = ['agoricAdmin', 'cosmoshub', 'osmosis']; const contractName = 'autoAutoStakeIt'; const contractBuilder = - '../packages/builders/scripts/testing/start-auto-stake-it.js'; + '../packages/builders/scripts/testing/init-auto-stake-it.js'; test.before(async t => { - const { deleteTestKeys, setupTestKeys, ...rest } = await commonSetup(t); + const { setupTestKeys, ...common } = await commonSetup(t); + const { assetInfo, chainInfo, deleteTestKeys, startContract } = common; deleteTestKeys(accounts).catch(); const wallets = await setupTestKeys(accounts); - t.context = { ...rest, wallets, deleteTestKeys }; - const { startContract } = rest; - await startContract(contractName, contractBuilder); + t.context = { ...common, wallets }; + + await startContract(contractName, contractBuilder, { + chainInfo: JSON.stringify(chainInfo), + assetInfo: JSON.stringify(assetInfo), + }); }); test.after(async t => { diff --git a/packages/boot/test/bootstrapTests/orchestration.test.ts b/packages/boot/test/bootstrapTests/orchestration.test.ts index fa976fd7dac..45303ecafbb 100644 --- a/packages/boot/test/bootstrapTests/orchestration.test.ts +++ b/packages/boot/test/bootstrapTests/orchestration.test.ts @@ -484,7 +484,7 @@ test.serial('auto-stake-it - proposal', async t => { await t.notThrowsAsync( evalProposal( - buildProposal('@agoric/builders/scripts/testing/start-auto-stake-it.js'), + buildProposal('@agoric/builders/scripts/testing/init-auto-stake-it.js'), ), ); }); diff --git a/packages/builders/scripts/testing/init-auto-stake-it.js b/packages/builders/scripts/testing/init-auto-stake-it.js new file mode 100644 index 00000000000..8c5a515b8ee --- /dev/null +++ b/packages/builders/scripts/testing/init-auto-stake-it.js @@ -0,0 +1,73 @@ +/** + * @file A proposal to start the auto-stake-it contract. + * + * AutoStakeIt allows users to to create an auto-forwarding address that + * transfers and stakes tokens on a remote chain when received. + */ +import { makeHelpers } from '@agoric/deploy-script-support'; +import { startAutoStakeIt } from '@agoric/orchestration/src/proposals/start-auto-stake-it.js'; +import { parseArgs } from 'node:util'; + +/** + * @import {ParseArgsConfig} from 'node:util' + */ + +/** @type {ParseArgsConfig['options']} */ +const parserOpts = { + chainInfo: { type: 'string' }, + assetInfo: { type: 'string' }, +}; + +/** @type {import('@agoric/deploy-script-support/src/externalTypes.js').CoreEvalBuilder} */ +export const defaultProposalBuilder = async ( + { publishRef, install }, + options, +) => { + return harden({ + sourceSpec: '@agoric/orchestration/src/proposals/start-auto-stake-it.js', + getManifestCall: [ + 'getManifest', + { + installKeys: { + autoAutoStakeIt: publishRef( + install( + '@agoric/orchestration/src/examples/auto-stake-it.contract.js', + ), + ), + }, + options, + }, + ], + }); +}; + +/** @type {import('@agoric/deploy-script-support/src/externalTypes.js').DeployScriptFunction} */ +export default async (homeP, endowments) => { + const { scriptArgs } = endowments; + + const { + values: { chainInfo, assetInfo }, + } = parseArgs({ + args: scriptArgs, + options: parserOpts, + }); + + const parseChainInfo = () => { + if (typeof chainInfo !== 'string') return undefined; + return JSON.parse(chainInfo); + }; + const parseAssetInfo = () => { + if (typeof assetInfo !== 'string') return undefined; + return JSON.parse(assetInfo); + }; + const opts = harden({ + chainInfo: parseChainInfo(), + assetInfo: parseAssetInfo(), + }); + + const { writeCoreEval } = await makeHelpers(homeP, endowments); + + await writeCoreEval(startAutoStakeIt.name, utils => + defaultProposalBuilder(utils, opts), + ); +}; diff --git a/packages/builders/scripts/testing/start-auto-stake-it.js b/packages/orchestration/src/proposals/start-auto-stake-it.js similarity index 55% rename from packages/builders/scripts/testing/start-auto-stake-it.js rename to packages/orchestration/src/proposals/start-auto-stake-it.js index 8a02140c012..69cfc7721e5 100644 --- a/packages/builders/scripts/testing/start-auto-stake-it.js +++ b/packages/orchestration/src/proposals/start-auto-stake-it.js @@ -11,6 +11,7 @@ import { deeplyFulfilled } from '@endo/marshal'; /** * @import {AutoStakeItSF} from '@agoric/orchestration/src/examples/auto-stake-it.contract.js'; + * @import {CosmosChainInfo, Denom, DenomDetail} from '@agoric/orchestration'; */ const contractName = 'autoAutoStakeIt'; @@ -18,26 +19,35 @@ const trace = makeTracer(contractName, true); /** * @param {BootstrapPowers} powers + * @param {{ + * options: { + * chainInfo: Record; + * assetInfo: [Denom, DenomDetail & { brandKey?: string }][]; + * }; + * }} config */ -export const startAutoStakeIt = async ({ - consume: { - agoricNames, - board, - chainStorage, - chainTimerService, - cosmosInterchainService, - localchain, - startUpgradable, - }, - installation: { - // @ts-expect-error not a WellKnownName - consume: { [contractName]: installation }, - }, - instance: { - // @ts-expect-error not a WellKnownName - produce: { [contractName]: produceInstance }, +export const startAutoStakeIt = async ( + { + consume: { + agoricNames, + board, + chainStorage, + chainTimerService, + cosmosInterchainService, + localchain, + startUpgradable, + }, + installation: { + // @ts-expect-error not a WellKnownName + consume: { [contractName]: installation }, + }, + instance: { + // @ts-expect-error not a WellKnownName + produce: { [contractName]: produceInstance }, + }, }, -}) => { + { options: { chainInfo, assetInfo } }, +) => { trace(`start ${contractName}`); await null; @@ -58,6 +68,8 @@ export const startAutoStakeIt = async ({ storageNode, marshaller, timerService: chainTimerService, + chainInfo, + assetInfo, }), ), }; @@ -67,10 +79,7 @@ export const startAutoStakeIt = async ({ }; harden(startAutoStakeIt); -export const getManifestForContract = ( - { restoreRef }, - { installKeys, ...options }, -) => { +export const getManifest = ({ restoreRef }, { installKeys, options }) => { return { manifest: { [startAutoStakeIt.name]: { @@ -97,32 +106,3 @@ export const getManifestForContract = ( options, }; }; - -/** @type {import('@agoric/deploy-script-support/src/externalTypes.js').CoreEvalBuilder} */ -export const defaultProposalBuilder = async ({ publishRef, install }) => { - return harden({ - // Somewhat unorthodox, source the exports from this builder module - sourceSpec: '@agoric/builders/scripts/testing/start-auto-stake-it.js', - getManifestCall: [ - 'getManifestForContract', - { - installKeys: { - autoAutoStakeIt: publishRef( - install( - '@agoric/orchestration/src/examples/auto-stake-it.contract.js', - ), - ), - }, - }, - ], - }); -}; - -/** @type {import('@agoric/deploy-script-support/src/externalTypes.js').DeployScriptFunction} */ -export default async (homeP, endowments) => { - // import dynamically so the module can work in CoreEval environment - const dspModule = await import('@agoric/deploy-script-support'); - const { makeHelpers } = dspModule; - const { writeCoreEval } = await makeHelpers(homeP, endowments); - await writeCoreEval(startAutoStakeIt.name, defaultProposalBuilder); -}; From 2195ace1fe125e2c0b9b05c32e1cf147a2604d60 Mon Sep 17 00:00:00 2001 From: 0xPatrick Date: Tue, 26 Nov 2024 00:44:58 -0500 Subject: [PATCH 30/56] chore(fusdc): remove write-chain-info.js - no longer needed since we call `registerChainsAndAssets` --- a3p-integration/proposals/f:fast-usdc/package.json | 2 -- 1 file changed, 2 deletions(-) diff --git a/a3p-integration/proposals/f:fast-usdc/package.json b/a3p-integration/proposals/f:fast-usdc/package.json index 6d5c1a0fc64..f8ce07cad71 100644 --- a/a3p-integration/proposals/f:fast-usdc/package.json +++ b/a3p-integration/proposals/f:fast-usdc/package.json @@ -1,9 +1,7 @@ { "agoricProposal": { "source": "subdir", - "$UNTIL": "write-chain-info to agoricNames until #10445 and chainHub setup", "sdk-generate": [ - "orchestration/write-chain-info.js", "fast-usdc/init-fast-usdc.js submission --net A3P_INTEGRATION" ], "type": "/agoric.swingset.CoreEvalProposal" From f5b8b226396e42cf8a0fe35656db48405b6ef6eb Mon Sep 17 00:00:00 2001 From: Ikenna Omekam Date: Thu, 14 Nov 2024 10:06:52 -0500 Subject: [PATCH 31/56] test: send-anywhere contract null upgrade - no longer relies on buggy agoricNames - continues to test async-flow resumability and cross-chain vow settlement across upgrade Co-authored-by: 0xPatrick --- .../orchestration/contract-upgrade.test.ts | 52 ++++--- .../testing/start-buggy-sendAnywhere.js | 143 ------------------ ...ndAnywhere.js => upgrade-send-anywhere.js} | 32 ++-- 3 files changed, 44 insertions(+), 183 deletions(-) delete mode 100644 packages/builders/scripts/testing/start-buggy-sendAnywhere.js rename packages/builders/scripts/testing/{fix-buggy-sendAnywhere.js => upgrade-send-anywhere.js} (81%) diff --git a/packages/boot/test/orchestration/contract-upgrade.test.ts b/packages/boot/test/orchestration/contract-upgrade.test.ts index ada1a4a4144..65293a800b7 100644 --- a/packages/boot/test/orchestration/contract-upgrade.test.ts +++ b/packages/boot/test/orchestration/contract-upgrade.test.ts @@ -4,6 +4,8 @@ import type { TestFn } from 'ava'; import { BridgeId } from '@agoric/internal'; import { buildVTransferEvent } from '@agoric/orchestration/tools/ibc-mocks.js'; +import fetchedChainInfo from '@agoric/orchestration/src/fetched-chain-info.js'; +import { withChainCapabilities } from '@agoric/orchestration'; import { makeWalletFactoryContext, type WalletFactoryTestContext, @@ -19,17 +21,13 @@ test.before(async t => { test.after.always(t => t.context.shutdown?.()); /** - * This test core-evals a buggy installation of the sendAnywhere contract by - * giving it a faulty `agoricNames` service with a lookup() function which - * returns a promise that never resolves. + * This test core-evals an installation of the sendAnywhere contract that + * initiates an IBC Transfer. Since that goes over a bridge and is tracked + * by a vow, we can restart the contract and see that the vow settles. We + * can manually trigger a bridge event in the testing context. * - * Because the send-anywhere flow requires a lookup(), it waits forever. This - * gives us a point at which we can upgrade the vat with a working agoricNames - * and see that the flow continues from that point. (The lookup call is not made - * directly in a flow, but instead from a host API which uses the retryable - * helper. As such it tests both the idempotent retry mechanism of retryable on - * upgrades, and the ability to resume an async-flow for which a host vow - * settles after an upgrade.) + * As such, this demonstrates the ability to resume an async-flow for for which + * a host vow settles after an upgrade. */ test('resume', async t => { const { @@ -44,9 +42,21 @@ test('resume', async t => { t.log('start sendAnywhere'); await evalProposal( - buildProposal( - '@agoric/builders/scripts/testing/start-buggy-sendAnywhere.js', - ), + buildProposal('@agoric/builders/scripts/testing/init-send-anywhere.js', [ + '--chainInfo', + JSON.stringify(withChainCapabilities(fetchedChainInfo)), + '--assetInfo', + JSON.stringify([ + [ + 'uist', + { + baseDenom: 'uist', + baseName: 'agoric', + chainName: 'agoric', + }, + ], + ]), + ]), ); t.log('making offer'); @@ -70,16 +80,9 @@ test('resume', async t => { // XXX golden test const getLogged = () => - JSON.parse(storage.data.get('published.sendAnywhere.log')!).values; - - // This log shows the flow started, but didn't get past the name lookup - t.deepEqual(getLogged(), ['sending {0} from cosmoshub to cosmos1whatever']); - - t.log('upgrade sendAnywhere with fix'); - await evalProposal( - buildProposal('@agoric/builders/scripts/testing/fix-buggy-sendAnywhere.js'), - ); + JSON.parse(storage.data.get('published.send-anywhere.log')!).values; + // This log shows the flow started, but didn't get past the IBC Transfer settlement t.deepEqual(getLogged(), [ 'sending {0} from cosmoshub to cosmos1whatever', 'got info for denoms: ibc/FE98AAD68F02F03565E9FA39A5E627946699B2B07115889ED812D8BA639576A9, ibc/toyatom, ibc/toyusdc, ubld, uist', @@ -87,6 +90,11 @@ test('resume', async t => { 'completed transfer to localAccount', ]); + t.log('null upgrading sendAnywhere'); + await evalProposal( + buildProposal('@agoric/builders/scripts/testing/upgrade-send-anywhere.js'), + ); + // simulate ibc/MsgTransfer ack from remote chain, enabling `.transfer()` promise // to resolve await runInbound( diff --git a/packages/builders/scripts/testing/start-buggy-sendAnywhere.js b/packages/builders/scripts/testing/start-buggy-sendAnywhere.js deleted file mode 100644 index 6f5ac66ee1d..00000000000 --- a/packages/builders/scripts/testing/start-buggy-sendAnywhere.js +++ /dev/null @@ -1,143 +0,0 @@ -/** - * @file This is for use in tests in a3p-integration - * Unlike most builder scripts, this one includes the proposal exports as well. - */ -import { - deeplyFulfilledObject, - makeTracer, - NonNullish, -} from '@agoric/internal'; -import { E, Far } from '@endo/far'; - -/// -/** - * @import {Installation} from '@agoric/zoe/src/zoeService/utils.js'; - */ - -const trace = makeTracer('StartBuggySA', true); - -/** - * @import {start as StartFn} from '@agoric/orchestration/src/examples/send-anywhere.contract.js'; - */ - -/** - * @param {BootstrapPowers & { - * installation: { - * consume: { - * sendAnywhere: Installation; - * }; - * }; - * }} powers - */ -export const startSendAnywhere = async ({ - consume: { - agoricNames, - board, - chainStorage, - chainTimerService, - cosmosInterchainService, - localchain, - startUpgradable, - }, - installation: { - consume: { sendAnywhere }, - }, - instance: { - // @ts-expect-error unknown instance - produce: { sendAnywhere: produceInstance }, - }, -}) => { - trace(startSendAnywhere.name); - - const marshaller = await E(board).getReadonlyMarshaller(); - - const privateArgs = await deeplyFulfilledObject( - harden({ - agoricNames, - localchain, - marshaller, - orchestrationService: cosmosInterchainService, - storageNode: E(NonNullish(await chainStorage)).makeChildNode( - 'sendAnywhere', - ), - timerService: chainTimerService, - }), - ); - - /** @type {import('@agoric/vats').NameHub} */ - // @ts-expect-error intentional fake - const agoricNamesHangs = Far('agoricNames that hangs', { - lookup: async () => { - trace('agoricNames.lookup being called that will never resolve'); - // BUG: this never resolves - return new Promise(() => {}); - }, - }); - - const { instance } = await E(startUpgradable)({ - label: 'sendAnywhere', - installation: sendAnywhere, - privateArgs: { - ...privateArgs, - agoricNames: agoricNamesHangs, - }, - }); - produceInstance.resolve(instance); - trace('done'); -}; -harden(startSendAnywhere); - -export const getManifestForValueVow = ({ restoreRef }, { sendAnywhereRef }) => { - trace('sendAnywhereRef', sendAnywhereRef); - return { - manifest: { - [startSendAnywhere.name]: { - consume: { - agoricNames: true, - board: true, - chainStorage: true, - chainTimerService: true, - cosmosInterchainService: true, - localchain: true, - - startUpgradable: true, - }, - installation: { - consume: { sendAnywhere: true }, - }, - instance: { - produce: { sendAnywhere: true }, - }, - }, - }, - installations: { - sendAnywhere: restoreRef(sendAnywhereRef), - }, - }; -}; - -/** @type {import('@agoric/deploy-script-support/src/externalTypes.js').CoreEvalBuilder} */ -export const defaultProposalBuilder = async ({ publishRef, install }) => - harden({ - // Somewhat unorthodox, source the exports from this builder module - sourceSpec: '@agoric/builders/scripts/testing/start-buggy-sendAnywhere.js', - getManifestCall: [ - 'getManifestForValueVow', - { - sendAnywhereRef: publishRef( - install( - '@agoric/orchestration/src/examples/send-anywhere.contract.js', - ), - ), - }, - ], - }); - -/** @type {import('@agoric/deploy-script-support/src/externalTypes.js').DeployScriptFunction} */ -export default async (homeP, endowments) => { - // import dynamically so the module can work in CoreEval environment - const dspModule = await import('@agoric/deploy-script-support'); - const { makeHelpers } = dspModule; - const { writeCoreEval } = await makeHelpers(homeP, endowments); - await writeCoreEval(startSendAnywhere.name, defaultProposalBuilder); -}; diff --git a/packages/builders/scripts/testing/fix-buggy-sendAnywhere.js b/packages/builders/scripts/testing/upgrade-send-anywhere.js similarity index 81% rename from packages/builders/scripts/testing/fix-buggy-sendAnywhere.js rename to packages/builders/scripts/testing/upgrade-send-anywhere.js index 8daa2dbf516..4acfaf5f8ad 100644 --- a/packages/builders/scripts/testing/fix-buggy-sendAnywhere.js +++ b/packages/builders/scripts/testing/upgrade-send-anywhere.js @@ -7,14 +7,14 @@ import { makeTracer, NonNullish, } from '@agoric/internal'; -import { E, Far } from '@endo/far'; +import { E } from '@endo/far'; /// /** * @import {Installation, Instance} from '@agoric/zoe/src/zoeService/utils.js'; */ -const trace = makeTracer('FixBuggySA', true); +const trace = makeTracer('UpgradeSA', true); /** * @import {start as StartFn} from '@agoric/orchestration/src/examples/send-anywhere.contract.js'; @@ -30,7 +30,7 @@ const trace = makeTracer('FixBuggySA', true); * }} powers * @param {...any} rest */ -export const fixSendAnywhere = async ( +export const upgradeSendAnywhere = async ( { consume: { agoricNames, @@ -45,7 +45,7 @@ export const fixSendAnywhere = async ( }, { options: { sendAnywhereRef } }, ) => { - trace(fixSendAnywhere.name); + trace(upgradeSendAnywhere.name); const saInstance = await instances.consume.sendAnywhere; trace('saInstance', saInstance); @@ -53,28 +53,24 @@ export const fixSendAnywhere = async ( const marshaller = await E(board).getReadonlyMarshaller(); - // This apparently pointless wrapper is to maintain structural parity - // with the buggy core-eval's wrapper to make lookup() hang. - const agoricNamesResolves = Far('agoricNames that resolves', { - lookup: async (...args) => { - return E(agoricNames).lookup(...args); - }, - }); - const privateArgs = await deeplyFulfilledObject( harden({ - agoricNames: agoricNamesResolves, + agoricNames, localchain, marshaller, orchestrationService: cosmosInterchainService, storageNode: E(NonNullish(await chainStorage)).makeChildNode( - 'sendAnywhere', + 'send-anywhere', ), timerService: chainTimerService, + // undefined so `registerKnownChainsAndAssets` does not run again + chainInfo: undefined, + assetInfo: undefined, }), ); trace('upgrading...'); + trace('ref', sendAnywhereRef); await E(saKit.adminFacet).upgradeContract( sendAnywhereRef.bundleID, privateArgs, @@ -82,13 +78,13 @@ export const fixSendAnywhere = async ( trace('done'); }; -harden(fixSendAnywhere); +harden(upgradeSendAnywhere); export const getManifestForValueVow = ({ restoreRef }, { sendAnywhereRef }) => { console.log('sendAnywhereRef', sendAnywhereRef); return { manifest: { - [fixSendAnywhere.name]: { + [upgradeSendAnywhere.name]: { consume: { agoricNames: true, board: true, @@ -120,7 +116,7 @@ export const getManifestForValueVow = ({ restoreRef }, { sendAnywhereRef }) => { export const defaultProposalBuilder = async ({ publishRef, install }) => harden({ // Somewhat unorthodox, source the exports from this builder module - sourceSpec: '@agoric/builders/scripts/testing/fix-buggy-sendAnywhere.js', + sourceSpec: '@agoric/builders/scripts/testing/upgrade-send-anywhere.js', getManifestCall: [ 'getManifestForValueVow', { @@ -139,5 +135,5 @@ export default async (homeP, endowments) => { const dspModule = await import('@agoric/deploy-script-support'); const { makeHelpers } = dspModule; const { writeCoreEval } = await makeHelpers(homeP, endowments); - await writeCoreEval(fixSendAnywhere.name, defaultProposalBuilder); + await writeCoreEval(upgradeSendAnywhere.name, defaultProposalBuilder); }; From a93b6241d2eddbbe2f5842f747b8515b0c87951b Mon Sep 17 00:00:00 2001 From: 0xPatrick Date: Tue, 26 Nov 2024 17:16:00 -0500 Subject: [PATCH 32/56] test(send-anywhere): explicitly check result key is undefined --- packages/boot/test/orchestration/restart-contracts.test.ts | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/packages/boot/test/orchestration/restart-contracts.test.ts b/packages/boot/test/orchestration/restart-contracts.test.ts index 8cae71baa2e..b727b8a74be 100644 --- a/packages/boot/test/orchestration/restart-contracts.test.ts +++ b/packages/boot/test/orchestration/restart-contracts.test.ts @@ -113,9 +113,12 @@ test.serial('send-anywhere', async t => { id: 'send-somewhere', numWantsSatisfied: 1, error: undefined, - result: undefined, }, }); + if (conclusion.updated !== 'offerStatus') { + throw new Error('expected offerStatus'); + } + t.true('result' in conclusion.status, 'transfer vow settled'); }); const validatorAddress: CosmosValidatorAddress = { From cb22e57a9d2fb67800dd157c5773a62f1184efeb Mon Sep 17 00:00:00 2001 From: 0xPatrick Date: Fri, 29 Nov 2024 17:13:32 -0500 Subject: [PATCH 33/56] refactor: explicit test ordering - test/bootstrapTests/orchestration.test.ts used a mixed of test and test.serial - the test without `.serial` interleaved and was confusing to debug - this mainly updates inline snapshots, which return different account and channel identifiers since all tests in this file share the same context --- .../test/bootstrapTests/orchestration.test.ts | 15 +++++++-------- 1 file changed, 7 insertions(+), 8 deletions(-) diff --git a/packages/boot/test/bootstrapTests/orchestration.test.ts b/packages/boot/test/bootstrapTests/orchestration.test.ts index 45303ecafbb..8802b622bfd 100644 --- a/packages/boot/test/bootstrapTests/orchestration.test.ts +++ b/packages/boot/test/bootstrapTests/orchestration.test.ts @@ -310,7 +310,7 @@ test.serial('revise chain info', async t => { }); }); -test('basic-flows', async t => { +test.serial('basic-flows', async t => { const { buildProposal, evalProposal, @@ -355,9 +355,9 @@ test('basic-flows', async t => { }); t.deepEqual(readPublished('basicFlows.cosmos1test'), { localAddress: - '/ibc-port/icacontroller-4/ordered/{"version":"ics27-1","controllerConnectionId":"connection-8","hostConnectionId":"connection-649","address":"cosmos1test","encoding":"proto3","txType":"sdk_multi_msg"}/ibc-channel/channel-4', + '/ibc-port/icacontroller-2/ordered/{"version":"ics27-1","controllerConnectionId":"connection-8","hostConnectionId":"connection-649","address":"cosmos1test","encoding":"proto3","txType":"sdk_multi_msg"}/ibc-channel/channel-2', remoteAddress: - '/ibc-hop/connection-8/ibc-port/icahost/ordered/{"version":"ics27-1","controllerConnectionId":"connection-8","hostConnectionId":"connection-649","address":"cosmos1test","encoding":"proto3","txType":"sdk_multi_msg"}/ibc-channel/channel-4', + '/ibc-hop/connection-8/ibc-port/icahost/ordered/{"version":"ics27-1","controllerConnectionId":"connection-8","hostConnectionId":"connection-649","address":"cosmos1test","encoding":"proto3","txType":"sdk_multi_msg"}/ibc-channel/channel-2', }); // create a local orchestration account @@ -378,12 +378,11 @@ test('basic-flows', async t => { wd.getCurrentWalletRecord().offerToPublicSubscriberPaths, ); t.deepEqual(publicSubscriberPaths['request-loa'], { - account: 'published.basicFlows.agoric1fakeLCAAddress1', + account: 'published.basicFlows.agoric1fakeLCAAddress', }); t.like(wd.getLatestUpdateRecord(), { status: { id: 'request-loa', numWantsSatisfied: 1 }, }); - t.is(readPublished('basicFlows.agoric1fakeLCAAddress'), ''); await wd.sendOffer({ id: 'transfer-to-noble-from-cosmos', @@ -531,7 +530,7 @@ test.serial('basic-flows - portfolio holder', async t => { [ 'request-portfolio-acct', { - agoric: 'published.basicFlows.agoric1fakeLCAAddress', + agoric: 'published.basicFlows.agoric1fakeLCAAddress1', cosmoshub: 'published.basicFlows.cosmos1test', // XXX support multiple chain addresses in ibc mocks osmosis: 'published.basicFlows.cosmos1test', @@ -545,9 +544,9 @@ test.serial('basic-flows - portfolio holder', async t => { // XXX this overrides a previous account, since mocks only provide one address t.deepEqual(readPublished('basicFlows.cosmos1test'), { localAddress: - '/ibc-port/icacontroller-3/ordered/{"version":"ics27-1","controllerConnectionId":"connection-1","hostConnectionId":"connection-1649","address":"cosmos1test","encoding":"proto3","txType":"sdk_multi_msg"}/ibc-channel/channel-3', + '/ibc-port/icacontroller-4/ordered/{"version":"ics27-1","controllerConnectionId":"connection-1","hostConnectionId":"connection-1649","address":"cosmos1test","encoding":"proto3","txType":"sdk_multi_msg"}/ibc-channel/channel-4', remoteAddress: - '/ibc-hop/connection-1/ibc-port/icahost/ordered/{"version":"ics27-1","controllerConnectionId":"connection-1","hostConnectionId":"connection-1649","address":"cosmos1test","encoding":"proto3","txType":"sdk_multi_msg"}/ibc-channel/channel-3', + '/ibc-hop/connection-1/ibc-port/icahost/ordered/{"version":"ics27-1","controllerConnectionId":"connection-1","hostConnectionId":"connection-1649","address":"cosmos1test","encoding":"proto3","txType":"sdk_multi_msg"}/ibc-channel/channel-4', }); // XXX this overrides a previous account, since mocks only provide one address t.is(readPublished('basicFlows.agoric1fakeLCAAddress'), ''); From df1af7a2bb15e7f88ea0db1cd66de33cc21be6ab Mon Sep 17 00:00:00 2001 From: 0xPatrick Date: Fri, 29 Nov 2024 17:16:32 -0500 Subject: [PATCH 34/56] chore: basic-flows.contract.js seeds `chainHub` - basic-flows.contract.js is provided with `chainInfo` and `assetInfo` in `privateArgs` via builder options - needed for tests that use `localAccount.transfer()`, now reliant on asset info, to pass --- .../test/bootstrapTests/orchestration.test.ts | 90 ++++++++++++++++--- .../scripts/orchestration/init-basic-flows.js | 44 ++++++++- .../src/examples/basic-flows.contract.js | 17 +++- .../src/proposals/start-basic-flows.js | 81 ++++++++++++----- 4 files changed, 195 insertions(+), 37 deletions(-) diff --git a/packages/boot/test/bootstrapTests/orchestration.test.ts b/packages/boot/test/bootstrapTests/orchestration.test.ts index 8802b622bfd..76c5d152c59 100644 --- a/packages/boot/test/bootstrapTests/orchestration.test.ts +++ b/packages/boot/test/bootstrapTests/orchestration.test.ts @@ -5,11 +5,17 @@ import { defaultMarshaller, documentStorageSchema, } from '@agoric/internal/src/storage-test-utils.js'; -import type { CosmosValidatorAddress } from '@agoric/orchestration'; +import { + withChainCapabilities, + type CosmosValidatorAddress, +} from '@agoric/orchestration'; import type { start as startStakeIca } from '@agoric/orchestration/src/examples/stake-ica.contract.js'; import type { Instance } from '@agoric/zoe/src/zoeService/utils.js'; import type { TestFn } from 'ava'; import { SIMULATED_ERRORS } from '@agoric/vats/tools/fake-bridge.js'; +import fetchedChainInfo from '@agoric/orchestration/src/fetched-chain-info.js'; +import { buildVTransferEvent } from '@agoric/orchestration/tools/ibc-mocks.js'; +import { BridgeId } from '@agoric/internal'; import { makeWalletFactoryContext, type WalletFactoryTestContext, @@ -316,11 +322,38 @@ test.serial('basic-flows', async t => { evalProposal, agoricNamesRemotes, readPublished, - bridgeUtils: { flushInboundQueue }, + bridgeUtils: { flushInboundQueue, runInbound }, } = t.context; await evalProposal( - buildProposal('@agoric/builders/scripts/orchestration/init-basic-flows.js'), + buildProposal( + '@agoric/builders/scripts/orchestration/init-basic-flows.js', + [ + '--chainInfo', + JSON.stringify(withChainCapabilities(fetchedChainInfo)), + '--assetInfo', + JSON.stringify([ + [ + 'ibc/uusdconagoric', + { + chainName: 'agoric', + baseName: 'noble', + baseDenom: 'uusdc', + }, + ], + // not tested until #10006. consider renaming to ibc/uusdconcosmos + // and updating boot/tools/ibc/mocks.ts + [ + 'ibc/uusdchash', + { + chainName: 'cosmoshub', + baseName: 'noble', + baseDenom: 'uusdc', + }, + ], + ]), + ], + ), ); const wd = @@ -442,7 +475,7 @@ test.serial('basic-flows', async t => { }, proposal: {}, offerArgs: { - amount: { denom: 'ibc/uusdchash', value: 10n }, + amount: { denom: 'ibc/uusdconagoric', value: 10n }, destination: { chainId: 'noble-1', value: 'noble1test', @@ -450,12 +483,29 @@ test.serial('basic-flows', async t => { }, }, }); - t.like(wd.getLatestUpdateRecord(), { - status: { - id: 'transfer-to-noble-from-agoric', - error: undefined, - }, + + await runInbound( + BridgeId.VTRANSFER, + buildVTransferEvent({ + sourceChannel: 'channel-62', + sequence: '1', + }), + ); + + const latestOfferStatus = () => { + const curr = wd.getLatestUpdateRecord(); + if (curr.updated === 'offerStatus') { + return curr.status; + } + throw new Error('expected updated to be "offerStatus"'); + }; + + const offerResult = latestOfferStatus(); + t.like(offerResult, { + id: 'transfer-to-noble-from-agoric', + error: undefined, }); + t.true('result' in offerResult, 'transfer vow settled'); await t.throwsAsync( wd.executeOffer({ @@ -467,7 +517,7 @@ test.serial('basic-flows', async t => { }, proposal: {}, offerArgs: { - amount: { denom: 'ibc/uusdchash', value: SIMULATED_ERRORS.TIMEOUT }, + amount: { denom: 'ibc/uusdconagoric', value: SIMULATED_ERRORS.TIMEOUT }, destination: { chainId: 'noble-1', value: 'noble1test', @@ -498,7 +548,25 @@ test.serial('basic-flows - portfolio holder', async t => { } = t.context; await evalProposal( - buildProposal('@agoric/builders/scripts/orchestration/init-basic-flows.js'), + buildProposal( + '@agoric/builders/scripts/orchestration/init-basic-flows.js', + [ + '--chainInfo', + JSON.stringify(withChainCapabilities(fetchedChainInfo)), + '--assetInfo', + JSON.stringify([ + [ + 'ubld', + { + baseDenom: 'ubld', + baseName: 'agoric', + chainName: 'agoric', + brandKey: 'BLD', + }, + ], + ]), + ], + ), ); const wd = diff --git a/packages/builders/scripts/orchestration/init-basic-flows.js b/packages/builders/scripts/orchestration/init-basic-flows.js index ab2de229cf3..430df76140a 100644 --- a/packages/builders/scripts/orchestration/init-basic-flows.js +++ b/packages/builders/scripts/orchestration/init-basic-flows.js @@ -1,8 +1,22 @@ import { makeHelpers } from '@agoric/deploy-script-support'; import { startBasicFlows } from '@agoric/orchestration/src/proposals/start-basic-flows.js'; +import { parseArgs } from 'node:util'; + +/** + * @import {ParseArgsConfig} from 'node:util' + */ + +/** @type {ParseArgsConfig['options']} */ +const parserOpts = { + chainInfo: { type: 'string' }, + assetInfo: { type: 'string' }, +}; /** @type {import('@agoric/deploy-script-support/src/externalTypes.js').CoreEvalBuilder} */ -export const defaultProposalBuilder = async ({ publishRef, install }) => { +export const defaultProposalBuilder = async ( + { publishRef, install }, + options, +) => { return harden({ sourceSpec: '@agoric/orchestration/src/proposals/start-basic-flows.js', getManifestCall: [ @@ -15,6 +29,7 @@ export const defaultProposalBuilder = async ({ publishRef, install }) => { ), ), }, + options, }, ], }); @@ -22,6 +37,31 @@ export const defaultProposalBuilder = async ({ publishRef, install }) => { /** @type {import('@agoric/deploy-script-support/src/externalTypes.js').DeployScriptFunction} */ export default async (homeP, endowments) => { + const { scriptArgs } = endowments; + + const { + values: { chainInfo, assetInfo }, + } = parseArgs({ + args: scriptArgs, + options: parserOpts, + }); + + const parseChainInfo = () => { + if (typeof chainInfo !== 'string') return undefined; + return JSON.parse(chainInfo); + }; + const parseAssetInfo = () => { + if (typeof assetInfo !== 'string') return undefined; + return JSON.parse(assetInfo); + }; + const opts = harden({ + chainInfo: parseChainInfo(), + assetInfo: parseAssetInfo(), + }); + const { writeCoreEval } = await makeHelpers(homeP, endowments); - await writeCoreEval(startBasicFlows.name, defaultProposalBuilder); + + await writeCoreEval(startBasicFlows.name, utils => + defaultProposalBuilder(utils, opts), + ); }; diff --git a/packages/orchestration/src/examples/basic-flows.contract.js b/packages/orchestration/src/examples/basic-flows.contract.js index 60f58cadd1f..ab8387d2ec8 100644 --- a/packages/orchestration/src/examples/basic-flows.contract.js +++ b/packages/orchestration/src/examples/basic-flows.contract.js @@ -6,10 +6,12 @@ import { InvitationShape } from '@agoric/zoe/src/typeGuards.js'; import { M } from '@endo/patterns'; import { preparePortfolioHolder } from '../exos/portfolio-holder-kit.js'; import { withOrchestration } from '../utils/start-helper.js'; +import { registerChainsAndAssets } from '../utils/chain-hub-helper.js'; import * as flows from './basic-flows.flows.js'; /** * @import {Zone} from '@agoric/zone'; + * @import {CosmosChainInfo, Denom, DenomDetail} from '@agoric/orchestration'; * @import {OrchestrationPowers, OrchestrationTools} from '../utils/start-helper.js'; */ @@ -17,15 +19,17 @@ import * as flows from './basic-flows.flows.js'; * @param {ZCF} zcf * @param {OrchestrationPowers & { * marshaller: Marshaller; - * }} _privateArgs + * chainInfo?: Record; + * assetInfo?: [Denom, DenomDetail & { brandKey?: string }][]; + * }} privateArgs * @param {Zone} zone * @param {OrchestrationTools} tools */ const contract = async ( zcf, - _privateArgs, + privateArgs, zone, - { orchestrateAll, vowTools }, + { chainHub, orchestrateAll, vowTools }, ) => { const makePortfolioHolder = preparePortfolioHolder( zone.subZone('portfolio'), @@ -56,6 +60,13 @@ const contract = async ( }, ); + registerChainsAndAssets( + chainHub, + zcf.getTerms().brands, + privateArgs.chainInfo, + privateArgs.assetInfo, + ); + return { publicFacet }; }; diff --git a/packages/orchestration/src/proposals/start-basic-flows.js b/packages/orchestration/src/proposals/start-basic-flows.js index e19b242ff90..59682e21e10 100644 --- a/packages/orchestration/src/proposals/start-basic-flows.js +++ b/packages/orchestration/src/proposals/start-basic-flows.js @@ -6,6 +6,7 @@ import { makeStorageNodeChild } from '@agoric/internal/src/lib-chainStorage.js'; import { E } from '@endo/far'; /** + * @import {CosmosChainInfo, Denom, DenomDetail} from '@agoric/orchestration'; * @import {BasicFlowsSF} from '../examples/basic-flows.contract.js'; */ @@ -15,30 +16,59 @@ const contractName = 'basicFlows'; /** * See `@agoric/builders/builders/scripts/orchestration/init-basic-flows.js` for * the accompanying proposal builder. Run `agoric run - * packages/builders/scripts/orchestration/init-basic-flows.js` to build the + * packages/builders/scripts/orchestration/init-basic-flows.js --chainInfo + * 'chainName:CosmosChainInfo' --assetInfo 'denom:DenomDetail'` to build the * contract and proposal files. * - * @param {BootstrapPowers} powers + * @param {BootstrapPowers & { + * installation: { + * consume: { + * basicFlows: Installation; + * }; + * }; + * instance: { + * produce: { + * basicFlows: Producer; + * }; + * }; + * issuer: { + * consume: { + * BLD: Issuer<'nat'>; + * IST: Issuer<'nat'>; + * USDC: Issuer<'nat'>; + * }; + * }; + * }} powers + * @param {{ + * options: { + * chainInfo: Record; + * assetInfo: [Denom, DenomDetail & { brandKey?: string }][]; + * }; + * }} config */ -export const startBasicFlows = async ({ - consume: { - agoricNames, - board, - chainStorage, - chainTimerService, - cosmosInterchainService, - localchain, - startUpgradable, - }, - installation: { - // @ts-expect-error not a WellKnownName - consume: { [contractName]: installation }, - }, - instance: { - // @ts-expect-error not a WellKnownName - produce: { [contractName]: produceInstance }, +export const startBasicFlows = async ( + { + consume: { + agoricNames, + board, + chainStorage, + chainTimerService, + cosmosInterchainService, + localchain, + startUpgradable, + }, + installation: { + consume: { [contractName]: installation }, + }, + instance: { + produce: { [contractName]: produceInstance }, + }, + issuer: { + consume: { BLD, IST }, + }, }, -}) => { + { options: { chainInfo, assetInfo } }, +) => { trace(`start ${contractName}`); await null; @@ -49,6 +79,10 @@ export const startBasicFlows = async ({ const startOpts = { label: 'basicFlows', installation, + issuerKeywordRecord: { + BLD: await BLD, + IST: await IST, + }, terms: undefined, privateArgs: { agoricNames: await agoricNames, @@ -57,6 +91,8 @@ export const startBasicFlows = async ({ storageNode, marshaller, timerService: await chainTimerService, + chainInfo, + assetInfo, }, }; @@ -67,7 +103,7 @@ harden(startBasicFlows); export const getManifestForContract = ( { restoreRef }, - { installKeys, ...options }, + { installKeys, options }, ) => { return { manifest: { @@ -87,6 +123,9 @@ export const getManifestForContract = ( instance: { produce: { [contractName]: true }, }, + issuer: { + consume: { BLD: true, IST: true }, + }, }, }, installations: { From fa9b36d0c5d747d7bc9963b8854a0f9f9ea81901 Mon Sep 17 00:00:00 2001 From: 0xPatrick Date: Wed, 27 Nov 2024 22:52:06 -0500 Subject: [PATCH 35/56] test(fast-usdc): support pfm transfers --- .../fast-usdc/test/fast-usdc.contract.test.ts | 30 ++++++++++++------ .../snapshots/fast-usdc.contract.test.ts.md | 3 ++ .../snapshots/fast-usdc.contract.test.ts.snap | Bin 5637 -> 5661 bytes packages/fast-usdc/test/supports.ts | 3 +- 4 files changed, 26 insertions(+), 10 deletions(-) diff --git a/packages/fast-usdc/test/fast-usdc.contract.test.ts b/packages/fast-usdc/test/fast-usdc.contract.test.ts index 7ec53744173..94e79dddbb8 100644 --- a/packages/fast-usdc/test/fast-usdc.contract.test.ts +++ b/packages/fast-usdc/test/fast-usdc.contract.test.ts @@ -404,10 +404,14 @@ const makeCustomer = ( const myMsg = local.find(lm => { if (lm.type !== 'VLOCALCHAIN_EXECUTE_TX') return false; const [ibcTransferMsg] = lm.messages; + // support advances to noble + other chains + const receiver = + ibcTransferMsg.receiver === 'pfm' + ? JSON.parse(ibcTransferMsg.memo).forward.receiver + : ibcTransferMsg.receiver; return ( ibcTransferMsg['@type'] === - '/ibc.applications.transfer.v1.MsgTransfer' && - ibcTransferMsg.receiver === EUD + '/ibc.applications.transfer.v1.MsgTransfer' && receiver === EUD ); }); if (!myMsg) { @@ -423,17 +427,25 @@ const makeCustomer = ( { amount: String(toReceive.value), denom: uusdcOnAgoric }, 'C4', ); - t.log(who, 'sees', ibcTransferMsg.token, 'sent to', EUD); - // TODO #10445 expect PFM memo - t.is(ibcTransferMsg.memo, '', 'TODO expecting PFM memo'); - - // TODO #10445 expect routing through noble, not osmosis + if (!EUD.startsWith('noble')) { + t.like( + JSON.parse(ibcTransferMsg.memo), + { + forward: { + receiver: EUD, + }, + }, + 'PFM receiver is EUD', + ); + } else { + t.like(ibcTransferMsg, { receiver: EUD }); + } t.is( ibcTransferMsg.sourceChannel, - fetchedChainInfo.agoric.connections['osmosis-1'].transferChannel + fetchedChainInfo.agoric.connections['noble-1'].transferChannel .channelId, - 'TODO expecting routing through Noble', + 'expect routing through Noble', ); }, }); diff --git a/packages/fast-usdc/test/snapshots/fast-usdc.contract.test.ts.md b/packages/fast-usdc/test/snapshots/fast-usdc.contract.test.ts.md index ece2a6e83cd..72890a09ece 100644 --- a/packages/fast-usdc/test/snapshots/fast-usdc.contract.test.ts.md +++ b/packages/fast-usdc/test/snapshots/fast-usdc.contract.test.ts.md @@ -43,6 +43,7 @@ Generated by [AVA](https://avajs.dev). bech32Prefix: 'agoric', chainId: 'agoric-3', icqEnabled: false, + pfmEnabled: true, stakingTokens: [ { denom: 'ubld', @@ -53,11 +54,13 @@ Generated by [AVA](https://avajs.dev). bech32Prefix: 'noble', chainId: 'noble-1', icqEnabled: false, + pfmEnabled: true, }, osmosis: { bech32Prefix: 'osmo', chainId: 'osmosis-1', icqEnabled: true, + pfmEnabled: true, stakingTokens: [ { denom: 'uosmo', diff --git a/packages/fast-usdc/test/snapshots/fast-usdc.contract.test.ts.snap b/packages/fast-usdc/test/snapshots/fast-usdc.contract.test.ts.snap index b4f6db225e5d35f97fc59405cd299d04a75b129f..c289cbdd0bb7e35e0f224dfca6d4478ef07e313f 100644 GIT binary patch literal 5661 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 diff --git a/packages/fast-usdc/test/supports.ts b/packages/fast-usdc/test/supports.ts index 2c9154ab227..7a64bcf2ff2 100644 --- a/packages/fast-usdc/test/supports.ts +++ b/packages/fast-usdc/test/supports.ts @@ -4,6 +4,7 @@ import { makeFakeStorageKit } from '@agoric/internal/src/storage-test-utils.js'; import { eventLoopIteration } from '@agoric/internal/src/testing-utils.js'; import { denomHash, + withChainCapabilities, type CosmosChainInfo, type Denom, } from '@agoric/orchestration'; @@ -196,7 +197,7 @@ export const commonSetup = async (t: ExecutionContext) => { ); const chainInfo = harden(() => { - const { agoric, osmosis, noble } = fetchedChainInfo; + const { agoric, osmosis, noble } = withChainCapabilities(fetchedChainInfo); return { agoric, osmosis, noble }; })(); From fe39f0afb0ddf9072b06b9f6cc09bc95059cfb65 Mon Sep 17 00:00:00 2001 From: 0xPatrick Date: Fri, 29 Nov 2024 17:26:11 -0500 Subject: [PATCH 36/56] test: deposit-withdraw requires asset info --- multichain-testing/test/basic-flows.test.ts | 11 +++++++---- .../test/deposit-withdraw-lca.test.ts | 11 +++++++---- .../test/deposit-withdraw-portfolio.test.ts | 11 +++++++---- multichain-testing/test/ica-channel-close.test.ts | 11 +++++++---- multichain-testing/test/tools/asset-info.test.ts | 2 ++ multichain-testing/tools/asset-info.ts | 14 +++++++++++++- 6 files changed, 43 insertions(+), 17 deletions(-) diff --git a/multichain-testing/test/basic-flows.test.ts b/multichain-testing/test/basic-flows.test.ts index 8db6ef7c84e..658ce851d67 100644 --- a/multichain-testing/test/basic-flows.test.ts +++ b/multichain-testing/test/basic-flows.test.ts @@ -16,12 +16,15 @@ const contractBuilder = '../packages/builders/scripts/orchestration/init-basic-flows.js'; test.before(async t => { - const { deleteTestKeys, setupTestKeys, ...rest } = await commonSetup(t); + const { setupTestKeys, ...common } = await commonSetup(t); + const { assetInfo, chainInfo, deleteTestKeys, startContract } = common; deleteTestKeys(accounts).catch(); const wallets = await setupTestKeys(accounts); - t.context = { ...rest, wallets, deleteTestKeys }; - const { startContract } = rest; - await startContract(contractName, contractBuilder); + t.context = { ...common, wallets }; + await startContract(contractName, contractBuilder, { + chainInfo: JSON.stringify(chainInfo), + assetInfo: JSON.stringify(assetInfo), + }); }); test.after(async t => { diff --git a/multichain-testing/test/deposit-withdraw-lca.test.ts b/multichain-testing/test/deposit-withdraw-lca.test.ts index 9ba574dff56..226b29d45dd 100644 --- a/multichain-testing/test/deposit-withdraw-lca.test.ts +++ b/multichain-testing/test/deposit-withdraw-lca.test.ts @@ -14,12 +14,15 @@ const contractBuilder = '../packages/builders/scripts/orchestration/init-basic-flows.js'; test.before(async t => { - const { deleteTestKeys, setupTestKeys, ...rest } = await commonSetup(t); + const { setupTestKeys, ...common } = await commonSetup(t); + const { assetInfo, chainInfo, deleteTestKeys, startContract } = common; deleteTestKeys(accounts).catch(); const wallets = await setupTestKeys(accounts); - t.context = { ...rest, wallets, deleteTestKeys }; - const { startContract } = rest; - await startContract(contractName, contractBuilder); + t.context = { ...common, wallets }; + await startContract(contractName, contractBuilder, { + chainInfo: JSON.stringify(chainInfo), + assetInfo: JSON.stringify(assetInfo), + }); }); test.after(async t => { diff --git a/multichain-testing/test/deposit-withdraw-portfolio.test.ts b/multichain-testing/test/deposit-withdraw-portfolio.test.ts index 24bb5277a80..afd484284b8 100644 --- a/multichain-testing/test/deposit-withdraw-portfolio.test.ts +++ b/multichain-testing/test/deposit-withdraw-portfolio.test.ts @@ -14,12 +14,15 @@ const contractBuilder = '../packages/builders/scripts/orchestration/init-basic-flows.js'; test.before(async t => { - const { deleteTestKeys, setupTestKeys, ...rest } = await commonSetup(t); + const { setupTestKeys, ...common } = await commonSetup(t); + const { assetInfo, chainInfo, deleteTestKeys, startContract } = common; deleteTestKeys(accounts).catch(); const wallets = await setupTestKeys(accounts); - t.context = { ...rest, wallets, deleteTestKeys }; - const { startContract } = rest; - await startContract(contractName, contractBuilder); + t.context = { ...common, wallets }; + await startContract(contractName, contractBuilder, { + chainInfo: JSON.stringify(chainInfo), + assetInfo: JSON.stringify(assetInfo), + }); }); test.after(async t => { diff --git a/multichain-testing/test/ica-channel-close.test.ts b/multichain-testing/test/ica-channel-close.test.ts index 9e844fa903b..ab7437da525 100644 --- a/multichain-testing/test/ica-channel-close.test.ts +++ b/multichain-testing/test/ica-channel-close.test.ts @@ -22,12 +22,15 @@ const contractBuilder = '../packages/builders/scripts/orchestration/init-basic-flows.js'; test.before(async t => { - const { deleteTestKeys, setupTestKeys, ...rest } = await commonSetup(t); + const { setupTestKeys, ...common } = await commonSetup(t); + const { assetInfo, chainInfo, deleteTestKeys, startContract } = common; deleteTestKeys(accounts).catch(); const wallets = await setupTestKeys(accounts); - t.context = { ...rest, wallets, deleteTestKeys }; - const { startContract } = rest; - await startContract(contractName, contractBuilder); + t.context = { ...common, wallets }; + await startContract(contractName, contractBuilder, { + chainInfo: JSON.stringify(chainInfo), + assetInfo: JSON.stringify(assetInfo), + }); }); test.after(async t => { diff --git a/multichain-testing/test/tools/asset-info.test.ts b/multichain-testing/test/tools/asset-info.test.ts index f12748de7fd..be054b65180 100644 --- a/multichain-testing/test/tools/asset-info.test.ts +++ b/multichain-testing/test/tools/asset-info.test.ts @@ -80,6 +80,7 @@ test('makeAssetInfo', async t => { { baseDenom: 'uist', baseName: 'agoric', + brandKey: 'IST', chainName: 'agoric', }, ], @@ -88,6 +89,7 @@ test('makeAssetInfo', async t => { { baseDenom: 'ubld', baseName: 'agoric', + brandKey: 'BLD', chainName: 'agoric', }, ], diff --git a/multichain-testing/tools/asset-info.ts b/multichain-testing/tools/asset-info.ts index 34c7d536b8c..f3e548d1968 100644 --- a/multichain-testing/tools/asset-info.ts +++ b/multichain-testing/tools/asset-info.ts @@ -37,6 +37,13 @@ export const makeAssetInfo = ( return `ibc/${denomHash({ denom, channelId })}`; }; + // `brandKey` instead of `brand` until #10580 + // only BLD, IST until #9966 + const BRAND_KEY_MAP: Record = { + ubld: 'BLD', + uist: 'IST', + }; + // only include chains present in `chainInfo` const tokens = Object.entries(tokenMap) .filter(([chain]) => chain in chainInfo) @@ -55,6 +62,7 @@ export const makeAssetInfo = ( { ...baseDetails, chainName: chain, + ...(BRAND_KEY_MAP[denom] && { brandKey: BRAND_KEY_MAP[denom] }), }, ]); @@ -62,11 +70,15 @@ export const makeAssetInfo = ( const issuingChainId = chainInfo[chain].chainId; for (const holdingChain of Object.keys(chainInfo)) { if (holdingChain === chain) continue; + const denomHash = toDenomHash(denom, issuingChainId, holdingChain); assetInfo.push([ - toDenomHash(denom, issuingChainId, holdingChain), + denomHash, { ...baseDetails, chainName: holdingChain, + ...(BRAND_KEY_MAP[denomHash] && { + brandKey: BRAND_KEY_MAP[denomHash], + }), }, ]); } From a2d491fdc571f56a6e83be037cbc6fe926354f68 Mon Sep 17 00:00:00 2001 From: 0xPatrick Date: Tue, 3 Dec 2024 13:03:58 -0500 Subject: [PATCH 37/56] chore: `startContract` stringifies `builderOpts` --- multichain-testing/test/auto-stake-it.test.ts | 4 ++-- multichain-testing/test/basic-flows.test.ts | 4 ++-- .../test/deposit-withdraw-lca.test.ts | 4 ++-- .../test/deposit-withdraw-portfolio.test.ts | 4 ++-- .../test/ica-channel-close.test.ts | 4 ++-- multichain-testing/test/send-anywhere.test.ts | 4 ++-- multichain-testing/test/support.ts | 16 ++++++++++++++-- 7 files changed, 26 insertions(+), 14 deletions(-) diff --git a/multichain-testing/test/auto-stake-it.test.ts b/multichain-testing/test/auto-stake-it.test.ts index 1c185c588b7..29b984ceec0 100644 --- a/multichain-testing/test/auto-stake-it.test.ts +++ b/multichain-testing/test/auto-stake-it.test.ts @@ -27,8 +27,8 @@ test.before(async t => { t.context = { ...common, wallets }; await startContract(contractName, contractBuilder, { - chainInfo: JSON.stringify(chainInfo), - assetInfo: JSON.stringify(assetInfo), + chainInfo, + assetInfo, }); }); diff --git a/multichain-testing/test/basic-flows.test.ts b/multichain-testing/test/basic-flows.test.ts index 658ce851d67..689db323524 100644 --- a/multichain-testing/test/basic-flows.test.ts +++ b/multichain-testing/test/basic-flows.test.ts @@ -22,8 +22,8 @@ test.before(async t => { const wallets = await setupTestKeys(accounts); t.context = { ...common, wallets }; await startContract(contractName, contractBuilder, { - chainInfo: JSON.stringify(chainInfo), - assetInfo: JSON.stringify(assetInfo), + chainInfo, + assetInfo, }); }); diff --git a/multichain-testing/test/deposit-withdraw-lca.test.ts b/multichain-testing/test/deposit-withdraw-lca.test.ts index 226b29d45dd..ad7fd4824d9 100644 --- a/multichain-testing/test/deposit-withdraw-lca.test.ts +++ b/multichain-testing/test/deposit-withdraw-lca.test.ts @@ -20,8 +20,8 @@ test.before(async t => { const wallets = await setupTestKeys(accounts); t.context = { ...common, wallets }; await startContract(contractName, contractBuilder, { - chainInfo: JSON.stringify(chainInfo), - assetInfo: JSON.stringify(assetInfo), + chainInfo, + assetInfo, }); }); diff --git a/multichain-testing/test/deposit-withdraw-portfolio.test.ts b/multichain-testing/test/deposit-withdraw-portfolio.test.ts index afd484284b8..ea97f1e7f17 100644 --- a/multichain-testing/test/deposit-withdraw-portfolio.test.ts +++ b/multichain-testing/test/deposit-withdraw-portfolio.test.ts @@ -20,8 +20,8 @@ test.before(async t => { const wallets = await setupTestKeys(accounts); t.context = { ...common, wallets }; await startContract(contractName, contractBuilder, { - chainInfo: JSON.stringify(chainInfo), - assetInfo: JSON.stringify(assetInfo), + chainInfo, + assetInfo, }); }); diff --git a/multichain-testing/test/ica-channel-close.test.ts b/multichain-testing/test/ica-channel-close.test.ts index ab7437da525..03b0ef9ac95 100644 --- a/multichain-testing/test/ica-channel-close.test.ts +++ b/multichain-testing/test/ica-channel-close.test.ts @@ -28,8 +28,8 @@ test.before(async t => { const wallets = await setupTestKeys(accounts); t.context = { ...common, wallets }; await startContract(contractName, contractBuilder, { - chainInfo: JSON.stringify(chainInfo), - assetInfo: JSON.stringify(assetInfo), + chainInfo, + assetInfo, }); }); diff --git a/multichain-testing/test/send-anywhere.test.ts b/multichain-testing/test/send-anywhere.test.ts index ba74b23338a..f1a8a720e5f 100644 --- a/multichain-testing/test/send-anywhere.test.ts +++ b/multichain-testing/test/send-anywhere.test.ts @@ -27,8 +27,8 @@ test.before(async t => { t.context = { ...common, wallets }; await startContract(contractName, contractBuilder, { - chainInfo: JSON.stringify(chainInfo), - assetInfo: JSON.stringify(assetInfo), + chainInfo, + assetInfo, }); }); diff --git a/multichain-testing/test/support.ts b/multichain-testing/test/support.ts index aef2bfab173..f3f8e752d96 100644 --- a/multichain-testing/test/support.ts +++ b/multichain-testing/test/support.ts @@ -4,6 +4,7 @@ import { execa } from 'execa'; import fse from 'fs-extra'; import childProcess from 'node:child_process'; import { withChainCapabilities } from '@agoric/orchestration'; +import { objectMap } from '@endo/patterns'; import { makeAgdTools } from '../tools/agd-tools.js'; import { type E2ETools } from '../tools/e2e-tools.js'; import { @@ -94,7 +95,7 @@ export const commonSetup = async (t: ExecutionContext) => { const startContract = async ( contractName: string, contractBuilder: string, - builderOpts?: Record, + builderOpts?: Record, ) => { const { vstorageClient } = tools; const instances = Object.fromEntries( @@ -104,7 +105,18 @@ export const commonSetup = async (t: ExecutionContext) => { return t.log('Contract found. Skipping installation...'); } t.log('bundle and install contract', contractName); - await deployBuilder(contractBuilder, builderOpts); + + const formattedOpts = builderOpts + ? objectMap( + // eslint-disable-next-line @typescript-eslint/no-explicit-any + builderOpts as Record, + value => { + if (typeof value === 'string') return value; + return JSON.stringify(value); + }, + ) + : undefined; + await deployBuilder(contractBuilder, formattedOpts); await retryUntilCondition( () => vstorageClient.queryData(`published.agoricNames.instance`), res => contractName in Object.fromEntries(res), From 0d2d4aa7886cc424e64a121821fc1373912aff82 Mon Sep 17 00:00:00 2001 From: Turadg Aleahmad Date: Tue, 3 Dec 2024 07:44:35 -0800 Subject: [PATCH 38/56] feat: export cli lib --- packages/agoric-cli/package.json | 3 ++- packages/agoric-cli/src/lib/index.js | 7 +++++++ 2 files changed, 9 insertions(+), 1 deletion(-) create mode 100644 packages/agoric-cli/src/lib/index.js diff --git a/packages/agoric-cli/package.json b/packages/agoric-cli/package.json index 13241c53219..ffdaedf4cea 100644 --- a/packages/agoric-cli/package.json +++ b/packages/agoric-cli/package.json @@ -10,7 +10,8 @@ }, "exports": { "./src/entrypoint.js": "./src/entrypoint.js", - "./src/helpers.js": "./src/helpers.js" + "./src/helpers.js": "./src/helpers.js", + "./src/lib/index.js": "./src/lib/index.js" }, "files": [ "src", diff --git a/packages/agoric-cli/src/lib/index.js b/packages/agoric-cli/src/lib/index.js new file mode 100644 index 00000000000..bf6ed5ccc44 --- /dev/null +++ b/packages/agoric-cli/src/lib/index.js @@ -0,0 +1,7 @@ +/** @file Utility library for use in other packages */ + +export * from './bundles.js'; +export * from './casting.js'; +export * from './chain.js'; +export * from './format.js'; +export * from './wallet.js'; From d71f36635cc2b97473db9bc817e28add13ed0f59 Mon Sep 17 00:00:00 2001 From: Turadg Aleahmad Date: Tue, 3 Dec 2024 07:48:23 -0800 Subject: [PATCH 39/56] build: yarn link relative agoric-sdk --- .../proposals/s:stake-bld/package.json | 52 +- .../proposals/s:stake-bld/yarn.lock | 1018 +++++++---------- 2 files changed, 484 insertions(+), 586 deletions(-) diff --git a/a3p-integration/proposals/s:stake-bld/package.json b/a3p-integration/proposals/s:stake-bld/package.json index ba0c30abf43..2c0a5093c38 100644 --- a/a3p-integration/proposals/s:stake-bld/package.json +++ b/a3p-integration/proposals/s:stake-bld/package.json @@ -9,6 +9,7 @@ "type": "module", "license": "Apache-2.0", "dependencies": { + "@agoric/client-utils": "dev", "@agoric/internal": "0.3.3-dev-5676146.0", "@agoric/synthetic-chain": "^0.4.3", "@cosmjs/stargate": "^0.32.3", @@ -16,7 +17,7 @@ "@endo/errors": "^1.2.2", "@endo/far": "^1.0.4", "@endo/init": "^1.0.4", - "agoric": "0.21.2-dev-5676146.0", + "agoric": "dev", "ava": "^5.3.1", "execa": "^8.0.1" }, @@ -26,5 +27,54 @@ "packageManager": "yarn@4.5.3", "devDependencies": { "@types/node": "^22.0.0" + }, + "resolutions": { + "@agoric/cosmos": "portal:../../agoric-sdk/golang/cosmos", + "@agoric/ertp": "portal:../../agoric-sdk/packages/ERTP", + "@agoric/swingset-vat": "portal:../../agoric-sdk/packages/SwingSet", + "@agoric/access-token": "portal:../../agoric-sdk/packages/access-token", + "agoric": "portal:../../agoric-sdk/packages/agoric-cli", + "@agoric/async-flow": "portal:../../agoric-sdk/packages/async-flow", + "@agoric/base-zone": "portal:../../agoric-sdk/packages/base-zone", + "@agoric/builders": "portal:../../agoric-sdk/packages/builders", + "@agoric/cache": "portal:../../agoric-sdk/packages/cache", + "@agoric/casting": "portal:../../agoric-sdk/packages/casting", + "@agoric/client-utils": "portal:../../agoric-sdk/packages/client-utils", + "@agoric/cosmic-proto": "portal:../../agoric-sdk/packages/cosmic-proto", + "@agoric/cosmic-swingset": "portal:../../agoric-sdk/packages/cosmic-swingset", + "@agoric/create-dapp": "portal:../../agoric-sdk/packages/create-dapp", + "@agoric/deploy-script-support": "portal:../../agoric-sdk/packages/deploy-script-support", + "@agoric/eslint-config": "portal:../../agoric-sdk/packages/eslint-config", + "@agoric/fast-usdc": "portal:../../agoric-sdk/packages/fast-usdc", + "@agoric/governance": "portal:../../agoric-sdk/packages/governance", + "@agoric/import-manager": "portal:../../agoric-sdk/packages/import-manager", + "@agoric/inter-protocol": "portal:../../agoric-sdk/packages/inter-protocol", + "@agoric/internal": "portal:../../agoric-sdk/packages/internal", + "@agoric/kmarshal": "portal:../../agoric-sdk/packages/kmarshal", + "@agoric/network": "portal:../../agoric-sdk/packages/network", + "@agoric/notifier": "portal:../../agoric-sdk/packages/notifier", + "@agoric/orchestration": "portal:../../agoric-sdk/packages/orchestration", + "@agoric/pegasus": "portal:../../agoric-sdk/packages/pegasus", + "@agoric/smart-wallet": "portal:../../agoric-sdk/packages/smart-wallet", + "@agoric/solo": "portal:../../agoric-sdk/packages/solo", + "@agoric/sparse-ints": "portal:../../agoric-sdk/packages/sparse-ints", + "@agoric/spawner": "portal:../../agoric-sdk/packages/spawner", + "@agoric/stat-logger": "portal:../../agoric-sdk/packages/stat-logger", + "@agoric/store": "portal:../../agoric-sdk/packages/store", + "@agoric/swing-store": "portal:../../agoric-sdk/packages/swing-store", + "@agoric/swingset-liveslots": "portal:../../agoric-sdk/packages/swingset-liveslots", + "@agoric/swingset-xsnap-supervisor": "portal:../../agoric-sdk/packages/swingset-xsnap-supervisor", + "@agoric/telemetry": "portal:../../agoric-sdk/packages/telemetry", + "@agoric/time": "portal:../../agoric-sdk/packages/time", + "@agoric/vat-data": "portal:../../agoric-sdk/packages/vat-data", + "@agoric/vats": "portal:../../agoric-sdk/packages/vats", + "@agoric/vm-config": "portal:../../agoric-sdk/packages/vm-config", + "@agoric/vow": "portal:../../agoric-sdk/packages/vow", + "@agoric/wallet": "portal:../../agoric-sdk/packages/wallet", + "@agoric/wallet-backend": "portal:../../agoric-sdk/packages/wallet/api", + "@agoric/xsnap": "portal:../../agoric-sdk/packages/xsnap", + "@agoric/xsnap-lockdown": "portal:../../agoric-sdk/packages/xsnap-lockdown", + "@agoric/zoe": "portal:../../agoric-sdk/packages/zoe", + "@agoric/zone": "portal:../../agoric-sdk/packages/zone" } } diff --git a/a3p-integration/proposals/s:stake-bld/yarn.lock b/a3p-integration/proposals/s:stake-bld/yarn.lock index 6eeed912071..0d13fa55ab9 100644 --- a/a3p-integration/proposals/s:stake-bld/yarn.lock +++ b/a3p-integration/proposals/s:stake-bld/yarn.lock @@ -5,23 +5,15 @@ __metadata: version: 8 cacheKey: 10c0 -"@agoric/access-token@npm:0.4.22-dev-5676146.0+5676146": - version: 0.4.22-dev-5676146.0 - resolution: "@agoric/access-token@npm:0.4.22-dev-5676146.0" +"@agoric/access-token@portal:../../agoric-sdk/packages/access-token::locator=root-workspace-0b6124%40workspace%3A.": + version: 0.0.0-use.local + resolution: "@agoric/access-token@portal:../../agoric-sdk/packages/access-token::locator=root-workspace-0b6124%40workspace%3A." dependencies: n-readlines: "npm:^1.0.0" proper-lockfile: "npm:^4.1.2" tmp: "npm:^0.2.1" - checksum: 10c0/c1fe4f9f1eaf2e4334ec190099f03d2ccff024e0b06693784230ccac6fbe7a98ebce63f365fade828b9c02c8967239e92c8fa0592d2661086e3b31eecd46e3b0 - languageName: node - linkType: hard - -"@agoric/assert@npm:0.6.1-dev-5676146.0+5676146": - version: 0.6.1-dev-5676146.0 - resolution: "@agoric/assert@npm:0.6.1-dev-5676146.0" - checksum: 10c0/3391d53d64f4ca74ae5a87b623dc7489a20d91f45716723c33e393cfe6536fb1553344b72d24ac966f49b83d56906140c263778968ff513dfcdbb30e1be68091 languageName: node - linkType: hard + linkType: soft "@agoric/babel-generator@npm:^7.17.6": version: 7.17.6 @@ -34,314 +26,306 @@ __metadata: languageName: node linkType: hard -"@agoric/base-zone@npm:0.1.1-dev-5676146.0+5676146": - version: 0.1.1-dev-5676146.0 - resolution: "@agoric/base-zone@npm:0.1.1-dev-5676146.0" +"@agoric/base-zone@portal:../../agoric-sdk/packages/base-zone::locator=root-workspace-0b6124%40workspace%3A.": + version: 0.0.0-use.local + resolution: "@agoric/base-zone@portal:../../agoric-sdk/packages/base-zone::locator=root-workspace-0b6124%40workspace%3A." dependencies: - "@agoric/store": "npm:0.9.3-dev-5676146.0+5676146" - "@endo/common": "npm:^1.1.0" - "@endo/exo": "npm:^1.2.1" - "@endo/far": "npm:^1.0.4" - "@endo/pass-style": "npm:^1.2.0" - "@endo/patterns": "npm:^1.2.0" - checksum: 10c0/b3dfa47af7cf4a686244e2a31243394b44756f127a7612f5d50c77b1a91f777514386c305866705b46219d2d1e0df2b8d5bff9e08f82275043bb0c198c0601e4 + "@agoric/store": "npm:^0.9.2" + "@endo/common": "npm:^1.2.8" + "@endo/errors": "npm:^1.2.8" + "@endo/exo": "npm:^1.5.7" + "@endo/far": "npm:^1.1.9" + "@endo/pass-style": "npm:^1.4.7" + "@endo/patterns": "npm:^1.4.7" languageName: node - linkType: hard + linkType: soft -"@agoric/cache@npm:0.3.3-dev-5676146.0+5676146": - version: 0.3.3-dev-5676146.0 - resolution: "@agoric/cache@npm:0.3.3-dev-5676146.0" +"@agoric/cache@portal:../../agoric-sdk/packages/cache::locator=root-workspace-0b6124%40workspace%3A.": + version: 0.0.0-use.local + resolution: "@agoric/cache@portal:../../agoric-sdk/packages/cache::locator=root-workspace-0b6124%40workspace%3A." dependencies: - "@agoric/internal": "npm:0.3.3-dev-5676146.0+5676146" - "@agoric/notifier": "npm:0.6.3-dev-5676146.0+5676146" - "@agoric/store": "npm:0.9.3-dev-5676146.0+5676146" - "@agoric/vat-data": "npm:0.5.3-dev-5676146.0+5676146" - "@endo/far": "npm:^1.0.4" - "@endo/marshal": "npm:^1.3.0" - checksum: 10c0/b2967955f99d3cfe9b30700373275290183a5b6284703b6bbfff98246342bd7ff995addc48e31a8b2c52c9330c1aed5566f9e73fc0ae5b753478c961d7cdf258 + "@agoric/internal": "npm:^0.3.2" + "@agoric/notifier": "npm:^0.6.2" + "@agoric/store": "npm:^0.9.2" + "@agoric/vat-data": "npm:^0.5.2" + "@endo/far": "npm:^1.1.9" + "@endo/marshal": "npm:^1.6.2" languageName: node - linkType: hard + linkType: soft -"@agoric/casting@npm:0.4.3-dev-5676146.0+5676146": - version: 0.4.3-dev-5676146.0 - resolution: "@agoric/casting@npm:0.4.3-dev-5676146.0" +"@agoric/casting@portal:../../agoric-sdk/packages/casting::locator=root-workspace-0b6124%40workspace%3A.": + version: 0.0.0-use.local + resolution: "@agoric/casting@portal:../../agoric-sdk/packages/casting::locator=root-workspace-0b6124%40workspace%3A." dependencies: - "@agoric/internal": "npm:0.3.3-dev-5676146.0+5676146" - "@agoric/notifier": "npm:0.6.3-dev-5676146.0+5676146" - "@agoric/spawner": "npm:0.6.9-dev-5676146.0+5676146" - "@agoric/store": "npm:0.9.3-dev-5676146.0+5676146" + "@agoric/internal": "npm:^0.3.2" + "@agoric/notifier": "npm:^0.6.2" + "@agoric/store": "npm:^0.9.2" "@cosmjs/encoding": "npm:^0.32.3" "@cosmjs/proto-signing": "npm:^0.32.3" "@cosmjs/stargate": "npm:^0.32.3" "@cosmjs/tendermint-rpc": "npm:^0.32.3" - "@endo/far": "npm:^1.0.4" - "@endo/init": "npm:^1.0.4" - "@endo/lockdown": "npm:^1.0.4" - "@endo/marshal": "npm:^1.3.0" - "@endo/promise-kit": "npm:^1.0.4" - node-fetch: "npm:^2.6.0" - checksum: 10c0/548c929c6535aea1d0a8e2cbc7fc3ec57d04dd8fd5b6e62ee565b674f8a87efe82536091e182a71a985244c0459e19b0195fc81b80a22c480859c37a69815367 + "@endo/errors": "npm:^1.2.8" + "@endo/far": "npm:^1.1.9" + "@endo/init": "npm:^1.1.7" + "@endo/lockdown": "npm:^1.0.13" + "@endo/marshal": "npm:^1.6.2" + "@endo/promise-kit": "npm:^1.1.8" languageName: node - linkType: hard + linkType: soft -"@agoric/cosmic-proto@npm:0.4.1-dev-5676146.0+5676146": - version: 0.4.1-dev-5676146.0 - resolution: "@agoric/cosmic-proto@npm:0.4.1-dev-5676146.0" +"@agoric/client-utils@portal:../../agoric-sdk/packages/client-utils::locator=root-workspace-0b6124%40workspace%3A.": + version: 0.0.0-use.local + resolution: "@agoric/client-utils@portal:../../agoric-sdk/packages/client-utils::locator=root-workspace-0b6124%40workspace%3A." dependencies: - "@cosmjs/amino": "npm:^0.32.3" - "@cosmjs/proto-signing": "npm:^0.32.3" + "@agoric/casting": "npm:^0.4.2" + "@agoric/ertp": "npm:^0.16.2" + "@agoric/internal": "npm:^0.3.2" + "@agoric/smart-wallet": "npm:^0.5.3" + "@agoric/vats": "npm:^0.15.1" "@cosmjs/stargate": "npm:^0.32.3" "@cosmjs/tendermint-rpc": "npm:^0.32.3" - "@endo/init": "npm:^1.0.3" - axios: "npm:^1.6.7" - checksum: 10c0/dc5a39feebce9209a393c37f6bfe6be550600718b2c841e13750a92d3a734d5ed718beb3d7532829c2da5e0344cf96b82f8d779dfc30d4b2c266d89902e2f4b8 + "@endo/common": "npm:^1.2.8" + "@endo/errors": "npm:^1.2.8" + "@endo/marshal": "npm:^1.6.2" + "@endo/pass-style": "npm:^1.4.7" + "@endo/patterns": "npm:^1.4.7" + "@endo/promise-kit": "npm:^1.1.8" languageName: node - linkType: hard + linkType: soft -"@agoric/ertp@npm:0.16.3-dev-5676146.0+5676146": - version: 0.16.3-dev-5676146.0 - resolution: "@agoric/ertp@npm:0.16.3-dev-5676146.0" +"@agoric/cosmic-proto@portal:../../agoric-sdk/packages/cosmic-proto::locator=root-workspace-0b6124%40workspace%3A.": + version: 0.0.0-use.local + resolution: "@agoric/cosmic-proto@portal:../../agoric-sdk/packages/cosmic-proto::locator=root-workspace-0b6124%40workspace%3A." dependencies: - "@agoric/assert": "npm:0.6.1-dev-5676146.0+5676146" - "@agoric/notifier": "npm:0.6.3-dev-5676146.0+5676146" - "@agoric/store": "npm:0.9.3-dev-5676146.0+5676146" - "@agoric/vat-data": "npm:0.5.3-dev-5676146.0+5676146" - "@agoric/zone": "npm:0.2.3-dev-5676146.0+5676146" - "@endo/eventual-send": "npm:^1.1.2" - "@endo/far": "npm:^1.0.4" - "@endo/marshal": "npm:^1.3.0" - "@endo/nat": "npm:^5.0.4" - "@endo/patterns": "npm:^1.2.0" - "@endo/promise-kit": "npm:^1.0.4" - checksum: 10c0/6a3ef33e6b1052253346a651f6f193dbda9551a2ed3f36f63af0b9da4d27ed80bdf63251f97cc631105c923ac23440ef456198f1b15b56b6aba86ec1a590b6f6 - languageName: node - linkType: hard - -"@agoric/governance@npm:0.10.4-dev-5676146.0+5676146": - version: 0.10.4-dev-5676146.0 - resolution: "@agoric/governance@npm:0.10.4-dev-5676146.0" - dependencies: - "@agoric/assert": "npm:0.6.1-dev-5676146.0+5676146" - "@agoric/ertp": "npm:0.16.3-dev-5676146.0+5676146" - "@agoric/internal": "npm:0.3.3-dev-5676146.0+5676146" - "@agoric/network": "npm:0.1.1-dev-5676146.0+5676146" - "@agoric/notifier": "npm:0.6.3-dev-5676146.0+5676146" - "@agoric/store": "npm:0.9.3-dev-5676146.0+5676146" - "@agoric/time": "npm:0.3.3-dev-5676146.0+5676146" - "@agoric/vat-data": "npm:0.5.3-dev-5676146.0+5676146" - "@agoric/zoe": "npm:0.26.3-dev-5676146.0+5676146" - "@endo/bundle-source": "npm:^3.1.0" - "@endo/captp": "npm:^4.0.4" - "@endo/eventual-send": "npm:^1.1.2" - "@endo/far": "npm:^1.0.4" - "@endo/marshal": "npm:^1.3.0" - "@endo/nat": "npm:^5.0.4" - "@endo/promise-kit": "npm:^1.0.4" + "@endo/base64": "npm:^1.0.9" + "@endo/init": "npm:^1.1.7" + languageName: node + linkType: soft + +"@agoric/ertp@portal:../../agoric-sdk/packages/ERTP::locator=root-workspace-0b6124%40workspace%3A.": + version: 0.0.0-use.local + resolution: "@agoric/ertp@portal:../../agoric-sdk/packages/ERTP::locator=root-workspace-0b6124%40workspace%3A." + dependencies: + "@agoric/notifier": "npm:^0.6.2" + "@agoric/store": "npm:^0.9.2" + "@agoric/vat-data": "npm:^0.5.2" + "@agoric/zone": "npm:^0.2.2" + "@endo/errors": "npm:^1.2.8" + "@endo/eventual-send": "npm:^1.2.8" + "@endo/far": "npm:^1.1.9" + "@endo/marshal": "npm:^1.6.2" + "@endo/nat": "npm:^5.0.13" + "@endo/patterns": "npm:^1.4.7" + "@endo/promise-kit": "npm:^1.1.8" + languageName: node + linkType: soft + +"@agoric/governance@portal:../../agoric-sdk/packages/governance::locator=root-workspace-0b6124%40workspace%3A.": + version: 0.0.0-use.local + resolution: "@agoric/governance@portal:../../agoric-sdk/packages/governance::locator=root-workspace-0b6124%40workspace%3A." + dependencies: + "@agoric/ertp": "npm:^0.16.2" + "@agoric/internal": "npm:^0.3.2" + "@agoric/notifier": "npm:^0.6.2" + "@agoric/store": "npm:^0.9.2" + "@agoric/time": "npm:^0.3.2" + "@agoric/vat-data": "npm:^0.5.2" + "@agoric/zoe": "npm:^0.26.2" + "@endo/bundle-source": "npm:^3.5.0" + "@endo/captp": "npm:^4.4.3" + "@endo/errors": "npm:^1.2.8" + "@endo/eventual-send": "npm:^1.2.8" + "@endo/far": "npm:^1.1.9" + "@endo/marshal": "npm:^1.6.2" + "@endo/nat": "npm:^5.0.13" + "@endo/promise-kit": "npm:^1.1.8" import-meta-resolve: "npm:^2.2.1" - checksum: 10c0/64a8a0579fde6dd60630175e5d1bd0a370532c993700049352f2cc83dbfde6cac90b1671acf625afadcc3449a8f4872d1dacc194f8724281b5ac82e6c1b887d1 - languageName: node - linkType: hard - -"@agoric/inter-protocol@npm:0.16.2-dev-5676146.0+5676146": - version: 0.16.2-dev-5676146.0 - resolution: "@agoric/inter-protocol@npm:0.16.2-dev-5676146.0" - dependencies: - "@agoric/assert": "npm:0.6.1-dev-5676146.0+5676146" - "@agoric/ertp": "npm:0.16.3-dev-5676146.0+5676146" - "@agoric/governance": "npm:0.10.4-dev-5676146.0+5676146" - "@agoric/internal": "npm:0.3.3-dev-5676146.0+5676146" - "@agoric/notifier": "npm:0.6.3-dev-5676146.0+5676146" - "@agoric/store": "npm:0.9.3-dev-5676146.0+5676146" - "@agoric/time": "npm:0.3.3-dev-5676146.0+5676146" - "@agoric/vat-data": "npm:0.5.3-dev-5676146.0+5676146" - "@agoric/vats": "npm:0.15.2-dev-5676146.0+5676146" - "@agoric/zoe": "npm:0.26.3-dev-5676146.0+5676146" - "@endo/captp": "npm:^4.0.4" - "@endo/eventual-send": "npm:^1.1.2" - "@endo/far": "npm:^1.0.4" - "@endo/marshal": "npm:^1.3.0" - "@endo/nat": "npm:^5.0.4" - "@endo/promise-kit": "npm:^1.0.4" - jessie.js: "npm:^0.3.2" - checksum: 10c0/6216bb903dc4b292f6b24fdc6121cd3540ebdd402f4c81dded60b00bbf2f8130c25a2565ccb80ffc68dbc2b625d0459df3215cbf69585ed84f101a5d53351e4c languageName: node - linkType: hard + linkType: soft + +"@agoric/inter-protocol@portal:../../agoric-sdk/packages/inter-protocol::locator=root-workspace-0b6124%40workspace%3A.": + version: 0.0.0-use.local + resolution: "@agoric/inter-protocol@portal:../../agoric-sdk/packages/inter-protocol::locator=root-workspace-0b6124%40workspace%3A." + dependencies: + "@agoric/ertp": "npm:^0.16.2" + "@agoric/governance": "npm:^0.10.3" + "@agoric/internal": "npm:^0.3.2" + "@agoric/notifier": "npm:^0.6.2" + "@agoric/store": "npm:^0.9.2" + "@agoric/time": "npm:^0.3.2" + "@agoric/vat-data": "npm:^0.5.2" + "@agoric/vats": "npm:^0.15.1" + "@agoric/zoe": "npm:^0.26.2" + "@agoric/zone": "npm:^0.2.2" + "@endo/captp": "npm:^4.4.3" + "@endo/errors": "npm:^1.2.8" + "@endo/eventual-send": "npm:^1.2.8" + "@endo/far": "npm:^1.1.9" + "@endo/marshal": "npm:^1.6.2" + "@endo/nat": "npm:^5.0.13" + "@endo/promise-kit": "npm:^1.1.8" + jessie.js: "npm:^0.3.4" + languageName: node + linkType: soft -"@agoric/internal@npm:0.3.3-dev-5676146.0, @agoric/internal@npm:0.3.3-dev-5676146.0+5676146": - version: 0.3.3-dev-5676146.0 - resolution: "@agoric/internal@npm:0.3.3-dev-5676146.0" +"@agoric/internal@portal:../../agoric-sdk/packages/internal::locator=root-workspace-0b6124%40workspace%3A.": + version: 0.0.0-use.local + resolution: "@agoric/internal@portal:../../agoric-sdk/packages/internal::locator=root-workspace-0b6124%40workspace%3A." dependencies: - "@agoric/assert": "npm:0.6.1-dev-5676146.0+5676146" - "@agoric/base-zone": "npm:0.1.1-dev-5676146.0+5676146" - "@endo/common": "npm:^1.1.0" - "@endo/far": "npm:^1.0.4" - "@endo/init": "npm:^1.0.4" - "@endo/marshal": "npm:^1.3.0" - "@endo/patterns": "npm:^1.2.0" - "@endo/promise-kit": "npm:^1.0.4" - "@endo/stream": "npm:^1.1.0" + "@agoric/base-zone": "npm:^0.1.0" + "@endo/common": "npm:^1.2.8" + "@endo/errors": "npm:^1.2.8" + "@endo/far": "npm:^1.1.9" + "@endo/init": "npm:^1.1.7" + "@endo/marshal": "npm:^1.6.2" + "@endo/pass-style": "npm:^1.4.7" + "@endo/patterns": "npm:^1.4.7" + "@endo/promise-kit": "npm:^1.1.8" + "@endo/stream": "npm:^1.2.8" anylogger: "npm:^0.21.0" - jessie.js: "npm:^0.3.2" - checksum: 10c0/cd2a81ff39790a1b333621b3815f0791b70d0822f201d491175e46602697c80814f1fb87a610167e541a9ad431a771cd7348afe24517a15c45d1591d3d494bc2 + jessie.js: "npm:^0.3.4" languageName: node - linkType: hard + linkType: soft -"@agoric/kmarshal@npm:0.1.1-dev-5676146.0+5676146": - version: 0.1.1-dev-5676146.0 - resolution: "@agoric/kmarshal@npm:0.1.1-dev-5676146.0" +"@agoric/kmarshal@portal:../../agoric-sdk/packages/kmarshal::locator=root-workspace-0b6124%40workspace%3A.": + version: 0.0.0-use.local + resolution: "@agoric/kmarshal@portal:../../agoric-sdk/packages/kmarshal::locator=root-workspace-0b6124%40workspace%3A." dependencies: - "@agoric/assert": "npm:0.6.1-dev-5676146.0+5676146" - "@endo/far": "npm:^1.0.4" - "@endo/marshal": "npm:^1.3.0" - checksum: 10c0/6acd0de1ad1cb2b4bd6065f13394222476a713be169dd7979a26934f223bcac2222d9e1560327f31417a774501e82703dce3c0cae0a327eae955e2072e8587d7 + "@endo/errors": "npm:^1.2.8" + "@endo/far": "npm:^1.1.9" + "@endo/marshal": "npm:^1.6.2" languageName: node - linkType: hard + linkType: soft -"@agoric/network@npm:0.1.1-dev-5676146.0+5676146": - version: 0.1.1-dev-5676146.0 - resolution: "@agoric/network@npm:0.1.1-dev-5676146.0" +"@agoric/network@portal:../../agoric-sdk/packages/network::locator=root-workspace-0b6124%40workspace%3A.": + version: 0.0.0-use.local + resolution: "@agoric/network@portal:../../agoric-sdk/packages/network::locator=root-workspace-0b6124%40workspace%3A." dependencies: - "@agoric/assert": "npm:0.6.1-dev-5676146.0+5676146" - "@agoric/internal": "npm:0.3.3-dev-5676146.0+5676146" - "@agoric/store": "npm:0.9.3-dev-5676146.0+5676146" - "@agoric/vat-data": "npm:0.5.3-dev-5676146.0+5676146" - "@endo/base64": "npm:^1.0.2" - "@endo/far": "npm:^1.0.4" - "@endo/patterns": "npm:^1.1.0" - "@endo/promise-kit": "npm:^1.0.4" - checksum: 10c0/92207ef3889c53526490de4d62b93788dfb009fb70809b473a50993adc0bc8fbbd2be8da43db78a51b5df9af19d7cbe24aab55c958daf4bdcb86ae1e6e55af95 + "@agoric/internal": "npm:^0.3.2" + "@agoric/store": "npm:^0.9.2" + "@agoric/vat-data": "npm:^0.5.2" + "@endo/base64": "npm:^1.0.9" + "@endo/errors": "npm:^1.2.8" + "@endo/far": "npm:^1.1.9" + "@endo/pass-style": "npm:^1.4.7" + "@endo/patterns": "npm:^1.4.7" + "@endo/promise-kit": "npm:^1.1.8" languageName: node - linkType: hard + linkType: soft -"@agoric/notifier@npm:0.6.3-dev-5676146.0+5676146": - version: 0.6.3-dev-5676146.0 - resolution: "@agoric/notifier@npm:0.6.3-dev-5676146.0" +"@agoric/notifier@portal:../../agoric-sdk/packages/notifier::locator=root-workspace-0b6124%40workspace%3A.": + version: 0.0.0-use.local + resolution: "@agoric/notifier@portal:../../agoric-sdk/packages/notifier::locator=root-workspace-0b6124%40workspace%3A." dependencies: - "@agoric/assert": "npm:0.6.1-dev-5676146.0+5676146" - "@agoric/internal": "npm:0.3.3-dev-5676146.0+5676146" - "@agoric/vat-data": "npm:0.5.3-dev-5676146.0+5676146" - "@endo/far": "npm:^1.0.4" - "@endo/marshal": "npm:^1.3.0" - "@endo/patterns": "npm:^1.2.0" - "@endo/promise-kit": "npm:^1.0.4" - checksum: 10c0/5357e05ff60d962189658e9476307f5c3a8fd4f6cf82d30dd4526050c5f747f33eafeb8cdb25753c61d91e1390a4c8408424fd6d15ecb103add72e5113b0c4a1 - languageName: node - linkType: hard - -"@agoric/smart-wallet@npm:0.5.4-dev-5676146.0+5676146": - version: 0.5.4-dev-5676146.0 - resolution: "@agoric/smart-wallet@npm:0.5.4-dev-5676146.0" - dependencies: - "@agoric/assert": "npm:0.6.1-dev-5676146.0+5676146" - "@agoric/casting": "npm:0.4.3-dev-5676146.0+5676146" - "@agoric/ertp": "npm:0.16.3-dev-5676146.0+5676146" - "@agoric/internal": "npm:0.3.3-dev-5676146.0+5676146" - "@agoric/notifier": "npm:0.6.3-dev-5676146.0+5676146" - "@agoric/store": "npm:0.9.3-dev-5676146.0+5676146" - "@agoric/vat-data": "npm:0.5.3-dev-5676146.0+5676146" - "@agoric/vats": "npm:0.15.2-dev-5676146.0+5676146" - "@agoric/zoe": "npm:0.26.3-dev-5676146.0+5676146" - "@endo/eventual-send": "npm:^1.1.2" - "@endo/far": "npm:^1.0.4" - "@endo/marshal": "npm:^1.3.0" - "@endo/nat": "npm:^5.0.4" - "@endo/promise-kit": "npm:^1.0.4" - checksum: 10c0/cc46165846a0d0b3f7290ec4f5fe60030f3272ee7278bd49274634daee5000d96222e2ed3e72f724943100101cee4d2f760e0bf2d5c08620b89930d3fbed5715 + "@agoric/internal": "npm:^0.3.2" + "@agoric/vat-data": "npm:^0.5.2" + "@endo/errors": "npm:^1.2.8" + "@endo/far": "npm:^1.1.9" + "@endo/marshal": "npm:^1.6.2" + "@endo/patterns": "npm:^1.4.7" + "@endo/promise-kit": "npm:^1.1.8" languageName: node - linkType: hard + linkType: soft -"@agoric/spawner@npm:0.6.9-dev-5676146.0+5676146": - version: 0.6.9-dev-5676146.0 - resolution: "@agoric/spawner@npm:0.6.9-dev-5676146.0" - dependencies: - "@agoric/assert": "npm:0.6.1-dev-5676146.0+5676146" - "@endo/eventual-send": "npm:^1.1.2" - "@endo/import-bundle": "npm:^1.0.4" - "@endo/marshal": "npm:^1.3.0" - checksum: 10c0/4f605a59a2da5fef37faf8923ebeb237e789f65f678a192c926bb1ccb3ead49eecb75b9120971da9cc4d046de0503087af38814e69811e9d6bfa7d1559b0c510 +"@agoric/smart-wallet@portal:../../agoric-sdk/packages/smart-wallet::locator=root-workspace-0b6124%40workspace%3A.": + version: 0.0.0-use.local + resolution: "@agoric/smart-wallet@portal:../../agoric-sdk/packages/smart-wallet::locator=root-workspace-0b6124%40workspace%3A." + dependencies: + "@agoric/ertp": "npm:^0.16.2" + "@agoric/internal": "npm:^0.3.2" + "@agoric/notifier": "npm:^0.6.2" + "@agoric/store": "npm:^0.9.2" + "@agoric/vat-data": "npm:^0.5.2" + "@agoric/vats": "npm:^0.15.1" + "@agoric/vow": "npm:^0.1.0" + "@agoric/zoe": "npm:^0.26.2" + "@agoric/zone": "npm:^0.2.2" + "@endo/errors": "npm:^1.2.8" + "@endo/eventual-send": "npm:^1.2.8" + "@endo/far": "npm:^1.1.9" + "@endo/marshal": "npm:^1.6.2" + "@endo/nat": "npm:^5.0.13" + "@endo/promise-kit": "npm:^1.1.8" languageName: node - linkType: hard + linkType: soft -"@agoric/store@npm:0.9.3-dev-5676146.0+5676146": - version: 0.9.3-dev-5676146.0 - resolution: "@agoric/store@npm:0.9.3-dev-5676146.0" +"@agoric/store@portal:../../agoric-sdk/packages/store::locator=root-workspace-0b6124%40workspace%3A.": + version: 0.0.0-use.local + resolution: "@agoric/store@portal:../../agoric-sdk/packages/store::locator=root-workspace-0b6124%40workspace%3A." dependencies: - "@endo/exo": "npm:^1.2.1" - "@endo/marshal": "npm:^1.3.0" - "@endo/pass-style": "npm:^1.2.0" - "@endo/patterns": "npm:^1.2.0" - checksum: 10c0/675e73bbcac024c456b658583ec3fd14a50f69fea5fc07aadf30e593978e5cadbc82d365b13976967b5509614a7adf0adad4e84712f7e0b6c13f2a2a93c9ea63 + "@endo/errors": "npm:^1.2.8" + "@endo/exo": "npm:^1.5.7" + "@endo/marshal": "npm:^1.6.2" + "@endo/pass-style": "npm:^1.4.7" + "@endo/patterns": "npm:^1.4.7" languageName: node - linkType: hard + linkType: soft -"@agoric/swing-store@npm:0.9.2-dev-5676146.0+5676146": - version: 0.9.2-dev-5676146.0 - resolution: "@agoric/swing-store@npm:0.9.2-dev-5676146.0" +"@agoric/swing-store@portal:../../agoric-sdk/packages/swing-store::locator=root-workspace-0b6124%40workspace%3A.": + version: 0.0.0-use.local + resolution: "@agoric/swing-store@portal:../../agoric-sdk/packages/swing-store::locator=root-workspace-0b6124%40workspace%3A." dependencies: - "@agoric/assert": "npm:0.6.1-dev-5676146.0+5676146" - "@agoric/internal": "npm:0.3.3-dev-5676146.0+5676146" - "@endo/base64": "npm:^1.0.2" - "@endo/bundle-source": "npm:^3.1.0" - "@endo/check-bundle": "npm:^1.0.4" - "@endo/nat": "npm:^5.0.4" + "@agoric/internal": "npm:^0.3.2" + "@endo/base64": "npm:^1.0.9" + "@endo/bundle-source": "npm:^3.5.0" + "@endo/check-bundle": "npm:^1.0.12" + "@endo/errors": "npm:^1.2.8" + "@endo/nat": "npm:^5.0.13" better-sqlite3: "npm:^9.1.1" - checksum: 10c0/4f18b4051bc41fb153da4b750144db727f9b59e8fd18196eea1427d12028b47ebf8448b14c47708a2347ed2a4c1ed887fdcf2c0048b5ab4e84869cd17e3dc935 languageName: node - linkType: hard + linkType: soft -"@agoric/swingset-liveslots@npm:0.10.3-dev-5676146.0+5676146": - version: 0.10.3-dev-5676146.0 - resolution: "@agoric/swingset-liveslots@npm:0.10.3-dev-5676146.0" +"@agoric/swingset-liveslots@portal:../../agoric-sdk/packages/swingset-liveslots::locator=root-workspace-0b6124%40workspace%3A.": + version: 0.0.0-use.local + resolution: "@agoric/swingset-liveslots@portal:../../agoric-sdk/packages/swingset-liveslots::locator=root-workspace-0b6124%40workspace%3A." dependencies: - "@agoric/assert": "npm:0.6.1-dev-5676146.0+5676146" - "@agoric/internal": "npm:0.3.3-dev-5676146.0+5676146" - "@agoric/store": "npm:0.9.3-dev-5676146.0+5676146" - "@endo/env-options": "npm:^1.1.1" - "@endo/errors": "npm:^1.1.0" - "@endo/eventual-send": "npm:^1.1.2" - "@endo/exo": "npm:^1.2.1" - "@endo/far": "npm:^1.0.4" - "@endo/init": "npm:^1.0.4" - "@endo/marshal": "npm:^1.3.0" - "@endo/nat": "npm:^5.0.4" - "@endo/pass-style": "npm:^1.2.0" - "@endo/patterns": "npm:^1.2.0" - "@endo/promise-kit": "npm:^1.0.4" - checksum: 10c0/17ff4c6b94992d5532b748b4b20a95d273f8eb9ee7345552b95050de90563f5f2b03416ff60b9ca3ce07564bb4f3aa993fbf7710f6b24dc88d902b701a8b6a91 - languageName: node - linkType: hard - -"@agoric/swingset-vat@npm:0.32.3-dev-5676146.0+5676146": - version: 0.32.3-dev-5676146.0 - resolution: "@agoric/swingset-vat@npm:0.32.3-dev-5676146.0" - dependencies: - "@agoric/assert": "npm:0.6.1-dev-5676146.0+5676146" - "@agoric/internal": "npm:0.3.3-dev-5676146.0+5676146" - "@agoric/kmarshal": "npm:0.1.1-dev-5676146.0+5676146" - "@agoric/store": "npm:0.9.3-dev-5676146.0+5676146" - "@agoric/swing-store": "npm:0.9.2-dev-5676146.0+5676146" - "@agoric/swingset-liveslots": "npm:0.10.3-dev-5676146.0+5676146" - "@agoric/swingset-xsnap-supervisor": "npm:0.10.3-dev-5676146.0+5676146" - "@agoric/time": "npm:0.3.3-dev-5676146.0+5676146" - "@agoric/vat-data": "npm:0.5.3-dev-5676146.0+5676146" - "@agoric/xsnap": "npm:0.14.3-dev-5676146.0+5676146" - "@agoric/xsnap-lockdown": "npm:0.14.1-dev-5676146.0+5676146" - "@endo/base64": "npm:^1.0.2" - "@endo/bundle-source": "npm:^3.1.0" - "@endo/captp": "npm:^4.0.4" - "@endo/check-bundle": "npm:^1.0.4" - "@endo/compartment-mapper": "npm:^1.1.2" - "@endo/eventual-send": "npm:^1.1.2" - "@endo/far": "npm:^1.0.4" - "@endo/import-bundle": "npm:^1.0.4" - "@endo/init": "npm:^1.0.4" - "@endo/marshal": "npm:^1.3.0" - "@endo/nat": "npm:^5.0.4" - "@endo/patterns": "npm:^1.2.0" - "@endo/promise-kit": "npm:^1.0.4" - "@endo/ses-ava": "npm:^1.1.2" - "@endo/stream": "npm:^1.1.0" - "@endo/zip": "npm:^1.0.2" + "@agoric/internal": "npm:^0.3.2" + "@agoric/store": "npm:^0.9.2" + "@endo/env-options": "npm:^1.1.8" + "@endo/errors": "npm:^1.2.8" + "@endo/eventual-send": "npm:^1.2.8" + "@endo/exo": "npm:^1.5.7" + "@endo/far": "npm:^1.1.9" + "@endo/init": "npm:^1.1.7" + "@endo/marshal": "npm:^1.6.2" + "@endo/nat": "npm:^5.0.13" + "@endo/pass-style": "npm:^1.4.7" + "@endo/patterns": "npm:^1.4.7" + "@endo/promise-kit": "npm:^1.1.8" + languageName: node + linkType: soft + +"@agoric/swingset-vat@portal:../../agoric-sdk/packages/SwingSet::locator=root-workspace-0b6124%40workspace%3A.": + version: 0.0.0-use.local + resolution: "@agoric/swingset-vat@portal:../../agoric-sdk/packages/SwingSet::locator=root-workspace-0b6124%40workspace%3A." + dependencies: + "@agoric/internal": "npm:^0.3.2" + "@agoric/kmarshal": "npm:^0.1.0" + "@agoric/store": "npm:^0.9.2" + "@agoric/swing-store": "npm:^0.9.1" + "@agoric/swingset-liveslots": "npm:^0.10.2" + "@agoric/swingset-xsnap-supervisor": "npm:^0.10.2" + "@agoric/time": "npm:^0.3.2" + "@agoric/vat-data": "npm:^0.5.2" + "@agoric/xsnap-lockdown": "npm:^0.14.0" + "@endo/base64": "npm:^1.0.9" + "@endo/bundle-source": "npm:^3.5.0" + "@endo/captp": "npm:^4.4.3" + "@endo/check-bundle": "npm:^1.0.12" + "@endo/compartment-mapper": "npm:^1.4.0" + "@endo/errors": "npm:^1.2.8" + "@endo/eventual-send": "npm:^1.2.8" + "@endo/far": "npm:^1.1.9" + "@endo/import-bundle": "npm:^1.3.2" + "@endo/init": "npm:^1.1.7" + "@endo/marshal": "npm:^1.6.2" + "@endo/nat": "npm:^5.0.13" + "@endo/pass-style": "npm:^1.4.7" + "@endo/patterns": "npm:^1.4.7" + "@endo/promise-kit": "npm:^1.1.8" + "@endo/ses-ava": "npm:^1.2.8" + "@endo/stream": "npm:^1.2.8" + "@endo/zip": "npm:^1.0.9" ansi-styles: "npm:^6.2.1" anylogger: "npm:^0.21.0" better-sqlite3: "npm:^9.1.1" @@ -351,19 +335,18 @@ __metadata: tmp: "npm:^0.2.1" yargs-parser: "npm:^21.1.1" peerDependencies: + "@agoric/xsnap": ^0.14.2 ava: ^5.3.0 bin: vat: bin/vat - checksum: 10c0/5eaa97f9e9a71bf20c590d44693c97e12bfbf42e2ce15991d48e3393ff1f9561b8e7717fa63dabc3c0d720795e8922452485003e86b68e307d90bd6aea4c79b0 languageName: node - linkType: hard + linkType: soft -"@agoric/swingset-xsnap-supervisor@npm:0.10.3-dev-5676146.0+5676146": - version: 0.10.3-dev-5676146.0 - resolution: "@agoric/swingset-xsnap-supervisor@npm:0.10.3-dev-5676146.0" - checksum: 10c0/495c847ccb69bcfb338e27a2b423ec480e303c52c51e0496aaeea820d17af100c59f2d45e540517c8eba4aea9645ef6c3e200ad3834d46087b4a21671791e077 +"@agoric/swingset-xsnap-supervisor@portal:../../agoric-sdk/packages/swingset-xsnap-supervisor::locator=root-workspace-0b6124%40workspace%3A.": + version: 0.0.0-use.local + resolution: "@agoric/swingset-xsnap-supervisor@portal:../../agoric-sdk/packages/swingset-xsnap-supervisor::locator=root-workspace-0b6124%40workspace%3A." languageName: node - linkType: hard + linkType: soft "@agoric/synthetic-chain@npm:^0.4.3": version: 0.4.3 @@ -380,145 +363,124 @@ __metadata: languageName: node linkType: hard -"@agoric/time@npm:0.3.3-dev-5676146.0+5676146": - version: 0.3.3-dev-5676146.0 - resolution: "@agoric/time@npm:0.3.3-dev-5676146.0" +"@agoric/time@portal:../../agoric-sdk/packages/time::locator=root-workspace-0b6124%40workspace%3A.": + version: 0.0.0-use.local + resolution: "@agoric/time@portal:../../agoric-sdk/packages/time::locator=root-workspace-0b6124%40workspace%3A." dependencies: - "@agoric/assert": "npm:0.6.1-dev-5676146.0+5676146" - "@endo/nat": "npm:^5.0.4" - "@endo/patterns": "npm:^1.2.0" - checksum: 10c0/a221f90a327ffaf9eccc6943b1f59b97b200df3a9932b9da7aee484f938e919302069b056182035d6681ebb3b70759841bcf221549f91f172f89848372efe30a + "@agoric/store": "npm:^0.9.2" + "@endo/errors": "npm:^1.2.8" + "@endo/nat": "npm:^5.0.13" + "@endo/patterns": "npm:^1.4.7" languageName: node - linkType: hard + linkType: soft -"@agoric/vat-data@npm:0.5.3-dev-5676146.0+5676146": - version: 0.5.3-dev-5676146.0 - resolution: "@agoric/vat-data@npm:0.5.3-dev-5676146.0" +"@agoric/vat-data@portal:../../agoric-sdk/packages/vat-data::locator=root-workspace-0b6124%40workspace%3A.": + version: 0.0.0-use.local + resolution: "@agoric/vat-data@portal:../../agoric-sdk/packages/vat-data::locator=root-workspace-0b6124%40workspace%3A." dependencies: - "@agoric/assert": "npm:0.6.1-dev-5676146.0+5676146" - "@agoric/base-zone": "npm:0.1.1-dev-5676146.0+5676146" - "@agoric/internal": "npm:0.3.3-dev-5676146.0+5676146" - "@agoric/store": "npm:0.9.3-dev-5676146.0+5676146" - "@agoric/swingset-liveslots": "npm:0.10.3-dev-5676146.0+5676146" - "@agoric/vow": "npm:0.1.1-dev-5676146.0+5676146" - checksum: 10c0/2c08e571cf1ab9af2dc1214c1d7fb9b73446ed9ddaca3a10db2b90160138c07728a0d37cfc9748a37dd424a2945da706bfecc152b2b87fbb59e81bdafaba0e77 + "@agoric/base-zone": "npm:^0.1.0" + "@agoric/store": "npm:^0.9.2" + "@agoric/swingset-liveslots": "npm:^0.10.2" + "@endo/errors": "npm:^1.2.8" + "@endo/exo": "npm:^1.5.7" + "@endo/patterns": "npm:^1.4.7" languageName: node - linkType: hard + linkType: soft -"@agoric/vats@npm:0.15.2-dev-5676146.0+5676146": - version: 0.15.2-dev-5676146.0 - resolution: "@agoric/vats@npm:0.15.2-dev-5676146.0" - dependencies: - "@agoric/assert": "npm:0.6.1-dev-5676146.0+5676146" - "@agoric/ertp": "npm:0.16.3-dev-5676146.0+5676146" - "@agoric/governance": "npm:0.10.4-dev-5676146.0+5676146" - "@agoric/internal": "npm:0.3.3-dev-5676146.0+5676146" - "@agoric/network": "npm:0.1.1-dev-5676146.0+5676146" - "@agoric/notifier": "npm:0.6.3-dev-5676146.0+5676146" - "@agoric/store": "npm:0.9.3-dev-5676146.0+5676146" - "@agoric/swingset-vat": "npm:0.32.3-dev-5676146.0+5676146" - "@agoric/time": "npm:0.3.3-dev-5676146.0+5676146" - "@agoric/vat-data": "npm:0.5.3-dev-5676146.0+5676146" - "@agoric/zoe": "npm:0.26.3-dev-5676146.0+5676146" - "@agoric/zone": "npm:0.2.3-dev-5676146.0+5676146" - "@endo/far": "npm:^1.0.4" - "@endo/import-bundle": "npm:^1.0.4" - "@endo/marshal": "npm:^1.3.0" - "@endo/nat": "npm:^5.0.4" - "@endo/patterns": "npm:^1.2.0" - "@endo/promise-kit": "npm:^1.0.4" +"@agoric/vats@portal:../../agoric-sdk/packages/vats::locator=root-workspace-0b6124%40workspace%3A.": + version: 0.0.0-use.local + resolution: "@agoric/vats@portal:../../agoric-sdk/packages/vats::locator=root-workspace-0b6124%40workspace%3A." + dependencies: + "@agoric/cosmic-proto": "npm:^0.4.0" + "@agoric/ertp": "npm:^0.16.2" + "@agoric/governance": "npm:^0.10.3" + "@agoric/internal": "npm:^0.3.2" + "@agoric/network": "npm:^0.1.0" + "@agoric/notifier": "npm:^0.6.2" + "@agoric/store": "npm:^0.9.2" + "@agoric/swingset-vat": "npm:^0.32.2" + "@agoric/time": "npm:^0.3.2" + "@agoric/vat-data": "npm:^0.5.2" + "@agoric/vow": "npm:^0.1.0" + "@agoric/zoe": "npm:^0.26.2" + "@agoric/zone": "npm:^0.2.2" + "@endo/errors": "npm:^1.2.8" + "@endo/far": "npm:^1.1.9" + "@endo/import-bundle": "npm:^1.3.2" + "@endo/marshal": "npm:^1.6.2" + "@endo/nat": "npm:^5.0.13" + "@endo/pass-style": "npm:^1.4.7" + "@endo/patterns": "npm:^1.4.7" + "@endo/promise-kit": "npm:^1.1.8" import-meta-resolve: "npm:^2.2.1" - jessie.js: "npm:^0.3.2" - checksum: 10c0/ac5117f609b112bf8902488d4769c3f6670cc3402cbe8e75db1c8f227f25e4334b5b447d4fa29cfe674e6d3b93554cdfd3d5858dff6c5b48f89b6e24af636da4 + jessie.js: "npm:^0.3.4" languageName: node - linkType: hard + linkType: soft -"@agoric/vow@npm:0.1.1-dev-5676146.0+5676146": - version: 0.1.1-dev-5676146.0 - resolution: "@agoric/vow@npm:0.1.1-dev-5676146.0" +"@agoric/vow@portal:../../agoric-sdk/packages/vow::locator=root-workspace-0b6124%40workspace%3A.": + version: 0.0.0-use.local + resolution: "@agoric/vow@portal:../../agoric-sdk/packages/vow::locator=root-workspace-0b6124%40workspace%3A." dependencies: - "@agoric/base-zone": "npm:0.1.1-dev-5676146.0+5676146" - "@endo/env-options": "npm:^1.1.1" - "@endo/eventual-send": "npm:^1.1.2" - "@endo/pass-style": "npm:^1.2.0" - "@endo/patterns": "npm:^1.2.0" - "@endo/promise-kit": "npm:^1.0.4" - checksum: 10c0/e0aa219b31e962b784bf4c48a2108b032aecf60c7cf05393e305c0279abee887a81879ca6999eb56cbaedebc656d7d575715ba5c470dd624f62304624475de60 + "@agoric/base-zone": "npm:^0.1.0" + "@agoric/internal": "npm:^0.3.2" + "@endo/env-options": "npm:^1.1.8" + "@endo/errors": "npm:^1.2.8" + "@endo/eventual-send": "npm:^1.2.8" + "@endo/pass-style": "npm:^1.4.7" + "@endo/patterns": "npm:^1.4.7" + "@endo/promise-kit": "npm:^1.1.8" languageName: node - linkType: hard + linkType: soft -"@agoric/xsnap-lockdown@npm:0.14.1-dev-5676146.0+5676146": - version: 0.14.1-dev-5676146.0 - resolution: "@agoric/xsnap-lockdown@npm:0.14.1-dev-5676146.0" - checksum: 10c0/8faa700ff6049b9cd29109c42e2ef3b228f18e265a5908e987af4ee32127e9b6451b7299538ec8fa50514c359f2b0b9a60beb6a5d2e126928def1e5232a3d919 +"@agoric/xsnap-lockdown@portal:../../agoric-sdk/packages/xsnap-lockdown::locator=root-workspace-0b6124%40workspace%3A.": + version: 0.0.0-use.local + resolution: "@agoric/xsnap-lockdown@portal:../../agoric-sdk/packages/xsnap-lockdown::locator=root-workspace-0b6124%40workspace%3A." languageName: node - linkType: hard + linkType: soft -"@agoric/xsnap@npm:0.14.3-dev-5676146.0+5676146": - version: 0.14.3-dev-5676146.0 - resolution: "@agoric/xsnap@npm:0.14.3-dev-5676146.0" - dependencies: - "@agoric/assert": "npm:0.6.1-dev-5676146.0+5676146" - "@agoric/internal": "npm:0.3.3-dev-5676146.0+5676146" - "@agoric/xsnap-lockdown": "npm:0.14.1-dev-5676146.0+5676146" - "@endo/bundle-source": "npm:^3.1.0" - "@endo/eventual-send": "npm:^1.1.2" - "@endo/init": "npm:^1.0.4" - "@endo/netstring": "npm:^1.0.4" - "@endo/promise-kit": "npm:^1.0.4" - "@endo/stream": "npm:^1.1.0" - "@endo/stream-node": "npm:^1.0.4" - glob: "npm:^7.1.6" - tmp: "npm:^0.2.1" - bin: - ava-xs: src/ava-xs.js - xsrepl: src/xsrepl - checksum: 10c0/0f5461b8c5cafa94388720cdcbd5b9fc65e0f2416d9084e3e90b60728cf050fcd95c009a67fda284cee2471058814ba504e655e0a3de82cbbc36e03c24e9fc50 - languageName: node - linkType: hard - -"@agoric/zoe@npm:0.26.3-dev-5676146.0+5676146": - version: 0.26.3-dev-5676146.0 - resolution: "@agoric/zoe@npm:0.26.3-dev-5676146.0" - dependencies: - "@agoric/assert": "npm:0.6.1-dev-5676146.0+5676146" - "@agoric/base-zone": "npm:0.1.1-dev-5676146.0+5676146" - "@agoric/ertp": "npm:0.16.3-dev-5676146.0+5676146" - "@agoric/internal": "npm:0.3.3-dev-5676146.0+5676146" - "@agoric/notifier": "npm:0.6.3-dev-5676146.0+5676146" - "@agoric/store": "npm:0.9.3-dev-5676146.0+5676146" - "@agoric/swingset-liveslots": "npm:0.10.3-dev-5676146.0+5676146" - "@agoric/swingset-vat": "npm:0.32.3-dev-5676146.0+5676146" - "@agoric/time": "npm:0.3.3-dev-5676146.0+5676146" - "@agoric/vat-data": "npm:0.5.3-dev-5676146.0+5676146" - "@agoric/zone": "npm:0.2.3-dev-5676146.0+5676146" - "@endo/bundle-source": "npm:^3.1.0" - "@endo/captp": "npm:^4.0.4" - "@endo/common": "npm:^1.1.0" - "@endo/eventual-send": "npm:^1.1.2" - "@endo/exo": "npm:^1.2.1" - "@endo/far": "npm:^1.0.4" - "@endo/import-bundle": "npm:^1.0.4" - "@endo/marshal": "npm:^1.3.0" - "@endo/nat": "npm:^5.0.4" - "@endo/patterns": "npm:^1.2.0" - "@endo/promise-kit": "npm:^1.0.4" +"@agoric/zoe@portal:../../agoric-sdk/packages/zoe::locator=root-workspace-0b6124%40workspace%3A.": + version: 0.0.0-use.local + resolution: "@agoric/zoe@portal:../../agoric-sdk/packages/zoe::locator=root-workspace-0b6124%40workspace%3A." + dependencies: + "@agoric/base-zone": "npm:^0.1.0" + "@agoric/ertp": "npm:^0.16.2" + "@agoric/internal": "npm:^0.3.2" + "@agoric/notifier": "npm:^0.6.2" + "@agoric/store": "npm:^0.9.2" + "@agoric/swingset-liveslots": "npm:^0.10.2" + "@agoric/swingset-vat": "npm:^0.32.2" + "@agoric/time": "npm:^0.3.2" + "@agoric/vat-data": "npm:^0.5.2" + "@agoric/vow": "npm:^0.1.0" + "@agoric/zone": "npm:^0.2.2" + "@endo/bundle-source": "npm:^3.5.0" + "@endo/captp": "npm:^4.4.3" + "@endo/common": "npm:^1.2.8" + "@endo/errors": "npm:^1.2.8" + "@endo/eventual-send": "npm:^1.2.8" + "@endo/exo": "npm:^1.5.7" + "@endo/far": "npm:^1.1.9" + "@endo/import-bundle": "npm:^1.3.2" + "@endo/marshal": "npm:^1.6.2" + "@endo/nat": "npm:^5.0.13" + "@endo/pass-style": "npm:^1.4.7" + "@endo/patterns": "npm:^1.4.7" + "@endo/promise-kit": "npm:^1.1.8" yargs-parser: "npm:^21.1.1" - checksum: 10c0/4db929e776483dd41c0453d322fe93d27d35826ab98e31e257314e41f2eb6c86eb2a1da09761790bbc5f2bfa41a348ef5c84534044b6d1de576eca1ecea31a82 languageName: node - linkType: hard + linkType: soft -"@agoric/zone@npm:0.2.3-dev-5676146.0+5676146": - version: 0.2.3-dev-5676146.0 - resolution: "@agoric/zone@npm:0.2.3-dev-5676146.0" +"@agoric/zone@portal:../../agoric-sdk/packages/zone::locator=root-workspace-0b6124%40workspace%3A.": + version: 0.0.0-use.local + resolution: "@agoric/zone@portal:../../agoric-sdk/packages/zone::locator=root-workspace-0b6124%40workspace%3A." dependencies: - "@agoric/base-zone": "npm:0.1.1-dev-5676146.0+5676146" - "@agoric/vat-data": "npm:0.5.3-dev-5676146.0+5676146" - "@endo/far": "npm:^1.0.4" - "@endo/pass-style": "npm:^1.2.0" - checksum: 10c0/82a7f1c741bb1c6bfca6398686e71b47135ee584f794dbbfc01ecdb37aea37a2607d857532caefd5c61a03f90a3fb7ac02374c189d4510b759209276f631a8d6 + "@agoric/base-zone": "npm:^0.1.0" + "@agoric/vat-data": "npm:^0.5.2" + "@endo/errors": "npm:^1.2.8" + "@endo/far": "npm:^1.1.9" + "@endo/pass-style": "npm:^1.4.7" languageName: node - linkType: hard + linkType: soft "@babel/code-frame@npm:^7.23.5": version: 7.23.5 @@ -873,14 +835,14 @@ __metadata: languageName: node linkType: hard -"@endo/base64@npm:^1.0.2, @endo/base64@npm:^1.0.9": +"@endo/base64@npm:^1.0.9": version: 1.0.9 resolution: "@endo/base64@npm:1.0.9" checksum: 10c0/63e487cf59b50a080fab389a8ab24d66264910ecf375dc19677c2ee7421d92a4be9c85e435b216b4adc9983384073a7eb753223f85ba77aec8d9fd3e0c1fe090 languageName: node linkType: hard -"@endo/bundle-source@npm:^3.1.0": +"@endo/bundle-source@npm:^3.5.0": version: 3.5.0 resolution: "@endo/bundle-source@npm:3.5.0" dependencies: @@ -902,7 +864,7 @@ __metadata: languageName: node linkType: hard -"@endo/captp@npm:^4.0.4": +"@endo/captp@npm:^4.4.3": version: 4.4.3 resolution: "@endo/captp@npm:4.4.3" dependencies: @@ -915,7 +877,7 @@ __metadata: languageName: node linkType: hard -"@endo/check-bundle@npm:^1.0.4": +"@endo/check-bundle@npm:^1.0.12": version: 1.0.12 resolution: "@endo/check-bundle@npm:1.0.12" dependencies: @@ -933,7 +895,7 @@ __metadata: languageName: node linkType: hard -"@endo/common@npm:^1.1.0, @endo/common@npm:^1.2.8": +"@endo/common@npm:^1.2.8": version: 1.2.8 resolution: "@endo/common@npm:1.2.8" dependencies: @@ -944,7 +906,7 @@ __metadata: languageName: node linkType: hard -"@endo/compartment-mapper@npm:^1.1.2, @endo/compartment-mapper@npm:^1.4.0": +"@endo/compartment-mapper@npm:^1.4.0": version: 1.4.0 resolution: "@endo/compartment-mapper@npm:1.4.0" dependencies: @@ -957,21 +919,14 @@ __metadata: languageName: node linkType: hard -"@endo/env-options@npm:^0.1.4": - version: 0.1.4 - resolution: "@endo/env-options@npm:0.1.4" - checksum: 10c0/5bf49d362849090bff328b15f906adb5b8b6220815e8955e45f81e7ff9a8ab17e509fff8bf30f4c619772f4f1a8cba8f1ca90faec724b53b5b3f1c89050c6b44 - languageName: node - linkType: hard - -"@endo/env-options@npm:^1.1.1, @endo/env-options@npm:^1.1.8": +"@endo/env-options@npm:^1.1.8": version: 1.1.8 resolution: "@endo/env-options@npm:1.1.8" checksum: 10c0/2f519f48a5b966dbd9e66134d4abc89ff02b9791d21146b49031ceb694584f3f41c6119125b6bb4eb0d347f5bcd846473b5f3c4ae6bae3dac19402fcaf522520 languageName: node linkType: hard -"@endo/errors@npm:^1.1.0, @endo/errors@npm:^1.2.2, @endo/errors@npm:^1.2.8": +"@endo/errors@npm:^1.2.2, @endo/errors@npm:^1.2.8": version: 1.2.8 resolution: "@endo/errors@npm:1.2.8" dependencies: @@ -992,16 +947,7 @@ __metadata: languageName: node linkType: hard -"@endo/eventual-send@npm:^0.17.6": - version: 0.17.6 - resolution: "@endo/eventual-send@npm:0.17.6" - dependencies: - "@endo/env-options": "npm:^0.1.4" - checksum: 10c0/3a8dae48e06ad3a8fdad074d0b6b10ced09f1e440f04f802d98372243ed8ead97278d85d4aa4a310dee34bc7146f09e7aaf6d01b7c06cbe3f8610544c97b5ce2 - languageName: node - linkType: hard - -"@endo/eventual-send@npm:^1.1.2, @endo/eventual-send@npm:^1.2.8": +"@endo/eventual-send@npm:^1.2.8": version: 1.2.8 resolution: "@endo/eventual-send@npm:1.2.8" dependencies: @@ -1010,7 +956,7 @@ __metadata: languageName: node linkType: hard -"@endo/exo@npm:^1.2.1": +"@endo/exo@npm:^1.5.7": version: 1.5.7 resolution: "@endo/exo@npm:1.5.7" dependencies: @@ -1025,17 +971,7 @@ __metadata: languageName: node linkType: hard -"@endo/far@npm:^0.2.3": - version: 0.2.22 - resolution: "@endo/far@npm:0.2.22" - dependencies: - "@endo/eventual-send": "npm:^0.17.6" - "@endo/pass-style": "npm:^0.1.7" - checksum: 10c0/bd30a168b47a26014cab296336a64aa2721975c386f7f87b6776dd33cf77f3e85ddb822e8422fbc2befb6920d72301e3b9b206fe71d970dce1870b708b09805d - languageName: node - linkType: hard - -"@endo/far@npm:^1.0.4, @endo/far@npm:^1.1.9": +"@endo/far@npm:^1.0.0, @endo/far@npm:^1.0.4, @endo/far@npm:^1.1.9": version: 1.1.9 resolution: "@endo/far@npm:1.1.9" dependencies: @@ -1046,7 +982,7 @@ __metadata: languageName: node linkType: hard -"@endo/import-bundle@npm:^1.0.4": +"@endo/import-bundle@npm:^1.3.2": version: 1.3.2 resolution: "@endo/import-bundle@npm:1.3.2" dependencies: @@ -1059,7 +995,7 @@ __metadata: languageName: node linkType: hard -"@endo/init@npm:^1.0.3, @endo/init@npm:^1.0.4, @endo/init@npm:^1.1.7": +"@endo/init@npm:^1.0.4, @endo/init@npm:^1.1.7": version: 1.1.7 resolution: "@endo/init@npm:1.1.7" dependencies: @@ -1071,7 +1007,7 @@ __metadata: languageName: node linkType: hard -"@endo/lockdown@npm:^1.0.13, @endo/lockdown@npm:^1.0.4": +"@endo/lockdown@npm:^1.0.13": version: 1.0.13 resolution: "@endo/lockdown@npm:1.0.13" dependencies: @@ -1080,7 +1016,7 @@ __metadata: languageName: node linkType: hard -"@endo/marshal@npm:^1.3.0, @endo/marshal@npm:^1.6.2": +"@endo/marshal@npm:^1.6.2": version: 1.6.2 resolution: "@endo/marshal@npm:1.6.2" dependencies: @@ -1107,36 +1043,14 @@ __metadata: languageName: node linkType: hard -"@endo/nat@npm:^5.0.13, @endo/nat@npm:^5.0.4": +"@endo/nat@npm:^5.0.13": version: 5.0.13 resolution: "@endo/nat@npm:5.0.13" checksum: 10c0/78578de4567c9bc4c6f50638c688886c07c38177a8d44192230d344221da06ccffc6d9ef8d423e27198d864ed7c57ef5ced9b1d05922eaa4e40bf82856b1aa11 languageName: node linkType: hard -"@endo/netstring@npm:^1.0.4": - version: 1.0.13 - resolution: "@endo/netstring@npm:1.0.13" - dependencies: - "@endo/init": "npm:^1.1.7" - "@endo/promise-kit": "npm:^1.1.8" - "@endo/stream": "npm:^1.2.8" - ses: "npm:^1.10.0" - checksum: 10c0/1d669ffca92609b3e179bd235c3660ef2fd36a808d4df523fdd6c276cd2a47e2177c43a4e37b4bfb8cacfd1b4e1657cec7d197518c795652c8c248997ee59948 - languageName: node - linkType: hard - -"@endo/pass-style@npm:^0.1.7": - version: 0.1.7 - resolution: "@endo/pass-style@npm:0.1.7" - dependencies: - "@endo/promise-kit": "npm:^0.2.60" - "@fast-check/ava": "npm:^1.1.5" - checksum: 10c0/0fc8ca918e4b2888619fa10765b9a414f1ab921b590f257421f4af4a523b80b2afc736280691ed99e8f8807ead3afc478c1a855772c52a4c8fbe43733f3fe656 - languageName: node - linkType: hard - -"@endo/pass-style@npm:^1.2.0, @endo/pass-style@npm:^1.4.7": +"@endo/pass-style@npm:^1.4.7": version: 1.4.7 resolution: "@endo/pass-style@npm:1.4.7" dependencies: @@ -1149,7 +1063,7 @@ __metadata: languageName: node linkType: hard -"@endo/patterns@npm:^1.1.0, @endo/patterns@npm:^1.2.0, @endo/patterns@npm:^1.4.7": +"@endo/patterns@npm:^1.4.7": version: 1.4.7 resolution: "@endo/patterns@npm:1.4.7" dependencies: @@ -1162,16 +1076,7 @@ __metadata: languageName: node linkType: hard -"@endo/promise-kit@npm:^0.2.60": - version: 0.2.60 - resolution: "@endo/promise-kit@npm:0.2.60" - dependencies: - ses: "npm:^0.18.8" - checksum: 10c0/45fa191d0211cf9e99a6b300c373849c7662e8832e20fbcfa4a8f4938d9c9509f22c3a76377629be70447adc1d2e4e99a56a99395af19ba2a0c1010bfe1da4dd - languageName: node - linkType: hard - -"@endo/promise-kit@npm:^1.0.4, @endo/promise-kit@npm:^1.1.8": +"@endo/promise-kit@npm:^1.1.8": version: 1.1.8 resolution: "@endo/promise-kit@npm:1.1.8" dependencies: @@ -1180,7 +1085,7 @@ __metadata: languageName: node linkType: hard -"@endo/ses-ava@npm:^1.1.2": +"@endo/ses-ava@npm:^1.2.8": version: 1.2.8 resolution: "@endo/ses-ava@npm:1.2.8" dependencies: @@ -1193,19 +1098,7 @@ __metadata: languageName: node linkType: hard -"@endo/stream-node@npm:^1.0.4": - version: 1.1.8 - resolution: "@endo/stream-node@npm:1.1.8" - dependencies: - "@endo/errors": "npm:^1.2.8" - "@endo/init": "npm:^1.1.7" - "@endo/stream": "npm:^1.2.8" - ses: "npm:^1.10.0" - checksum: 10c0/d07769acf381b4b5a904bfdae1b7aba0b7cb11f8ed1a38892a072b68e3dd8eb1954c77984a6eb7af09006ad5e707a8aa4e2c5d4424eb6898beae9ceb0015d8e3 - languageName: node - linkType: hard - -"@endo/stream@npm:^1.1.0, @endo/stream@npm:^1.2.8": +"@endo/stream@npm:^1.2.8": version: 1.2.8 resolution: "@endo/stream@npm:1.2.8" dependencies: @@ -1230,7 +1123,7 @@ __metadata: languageName: node linkType: hard -"@endo/zip@npm:^1.0.2, @endo/zip@npm:^1.0.7, @endo/zip@npm:^1.0.9": +"@endo/zip@npm:^1.0.7, @endo/zip@npm:^1.0.9": version: 1.0.9 resolution: "@endo/zip@npm:1.0.9" checksum: 10c0/3fccea31bd5dad938a3b5f531454d3c49513892d6d5aba1f0af1034ff0ae54c3e28a346a9df08bd9e5201354acccd631e45c9c0e68fa2848a876a3919f3830dc @@ -1651,48 +1544,50 @@ __metadata: languageName: node linkType: hard -"agoric@npm:0.21.2-dev-5676146.0": - version: 0.21.2-dev-5676146.0 - resolution: "agoric@npm:0.21.2-dev-5676146.0" - dependencies: - "@agoric/access-token": "npm:0.4.22-dev-5676146.0+5676146" - "@agoric/assert": "npm:0.6.1-dev-5676146.0+5676146" - "@agoric/cache": "npm:0.3.3-dev-5676146.0+5676146" - "@agoric/casting": "npm:0.4.3-dev-5676146.0+5676146" - "@agoric/cosmic-proto": "npm:0.4.1-dev-5676146.0+5676146" - "@agoric/ertp": "npm:0.16.3-dev-5676146.0+5676146" - "@agoric/governance": "npm:0.10.4-dev-5676146.0+5676146" - "@agoric/inter-protocol": "npm:0.16.2-dev-5676146.0+5676146" - "@agoric/internal": "npm:0.3.3-dev-5676146.0+5676146" - "@agoric/network": "npm:0.1.1-dev-5676146.0+5676146" - "@agoric/smart-wallet": "npm:0.5.4-dev-5676146.0+5676146" - "@agoric/store": "npm:0.9.3-dev-5676146.0+5676146" - "@agoric/swingset-vat": "npm:0.32.3-dev-5676146.0+5676146" - "@agoric/vats": "npm:0.15.2-dev-5676146.0+5676146" - "@agoric/zoe": "npm:0.26.3-dev-5676146.0+5676146" - "@agoric/zone": "npm:0.2.3-dev-5676146.0+5676146" +"agoric@portal:../../agoric-sdk/packages/agoric-cli::locator=root-workspace-0b6124%40workspace%3A.": + version: 0.0.0-use.local + resolution: "agoric@portal:../../agoric-sdk/packages/agoric-cli::locator=root-workspace-0b6124%40workspace%3A." + dependencies: + "@agoric/access-token": "npm:^0.4.21" + "@agoric/cache": "npm:^0.3.2" + "@agoric/casting": "npm:^0.4.2" + "@agoric/client-utils": "npm:^0.1.0" + "@agoric/cosmic-proto": "npm:^0.4.0" + "@agoric/ertp": "npm:^0.16.2" + "@agoric/governance": "npm:^0.10.3" + "@agoric/inter-protocol": "npm:^0.16.1" + "@agoric/internal": "npm:^0.3.2" + "@agoric/network": "npm:^0.1.0" + "@agoric/smart-wallet": "npm:^0.5.3" + "@agoric/store": "npm:^0.9.2" + "@agoric/swingset-vat": "npm:^0.32.2" + "@agoric/vats": "npm:^0.15.1" + "@agoric/zoe": "npm:^0.26.2" + "@agoric/zone": "npm:^0.2.2" "@confio/relayer": "npm:^0.11.3" "@cosmjs/crypto": "npm:^0.32.3" "@cosmjs/encoding": "npm:^0.32.3" "@cosmjs/math": "npm:^0.32.3" "@cosmjs/proto-signing": "npm:^0.32.3" "@cosmjs/stargate": "npm:^0.32.3" - "@endo/bundle-source": "npm:^3.1.0" - "@endo/captp": "npm:^4.0.4" - "@endo/compartment-mapper": "npm:^1.1.2" - "@endo/env-options": "npm:^1.1.1" - "@endo/far": "npm:^1.0.4" - "@endo/init": "npm:^1.0.4" - "@endo/marshal": "npm:^1.3.0" - "@endo/nat": "npm:^5.0.4" - "@endo/patterns": "npm:^1.2.0" - "@endo/promise-kit": "npm:^1.0.4" + "@endo/bundle-source": "npm:^3.5.0" + "@endo/captp": "npm:^4.4.3" + "@endo/compartment-mapper": "npm:^1.4.0" + "@endo/env-options": "npm:^1.1.8" + "@endo/errors": "npm:^1.2.8" + "@endo/far": "npm:^1.1.9" + "@endo/init": "npm:^1.1.7" + "@endo/marshal": "npm:^1.6.2" + "@endo/nat": "npm:^5.0.13" + "@endo/patterns": "npm:^1.4.7" + "@endo/promise-kit": "npm:^1.1.8" + "@endo/zip": "npm:^1.0.9" "@iarna/toml": "npm:^2.2.3" anylogger: "npm:^0.21.0" chalk: "npm:^5.2.0" - commander: "npm:^11.1.0" + commander: "npm:^12.1.0" deterministic-json: "npm:^1.0.5" - esm: "github:agoric-labs/esm#Agoric-built" + esm: "agoric-labs/esm#Agoric-built" inquirer: "npm:^8.2.2" opener: "npm:^1.5.2" tmp: "npm:^0.2.1" @@ -1700,9 +1595,8 @@ __metadata: bin: agops: src/bin-agops.js agoric: src/entrypoint.js - checksum: 10c0/abcea0bfd4594c2841d3e69ed6c78bedd5a4c573efa9ebcb34730e87ea445ab283e06a7dff2a0f44834faae3bb4dfc0153a2bd34cfd859064208cd7bfb92a19b languageName: node - linkType: hard + linkType: soft "ajv@npm:7.1.1": version: 7.1.1 @@ -2369,10 +2263,10 @@ __metadata: languageName: node linkType: hard -"commander@npm:^11.1.0": - version: 11.1.0 - resolution: "commander@npm:11.1.0" - checksum: 10c0/13cc6ac875e48780250f723fb81c1c1178d35c5decb1abb1b628b3177af08a8554e76b2c0f29de72d69eef7c864d12613272a71fabef8047922bc622ab75a179 +"commander@npm:^12.1.0": + version: 12.1.0 + resolution: "commander@npm:12.1.0" + checksum: 10c0/6e1996680c083b3b897bfc1cfe1c58dfbcd9842fd43e1aaf8a795fbc237f65efcc860a3ef457b318e73f29a4f4a28f6403c3d653d021d960e4632dd45bde54a9 languageName: node linkType: hard @@ -2680,7 +2574,7 @@ __metadata: languageName: node linkType: hard -"esm@github:agoric-labs/esm#Agoric-built": +"esm@agoric-labs/esm#Agoric-built": version: 3.2.25 resolution: "esm@https://github.com/agoric-labs/esm.git#commit=3603726ad4636b2f865f463188fcaade6375638e" checksum: 10c0/fc1e112a3a681e7b4152d4f5c76dd5aa9e30496d2020490ffa0fb61aaf57d1e12dae0c1074fdd2e0f08949ab2df7e00e750262356781f072e4119955ee10b754 @@ -3566,12 +3460,12 @@ __metadata: languageName: node linkType: hard -"jessie.js@npm:^0.3.2": - version: 0.3.3 - resolution: "jessie.js@npm:0.3.3" +"jessie.js@npm:^0.3.4": + version: 0.3.4 + resolution: "jessie.js@npm:0.3.4" dependencies: - "@endo/far": "npm:^0.2.3" - checksum: 10c0/883897ce3e8e8608f324efcffac9a1e445315cadd88935f2d09bad7fb180806ae1352e7332e99c84b7c097f9ac03bd7cb45dfc46a5d276871031d0c43f9cad51 + "@endo/far": "npm:^1.0.0" + checksum: 10c0/853ab3f8a0e30df11742882f5e11479d1303033a5a203a247d8ffbf4c6f3f3d4bcbefa53084ae4632e6ab106e348f23dc988280486cbeaaf5d16487fa3d40e96 languageName: node linkType: hard @@ -4083,20 +3977,6 @@ __metadata: languageName: node linkType: hard -"node-fetch@npm:^2.6.0": - version: 2.7.0 - resolution: "node-fetch@npm:2.7.0" - dependencies: - whatwg-url: "npm:^5.0.0" - peerDependencies: - encoding: ^0.1.0 - peerDependenciesMeta: - encoding: - optional: true - checksum: 10c0/b55786b6028208e6fbe594ccccc213cab67a72899c9234eb59dba51062a299ea853210fcf526998eaa2867b0963ad72338824450905679ff0fa304b8c5093ae8 - languageName: node - linkType: hard - "node-gyp-build@npm:^4.4.0": version: 4.8.0 resolution: "node-gyp-build@npm:4.8.0" @@ -4691,6 +4571,7 @@ __metadata: version: 0.0.0-use.local resolution: "root-workspace-0b6124@workspace:." dependencies: + "@agoric/client-utils": "npm:dev" "@agoric/internal": "npm:0.3.3-dev-5676146.0" "@agoric/synthetic-chain": "npm:^0.4.3" "@cosmjs/stargate": "npm:^0.32.3" @@ -4699,7 +4580,7 @@ __metadata: "@endo/far": "npm:^1.0.4" "@endo/init": "npm:^1.0.4" "@types/node": "npm:^22.0.0" - agoric: "npm:0.21.2-dev-5676146.0" + agoric: "npm:dev" ava: "npm:^5.3.1" execa: "npm:^8.0.1" languageName: unknown @@ -4780,15 +4661,6 @@ __metadata: languageName: node linkType: hard -"ses@npm:^0.18.8": - version: 0.18.8 - resolution: "ses@npm:0.18.8" - dependencies: - "@endo/env-options": "npm:^0.1.4" - checksum: 10c0/2c5c5e40f6a8edee081e1c62b65316128823070a68858c6ee45810fb14464d14a9f82499bf4d1cb274b46e35e199f7c55565755236a708d25ace493da206083f - languageName: node - linkType: hard - "ses@npm:^1.10.0": version: 1.10.0 resolution: "ses@npm:1.10.0" @@ -5213,13 +5085,6 @@ __metadata: languageName: node linkType: hard -"tr46@npm:~0.0.3": - version: 0.0.3 - resolution: "tr46@npm:0.0.3" - checksum: 10c0/047cb209a6b60c742f05c9d3ace8fa510bff609995c129a37ace03476a9b12db4dbf975e74600830ef0796e18882b2381fb5fb1f6b4f96b832c374de3ab91a11 - languageName: node - linkType: hard - "triple-beam@npm:1.3.0": version: 1.3.0 resolution: "triple-beam@npm:1.3.0" @@ -5357,13 +5222,6 @@ __metadata: languageName: node linkType: hard -"webidl-conversions@npm:^3.0.0": - version: 3.0.1 - resolution: "webidl-conversions@npm:3.0.1" - checksum: 10c0/5612d5f3e54760a797052eb4927f0ddc01383550f542ccd33d5238cfd65aeed392a45ad38364970d0a0f4fea32e1f4d231b3d8dac4a3bdd385e5cf802ae097db - languageName: node - linkType: hard - "well-known-symbols@npm:^2.0.0": version: 2.0.0 resolution: "well-known-symbols@npm:2.0.0" @@ -5371,16 +5229,6 @@ __metadata: languageName: node linkType: hard -"whatwg-url@npm:^5.0.0": - version: 5.0.0 - resolution: "whatwg-url@npm:5.0.0" - dependencies: - tr46: "npm:~0.0.3" - webidl-conversions: "npm:^3.0.0" - checksum: 10c0/1588bed84d10b72d5eec1d0faa0722ba1962f1821e7539c535558fb5398d223b0c50d8acab950b8c488b4ba69043fd833cc2697056b167d8ad46fac3995a55d5 - languageName: node - linkType: hard - "which@npm:^2.0.1": version: 2.0.2 resolution: "which@npm:2.0.2" From 3ce6d566f63aa8087cf01f613392a1362a913e3a Mon Sep 17 00:00:00 2001 From: Turadg Aleahmad Date: Tue, 3 Dec 2024 07:48:58 -0800 Subject: [PATCH 40/56] refactor: use agoric cli lib --- .../proposals/s:stake-bld/test-lib/chain.js | 140 --------- .../proposals/s:stake-bld/test-lib/index.js | 6 +- .../proposals/s:stake-bld/test-lib/rpc.js | 266 ------------------ .../proposals/s:stake-bld/test-lib/wallet.js | 57 +--- 4 files changed, 4 insertions(+), 465 deletions(-) delete mode 100644 a3p-integration/proposals/s:stake-bld/test-lib/chain.js delete mode 100644 a3p-integration/proposals/s:stake-bld/test-lib/rpc.js diff --git a/a3p-integration/proposals/s:stake-bld/test-lib/chain.js b/a3p-integration/proposals/s:stake-bld/test-lib/chain.js deleted file mode 100644 index 74cc0d3c14f..00000000000 --- a/a3p-integration/proposals/s:stake-bld/test-lib/chain.js +++ /dev/null @@ -1,140 +0,0 @@ -/** @file copied from packages/agoric-cli */ -// TODO DRY in https://github.com/Agoric/agoric-sdk/issues/9109 -// @ts-check -/* global process */ - -const agdBinary = 'agd'; - -/** - * @param {ReadonlyArray} swingsetArgs - * @param {import('./rpc.js').MinimalNetworkConfig & { - * from: string, - * fees?: string, - * dryRun?: boolean, - * verbose?: boolean, - * keyring?: {home?: string, backend: string} - * stdout?: Pick - * execFileSync: typeof import('child_process').execFileSync - * }} opts - */ -export const execSwingsetTransaction = (swingsetArgs, opts) => { - const { - from, - fees, - dryRun = false, - verbose = true, - keyring = undefined, - chainName, - rpcAddrs, - stdout = process.stdout, - execFileSync, - } = opts; - const homeOpt = keyring?.home ? [`--home=${keyring.home}`] : []; - const backendOpt = keyring?.backend - ? [`--keyring-backend=${keyring.backend}`] - : []; - const feeOpt = fees ? ['--fees', fees] : []; - const cmd = [`--node=${rpcAddrs[0]}`, `--chain-id=${chainName}`].concat( - homeOpt, - backendOpt, - feeOpt, - [`--from=${from}`, 'tx', 'swingset'], - swingsetArgs, - ); - - if (dryRun) { - stdout.write(`Run this interactive command in shell:\n\n`); - stdout.write(`${agdBinary} `); - stdout.write(cmd.join(' ')); - stdout.write('\n'); - } else { - const yesCmd = cmd.concat(['--yes']); - if (verbose) console.log('Executing ', agdBinary, yesCmd); - const out = execFileSync(agdBinary, yesCmd, { encoding: 'utf-8' }); - - // agd puts this diagnostic on stdout rather than stderr :-/ - // "Default sign-mode 'direct' not supported by Ledger, using sign-mode 'amino-json'. - if (out.startsWith('Default sign-mode')) { - const stripDiagnostic = out.replace(/^Default[^\n]+\n/, ''); - return stripDiagnostic; - } - return out; - } -}; -harden(execSwingsetTransaction); - -/** - * @param {import('./rpc.js').MinimalNetworkConfig & { - * execFileSync: typeof import('child_process').execFileSync, - * delay: (ms: number) => Promise, - * period?: number, - * retryMessage?: string, - * }} opts - * @returns {(l: (b: { time: string, height: string }) => Promise) => Promise} - */ -export const pollBlocks = opts => async lookup => { - const { execFileSync, delay, rpcAddrs, period = 3 * 1000 } = opts; - assert(execFileSync, 'missing execFileSync'); - const { retryMessage } = opts; - - const nodeArgs = [`--node=${rpcAddrs[0]}`]; - - await null; // separate sync prologue - - for (;;) { - const sTxt = execFileSync(agdBinary, ['status', ...nodeArgs]); - const status = JSON.parse(sTxt.toString()); - const { - SyncInfo: { latest_block_time: time, latest_block_height: height }, - } = status; - try { - // see await null above - const result = await lookup({ time, height }); - return result; - } catch (_err) { - console.error( - time, - retryMessage || 'not in block', - height, - 'retrying...', - ); - await delay(period); - } - } -}; - -/** - * @param {string} txhash - * @param {import('./rpc.js').MinimalNetworkConfig & { - * execFileSync: typeof import('child_process').execFileSync, - * delay: (ms: number) => Promise, - * period?: number, - * }} opts - */ -export const pollTx = async (txhash, opts) => { - const { execFileSync, rpcAddrs, chainName } = opts; - assert(execFileSync, 'missing execFileSync in pollTx'); - - const nodeArgs = [`--node=${rpcAddrs[0]}`]; - const outJson = ['--output', 'json']; - - const lookup = async () => { - const out = execFileSync( - agdBinary, - [ - 'query', - 'tx', - txhash, - `--chain-id=${chainName}`, - ...nodeArgs, - ...outJson, - ], - { stdio: ['ignore', 'pipe', 'ignore'] }, - ); - // XXX this type is defined in a .proto file somewhere - /** @type {{ height: string, txhash: string, code: number, timestamp: string }} */ - const info = JSON.parse(out.toString()); - return info; - }; - return pollBlocks({ ...opts, retryMessage: 'tx not in block' })(lookup); -}; diff --git a/a3p-integration/proposals/s:stake-bld/test-lib/index.js b/a3p-integration/proposals/s:stake-bld/test-lib/index.js index a35b9b94fe0..9c22b218e19 100644 --- a/a3p-integration/proposals/s:stake-bld/test-lib/index.js +++ b/a3p-integration/proposals/s:stake-bld/test-lib/index.js @@ -1,11 +1,9 @@ /* eslint-env node */ import { execFileSync } from 'child_process'; +import { LOCAL_CONFIG as networkConfig } from '@agoric/client-utils'; import { makeWalletUtils } from './wallet.js'; -export const networkConfig = { - rpcAddrs: ['http://0.0.0.0:26657'], - chainName: 'agoriclocal', -}; +export { networkConfig }; /** * Resolve after a delay in milliseconds. diff --git a/a3p-integration/proposals/s:stake-bld/test-lib/rpc.js b/a3p-integration/proposals/s:stake-bld/test-lib/rpc.js deleted file mode 100644 index a3ac266ee88..00000000000 --- a/a3p-integration/proposals/s:stake-bld/test-lib/rpc.js +++ /dev/null @@ -1,266 +0,0 @@ -/** @file copied from packages/agoric-cli */ -// TODO DRY in https://github.com/Agoric/agoric-sdk/issues/9109 -// @ts-check -/* eslint-env node */ - -import { Fail } from '@endo/errors'; -import { - boardSlottingMarshaller, - makeBoardRemote, -} from '@agoric/internal/src/marshal.js'; - -export { boardSlottingMarshaller }; - -export const boardValToSlot = val => { - if ('getBoardId' in val) { - return val.getBoardId(); - } - Fail`unknown obj in boardSlottingMarshaller.valToSlot ${val}`; -}; - -export const networkConfigUrl = agoricNetSubdomain => - `https://${agoricNetSubdomain}.agoric.net/network-config`; -export const rpcUrl = agoricNetSubdomain => - `https://${agoricNetSubdomain}.rpc.agoric.net:443`; - -/** - * @typedef {{ rpcAddrs: string[], chainName: string }} MinimalNetworkConfig - */ - -/** @type {MinimalNetworkConfig} */ -const networkConfig = { - rpcAddrs: ['http://0.0.0.0:26657'], - chainName: 'agoriclocal', -}; -export { networkConfig }; -// console.warn('networkConfig', networkConfig); - -/** - * @param {object} powers - * @param {typeof window.fetch} powers.fetch - * @param {MinimalNetworkConfig} config - */ -export const makeVStorage = (powers, config = networkConfig) => { - /** @param {string} path */ - const getJSON = path => { - const url = config.rpcAddrs[0] + path; - // console.warn('fetching', url); - return powers.fetch(url, { keepalive: true }).then(res => res.json()); - }; - // height=0 is the same as omitting height and implies the highest block - const url = (path = 'published', { kind = 'children', height = 0 } = {}) => - `/abci_query?path=%22/custom/vstorage/${kind}/${path}%22&height=${height}`; - - const readStorage = (path = 'published', { kind = 'children', height = 0 }) => - getJSON(url(path, { kind, height })) - .catch(err => { - throw Error(`cannot read ${kind} of ${path}: ${err.message}`); - }) - .then(data => { - const { - result: { response }, - } = data; - if (response?.code !== 0) { - /** @type {any} */ - const err = Error( - `error code ${response?.code} reading ${kind} of ${path}: ${response.log}`, - ); - err.code = response?.code; - err.codespace = response?.codespace; - throw err; - } - return data; - }); - - return { - url, - decode({ result: { response } }) { - const { code } = response; - if (code !== 0) { - throw response; - } - const { value } = response; - return Buffer.from(value, 'base64').toString(); - }, - /** - * - * @param {string} path - * @returns {Promise} latest vstorage value at path - */ - async readLatest(path = 'published') { - const raw = await readStorage(path, { kind: 'data' }); - return this.decode(raw); - }, - async keys(path = 'published') { - const raw = await readStorage(path, { kind: 'children' }); - return JSON.parse(this.decode(raw)).children; - }, - /** - * @param {string} path - * @param {number} [height] default is highest - * @returns {Promise<{blockHeight: number, values: string[]}>} - */ - async readAt(path, height = undefined) { - const raw = await readStorage(path, { kind: 'data', height }); - const txt = this.decode(raw); - /** @type {{ value: string }} */ - const { value } = JSON.parse(txt); - return JSON.parse(value); - }, - /** - * Read values going back as far as available - * - * @param {string} path - * @param {number | string} [minHeight] - * @returns {Promise} - */ - async readFully(path, minHeight = undefined) { - const parts = []; - // undefined the first iteration, to query at the highest - let blockHeight; - await null; - do { - // console.debug('READING', { blockHeight }); - let values; - try { - ({ blockHeight, values } = await this.readAt( - path, - blockHeight && Number(blockHeight) - 1, - )); - // console.debug('readAt returned', { blockHeight }); - } catch (err) { - if ( - // CosmosSDK ErrNotFound; there is no data at the path - (err.codespace === 'sdk' && err.code === 38) || - // CosmosSDK ErrUnknownRequest; misrepresentation of the same until - // https://github.com/Agoric/agoric-sdk/commit/dafc7c1708977aaa55e245dc09a73859cf1df192 - // TODO remove after upgrade-12 - err.message.match(/unknown request/) - ) { - // console.error(err); - break; - } - throw err; - } - parts.push(values); - // console.debug('PUSHED', values); - // console.debug('NEW', { blockHeight, minHeight }); - if (minHeight && Number(blockHeight) <= Number(minHeight)) break; - } while (blockHeight > 0); - return parts.flat(); - }, - }; -}; -/** @typedef {ReturnType} VStorage */ - -export const makeFromBoard = () => { - const cache = new Map(); - const convertSlotToVal = (boardId, iface) => { - if (cache.has(boardId)) { - return cache.get(boardId); - } - const val = makeBoardRemote({ boardId, iface }); - cache.set(boardId, val); - return val; - }; - return harden({ convertSlotToVal }); -}; -/** @typedef {ReturnType} IdMap */ - -export const storageHelper = { - /** @param { string } txt */ - parseCapData: txt => { - assert(typeof txt === 'string', typeof txt); - /** @type {{ value: string }} */ - const { value } = JSON.parse(txt); - const specimen = JSON.parse(value); - const { blockHeight, values } = specimen; - assert(values, `empty values in specimen ${value}`); - const capDatas = storageHelper.parseMany(values); - return { blockHeight, capDatas }; - }, - /** - * @param {string} txt - * @param {IdMap} ctx - */ - unserializeTxt: (txt, ctx) => { - const { capDatas } = storageHelper.parseCapData(txt); - return capDatas.map(capData => - boardSlottingMarshaller(ctx.convertSlotToVal).fromCapData(capData), - ); - }, - /** @param {string[]} capDataStrings array of stringified capData */ - parseMany: capDataStrings => { - assert(capDataStrings && capDataStrings.length); - /** @type {{ body: string, slots: string[] }[]} */ - const capDatas = capDataStrings.map(s => JSON.parse(s)); - for (const capData of capDatas) { - assert(typeof capData === 'object' && capData !== null); - assert('body' in capData && 'slots' in capData); - assert(typeof capData.body === 'string'); - assert(Array.isArray(capData.slots)); - } - return capDatas; - }, -}; -harden(storageHelper); - -/** - * @param {IdMap} ctx - * @param {VStorage} vstorage - * @returns {Promise} - */ -export const makeAgoricNames = async (ctx, vstorage) => { - const reverse = {}; - const entries = await Promise.all( - ['brand', 'instance', 'vbankAsset'].map(async kind => { - const content = await vstorage.readLatest( - `published.agoricNames.${kind}`, - ); - /** @type {Array<[string, import('@agoric/vats/tools/board-utils.js').BoardRemote]>} */ - const parts = storageHelper.unserializeTxt(content, ctx).at(-1); - for (const [name, remote] of parts) { - if ('getBoardId' in remote) { - reverse[remote.getBoardId()] = name; - } - } - return [kind, Object.fromEntries(parts)]; - }), - ); - return { ...Object.fromEntries(entries), reverse }; -}; - -/** - * @param {{ fetch: typeof window.fetch }} io - * @param {MinimalNetworkConfig} config - */ -export const makeVstorageKit = async ({ fetch }, config = networkConfig) => { - await null; - try { - const vstorage = makeVStorage({ fetch }, config); - const fromBoard = makeFromBoard(); - const agoricNames = await makeAgoricNames(fromBoard, vstorage); - - const marshaller = boardSlottingMarshaller(fromBoard.convertSlotToVal); - - /** @type {(txt: string) => unknown} */ - const unserializeHead = txt => - storageHelper.unserializeTxt(txt, fromBoard).at(-1); - - /** @type {(path: string) => Promise} */ - const readLatestHead = path => - vstorage.readLatest(path).then(unserializeHead); - - return { - agoricNames, - fromBoard, - marshaller, - readLatestHead, - unserializeHead, - vstorage, - }; - } catch (err) { - throw Error(`RPC failure (${config.rpcAddrs}): ${err.message}`); - } -}; -/** @typedef {Awaited>} RpcUtils */ diff --git a/a3p-integration/proposals/s:stake-bld/test-lib/wallet.js b/a3p-integration/proposals/s:stake-bld/test-lib/wallet.js index e9461522e1d..e3ef23af929 100644 --- a/a3p-integration/proposals/s:stake-bld/test-lib/wallet.js +++ b/a3p-integration/proposals/s:stake-bld/test-lib/wallet.js @@ -1,61 +1,8 @@ -/** - * @file copied from packages/agoric-cli, - * removing polling and coalescing features whose dependencies cause import problems here - */ -// TODO DRY in https://github.com/Agoric/agoric-sdk/issues/9109 // @ts-check -/* global */ +import { makeVstorageKit } from '@agoric/client-utils'; +import { sendAction } from 'agoric/src/lib/index.js'; import { inspect } from 'util'; -import { execSwingsetTransaction, pollTx } from './chain.js'; -import { makeVstorageKit } from './rpc.js'; - -/** - * Sign and broadcast a wallet-action. - * - * @throws { Error & { code: number } } if transaction fails - * @param {import('@agoric/smart-wallet/src/smartWallet.js').BridgeAction} bridgeAction - * @param {import('./rpc.js').MinimalNetworkConfig & { - * from: string, - * marshaller: import('@endo/marshal').Marshal<'string'>, - * fees?: string, - * verbose?: boolean, - * keyring?: {home?: string, backend: string}, - * stdout: Pick, - * execFileSync: typeof import('child_process').execFileSync, - * delay: (ms: number) => Promise, - * dryRun?: boolean, - * }} opts - */ -export const sendAction = async (bridgeAction, opts) => { - const { marshaller } = opts; - // @ts-expect-error BridgeAction has methods disallowed by Passable - const offerBody = JSON.stringify(marshaller.toCapData(harden(bridgeAction))); - - // tryExit should not require --allow-spend - // https://github.com/Agoric/agoric-sdk/issues/7291 - const spendMethods = ['executeOffer', 'tryExitOffer']; - const spendArg = spendMethods.includes(bridgeAction.method) - ? ['--allow-spend'] - : []; - - const act = ['wallet-action', ...spendArg, offerBody]; - const out = execSwingsetTransaction([...act, '--output', 'json'], opts); - if (opts.dryRun) { - return; - } - - assert(out); // not dry run - const tx = JSON.parse(out); - if (tx.code !== 0) { - const err = Error(`failed to send tx: ${tx.raw_log} code: ${tx.code}`); - // @ts-expect-error XXX how to add properties to an error? - err.code = tx.code; - throw err; - } - - return pollTx(tx.txhash, opts); -}; export const makeWalletUtils = async ( { delay, execFileSync, fetch }, From ce195aba9862df4e5467e1d955ae81cea67fc245 Mon Sep 17 00:00:00 2001 From: Samuel Siegart Date: Tue, 3 Dec 2024 18:41:58 -0800 Subject: [PATCH 41/56] test(fast-usdc): bootstrap test for advancement (#10606) refs https://github.com/Agoric/agoric-sdk/issues/10511 Does *not* count computrons yet. This makes 5 oracles submit evidence to provide a realistic scenario for measurement. --- .../boot/test/fast-usdc/fast-usdc.test.ts | 75 +++++++++++++----- .../fast-usdc/snapshots/fast-usdc.test.ts.md | 8 +- .../snapshots/fast-usdc.test.ts.snap | Bin 1242 -> 1193 bytes .../scripts/fast-usdc/init-fast-usdc.js | 2 - packages/fast-usdc/src/type-guards.js | 2 +- 5 files changed, 58 insertions(+), 29 deletions(-) diff --git a/packages/boot/test/fast-usdc/fast-usdc.test.ts b/packages/boot/test/fast-usdc/fast-usdc.test.ts index e13f95849e7..49da38cf01e 100644 --- a/packages/boot/test/fast-usdc/fast-usdc.test.ts +++ b/packages/boot/test/fast-usdc/fast-usdc.test.ts @@ -9,6 +9,7 @@ import { Fail } from '@endo/errors'; import { unmarshalFromVstorage } from '@agoric/internal/src/marshal.js'; import { makeMarshal } from '@endo/marshal'; import { defaultMarshaller } from '@agoric/internal/src/storage-test-utils.js'; +import { eventLoopIteration } from '@agoric/internal/src/testing-utils.js'; import { makeWalletFactoryContext, type WalletFactoryTestContext, @@ -41,8 +42,6 @@ test.serial( } = t.context; const [watcherWallet] = await Promise.all([ - wd.provideSmartWallet('agoric144rrhh4m09mh7aaffhm6xy223ym76gve2x7y78'), - wd.provideSmartWallet('agoric19d6gnr9fyp6hev4tlrg87zjrzsd5gzr5qlfq2p'), wd.provideSmartWallet('agoric19uscwxdac6cf6z7d5e26e0jm0lgwstc47cpll8'), wd.provideSmartWallet('agoric1krunjcqfrf7la48zrvdfeeqtls5r00ep68mzkr'), wd.provideSmartWallet('agoric1n4fcxsnkxe4gj6e24naec99hzmc4pjfdccy5nj'), @@ -129,26 +128,62 @@ test.serial('writes fee config to vstorage', async t => { await documentStorageSchema(t, storage, doc); }); -test.serial('writes status updates to vstorage', async t => { - const { walletFactoryDriver: wd, storage } = t.context; - const wallet = await wd.provideSmartWallet( - 'agoric144rrhh4m09mh7aaffhm6xy223ym76gve2x7y78', +test.serial('makes usdc advance', async t => { + const { walletFactoryDriver: wd, storage, agoricNamesRemotes } = t.context; + const oracles = await Promise.all([ + wd.provideSmartWallet('agoric19uscwxdac6cf6z7d5e26e0jm0lgwstc47cpll8'), + wd.provideSmartWallet('agoric1krunjcqfrf7la48zrvdfeeqtls5r00ep68mzkr'), + wd.provideSmartWallet('agoric1n4fcxsnkxe4gj6e24naec99hzmc4pjfdccy5nj'), + ]); + await Promise.all( + oracles.map(wallet => + wallet.sendOffer({ + id: 'claim-oracle-invitation', + invitationSpec: { + source: 'purse', + instance: agoricNamesRemotes.instance.fastUsdc, + description: 'oracle operator invitation', + }, + proposal: {}, + }), + ), ); - const submitMockEvidence = (mockEvidence: CctpTxEvidence) => - wallet.sendOffer({ - id: 'submit-mock-evidence', - invitationSpec: { - source: 'agoricContract', - instancePath: ['fastUsdc'], - callPipe: [['makeTestPushInvitation', [mockEvidence]]], - }, - proposal: {}, - }); - const mockEvidence1 = MockCctpTxEvidences.AGORIC_PLUS_OSMO(); - const mockEvidence2 = MockCctpTxEvidences.AGORIC_PLUS_DYDX(); - await submitMockEvidence(mockEvidence1); - await submitMockEvidence(mockEvidence2); + // @ts-expect-error it doesnt recognize usdc as a Brand type + const usdc = agoricNamesRemotes.vbankAsset.USDC.brand as Brand<'nat'>; + await oracles[0].sendOffer({ + id: 'deposit-lp-0', + invitationSpec: { + source: 'agoricContract', + instancePath: ['fastUsdc'], + callPipe: [['makeDepositInvitation', []]], + }, + proposal: { + give: { + USDC: { brand: usdc, value: 150_000_000n }, + }, + }, + }); + await eventLoopIteration(); + + const evidence = MockCctpTxEvidences.AGORIC_PLUS_OSMO(); + // TODO - start counting computrons + await Promise.all( + oracles.map(wallet => + wallet.sendOffer({ + id: 'submit-mock-evidence-osmo', + invitationSpec: { + source: 'continuing', + previousOffer: 'claim-oracle-invitation', + invitationMakerName: 'SubmitEvidence', + invitationArgs: [evidence], + }, + proposal: {}, + }), + ), + ); + await eventLoopIteration(); + // TODO - stop counting computrons const doc = { node: `fastUsdc.status`, diff --git a/packages/boot/test/fast-usdc/snapshots/fast-usdc.test.ts.md b/packages/boot/test/fast-usdc/snapshots/fast-usdc.test.ts.md index f953f9ea514..1441f49490d 100644 --- a/packages/boot/test/fast-usdc/snapshots/fast-usdc.test.ts.md +++ b/packages/boot/test/fast-usdc/snapshots/fast-usdc.test.ts.md @@ -72,7 +72,7 @@ Generated by [AVA](https://avajs.dev). ], ] -## writes status updates to vstorage +## makes usdc advance > Under "published", the "fastUsdc.status" node is delegated to the statuses of fast USDC transfers identified by their tx hashes. > The example below illustrates the schema of the data published there. @@ -82,10 +82,6 @@ Generated by [AVA](https://avajs.dev). [ [ 'published.fastUsdc.status.0xc81bc6105b60a234c7c50ac17816ebcd5561d366df8bf3be59ff387552761702', - 'OBSERVED', - ], - [ - 'published.fastUsdc.status.0xd81bc6105b60a234c7c50ac17816ebcd5561d366df8bf3be59ff387552761799', - 'OBSERVED', + 'ADVANCING', ], ] diff --git a/packages/boot/test/fast-usdc/snapshots/fast-usdc.test.ts.snap b/packages/boot/test/fast-usdc/snapshots/fast-usdc.test.ts.snap index 9489b8bc7ff297097930bdd8547b32b0ecc731b5..820fa8ddbf3bcfa3c1b40a990a2289fbb9915614 100644 GIT binary patch literal 1193 zcmV;a1XlY&RzVpL2 zz;^)f2LL=thPmcm@U9`(#2mjaFE0Z*2}z0v2-zkuPIr>GSP-Sb15`kk5;7y>sVMeB ztT$sB@J5S85r*f)$XMWmm5q{fNcO=Gyr-=CS-0Zq?IB0Am_TX9q(fFJSv4z6J=cpiAs$;p0NAQ zX1Qz&$KKj(@LJV%N=^-#?>c8|wVJzSyS2)h(pkG!&%~Zji#po6`TlLlR*1)uAILV- zK^&=Jg^VMs--shE8Q1@w9EQxpu>aRiBv8_|@%>s`r@Do7?TBl(Mx$6D4HOj^Vv}hU zNy{YeO^i^okg`b7bekKhgFNs9KIp9=>9km;zRxnH>CWY?M%sJD!gdQO_F20VBK0tg zuhSq5yGl!z^k;%lyoGH>V?X^$x{;3gCQA~Fg~DY-%0d-WFJ@BEHj}Ew!Z3)Ml*dsI zqqM5@v8y_!tkXdzuRdNJsln+3HK6G!G>;bp>&N>h25-(R1`i)C291<=n&sWG7UaGL zfFA(hPXJgZ02}w#11s&b^Amlx$cOjs64RJkdlOd651CF^Z%(W(v|0ZOlL7O>0p!!k zfW4t*5HL^7-wD7S0`O3_X)`*IC#GuvJZ%76%DU#KT)PIq4Flkftm}y>*AESVj|_nC zv#y1y0vYLkelsRED=>=NLBw<{QzJDGj3=UQ8|A<>MxUQ>$a#`QBGc%(9t*peevw6z zb8OqTC-4_%!_T|6or&<0c?|#8?!rG$%=b)y4@`iM&Ew@YPt2c9fL~02c`M^Of7o>y z$lU0eC+4FTz`6y{$ifz;G6)Ocngy_*bzQv6sl8*(R5!z!EZHZsfk|ls`^9Wn(>Zil z-^`fV0g^vlkhvAIS`R~PqIhZ`ziF7M`X|rfaQNw;42Oa295WjZG_@#7KH_iWcX3c-~2+dcT>8>i;eO_}sUU6*KtJthmKEtcr zwHbG+HK&3e7p_}zM7dHCe$DgC9=e;pU#?YMw^Xe-Rl77yM##A1>swdq7aHd-JU6@v zckX!;24s%81_K9F$tn8dzW`dYNckug4McK6et?2{dkG?tRQG9%sTQjL_LBS!gGW`G HJq!QvF^1fmy?oVXwmQW5gok8ZsA zAO#8bV68p#oB6%*%x`=%3X&|`RBzuR9qWWTPh6F;CdDEm!CF}ohuchNY)k1(@;b#T zH|KIfVG~fgv0!|{n&u@G^kFDel($92Y+W~W&n>up5hV24TM3uqhW)`sRhA<`f70eff_LL7V7(pfphO)6N7gTEe4P8E(WWHx5;vQparFG z0pLdf_yYiD5a86odf=EjJ2NzAQ(>>)&T~!1x;12VqJ(Sn^ybjh$tLey;xgtz(uI6J z9B`{==>{yL{Tl+@M}WtQLtD^+GTOcc@Vo_ZzUW#Wacx@w*DQc{impdST<=-{pI87t z6kR7q3S^n{{AvvyR#2KX}gwCdsa8fIc(iPzoeZMPblOTRdr#xx*61 zj`go)w4ZVSPC5XqMcCv>2H^l)aR9CtU8nYVYacj=s+;8vm+Z5{fw3}#{pxU7+uQN7 zzB^=Q53szmAY-#Qw~{1OC-GcYeodH>`sdf)a`@@*EQhY_?6VslXlh%U)n+!qU<>>| z7QmCe1)wz7ZN=Ix(M`VJ62QAdOTcykpb7vl9<&H7BhhENz)3_s5NrDe0Nm~g_1-(7 zjP{BAGY0`~6ddgXm&cpCERXJ?7u-%*^MbJIxqeV}d1di*xD@&>551+DSEV2nzF+mk zVznxwS`aM;x$*uH~Ar3y!&c1YE{rsi%wTB=h{t=nw<-N)D+WY>2 z?cL?FPj7b}Nad{=4Zdr% { /** @type {TypedPattern} */ const deposit = M.splitRecord( { give: { USDC: makeNatAmountShape(USDC, 1n) } }, - { want: { PoolShare: makeNatAmountShape(PoolShares) } }, + { want: M.splitRecord({}, { PoolShare: makeNatAmountShape(PoolShares) }) }, ); /** @type {TypedPattern} */ const withdraw = M.splitRecord({ From 0e2070754d6811acd40cb026792d4295189ae771 Mon Sep 17 00:00:00 2001 From: 0xPatrick Date: Sat, 30 Nov 2024 01:45:27 -0500 Subject: [PATCH 42/56] feat: register interchain bank assets proposal - create `register-interchain-bank-assets.js` for multichain-testing environment - allow users to submit offers using new brands like OSMO, ION - override existing brands like ATOM (ibc/toyatom) with starship denom - create `make-bank-asset-info.ts` to gather `InterchainAssetOptions` from starship env - update `make start` and ci `multichain-e2e-template.yaml` to call these scripts - deploy-cli.ts `deployBuilder` accepts `builderOpts` --- .github/workflows/multichain-e2e-template.yml | 4 + multichain-testing/.gitignore | 5 +- multichain-testing/Makefile | 7 +- multichain-testing/README.md | 2 +- multichain-testing/scripts/deploy-cli.ts | 17 +- .../scripts/make-bank-asset-info.ts | 30 +++ ...register-interchain-bank-assets.builder.js | 51 +++++ .../src/revise-chain-info.builder.js | 2 +- .../test/scripts/make-bank-asset-info.test.ts | 30 +++ .../test/tools/asset-info.test.ts | 2 + multichain-testing/tools/asset-info.ts | 29 +-- multichain-testing/tools/e2e-tools.js | 2 +- multichain-testing/tsconfig.json | 1 + .../register-interchain-bank-assets.js | 199 ++++++++++++++++++ 14 files changed, 359 insertions(+), 22 deletions(-) create mode 100755 multichain-testing/scripts/make-bank-asset-info.ts create mode 100644 multichain-testing/src/register-interchain-bank-assets.builder.js create mode 100644 multichain-testing/test/scripts/make-bank-asset-info.test.ts create mode 100644 packages/builders/scripts/testing/register-interchain-bank-assets.js diff --git a/.github/workflows/multichain-e2e-template.yml b/.github/workflows/multichain-e2e-template.yml index 58c7ee81013..58455e3b9b4 100644 --- a/.github/workflows/multichain-e2e-template.yml +++ b/.github/workflows/multichain-e2e-template.yml @@ -92,6 +92,10 @@ jobs: run: make override-chain-registry working-directory: ./agoric-sdk/multichain-testing + - name: Register Interchain Bank Assets + run: make register-bank-assets + working-directory: ./agoric-sdk/multichain-testing + - name: Run @agoric/multichain-testing E2E Tests run: yarn ${{ inputs.test_command }} working-directory: ./agoric-sdk/multichain-testing diff --git a/multichain-testing/.gitignore b/multichain-testing/.gitignore index bd550b4d526..a59e6798973 100644 --- a/multichain-testing/.gitignore +++ b/multichain-testing/.gitignore @@ -2,6 +2,7 @@ !.yarn/patches/* # fetched chain info from running starship starship-chain-info.js -# output of build script to get update running chain info -revise-chain-info* +# builder prefix for contract starters start* +# builder prefix for core evals +eval-* diff --git a/multichain-testing/Makefile b/multichain-testing/Makefile index 5301808e631..0f2bd61450d 100644 --- a/multichain-testing/Makefile +++ b/multichain-testing/Makefile @@ -79,6 +79,11 @@ override-chain-registry: scripts/fetch-starship-chain-info.ts && \ scripts/deploy-cli.ts src/revise-chain-info.builder.js +register-bank-assets: + scripts/fetch-starship-chain-info.ts && \ + scripts/deploy-cli.ts src/register-interchain-bank-assets.builder.js \ + assets="$$(scripts/make-bank-asset-info.ts)" + ADDR=agoric1ldmtatp24qlllgxmrsjzcpe20fvlkp448zcuce COIN=1000000000uist @@ -101,5 +106,5 @@ wait-for-pods: scripts/pod-readiness.ts .PHONY: start -start: install wait-for-pods port-forward fund-provision-pool override-chain-registry +start: install wait-for-pods port-forward fund-provision-pool override-chain-registry register-bank-assets diff --git a/multichain-testing/README.md b/multichain-testing/README.md index cb090092cde..5a43a2aff24 100644 --- a/multichain-testing/README.md +++ b/multichain-testing/README.md @@ -59,7 +59,7 @@ make wait-for-pods make port-forward # set up Agoric testing environment -make fund-provision-pool override-chain-registry +make fund-provision-pool override-chain-registry register-bank-assets ``` If you get an error like "connection refused", you need to wait longer, until all the pods are Running. diff --git a/multichain-testing/scripts/deploy-cli.ts b/multichain-testing/scripts/deploy-cli.ts index 2dfd7b94d06..65e2320da71 100755 --- a/multichain-testing/scripts/deploy-cli.ts +++ b/multichain-testing/scripts/deploy-cli.ts @@ -9,17 +9,28 @@ import { makeAgdTools } from '../tools/agd-tools.js'; import { makeDeployBuilder } from '../tools/deploy.js'; async function main() { - const builder = process.argv[2]; + const [builder, ...rawArgs] = process.argv.slice(2); + + // Parse builder options from command line arguments + const builderOpts: Record = {}; + for (const arg of rawArgs) { + const [key, value] = arg.split('='); + if (key && value) { + builderOpts[key] = value; + } + } if (!builder) { - console.error('USAGE: deploy-cli.ts '); + console.error( + 'USAGE: deploy-cli.ts [key1=value1] [key2=value2]', + ); process.exit(1); } try { const agdTools = await makeAgdTools(console.log, childProcess); const deployBuilder = makeDeployBuilder(agdTools, fse.readJSON, execa); - await deployBuilder(builder); + await deployBuilder(builder, builderOpts); } catch (err) { console.error(err); process.exit(1); diff --git a/multichain-testing/scripts/make-bank-asset-info.ts b/multichain-testing/scripts/make-bank-asset-info.ts new file mode 100755 index 00000000000..257a81986b1 --- /dev/null +++ b/multichain-testing/scripts/make-bank-asset-info.ts @@ -0,0 +1,30 @@ +#!/usr/bin/env -S node --import ts-blank-space/register +/* eslint-env node */ + +import '@endo/init'; +import starshipChainInfo from '../starship-chain-info.js'; +import { makeAssetInfo } from '../tools/asset-info.ts'; + +const main = () => { + if (!starshipChainInfo) { + throw new Error( + 'starshipChainInfo not found. run `./scripts/fetch-starship-chain-info.ts` first.', + ); + } + + const assetInfo = makeAssetInfo(starshipChainInfo) + .filter( + ([_, { chainName, baseName }]) => + chainName === 'agoric' && baseName !== 'agoric', + ) + .map(([denom, { baseDenom }]) => ({ + denom, + issuerName: baseDenom.replace(/^u/, '').toUpperCase(), + decimalPlaces: 6, // TODO do not assume 6 + })); + + // Directly output JSON string for proposal builder options + process.stdout.write(JSON.stringify(assetInfo)); +}; + +main(); diff --git a/multichain-testing/src/register-interchain-bank-assets.builder.js b/multichain-testing/src/register-interchain-bank-assets.builder.js new file mode 100644 index 00000000000..0417c2b92d5 --- /dev/null +++ b/multichain-testing/src/register-interchain-bank-assets.builder.js @@ -0,0 +1,51 @@ +/* global harden */ +/// +import { makeHelpers } from '@agoric/deploy-script-support'; +import { parseArgs } from 'node:util'; + +/** + * @import {ParseArgsConfig} from 'node:util'; + * @import {CoreEvalBuilder, DeployScriptFunction} from '@agoric/deploy-script-support/src/externalTypes.js'; + */ + +/** @type {ParseArgsConfig['options']} */ +const parserOpts = { + assets: { type: 'string' }, +}; + +/** @type {CoreEvalBuilder} */ +export const defaultProposalBuilder = async (_, options) => { + return harden({ + sourceSpec: + '@agoric/builders/scripts/testing/register-interchain-bank-assets.js', + getManifestCall: ['getManifestCall', options], + }); +}; + +/** @type {DeployScriptFunction} */ +export default async (homeP, endowments) => { + const { scriptArgs } = endowments; + + const { + values: { assets }, + } = parseArgs({ + args: scriptArgs, + options: parserOpts, + }); + + const parseAssets = () => { + if (typeof assets !== 'string') { + throw Error( + 'must provide --assets=JSON.stringify({ denom: Denom; issuerName: string; decimalPlaces: number; }[])', + ); + } + return JSON.parse(assets); + }; + + const opts = harden({ assets: parseAssets() }); + + const { writeCoreEval } = await makeHelpers(homeP, endowments); + await writeCoreEval('eval-register-interchain-bank-assets', utils => + defaultProposalBuilder(utils, opts), + ); +}; diff --git a/multichain-testing/src/revise-chain-info.builder.js b/multichain-testing/src/revise-chain-info.builder.js index 10673129466..1269350a491 100644 --- a/multichain-testing/src/revise-chain-info.builder.js +++ b/multichain-testing/src/revise-chain-info.builder.js @@ -19,5 +19,5 @@ export const defaultProposalBuilder = async () => /** @type {import('@agoric/deploy-script-support/src/externalTypes.js').DeployScriptFunction} */ export default async (homeP, endowments) => { const { writeCoreEval } = await makeHelpers(homeP, endowments); - await writeCoreEval('revise-chain-info', defaultProposalBuilder); + await writeCoreEval('eval-revise-chain-info', defaultProposalBuilder); }; diff --git a/multichain-testing/test/scripts/make-bank-asset-info.test.ts b/multichain-testing/test/scripts/make-bank-asset-info.test.ts new file mode 100644 index 00000000000..d04adf4dbe8 --- /dev/null +++ b/multichain-testing/test/scripts/make-bank-asset-info.test.ts @@ -0,0 +1,30 @@ +import test from 'ava'; +import { execFileSync } from 'node:child_process'; + +test('make-bank-asset-info', async t => { + const stdout = execFileSync('./scripts/make-bank-asset-info.ts', { + encoding: 'utf8', + }); + + const assetInfo = JSON.parse(stdout); + + t.like(assetInfo, [ + { + issuerName: 'ATOM', + decimalPlaces: 6, + }, + { + issuerName: 'OSMO', + decimalPlaces: 6, + }, + { + issuerName: 'ION', + decimalPlaces: 6, + }, + ]); + + for (const { denom } of assetInfo) { + t.regex(denom, /^ibc\//); + t.is(denom.length, 68); + } +}); diff --git a/multichain-testing/test/tools/asset-info.test.ts b/multichain-testing/test/tools/asset-info.test.ts index be054b65180..1806a3c4e26 100644 --- a/multichain-testing/test/tools/asset-info.test.ts +++ b/multichain-testing/test/tools/asset-info.test.ts @@ -106,6 +106,7 @@ test('makeAssetInfo', async t => { { baseDenom: 'uosmo', baseName: 'osmosis', + brandKey: 'OSMO', chainName: 'agoric', }, ], @@ -138,6 +139,7 @@ test('makeAssetInfo', async t => { { baseDenom: 'uatom', baseName: 'cosmoshub', + brandKey: 'ATOM', chainName: 'agoric', }, ], diff --git a/multichain-testing/tools/asset-info.ts b/multichain-testing/tools/asset-info.ts index f3e548d1968..ef4faf1d5ac 100644 --- a/multichain-testing/tools/asset-info.ts +++ b/multichain-testing/tools/asset-info.ts @@ -6,7 +6,12 @@ import { } from '@agoric/orchestration'; import type { IBCChannelID } from '@agoric/vats'; -/** make asset info for current env */ +/** + * Make asset info for the current environment. + * + * until #10580, the contract's `issuerKeywordRecord` must include 'ATOM', + * 'OSMO', 'IST', etc. for the local `chainHub` to know about brands. + */ export const makeAssetInfo = ( chainInfo: Record, tokenMap: Record = { @@ -37,13 +42,6 @@ export const makeAssetInfo = ( return `ibc/${denomHash({ denom, channelId })}`; }; - // `brandKey` instead of `brand` until #10580 - // only BLD, IST until #9966 - const BRAND_KEY_MAP: Record = { - ubld: 'BLD', - uist: 'IST', - }; - // only include chains present in `chainInfo` const tokens = Object.entries(tokenMap) .filter(([chain]) => chain in chainInfo) @@ -62,7 +60,11 @@ export const makeAssetInfo = ( { ...baseDetails, chainName: chain, - ...(BRAND_KEY_MAP[denom] && { brandKey: BRAND_KEY_MAP[denom] }), + ...(chain === 'agoric' && { + // `brandKey` instead of `brand` until #10580 + // assumes issuerKeywordRecord includes brand keywords like `IST`, `OSMO` + brandKey: denom.replace(/^u/, '').toUpperCase(), + }), }, ]); @@ -70,14 +72,15 @@ export const makeAssetInfo = ( const issuingChainId = chainInfo[chain].chainId; for (const holdingChain of Object.keys(chainInfo)) { if (holdingChain === chain) continue; - const denomHash = toDenomHash(denom, issuingChainId, holdingChain); assetInfo.push([ - denomHash, + toDenomHash(denom, issuingChainId, holdingChain), { ...baseDetails, chainName: holdingChain, - ...(BRAND_KEY_MAP[denomHash] && { - brandKey: BRAND_KEY_MAP[denomHash], + ...(holdingChain === 'agoric' && { + // `brandKey` instead of `brand` until #10580 + // assumes issuerKeywordRecord includes brand keywords like `IST`, `OSMO` + brandKey: denom.replace(/^u/, '').toUpperCase(), }), }, ]); diff --git a/multichain-testing/tools/e2e-tools.js b/multichain-testing/tools/e2e-tools.js index a3c4ce4207c..51583c006b8 100644 --- a/multichain-testing/tools/e2e-tools.js +++ b/multichain-testing/tools/e2e-tools.js @@ -169,7 +169,7 @@ export const provisionSmartWallet = async ( for await (const [name, qty] of Object.entries(balances)) { const info = byName[name]; if (!info) { - throw Error(name); + throw Error(`${name} not found in vbank assets`); } const { denom, displayInfo } = info; const { decimalPlaces } = displayInfo; diff --git a/multichain-testing/tsconfig.json b/multichain-testing/tsconfig.json index d08285caec4..8915139d881 100644 --- a/multichain-testing/tsconfig.json +++ b/multichain-testing/tsconfig.json @@ -1,6 +1,7 @@ { "extends": "../tsconfig.json", "include": [ + "src", "tools", "test" ], diff --git a/packages/builders/scripts/testing/register-interchain-bank-assets.js b/packages/builders/scripts/testing/register-interchain-bank-assets.js new file mode 100644 index 00000000000..dc99315c52b --- /dev/null +++ b/packages/builders/scripts/testing/register-interchain-bank-assets.js @@ -0,0 +1,199 @@ +/** + * @file register-interchain-bank-assets.js Core Eval + * + * Used to populate vbank in testing environments. + */ +import { AssetKind } from '@agoric/ertp'; +import { makeTracer } from '@agoric/internal'; +import { E } from '@endo/far'; +import { makeMarshal } from '@endo/marshal'; + +const { Fail } = assert; + +const trace = makeTracer('RegisterInterchainBankAssets', true); + +/** @import {Board} from '@agoric/vats'; */ + +/** + * @typedef {object} InterchainAssetOptions + * @property {string} denom + * @property {number} decimalPlaces + * @property {string} issuerName + * @property {string} keyword - defaults to `issuerName` if not provided + * @property {string} [proposedName] - defaults to `issuerName` if not provided + */ + +// vstorage paths under published.* +const BOARD_AUX = 'boardAux'; + +const marshalData = makeMarshal(_val => Fail`data only`); + +/** + * Make a storage node for auxiliary data for a value on the board. + * + * @param {ERef} chainStorage + * @param {string} boardId + */ +const makeBoardAuxNode = async (chainStorage, boardId) => { + const boardAux = E(chainStorage).makeChildNode(BOARD_AUX); + return E(boardAux).makeChildNode(boardId); +}; + +/** + * see `publishAgoricBrandsDisplayInfo` {@link @agoric/smart-wallet/proposals/upgrade-walletFactory-proposal.js} + * + * @param {ERef} chainStorage + * @param {ERef} board + * @param {Brand<'nat'>} brand + */ +const publishBrandInfo = async (chainStorage, board, brand) => { + const [boardId, displayInfo, allegedName] = await Promise.all([ + E(board).getId(brand), + E(brand).getDisplayInfo(), + E(brand).getAllegedName(), + ]); + const node = makeBoardAuxNode(chainStorage, boardId); + const aux = marshalData.toCapData(harden({ allegedName, displayInfo })); + await E(node).setValue(JSON.stringify(aux)); +}; + +/** + * @param {BootstrapPowers} powers + * @param {object} config + * @param {object} config.options + * @param {InterchainAssetOptions[]} config.options.assets + */ +export const publishInterchainAssets = async ( + { + consume: { + agoricNamesAdmin, + bankManager, + board, + chainStorage, + startUpgradable, + }, + brand: { produce: produceBrands }, + issuer: { produce: produceIssuers }, + installation: { + consume: { mintHolder }, + }, + }, + { options: { assets } }, +) => { + trace(`${publishInterchainAssets.name} starting...`); + trace(assets); + await null; + for (const interchainAssetOptions of assets) { + const { + denom, + decimalPlaces, + issuerName, + keyword = issuerName, + proposedName = issuerName, + } = interchainAssetOptions; + + trace('interchainAssetOptions', { + denom, + decimalPlaces, + issuerName, + keyword, + proposedName, + }); + + assert.typeof(denom, 'string'); + assert.typeof(decimalPlaces, 'number'); + assert.typeof(keyword, 'string'); + assert.typeof(issuerName, 'string'); + assert.typeof(proposedName, 'string'); + + const terms = { + keyword: issuerName, // "keyword" is a misnomer in mintHolder terms + assetKind: AssetKind.NAT, + displayInfo: { + decimalPlaces, + assetKind: AssetKind.NAT, + }, + }; + const { creatorFacet: mint, publicFacet: issuer } = await E( + startUpgradable, + )({ + installation: mintHolder, + label: issuerName, + privateArgs: undefined, + terms, + }); + + const brand = await E(issuer).getBrand(); + const kit = /** @type {IssuerKit<'nat'>} */ ({ mint, issuer, brand }); + + /** + * `addAssetToVault.js` will register the issuer with the `reserveKit`, + * but we don't need to do that here. + */ + + await Promise.all([ + E(E(agoricNamesAdmin).lookupAdmin('issuer')).update(issuerName, issuer), + E(E(agoricNamesAdmin).lookupAdmin('brand')).update(issuerName, brand), + // triggers benign UnhandledPromiseRejection 'Error: keyword "ATOM" must + // be unique' in provisionPool in testing environments + E(bankManager).addAsset(denom, issuerName, proposedName, kit), + ]); + + // publish brands and issuers to Bootstrap space for use in proposals + produceBrands[keyword].reset(); + produceIssuers[keyword].reset(); + produceBrands[keyword].resolve(brand); + produceIssuers[keyword].resolve(issuer); + + // publish brand info / boardAux for offer legibility + await publishBrandInfo( + // @ts-expect-error 'Promise' is not assignable to + // parameter of type 'ERef' + chainStorage, + board, + brand, + ); + } + trace(`${publishInterchainAssets.name} complete`); +}; + +/** + * @param {unknown} _powers + * @param {{ assets: InterchainAssetOptions[] }} options + */ +export const getManifestCall = (_powers, options) => { + /** @type {Record} */ + const IssuerKws = options.assets.reduce( + /** + * @param {Record} acc + * @param {InterchainAssetOptions} assetOptions + */ + (acc, { issuerName }) => Object.assign(acc, { [issuerName]: true }), + {}, + ); + harden(IssuerKws); + + return { + manifest: { + [publishInterchainAssets.name]: { + consume: { + agoricNamesAdmin: true, + bankManager: true, + board: true, + chainStorage: true, + startUpgradable: true, + }, + brand: { + produce: IssuerKws, + }, + issuer: { + produce: IssuerKws, + }, + installation: { + consume: { mintHolder: true }, + }, + }, + }, + options, + }; +}; From 5cafda6636d79329fe6e1f4d5561ccdec95d3a0b Mon Sep 17 00:00:00 2001 From: 0xPatrick Date: Sat, 30 Nov 2024 04:19:51 -0500 Subject: [PATCH 43/56] chore: pfm timeout is Go time duration string --- packages/orchestration/src/cosmos-api.ts | 17 +++++++++++++++-- packages/orchestration/src/exos/chain-hub.js | 4 ++-- .../orchestration/test/exos/chain-hub.test.ts | 10 +++++----- .../local-orchestration-account-kit.test.ts | 6 +++--- 4 files changed, 25 insertions(+), 12 deletions(-) diff --git a/packages/orchestration/src/cosmos-api.ts b/packages/orchestration/src/cosmos-api.ts index 661d92a23d5..dad627c1382 100644 --- a/packages/orchestration/src/cosmos-api.ts +++ b/packages/orchestration/src/cosmos-api.ts @@ -370,8 +370,8 @@ export interface ForwardInfo { receiver: ChainAddress['value']; port: IBCPortID; channel: IBCChannelID; - /** e.g. '10min' */ - timeout: string; + /** e.g. '10m' */ + timeout: GoDuration; /** default is 3? */ retries: number; next?: { @@ -404,3 +404,16 @@ export type TransferRoute = { forwardInfo?: never; } ); + +/** Single units allowed in Go time duration strings */ +type GoDurationUnit = 'h' | 'm' | 's' | 'ms' | 'us' | 'ns'; + +/** + * Type for a time duration string in Go (cosmos-sdk). For example, "1h", "3m". + * + * Note: this does not support composite values like "1h30m", "1m30s", + * which are allowed in Go. + * + * @see https://pkg.go.dev/time#ParseDuration + */ +export type GoDuration = `${number}${GoDurationUnit}`; diff --git a/packages/orchestration/src/exos/chain-hub.js b/packages/orchestration/src/exos/chain-hub.js index 1477ca91de8..8f40d34b563 100644 --- a/packages/orchestration/src/exos/chain-hub.js +++ b/packages/orchestration/src/exos/chain-hub.js @@ -21,7 +21,7 @@ import { getBech32Prefix } from '../utils/address.js'; * @import {NameHub} from '@agoric/vats'; * @import {Vow, VowTools} from '@agoric/vow'; * @import {Zone} from '@agoric/zone'; - * @import {CosmosAssetInfo, CosmosChainInfo, ForwardInfo, IBCConnectionInfo, IBCMsgTransferOptions, TransferRoute} from '../cosmos-api.js'; + * @import {CosmosAssetInfo, CosmosChainInfo, ForwardInfo, IBCConnectionInfo, IBCMsgTransferOptions, TransferRoute, GoDuration} from '../cosmos-api.js'; * @import {ChainInfo, KnownChains} from '../chain-info.js'; * @import {ChainAddress, Denom, DenomAmount} from '../orchestration-api.js'; * @import {Remote, TypedPattern} from '@agoric/internal'; @@ -179,7 +179,7 @@ const ChainIdArgShape = M.or( const DefaultPfmTimeoutOpts = harden( /** @type {const} */ ({ retries: 3, - timeout: '10min', + timeout: /** @type {const} */ ('10m'), }), ); diff --git a/packages/orchestration/test/exos/chain-hub.test.ts b/packages/orchestration/test/exos/chain-hub.test.ts index 02505f41778..870d5c9672d 100644 --- a/packages/orchestration/test/exos/chain-hub.test.ts +++ b/packages/orchestration/test/exos/chain-hub.test.ts @@ -325,7 +325,7 @@ test('makeTransferRoute - through issuing chain', async t => { port: 'transfer', channel: 'channel-1', retries: 3, - timeout: '10min', + timeout: '10m', }, }, }); @@ -348,7 +348,7 @@ test('makeTransferRoute - through issuing chain', async t => { timeoutTimestamp: 0n, }); t.like(transferMsg, { - memo: '{"forward":{"receiver":"osmo1234","port":"transfer","channel":"channel-1","retries":3,"timeout":"10min"}}', + memo: '{"forward":{"receiver":"osmo1234","port":"transfer","channel":"channel-1","retries":3,"timeout":"10m"}}', receiver: 'pfm', }); }); @@ -367,7 +367,7 @@ test('makeTransferRoute - takes forwardOpts', t => { const amt: DenomAmount = harden({ denom: uusdcOnOsmosis, value: 100n }); const forwardOpts = harden({ retries: 1, - timeout: '3min', + timeout: '3m' as const, }); // 100 USDC on osmosis -> agoric @@ -386,11 +386,11 @@ test('makeTransferRoute - takes forwardOpts', t => { }); t.like( - chainHub.makeTransferRoute(dest, amt, 'osmosis', { timeout: '99min' }), + chainHub.makeTransferRoute(dest, amt, 'osmosis', { timeout: '99m' }), { forwardInfo: { forward: { - timeout: '99min', + timeout: '99m' as const, }, }, }, diff --git a/packages/orchestration/test/exos/local-orchestration-account-kit.test.ts b/packages/orchestration/test/exos/local-orchestration-account-kit.test.ts index afec573e19c..ed618734166 100644 --- a/packages/orchestration/test/exos/local-orchestration-account-kit.test.ts +++ b/packages/orchestration/test/exos/local-orchestration-account-kit.test.ts @@ -299,7 +299,7 @@ test('transfer', async t => { t.like(lastestTxMsg(), { receiver: PFM_RECEIVER, - memo: '{"forward":{"receiver":"dydx1test","port":"transfer","channel":"channel-33","retries":3,"timeout":"10min"}}', + memo: '{"forward":{"receiver":"dydx1test","port":"transfer","channel":"channel-33","retries":3,"timeout":"10m"}}', }); t.log('accepts pfm `forwardOpts`'); @@ -309,7 +309,7 @@ test('transfer', async t => { dydxDest, { forwardOpts: { - timeout: '999min', + timeout: '999m', }, }, fetchedChainInfo.agoric.connections['noble-1'].transferChannel.channelId, @@ -318,7 +318,7 @@ test('transfer', async t => { t.like(JSON.parse(lastestTxMsg().memo), { forward: { - timeout: '999min', + timeout: '999m', }, }); }); From 57cc060c1f11e69d9ef26a3a129213ab021cbc51 Mon Sep 17 00:00:00 2001 From: 0xPatrick Date: Sat, 30 Nov 2024 04:37:42 -0500 Subject: [PATCH 44/56] test: `faucetTools.fundFaucet` - adds helper to fund agoric faucet with interchain tokens - allows callers to request `OSMO`, `ATOM`, etc, via `provisionSmartWallet` --- multichain-testing/test/auto-stake-it.test.ts | 60 +++--------------- multichain-testing/test/support.ts | 8 +++ multichain-testing/tools/agd-lib.js | 15 ++++- multichain-testing/tools/e2e-tools.js | 7 ++- multichain-testing/tools/faucet-tools.ts | 39 ++++++++++++ multichain-testing/tools/ibc-transfer.ts | 62 ++++++++++++++++++- multichain-testing/tools/sleep.ts | 2 + 7 files changed, 135 insertions(+), 58 deletions(-) create mode 100644 multichain-testing/tools/faucet-tools.ts diff --git a/multichain-testing/test/auto-stake-it.test.ts b/multichain-testing/test/auto-stake-it.test.ts index 29b984ceec0..d4bfded2086 100644 --- a/multichain-testing/test/auto-stake-it.test.ts +++ b/multichain-testing/test/auto-stake-it.test.ts @@ -1,11 +1,8 @@ import anyTest from '@endo/ses-ava/prepare-endo.js'; -import type { ExecutionContext, TestFn } from 'ava'; +import type { TestFn } from 'ava'; import starshipChainInfo from '../starship-chain-info.js'; import { makeDoOffer } from '../tools/e2e-tools.js'; -import { - createFundedWalletAndClient, - makeIBCTransferMsg, -} from '../tools/ibc-transfer.js'; +import { makeFundAndTransfer } from '../tools/ibc-transfer.js'; import { makeQueryClient } from '../tools/query.js'; import type { SetupContextWithWallets } from './support.js'; import { chainConfig, commonSetup } from './support.js'; @@ -37,53 +34,6 @@ test.after(async t => { deleteTestKeys(accounts); }); -const makeFundAndTransfer = (t: ExecutionContext) => { - const { retryUntilCondition, useChain } = t.context; - return async (chainName: string, agoricAddr: string, amount = 100n) => { - const { staking } = useChain(chainName).chainInfo.chain; - const denom = staking?.staking_tokens?.[0].denom; - if (!denom) throw Error(`no denom for ${chainName}`); - - const { client, address, wallet } = await createFundedWalletAndClient( - t, - chainName, - useChain, - ); - const balancesResult = await retryUntilCondition( - () => client.getAllBalances(address), - coins => !!coins?.length, - `Faucet balances found for ${address}`, - ); - - console.log('Balances:', balancesResult); - - const transferArgs = makeIBCTransferMsg( - { denom, value: amount }, - { address: agoricAddr, chainName: 'agoric' }, - { address: address, chainName }, - Date.now(), - useChain, - ); - console.log('Transfer Args:', transferArgs); - // TODO #9200 `sendIbcTokens` does not support `memo` - // @ts-expect-error spread argument for concise code - const txRes = await client.sendIbcTokens(...transferArgs); - if (txRes && txRes.code !== 0) { - console.error(txRes); - throw Error(`failed to ibc transfer funds to ${chainName}`); - } - const { events: _events, ...txRest } = txRes; - console.log(txRest); - t.is(txRes.code, 0, `Transaction succeeded`); - t.log(`Funds transferred to ${agoricAddr}`); - return { - client, - address, - wallet, - }; - }; -}; - const autoStakeItScenario = test.macro({ title: (_, chainName: string) => `auto-stake-it on ${chainName}`, exec: async (t, chainName: string) => { @@ -96,7 +46,11 @@ const autoStakeItScenario = test.macro({ useChain, } = t.context; - const fundAndTransfer = makeFundAndTransfer(t); + const fundAndTransfer = makeFundAndTransfer( + t, + retryUntilCondition, + useChain, + ); // 2. Find 'stakingDenom' denom on agoric const remoteChainInfo = starshipChainInfo[chainName]; diff --git a/multichain-testing/test/support.ts b/multichain-testing/test/support.ts index f3f8e752d96..18e8006f155 100644 --- a/multichain-testing/test/support.ts +++ b/multichain-testing/test/support.ts @@ -19,6 +19,7 @@ import { makeHermes } from '../tools/hermes-tools.js'; import { makeNobleTools } from '../tools/noble-tools.js'; import { makeAssetInfo } from '../tools/asset-info.js'; import starshipChainInfo from '../starship-chain-info.js'; +import { makeFaucetTools } from '../tools/faucet-tools.js'; export const FAUCET_POUR = 10_000n * 1_000_000n; @@ -84,6 +85,12 @@ export const commonSetup = async (t: ExecutionContext) => { const nobleTools = makeNobleTools(childProcess); const assetInfo = makeAssetInfo(starshipChainInfo); const chainInfo = withChainCapabilities(starshipChainInfo); + const faucetTools = makeFaucetTools( + t, + tools.agd, + retryUntilCondition, + useChain, + ); /** * Starts a contract if instance not found. Takes care of installing @@ -135,6 +142,7 @@ export const commonSetup = async (t: ExecutionContext) => { startContract, assetInfo, chainInfo, + faucetTools, }; }; diff --git a/multichain-testing/tools/agd-lib.js b/multichain-testing/tools/agd-lib.js index a301945f148..a28d408493b 100644 --- a/multichain-testing/tools/agd-lib.js +++ b/multichain-testing/tools/agd-lib.js @@ -164,6 +164,19 @@ export const makeAgd = ({ execFileSync }) => { }, ).toString(); }, + /** @param {string} name key name in keyring */ + showAddress: name => { + return execFileSync( + kubectlBinary, + [...binaryArgs, 'keys', 'show', name, '-a', ...keyringArgs], + { + encoding: 'utf-8', + stdio: ['pipe', 'pipe', 'ignore'], + }, + ) + .toString() + .trim(); + }, /** @param {string} name */ delete: name => { return exec([...keyringArgs, 'keys', 'delete', name, '-y'], { @@ -181,7 +194,7 @@ export const makeAgd = ({ execFileSync }) => { return make(); }; -/** @typedef {ReturnType} Agd */ +/** @typedef {ReturnType} Agd */ /** @param {{ execFileSync: typeof import('child_process').execFileSync, log: typeof console.log }} powers */ export const makeCopyFiles = ( diff --git a/multichain-testing/tools/e2e-tools.js b/multichain-testing/tools/e2e-tools.js index 51583c006b8..f820e7c8077 100644 --- a/multichain-testing/tools/e2e-tools.js +++ b/multichain-testing/tools/e2e-tools.js @@ -144,7 +144,11 @@ export const provisionSmartWallet = async ( // TODO: skip this query if balances is {} const vbankEntries = await q.queryData('published.agoricNames.vbankAsset'); const byName = Object.fromEntries( - vbankEntries.map(([_denom, info]) => [info.issuerName, info]), + vbankEntries.map(([denom, info]) => { + /// XXX better way to filter out old ATOM denom? + if (denom === 'ibc/toyatom') return [undefined, undefined]; + return [info.issuerName, info]; + }), ); progress({ send: balances, to: address }); @@ -543,6 +547,7 @@ export const makeE2ETools = async ( /** @param {string} name */ deleteKey: async name => agd.keys.delete(name), copyFiles, + agd, }; }; diff --git a/multichain-testing/tools/faucet-tools.ts b/multichain-testing/tools/faucet-tools.ts new file mode 100644 index 00000000000..272dd464cae --- /dev/null +++ b/multichain-testing/tools/faucet-tools.ts @@ -0,0 +1,39 @@ +import type { ExecutionContext } from 'ava'; +import type { Denom } from '@agoric/orchestration'; +import { makeFundAndTransfer } from './ibc-transfer.js'; +import type { MultichainRegistry } from './registry.js'; +import type { RetryUntilCondition } from './sleep.js'; +import type { AgdTools } from './agd-tools.js'; + +type ChainName = string; + +// 90% of default faucet pour +const DEFAULT_QTY = (10_000_000_000n * 9n) / 10n; + +/** + * Determines the agoric `faucet` address and sends funds to it. + * + * Allows use of brands like OSMO, ATOM, etc. with `provisionSmartWallet`. + */ +export const makeFaucetTools = ( + t: ExecutionContext, + agd: AgdTools['agd'], + retryUntilCondition: RetryUntilCondition, + useChain: MultichainRegistry['useChain'], +) => { + const fundAndTransfer = makeFundAndTransfer(t, retryUntilCondition, useChain); + return { + /** + * @param assets denom on the issuing chain + * @param [qty] number of tokens + */ + fundFaucet: async (assets: [ChainName, Denom][], qty = DEFAULT_QTY) => { + const faucetAddr = agd.keys.showAddress('faucet'); + console.log(`Faucet address: ${faucetAddr}`); + + for (const [chainName, denom] of assets) { + await fundAndTransfer(chainName, faucetAddr, qty, denom); + } + }, + }; +}; diff --git a/multichain-testing/tools/ibc-transfer.ts b/multichain-testing/tools/ibc-transfer.ts index 41db593cff2..3437080afd3 100644 --- a/multichain-testing/tools/ibc-transfer.ts +++ b/multichain-testing/tools/ibc-transfer.ts @@ -16,6 +16,7 @@ import { MsgTransfer } from '@agoric/cosmic-proto/ibc/applications/transfer/v1/t import { createWallet } from './wallet.js'; import chainInfo from '../starship-chain-info.js'; import type { MultichainRegistry } from './registry.js'; +import type { RetryUntilCondition } from './sleep.js'; interface MakeFeeObjectArgs { denom?: string; @@ -118,14 +119,15 @@ export const makeIBCTransferMsg = ( }; export const createFundedWalletAndClient = async ( - t: ExecutionContext, + log: (...args: unknown[]) => void, chainName: string, useChain: MultichainRegistry['useChain'], + mnemonic?: string, ) => { const { chain, creditFromFaucet, getRpcEndpoint } = useChain(chainName); - const wallet = await createWallet(chain.bech32_prefix); + const wallet = await createWallet(chain.bech32_prefix, mnemonic); const address = (await wallet.getAccounts())[0].address; - t.log(`Requesting faucet funds for ${address}`); + log(`Requesting faucet funds for ${address}`); await creditFromFaucet(address); // TODO use telescope generated rpc client from @agoric/cosmic-proto // https://github.com/Agoric/agoric-sdk/issues/9200 @@ -135,3 +137,57 @@ export const createFundedWalletAndClient = async ( ); return { client, wallet, address }; }; + +export const makeFundAndTransfer = ( + t: ExecutionContext, + retryUntilCondition: RetryUntilCondition, + useChain: MultichainRegistry['useChain'], +) => { + return async ( + chainName: string, + agoricAddr: string, + amount = 100n, + denom?: string, + ) => { + const { staking } = useChain(chainName).chainInfo.chain; + const denomToTransfer = denom || staking?.staking_tokens?.[0].denom; + if (!denomToTransfer) throw Error(`no denom for ${chainName}`); + + const { client, address, wallet } = await createFundedWalletAndClient( + t.log, + chainName, + useChain, + ); + const balancesResult = await retryUntilCondition( + () => client.getAllBalances(address), + coins => !!coins?.length, + `Faucet balances found for ${address}`, + ); + console.log('Balances:', balancesResult); + + const transferArgs = makeIBCTransferMsg( + { denom: denomToTransfer, value: amount }, + { address: agoricAddr, chainName: 'agoric' }, + { address: address, chainName }, + Date.now(), + useChain, + ); + console.log('Transfer Args:', transferArgs); + // TODO #9200 `sendIbcTokens` does not support `memo` + // @ts-expect-error spread argument for concise code + const txRes = await client.sendIbcTokens(...transferArgs); + if (txRes && txRes.code !== 0) { + console.error(txRes); + throw Error(`failed to ibc transfer funds to ${chainName}`); + } + const { events: _events, ...txRest } = txRes; + console.log(txRest); + t.is(txRes.code, 0, `Transaction succeeded`); + t.log(`Funds transferred to ${agoricAddr}`); + return { + client, + address, + wallet, + }; + }; +}; diff --git a/multichain-testing/tools/sleep.ts b/multichain-testing/tools/sleep.ts index 66251a87dca..1b0d1a58807 100644 --- a/multichain-testing/tools/sleep.ts +++ b/multichain-testing/tools/sleep.ts @@ -75,3 +75,5 @@ export const makeRetryUntilCondition = (defaultOptions: RetryOptions = {}) => { ...options, }); }; + +export type RetryUntilCondition = ReturnType; From 748883d97b625a2a98f2253799d6e6baac3de4f1 Mon Sep 17 00:00:00 2001 From: 0xPatrick Date: Sat, 30 Nov 2024 04:38:44 -0500 Subject: [PATCH 45/56] test: send-anywhere pfm scenarios --- multichain-testing/test/send-anywhere.test.ts | 50 +++++++++++-------- .../src/proposals/start-send-anywhere.js | 29 +++++++++-- 2 files changed, 53 insertions(+), 26 deletions(-) diff --git a/multichain-testing/test/send-anywhere.test.ts b/multichain-testing/test/send-anywhere.test.ts index f1a8a720e5f..11508f22cc6 100644 --- a/multichain-testing/test/send-anywhere.test.ts +++ b/multichain-testing/test/send-anywhere.test.ts @@ -21,7 +21,8 @@ const contractBuilder = test.before(async t => { const { setupTestKeys, ...common } = await commonSetup(t); - const { assetInfo, chainInfo, deleteTestKeys, startContract } = common; + const { assetInfo, chainInfo, deleteTestKeys, faucetTools, startContract } = + common; deleteTestKeys(accounts).catch(); const wallets = await setupTestKeys(accounts); t.context = { ...common, wallets }; @@ -30,6 +31,11 @@ test.before(async t => { chainInfo, assetInfo, }); + + await faucetTools.fundFaucet([ + ['cosmoshub', 'uatom'], + ['osmosis', 'uosmo'], + ]); }); test.after(async t => { @@ -37,12 +43,14 @@ test.after(async t => { deleteTestKeys(accounts); }); +type BrandKW = 'IST' | 'OSMO' | 'ATOM'; + const sendAnywhereScenario = test.macro({ - title: (_, chainName: string, acctIdx: number) => - `send-anywhere ${chainName}${acctIdx}`, - exec: async (t, chainName: string, acctIdx: number) => { - const config = chainConfig[chainName]; - if (!config) return t.fail(`Unknown chain: ${chainName}`); + title: (_, destChainName: string, acctIdx: number, brandKw: BrandKW) => + `send-anywhere ${brandKw} from agoric to ${destChainName}${acctIdx}`, + exec: async (t, destChainName: string, acctIdx: number, brandKw: BrandKW) => { + const config = chainConfig[destChainName]; + if (!config) return t.fail(`Unknown chain: ${destChainName}`); const { wallets, @@ -53,13 +61,13 @@ const sendAnywhereScenario = test.macro({ } = t.context; t.log('Create a receiving wallet for the send-anywhere transfer'); - const chain = useChain(chainName).chain; + const chain = useChain(destChainName).chain; t.log('Create an agoric smart wallet to initiate send-anywhere transfer'); - const agoricAddr = wallets[`${chainName}${acctIdx}`]; + const agoricAddr = wallets[`${destChainName}${acctIdx}`]; const wdUser1 = await provisionSmartWallet(agoricAddr, { - BLD: 100_000n, - IST: 100_000n, + BLD: 1_000n, + [brandKw]: 1_000n, }); t.log(`provisioning agoric smart wallet for ${agoricAddr}`); @@ -68,11 +76,11 @@ const sendAnywhereScenario = test.macro({ const brands = await vstorageClient.queryData( 'published.agoricNames.brand', ); - const istBrand = Object.fromEntries(brands).IST; + const brand = Object.fromEntries(brands)[brandKw]; - const apiUrl = await useChain(chainName).getRestEndpoint(); + const apiUrl = await useChain(destChainName).getRestEndpoint(); const queryClient = makeQueryClient(apiUrl); - t.log(`Made ${chainName} query client`); + t.log(`Made ${destChainName} query client`); const doSendAnywhere = async (amount: Amount) => { t.log(`Sending ${amount.value} ${amount.brand}.`); @@ -83,8 +91,8 @@ const sendAnywhereScenario = test.macro({ encoding: 'bech32', }; t.log('Will send payment to:', receiver); - t.log(`${chainName} offer`); - const offerId = `${chainName}-makeSendInvitation-${Date.now()}`; + t.log(`${destChainName} offer`); + const offerId = `${destChainName}-makeSendInvitation-${Date.now()}`; await doOffer({ id: offerId, invitationSpec: { @@ -92,7 +100,7 @@ const sendAnywhereScenario = test.macro({ instancePath: [contractName], callPipe: [['makeSendInvitation']], }, - offerArgs: { destAddr: receiver.value, chainName }, + offerArgs: { destAddr: receiver.value, chainName: destChainName }, proposal: { give: { Send: amount } }, }); @@ -123,12 +131,12 @@ const sendAnywhereScenario = test.macro({ console.log(`${agoricAddr} offer amounts:`, offerAmounts); for (const value of offerAmounts) { - await doSendAnywhere(AmountMath.make(istBrand, value)); + await doSendAnywhere(AmountMath.make(brand, value)); } }, }); -test.serial(sendAnywhereScenario, 'osmosis', 1); -test.serial(sendAnywhereScenario, 'osmosis', 2); -test.serial(sendAnywhereScenario, 'cosmoshub', 1); -test.serial(sendAnywhereScenario, 'cosmoshub', 2); +test.serial(sendAnywhereScenario, 'osmosis', 1, 'IST'); +test.serial(sendAnywhereScenario, 'osmosis', 2, 'ATOM'); // exercises PFM (agoric -> cosmoshub -> osmosis) +test.serial(sendAnywhereScenario, 'cosmoshub', 1, 'IST'); +test.serial(sendAnywhereScenario, 'cosmoshub', 2, 'OSMO'); // exercises PFM (agoric -> osmosis -> cosmoshub) diff --git a/packages/orchestration/src/proposals/start-send-anywhere.js b/packages/orchestration/src/proposals/start-send-anywhere.js index b0db84c3f32..0599f077dd9 100644 --- a/packages/orchestration/src/proposals/start-send-anywhere.js +++ b/packages/orchestration/src/proposals/start-send-anywhere.js @@ -31,7 +31,6 @@ const trace = makeTracer('StartSA', true); * consume: { * BLD: Issuer<'nat'>; * IST: Issuer<'nat'>; - * USDC: Issuer<'nat'>; * }; * }; * }} powers @@ -84,13 +83,33 @@ export const startSendAnywhere = async ( }), ); + /** @param {() => Promise} p */ + const safeFulfill = async p => + E.when( + p(), + i => i, + () => undefined, + ); + + const atomIssuer = await safeFulfill(() => + E(agoricNames).lookup('issuer', 'ATOM'), + ); + const osmoIssuer = await safeFulfill(() => + E(agoricNames).lookup('issuer', 'OSMO'), + ); + + const issuerKeywordRecord = harden({ + BLD: await BLD, + IST: await IST, + ...(atomIssuer && { ATOM: atomIssuer }), + ...(osmoIssuer && { OSMO: osmoIssuer }), + }); + trace('issuerKeywordRecord', issuerKeywordRecord); + const { instance } = await E(startUpgradable)({ label: 'send-anywhere', installation: sendAnywhere, - issuerKeywordRecord: { - Stable: await IST, - Stake: await BLD, - }, + issuerKeywordRecord, privateArgs, }); produceInstance.resolve(instance); From 5d4f84c0d911e3d2745c0e3a2003b93a87dd2545 Mon Sep 17 00:00:00 2001 From: Dan Connolly Date: Tue, 3 Dec 2024 00:22:13 -0600 Subject: [PATCH 46/56] refactor(fast-usdc): inject io to addOperatorCommands --- packages/fast-usdc/src/cli/cli.js | 15 +++++++++- .../fast-usdc/src/cli/operator-commands.js | 30 +++++++++---------- 2 files changed, 28 insertions(+), 17 deletions(-) diff --git a/packages/fast-usdc/src/cli/cli.js b/packages/fast-usdc/src/cli/cli.js index 56a74fbc25b..afaf1eadf9a 100644 --- a/packages/fast-usdc/src/cli/cli.js +++ b/packages/fast-usdc/src/cli/cli.js @@ -1,3 +1,5 @@ +/* eslint-env node */ +/* global globalThis */ import { assertParsableNumber } from '@agoric/zoe/src/contractSupport/ratio.js'; import { Command, @@ -34,6 +36,11 @@ export const initProgram = ( writeFile = writeAsync, mkdir = mkdirSync, exists = existsSync, + fetch = globalThis.fetch, + stdout = process.stdout, + stderr = process.stderr, + env = process.env, + now = () => Date.now(), ) => { const program = new Command(); @@ -56,7 +63,13 @@ export const initProgram = ( }; addConfigCommands(program, configHelpers, makeConfigFile); - addOperatorCommands(program); + addOperatorCommands(program, { + fetch, + stdout, + stderr, + env, + now, + }); /** @param {string} value */ const parseDecimal = value => { diff --git a/packages/fast-usdc/src/cli/operator-commands.js b/packages/fast-usdc/src/cli/operator-commands.js index 3542bdcf074..73f380b2460 100644 --- a/packages/fast-usdc/src/cli/operator-commands.js +++ b/packages/fast-usdc/src/cli/operator-commands.js @@ -1,4 +1,3 @@ -/* eslint-env node */ /** * @import {Command} from 'commander'; * @import {OfferSpec} from '@agoric/smart-wallet/src/offers.js'; @@ -11,8 +10,18 @@ import { outputActionAndHint } from './bridge-action.js'; /** * @param {Command} program + * @param {{ + * fetch: Window['fetch']; + * stdout: typeof process.stdout; + * stderr: typeof process.stderr; + * env: typeof process.env; + * now: typeof Date.now; + * }} io */ -export const addOperatorCommands = program => { +export const addOperatorCommands = ( + program, + { fetch, stderr, stdout, env, now }, +) => { const operator = program .command('operator') .description('Oracle operator commands'); @@ -24,17 +33,9 @@ export const addOperatorCommands = program => { 'after', '\nPipe the STDOUT to a file such as accept.json, then use the Agoric CLI to broadcast it:\n agoric wallet send --offer accept.json --from gov1 --keyring-backend="test"', ) - .option( - '--offerId ', - 'Offer id', - String, - `operatorAccept-${Date.now()}`, - ) + .option('--offerId ', 'Offer id', String, `operatorAccept-${now()}`) .action(async opts => { - const networkConfig = await fetchEnvNetworkConfig({ - env: process.env, - fetch, - }); + const networkConfig = await fetchEnvNetworkConfig({ env, fetch }); const vsk = await makeVstorageKit({ fetch }, networkConfig); const instance = vsk.agoricNames.instance.fastUsdc; assert(instance, 'fastUsdc instance not in agoricNames'); @@ -56,10 +57,7 @@ export const addOperatorCommands = program => { offer, }; - outputActionAndHint(bridgeAction, { - stderr: process.stderr, - stdout: process.stdout, - }); + outputActionAndHint(bridgeAction, { stderr, stdout }); }); operator From 448aa3a194b55ebeb5423f0027c543f8c6807239 Mon Sep 17 00:00:00 2001 From: Dan Connolly Date: Tue, 3 Dec 2024 01:16:12 -0600 Subject: [PATCH 47/56] feat(fast-usdc): operator attest cli command using a LegibleCapData blob arg --- .../fast-usdc/src/cli/operator-commands.js | 38 +++++++- .../test/cli/operator-commands.test.ts | 96 +++++++++++++++++++ 2 files changed, 129 insertions(+), 5 deletions(-) create mode 100644 packages/fast-usdc/test/cli/operator-commands.test.ts diff --git a/packages/fast-usdc/src/cli/operator-commands.js b/packages/fast-usdc/src/cli/operator-commands.js index 73f380b2460..a9312cb4240 100644 --- a/packages/fast-usdc/src/cli/operator-commands.js +++ b/packages/fast-usdc/src/cli/operator-commands.js @@ -2,11 +2,22 @@ * @import {Command} from 'commander'; * @import {OfferSpec} from '@agoric/smart-wallet/src/offers.js'; * @import {ExecuteOfferAction} from '@agoric/smart-wallet/src/smartWallet.js'; + * @import {OperatorKit} from '../exos/operator-kit.js'; */ import { fetchEnvNetworkConfig, makeVstorageKit } from '@agoric/client-utils'; +import { mustMatch } from '@agoric/internal'; import { INVITATION_MAKERS_DESC } from '../exos/transaction-feed.js'; +import { CctpTxEvidenceShape } from '../type-guards.js'; import { outputActionAndHint } from './bridge-action.js'; +import { fromExternalConfig } from '../utils/config-marshal.js'; + +/** @param {string} arg */ +const parseCCTPEvidence = arg => { + const evidence = fromExternalConfig(JSON.parse(arg), {}); + mustMatch(evidence, CctpTxEvidenceShape); + return evidence; +}; /** * @param {Command} program @@ -64,11 +75,28 @@ export const addOperatorCommands = ( .command('attest') .description('Attest to an observed Fast USDC transfer') .requiredOption('--previousOfferId ', 'Offer id', String) - .action(async options => { - const { previousOfferId } = options; - console.error( - 'TODO: Implement attest logic for request:', - previousOfferId, + .requiredOption('--evidence ', 'CCTP evidence', parseCCTPEvidence) + .option('--offerId ', 'Offer id', String, `operatorAttest-${now()}`) + .action(async opts => { + const { previousOfferId, evidence } = opts; + + /** @type {OfferSpec} */ + const offer = { + id: opts.offerId, + invitationSpec: { + source: 'continuing', + previousOffer: previousOfferId, + /** @type {string & keyof OperatorKit['invitationMakers'] } */ + invitationMakerName: 'SubmitEvidence', + /** @type {Parameters } */ + invitationArgs: [evidence], + }, + proposal: {}, + }; + + outputActionAndHint( + { method: 'executeOffer', offer }, + { stderr, stdout }, ); }); diff --git a/packages/fast-usdc/test/cli/operator-commands.test.ts b/packages/fast-usdc/test/cli/operator-commands.test.ts new file mode 100644 index 00000000000..c8885b05029 --- /dev/null +++ b/packages/fast-usdc/test/cli/operator-commands.test.ts @@ -0,0 +1,96 @@ +import test from 'ava'; +import { Command } from 'commander'; +import type { Passable } from '@endo/pass-style'; +import { addOperatorCommands } from '../../src/cli/operator-commands.js'; +import { MockCctpTxEvidences } from '../fixtures.js'; +import { toExternalConfig } from '../../src/utils/config-marshal.js'; + +export const flags = ( + record: Record, +): string[] => { + // @ts-expect-error undefined is filtered out + const skipUndef: [string, string][] = Object.entries(record).filter( + ([_k, v]) => v !== undefined, + ); + return skipUndef.map(([k, v]) => [`--${k}`, v]).flat(); +}; + +test('fast-usdc operator attest sub-command', async t => { + const evidence = harden( + MockCctpTxEvidences.AGORIC_PLUS_DYDX(), + ) as unknown as Passable; + const argv = [ + ...`node fast-usdc operator attest`.split(' '), + ...flags({ + previousOfferId: 123, + evidence: JSON.stringify(toExternalConfig(evidence, {})), + }), + ]; + const program = new Command(); + program.exitOverride(); + const out = [] as string[]; + const err = [] as string[]; + + addOperatorCommands(program, { + fetch: null as unknown as Window['fetch'], + stdout: { + write: txt => { + out.push(txt); + return true; + }, + } as unknown as typeof process.stdout, + stderr: { + write: txt => { + err.push(txt); + return true; + }, + } as unknown as typeof process.stderr, + env: {}, + now: () => 1234, + }); + + await program.parseAsync(argv); + + t.deepEqual(out, [ + JSON.stringify({ + body: `#${JSON.stringify({ + method: 'executeOffer', + offer: { + id: 'operatorAttest-1234', + invitationSpec: { + invitationArgs: [ + { + aux: { + forwardingChannel: 'channel-21', + recipientAddress: + 'agoric16kv2g7snfc4q24vg3pjdlnnqgngtjpwtetd2h689nz09lcklvh5s8u37ek?EUD=dydx183dejcnmkka5dzcu9xw6mywq0p2m5peks28men', + }, + blockHash: + '0x80d7343e04f8160892e94f02d6a9b9f255663ed0ac34caca98544c8143fee699', + blockNumber: '+21037669', + blockTimestamp: '+1730762099', + chainId: 1, + tx: { + amount: '+300000000', + forwardingAddress: + 'noble1x0ydg69dh6fqvr27xjvp6maqmrldam6yfelktz', + }, + txHash: + '0xd81bc6105b60a234c7c50ac17816ebcd5561d366df8bf3be59ff387552761799', + }, + ], + invitationMakerName: 'SubmitEvidence', + previousOffer: '123', + source: 'continuing', + }, + proposal: {}, + }, + })}`, + slots: [], + }), + '\n', + ]); + t.deepEqual(err, [ + 'Now use `agoric wallet send ...` to sign and broadcast the offer.\n', + ]); +}); From c6a2123970a3687fe85c9a2d83f2ffe403cbc368 Mon Sep 17 00:00:00 2001 From: Dan Connolly Date: Tue, 3 Dec 2024 01:38:27 -0600 Subject: [PATCH 48/56] chore(fast-usdc): use an arg for each evidence property --- packages/fast-usdc/package.json | 1 + .../fast-usdc/src/cli/operator-commands.js | 45 +++++++++++++++---- .../test/cli/operator-commands.test.ts | 16 +++++-- 3 files changed, 51 insertions(+), 11 deletions(-) diff --git a/packages/fast-usdc/package.json b/packages/fast-usdc/package.json index 007e1e90140..22759fefcd8 100644 --- a/packages/fast-usdc/package.json +++ b/packages/fast-usdc/package.json @@ -49,6 +49,7 @@ "@endo/far": "^1.1.9", "@endo/init": "^1.1.7", "@endo/marshal": "^1.6.2", + "@endo/nat": "^5.0.13", "@endo/pass-style": "^1.4.7", "@endo/patterns": "^1.4.7", "@endo/promise-kit": "^1.1.8", diff --git a/packages/fast-usdc/src/cli/operator-commands.js b/packages/fast-usdc/src/cli/operator-commands.js index a9312cb4240..06a3fdc01df 100644 --- a/packages/fast-usdc/src/cli/operator-commands.js +++ b/packages/fast-usdc/src/cli/operator-commands.js @@ -7,16 +7,22 @@ import { fetchEnvNetworkConfig, makeVstorageKit } from '@agoric/client-utils'; import { mustMatch } from '@agoric/internal'; +import { Nat } from '@endo/nat'; +import { InvalidArgumentError } from 'commander'; import { INVITATION_MAKERS_DESC } from '../exos/transaction-feed.js'; import { CctpTxEvidenceShape } from '../type-guards.js'; import { outputActionAndHint } from './bridge-action.js'; -import { fromExternalConfig } from '../utils/config-marshal.js'; /** @param {string} arg */ -const parseCCTPEvidence = arg => { - const evidence = fromExternalConfig(JSON.parse(arg), {}); - mustMatch(evidence, CctpTxEvidenceShape); - return evidence; +const parseNat = arg => { + const n = Nat(BigInt(arg)); + return n; +}; + +/** @param {string} arg */ +const parseHex = arg => { + if (!arg.startsWith('0x')) throw new InvalidArgumentError('not a hex string'); + return arg; }; /** @@ -75,14 +81,37 @@ export const addOperatorCommands = ( .command('attest') .description('Attest to an observed Fast USDC transfer') .requiredOption('--previousOfferId ', 'Offer id', String) - .requiredOption('--evidence ', 'CCTP evidence', parseCCTPEvidence) + .requiredOption('--forwardingChannel ', 'Channel id', String) + .requiredOption('--recipientAddress ', 'bech32 address', String) + .requiredOption('--blockHash <0xhex>', 'hex hash', parseHex) + .requiredOption('--blockNumber ', 'number', parseNat) + .requiredOption('--blockTimestamp ', 'number', parseNat) + .requiredOption('--chainId ', 'chain id', Number) + .requiredOption('--amount ', 'number', parseNat) + .requiredOption('--forwardingAddress ', 'bech32 address', String) + .requiredOption('--txHash <0xhexo>', 'hex hash', parseHex) .option('--offerId ', 'Offer id', String, `operatorAttest-${now()}`) .action(async opts => { - const { previousOfferId, evidence } = opts; + const { + offerId, + previousOfferId, + forwardingChannel, + recipientAddress, + amount, + forwardingAddress, + ...flat + } = opts; + + const evidence = harden({ + aux: { forwardingChannel, recipientAddress }, + tx: { amount, forwardingAddress }, + ...flat, + }); + mustMatch(evidence, CctpTxEvidenceShape); /** @type {OfferSpec} */ const offer = { - id: opts.offerId, + id: offerId, invitationSpec: { source: 'continuing', previousOffer: previousOfferId, diff --git a/packages/fast-usdc/test/cli/operator-commands.test.ts b/packages/fast-usdc/test/cli/operator-commands.test.ts index c8885b05029..02b7d38e0d8 100644 --- a/packages/fast-usdc/test/cli/operator-commands.test.ts +++ b/packages/fast-usdc/test/cli/operator-commands.test.ts @@ -1,9 +1,8 @@ +import type { Passable } from '@endo/pass-style'; import test from 'ava'; import { Command } from 'commander'; -import type { Passable } from '@endo/pass-style'; import { addOperatorCommands } from '../../src/cli/operator-commands.js'; import { MockCctpTxEvidences } from '../fixtures.js'; -import { toExternalConfig } from '../../src/utils/config-marshal.js'; export const flags = ( record: Record, @@ -23,7 +22,18 @@ test('fast-usdc operator attest sub-command', async t => { ...`node fast-usdc operator attest`.split(' '), ...flags({ previousOfferId: 123, - evidence: JSON.stringify(toExternalConfig(evidence, {})), + forwardingChannel: 'channel-21', + recipientAddress: + 'agoric16kv2g7snfc4q24vg3pjdlnnqgngtjpwtetd2h689nz09lcklvh5s8u37ek?EUD=dydx183dejcnmkka5dzcu9xw6mywq0p2m5peks28men', + blockHash: + '0x80d7343e04f8160892e94f02d6a9b9f255663ed0ac34caca98544c8143fee699', + blockNumber: 21037669, + blockTimestamp: 1730762099, + chainId: 1, + amount: 300000000, + forwardingAddress: 'noble1x0ydg69dh6fqvr27xjvp6maqmrldam6yfelktz', + txHash: + '0xd81bc6105b60a234c7c50ac17816ebcd5561d366df8bf3be59ff387552761799', }), ]; const program = new Command(); From f1df99f8d431d1b9a26f2687aa2c4c80a17537c0 Mon Sep 17 00:00:00 2001 From: Dan Connolly Date: Tue, 3 Dec 2024 01:43:40 -0600 Subject: [PATCH 49/56] chore: don't kludge fromCapData --- .../test/cli/operator-commands.test.ts | 79 +++++++++---------- 1 file changed, 39 insertions(+), 40 deletions(-) diff --git a/packages/fast-usdc/test/cli/operator-commands.test.ts b/packages/fast-usdc/test/cli/operator-commands.test.ts index 02b7d38e0d8..ff0b7157888 100644 --- a/packages/fast-usdc/test/cli/operator-commands.test.ts +++ b/packages/fast-usdc/test/cli/operator-commands.test.ts @@ -3,6 +3,7 @@ import test from 'ava'; import { Command } from 'commander'; import { addOperatorCommands } from '../../src/cli/operator-commands.js'; import { MockCctpTxEvidences } from '../fixtures.js'; +import { makeMarshal } from '@endo/marshal'; export const flags = ( record: Record, @@ -14,6 +15,8 @@ export const flags = ( return skipUndef.map(([k, v]) => [`--${k}`, v]).flat(); }; +const marshalData = makeMarshal(_v => assert.fail('data only')); + test('fast-usdc operator attest sub-command', async t => { const evidence = harden( MockCctpTxEvidences.AGORIC_PLUS_DYDX(), @@ -61,46 +64,42 @@ test('fast-usdc operator attest sub-command', async t => { await program.parseAsync(argv); - t.deepEqual(out, [ - JSON.stringify({ - body: `#${JSON.stringify({ - method: 'executeOffer', - offer: { - id: 'operatorAttest-1234', - invitationSpec: { - invitationArgs: [ - { - aux: { - forwardingChannel: 'channel-21', - recipientAddress: - 'agoric16kv2g7snfc4q24vg3pjdlnnqgngtjpwtetd2h689nz09lcklvh5s8u37ek?EUD=dydx183dejcnmkka5dzcu9xw6mywq0p2m5peks28men', - }, - blockHash: - '0x80d7343e04f8160892e94f02d6a9b9f255663ed0ac34caca98544c8143fee699', - blockNumber: '+21037669', - blockTimestamp: '+1730762099', - chainId: 1, - tx: { - amount: '+300000000', - forwardingAddress: - 'noble1x0ydg69dh6fqvr27xjvp6maqmrldam6yfelktz', - }, - txHash: - '0xd81bc6105b60a234c7c50ac17816ebcd5561d366df8bf3be59ff387552761799', - }, - ], - invitationMakerName: 'SubmitEvidence', - previousOffer: '123', - source: 'continuing', + const action = marshalData.fromCapData(JSON.parse(out.join(''))); + t.deepEqual(action, { + method: 'executeOffer', + offer: { + id: 'operatorAttest-1234', + invitationSpec: { + invitationArgs: [ + { + aux: { + forwardingChannel: 'channel-21', + recipientAddress: + 'agoric16kv2g7snfc4q24vg3pjdlnnqgngtjpwtetd2h689nz09lcklvh5s8u37ek?EUD=dydx183dejcnmkka5dzcu9xw6mywq0p2m5peks28men', + }, + blockHash: + '0x80d7343e04f8160892e94f02d6a9b9f255663ed0ac34caca98544c8143fee699', + blockNumber: 21037669n, + blockTimestamp: 1730762099n, + chainId: 1, + tx: { + amount: 300000000n, + forwardingAddress: 'noble1x0ydg69dh6fqvr27xjvp6maqmrldam6yfelktz', + }, + txHash: + '0xd81bc6105b60a234c7c50ac17816ebcd5561d366df8bf3be59ff387552761799', }, - proposal: {}, - }, - })}`, - slots: [], - }), - '\n', - ]); - t.deepEqual(err, [ + ], + invitationMakerName: 'SubmitEvidence', + previousOffer: '123', + source: 'continuing', + }, + proposal: {}, + }, + }); + + t.is( + err.join(''), 'Now use `agoric wallet send ...` to sign and broadcast the offer.\n', - ]); + ); }); From 11df834abbc903ca49dc42501dd89aea034aaaaa Mon Sep 17 00:00:00 2001 From: Dan Connolly Date: Tue, 3 Dec 2024 01:48:06 -0600 Subject: [PATCH 50/56] chore: avoid magic strings in attest test --- .../test/cli/operator-commands.test.ts | 47 ++++--------------- 1 file changed, 10 insertions(+), 37 deletions(-) diff --git a/packages/fast-usdc/test/cli/operator-commands.test.ts b/packages/fast-usdc/test/cli/operator-commands.test.ts index ff0b7157888..3c58b9b5dab 100644 --- a/packages/fast-usdc/test/cli/operator-commands.test.ts +++ b/packages/fast-usdc/test/cli/operator-commands.test.ts @@ -6,37 +6,29 @@ import { MockCctpTxEvidences } from '../fixtures.js'; import { makeMarshal } from '@endo/marshal'; export const flags = ( - record: Record, + record: Record, ): string[] => { // @ts-expect-error undefined is filtered out const skipUndef: [string, string][] = Object.entries(record).filter( ([_k, v]) => v !== undefined, ); - return skipUndef.map(([k, v]) => [`--${k}`, v]).flat(); + return skipUndef.map(([k, v]) => [`--${k}`, `${v}`]).flat(); }; const marshalData = makeMarshal(_v => assert.fail('data only')); test('fast-usdc operator attest sub-command', async t => { - const evidence = harden( - MockCctpTxEvidences.AGORIC_PLUS_DYDX(), - ) as unknown as Passable; + const evidence = harden(MockCctpTxEvidences.AGORIC_PLUS_DYDX()); + const { aux, tx, ...flat } = evidence; const argv = [ ...`node fast-usdc operator attest`.split(' '), ...flags({ previousOfferId: 123, - forwardingChannel: 'channel-21', - recipientAddress: - 'agoric16kv2g7snfc4q24vg3pjdlnnqgngtjpwtetd2h689nz09lcklvh5s8u37ek?EUD=dydx183dejcnmkka5dzcu9xw6mywq0p2m5peks28men', - blockHash: - '0x80d7343e04f8160892e94f02d6a9b9f255663ed0ac34caca98544c8143fee699', - blockNumber: 21037669, - blockTimestamp: 1730762099, - chainId: 1, - amount: 300000000, - forwardingAddress: 'noble1x0ydg69dh6fqvr27xjvp6maqmrldam6yfelktz', - txHash: - '0xd81bc6105b60a234c7c50ac17816ebcd5561d366df8bf3be59ff387552761799', + forwardingChannel: aux.forwardingChannel, + recipientAddress: aux.recipientAddress, + amount: tx.amount, + forwardingAddress: tx.forwardingAddress, + ...flat, }), ]; const program = new Command(); @@ -70,26 +62,7 @@ test('fast-usdc operator attest sub-command', async t => { offer: { id: 'operatorAttest-1234', invitationSpec: { - invitationArgs: [ - { - aux: { - forwardingChannel: 'channel-21', - recipientAddress: - 'agoric16kv2g7snfc4q24vg3pjdlnnqgngtjpwtetd2h689nz09lcklvh5s8u37ek?EUD=dydx183dejcnmkka5dzcu9xw6mywq0p2m5peks28men', - }, - blockHash: - '0x80d7343e04f8160892e94f02d6a9b9f255663ed0ac34caca98544c8143fee699', - blockNumber: 21037669n, - blockTimestamp: 1730762099n, - chainId: 1, - tx: { - amount: 300000000n, - forwardingAddress: 'noble1x0ydg69dh6fqvr27xjvp6maqmrldam6yfelktz', - }, - txHash: - '0xd81bc6105b60a234c7c50ac17816ebcd5561d366df8bf3be59ff387552761799', - }, - ], + invitationArgs: [evidence], invitationMakerName: 'SubmitEvidence', previousOffer: '123', source: 'continuing', From 843ad24f5cc4becf547ae54acde4b4289d6033b2 Mon Sep 17 00:00:00 2001 From: Dan Connolly Date: Tue, 3 Dec 2024 11:13:07 -0600 Subject: [PATCH 51/56] refactor: mockStream, concise flags --- .../test/cli/operator-commands.test.ts | 29 +++++-------------- 1 file changed, 8 insertions(+), 21 deletions(-) diff --git a/packages/fast-usdc/test/cli/operator-commands.test.ts b/packages/fast-usdc/test/cli/operator-commands.test.ts index 3c58b9b5dab..b0e25b26109 100644 --- a/packages/fast-usdc/test/cli/operator-commands.test.ts +++ b/packages/fast-usdc/test/cli/operator-commands.test.ts @@ -1,9 +1,9 @@ -import type { Passable } from '@endo/pass-style'; import test from 'ava'; import { Command } from 'commander'; import { addOperatorCommands } from '../../src/cli/operator-commands.js'; import { MockCctpTxEvidences } from '../fixtures.js'; import { makeMarshal } from '@endo/marshal'; +import type { Writable } from 'node:stream'; export const flags = ( record: Record, @@ -17,20 +17,17 @@ export const flags = ( const marshalData = makeMarshal(_v => assert.fail('data only')); +const mockStream = (buf: string[]): T => + ({ write: txt => (buf.push(txt), true) }) as T; + test('fast-usdc operator attest sub-command', async t => { const evidence = harden(MockCctpTxEvidences.AGORIC_PLUS_DYDX()); const { aux, tx, ...flat } = evidence; const argv = [ ...`node fast-usdc operator attest`.split(' '), - ...flags({ - previousOfferId: 123, - forwardingChannel: aux.forwardingChannel, - recipientAddress: aux.recipientAddress, - amount: tx.amount, - forwardingAddress: tx.forwardingAddress, - ...flat, - }), + ...flags({ previousOfferId: 123, ...aux, ...tx, ...flat }), ]; + t.log(...argv); const program = new Command(); program.exitOverride(); const out = [] as string[]; @@ -38,18 +35,8 @@ test('fast-usdc operator attest sub-command', async t => { addOperatorCommands(program, { fetch: null as unknown as Window['fetch'], - stdout: { - write: txt => { - out.push(txt); - return true; - }, - } as unknown as typeof process.stdout, - stderr: { - write: txt => { - err.push(txt); - return true; - }, - } as unknown as typeof process.stderr, + stdout: mockStream(out), + stderr: mockStream(err), env: {}, now: () => 1234, }); From ccb969e105689d5454f9519820bdf4b3eac97025 Mon Sep 17 00:00:00 2001 From: Dan Connolly Date: Tue, 3 Dec 2024 13:43:09 -0600 Subject: [PATCH 52/56] refactor: move mockStream(...) to fast-usdc/tools/ --- packages/fast-usdc/package.json | 3 ++- .../fast-usdc/test/cli/operator-commands.test.ts | 7 ++----- packages/fast-usdc/tools/mock-io.ts | 14 ++++++++++++++ 3 files changed, 18 insertions(+), 6 deletions(-) create mode 100644 packages/fast-usdc/tools/mock-io.ts diff --git a/packages/fast-usdc/package.json b/packages/fast-usdc/package.json index 22759fefcd8..0643f9bf809 100644 --- a/packages/fast-usdc/package.json +++ b/packages/fast-usdc/package.json @@ -5,7 +5,8 @@ "type": "module", "files": [ "contract", - "src" + "src", + "tools" ], "bin": { "fast-usdc": "./src/cli/bin.js" diff --git a/packages/fast-usdc/test/cli/operator-commands.test.ts b/packages/fast-usdc/test/cli/operator-commands.test.ts index b0e25b26109..0dcc411cf73 100644 --- a/packages/fast-usdc/test/cli/operator-commands.test.ts +++ b/packages/fast-usdc/test/cli/operator-commands.test.ts @@ -1,9 +1,9 @@ +import { makeMarshal } from '@endo/marshal'; import test from 'ava'; import { Command } from 'commander'; import { addOperatorCommands } from '../../src/cli/operator-commands.js'; +import { mockStream } from '../../tools/mock-io.js'; import { MockCctpTxEvidences } from '../fixtures.js'; -import { makeMarshal } from '@endo/marshal'; -import type { Writable } from 'node:stream'; export const flags = ( record: Record, @@ -17,9 +17,6 @@ export const flags = ( const marshalData = makeMarshal(_v => assert.fail('data only')); -const mockStream = (buf: string[]): T => - ({ write: txt => (buf.push(txt), true) }) as T; - test('fast-usdc operator attest sub-command', async t => { const evidence = harden(MockCctpTxEvidences.AGORIC_PLUS_DYDX()); const { aux, tx, ...flat } = evidence; diff --git a/packages/fast-usdc/tools/mock-io.ts b/packages/fast-usdc/tools/mock-io.ts new file mode 100644 index 00000000000..0cb6ced28e6 --- /dev/null +++ b/packages/fast-usdc/tools/mock-io.ts @@ -0,0 +1,14 @@ +import type { Writable } from 'node:stream'; + +/** + * mock stdout / stderr, for example + * + * @param buf - caller-provided buffer for written data + */ +export const mockStream = (buf: string[]): T => + ({ + write: txt => { + buf.push(txt); + return true; + }, + }) as T; From 8674c750bd0db5a6e33049d4b994016b0b9e52b3 Mon Sep 17 00:00:00 2001 From: Dan Connolly Date: Tue, 3 Dec 2024 13:47:16 -0600 Subject: [PATCH 53/56] refactor: move flags() to fast-usdc/tools/ --- packages/fast-usdc/test/cli/operator-commands.test.ts | 11 +---------- packages/fast-usdc/tools/cli-tools.ts | 9 +++++++++ 2 files changed, 10 insertions(+), 10 deletions(-) create mode 100644 packages/fast-usdc/tools/cli-tools.ts diff --git a/packages/fast-usdc/test/cli/operator-commands.test.ts b/packages/fast-usdc/test/cli/operator-commands.test.ts index 0dcc411cf73..36c645adb8a 100644 --- a/packages/fast-usdc/test/cli/operator-commands.test.ts +++ b/packages/fast-usdc/test/cli/operator-commands.test.ts @@ -2,19 +2,10 @@ import { makeMarshal } from '@endo/marshal'; import test from 'ava'; import { Command } from 'commander'; import { addOperatorCommands } from '../../src/cli/operator-commands.js'; +import { flags } from '../../tools/cli-tools.js'; import { mockStream } from '../../tools/mock-io.js'; import { MockCctpTxEvidences } from '../fixtures.js'; -export const flags = ( - record: Record, -): string[] => { - // @ts-expect-error undefined is filtered out - const skipUndef: [string, string][] = Object.entries(record).filter( - ([_k, v]) => v !== undefined, - ); - return skipUndef.map(([k, v]) => [`--${k}`, `${v}`]).flat(); -}; - const marshalData = makeMarshal(_v => assert.fail('data only')); test('fast-usdc operator attest sub-command', async t => { diff --git a/packages/fast-usdc/tools/cli-tools.ts b/packages/fast-usdc/tools/cli-tools.ts new file mode 100644 index 00000000000..12af12653e3 --- /dev/null +++ b/packages/fast-usdc/tools/cli-tools.ts @@ -0,0 +1,9 @@ +export const flags = ( + record: Record, +): string[] => { + // @ts-expect-error undefined is filtered out + const skipUndef: [string, string][] = Object.entries(record).filter( + ([_k, v]) => v !== undefined, + ); + return skipUndef.map(([k, v]) => [`--${k}`, `${v}`]).flat(); +}; From 13e68a99c21418368df9e4276cc10cd10190e54e Mon Sep 17 00:00:00 2001 From: Dan Connolly Date: Tue, 3 Dec 2024 13:59:26 -0600 Subject: [PATCH 54/56] chore: use AGORIC_NET for agoric RPC endpoint in transfer cmd --- packages/fast-usdc/src/cli/config.js | 1 - packages/fast-usdc/src/cli/transfer.js | 13 ++++++++++--- packages/fast-usdc/test/cli/transfer.test.ts | 1 + 3 files changed, 11 insertions(+), 4 deletions(-) diff --git a/packages/fast-usdc/src/cli/config.js b/packages/fast-usdc/src/cli/config.js index 2dd63fdad2d..2b67a4868a3 100644 --- a/packages/fast-usdc/src/cli/config.js +++ b/packages/fast-usdc/src/cli/config.js @@ -6,7 +6,6 @@ import { stdin as input, stdout as output } from 'node:process'; nobleSeed: string, ethSeed: string, nobleToAgoricChannel: string, - agoricRpc: string, nobleApi: string, nobleRpc: string, ethRpc: string, diff --git a/packages/fast-usdc/src/cli/transfer.js b/packages/fast-usdc/src/cli/transfer.js index f27004f5cc0..9120f93be0a 100644 --- a/packages/fast-usdc/src/cli/transfer.js +++ b/packages/fast-usdc/src/cli/transfer.js @@ -1,13 +1,18 @@ +/* eslint-env node */ /* global globalThis */ -import { makeVStorage } from '@agoric/client-utils'; +import { + fetchEnvNetworkConfig, + makeVStorage, + pickEndpoint, +} from '@agoric/client-utils'; +import { queryFastUSDCLocalChainAccount } from '../util/agoric.js'; import { depositForBurn, makeProvider } from '../util/cctp.js'; import { makeSigner, queryForwardingAccount, registerFwdAccount, } from '../util/noble.js'; -import { queryFastUSDCLocalChainAccount } from '../util/agoric.js'; /** @import { File } from '../util/file' */ /** @import { VStorage } from '@agoric/client-utils' */ @@ -23,13 +28,15 @@ const transfer = async ( /** @type {VStorage | undefined} */ vstorage, /** @type {{signer: SigningStargateClient, address: string} | undefined} */ nobleSigner, /** @type {ethProvider | undefined} */ ethProvider, + env = process.env, ) => { const execute = async ( /** @type {import('./config').ConfigOpts} */ config, ) => { + const netConfig = await fetchEnvNetworkConfig({ env, fetch }); vstorage ||= makeVStorage( { fetch }, - { chainName: 'agoric', rpcAddrs: [config.agoricRpc] }, + { chainName: 'agoric', rpcAddrs: [pickEndpoint(netConfig)] }, ); const agoricAddr = await queryFastUSDCLocalChainAccount(vstorage, out); const appendedAddr = `${agoricAddr}?EUD=${destination}`; diff --git a/packages/fast-usdc/test/cli/transfer.test.ts b/packages/fast-usdc/test/cli/transfer.test.ts index d820492c2ed..d3c319f1f6b 100644 --- a/packages/fast-usdc/test/cli/transfer.test.ts +++ b/packages/fast-usdc/test/cli/transfer.test.ts @@ -142,6 +142,7 @@ test('Transfer signs and broadcasts the depositForBurn message on Ethereum', asy vstorageMock.vstorage, { signer: signerMock.signer, address: nobleSignerAddress }, mockEthProvider.provider, + {}, ); t.is(signerMock.getSigned(), undefined); From 4c92dbbac7cc59895ae747ea7ca1c3b8480186dd Mon Sep 17 00:00:00 2001 From: Dan Connolly Date: Tue, 3 Dec 2024 15:30:00 -0600 Subject: [PATCH 55/56] docs(fast-usdc): add cli help text re AGORIC_NET --- packages/fast-usdc/src/cli/cli.js | 13 +++++++++++++ 1 file changed, 13 insertions(+) diff --git a/packages/fast-usdc/src/cli/cli.js b/packages/fast-usdc/src/cli/cli.js index afaf1eadf9a..9488bf574c2 100644 --- a/packages/fast-usdc/src/cli/cli.js +++ b/packages/fast-usdc/src/cli/cli.js @@ -62,6 +62,19 @@ export const initProgram = ( return makeFile(getConfigPath(), readFile, writeFile, mkdir, exists); }; + program.addHelpText( + 'afterAll', + ` + Agoric test networks provide configuration info at, for example, + + https://devnet.agoric.net/network-config + + To use RPC endpoints from such a configuration, use: + export AGORIC_NET=devnet + + Use AGORIC_NET=local or leave it unset to use localhost and chain id agoriclocal. + `, + ); addConfigCommands(program, configHelpers, makeConfigFile); addOperatorCommands(program, { fetch, From 918eabee99e26754f7d3b0dde1c84fbae68113c2 Mon Sep 17 00:00:00 2001 From: Dan Connolly Date: Tue, 3 Dec 2024 19:12:42 -0600 Subject: [PATCH 56/56] chore(fast-usdc): regen snapshots with AGORIC_NET docs --- .../test/cli/snapshots/cli.test.ts.md | 96 ++++++++++++++++-- .../test/cli/snapshots/cli.test.ts.snap | Bin 1557 -> 1731 bytes 2 files changed, 88 insertions(+), 8 deletions(-) diff --git a/packages/fast-usdc/test/cli/snapshots/cli.test.ts.md b/packages/fast-usdc/test/cli/snapshots/cli.test.ts.md index ed8f08e0f82..07607d1eab1 100644 --- a/packages/fast-usdc/test/cli/snapshots/cli.test.ts.md +++ b/packages/fast-usdc/test/cli/snapshots/cli.test.ts.md @@ -25,7 +25,17 @@ Generated by [AVA](https://avajs.dev). withdraw [options] Withdraw assets from the liquidity pool␊ transfer Transfer USDC from Ethereum/L2 to Cosmos via Fast␊ USDC␊ - help [command] display help for command` + help [command] display help for command␊ + ␊ + Agoric test networks provide configuration info at, for example,␊ + ␊ + https://devnet.agoric.net/network-config␊ + ␊ + To use RPC endpoints from such a configuration, use:␊ + export AGORIC_NET=devnet␊ + ␊ + Use AGORIC_NET=local or leave it unset to use localhost and chain id agoriclocal.␊ + ` ## shows help for transfer command @@ -40,7 +50,17 @@ Generated by [AVA](https://avajs.dev). dest Destination address in Cosmos␊ ␊ Options:␊ - -h, --help display help for command` + -h, --help display help for command␊ + ␊ + Agoric test networks provide configuration info at, for example,␊ + ␊ + https://devnet.agoric.net/network-config␊ + ␊ + To use RPC endpoints from such a configuration, use:␊ + export AGORIC_NET=devnet␊ + ␊ + Use AGORIC_NET=local or leave it unset to use localhost and chain id agoriclocal.␊ + ` ## shows help for config command @@ -57,7 +77,17 @@ Generated by [AVA](https://avajs.dev). show Show current config␊ init [options] Set initial config values␊ update [options] Update config values␊ - help [command] display help for command` + help [command] display help for command␊ + ␊ + Agoric test networks provide configuration info at, for example,␊ + ␊ + https://devnet.agoric.net/network-config␊ + ␊ + To use RPC endpoints from such a configuration, use:␊ + export AGORIC_NET=devnet␊ + ␊ + Use AGORIC_NET=local or leave it unset to use localhost and chain id agoriclocal.␊ + ` ## shows help for config init command @@ -93,7 +123,17 @@ Generated by [AVA](https://avajs.dev). "0xbd3fa81b58ba92a82136038b25adec7066af3155")␊ --token-contract-address [address] Address of USDC token contract (default:␊ "0xa0b86991c6218b36c1d19d4a2e9eb0ce3606eb48")␊ - -h, --help display help for command` + -h, --help display help for command␊ + ␊ + Agoric test networks provide configuration info at, for example,␊ + ␊ + https://devnet.agoric.net/network-config␊ + ␊ + To use RPC endpoints from such a configuration, use:␊ + export AGORIC_NET=devnet␊ + ␊ + Use AGORIC_NET=local or leave it unset to use localhost and chain id agoriclocal.␊ + ` ## shows help for config update command @@ -120,7 +160,17 @@ Generated by [AVA](https://avajs.dev). --noble-to-agoric-channel [channel] Channel ID on Noble for Agoric␊ --token-messenger-address [address] Address of TokenMessenger contract␊ --token-contract-address [address] Address of USDC token contract␊ - -h, --help display help for command` + -h, --help display help for command␊ + ␊ + Agoric test networks provide configuration info at, for example,␊ + ␊ + https://devnet.agoric.net/network-config␊ + ␊ + To use RPC endpoints from such a configuration, use:␊ + export AGORIC_NET=devnet␊ + ␊ + Use AGORIC_NET=local or leave it unset to use localhost and chain id agoriclocal.␊ + ` ## shows help for config show command @@ -131,7 +181,17 @@ Generated by [AVA](https://avajs.dev). Show current config␊ ␊ Options:␊ - -h, --help display help for command` + -h, --help display help for command␊ + ␊ + Agoric test networks provide configuration info at, for example,␊ + ␊ + https://devnet.agoric.net/network-config␊ + ␊ + To use RPC endpoints from such a configuration, use:␊ + export AGORIC_NET=devnet␊ + ␊ + Use AGORIC_NET=local or leave it unset to use localhost and chain id agoriclocal.␊ + ` ## shows help for deposit command @@ -147,7 +207,17 @@ Generated by [AVA](https://avajs.dev). Options:␊ --id [offer-id] Offer ID␊ --fee [fee] Cosmos fee␊ - -h, --help display help for command` + -h, --help display help for command␊ + ␊ + Agoric test networks provide configuration info at, for example,␊ + ␊ + https://devnet.agoric.net/network-config␊ + ␊ + To use RPC endpoints from such a configuration, use:␊ + export AGORIC_NET=devnet␊ + ␊ + Use AGORIC_NET=local or leave it unset to use localhost and chain id agoriclocal.␊ + ` ## shows help for withdraw command @@ -163,7 +233,17 @@ Generated by [AVA](https://avajs.dev). Options:␊ --id [offer-id] Offer ID␊ --fee [fee] Cosmos fee␊ - -h, --help display help for command` + -h, --help display help for command␊ + ␊ + Agoric test networks provide configuration info at, for example,␊ + ␊ + https://devnet.agoric.net/network-config␊ + ␊ + To use RPC endpoints from such a configuration, use:␊ + export AGORIC_NET=devnet␊ + ␊ + Use AGORIC_NET=local or leave it unset to use localhost and chain id agoriclocal.␊ + ` ## shows error when deposit command is run without options diff --git a/packages/fast-usdc/test/cli/snapshots/cli.test.ts.snap b/packages/fast-usdc/test/cli/snapshots/cli.test.ts.snap index 2150beaaf1008567472a39ea2e1411ad7bedd15b..2d0eac4dcb4aaa55da830deb8489ef90b7b6a80e 100644 GIT binary patch literal 1731 zcmV;!20ZyeRzV=})o&-5b0}&8)7|yur7LrC z{uX~r6d#KS00000000B+S}d< z$j^6I?%ew9mL4njZhdk4-#aIg^l%4UB2_t(jtw0iD$1EWg^taGfH3FOvf3{WKyjc< zp&+)3HNi6?6`Z`;Z-Y>%Q{L#>{tNhAJ?EDGsq1dsW4KYJcM+f zML`#Zey!~B0AV*I%6pQ3?YW+Cs6bnBaj9WN62avHY|dQTgKr&lN#rZ7e!^J&b-gk$ zd-ai4>S?U8Plty?W$2U3#Nmmq*f*BdPX5Hk8UW+QOTtJG%?b;EhbV~RV$9MbL2Mtd zRv1;%0&p|80%exLrEd!3zshAeAh^NX!fl;vjqOM`JxeU03J|!`KCWlB%u^@5! zfQ?he1z@ko1+_t;RKQT3b8#ji6ueKJG!T&>+6_RN%Ymr1SOi{>AoOuf%kY#6<<9!L zgMEgoLSm5>hHBkNESrd00LKXvU%zStGAHDerEZjw?E%T_T+@p+Y49TCLc!h-N3Rds zzZ^b2{w`6bMV?5^PWap=K5zj(l0E`e5HX1=-2?Ho$E5#nVuHom?(;NN7j)Xv_t};7ixdg4(p^BeU;-{GV#E(#C^eA+Q z!tDB!izu~V0<>vGWh_W&Fwux%3(O9B@#@nuL4-DRBH^EoS#2O^H{rC! z@YPt=+kR(#y;k3GmgpZ zvf1$%(dBy0fKdDlSvf!{k@ZlN)0(bh{+t5rnMd4(W4-!ix>#prr9W(^RX;o4>P6St za7nAyZM3>%yG~m5+D5aw(dyP4#6f$j+H4Ycqt`8%*Gbd|LTuaBV3~ZSTB&l{= z&F$@)-K^JI-HoPQb86epCaL2#cB?jSG^XS9Tl_)$4R{qQ#1;4Kp9R;zN>?iA(tBvKI*usPQ)lg8= z`~Bieu`hE0y*qj-R@5S}tSLGK`Ab&)UT*uEogYsOl?Bv+4%Z6GRNqb|x(@c^ITsN+ zE~3ek=6csf9G5nhY+Bfj{-E1aOs5AqI(BC4y=w1W*LooY%cj>og$ z0LuEr*G9$tp;0Vh4olZyF_Ovy2=P}Clo(fKQcfDwC9NkFuX!+pw*rS;0RabX8W7*K zwJWI^t+~u_5l3yXb2gk98xr?JDYHXL8H`1yRNxsR1d&wGMIhJ19!@YHjs`kw3}~=B z6OfzXK@9jB9&FEN$Bh$VbQ_N8pG?h#=Q-p%2Kj&kS0;?KM@qoB0vV!BU5ZXIPlsFE zQ)Ao8VS98vPZN$!VCoc}Lgj(BZxqh69Gq6MtA;u@1&;cD9(2hOQ2_8D2k>z*z|p&o Z0*p`Q!5A~80OG>v_8-Ax@1c|>004MELcIV0 literal 1557 zcmV+w2I~1iRzV3h~XCGT;{y0t{og2#|qD7+g>l@I(O-qa;G6B$bTBGT=)7^49Z+ zB0p~Y@zL7tHQm-fUi)O@_l;9YMz{w)k*c0Z&xHYx73EBx!NBEFM3{HxIQ`=zP#h>z zD2S`lmEbXv3Qk`f_93LN6Y5cQ2{GrP?NcYVXYClOEdJ5CGQpGWFv6Qmm1S5vxU zQF^ybsj)Ei?6D)K3iC2ys^Qy0d!fI$i4e%tRg6+*g_<6RD*Z}Hm}5RCVS+j~lh`8) zi{nqTFOvhya-K){=5)eSe3h)Vi4N1$vM$WUjc3jqrUMBFIarFiLTu3TC4! zY-I-2IdT@|Vf#c`@Ef+-W!XOdh*_6=+^0&|XfXs_I zWopsfebqJtrQ*G4Erm@skiKA5mU z%p$^oICy?^-9+>Z1|66)X@ILh)LcBeMi{-${f5(J?rzKNwp+d7cGqortzGXvY2z*qn=Wp5n_V2<@6Eg3U$uFu_|EiHoaCv#A{pQM z%}U1aZdE1Y$ydY#KGH{2)p_^BPsQVIJ*+zIQX|Eu$CP*2s;|_~CvfMrlS<5g zTSxStYbDTC)fdNEp!i}x?e#os7t98x9TTTJ^F{$lVkb ze8g$HzihE&TrH}8*>6~!{Z;0yvf|`8i&mU$=Je#L%;hWH6ni@vdnkmaPS<276bDpV zWm-c>S%@7gcxtJ|J&353l#M{(>xAm`ke7L(rbScBaXeTC2T*oSLh6}XQyEKaVHp}M z#!`I@A-$GBjd4{c^{k3p)9d8sHD42W8}N)PAmE`(BNCe0ZzFf3w~`w^V%Z1R^5N9@ zkkJpdf(&W}j8(2Q;4vaZiBvE|AoF2QM$!9|fewwa4EC1-ax*$e0ngFF?rMJAxDd)= zIHhX0uoj+J$oCBLu?DVOC>7;uz_Vy?UeX|O>><(E0@W=xApc-KL@lk>C;VKwYrBpz?Ho5%+-)*F6 Hxf}oh{;Bw$