mirror of https://github.com/vuejs/core.git
Merge branch 'vapor' into edison/feat/vaporTeleport
This commit is contained in:
commit
1033d2bd3d
|
@ -14,7 +14,7 @@ jobs:
|
|||
- uses: actions/checkout@v4
|
||||
|
||||
- name: Install pnpm
|
||||
uses: pnpm/action-setup@v4.0.0
|
||||
uses: pnpm/action-setup@v4.1.0
|
||||
|
||||
- name: Install Node.js
|
||||
uses: actions/setup-node@v4
|
||||
|
|
|
@ -17,7 +17,7 @@ jobs:
|
|||
ref: minor
|
||||
|
||||
- name: Install pnpm
|
||||
uses: pnpm/action-setup@v4.0.0
|
||||
uses: pnpm/action-setup@v4.1.0
|
||||
|
||||
- name: Install Node.js
|
||||
uses: actions/setup-node@v4
|
||||
|
|
|
@ -15,7 +15,7 @@ jobs:
|
|||
- uses: actions/checkout@v4
|
||||
|
||||
- name: Install pnpm
|
||||
uses: pnpm/action-setup@v4.0.0
|
||||
uses: pnpm/action-setup@v4.1.0
|
||||
|
||||
- name: Install Node.js
|
||||
uses: actions/setup-node@v4
|
||||
|
|
|
@ -25,7 +25,7 @@ jobs:
|
|||
- uses: actions/checkout@v4
|
||||
|
||||
- name: Install pnpm
|
||||
uses: pnpm/action-setup@v4.0.0
|
||||
uses: pnpm/action-setup@v4.1.0
|
||||
|
||||
- name: Install Node.js
|
||||
uses: actions/setup-node@v4
|
||||
|
|
|
@ -25,7 +25,7 @@ jobs:
|
|||
- uses: actions/checkout@v4
|
||||
|
||||
- name: Install pnpm
|
||||
uses: pnpm/action-setup@v4.0.0
|
||||
uses: pnpm/action-setup@v4.1.0
|
||||
|
||||
- name: Install Node.js
|
||||
uses: actions/setup-node@v4
|
||||
|
@ -37,7 +37,7 @@ jobs:
|
|||
run: pnpm install
|
||||
|
||||
- name: Download Size Data
|
||||
uses: dawidd6/action-download-artifact@v7
|
||||
uses: dawidd6/action-download-artifact@v9
|
||||
with:
|
||||
name: size-data
|
||||
run_id: ${{ github.event.workflow_run.id }}
|
||||
|
@ -56,7 +56,7 @@ jobs:
|
|||
path: temp/size/base.txt
|
||||
|
||||
- name: Download Previous Size Data
|
||||
uses: dawidd6/action-download-artifact@v7
|
||||
uses: dawidd6/action-download-artifact@v9
|
||||
with:
|
||||
branch: ${{ steps.pr-base.outputs.content }}
|
||||
workflow: size-data.yml
|
||||
|
|
|
@ -14,7 +14,7 @@ jobs:
|
|||
- uses: actions/checkout@v4
|
||||
|
||||
- name: Install pnpm
|
||||
uses: pnpm/action-setup@v4.0.0
|
||||
uses: pnpm/action-setup@v4.1.0
|
||||
|
||||
- name: Install Node.js
|
||||
uses: actions/setup-node@v4
|
||||
|
@ -35,7 +35,7 @@ jobs:
|
|||
- uses: actions/checkout@v4
|
||||
|
||||
- name: Install pnpm
|
||||
uses: pnpm/action-setup@v4.0.0
|
||||
uses: pnpm/action-setup@v4.1.0
|
||||
|
||||
- name: Install Node.js
|
||||
uses: actions/setup-node@v4
|
||||
|
@ -63,7 +63,7 @@ jobs:
|
|||
key: chromium-${{ hashFiles('pnpm-lock.yaml') }}
|
||||
|
||||
- name: Install pnpm
|
||||
uses: pnpm/action-setup@v4.0.0
|
||||
uses: pnpm/action-setup@v4.1.0
|
||||
|
||||
- name: Install Node.js
|
||||
uses: actions/setup-node@v4
|
||||
|
@ -114,7 +114,7 @@ jobs:
|
|||
- uses: actions/checkout@v4
|
||||
|
||||
- name: Install pnpm
|
||||
uses: pnpm/action-setup@v4.0.0
|
||||
uses: pnpm/action-setup@v4.1.0
|
||||
|
||||
- name: Install Node.js
|
||||
uses: actions/setup-node@v4
|
||||
|
|
|
@ -1 +1 @@
|
|||
20
|
||||
22.14.0
|
||||
|
|
|
@ -44,7 +44,9 @@ Please make sure to read the [Contributing Guide](https://github.com/vuejs/core/
|
|||
|
||||
Thank you to all the people who already contributed to Vue!
|
||||
|
||||
<a href="https://github.com/vuejs/core/graphs/contributors"><img src="https://opencollective.com/vuejs/contributors.svg?width=890" /></a>
|
||||
<a href="https://github.com/vuejs/core/graphs/contributors"><img src="https://opencollective.com/vuejs/contributors.svg?width=890&limit=500" /></a>
|
||||
|
||||
<sub>_Note: Showing the first 500 contributors only due to GitHub image size limitations_</sub>
|
||||
|
||||
## License
|
||||
|
||||
|
|
|
@ -1,3 +1,3 @@
|
|||
[build.environment]
|
||||
NODE_VERSION = "18"
|
||||
NODE_VERSION = "22"
|
||||
NPM_FLAGS = "--version" # prevent Netlify npm install
|
||||
|
|
48
package.json
48
package.json
|
@ -1,7 +1,7 @@
|
|||
{
|
||||
"private": true,
|
||||
"version": "3.5.13",
|
||||
"packageManager": "pnpm@9.15.4",
|
||||
"packageManager": "pnpm@10.6.5",
|
||||
"type": "module",
|
||||
"scripts": {
|
||||
"dev": "node scripts/dev.js",
|
||||
|
@ -65,53 +65,53 @@
|
|||
"@babel/parser": "catalog:",
|
||||
"@babel/types": "catalog:",
|
||||
"@rollup/plugin-alias": "^5.1.1",
|
||||
"@rollup/plugin-commonjs": "^28.0.2",
|
||||
"@rollup/plugin-commonjs": "^28.0.3",
|
||||
"@rollup/plugin-json": "^6.1.0",
|
||||
"@rollup/plugin-node-resolve": "^16.0.0",
|
||||
"@rollup/plugin-node-resolve": "^16.0.1",
|
||||
"@rollup/plugin-replace": "5.0.4",
|
||||
"@swc/core": "^1.10.8",
|
||||
"@swc/core": "^1.11.12",
|
||||
"@types/hash-sum": "^1.0.2",
|
||||
"@types/node": "^22.10.7",
|
||||
"@types/node": "^22.13.13",
|
||||
"@types/semver": "^7.5.8",
|
||||
"@types/serve-handler": "^6.1.4",
|
||||
"@vitest/coverage-v8": "^3.0.2",
|
||||
"@vitest/ui": "^3.0.2",
|
||||
"@vitest/coverage-v8": "^3.0.9",
|
||||
"@vitest/eslint-plugin": "^1.1.38",
|
||||
"@vue/consolidate": "1.0.0",
|
||||
"conventional-changelog-cli": "^5.0.0",
|
||||
"enquirer": "^2.4.1",
|
||||
"esbuild": "^0.24.2",
|
||||
"esbuild": "^0.25.1",
|
||||
"esbuild-plugin-polyfill-node": "^0.3.0",
|
||||
"eslint": "^9.18.0",
|
||||
"eslint-plugin-import-x": "^4.6.1",
|
||||
"@vitest/eslint-plugin": "^1.1.25",
|
||||
"eslint": "^9.23.0",
|
||||
"eslint-plugin-import-x": "^4.9.1",
|
||||
"estree-walker": "catalog:",
|
||||
"jsdom": "^26.0.0",
|
||||
"lint-staged": "^15.4.1",
|
||||
"lint-staged": "^15.5.0",
|
||||
"lodash": "^4.17.21",
|
||||
"magic-string": "^0.30.17",
|
||||
"markdown-table": "^3.0.4",
|
||||
"marked": "13.0.3",
|
||||
"npm-run-all2": "^7.0.2",
|
||||
"picocolors": "^1.1.1",
|
||||
"prettier": "^3.4.2",
|
||||
"prettier": "^3.5.3",
|
||||
"pretty-bytes": "^6.1.1",
|
||||
"pug": "^3.0.3",
|
||||
"puppeteer": "~24.1.0",
|
||||
"puppeteer": "~24.4.0",
|
||||
"rimraf": "^6.0.1",
|
||||
"rollup": "^4.31.0",
|
||||
"rollup-plugin-dts": "^6.1.1",
|
||||
"rollup-plugin-esbuild": "^6.1.1",
|
||||
"rollup": "^4.37.0",
|
||||
"rollup-plugin-dts": "^6.2.1",
|
||||
"rollup-plugin-esbuild": "^6.2.1",
|
||||
"rollup-plugin-polyfill-node": "^0.13.0",
|
||||
"semver": "^7.6.3",
|
||||
"semver": "^7.7.1",
|
||||
"serve": "^14.2.4",
|
||||
"serve-handler": "^6.1.6",
|
||||
"simple-git-hooks": "^2.11.1",
|
||||
"simple-git-hooks": "^2.12.1",
|
||||
"todomvc-app-css": "^2.4.3",
|
||||
"tslib": "^2.8.1",
|
||||
"typescript": "~5.6.2",
|
||||
"typescript-eslint": "^8.20.0",
|
||||
"typescript-eslint": "^8.27.0",
|
||||
"vite": "catalog:",
|
||||
"vitest": "^3.0.2"
|
||||
"vitest": "^3.0.9"
|
||||
},
|
||||
"pnpm": {
|
||||
"peerDependencyRules": {
|
||||
|
@ -122,6 +122,12 @@
|
|||
"@typescript-eslint/type-utils>eslint": "^9.0.0",
|
||||
"@typescript-eslint/utils>eslint": "^9.0.0"
|
||||
}
|
||||
}
|
||||
},
|
||||
"onlyBuiltDependencies": [
|
||||
"@swc/core",
|
||||
"esbuild",
|
||||
"puppeteer",
|
||||
"simple-git-hooks"
|
||||
]
|
||||
}
|
||||
}
|
||||
|
|
|
@ -9,7 +9,7 @@ app.directive<HTMLElement, string, 'prevent' | 'stop', 'arg1' | 'arg2'>(
|
|||
mounted(el, binding) {
|
||||
expectType<HTMLElement>(el)
|
||||
expectType<string>(binding.value)
|
||||
expectType<{ prevent: boolean; stop: boolean }>(binding.modifiers)
|
||||
expectType<{ prevent?: boolean; stop?: boolean }>(binding.modifiers)
|
||||
expectType<'arg1' | 'arg2'>(binding.arg!)
|
||||
|
||||
// @ts-expect-error not any
|
||||
|
|
|
@ -12,8 +12,11 @@ app.use(PluginWithoutType, 2)
|
|||
app.use(PluginWithoutType, { anything: 'goes' }, true)
|
||||
|
||||
type PluginOptions = {
|
||||
/** option1 */
|
||||
option1?: string
|
||||
/** option2 */
|
||||
option2: number
|
||||
/** option3 */
|
||||
option3: boolean
|
||||
}
|
||||
|
||||
|
@ -25,6 +28,20 @@ const PluginWithObjectOptions = {
|
|||
},
|
||||
}
|
||||
|
||||
const objectPluginOptional = {
|
||||
install(app: App, options?: PluginOptions) {},
|
||||
}
|
||||
app.use(objectPluginOptional)
|
||||
app.use(
|
||||
objectPluginOptional,
|
||||
// Test JSDoc and `go to definition` for options
|
||||
{
|
||||
option1: 'foo',
|
||||
option2: 1,
|
||||
option3: true,
|
||||
},
|
||||
)
|
||||
|
||||
for (const Plugin of [
|
||||
PluginWithObjectOptions,
|
||||
PluginWithObjectOptions.install,
|
||||
|
@ -92,7 +109,27 @@ const PluginTyped: Plugin<PluginOptions> = (app, options) => {}
|
|||
|
||||
// @ts-expect-error: needs options
|
||||
app.use(PluginTyped)
|
||||
app.use(PluginTyped, { option2: 2, option3: true })
|
||||
app.use(
|
||||
PluginTyped,
|
||||
// Test autocomplete for options
|
||||
{
|
||||
option1: '',
|
||||
option2: 2,
|
||||
option3: true,
|
||||
},
|
||||
)
|
||||
|
||||
const functionPluginOptional = (app: App, options?: PluginOptions) => {}
|
||||
app.use(functionPluginOptional)
|
||||
app.use(functionPluginOptional, { option2: 2, option3: true })
|
||||
|
||||
// type optional params
|
||||
const functionPluginOptional2: Plugin<[options?: PluginOptions]> = (
|
||||
app,
|
||||
options,
|
||||
) => {}
|
||||
app.use(functionPluginOptional2)
|
||||
app.use(functionPluginOptional2, { option2: 2, option3: true })
|
||||
|
||||
// vuetify usage
|
||||
const key: string = ''
|
||||
|
|
|
@ -29,7 +29,7 @@ describe('custom', () => {
|
|||
value: number
|
||||
oldValue: number | null
|
||||
arg?: 'Arg'
|
||||
modifiers: Record<'a' | 'b', boolean>
|
||||
modifiers: Partial<Record<'a' | 'b', boolean>>
|
||||
}>(testDirective<number, 'a' | 'b', 'Arg'>())
|
||||
|
||||
expectType<{
|
||||
|
|
|
@ -4,6 +4,7 @@ import {
|
|||
type MaybeRefOrGetter,
|
||||
type Ref,
|
||||
type ShallowRef,
|
||||
type TemplateRef,
|
||||
type ToRefs,
|
||||
type WritableComputedRef,
|
||||
computed,
|
||||
|
@ -535,7 +536,7 @@ expectType<string>(toValue(unref2))
|
|||
|
||||
// useTemplateRef
|
||||
const tRef = useTemplateRef('foo')
|
||||
expectType<Readonly<ShallowRef<unknown>>>(tRef)
|
||||
expectType<TemplateRef>(tRef)
|
||||
|
||||
const tRef2 = useTemplateRef<HTMLElement>('bar')
|
||||
expectType<Readonly<ShallowRef<HTMLElement | null>>>(tRef2)
|
||||
expectType<TemplateRef<HTMLElement>>(tRef2)
|
||||
|
|
|
@ -182,8 +182,9 @@ onMounted(() => {
|
|||
|
||||
body {
|
||||
font-size: 13px;
|
||||
font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, Oxygen,
|
||||
Ubuntu, Cantarell, 'Open Sans', 'Helvetica Neue', sans-serif;
|
||||
font-family:
|
||||
-apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, Oxygen, Ubuntu,
|
||||
Cantarell, 'Open Sans', 'Helvetica Neue', sans-serif;
|
||||
margin: 0;
|
||||
--base: #444;
|
||||
--nav-height: 50px;
|
||||
|
|
|
@ -17,7 +17,10 @@ export async function downloadProject(store: ReplStore) {
|
|||
|
||||
// basic structure
|
||||
zip.file('index.html', index)
|
||||
zip.file('package.json', pkg)
|
||||
zip.file(
|
||||
'package.json',
|
||||
pkg.replace(`"vue": "latest"`, `"vue": "${store.vueVersion || 'latest'}"`),
|
||||
)
|
||||
zip.file('vite.config.js', config)
|
||||
zip.file('README.md', readme)
|
||||
|
||||
|
|
|
@ -8,10 +8,10 @@
|
|||
"serve": "vite preview"
|
||||
},
|
||||
"dependencies": {
|
||||
"vue": "^3.4.0"
|
||||
"vue": "latest"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@vitejs/plugin-vue": "^5.2.1",
|
||||
"vite": "^6.0.7"
|
||||
"@vitejs/plugin-vue": "^5.2.3",
|
||||
"vite": "^6.2.2"
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,8 +1,9 @@
|
|||
body {
|
||||
margin: 0;
|
||||
overflow: hidden;
|
||||
font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, Oxygen,
|
||||
Ubuntu, Cantarell, 'Open Sans', 'Helvetica Neue', sans-serif;
|
||||
font-family:
|
||||
-apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, Oxygen, Ubuntu,
|
||||
Cantarell, 'Open Sans', 'Helvetica Neue', sans-serif;
|
||||
--bg: #1d1f21;
|
||||
--border: #333;
|
||||
}
|
||||
|
|
|
@ -50,7 +50,7 @@
|
|||
"@vue/shared": "workspace:*",
|
||||
"estree-walker": "catalog:",
|
||||
"magic-string": "catalog:",
|
||||
"postcss": "^8.5.1",
|
||||
"postcss": "^8.5.3",
|
||||
"source-map-js": "catalog:"
|
||||
},
|
||||
"devDependencies": {
|
||||
|
@ -61,8 +61,8 @@
|
|||
"merge-source-map": "^1.1.0",
|
||||
"minimatch": "~10.0.1",
|
||||
"postcss-modules": "^6.0.1",
|
||||
"postcss-selector-parser": "^7.0.0",
|
||||
"postcss-selector-parser": "^7.1.0",
|
||||
"pug": "^3.0.3",
|
||||
"sass": "^1.83.4"
|
||||
"sass": "^1.86.0"
|
||||
}
|
||||
}
|
||||
|
|
|
@ -39,7 +39,7 @@ export function rewriteDefaultAST(
|
|||
ast.forEach(node => {
|
||||
if (node.type === 'ExportDefaultDeclaration') {
|
||||
if (node.declaration.type === 'ClassDeclaration' && node.declaration.id) {
|
||||
let start: number =
|
||||
const start: number =
|
||||
node.declaration.decorators && node.declaration.decorators.length > 0
|
||||
? node.declaration.decorators[
|
||||
node.declaration.decorators.length - 1
|
||||
|
|
|
@ -20,7 +20,7 @@ describe.skipIf(!global.gc)('reactivity/gc', () => {
|
|||
}
|
||||
|
||||
// #9233
|
||||
it.todo('should release computed cache', async () => {
|
||||
it('should release computed cache', async () => {
|
||||
const src = ref<{} | undefined>({})
|
||||
// @ts-expect-error ES2021 API
|
||||
const srcRef = new WeakRef(src.value!)
|
||||
|
@ -35,7 +35,7 @@ describe.skipIf(!global.gc)('reactivity/gc', () => {
|
|||
expect(srcRef.deref()).toBeUndefined()
|
||||
})
|
||||
|
||||
it.todo('should release reactive property dep', async () => {
|
||||
it('should release reactive property dep', async () => {
|
||||
const src = reactive({ foo: 1 })
|
||||
|
||||
let c: ComputedRef | undefined = computed(() => src.foo)
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
import { isRef, ref } from '../src/ref'
|
||||
import { isRef, ref, shallowRef } from '../src/ref'
|
||||
import {
|
||||
isProxy,
|
||||
isReactive,
|
||||
|
@ -301,6 +301,13 @@ describe('reactivity/reactive', () => {
|
|||
expect(() => markRaw(obj)).not.toThrowError()
|
||||
})
|
||||
|
||||
test('should not markRaw object as reactive', () => {
|
||||
const a = reactive({ a: 1 })
|
||||
const b = reactive({ b: 2 }) as any
|
||||
b.a = markRaw(toRaw(a))
|
||||
expect(b.a === a).toBe(false)
|
||||
})
|
||||
|
||||
test('should not observe non-extensible objects', () => {
|
||||
const obj = reactive({
|
||||
foo: Object.preventExtensions({ a: 1 }),
|
||||
|
@ -419,4 +426,17 @@ describe('reactivity/reactive', () => {
|
|||
map.set(void 0, 1)
|
||||
expect(c.value).toBe(1)
|
||||
})
|
||||
|
||||
test('should return true for reactive objects', () => {
|
||||
expect(isReactive(reactive({}))).toBe(true)
|
||||
expect(isReactive(readonly(reactive({})))).toBe(true)
|
||||
expect(isReactive(ref({}).value)).toBe(true)
|
||||
expect(isReactive(readonly(ref({})).value)).toBe(true)
|
||||
expect(isReactive(shallowReactive({}))).toBe(true)
|
||||
})
|
||||
|
||||
test('should return false for non-reactive objects', () => {
|
||||
expect(isReactive(ref(true))).toBe(false)
|
||||
expect(isReactive(shallowRef({}).value)).toBe(false)
|
||||
})
|
||||
})
|
||||
|
|
|
@ -87,7 +87,10 @@ export class ComputedRefImpl<T = any> implements Dependency, Subscriber {
|
|||
get dep(): Dependency {
|
||||
return this
|
||||
}
|
||||
// for backwards compat
|
||||
/**
|
||||
* @internal
|
||||
* for backwards compat
|
||||
*/
|
||||
get _dirty(): boolean {
|
||||
const flags = this.flags
|
||||
if (
|
||||
|
@ -99,6 +102,10 @@ export class ComputedRefImpl<T = any> implements Dependency, Subscriber {
|
|||
}
|
||||
return false
|
||||
}
|
||||
/**
|
||||
* @internal
|
||||
* for backwards compat
|
||||
*/
|
||||
set _dirty(v: boolean) {
|
||||
if (v) {
|
||||
this.flags |= SubscriberFlags.Dirty
|
||||
|
|
|
@ -108,9 +108,9 @@ export declare const ShallowReactiveMarker: unique symbol
|
|||
export type ShallowReactive<T> = T & { [ShallowReactiveMarker]?: true }
|
||||
|
||||
/**
|
||||
* Shallow version of {@link reactive()}.
|
||||
* Shallow version of {@link reactive}.
|
||||
*
|
||||
* Unlike {@link reactive()}, there is no deep conversion: only root-level
|
||||
* Unlike {@link reactive}, there is no deep conversion: only root-level
|
||||
* properties are reactive for a shallow reactive object. Property values are
|
||||
* stored and exposed as-is - this also means properties with ref values will
|
||||
* not be automatically unwrapped.
|
||||
|
@ -178,7 +178,7 @@ export type DeepReadonly<T> = T extends Builtin
|
|||
* the original.
|
||||
*
|
||||
* A readonly proxy is deep: any nested property accessed will be readonly as
|
||||
* well. It also has the same ref-unwrapping behavior as {@link reactive()},
|
||||
* well. It also has the same ref-unwrapping behavior as {@link reactive},
|
||||
* except the unwrapped values will also be made readonly.
|
||||
*
|
||||
* @example
|
||||
|
@ -215,9 +215,9 @@ export function readonly<T extends object>(
|
|||
}
|
||||
|
||||
/**
|
||||
* Shallow version of {@link readonly()}.
|
||||
* Shallow version of {@link readonly}.
|
||||
*
|
||||
* Unlike {@link readonly()}, there is no deep conversion: only root-level
|
||||
* Unlike {@link readonly}, there is no deep conversion: only root-level
|
||||
* properties are made readonly. Property values are stored and exposed as-is -
|
||||
* this also means properties with ref values will not be automatically
|
||||
* unwrapped.
|
||||
|
@ -279,16 +279,16 @@ function createReactiveObject(
|
|||
) {
|
||||
return target
|
||||
}
|
||||
// target already has corresponding Proxy
|
||||
const existingProxy = proxyMap.get(target)
|
||||
if (existingProxy) {
|
||||
return existingProxy
|
||||
}
|
||||
// only specific value types can be observed.
|
||||
const targetType = getTargetType(target)
|
||||
if (targetType === TargetType.INVALID) {
|
||||
return target
|
||||
}
|
||||
// target already has corresponding Proxy
|
||||
const existingProxy = proxyMap.get(target)
|
||||
if (existingProxy) {
|
||||
return existingProxy
|
||||
}
|
||||
const proxy = new Proxy(
|
||||
target,
|
||||
targetType === TargetType.COLLECTION ? collectionHandlers : baseHandlers,
|
||||
|
@ -298,8 +298,8 @@ function createReactiveObject(
|
|||
}
|
||||
|
||||
/**
|
||||
* Checks if an object is a proxy created by {@link reactive()} or
|
||||
* {@link shallowReactive()} (or {@link ref()} in some cases).
|
||||
* Checks if an object is a proxy created by {@link reactive} or
|
||||
* {@link shallowReactive} (or {@link ref} in some cases).
|
||||
*
|
||||
* @example
|
||||
* ```js
|
||||
|
@ -327,7 +327,7 @@ export function isReactive(value: unknown): boolean {
|
|||
* readonly object can change, but they can't be assigned directly via the
|
||||
* passed object.
|
||||
*
|
||||
* The proxies created by {@link readonly()} and {@link shallowReadonly()} are
|
||||
* The proxies created by {@link readonly} and {@link shallowReadonly} are
|
||||
* both considered readonly, as is a computed ref without a set function.
|
||||
*
|
||||
* @param value - The value to check.
|
||||
|
@ -343,7 +343,7 @@ export function isShallow(value: unknown): boolean {
|
|||
|
||||
/**
|
||||
* Checks if an object is a proxy created by {@link reactive},
|
||||
* {@link readonly}, {@link shallowReactive} or {@link shallowReadonly()}.
|
||||
* {@link readonly}, {@link shallowReactive} or {@link shallowReadonly}.
|
||||
*
|
||||
* @param value - The value to check.
|
||||
* @see {@link https://vuejs.org/api/reactivity-utilities.html#isproxy}
|
||||
|
@ -356,8 +356,8 @@ export function isProxy(value: any): boolean {
|
|||
* Returns the raw, original object of a Vue-created proxy.
|
||||
*
|
||||
* `toRaw()` can return the original object from proxies created by
|
||||
* {@link reactive()}, {@link readonly()}, {@link shallowReactive()} or
|
||||
* {@link shallowReadonly()}.
|
||||
* {@link reactive}, {@link readonly}, {@link shallowReactive} or
|
||||
* {@link shallowReadonly}.
|
||||
*
|
||||
* This is an escape hatch that can be used to temporarily read without
|
||||
* incurring proxy access / tracking overhead or write without triggering
|
||||
|
@ -397,7 +397,7 @@ export type Raw<T> = T & { [RawSymbol]?: true }
|
|||
* ```
|
||||
*
|
||||
* **Warning:** `markRaw()` together with the shallow APIs such as
|
||||
* {@link shallowReactive()} allow you to selectively opt-out of the default
|
||||
* {@link shallowReactive} allow you to selectively opt-out of the default
|
||||
* deep reactive/readonly conversion and embed raw, non-proxied objects in your
|
||||
* state graph.
|
||||
*
|
||||
|
|
|
@ -68,7 +68,7 @@ export type ShallowRef<T = any, S = T> = Ref<T, S> & {
|
|||
}
|
||||
|
||||
/**
|
||||
* Shallow version of {@link ref()}.
|
||||
* Shallow version of {@link ref}.
|
||||
*
|
||||
* @example
|
||||
* ```js
|
||||
|
@ -238,7 +238,7 @@ export function unref<T>(ref: MaybeRef<T> | ComputedRef<T>): T {
|
|||
|
||||
/**
|
||||
* Normalizes values / refs / getters to values.
|
||||
* This is similar to {@link unref()}, except that it also normalizes getters.
|
||||
* This is similar to {@link unref}, except that it also normalizes getters.
|
||||
* If the argument is a getter, it will be invoked and its return value will
|
||||
* be returned.
|
||||
*
|
||||
|
@ -348,7 +348,7 @@ export type ToRefs<T = any> = {
|
|||
/**
|
||||
* Converts a reactive object to a plain object where each property of the
|
||||
* resulting object is a ref pointing to the corresponding property of the
|
||||
* original object. Each individual ref is created using {@link toRef()}.
|
||||
* original object. Each individual ref is created using {@link toRef}.
|
||||
*
|
||||
* @param object - Reactive object to be made into an object of linked refs.
|
||||
* @see {@link https://vuejs.org/api/reactivity-utilities.html#torefs}
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
/* eslint-disable */
|
||||
// Ported from https://github.com/stackblitz/alien-signals/blob/v1.0.4/src/system.ts
|
||||
// Ported from https://github.com/stackblitz/alien-signals/blob/v1.0.13/src/system.ts
|
||||
import type { ComputedRefImpl as Computed } from './computed.js'
|
||||
import type { ReactiveEffect as Effect } from './effect.js'
|
||||
|
||||
|
@ -32,9 +32,16 @@ export const enum SubscriberFlags {
|
|||
Propagated = Dirty | PendingComputed,
|
||||
}
|
||||
|
||||
interface OneWayLink<T> {
|
||||
target: T
|
||||
linked: OneWayLink<T> | undefined
|
||||
}
|
||||
|
||||
const notifyBuffer: (Effect | undefined)[] = []
|
||||
|
||||
let batchDepth = 0
|
||||
let queuedEffects: Effect | undefined
|
||||
let queuedEffectsTail: Effect | undefined
|
||||
let notifyIndex = 0
|
||||
let notifyBufferLength = 0
|
||||
|
||||
export function startBatch(): void {
|
||||
++batchDepth
|
||||
|
@ -67,80 +74,81 @@ export function link(dep: Dependency, sub: Subscriber): Link | undefined {
|
|||
return linkNewDep(dep, sub, nextDep, currentDep)
|
||||
}
|
||||
|
||||
export function propagate(link: Link): void {
|
||||
export function propagate(current: Link): void {
|
||||
let next = current.nextSub
|
||||
let branchs: OneWayLink<Link | undefined> | undefined
|
||||
let branchDepth = 0
|
||||
let targetFlag = SubscriberFlags.Dirty
|
||||
let subs = link
|
||||
let stack = 0
|
||||
|
||||
top: do {
|
||||
const sub = link.sub
|
||||
const sub = current.sub
|
||||
const subFlags = sub.flags
|
||||
|
||||
let shouldNotify = false
|
||||
|
||||
if (
|
||||
(!(
|
||||
!(
|
||||
subFlags &
|
||||
(SubscriberFlags.Tracking |
|
||||
SubscriberFlags.Recursed |
|
||||
SubscriberFlags.Propagated)
|
||||
) &&
|
||||
((sub.flags = subFlags | targetFlag), true)) ||
|
||||
(subFlags & SubscriberFlags.Recursed &&
|
||||
!(subFlags & SubscriberFlags.Tracking) &&
|
||||
((sub.flags = (subFlags & ~SubscriberFlags.Recursed) | targetFlag),
|
||||
true)) ||
|
||||
(!(subFlags & SubscriberFlags.Propagated) &&
|
||||
isValidLink(link, sub) &&
|
||||
((sub.flags = subFlags | SubscriberFlags.Recursed | targetFlag),
|
||||
(sub as Dependency).subs !== undefined))
|
||||
)
|
||||
) {
|
||||
sub.flags = subFlags | targetFlag
|
||||
shouldNotify = true
|
||||
} else if (
|
||||
subFlags & SubscriberFlags.Recursed &&
|
||||
!(subFlags & SubscriberFlags.Tracking)
|
||||
) {
|
||||
sub.flags = (subFlags & ~SubscriberFlags.Recursed) | targetFlag
|
||||
shouldNotify = true
|
||||
} else if (
|
||||
!(subFlags & SubscriberFlags.Propagated) &&
|
||||
isValidLink(current, sub)
|
||||
) {
|
||||
sub.flags = subFlags | SubscriberFlags.Recursed | targetFlag
|
||||
shouldNotify = (sub as Dependency).subs !== undefined
|
||||
}
|
||||
|
||||
if (shouldNotify) {
|
||||
const subSubs = (sub as Dependency).subs
|
||||
if (subSubs !== undefined) {
|
||||
current = subSubs
|
||||
if (subSubs.nextSub !== undefined) {
|
||||
subSubs.prevSub = subs
|
||||
link = subs = subSubs
|
||||
targetFlag = SubscriberFlags.PendingComputed
|
||||
++stack
|
||||
} else {
|
||||
link = subSubs
|
||||
targetFlag = SubscriberFlags.PendingComputed
|
||||
branchs = { target: next, linked: branchs }
|
||||
++branchDepth
|
||||
next = current.nextSub
|
||||
}
|
||||
targetFlag = SubscriberFlags.PendingComputed
|
||||
continue
|
||||
}
|
||||
if (subFlags & SubscriberFlags.Effect) {
|
||||
if (queuedEffectsTail !== undefined) {
|
||||
queuedEffectsTail.depsTail!.nextDep = sub.deps
|
||||
} else {
|
||||
queuedEffects = sub as Effect
|
||||
}
|
||||
queuedEffectsTail = sub as Effect
|
||||
notifyBuffer[notifyBufferLength++] = sub as Effect
|
||||
}
|
||||
} else if (!(subFlags & (SubscriberFlags.Tracking | targetFlag))) {
|
||||
sub.flags = subFlags | targetFlag
|
||||
} else if (
|
||||
!(subFlags & targetFlag) &&
|
||||
subFlags & SubscriberFlags.Propagated &&
|
||||
isValidLink(link, sub)
|
||||
isValidLink(current, sub)
|
||||
) {
|
||||
sub.flags = subFlags | targetFlag
|
||||
}
|
||||
|
||||
if ((link = subs.nextSub!) !== undefined) {
|
||||
subs = link
|
||||
targetFlag = stack
|
||||
if ((current = next!) !== undefined) {
|
||||
next = current.nextSub
|
||||
targetFlag = branchDepth
|
||||
? SubscriberFlags.PendingComputed
|
||||
: SubscriberFlags.Dirty
|
||||
continue
|
||||
}
|
||||
|
||||
while (stack) {
|
||||
--stack
|
||||
const dep = subs.dep
|
||||
const depSubs = dep.subs!
|
||||
subs = depSubs.prevSub!
|
||||
depSubs.prevSub = undefined
|
||||
if ((link = subs.nextSub!) !== undefined) {
|
||||
subs = link
|
||||
targetFlag = stack
|
||||
while (branchDepth--) {
|
||||
current = branchs!.target!
|
||||
branchs = branchs!.linked
|
||||
if (current !== undefined) {
|
||||
next = current.nextSub
|
||||
targetFlag = branchDepth
|
||||
? SubscriberFlags.PendingComputed
|
||||
: SubscriberFlags.Dirty
|
||||
continue top
|
||||
|
@ -194,35 +202,26 @@ export function processComputedUpdate(
|
|||
computed: Computed,
|
||||
flags: SubscriberFlags,
|
||||
): void {
|
||||
if (
|
||||
flags & SubscriberFlags.Dirty ||
|
||||
(checkDirty(computed.deps!)
|
||||
? true
|
||||
: ((computed.flags = flags & ~SubscriberFlags.PendingComputed), false))
|
||||
) {
|
||||
if (flags & SubscriberFlags.Dirty || checkDirty(computed.deps!)) {
|
||||
if (computed.update()) {
|
||||
const subs = computed.subs
|
||||
if (subs !== undefined) {
|
||||
shallowPropagate(subs)
|
||||
}
|
||||
}
|
||||
} else {
|
||||
computed.flags = flags & ~SubscriberFlags.PendingComputed
|
||||
}
|
||||
}
|
||||
|
||||
export function processEffectNotifications(): void {
|
||||
while (queuedEffects !== undefined) {
|
||||
const effect = queuedEffects
|
||||
const depsTail = effect.depsTail!
|
||||
const queuedNext = depsTail.nextDep
|
||||
if (queuedNext !== undefined) {
|
||||
depsTail.nextDep = undefined
|
||||
queuedEffects = queuedNext.sub as Effect
|
||||
} else {
|
||||
queuedEffects = undefined
|
||||
queuedEffectsTail = undefined
|
||||
}
|
||||
while (notifyIndex < notifyBufferLength) {
|
||||
const effect = notifyBuffer[notifyIndex]!
|
||||
notifyBuffer[notifyIndex++] = undefined
|
||||
effect.notify()
|
||||
}
|
||||
notifyIndex = 0
|
||||
notifyBufferLength = 0
|
||||
}
|
||||
|
||||
function linkNewDep(
|
||||
|
@ -259,15 +258,18 @@ function linkNewDep(
|
|||
return newLink
|
||||
}
|
||||
|
||||
function checkDirty(link: Link): boolean {
|
||||
let stack = 0
|
||||
function checkDirty(current: Link): boolean {
|
||||
let prevLinks: OneWayLink<Link> | undefined
|
||||
let checkDepth = 0
|
||||
let dirty: boolean
|
||||
|
||||
top: do {
|
||||
dirty = false
|
||||
const dep = link.dep
|
||||
const dep = current.dep
|
||||
|
||||
if ('flags' in dep) {
|
||||
if (current.sub.flags & SubscriberFlags.Dirty) {
|
||||
dirty = true
|
||||
} else if ('flags' in dep) {
|
||||
const depFlags = dep.flags
|
||||
if (
|
||||
(depFlags & (SubscriberFlags.Computed | SubscriberFlags.Dirty)) ===
|
||||
|
@ -285,58 +287,49 @@ function checkDirty(link: Link): boolean {
|
|||
(SubscriberFlags.Computed | SubscriberFlags.PendingComputed)) ===
|
||||
(SubscriberFlags.Computed | SubscriberFlags.PendingComputed)
|
||||
) {
|
||||
const depSubs = dep.subs!
|
||||
if (depSubs.nextSub !== undefined) {
|
||||
depSubs.prevSub = link
|
||||
if (current.nextSub !== undefined || current.prevSub !== undefined) {
|
||||
prevLinks = { target: current, linked: prevLinks }
|
||||
}
|
||||
link = dep.deps!
|
||||
++stack
|
||||
current = dep.deps!
|
||||
++checkDepth
|
||||
continue
|
||||
}
|
||||
}
|
||||
|
||||
if (!dirty && link.nextDep !== undefined) {
|
||||
link = link.nextDep
|
||||
if (!dirty && current.nextDep !== undefined) {
|
||||
current = current.nextDep
|
||||
continue
|
||||
}
|
||||
|
||||
if (stack) {
|
||||
let sub = link.sub as Computed
|
||||
do {
|
||||
--stack
|
||||
const subSubs = sub.subs!
|
||||
|
||||
if (dirty) {
|
||||
if (sub.update()) {
|
||||
if ((link = subSubs.prevSub!) !== undefined) {
|
||||
subSubs.prevSub = undefined
|
||||
shallowPropagate(subSubs)
|
||||
sub = link.sub as Computed
|
||||
} else {
|
||||
sub = subSubs.sub as Computed
|
||||
}
|
||||
continue
|
||||
while (checkDepth) {
|
||||
--checkDepth
|
||||
const sub = current.sub as Computed
|
||||
const firstSub = sub.subs!
|
||||
if (dirty) {
|
||||
if (sub.update()) {
|
||||
if (firstSub.nextSub !== undefined) {
|
||||
current = prevLinks!.target
|
||||
prevLinks = prevLinks!.linked
|
||||
shallowPropagate(firstSub)
|
||||
} else {
|
||||
current = firstSub
|
||||
}
|
||||
} else {
|
||||
sub.flags &= ~SubscriberFlags.PendingComputed
|
||||
continue
|
||||
}
|
||||
|
||||
if ((link = subSubs.prevSub!) !== undefined) {
|
||||
subSubs.prevSub = undefined
|
||||
if (link.nextDep !== undefined) {
|
||||
link = link.nextDep
|
||||
continue top
|
||||
}
|
||||
sub = link.sub as Computed
|
||||
} else {
|
||||
if ((link = subSubs.nextDep!) !== undefined) {
|
||||
continue top
|
||||
}
|
||||
sub = subSubs.sub as Computed
|
||||
}
|
||||
|
||||
dirty = false
|
||||
} while (stack)
|
||||
} else {
|
||||
sub.flags &= ~SubscriberFlags.PendingComputed
|
||||
}
|
||||
if (firstSub.nextSub !== undefined) {
|
||||
current = prevLinks!.target
|
||||
prevLinks = prevLinks!.linked
|
||||
} else {
|
||||
current = firstSub
|
||||
}
|
||||
if (current.nextDep !== undefined) {
|
||||
current = current.nextDep
|
||||
continue top
|
||||
}
|
||||
dirty = false
|
||||
}
|
||||
|
||||
return dirty
|
||||
|
|
|
@ -40,9 +40,9 @@ export interface App<HostElement = any> {
|
|||
|
||||
use<Options extends unknown[]>(
|
||||
plugin: Plugin<Options>,
|
||||
...options: Options
|
||||
...options: NoInfer<Options>
|
||||
): this
|
||||
use<Options>(plugin: Plugin<Options>, options: Options): this
|
||||
use<Options>(plugin: Plugin<Options>, options: NoInfer<Options>): this
|
||||
|
||||
mixin(mixin: ComponentOptions): this
|
||||
component(name: string): Component | undefined
|
||||
|
@ -266,9 +266,11 @@ export type ObjectPlugin<Options = any[]> = {
|
|||
export type FunctionPlugin<Options = any[]> = PluginInstallFunction<Options> &
|
||||
Partial<ObjectPlugin<Options>>
|
||||
|
||||
export type Plugin<Options = any[]> =
|
||||
| FunctionPlugin<Options>
|
||||
| ObjectPlugin<Options>
|
||||
export type Plugin<
|
||||
Options = any[],
|
||||
// TODO: in next major Options extends unknown[] and remove P
|
||||
P extends unknown[] = Options extends unknown[] ? Options : [Options],
|
||||
> = FunctionPlugin<P> | ObjectPlugin<P>
|
||||
|
||||
export function createAppContext(): AppContext {
|
||||
return {
|
||||
|
|
|
@ -201,6 +201,11 @@ const KeepAliveImpl: ComponentOptions = {
|
|||
// Update components tree
|
||||
devtoolsComponentAdded(instance)
|
||||
}
|
||||
|
||||
// for e2e test
|
||||
if (__DEV__ && __BROWSER__) {
|
||||
;(instance as any).__keepAliveStorageContainer = storageContainer
|
||||
}
|
||||
}
|
||||
|
||||
function unmount(vnode: VNode) {
|
||||
|
|
|
@ -4,6 +4,8 @@ import {
|
|||
isReadonly,
|
||||
isRef,
|
||||
isShallow,
|
||||
pauseTracking,
|
||||
resetTracking,
|
||||
toRaw,
|
||||
} from '@vue/reactivity'
|
||||
import { EMPTY_OBJ, extend, isArray, isFunction, isObject } from '@vue/shared'
|
||||
|
@ -34,13 +36,16 @@ export function initCustomFormatter(): void {
|
|||
if (obj.__isVue) {
|
||||
return ['div', vueStyle, `VueInstance`]
|
||||
} else if (isRef(obj)) {
|
||||
// avoid tracking during debugger accessing
|
||||
pauseTracking()
|
||||
const value = obj.value
|
||||
resetTracking()
|
||||
return [
|
||||
'div',
|
||||
{},
|
||||
['span', vueStyle, genRefFlag(obj)],
|
||||
'<',
|
||||
// avoid debugger accessing value affecting behavior
|
||||
formatValue('_value' in obj ? obj._value : obj),
|
||||
formatValue(value),
|
||||
`>`,
|
||||
]
|
||||
} else if (isReactive(obj)) {
|
||||
|
|
|
@ -111,7 +111,9 @@ export type Directive<
|
|||
| ObjectDirective<HostElement, Value, Modifiers, Arg>
|
||||
| FunctionDirective<HostElement, Value, Modifiers, Arg>
|
||||
|
||||
export type DirectiveModifiers<K extends string = string> = Record<K, boolean>
|
||||
export type DirectiveModifiers<K extends string = string> = Partial<
|
||||
Record<K, boolean>
|
||||
>
|
||||
|
||||
export function validateDirectiveName(name: string): void {
|
||||
if (isBuiltInDirective(name)) {
|
||||
|
|
|
@ -5,6 +5,8 @@ import { EMPTY_OBJ } from '@vue/shared'
|
|||
|
||||
export const knownTemplateRefs: WeakSet<ShallowRef> = new WeakSet()
|
||||
|
||||
export type TemplateRef<T = unknown> = Readonly<ShallowRef<T | null>>
|
||||
|
||||
export function useTemplateRef<T = unknown, Keys extends string = string>(
|
||||
key: Keys,
|
||||
): Readonly<ShallowRef<T | null>> {
|
||||
|
|
|
@ -64,7 +64,7 @@ export { defineComponent } from './apiDefineComponent'
|
|||
export { defineAsyncComponent } from './apiAsyncComponent'
|
||||
export { useAttrs, useSlots } from './apiSetupHelpers'
|
||||
export { useModel } from './helpers/useModel'
|
||||
export { useTemplateRef } from './helpers/useTemplateRef'
|
||||
export { useTemplateRef, type TemplateRef } from './helpers/useTemplateRef'
|
||||
export { useId } from './helpers/useId'
|
||||
export {
|
||||
hydrateOnIdle,
|
||||
|
|
|
@ -2120,7 +2120,13 @@ function baseCreateRenderer(
|
|||
queuePostRenderEffect(() => transition!.enter(el!), parentSuspense)
|
||||
} else {
|
||||
const { leave, delayLeave, afterLeave } = transition!
|
||||
const remove = () => hostInsert(el!, container, anchor)
|
||||
const remove = () => {
|
||||
if (vnode.ctx!.isUnmounted) {
|
||||
hostRemove(el!)
|
||||
} else {
|
||||
hostInsert(el!, container, anchor)
|
||||
}
|
||||
}
|
||||
const performLeave = () => {
|
||||
leave(el!, () => {
|
||||
remove()
|
||||
|
|
|
@ -1,5 +1,6 @@
|
|||
// @vitest-environment jsdom
|
||||
|
||||
import type { ElementHandle } from 'puppeteer'
|
||||
import { E2E_TIMEOUT, setupPuppeteer } from './e2eUtils'
|
||||
import path from 'node:path'
|
||||
import { Transition, createApp, h, nextTick, ref } from 'vue'
|
||||
|
@ -1655,6 +1656,74 @@ describe('e2e: Transition', () => {
|
|||
},
|
||||
E2E_TIMEOUT,
|
||||
)
|
||||
|
||||
// #12860
|
||||
test(
|
||||
'unmount children',
|
||||
async () => {
|
||||
const unmountSpy = vi.fn()
|
||||
let storageContainer: ElementHandle<HTMLDivElement>
|
||||
const setStorageContainer = (container: any) =>
|
||||
(storageContainer = container)
|
||||
await page().exposeFunction('unmountSpy', unmountSpy)
|
||||
await page().exposeFunction('setStorageContainer', setStorageContainer)
|
||||
await page().evaluate(() => {
|
||||
const { unmountSpy, setStorageContainer } = window as any
|
||||
const { createApp, ref, h, onUnmounted, getCurrentInstance } = (
|
||||
window as any
|
||||
).Vue
|
||||
createApp({
|
||||
template: `
|
||||
<div id="container">
|
||||
<transition>
|
||||
<KeepAlive :include="includeRef">
|
||||
<TrueBranch v-if="toggle"></TrueBranch>
|
||||
</KeepAlive>
|
||||
</transition>
|
||||
</div>
|
||||
<button id="toggleBtn" @click="click">button</button>
|
||||
`,
|
||||
components: {
|
||||
TrueBranch: {
|
||||
name: 'TrueBranch',
|
||||
setup() {
|
||||
const instance = getCurrentInstance()
|
||||
onUnmounted(() => {
|
||||
unmountSpy()
|
||||
setStorageContainer(instance.__keepAliveStorageContainer)
|
||||
})
|
||||
const count = ref(0)
|
||||
return () => h('div', count.value)
|
||||
},
|
||||
},
|
||||
},
|
||||
setup: () => {
|
||||
const includeRef = ref(['TrueBranch'])
|
||||
const toggle = ref(true)
|
||||
const click = () => {
|
||||
toggle.value = !toggle.value
|
||||
if (toggle.value) {
|
||||
includeRef.value = ['TrueBranch']
|
||||
} else {
|
||||
includeRef.value = []
|
||||
}
|
||||
}
|
||||
return { toggle, click, unmountSpy, includeRef }
|
||||
},
|
||||
}).mount('#app')
|
||||
})
|
||||
|
||||
await transitionFinish()
|
||||
expect(await html('#container')).toBe('<div>0</div>')
|
||||
|
||||
await click('#toggleBtn')
|
||||
await transitionFinish()
|
||||
expect(await html('#container')).toBe('<!--v-if-->')
|
||||
expect(unmountSpy).toBeCalledTimes(1)
|
||||
expect(await storageContainer!.evaluate(x => x.innerHTML)).toBe(``)
|
||||
},
|
||||
E2E_TIMEOUT,
|
||||
)
|
||||
})
|
||||
|
||||
describe('transition with Suspense', () => {
|
||||
|
|
|
@ -139,7 +139,7 @@ describe('e2e: todomvc', () => {
|
|||
// editing triggered by blur
|
||||
await click('.filters li:nth-child(1) a')
|
||||
await timeout(1)
|
||||
await click('.todo:nth-child(1) label', { clickCount: 2 })
|
||||
await click('.todo:nth-child(1) label', { count: 2 })
|
||||
expect(await count('.todo.editing')).toBe(1)
|
||||
expect(await isFocused('.todo:nth-child(1) .edit')).toBe(true)
|
||||
await clearValue('.todo:nth-child(1) .edit')
|
||||
|
@ -149,13 +149,13 @@ describe('e2e: todomvc', () => {
|
|||
expect(await text('.todo:nth-child(1) label')).toBe('edited!')
|
||||
|
||||
// editing triggered by enter
|
||||
await click('.todo label', { clickCount: 2 })
|
||||
await click('.todo label', { count: 2 })
|
||||
await enterValue('.todo:nth-child(1) .edit', 'edited again!')
|
||||
expect(await count('.todo.editing')).toBe(0)
|
||||
expect(await text('.todo:nth-child(1) label')).toBe('edited again!')
|
||||
|
||||
// cancel
|
||||
await click('.todo label', { clickCount: 2 })
|
||||
await click('.todo label', { count: 2 })
|
||||
await clearValue('.todo:nth-child(1) .edit')
|
||||
await page().type('.todo:nth-child(1) .edit', 'edited!')
|
||||
await page().keyboard.press('Escape')
|
||||
|
@ -163,7 +163,7 @@ describe('e2e: todomvc', () => {
|
|||
expect(await text('.todo:nth-child(1) label')).toBe('edited again!')
|
||||
|
||||
// empty value should remove
|
||||
await click('.todo label', { clickCount: 2 })
|
||||
await click('.todo label', { count: 2 })
|
||||
await enterValue('.todo:nth-child(1) .edit', ' ')
|
||||
expect(await count('.todo')).toBe(3)
|
||||
|
||||
|
|
|
@ -88,7 +88,7 @@ describe('e2e: tree', () => {
|
|||
expect(await isVisible('#demo ul')).toBe(true)
|
||||
expect(await text('#demo li div span')).toContain('[-]')
|
||||
|
||||
await click('#demo ul > .item div', { clickCount: 2 })
|
||||
await click('#demo ul > .item div', { count: 2 })
|
||||
expect(await count('.item')).toBe(15)
|
||||
expect(await count('.item > ul')).toBe(5)
|
||||
expect(await text('#demo ul > .item:nth-child(1)')).toContain('[-]')
|
||||
|
|
1884
pnpm-lock.yaml
1884
pnpm-lock.yaml
File diff suppressed because it is too large
Load Diff
|
@ -3,10 +3,10 @@ packages:
|
|||
- 'packages-private/*'
|
||||
|
||||
catalog:
|
||||
'@babel/parser': ^7.25.3
|
||||
'@babel/types': ^7.25.2
|
||||
'@babel/parser': ^7.26.10
|
||||
'@babel/types': ^7.26.10
|
||||
'estree-walker': ^2.0.2
|
||||
'magic-string': ^0.30.11
|
||||
'source-map-js': ^1.2.0
|
||||
'vite': ^6.1.0
|
||||
'@vitejs/plugin-vue': https://pkg.pr.new/@vitejs/plugin-vue@c156992
|
||||
'magic-string': ^0.30.17
|
||||
'source-map-js': ^1.2.1
|
||||
|
|
|
@ -111,7 +111,7 @@ async function renderUsages() {
|
|||
*/
|
||||
async function importJSON(filePath) {
|
||||
if (!existsSync(filePath)) return undefined
|
||||
return (await import(filePath, { assert: { type: 'json' } })).default
|
||||
return (await import(filePath, { with: { type: 'json' } })).default
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -36,7 +36,7 @@ exec('pnpm', ['build', 'vue', '-f', 'global-runtime']).then(() => {
|
|||
prodBuild.includes('annotation,annotation-xml,maction')
|
||||
) {
|
||||
errors.push(
|
||||
'prod build contains unexpected domTagConifg lists.\n' +
|
||||
'prod build contains unexpected domTagConfig lists.\n' +
|
||||
'This means helpers like isHTMLTag() is used in runtime code paths when it should be compiler-only.',
|
||||
)
|
||||
}
|
||||
|
|
|
@ -17,7 +17,6 @@
|
|||
"packages/runtime-dom/src",
|
||||
"packages/reactivity/src",
|
||||
"packages/shared/src",
|
||||
"packages/global.d.ts",
|
||||
"packages/compiler-sfc/src",
|
||||
"packages/compiler-ssr/src",
|
||||
"packages/server-renderer/src"
|
||||
|
|
Loading…
Reference in New Issue