Skip to content

Commit

Permalink
feat: add onStop option to watch
Browse files Browse the repository at this point in the history
  • Loading branch information
hlysine committed May 31, 2023
1 parent 098172b commit 8ad1d99
Show file tree
Hide file tree
Showing 2 changed files with 35 additions and 4 deletions.
23 changes: 23 additions & 0 deletions src/__tests__/core.test.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -504,6 +504,29 @@ describe('watch', () => {

expect(effectFn).toBeCalledTimes(3);
});
it('calls onStop function', () => {
const counter = ref(1);
const effectFn = jest.fn();
const cleanupFn = jest.fn();
const stopFn = jest.fn();

const runner = watch(
counter,
() => {
effectFn(counter.value);
return cleanupFn;
},
{ onStop: stopFn, immediate: true }
);

expect(stopFn).toBeCalledTimes(0);
expect(cleanupFn).toBeCalledTimes(0);

runner();

expect(stopFn).toBeCalledTimes(1);
expect(cleanupFn).toBeCalledTimes(1);
});
it('cleans up properly', () => {
const counter = ref(1);
const effectFn = jest.fn();
Expand Down
16 changes: 12 additions & 4 deletions src/core.ts
Original file line number Diff line number Diff line change
Expand Up @@ -361,6 +361,7 @@ export type WatchCallback<V = any, OV = any> = (
export interface WatchOptions<Immediate = boolean> extends DebuggerOptions {
immediate?: Immediate;
deep?: boolean;
onStop?: () => void;
}

export type WatchStopHandle = () => void;
Expand Down Expand Up @@ -432,6 +433,7 @@ export const watch: WatchOverloads = <
const immediate = options?.immediate ?? false;
const onTrack = options?.onTrack ?? undefined;
const onTrigger = options?.onTrigger ?? undefined;
const onStop = options?.onStop ?? undefined;

let getter: () => any;
let isMultiSource = false;
Expand Down Expand Up @@ -498,6 +500,7 @@ export const watch: WatchOverloads = <
allowRecurse: true,
onTrack,
onTrigger,
onStop,
});
if (immediate) {
job();
Expand All @@ -514,12 +517,17 @@ export const watch: WatchOverloads = <
return () => effect.effect.stop();
};

export interface UseWatchOptions<Immediate = boolean> extends DebuggerOptions {
immediate?: Immediate;
deep?: boolean;
}

interface UseWatchOverloads {
// overload: array of multiple sources + cb
<T extends MultiWatchSources, Immediate extends Readonly<boolean> = false>(
sources: [...T],
cb: WatchCallback<MapSources<T, false>, MapSources<T, Immediate>>,
options?: WatchOptions<Immediate>
options?: UseWatchOptions<Immediate>
): void;
// overload: multiple sources w/ `as const`
// watch([foo, bar] as const, () => {})
Expand All @@ -530,19 +538,19 @@ interface UseWatchOverloads {
>(
source: T,
cb: WatchCallback<MapSources<T, false>, MapSources<T, Immediate>>,
options?: WatchOptions<Immediate>
options?: UseWatchOptions<Immediate>
): void;
// overload: single source + cb
<T, Immediate extends Readonly<boolean> = false>(
source: WatchSource<T>,
cb: WatchCallback<T, Immediate extends true ? T | undefined : T>,
options?: WatchOptions<Immediate>
options?: UseWatchOptions<Immediate>
): void;
// overload: watching reactive object w/ cb
<T extends object, Immediate extends Readonly<boolean> = false>(
source: T,
cb: WatchCallback<T, Immediate extends true ? T | undefined : T>,
options?: WatchOptions<Immediate>
options?: UseWatchOptions<Immediate>
): void;
}

Expand Down

0 comments on commit 8ad1d99

Please sign in to comment.