/**
 * @license
 * Copyright (C) 2017 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.js';
import './gr-file-list-header.js';
import {GrFileListConstants} from '../gr-file-list-constants.js';
import {GerritNav} from '../../core/gr-navigation/gr-navigation.js';
import {generateChange} from '../../../test/test-utils.js';

const basicFixture = fixtureFromElement('gr-file-list-header');

suite('gr-file-list-header tests', () => {
  let element;

  setup(() => {
    stub('gr-rest-api-interface', {
      getConfig() { return Promise.resolve({test: 'config'}); },
      getAccount() { return Promise.resolve(null); },
      _fetchSharedCacheURL() { return Promise.resolve({}); },
    });
    element = basicFixture.instantiate();
  });

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

  test('Diff preferences hidden when no prefs or diffPrefsDisabled', () => {
    element.diffPrefsDisabled = true;
    flushAsynchronousOperations();
    assert.isTrue(element.$.diffPrefsContainer.hidden);

    element.diffPrefsDisabled = false;
    flushAsynchronousOperations();
    assert.isTrue(element.$.diffPrefsContainer.hidden);

    element.diffPrefsDisabled = true;
    element.diffPrefs = {font_size: '12'};
    flushAsynchronousOperations();
    assert.isTrue(element.$.diffPrefsContainer.hidden);

    element.diffPrefsDisabled = false;
    flushAsynchronousOperations();
    assert.isFalse(element.$.diffPrefsContainer.hidden);
  });

  test('_computeDescriptionReadOnly', () => {
    assert.equal(element._computeDescriptionReadOnly(false,
        {owner: {_account_id: 1}}, {_account_id: 1}), true);
    assert.equal(element._computeDescriptionReadOnly(true,
        {owner: {_account_id: 0}}, {_account_id: 1}), true);
    assert.equal(element._computeDescriptionReadOnly(true,
        {owner: {_account_id: 1}}, {_account_id: 1}), false);
  });

  test('_computeDescriptionPlaceholder', () => {
    assert.equal(element._computeDescriptionPlaceholder(true),
        'No patchset description');
    assert.equal(element._computeDescriptionPlaceholder(false),
        'Add patchset description');
  });

  test('description editing', () => {
    const putDescStub = sinon.stub(element.$.restAPI, 'setDescription')
        .returns(Promise.resolve({ok: true}));

    element.changeNum = '42';
    element.basePatchNum = 'PARENT';
    element.patchNum = 1;

    element.change = {
      change_id: 'Iad9dc96274af6946f3632be53b106ef80f7ba6ca',
      revisions: {
        rev1: {_number: 1, description: 'test', commit: {commit: 'rev1'}},
      },
      current_revision: 'rev1',
      status: 'NEW',
      labels: {},
      actions: {},
      owner: {_account_id: 1},
    };
    element.account = {_account_id: 1};
    element.loggedIn = true;

    flushAsynchronousOperations();

    // The element has a description, so the account chip should be visible
    // and the description label should not exist.
    const chip = element.root.querySelector('#descriptionChip');
    let label = element.root.querySelector('#descriptionLabel');

    assert.equal(chip.text, 'test');
    assert.isNotOk(label);

    // Simulate tapping the remove button, but call function directly so that
    // can determine what happens after the promise is resolved.
    return element._handleDescriptionRemoved()
        .then(() => {
          // The API stub should be called with an empty string for the new
          // description.
          assert.equal(putDescStub.lastCall.args[2], '');
          assert.equal(element.change.revisions.rev1.description, '');

          flushAsynchronousOperations();
          // The editable label should now be visible and the chip hidden.
          label = element.root.querySelector('#descriptionLabel');
          assert.isOk(label);
          assert.equal(getComputedStyle(chip).display, 'none');
          assert.notEqual(getComputedStyle(label).display, 'none');
          assert.isFalse(label.readOnly);
          // Edit the label to have a new value of test2, and save.
          label.editing = true;
          label._inputText = 'test2';
          label._save();
          flushAsynchronousOperations();
          // The API stub should be called with an `test2` for the new
          // description.
          assert.equal(putDescStub.callCount, 2);
          assert.equal(putDescStub.lastCall.args[2], 'test2');
        })
        .then(() => {
          flushAsynchronousOperations();
          // The chip should be visible again, and the label hidden.
          assert.equal(element.change.revisions.rev1.description, 'test2');
          assert.equal(getComputedStyle(label).display, 'none');
          assert.notEqual(getComputedStyle(chip).display, 'none');
        });
  });

  test('expandAllDiffs called when expand button clicked', () => {
    element.shownFileCount = 1;
    flushAsynchronousOperations();
    sinon.stub(element, '_expandAllDiffs');
    MockInteractions.tap(element.root.querySelector(
        '#expandBtn'));
    assert.isTrue(element._expandAllDiffs.called);
  });

  test('collapseAllDiffs called when expand button clicked', () => {
    element.shownFileCount = 1;
    flushAsynchronousOperations();
    sinon.stub(element, '_collapseAllDiffs');
    MockInteractions.tap(element.root.querySelector(
        '#collapseBtn'));
    assert.isTrue(element._collapseAllDiffs.called);
  });

  test('show/hide diffs disabled for large amounts of files', done => {
    const computeSpy = sinon.spy(element, '_fileListActionsVisible');
    element._files = [];
    element.changeNum = '42';
    element.basePatchNum = 'PARENT';
    element.patchNum = '2';
    element.shownFileCount = 1;
    flush(() => {
      assert.isTrue(computeSpy.lastCall.returnValue);
      _.times(element._maxFilesForBulkActions + 1, () => {
        element.shownFileCount = element.shownFileCount + 1;
      });
      assert.isFalse(computeSpy.lastCall.returnValue);
      done();
    });
  });

  test('fileViewActions are properly hidden', () => {
    const actions = element.shadowRoot
        .querySelector('.fileViewActions');
    assert.equal(getComputedStyle(actions).display, 'none');
    element.filesExpanded = GrFileListConstants.FilesExpandedState.SOME;
    flushAsynchronousOperations();
    assert.notEqual(getComputedStyle(actions).display, 'none');
    element.filesExpanded = GrFileListConstants.FilesExpandedState.ALL;
    flushAsynchronousOperations();
    assert.notEqual(getComputedStyle(actions).display, 'none');
    element.filesExpanded = GrFileListConstants.FilesExpandedState.NONE;
    flushAsynchronousOperations();
    assert.equal(getComputedStyle(actions).display, 'none');
  });

  test('expand/collapse buttons are toggled correctly', () => {
    element.shownFileCount = 10;
    flushAsynchronousOperations();
    const expandBtn = element.shadowRoot.querySelector('#expandBtn');
    const collapseBtn = element.shadowRoot.querySelector('#collapseBtn');
    assert.notEqual(getComputedStyle(expandBtn).display, 'none');
    assert.equal(getComputedStyle(collapseBtn).display, 'none');
    element.filesExpanded = GrFileListConstants.FilesExpandedState.SOME;
    flushAsynchronousOperations();
    assert.notEqual(getComputedStyle(expandBtn).display, 'none');
    assert.equal(getComputedStyle(collapseBtn).display, 'none');
    element.filesExpanded = GrFileListConstants.FilesExpandedState.ALL;
    flushAsynchronousOperations();
    assert.equal(getComputedStyle(expandBtn).display, 'none');
    assert.notEqual(getComputedStyle(collapseBtn).display, 'none');
    element.filesExpanded = GrFileListConstants.FilesExpandedState.NONE;
    flushAsynchronousOperations();
    assert.notEqual(getComputedStyle(expandBtn).display, 'none');
    assert.equal(getComputedStyle(collapseBtn).display, 'none');
  });

  test('navigateToChange called when range select changes', () => {
    const navigateToChangeStub = sinon.stub(GerritNav, 'navigateToChange');
    element.change = {
      change_id: 'Iad9dc96274af6946f3632be53b106ef80f7ba6ca',
      revisions: {
        rev2: {_number: 2},
        rev1: {_number: 1},
        rev13: {_number: 13},
        rev3: {_number: 3},
      },
      status: 'NEW',
      labels: {},
    };
    element.basePatchNum = 1;
    element.patchNum = 2;

    element._handlePatchChange({detail: {basePatchNum: 1, patchNum: 3}});
    assert.equal(navigateToChangeStub.callCount, 1);
    assert.isTrue(navigateToChangeStub.lastCall
        .calledWithExactly(element.change, 3, 1));
  });

  test('class is applied to file list on old patch set', () => {
    const allPatchSets = [{num: 4}, {num: 2}, {num: 1}];
    assert.equal(element._computePatchInfoClass('1', allPatchSets),
        'patchInfoOldPatchSet');
    assert.equal(element._computePatchInfoClass('2', allPatchSets),
        'patchInfoOldPatchSet');
    assert.equal(element._computePatchInfoClass('4', allPatchSets), '');
  });

  suite('editMode behavior', () => {
    setup(() => {
      element.diffPrefsDisabled = false;
      element.diffPrefs = {};
    });

    const isVisible = el => {
      assert.ok(el);
      return getComputedStyle(el).getPropertyValue('display') !== 'none';
    };

    test('patch specific elements', () => {
      element.editMode = true;
      element.allPatchSets = generateChange({revisionsCount: 2}).revisions;
      flushAsynchronousOperations();

      assert.isFalse(isVisible(element.$.diffPrefsContainer));
      assert.isFalse(isVisible(element.shadowRoot
          .querySelector('.descriptionContainer')));

      element.editMode = false;
      flushAsynchronousOperations();

      assert.isTrue(isVisible(element.shadowRoot
          .querySelector('.descriptionContainer')));
      assert.isTrue(isVisible(element.$.diffPrefsContainer));
    });

    test('edit-controls visibility', () => {
      element.editMode = false;
      flushAsynchronousOperations();
      // on the first render, when editMode is false, editControls are not
      // in the DOM to reduce size of DOM and make first render faster.
      assert.isNull(element.shadowRoot
          .querySelector('#editControls'));

      element.editMode = true;
      flushAsynchronousOperations();
      assert.isTrue(isVisible(element.shadowRoot
          .querySelector('#editControls').parentElement));

      element.editMode = false;
      flushAsynchronousOperations();
      assert.isFalse(isVisible(element.shadowRoot
          .querySelector('#editControls').parentElement));
    });

    test('_computeUploadHelpContainerClass', () => {
      // Only show the upload helper button when an unmerged change is viewed
      // by its owner.
      const accountA = {_account_id: 1};
      const accountB = {_account_id: 2};
      assert.notInclude(element._computeUploadHelpContainerClass(
          {owner: accountA}, accountA), 'hide');
      assert.include(element._computeUploadHelpContainerClass(
          {owner: accountA}, accountB), 'hide');
    });
  });
});

