// Copyright (C) 2018 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 {produce} from 'immer';

import {assertExists} from '../base/logging';
import {Time} from '../base/time';
import {PrimaryTrackSortKey} from '../public';
import {SLICE_TRACK_KIND} from '../tracks/chrome_slices';
import {HEAP_PROFILE_TRACK_KIND} from '../tracks/heap_profile';
import {
  PROCESS_SCHEDULING_TRACK_KIND,
} from '../tracks/process_summary/process_scheduling_track';
import {THREAD_STATE_TRACK_KIND} from '../tracks/thread_state';

import {StateActions} from './actions';
import {createEmptyState} from './empty_state';
import {
  InThreadTrackSortKey,
  ProfileType,
  SCROLLING_TRACK_GROUP,
  State,
  TraceUrlSource,
  TrackSortKey,
} from './state';

function fakeTrack(state: State, args: {
  key: string,
  uri?: string,
  trackGroup?: string,
  trackSortKey?: TrackSortKey,
  name?: string,
  tid?: string
}): State {
  return produce(state, (draft) => {
    StateActions.addTrack(draft, {
      uri: args.uri || 'sometrack',
      key: args.key,
      name: args.name || 'A track',
      trackSortKey: args.trackSortKey === undefined ?
        PrimaryTrackSortKey.ORDINARY_TRACK :
        args.trackSortKey,
      trackGroup: args.trackGroup || SCROLLING_TRACK_GROUP,
    });
  });
}

function fakeTrackGroup(
  state: State, args: {id: string, summaryTrackId: string}): State {
  return produce(state, (draft) => {
    StateActions.addTrackGroup(draft, {
      name: 'A group',
      id: args.id,
      collapsed: false,
      summaryTrackKey: args.summaryTrackId,
    });
  });
}

function pinnedAndScrollingTracks(
  state: State,
  keys: string[],
  pinnedTracks: string[],
  scrollingTracks: string[]): State {
  for (const key of keys) {
    state = fakeTrack(state, {key});
  }
  state = produce(state, (draft) => {
    draft.pinnedTracks = pinnedTracks;
    draft.scrollingTracks = scrollingTracks;
  });
  return state;
}

test('add scrolling tracks', () => {
  const once = produce(createEmptyState(), (draft) => {
    StateActions.addTrack(draft, {
      uri: 'cpu',
      name: 'Cpu 1',
      trackSortKey: PrimaryTrackSortKey.ORDINARY_TRACK,
      trackGroup: SCROLLING_TRACK_GROUP,
    });
  });
  const twice = produce(once, (draft) => {
    StateActions.addTrack(draft, {
      uri: 'cpu',
      name: 'Cpu 2',
      trackSortKey: PrimaryTrackSortKey.ORDINARY_TRACK,
      trackGroup: SCROLLING_TRACK_GROUP,
    });
  });

  expect(Object.values(twice.tracks).length).toBe(2);
  expect(twice.scrollingTracks.length).toBe(2);
});

test('add track to track group', () => {
  let state = createEmptyState();
  state = fakeTrack(state, {key: 's'});

  const afterGroup = produce(state, (draft) => {
    StateActions.addTrackGroup(draft, {
      name: 'A track group',
      id: '123-123-123',
      summaryTrackKey: 's',
      collapsed: false,
    });
  });

  const afterTrackAdd = produce(afterGroup, (draft) => {
    StateActions.addTrack(draft, {
      key: '1',
      uri: 'slices',
      name: 'renderer 1',
      trackSortKey: PrimaryTrackSortKey.ORDINARY_TRACK,
      trackGroup: '123-123-123',
    });
  });

  expect(afterTrackAdd.trackGroups['123-123-123'].tracks[0]).toBe('s');
  expect(afterTrackAdd.trackGroups['123-123-123'].tracks[1]).toBe('1');
});

test('reorder tracks', () => {
  const once = produce(createEmptyState(), (draft) => {
    StateActions.addTrack(draft, {
      uri: 'cpu',
      name: 'Cpu 1',
      trackSortKey: PrimaryTrackSortKey.ORDINARY_TRACK,
    });
    StateActions.addTrack(draft, {
      uri: 'cpu',
      name: 'Cpu 2',
      trackSortKey: PrimaryTrackSortKey.ORDINARY_TRACK,
    });
  });

  const firstTrackId = once.scrollingTracks[0];
  const secondTrackId = once.scrollingTracks[1];

  const twice = produce(once, (draft) => {
    StateActions.moveTrack(draft, {
      srcId: `${firstTrackId}`,
      op: 'after',
      dstId: `${secondTrackId}`,
    });
  });

  expect(twice.scrollingTracks[0]).toBe(secondTrackId);
  expect(twice.scrollingTracks[1]).toBe(firstTrackId);
});

test('reorder pinned to scrolling', () => {
  let state = createEmptyState();
  state = pinnedAndScrollingTracks(state, ['a', 'b', 'c'], ['a', 'b'], ['c']);

  const after = produce(state, (draft) => {
    StateActions.moveTrack(draft, {
      srcId: 'b',
      op: 'before',
      dstId: 'c',
    });
  });

  expect(after.pinnedTracks).toEqual(['a']);
  expect(after.scrollingTracks).toEqual(['b', 'c']);
});

test('reorder scrolling to pinned', () => {
  let state = createEmptyState();
  state = pinnedAndScrollingTracks(state, ['a', 'b', 'c'], ['a'], ['b', 'c']);

  const after = produce(state, (draft) => {
    StateActions.moveTrack(draft, {
      srcId: 'b',
      op: 'after',
      dstId: 'a',
    });
  });

  expect(after.pinnedTracks).toEqual(['a', 'b']);
  expect(after.scrollingTracks).toEqual(['c']);
});

test('reorder clamp bottom', () => {
  let state = createEmptyState();
  state = pinnedAndScrollingTracks(state, ['a', 'b', 'c'], ['a', 'b'], ['c']);

  const after = produce(state, (draft) => {
    StateActions.moveTrack(draft, {
      srcId: 'a',
      op: 'before',
      dstId: 'a',
    });
  });
  expect(after).toEqual(state);
});

test('reorder clamp top', () => {
  let state = createEmptyState();
  state = pinnedAndScrollingTracks(state, ['a', 'b', 'c'], ['a'], ['b', 'c']);

  const after = produce(state, (draft) => {
    StateActions.moveTrack(draft, {
      srcId: 'c',
      op: 'after',
      dstId: 'c',
    });
  });
  expect(after).toEqual(state);
});

test('pin', () => {
  let state = createEmptyState();
  state = pinnedAndScrollingTracks(state, ['a', 'b', 'c'], ['a'], ['b', 'c']);

  const after = produce(state, (draft) => {
    StateActions.toggleTrackPinned(draft, {
      trackKey: 'c',
    });
  });
  expect(after.pinnedTracks).toEqual(['a', 'c']);
  expect(after.scrollingTracks).toEqual(['b']);
});

test('unpin', () => {
  let state = createEmptyState();
  state = pinnedAndScrollingTracks(state, ['a', 'b', 'c'], ['a', 'b'], ['c']);

  const after = produce(state, (draft) => {
    StateActions.toggleTrackPinned(draft, {
      trackKey: 'a',
    });
  });
  expect(after.pinnedTracks).toEqual(['b']);
  expect(after.scrollingTracks).toEqual(['a', 'c']);
});

test('open trace', () => {
  const state = createEmptyState();
  const recordConfig = state.recordConfig;
  const after = produce(state, (draft) => {
    StateActions.openTraceFromUrl(draft, {
      url: 'https://example.com/bar',
    });
  });

  expect(after.engine).not.toBeUndefined();
  expect((after.engine!!.source as TraceUrlSource).url)
    .toBe('https://example.com/bar');
  expect(after.recordConfig).toBe(recordConfig);
});

test('open second trace from file', () => {
  const once = produce(createEmptyState(), (draft) => {
    StateActions.openTraceFromUrl(draft, {
      url: 'https://example.com/bar',
    });
  });

  const twice = produce(once, (draft) => {
    StateActions.addTrack(draft, {
      uri: 'cpu',
      name: 'Cpu 1',
      trackSortKey: PrimaryTrackSortKey.ORDINARY_TRACK,
    });
  });

  const thrice = produce(twice, (draft) => {
    StateActions.openTraceFromUrl(draft, {
      url: 'https://example.com/foo',
    });
  });

  expect(thrice.engine).not.toBeUndefined();
  expect((thrice.engine!!.source as TraceUrlSource).url)
    .toBe('https://example.com/foo');
  expect(thrice.pinnedTracks.length).toBe(0);
  expect(thrice.scrollingTracks.length).toBe(0);
});

test('setEngineReady with missing engine is ignored', () => {
  const state = createEmptyState();
  produce(state, (draft) => {
    StateActions.setEngineReady(
      draft, {engineId: '1', ready: true, mode: 'WASM'});
  });
});

test('setEngineReady', () => {
  const state = createEmptyState();
  const after = produce(state, (draft) => {
    StateActions.openTraceFromUrl(draft, {
      url: 'https://example.com/bar',
    });
    const latestEngineId = assertExists(draft.engine).id;
    StateActions.setEngineReady(
      draft, {engineId: latestEngineId, ready: true, mode: 'WASM'});
  });
  expect(after.engine!!.ready).toBe(true);
});

test('sortTracksByPriority', () => {
  let state = createEmptyState();
  state = fakeTrackGroup(state, {id: 'g', summaryTrackId: 'b'});
  state = fakeTrack(state, {
    key: 'b',
    uri: HEAP_PROFILE_TRACK_KIND,
    trackSortKey: PrimaryTrackSortKey.HEAP_PROFILE_TRACK,
    trackGroup: 'g',
  });
  state = fakeTrack(state, {
    key: 'a',
    uri: PROCESS_SCHEDULING_TRACK_KIND,
    trackSortKey: PrimaryTrackSortKey.PROCESS_SCHEDULING_TRACK,
    trackGroup: 'g',
  });

  const after = produce(state, (draft) => {
    StateActions.sortThreadTracks(draft, {});
  });

  // High Priority tracks should be sorted before Low Priority tracks:
  // 'b' appears twice because it's the summary track
  expect(after.trackGroups['g'].tracks).toEqual(['a', 'b', 'b']);
});

test('sortTracksByPriorityAndKindAndName', () => {
  let state = createEmptyState();
  state = fakeTrackGroup(state, {id: 'g', summaryTrackId: 'b'});
  state = fakeTrack(state, {
    key: 'a',
    uri: PROCESS_SCHEDULING_TRACK_KIND,
    trackSortKey: PrimaryTrackSortKey.PROCESS_SCHEDULING_TRACK,
    trackGroup: 'g',
  });
  state = fakeTrack(state, {
    key: 'b',
    uri: SLICE_TRACK_KIND,
    trackGroup: 'g',
    trackSortKey: PrimaryTrackSortKey.MAIN_THREAD,
  });
  state = fakeTrack(state, {
    key: 'c',
    uri: SLICE_TRACK_KIND,
    trackGroup: 'g',
    trackSortKey: PrimaryTrackSortKey.RENDER_THREAD,
  });
  state = fakeTrack(state, {
    key: 'd',
    uri: SLICE_TRACK_KIND,
    trackGroup: 'g',
    trackSortKey: PrimaryTrackSortKey.GPU_COMPLETION_THREAD,
  });
  state = fakeTrack(
    state, {key: 'e', uri: HEAP_PROFILE_TRACK_KIND, trackGroup: 'g'});
  state = fakeTrack(
    state, {key: 'f', uri: SLICE_TRACK_KIND, trackGroup: 'g', name: 'T2'});
  state = fakeTrack(
    state, {key: 'g', uri: SLICE_TRACK_KIND, trackGroup: 'g', name: 'T10'});

  const after = produce(state, (draft) => {
    StateActions.sortThreadTracks(draft, {});
  });

  // The order should be determined by:
  // 1.High priority
  // 2.Non ordinary track kinds
  // 3.Low priority
  // 4.Collated name string (ie. 'T2' will be before 'T10')
  expect(after.trackGroups['g'].tracks)
    .toEqual(['a', 'b', 'b', 'c', 'd', 'e', 'f', 'g']);
});

test('sortTracksByTidThenName', () => {
  let state = createEmptyState();
  state = fakeTrackGroup(state, {id: 'g', summaryTrackId: 'a'});
  state = fakeTrack(state, {
    key: 'a',
    uri: SLICE_TRACK_KIND,
    trackSortKey: {
      utid: 1,
      priority: InThreadTrackSortKey.ORDINARY,
    },
    trackGroup: 'g',
    name: 'aaa',
    tid: '1',
  });
  state = fakeTrack(state, {
    key: 'b',
    uri: SLICE_TRACK_KIND,
    trackSortKey: {
      utid: 2,
      priority: InThreadTrackSortKey.ORDINARY,
    },
    trackGroup: 'g',
    name: 'bbb',
    tid: '2',
  });
  state = fakeTrack(state, {
    key: 'c',
    uri: THREAD_STATE_TRACK_KIND,
    trackSortKey: {
      utid: 1,
      priority: InThreadTrackSortKey.ORDINARY,
    },
    trackGroup: 'g',
    name: 'ccc',
    tid: '1',
  });

  const after = produce(state, (draft) => {
    StateActions.sortThreadTracks(draft, {});
  });

  expect(after.trackGroups['g'].tracks).toEqual(['a', 'a', 'c', 'b']);
});

test('perf samples open flamegraph', () => {
  const state = createEmptyState();

  const afterSelectingPerf = produce(state, (draft) => {
    StateActions.selectPerfSamples(draft, {
      id: 0,
      upid: 0,
      leftTs: Time.fromRaw(0n),
      rightTs: Time.fromRaw(0n),
      type: ProfileType.PERF_SAMPLE,
    });
  });

  expect(assertExists(afterSelectingPerf.currentFlamegraphState).type)
    .toBe(ProfileType.PERF_SAMPLE);
});

test('heap profile opens flamegraph', () => {
  const state = createEmptyState();

  const afterSelectingPerf = produce(state, (draft) => {
    StateActions.selectHeapProfile(draft, {
      id: 0,
      upid: 0,
      ts: Time.fromRaw(0n),
      type: ProfileType.JAVA_HEAP_GRAPH,
    });
  });

  expect(assertExists(afterSelectingPerf.currentFlamegraphState).type)
    .toBe(ProfileType.JAVA_HEAP_GRAPH);
});
