유형 문제: Nuxt, Vue 구성 API로 Vuetify
29261 단어 vuenuxttypescriptvuetify
저는 현재 Nuxt를 기반으로 하는 작은 장난감 프로젝트를 진행하고 있습니다. 이 프로젝트는 다음 기술 기반을 사용합니다.
또한 Vue3에서 사용할 Vue Composition API를 추가했습니다. 그러나 Nuxt와 Typescript를 사용하는 환경에는 몇 가지 문제가 있습니다.
시작하겠습니다! 어떤 문제가 있었고 그것을 해결하는 방법.
Nuxt 구성 요소 옵션
Nuxt.js는 다양한 구성 요소 옵션을 제공하며 Typescript를 사용하는 경우
@nuxt/types
에서 구성 요소 옵션을 찾을 수 있습니다.// node_modules/@nuxt/types/app/vue.d.ts
/**
* Extends interfaces in Vue.js
*/
import Vue from 'vue'
import { MetaInfo } from 'vue-meta'
import { Route } from 'vue-router'
import { Context, Middleware, Transition, NuxtApp } from './index'
import { NuxtRuntimeConfig } from '../config/runtime'
declare module 'vue/types/options' {
interface ComponentOptions<V extends Vue> {
asyncData?(ctx: Context): Promise<object | void> | object | void
fetch?(ctx: Context): Promise<void> | void
fetchDelay?: number
fetchOnServer?: boolean | (() => boolean)
head?: MetaInfo | (() => MetaInfo)
key?: string | ((to: Route) => string)
layout?: string | ((ctx: Context) => string)
loading?: boolean
middleware?: Middleware | Middleware[]
scrollToTop?: boolean
transition?: string | Transition | ((to: Route, from: Route | undefined) => string | Transition)
validate?(ctx: Context): Promise<boolean> | boolean
watchQuery?: boolean | string[] | ((newQuery: Route['query'], oldQuery: Route['query']) => boolean)
meta?: { [key: string]: any }
}
}
declare module 'vue/types/vue' {
interface Vue {
$config: NuxtRuntimeConfig
$nuxt: NuxtApp
$fetch(): void
$fetchState: {
error: Error | null
pending: boolean
timestamp: number
}
}
}
그러나 Nuxt 구성 요소에서 Vue Composition API를 사용하면 기본 유형 범위가
@nuxt/types
에서 @vue/composition-api
로 변경됩니다.따라서
layout
, middleware
, fetch
와 같이 nuxt에만 있는 일부 구성 요소 옵션에는 유형을 사용할 수 없습니다.예를 들어 보겠습니다.
<template>
<div>Hello Vue Composition API!</div>
</template>
<script lang="ts">
import { defineComponent } from '@vue/composition-api'
export default defineComponent({
layout: 'some-layout' // Error: No overload matches this call
})
</script>
기본적으로 Typescript 환경에서 composition-api를 사용하기 위해
definedComponent
를 선언합니다.layout
속성을 사용하려면 definedComponent
에서 선언해야 하지만 IDE 또는 편집기에서 해당 유형을 찾을 수 없다는 오류(또는 경고)가 표시됩니다.이 상황에서
layout
를 사용할 수 없는 이유를 추론할 수 있습니다.// node_modules/@vue/composition-api/dist/index.d.ts
import Vue$1, { VueConstructor, ComponentOptions, VNode, CreateElement } from 'vue';
...
interface ComponentOptionsBase<Props, D = Data, C extends ComputedOptions = {}, M extends MethodOptions = {}> extends Omit<ComponentOptions<Vue, D, M, C, Props>, 'data' | 'computed' | 'method' | 'setup' | 'props'> {
data?: (this: Props, vm: Props) => D;
computed?: C;
methods?: M;
}
...
declare type ComponentOptionsWithoutProps<Props = unknown, RawBindings = Data, D = Data, C extends ComputedOptions = {}, M extends MethodOptions = {}> = ComponentOptionsBase<Props, D, C, M> & {
props?: undefined;
setup?: SetupFunction<Props, RawBindings>;
} & ThisType<ComponentRenderProxy<Props, RawBindings, D, C, M>>;
...
declare function defineComponent<RawBindings, D = Data, C extends ComputedOptions = {}, M extends MethodOptions = {}>(options: ComponentOptionsWithoutProps<unknown, RawBindings, D, C, M>): VueProxy<unknown, RawBindings, D, C, M>;
declare function defineComponent<PropNames extends string, RawBindings = Data, D = Data, C extends ComputedOptions = {}, M extends MethodOptions = {}, PropsOptions extends ComponentPropsOptions = ComponentPropsOptions>(options: ComponentOptionsWithArrayProps<PropNames, RawBindings, D, C, M>): VueProxy<Readonly<{
[key in PropNames]?: any;
}>, RawBindings, D, C, M>;
declare function defineComponent<Props, RawBindings = Data, D = Data, C extends ComputedOptions = {}, M extends MethodOptions = {}, PropsOptions extends ComponentPropsOptions = ComponentPropsOptions>(options: HasDefined<Props> extends true ? ComponentOptionsWithProps<PropsOptions, RawBindings, D, C, M, Props> : ComponentOptionsWithProps<PropsOptions, RawBindings, D, C, M>): VueProxy<PropsOptions, RawBindings, D, C, M>;
예! 찾았습니다! 문제는
definedComponent
가 기본 VueComponentOptions
유형만 지원한다는 것입니다. 이 문제를 어떻게 해결할 수 있습니까?vue-shims.d.ts
먼저 프로젝트 루트의
vue-shim.d.ts
폴더에 파일@types
을 생성합니다. (이 documentation , vue-shim.d.ts
를 본 적이 있다면 이미 존재합니다.)import Vue from 'vue'
import { Context, Middleware } from '@nuxt/types'
...
declare module 'vue/types/options' {
interface ComponentOptions<V extends Vue> {
fetch?(ctx: Context): Promise<void> | void
layout?: string | ((ctx: Context) => string)
middleware?: Middleware | Middleware[]
}
}
그리고 위의 코드와 같이
ComponentOptions
인터페이스를 'vue/types/options'
모듈에서 extends Vue로 선언합니다.내부적으로 이 선언의 의미는 다음과 같습니다.
좋은! 이제 Nuxt.js ComponentOptions 유형을 사용할 수 있습니다!
$vuetify
Vuetify is a Material Design component framework for Vue.js
Vuetify는 Nuxt 및 Composition 환경의 ComponentOptions와 같은 유형과 유사한 문제가 있습니다. 즉,
this.$vuetify
에서 definedComponent
유형에 접근할 수 없습니다.아마도 Nuxt.js에서 Vueitfy를 사용한다면 @nuxtjs/vuetify
@nuxtjs/vuetify
는 다음과 같이 Nuxt 컨텍스트에서 $vuetify
유형을 제공합니다.// node_modules/@nuxtjs/vuetify/dist/index.d.ts
import { Module } from '@nuxt/types';
import { Framework } from 'vuetify';
import { Options, TreeShakeOptions, VuetifyLoaderOptions } from './options';
declare module '@nuxt/types' {
interface Configuration {
vuetify?: Options;
}
interface Context {
$vuetify: Framework;
}
}
declare const vuetifyModule: Module<Options>;
export { Options, TreeShakeOptions, VuetifyLoaderOptions };
export default vuetifyModule;
이 문제는 위의 문제와 같이 새로운 타입을 선언함으로써도 해결할 수 있습니다.
// vue-shim.d.ts
import { Framework } from 'vuetify'
...
declare module 'vue/types/vue' {
interface Vue {
$vuetify: Framework
}
}
이제
$vuetify
유형도 이와 같이 사용할 수 있습니다!<script lang="ts">
import { defineComponent } from '@vue/composition-api'
export default defineComponent({
setup(_, context) {
...
const { width } = context.root.$vuetify.breakpoint
...
}
})
</script>
결론
Nuxt.js
와 Vue Composition API
를 함께 사용하는 것은 아주 좋은 선택이 될 수 있습니다. 그러나 합성 API는 Nuxt(특히 TypeScript)에 대해 아직 완전히 지원되지 않습니다.물론 이 글의 내용이 전부는 아니지만 Typescript 환경에서 Nuxt와 Composition API를 사용하고자 하는 분들에게 도움이 되었으면 합니다.
이 주제가 더 궁금하시다면 nuxt-community/composition-api 프로젝트를 확인해보세요!
고맙습니다!
Reference
이 문제에 관하여(유형 문제: Nuxt, Vue 구성 API로 Vuetify), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다 https://dev.to/jaeheonjee/types-problem-nuxt-vuetify-with-vue-composition-api-33f2텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
우수한 개발자 콘텐츠 발견에 전념 (Collection and Share based on the CC Protocol.)