是否可以将 Vue 3 与组合 API 和 vue class 组件一起使用?
Is it possible to use Vue 3 with the composition API and vue class components?
在过去的 8 个月里,我们使用 vue 3 和 class components 构建了一个项目,但由于它似乎不再维护,我们想逐渐切换到组合 API,更准确地说是安装脚本语法。
我们目前使用的是vue3.0.0和vue-class-components 8.0.0.
我们的目标是,因为我们必须不断向项目添加新功能,开始创建具有组合 API 的新组件,同时保留已经使用 vue class 组件编写的组件.而且,随着我们的进行,我们将尝试用组合 API.
重写它们
我尝试使用 vue class 组件创建一个简单的 HelloWorld 组件:
<template>
<div>
<TestComponent :test="'test string'" />
</div>
</template>
<script lang="ts">
import { Options, Vue } from 'vue-class-component';
import TestComponent from './TestComponent.vue';
@Options({
components: { TestComponent }
})
export default class HelloWorld extends Vue {
}
</script>
并添加一个测试组件:
<template>
<h1>Test composant {{ test }}</h1>
</template>
<script lang="ts">
export default {
name: 'TestComponent',
props: { test: {type: String, required: true }},
setup(props: { test: string }, context: unknown) { console.log(context); return { test: props.test } }
}
</script>
但是,我在代码中发现了一个错误:在 HelloWorld 中声明 TestComponent 时,编译器告诉我他期待在 TestComponent 中声明的参数 'test':
Argument of type '{ name: string; props: { test: StringConstructor; required: boolean; }; setup(props: { test: string; }, context: unknown): { test: string; }; }' is not assignable to parameter of type 'Component<any, any, any, ComputedOptions, MethodOptions>'.
Type '{ name: string; props: { test: StringConstructor; required: boolean; }; setup(props: { test: string; }, context: unknown): { test: string; }; }' is not assignable to type 'ComponentOptions<any, any, any, ComputedOptions, MethodOptions, any, any, any>'.
Type '{ name: string; props: { test: StringConstructor; required: boolean; }; setup(props: { test: string; }, context: unknown): { test: string; }; }' is not assignable to type 'ComponentOptionsBase<any, any, any, ComputedOptions, MethodOptions, any, any, any, string, {}>'.
Types of property 'setup' are incompatible.
Type '(props: { test: string; }, context: unknown) => { test: string; }' is not assignable to type '(this: void, props: Readonly<LooseRequired<any>>, ctx: SetupContext<any>) => any'.
Types of parameters 'props' and 'props' are incompatible.
Property 'test' is missing in type 'Readonly<LooseRequired<any>>' but required in type '{ test: string; }'.ts(2345)
TestComponent.vue.ts(5, 18): 'test' is declared here.
更新:
我尝试在main.ts中全局注册TestComponent,但还是报错
有没有办法让两者一起工作?
请注意 :test
是 v-bind:test
的语法糖,这意味着如果您没有 :test
的反应变量绑定,您应该使用 test
反而。见下文:
// note there is no colon before test, which means you are just passing a constant string.
<TestComponent test="test string" />
一个问题是您的 props
声明不正确。应该是:
// ❌ invalid
// props: {
// test: String,
// required: true
// },
props: {
test: {
type: String,
required: true
}
},
此外,您不需要键入 setup()
的参数,因为它们通常是从 defineComponent()
实用程序推断出来的,enables type inference 在 Vue 组件中:
// export default {
// setup(props: { test: string }, context: unknown) { /*...*/ }
// }
import { defineComponent } from 'vue'
export default defineComponent({
setup(props, context) { /*...*/ }
})
在过去的 8 个月里,我们使用 vue 3 和 class components 构建了一个项目,但由于它似乎不再维护,我们想逐渐切换到组合 API,更准确地说是安装脚本语法。
我们目前使用的是vue3.0.0和vue-class-components 8.0.0.
我们的目标是,因为我们必须不断向项目添加新功能,开始创建具有组合 API 的新组件,同时保留已经使用 vue class 组件编写的组件.而且,随着我们的进行,我们将尝试用组合 API.
重写它们我尝试使用 vue class 组件创建一个简单的 HelloWorld 组件:
<template>
<div>
<TestComponent :test="'test string'" />
</div>
</template>
<script lang="ts">
import { Options, Vue } from 'vue-class-component';
import TestComponent from './TestComponent.vue';
@Options({
components: { TestComponent }
})
export default class HelloWorld extends Vue {
}
</script>
并添加一个测试组件:
<template>
<h1>Test composant {{ test }}</h1>
</template>
<script lang="ts">
export default {
name: 'TestComponent',
props: { test: {type: String, required: true }},
setup(props: { test: string }, context: unknown) { console.log(context); return { test: props.test } }
}
</script>
但是,我在代码中发现了一个错误:在 HelloWorld 中声明 TestComponent 时,编译器告诉我他期待在 TestComponent 中声明的参数 'test':
Argument of type '{ name: string; props: { test: StringConstructor; required: boolean; }; setup(props: { test: string; }, context: unknown): { test: string; }; }' is not assignable to parameter of type 'Component<any, any, any, ComputedOptions, MethodOptions>'.
Type '{ name: string; props: { test: StringConstructor; required: boolean; }; setup(props: { test: string; }, context: unknown): { test: string; }; }' is not assignable to type 'ComponentOptions<any, any, any, ComputedOptions, MethodOptions, any, any, any>'.
Type '{ name: string; props: { test: StringConstructor; required: boolean; }; setup(props: { test: string; }, context: unknown): { test: string; }; }' is not assignable to type 'ComponentOptionsBase<any, any, any, ComputedOptions, MethodOptions, any, any, any, string, {}>'.
Types of property 'setup' are incompatible.
Type '(props: { test: string; }, context: unknown) => { test: string; }' is not assignable to type '(this: void, props: Readonly<LooseRequired<any>>, ctx: SetupContext<any>) => any'.
Types of parameters 'props' and 'props' are incompatible.
Property 'test' is missing in type 'Readonly<LooseRequired<any>>' but required in type '{ test: string; }'.ts(2345)
TestComponent.vue.ts(5, 18): 'test' is declared here.
更新: 我尝试在main.ts中全局注册TestComponent,但还是报错
有没有办法让两者一起工作?
请注意 :test
是 v-bind:test
的语法糖,这意味着如果您没有 :test
的反应变量绑定,您应该使用 test
反而。见下文:
// note there is no colon before test, which means you are just passing a constant string.
<TestComponent test="test string" />
一个问题是您的 props
声明不正确。应该是:
// ❌ invalid
// props: {
// test: String,
// required: true
// },
props: {
test: {
type: String,
required: true
}
},
此外,您不需要键入 setup()
的参数,因为它们通常是从 defineComponent()
实用程序推断出来的,enables type inference 在 Vue 组件中:
// export default {
// setup(props: { test: string }, context: unknown) { /*...*/ }
// }
import { defineComponent } from 'vue'
export default defineComponent({
setup(props, context) { /*...*/ }
})