Project import generated by Copybara.
GitOrigin-RevId: d9e9e3fb4e31372ec1fb43b178994ca78fa8fe70
diff --git a/static_src/elements/hotlist/mr-hotlist-people-page/mr-hotlist-people-page.test.js b/static_src/elements/hotlist/mr-hotlist-people-page/mr-hotlist-people-page.test.js
new file mode 100644
index 0000000..b7dd6dc
--- /dev/null
+++ b/static_src/elements/hotlist/mr-hotlist-people-page/mr-hotlist-people-page.test.js
@@ -0,0 +1,176 @@
+// 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.
+
+import {assert} from 'chai';
+import sinon from 'sinon';
+
+import {store, resetState} from 'reducers/base.js';
+import {hotlists} from 'reducers/hotlists.js';
+import * as sitewide from 'reducers/sitewide.js';
+
+import * as example from 'shared/test/constants-hotlists.js';
+import * as exampleUsers from 'shared/test/constants-users.js';
+
+import {MrHotlistPeoplePage} from './mr-hotlist-people-page.js';
+
+/** @type {MrHotlistPeoplePage} */
+let element;
+
+describe('mr-hotlist-people-page (unconnected)', () => {
+ beforeEach(() => {
+ // @ts-ignore
+ element = document.createElement('mr-hotlist-people-page-base');
+ document.body.appendChild(element);
+ });
+
+ afterEach(() => {
+ document.body.removeChild(element);
+ });
+
+ it('shows hotlist fetch error', async () => {
+ element._fetchError = new Error('This is an important error');
+ element._fetchError.description = 'This is an important error';
+ await element.updateComplete;
+ assert.include(element.shadowRoot.innerHTML, 'important error');
+ });
+
+ it('renders placeholders with no data', async () => {
+ await element.updateComplete;
+
+ const placeholders = element.shadowRoot.querySelectorAll('.placeholder');
+ assert.equal(placeholders.length, 2);
+ });
+
+ it('renders placeholders with editors list but no user data', async () => {
+ element._editors = [null, null];
+ await element.updateComplete;
+
+ const placeholders = element.shadowRoot.querySelectorAll('.placeholder');
+ assert.equal(placeholders.length, 3);
+ });
+
+ it('renders "No editors"', async () => {
+ element._editors = [];
+ await element.updateComplete;
+
+ assert.include(element.shadowRoot.innerHTML, 'No editors');
+ });
+
+ it('renders hotlist', async () => {
+ element._hotlist = example.HOTLIST;
+ element._owner = exampleUsers.USER;
+ element._editors = [exampleUsers.USER_2];
+ await element.updateComplete;
+ });
+
+ it('shows controls iff user has admin permissions', async () => {
+ element._editors = [exampleUsers.USER_2];
+ await element.updateComplete;
+
+ assert.equal(element.shadowRoot.querySelectorAll('button').length, 0);
+
+ element._permissions = [hotlists.ADMINISTER];
+ await element.updateComplete;
+
+ assert.equal(element.shadowRoot.querySelectorAll('button').length, 2);
+ });
+
+ it('shows remove button if user is editing themselves', async () => {
+ element._editors = [exampleUsers.USER, exampleUsers.USER_2];
+ element._currentUserName = exampleUsers.USER_2.name;
+ await element.updateComplete;
+
+ assert.equal(element.shadowRoot.querySelectorAll('button').length, 1);
+ });
+});
+
+describe('mr-hotlist-people-page (connected)', () => {
+ beforeEach(() => {
+ store.dispatch(resetState());
+
+ // @ts-ignore
+ element = document.createElement('mr-hotlist-people-page');
+ document.body.appendChild(element);
+
+ // Stop Redux from overriding values being tested.
+ sinon.stub(element, 'stateChanged');
+ });
+
+ afterEach(() => {
+ element.stateChanged.restore();
+ document.body.removeChild(element);
+ });
+
+ it('initializes', async () => {
+ assert.instanceOf(element, MrHotlistPeoplePage);
+ });
+
+ it('updates page title and header', async () => {
+ element._hotlist = {...example.HOTLIST, displayName: 'Hotlist-Name'};
+ await element.updateComplete;
+
+ const state = store.getState();
+ assert.deepEqual(sitewide.pageTitle(state), 'People - Hotlist-Name');
+ assert.deepEqual(sitewide.headerTitle(state), 'Hotlist Hotlist-Name');
+ });
+
+ it('adds editors', async () => {
+ element._hotlist = example.HOTLIST;
+ element._permissions = [hotlists.ADMINISTER];
+ await element.updateComplete;
+
+ const input = /** @type {HTMLInputElement} */
+ (element.shadowRoot.getElementById('add'));
+ input.value = 'test@example.com, test2@example.com';
+
+ const update = sinon.spy(hotlists, 'update');
+ try {
+ await element._onAddEditors(new Event('submit'));
+
+ const editors = ['users/test@example.com', 'users/test2@example.com'];
+ sinon.assert.calledWith(update, example.HOTLIST.name, {editors});
+ } finally {
+ update.restore();
+ }
+ });
+
+ it('_onAddEditors ignores empty input', async () => {
+ element._permissions = [hotlists.ADMINISTER];
+ await element.updateComplete;
+
+ const input = /** @type {HTMLInputElement} */
+ (element.shadowRoot.getElementById('add'));
+ input.value = ' ';
+
+ const update = sinon.spy(hotlists, 'update');
+ try {
+ await element._onAddEditors(new Event('submit'));
+ sinon.assert.notCalled(update);
+ } finally {
+ update.restore();
+ }
+ });
+
+ it('removes editors', async () => {
+ element._hotlist = example.HOTLIST;
+
+ const removeEditors = sinon.spy(hotlists, 'removeEditors');
+ try {
+ await element._removeEditor(exampleUsers.NAME_2);
+
+ sinon.assert.calledWith(
+ removeEditors, example.HOTLIST.name, [exampleUsers.NAME_2]);
+ } finally {
+ removeEditors.restore();
+ }
+ });
+});
+
+it('mr-hotlist-people-page (stateChanged)', () => {
+ // @ts-ignore
+ element = document.createElement('mr-hotlist-people-page');
+ document.body.appendChild(element);
+ assert.instanceOf(element, MrHotlistPeoplePage);
+ document.body.removeChild(element);
+});