-
Notifications
You must be signed in to change notification settings - Fork 1.3k
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
[PM-3726] Force migration of legacy user's encryption key #6195
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.
Looks good overall. I wonder though, if we have a plan to remove this code after all users have been migrated? This code feels almost like a "one off" that might add bloat to the code base in the long run. Just a thought.
New Issues
Fixed Issues
|
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.
Awesome work on this!
Several clarifying questions below + tests are failing at the moment.
apps/web/src/app/auth/migrate-encryption/migrate-legacy-encryption.component.ts
Outdated
Show resolved
Hide resolved
apps/web/src/app/auth/migrate-encryption/migrate-legacy-encryption.component.ts
Show resolved
Hide resolved
apps/web/src/app/auth/migrate-encryption/migrate-legacy-encryption.component.ts
Show resolved
Hide resolved
apps/web/src/app/auth/migrate-encryption/migrate-legacy-encryption.service.spec.ts
Outdated
Show resolved
Hide resolved
apps/web/src/app/auth/migrate-encryption/migrate-legacy-encryption.service.ts
Outdated
Show resolved
Hide resolved
apps/web/src/app/auth/migrate-encryption/migrate-legacy-encryption.service.ts
Show resolved
Hide resolved
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!
apps/web/src/app/auth/migrate-encryption/migrate-legacy-encryption.component.ts
Show resolved
Hide resolved
- also remove card in vault since legacy users can't login
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.
Platform changes look good, just one question for @djsmith85's expertise on locale file stuff.
@@ -475,8 +475,8 @@ | |||
"maxFileSize": { | |||
"message": "Maximum file size is 500 MB." | |||
}, | |||
"updateKey": { | |||
"message": "You cannot use this feature until you update your encryption key." | |||
"encryptionKeyMigrationRequired": { |
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.
@djsmith85 What's the rule on updating locale keys again? Should we avoid changing the key or is this correct when we also update the 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.
@justindbaur Thanks for the ping.
If the message is changed then the key need to be changed for the translations to be removed in Crowdin. Additionally we need to check if the previous key was used elsewhere/possibly within a different context and also update all usages within the clients.
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 from the vault's perspective
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 really solid overall, just presented a couple of non-blocking nits.
This doesn't touch autofill, but let me know if you'd like a re-review/approval at some point.
<bit-label>{{ "masterPass" | i18n }}</bit-label> | ||
<input | ||
id="masterPassword" | ||
bitInput | ||
type="password" | ||
formControlName="masterPassword" | ||
appAutofocus | ||
/> |
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.
Accessibility Nit - Does this <bit-label>
component directly relate to the subsequent <input>
label somehow? Ideally the label for the form would have a for="<id>
value for each input field (ie. for="masterPassword
in this case)
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.
Good catch, added.
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.
Based on this comment from @shane-melton, the bit-label does not need/support a for-attribute. The bit-form-field takes care of it
const allowedStatuses = [ | ||
EmergencyAccessStatusType.Confirmed, | ||
EmergencyAccessStatusType.RecoveryInitiated, | ||
EmergencyAccessStatusType.RecoveryApproved, | ||
]; | ||
|
||
const filteredAccesses = emergencyAccess.data.filter((d) => allowedStatuses.includes(d.status)); | ||
|
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.
Very minor nit here, but in cases where I'm attempting to identify if a value exists within an array of values, using a Set data type is usually more performant.
const allowedStatuses = [ | |
EmergencyAccessStatusType.Confirmed, | |
EmergencyAccessStatusType.RecoveryInitiated, | |
EmergencyAccessStatusType.RecoveryApproved, | |
]; | |
const filteredAccesses = emergencyAccess.data.filter((d) => allowedStatuses.includes(d.status)); | |
const allowedStatuses = new Set([ | |
EmergencyAccessStatusType.Confirmed, | |
EmergencyAccessStatusType.RecoveryInitiated, | |
EmergencyAccessStatusType.RecoveryApproved, | |
]); | |
const filteredAccesses = emergencyAccess.data.filter((d) => allowedStatuses.has(d.status)); | |
.has()
identifies whether a value exists in O(1)
runtime, while .includes()
identifies values in O(n)
.
Not a blocking request, just a consideration.
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.
Nice! TIL
cdbe93c
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.
New changes look good to me! Nice work 👍
>{{ "learnMore" | i18n }}</a | ||
> | ||
</p> | ||
<app-callout type="warning">{{ "updateEncryptionKeyWarning" | i18n }}</app-callout> |
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.
Should be using the bit callout component instead of the deprecated app-callout.
I wanted to avoid running this code for every route so I've only put it on the lock guard and a direct navigation on the login component. Legacy users will be sent to the lock guard anyway if they try to get around the migration.
The direction we're headed is that you shouldn't get past auth without having a User Key. Regardless, the Auth guard checks for this and redirects to the lock component if the User Key isn't found. |
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'm not going to block this. Please ensure this service gets refactored before anyone else uses it! I also think the migration service knows far to much about HOW to encrypt things, which should be internal concerns of those domains.
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.
Nice work! One small tweak
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.
Approving as the changes I requested (messages and bit-label) have been addressed.
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!
@@ -141,10 +142,18 @@ export class VaultTimeoutService implements VaultTimeoutServiceAbstraction { | |||
} | |||
|
|||
private async migrateKeyForNeverLockIfNeeded(): Promise<void> { | |||
// Web can't set vault timeout to never |
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.
Technically we can in dev mode.
* [PM-3726] migrate legacy user's encryption key * [PM-3726] add 2fa support and pr feedback * [PM-3726] revert launch.json & webpack.config changes * [PM-3726] remove update key component - also remove card in vault since legacy users can't login * [PM-3726] Fix i18n & PR feedback * [PM-3726] make standalone component * [PM-3726] linter * [PM-3726] missing await * [PM-3726] logout legacy users with vault timeout to never * [PM-3726] add await * [PM-3726] skip auto key migration for legacy users * [PM-3726] pr feedback * [PM-3726] move check for web into migrate method --------- Co-authored-by: Jared Snider <[email protected]> (cherry picked from commit 8c06508)
Type of change
Objective
Legacy encryption users have been unable to login following the key migration. Although we included code to account for legacy accounts within the crypto service, we made the assumption during the login process that a user key should always be available.
The PR detects these accounts and creates a new migration component for them. This new migration component is only available on web currently, so other clients will have their login process short circuited with an error directing them to migrate on web.
I have also removed references to the old
UpdateKeyComponent
and the card on the vault page. The migration is now required.Code changes
Screenshots
Before you submit