From 531b13c17ce87e1cffb2ec0f5d47b34ae617f926 Mon Sep 17 00:00:00 2001 From: 0xPatrick Date: Tue, 17 Dec 2024 11:28:47 -0500 Subject: [PATCH] feat!: `publishAccountInfo` in `withOrchestration` opts BREAKING CHANGE: in order for the Orchestration API to automatically publish account info to vstorage, callers must specify `{ publicAccountInfo: true }` in the `withOrchestration` start helper --- .../boot/test/fast-usdc/fast-usdc.test.ts | 6 +--- .../fast-usdc/snapshots/fast-usdc.test.ts.md | 25 -------------- .../snapshots/fast-usdc.test.ts.snap | Bin 3517 -> 3011 bytes packages/fast-usdc/src/fast-usdc.contract.js | 1 + .../src/examples/auto-stake-it.contract.js | 2 +- .../src/examples/basic-flows.contract.js | 2 +- .../src/examples/send-anywhere.contract.js | 9 ++--- .../examples/staking-combinations.contract.js | 2 +- .../src/examples/swap.contract.js | 2 +- .../src/examples/unbond.contract.js | 2 +- .../src/exos/cosmos-orchestration-account.js | 31 ++++++++++-------- .../src/exos/local-chain-facade.js | 16 +++++---- .../src/exos/local-orchestration-account.js | 16 ++++++--- .../src/exos/remote-chain-facade.js | 20 ++++++----- packages/orchestration/src/facade.js | 11 ++----- .../src/fixtures/query-flows.contract.js | 2 +- .../orchestration/src/utils/start-helper.js | 21 ++++++++---- 17 files changed, 80 insertions(+), 88 deletions(-) diff --git a/packages/boot/test/fast-usdc/fast-usdc.test.ts b/packages/boot/test/fast-usdc/fast-usdc.test.ts index 39791f0c077..8f9e7027977 100644 --- a/packages/boot/test/fast-usdc/fast-usdc.test.ts +++ b/packages/boot/test/fast-usdc/fast-usdc.test.ts @@ -181,11 +181,7 @@ test.serial('writes account addresses to vstorage', async t => { showValue: JSON.parse, pattern: /published\.fastUsdc\.(feeConfig|feedPolicy|poolMetrics)/, replacement: '', - note: `Under "published", the "fastUsdc" node is delegated to FastUSDC contract. - Note: published.fastUsdc.[settleAcctAddr], published.fastUsdc.[poolAcctAddr], - and published.fastUsdc.[intermediateAcctAddr] are published by @agoric/orchestration - via 'withOrchestration' and (local|cosmos)-orch-account-kit.js. - `, + note: 'Under "published", the "fastUsdc" node is delegated to FastUSDC contract.', }; await documentStorageSchema(t, storage, doc); 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 3161bdab352..2078d71d7a7 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 @@ -131,10 +131,6 @@ Generated by [AVA](https://avajs.dev). ## writes account addresses to vstorage > Under "published", the "fastUsdc" node is delegated to FastUSDC contract. -> Note: published.fastUsdc.[settleAcctAddr], published.fastUsdc.[poolAcctAddr], -> and published.fastUsdc.[intermediateAcctAddr] are published by @agoric/orchestration -> via 'withOrchestration' and (local|cosmos)-orch-account-kit.js. -> > The example below illustrates the schema of the data published there. > > See also board marshalling conventions (_to appear_). @@ -147,27 +143,6 @@ Generated by [AVA](https://avajs.dev). settlementAccount: 'agoric1qyqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqc09z0g', }, ], - [ - 'published.fastUsdc.agoric1qqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqp7zqht', - { - body: '#""', - slots: [], - }, - ], - [ - 'published.fastUsdc.agoric1qyqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqc09z0g', - { - body: '#""', - slots: [], - }, - ], - [ - 'published.fastUsdc.noble1test', - { - body: '#{"localAddress":"/ibc-port/icacontroller-1/ordered/{\\"version\\":\\"ics27-1\\",\\"controllerConnectionId\\":\\"connection-72\\",\\"hostConnectionId\\":\\"connection-40\\",\\"address\\":\\"noble1test\\",\\"encoding\\":\\"proto3\\",\\"txType\\":\\"sdk_multi_msg\\"}/ibc-channel/channel-1","remoteAddress":"/ibc-hop/connection-72/ibc-port/icahost/ordered/{\\"version\\":\\"ics27-1\\",\\"controllerConnectionId\\":\\"connection-72\\",\\"hostConnectionId\\":\\"connection-40\\",\\"address\\":\\"noble1test\\",\\"encoding\\":\\"proto3\\",\\"txType\\":\\"sdk_multi_msg\\"}/ibc-channel/channel-1"}', - slots: [], - }, - ], ] ## makes usdc advance 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 adaeecaee9759386dd329dd62260485606d09bdc..24bf77ac0d8f0d84cee090506618fe1a82d024f3 100644 GIT binary patch literal 3011 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 F008NM%w+%o literal 3517 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 cqcJgeVr#raE( zx-n35k-toc6v7S-*h790b@`H6tGCo1QO_-Y3DL&*yPEgU;Yp|Jldf6s-KMkB^(c4*c&`1+Wbg9V zl)3FUHFu@L=YEBZcJhk^_$mSN>CiM;JCldMCwwR^TG#{b-z&UvN-#3=dkG^4_*pwO zI%?C+9jG?mS$&}1ym$AX;f(+tl}aqR4j$jC$D z6f*KN;vQt=x5VAa$Zj3!gXd14zIb2t!MmFmtM{Ki|G+u^T0SiT{~!YYIlH8JI0GEX z0LE-oe>els46r$)`Z;<}&%W8{_~&mrI)3t+MaS=QmVE_+NaH?f1`Wt-m~9Yduq`#F1&F{_3>JzqEH}{p}(Uvm$*q6rLA> zheaURZ)g4eBJiss@Y}Q5)?bUj--^J$?zgjEoVT-{OnHs@``aVkJKt1iy*B5}+BN8` rZxM1$TI>Cu&A-lQu}icav0#L6QopwmP@8>c(f9uVtNRur^D_Vd=*a4% diff --git a/packages/fast-usdc/src/fast-usdc.contract.js b/packages/fast-usdc/src/fast-usdc.contract.js index 2af84600fd6..d19469e9d3b 100644 --- a/packages/fast-usdc/src/fast-usdc.contract.js +++ b/packages/fast-usdc/src/fast-usdc.contract.js @@ -90,6 +90,7 @@ const publishAddresses = (contractNode, addresses) => { * feeConfig: FeeConfig; * marshaller: Marshaller; * poolMetricsNode: Remote; + * storageNode: Remote; * }} privateArgs * @param {Zone} zone * @param {OrchestrationTools} tools diff --git a/packages/orchestration/src/examples/auto-stake-it.contract.js b/packages/orchestration/src/examples/auto-stake-it.contract.js index 4db3c55adcb..667a6ebc72f 100644 --- a/packages/orchestration/src/examples/auto-stake-it.contract.js +++ b/packages/orchestration/src/examples/auto-stake-it.contract.js @@ -81,7 +81,7 @@ const contract = async ( return { publicFacet, creatorFacet }; }; -export const start = withOrchestration(contract); +export const start = withOrchestration(contract, { publishAccountInfo: true }); harden(start); /** @typedef {typeof start} AutoStakeItSF */ diff --git a/packages/orchestration/src/examples/basic-flows.contract.js b/packages/orchestration/src/examples/basic-flows.contract.js index ab8387d2ec8..cef9b27c4e9 100644 --- a/packages/orchestration/src/examples/basic-flows.contract.js +++ b/packages/orchestration/src/examples/basic-flows.contract.js @@ -70,7 +70,7 @@ const contract = async ( return { publicFacet }; }; -export const start = withOrchestration(contract); +export const start = withOrchestration(contract, { publishAccountInfo: true }); harden(start); /** @typedef {typeof start} BasicFlowsSF */ diff --git a/packages/orchestration/src/examples/send-anywhere.contract.js b/packages/orchestration/src/examples/send-anywhere.contract.js index b277d5733ad..344e9b25563 100644 --- a/packages/orchestration/src/examples/send-anywhere.contract.js +++ b/packages/orchestration/src/examples/send-anywhere.contract.js @@ -9,7 +9,7 @@ import * as flows from './send-anywhere.flows.js'; import * as sharedFlows from './shared.flows.js'; /** - * @import {Vow} from '@agoric/vow'; + * @import {Remote, Vow} from '@agoric/vow'; * @import {Zone} from '@agoric/zone'; * @import {OrchestrationPowers, OrchestrationTools} from '../utils/start-helper.js'; * @import {CosmosChainInfo, Denom, DenomDetail} from '@agoric/orchestration'; @@ -28,9 +28,10 @@ harden(SingleNatAmountRecord); * * @param {ZCF} zcf * @param {OrchestrationPowers & { - * marshaller: Marshaller; - * chainInfo?: Record; * assetInfo?: [Denom, DenomDetail & { brandKey?: string }][]; + * chainInfo?: Record; + * marshaller: Marshaller; + * storageNode: Remote; * }} privateArgs * @param {Zone} zone * @param {OrchestrationTools} tools @@ -97,5 +98,5 @@ export const contract = async ( }; harden(contract); -export const start = withOrchestration(contract); +export const start = withOrchestration(contract, { publishAccountInfo: true }); harden(start); diff --git a/packages/orchestration/src/examples/staking-combinations.contract.js b/packages/orchestration/src/examples/staking-combinations.contract.js index 209fe7dc787..a6d571647e3 100644 --- a/packages/orchestration/src/examples/staking-combinations.contract.js +++ b/packages/orchestration/src/examples/staking-combinations.contract.js @@ -159,5 +159,5 @@ const contract = async ( return harden({ publicFacet, creatorFacet }); }; -export const start = withOrchestration(contract); +export const start = withOrchestration(contract, { publishAccountInfo: true }); harden(start); diff --git a/packages/orchestration/src/examples/swap.contract.js b/packages/orchestration/src/examples/swap.contract.js index 400eae50b92..06da8620bc4 100644 --- a/packages/orchestration/src/examples/swap.contract.js +++ b/packages/orchestration/src/examples/swap.contract.js @@ -89,5 +89,5 @@ const contract = async ( return harden({ publicFacet }); }; -export const start = withOrchestration(contract); +export const start = withOrchestration(contract, { publishAccountInfo: true }); harden(start); diff --git a/packages/orchestration/src/examples/unbond.contract.js b/packages/orchestration/src/examples/unbond.contract.js index dda006c31bf..c7c3f320585 100644 --- a/packages/orchestration/src/examples/unbond.contract.js +++ b/packages/orchestration/src/examples/unbond.contract.js @@ -54,5 +54,5 @@ const contract = async ( return harden({ publicFacet }); }; -export const start = withOrchestration(contract); +export const start = withOrchestration(contract, { publishAccountInfo: true }); harden(start); diff --git a/packages/orchestration/src/exos/cosmos-orchestration-account.js b/packages/orchestration/src/exos/cosmos-orchestration-account.js index 1e1ae810283..56f094fa102 100644 --- a/packages/orchestration/src/exos/cosmos-orchestration-account.js +++ b/packages/orchestration/src/exos/cosmos-orchestration-account.js @@ -87,20 +87,20 @@ const trace = makeTracer('CosmosOrchAccount'); const { Vow$ } = NetworkShape; // TODO #9611 /** - * @typedef {object} ComosOrchestrationAccountNotification + * @typedef {object} CosmosOrchestrationAccountNotification * @property {ChainAddress} chainAddress */ /** * @private * @typedef {{ - * topicKit: RecorderKit; * account: IcaAccount; * chainAddress: ChainAddress; + * icqConnection: ICQConnection | undefined; * localAddress: LocalIbcAddress; * remoteAddress: RemoteIbcAddress; - * icqConnection: ICQConnection | undefined; * timer: Remote; + * topicKit: RecorderKit | undefined; * }} State * Internal to the IcaAccountHolder exo */ @@ -291,26 +291,29 @@ export const prepareCosmosOrchestrationAccountKit = ( * @param {RemoteIbcAddress} info.remoteAddress * @param {object} io * @param {IcaAccount} io.account - * @param {Remote} io.storageNode - * @param {ICQConnection | undefined} io.icqConnection + * @param {Remote} [io.storageNode] + * @param {ICQConnection} [io.icqConnection] * @param {Remote} io.timer * @returns {State} */ ({ chainAddress, localAddress, remoteAddress }, io) => { const { storageNode } = io; // must be the fully synchronous maker because the kit is held in durable state - const topicKit = makeRecorderKit(storageNode, PUBLIC_TOPICS.account[1]); + const topicKit = storageNode + ? makeRecorderKit(storageNode, PUBLIC_TOPICS.account[1]) + : undefined; // TODO determine what goes in vstorage https://github.com/Agoric/agoric-sdk/issues/9066 // XXX consider parsing local/remoteAddr to portId, channelId, counterpartyPortId, counterpartyChannelId, connectionId, counterpartyConnectionId // FIXME these values will not update if IcaAccount gets new values after reopening. // consider having IcaAccount responsible for the owning the writer. It might choose to share it with COA. - void E(topicKit.recorder).write( - /** @type {CosmosOrchestrationAccountStorageState} */ ({ - localAddress, - remoteAddress, - }), - ); - + if (topicKit) { + void E(topicKit.recorder).write( + /** @type {CosmosOrchestrationAccountStorageState} */ ({ + localAddress, + remoteAddress, + }), + ); + } const { account, icqConnection, timer } = io; return { account, @@ -333,6 +336,7 @@ export const prepareCosmosOrchestrationAccountKit = ( return account; }, getUpdater() { + if (!this.state.topicKit) throw Fail`no topicKit`; return this.state.topicKit.recorder; }, /** @@ -731,6 +735,7 @@ export const prepareCosmosOrchestrationAccountKit = ( return asVow(async () => { await null; const { topicKit } = this.state; + if (!topicKit) throw Fail`No topicKit; storageNode not provided`; return harden({ account: { description: PUBLIC_TOPICS.account[0], diff --git a/packages/orchestration/src/exos/local-chain-facade.js b/packages/orchestration/src/exos/local-chain-facade.js index 7f4ace2d8b4..dfa4061b183 100644 --- a/packages/orchestration/src/exos/local-chain-facade.js +++ b/packages/orchestration/src/exos/local-chain-facade.js @@ -36,7 +36,7 @@ import { chainFacadeMethods, TypedJsonShape } from '../typeGuards.js'; * @typedef {{ * makeLocalOrchestrationAccountKit: MakeLocalOrchestrationAccountKit; * orchestration: Remote; - * storageNode: Remote; + * storageNode: Remote | undefined; * agoricNames: Remote; * timer: Remote; * localchain: Remote; @@ -79,7 +79,7 @@ const prepareLocalChainFacadeKit = ( .returns(VowShape), }), makeChildNodeWatcher: M.interface('makeChildNodeWatcher', { - onFulfilled: M.call(M.remotable()) + onFulfilled: M.call(M.or(M.remotable(), M.undefined())) .optional({ account: M.remotable(), address: M.string() }) // empty context .returns(M.remotable()), }), @@ -145,11 +145,13 @@ const prepareLocalChainFacadeKit = ( * @param {[LocalChainAccount, ChainAddress['value']]} results */ onFulfilled([account, address]) { - return watch( - E(storageNode).makeChildNode(address), - this.facets.makeChildNodeWatcher, - { account, address }, - ); + const optionalStorageNode = storageNode + ? E(storageNode).makeChildNode(address) + : undefined; + return watch(optionalStorageNode, this.facets.makeChildNodeWatcher, { + account, + address, + }); }, }, makeChildNodeWatcher: { diff --git a/packages/orchestration/src/exos/local-orchestration-account.js b/packages/orchestration/src/exos/local-orchestration-account.js index 8b5a04d9a4e..9a35b866133 100644 --- a/packages/orchestration/src/exos/local-orchestration-account.js +++ b/packages/orchestration/src/exos/local-orchestration-account.js @@ -57,7 +57,7 @@ const EVow$ = shape => M.or(Vow$(shape), M.promise(/* shape */)); /** * @private * @typedef {{ - * topicKit: RecorderKit; + * topicKit: RecorderKit | undefined; * packetTools: PacketTools; * account: LocalChainAccount; * address: ChainAddress; @@ -181,17 +181,22 @@ export const prepareLocalOrchestrationAccountKit = ( * @param {object} initState * @param {LocalChainAccount} initState.account * @param {ChainAddress} initState.address - * @param {Remote} initState.storageNode + * @param {Remote} [initState.storageNode] * @returns {State} */ ({ account, address, storageNode }) => { // must be the fully synchronous maker because the kit is held in durable state - const topicKit = makeRecorderKit(storageNode, PUBLIC_TOPICS.account[1]); + const topicKit = storageNode + ? makeRecorderKit(storageNode, PUBLIC_TOPICS.account[1]) + : undefined; // TODO determine what goes in vstorage https://github.com/Agoric/agoric-sdk/issues/9066 - void E(topicKit.recorder).write(''); + if (topicKit) { + void E(topicKit.recorder).write(''); + } + const packetTools = makePacketTools(account); - return { account, address, topicKit, packetTools }; + return { account, address, packetTools, topicKit }; }, { helper: { @@ -548,6 +553,7 @@ export const prepareLocalOrchestrationAccountKit = ( return asVow(async () => { await null; const { topicKit } = this.state; + if (!topicKit) throw Fail`No topicKit; storageNode not provided`; return harden({ account: { description: PUBLIC_TOPICS.account[0], diff --git a/packages/orchestration/src/exos/remote-chain-facade.js b/packages/orchestration/src/exos/remote-chain-facade.js index 3349eb39c5d..ee22af9ba9c 100644 --- a/packages/orchestration/src/exos/remote-chain-facade.js +++ b/packages/orchestration/src/exos/remote-chain-facade.js @@ -33,7 +33,7 @@ const trace = makeTracer('RemoteChainFacade'); * typeof prepareCosmosOrchestrationAccount * >; * orchestration: Remote; - * storageNode: Remote; + * storageNode: Remote | undefined; * timer: Remote; * vowTools: VowTools; * }} RemoteChainFacadePowers @@ -94,7 +94,7 @@ const prepareRemoteChainFacadeKit = ( ).returns(VowShape), }), makeChildNodeWatcher: M.interface('makeChildNodeWatcher', { - onFulfilled: M.call(M.remotable(), { + onFulfilled: M.call(M.or(M.remotable(), M.undefined()), { account: M.remotable(), chainAddress: ChainAddressShape, localAddress: M.string(), @@ -210,16 +210,20 @@ const prepareRemoteChainFacadeKit = ( * @param {IcaAccount} account */ onFulfilled([chainAddress, localAddress, remoteAddress], account) { - return watch( - E(storageNode).makeChildNode(chainAddress.value), - this.facets.makeChildNodeWatcher, - { account, chainAddress, localAddress, remoteAddress }, - ); + const optionalStorageNode = storageNode + ? E(storageNode).makeChildNode(chainAddress.value) + : undefined; + return watch(optionalStorageNode, this.facets.makeChildNodeWatcher, { + account, + chainAddress, + localAddress, + remoteAddress, + }); }, }, makeChildNodeWatcher: { /** - * @param {Remote} childNode + * @param {Remote | undefined} childNode * @param {{ * account: IcaAccount; * chainAddress: ChainAddress; diff --git a/packages/orchestration/src/facade.js b/packages/orchestration/src/facade.js index 65de08c9e78..07cc8e77770 100644 --- a/packages/orchestration/src/facade.js +++ b/packages/orchestration/src/facade.js @@ -2,15 +2,14 @@ import { assertAllDefined, deepMapObject } from '@agoric/internal'; /** - * @import {AsyncFlowTools, GuestInterface, HostArgs, HostOf} from '@agoric/async-flow'; + * @import {AsyncFlowTools, GuestInterface, HostArgs} from '@agoric/async-flow'; * @import {Zone} from '@agoric/zone'; * @import {Vow, VowTools} from '@agoric/vow'; * @import {TimerService} from '@agoric/time'; - * @import {RecorderKit, MakeRecorderKit} from '@agoric/zoe/src/contractSupport/recorder.js'. * @import {HostOrchestrator} from './exos/orchestrator.js'; * @import {Remote} from '@agoric/internal'; * @import {CosmosInterchainService} from './exos/exo-interfaces.js'; - * @import {Chain, ChainInfo, CosmosChainInfo, IBCConnectionInfo, OrchestrationAccount, OrchestrationFlow, Orchestrator} from './types.js'; + * @import {OrchestrationFlow, Orchestrator} from './types.js'; */ /** @@ -31,9 +30,7 @@ import { assertAllDefined, deepMapObject } from '@agoric/internal'; * zone: Zone; * timerService: Remote; * zcf: ZCF; - * storageNode: Remote; * orchestrationService: Remote; - * makeRecorderKit: MakeRecorderKit; * makeOrchestrator: () => HostOrchestrator; * vowTools: VowTools; * asyncFlowTools: AsyncFlowTools; @@ -43,9 +40,7 @@ export const makeOrchestrationFacade = ({ zone, timerService, zcf, - storageNode, orchestrationService, - makeRecorderKit, makeOrchestrator, vowTools, asyncFlowTools, @@ -54,9 +49,7 @@ export const makeOrchestrationFacade = ({ zone, timerService, zcf, - storageNode, orchestrationService, - makeRecorderKit, makeOrchestrator, vowTools, asyncFlowTools, diff --git a/packages/orchestration/src/fixtures/query-flows.contract.js b/packages/orchestration/src/fixtures/query-flows.contract.js index d8e1c8eb271..d735bfe78ca 100644 --- a/packages/orchestration/src/fixtures/query-flows.contract.js +++ b/packages/orchestration/src/fixtures/query-flows.contract.js @@ -64,7 +64,7 @@ const contract = async (zcf, _privateArgs, zone, { orchestrateAll }) => { return { publicFacet }; }; -export const start = withOrchestration(contract); +export const start = withOrchestration(contract, { publishAccountInfo: true }); harden(start); /** @typedef {typeof start} QueryFlowsSF */ diff --git a/packages/orchestration/src/utils/start-helper.js b/packages/orchestration/src/utils/start-helper.js index e6c36bd523c..463e28f2c87 100644 --- a/packages/orchestration/src/utils/start-helper.js +++ b/packages/orchestration/src/utils/start-helper.js @@ -14,7 +14,7 @@ import { makeZcfTools } from './zcf-tools.js'; /** * @import {LocalChain} from '@agoric/vats/src/localchain.js'; - * @import {TimerService, TimerBrand} from '@agoric/time'; + * @import {TimerService} from '@agoric/time'; * @import {Baggage} from '@agoric/vat-data'; * @import {NameHub} from '@agoric/vats'; * @import {Remote} from '@agoric/vow'; @@ -26,12 +26,19 @@ import { makeZcfTools } from './zcf-tools.js'; * @typedef {{ * localchain: Remote; * orchestrationService: Remote; - * storageNode: Remote; + * storageNode?: Remote; * timerService: Remote; * agoricNames: Remote; * }} OrchestrationPowers */ +/** + * @typedef {object} WithOrchestrationOpts + * @property {boolean} [publishAccountInfo] - Controls whether account + * information (address, channel identifiers for ICAs) should be automatically + * published to vstorage + */ + /** * Helper that a contract start function can use to set up the objects needed * for orchestration. @@ -144,7 +151,6 @@ export const provideOrchestration = ( makeOrchestrationFacade({ zone, zcf, - makeRecorderKit, makeOrchestrator, asyncFlowTools, vowTools, @@ -199,16 +205,19 @@ harden(provideOrchestration); * zone: Zone, * tools: OrchestrationTools, * ) => Promise} contractFn + * @param {WithOrchestrationOpts} [opts] * @returns {(zcf: ZCF, privateArgs: PA, baggage: Baggage) => Promise} a * Zoe start function */ export const withOrchestration = - contractFn => async (zcf, privateArgs, baggage) => { + (contractFn, opts) => async (zcf, privateArgs, baggage) => { + const { marshaller, ...allOrchPowers } = privateArgs; + const { storageNode: _, ...requiredOrchPowers } = allOrchPowers; const { zone, ...tools } = provideOrchestration( zcf, baggage, - privateArgs, - privateArgs.marshaller, + opts?.publishAccountInfo ? allOrchPowers : requiredOrchPowers, + marshaller, ); return contractFn(zcf, privateArgs, zone, tools); };