/**
 * @license
 * Copyright (C) 2015 The Android Open Source Project
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 * http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

import '../../../test/common-test-setup-karma';
import '../../edit/gr-edit-constants';
import './gr-change-view';
import {
  ChangeStatus,
  CommentSide,
  DefaultBase,
  DiffViewMode,
  HttpMethod,
  MessageTag,
  PrimaryTab,
  SecondaryTab,
} from '../../../constants/constants';
import {GrEditConstants} from '../../edit/gr-edit-constants';
import {_testOnly_resetEndpoints} from '../../shared/gr-js-api-interface/gr-plugin-endpoints';
import {GerritNav} from '../../core/gr-navigation/gr-navigation';
import {getPluginLoader} from '../../shared/gr-js-api-interface/gr-plugin-loader';
import {_testOnly_initGerritPluginApi} from '../../shared/gr-js-api-interface/gr-gerrit';
import {EventType, PluginApi} from '../../../api/plugin';

import 'lodash/lodash';
import {
  stubRestApi,
  TestKeyboardShortcutBinder,
} from '../../../test/test-utils';
import {Shortcut} from '../../../mixins/keyboard-shortcut-mixin/keyboard-shortcut-mixin';
import {
  createAppElementChangeViewParams,
  createApproval,
  createChange,
  createChangeMessages,
  createCommit,
  createMergeable,
  createPreferences,
  createRevision,
  createRevisions,
  createServerInfo,
  createUserConfig,
  TEST_NUMERIC_CHANGE_ID,
  TEST_PROJECT_NAME,
  createEditRevision,
  createAccountWithIdNameAndEmail,
  createChangeViewChange,
  createRelatedChangeAndCommitInfo,
} from '../../../test/test-data-generators';
import {ChangeViewPatchRange, GrChangeView} from './gr-change-view';
import {
  AccountId,
  ApprovalInfo,
  BasePatchSetNum,
  ChangeId,
  ChangeInfo,
  CommitId,
  CommitInfo,
  EditInfo,
  EditPatchSetNum,
  ElementPropertyDeepChange,
  GitRef,
  NumericChangeId,
  ParentPatchSetNum,
  PatchRange,
  PatchSetNum,
  RelatedChangeAndCommitInfo,
  ReviewInputTag,
  RevisionInfo,
  RevisionPatchSetNum,
  RobotId,
  Timestamp,
  UrlEncodedCommentId,
} from '../../../types/common';
import {
  pressAndReleaseKeyOn,
  tap,
} from '@polymer/iron-test-helpers/mock-interactions';
import {GrEditControls} from '../../edit/gr-edit-controls/gr-edit-controls';
import {AppElementChangeViewParams} from '../../gr-app-types';
import {SinonFakeTimers, SinonStubbedMember} from 'sinon/pkg/sinon-esm';
import {RestApiService} from '../../../services/gr-rest-api/gr-rest-api';
import {CustomKeyboardEvent} from '../../../types/events';
import {
  CommentThread,
  DraftInfo,
  UIDraft,
  UIRobot,
} from '../../../utils/comment-util';
import {ChangeComments} from '../../diff/gr-comment-api/gr-comment-api';
import {GerritView} from '../../../services/router/router-model';
import {ParsedChangeInfo} from '../../../types/types';
import {GrRelatedChangesList} from '../gr-related-changes-list/gr-related-changes-list';
import {appContext} from '../../../services/app-context';
import {ChangeStates} from '../../shared/gr-change-status/gr-change-status';

const pluginApi = _testOnly_initGerritPluginApi();
const fixture = fixtureFromElement('gr-change-view');

suite('gr-change-view tests', () => {
  let element: GrChangeView;

  let navigateToChangeStub: SinonStubbedMember<
    typeof GerritNav.navigateToChange
  >;

  suiteSetup(() => {
    const kb = TestKeyboardShortcutBinder.push();
    kb.bindShortcut(Shortcut.SEND_REPLY, 'ctrl+enter');
    kb.bindShortcut(Shortcut.REFRESH_CHANGE, 'shift+r');
    kb.bindShortcut(Shortcut.OPEN_REPLY_DIALOG, 'a');
    kb.bindShortcut(Shortcut.OPEN_DOWNLOAD_DIALOG, 'd');
    kb.bindShortcut(Shortcut.TOGGLE_DIFF_MODE, 'm');
    kb.bindShortcut(Shortcut.TOGGLE_CHANGE_STAR, 's');
    kb.bindShortcut(Shortcut.UP_TO_DASHBOARD, 'u');
    kb.bindShortcut(Shortcut.EXPAND_ALL_MESSAGES, 'x');
    kb.bindShortcut(Shortcut.COLLAPSE_ALL_MESSAGES, 'z');
    kb.bindShortcut(Shortcut.OPEN_DIFF_PREFS, ',');
    kb.bindShortcut(Shortcut.EDIT_TOPIC, 't');
  });

  suiteTeardown(() => {
    TestKeyboardShortcutBinder.pop();
  });

  const TEST_SCROLL_TOP_PX = 100;

  const ROBOT_COMMENTS_LIMIT = 10;

  // TODO: should have a mock service to generate VALID fake data
  const THREADS: CommentThread[] = [
    {
      comments: [
        {
          path: '/COMMIT_MSG',
          author: {
            _account_id: 1000000 as AccountId,
            name: 'user',
            username: 'user',
          },
          patch_set: 2 as PatchSetNum,
          robot_id: 'rb1' as RobotId,
          id: 'ecf0b9fa_fe1a5f62' as UrlEncodedCommentId,
          line: 5,
          updated: '2018-02-08 18:49:18.000000000' as Timestamp,
          message: 'test',
          unresolved: true,
        },
        {
          path: '/COMMIT_MSG',
          author: {
            _account_id: 1000000 as AccountId,
            name: 'user',
            username: 'user',
          },
          patch_set: 4 as PatchSetNum,
          id: 'ecf0b9fa_fe1a5f62_1' as UrlEncodedCommentId,
          line: 5,
          updated: '2018-02-08 18:49:18.000000000' as Timestamp,
          message: 'test',
          unresolved: true,
        },
        {
          id: '503008e2_0ab203ee' as UrlEncodedCommentId,
          path: '/COMMIT_MSG',
          line: 5,
          in_reply_to: 'ecf0b9fa_fe1a5f62' as UrlEncodedCommentId,
          updated: '2018-02-13 22:48:48.018000000' as Timestamp,
          message: 'draft',
          unresolved: false,
          __draft: true,
          __draftID: '0.m683trwff68',
          __editing: false,
          patch_set: 2 as PatchSetNum,
        },
      ],
      patchNum: 4 as RevisionPatchSetNum,
      path: '/COMMIT_MSG',
      line: 5,
      rootId: 'ecf0b9fa_fe1a5f62' as UrlEncodedCommentId,
      commentSide: CommentSide.REVISION,
    },
    {
      comments: [
        {
          path: '/COMMIT_MSG',
          author: {
            _account_id: 1000000 as AccountId,
            name: 'user',
            username: 'user',
          },
          patch_set: 3 as PatchSetNum,
          id: 'ecf0b9fa_fe5f62' as UrlEncodedCommentId,
          robot_id: 'rb2' as RobotId,
          line: 5,
          updated: '2018-02-08 18:49:18.000000000' as Timestamp,
          message: 'test',
          unresolved: true,
        },
        {
          path: 'test.txt',
          author: {
            _account_id: 1000000 as AccountId,
            name: 'user',
            username: 'user',
          },
          patch_set: 3 as PatchSetNum,
          id: '09a9fb0a_1484e6cf' as UrlEncodedCommentId,
          side: CommentSide.PARENT,
          updated: '2018-02-13 22:47:19.000000000' as Timestamp,
          message: 'Some comment on another patchset.',
          unresolved: false,
        },
      ],
      patchNum: 3 as PatchSetNum,
      path: 'test.txt',
      rootId: '09a9fb0a_1484e6cf' as UrlEncodedCommentId,
      commentSide: CommentSide.PARENT,
    },
    {
      comments: [
        {
          path: '/COMMIT_MSG',
          author: {
            _account_id: 1000000 as AccountId,
            name: 'user',
            username: 'user',
          },
          patch_set: 2 as PatchSetNum,
          id: '8caddf38_44770ec1' as UrlEncodedCommentId,
          line: 4,
          updated: '2018-02-13 22:48:40.000000000' as Timestamp,
          message: 'Another unresolved comment',
          unresolved: true,
        },
      ],
      patchNum: 2 as RevisionPatchSetNum,
      path: '/COMMIT_MSG',
      line: 4,
      rootId: '8caddf38_44770ec1' as UrlEncodedCommentId,
      commentSide: CommentSide.REVISION,
    },
    {
      comments: [
        {
          path: '/COMMIT_MSG',
          author: {
            _account_id: 1000000 as AccountId,
            name: 'user',
            username: 'user',
          },
          patch_set: 2 as PatchSetNum,
          id: 'scaddf38_44770ec1' as UrlEncodedCommentId,
          line: 4,
          updated: '2018-02-14 22:48:40.000000000' as Timestamp,
          message: 'Yet another unresolved comment',
          unresolved: true,
        },
      ],
      patchNum: 2 as RevisionPatchSetNum,
      path: '/COMMIT_MSG',
      line: 4,
      rootId: 'scaddf38_44770ec1' as UrlEncodedCommentId,
      commentSide: CommentSide.REVISION,
    },
    {
      comments: [
        {
          id: 'zcf0b9fa_fe1a5f62' as UrlEncodedCommentId,
          path: '/COMMIT_MSG',
          line: 6,
          updated: '2018-02-15 22:48:48.018000000' as Timestamp,
          message: 'resolved draft',
          unresolved: false,
          __draft: true,
          __draftID: '0.m683trwff68',
          __editing: false,
          patch_set: 2 as PatchSetNum,
        },
      ],
      patchNum: 4 as RevisionPatchSetNum,
      path: '/COMMIT_MSG',
      line: 6,
      rootId: 'zcf0b9fa_fe1a5f62' as UrlEncodedCommentId,
      commentSide: CommentSide.REVISION,
    },
    {
      comments: [
        {
          path: '/COMMIT_MSG',
          author: {
            _account_id: 1000000 as AccountId,
            name: 'user',
            username: 'user',
          },
          patch_set: 4 as PatchSetNum,
          id: 'rc1' as UrlEncodedCommentId,
          line: 5,
          updated: '2019-02-08 18:49:18.000000000' as Timestamp,
          message: 'test',
          unresolved: true,
          robot_id: 'rc1' as RobotId,
        },
      ],
      patchNum: 4 as RevisionPatchSetNum,
      path: '/COMMIT_MSG',
      line: 5,
      rootId: 'rc1' as UrlEncodedCommentId,
      commentSide: CommentSide.REVISION,
    },
    {
      comments: [
        {
          path: '/COMMIT_MSG',
          author: {
            _account_id: 1000000 as AccountId,
            name: 'user',
            username: 'user',
          },
          patch_set: 4 as PatchSetNum,
          id: 'rc2' as UrlEncodedCommentId,
          line: 5,
          updated: '2019-03-08 18:49:18.000000000' as Timestamp,
          message: 'test',
          unresolved: true,
          robot_id: 'rc2' as RobotId,
        },
        {
          path: '/COMMIT_MSG',
          author: {
            _account_id: 1000000 as AccountId,
            name: 'user',
            username: 'user',
          },
          patch_set: 4 as PatchSetNum,
          id: 'c2_1' as UrlEncodedCommentId,
          line: 5,
          updated: '2019-03-08 18:49:18.000000000' as Timestamp,
          message: 'test',
          unresolved: true,
        },
      ],
      patchNum: 4 as RevisionPatchSetNum,
      path: '/COMMIT_MSG',
      line: 5,
      rootId: 'rc2' as UrlEncodedCommentId,
      commentSide: CommentSide.REVISION,
    },
  ];

  setup(() => {
    // Since pluginEndpoints are global, must reset state.
    _testOnly_resetEndpoints();
    navigateToChangeStub = sinon.stub(GerritNav, 'navigateToChange');

    stubRestApi('getConfig').returns(
      Promise.resolve({
        ...createServerInfo(),
        user: {
          ...createUserConfig(),
          anonymous_coward_name: 'test coward name',
        },
      })
    );
    stubRestApi('getAccount').returns(Promise.resolve(undefined));
    stubRestApi('getDiffComments').returns(Promise.resolve({}));
    stubRestApi('getDiffRobotComments').returns(Promise.resolve({}));
    stubRestApi('getDiffDrafts').returns(Promise.resolve({}));
    element = fixture.instantiate();
    element._changeNum = TEST_NUMERIC_CHANGE_ID;
    sinon.stub(element.$.actions, 'reload').returns(Promise.resolve());
    getPluginLoader().loadPlugins([]);
    pluginApi.install(
      plugin => {
        plugin.registerDynamicCustomComponent(
          'change-view-tab-header',
          'gr-checks-change-view-tab-header-view'
        );
        plugin.registerDynamicCustomComponent(
          'change-view-tab-content',
          'gr-checks-view'
        );
      },
      '0.1',
      'http://some/plugins/url.js'
    );
  });

  teardown(done => {
    flush(() => {
      done();
    });
  });

  test('_handleMessageAnchorTap', () => {
    element._changeNum = 1 as NumericChangeId;
    element._patchRange = {
      basePatchNum: ParentPatchSetNum,
      patchNum: 1 as RevisionPatchSetNum,
    };
    element._change = createChangeViewChange();
    const getUrlStub = sinon.stub(GerritNav, 'getUrlForChange');
    const replaceStateStub = sinon.stub(history, 'replaceState');
    element._handleMessageAnchorTap(
      new CustomEvent('message-anchor-tap', {detail: {id: 'a12345'}})
    );

    assert.equal(getUrlStub.lastCall.args[4], '#message-a12345');
    assert.isTrue(replaceStateStub.called);
  });

  test('_handleDiffAgainstBase', () => {
    element._change = {
      ...createChangeViewChange(),
      revisions: createRevisions(10),
    };
    element._patchRange = {
      patchNum: 3 as RevisionPatchSetNum,
      basePatchNum: 1 as BasePatchSetNum,
    };
    sinon.stub(element, 'shouldSuppressKeyboardShortcut').returns(false);
    element._handleDiffAgainstBase(new CustomEvent('') as CustomKeyboardEvent);
    assert(navigateToChangeStub.called);
    const args = navigateToChangeStub.getCall(0).args;
    assert.equal(args[0], element._change);
    assert.equal(args[1], 3 as PatchSetNum);
  });

  test('_handleDiffAgainstLatest', () => {
    element._change = {
      ...createChangeViewChange(),
      revisions: createRevisions(10),
    };
    element._patchRange = {
      basePatchNum: 1 as BasePatchSetNum,
      patchNum: 3 as RevisionPatchSetNum,
    };
    sinon.stub(element, 'shouldSuppressKeyboardShortcut').returns(false);
    element._handleDiffAgainstLatest(
      new CustomEvent('') as CustomKeyboardEvent
    );
    assert(navigateToChangeStub.called);
    const args = navigateToChangeStub.getCall(0).args;
    assert.equal(args[0], element._change);
    assert.equal(args[1], 10 as PatchSetNum);
    assert.equal(args[2], 1 as PatchSetNum);
  });

  test('_handleDiffBaseAgainstLeft', () => {
    element._change = {
      ...createChangeViewChange(),
      revisions: createRevisions(10),
    };
    element._patchRange = {
      patchNum: 3 as RevisionPatchSetNum,
      basePatchNum: 1 as BasePatchSetNum,
    };
    sinon.stub(element, 'shouldSuppressKeyboardShortcut').returns(false);
    element._handleDiffBaseAgainstLeft(
      new CustomEvent('') as CustomKeyboardEvent
    );
    assert(navigateToChangeStub.called);
    const args = navigateToChangeStub.getCall(0).args;
    assert.equal(args[0], element._change);
    assert.equal(args[1], 1 as PatchSetNum);
  });

  test('_handleDiffRightAgainstLatest', () => {
    element._change = {
      ...createChangeViewChange(),
      revisions: createRevisions(10),
    };
    element._patchRange = {
      basePatchNum: 1 as BasePatchSetNum,
      patchNum: 3 as RevisionPatchSetNum,
    };
    sinon.stub(element, 'shouldSuppressKeyboardShortcut').returns(false);
    element._handleDiffRightAgainstLatest(
      new CustomEvent('') as CustomKeyboardEvent
    );
    assert(navigateToChangeStub.called);
    const args = navigateToChangeStub.getCall(0).args;
    assert.equal(args[1], 10 as PatchSetNum);
    assert.equal(args[2], 3 as PatchSetNum);
  });

  test('_handleDiffBaseAgainstLatest', () => {
    element._change = {
      ...createChangeViewChange(),
      revisions: createRevisions(10),
    };
    element._patchRange = {
      basePatchNum: 1 as BasePatchSetNum,
      patchNum: 3 as RevisionPatchSetNum,
    };
    sinon.stub(element, 'shouldSuppressKeyboardShortcut').returns(false);
    element._handleDiffBaseAgainstLatest(
      new CustomEvent('') as CustomKeyboardEvent
    );
    assert(navigateToChangeStub.called);
    const args = navigateToChangeStub.getCall(0).args;
    assert.equal(args[1], 10 as PatchSetNum);
    assert.isNotOk(args[2]);
  });

  suite('plugins adding to file tab', () => {
    setup(done => {
      element._changeNum = TEST_NUMERIC_CHANGE_ID;
      // Resolving it here instead of during setup() as other tests depend
      // on flush() not being called during setup.
      flush(() => done());
    });

    test('plugin added tab shows up as a dynamic endpoint', () => {
      assert(
        element._dynamicTabHeaderEndpoints.includes(
          'change-view-tab-header-url'
        )
      );
      const primaryTabs = element.shadowRoot!.querySelector('#primaryTabs')!;
      const paperTabs = primaryTabs.querySelectorAll<HTMLElement>('paper-tab');
      // 4 Tabs are : Files, Comment Threads, Plugin, Findings
      assert.equal(primaryTabs.querySelectorAll('paper-tab').length, 4);
      assert.equal(paperTabs[2].dataset.name, 'change-view-tab-header-url');
    });

    test('_setActivePrimaryTab switched tab correctly', done => {
      element._setActivePrimaryTab(
        new CustomEvent('', {
          detail: {tab: 'change-view-tab-header-url'},
        })
      );
      flush(() => {
        assert.equal(element._activeTabs[0], 'change-view-tab-header-url');
        done();
      });
    });

    test('show-primary-tab switched primary tab correctly', done => {
      element.dispatchEvent(
        new CustomEvent('show-primary-tab', {
          composed: true,
          bubbles: true,
          detail: {
            tab: 'change-view-tab-header-url',
          },
        })
      );
      flush(() => {
        assert.equal(element._activeTabs[0], 'change-view-tab-header-url');
        done();
      });
    });

    test('param change should switch primary tab correctly', done => {
      assert.equal(element._activeTabs[0], PrimaryTab.FILES);
      const queryMap = new Map<string, string>();
      queryMap.set('tab', PrimaryTab.FINDINGS);
      // view is required
      element.params = {
        ...createAppElementChangeViewParams(),
        ...element.params,
        queryMap,
      };
      flush(() => {
        assert.equal(element._activeTabs[0], PrimaryTab.FINDINGS);
        done();
      });
    });

    test('invalid param change should not switch primary tab', done => {
      assert.equal(element._activeTabs[0], PrimaryTab.FILES);
      const queryMap = new Map<string, string>();
      queryMap.set('tab', 'random');
      // view is required
      element.params = {
        ...createAppElementChangeViewParams(),
        ...element.params,
        queryMap,
      };
      flush(() => {
        assert.equal(element._activeTabs[0], PrimaryTab.FILES);
        done();
      });
    });

    test('switching tab sets _selectedTabPluginEndpoint', done => {
      const paperTabs = element.shadowRoot!.querySelector('#primaryTabs')!;
      tap(paperTabs.querySelectorAll('paper-tab')[2]);
      flush(() => {
        assert.equal(
          element._selectedTabPluginEndpoint,
          'change-view-tab-content-url'
        );
        done();
      });
    });
  });

  suite('keyboard shortcuts', () => {
    let clock: SinonFakeTimers;
    setup(() => {
      clock = sinon.useFakeTimers();
    });

    teardown(() => {
      clock.restore();
      sinon.restore();
    });

    test('t to add topic', () => {
      const editStub = sinon.stub(element.$.metadata, 'editTopic');
      pressAndReleaseKeyOn(element, 83, null, 't');
      assert(editStub.called);
    });

    test('S should toggle the CL star', () => {
      const starStub = sinon.stub(element.$.changeStar, 'toggleStar');
      pressAndReleaseKeyOn(element, 83, null, 's');
      assert(starStub.called);
    });

    test('toggle star is throttled', () => {
      const starStub = sinon.stub(element.$.changeStar, 'toggleStar');
      pressAndReleaseKeyOn(element, 83, null, 's');
      assert(starStub.called);
      pressAndReleaseKeyOn(element, 83, null, 's');
      assert.equal(starStub.callCount, 1);
      clock.tick(1000);
      pressAndReleaseKeyOn(element, 83, null, 's');
      assert.equal(starStub.callCount, 2);
    });

    test('U should navigate to root if no backPage set', () => {
      const relativeNavStub = sinon.stub(GerritNav, 'navigateToRelativeUrl');
      pressAndReleaseKeyOn(element, 85, null, 'u');
      assert.isTrue(relativeNavStub.called);
      assert.isTrue(
        relativeNavStub.lastCall.calledWithExactly(GerritNav.getUrlForRoot())
      );
    });

    test('U should navigate to backPage if set', () => {
      const relativeNavStub = sinon.stub(GerritNav, 'navigateToRelativeUrl');
      element.backPage = '/dashboard/self';
      pressAndReleaseKeyOn(element, 85, null, 'u');
      assert.isTrue(relativeNavStub.called);
      assert.isTrue(
        relativeNavStub.lastCall.calledWithExactly('/dashboard/self')
      );
    });

    test('A fires an error event when not logged in', done => {
      sinon.stub(element, '_getLoggedIn').returns(Promise.resolve(false));
      const loggedInErrorSpy = sinon.spy();
      element.addEventListener('show-auth-required', loggedInErrorSpy);
      pressAndReleaseKeyOn(element, 65, null, 'a');
      flush(() => {
        assert.isFalse(element.$.replyOverlay.opened);
        assert.isTrue(loggedInErrorSpy.called);
        done();
      });
    });

    test('shift A does not open reply overlay', done => {
      sinon.stub(element, '_getLoggedIn').returns(Promise.resolve(true));
      pressAndReleaseKeyOn(element, 65, 'shift', 'a');
      flush(() => {
        assert.isFalse(element.$.replyOverlay.opened);
        done();
      });
    });

    test('A toggles overlay when logged in', done => {
      sinon.stub(element, '_getLoggedIn').returns(Promise.resolve(true));
      element._change = {
        ...createChangeViewChange(),
        revisions: createRevisions(1),
        messages: createChangeMessages(1),
      };
      element._change.labels = {};
      stubRestApi('getChangeDetail').callsFake(() =>
        Promise.resolve({
          ...createChangeViewChange(),
          // element has latest info
          revisions: createRevisions(1),
          messages: createChangeMessages(1),
          current_revision: 'rev1' as CommitId,
        })
      );

      const openSpy = sinon.spy(element, '_openReplyDialog');

      pressAndReleaseKeyOn(element, 65, null, 'a');
      flush(() => {
        assert.isTrue(element.$.replyOverlay.opened);
        element.$.replyOverlay.close();
        assert.isFalse(element.$.replyOverlay.opened);
        assert(
          openSpy.lastCall.calledWithExactly(
            element.$.replyDialog.FocusTarget.ANY
          ),
          '_openReplyDialog should have been passed ANY'
        );
        assert.equal(openSpy.callCount, 1);
        done();
      });
    });

    test('fullscreen-overlay-opened hides content', () => {
      element._loggedIn = true;
      element._loading = false;
      element._change = {
        ...createChangeViewChange(),
        labels: {},
        actions: {
          abandon: {
            enabled: true,
            label: 'Abandon',
            method: HttpMethod.POST,
            title: 'Abandon',
          },
        },
      };
      const handlerSpy = sinon.spy(element, '_handleHideBackgroundContent');
      element.$.replyDialog.dispatchEvent(
        new CustomEvent('fullscreen-overlay-opened', {
          composed: true,
          bubbles: true,
        })
      );
      assert.isTrue(handlerSpy.called);
      assert.isTrue(element.$.mainContent.classList.contains('overlayOpen'));
      assert.equal(getComputedStyle(element.$.actions).display, 'flex');
    });

    test('fullscreen-overlay-closed shows content', () => {
      element._loggedIn = true;
      element._loading = false;
      element._change = {
        ...createChangeViewChange(),
        labels: {},
        actions: {
          abandon: {
            enabled: true,
            label: 'Abandon',
            method: HttpMethod.POST,
            title: 'Abandon',
          },
        },
      };
      const handlerSpy = sinon.spy(element, '_handleShowBackgroundContent');
      element.$.replyDialog.dispatchEvent(
        new CustomEvent('fullscreen-overlay-closed', {
          composed: true,
          bubbles: true,
        })
      );
      assert.isTrue(handlerSpy.called);
      assert.isFalse(element.$.mainContent.classList.contains('overlayOpen'));
    });

    test('expand all messages when expand-diffs fired', () => {
      const handleExpand = sinon.stub(element.$.fileList, 'expandAllDiffs');
      element.$.fileListHeader.dispatchEvent(
        new CustomEvent('expand-diffs', {
          composed: true,
          bubbles: true,
        })
      );
      assert.isTrue(handleExpand.called);
    });

    test('collapse all messages when collapse-diffs fired', () => {
      const handleCollapse = sinon.stub(element.$.fileList, 'collapseAllDiffs');
      element.$.fileListHeader.dispatchEvent(
        new CustomEvent('collapse-diffs', {
          composed: true,
          bubbles: true,
        })
      );
      assert.isTrue(handleCollapse.called);
    });

    test('X should expand all messages', done => {
      flush(() => {
        const handleExpand = sinon.stub(
          element.messagesList!,
          'handleExpandCollapse'
        );
        pressAndReleaseKeyOn(element, 88, null, 'x');
        assert(handleExpand.calledWith(true));
        done();
      });
    });

    test('Z should collapse all messages', done => {
      flush(() => {
        const handleExpand = sinon.stub(
          element.messagesList!,
          'handleExpandCollapse'
        );
        pressAndReleaseKeyOn(element, 90, null, 'z');
        assert(handleExpand.calledWith(false));
        done();
      });
    });

    test('d should open download overlay', () => {
      const stub = sinon
        .stub(element.$.downloadOverlay, 'open')
        .returns(Promise.resolve());
      pressAndReleaseKeyOn(element, 68, null, 'd');
      assert.isTrue(stub.called);
    });

    test(', should open diff preferences', () => {
      const stub = sinon.stub(
        element.$.fileList.$.diffPreferencesDialog,
        'open'
      );
      element._loggedIn = false;
      element.disableDiffPrefs = true;
      pressAndReleaseKeyOn(element, 188, null, ',');
      assert.isFalse(stub.called);

      element._loggedIn = true;
      pressAndReleaseKeyOn(element, 188, null, ',');
      assert.isFalse(stub.called);

      element.disableDiffPrefs = false;
      pressAndReleaseKeyOn(element, 188, null, ',');
      assert.isTrue(stub.called);
    });

    test('m should toggle diff mode', () => {
      sinon.stub(element, 'shouldSuppressKeyboardShortcut').returns(false);
      const setModeStub = sinon.stub(
        element.$.fileListHeader,
        'setDiffViewMode'
      );
      const e = {preventDefault: () => {}} as CustomKeyboardEvent;
      flush();

      element.viewState.diffMode = DiffViewMode.SIDE_BY_SIDE;
      element._handleToggleDiffMode(e);
      assert.isTrue(setModeStub.calledWith(DiffViewMode.UNIFIED));

      element.viewState.diffMode = DiffViewMode.UNIFIED;
      element._handleToggleDiffMode(e);
      assert.isTrue(setModeStub.calledWith(DiffViewMode.SIDE_BY_SIDE));
    });
  });

  suite('reloading drafts', () => {
    let reloadStub: SinonStubbedMember<
      typeof element.$.commentAPI.reloadDrafts
    >;
    const drafts: {[path: string]: UIDraft[]} = {
      'testfile.txt': [
        {
          patch_set: 5 as PatchSetNum,
          id: 'dd2982f5_c01c9e6a' as UrlEncodedCommentId,
          line: 1,
          updated: '2017-11-08 18:47:45.000000000' as Timestamp,
          message: 'test',
          unresolved: true,
        },
      ],
    };
    setup(() => {
      // Fake computeDraftCount as its required for ChangeComments,
      // see gr-comment-api#reloadDrafts.
      reloadStub = sinon.stub(element.$.commentAPI, 'reloadDrafts').returns(
        Promise.resolve({
          drafts,
          getAllThreadsForChange: () => [] as CommentThread[],
          computeDraftCount: () => 1,
        } as ChangeComments)
      );
      element._changeNum = 1 as NumericChangeId;
    });

    test('drafts are reloaded when reload-drafts fired', done => {
      element.$.fileList.dispatchEvent(
        new CustomEvent('reload-drafts', {
          detail: {
            resolve: () => {
              assert.isTrue(reloadStub.called);
              assert.deepEqual(element._diffDrafts, drafts);
              done();
            },
          },
          composed: true,
          bubbles: true,
        })
      );
    });

    test('drafts are reloaded when comment-refresh fired', () => {
      element.dispatchEvent(
        new CustomEvent('comment-refresh', {
          composed: true,
          bubbles: true,
        })
      );
      assert.isTrue(reloadStub.called);
    });
  });

  suite('_recomputeComments', () => {
    setup(() => {
      element._changeNum = TEST_NUMERIC_CHANGE_ID;
      element._change = createChangeViewChange();
      flush();
      // Fake computeDraftCount as its required for ChangeComments,
      // see gr-comment-api#reloadDrafts.
      sinon.stub(element.$.commentAPI, 'reloadDrafts').returns(
        Promise.resolve({
          drafts: {},
          getAllThreadsForChange: () => THREADS,
          computeDraftCount: () => 0,
        } as ChangeComments)
      );
      element._change = createChangeViewChange();
      element._changeNum = element._change._number;
    });

    test('draft threads should be a new copy with correct states', done => {
      element.$.fileList.dispatchEvent(
        new CustomEvent('reload-drafts', {
          detail: {
            resolve: () => {
              assert.equal(element._draftCommentThreads!.length, 2);
              assert.equal(
                element._draftCommentThreads![0].rootId,
                THREADS[0].rootId
              );
              assert.notEqual(
                element._draftCommentThreads![0].comments,
                THREADS[0].comments
              );
              assert.notEqual(
                element._draftCommentThreads![0].comments[0],
                THREADS[0].comments[0]
              );
              assert.isTrue(
                element
                  ._draftCommentThreads![0].comments.slice(0, 2)
                  .every(c => c.collapsed === true)
              );

              assert.isTrue(
                element._draftCommentThreads![0].comments[2].collapsed === false
              );
              done();
            },
          },
          composed: true,
          bubbles: true,
        })
      );
    });
  });

  test('diff comments modified', () => {
    const reloadThreadsSpy = sinon.spy(element, '_handleReloadCommentThreads');
    return element._reloadComments().then(() => {
      element.dispatchEvent(
        new CustomEvent('diff-comments-modified', {
          composed: true,
          bubbles: true,
        })
      );
      assert.isTrue(reloadThreadsSpy.called);
    });
  });

  test('thread list modified', () => {
    const reloadDiffSpy = sinon.spy(element, '_handleReloadDiffComments');
    element._activeTabs = [PrimaryTab.COMMENT_THREADS, SecondaryTab.CHANGE_LOG];
    flush();

    return element._reloadComments().then(() => {
      element.threadList!.dispatchEvent(
        new CustomEvent('thread-list-modified', {
          composed: true,
          bubbles: true,
        })
      );
      assert.isTrue(reloadDiffSpy.called);

      let draftStub = sinon
        .stub(element._changeComments!, 'computeDraftCount')
        .returns(1);
      assert.equal(
        element._computeTotalCommentCounts(5, element._changeComments!),
        '5 unresolved, 1 draft'
      );
      assert.equal(
        element._computeTotalCommentCounts(0, element._changeComments!),
        '1 draft'
      );
      draftStub.restore();
      draftStub = sinon
        .stub(element._changeComments!, 'computeDraftCount')
        .returns(0);
      assert.equal(
        element._computeTotalCommentCounts(0, element._changeComments!),
        ''
      );
      assert.equal(
        element._computeTotalCommentCounts(1, element._changeComments!),
        '1 unresolved'
      );
      draftStub.restore();
      draftStub = sinon
        .stub(element._changeComments!, 'computeDraftCount')
        .returns(2);
      assert.equal(
        element._computeTotalCommentCounts(1, element._changeComments!),
        '1 unresolved, 2 drafts'
      );
      draftStub.restore();
    });
  });

  suite('thread list and change log tabs', () => {
    setup(() => {
      element._changeNum = TEST_NUMERIC_CHANGE_ID;
      element._patchRange = {
        basePatchNum: ParentPatchSetNum,
        patchNum: 1 as RevisionPatchSetNum,
      };
      element._change = {
        ...createChangeViewChange(),
        revisions: {
          rev2: createRevision(2),
          rev1: createRevision(1),
          rev13: createRevision(13),
          rev3: createRevision(3),
        },
        current_revision: 'rev3' as CommitId,
        status: ChangeStatus.NEW,
        labels: {
          test: {
            all: [],
            default_value: 0,
            values: {},
            approved: {},
          },
        },
      };
      const relatedChanges = element.shadowRoot!.querySelector(
        '#relatedChanges'
      ) as GrRelatedChangesList;
      sinon.stub(relatedChanges, 'reload');
      sinon.stub(element, 'loadData').returns(Promise.resolve([]));
      sinon.spy(element, '_paramsChanged');
      element.params = createAppElementChangeViewParams();
    });
  });

  suite('Findings comment tab', () => {
    setup(done => {
      element._changeNum = TEST_NUMERIC_CHANGE_ID;
      element._change = {
        ...createChangeViewChange(),
        revisions: {
          rev2: createRevision(2),
          rev1: createRevision(1),
          rev13: createRevision(13),
          rev3: createRevision(3),
          rev4: createRevision(4),
        },
        current_revision: 'rev4' as CommitId,
      };
      element._commentThreads = THREADS;
      const paperTabs = element.shadowRoot!.querySelector('#primaryTabs')!;
      tap(paperTabs.querySelectorAll('paper-tab')[3]);
      flush(() => {
        done();
      });
    });

    test('robot comments count per patchset', () => {
      const count = element._robotCommentCountPerPatchSet(THREADS);
      const expectedCount = {
        2: 1,
        3: 1,
        4: 2,
      };
      assert.deepEqual(count, expectedCount);
      assert.equal(
        element._computeText(createRevision(2), THREADS),
        'Patchset 2 (1 finding)'
      );
      assert.equal(
        element._computeText(createRevision(4), THREADS),
        'Patchset 4 (2 findings)'
      );
      assert.equal(
        element._computeText(createRevision(5), THREADS),
        'Patchset 5'
      );
    });

    test('only robot comments are rendered', () => {
      assert.equal(element._robotCommentThreads!.length, 2);
      assert.equal(
        (element._robotCommentThreads![0].comments[0] as UIRobot).robot_id,
        'rc1'
      );
      assert.equal(
        (element._robotCommentThreads![1].comments[0] as UIRobot).robot_id,
        'rc2'
      );
    });

    test('changing patchsets resets robot comments', done => {
      element.set('_change.current_revision', 'rev3');
      flush(() => {
        assert.equal(element._robotCommentThreads!.length, 1);
        done();
      });
    });

    test('Show more button is hidden', () => {
      assert.isNull(element.shadowRoot!.querySelector('.show-robot-comments'));
    });

    suite('robot comments show more button', () => {
      setup(done => {
        const arr = [];
        for (let i = 0; i <= 30; i++) {
          arr.push(...THREADS);
        }
        element._commentThreads = arr;
        flush(() => {
          done();
        });
      });

      test('Show more button is rendered', () => {
        assert.isOk(element.shadowRoot!.querySelector('.show-robot-comments'));
        assert.equal(
          element._robotCommentThreads!.length,
          ROBOT_COMMENTS_LIMIT
        );
      });

      test('Clicking show more button renders all comments', done => {
        tap(element.shadowRoot!.querySelector('.show-robot-comments')!);
        flush(() => {
          assert.equal(element._robotCommentThreads!.length, 62);
          done();
        });
      });
    });
  });

  test('reply button is not visible when logged out', () => {
    assert.equal(getComputedStyle(element.$.replyBtn).display, 'none');
    element._loggedIn = true;
    assert.notEqual(getComputedStyle(element.$.replyBtn).display, 'none');
  });

  test('download tap calls _handleOpenDownloadDialog', () => {
    const openDialogStub = sinon.stub(element, '_handleOpenDownloadDialog');
    element.$.actions.dispatchEvent(
      new CustomEvent('download-tap', {
        composed: true,
        bubbles: true,
      })
    );
    assert.isTrue(openDialogStub.called);
  });

  test('fetches the server config on attached', done => {
    flush(() => {
      assert.equal(
        element._serverConfig!.user.anonymous_coward_name,
        'test coward name'
      );
      done();
    });
  });

  test('_changeStatuses', () => {
    element._loading = false;
    element._change = {
      ...createChangeViewChange(),
      revisions: {
        rev2: createRevision(2),
        rev1: createRevision(1),
        rev13: createRevision(13),
        rev3: createRevision(3),
      },
      current_revision: 'rev3' as CommitId,
      status: ChangeStatus.MERGED,
      work_in_progress: true,
      labels: {
        test: {
          all: [],
          default_value: 0,
          values: {},
          approved: {},
        },
      },
    };
    element._mergeable = true;
    const expectedStatuses = [ChangeStates.MERGED, ChangeStates.WIP];
    assert.deepEqual(element._changeStatuses, expectedStatuses);
    flush();
    const statusChips = element.shadowRoot!.querySelectorAll(
      'gr-change-status'
    );
    assert.equal(statusChips.length, 2);
  });

  suite('ChangeStatus revert', () => {
    test('do not show any chip if no revert created', done => {
      const change = {
        ...createChange(),
        messages: createChangeMessages(2),
      };
      const getChangeStub = stubRestApi('getChange');
      getChangeStub.onFirstCall().returns(
        Promise.resolve({
          ...createChange(),
        })
      );
      getChangeStub.onSecondCall().returns(
        Promise.resolve({
          ...createChange(),
        })
      );
      element._change = change;
      element._mergeable = true;
      element._submitEnabled = true;
      flush();
      element.computeRevertSubmitted(element._change);
      flush(() => {
        assert.isFalse(
          element._changeStatuses?.includes(ChangeStates.REVERT_SUBMITTED)
        );
        assert.isFalse(
          element._changeStatuses?.includes(ChangeStates.REVERT_CREATED)
        );
        done();
      });
    });

    test('do not show any chip if all reverts are abandoned', done => {
      const change = {
        ...createChange(),
        messages: createChangeMessages(2),
      };
      change.messages[0].message = 'Created a revert of this change as 12345';
      change.messages[0].tag = MessageTag.TAG_REVERT as ReviewInputTag;

      change.messages[1].message = 'Created a revert of this change as 23456';
      change.messages[1].tag = MessageTag.TAG_REVERT as ReviewInputTag;

      const getChangeStub = stubRestApi('getChange');
      getChangeStub.onFirstCall().returns(
        Promise.resolve({
          ...createChange(),
          status: ChangeStatus.ABANDONED,
        })
      );
      getChangeStub.onSecondCall().returns(
        Promise.resolve({
          ...createChange(),
          status: ChangeStatus.ABANDONED,
        })
      );
      element._change = change;
      element._mergeable = true;
      element._submitEnabled = true;
      flush();
      element.computeRevertSubmitted(element._change);
      flush(() => {
        assert.isFalse(
          element._changeStatuses?.includes(ChangeStates.REVERT_SUBMITTED)
        );
        assert.isFalse(
          element._changeStatuses?.includes(ChangeStates.REVERT_CREATED)
        );
        done();
      });
    });

    test('show revert created if no revert is merged', done => {
      const change = {
        ...createChange(),
        messages: createChangeMessages(2),
      };
      change.messages[0].message = 'Created a revert of this change as 12345';
      change.messages[0].tag = MessageTag.TAG_REVERT as ReviewInputTag;

      change.messages[1].message = 'Created a revert of this change as 23456';
      change.messages[1].tag = MessageTag.TAG_REVERT as ReviewInputTag;

      const getChangeStub = stubRestApi('getChange');
      getChangeStub.onFirstCall().returns(
        Promise.resolve({
          ...createChange(),
        })
      );
      getChangeStub.onSecondCall().returns(
        Promise.resolve({
          ...createChange(),
        })
      );
      element._change = change;
      element._mergeable = true;
      element._submitEnabled = true;
      flush();
      element.computeRevertSubmitted(element._change);
      flush(() => {
        assert.isFalse(
          element._changeStatuses?.includes(ChangeStates.REVERT_SUBMITTED)
        );
        assert.isTrue(
          element._changeStatuses?.includes(ChangeStates.REVERT_CREATED)
        );
        done();
      });
    });

    test('show revert submitted if revert is merged', done => {
      const change = {
        ...createChange(),
        messages: createChangeMessages(2),
      };
      change.messages[0].message = 'Created a revert of this change as 12345';
      change.messages[0].tag = MessageTag.TAG_REVERT as ReviewInputTag;
      const getChangeStub = stubRestApi('getChange');
      getChangeStub.onFirstCall().returns(
        Promise.resolve({
          ...createChange(),
          status: ChangeStatus.MERGED,
        })
      );
      getChangeStub.onSecondCall().returns(
        Promise.resolve({
          ...createChange(),
        })
      );
      element._change = change;
      element._mergeable = true;
      element._submitEnabled = true;
      flush();
      element.computeRevertSubmitted(element._change);
      flush(() => {
        assert.isFalse(
          element._changeStatuses?.includes(ChangeStates.REVERT_CREATED)
        );
        assert.isTrue(
          element._changeStatuses?.includes(ChangeStates.REVERT_SUBMITTED)
        );
        done();
      });
    });
  });

  test('diff preferences open when open-diff-prefs is fired', () => {
    const overlayOpenStub = sinon.stub(element.$.fileList, 'openDiffPrefs');
    element.$.fileListHeader.dispatchEvent(
      new CustomEvent('open-diff-prefs', {
        composed: true,
        bubbles: true,
      })
    );
    assert.isTrue(overlayOpenStub.called);
  });

  test('_prepareCommitMsgForLinkify', () => {
    let commitMessage = 'R=test@google.com';
    let result = element._prepareCommitMsgForLinkify(commitMessage);
    assert.equal(result, 'R=\u200Btest@google.com');

    commitMessage = 'R=test@google.com\nR=test@google.com';
    result = element._prepareCommitMsgForLinkify(commitMessage);
    assert.equal(result, 'R=\u200Btest@google.com\nR=\u200Btest@google.com');

    commitMessage = 'CC=test@google.com';
    result = element._prepareCommitMsgForLinkify(commitMessage);
    assert.equal(result, 'CC=\u200Btest@google.com');
  });

  test('_isSubmitEnabled', () => {
    assert.isFalse(element._isSubmitEnabled({}));
    assert.isFalse(element._isSubmitEnabled({submit: {}}));
    assert.isTrue(element._isSubmitEnabled({submit: {enabled: true}}));
  });

  test('_reload is called when an approved label is removed', () => {
    const vote: ApprovalInfo = {
      ...createApproval(),
      _account_id: 1 as AccountId,
      name: 'bojack',
      value: 1,
    };
    element._changeNum = TEST_NUMERIC_CHANGE_ID;
    element._patchRange = {
      basePatchNum: ParentPatchSetNum,
      patchNum: 1 as RevisionPatchSetNum,
    };
    const change = {
      ...createChangeViewChange(),
      owner: createAccountWithIdNameAndEmail(),
      revisions: {
        rev2: createRevision(2),
        rev1: createRevision(1),
        rev13: createRevision(13),
        rev3: createRevision(3),
      },
      current_revision: 'rev3' as CommitId,
      status: ChangeStatus.NEW,
      labels: {
        test: {
          all: [vote],
          default_value: 0,
          values: {},
          approved: {},
        },
      },
    };
    element._change = change;
    flush();
    const reloadStub = sinon.stub(element, 'loadData');
    element.splice('_change.labels.test.all', 0, 1);
    assert.isFalse(reloadStub.called);
    change.labels.test.all.push(vote);
    change.labels.test.all.push(vote);
    change.labels.test.approved = vote;
    flush();
    element.splice('_change.labels.test.all', 0, 2);
    assert.isTrue(reloadStub.called);
    assert.isTrue(reloadStub.calledOnce);
  });

  test('reply button has updated count when there are drafts', () => {
    const getLabel = element._computeReplyButtonLabel;

    assert.equal(getLabel(null, false), 'Reply');
    assert.equal(getLabel(null, true), 'Start Review');

    const changeRecord: ElementPropertyDeepChange<
      GrChangeView,
      '_diffDrafts'
    > = {base: undefined, path: '', value: undefined};
    assert.equal(getLabel(changeRecord, false), 'Reply');

    changeRecord.base = {};
    assert.equal(getLabel(changeRecord, false), 'Reply');

    changeRecord.base = {
      'file1.txt': [{}],
      'file2.txt': [{}, {}],
    };
    assert.equal(getLabel(changeRecord, false), 'Reply (3)');
    assert.equal(getLabel(changeRecord, true), 'Start Review (3)');
  });

  test('comment events properly update diff drafts', () => {
    element._patchRange = {
      basePatchNum: ParentPatchSetNum,
      patchNum: 2 as RevisionPatchSetNum,
    };
    const draft: DraftInfo = {
      __draft: true,
      id: 'id1' as UrlEncodedCommentId,
      path: '/foo/bar.txt',
      message: 'hello',
    };
    element._handleCommentSave(new CustomEvent('', {detail: {comment: draft}}));
    draft.patch_set = 2 as PatchSetNum;
    assert.deepEqual(element._diffDrafts, {'/foo/bar.txt': [draft]});
    draft.patch_set = undefined;
    draft.message = 'hello, there';
    element._handleCommentSave(new CustomEvent('', {detail: {comment: draft}}));
    draft.patch_set = 2 as PatchSetNum;
    assert.deepEqual(element._diffDrafts, {'/foo/bar.txt': [draft]});
    const draft2: DraftInfo = {
      __draft: true,
      id: 'id2' as UrlEncodedCommentId,
      path: '/foo/bar.txt',
      message: 'hola',
    };
    element._handleCommentSave(
      new CustomEvent('', {detail: {comment: draft2}})
    );
    draft2.patch_set = 2 as PatchSetNum;
    assert.deepEqual(element._diffDrafts, {'/foo/bar.txt': [draft, draft2]});
    draft.patch_set = undefined;
    element._handleCommentDiscard(
      new CustomEvent('', {detail: {comment: draft}})
    );
    draft.patch_set = 2 as PatchSetNum;
    assert.deepEqual(element._diffDrafts, {'/foo/bar.txt': [draft2]});
    element._handleCommentDiscard(
      new CustomEvent('', {detail: {comment: draft2}})
    );
    assert.deepEqual(element._diffDrafts, {});
  });

  test('change num change', () => {
    const change = {
      ...createChangeViewChange(),
      labels: {},
    } as ParsedChangeInfo;
    stubRestApi('getChangeDetail').returns(Promise.resolve(change));
    element._changeNum = undefined;
    element._patchRange = {
      basePatchNum: ParentPatchSetNum,
      patchNum: 2 as RevisionPatchSetNum,
    };
    element._change = change;
    element.viewState.changeNum = null;
    element.viewState.diffMode = DiffViewMode.UNIFIED;
    assert.equal(element.viewState.numFilesShown, 200);
    assert.equal(element._numFilesShown, 200);
    element._numFilesShown = 150;
    flush();
    assert.equal(element.viewState.diffMode, DiffViewMode.UNIFIED);
    assert.equal(element.viewState.numFilesShown, 150);

    element._changeNum = 1 as NumericChangeId;
    element.params = {
      ...createAppElementChangeViewParams(),
      changeNum: 1 as NumericChangeId,
    };
    flush();
    assert.equal(element.viewState.diffMode, DiffViewMode.UNIFIED);
    assert.equal(element.viewState.changeNum, 1);

    element._changeNum = 2 as NumericChangeId;
    element.params = {
      ...createAppElementChangeViewParams(),
      changeNum: 2 as NumericChangeId,
    };
    flush();
    assert.equal(element.viewState.diffMode, DiffViewMode.UNIFIED);
    assert.equal(element.viewState.changeNum, 2);
    assert.equal(element.viewState.numFilesShown, 200);
    assert.equal(element._numFilesShown, 200);
  });

  test('_setDiffViewMode is called with reset when new change is loaded', () => {
    const setDiffViewModeStub = sinon.stub(element, '_setDiffViewMode');
    element.viewState = {changeNum: 1 as NumericChangeId};
    element._changeNum = 2 as NumericChangeId;
    element._resetFileListViewState();
    assert.isTrue(setDiffViewModeStub.calledWithExactly(true));
  });

  test('diffViewMode is propagated from file list header', () => {
    element.viewState = {diffMode: DiffViewMode.UNIFIED};
    element.$.fileListHeader.diffViewMode = DiffViewMode.SIDE_BY_SIDE;
    assert.equal(element.viewState.diffMode, DiffViewMode.SIDE_BY_SIDE);
  });

  test('diffMode defaults to side by side without preferences', done => {
    stubRestApi('getPreferences').returns(Promise.resolve(createPreferences()));
    // No user prefs or diff view mode set.

    element._setDiffViewMode()!.then(() => {
      assert.equal(element.viewState.diffMode, DiffViewMode.SIDE_BY_SIDE);
      done();
    });
  });

  test('diffMode defaults to preference when not already set', done => {
    stubRestApi('getPreferences').returns(
      Promise.resolve({
        ...createPreferences(),
        default_diff_view: DiffViewMode.UNIFIED,
      })
    );

    element._setDiffViewMode()!.then(() => {
      assert.equal(element.viewState.diffMode, DiffViewMode.UNIFIED);
      done();
    });
  });

  test('existing diffMode overrides preference', done => {
    element.viewState.diffMode = DiffViewMode.SIDE_BY_SIDE;
    stubRestApi('getPreferences').returns(
      Promise.resolve({
        ...createPreferences(),
        default_diff_view: DiffViewMode.UNIFIED,
      })
    );
    element._setDiffViewMode()!.then(() => {
      assert.equal(element.viewState.diffMode, DiffViewMode.SIDE_BY_SIDE);
      done();
    });
  });

  test('don’t reload entire page when patchRange changes', async () => {
    const reloadStub = sinon
      .stub(element, 'loadData')
      .callsFake(() => Promise.resolve([]));
    const reloadPatchDependentStub = sinon
      .stub(element, '_reloadPatchNumDependentResources')
      .callsFake(() => Promise.resolve([undefined, undefined, undefined]));
    flush();
    const collapseStub = sinon.stub(element.$.fileList, 'collapseAllDiffs');

    const value: AppElementChangeViewParams = {
      ...createAppElementChangeViewParams(),
      view: GerritView.CHANGE,
      patchNum: 1 as RevisionPatchSetNum,
    };
    element.params = value;
    await flush();
    assert.isTrue(reloadStub.calledOnce);

    element._initialLoadComplete = true;
    element._change = {
      ...createChangeViewChange(),
      revisions: {
        rev1: createRevision(1),
        rev2: createRevision(2),
      },
    };

    value.basePatchNum = 1 as BasePatchSetNum;
    value.patchNum = 2 as RevisionPatchSetNum;
    element.params = {...value};
    await flush();
    assert.isFalse(reloadStub.calledTwice);
    assert.isTrue(reloadPatchDependentStub.calledOnce);
    assert.isTrue(collapseStub.calledTwice);
  });

  test('reload ported comments when patchNum changes', async () => {
    sinon.stub(element, 'loadData').callsFake(() => Promise.resolve([]));
    sinon.stub(element, '_getCommitInfo');
    sinon.stub(element.$.fileList, 'reload');
    flush();
    const reloadPortedCommentsStub = sinon.stub(
      element.$.commentAPI,
      'reloadPortedComments'
    );
    sinon.stub(element.$.fileList, 'collapseAllDiffs');

    const value: AppElementChangeViewParams = {
      ...createAppElementChangeViewParams(),
      view: GerritView.CHANGE,
      patchNum: 1 as RevisionPatchSetNum,
    };
    element.params = value;
    await flush();

    element._initialLoadComplete = true;
    element._change = {
      ...createChangeViewChange(),
      revisions: {
        rev1: createRevision(1),
        rev2: createRevision(2),
      },
    };

    value.basePatchNum = 1 as BasePatchSetNum;
    value.patchNum = 2 as RevisionPatchSetNum;
    element.params = {...value};
    await flush();
    assert.isTrue(reloadPortedCommentsStub.calledOnce);
  });

  test('reload entire page when patchRange doesnt change', async () => {
    const reloadStub = sinon
      .stub(element, 'loadData')
      .callsFake(() => Promise.resolve([]));
    const collapseStub = sinon.stub(element.$.fileList, 'collapseAllDiffs');
    const value: AppElementChangeViewParams = createAppElementChangeViewParams();
    element.params = value;
    await flush();
    assert.isTrue(reloadStub.calledOnce);
    element._initialLoadComplete = true;
    element.params = {...value};
    await flush();
    assert.isTrue(reloadStub.calledTwice);
    assert.isTrue(collapseStub.calledTwice);
  });

  test('do not handle new change numbers', async () => {
    const recreateSpy = sinon.spy();
    element.addEventListener('recreate-change-view', recreateSpy);

    const value: AppElementChangeViewParams = createAppElementChangeViewParams();
    element.params = value;
    await flush();
    assert.isFalse(recreateSpy.calledOnce);

    value.changeNum = 555111333 as NumericChangeId;
    element.params = {...value};
    await flush();
    assert.isTrue(recreateSpy.calledOnce);
  });

  test('related changes are not updated after other action', done => {
    sinon.stub(element, 'loadData').callsFake(() => Promise.resolve([]));
    flush();
    const relatedChanges = element.shadowRoot!.querySelector(
      '#relatedChanges'
    ) as GrRelatedChangesList;
    sinon.stub(relatedChanges, 'reload');
    element.loadData(true).then(() => {
      assert.isFalse(navigateToChangeStub.called);
      done();
    });
  });

  test('_computeCopyTextForTitle', () => {
    const change: ChangeInfo = {
      ...createChangeViewChange(),
      _number: 123 as NumericChangeId,
      subject: 'test subject',
      revisions: {
        rev1: createRevision(1),
        rev3: createRevision(3),
      },
      current_revision: 'rev3' as CommitId,
    };
    sinon.stub(GerritNav, 'getUrlForChange').returns('/change/123');
    assert.equal(
      element._computeCopyTextForTitle(change),
      `123: test subject | http://${location.host}/change/123`
    );
  });

  test('get latest revision', () => {
    let change: ChangeInfo = {
      ...createChange(),
      revisions: {
        rev1: createRevision(1),
        rev3: createRevision(3),
      },
      current_revision: 'rev3' as CommitId,
    };
    assert.equal(element._getLatestRevisionSHA(change), 'rev3');
    change = {
      ...createChange(),
      revisions: {
        rev1: createRevision(1),
      },
      current_revision: undefined,
    };
    assert.equal(element._getLatestRevisionSHA(change), 'rev1');
  });

  test('show commit message edit button', () => {
    const change = createChange();
    const mergedChanged: ChangeInfo = {
      ...createChangeViewChange(),
      status: ChangeStatus.MERGED,
    };
    assert.isTrue(element._computeHideEditCommitMessage(false, false, change));
    assert.isTrue(element._computeHideEditCommitMessage(true, true, change));
    assert.isTrue(element._computeHideEditCommitMessage(false, true, change));
    assert.isFalse(element._computeHideEditCommitMessage(true, false, change));
    assert.isTrue(
      element._computeHideEditCommitMessage(true, false, mergedChanged)
    );
    assert.isTrue(
      element._computeHideEditCommitMessage(true, false, change, true)
    );
    assert.isFalse(
      element._computeHideEditCommitMessage(true, false, change, false)
    );
  });

  test('_handleCommitMessageSave trims trailing whitespace', () => {
    element._change = createChangeViewChange();
    // Response code is 500, because we want to avoid window reloading
    const putStub = stubRestApi('putChangeCommitMessage').returns(
      Promise.resolve(new Response(null, {status: 500}))
    );

    const mockEvent = (content: string) =>
      new CustomEvent('', {detail: {content}});

    element._handleCommitMessageSave(mockEvent('test \n  test '));
    assert.equal(putStub.lastCall.args[1], 'test\n  test');

    element._handleCommitMessageSave(mockEvent('  test\ntest'));
    assert.equal(putStub.lastCall.args[1], '  test\ntest');

    element._handleCommitMessageSave(mockEvent('\n\n\n\n\n\n\n\n'));
    assert.equal(putStub.lastCall.args[1], '\n\n\n\n\n\n\n\n');
  });

  test('topic is coalesced to null', done => {
    sinon.stub(element, '_changeChanged');
    stubRestApi('getChangeDetail').returns(
      Promise.resolve({
        ...createChangeViewChange(),
        labels: {},
        current_revision: 'foo' as CommitId,
        revisions: {foo: createRevision()},
      })
    );

    element._getChangeDetail().then(() => {
      assert.isNull(element._change!.topic);
      done();
    });
  });

  test('commit sha is populated from getChangeDetail', done => {
    sinon.stub(element, '_changeChanged');
    stubRestApi('getChangeDetail').callsFake(() =>
      Promise.resolve({
        ...createChangeViewChange(),
        labels: {},
        current_revision: 'foo' as CommitId,
        revisions: {foo: createRevision()},
      })
    );

    element._getChangeDetail().then(() => {
      assert.equal('foo', element._commitInfo!.commit);
      done();
    });
  });

  test('edit is added to change', () => {
    sinon.stub(element, '_changeChanged');
    const changeRevision = createRevision();
    stubRestApi('getChangeDetail').callsFake(() =>
      Promise.resolve({
        ...createChangeViewChange(),
        labels: {},
        current_revision: 'foo' as CommitId,
        revisions: {foo: {...changeRevision}},
      })
    );
    const editCommit: CommitInfo = {
      ...createCommit(),
      commit: 'bar' as CommitId,
    };
    sinon.stub(element, '_getEdit').callsFake(() =>
      Promise.resolve({
        base_patch_set_number: 1 as BasePatchSetNum,
        commit: {...editCommit},
        base_revision: 'abc',
        ref: 'some/ref' as GitRef,
      })
    );
    element._patchRange = {};

    return element._getChangeDetail().then(() => {
      const revs = element._change!.revisions!;
      assert.equal(Object.keys(revs).length, 2);
      assert.deepEqual(revs['foo'], changeRevision);
      assert.deepEqual(revs['bar'], {
        ...createEditRevision(),
        commit: editCommit,
        fetch: undefined,
      });
    });
  });

  test('_getBasePatchNum', () => {
    const _change: ChangeInfo = {
      ...createChangeViewChange(),
      revisions: {
        '98da160735fb81604b4c40e93c368f380539dd0e': createRevision(),
      },
    };
    const _patchRange: ChangeViewPatchRange = {
      basePatchNum: ParentPatchSetNum,
    };
    assert.equal(element._getBasePatchNum(_change, _patchRange), 'PARENT');

    element._prefs = {
      ...createPreferences(),
      default_base_for_merges: DefaultBase.FIRST_PARENT,
    };

    const _change2: ChangeInfo = {
      ...createChangeViewChange(),
      revisions: {
        '98da160735fb81604b4c40e93c368f380539dd0e': {
          ...createRevision(1),
          commit: {
            ...createCommit(),
            parents: [
              {
                commit: '6e12bdf1176eb4ab24d8491ba3b6d0704409cde8' as CommitId,
                subject: 'test',
              },
              {
                commit: '22f7db4754b5d9816fc581f3d9a6c0ef8429c841' as CommitId,
                subject: 'test3',
              },
            ],
          },
        },
      },
    };
    assert.equal(element._getBasePatchNum(_change2, _patchRange), -1);

    _patchRange.patchNum = 1 as RevisionPatchSetNum;
    assert.equal(element._getBasePatchNum(_change2, _patchRange), 'PARENT');
  });

  test('_openReplyDialog called with `ANY` when coming from tap event', done => {
    flush(() => {
      const openStub = sinon.stub(element, '_openReplyDialog');
      tap(element.$.replyBtn);
      assert(
        openStub.lastCall.calledWithExactly(
          element.$.replyDialog.FocusTarget.ANY
        ),
        '_openReplyDialog should have been passed ANY'
      );
      assert.equal(openStub.callCount, 1);
      done();
    });
  });

  test(
    '_openReplyDialog called with `BODY` when coming from message reply' +
      'event',
    done => {
      flush(() => {
        const openStub = sinon.stub(element, '_openReplyDialog');
        element.messagesList!.dispatchEvent(
          new CustomEvent('reply', {
            detail: {message: {message: 'text'}},
            composed: true,
            bubbles: true,
          })
        );
        assert(
          openStub.lastCall.calledWithExactly(
            element.$.replyDialog.FocusTarget.BODY
          ),
          '_openReplyDialog should have been passed BODY'
        );
        assert.equal(openStub.callCount, 1);
        done();
      });
    }
  );

  test('reply dialog focus can be controlled', () => {
    const FocusTarget = element.$.replyDialog.FocusTarget;
    const openStub = sinon.stub(element, '_openReplyDialog');

    const e = new CustomEvent('show-reply-dialog', {
      detail: {value: {ccsOnly: false}},
    });
    element._handleShowReplyDialog(e);
    assert(
      openStub.lastCall.calledWithExactly(FocusTarget.REVIEWERS),
      '_openReplyDialog should have been passed REVIEWERS'
    );
    assert.equal(openStub.callCount, 1);

    e.detail.value = {ccsOnly: true};
    element._handleShowReplyDialog(e);
    assert(
      openStub.lastCall.calledWithExactly(FocusTarget.CCS),
      '_openReplyDialog should have been passed CCS'
    );
    assert.equal(openStub.callCount, 2);
  });

  test('getUrlParameter functionality', () => {
    const locationStub = sinon.stub(element, '_getLocationSearch');

    locationStub.returns('?test');
    assert.equal(element._getUrlParameter('test'), 'test');
    locationStub.returns('?test2=12&test=3');
    assert.equal(element._getUrlParameter('test'), 'test');
    locationStub.returns('');
    assert.isNull(element._getUrlParameter('test'));
    locationStub.returns('?');
    assert.isNull(element._getUrlParameter('test'));
    locationStub.returns('?test2');
    assert.isNull(element._getUrlParameter('test'));
  });

  test('revert dialog opened with revert param', done => {
    const awaitPluginsLoadedStub = sinon
      .stub(getPluginLoader(), 'awaitPluginsLoaded')
      .callsFake(() => Promise.resolve());

    element._patchRange = {
      basePatchNum: ParentPatchSetNum,
      patchNum: 2 as RevisionPatchSetNum,
    };
    element._change = {
      ...createChangeViewChange(),
      revisions: {
        rev1: createRevision(1),
        rev2: createRevision(2),
      },
      current_revision: 'rev1' as CommitId,
      status: ChangeStatus.MERGED,
      labels: {},
      actions: {},
    };

    sinon.stub(element, '_getUrlParameter').callsFake(param => {
      assert.equal(param, 'revert');
      return param;
    });

    sinon.stub(element.$.actions, 'showRevertDialog').callsFake(done);

    element._maybeShowRevertDialog();
    assert.isTrue(awaitPluginsLoadedStub.called);
  });

  suite('scroll related tests', () => {
    test('document scrolling calls function to set scroll height', done => {
      const originalHeight = document.body.scrollHeight;
      const scrollStub = sinon.stub(element, 'handleScroll').callsFake(() => {
        assert.isTrue(scrollStub.called);
        document.body.style.height = `${originalHeight}px`;
        scrollStub.restore();
        done();
      });
      document.body.style.height = '10000px';
      element.handleScroll();
    });

    test('scrollTop is set correctly', async () => {
      element.viewState = {scrollTop: TEST_SCROLL_TOP_PX};

      sinon.stub(element, 'loadData').callsFake(() => {
        // When element is reloaded, ensure that the history
        // state has the scrollTop set earlier. This will then
        // be reset.
        assert.isTrue(element.viewState.scrollTop === TEST_SCROLL_TOP_PX);
        return Promise.resolve([]);
      });

      // simulate reloading component, which is done when route
      // changes to match a regex of change view type.
      element.params = {...createAppElementChangeViewParams()};
      await flush();
    });

    test('scrollTop is reset when new change is loaded', () => {
      element._resetFileListViewState();
      assert.equal(element.viewState.scrollTop, 0);
    });
  });

  suite('reply dialog tests', () => {
    setup(() => {
      sinon.stub(element.$.replyDialog, '_draftChanged');
      element._change = {
        ...createChangeViewChange(),
        revisions: createRevisions(1),
        messages: createChangeMessages(1),
      };
      element._change.labels = {};
      stubRestApi('getChangeDetail').callsFake(() =>
        Promise.resolve({
          ...createChangeViewChange(),
          // element has latest info
          revisions: {rev1: createRevision()},
          messages: createChangeMessages(1),
          current_revision: 'rev1' as CommitId,
        })
      );
    });

    test('show reply dialog on open-reply-dialog event', done => {
      const openReplyDialogStub = sinon.stub(element, '_openReplyDialog');
      element.dispatchEvent(
        new CustomEvent('open-reply-dialog', {
          composed: true,
          bubbles: true,
          detail: {},
        })
      );
      flush(() => {
        assert.isTrue(openReplyDialogStub.calledOnce);
        done();
      });
    });

    test('reply from comment adds quote text', () => {
      const e = new CustomEvent('', {
        detail: {message: {message: 'quote text'}},
      });
      element._handleMessageReply(e);
      assert.equal(element.$.replyDialog.quote, '> quote text\n\n');
    });

    test('reply from comment replaces quote text', () => {
      element.$.replyDialog.draft = '> old quote text\n\n some draft text';
      element.$.replyDialog.quote = '> old quote text\n\n';
      const e = new CustomEvent('', {
        detail: {message: {message: 'quote text'}},
      });
      element._handleMessageReply(e);
      assert.equal(element.$.replyDialog.quote, '> quote text\n\n');
    });

    test('reply from same comment preserves quote text', () => {
      element.$.replyDialog.draft = '> quote text\n\n some draft text';
      element.$.replyDialog.quote = '> quote text\n\n';
      const e = new CustomEvent('', {
        detail: {message: {message: 'quote text'}},
      });
      element._handleMessageReply(e);
      assert.equal(
        element.$.replyDialog.draft,
        '> quote text\n\n some draft text'
      );
      assert.equal(element.$.replyDialog.quote, '> quote text\n\n');
    });

    test('reply from top of page contains previous draft', () => {
      const div = document.createElement('div');
      element.$.replyDialog.draft = '> quote text\n\n some draft text';
      element.$.replyDialog.quote = '> quote text\n\n';
      const e = ({
        target: div,
        preventDefault: sinon.spy(),
      } as unknown) as MouseEvent;
      element._handleReplyTap(e);
      assert.equal(
        element.$.replyDialog.draft,
        '> quote text\n\n some draft text'
      );
      assert.equal(element.$.replyDialog.quote, '> quote text\n\n');
    });
  });

  test('reply button is disabled until server config is loaded', done => {
    assert.isTrue(element._replyDisabled);
    // fetches the server config on attached
    flush(() => {
      assert.isFalse(element._replyDisabled);
      done();
    });
  });

  test('header class computation', () => {
    assert.equal(element._computeHeaderClass(), 'header');
    assert.equal(element._computeHeaderClass(true), 'header editMode');
  });

  test('_maybeScrollToMessage', done => {
    flush(() => {
      const scrollStub = sinon.stub(element.messagesList!, 'scrollToMessage');

      element._maybeScrollToMessage('');
      assert.isFalse(scrollStub.called);
      element._maybeScrollToMessage('message');
      assert.isFalse(scrollStub.called);
      element._maybeScrollToMessage('#message-TEST');
      assert.isTrue(scrollStub.called);
      assert.equal(scrollStub.lastCall.args[0], 'TEST');
      done();
    });
  });

  test('topic update reloads related changes', () => {
    flush();
    const relatedChanges = element.shadowRoot!.querySelector(
      '#relatedChanges'
    ) as GrRelatedChangesList;
    const reloadStub = sinon.stub(relatedChanges, 'reload');
    element.dispatchEvent(new CustomEvent('topic-changed'));
    assert.isTrue(reloadStub.calledOnce);
  });

  test('_computeEditMode', () => {
    const callCompute = (
      range: PatchRange,
      params: AppElementChangeViewParams
    ) =>
      element._computeEditMode(
        {base: range, path: '', value: range},
        {base: params, path: '', value: params}
      );
    assert.isTrue(
      callCompute(
        {basePatchNum: ParentPatchSetNum, patchNum: 1 as RevisionPatchSetNum},
        {...createAppElementChangeViewParams(), edit: true}
      )
    );
    assert.isFalse(
      callCompute(
        {basePatchNum: ParentPatchSetNum, patchNum: 1 as RevisionPatchSetNum},
        createAppElementChangeViewParams()
      )
    );
    assert.isTrue(
      callCompute(
        {basePatchNum: 1 as BasePatchSetNum, patchNum: EditPatchSetNum},
        createAppElementChangeViewParams()
      )
    );
  });

  test('_processEdit', () => {
    element._patchRange = {};
    const change: ParsedChangeInfo = {
      ...createChangeViewChange(),
      current_revision: 'foo' as CommitId,
      revisions: {
        foo: {...createRevision(), actions: {cherrypick: {enabled: true}}},
      },
    };
    let mockChange;

    // With no edit, mockChange should be unmodified.
    element._processEdit((mockChange = _.cloneDeep(change)), false);
    assert.deepEqual(mockChange, change);

    const editCommit: CommitInfo = {
      ...createCommit(),
      commit: 'bar' as CommitId,
    };
    // When edit is not based on the latest PS, current_revision should be
    // unmodified.
    const edit: EditInfo = {
      ref: 'ref/test/abc' as GitRef,
      base_revision: 'abc',
      base_patch_set_number: 1 as BasePatchSetNum,
      commit: {...editCommit},
      fetch: {},
    };
    element._processEdit((mockChange = _.cloneDeep(change)), edit);
    assert.notDeepEqual(mockChange, change);
    assert.equal(mockChange.revisions.bar._number, EditPatchSetNum);
    assert.equal(mockChange.current_revision, change.current_revision);
    assert.deepEqual(mockChange.revisions.bar.commit, editCommit);
    assert.notOk(mockChange.revisions.bar.actions);

    edit.base_revision = 'foo';
    element._processEdit((mockChange = _.cloneDeep(change)), edit);
    assert.notDeepEqual(mockChange, change);
    assert.equal(mockChange.current_revision, 'bar');
    assert.deepEqual(
      mockChange.revisions.bar.actions,
      mockChange.revisions.foo.actions
    );

    // If _patchRange.patchNum is defined, do not load edit.
    element._patchRange.patchNum = 5 as RevisionPatchSetNum;
    change.current_revision = 'baz' as CommitId;
    element._processEdit((mockChange = _.cloneDeep(change)), edit);
    assert.equal(element._patchRange.patchNum, 5 as RevisionPatchSetNum);
    assert.notOk(mockChange.revisions.bar.actions);
  });

  test('file-action-tap handling', () => {
    element._patchRange = {
      basePatchNum: ParentPatchSetNum,
      patchNum: 1 as RevisionPatchSetNum,
    };
    element._change = {
      ...createChangeViewChange(),
    };
    const fileList = element.$.fileList;
    const Actions = GrEditConstants.Actions;
    element.$.fileListHeader.editMode = true;
    flush();
    const controls = element.$.fileListHeader.shadowRoot!.querySelector(
      '#editControls'
    ) as GrEditControls;
    const openDeleteDialogStub = sinon.stub(controls, 'openDeleteDialog');
    const openRenameDialogStub = sinon.stub(controls, 'openRenameDialog');
    const openRestoreDialogStub = sinon.stub(controls, 'openRestoreDialog');
    const getEditUrlForDiffStub = sinon.stub(GerritNav, 'getEditUrlForDiff');
    const navigateToRelativeUrlStub = sinon.stub(
      GerritNav,
      'navigateToRelativeUrl'
    );

    // Delete
    fileList.dispatchEvent(
      new CustomEvent('file-action-tap', {
        detail: {action: Actions.DELETE.id, path: 'foo'},
        bubbles: true,
        composed: true,
      })
    );
    flush();

    assert.isTrue(openDeleteDialogStub.called);
    assert.equal(openDeleteDialogStub.lastCall.args[0], 'foo');

    // Restore
    fileList.dispatchEvent(
      new CustomEvent('file-action-tap', {
        detail: {action: Actions.RESTORE.id, path: 'foo'},
        bubbles: true,
        composed: true,
      })
    );
    flush();

    assert.isTrue(openRestoreDialogStub.called);
    assert.equal(openRestoreDialogStub.lastCall.args[0], 'foo');

    // Rename
    fileList.dispatchEvent(
      new CustomEvent('file-action-tap', {
        detail: {action: Actions.RENAME.id, path: 'foo'},
        bubbles: true,
        composed: true,
      })
    );
    flush();

    assert.isTrue(openRenameDialogStub.called);
    assert.equal(openRenameDialogStub.lastCall.args[0], 'foo');

    // Open
    fileList.dispatchEvent(
      new CustomEvent('file-action-tap', {
        detail: {action: Actions.OPEN.id, path: 'foo'},
        bubbles: true,
        composed: true,
      })
    );
    flush();

    assert.isTrue(getEditUrlForDiffStub.called);
    assert.equal(getEditUrlForDiffStub.lastCall.args[1], 'foo');
    assert.equal(getEditUrlForDiffStub.lastCall.args[2], 1 as PatchSetNum);
    assert.isTrue(navigateToRelativeUrlStub.called);
  });

  test('_selectedRevision updates when patchNum is changed', () => {
    const revision1: RevisionInfo = createRevision(1);
    const revision2: RevisionInfo = createRevision(2);
    stubRestApi('getChangeDetail').returns(
      Promise.resolve({
        ...createChangeViewChange(),
        revisions: {
          aaa: revision1,
          bbb: revision2,
        },
        labels: {},
        actions: {},
        current_revision: 'bbb' as CommitId,
      })
    );
    sinon.stub(element, '_getEdit').returns(Promise.resolve(false));
    sinon
      .stub(element, '_getPreferences')
      .returns(Promise.resolve(createPreferences()));
    element._patchRange = {patchNum: 2 as RevisionPatchSetNum};
    return element._getChangeDetail().then(() => {
      assert.strictEqual(element._selectedRevision, revision2);

      element.set('_patchRange.patchNum', '1');
      assert.strictEqual(element._selectedRevision, revision1);
    });
  });

  test('_selectedRevision is assigned when patchNum is edit', () => {
    const revision1 = createRevision(1);
    const revision2 = createRevision(2);
    const revision3 = createEditRevision();
    stubRestApi('getChangeDetail').returns(
      Promise.resolve({
        ...createChangeViewChange(),
        revisions: {
          aaa: revision1,
          bbb: revision2,
          ccc: revision3,
        },
        labels: {},
        actions: {},
        current_revision: 'ccc' as CommitId,
      })
    );
    sinon.stub(element, '_getEdit').returns(Promise.resolve(undefined));
    sinon
      .stub(element, '_getPreferences')
      .returns(Promise.resolve(createPreferences()));
    element._patchRange = {patchNum: EditPatchSetNum};
    return element._getChangeDetail().then(() => {
      assert.strictEqual(element._selectedRevision, revision3);
    });
  });

  test('_sendShowChangeEvent', () => {
    const change = {...createChangeViewChange(), labels: {}};
    element._change = {...change};
    element._patchRange = {patchNum: 4 as RevisionPatchSetNum};
    element._mergeable = true;
    const showStub = sinon.stub(appContext.jsApiService, 'handleEvent');
    element._sendShowChangeEvent();
    assert.isTrue(showStub.calledOnce);
    assert.equal(showStub.lastCall.args[0], EventType.SHOW_CHANGE);
    assert.deepEqual(showStub.lastCall.args[1], {
      change,
      patchNum: 4,
      info: {mergeable: true},
    });
  });

  suite('_handleEditTap', () => {
    let fireEdit: () => void;

    setup(() => {
      fireEdit = () => {
        element.$.actions.dispatchEvent(new CustomEvent('edit-tap'));
      };
      navigateToChangeStub.restore();

      element._change = {
        ...createChangeViewChange(),
        revisions: {rev1: createRevision()},
      };
    });

    test('edit exists in revisions', done => {
      sinon.stub(GerritNav, 'navigateToChange').callsFake((...args) => {
        assert.equal(args.length, 2);
        assert.equal(args[1], EditPatchSetNum); // patchNum
        done();
      });

      element.set('_change.revisions.rev2', {
        _number: EditPatchSetNum,
      });
      flush();

      fireEdit();
    });

    test('no edit exists in revisions, non-latest patchset', done => {
      sinon.stub(GerritNav, 'navigateToChange').callsFake((...args) => {
        assert.equal(args.length, 4);
        assert.equal(args[1], 1 as PatchSetNum); // patchNum
        assert.equal(args[3], true); // opt_isEdit
        done();
      });

      element.set('_change.revisions.rev2', {_number: 2});
      element._patchRange = {patchNum: 1 as RevisionPatchSetNum};
      flush();

      fireEdit();
    });

    test('no edit exists in revisions, latest patchset', done => {
      sinon.stub(GerritNav, 'navigateToChange').callsFake((...args) => {
        assert.equal(args.length, 4);
        // No patch should be specified when patchNum == latest.
        assert.isNotOk(args[1]); // patchNum
        assert.equal(args[3], true); // opt_isEdit
        done();
      });

      element.set('_change.revisions.rev2', {_number: 2});
      element._patchRange = {patchNum: 2 as RevisionPatchSetNum};
      flush();

      fireEdit();
    });
  });

  test('_handleStopEditTap', done => {
    element._change = {
      ...createChangeViewChange(),
    };
    sinon.stub(element.$.metadata, '_computeLabelNames');
    navigateToChangeStub.restore();
    sinon.stub(GerritNav, 'navigateToChange').callsFake((...args) => {
      assert.equal(args.length, 2);
      assert.equal(args[1], 1 as PatchSetNum); // patchNum
      done();
    });

    element._patchRange = {patchNum: 1 as RevisionPatchSetNum};
    element.$.actions.dispatchEvent(
      new CustomEvent('stop-edit-tap', {bubbles: false})
    );
  });

  suite('plugin endpoints', () => {
    test('endpoint params', done => {
      element._change = {...createChangeViewChange(), labels: {}};
      element._selectedRevision = createRevision();
      let hookEl: HTMLElement;
      let plugin: PluginApi;
      pluginApi.install(
        p => {
          plugin = p;
          plugin
            .hook('change-view-integration')
            .getLastAttached()
            .then(el => (hookEl = el));
        },
        '0.1',
        'http://some/plugins/url.js'
      );
      flush(() => {
        assert.strictEqual((hookEl as any).plugin, plugin);
        assert.strictEqual((hookEl as any).change, element._change);
        assert.strictEqual((hookEl as any).revision, element._selectedRevision);
        done();
      });
    });
  });

  suite('_getMergeability', () => {
    let getMergeableStub: SinonStubbedMember<RestApiService['getMergeable']>;
    setup(() => {
      element._change = {...createChangeViewChange(), labels: {}};
      getMergeableStub = stubRestApi('getMergeable').returns(
        Promise.resolve({...createMergeable(), mergeable: true})
      );
    });

    test('merged change', () => {
      element._mergeable = null;
      element._change!.status = ChangeStatus.MERGED;
      return element._getMergeability().then(() => {
        assert.isFalse(element._mergeable);
        assert.isFalse(getMergeableStub.called);
      });
    });

    test('abandoned change', () => {
      element._mergeable = null;
      element._change!.status = ChangeStatus.ABANDONED;
      return element._getMergeability().then(() => {
        assert.isFalse(element._mergeable);
        assert.isFalse(getMergeableStub.called);
      });
    });

    test('open change', () => {
      element._mergeable = null;
      return element._getMergeability().then(() => {
        assert.isTrue(element._mergeable);
        assert.isTrue(getMergeableStub.called);
      });
    });
  });

  test('_handleToggleStar called when star is tapped', () => {
    element._change = {
      ...createChangeViewChange(),
      owner: {_account_id: 1 as AccountId},
      starred: false,
    };
    element._loggedIn = true;
    const stub = sinon.stub(element, '_handleToggleStar');
    flush();

    tap(element.$.changeStar.shadowRoot!.querySelector('button')!);
    assert.isTrue(stub.called);
  });

  suite('gr-reporting tests', () => {
    setup(() => {
      element._patchRange = {
        basePatchNum: ParentPatchSetNum,
        patchNum: 1 as RevisionPatchSetNum,
      };
      sinon.stub(element, '_getChangeDetail').returns(Promise.resolve(false));
      sinon.stub(element, '_getProjectConfig').returns(Promise.resolve());
      sinon.stub(element, '_reloadComments').returns(Promise.resolve());
      sinon.stub(element, '_getMergeability').returns(Promise.resolve());
      sinon.stub(element, '_getLatestCommitMessage').returns(Promise.resolve());
      sinon
        .stub(element, '_reloadPatchNumDependentResources')
        .returns(Promise.resolve([undefined, undefined, undefined]));
    });

    test("don't report changeDisplayed on reply", done => {
      const changeDisplayStub = sinon.stub(
        appContext.reportingService,
        'changeDisplayed'
      );
      const changeFullyLoadedStub = sinon.stub(
        appContext.reportingService,
        'changeFullyLoaded'
      );
      element._handleReplySent();
      flush(() => {
        assert.isFalse(changeDisplayStub.called);
        assert.isFalse(changeFullyLoadedStub.called);
        done();
      });
    });

    test('report changeDisplayed on _paramsChanged', async () => {
      const changeDisplayStub = sinon.stub(
        appContext.reportingService,
        'changeDisplayed'
      );
      const changeFullyLoadedStub = sinon.stub(
        appContext.reportingService,
        'changeFullyLoaded'
      );
      element.params = {
        ...createAppElementChangeViewParams(),
        changeNum: TEST_NUMERIC_CHANGE_ID,
        project: TEST_PROJECT_NAME,
      };
      await flush();
      assert.isTrue(changeDisplayStub.called);
      assert.isTrue(changeFullyLoadedStub.called);
    });
  });

  test('_calculateHasParent', () => {
    const changeId = '123' as ChangeId;
    const relatedChanges: RelatedChangeAndCommitInfo[] = [];

    assert.equal(element._calculateHasParent(changeId, relatedChanges), false);

    relatedChanges.push({
      ...createRelatedChangeAndCommitInfo(),
      change_id: '123' as ChangeId,
    });
    assert.equal(element._calculateHasParent(changeId, relatedChanges), false);

    relatedChanges.push({
      ...createRelatedChangeAndCommitInfo(),
      change_id: '234' as ChangeId,
    });
    assert.equal(element._calculateHasParent(changeId, relatedChanges), true);
  });
});
