-
Notifications
You must be signed in to change notification settings - Fork 10
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
[RW-13480][risk=no] Workspace Banners for Initial Credits #8951
base: main
Are you sure you want to change the base?
Conversation
plusDays(workspace.initialCredits.expirationEpochMillis, 5) < Date.now(); | ||
let message; | ||
let title; | ||
if (isExpiringSoon && isEligibleForExtension) { |
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 feels complicated, but the only way that I can think of simplifying it is to break up individual phrases into variables and then have several ternary statements. I feel like that might be more efficient, but I'm not sure it would be more readable.
I would love thoughts here.
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.
your comment refers to an outdated version. is there a similar comment for the updated version?
….6 in /ui (#8953) Signed-off-by: dependabot[bot] <[email protected]> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
zIndex={500} | ||
/> | ||
<> | ||
{((isExpiringSoon && isEligibleForExtension) || isExpired) && ( |
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.
There is no reason to show this banner if one of these conditions is not true.
This component is only used by the breadcrumbs component. So this condition could be shifted up, but these conditions would need to be recalculated. In that case, if appropriate, breadcrumbs could calculate these values and then pass them down.
The only other usage of workspace in this component is the construction of the link associated with the "Edit Workspace" button.
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.
In that case, why is isExhausted
a parameter to the text functions used to construct message
? If only isExhausted
is true, then we don't need message
.
@Mapping( | ||
target = "initialCredits.extensionEpochMillis", | ||
source = "dbWorkspace.creator", | ||
qualifiedByName = "getInitialCreditsExpiration") |
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 sets extension to the same value as expiration. Is this intentional?
plusDays(workspace.initialCredits.expirationEpochMillis, 5) < Date.now(); | ||
let message; | ||
let title; | ||
if (isExpiringSoon && isEligibleForExtension) { |
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.
your comment refers to an outdated version. is there a similar comment for the updated version?
@@ -19,23 +23,167 @@ interface Props extends NavigationProps { | |||
onClose: Function; | |||
} | |||
|
|||
const InitialCreditsArticleLink = () => ( |
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.
these 2 links have different text but the same URL. that does not seem right.
const isExpiringSoon = | ||
workspace && | ||
!isExpired && | ||
plusDays( |
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.
could use your new minusDays here
) => { | ||
const whose = whoseCredits(isCreator); | ||
let whatIsHappening: string; | ||
if (isExhausted || (isExpired && !isEligibleForExtension)) { |
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 think you were looking for a way to simplify the logic? I like these function names and I think the outputs make sense, so I'd keep those.
Maybe one way to simplify the logic would involve an enum of possible states, named something like ExtensionCondition. Before calling these text functions, we would call another function determineCondition() to generate the enum. then these text functions become switch or cond statements, something like:
case EXHAUSTED | EXPIRED_CANNOT_EXTEND: ...
case EXPIRED_CAN_EXTEND: ...
case EXPIRING_SOON_OWNER_CAN_EXTEND | EXPIRING_SOON_NONOWNER_CAN_EXTEND: ...
I don't know that this would actually be better.
whatIsHappening = 'have run out.'; | ||
} else if (isExpired && isEligibleForExtension) { | ||
whatIsHappening = 'have expired.'; | ||
} else if (isExpiringSoon && isEligibleForExtension) { |
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.
what happens in the case of isExpiringSoon && !isEligibleForExtension
? If that never happens here, do you mind adding a comment?
} else { | ||
return ( | ||
<> | ||
{isEligibleForExtension && (isExpired || isExpiringSoon) && ( |
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.
because this section does not mention adding a billing account, the Edit Workspace button lacks the context that explains why it's there. From a program perspective, adding a billing account is the preferred outcome, so I think we should suggest that whenever possible.
render( | ||
<MemoryRouter> | ||
<InvalidBillingBanner | ||
{...{ signatureState }} |
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 doesn't look right. None of these props are used by InvalidBillingBanner.
beforeEach(() => { | ||
registerApiClient(ProfileApi, new ProfileApiStub()); | ||
|
||
// Do I need this? |
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 think so
// Set expiration date to be in the past if expired, in the future if not. | ||
// If expiring soon, set it to be within the warning threshold, and just outside otherwise. | ||
// Expired and expiringSoon are mutually exclusive. | ||
const daysUntilExpiration = expired |
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 like this
}; | ||
|
||
it('should show expiring soon banner to user who created the workspace', async () => { | ||
setupWorkspace(false, false, true, true); |
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'd prefer to see these made explicit, like
const exhausted = false;
const expired = false;
const expiringSoon = true;
const ownedByMe = true;
setupWorkspace(exhausted, expired, expiringSoon, ownedByMe);
); | ||
}); | ||
|
||
it('should show expired banner to user who did not create the workspace and the owner is not eligible for extension', async () => { |
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 would like to see "exhausted" tests as well
There are several different banner variants here. I tried to err on the side of readability even if that meant that the code was a little longer. With that said, I am certainly open to feedback if you have thoughts on how the code can be better organized.
In order to show each of these banners, you will need to manipulate five different states:
now>= expirationDate - initialCreditsExpirationWarningDays
&&now<expirationDate
now >= expirationDate - initialCreditsExpirationWarningDays
Creator Expiring Soon Eligible for Extension
!isExpired && isExpiringSoon && !isExhausted && isEligible && isCreator
Non-creator Expiring Soon Eligible for Extension
!isExpired && isExpiringSoon && !isExhausted && isEligible && !isCreator
Creator Expired Eligible for Extension
isExpired && !isExhausted && isEligible && isCreator
[Non-creator Expired Eligible for Extension]
isExpired && !isExhausted && isEligible && !isCreator
Creator Expired Not Eligible for Extension
(isExpired || isExhausted) && !isEligible && isCreator
Non-creator Expired Not Eligible for Extension
(isExpired || isExhausted) && !isEligible && !isCreator
PR checklist
[risk=no|low|moderate|severe]
in the PR title as outlined in CONTRIBUTING.md.