Commit 1ab548f4 by Torkel Ödegaard Committed by GitHub

Merge pull request #15832 from grafana/stop-playlist

Alternative fix to detecting when to stop a playlist
parents 2604e9e4 3375c72d
......@@ -7,6 +7,7 @@ import coreModule from '../../core/core_module';
import appEvents from 'app/core/app_events';
import locationUtil from 'app/core/utils/location_util';
import kbn from 'app/core/utils/kbn';
import { store } from 'app/store/store';
export class PlaylistSrv {
private cancelPromise: any;
......@@ -15,6 +16,8 @@ export class PlaylistSrv {
private interval: number;
private startUrl: string;
private numberOfLoops = 0;
private storeUnsub: () => void;
private validPlaylistUrl: string;
isPlaying: boolean;
/** @ngInject */
......@@ -39,15 +42,16 @@ export class PlaylistSrv {
const dash = this.dashboards[this.index];
const queryParams = this.$location.search();
const filteredParams = _.pickBy(queryParams, value => value !== null);
const nextDashboardUrl = locationUtil.stripBaseFromUrl(dash.url);
// this is done inside timeout to make sure digest happens after
// as this can be called from react
this.$timeout(() => {
const stripedUrl = locationUtil.stripBaseFromUrl(dash.url);
this.$location.url(stripedUrl + '?' + toUrlParams(filteredParams));
this.$location.url(nextDashboardUrl + '?' + toUrlParams(filteredParams));
});
this.index++;
this.validPlaylistUrl = nextDashboardUrl;
this.cancelPromise = this.$timeout(() => this.next(), this.interval);
}
......@@ -56,6 +60,15 @@ export class PlaylistSrv {
this.next();
}
// Detect url changes not caused by playlist srv and stop playlist
storeUpdated() {
const state = store.getState();
if (state.location.path !== this.validPlaylistUrl) {
this.stop();
}
}
start(playlistId) {
this.stop();
......@@ -63,6 +76,10 @@ export class PlaylistSrv {
this.index = 0;
this.isPlaying = true;
// setup location tracking
this.storeUnsub = store.subscribe(() => this.storeUpdated());
this.validPlaylistUrl = this.$location.path();
appEvents.emit('playlist-started');
return this.backendSrv.get(`/api/playlists/${playlistId}`).then(playlist => {
......@@ -85,6 +102,10 @@ export class PlaylistSrv {
this.index = 0;
this.isPlaying = false;
if (this.storeUnsub) {
this.storeUnsub();
}
if (this.cancelPromise) {
this.$timeout.cancel(this.cancelPromise);
}
......
import configureMockStore from 'redux-mock-store';
import { PlaylistSrv } from '../playlist_srv';
import { setStore } from 'app/store/store';
const mockStore = configureMockStore();
setStore(
mockStore({
location: {},
})
);
const dashboards = [{ url: 'dash1' }, { url: 'dash2' }];
......@@ -19,6 +29,7 @@ const createPlaylistSrv = (): [PlaylistSrv, { url: jest.MockInstance<any, any> }
const mockLocation = {
url: jest.fn(),
search: () => ({}),
path: () => '/playlists/1',
};
const mockTimeout = jest.fn();
......@@ -96,4 +107,32 @@ describe('PlaylistSrv', () => {
expect(hrefMock).toHaveBeenCalledTimes(3);
expect(hrefMock).toHaveBeenLastCalledWith(initialUrl);
});
it('storeUpdated should stop playlist when navigating away', async () => {
await srv.start(1);
srv.storeUpdated();
expect(srv.isPlaying).toBe(false);
});
it('storeUpdated should not stop playlist when navigating to next dashboard', async () => {
await srv.start(1);
srv.next();
setStore(
mockStore({
location: {
path: 'dash2',
},
})
);
expect((srv as any).validPlaylistUrl).toBe('dash2');
srv.storeUpdated();
expect(srv.isPlaying).toBe(true);
});
});
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment