1
0
mirror of https://github.com/bitwarden/browser.git synced 2025-03-20 14:59:32 +01:00

[PM-16858] - adjust generator dialog action button to match browser extension UI (#12788)

* adjust generator dialog buttons to match browser extension UI

* put dialog label into generator config

* fix types. remove i18n key

* use event emitted pattern for getting algorithm config

* favor arrow function

* move function call

* append key to i18n prop

* fix test
This commit is contained in:
Jordan Aasen 2025-01-10 17:21:12 -08:00 committed by GitHub
parent 3c994930ac
commit e1434d8dd5
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
11 changed files with 46 additions and 6 deletions

View File

@ -2879,6 +2879,12 @@
"weakAndBreachedMasterPasswordDesc": {
"message": "Weak password identified and found in a data breach. Use a strong and unique password to protect your account. Are you sure you want to use this password?"
},
"useThisPassword": {
"message": "Use this password"
},
"useThisUsername": {
"message": "Use this username"
},
"checkForBreaches": {
"message": "Check known data breaches for this password"
},

View File

@ -4,6 +4,7 @@
<vault-cipher-form-generator
[type]="data.type"
(valueGenerated)="onCredentialGenerated($event)"
[algorithm]="algorithm"
/>
<bit-item>
<button
@ -25,13 +26,10 @@
type="button"
class="primary"
(click)="applyCredentials()"
appA11yTitle="{{ 'select' | i18n }}"
appA11yTitle="{{ buttonLabel }}"
bitDialogClose
>
<i class="bwi bwi-lg bwi-fw bwi-check" aria-hidden="true"></i>
</button>
<button type="button" data-dismiss="modal" (click)="clearCredentials()" bitDialogClose>
{{ "cancel" | i18n }}
{{ buttonLabel }}
</button>
</div>
</ng-container>

View File

@ -14,6 +14,7 @@ import {
CredentialGeneratorHistoryDialogComponent,
GeneratorModule,
} from "@bitwarden/generator-components";
import { AlgorithmInfo } from "@bitwarden/generator-core";
import { CipherFormGeneratorComponent } from "@bitwarden/vault";
type CredentialGeneratorParams = {
@ -38,12 +39,17 @@ type CredentialGeneratorParams = {
})
export class CredentialGeneratorDialogComponent {
credentialValue?: string;
buttonLabel?: string;
constructor(
@Inject(DIALOG_DATA) protected data: CredentialGeneratorParams,
private dialogService: DialogService,
) {}
algorithm = (selected: AlgorithmInfo) => {
this.buttonLabel = selected.useGeneratedValue;
};
applyCredentials = () => {
this.data.onCredentialGenerated(this.credentialValue);
};

View File

@ -93,6 +93,10 @@ export class PasswordGeneratorComponent implements OnInit, OnDestroy {
@Output()
readonly onGenerated = new EventEmitter<GeneratedCredential>();
/** emits algorithm info when the selected algorithm changes */
@Output()
readonly onAlgorithm = new EventEmitter<AlgorithmInfo>();
async ngOnInit() {
if (this.userId) {
this.userId$.next(this.userId);
@ -185,6 +189,7 @@ export class PasswordGeneratorComponent implements OnInit, OnDestroy {
// template bindings refresh immediately
this.zone.run(() => {
this.algorithm$.next(algorithm);
this.onAlgorithm.next(algorithm);
});
});

View File

@ -78,6 +78,10 @@ export class UsernameGeneratorComponent implements OnInit, OnDestroy {
@Output()
readonly onGenerated = new EventEmitter<GeneratedCredential>();
/** emits algorithm info when the selected algorithm changes */
@Output()
readonly onAlgorithm = new EventEmitter<AlgorithmInfo>();
/** Removes bottom margin from internal elements */
@Input({ transform: coerceBooleanProperty }) disableMargin = false;
@ -247,6 +251,7 @@ export class UsernameGeneratorComponent implements OnInit, OnDestroy {
// template bindings refresh immediately
this.zone.run(() => {
this.algorithm$.next(algorithm);
this.onAlgorithm.next(algorithm);
});
});

View File

@ -58,6 +58,7 @@ const PASSPHRASE: CredentialGeneratorConfiguration<
generateKey: "generatePassphrase",
generatedValueKey: "passphrase",
copyKey: "copyPassphrase",
useGeneratedValueKey: "useThisPassphrase",
onlyOnRequest: false,
request: [],
engine: {
@ -119,6 +120,7 @@ const PASSWORD: CredentialGeneratorConfiguration<
generateKey: "generatePassword",
generatedValueKey: "password",
copyKey: "copyPassword",
useGeneratedValueKey: "useThisPassword",
onlyOnRequest: false,
request: [],
engine: {
@ -195,6 +197,7 @@ const USERNAME: CredentialGeneratorConfiguration<EffUsernameGenerationOptions, N
generateKey: "generateUsername",
generatedValueKey: "username",
copyKey: "copyUsername",
useGeneratedValueKey: "useThisUsername",
onlyOnRequest: false,
request: [],
engine: {
@ -247,6 +250,7 @@ const CATCHALL: CredentialGeneratorConfiguration<CatchallGenerationOptions, NoPo
generateKey: "generateEmail",
generatedValueKey: "email",
copyKey: "copyEmail",
useGeneratedValueKey: "useThisEmail",
onlyOnRequest: false,
request: [],
engine: {
@ -302,6 +306,7 @@ const SUBADDRESS: CredentialGeneratorConfiguration<SubaddressGenerationOptions,
generateKey: "generateEmail",
generatedValueKey: "email",
copyKey: "copyEmail",
useGeneratedValueKey: "useThisEmail",
onlyOnRequest: false,
request: [],
engine: {
@ -359,6 +364,7 @@ export function toCredentialGeneratorConfiguration<Settings extends ApiSettings
generateKey: "generateEmail",
generatedValueKey: "email",
copyKey: "copyEmail",
useGeneratedValueKey: "useThisEmail",
onlyOnRequest: true,
request: configuration.forwarder.request,
engine: {

View File

@ -74,6 +74,7 @@ const SomeNameKey = "passphraseKey";
const SomeGenerateKey = "generateKey";
const SomeGeneratedValueKey = "generatedValueKey";
const SomeCopyKey = "copyKey";
const SomeUseGeneratedValueKey = "useGeneratedValueKey";
// fake the configuration
const SomeConfiguration: CredentialGeneratorConfiguration<SomeSettings, SomePolicy> = {
@ -83,6 +84,7 @@ const SomeConfiguration: CredentialGeneratorConfiguration<SomeSettings, SomePoli
generateKey: SomeGenerateKey,
generatedValueKey: SomeGeneratedValueKey,
copyKey: SomeCopyKey,
useGeneratedValueKey: SomeUseGeneratedValueKey,
onlyOnRequest: false,
request: [],
engine: {

View File

@ -258,6 +258,7 @@ export class CredentialGeneratorService {
generate: this.i18nService.t(generator.generateKey),
generatedValue: this.i18nService.t(generator.generatedValueKey),
copy: this.i18nService.t(generator.copyKey),
useGeneratedValue: this.i18nService.t(generator.useGeneratedValueKey),
onlyOnRequest: generator.onlyOnRequest,
request: generator.request,
};

View File

@ -37,6 +37,9 @@ export type AlgorithmInfo = {
/* Localized copy button label */
copy: string;
/* Localized dialog button label */
useGeneratedValue: string;
/* Localized generated value label */
generatedValue: string;
@ -82,6 +85,9 @@ export type CredentialGeneratorInfo = {
/* Localization key for the copy button label */
copyKey: string;
/* Localized "use generated credential" button label */
useGeneratedValueKey: string;
/* Localization key for describing values generated by this generator */
generatedValueKey: string;

View File

@ -2,9 +2,11 @@
*ngIf="type === 'password'"
[disableMargin]="disableMargin"
(onGenerated)="onCredentialGenerated($event)"
(onAlgorithm)="algorithm($event)"
></tools-password-generator>
<tools-username-generator
*ngIf="type === 'username'"
[disableMargin]="disableMargin"
(onGenerated)="onCredentialGenerated($event)"
(onAlgorithm)="algorithm($event)"
></tools-username-generator>

View File

@ -5,7 +5,7 @@ import { CommonModule } from "@angular/common";
import { Component, EventEmitter, Input, Output } from "@angular/core";
import { GeneratorModule } from "@bitwarden/generator-components";
import { GeneratedCredential } from "@bitwarden/generator-core";
import { AlgorithmInfo, GeneratedCredential } from "@bitwarden/generator-core";
/**
* Renders a password or username generator UI and emits the most recently generated value.
@ -18,6 +18,9 @@ import { GeneratedCredential } from "@bitwarden/generator-core";
imports: [CommonModule, GeneratorModule],
})
export class CipherFormGeneratorComponent {
@Input()
algorithm: (selected: AlgorithmInfo) => void;
/**
* The type of generator form to show.
*/