From 81c3281899e2fe1f702e8078f885e847e012efb1 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Fernando=20Fern=C3=A1ndez?= Date: Tue, 13 May 2025 12:03:39 +0000 Subject: [PATCH 1/3] chore(computedEager): mark for deprecation --- packages/shared/computedEager/index.ts | 1 + 1 file changed, 1 insertion(+) diff --git a/packages/shared/computedEager/index.ts b/packages/shared/computedEager/index.ts index 597904870ba..275e6f50b60 100644 --- a/packages/shared/computedEager/index.ts +++ b/packages/shared/computedEager/index.ts @@ -14,6 +14,7 @@ export type ComputedEagerReturn = Readonly> * computed, effect, watch, watchEffect, render dependencies will not be triggered. * refer: https://github.com/vuejs/core/pull/5912 * + * @deprecated * @param fn effect function * @param options WatchOptionsBase * @returns readonly shallowRef From abd4369043c92ada909498bc097c2b5a939c3d7e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Fernando=20Fern=C3=A1ndez?= Date: Tue, 13 May 2025 16:05:06 +0000 Subject: [PATCH 2/3] chore(computedEager): alias to computed --- packages/shared/computedEager/index.test.ts | 101 -------------------- packages/shared/computedEager/index.ts | 17 +--- 2 files changed, 4 insertions(+), 114 deletions(-) delete mode 100644 packages/shared/computedEager/index.test.ts diff --git a/packages/shared/computedEager/index.test.ts b/packages/shared/computedEager/index.test.ts deleted file mode 100644 index a27a39cbcd5..00000000000 --- a/packages/shared/computedEager/index.test.ts +++ /dev/null @@ -1,101 +0,0 @@ -import { describe, expect, it, vi } from 'vitest' -import { computed, shallowRef, watch } from 'vue' -import { nextTwoTick } from '../../.test' -import { computedEager } from './index' - -describe('computedEager', () => { - it('should be defined', () => { - expect(computedEager).toBeDefined() - }) - - it('should work', async () => { - const foo = shallowRef(0) - - const plusOneComputed = computed(() => { - return foo.value + 1 - }) - const plusOneEagerComputed = computedEager(() => { - return foo.value + 1 - }) - - const plusOneComputedSpy = vi.fn() - const plusOneComputedRefSpy = vi.fn() - watch(() => plusOneComputed.value, plusOneComputedSpy) - watch(() => plusOneEagerComputed.value, plusOneComputedRefSpy) - - expect(plusOneComputed.value).toBe(1) - expect(plusOneEagerComputed.value).toBe(1) - expect(plusOneComputedSpy).toBeCalledTimes(0) - expect(plusOneComputedRefSpy).toBeCalledTimes(0) - - foo.value++ - await nextTwoTick() - - expect(plusOneComputed.value).toBe(2) - expect(plusOneEagerComputed.value).toBe(2) - expect(plusOneComputedSpy).toBeCalledTimes(1) - expect(plusOneComputedRefSpy).toBeCalledTimes(1) - - foo.value-- - await nextTwoTick() - - expect(plusOneComputed.value).toBe(1) - expect(plusOneEagerComputed.value).toBe(1) - expect(plusOneComputedSpy).toBeCalledTimes(2) - expect(plusOneComputedRefSpy).toBeCalledTimes(2) - }) - - it('should not trigger collect change if result is not changed', async () => { - const foo = shallowRef(1) - - const isOddComputed = computed(() => { - return foo.value % 2 === 0 - }) - const isOddEagerComputed = computedEager(() => { - return foo.value % 2 === 0 - }) - - const isOddComputedSpy = vi.fn() - const isOddComputedRefSpy = vi.fn() - const isOddComputedCollectSpy = vi.fn() - const isOddComputedRefCollectSpy = vi.fn() - - watch(() => { - isOddComputedCollectSpy() - return isOddComputed.value - }, isOddComputedSpy) - watch(() => { - isOddComputedRefCollectSpy() - return isOddEagerComputed.value - }, isOddComputedRefSpy) - - expect(isOddComputed.value).toBe(false) - expect(isOddEagerComputed.value).toBe(false) - expect(isOddComputedSpy).toBeCalledTimes(0) - expect(isOddComputedRefSpy).toBeCalledTimes(0) - expect(isOddComputedCollectSpy).toBeCalledTimes(1) - expect(isOddComputedRefCollectSpy).toBeCalledTimes(1) - - foo.value++ - await nextTwoTick() - - expect(isOddComputed.value).toBe(true) - expect(isOddEagerComputed.value).toBe(true) - expect(isOddComputedSpy).toBeCalledTimes(1) - expect(isOddComputedRefSpy).toBeCalledTimes(1) - expect(isOddComputedCollectSpy).toBeCalledTimes(2) - expect(isOddComputedRefCollectSpy).toBeCalledTimes(2) - - foo.value += 2 - await nextTwoTick() - - expect(isOddComputed.value).toBe(true) - expect(isOddEagerComputed.value).toBe(true) - expect(isOddComputedSpy).toBeCalledTimes(1) - expect(isOddComputedRefSpy).toBeCalledTimes(1) - // Since Vue 3.4, computed will not trigger collect change if result is not changed - // refer: https://github.com/vuejs/core/pull/5912 - expect(isOddComputedCollectSpy).toBeCalledTimes(2) - expect(isOddComputedRefCollectSpy).toBeCalledTimes(2) - }) -}) diff --git a/packages/shared/computedEager/index.ts b/packages/shared/computedEager/index.ts index 275e6f50b60..f1d1c063385 100644 --- a/packages/shared/computedEager/index.ts +++ b/packages/shared/computedEager/index.ts @@ -2,7 +2,7 @@ // by @linusborg https://github.com/LinusBorg import type { ShallowRef, WatchOptionsBase } from 'vue' -import { readonly, shallowRef, watchEffect } from 'vue' +import { computed } from 'vue' export type ComputedEagerOptions = WatchOptionsBase @@ -14,22 +14,13 @@ export type ComputedEagerReturn = Readonly> * computed, effect, watch, watchEffect, render dependencies will not be triggered. * refer: https://github.com/vuejs/core/pull/5912 * - * @deprecated + * @deprecated - This composable will be removed in the next major version of VueUse * @param fn effect function * @param options WatchOptionsBase * @returns readonly shallowRef */ -export function computedEager(fn: () => T, options?: ComputedEagerOptions): ComputedEagerReturn { - const result = shallowRef() - - watchEffect(() => { - result.value = fn() - }, { - ...options, - flush: options?.flush ?? 'sync', - }) - - return readonly(result) +export function computedEager(fn: () => T, _?: ComputedEagerOptions): ComputedEagerReturn { + return computed(fn) } // alias From 47a5769f77f99c7e66945303d73db4b2a0887806 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Fernando=20Fern=C3=A1ndez?= Date: Wed, 14 May 2025 07:35:38 +0000 Subject: [PATCH 3/3] chore(computedEager): reintroduce tests, clarify deprecation message --- packages/shared/computedEager/index.test.ts | 101 ++++++++++++++++++++ packages/shared/computedEager/index.ts | 4 +- 2 files changed, 103 insertions(+), 2 deletions(-) create mode 100644 packages/shared/computedEager/index.test.ts diff --git a/packages/shared/computedEager/index.test.ts b/packages/shared/computedEager/index.test.ts new file mode 100644 index 00000000000..a27a39cbcd5 --- /dev/null +++ b/packages/shared/computedEager/index.test.ts @@ -0,0 +1,101 @@ +import { describe, expect, it, vi } from 'vitest' +import { computed, shallowRef, watch } from 'vue' +import { nextTwoTick } from '../../.test' +import { computedEager } from './index' + +describe('computedEager', () => { + it('should be defined', () => { + expect(computedEager).toBeDefined() + }) + + it('should work', async () => { + const foo = shallowRef(0) + + const plusOneComputed = computed(() => { + return foo.value + 1 + }) + const plusOneEagerComputed = computedEager(() => { + return foo.value + 1 + }) + + const plusOneComputedSpy = vi.fn() + const plusOneComputedRefSpy = vi.fn() + watch(() => plusOneComputed.value, plusOneComputedSpy) + watch(() => plusOneEagerComputed.value, plusOneComputedRefSpy) + + expect(plusOneComputed.value).toBe(1) + expect(plusOneEagerComputed.value).toBe(1) + expect(plusOneComputedSpy).toBeCalledTimes(0) + expect(plusOneComputedRefSpy).toBeCalledTimes(0) + + foo.value++ + await nextTwoTick() + + expect(plusOneComputed.value).toBe(2) + expect(plusOneEagerComputed.value).toBe(2) + expect(plusOneComputedSpy).toBeCalledTimes(1) + expect(plusOneComputedRefSpy).toBeCalledTimes(1) + + foo.value-- + await nextTwoTick() + + expect(plusOneComputed.value).toBe(1) + expect(plusOneEagerComputed.value).toBe(1) + expect(plusOneComputedSpy).toBeCalledTimes(2) + expect(plusOneComputedRefSpy).toBeCalledTimes(2) + }) + + it('should not trigger collect change if result is not changed', async () => { + const foo = shallowRef(1) + + const isOddComputed = computed(() => { + return foo.value % 2 === 0 + }) + const isOddEagerComputed = computedEager(() => { + return foo.value % 2 === 0 + }) + + const isOddComputedSpy = vi.fn() + const isOddComputedRefSpy = vi.fn() + const isOddComputedCollectSpy = vi.fn() + const isOddComputedRefCollectSpy = vi.fn() + + watch(() => { + isOddComputedCollectSpy() + return isOddComputed.value + }, isOddComputedSpy) + watch(() => { + isOddComputedRefCollectSpy() + return isOddEagerComputed.value + }, isOddComputedRefSpy) + + expect(isOddComputed.value).toBe(false) + expect(isOddEagerComputed.value).toBe(false) + expect(isOddComputedSpy).toBeCalledTimes(0) + expect(isOddComputedRefSpy).toBeCalledTimes(0) + expect(isOddComputedCollectSpy).toBeCalledTimes(1) + expect(isOddComputedRefCollectSpy).toBeCalledTimes(1) + + foo.value++ + await nextTwoTick() + + expect(isOddComputed.value).toBe(true) + expect(isOddEagerComputed.value).toBe(true) + expect(isOddComputedSpy).toBeCalledTimes(1) + expect(isOddComputedRefSpy).toBeCalledTimes(1) + expect(isOddComputedCollectSpy).toBeCalledTimes(2) + expect(isOddComputedRefCollectSpy).toBeCalledTimes(2) + + foo.value += 2 + await nextTwoTick() + + expect(isOddComputed.value).toBe(true) + expect(isOddEagerComputed.value).toBe(true) + expect(isOddComputedSpy).toBeCalledTimes(1) + expect(isOddComputedRefSpy).toBeCalledTimes(1) + // Since Vue 3.4, computed will not trigger collect change if result is not changed + // refer: https://github.com/vuejs/core/pull/5912 + expect(isOddComputedCollectSpy).toBeCalledTimes(2) + expect(isOddComputedRefCollectSpy).toBeCalledTimes(2) + }) +}) diff --git a/packages/shared/computedEager/index.ts b/packages/shared/computedEager/index.ts index f1d1c063385..4002fd60b42 100644 --- a/packages/shared/computedEager/index.ts +++ b/packages/shared/computedEager/index.ts @@ -14,9 +14,9 @@ export type ComputedEagerReturn = Readonly> * computed, effect, watch, watchEffect, render dependencies will not be triggered. * refer: https://github.com/vuejs/core/pull/5912 * - * @deprecated - This composable will be removed in the next major version of VueUse + * @deprecated - Replace with Vue's own computed function * @param fn effect function - * @param options WatchOptionsBase + * @param _ WatchOptionsBase * @returns readonly shallowRef */ export function computedEager(fn: () => T, _?: ComputedEagerOptions): ComputedEagerReturn {