rollup+antd+vite构建npm包

2,618 阅读3分钟

初始化pacage.json

1.yarn init

初始化一个pakage.json,里面包含一些基础的信息

2.安装依赖包

详情查看pakage.json👇🏻

{
  "name": "rollup-demo",
  "version": "0.1.5",
  "main": "./dist/index.js",
  "module": "./dist/index.esm.js",
  "author": "red-pen",
  "license": "MIT",
  "types": "./dist/index.d.ts",
  "files": [
    "dist"
  ],
  "repository": {
    "type": "git",
    "url": "https://github.com/red-pen/rollup.git"
  },
  "scripts": {
    "dev": "rollup -w -c",
    "start": "vite --host --open",
    "build": "rollup -c",
    "test": "echo \"Error: no test specified\" && exit 1"
  },
  "peerDependencies": {
    "antd": ">=4.0.0",
    "react": ">=16.8.0",
    "react-dom": ">=16.8.0"
  },
  "devDependencies": {
    "@babel/core": "^7.18.10",
    "@babel/preset-env": "^7.18.10",
    "@babel/preset-react": "^7.18.6",
    "@babel/preset-typescript": "^7.18.6",
    "@rollup/plugin-image": "^2.1.1",
    "@types/axios": "^0.14.0",
    "@types/crypto-js": "^4.1.1",
    "@types/react": "^18.0.17",
    "@types/react-dom": "^18.0.6",
    "@typescript-eslint/eslint-plugin": "^5.33.1",
    "@typescript-eslint/parser": "^5.33.1",
    "@vitejs/plugin-react": "^2.0.1",
    "antd": "^4.22.6",
    "babel-plugin-import": "^1.13.5",
    "less": "^4.1.3",
    "less-bundle-promise": "^1.0.7",
    "less-loader": "^11.0.0",
    "postcss": "^8.4.16",
    "react": "^18.2.0",
    "react-dom": "^18.2.0",
    "rollup": "^2.78.1",
    "rollup-plugin-babel": "^4.4.0",
    "rollup-plugin-commonjs": "^10.1.0",
    "rollup-plugin-dts": "^4.2.2",
    "rollup-plugin-node-resolve": "^5.2.0",
    "rollup-plugin-postcss": "^4.0.2",
    "typescript": "^4.8.3",
    "vite": "^3.0.8"
  }
}

vite启动配置

根目录新增一个index.html文件,通过script标签引入入口文件,添加type="module",代码如下👇🏻

<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8" />
    <meta http-equiv="X-UA-Compatible" content="IE=edge" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <title>Document</title>
  </head>
  <body>
    <div id="root"></div>
    <script type="module" src="./entry.tsx"></script>
  </body>
</html>

启动效果如图👇🏻

image.png

打包

新增.babelrc文件

{
  "presets": ["@babel/preset-env", "@babel/preset-react", "@babel/preset-typescript"],
  "plugins": [
    [
      "import",
      {
        "libraryName": "antd",
        "libraryDirectory": "es",
        "style": true
      }
    ]
  ]
}

新增 tsconfig.json文件

{
  "compilerOptions": {
    "baseUrl": "src",
    "module": "esnext",
    "target": "es5",
    "lib": ["es6", "dom", "es7", "es2017", "es2018", "esnext"],
    "sourceMap": true,
    "allowJs": true,
    "jsx": "react-jsx",
    "removeComments": true,
    "moduleResolution": "node",
    "forceConsistentCasingInFileNames": true,
    "allowSyntheticDefaultImports": true,
    "noImplicitReturns": true,
    "noImplicitThis": true,
    "noImplicitAny": true,
    "importHelpers": true,
    "strictNullChecks": true,
    "suppressImplicitAnyIndexErrors": true,
    "downlevelIteration": true,
    "experimentalDecorators": true,
    "skipLibCheck": true
  },
  "exclude": ["node_modules", "dist"]
}

基础配置,新建rollup.config.js

import postcss from "rollup-plugin-postcss";
import resolve from 'rollup-plugin-node-resolve'  // 帮助寻找node_modules里的包
import babel from 'rollup-plugin-babel'       // rollup 的 babel 插件,ES6转ES5
import replace from 'rollup-plugin-replace'    // 替换待打包文件里的一些变量,如 process在浏览器端是不存在的,需要被替换
import commonjs from 'rollup-plugin-commonjs'   // 将非ES6语法的包转为ES6可用
import uglify from 'rollup-plugin-uglify'      // 压缩包
import nested from "postcss-nested"; // 处理less
import cssnext from "postcss-cssnext";
import cssnano from "cssnano";
import json from "rollup-plugin-json";
import image from '@rollup/plugin-image';
const env = process.env.NODE_ENV
const config = {
  input: './src/index.js',
  external: ['react', 'antd'],   // 将其视为外部模块,不会打包在库中
  output: { 
    file: "./lib/bundle.js",
    format: 'cjs',   // 输出格式
    sourcemap: true,
    exports: "named"             
  },
  plugins: [
    image(),
    replace({
      'process.env.NODE_ENV': JSON.stringify(env)
    }),
    postcss({
      use: [
        ['less', {
          javascriptEnabled: true,
          modifyVars: { // 配置antd主题颜色
            "primary-color": "#52C9A0", // 主色
            "border-radius-base": "4px",
            "success-color": "#52C41A", // 成功色
            "warning-color": "#FAAD14", // 警告包
            "error-color": "#F5222D", // 错误色
            "body-background": "#FAFAFA", // 页面背影颜色
            // link coloe
            "link-color": "#52C9A0", // 链接的颜色
            "link-hover-color": "#5DDEB1", // 链接hover色
            "link-active-color": "#52C9A0", // 链接active色
          }
        }]
      ],
      plugins: [
        nested(), 
        cssnext({ warnForDuplicates: false }), 
        cssnano()
      ],
      extensions: [".css",'.less',],
      extract: false,
    }),
    // babel处理不包含node_modules文件的所有js
    babel({
      exclude: '**/node_modules/**',
      runtimeHelpers: true
    }),
    resolve(),
    // 这里有些引入使用某个库的api但报未导出改api通过namedExports来手动导出
    commonjs(
      {
          include: 'node_modules/**',
          namedExports: {
            'node_modules/react-is/index.js': ['isFragment','isMemo'],
            'node_modules/react-dom/index.js': ['findDOMNode']
          }
        }
  ),
  json(),
   ]
}

if (env === 'production') {
  config.plugins.push(
    uglify({  // 如果是生产环境就压缩bundle.js文件
      compress: {
        pure_getters: true,
        unsafe: true,
        unsafe_comps: true,
        warnings: false
      }
    })
  )
}

export default config

执行命令:yarn build

image.png

发布npm包

如果在npm官网注册了过,可以直接执行yarn publish, 如果没有在npm注册过,可以先执行yarn adduser 完善内容, image.png 然后执行npm publish

image.png 注意:name不要和npm上面其他人的项目名称的重复!!!

在npm官网查看自己的包

npm包已经在npm官网注册好了,可以在其他项目引入这个项目使用了 image.png

三方项目引用

import Demo from 'rollup-demo-redpen';

...
<Demo />

效果如图👇🏻

image.png

完整代码请到:github.com/red-pen/rol…