介绍
在多个项目上工作时往往会发生的情况是,每个项目都需要相同的通用组件,例如有程式化的文本字段或更复杂的诸如日期选择器之类的东西。
最好的行动过程是编写一个组件并从单个点进行更新,它是从中分发的软件包。
我们将要做的是编写一个NPM软件包,该软件包将带有打字稿类型定义的VUE 3组件进行启动!我选择制作的组件是此演示的三态复选框。
开始
我将在此项目中使用Vite,因为它是WebPack作为构建工具和开发服务器的不错替代方法。使用您选择的软件包管理器来创建一个项目,我会选择yarn
:
yarn create vite
选择这些设置并命名您的项目理想情况下,您将如何命名最终组成部分:
√ Project name: ... vue-tri-state-checkbox
√ Select a framework: » Vue
√ Select a variant: » TypeScript
清除您不需要的任何文件或代码的项目,我通常只使用App.vue
进行测试目的,并使用components
文件夹用于存储组件并导出它们。
您的src
文件夹应该看起来像:
组件
在VUE 3的工作原理上写下您的组件,我将使用它作为我的组件的示例:
<template>
<label>
<input
type="checkbox"
:disabled="disabled"
:indeterminate="val === null"
:checked="val === true"
@click="change"
/>
<span>
{{ label }}
</span>
</label>
</template>
<script setup lang="ts">
import { ref, watch } from "vue";
const props = withDefaults(
defineProps<{
label?: string;
modelValue: boolean | null;
disabled?: boolean;
color?: string;
}>(),
{
color: "#2f4fef"
}
);
const emit = defineEmits<{
(e: "update:modelValue", value: boolean | null): void;
}>();
const val = ref<boolean | null>(false);
const change = () => {
if (val.value === false) val.value = null;
else if (val.value === null) val.value = true;
else val.value = false;
emit("update:modelValue", val.value);
};
watch(
() => props.modelValue,
(value) => (val.value = value)
);
</script>
使组件可导出
在您的src
文件夹中,我们将创建一个index.ts
文件,该文件将用于从components
文件夹导出组件。
import TriStateCheckbox from "./components/triStateCheckbox.vue";
export { TriStateCheckbox };
我们将需要一些新的依赖项,因此将这些软件包添加到您的开发依赖项中,这些软件包将很快解释:
yarn add vite-plugin-dts path -D
默认的vite.config.ts
您在这一点上应该有类似于以下内容:
import { defineConfig } from "vite";
import vue from "@vitejs/plugin-vue";
// https://vitejs.dev/config/
export default defineConfig({
plugins: [vue()]
});
我们将增加几行,因此:
import vue from "@vitejs/plugin-vue";
import * as path from "path";
import { defineConfig } from "vite";
import dts from "vite-plugin-dts";
export default defineConfig({
plugins: [vue(), dts()],
build: {
lib: {
entry: path.resolve(__dirname, "src/index.ts"),
name: "TriStateCheckbox",
fileName: "vue-tri-state-checkbox"
},
rollupOptions: {
external: ["vue"],
output: {
globals: {
vue: "Vue"
}
}
}
},
resolve: {
alias: {
"@": path.resolve(__dirname, "src")
}
}
});
让我们介绍这里发生的事情:首先,在plugins
属性中,我们添加了dts
,这是vite-plugin-dts
软件包的一部分。它的主要目的是从VUE文件中创建类型定义文件以自动以获得更好的开发体验,也就是说,它可以从.vue
创建d.ts
文件。
在build
属性中,我们定义了一些其他属性,这些属性将用于定义软件包本身的构建过程如何工作。
lib
告诉构建过程,将整个东西像对待整个库一样对待,请阅读更多here。我们在此处定义的属性是:
-
build
-包装导出的位置,也就是说用户在发布后从何处导入软件包,在这里我们使用path
函数和__dirname
变量指向先前定义的index.ts
folde4index.ts
文件夹,该变量指向主要项目的文件夹 -
name
-包装的唯一标识符,尝试将其与您的软件包名称保持一致 -
fileName
-一种唯一标识符,将用于描述包装文件输出
在rollupOptions
中,我们将定义一些内容来告诉croulup如何配置模块bundler:
最后,使用resolve
属性将@
定义为src
文件夹路径的别名。
接下来,我们将编辑tsconfig.json
文件:
{
"compilerOptions": {
"target": "ESNext",
"useDefineForClassFields": true,
"module": "ESNext",
"moduleResolution": "Node",
"strict": true,
"jsx": "preserve",
"resolveJsonModule": true,
"isolatedModules": true,
"esModuleInterop": true,
"lib": ["ESNext", "DOM"],
"skipLibCheck": true,
"noEmit": true
},
"include": ["src/**/*.ts", "src/**/*.d.ts", "src/**/*.tsx", "src/**/*.vue"],
"references": [{ "path": "./tsconfig.node.json" }]
}
明显的更改是target
属性,通常是从ES2020
的过渡,默认为ESNext
。
建立包裹
您都完成了上面提到的文件的编辑时,我们需要查看构建过程是否通过运行yarn build
来工作。
您应该获得与此类似的输出:
$ vue-tsc && vite build
vite v4.3.9 building for production...
✓ 4 modules transformed.
dist/style.css 2.15 kB │ gzip: 0.65 kB
dist/vue-tri-state-checkbox.js 1.12 kB │ gzip: 0.58 kB
dist/vue-tri-state-checkbox.umd.cjs 1.09 kB │ gzip: 0.61 kB
[vite:dts] Start generate declaration files...
✓ built in 1.29s
[vite:dts] Declaration files built in 822ms.
Done in 3.49s.
有3个生成的文件,如果您添加了更多依赖项或将组件拆分为多个文件,则可能还有更多。这些是:
-
style.css
-包装的CSS捆绑在一个单数入口点 -
vue-tri-state-checkbox.js
-包含捆绑的JavaScript代码 的主要软件包入口点
-
vue-tri-state-checkbox.umd.cjs
-通用模块系统和常见的JS入口点
所有这些都位于dist
文件夹中,该文件夹将用于使用NPM分配包装。
不过,在我们这样做之前,我们必须编辑package.json
。
package.json
我们需要更改package.json
才能分发新创建的组件(单词和软件包将从现在开始互换使用):
-
private
需要设置为false
- 添加
files
属性以指定哪些文件将在软件包函数中起作用,在使用yarn build
构建组件后,所有分发文件都将在dist
文件夹中
"files": ["dist", "src/components/"],
此外,我们将添加src/components
文件夹,因为这些组件是从那里导出的。
- 在
repository
属性中命名您的git存储库
"repository": {
"type": "git",
"url": "git+https://github.com/MatijaNovosel/tri-state-checkbox.git"
},
- 指定一些关键字
"keywords": [
"checkbox",
"material",
"material-ui",
"tri-state-checkbox",
"vue3",
"vue",
"vuejs"
],
- 通过
main
属性设置包装的主要入口点
"main": "./dist/vue-tri-state-checkbox.umd.cjs",
- 设置
module
属性,它被main
属性掩盖为noted here,但仍然需要
"module": "./dist/vue-tri-state-checkbox.js",
- 定义
dts
包装生成的软件包类型的types
属性
"types": "./dist/index.d.ts",
- 设置将用于分发软件包文件的
exports
属性
"exports": {
".": {
"import": "./dist/vue-material-time-picker.js",
"require": "./dist/vue-material-time-picker.umd.cjs"
},
"./dist/style.css": {
"import": "./dist/style.css",
"require": "./dist/style.css"
}
},
- 最后,添加仅包含
vue
的peerDependencies
属性,该部分将用于定义该软件包所依赖的包装
"peerDependencies": {
"vue": "^3.0.0"
},
完整的package.json
文件如下:
{
"name": "vue-tri-state-checkbox",
"private": false,
"version": "0.0.1",
"type": "module",
"repository": {
"type": "git",
"url": "git+https://github.com/MatijaNovosel/tri-state-checkbox.git"
},
"keywords": [
"checkbox",
"vue-tri-state-checkbox",
"material",
"material-ui",
"vue3",
"vue",
"vuejs"
],
"files": ["dist", "src/components/"],
"main": "./dist/vue-tri-state-checkbox.umd.cjs",
"module": "./dist/vue-tri-state-checkbox.js",
"exports": {
".": {
"import": "./dist/vue-tri-state-checkbox.js",
"require": "./dist/vue-tri-state-checkbox.umd.cjs"
},
"./dist/style.css": {
"import": "./dist/style.css",
"require": "./dist/style.css"
}
},
"types": "./dist/index.d.ts",
"scripts": {
"dev": "vite",
"build": "vue-tsc && vite build",
"preview": "vite preview"
},
"dependencies": {
"sass": "^1.62.1",
"vue": "^3.2.47"
},
"peerDependencies": {
"vue": "^3.0.0"
},
"devDependencies": {
"@vitejs/plugin-vue": "^4.1.0",
"path": "^0.12.7",
"typescript": "^5.0.2",
"vite": "^4.3.9",
"vite-plugin-dts": "^2.3.0",
"vue-tsc": "^1.4.2"
}
}
不要忘记将版本设置为0.0.1
或您选择的其他选择。
分发包裹
首先,您需要使用npm login
登录,完成该过程,然后运行npm publish
。
如果一切都进行了计划,您应该在输出中看到此支架:
npm notice Publishing to https://registry.npmjs.org/
+ vue-tri-state-checkbox@0.0.1
检查NPM页面本身应该可以立即安装:
在新项目的内部,您应该能够使用选择的软件包管理器:yarn add vue-tri-state-checkbox
。
使用该组件,在全球定义它或仅在本地导入它,包括CSS文件:
<template>
<tri-state-checkbox v-model="val" />
</template>
<script lang="ts" setup>
import { ref } from "vue";
import { TriStateCheckbox} from "vue-tri-state-checkbox";
import "vue-tri-state-checkbox/dist/style.css";
const val = ref(null);
</script>
更新软件包
如果您需要随时对项目进行更改,只需在package.json
版本编号上,再次构建包装并运行npm publish
。
结论
即使有点乏味,使您的项目的可导出组件可以节省时间,而且非常实用。
可以找到该项目的源代码here。