diff --git a/packages/runtime-core/__tests__/apiOptions.spec.ts b/packages/runtime-core/__tests__/apiOptions.spec.ts index 00ecb6e4c..6b6014c05 100644 --- a/packages/runtime-core/__tests__/apiOptions.spec.ts +++ b/packages/runtime-core/__tests__/apiOptions.spec.ts @@ -113,6 +113,7 @@ describe('api: options', () => { const spyB = jest.fn(returnThis) const spyC = jest.fn(returnThis) const spyD = jest.fn(returnThis) + const spyE = jest.fn(returnThis) let ctx: any const Comp = { @@ -123,7 +124,10 @@ describe('api: options', () => { baz: { qux: 3 }, - qux: 4 + qux: 4, + dot: { + path: 5 + } } }, watch: { @@ -137,7 +141,8 @@ describe('api: options', () => { }, qux: { handler: 'onQuxChange' - } + }, + 'dot.path': spyE }, methods: { onFooChange: spyA, @@ -175,6 +180,11 @@ describe('api: options', () => { await nextTick() expect(spyD).toHaveBeenCalledTimes(1) assertCall(spyD, 0, [5, 4]) + + ctx.dot.path++ + await nextTick() + expect(spyE).toHaveBeenCalledTimes(1) + assertCall(spyE, 0, [6, 5]) }) test('watch array', async () => { diff --git a/packages/runtime-core/src/componentOptions.ts b/packages/runtime-core/src/componentOptions.ts index ff499d36c..0ff710c36 100644 --- a/packages/runtime-core/src/componentOptions.ts +++ b/packages/runtime-core/src/componentOptions.ts @@ -816,7 +816,9 @@ function createWatcher( publicThis: ComponentPublicInstance, key: string ) { - const getter = () => (publicThis as any)[key] + const getter = key.includes('.') + ? createPathGetter(publicThis, key) + : () => (publicThis as any)[key] if (isString(raw)) { const handler = ctx[raw] if (isFunction(handler)) { @@ -840,7 +842,18 @@ function createWatcher( } } } else if (__DEV__) { - warn(`Invalid watch option: "${key}"`) + warn(`Invalid watch option: "${key}"`, raw) + } +} + +function createPathGetter(ctx: any, path: string) { + const segments = path.split('.') + return () => { + let cur = ctx + for (let i = 0; i < segments.length && cur; i++) { + cur = cur[segments[i]] + } + return cur } }