-
Notifications
You must be signed in to change notification settings - Fork 208
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
7502 followup: factor out factory #7519
Conversation
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM, with questions.
If merging this isn't urgent, I'd like to wait to give @erights a chance to say why we thought using singletons was a better choice for this case, and whether things have changed so it makes sense to switch to prepareDurable
.
mintGains: M.call(AmountKeywordRecordShape, M.any()).returns(SeatShape), | ||
burnLosses: M.call(AmountKeywordRecordShape, M.any()).returns( |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Lets use M.remotable('zcfSeat')
instead of M.any()
.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Oh yeah I had postponed expressing the optionalality of the seat arg:
agoric-sdk/packages/zoe/src/contractFacet/types.js
Lines 142 to 146 in 0a11269
* @callback ZCFMintMintGains | |
* @param {AmountKeywordRecord} gains | |
* @param {ZCFSeat} [zcfSeat] | |
* @returns {ZCFSeat} | |
*/ |
Turns out ZCFMintI has this same issue. I'll fix that and re-use it.
* baggage for the state of the zcfMint, makes a durableZcfMint from that | ||
* baggage, and registers that baggage to be revived with the factory. | ||
*/ | ||
// TODO refactor zcfMintFactory uses to makeZcfMint directly |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
was this supposed to be "zcfMintFactory used to makeZcfMint directly"? Otherwise I'm not able to make sense of it.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
That was an interim state in the refactoring
/** @type {Amount<AssetKind>} */ total, | ||
/** @type {Amount<AssetKind>} */ amountToAdd, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I don't see how these types help when add
's only use is to be passed to .reduce()
. gains
is already typed because it is externally visible.
Are they here out of habit, or do they improve maintainability somehow?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
interim state. a subsequent commit had,
/** @type {(total: Amount, amountToAdd: Amount) => Amount} */
const add = (total, amountToAdd) =>
AmountMath.add(total, amountToAdd, mintyBrand);
the type declaration doesn't add much but imo it's still better
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I used the opportunity to see if it reminded me of why I may once have objected. I found one possible reason, and explain in the comments why I am not concerned in this case. I got through the whole review without being reminded of any other reason. With @Chris-Hibbert also not remembering or having any reason to object...
LGTM, thanks!
* @param {(exit?: undefined) => { zcfSeat: any; userSeat: Promise<UserSeat> }} makeEmptySeatKit | ||
* @param {ZcfMintReallocator} reallocator | ||
*/ | ||
export const prepareDurableZcfMint = ( |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
When a function is already named prepare*
and takes a baggage as first argument, the "Durable" part of the name is implied, and so redundant. My naming habit is to say "durable" explicitly only when the name does not start with "prepare".
export const prepareDurableZcfMint = ( | |
export const prepareZcfMint = ( |
/** @type {ZcfMintReallocator} */ reallocator, | ||
/** | ||
* | ||
* @param {import('@agoric/vat-data').Baggage} zcfBaggage |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks for restoring the @param
convention, even if for a different reason. With the two side by side, I again find the @param
convention more readable. YMMV
const add = (total, amountToAdd) => | ||
AmountMath.add(total, amountToAdd, mintyBrand); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This curried add
is an example of an issue that pushed me towards lexical state. When there are a lot of these curried functions, that curry over per-instance state, then having to recreate them per method invocation(!) is oppressive.
In this case, it is one function whose creation code only needs to be repeated twice. It does happen on each invocation of the relevant methods, rather than per singleton kind creation. But these are low frequency methods. So in this case, neither the readability cost nor the runtime cost should hold us back from switching to an exoClass.
(Continuing the review, looking for other red flags against using an exoClass for these.)
mintyDisplayInfo.assetKind, | ||
); | ||
|
||
return { empty, keyword, mintyBrand, zoeMint, mintyIssuerRecord }; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It's funny that, as lexical state, the redundancy of mintyBrand
vs mintyIssuerRecord.brand
would not bother me. As persistent state, it itches, because I think of exoClass instance state as something with potentially high cardinality. In this case, of course, the cardinality is not actually any higher.
Another reason to avoid the redundancy is because it is more persistent state that could be inconsistent. The prior baggage form did not have the redundancy, but (like add
) it is because it only needed to restore the lexical variable per kind, not per invocation.
So I'm on the fence. No change suggested. But if the above changed your mind, that change would be fine with me too.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Agree. PTAAL at b200a59
bb91d3e
to
f3c4bf7
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Here's a left-over nit that didn't get sent with the rest of my review. As it says: "if convenient".
/** @type { (exit?: undefined) => { zcfSeat: any; userSeat: Promise<UserSeat> }} */ makeEmptySeatKit, | ||
/** @type {ZcfMintReallocator} */ reallocator, | ||
/** | ||
* |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
drop blank line if convenient.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
ok will do in my rebase cleanup
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
got 'em all 0160e2f
Description
#7502 fixed an error in zcfMint kind restoration during reincarnation. While investigating it became clear that kind redefinitions could be simplified.
This turns the singleton into an Exo class, sharing the behavior across instances.
Using that prepare it also factors out the ZCFMintFactory and uses the maker directly.
Finally it has some types and helpers to support the change.
Of note: it switches some function declarations back to the
@param
style because I learned that tsc doesn't check the arguments at the callsite without it.Security Considerations
noop
Scaling Considerations
noop
Documentation Considerations
noop
Testing Considerations
CI. Incidentally, while iterating there were some bugs that none of the Zoe package tests caught. Only the vats bootstrapTests did.