-
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
test: add assertAmountsEqual() helper #2453
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.
Hmm, I think this effort might have to wait until after the amountMath refactoring. Here's why:
The function as written will pass even if the "amounts" aren't equal! See the zcf.makeInvitation - no customProperties
test in test-zcf.js
for an example of something passing when it shouldn't be. Even if we added more checks (such as .brand !== undefined
) I think that would be the wrong solution. I think we actually want to use amountMath.isEqual
to get the real, robust, and canonical answer on whether the two are equal. That will save us from any errors in trying to replicate it. (Of course, if we want to add other checks after it fails to provide a better error message we can. My worry is that we will have passes when we should have failures.)
But now, that means that we have to pass in an amountMath, which is difficult and annoying. I tried doing this, and I don't recommend it. However, after the amountMath refactoring, we won't need to.
So, I think this PR is the best that we could do now, but I think it's risky and I would probably prefer to redo it after the amountMath refactoring.
@@ -302,7 +303,7 @@ test(`zcf.makeInvitation - no customProperties`, async t => { | |||
// https://github.com/Agoric/agoric-sdk/issues/1705 | |||
// @ts-ignore | |||
const details = await E(zoe).getInvitationDetails(invitationP); | |||
t.deepEqual(details, { | |||
assertAmountsEqual(t, details, { |
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 no, this is passing but it shouldn't. This is a record, not an amount, so when assertAmountsEqual
checks .brand
and .value
both are undefined, and undefined === undefined so this passes.
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.
Also, even if these were amounts, we should ensure this fails because MathKind.SET wasn't passed in, so MathKind.NAT was used as the default, and that is wrong.
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 reverted this incorrect conversion fo deepEqual()
to assertAmountsEqual()
. I'll convert the PR to draft
until we have a solution for AmountMaths.
blocked on: #2311
Hey @Chris-Hibbert, now that the new amountMath is in, we can revisit this! |
8b63cac
to
37d1a21
Compare
37d1a21
to
ccf6560
Compare
switched from deepEqual() to assertAmountsEqual() on a non-amount.
ccf6560
to
3b56933
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.
We should never have to pass a MathKind in to know whether two amounts are equal. We should change this API
packages/zoe/test/zoeTestHelpers.js
Outdated
t, | ||
amount, | ||
expected, | ||
mathKind = MathKind.NAT, |
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 should be unnecessary if we are just comparing whether two values are equal.
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.
done
packages/zoe/test/zoeTestHelpers.js
Outdated
switch (mathKind) { | ||
case MathKind.NAT: | ||
valuesEqual = amount.value === expected.value; | ||
break; | ||
case MathKind.STRING_SET: | ||
valuesEqual = setMathHelpers.doIsEqual(amount.value, expected.value); | ||
break; | ||
case MathKind.SET: | ||
valuesEqual = setMathHelpers.doIsEqual(amount.value, expected.value); | ||
break; | ||
default: | ||
valuesEqual = false; | ||
} | ||
|
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.
Why are we doing this? amountMath.isEqual(x, y)
will do everything we need to do.
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 gives more detailed error messages when there isn't a match. If that's not valuable, then we can switch all the tests to use t.is(amountMath.isEqual(amount, expected, message))
.
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.
also, amountMath.isEqual()
throws when the brands don't match, which is less helpful in a test.
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.
We can still have the detailed error messages without having to pass in the mathKind. Some options:
-
Use
amountMath.isEqual(
directly. If we know the brands are the same and amountMath.isEqual is false, then we know the values are different and can use the appropriate error message. -
Use
getMathKind
to switch which helpers to use based on the value alone. -
Use
isSetValue
andisNatValue
to switch which helpers to use based on the value alone.
Both of these don't need the mathKind to be passed in, so we should definitely remove that.
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.
also, amountMath.isEqual() throws when the brands don't match, which is less helpful in a test.
An easy fix for this is only use amountMath.isEqual
if you've already checked that the brands match
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.
done. Thanks.
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.
Looks good, thanks
closes: #2442