使用 TypeScript 向 Vue 3 添加全局属性

Nab*_*bor 4 typescript vue.js vuejs3

我想像这里建议的那样向 Vue 3 应用程序添加一个全局属性

原型方法不适用于 TypeScript。

我找到了一个示例,我将其转换为 config.d.ts

import Vue from 'vue'

import base from '@/config/config.json'
import dev from '@/config/config.dev.json'
import prod from '@/config/config.prod.json'

let config
if (process.env.NODE_ENV === 'production') {
  config = Object.freeze(Object.assign(base, prod))
} else {
  config = Object.freeze(Object.assign(base, dev))
}

declare module 'vue/types/vue' {
  interface Vue {
    $config: config
  }
}
Run Code Online (Sandbox Code Playgroud)

我想加载一些具有 dev 或 prod 范围的本地配置文件。范围内的文件不会被检入 GIT 存储库。

main.ts 现在看起来像这样......

import Vue from 'vue'
import {createApp} from 'vue'
import App from './App.vue'
import Config from '@/plugins/config.d.ts'

Vue.use(Config)
createApp(App).mount('#app')
Run Code Online (Sandbox Code Playgroud)

问题:

ERROR in src/main.ts:6:5
TS2339: Property 'use' does not exist on type 'typeof import("d:/Martin/Entwicklung/2020/STA-Electron/node_modules/vue/dist/vue")'.
    4 | import Config from '@/plugins/config.d.ts'
    5 |
  > 6 | Vue.use(Config)
      |     ^^^
    7 | createApp(App).mount('#app')
    8 |
Run Code Online (Sandbox Code Playgroud)

我理想中想要实现的是可以在Vue 3的setup方法中使用的全局config$config属性

ERROR in src/main.ts:6:5
TS2339: Property 'use' does not exist on type 'typeof import("d:/Martin/Entwicklung/2020/STA-Electron/node_modules/vue/dist/vue")'.
    4 | import Config from '@/plugins/config.d.ts'
    5 |
  > 6 | Vue.use(Config)
      |     ^^^
    7 | createApp(App).mount('#app')
    8 |
Run Code Online (Sandbox Code Playgroud)

我怎样才能解决这个问题?

更新

在 danielv 回答之后,新插件看起来像这样

export default defineComponent({
  name: 'App',
  components: {},
  setup(props, context) {
    const elem = ref(context.$config.prop1)
    const doSth = () => {
      console.log('Config', context.$config)
    }
    return {doSth, elem}
  },
})
Run Code Online (Sandbox Code Playgroud)

main.ts 也变成了这个

import {App} from 'vue'

export interface ConfigOptions {
  base: any
  dev: any
  prod: any
}

export default {
  install: (app: App, options: ConfigOptions) => {
    app.config.globalProperties.$config =
      process.env.NODE_ENV === 'production'
        ? Object.freeze(Object.assign({}, options.base, options.prod))
        : Object.freeze(Object.assign({}, options.base, options.dev))
  },
}
Run Code Online (Sandbox Code Playgroud)

这个简单的插件可以在模板中使用

import {createApp} from 'vue'
import App from '@/App.vue'
import ConfigPlugin from '@/plugins/config'
import base from '@/config/config.json'
import dev from '@/config/config.dev.json'
import prod from '@/config/config.prod.json'

createApp(App).use(ConfigPlugin, {base, dev, prod}).mount('#app')
Run Code Online (Sandbox Code Playgroud)

IntelliJ 抱怨未知变量 prop1,但它有效。

我搜索了很多,但发现没有办法将我的 $config 插入到与组合 api 一起使用的设置方法中。

nam*_*ato 17

您可以@vue/runtime-core在应用程序中扩充TypeScript 模块:

declare module '@vue/runtime-core' {
  interface ComponentCustomProperties {
    $config: Record<string, unknown>;
  }
}
Run Code Online (Sandbox Code Playgroud)

类似于过去在 Vue 2 中的工作方式

似乎这还没有进入 Vue 3 文档,而是通过vuejs/vue-next#982引入。查看ComponentCustomProperties接口源代码以获取更多信息。

  • 在按照链接文档中的定义扩充模块之前,不要忘记添加“import Vue from 'vue'”。 (2认同)
  • 编译器不喜欢这个`模块'"../../../node_modules/vue/dist/vue"'没有导出成员'defineComponent'。`? (2认同)
  • 要增强“globalProperties”,您需要先导入“import { ComponentCustomProperties } from 'vue';”,否则编译器会抱怨它 (2认同)