blob: 599a7486d42c6b3929ca6ac1bf0b22a1fe46eece [file] [log] [blame]
// Copyright (C) 2023 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 {createStore, Track, TrackDescriptor} from '../public';
import {createEmptyState} from './empty_state';
import {TrackManager} from './track_cache';
function makeMockTrack(): Track {
return {
onCreate: jest.fn(),
onUpdate: jest.fn(),
onDestroy: jest.fn(),
render: jest.fn(),
onFullRedraw: jest.fn(),
getSliceRect: jest.fn(),
getHeight: jest.fn(),
getTrackShellButtons: jest.fn(),
onMouseMove: jest.fn(),
onMouseClick: jest.fn(),
onMouseOut: jest.fn(),
};
}
async function settle() {
await new Promise((r) => setTimeout(r, 0));
}
let track: Track;
let td: TrackDescriptor;
let trackCache: TrackManager;
beforeEach(() => {
track = makeMockTrack();
td = {
uri: 'test',
trackFactory: () => track,
};
const store = createStore(createEmptyState());
trackCache = new TrackManager(store);
});
describe('TrackCache', () => {
it('calls track lifecycle hooks', async () => {
const entry = trackCache.resolveTrack('foo', td);
entry.update();
await settle();
expect(track.onUpdate).toHaveBeenCalledTimes(1);
});
it('reuses tracks', async () => {
const first = trackCache.resolveTrack('foo', td);
trackCache.flushOldTracks();
first.update();
const second = trackCache.resolveTrack('foo', td);
trackCache.flushOldTracks();
second.update();
// Ensure onCreate only called once
expect(track.onCreate).toHaveBeenCalledTimes(1);
expect(first).toBe(second);
});
it('destroys tracks', async () => {
const t = trackCache.resolveTrack('foo', td);
t.update();
// Double flush should destroy all tracks
trackCache.flushOldTracks();
trackCache.flushOldTracks();
await settle();
// Ensure onCreate only called once
expect(track.onDestroy).toHaveBeenCalledTimes(1);
});
});
describe('TrackCacheEntry', () => {
it('updates', async () => {
const entry = trackCache.resolveTrack('foo', td);
entry.update();
await settle();
expect(track.onUpdate).toHaveBeenCalledTimes(1);
});
it('throws if updated when destroyed', async () => {
const entry = trackCache.resolveTrack('foo', td);
// Double flush should destroy all tracks
trackCache.flushOldTracks();
trackCache.flushOldTracks();
await settle();
expect(() => entry.update()).toThrow();
});
});