Commit 2a439018 authored by Viktor Semeniuk's avatar Viktor Semeniuk Committed by Commit Bot

[Passwords] UI for password check


This change adds basic UI for password check page. Change includes
number of compromised credentials, last refresh time, and button to run
password check manually.

Bug: 1047726
Change-Id: If7a9f7ad2c35ccd070e090514d38d313a22d6d6b
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/2068602Reviewed-by: default avatarMarc Treib <treib@chromium.org>
Reviewed-by: default avatarJan Wilken Dörrie <jdoerrie@chromium.org>
Commit-Queue: Viktor Semeniuk <vsemeniuk@google.com>
Cr-Commit-Position: refs/heads/master@{#744616}
parent 4369629b
......@@ -448,9 +448,18 @@
<message name="IDS_SETTINGS_CHECK_PASSWORDS" desc="Name for the check passwords subsection and settings entry used to perform a password bulk check.">
Check passwords
</message>
<message name="IDS_SETTINGS_CHECKED_PASSWORDS" desc="Title above amount of found compromised passwords after password bulk check.">
Checked passwords
</message>
<message name="IDS_SETTINGS_CHECK_PASSWORDS_DESCRIPTION" desc="Explanation of the passwords bulk check feature found within the password settings.">
Keep your passwords safe from data breaches and other security issues
</message>
<message name="IDS_SETTINGS_LEAKED_PASSWORDS_COUNT" desc="Number of compromised passwords found during bulk check.">
<ph name="COUNT">$1<ex>5</ex></ph> compromised passwords
</message>
<message name="IDS_SETTINGS_CHECK_PASSWORDS_AGAIN" desc="Button to start bulk password check manually in passwords check section.">
Check again
</message>
<message name="IDS_SETTINGS_PASSWORDS_SAVE_PASSWORDS_TOGGLE_LABEL" desc="Label for a toggle that allows users to be prompted if they want to save their passwords when logging into webpages.">
Offer to save passwords
</message>
......
956520bbbe69fb947a771b72de567f1bac2ac5c4
\ No newline at end of file
956520bbbe69fb947a771b72de567f1bac2ac5c4
\ No newline at end of file
956520bbbe69fb947a771b72de567f1bac2ac5c4
\ No newline at end of file
......@@ -52,10 +52,9 @@
</template>
<template is="dom-if" route-path="/passwords/check">
<settings-subpage
associated-control="[[$$('#passwordManagerButton')]]"
page-title="$i18n{checkPasswords}"
learn-more-url="$i18n{passwordCheckLearnMoreURL}">
<password-check></password-check>
<settings-password-check></settings-password-check>
</settings-subpage>
</template>
<template is="dom-if" route-path="/payments">
......
<link rel="import" href="chrome://resources/html/polymer.html">
<dom-module id="password-check">
<link rel="import" href="chrome://resources/cr_elements/cr_button/cr_button.html">
<link rel="import" href="../i18n_setup.html">
<link rel="import" href="../settings_shared_css.html">
<link rel="import" href="chrome://resources/cr_elements/icons.html">
<link rel="import" href="chrome://resources/polymer/v1_0/iron-icon/iron-icon.html">
<link rel="import" href="chrome://resources/html/i18n_behavior.html">
<dom-module id="settings-password-check">
<template>
<style include="settings-shared">
#leak-passwords-icon {
--iron-icon-fill-color: var(--google-red-600);
padding-inline-end: 20px;
}
</style>
<div class="settings-box first two-line" id="leakCheckHeader">
<!--TODO(https://crbug.com/1047726) add background to icon-->
<iron-icon id="leak-passwords-icon" icon="cr:warning"></iron-icon>
<div class="start settings-box-text">
<div>
$i18n{checkedPasswords}
<span class="secondary inline" id="lastCompletedCheck">
&bull; [[getLastCompletedCheck_(passwordLeakCount_)]]
</span>
</div>
<div class="secondary" id="passwordLeakCount"
name="[[passwordLeakCount_]]">
[[getLeakedPasswordsCount_(passwordLeakCount_)]]
</div>
</div>
<cr-button id="controlPasswordCheckButton"
on-click="onPasswordCheckButtonClick_">
$i18n{checkPasswordsAgain}
</cr-button>
</div>
<div class="settings-box"></div>
</template>
<script src="password_check.js"></script>
</dom-module>
......@@ -4,4 +4,52 @@
Polymer({
is: 'settings-password-check',
behaviors: [I18nBehavior],
properties: {
/** @private */
passwordLeakCount_: {
type: Number,
value: 0,
},
/** @private */
lastCompletedCheck_: Date,
},
/**
* @type {PasswordManagerProxy}
* @private
*/
passwordManager_: null,
/** @override */
attached() {
// It's just a placeholder at the moment.
this.passwordLeakCount_ = 5;
// Set the manager. These can be overridden by tests.
this.passwordManager_ = PasswordManagerImpl.getInstance();
},
/**
* Start/Stop bulk password check.
* @private
*/
onPasswordCheckButtonClick_() {
// TODO(https://crbug.com/1047726): By click on this button user should be
// able to 'Cancel' current check.
this.passwordManager_.startBulkPasswordCheck();
},
getLeakedPasswordsCount_() {
return this.i18n('checkPasswordLeakCount', this.passwordLeakCount_);
},
getLastCompletedCheck_() {
// TODO(https://crbug.com/1047726): use lastCompletedCheck_ to return proper
// passed time from the last password check.
return '5 min ago';
},
});
......@@ -148,6 +148,11 @@ class PasswordManagerProxy {
* @return {!Promise<(boolean)>} A promise that resolves to the opt-in state.
*/
isOptedInForAccountStorage() {}
/**
* Requests the start of the bulk password check.
*/
startBulkPasswordCheck() {}
}
/** @typedef {chrome.passwordsPrivate.PasswordUiEntry} */
......@@ -289,6 +294,9 @@ class PasswordManagerImpl {
chrome.passwordsPrivate.isOptedInForAccountStorage(resolve);
});
}
/** @override */
startBulkPasswordCheck() {}
}
cr.addSingletonGetter(PasswordManagerImpl);
......@@ -738,7 +738,10 @@ void AddAutofillStrings(content::WebUIDataSource* html_source,
{"autofillPageTitle", IDS_SETTINGS_AUTOFILL},
{"passwords", IDS_SETTINGS_PASSWORDS},
{"checkPasswords", IDS_SETTINGS_CHECK_PASSWORDS},
{"checkedPasswords", IDS_SETTINGS_CHECKED_PASSWORDS},
{"checkPasswordsDescription", IDS_SETTINGS_CHECK_PASSWORDS_DESCRIPTION},
{"checkPasswordLeakCount", IDS_SETTINGS_LEAKED_PASSWORDS_COUNT},
{"checkPasswordsAgain", IDS_SETTINGS_CHECK_PASSWORDS_AGAIN},
{"creditCards", IDS_AUTOFILL_PAYMENT_METHODS},
{"noCreditCardsFound", IDS_SETTINGS_PAYMENT_METHODS_NONE},
{"googlePayments", IDS_SETTINGS_GOOGLE_PAYMENTS},
......
......@@ -341,6 +341,33 @@ TEST_F('CrSettingsPasswordsSectionTest', 'All', function() {
mocha.run();
});
/**
* Test fixture for
* chrome/browser/resources/settings/autofill_page/passwords_check.html.
* @constructor
* @extends {CrSettingsBrowserTest}
*/
function CrSettingsPasswordsCheckTest() {}
CrSettingsPasswordsCheckTest.prototype = {
__proto__: CrSettingsBrowserTest.prototype,
/** @override */
browsePreload: 'chrome://settings/autofill_page/passwords_check.html',
/** @override */
extraLibraries: CrSettingsBrowserTest.prototype.extraLibraries.concat([
'password_check_test.js',
'../test_browser_proxy.js',
'passwords_and_autofill_fake_data.js',
'test_password_manager_proxy.js',
]),
};
TEST_F('CrSettingsPasswordsCheckTest', 'All', function() {
mocha.run();
});
GEN('#if defined(OS_CHROMEOS)');
/**
* Test fixture for CrOS specific behavior in
......
// Copyright 2020 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
/** @fileoverview Runs the Polymer Check Password tests. */
cr.define('settings_passwords_check', function() {
function createCheckPasswordSection() {
// Create a passwords-section to use for testing.
const passwordsSection =
this.document.createElement('settings-password-check');
this.document.body.appendChild(passwordsSection);
Polymer.dom.flush();
return passwordsSection;
}
suite('PasswordsCheckSection', function() {
/** @type {TestPasswordManagerProxy} */
let passwordManager = null;
suiteSetup(function() {
loadTimeData.overrideValues({enablePasswordCheck: true});
});
setup(function() {
PolymerTest.clearBody();
// Override the PasswordManagerImpl for testing.
passwordManager = new TestPasswordManagerProxy();
PasswordManagerImpl.instance_ = passwordManager;
});
// Test verifies that clicking 'Check again' make proper function call to
// password manager
test('testCheckAgainButton', function() {
const checkSection = createCheckPasswordSection();
checkSection.$.controlPasswordCheckButton.click();
return passwordManager.whenCalled('startBulkPasswordCheck');
});
});
});
......@@ -11,7 +11,7 @@
*/
class TestPasswordManagerProxy extends TestBrowserProxy {
constructor() {
super(['requestPlaintextPassword']);
super(['requestPlaintextPassword', 'startBulkPasswordCheck']);
this.actual_ = new PasswordManagerExpectations();
......@@ -138,4 +138,9 @@ class TestPasswordManagerProxy extends TestBrowserProxy {
expected.listening.accountStorageOptInState,
actual.listening.accountStorageOptInState);
}
/** @override */
startBulkPasswordCheck() {
this.methodCalled('startBulkPasswordCheck');
}
}
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment