/* eslint-disable dot-notation */
import './index';
import { assert } from 'chai';
import { $$ } from 'common-sk/modules/dom';

import { eventPromise, setUpElementUnderTest } from '../../../infra-sk/modules/test_util';
import { DataFrame, pivot, TraceSet } from '../json';
import {
  KeyValues,
  keyValuesFromTraceSet, PivotTableSk, PivotTableSkChangeEventDetail, SortHistory, SortSelection,
} from './pivot-table-sk';

const df: DataFrame = {
  header: [],
  paramset: {},
  traceset: {
    ',arch=x86,config=8888,': [1, 1.3e27],
    ',arch=arm,config=8888,': [2, 2.3e27],
    ',arch=x86,config=gpu,': [3, 1.2345],
    ',arch=arm,config=gpu,': [3, Math.PI],
  },
  skip: 0,
};

const req: pivot.Request = {
  group_by: ['config', 'arch'],
  operation: 'avg',
  summary: ['avg', 'sum'],
};

const query = 'config=8888&config=gpu&arch=x86&arch=arm';

describe('pivot-table-sk', () => {
  const newInstance = setUpElementUnderTest<PivotTableSk>('pivot-table-sk');

  let element: PivotTableSk;
  beforeEach(() => {
    element = newInstance((el: PivotTableSk) => {
      el.set(df, req, query);
    });
  });

  describe('click sort icon on first column', () => {
    it('sorts column descending', async () => {
      let firstSortSelection = element['sortHistory']!.history[0];
      assert.deepEqual(firstSortSelection, new SortSelection(0, 'summaryValues', 'up'));

      const event = eventPromise<CustomEvent<PivotTableSkChangeEventDetail>>('change');

      // Click on the sort up icon that appears over the 'config' column.
      $$<HTMLElement>('sort-icon-sk', element)!.click();

      const encodedHistory = (await event).detail;

      // Confirm it changes to a drop down icon.
      assert.isNotNull($$<HTMLElement>('arrow-drop-down-icon-sk', element));

      // Confirm sort state has changed.
      firstSortSelection = element['sortHistory']!.history[0];
      assert.deepEqual(firstSortSelection, new SortSelection(0, 'keyValues', 'down'));
      assert.isTrue(encodedHistory.startsWith(firstSortSelection.encode()));
    });
  });
});

describe('SortSelection', () => {
  it('changes the direction on toggleDirection', () => {
    const s = new SortSelection(1, 'summaryValues', 'up');
    s.toggleDirection();
    assert.equal(s.dir, 'down');
  });

  it('builds an accurate compareFunction for summary values', () => {
    const keyValues = keyValuesFromTraceSet(df.traceset, req);
    // Sort up on the second column of summary values, aka 'sum'.
    const s = new SortSelection(1, 'summaryValues', 'up');
    const compare = s.buildCompare(df.traceset, keyValues);

    assert.equal(compare(',arch=x86,config=8888,', ',arch=x86,config=8888,'), 0, 'matching keys returns 0');
    assert.isTrue(compare(',arch=x86,config=8888,', ',arch=arm,config=8888,') < 0, '1.3e27 < 2.3e27 sorting up');
    s.toggleDirection();
    assert.isTrue(compare(',arch=x86,config=8888,', ',arch=arm,config=8888,') > 0, '1.3e27 < 2.3e27 sorting down');
  });

  it('builds a compareFunction that operates correctly in sort for summary values', () => {
    const keyValues = keyValuesFromTraceSet(df.traceset, req);
    // Sort up on the second column of summary values, aka 'sum'.
    const s = new SortSelection(1, 'summaryValues', 'up');
    const compare = s.buildCompare(df.traceset, keyValues);

    assert.deepEqual(
      Object.keys(df.traceset).sort(compare).map((traceKey) => df.traceset[traceKey][1]),
      [
        1.2345,
        Math.PI,
        1.3e27,
        2.3e27,
      ],
    );
  });

  it('builds an accurate compareFunction for key values', () => {
    const keyValues = keyValuesFromTraceSet(df.traceset, req);
    // Sort up on the first column of key values, aka 'config'.
    const s = new SortSelection(0, 'keyValues', 'up');
    const compare = s.buildCompare(df.traceset, keyValues);

    assert.equal(compare(',arch=x86,config=gpu,', ',arch=x86,config=gpu,'), 0, 'matching keys returns 0');
    assert.equal(compare(',arch=arm,config=8888,', ',arch=x86,config=gpu,'), -1, '8888 < gpu sorting up');
    s.toggleDirection();
    assert.equal(compare(',arch=arm,config=8888,', ',arch=x86,config=gpu,'), 1, '8888 < gpu sorting down');
  });

  it('round trips through encode and decode', () => {
    const expected = new SortSelection(2, 'keyValues', 'down');
    const encoded = expected.encode();
    assert.equal(encoded, 'dk2');
    const actual = SortSelection.decode(expected.encode());
    assert.deepEqual(actual, expected);
  });

  it('decode robustly handles invalid strings', () => {
    const actual = SortSelection.decode('');
    assert.deepEqual(actual, new SortSelection(0, 'summaryValues', 'down'));
  });
});

describe('SortHistory', () => {
  it('moves selected columns to the front of the list and toggles their direction', () => {
    const history = new SortHistory(req.group_by!.length, req.summary!.length);

    const first = history.history[0];
    assert.deepEqual(first, new SortSelection(0, 'summaryValues', 'up'));

    // If we select the second keyValues column to sort on then it should move to
    // the front of the history list and be in the opposite direction.

    history.selectColumnToSortOn(1, 'keyValues');

    const newFirst = history.history[0];
    assert.deepEqual(newFirst, new SortSelection(1, 'keyValues', 'down'));
  });

  it('builds a compareFunction that operates correctly in sort', () => {
    const history = new SortHistory(req.group_by!.length, req.summary!.length);

    // Configure history so that is sorts on the second key value down, and
    // breaks ties by looking at the first key value also in the down direction:
    history.selectColumnToSortOn(0, 'summaryValues');
    history.selectColumnToSortOn(1, 'summaryValues');

    // Sort this traceset and it should come out in this order:
    const traceset: TraceSet = {
      ',arch=x86,config=gpu,': [4, 2],
      ',arch=arm,config=gpu,': [3, 2],
      ',arch=arm,config=8888,': [2, 1],
      ',arch=x86,config=8888,': [1, 1],
    };
    const keyValues = keyValuesFromTraceSet(traceset, req);
    const keys = Object.keys(traceset);
    keys.sort(history.buildCompare(traceset, keyValues));
    const expected = [
      ',arch=x86,config=gpu,',
      ',arch=arm,config=gpu,',
      ',arch=arm,config=8888,',
      ',arch=x86,config=8888,',
    ];
    assert.deepEqual(keys, expected);
  });
});

describe('keyValuesFromTraceSet', () => {
  it('returns empty keyValues for an empty TraceSet', () => {
    assert.isEmpty(keyValuesFromTraceSet({}, req));
  });

  it('correctly orders key values based on the request', () => {
    const actual = keyValuesFromTraceSet(df.traceset, req);
    const expected: KeyValues = {
      ',arch=x86,config=gpu,': ['gpu', 'x86'],
      ',arch=arm,config=gpu,': ['gpu', 'arm'],
      ',arch=arm,config=8888,': ['8888', 'arm'],
      ',arch=x86,config=8888,': ['8888', 'x86'],
    };
    assert.deepEqual(actual, expected);
  });

  it('drops keys that do not appear in the pivot.Request.group_by', () => {
    const reqWithOnlyOneGroupBy: pivot.Request = {
      group_by: ['arch'], // Only has arch.
      operation: 'avg',
      summary: ['avg', 'sum'],
    };
    const actual = keyValuesFromTraceSet(df.traceset, reqWithOnlyOneGroupBy);
    const expected: KeyValues = {
      ',arch=x86,config=gpu,': ['x86'],
      ',arch=arm,config=gpu,': ['arm'],
      ',arch=arm,config=8888,': ['arm'],
      ',arch=x86,config=8888,': ['x86'],
    };
    assert.deepEqual(actual, expected);
  });

  it('round trips through encode and decode', () => {
    const expected = new SortHistory(req.group_by!.length, req.summary!.length);
    const actual = new SortHistory(req.group_by!.length, req.summary!.length);
    actual.history = [];
    actual.decode(expected.encode());
    assert.deepEqual(actual, expected);
  });
});
