Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -191,6 +191,114 @@ describe('KbnUrlStateStorage', () => {
});
});

describe('useHashQuery: false', () => {
let urlStateStorage: IKbnUrlStateStorage;
let history: History;
const getCurrentUrl = () => history.createHref(history.location);
beforeEach(() => {
history = createBrowserHistory();
history.push('/');
urlStateStorage = createKbnUrlStateStorage({ useHash: false, history, useHashQuery: false });
});

it('should persist state to url', async () => {
const state = { test: 'test', ok: 1 };
const key = '_s';
await urlStateStorage.set(key, state);
expect(getCurrentUrl()).toMatchInlineSnapshot(`"/?_s=(ok:1,test:test)"`);
expect(urlStateStorage.get(key)).toEqual(state);
});

it('should flush state to url', () => {
const state = { test: 'test', ok: 1 };
const key = '_s';
urlStateStorage.set(key, state);
expect(getCurrentUrl()).toMatchInlineSnapshot(`"/"`);
expect(!!urlStateStorage.kbnUrlControls.flush()).toBe(true);
expect(getCurrentUrl()).toMatchInlineSnapshot(`"/?_s=(ok:1,test:test)"`);
expect(urlStateStorage.get(key)).toEqual(state);

expect(!!urlStateStorage.kbnUrlControls.flush()).toBe(false); // nothing to flush, not update
});

it('should cancel url updates', async () => {
const state = { test: 'test', ok: 1 };
const key = '_s';
const pr = urlStateStorage.set(key, state);
expect(getCurrentUrl()).toMatchInlineSnapshot(`"/"`);
urlStateStorage.cancel();
await pr;
expect(getCurrentUrl()).toMatchInlineSnapshot(`"/"`);
expect(urlStateStorage.get(key)).toEqual(null);
});

it('should cancel url updates if synchronously returned to the same state', async () => {
const state1 = { test: 'test', ok: 1 };
const state2 = { test: 'test', ok: 2 };
const key = '_s';
const pr1 = urlStateStorage.set(key, state1);
await pr1;
const historyLength = history.length;
const pr2 = urlStateStorage.set(key, state2);
const pr3 = urlStateStorage.set(key, state1);
await Promise.all([pr2, pr3]);
expect(history.length).toBe(historyLength);
});

it('should notify about url changes', async () => {
expect(urlStateStorage.change$).toBeDefined();
const key = '_s';
const destroy$ = new Subject();
const result = urlStateStorage.change$!(key).pipe(takeUntil(destroy$), toArray()).toPromise();

history.push(`/?${key}=(ok:1,test:test)`);
history.push(`/?query=test&${key}=(ok:2,test:test)&some=test`);
history.push(`/?query=test&some=test`);

destroy$.next();
destroy$.complete();

expect(await result).toEqual([{ test: 'test', ok: 1 }, { test: 'test', ok: 2 }, null]);
});

it("shouldn't throw in case of parsing error", async () => {
const key = '_s';
history.replace(`/?${key}=(ok:2,test:`); // malformed rison
expect(() => urlStateStorage.get(key)).not.toThrow();
expect(urlStateStorage.get(key)).toBeNull();
});

it('should notify about errors', () => {
const cb = jest.fn();
urlStateStorage = createKbnUrlStateStorage({
useHash: false,
useHashQuery: false,
history,
onGetError: cb,
});
const key = '_s';
history.replace(`/?${key}=(ok:2,test:`); // malformed rison
expect(() => urlStateStorage.get(key)).not.toThrow();
expect(cb).toBeCalledWith(expect.any(Error));
});

describe('withNotifyOnErrors integration', () => {
test('toast is shown', () => {
const toasts = coreMock.createStart().notifications.toasts;
urlStateStorage = createKbnUrlStateStorage({
useHash: true,
useHashQuery: false,
history,
...withNotifyOnErrors(toasts),
});
const key = '_s';
history.replace(`/?${key}=(ok:2,test:`); // malformed rison
expect(() => urlStateStorage.get(key)).not.toThrow();
expect(toasts.addError).toBeCalled();
});
});
});

describe('ScopedHistory integration', () => {
let urlStateStorage: IKbnUrlStateStorage;
let history: ScopedHistory;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -58,16 +58,19 @@ export interface IKbnUrlStateStorage extends IStateStorage {
export const createKbnUrlStateStorage = (
{
useHash = false,
useHashQuery = true,
history,
onGetError,
onSetError,
}: {
useHash: boolean;
useHashQuery?: boolean;
history?: History;
onGetError?: (error: Error) => void;
onSetError?: (error: Error) => void;
} = {
useHash: false,
useHashQuery: true,
}
): IKbnUrlStateStorage => {
const url = createKbnUrlControls(history);
Expand All @@ -80,7 +83,12 @@ export const createKbnUrlStateStorage = (
// syncState() utils doesn't wait for this promise
return url.updateAsync((currentUrl) => {
try {
return setStateToKbnUrl(key, state, { useHash }, currentUrl);
return setStateToKbnUrl(
key,
state,
{ useHash, storeInHashQuery: useHashQuery },
currentUrl
);
} catch (error) {
if (onSetError) onSetError(error);
}
Expand All @@ -90,7 +98,7 @@ export const createKbnUrlStateStorage = (
// if there is a pending url update, then state will be extracted from that pending url,
// otherwise current url will be used to retrieve state from
try {
return getStateFromKbnUrl(key, url.getPendingUrl());
return getStateFromKbnUrl(key, url.getPendingUrl(), { getFromHashQuery: useHashQuery });
} catch (e) {
if (onGetError) onGetError(e);
return null;
Expand All @@ -106,7 +114,7 @@ export const createKbnUrlStateStorage = (
unlisten();
};
}).pipe(
map(() => getStateFromKbnUrl<State>(key)),
map(() => getStateFromKbnUrl<State>(key, undefined, { getFromHashQuery: useHashQuery })),
catchError((error) => {
if (onGetError) onGetError(error);
return of(null);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -56,7 +56,7 @@ export const AgentLogs: React.FunctionComponent<Pick<AgentLogsProps, 'agent' | '
const [isSyncReady, setIsSyncReady] = useState<boolean>(false);

useEffect(() => {
const stateStorage = createKbnUrlStateStorage();
const stateStorage = createKbnUrlStateStorage({ useHashQuery: false, useHash: false });
const { start, stop } = syncState({
storageKey: STATE_STORAGE_KEY,
stateContainer: stateContainer as INullableBaseStateContainer<AgentLogsState>,
Expand Down