From 77f0a731610e7f3f21873cf26165fde125cda315 Mon Sep 17 00:00:00 2001 From: baiwusanyu-c <740132583@qq.com> Date: Mon, 24 Jul 2023 15:59:19 +0800 Subject: [PATCH 1/7] feat(custom-element): Support css `:host` selector --- packages/runtime-core/src/component.ts | 6 +++++ packages/runtime-dom/src/apiCustomElement.ts | 9 +++++++ .../runtime-dom/src/helpers/useCssVars.ts | 27 ++++++++++++------- 3 files changed, 33 insertions(+), 9 deletions(-) diff --git a/packages/runtime-core/src/component.ts b/packages/runtime-core/src/component.ts index 57a53a39b76..634e2f8642a 100644 --- a/packages/runtime-core/src/component.ts +++ b/packages/runtime-core/src/component.ts @@ -318,6 +318,12 @@ export interface ComponentInternalInstance { * @internal */ ceReload?: (newStyles?: string[]) => void + /** + * Set the css variables related to the :host selector + * to the style of the custom element + * @internal + */ + ceSetCssVars?: (vars: Record) => void // the rest are only for stateful components --------------------------------- diff --git a/packages/runtime-dom/src/apiCustomElement.ts b/packages/runtime-dom/src/apiCustomElement.ts index 5662b0b535b..d64b1f87199 100644 --- a/packages/runtime-dom/src/apiCustomElement.ts +++ b/packages/runtime-dom/src/apiCustomElement.ts @@ -365,6 +365,9 @@ export class VueElement extends BaseClass { vnode.ce = instance => { this._instance = instance instance.isCE = true + instance.ceSetCssVars = (cssvars: Record) => { + this._setCssVars(cssvars) + } // HMR if (__DEV__) { instance.ceReload = newStyles => { @@ -414,6 +417,12 @@ export class VueElement extends BaseClass { return vnode } + private _setCssVars(vars: Record) { + for (const key in vars) { + this.style.setProperty(`--${key}`, vars[key]) + } + } + private _applyStyles(styles: string[] | undefined) { if (styles) { styles.forEach(css => { diff --git a/packages/runtime-dom/src/helpers/useCssVars.ts b/packages/runtime-dom/src/helpers/useCssVars.ts index e0a95c9ca99..ac4138fe04e 100644 --- a/packages/runtime-dom/src/helpers/useCssVars.ts +++ b/packages/runtime-dom/src/helpers/useCssVars.ts @@ -6,7 +6,8 @@ import { Static, watchPostEffect, onMounted, - onUnmounted + onUnmounted, + ComponentInternalInstance } from '@vue/runtime-core' import { ShapeFlags } from '@vue/shared' @@ -28,12 +29,12 @@ export function useCssVars(getter: (ctx: any) => Record) { const updateTeleports = (instance.ut = (vars = getter(instance.proxy)) => { Array.from( document.querySelectorAll(`[data-v-owner="${instance.uid}"]`) - ).forEach(node => setVarsOnNode(node, vars)) + ).forEach(node => setVarsOnNode(node, vars, instance)) }) const setVars = () => { const vars = getter(instance.proxy) - setVarsOnVNode(instance.subTree, vars) + setVarsOnVNode(instance.subTree, vars, instance) updateTeleports(vars) } @@ -46,13 +47,17 @@ export function useCssVars(getter: (ctx: any) => Record) { }) } -function setVarsOnVNode(vnode: VNode, vars: Record) { +function setVarsOnVNode( + vnode: VNode, + vars: Record, + instance: ComponentInternalInstance +) { if (__FEATURE_SUSPENSE__ && vnode.shapeFlag & ShapeFlags.SUSPENSE) { const suspense = vnode.suspense! vnode = suspense.activeBranch! if (suspense.pendingBranch && !suspense.isHydrating) { suspense.effects.push(() => { - setVarsOnVNode(suspense.activeBranch!, vars) + setVarsOnVNode(suspense.activeBranch!, vars, instance) }) } } @@ -63,24 +68,28 @@ function setVarsOnVNode(vnode: VNode, vars: Record) { } if (vnode.shapeFlag & ShapeFlags.ELEMENT && vnode.el) { - setVarsOnNode(vnode.el as Node, vars) + setVarsOnNode(vnode.el as Node, vars, instance) } else if (vnode.type === Fragment) { - ;(vnode.children as VNode[]).forEach(c => setVarsOnVNode(c, vars)) + ;(vnode.children as VNode[]).forEach(c => setVarsOnVNode(c, vars, instance)) } else if (vnode.type === Static) { let { el, anchor } = vnode while (el) { - setVarsOnNode(el as Node, vars) + setVarsOnNode(el as Node, vars, instance) if (el === anchor) break el = el.nextSibling } } } -function setVarsOnNode(el: Node, vars: Record) { +function setVarsOnNode(el: Node, vars: Record, instance:ComponentInternalInstance | null) { if (el.nodeType === 1) { const style = (el as HTMLElement).style for (const key in vars) { style.setProperty(`--${key}`, vars[key]) } + + if(instance && instance.isCE ) { + instance.ceSetCssVars && instance.ceSetCssVars(vars) + } } } From 2f9cf3e87d1c0fe253c2df974d6d0e3134c731e3 Mon Sep 17 00:00:00 2001 From: baiwusanyu-c <740132583@qq.com> Date: Tue, 25 Jul 2023 09:15:16 +0800 Subject: [PATCH 2/7] feat(custom-element): added unit test --- .../__tests__/helpers/useCssVars.spec.ts | 23 ++++++++++++++++++- 1 file changed, 22 insertions(+), 1 deletion(-) diff --git a/packages/runtime-dom/__tests__/helpers/useCssVars.spec.ts b/packages/runtime-dom/__tests__/helpers/useCssVars.spec.ts index 7d24ec0f434..614b1863f56 100644 --- a/packages/runtime-dom/__tests__/helpers/useCssVars.spec.ts +++ b/packages/runtime-dom/__tests__/helpers/useCssVars.spec.ts @@ -9,7 +9,8 @@ import { ComponentOptions, Suspense, Teleport, - FunctionalComponent + FunctionalComponent, + defineCustomElement } from '@vue/runtime-dom' describe('useCssVars', () => { @@ -275,4 +276,24 @@ describe('useCssVars', () => { expect((c as HTMLElement).style.getPropertyValue(`--color`)).toBe('red') } }) + + // #8826 + test('with custom element', async () => { + const state = reactive({ color: 'red' }) + const container = document.createElement('div') + const App = defineCustomElement({ + styles: [`div { color: red; }`], + setup() { + useCssVars(() => state) + return () => { + return h('div', 'hello') + } + } + }) + customElements.define('css-vars-ce', App) + container.innerHTML = `` + document.body.appendChild(container) + await nextTick() + expect(container.innerHTML).toBe(``) + }) }) From 9e8f70d33acbd27b854cb92aa4b5c03c753a83b3 Mon Sep 17 00:00:00 2001 From: baiwusanyu-c <740132583@qq.com> Date: Tue, 25 Jul 2023 09:48:53 +0800 Subject: [PATCH 3/7] feat(custom-element): updated code --- packages/runtime-dom/src/helpers/useCssVars.ts | 18 +++++++++++------- 1 file changed, 11 insertions(+), 7 deletions(-) diff --git a/packages/runtime-dom/src/helpers/useCssVars.ts b/packages/runtime-dom/src/helpers/useCssVars.ts index ac4138fe04e..bd20cf79621 100644 --- a/packages/runtime-dom/src/helpers/useCssVars.ts +++ b/packages/runtime-dom/src/helpers/useCssVars.ts @@ -81,15 +81,19 @@ function setVarsOnVNode( } } -function setVarsOnNode(el: Node, vars: Record, instance:ComponentInternalInstance | null) { +function setVarsOnNode( + el: Node, + vars: Record, + instance: ComponentInternalInstance | null +) { if (el.nodeType === 1) { - const style = (el as HTMLElement).style - for (const key in vars) { - style.setProperty(`--${key}`, vars[key]) - } - - if(instance && instance.isCE ) { + if (instance && instance.isCE) { instance.ceSetCssVars && instance.ceSetCssVars(vars) + } else { + const style = (el as HTMLElement).style + for (const key in vars) { + style.setProperty(`--${key}`, vars[key]) + } } } } From fa80f9bb98118e511fee2339e88ad9f4f85274f3 Mon Sep 17 00:00:00 2001 From: baiwusanyu-c <740132583@qq.com> Date: Wed, 3 Jan 2024 10:07:14 +0800 Subject: [PATCH 4/7] Merge remote-tracking branch 'origin/main' into bwsy/fix/CEHostSelector # Conflicts: # packages/runtime-dom/__tests__/helpers/useCssVars.spec.ts # packages/runtime-dom/src/helpers/useCssVars.ts --- .eslintignore | 4 + .eslintrc.cjs | 92 +- .git-blame-ignore-revs | 2 + .github/contributing.md | 6 +- .github/renovate.json5 | 20 +- .github/workflows/autofix.yml | 2 +- .github/workflows/ci.yml | 53 +- .prettierignore | 3 + .prettierrc | 10 +- .vscode/launch.json | 2 +- CHANGELOG.md | 642 +- changelogs/CHANGELOG-3.3.md | 598 ++ package.json | 41 +- .../__snapshots__/parse.spec.ts.snap | 5747 +++++------------ .../compiler-core/__tests__/codegen.spec.ts | 293 +- .../compiler-core/__tests__/compile.spec.ts | 108 +- .../compiler-core/__tests__/parse.spec.ts | 2361 +++---- .../compiler-core/__tests__/scopeId.spec.ts | 22 +- packages/compiler-core/__tests__/testUtils.ts | 31 +- .../compiler-core/__tests__/transform.spec.ts | 118 +- .../transformExpressions.spec.ts.snap | 6 +- .../__tests__/transforms/hoistStatic.spec.ts | 258 +- .../transforms/noopDirectiveTransform.spec.ts | 10 +- .../transforms/transformElement.spec.ts | 588 +- .../transforms/transformExpressions.spec.ts | 263 +- .../transforms/transformSlotOutlet.spec.ts | 187 +- .../transforms/transformText.spec.ts | 88 +- .../__tests__/transforms/vBind.spec.ts | 260 +- .../__tests__/transforms/vFor.spec.ts | 332 +- .../__tests__/transforms/vIf.spec.ts | 251 +- .../__tests__/transforms/vMemo.spec.ts | 18 +- .../__tests__/transforms/vModel.spec.ts | 267 +- .../__tests__/transforms/vOn.spec.ts | 348 +- .../__tests__/transforms/vOnce.spec.ts | 46 +- .../__tests__/transforms/vSlot.spec.ts | 466 +- .../compiler-core/__tests__/utils.spec.ts | 37 +- packages/compiler-core/package.json | 7 +- packages/compiler-core/src/ast.ts | 162 +- packages/compiler-core/src/babelUtils.ts | 78 +- packages/compiler-core/src/codegen.ts | 285 +- .../compiler-core/src/compat/compatConfig.ts | 50 +- .../src/compat/transformFilter.ts | 16 +- packages/compiler-core/src/compile.ts | 57 +- packages/compiler-core/src/errors.ts | 22 +- packages/compiler-core/src/index.ts | 17 +- packages/compiler-core/src/options.ts | 72 +- packages/compiler-core/src/parse.ts | 1189 ---- packages/compiler-core/src/parser.ts | 1071 +++ packages/compiler-core/src/runtimeHelpers.ts | 4 +- packages/compiler-core/src/tokenizer.ts | 1176 ++++ packages/compiler-core/src/transform.ts | 80 +- .../src/transforms/hoistStatic.ts | 52 +- .../src/transforms/noopDirectiveTransform.ts | 2 +- .../src/transforms/transformElement.ts | 177 +- .../src/transforms/transformExpression.ts | 107 +- .../src/transforms/transformSlotOutlet.ts | 28 +- .../src/transforms/transformText.ts | 24 +- .../compiler-core/src/transforms/vBind.ts | 25 +- packages/compiler-core/src/transforms/vFor.ts | 263 +- packages/compiler-core/src/transforms/vIf.ts | 93 +- .../compiler-core/src/transforms/vMemo.ts | 12 +- .../compiler-core/src/transforms/vModel.ts | 44 +- packages/compiler-core/src/transforms/vOn.ts | 34 +- .../compiler-core/src/transforms/vOnce.ts | 4 +- .../compiler-core/src/transforms/vSlot.ts | 132 +- packages/compiler-core/src/utils.ts | 165 +- .../compiler-core/src/validateExpression.ts | 16 +- .../__tests__/decoderHtmlBrowser.spec.ts | 8 +- packages/compiler-dom/__tests__/parse.spec.ts | 215 +- .../__tests__/transforms/Transition.spec.ts | 28 +- .../transforms/ignoreSideEffectTags.spec.ts | 6 +- .../transforms/stringifyStatic.spec.ts | 230 +- .../transforms/transformStyle.spec.ts | 34 +- .../__tests__/transforms/vHtml.spec.ts | 26 +- .../__tests__/transforms/vModel.spec.ts | 36 +- .../__tests__/transforms/vOn.spec.ts | 156 +- .../__tests__/transforms/vShow.spec.ts | 12 +- .../__tests__/transforms/vText.spec.ts | 30 +- packages/compiler-dom/package.json | 2 +- packages/compiler-dom/src/decodeHtml.ts | 133 - packages/compiler-dom/src/errors.ts | 20 +- packages/compiler-dom/src/index.ts | 36 +- packages/compiler-dom/src/namedChars.json | 2233 ------- packages/compiler-dom/src/parserOptions.ts | 71 +- packages/compiler-dom/src/runtimeHelpers.ts | 2 +- .../compiler-dom/src/transforms/Transition.ts | 21 +- .../src/transforms/ignoreSideEffectTags.ts | 6 +- .../src/transforms/stringifyStatic.ts | 66 +- .../src/transforms/transformStyle.ts | 14 +- packages/compiler-dom/src/transforms/vHtml.ts | 16 +- .../compiler-dom/src/transforms/vModel.ts | 32 +- packages/compiler-dom/src/transforms/vOn.ts | 42 +- packages/compiler-dom/src/transforms/vShow.ts | 8 +- packages/compiler-dom/src/transforms/vText.ts | 22 +- .../__snapshots__/compileScript.spec.ts.snap | 244 +- .../compileTemplate.spec.ts.snap | 19 - .../__tests__/compileScript.spec.ts | 409 +- .../__snapshots__/defineEmits.spec.ts.snap | 3 +- .../__snapshots__/defineExpose.spec.ts.snap | 3 +- .../__snapshots__/defineModel.spec.ts.snap | 91 +- .../__snapshots__/defineOptions.spec.ts.snap | 6 +- .../definePropsDestructure.spec.ts.snap | 15 +- .../__snapshots__/hoistStatic.spec.ts.snap | 15 +- .../importUsageCheck.spec.ts.snap | 215 + .../reactivityTransform.spec.ts.snap | 113 - .../compileScript/defineEmits.spec.ts | 10 +- .../compileScript/defineExpose.spec.ts | 2 +- .../compileScript/defineModel.spec.ts | 99 +- .../compileScript/defineOptions.spec.ts | 46 +- .../compileScript/defineProps.spec.ts | 88 +- .../definePropsDestructure.spec.ts | 96 +- .../compileScript/defineSlots.spec.ts | 2 +- .../compileScript/hoistStatic.spec.ts | 28 +- .../compileScript/importUsageCheck.spec.ts | 235 + .../compileScript/reactivityTransform.spec.ts | 193 - .../compileScript/resolveType.spec.ts | 341 +- .../__tests__/compileStyle.spec.ts | 58 +- .../__tests__/compileTemplate.spec.ts | 289 +- .../compiler-sfc/__tests__/cssVars.spec.ts | 64 +- packages/compiler-sfc/__tests__/parse.spec.ts | 196 +- .../__tests__/rewriteDefault.spec.ts | 79 +- .../templateTransformAssetUrl.spec.ts | 56 +- .../__tests__/templateTransformSrcset.spec.ts | 32 +- .../__tests__/templateUtils.spec.ts | 4 +- packages/compiler-sfc/__tests__/utils.ts | 20 +- packages/compiler-sfc/package.json | 9 +- packages/compiler-sfc/src/cache.ts | 2 +- packages/compiler-sfc/src/compileScript.ts | 226 +- packages/compiler-sfc/src/compileStyle.ts | 58 +- packages/compiler-sfc/src/compileTemplate.ts | 104 +- packages/compiler-sfc/src/index.ts | 42 +- packages/compiler-sfc/src/parse.ts | 211 +- packages/compiler-sfc/src/rewriteDefault.ts | 15 +- .../src/script/analyzeScriptBindings.ts | 8 +- packages/compiler-sfc/src/script/context.ts | 45 +- .../compiler-sfc/src/script/defineEmits.ts | 26 +- .../compiler-sfc/src/script/defineExpose.ts | 6 +- .../compiler-sfc/src/script/defineModel.ts | 96 +- .../compiler-sfc/src/script/defineOptions.ts | 17 +- .../compiler-sfc/src/script/defineProps.ts | 87 +- .../src/script/definePropsDestructure.ts | 45 +- .../compiler-sfc/src/script/defineSlots.ts | 8 +- .../src/script/importUsageCheck.ts | 150 +- .../compiler-sfc/src/script/normalScript.ts | 39 +- .../compiler-sfc/src/script/resolveType.ts | 277 +- .../compiler-sfc/src/script/topLevelAwait.ts | 14 +- packages/compiler-sfc/src/script/utils.ts | 22 +- packages/compiler-sfc/src/style/cssVars.ts | 36 +- .../compiler-sfc/src/style/pluginScoped.ts | 20 +- packages/compiler-sfc/src/style/pluginTrim.ts | 4 +- .../compiler-sfc/src/style/preprocessors.ts | 33 +- .../src/template/templateUtils.ts | 2 +- .../src/template/transformAssetUrl.ts | 42 +- .../src/template/transformSrcset.ts | 31 +- packages/compiler-sfc/src/warn.ts | 2 +- .../__tests__/ssrComponent.spec.ts | 8 +- .../compiler-ssr/__tests__/ssrElement.spec.ts | 30 +- .../__tests__/ssrInjectCssVars.spec.ts | 24 +- .../compiler-ssr/__tests__/ssrPortal.spec.ts | 2 +- .../compiler-ssr/__tests__/ssrScopeId.spec.ts | 28 +- .../__tests__/ssrSlotOutlet.spec.ts | 30 +- .../__tests__/ssrSuspense.spec.ts | 2 +- .../compiler-ssr/__tests__/ssrText.spec.ts | 14 +- .../__tests__/ssrTransitionGroup.spec.ts | 18 +- .../compiler-ssr/__tests__/ssrVFor.spec.ts | 12 +- .../compiler-ssr/__tests__/ssrVIf.spec.ts | 9 +- .../compiler-ssr/__tests__/ssrVModel.spec.ts | 32 +- .../compiler-ssr/__tests__/ssrVShow.spec.ts | 10 +- packages/compiler-ssr/__tests__/utils.ts | 2 +- packages/compiler-ssr/package.json | 2 +- packages/compiler-ssr/src/errors.ts | 18 +- packages/compiler-ssr/src/index.ts | 34 +- packages/compiler-ssr/src/runtimeHelpers.ts | 2 +- .../compiler-ssr/src/ssrCodegenTransform.ts | 64 +- .../src/transforms/ssrInjectCssVars.ts | 15 +- .../transforms/ssrInjectFallthroughAttrs.ts | 21 +- .../src/transforms/ssrTransformComponent.ts | 155 +- .../src/transforms/ssrTransformElement.ts | 152 +- .../src/transforms/ssrTransformSlotOutlet.ts | 32 +- .../src/transforms/ssrTransformSuspense.ts | 32 +- .../src/transforms/ssrTransformTeleport.ts | 30 +- .../src/transforms/ssrTransformTransition.ts | 15 +- .../transforms/ssrTransformTransitionGroup.ts | 29 +- .../compiler-ssr/src/transforms/ssrVFor.ts | 26 +- .../compiler-ssr/src/transforms/ssrVIf.ts | 32 +- .../compiler-ssr/src/transforms/ssrVModel.ts | 78 +- .../compiler-ssr/src/transforms/ssrVShow.ts | 22 +- packages/dts-built-test/src/index.ts | 2 +- packages/dts-test/appDirective.test-d.ts | 14 + packages/dts-test/appUse.test-d.ts | 20 +- packages/dts-test/built.test-d.ts | 2 +- packages/dts-test/compiler.test-d.ts | 12 +- packages/dts-test/component.test-d.ts | 140 +- .../dts-test/componentInstance.test-d.tsx | 139 + .../componentTypeExtensions.test-d.tsx | 8 +- packages/dts-test/defineComponent.test-d.tsx | 368 +- .../dts-test/defineCustomElement.test-d.ts | 30 +- packages/dts-test/extractProps.test-d.ts | 10 +- .../dts-test/functionalComponent.test-d.tsx | 12 +- packages/dts-test/h.test-d.ts | 75 +- packages/dts-test/inject.test-d.ts | 2 +- packages/dts-test/reactivity.test-d.ts | 17 +- packages/dts-test/reactivityMacros.test-d.ts | 110 - packages/dts-test/ref.test-d.ts | 100 +- packages/dts-test/setupHelpers.test-d.ts | 91 +- packages/dts-test/tsx.test-d.tsx | 20 +- packages/dts-test/watch.test-d.ts | 51 +- packages/global.d.ts | 15 +- packages/reactivity-transform/LICENSE | 21 - packages/reactivity-transform/README.md | 123 - .../reactivityTransform.spec.ts.snap | 292 - .../__tests__/reactivityTransform.spec.ts | 564 -- packages/reactivity-transform/package.json | 41 - .../reactivity-transform/src/babelPlugin.ts | 3 - packages/reactivity-transform/src/index.ts | 1 - .../src/reactivityTransform.ts | 794 --- .../__tests__/collections/Map.spec.ts | 6 +- .../__tests__/collections/Set.spec.ts | 5 +- .../__tests__/collections/WeakMap.spec.ts | 2 +- .../__tests__/collections/WeakSet.spec.ts | 2 +- .../collections/shallowReadonly.spec.ts | 22 +- .../reactivity/__tests__/computed.bench.ts | 4 +- .../reactivity/__tests__/computed.spec.ts | 201 +- .../__tests__/deferredComputed.spec.ts | 62 +- packages/reactivity/__tests__/effect.spec.ts | 155 +- .../reactivity/__tests__/effectScope.spec.ts | 12 +- packages/reactivity/__tests__/gc.spec.ts | 81 + .../reactivity/__tests__/reactive.spec.ts | 18 +- .../__tests__/reactiveArray.bench.ts | 2 +- .../__tests__/reactiveArray.spec.ts | 37 +- .../reactivity/__tests__/reactiveMap.bench.ts | 2 +- .../__tests__/reactiveObject.bench.ts | 2 +- .../reactivity/__tests__/readonly.spec.ts | 58 +- packages/reactivity/__tests__/ref.bench.ts | 2 +- packages/reactivity/__tests__/ref.spec.ts | 32 +- .../__tests__/shallowReactive.spec.ts | 16 +- .../__tests__/shallowReadonly.spec.ts | 26 +- packages/reactivity/package.json | 2 +- packages/reactivity/src/baseHandlers.ts | 45 +- packages/reactivity/src/collectionHandlers.ts | 63 +- packages/reactivity/src/computed.ts | 51 +- packages/reactivity/src/constants.ts | 30 + packages/reactivity/src/deferredComputed.ts | 92 +- packages/reactivity/src/dep.ts | 64 +- packages/reactivity/src/effect.ts | 406 +- packages/reactivity/src/effectScope.ts | 8 +- packages/reactivity/src/index.ts | 22 +- packages/reactivity/src/operations.ts | 15 - packages/reactivity/src/reactive.ts | 37 +- packages/reactivity/src/reactiveEffect.ts | 150 + packages/reactivity/src/ref.ts | 115 +- .../__tests__/apiAsyncComponent.spec.ts | 120 +- .../__tests__/apiCreateApp.spec.ts | 132 +- .../runtime-core/__tests__/apiExpose.spec.ts | 72 +- .../runtime-core/__tests__/apiInject.spec.ts | 93 +- .../__tests__/apiLifecycle.spec.ts | 84 +- .../runtime-core/__tests__/apiOptions.spec.ts | 506 +- .../__tests__/apiSetupContext.spec.ts | 54 +- .../__tests__/apiSetupHelpers.spec.ts | 452 +- .../runtime-core/__tests__/apiWatch.bench.ts | 2 +- .../runtime-core/__tests__/apiWatch.spec.ts | 291 +- .../__tests__/componentEmits.spec.ts | 114 +- .../__tests__/componentProps.spec.ts | 214 +- .../__tests__/componentPublicInstance.spec.ts | 93 +- .../__tests__/componentSlots.spec.ts | 64 +- .../components/BaseTransition.spec.ts | 138 +- .../__tests__/components/KeepAlive.spec.ts | 154 +- .../__tests__/components/Suspense.spec.ts | 481 +- .../__tests__/components/Teleport.spec.ts | 186 +- .../runtime-core/__tests__/directives.spec.ts | 71 +- .../__tests__/errorHandling.spec.ts | 104 +- packages/runtime-core/__tests__/h.spec.ts | 24 +- .../__tests__/helpers/createSlots.spec.ts | 14 +- .../__tests__/helpers/renderList.spec.ts | 16 +- .../__tests__/helpers/renderSlot.spec.ts | 20 +- .../__tests__/helpers/resolveAssets.spec.ts | 48 +- .../__tests__/helpers/toHandlers.spec.ts | 4 +- .../__tests__/helpers/withMemo.spec.ts | 34 +- packages/runtime-core/__tests__/hmr.spec.ts | 223 +- .../runtime-core/__tests__/hydration.spec.ts | 501 +- packages/runtime-core/__tests__/misc.spec.ts | 4 +- .../rendererAttrsFallthrough.spec.ts | 146 +- .../__tests__/rendererChildren.spec.ts | 108 +- .../__tests__/rendererComponent.spec.ts | 90 +- .../__tests__/rendererElement.spec.ts | 6 +- .../__tests__/rendererFragment.spec.ts | 130 +- .../__tests__/rendererOptimizedMode.spec.ts | 286 +- .../__tests__/rendererTemplateRef.spec.ts | 104 +- .../runtime-core/__tests__/scheduler.spec.ts | 12 +- .../runtime-core/__tests__/scopeId.spec.ts | 78 +- packages/runtime-core/__tests__/vnode.spec.ts | 152 +- .../runtime-core/__tests__/vnodeHooks.spec.ts | 28 +- packages/runtime-core/package.json | 2 +- .../runtime-core/src/apiAsyncComponent.ts | 35 +- packages/runtime-core/src/apiComputed.ts | 4 +- packages/runtime-core/src/apiCreateApp.ts | 125 +- .../runtime-core/src/apiDefineComponent.ts | 66 +- packages/runtime-core/src/apiInject.ts | 8 +- packages/runtime-core/src/apiLifecycle.ts | 26 +- packages/runtime-core/src/apiSetupHelpers.ts | 219 +- packages/runtime-core/src/apiWatch.ts | 178 +- .../src/compat/attrsFallthrough.ts | 4 +- .../runtime-core/src/compat/compatConfig.ts | 116 +- packages/runtime-core/src/compat/component.ts | 10 +- .../runtime-core/src/compat/componentAsync.ts | 6 +- .../src/compat/componentFunctional.ts | 12 +- .../src/compat/componentVModel.ts | 16 +- .../src/compat/customDirective.ts | 14 +- packages/runtime-core/src/compat/global.ts | 101 +- .../runtime-core/src/compat/globalConfig.ts | 12 +- packages/runtime-core/src/compat/instance.ts | 22 +- .../src/compat/instanceChildren.ts | 10 +- .../src/compat/instanceEventEmitter.ts | 20 +- .../src/compat/instanceListeners.ts | 4 +- packages/runtime-core/src/compat/props.ts | 13 +- packages/runtime-core/src/compat/renderFn.ts | 60 +- .../runtime-core/src/compat/renderHelpers.ts | 20 +- packages/runtime-core/src/component.ts | 257 +- packages/runtime-core/src/componentEmits.ts | 56 +- packages/runtime-core/src/componentOptions.ts | 170 +- packages/runtime-core/src/componentProps.ts | 89 +- .../src/componentPublicInstance.ts | 129 +- .../src/componentRenderContext.ts | 6 +- .../runtime-core/src/componentRenderUtils.ts | 83 +- packages/runtime-core/src/componentSlots.ts | 46 +- .../src/components/BaseTransition.ts | 57 +- .../runtime-core/src/components/KeepAlive.ts | 77 +- .../runtime-core/src/components/Suspense.ts | 210 +- .../runtime-core/src/components/Teleport.ts | 95 +- packages/runtime-core/src/customFormatter.ts | 34 +- packages/runtime-core/src/devtools.ts | 30 +- packages/runtime-core/src/directives.ts | 28 +- packages/runtime-core/src/enums.ts | 4 +- packages/runtime-core/src/errorHandling.ts | 28 +- packages/runtime-core/src/featureFlags.ts | 7 +- packages/runtime-core/src/h.ts | 79 +- .../runtime-core/src/helpers/createSlots.ts | 4 +- .../runtime-core/src/helpers/renderList.ts | 20 +- .../runtime-core/src/helpers/renderSlot.ts | 24 +- .../runtime-core/src/helpers/resolveAssets.ts | 22 +- .../runtime-core/src/helpers/toHandlers.ts | 4 +- .../runtime-core/src/helpers/useSsrContext.ts | 2 +- packages/runtime-core/src/helpers/withMemo.ts | 4 +- packages/runtime-core/src/hmr.ts | 26 +- packages/runtime-core/src/hydration.ts | 336 +- packages/runtime-core/src/index.ts | 101 +- packages/runtime-core/src/profiling.ts | 9 +- packages/runtime-core/src/renderer.ts | 520 +- .../runtime-core/src/rendererTemplateRef.ts | 18 +- packages/runtime-core/src/scheduler.ts | 21 +- packages/runtime-core/src/vnode.ts | 108 +- packages/runtime-core/src/warning.ts | 28 +- .../runtime-dom/__tests__/createApp.spec.ts | 6 +- .../__tests__/customElement.spec.ts | 130 +- .../__tests__/customizedBuiltIn.spec.ts | 8 +- .../__tests__/directives/vCloak.spec.ts | 2 +- .../__tests__/directives/vModel.spec.ts | 250 +- .../__tests__/directives/vOn.spec.ts | 8 +- .../__tests__/directives/vShow.spec.ts | 26 +- .../__tests__/helpers/useCssModule.spec.ts | 14 +- .../runtime-dom/__tests__/nodeOps.spec.ts | 26 +- .../runtime-dom/__tests__/patchAttrs.spec.ts | 6 +- .../runtime-dom/__tests__/patchClass.spec.ts | 7 +- .../runtime-dom/__tests__/patchEvents.spec.ts | 2 +- .../runtime-dom/__tests__/patchProps.spec.ts | 20 +- .../runtime-dom/__tests__/patchStyle.spec.ts | 20 +- packages/runtime-dom/package.json | 2 +- packages/runtime-dom/src/apiCustomElement.ts | 72 +- .../runtime-dom/src/components/Transition.ts | 42 +- .../src/components/TransitionGroup.ts | 48 +- packages/runtime-dom/src/directives/vModel.ts | 40 +- packages/runtime-dom/src/directives/vOn.ts | 20 +- packages/runtime-dom/src/directives/vShow.ts | 4 +- packages/runtime-dom/src/index.ts | 68 +- packages/runtime-dom/src/jsx.ts | 6 +- packages/runtime-dom/src/modules/events.ts | 16 +- packages/runtime-dom/src/modules/style.ts | 8 +- .../__tests__/testRuntime.spec.ts | 64 +- packages/runtime-test/src/index.ts | 10 +- packages/runtime-test/src/nodeOps.ts | 34 +- packages/runtime-test/src/patchProp.ts | 6 +- packages/runtime-test/src/serialize.ts | 16 +- packages/runtime-test/src/triggerEvent.ts | 4 +- .../server-renderer/__tests__/render.spec.ts | 416 +- .../__tests__/ssrAttrFallthrough.spec.ts | 30 +- .../__tests__/ssrCompilerOptions.spec.ts | 68 +- .../__tests__/ssrComputed.spec.ts | 4 +- .../__tests__/ssrDirectives.spec.ts | 322 +- .../__tests__/ssrDynamicComponent.spec.ts | 34 +- .../__tests__/ssrInterpolate.spec.ts | 14 +- .../__tests__/ssrRenderAttrs.spec.ts | 74 +- .../__tests__/ssrRenderList.spec.ts | 10 +- .../__tests__/ssrScopeId.spec.ts | 60 +- .../server-renderer/__tests__/ssrSlot.spec.ts | 86 +- .../__tests__/ssrSuspense.spec.ts | 46 +- .../__tests__/ssrTeleport.spec.ts | 66 +- .../__tests__/ssrVModelHelpers.spec.ts | 62 +- .../__tests__/ssrWatch.spec.ts | 6 +- .../__tests__/webStream.spec.ts | 20 +- packages/server-renderer/package.json | 2 +- .../server-renderer/src/helpers/ssrCompile.ts | 32 +- .../src/helpers/ssrGetDirectiveProps.ts | 8 +- .../src/helpers/ssrRenderAttrs.ts | 20 +- .../src/helpers/ssrRenderComponent.ts | 15 +- .../src/helpers/ssrRenderList.ts | 4 +- .../src/helpers/ssrRenderSlot.ts | 19 +- .../src/helpers/ssrRenderSuspense.ts | 4 +- .../src/helpers/ssrRenderTeleport.ts | 11 +- .../src/helpers/ssrVModelHelpers.ts | 6 +- packages/server-renderer/src/index.ts | 2 +- packages/server-renderer/src/internal.ts | 4 +- packages/server-renderer/src/render.ts | 70 +- .../server-renderer/src/renderToStream.ts | 46 +- .../server-renderer/src/renderToString.ts | 10 +- packages/sfc-playground/package.json | 2 +- packages/sfc-playground/src/App.vue | 53 +- packages/sfc-playground/src/Header.vue | 39 +- packages/sfc-playground/src/VersionSelect.vue | 2 +- .../sfc-playground/src/download/download.ts | 2 +- .../src/download/template/vite.config.js | 2 +- packages/sfc-playground/src/icons/GitHub.vue | 3 +- packages/sfc-playground/src/icons/Moon.vue | 5 +- packages/sfc-playground/src/icons/Reload.vue | 14 + packages/sfc-playground/src/icons/Sun.vue | 45 +- packages/sfc-playground/src/main.ts | 2 +- .../sfc-playground/src/vue-dev-proxy-prod.ts | 2 +- packages/sfc-playground/vite.config.ts | 27 +- packages/shared/__tests__/codeframe.spec.ts | 4 +- packages/shared/__tests__/looseEqual.spec.ts | 14 +- .../shared/__tests__/normalizeProp.spec.ts | 16 +- .../shared/__tests__/toDisplayString.spec.ts | 24 +- packages/shared/package.json | 2 +- packages/shared/src/codeframe.ts | 6 +- packages/shared/src/domAttrConfig.ts | 8 +- packages/shared/src/domTagConfig.ts | 13 + packages/shared/src/general.ts | 10 +- packages/shared/src/globalsAllowList.ts | 2 +- packages/shared/src/makeMap.ts | 12 +- packages/shared/src/normalizeProp.ts | 6 +- packages/shared/src/patchFlags.ts | 6 +- packages/shared/src/shapeFlags.ts | 4 +- packages/shared/src/slotFlags.ts | 6 +- packages/shared/src/toDisplayString.ts | 12 +- packages/template-explorer/src/index.ts | 68 +- packages/template-explorer/src/options.ts | 66 +- packages/template-explorer/src/theme.ts | 118 +- packages/template-explorer/style.css | 5 +- .../vue-compat/__tests__/compiler.spec.ts | 56 +- .../__tests__/componentAsync.spec.ts | 24 +- .../__tests__/componentFunctional.spec.ts | 32 +- .../__tests__/componentVModel.spec.ts | 20 +- packages/vue-compat/__tests__/filters.spec.ts | 72 +- packages/vue-compat/__tests__/global.spec.ts | 119 +- .../vue-compat/__tests__/globalConfig.spec.ts | 12 +- .../vue-compat/__tests__/instance.spec.ts | 90 +- packages/vue-compat/__tests__/misc.spec.ts | 82 +- packages/vue-compat/__tests__/options.spec.ts | 50 +- .../vue-compat/__tests__/renderFn.spec.ts | 112 +- packages/vue-compat/__tests__/utils.ts | 4 +- packages/vue-compat/package.json | 4 +- packages/vue-compat/src/createCompatVue.ts | 12 +- packages/vue-compat/src/dev.ts | 2 +- packages/vue-compat/src/index.ts | 28 +- packages/vue-compat/src/runtime.ts | 2 +- packages/vue/README.md | 21 +- .../vue/__tests__/customElementCasing.spec.ts | 6 +- packages/vue/__tests__/e2e/Transition.spec.ts | 476 +- .../vue/__tests__/e2e/TransitionGroup.spec.ts | 98 +- packages/vue/__tests__/e2e/commits.mock.ts | 126 +- packages/vue/__tests__/e2e/commits.spec.ts | 12 +- packages/vue/__tests__/e2e/e2eUtils.ts | 22 +- packages/vue/__tests__/e2e/grid.spec.ts | 24 +- packages/vue/__tests__/e2e/markdown.spec.ts | 12 +- packages/vue/__tests__/e2e/svg.spec.ts | 20 +- packages/vue/__tests__/e2e/todomvc.spec.ts | 12 +- packages/vue/__tests__/e2e/tree.spec.ts | 42 +- packages/vue/__tests__/index.spec.ts | 66 +- .../vue/__tests__/mathmlNamespace.spec.ts | 80 + .../__tests__/runtimeCompilerOptions.spec.ts | 24 +- packages/vue/__tests__/svgNamespace.spec.ts | 16 +- packages/vue/index.mjs | 2 +- packages/vue/jsx-runtime/index.d.ts | 3 +- packages/vue/jsx-runtime/index.mjs | 7 +- packages/vue/jsx.d.ts | 3 +- packages/vue/macros-global.d.ts | 19 - packages/vue/macros.d.ts | 24 +- packages/vue/package.json | 12 +- packages/vue/ref-macros.d.ts | 2 - packages/vue/server-renderer/index.mjs | 2 +- packages/vue/src/dev.ts | 2 +- packages/vue/src/index.ts | 28 +- packages/vue/src/runtime.ts | 2 +- packages/vue/types/jsx-register.d.ts | 4 - pnpm-lock.yaml | 1169 ++-- rollup.config.js | 110 +- rollup.dts.config.js | 93 +- scripts/aliases.js | 7 +- scripts/build.js | 31 +- scripts/const-enum.js | 255 - scripts/dev.js | 28 +- scripts/inline-enums.js | 279 + scripts/pre-dev-sfc.js | 5 +- scripts/release.js | 172 +- scripts/{setupVitest.ts => setup-vitest.ts} | 24 +- scripts/size-report.ts | 8 +- scripts/usage-size.ts | 25 +- scripts/utils.js | 10 +- scripts/{verifyCommit.js => verify-commit.js} | 12 +- scripts/verify-treeshaking.js | 49 + tsconfig.json | 5 +- vitest.config.ts | 19 +- vitest.e2e.config.ts | 4 +- vitest.unit.config.ts | 4 +- 513 files changed, 23786 insertions(+), 26056 deletions(-) create mode 100644 .eslintignore create mode 100644 .git-blame-ignore-revs create mode 100644 changelogs/CHANGELOG-3.3.md delete mode 100644 packages/compiler-core/src/parse.ts create mode 100644 packages/compiler-core/src/parser.ts create mode 100644 packages/compiler-core/src/tokenizer.ts delete mode 100644 packages/compiler-dom/src/decodeHtml.ts delete mode 100644 packages/compiler-dom/src/namedChars.json create mode 100644 packages/compiler-sfc/__tests__/compileScript/__snapshots__/importUsageCheck.spec.ts.snap delete mode 100644 packages/compiler-sfc/__tests__/compileScript/__snapshots__/reactivityTransform.spec.ts.snap create mode 100644 packages/compiler-sfc/__tests__/compileScript/importUsageCheck.spec.ts delete mode 100644 packages/compiler-sfc/__tests__/compileScript/reactivityTransform.spec.ts create mode 100644 packages/dts-test/appDirective.test-d.ts create mode 100644 packages/dts-test/componentInstance.test-d.tsx delete mode 100644 packages/dts-test/reactivityMacros.test-d.ts delete mode 100644 packages/reactivity-transform/LICENSE delete mode 100644 packages/reactivity-transform/README.md delete mode 100644 packages/reactivity-transform/__tests__/__snapshots__/reactivityTransform.spec.ts.snap delete mode 100644 packages/reactivity-transform/__tests__/reactivityTransform.spec.ts delete mode 100644 packages/reactivity-transform/package.json delete mode 100644 packages/reactivity-transform/src/babelPlugin.ts delete mode 100644 packages/reactivity-transform/src/index.ts delete mode 100644 packages/reactivity-transform/src/reactivityTransform.ts create mode 100644 packages/reactivity/__tests__/gc.spec.ts create mode 100644 packages/reactivity/src/constants.ts delete mode 100644 packages/reactivity/src/operations.ts create mode 100644 packages/reactivity/src/reactiveEffect.ts create mode 100644 packages/sfc-playground/src/icons/Reload.vue create mode 100644 packages/vue/__tests__/mathmlNamespace.spec.ts delete mode 100644 packages/vue/macros-global.d.ts delete mode 100644 packages/vue/ref-macros.d.ts delete mode 100644 packages/vue/types/jsx-register.d.ts delete mode 100644 scripts/const-enum.js create mode 100644 scripts/inline-enums.js rename scripts/{setupVitest.ts => setup-vitest.ts} (87%) rename scripts/{verifyCommit.js => verify-commit.js} (76%) create mode 100644 scripts/verify-treeshaking.js diff --git a/.eslintignore b/.eslintignore new file mode 100644 index 00000000000..4d4f41e301f --- /dev/null +++ b/.eslintignore @@ -0,0 +1,4 @@ +node_modules +dist +temp +coverage diff --git a/.eslintrc.cjs b/.eslintrc.cjs index 4296d0f39b6..b8afcf9843f 100644 --- a/.eslintrc.cjs +++ b/.eslintrc.cjs @@ -1,14 +1,22 @@ -/* eslint-disable no-restricted-globals */ - +const { builtinModules } = require('node:module') const DOMGlobals = ['window', 'document'] const NodeGlobals = ['module', 'require'] +const banConstEnum = { + selector: 'TSEnumDeclaration[const=true]', + message: + 'Please use non-const enums. This project automatically inlines enums.', +} + +/** + * @type {import('eslint-define-config').ESLintConfig} + */ module.exports = { parser: '@typescript-eslint/parser', parserOptions: { - sourceType: 'module' + sourceType: 'module', }, - plugins: ['jest'], + plugins: ['jest', 'import', '@typescript-eslint'], rules: { 'no-debugger': 'error', // most of the codebase are expected to be env agnostic @@ -16,14 +24,34 @@ module.exports = { 'no-restricted-syntax': [ 'error', + banConstEnum, // since we target ES2015 for baseline support, we need to forbid object // rest spread usage in destructure as it compiles into a verbose helper. 'ObjectPattern > RestElement', // tsc compiles assignment spread into Object.assign() calls, but esbuild // still generates verbose helpers, so spread assignment is also prohiboted 'ObjectExpression > SpreadElement', - 'AwaitExpression' - ] + 'AwaitExpression', + ], + 'sort-imports': ['error', { ignoreDeclarationSort: true }], + + 'import/no-nodejs-modules': [ + 'error', + { allow: builtinModules.map(mod => `node:${mod}`) }, + ], + // This rule enforces the preference for using '@ts-expect-error' comments in TypeScript + // code to indicate intentional type errors, improving code clarity and maintainability. + '@typescript-eslint/prefer-ts-expect-error': 'error', + // Enforce the use of 'import type' for importing types + '@typescript-eslint/consistent-type-imports': [ + 'error', + { + fixStyle: 'inline-type-imports', + disallowTypeAnnotations: false, + }, + ], + // Enforce the use of top-level import type qualifier when an import only has specifiers with inline type qualifiers + '@typescript-eslint/no-import-type-side-effects': 'error', }, overrides: [ // tests, no restrictions (runs in Node / jest with jsdom) @@ -33,56 +61,66 @@ module.exports = { 'no-restricted-globals': 'off', 'no-restricted-syntax': 'off', 'jest/no-disabled-tests': 'error', - 'jest/no-focused-tests': 'error' - } + 'jest/no-focused-tests': 'error', + }, }, // shared, may be used in any env { - files: ['packages/shared/**'], + files: ['packages/shared/**', '.eslintrc.cjs'], rules: { - 'no-restricted-globals': 'off' - } + 'no-restricted-globals': 'off', + }, }, // Packages targeting DOM { files: ['packages/{vue,vue-compat,runtime-dom}/**'], rules: { - 'no-restricted-globals': ['error', ...NodeGlobals] - } + 'no-restricted-globals': ['error', ...NodeGlobals], + }, }, // Packages targeting Node { - files: [ - 'packages/{compiler-sfc,compiler-ssr,server-renderer,reactivity-transform}/**' - ], + files: ['packages/{compiler-sfc,compiler-ssr,server-renderer}/**'], rules: { 'no-restricted-globals': ['error', ...DOMGlobals], - 'no-restricted-syntax': 'off' - } + 'no-restricted-syntax': ['error', banConstEnum], + }, }, // Private package, browser only + no syntax restrictions { files: ['packages/template-explorer/**', 'packages/sfc-playground/**'], rules: { 'no-restricted-globals': ['error', ...NodeGlobals], - 'no-restricted-syntax': 'off' - } + 'no-restricted-syntax': ['error', banConstEnum], + }, }, // JavaScript files { files: ['*.js', '*.cjs'], rules: { // We only do `no-unused-vars` checks for js files, TS files are checked by TypeScript itself. - 'no-unused-vars': ['error', { vars: 'all', args: 'none' }] - } + 'no-unused-vars': ['error', { vars: 'all', args: 'none' }], + }, }, // Node scripts { - files: ['scripts/**', '*.{js,ts}', 'packages/**/index.js'], + files: [ + 'scripts/**', + './*.{js,ts}', + 'packages/*/*.js', + 'packages/vue/*/*.js', + ], rules: { 'no-restricted-globals': 'off', - 'no-restricted-syntax': 'off' - } - } - ] + 'no-restricted-syntax': ['error', banConstEnum], + }, + }, + // Import nodejs modules in compiler-sfc + { + files: ['packages/compiler-sfc/src/**'], + rules: { + 'import/no-nodejs-modules': ['error', { allow: builtinModules }], + }, + }, + ], } diff --git a/.git-blame-ignore-revs b/.git-blame-ignore-revs new file mode 100644 index 00000000000..d06b03a3f89 --- /dev/null +++ b/.git-blame-ignore-revs @@ -0,0 +1,2 @@ +# update prettier & eslint config (#9162) +bfe6b459d3a0ce6168611ee1ac7e6e789709df9d diff --git a/.github/contributing.md b/.github/contributing.md index afdae671193..da1bd5ec453 100644 --- a/.github/contributing.md +++ b/.github/contributing.md @@ -63,7 +63,7 @@ Hi! I'm really excited that you are interested in contributing to Vue.js. Before You will need [Node.js](https://nodejs.org) **version 18.12+**, and [PNPM](https://pnpm.io) **version 8+**. -We also recommend installing [ni](https://github.com/antfu/ni) to help switching between repos using different package managers. `ni` also provides the handy `nr` command which running npm scripts easier. +We also recommend installing [@antfu/ni](https://github.com/antfu/ni) to help switching between repos using different package managers. `ni` also provides the handy `nr` command which running npm scripts easier. After cloning the repo, run: @@ -86,11 +86,11 @@ The project uses [simple-git-hooks](https://github.com/toplenboren/simple-git-ho - Type check the entire project - Automatically format changed files using Prettier -- Verify commit message format (logic in `scripts/verifyCommit.js`) +- Verify commit message format (logic in `scripts/verify-commit.js`) ## Scripts -**The examples below will be using the `nr` command from the [ni](https://github.com/antfu/ni) package.** You can also use plain `npm run`, but you will need to pass all additional arguments after the command after an extra `--`. For example, `nr build runtime --all` is equivalent to `npm run build -- runtime --all`. +**The examples below will be using the `nr` command from the [@antfu/ni](https://github.com/antfu/ni) package.** You can also use plain `npm run`, but you will need to pass all additional arguments after the command after an extra `--`. For example, `nr build runtime --all` is equivalent to `npm run build -- runtime --all`. The `run-s` and `run-p` commands found in some scripts are from [npm-run-all](https://github.com/mysticatea/npm-run-all) for orchestrating multiple scripts. `run-s` means "run in sequence" while `run-p` means "run in parallel". diff --git a/.github/renovate.json5 b/.github/renovate.json5 index 088913317c7..a43f4ae30cf 100644 --- a/.github/renovate.json5 +++ b/.github/renovate.json5 @@ -7,35 +7,35 @@ packageRules: [ { depTypeList: ['peerDependencies'], - enabled: false + enabled: false, }, { groupName: 'test', matchPackageNames: ['vitest', 'jsdom', 'puppeteer'], - matchPackagePrefixes: ['@vitest'] + matchPackagePrefixes: ['@vitest'], }, { groupName: 'playground', matchFileNames: [ 'packages/sfc-playground/package.json', - 'packages/template-explorer/package.json' - ] + 'packages/template-explorer/package.json', + ], }, { groupName: 'compiler', matchPackageNames: ['magic-string'], - matchPackagePrefixes: ['@babel', 'postcss'] + matchPackagePrefixes: ['@babel', 'postcss'], }, { groupName: 'build', matchPackageNames: ['vite', 'terser'], - matchPackagePrefixes: ['rollup', 'esbuild', '@rollup', '@vitejs'] + matchPackagePrefixes: ['rollup', 'esbuild', '@rollup', '@vitejs'], }, { groupName: 'lint', matchPackageNames: ['simple-git-hooks', 'lint-staged'], - matchPackagePrefixes: ['@typescript-eslint', 'eslint', 'prettier'] - } + matchPackagePrefixes: ['@typescript-eslint', 'eslint', 'prettier'], + }, ], ignoreDeps: [ 'vue', @@ -45,6 +45,6 @@ 'typescript', // ESM only - 'estree-walker' - ] + 'estree-walker', + ], } diff --git a/.github/workflows/autofix.yml b/.github/workflows/autofix.yml index 5e7bb63c22f..d7f11b0d220 100644 --- a/.github/workflows/autofix.yml +++ b/.github/workflows/autofix.yml @@ -30,4 +30,4 @@ jobs: - name: Run prettier run: pnpm run format - - uses: autofix-ci/action@bee19d72e71787c12ca0f29de72f2833e437e4c9 + - uses: autofix-ci/action@ea32e3a12414e6d3183163c3424a7d7a8631ad84 diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index b9e8078dd79..e458fbd57f3 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -58,31 +58,6 @@ jobs: - name: Run ssr unit tests run: pnpm run test-unit server-renderer - benchmarks: - runs-on: ubuntu-latest - if: github.event_name == 'push' || github.event.pull_request.head.repo.full_name != github.repository - env: - PUPPETEER_SKIP_DOWNLOAD: 'true' - steps: - - uses: actions/checkout@v4 - - - name: Install pnpm - uses: pnpm/action-setup@v2 - - - name: Install Node.js - uses: actions/setup-node@v4 - with: - node-version-file: '.node-version' - cache: 'pnpm' - - - run: pnpm install - - - name: Run benchmarks - uses: CodSpeedHQ/action@v2 - with: - run: pnpm vitest bench --run - token: ${{ secrets.CODSPEED_TOKEN }} - e2e-test: runs-on: ubuntu-latest if: github.event_name == 'push' || github.event.pull_request.head.repo.full_name != github.repository @@ -110,6 +85,9 @@ jobs: - name: Run e2e tests run: pnpm run test-e2e + - name: verify treeshaking + run: node scripts/verify-treeshaking.js + lint-and-test-dts: runs-on: ubuntu-latest if: github.event_name == 'push' || github.event.pull_request.head.repo.full_name != github.repository @@ -137,3 +115,28 @@ jobs: - name: Run type declaration tests run: pnpm run test-dts + + # benchmarks: + # runs-on: ubuntu-latest + # if: github.event_name == 'push' || github.event.pull_request.head.repo.full_name != github.repository + # env: + # PUPPETEER_SKIP_DOWNLOAD: 'true' + # steps: + # - uses: actions/checkout@v4 + + # - name: Install pnpm + # uses: pnpm/action-setup@v2 + + # - name: Install Node.js + # uses: actions/setup-node@v4 + # with: + # node-version-file: '.node-version' + # cache: 'pnpm' + + # - run: pnpm install + + # - name: Run benchmarks + # uses: CodSpeedHQ/action@v2 + # with: + # run: pnpm vitest bench --run + # token: ${{ secrets.CODSPEED_TOKEN }} diff --git a/.prettierignore b/.prettierignore index 1521c8b7652..fbd3dca8ca3 100644 --- a/.prettierignore +++ b/.prettierignore @@ -1 +1,4 @@ dist +*.md +*.html +pnpm-lock.yaml diff --git a/.prettierrc b/.prettierrc index ef93d94821a..759232e7cf6 100644 --- a/.prettierrc +++ b/.prettierrc @@ -1,5 +1,5 @@ -semi: false -singleQuote: true -printWidth: 80 -trailingComma: 'none' -arrowParens: 'avoid' +{ + "semi": false, + "singleQuote": true, + "arrowParens": "avoid" +} diff --git a/.vscode/launch.json b/.vscode/launch.json index b63ffc79b80..b616400b48e 100644 --- a/.vscode/launch.json +++ b/.vscode/launch.json @@ -21,7 +21,7 @@ "console": "integratedTerminal", "sourceMaps": true, "windows": { - "program": "${workspaceFolder}/node_modules/jest/bin/jest", + "program": "${workspaceFolder}/node_modules/jest/bin/jest" } } ] diff --git a/CHANGELOG.md b/CHANGELOG.md index 697a618d82c..44f187edf4e 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,592 +1,466 @@ -## [3.3.12](https://github.com/vuejs/core/compare/v3.3.11...v3.3.12) (2023-12-16) +## [3.4.3](https://github.com/vuejs/core/compare/v3.4.2...v3.4.3) (2023-12-30) ### Bug Fixes -* **hydration:** handle appear transition before patch props ([#9837](https://github.com/vuejs/core/issues/9837)) ([e70f4c4](https://github.com/vuejs/core/commit/e70f4c47c553b6e16d8fad70743271ca23802fe7)), closes [#9832](https://github.com/vuejs/core/issues/9832) -* **sfc/cssVars:** fix loss of CSS v-bind variables when setting inline style with string value ([#9824](https://github.com/vuejs/core/issues/9824)) ([0a387df](https://github.com/vuejs/core/commit/0a387dfb1d04afb6eae4296b6da76dfdaca77af4)), closes [#9821](https://github.com/vuejs/core/issues/9821) -* **ssr:** fix suspense hydration of fallback content ([#7188](https://github.com/vuejs/core/issues/7188)) ([60415b5](https://github.com/vuejs/core/commit/60415b5d67df55f1fd6b176615299c08640fa142)) -* **types:** add `xmlns:xlink` to `SVGAttributes` ([#9300](https://github.com/vuejs/core/issues/9300)) ([0d61b42](https://github.com/vuejs/core/commit/0d61b429ecf63591d31e09702058fa4c7132e1a7)), closes [#9299](https://github.com/vuejs/core/issues/9299) -* **types:** fix `shallowRef` type error ([#9839](https://github.com/vuejs/core/issues/9839)) ([9a57158](https://github.com/vuejs/core/commit/9a571582b53220270e498d8712ea59312c0bef3a)) -* **types:** support for generic keyof slots ([#8374](https://github.com/vuejs/core/issues/8374)) ([213eba4](https://github.com/vuejs/core/commit/213eba479ce080efc1053fe636f6be4a4c889b44)) +* **compiler-sfc:** respect sfc parse options in cache key ([b8d58ec](https://github.com/vuejs/core/commit/b8d58ec4f42cbeb9443bf06138add46158db9af0)) -## [3.3.11](https://github.com/vuejs/core/compare/v3.3.10...v3.3.11) (2023-12-08) +## [3.4.2](https://github.com/vuejs/core/compare/v3.4.1...v3.4.2) (2023-12-30) ### Bug Fixes -* **custom-element:** correctly handle number type props in prod ([#8989](https://github.com/vuejs/core/issues/8989)) ([d74d364](https://github.com/vuejs/core/commit/d74d364d62db8e48881af6b5a75ce4fb5f36cc35)) -* **reactivity:** fix mutation on user proxy of reactive Array ([6ecbd5c](https://github.com/vuejs/core/commit/6ecbd5ce2a7f59314a8326a1d193874b87f4d8c8)), closes [#9742](https://github.com/vuejs/core/issues/9742) [#9751](https://github.com/vuejs/core/issues/9751) [#9750](https://github.com/vuejs/core/issues/9750) -* **runtime-dom:** fix width and height prop check condition ([5b00286](https://github.com/vuejs/core/commit/5b002869c533220706f9788b496b8ca8d8e98609)), closes [#9762](https://github.com/vuejs/core/issues/9762) -* **shared:** handle Map with symbol keys in toDisplayString ([#9731](https://github.com/vuejs/core/issues/9731)) ([364821d](https://github.com/vuejs/core/commit/364821d6bdb1775e2f55a69bcfb9f40f7acf1506)), closes [#9727](https://github.com/vuejs/core/issues/9727) -* **shared:** handle more Symbol cases in toDisplayString ([983d45d](https://github.com/vuejs/core/commit/983d45d4f8eb766b5a16b7ea93b86d3c51618fa6)) -* **Suspense:** properly get anchor when mount fallback vnode ([#9770](https://github.com/vuejs/core/issues/9770)) ([b700328](https://github.com/vuejs/core/commit/b700328342e17dc16b19316c2e134a26107139d2)), closes [#9769](https://github.com/vuejs/core/issues/9769) -* **types:** ref() return type should not be any when initial value is any ([#9768](https://github.com/vuejs/core/issues/9768)) ([cdac121](https://github.com/vuejs/core/commit/cdac12161ec27b45ded48854c3d749664b6d4a6d)) -* **watch:** should not fire pre watcher on child component unmount ([#7181](https://github.com/vuejs/core/issues/7181)) ([6784f0b](https://github.com/vuejs/core/commit/6784f0b1f8501746ea70d87d18ed63a62cf6b76d)), closes [#7030](https://github.com/vuejs/core/issues/7030) +* **compiler-sfc:** fix dev regression for dot / namespace component usage ([dce99c1](https://github.com/vuejs/core/commit/dce99c12df981ca45a4d848c37ba8b16496025f0)), closes [#9947](https://github.com/vuejs/core/issues/9947) +* **runtime-core:** support deep: false when watch reactive ([#9928](https://github.com/vuejs/core/issues/9928)) ([4f703d1](https://github.com/vuejs/core/commit/4f703d120d76d711084346f73ea295c73e6ef6b6)), closes [#9916](https://github.com/vuejs/core/issues/9916) +* **ssr:** fix hydration error for slot outlet inside transition-group ([#9937](https://github.com/vuejs/core/issues/9937)) ([6cb00ed](https://github.com/vuejs/core/commit/6cb00ed0f9b64428ec18fada0f68467d6a813fde)), closes [#9933](https://github.com/vuejs/core/issues/9933) -## [3.3.10](https://github.com/vuejs/core/compare/v3.3.9...v3.3.10) (2023-12-04) +## [3.4.1](https://github.com/vuejs/core/compare/v3.4.0...v3.4.1) (2023-12-30) ### Bug Fixes -* **app:** prevent template from being cached between apps with different options ([#9724](https://github.com/vuejs/core/issues/9724)) ([ec71585](https://github.com/vuejs/core/commit/ec715854ca12520b2afc9e9b3981cbae05ae5206)), closes [#9618](https://github.com/vuejs/core/issues/9618) -* **compiler-sfc:** avoid passing forEach index to genMap ([f12db7f](https://github.com/vuejs/core/commit/f12db7fb564a534cef2e5805cc9f54afe5d72fbf)) -* **compiler-sfc:** deindent pug/jade templates ([6345197](https://github.com/vuejs/core/commit/634519720a21fb5a6871454e1cadad7053a568b8)), closes [#3231](https://github.com/vuejs/core/issues/3231) [#3842](https://github.com/vuejs/core/issues/3842) [#7723](https://github.com/vuejs/core/issues/7723) -* **compiler-sfc:** fix :where and :is selector in scoped mode with multiple selectors ([#9735](https://github.com/vuejs/core/issues/9735)) ([c3e2c55](https://github.com/vuejs/core/commit/c3e2c556b532656b50b8ab5cd2d9eabc26622d63)), closes [#9707](https://github.com/vuejs/core/issues/9707) -* **compiler-sfc:** generate more treeshaking friendly code ([#9507](https://github.com/vuejs/core/issues/9507)) ([8d74ca0](https://github.com/vuejs/core/commit/8d74ca0e6fa2738ca6854b7e879ff59419f948c7)), closes [#9500](https://github.com/vuejs/core/issues/9500) -* **compiler-sfc:** support inferring generic types ([#8511](https://github.com/vuejs/core/issues/8511)) ([eb5e307](https://github.com/vuejs/core/commit/eb5e307c0be62002e62c4c800d0dfacb39b0d4ca)), closes [#8482](https://github.com/vuejs/core/issues/8482) -* **compiler-sfc:** support resolving components from props ([#8785](https://github.com/vuejs/core/issues/8785)) ([7cbcee3](https://github.com/vuejs/core/commit/7cbcee3d831241a8bd3588ae92d3f27e3641e25f)) -* **compiler-sfc:** throw error when failing to load TS during type resolution ([#8883](https://github.com/vuejs/core/issues/8883)) ([4936d2e](https://github.com/vuejs/core/commit/4936d2e11a8d0ca3704bfe408548cb26bb3fd5e9)) -* **cssVars:** cssVar names should be double-escaped when generating code for ssr ([#8824](https://github.com/vuejs/core/issues/8824)) ([5199a12](https://github.com/vuejs/core/commit/5199a12f8855cd06f24bf355708b5a2134f63176)), closes [#7823](https://github.com/vuejs/core/issues/7823) -* **deps:** update compiler to ^7.23.4 ([#9681](https://github.com/vuejs/core/issues/9681)) ([31f6ebc](https://github.com/vuejs/core/commit/31f6ebc4df84490ed29fb75e7bf4259200eb51f0)) -* **runtime-core:** Suspense get anchor properly in Transition ([#9309](https://github.com/vuejs/core/issues/9309)) ([65f3fe2](https://github.com/vuejs/core/commit/65f3fe273127a8b68e1222fbb306d28d85f01757)), closes [#8105](https://github.com/vuejs/core/issues/8105) -* **runtime-dom:** set width/height with units as attribute ([#8781](https://github.com/vuejs/core/issues/8781)) ([bfc1838](https://github.com/vuejs/core/commit/bfc1838f31199de3f189198a3c234fa7bae91386)) -* **ssr:** avoid computed being accidentally cached before server render ([#9688](https://github.com/vuejs/core/issues/9688)) ([30d5d93](https://github.com/vuejs/core/commit/30d5d93a92b2154406ec04f8aca6b217fa01177c)), closes [#5300](https://github.com/vuejs/core/issues/5300) -* **types:** expose emits as props in functional components ([#9234](https://github.com/vuejs/core/issues/9234)) ([887e54c](https://github.com/vuejs/core/commit/887e54c347ea9eac4c721b5e2288f054873d1d30)) -* **types:** fix reactive collection types ([#8960](https://github.com/vuejs/core/issues/8960)) ([ad27473](https://github.com/vuejs/core/commit/ad274737015c36906d76f3189203093fa3a2e4e7)), closes [#8904](https://github.com/vuejs/core/issues/8904) -* **types:** improve return type withKeys and withModifiers ([#9734](https://github.com/vuejs/core/issues/9734)) ([43c3cfd](https://github.com/vuejs/core/commit/43c3cfdec5ae5d70fa2a21e857abc2d73f1a0d07)) +* **compat:** correct enum value for COMPILER_FILTERS feature ([#9875](https://github.com/vuejs/core/issues/9875)) ([77d33e2](https://github.com/vuejs/core/commit/77d33e263cf19983caf4e5c53a0eb0bee374843c)) +* **defineModel:** always default modifiers to empty object ([9bc3c7e](https://github.com/vuejs/core/commit/9bc3c7e29cf15f5ca96703542d10cfd786a3fc55)), closes [#9945](https://github.com/vuejs/core/issues/9945) +* **defineModel:** support local mutation when only prop but no listener is passed ([97ce041](https://github.com/vuejs/core/commit/97ce041910b6ca4bef10f939493d6b5a06ea5b07)) +* **types:** fix defineModel watch type error ([#9942](https://github.com/vuejs/core/issues/9942)) ([4af8583](https://github.com/vuejs/core/commit/4af85835f7e593a7dffa7dc7e99f14877eb70fd1)), closes [#9939](https://github.com/vuejs/core/issues/9939) -### Performance Improvements +### Features -* optimize on* prop check ([38aaa8c](https://github.com/vuejs/core/commit/38aaa8c88648c54fe2616ad9c0961288092fcb44)) -* **runtime-dom:** cache modifier wrapper functions ([da4a4fb](https://github.com/vuejs/core/commit/da4a4fb5e8eee3c6d31f24ebd79a9d0feca56cb2)), closes [#8882](https://github.com/vuejs/core/issues/8882) -* **v-on:** constant handlers with modifiers should not be treated as dynamic ([4d94ebf](https://github.com/vuejs/core/commit/4d94ebfe75174b340d2b794e699cad1add3600a9)) +* **compiler-sfc:** support passing template parsing options when parsing sfc ([6fab855](https://github.com/vuejs/core/commit/6fab8551e4aeef4610987640de8b435b1ae321bb)) (necessary to fix https://github.com/vitejs/vite-plugin-vue/issues/322) -## [3.3.9](https://github.com/vuejs/core/compare/v3.3.8...v3.3.9) (2023-11-25) +# [3.4.0 Slam Dunk](https://github.com/vuejs/core/compare/v3.4.0-rc.3...v3.4.0) (2023-12-29) +> Read [this blog post](https://blog.vuejs.org/posts/vue-3-4) for an overview of the release highlights. -### Bug Fixes - -* **compiler-core:** avoid rewriting scope variables in inline for loops ([#7245](https://github.com/vuejs/core/issues/7245)) ([a2d810e](https://github.com/vuejs/core/commit/a2d810eb40cef631f61991ca68b426ee9546aba0)), closes [#7238](https://github.com/vuejs/core/issues/7238) -* **compiler-core:** fix `resolveParserPlugins` decorators check ([#9566](https://github.com/vuejs/core/issues/9566)) ([9d0eba9](https://github.com/vuejs/core/commit/9d0eba916f3bf6fb5c03222400edae1a2db7444f)), closes [#9560](https://github.com/vuejs/core/issues/9560) -* **compiler-sfc:** consistently escape type-only prop names ([#8654](https://github.com/vuejs/core/issues/8654)) ([3e08d24](https://github.com/vuejs/core/commit/3e08d246dfd8523c54fb8e7a4a6fd5506ffb1bcc)), closes [#8635](https://github.com/vuejs/core/issues/8635) [#8910](https://github.com/vuejs/core/issues/8910) [vitejs/vite-plugin-vue#184](https://github.com/vitejs/vite-plugin-vue/issues/184) -* **compiler-sfc:** malformed filename on windows using path.posix.join() ([#9478](https://github.com/vuejs/core/issues/9478)) ([f18a174](https://github.com/vuejs/core/commit/f18a174979626b3429db93c5d5b7ae5448917c70)), closes [#8671](https://github.com/vuejs/core/issues/8671) [#9583](https://github.com/vuejs/core/issues/9583) [#9446](https://github.com/vuejs/core/issues/9446) [#9473](https://github.com/vuejs/core/issues/9473) -* **compiler-sfc:** support `:is` and `:where` selector in scoped css rewrite ([#8929](https://github.com/vuejs/core/issues/8929)) ([3227e50](https://github.com/vuejs/core/commit/3227e50b32105f8893f7dff2f29278c5b3a9f621)) -* **compiler-sfc:** support resolve extends interface for defineEmits ([#8470](https://github.com/vuejs/core/issues/8470)) ([9e1b74b](https://github.com/vuejs/core/commit/9e1b74bcd5fa4151f5d1bc02c69fbbfa4762f577)), closes [#8465](https://github.com/vuejs/core/issues/8465) -* **hmr/transition:** fix kept-alive component inside transition disappearing after hmr ([#7126](https://github.com/vuejs/core/issues/7126)) ([d11e978](https://github.com/vuejs/core/commit/d11e978fc98dcc83526c167e603b8308f317f786)), closes [#7121](https://github.com/vuejs/core/issues/7121) -* **hydration:** force hydration for v-bind with .prop modifier ([364f319](https://github.com/vuejs/core/commit/364f319d214226770d97c98d8fcada80c9e8dde3)), closes [#7490](https://github.com/vuejs/core/issues/7490) -* **hydration:** properly hydrate indeterminate prop ([34b5a5d](https://github.com/vuejs/core/commit/34b5a5da4ae9c9faccac237acd7acc8e7e017571)), closes [#7476](https://github.com/vuejs/core/issues/7476) -* **reactivity:** clear method on readonly collections should return undefined ([#7316](https://github.com/vuejs/core/issues/7316)) ([657476d](https://github.com/vuejs/core/commit/657476dcdb964be4fbb1277c215c073f3275728e)) -* **reactivity:** onCleanup also needs to be cleaned ([#8655](https://github.com/vuejs/core/issues/8655)) ([73fd810](https://github.com/vuejs/core/commit/73fd810eebdd383a2b4629f67736c4db1f428abd)), closes [#5151](https://github.com/vuejs/core/issues/5151) [#7695](https://github.com/vuejs/core/issues/7695) -* **ssr:** hydration `__vnode` missing for devtools ([#9328](https://github.com/vuejs/core/issues/9328)) ([5156ac5](https://github.com/vuejs/core/commit/5156ac5b38cfa80d3db26f2c9bf40cb22a7521cb)) -* **types:** allow falsy value types in `StyleValue` ([#7954](https://github.com/vuejs/core/issues/7954)) ([17aa92b](https://github.com/vuejs/core/commit/17aa92b79b31d8bb8b5873ddc599420cb9806db8)), closes [#7955](https://github.com/vuejs/core/issues/7955) -* **types:** defineCustomElement using defineComponent return type with emits ([#7937](https://github.com/vuejs/core/issues/7937)) ([5d932a8](https://github.com/vuejs/core/commit/5d932a8e6d14343c9d7fc7c2ecb58ac618b2f938)), closes [#7782](https://github.com/vuejs/core/issues/7782) -* **types:** fix `unref` and `toValue` when input union type contains ComputedRef ([#8748](https://github.com/vuejs/core/issues/8748)) ([176d476](https://github.com/vuejs/core/commit/176d47671271b1abc21b1508e9a493c7efca6451)), closes [#8747](https://github.com/vuejs/core/issues/8747) [#8857](https://github.com/vuejs/core/issues/8857) -* **types:** fix instance type when props type is incompatible with setup returned type ([#7338](https://github.com/vuejs/core/issues/7338)) ([0e1e8f9](https://github.com/vuejs/core/commit/0e1e8f919e5a74cdaadf9c80ee135088b25e7fa3)), closes [#5885](https://github.com/vuejs/core/issues/5885) -* **types:** fix shallowRef return type with union value type ([#7853](https://github.com/vuejs/core/issues/7853)) ([7c44800](https://github.com/vuejs/core/commit/7c448000b0def910c2cfabfdf7ff20a3d6bc844f)), closes [#7852](https://github.com/vuejs/core/issues/7852) -* **types:** more precise types for class bindings ([#8012](https://github.com/vuejs/core/issues/8012)) ([46e3374](https://github.com/vuejs/core/commit/46e33744c890bd49482c5e5c5cdea44e00ec84d5)) -* **types:** remove optional properties from defineProps return type ([#6421](https://github.com/vuejs/core/issues/6421)) ([94c049d](https://github.com/vuejs/core/commit/94c049d930d922069e38ea8700d7ff0970f71e61)), closes [#6420](https://github.com/vuejs/core/issues/6420) -* **types:** return type of withDefaults should be readonly ([#8601](https://github.com/vuejs/core/issues/8601)) ([f15debc](https://github.com/vuejs/core/commit/f15debc01acb22d23f5acee97e6f02db88cef11a)) -* **types:** revert class type restrictions ([5d077c8](https://github.com/vuejs/core/commit/5d077c8754cc14f85d2d6d386df70cf8c0d93842)), closes [#8012](https://github.com/vuejs/core/issues/8012) -* **types:** update jsx type definitions ([#8607](https://github.com/vuejs/core/issues/8607)) ([58e2a94](https://github.com/vuejs/core/commit/58e2a94871ae06a909c5f8bad07fb401193e6a38)) -* **types:** widen ClassValue type ([2424013](https://github.com/vuejs/core/commit/242401305944422d0c361b16101a4d18908927af)) -* **v-model:** avoid overwriting number input with same value ([#7004](https://github.com/vuejs/core/issues/7004)) ([40f4b77](https://github.com/vuejs/core/commit/40f4b77bb570868cb6e47791078767797e465989)), closes [#7003](https://github.com/vuejs/core/issues/7003) -* **v-model:** unnecessary value binding error should apply to dynamic instead of static binding ([2859b65](https://github.com/vuejs/core/commit/2859b653c9a22460e60233cac10fe139e359b046)), closes [#3596](https://github.com/vuejs/core/issues/3596) +### Potential Actions Needed +1. To fully leverage new features in 3.4, it is recommended to also update the following dependencies when upgrading to 3.4: + - Volar / vue-tsc@^1.8.27 (**required**) + - @vitejs/plugin-vue@^5.0.0 (if using Vite) + - nuxt@^3.9.0 (if using Nuxt) + - vue-loader@^17.4.0 (if using webpack or vue-cli) -## [3.3.8](https://github.com/vuejs/core/compare/v3.3.7...v3.3.8) (2023-11-06) - - -### Bug Fixes - -* **compile-sfc:** support `Error` type in `defineProps` ([#5955](https://github.com/vuejs/core/issues/5955)) ([a989345](https://github.com/vuejs/core/commit/a9893458ec519aae442e1b99e64e6d74685cd22c)) -* **compiler-core:** known global should be shadowed by local variables in expression rewrite ([#9492](https://github.com/vuejs/core/issues/9492)) ([a75d1c5](https://github.com/vuejs/core/commit/a75d1c5c6242e91a73cc5ba01e6da620dea0b3d9)), closes [#9482](https://github.com/vuejs/core/issues/9482) -* **compiler-sfc:** fix dynamic directive arguments usage check for slots ([#9495](https://github.com/vuejs/core/issues/9495)) ([b39fa1f](https://github.com/vuejs/core/commit/b39fa1f8157647859331ce439c42ae016a49b415)), closes [#9493](https://github.com/vuejs/core/issues/9493) -* **deps:** update dependency @vue/repl to ^2.6.2 ([#9536](https://github.com/vuejs/core/issues/9536)) ([5cef325](https://github.com/vuejs/core/commit/5cef325f41e3b38657c72fa1a38dedeee1c7a60a)) -* **deps:** update dependency @vue/repl to ^2.6.3 ([#9540](https://github.com/vuejs/core/issues/9540)) ([176d590](https://github.com/vuejs/core/commit/176d59058c9aecffe9da4d4311e98496684f06d4)) -* **hydration:** fix tagName access error on comment/text node hydration mismatch ([dd8a0cf](https://github.com/vuejs/core/commit/dd8a0cf5dcde13d2cbd899262a0e07f16e14e489)), closes [#9531](https://github.com/vuejs/core/issues/9531) -* **types:** avoid exposing lru-cache types in generated dts ([462aeb3](https://github.com/vuejs/core/commit/462aeb3b600765e219ded2ee9a0ed1e74df61de0)), closes [#9521](https://github.com/vuejs/core/issues/9521) -* **warn:** avoid warning on empty children with Suspense ([#3962](https://github.com/vuejs/core/issues/3962)) ([405f345](https://github.com/vuejs/core/commit/405f34587a63a5f1e3d147b9848219ea98acc22d)) - +2. If using TSX with Vue, check actions needed in [Removed: Global JSX Namespace](https://blog.vuejs.org/posts/vue-3-4#global-jsx-namespace). +3. Make sure you are no longer using any deprecated features (if you are, you should have warnings in the console telling you so). They may have been [removed in 3.4](https://blog.vuejs.org/posts/vue-3-4#other-removed-features). -## [3.3.7](https://github.com/vuejs/core/compare/v3.3.6...v3.3.7) (2023-10-24) +### Features +* **general:** MathML support ([#7836](https://github.com/vuejs/core/issues/7836)) ([d42b6ba](https://github.com/vuejs/core/commit/d42b6ba3f530746eb1221eb7a4be0f44eb56f7d3)), closes [#7820](https://github.com/vuejs/core/issues/7820) +* **reactivity:** more efficient reactivity system ([#5912](https://github.com/vuejs/core/issues/5912)) ([16e06ca](https://github.com/vuejs/core/commit/16e06ca08f5a1e2af3fc7fb35de153dbe0c3087d)), closes [#311](https://github.com/vuejs/core/issues/311) [#1811](https://github.com/vuejs/core/issues/1811) [#6018](https://github.com/vuejs/core/issues/6018) [#7160](https://github.com/vuejs/core/issues/7160) [#8714](https://github.com/vuejs/core/issues/8714) [#9149](https://github.com/vuejs/core/issues/9149) [#9419](https://github.com/vuejs/core/issues/9419) [#9464](https://github.com/vuejs/core/issues/9464) +* **reactivity:** expose last result for computed getter ([#9497](https://github.com/vuejs/core/issues/9497)) ([48b47a1](https://github.com/vuejs/core/commit/48b47a1ab63577e2dbd91947eea544e3ef185b85)) +* **runtime-core / dx:** link errors to docs in prod build ([#9165](https://github.com/vuejs/core/issues/9165)) ([9f8ba98](https://github.com/vuejs/core/commit/9f8ba9821fe166f77e63fa940e9e7e13ec3344fa)) +* **runtime-core:** add `once` option to watch ([#9034](https://github.com/vuejs/core/issues/9034)) ([a645e7a](https://github.com/vuejs/core/commit/a645e7aa51006516ba668b3a4365d296eb92ee7d)) +* **runtime-core:** provide full props to props validator functions ([#3258](https://github.com/vuejs/core/issues/3258)) ([8e27692](https://github.com/vuejs/core/commit/8e27692029a4645cd54287f776c0420f2b82740b)) +* **compiler-core:** export error message ([#8729](https://github.com/vuejs/core/issues/8729)) ([f7e80ee](https://github.com/vuejs/core/commit/f7e80ee4a065a9eaba98720abf415d9e87756cbd)) +* **compiler-core:** support specifying root namespace when parsing ([40f72d5](https://github.com/vuejs/core/commit/40f72d5e50b389cb11b7ca13461aa2a75ddacdb4)) +* **compiler-core:** support v-bind shorthand for key and value with the same name ([#9451](https://github.com/vuejs/core/issues/9451)) ([26399aa](https://github.com/vuejs/core/commit/26399aa6fac1596b294ffeba06bb498d86f5508c)) +* **compiler-core:** improve parsing tolerance for language-tools ([41ff68e](https://github.com/vuejs/core/commit/41ff68ea579d933333392146625560359acb728a)) +* **compiler-core:** support accessing Error as global in template expressions ([#7018](https://github.com/vuejs/core/issues/7018)) ([bcca475](https://github.com/vuejs/core/commit/bcca475dbc58d76434cd8120b94929758cee2825)) +* **compiler-core:** lift vnode hooks deprecation warning to error ([8abc754](https://github.com/vuejs/core/commit/8abc754d5d86d9dfd5a7927b846f1a743f352364)) +* **compiler-core:** export runtime error strings ([#9301](https://github.com/vuejs/core/issues/9301)) ([feb2f2e](https://github.com/vuejs/core/commit/feb2f2edce2d91218a5e9a52c81e322e4033296b)) +* **compiler-core:** add current filename to TransformContext ([#8950](https://github.com/vuejs/core/issues/8950)) ([638f1ab](https://github.com/vuejs/core/commit/638f1abbb632000553e2b7d75e87c95d8ca192d6)) +* **compiler-sfc:** analyze import usage in template via AST ([#9729](https://github.com/vuejs/core/issues/9729)) ([e8bbc94](https://github.com/vuejs/core/commit/e8bbc946cba6bf74c9da56f938b67d2a04c340ba)), closes [#8897](https://github.com/vuejs/core/issues/8897) [nuxt/nuxt#22416](https://github.com/nuxt/nuxt/issues/22416) +* **compiler-sfc:** expose resolve type-based props and emits ([#8874](https://github.com/vuejs/core/issues/8874)) ([9e77580](https://github.com/vuejs/core/commit/9e77580c0c2f0d977bd0031a1d43cc334769d433)) +* **compiler-sfc:** bump postcss-modules to v6 ([2a507e3](https://github.com/vuejs/core/commit/2a507e32f0e2ef73813705a568b8633f68bda7a9)) +* **compiler-sfc:** promote defineModel stable ([#9598](https://github.com/vuejs/core/issues/9598)) ([ef688ba](https://github.com/vuejs/core/commit/ef688ba92bfccbc8b7ea3997eb297665d13e5249)) +* **compiler-sfc:** support import attributes and `using` syntax ([#8786](https://github.com/vuejs/core/issues/8786)) ([5b2bd1d](https://github.com/vuejs/core/commit/5b2bd1df78e8ff524c3a184adaa284681aba6574)) +* **compiler-sfc:** `defineModel` support local mutation by default, remove local option ([f74785b](https://github.com/vuejs/core/commit/f74785bc4ad351102dde17fdfd2c7276b823111f)), closes [/github.com/vuejs/rfcs/discussions/503#discussioncomment-7566278](https://github.com//github.com/vuejs/rfcs/discussions/503/issues/discussioncomment-7566278) +* **ssr:** add `__VUE_PROD_HYDRATION_MISMATCH_DETAILS__` feature flag ([#9550](https://github.com/vuejs/core/issues/9550)) ([bc7698d](https://github.com/vuejs/core/commit/bc7698dbfed9b5327a93565f9df336ae5a94d605)) +* **ssr:** improve ssr hydration mismatch checks ([#5953](https://github.com/vuejs/core/issues/5953)) ([2ffc1e8](https://github.com/vuejs/core/commit/2ffc1e8cfdc6ec9c45c4a4dd8e3081b2aa138f1e)), closes [#5063](https://github.com/vuejs/core/issues/5063) +* **types:** use enum to replace const enum ([#9261](https://github.com/vuejs/core/issues/9261)) ([fff7b86](https://github.com/vuejs/core/commit/fff7b864f4292d0430ba2bda7098ad43876b0210)), closes [#1228](https://github.com/vuejs/core/issues/1228) +* **types:** add emits and slots type to `FunctionalComponent` ([#8644](https://github.com/vuejs/core/issues/8644)) ([927ab17](https://github.com/vuejs/core/commit/927ab17cfc645e82d061fdf227c34689491268e1)) +* **types:** export `AriaAttributes` type ([#8909](https://github.com/vuejs/core/issues/8909)) ([fd0b6ba](https://github.com/vuejs/core/commit/fd0b6ba01660499fa07b0cf360eefaac8cca8287)) +* **types:** export `ObjectPlugin` and `FunctionPlugin` types ([#8946](https://github.com/vuejs/core/issues/8946)) ([fa4969e](https://github.com/vuejs/core/commit/fa4969e7a3aefa6863203f9294fc5e769ddf6d8f)), closes [#8577](https://github.com/vuejs/core/issues/8577) +* **types:** expose `DefineProps` type ([096ba81](https://github.com/vuejs/core/commit/096ba81817b7da15f61bc55fc1a93f72ac9586e0)) +* **types:** expose `PublicProps` type ([#2403](https://github.com/vuejs/core/issues/2403)) ([44135dc](https://github.com/vuejs/core/commit/44135dc95fb8fea26b84d1433839d28b8c21f708)) +* **types:** improve event type inference when using `h` with native elements ([#9756](https://github.com/vuejs/core/issues/9756)) ([a625376](https://github.com/vuejs/core/commit/a625376ac8901eea81bf3c66cb531f2157f073ef)) +* **types:** provide `ComponentInstance` type ([#5408](https://github.com/vuejs/core/issues/5408)) ([bfb8565](https://github.com/vuejs/core/commit/bfb856565d3105db4b18991ae9e404e7cc989b25)) +* **types:** support passing generics when registering global directives ([#9660](https://github.com/vuejs/core/issues/9660)) ([a41409e](https://github.com/vuejs/core/commit/a41409ed02a8c7220e637f56caf6813edeb077f8)) -### Bug Fixes -* **compiler-sfc:** avoid gen useCssVars when targeting SSR ([#6979](https://github.com/vuejs/core/issues/6979)) ([c568778](https://github.com/vuejs/core/commit/c568778ea3265d8e57f788b00864c9509bf88a4e)), closes [#6926](https://github.com/vuejs/core/issues/6926) -* **compiler-ssr:** proper scope analysis for ssr vnode slot fallback ([#7184](https://github.com/vuejs/core/issues/7184)) ([e09c26b](https://github.com/vuejs/core/commit/e09c26bc9bc4394c2c2d928806d382515c2676f3)), closes [#7095](https://github.com/vuejs/core/issues/7095) -* correctly resolve types from relative paths on Windows ([#9446](https://github.com/vuejs/core/issues/9446)) ([089d36d](https://github.com/vuejs/core/commit/089d36d167dc7834065b03ca689f9b6a44eead8a)), closes [#8671](https://github.com/vuejs/core/issues/8671) -* **hmr:** fix hmr error for hoisted children array in v-for ([7334376](https://github.com/vuejs/core/commit/733437691f70ebca8dd6cc3bc8356f5b57d4d5d8)), closes [#6978](https://github.com/vuejs/core/issues/6978) [#7114](https://github.com/vuejs/core/issues/7114) -* **reactivity:** assigning array.length while observing a symbol property ([#7568](https://github.com/vuejs/core/issues/7568)) ([e9e2778](https://github.com/vuejs/core/commit/e9e2778e9ec5cca07c1df5f0c9b7b3595a1a3244)) -* **scheduler:** ensure jobs are in the correct order ([#7748](https://github.com/vuejs/core/issues/7748)) ([a8f6638](https://github.com/vuejs/core/commit/a8f663867b8cd2736b82204bc58756ef02441276)), closes [#7576](https://github.com/vuejs/core/issues/7576) -* **ssr:** fix hydration mismatch for disabled teleport at component root ([#9399](https://github.com/vuejs/core/issues/9399)) ([d8990fc](https://github.com/vuejs/core/commit/d8990fc6182d1c2cf0a8eab7b35a9d04df668507)), closes [#6152](https://github.com/vuejs/core/issues/6152) -* **Suspense:** calling hooks before the transition finishes ([#9388](https://github.com/vuejs/core/issues/9388)) ([00de3e6](https://github.com/vuejs/core/commit/00de3e61ed7a55e7d6c2e1987551d66ad0f909ff)), closes [#5844](https://github.com/vuejs/core/issues/5844) [#5952](https://github.com/vuejs/core/issues/5952) -* **transition/ssr:** make transition appear work with SSR ([#8859](https://github.com/vuejs/core/issues/8859)) ([5ea8a8a](https://github.com/vuejs/core/commit/5ea8a8a4fab4e19a71e123e4d27d051f5e927172)), closes [#6951](https://github.com/vuejs/core/issues/6951) -* **types:** fix ComponentCustomProps augmentation ([#9468](https://github.com/vuejs/core/issues/9468)) ([7374e93](https://github.com/vuejs/core/commit/7374e93f0281f273b90ab5a6724cc47332a01d6c)), closes [#8376](https://github.com/vuejs/core/issues/8376) -* **types:** improve `h` overload to support union of string and component ([#5432](https://github.com/vuejs/core/issues/5432)) ([16ecb44](https://github.com/vuejs/core/commit/16ecb44c89cd8299a3b8de33cccc2e2cc36f065b)), closes [#5431](https://github.com/vuejs/core/issues/5431) +### Performance Improvements +* **compiler-sfc:** avoid sfc source map unnecessary serialization and parsing ([f15d2f6](https://github.com/vuejs/core/commit/f15d2f6cf69c0c39f8dfb5c33122790c68bf92e2)) +* **compiler-sfc:** remove magic-string trim on script ([e8e3ec6](https://github.com/vuejs/core/commit/e8e3ec6ca7392e43975c75b56eaaa711d5ea9410)) +* **compiler-sfc:** use faster source map addMapping ([50cde7c](https://github.com/vuejs/core/commit/50cde7cfbcc49022ba88f5f69fa9b930b483c282)) +* **compiler-core:** optimize away isBuiltInType ([66c0ed0](https://github.com/vuejs/core/commit/66c0ed0a3c1c6f37dafc6b1c52b75c6bf60e3136)) +* **compiler-core:** optimize position cloning ([2073236](https://github.com/vuejs/core/commit/20732366b9b3530d33b842cf1fc985919afb9317)) +* **codegen:** optimize line / column calculation during codegen ([3be53d9](https://github.com/vuejs/core/commit/3be53d9b974dae1a10eb795cade71ae765e17574)) +* **codegen:** optimize source map generation ([c11002f](https://github.com/vuejs/core/commit/c11002f16afd243a2b15b546816e73882eea9e4d)) +* **shared:** optimize makeMap ([ae6fba9](https://github.com/vuejs/core/commit/ae6fba94954bac6430902f77b0d1113a98a75b18)) -## [3.3.6](https://github.com/vuejs/core/compare/v3.3.5...v3.3.6) (2023-10-20) +### BREAKING CHANGES +#### Global JSX Registration Removed -### Bug Fixes +Starting in 3.4, Vue no longer registers the global `JSX` namespace by default. This is necessary to avoid global namespace collision with React so that TSX of both libs can co-exist in the same project. This should not affect SFC-only users with latest version of Volar. -* **compiler-sfc:** model name conflict ([#8798](https://github.com/vuejs/core/issues/8798)) ([df81da8](https://github.com/vuejs/core/commit/df81da8be97c8a1366563c7e3e01076ef02eb8f7)) -* **compiler-sfc:** support asset paths containing spaces ([#8752](https://github.com/vuejs/core/issues/8752)) ([36c99a9](https://github.com/vuejs/core/commit/36c99a9c6bb6bc306be054c3c8a85ff8ce50605a)) -* **compiler-ssr:** fix missing scopeId on server-rendered TransitionGroup ([#7557](https://github.com/vuejs/core/issues/7557)) ([61c1357](https://github.com/vuejs/core/commit/61c135742795aa5e3189a79c7dec6afa21bbc8d9)), closes [#7554](https://github.com/vuejs/core/issues/7554) -* **compiler-ssr:** fix ssr compile error for select with non-option children ([#9442](https://github.com/vuejs/core/issues/9442)) ([cdb2e72](https://github.com/vuejs/core/commit/cdb2e725e7ea297f1f4180fb04889a3b757bc84e)), closes [#9440](https://github.com/vuejs/core/issues/9440) -* **runtime-core:** delete stale slots which are present but undefined ([#6484](https://github.com/vuejs/core/issues/6484)) ([75b8722](https://github.com/vuejs/core/commit/75b872213574cb37e2c9e8a15f65613f867ca9a6)), closes [#9109](https://github.com/vuejs/core/issues/9109) -* **runtime-core:** fix error when using cssvars with disabled teleport ([#7341](https://github.com/vuejs/core/issues/7341)) ([8f0472c](https://github.com/vuejs/core/commit/8f0472c9abedb337dc256143b69d8ab8759dbf5c)), closes [#7342](https://github.com/vuejs/core/issues/7342) -* **teleport:** ensure descendent component would be unmounted correctly ([#6529](https://github.com/vuejs/core/issues/6529)) ([4162311](https://github.com/vuejs/core/commit/4162311efdb0db5ca458542e1604b19efa2fae0e)), closes [#6347](https://github.com/vuejs/core/issues/6347) -* **types:** support contenteditable="plaintext-only" ([#8796](https://github.com/vuejs/core/issues/8796)) ([26ca89e](https://github.com/vuejs/core/commit/26ca89e5cf734fbef81e182050d2a215ec8a437b)) +If you are using TSX, there are two options: +1. Explicitly set [jsxImportSource](https://www.typescriptlang.org/tsconfig#jsxImportSource) to `'vue'` in `tsconfig.json` before upgrading to 3.4. You can also opt-in per file by adding a `/* @jsxImportSource vue */` comment at the top of the file. -### Performance Improvements +2. If you have code that depends on the presence of the global `JSX` namespace, e.g. usage of types like `JSX.Element` etc., you can retain the exact pre-3.4 global behavior by explicitly referencing `vue/jsx`, which registers the global `JSX` namespace. -* replace Map/Set with WeakMap/WeakSet ([#8549](https://github.com/vuejs/core/issues/8549)) ([712f96d](https://github.com/vuejs/core/commit/712f96d6ac4d3d984732cba448cb84624daba850)) +Note that this is a type-only breaking change in a minor release, which adheres to our [release policy](https://vuejs.org/about/releases.html#semantic-versioning-edge-cases). +#### Deprecated Features Removed +- [Reactivity Transform](https://vuejs.org/guide/extras/reactivity-transform.html) was marked deprecated in 3.3 and is now removed in 3.4. This change does not require a major due to the feature being experimental. Users who wish to continue using the feature can do so via the [Vue Macros plugin](https://vue-macros.dev/features/reactivity-transform.html). +- `app.config.unwrapInjectedRef` has been removed. It was deprecated and enabled by default in 3.3. In 3.4 it is no longer possible to disable this behavior. +- `@vnodeXXX` event listeners in templates are now a compiler error instead of a deprecation warning. Use `@vue:XXX` listeners instead. +- `v-is` directive has been removed. It was deprecated in 3.3. Use the [`is` attribute with `vue:` prefix](https://vuejs.org/api/built-in-special-attributes.html#is) instead. -## [3.3.5](https://github.com/vuejs/core/compare/v3.3.4...v3.3.5) (2023-10-20) +# [3.4.0-rc.3](https://github.com/vuejs/core/compare/v3.4.0-rc.2...v3.4.0-rc.3) (2023-12-27) ### Bug Fixes -* add isGloballyWhitelisted back, but deprecated ([#8556](https://github.com/vuejs/core/issues/8556)) ([63dfe8e](https://github.com/vuejs/core/commit/63dfe8eab499979bcc2f7829e82464e13899c895)), closes [#8416](https://github.com/vuejs/core/issues/8416) -* **build:** disable useDefineForClassFields in esbuild ([#9252](https://github.com/vuejs/core/issues/9252)) ([6d14fa8](https://github.com/vuejs/core/commit/6d14fa88e85d4c9e264be394ddb37a54ca6738a8)) -* **compat:** return value of vue compat set() ([#9377](https://github.com/vuejs/core/issues/9377)) ([e3c2d69](https://github.com/vuejs/core/commit/e3c2d699f694d9500ddee78571172a24f0e3b17a)) -* **compiler-sfc:** don't hoist props and emit ([#8535](https://github.com/vuejs/core/issues/8535)) ([24db951](https://github.com/vuejs/core/commit/24db9516d8b4857182ec1a3af86cb7346691679b)), closes [#7805](https://github.com/vuejs/core/issues/7805) [#7812](https://github.com/vuejs/core/issues/7812) -* **compiler-sfc:** don't registerTS when bundling for browsers ([#8582](https://github.com/vuejs/core/issues/8582)) ([6f45f76](https://github.com/vuejs/core/commit/6f45f76df2c43796b35067ef8f8b9a7bca454040)) -* **compiler-sfc:** fix using imported ref as template ref during dev ([#7593](https://github.com/vuejs/core/issues/7593)) ([776ebf2](https://github.com/vuejs/core/commit/776ebf25b2e7570e78ac1c148fc45c823c21a542)), closes [#7567](https://github.com/vuejs/core/issues/7567) -* **compiler-sfc:** handle dynamic directive arguments in template usage check ([#8538](https://github.com/vuejs/core/issues/8538)) ([e404a69](https://github.com/vuejs/core/commit/e404a699f48ae5c5a5da947f42679343192158c7)), closes [#8537](https://github.com/vuejs/core/issues/8537) -* **compiler-sfc:** ignore style v-bind in double slash comments ([#5409](https://github.com/vuejs/core/issues/5409)) ([381b497](https://github.com/vuejs/core/commit/381b4977af25ba5392704f72ec6b3f2394d87ae7)) -* **compiler-sfc:** pass options directly to stylus ([#3848](https://github.com/vuejs/core/issues/3848)) ([d6446a6](https://github.com/vuejs/core/commit/d6446a6d40774b79045a9ddba7b5fd5201d51450)) -* **compiler-sfc:** support resolve multiple re-export /w same source type name ([#8365](https://github.com/vuejs/core/issues/8365)) ([4fa8da8](https://github.com/vuejs/core/commit/4fa8da8576717c619e1e8c04d19038488c75fbea)), closes [#8364](https://github.com/vuejs/core/issues/8364) -* **compiler-sfc:** typo in experimental feature warnings ([#8513](https://github.com/vuejs/core/issues/8513)) ([fd1a3f9](https://github.com/vuejs/core/commit/fd1a3f95990d7c372fa1c0c40c55caca761a33a4)) -* **deps:** update dependency monaco-editor to ^0.44.0 ([#9237](https://github.com/vuejs/core/issues/9237)) ([8611874](https://github.com/vuejs/core/commit/8611874e09a827b6491173836c8942284d5de22c)) -* **deps:** update playground ([#9154](https://github.com/vuejs/core/issues/9154)) ([c8566a2](https://github.com/vuejs/core/commit/c8566a22b7cf37e6aefab7bad7b97ce2db9fae4c)) -* **playground:** fix github button style ([#7722](https://github.com/vuejs/core/issues/7722)) ([5ee992c](https://github.com/vuejs/core/commit/5ee992cfeabc6c4b871980c6057d0ac7140ad2fa)) -* **runtime-core:** swap client/server debug labels ([#9089](https://github.com/vuejs/core/issues/9089)) ([8f311c6](https://github.com/vuejs/core/commit/8f311c6f823f6776ca1c49bfbbbf8c7d9dea9cf1)) -* **ssr:** render correct initial selected state for select with v-model ([#7432](https://github.com/vuejs/core/issues/7432)) ([201c46d](https://github.com/vuejs/core/commit/201c46df07a38f3c2b73f384e8e6846dc62f224e)), closes [#7392](https://github.com/vuejs/core/issues/7392) -* **ssr:** reset current instance if setting up options component errors ([#7743](https://github.com/vuejs/core/issues/7743)) ([020851e](https://github.com/vuejs/core/commit/020851e57d9a9f727c6ea07e9c1575430af02b73)), closes [#7733](https://github.com/vuejs/core/issues/7733) -* **teleport:** handle target change while disabled ([#7837](https://github.com/vuejs/core/issues/7837)) ([140a89b](https://github.com/vuejs/core/commit/140a89b833bceed60838182b875d2953c70af114)), closes [#7835](https://github.com/vuejs/core/issues/7835) -* **transition:** handle possible auto value for transition/animation durations ([96c76fa](https://github.com/vuejs/core/commit/96c76facb7de37fc241ccd55e121fd60a49a1452)), closes [#8409](https://github.com/vuejs/core/issues/8409) -* **types/jsx:** add `inert` attribute and missing `hidden` values ([#8090](https://github.com/vuejs/core/issues/8090)) ([ceb0732](https://github.com/vuejs/core/commit/ceb0732e0b1bb4c8c505d80e97ff6fc89035fa90)) -* **types/jsx:** add missing loading attr for img element ([#6160](https://github.com/vuejs/core/issues/6160)) ([68d6b43](https://github.com/vuejs/core/commit/68d6b43f7e29b76aab2c6c1882885380a43fa3e3)) -* **types:** correct withDefaults return type for boolean prop with undefined default value ([#8602](https://github.com/vuejs/core/issues/8602)) ([f07cb18](https://github.com/vuejs/core/commit/f07cb18fedf9a446545aadf76bcdfb957c7ebcbd)) -* **types:** ensure nextTick return type reflect correct Promise value ([#8406](https://github.com/vuejs/core/issues/8406)) ([6a22b1f](https://github.com/vuejs/core/commit/6a22b1f6c287b60eda385df8a514335af8e040ea)) -* **types:** support correct types for style on svg elements ([#6322](https://github.com/vuejs/core/issues/6322)) ([364dc53](https://github.com/vuejs/core/commit/364dc53c7cc6f97d812ad175199c698faa92538e)) +* also export runtime error strings in all cjs builds ([38706e4](https://github.com/vuejs/core/commit/38706e4a1e5e5380e7df910b2a784d0a9bc9db29)) -### Performance Improvements +### Features -* **compiler-sfc:** lazy require typescript ([d2c3d8b](https://github.com/vuejs/core/commit/d2c3d8b70b2df6e16f053a7ac58e6b04e7b2078f)) -* **custom-element:** cancel `MutationObserver` listener when disconnected ([#8666](https://github.com/vuejs/core/issues/8666)) ([24d98f0](https://github.com/vuejs/core/commit/24d98f03276de5b0fbced5a4c9d61b24e7d9d084)) -* mark `defineComponent` as side-effects-free ([#8512](https://github.com/vuejs/core/issues/8512)) ([438027c](https://github.com/vuejs/core/commit/438027cf9ecb63260f59d3027e0b188717694795)) +* **defineModel:** support modifiers and transformers ([a772031](https://github.com/vuejs/core/commit/a772031ea8431bd732ffeaeaac09bd76a0daec9b)) -## [3.3.4](https://github.com/vuejs/core/compare/v3.3.3...v3.3.4) (2023-05-18) +# [3.4.0-rc.2](https://github.com/vuejs/core/compare/v3.4.0-rc.1...v3.4.0-rc.2) (2023-12-26) ### Bug Fixes -* **build:** ensure correct typing for node esm ([d621d4c](https://github.com/vuejs/core/commit/d621d4c646b2d7b190fbd44ad1fd04512b3de300)) -* **build:** fix __DEV__ flag replacement edge case ([8b7c04b](https://github.com/vuejs/core/commit/8b7c04b18f73aad9a08dd57eba90101b5b2aef28)), closes [#8353](https://github.com/vuejs/core/issues/8353) -* **compiler-sfc:** handle imported types from default exports ([5aec717](https://github.com/vuejs/core/commit/5aec717a2402652306085f58432ba3ab91848a74)), closes [#8355](https://github.com/vuejs/core/issues/8355) - - +* **deps:** update dependency @vue/repl to ^3.1.0 ([#9911](https://github.com/vuejs/core/issues/9911)) ([f96c413](https://github.com/vuejs/core/commit/f96c413e8ef2f24cacda5bb499492922f62c6e8b)) +* **types:** fix distribution of union types when unwrapping setup bindings ([#9909](https://github.com/vuejs/core/issues/9909)) ([0695c69](https://github.com/vuejs/core/commit/0695c69e0dfaf99882a623fe75b433c9618ea648)), closes [#9903](https://github.com/vuejs/core/issues/9903) +* **warning:** ensure prod hydration warnings actually work ([b4ebe7a](https://github.com/vuejs/core/commit/b4ebe7ae8b904f28cdda33caf87bc05718d3a08a)) -## [3.3.3](https://github.com/vuejs/core/compare/v3.3.2...v3.3.3) (2023-05-18) +### Features -### Bug Fixes - -* avoid regex s flag for old browsers ([91f1c62](https://github.com/vuejs/core/commit/91f1c62e6384a8b09f90e7e43b8d347901e529a0)), closes [#8316](https://github.com/vuejs/core/issues/8316) -* **build:** fix dev flag replacement in esm-builder builds ([#8314](https://github.com/vuejs/core/issues/8314)) ([003836f](https://github.com/vuejs/core/commit/003836f90e1f00ebd04b77ec07ccfa4e649a2ff4)), closes [#8312](https://github.com/vuejs/core/issues/8312) -* **compiler-sfc:** don't hoist regexp literial ([#8300](https://github.com/vuejs/core/issues/8300)) ([8ec73a3](https://github.com/vuejs/core/commit/8ec73a3aea7a52e9479f107ae5737761166ddae6)) -* **compiler-sfc:** fix props destructing default value type checking with unresolved type ([#8340](https://github.com/vuejs/core/issues/8340)) ([f69dbab](https://github.com/vuejs/core/commit/f69dbabf8794426c3e9ed33ae77dd8ce655eafd2)), closes [#8326](https://github.com/vuejs/core/issues/8326) -* **compiler-sfc:** fix type import from path aliased vue file ([fab9c72](https://github.com/vuejs/core/commit/fab9c727805c6186c490f99023e8cf5401b0b5a9)), closes [#8348](https://github.com/vuejs/core/issues/8348) -* **compiler-sfc:** handle ts files with relative imports with .js extension ([b36addd](https://github.com/vuejs/core/commit/b36addd3bde07467e9ff5641bd1c2bdc3085944c)), closes [#8339](https://github.com/vuejs/core/issues/8339) -* **compiler-sfc:** parses correctly when inline mode is off ([#8337](https://github.com/vuejs/core/issues/8337)) ([ecbd42a](https://github.com/vuejs/core/commit/ecbd42a1444e3c599e464dec002e43d548d99669)), closes [#6088](https://github.com/vuejs/core/issues/6088) -* **compiler-sfc:** support defineEmits type reference with unions ([#8299](https://github.com/vuejs/core/issues/8299)) ([b133e0f](https://github.com/vuejs/core/commit/b133e0fd97b0b4fabbb43151c19031b8fb47c05b)), closes [#7943](https://github.com/vuejs/core/issues/7943) -* **types:** support generic usage with withDefaults + defineProps ([#8335](https://github.com/vuejs/core/issues/8335)) ([216f269](https://github.com/vuejs/core/commit/216f26995b63c2df26ca0f39f390fe8d59cdabfa)), closes [#8310](https://github.com/vuejs/core/issues/8310) [#8331](https://github.com/vuejs/core/issues/8331) [#8325](https://github.com/vuejs/core/issues/8325) +* **compiler-sfc:** export aggregated error messages for compiler-core and compiler-dom ([25c726e](https://github.com/vuejs/core/commit/25c726eca81fc384b41fafbeba5e8dfcda1f030f)) -## [3.3.2](https://github.com/vuejs/core/compare/v3.3.1...v3.3.2) (2023-05-12) +# [3.4.0-rc.1](https://github.com/vuejs/core/compare/v3.4.0-beta.4...v3.4.0-rc.1) (2023-12-25) ### Bug Fixes -* **compiler-core:** treat floating point numbers as constants ([8dc8cf8](https://github.com/vuejs/core/commit/8dc8cf852bf8057aa5c4b5670f09e8c28a168b73)), closes [#8295](https://github.com/vuejs/core/issues/8295) -* **compiler-dom:** do not throw in production on side effect tags ([c454b9d](https://github.com/vuejs/core/commit/c454b9d7f431d57abedb7184d1e4059914c4463f)), closes [#8287](https://github.com/vuejs/core/issues/8287) [#8292](https://github.com/vuejs/core/issues/8292) -* **compiler-sfc:** fix regression on props destructure when transform is not enabled ([f25bd37](https://github.com/vuejs/core/commit/f25bd37c6707fde19d164d90a38de41168941f4b)), closes [#8289](https://github.com/vuejs/core/issues/8289) -* **compiler-sfc:** handle prop keys that need escaping ([#7803](https://github.com/vuejs/core/issues/7803)) ([690ef29](https://github.com/vuejs/core/commit/690ef296357c7fc09f66ba9408df548e117f686f)), closes [#8291](https://github.com/vuejs/core/issues/8291) -* **compiler-sfc:** properly parse d.ts files when resolving types ([aa1e77d](https://github.com/vuejs/core/commit/aa1e77d532b951ea5d3a5e26214a8b0c9c02fb6f)), closes [#8285](https://github.com/vuejs/core/issues/8285) -* **compiler-sfc:** raise specific warning for failed extends and allow ignoring extends ([8235072](https://github.com/vuejs/core/commit/82350721a408e1f552c613c05971439d6c218d87)), closes [#8286](https://github.com/vuejs/core/issues/8286) +* **compiler-core:** fix parsing `', + { parseMode: 'sfc' }, + ) + const element = ast.children[0] as ElementNode + expect(element).toMatchObject({ + type: NodeTypes.ELEMENT, + ns: Namespaces.HTML, + tag: 'script', + tagType: ElementTypes.ELEMENT, + codegenNode: undefined, + children: [], + innerLoc: { + start: { column: 67, line: 1, offset: 66 }, + end: { column: 67, line: 1, offset: 66 }, + }, + props: [ + { + loc: { + source: 'setup', + end: { column: 14, line: 1, offset: 13 }, + start: { column: 9, line: 1, offset: 8 }, + }, + name: 'setup', + nameLoc: { + source: 'setup', + end: { column: 14, line: 1, offset: 13 }, + start: { column: 9, line: 1, offset: 8 }, + }, + type: NodeTypes.ATTRIBUTE, + value: undefined, + }, + { + loc: { + source: 'lang="ts"', + end: { column: 24, line: 1, offset: 23 }, + start: { column: 15, line: 1, offset: 14 }, + }, + name: 'lang', + nameLoc: { + source: 'lang', + end: { column: 19, line: 1, offset: 18 }, + start: { column: 15, line: 1, offset: 14 }, + }, + type: NodeTypes.ATTRIBUTE, + value: { + content: 'ts', + loc: { + source: '"ts"', + end: { column: 24, line: 1, offset: 23 }, + start: { column: 20, line: 1, offset: 19 }, + }, + type: NodeTypes.TEXT, + }, + }, + { + loc: { + source: 'generic="T extends Record"', + end: { column: 66, line: 1, offset: 65 }, + start: { column: 25, line: 1, offset: 24 }, + }, + name: 'generic', + nameLoc: { + source: 'generic', + end: { column: 32, line: 1, offset: 31 }, + start: { column: 25, line: 1, offset: 24 }, + }, + type: NodeTypes.ATTRIBUTE, + value: { + content: 'T extends Record', + loc: { + source: '"T extends Record"', + end: { column: 66, line: 1, offset: 65 }, + start: { column: 33, line: 1, offset: 32 }, + }, + type: NodeTypes.TEXT, + }, + }, + ], }) }) @@ -943,76 +1081,95 @@ describe('compiler: parse', () => { { type: NodeTypes.ATTRIBUTE, name: 'id', + nameLoc: { + start: { offset: 5, line: 1, column: 6 }, + end: { offset: 7, line: 1, column: 8 }, + source: 'id', + }, value: { type: NodeTypes.TEXT, content: 'a', loc: { start: { offset: 8, line: 1, column: 9 }, end: { offset: 9, line: 1, column: 10 }, - source: 'a' - } + source: 'a', + }, }, loc: { start: { offset: 5, line: 1, column: 6 }, end: { offset: 9, line: 1, column: 10 }, - source: 'id=a' - } + source: 'id=a', + }, }, { type: NodeTypes.ATTRIBUTE, name: 'class', + nameLoc: { + start: { offset: 10, line: 1, column: 11 }, + end: { offset: 15, line: 1, column: 16 }, + source: 'class', + }, value: { type: NodeTypes.TEXT, content: 'c', loc: { start: { offset: 16, line: 1, column: 17 }, end: { offset: 19, line: 1, column: 20 }, - source: '"c"' - } + source: '"c"', + }, }, loc: { start: { offset: 10, line: 1, column: 11 }, end: { offset: 19, line: 1, column: 20 }, - source: 'class="c"' - } + source: 'class="c"', + }, }, { type: NodeTypes.ATTRIBUTE, name: 'inert', + nameLoc: { + start: { offset: 20, line: 1, column: 21 }, + end: { offset: 25, line: 1, column: 26 }, + source: 'inert', + }, value: undefined, loc: { start: { offset: 20, line: 1, column: 21 }, end: { offset: 25, line: 1, column: 26 }, - source: 'inert' - } + source: 'inert', + }, }, { type: NodeTypes.ATTRIBUTE, name: 'style', + nameLoc: { + start: { offset: 26, line: 1, column: 27 }, + end: { offset: 31, line: 1, column: 32 }, + source: 'style', + }, value: { type: NodeTypes.TEXT, content: '', loc: { start: { offset: 32, line: 1, column: 33 }, end: { offset: 34, line: 1, column: 35 }, - source: "''" - } + source: "''", + }, }, loc: { start: { offset: 26, line: 1, column: 27 }, end: { offset: 34, line: 1, column: 35 }, - source: "style=''" - } - } + source: "style=''", + }, + }, ], - isSelfClosing: false, children: [], loc: { start: { offset: 0, line: 1, column: 1 }, end: { offset: 41, line: 1, column: 42 }, - source: '
' - } + source: '
', + }, }) }) @@ -1024,60 +1181,40 @@ describe('compiler: parse', () => { expect(element).toStrictEqual({ children: [], codegenNode: undefined, - isSelfClosing: false, loc: { - end: { - column: 10, - line: 3, - offset: 29 - }, + start: { column: 1, line: 1, offset: 0 }, + end: { column: 10, line: 3, offset: 29 }, source: '
', - start: { - column: 1, - line: 1, - offset: 0 - } }, ns: Namespaces.HTML, props: [ { - loc: { - end: { - column: 3, - line: 3, - offset: 22 - }, - source: 'class=" \n\t c \t\n "', - start: { - column: 6, - line: 1, - offset: 5 - } - }, name: 'class', + nameLoc: { + start: { column: 6, line: 1, offset: 5 }, + end: { column: 11, line: 1, offset: 10 }, + source: 'class', + }, type: NodeTypes.ATTRIBUTE, value: { content: 'c', loc: { - end: { - column: 3, - line: 3, - offset: 22 - }, + start: { column: 12, line: 1, offset: 11 }, + end: { column: 3, line: 3, offset: 22 }, source: '" \n\t c \t\n "', - start: { - column: 12, - line: 1, - offset: 11 - } }, - type: NodeTypes.TEXT - } - } - ], - tag: 'div', + type: NodeTypes.TEXT, + }, + loc: { + start: { column: 6, line: 1, offset: 5 }, + end: { column: 3, line: 3, offset: 22 }, + source: 'class=" \n\t c \t\n "', + }, + }, + ], + tag: 'div', tagType: ElementTypes.ELEMENT, - type: NodeTypes.ELEMENT + type: NodeTypes.ELEMENT, }) }) @@ -1088,14 +1225,15 @@ describe('compiler: parse', () => { expect(directive).toStrictEqual({ type: NodeTypes.DIRECTIVE, name: 'if', + rawName: 'v-if', arg: undefined, modifiers: [], exp: undefined, loc: { start: { offset: 5, line: 1, column: 6 }, end: { offset: 9, line: 1, column: 10 }, - source: 'v-if' - } + source: 'v-if', + }, }) }) @@ -1106,6 +1244,7 @@ describe('compiler: parse', () => { expect(directive).toStrictEqual({ type: NodeTypes.DIRECTIVE, name: 'if', + rawName: 'v-if', arg: undefined, modifiers: [], exp: { @@ -1116,14 +1255,14 @@ describe('compiler: parse', () => { loc: { start: { offset: 11, line: 1, column: 12 }, end: { offset: 12, line: 1, column: 13 }, - source: 'a' - } + source: 'a', + }, }, loc: { start: { offset: 5, line: 1, column: 6 }, end: { offset: 13, line: 1, column: 14 }, - source: 'v-if="a"' - } + source: 'v-if="a"', + }, }) }) @@ -1134,33 +1273,25 @@ describe('compiler: parse', () => { expect(directive).toStrictEqual({ type: NodeTypes.DIRECTIVE, name: 'on', + rawName: 'v-on:click', arg: { type: NodeTypes.SIMPLE_EXPRESSION, content: 'click', isStatic: true, constType: ConstantTypes.CAN_STRINGIFY, - loc: { + start: { column: 11, line: 1, offset: 10 }, + end: { column: 16, line: 1, offset: 15 }, source: 'click', - start: { - column: 11, - line: 1, - offset: 10 - }, - end: { - column: 16, - line: 1, - offset: 15 - } - } + }, }, modifiers: [], exp: undefined, loc: { start: { offset: 5, line: 1, column: 6 }, end: { offset: 15, line: 1, column: 16 }, - source: 'v-on:click' - } + source: 'v-on:click', + }, }) }) @@ -1173,8 +1304,7 @@ describe('compiler: parse', () => { loc: { start: { offset: 12, line: 1, column: 13 }, end: { offset: 16, line: 1, column: 17 }, - source: 'slot' - } + }, }) }) @@ -1184,11 +1314,11 @@ describe('compiler: parse', () => { const directive = (ast.children[0] as ElementNode) .props[0] as DirectiveNode expect(directive.arg).toMatchObject({ + content: 'item.item', loc: { start: { offset: 6, line: 1, column: 7 }, end: { offset: 15, line: 1, column: 16 }, - source: 'item.item' - } + }, }) }) @@ -1199,33 +1329,25 @@ describe('compiler: parse', () => { expect(directive).toStrictEqual({ type: NodeTypes.DIRECTIVE, name: 'on', + rawName: 'v-on:[event]', arg: { type: NodeTypes.SIMPLE_EXPRESSION, content: 'event', isStatic: false, constType: ConstantTypes.NOT_CONSTANT, - loc: { + start: { column: 11, line: 1, offset: 10 }, + end: { column: 18, line: 1, offset: 17 }, source: '[event]', - start: { - column: 11, - line: 1, - offset: 10 - }, - end: { - column: 18, - line: 1, - offset: 17 - } - } + }, }, modifiers: [], exp: undefined, loc: { start: { offset: 5, line: 1, column: 6 }, end: { offset: 17, line: 1, column: 18 }, - source: 'v-on:[event]' - } + source: 'v-on:[event]', + }, }) }) @@ -1236,14 +1358,15 @@ describe('compiler: parse', () => { expect(directive).toStrictEqual({ type: NodeTypes.DIRECTIVE, name: 'on', + rawName: 'v-on.enter', arg: undefined, modifiers: ['enter'], exp: undefined, loc: { start: { offset: 5, line: 1, column: 6 }, end: { offset: 15, line: 1, column: 16 }, - source: 'v-on.enter' - } + source: 'v-on.enter', + }, }) }) @@ -1254,14 +1377,15 @@ describe('compiler: parse', () => { expect(directive).toStrictEqual({ type: NodeTypes.DIRECTIVE, name: 'on', + rawName: 'v-on.enter.exact', arg: undefined, modifiers: ['enter', 'exact'], exp: undefined, loc: { start: { offset: 5, line: 1, column: 6 }, end: { offset: 21, line: 1, column: 22 }, - source: 'v-on.enter.exact' - } + source: 'v-on.enter.exact', + }, }) }) @@ -1272,33 +1396,25 @@ describe('compiler: parse', () => { expect(directive).toStrictEqual({ type: NodeTypes.DIRECTIVE, name: 'on', + rawName: 'v-on:click.enter.exact', arg: { type: NodeTypes.SIMPLE_EXPRESSION, content: 'click', isStatic: true, constType: ConstantTypes.CAN_STRINGIFY, - loc: { + start: { column: 11, line: 1, offset: 10 }, + end: { column: 16, line: 1, offset: 15 }, source: 'click', - start: { - column: 11, - line: 1, - offset: 10 - }, - end: { - column: 16, - line: 1, - offset: 15 - } - } + }, }, modifiers: ['enter', 'exact'], exp: undefined, loc: { start: { offset: 5, line: 1, column: 6 }, end: { offset: 27, line: 1, column: 28 }, - source: 'v-on:click.enter.exact' - } + source: 'v-on:click.enter.exact', + }, }) }) @@ -1309,41 +1425,34 @@ describe('compiler: parse', () => { expect(directive).toStrictEqual({ type: NodeTypes.DIRECTIVE, name: 'on', + rawName: 'v-on:[a.b].camel', arg: { type: NodeTypes.SIMPLE_EXPRESSION, content: 'a.b', isStatic: false, constType: ConstantTypes.NOT_CONSTANT, - loc: { + start: { column: 11, line: 1, offset: 10 }, + end: { column: 16, line: 1, offset: 15 }, source: '[a.b]', - start: { - column: 11, - line: 1, - offset: 10 - }, - end: { - column: 16, - line: 1, - offset: 15 - } - } + }, }, modifiers: ['camel'], exp: undefined, loc: { start: { offset: 5, line: 1, column: 6 }, end: { offset: 21, line: 1, column: 22 }, - source: 'v-on:[a.b].camel' - } + source: 'v-on:[a.b].camel', + }, }) }) + test('directive with no name', () => { let errorCode = -1 const ast = baseParse('
', { onError: err => { errorCode = err.code as number - } + }, }) const directive = (ast.children[0] as ElementNode).props[0] @@ -1355,8 +1464,13 @@ describe('compiler: parse', () => { loc: { start: { offset: 5, line: 1, column: 6 }, end: { offset: 7, line: 1, column: 8 }, - source: 'v-' - } + source: 'v-', + }, + nameLoc: { + start: { offset: 5, line: 1, column: 6 }, + end: { offset: 7, line: 1, column: 8 }, + source: 'v-', + }, }) }) @@ -1367,25 +1481,17 @@ describe('compiler: parse', () => { expect(directive).toStrictEqual({ type: NodeTypes.DIRECTIVE, name: 'bind', + rawName: ':a', arg: { type: NodeTypes.SIMPLE_EXPRESSION, content: 'a', isStatic: true, constType: ConstantTypes.CAN_STRINGIFY, - loc: { + start: { column: 7, line: 1, offset: 6 }, + end: { column: 8, line: 1, offset: 7 }, source: 'a', - start: { - column: 7, - line: 1, - offset: 6 - }, - end: { - column: 8, - line: 1, - offset: 7 - } - } + }, }, modifiers: [], exp: { @@ -1393,18 +1499,17 @@ describe('compiler: parse', () => { content: 'b', isStatic: false, constType: ConstantTypes.NOT_CONSTANT, - loc: { start: { offset: 8, line: 1, column: 9 }, end: { offset: 9, line: 1, column: 10 }, - source: 'b' - } + source: 'b', + }, }, loc: { start: { offset: 5, line: 1, column: 6 }, end: { offset: 9, line: 1, column: 10 }, - source: ':a=b' - } + source: ':a=b', + }, }) }) @@ -1415,25 +1520,17 @@ describe('compiler: parse', () => { expect(directive).toStrictEqual({ type: NodeTypes.DIRECTIVE, name: 'bind', + rawName: '.a', arg: { type: NodeTypes.SIMPLE_EXPRESSION, content: 'a', isStatic: true, constType: ConstantTypes.CAN_STRINGIFY, - loc: { + start: { column: 7, line: 1, offset: 6 }, + end: { column: 8, line: 1, offset: 7 }, source: 'a', - start: { - column: 7, - line: 1, - offset: 6 - }, - end: { - column: 8, - line: 1, - offset: 7 - } - } + }, }, modifiers: ['prop'], exp: { @@ -1441,18 +1538,17 @@ describe('compiler: parse', () => { content: 'b', isStatic: false, constType: ConstantTypes.NOT_CONSTANT, - loc: { start: { offset: 8, line: 1, column: 9 }, end: { offset: 9, line: 1, column: 10 }, - source: 'b' - } + source: 'b', + }, }, loc: { start: { offset: 5, line: 1, column: 6 }, end: { offset: 9, line: 1, column: 10 }, - source: '.a=b' - } + source: '.a=b', + }, }) }) @@ -1463,25 +1559,17 @@ describe('compiler: parse', () => { expect(directive).toStrictEqual({ type: NodeTypes.DIRECTIVE, name: 'bind', + rawName: ':a.sync', arg: { type: NodeTypes.SIMPLE_EXPRESSION, content: 'a', isStatic: true, constType: ConstantTypes.CAN_STRINGIFY, - loc: { + start: { column: 7, line: 1, offset: 6 }, + end: { column: 8, line: 1, offset: 7 }, source: 'a', - start: { - column: 7, - line: 1, - offset: 6 - }, - end: { - column: 8, - line: 1, - offset: 7 - } - } + }, }, modifiers: ['sync'], exp: { @@ -1493,14 +1581,14 @@ describe('compiler: parse', () => { loc: { start: { offset: 13, line: 1, column: 14 }, end: { offset: 14, line: 1, column: 15 }, - source: 'b' - } + source: 'b', + }, }, loc: { start: { offset: 5, line: 1, column: 6 }, end: { offset: 14, line: 1, column: 15 }, - source: ':a.sync=b' - } + source: ':a.sync=b', + }, }) }) @@ -1511,25 +1599,17 @@ describe('compiler: parse', () => { expect(directive).toStrictEqual({ type: NodeTypes.DIRECTIVE, name: 'on', + rawName: '@a', arg: { type: NodeTypes.SIMPLE_EXPRESSION, content: 'a', isStatic: true, constType: ConstantTypes.CAN_STRINGIFY, - loc: { + start: { column: 7, line: 1, offset: 6 }, + end: { column: 8, line: 1, offset: 7 }, source: 'a', - start: { - column: 7, - line: 1, - offset: 6 - }, - end: { - column: 8, - line: 1, - offset: 7 - } - } + }, }, modifiers: [], exp: { @@ -1541,14 +1621,14 @@ describe('compiler: parse', () => { loc: { start: { offset: 8, line: 1, column: 9 }, end: { offset: 9, line: 1, column: 10 }, - source: 'b' - } + source: 'b', + }, }, loc: { start: { offset: 5, line: 1, column: 6 }, end: { offset: 9, line: 1, column: 10 }, - source: '@a=b' - } + source: '@a=b', + }, }) }) @@ -1559,25 +1639,17 @@ describe('compiler: parse', () => { expect(directive).toStrictEqual({ type: NodeTypes.DIRECTIVE, name: 'on', + rawName: '@a.enter', arg: { type: NodeTypes.SIMPLE_EXPRESSION, content: 'a', isStatic: true, constType: ConstantTypes.CAN_STRINGIFY, - loc: { + start: { column: 7, line: 1, offset: 6 }, + end: { column: 8, line: 1, offset: 7 }, source: 'a', - start: { - column: 7, - line: 1, - offset: 6 - }, - end: { - column: 8, - line: 1, - offset: 7 - } - } + }, }, modifiers: ['enter'], exp: { @@ -1589,14 +1661,14 @@ describe('compiler: parse', () => { loc: { start: { offset: 14, line: 1, column: 15 }, end: { offset: 15, line: 1, column: 16 }, - source: 'b' - } + source: 'b', + }, }, loc: { start: { offset: 5, line: 1, column: 6 }, end: { offset: 15, line: 1, column: 16 }, - source: '@a.enter=b' - } + source: '@a.enter=b', + }, }) }) @@ -1607,24 +1679,17 @@ describe('compiler: parse', () => { expect(directive).toStrictEqual({ type: NodeTypes.DIRECTIVE, name: 'slot', + rawName: '#a', arg: { type: NodeTypes.SIMPLE_EXPRESSION, content: 'a', isStatic: true, constType: ConstantTypes.CAN_STRINGIFY, loc: { + start: { column: 8, line: 1, offset: 7 }, + end: { column: 9, line: 1, offset: 8 }, source: 'a', - start: { - column: 8, - line: 1, - offset: 7 - }, - end: { - column: 9, - line: 1, - offset: 8 - } - } + }, }, modifiers: [], exp: { @@ -1636,14 +1701,14 @@ describe('compiler: parse', () => { loc: { start: { offset: 10, line: 1, column: 11 }, end: { offset: 15, line: 1, column: 16 }, - source: '{ b }' - } + source: '{ b }', + }, }, loc: { start: { offset: 6, line: 1, column: 7 }, end: { offset: 16, line: 1, column: 17 }, - source: '#a="{ b }"' - } + source: '#a="{ b }"', + }, }) }) @@ -1655,32 +1720,32 @@ describe('compiler: parse', () => { expect(directive).toMatchObject({ type: NodeTypes.DIRECTIVE, name: 'slot', + rawName: 'v-slot:foo.bar', arg: { type: NodeTypes.SIMPLE_EXPRESSION, content: 'foo.bar', isStatic: true, constType: ConstantTypes.CAN_STRINGIFY, loc: { - source: 'foo.bar', start: { column: 14, line: 1, - offset: 13 + offset: 13, }, end: { column: 21, line: 1, - offset: 20 - } - } - } + offset: 20, + }, + }, + }, }) }) test('v-pre', () => { const ast = baseParse( `
{{ bar }}
\n` + - `
{{ bar }}
` + `
{{ bar }}
`, ) const divWithPre = ast.children[0] as ElementNode @@ -1690,29 +1755,22 @@ describe('compiler: parse', () => { name: `:id`, value: { type: NodeTypes.TEXT, - content: `foo` + content: `foo`, }, loc: { - source: `:id="foo"`, - start: { - line: 1, - column: 12 - }, - end: { - line: 1, - column: 21 - } - } - } + start: { line: 1, column: 12 }, + end: { line: 1, column: 21 }, + }, + }, ]) expect(divWithPre.children[0]).toMatchObject({ type: NodeTypes.ELEMENT, tagType: ElementTypes.ELEMENT, - tag: `Comp` + tag: `Comp`, }) expect(divWithPre.children[1]).toMatchObject({ type: NodeTypes.TEXT, - content: `{{ bar }}` + content: `{{ bar }}`, }) // should not affect siblings after it @@ -1724,44 +1782,72 @@ describe('compiler: parse', () => { arg: { type: NodeTypes.SIMPLE_EXPRESSION, isStatic: true, - content: `id` + content: `id`, }, exp: { type: NodeTypes.SIMPLE_EXPRESSION, isStatic: false, - content: `foo` + content: `foo`, }, loc: { - source: `:id="foo"`, start: { line: 2, - column: 6 + column: 6, }, end: { line: 2, - column: 15 - } - } - } + column: 15, + }, + }, + }, ]) expect(divWithoutPre.children[0]).toMatchObject({ type: NodeTypes.ELEMENT, tagType: ElementTypes.COMPONENT, - tag: `Comp` + tag: `Comp`, }) expect(divWithoutPre.children[1]).toMatchObject({ type: NodeTypes.INTERPOLATION, content: { type: NodeTypes.SIMPLE_EXPRESSION, content: `bar`, - isStatic: false - } + isStatic: false, + }, }) }) + // https://github.com/vuejs/docs/issues/2586 + test('v-pre with half-open interpolation', () => { + const ast = baseParse( + `
+ {{ number + }} +
+ `, + ) + expect((ast.children[0] as ElementNode).children).toMatchObject([ + { + type: NodeTypes.ELEMENT, + children: [{ type: NodeTypes.TEXT, content: `{{ number ` }], + }, + { + type: NodeTypes.ELEMENT, + children: [{ type: NodeTypes.TEXT, content: `}}` }], + }, + ]) + + const ast2 = baseParse(`
{{ number
`) + expect((ast2.children[0] as ElementNode).children).toMatchObject([ + { + type: NodeTypes.ELEMENT, + children: [{ type: NodeTypes.TEXT, content: `{{ number ` }], + }, + ]) + }) + test('self-closing v-pre', () => { const ast = baseParse( - `
\n
{{ bar }}
` + `
\n
{{ bar }}
`, ) // should not affect siblings after it const divWithoutPre = ast.children[1] as ElementNode @@ -1772,38 +1858,37 @@ describe('compiler: parse', () => { arg: { type: NodeTypes.SIMPLE_EXPRESSION, isStatic: true, - content: `id` + content: `id`, }, exp: { type: NodeTypes.SIMPLE_EXPRESSION, isStatic: false, - content: `foo` + content: `foo`, }, loc: { - source: `:id="foo"`, start: { line: 2, - column: 6 + column: 6, }, end: { line: 2, - column: 15 - } - } - } + column: 15, + }, + }, + }, ]) expect(divWithoutPre.children[0]).toMatchObject({ type: NodeTypes.ELEMENT, tagType: ElementTypes.COMPONENT, - tag: `Comp` + tag: `Comp`, }) expect(divWithoutPre.children[1]).toMatchObject({ type: NodeTypes.INTERPOLATION, content: { type: NodeTypes.SIMPLE_EXPRESSION, content: `bar`, - isStatic: false - } + isStatic: false, + }, }) }) @@ -1818,133 +1903,177 @@ describe('compiler: parse', () => { loc: { start: { offset: 5, line: 1, column: 6 }, end: { offset: 10, line: 1, column: 11 }, - source: 'hello' - } + source: 'hello', + }, }) }) }) - test('self closing single tag', () => { - const ast = baseParse('
') + describe('Edge Cases', () => { + test('self closing single tag', () => { + const ast = baseParse('
') - expect(ast.children).toHaveLength(1) - expect(ast.children[0]).toMatchObject({ tag: 'div' }) - }) + expect(ast.children).toHaveLength(1) + expect(ast.children[0]).toMatchObject({ tag: 'div' }) + }) - test('self closing multiple tag', () => { - const ast = baseParse( - `
\n` + - `

` - ) + test('self closing multiple tag', () => { + const ast = baseParse( + `

\n` + + `

`, + ) - expect(ast).toMatchSnapshot() + expect(ast).toMatchSnapshot() - expect(ast.children).toHaveLength(2) - expect(ast.children[0]).toMatchObject({ tag: 'div' }) - expect(ast.children[1]).toMatchObject({ tag: 'p' }) - }) + expect(ast.children).toHaveLength(2) + expect(ast.children[0]).toMatchObject({ tag: 'div' }) + expect(ast.children[1]).toMatchObject({ tag: 'p' }) + }) - test('valid html', () => { - const ast = baseParse( - `

\n` + - `

\n` + - ` \n` + - `

` - ) + test('valid html', () => { + const ast = baseParse( + `
\n` + + `

\n` + + ` \n` + + `

`, + ) - expect(ast).toMatchSnapshot() + expect(ast).toMatchSnapshot() - expect(ast.children).toHaveLength(1) - const el = ast.children[0] as any - expect(el).toMatchObject({ - tag: 'div' - }) - expect(el.children).toHaveLength(2) - expect(el.children[0]).toMatchObject({ - tag: 'p' - }) - expect(el.children[1]).toMatchObject({ - type: NodeTypes.COMMENT + expect(ast.children).toHaveLength(1) + const el = ast.children[0] as any + expect(el).toMatchObject({ + tag: 'div', + }) + expect(el.children).toHaveLength(2) + expect(el.children[0]).toMatchObject({ + tag: 'p', + }) + expect(el.children[1]).toMatchObject({ + type: NodeTypes.COMMENT, + }) }) - }) - test('invalid html', () => { - expect(() => { - baseParse(`
\n\n
\n`) - }).toThrow('Element is missing end tag.') + test('invalid html', () => { + expect(() => { + baseParse(`
\n\n
\n`) + }).toThrow('Element is missing end tag.') - const spy = vi.fn() - const ast = baseParse(`
\n\n
\n`, { - onError: spy - }) + const spy = vi.fn() + const ast = baseParse(`
\n\n
\n`, { + onError: spy, + }) - expect(spy.mock.calls).toMatchObject([ - [ - { - code: ErrorCodes.X_MISSING_END_TAG, - loc: { - start: { - offset: 6, - line: 2, - column: 1 - } - } - } - ], - [ + expect(spy.mock.calls).toMatchObject([ + [ + { + code: ErrorCodes.X_MISSING_END_TAG, + loc: { + start: { + offset: 6, + line: 2, + column: 1, + }, + }, + }, + ], + [ + { + code: ErrorCodes.X_INVALID_END_TAG, + loc: { + start: { + offset: 20, + line: 4, + column: 1, + }, + }, + }, + ], + ]) + + expect(ast).toMatchSnapshot() + }) + + test('parse with correct location info', () => { + const fooSrc = `foo\n is ` + const barSrc = `{{ bar }}` + const butSrc = ` but ` + const bazSrc = `{{ baz }}` + const [foo, bar, but, baz] = baseParse( + fooSrc + barSrc + butSrc + bazSrc, + ).children + + let offset = 0 + expect(foo.loc.start).toEqual({ line: 1, column: 1, offset }) + offset += fooSrc.length + expect(foo.loc.end).toEqual({ line: 2, column: 5, offset }) + + expect(bar.loc.start).toEqual({ line: 2, column: 5, offset }) + const barInner = (bar as InterpolationNode).content + offset += 3 + expect(barInner.loc.start).toEqual({ line: 2, column: 8, offset }) + offset += 3 + expect(barInner.loc.end).toEqual({ line: 2, column: 11, offset }) + offset += 3 + expect(bar.loc.end).toEqual({ line: 2, column: 14, offset }) + + expect(but.loc.start).toEqual({ line: 2, column: 14, offset }) + offset += butSrc.length + expect(but.loc.end).toEqual({ line: 2, column: 19, offset }) + + expect(baz.loc.start).toEqual({ line: 2, column: 19, offset }) + const bazInner = (baz as InterpolationNode).content + offset += 3 + expect(bazInner.loc.start).toEqual({ line: 2, column: 22, offset }) + offset += 3 + expect(bazInner.loc.end).toEqual({ line: 2, column: 25, offset }) + offset += 3 + expect(baz.loc.end).toEqual({ line: 2, column: 28, offset }) + }) + + // With standard HTML parsing, the following input would ignore the slash + // and treat "<" and "template" as attributes on the open tag of "Hello", + // causing `