Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: add FastLP to vbank #10709

Merged
merged 5 commits into from
Dec 18, 2024
Merged

feat: add FastLP to vbank #10709

merged 5 commits into from
Dec 18, 2024

Conversation

dckc
Copy link
Member

@dckc dckc commented Dec 17, 2024

closes: #10703

Description

  • add FastLP / ufastlp to vbank

Security Considerations

Adds bankManager to the FastUSDC core eval permit, which introduces an audit burden to see that is used only for the relevant addAsset call.

Scaling Considerations

eliminates up-calls from go to JS on each FastLP balance update

Documentation Considerations

Existing docs suffice; to wit: VBank Assets and Cosmos Bank Balances

Testing Considerations

  • update tests that relied on getting FastLP balances from published.wallet.${addr}.current.

Upgrade Considerations

unreleased

Copy link

cloudflare-workers-and-pages bot commented Dec 17, 2024

Deploying agoric-sdk with  Cloudflare Pages  Cloudflare Pages

Latest commit: 3815e4c
Status: ✅  Deploy successful!
Preview URL: https://e5218bae.agoric-sdk.pages.dev
Branch Preview URL: https://dc-fastlp-vbank.agoric-sdk.pages.dev

View logs

@dckc dckc added the force:integration Force integration tests to run on PR label Dec 17, 2024
@dckc
Copy link
Member Author

dckc commented Dec 17, 2024

ci shows evidence of the breaking change:

  ✘ [fail]: fast-usdc › lp deposits

  Error {
    message: 'lp has pool shares condition failed after 6 retries.',

Tue, 17 Dec 2024 02:33:48 GMT

@dckc dckc marked this pull request as ready for review December 17, 2024 22:55
@dckc dckc requested a review from a team as a code owner December 17, 2024 22:55
import type { Amount, Brand } from '@agoric/ertp';
const { fromEntries } = Object;

// @ts-expect-error Type 'Brand' does not satisfy the constraint 'string | number | symbol'
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@@ -107,23 +110,64 @@ test.after(async t => {
deleteTestKeys(accounts);
});

type VStorageClient = Awaited<ReturnType<typeof commonSetup>>['vstorageClient'];
const agoricNamesQ = (vsc: VStorageClient) =>
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

not a blocker but I find these one-off abstractions a little hard to work with. I hope we can design good general abstractions in @agoric/client-utils to invest in. #10713 attempts to replace test calls to VStorageClient with SmartWalletKit, getting typed data for query paths.

If the client-utils abstractions aren't right, let's work on to improve them, so all consumers benefit.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for #10713; I looked it over and made some comments.

The cycle time in multi-chain testing is extremely high, so I'm not eager to go beyond this 1 test file for this feature.

In general, my habit is to experiment until I see a pattern that works well in at least 2 or 3 cases and then DRY it out.

harden({
metrics: () =>
vsc.queryData(
`published.${contractName}.poolMetrics`,
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't get why this is parameterized for any contractName when it's bound to fastLPQ.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

copy/paste left-over.

if I change anything else, I'll remove the parameter. not worth another round of ci on its own, I suggest

produceShareIssuer.resolve(shareIssuer);
produceShareBrand.resolve(shareBrand);
await publishDisplayInfo(shareBrand, { board, chainStorage });

const { denom, issuerName } = ShareAssetInfo;
trace('addAsset', denom, shareBrand);
await E(bankManager).addAsset(denom, issuerName, issuerName, {
Copy link
Member

@turadg turadg Dec 18, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

not objecting, but why use a ZCFMint when the start eval is now concerned with the Issuer?

oh, so minting appears synchronous within the contract?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

yes. A ZCFMint is the normal Zoe API for a token issued by a contract.

// XXX #10491 should not need to resort to string match on brand
t.falsy(
purses.find(p => `${p.brand}`.match(/FastLP/)),
'FastLP balance not in wallet record',
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is there a way to assert that it is in the wallet's bank in this test context? I might suggest at least saying 'FastLP balance should be in bank, not in wallet record', or maybe put a want in the proposal. Otherwise, looking at this assertion on its own might make it seem like we just don't expect fastlp tokens at all. Maybe it's not necessary at all?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

good idea... I think I can do that...

Copy link
Member

@0xpatrickdev 0xpatrickdev Dec 18, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Something like this should help with that:

Wrote this before reading the code changes, seems you already have this.

const queryClient = makeQueryClient(
  await useChain('agoric').getRestEndpoint(),
);
const { balance } = await queryClient.queryBalance('$ADDR', 'ufastlp')

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

yeah; there's no rest endpoint in the bootstrap world

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ah getOutboundMessages didn't know about this, neat.

@dckc dckc requested review from samsiegart and turadg December 18, 2024 16:15
Copy link
Contributor

@samsiegart samsiegart left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM but deferring approval to other reviewers since I'm not sure about the bankManager stuff in fast-usdc.start.js

// XXX #10491 should not need to resort to string match on brand
t.falsy(
purses.find(p => `${p.brand}`.match(/FastLP/)),
'FastLP balance not in wallet record',
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ah getOutboundMessages didn't know about this, neat.


const { EV } = t.context.runUtils;
const agoricNames = await EV.vat('bootstrap').consumeItem('agoricNames');
const board = await EV.vat('bootstrap').consumeItem('board');
const getBoardAux = async name => {
const brand = await EV(agoricNames).lookup('brand', name);
const id = await EV(board).getId(brand);
t.is(id || null, lpId);
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I had a little trouble making sense of what it's testing. Casting all falsy id to null because lpId will either have a string or null? I can't tell why that's necessary.

please try to make it clearer

Copy link
Member Author

@dckc dckc Dec 18, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

yeah; that's goofy.

I fixed it so lpId is definitely a string instead of making the other side maybe null.

The type of t.is() says both sides are the same type.

@dckc dckc added the automerge:rebase Automatically rebase updates, then merge label Dec 18, 2024
dckc added 5 commits December 18, 2024 20:19
 - prune balancesFromPurses, which was not type-safe
 - factor out vstorage queries for type safety
 - add static check on deposit / withdraw proposals
   - refactor usdcToGive as give.USDC etc.

balancesFromPurses() seemed to return a Record<Brand, Amount>
but Brands can't be record keys. It "worked" by stringifying the brands.

```
> b = {[Symbol.toStringTag]:'B123'}
{ [Symbol(Symbol.toStringTag)]: 'B123' }
> b.toString()
'[object B123]'
> fromEntries([[b, 1]])
{ '[object B123]': 1 }
```
@mergify mergify bot merged commit c1d2b71 into master Dec 18, 2024
81 checks passed
@mergify mergify bot deleted the dc-fastlp-vbank branch December 18, 2024 21:09
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
automerge:rebase Automatically rebase updates, then merge force:integration Force integration tests to run on PR
Projects
None yet
Development

Successfully merging this pull request may close these issues.

add FastLP to vbank in initial deployment
4 participants