在我们实际的开发工作中,对于多次使用的组件或内容,会抽离作为组件,以便在不同模块使用,这样大大提高了代码的复用性。
那如果我们在不同项目中使用共公组件,就需要把组件封装成 npm 包,在不同项目中直接进行 npm install xxx 就可以实现复用。
那我们看一下,如何封装一个 npm 包
1、初始化 react+Ts项目
npx create-react-app [文件名] --template typescript
2、删除多余内容,只留下 src
node_modules
tsconfig.json
package.json
即可
3、清空 src 中的文件,新建 index.ts
[入口文件] 和 components
[模板文件夹]
index.ts
入口文件
// index.ts 入口文件 注意这里是 export 不是 import
export * from './components/Text'
components 文件夹下 新建 index.ts
和 Text.tsx
模版
// components/index.ts 文件
export * from './Text'
// components/Text.tsx 文件
import React, { FC } from 'react'
type TextProps = {
name: string
}
export const Text: FC<TextProps> = (props) => {
return <div>{props.name}</div>
}
// 重要: 模板使用的 标签名 <Text name={'xhh'} />
Text.displayName = 'Text'
image.png
好了,到目前位置,我们的模板就已经新建完成,下面就是需要打包及发布
4、修改 package.json
{
...
"author": "xiaohuihui",
"license": "ISC",
"main": "dist/npm_test.cjs.js",
"module": "dist/npm_test.esm.js",
"types": "dist/index.d.ts",
"sideEffects": false,
"files": [
"dist",
"typings"
],
"scripts": {
"prepare": "install-peers",
"build": "rollpkg build",
"watch": "rollpkg watch",
"prepublishOnly": "npm run build"
},
...
}
把"dependencies": {...}
修改为"peerDependencies": {...}
,peerDependencies
的目的是提示宿主环境去安装满足插件peerDependencies所指定依赖的包,然后在插件import或者require所依赖的包的时候,永远都是引用宿主环境统一安装的npm包,最终解决插件与所依赖包不一致的问题。
其他依赖 放在devDependencies
中,需要安装 npm i rollpkg install-peers-cli -D
package.json
完整配置:
{
"name": "npm_test",
"version": "0.1.0",
"private": false,
"author": "xhh",
"license": "ISC",
"main": "dist/npm_test.cjs.js",
"module": "dist/npm_test.esm.js",
"types": "dist/index.d.ts",
"sideEffects": false,
"files": [
"dist",
"typings"
],
"peerDependencies": {
"react": "^18.1.0",
"react-dom": "^18.1.0",
"react-scripts": "5.0.1"
},
"scripts": {
"prepare": "install-peers",
"build": "rollpkg build",
"watch": "rollpkg watch",
"prepublishOnly": "npm run build"
},
"devDependencies": {
"@testing-library/jest-dom": "^5.16.4",
"@testing-library/react": "^13.2.0",
"@testing-library/user-event": "^13.5.0",
"@types/jest": "^27.5.0",
"@types/node": "^16.11.34",
"@types/react": "^18.0.9",
"rollpkg": "^0.5.7",
"typescript": "^4.6.4",
"install-peers-cli": "^2.2.0",
"web-vitals": "^2.1.4",
"@types/react-dom": "^18.0.3"
},
"publishConfig": {
"registry": "xxxx"
}
}
5、在 tsconfig.json
中添加 "extends": "rollpkg/configs/tsconfig.json",
// tsconfig.json
{
"extends": "rollpkg/configs/tsconfig.json",
"compilerOptions": {
"target": "es5",
"lib": [
"dom",
"dom.iterable",
"esnext"
],
"sourceMap": true,
"allowJs": true,
"skipLibCheck": true,
"esModuleInterop": true,
"allowSyntheticDefaultImports": true,
"experimentalDecorators": true,
"strict": true,
"strictNullChecks": true,
"strictFunctionTypes": true,
"forceConsistentCasingInFileNames": true,
"module": "esnext",
"downlevelIteration": true,
"moduleResolution": "node",
"resolveJsonModule": true,
"isolatedModules": true,
"noEmit": true,
"removeComments": true,
"noUnusedLocals": false,
"noUnusedParameters": false,
"noImplicitAny": true,
"noImplicitReturns": true,
"noImplicitThis": true,
"jsx": "react-jsx",
"noFallthroughCasesInSwitch": true
}
}
6、添加eslint
相关内容
.eslintrc.json
{
"extends": ["./node_modules/rollpkg/configs/eslint"],
"rules": {
"quotes": [
"warn",
"single"
],
"semi": ["warn", "never"],
"no-console": "warn",
"no-debugger": "warn",
"no-alert": "warn",
"camelcase": "warn",
"@typescript-eslint/no-empty-interface": "warn",
"@typescript-eslint/no-empty-function": "warn",
"@typescript-eslint/no-unused-vars": "warn",
"jsx-a11y/click-events-have-key-events": "off",
"jsx-a11y/no-noninteractive-element-interactions": "off"
}
}
.eslintrc.commit.json
{
"extends": "./.eslintrc.json",
"rules": {
"no-console": "error",
"no-debugger": "error",
"no-alert": "error",
"camelcase": "error",
"@typescript-eslint/no-empty-interface": "error",
"@typescript-eslint/no-empty-function": "error",
"@typescript-eslint/no-unused-vars": "error"
}
}
好了,现在配置也改好了,直接执行 npm run build
打包,然后执行 npm publish
发布即可
网友评论