前端工程化:发布一个属于自己的规范 npm 包

news2024/11/26 13:43:55

初始化项目

首先在github创建一个仓库,协议选择MIT,gitignore选择Node,添加README.md描述文件。使用git clone将项目克隆到本地。cd 进入目录,使用vscode打开(终端输入code . 命令即可)。

然后创建一个合理的目录结构:

配置 typescript

{
  "compilerOptions": {
    "target":  "ES5",
    "outDir": "lib",
    "lib": [
      "DOM",
      "ES2018"
    ],
    "declaration": true,
    "checkJs": false,
    "noEmitOnError": true,
    "emitDeclarationOnly": true,
    "allowJs": true,
    "experimentalDecorators": true,
    "skipLibCheck": true,
    "esModuleInterop": true,
    "importHelpers": true,
    "allowSyntheticDefaultImports": true,
    "strict": true,
    "forceConsistentCasingInFileNames": true,
    "noFallthroughCasesInSwitch": true,
    "module": "commonjs",
    "moduleResolution": "node",
    "resolveJsonModule": true,
    "isolatedModules": true,
    "pretty": true,
    "jsx": "react-jsx",
    "newLine": "lf",
    "typeRoots": [
      "./src/@types",
      "./node_modules/@types"
    ]
  },
  "include": [
    "src",
  ],
  "exclude": [
    "node_modules"
  ]
}

统一代码风格

首先,配置eslint,使用遵循Airbnb推出的JavaScript风格指南的eslint-config-airbnb,eslint-config-airbnb-typescript。

 其次,配置prettier,安装依赖prettier,.prettierrc.js的推荐配置如下:

module.exports = {
    // 一行最多 80 字符
    printWidth: 80,
    // 使用 2 个空格缩进
    tabWidth: 2,
    // 不使用缩进符,而使用空格
    useTabs: false,
    // 行尾需要有分号
    semi: true,
    // 使用单引号
    singleQuote: true,
    // 结尾处不加逗号
    trailingComma: "none",
    // 对象的 key 仅在必要时用引号
    quoteProps: 'as-needed',
    // jsx 不使用单引号,而使用双引号
    jsxSingleQuote: false,
    // 大括号内的首尾需要空格
    bracketSpacing: true,
    // jsx 标签的反尖括号需要换行
    jsxBracketSameLine: false,
    // 箭头函数,只有一个参数的时候,也需要括号
    arrowParens: 'always',
    // 每个文件格式化的范围是文件的全部内容
    rangeStart: 0,
    rangeEnd: Infinity,
    // 不需要写文件开头的 @prettier
    requirePragma: false,
    // 不需要自动在文件开头插入 @prettier
    insertPragma: false,
    // 使用默认的折行标准
    proseWrap: 'preserve',
    // 根据显示样式决定 html 要不要折行
    htmlWhitespaceSensitivity: 'css',
    // vue 文件中的 script 和 style 内不用缩进
    vueIndentScriptAndStyle: false,
    // 换行符使用 lf
    endOfLine: 'lf',
};

最后,增加 git 提交校验,安装依赖husky和lint-staged,其中,husky用于git 的hook,lint-staged用于针对暂存的 git 文件运行 linters。

在package.json中配置安装 husky 的命令,以及lint-staged检查:

执行npm run prepare 安装 husky,并在生成的.husky/pre-commit文件(如果没有生成,手动创建一个即可)中添加 npx lint-staged 命令:

All ready!执行git commit 提交代码就会触发 prettier和eslint自动修复。

配置babel

module.exports = {
  env: {
    test: {
      presets: [
        '@babel/preset-env'
      ]
    },
    build: {
      presets: [
        [
          '@babel/preset-env',
          {
            // rollupjs 会处理模块,所以设置成 false
            modules: false,
            loose: true
          }
        ]
      ]
    }
  }
}

配置rollup

如果开发的是工具包,rollup更适合作为打包工具,如果是组件,比如vue组件,则@vue/cli 的 lib 模式更适合。根据开发环境区分不同的配置并在package.json的script中添加脚本命令,输出不同规范的产物:umd、umd.min、cjs、esm。

通用配置rollup.config.base.js

import { nodeResolve } from '@rollup/plugin-node-resolve'; // 解析 node_modules 中的模块
import commonjs from '@rollup/plugin-commonjs'; // cjs => esm
import alias from '@rollup/plugin-alias'; // alias 和 resolve 功能
import replace from '@rollup/plugin-replace';
import eslint from '@rollup/plugin-eslint';
import { babel } from '@rollup/plugin-babel';
import { terser } from 'rollup-plugin-terser';
import clear from 'rollup-plugin-clear';
import typescript from '@rollup/plugin-typescript';
import json from '@rollup/plugin-json'; // 支持在源码中直接引入json文件,不影响下面的
import { name as pkgName, version, author } from '../package.json';

const banner = '/*!\n'
  + ` * ${pkgName} v${version}\n`
  + ` * (c) 2023-${new Date().getFullYear()} ${author}\n`
  + ' * Released under the MIT License.\n'
  + ' */';

export default {
  input: 'src/index.ts',
  // 同时打包多种规范的产物
  output: [
    {
      file: `lib/${pkgName}.umd.js`,
      format: 'umd',
      name: pkgName,
      banner
    },
    {
      file: `lib/${pkgName}.umd.min.js`,
      format: 'umd',
      name: pkgName,
      banner,
      plugins: [terser()]
    },
    {
      file: `lib/${pkgName}.cjs.js`,
      format: 'cjs',
      name: pkgName,
      banner
    },
    {
      file: `lib/${pkgName}.esm.js`,
      format: 'es',
      banner
    }
  ],
  // 注意 plugin 的使用顺序
  plugins: [
    json(),
    clear({
      targets: ['lib']
    }),
    alias(),
    replace({
      'process.env.NODE_ENV': JSON.stringify(
        process.env.NODE_ENV || 'development'
      ),
      preventAssignment: true
    }),
    nodeResolve(),
    commonjs({
      include: 'node_modules/**'
    }),
    typescript(),
    eslint({
      throwOnError: true, // 抛出异常并阻止打包
      include: ['src/**'],
      exclude: ['node_modules/**']
    }),
    babel({ babelHelpers: 'bundled' })
  ]
};

开发环境配置rollup.config.dev.js

import serve from 'rollup-plugin-serve';
import livereload from 'rollup-plugin-livereload';
import baseConfig from './rollup.config.base';

export default {
  ...baseConfig,
  plugins: [
    ...baseConfig.plugins,
    livereload({
      watch: 'examples/browser'
    }),
    serve({
      port: 8080,
      contentBase: ['lib', 'examples/browser'],
      openPage: 'index.html'
    })
  ]
};

正式环境配置rollup.config.prod.js

import filesize from 'rollup-plugin-filesize';
import baseConfig from './rollup.config.base';

export default {
  ...baseConfig,
  plugins: [...baseConfig.plugins, filesize()]
};

 添加开发与打包相关的脚本命令到package.json,借助npm-run-all 依赖,npm run build按顺序执行z,buildjs,buildts。

添加支持tree shaking 的配置到package.json中。

发布到npm

编写发布到npm时需要忽略的文件与目录的配置,即.npmignore。

# OSX
.DS_Store

# IDE
.idea

# npm
node_modules

# jest
coverage

# dev
bin
src
scripts
test
.babelrc.js
.eslintrc.js
.eslintignore
.prettierrc.js
.prettierignore
tsconfig.json

#doc
docs
examples

#other
.github
.husky

添加发布相关的脚本命令到package.json中,其中 npm --no-git-tag-version version 分别修改版本号中的major,minor,patch。

然后登录npm官网(npm login --registry https://registry.npmjs.org/),登录成功后,直接发布即可(npm publish --registry https://registry.npmjs.org/)。

发布过程中常见的报错:

        1. 400:版本问题,修改package.json的version即可;

        2. 401:npm源设置成第三方源(淘宝源)的时候发生的,比如我们经常会将镜像源设置成淘宝源。因此在发布时,应该使用默认的npm源登录,即npm login --registry https://registry.npmjs.org/;

        3. 403:包名重复,修改包名重新发布。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/551703.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

CentOS-7 安装 MariaDB-10.8

一、安装之前删除已存在的 Mysql/MariaDB 1 查找存在的 MariaDB # 注意大小写 rpm -qa | grep MariaDB # rpm -qa 列出所有被安装的rpm package (-qa:query all) rpm -qa | grep mariadb # grep (缩写来自Globally search a Regular Expre…

C++ 折叠参数包:悄然增强编程效率

前言 欢迎来到💖小K💖的💞C专栏💞,本节将为大家带来折叠参数包的详细讲解,折叠参数包为C模板编程提供了更加灵活和强大的工具,可以提高代码的简洁性和可读性,看完后希望对你有收获 文…

室内外融合定位UWB信标定位方案

大家好,我是北京华星智控公司小智,今天我给大家介绍室内外融合定位系统方案,该方案室外采用北斗卫星定位技术室内采用UWB定位技术从而实现室内外精确定位无缝切换,实现室内外的融合定位。 室内外融合定位系统, 该方案…

Binder相关问题

Binder相关问题 1、Binder是什么?2、Binder有什么优势?3、Binder如何做到一次拷贝的?4、MMAP的原理是什么?5、Binder机制是如何跨进程的?6、为什么Intent不能传递大数据7、AIDL生成Java类细节8、四大组件底层的通信机制…

波奇学Linux:yum和vim

Linux三种安装方式 源代码安装 用户下载->软件源码->源码编译->可执行程序 rpm安装:相当于去官网下载Linux安装包 可能存在依赖项不匹配问题。 yum安装包 用户yum下载->软件安装包->可执行程序 yum是软件包管理器,解决安装源&…

玩客云刷Armbian带docker详细教程(附所有软件)

文章目录 介绍一.准备工作1.硬件准备2.软件准备 二.开始折腾1.烧录系统固件2.刷入系统1.准备镜像2.刷入镜像3.刷入镜像到系统 三.功能介绍1.网页终端2.设备状态3.AriaNg4.qBittorrent5.微力同步6.filebrowser7.Portainer 四.拓展1.添加Alist1.介绍2.安装3.配置3.1查看密码3.2修…

chatgpt赋能Python-pythoncidere

PythonCider:提供最优质的 Python 编程知识 Python 是目前最受欢迎的编程语言之一,特别在数据科学和人工智能方面应用广泛。如果你是一名 Python 开发者或者正在学习 Python 编程,PythonCider 是一个你绝对不能错过的网站。 什么是 PythonC…

JavaScript实战训练小项目 WebAPI

JavaScript实战训练小项目 文章目录 JavaScript实战训练小项目 & WebAPI1. JS操作DOM树1.1 获得HTML控件/元素标签1.2 操纵控件1.2.1 获取属性值1.2.1 修改属性值 1.3 实现一个猜数字的功能 2. JQuery3. 简单计算器4. 聚合搜索5. 表白墙 JavaScript实战训练小项目 & We…

OpenLayers入门教程汇总目录

前言 本篇作为OpenLayers入门教程的目录,用于整理汇总专栏所有文章,方便查找。 入门 Gis开发入门,OpenLayers、Leaflet、Maplibre-gl和Cesiumjs地图引擎介绍以及几种地图服务vms、vmts介绍vue项目集成并使用OpenLayers地图的两种方式 加…

记ABAC的落地实践

为什么使用ABAC 一般提到授权,我们就会想到角色(role)。什么样的用户拥有什么样的角色可以怎么操作什么样的资源,这是我们普遍使用的权限系统的模型。这里的角色实质上是包含了一组用户操作资源的规则集合。一旦角色被创建&#…

【RISC-V】执行环境

裸机程序 操作系统 虚拟化 RISC-V处理器3种模式 机器模式(M模式) 安全执行环境,通常运行SBI固件,为操作系统提供服务。 特权模式(S模式) 运行操作系统内核,为应用程序提供服务。 用户模式(U模式) 运行应用程序。 虚拟化新增特权模式 …

Boundary IoU:Improving Object-Centric Image Segmentation Evaluation总结笔记

Boundary IoU:Improving Object-Centric Image Segmentation Evaluation(边界Iou:改进以对象为中心的图像分割评价) 目录 一、论文出发点 二、论文核心思想 三、相关工作 四、敏感度分析 五、Boundary IoU定义和实验证明 六、应用 七…

【系统移植】uboot 通过 NFS 加载根文件系统(一) —— 网络环境配置

前面试过了SD卡烧录根文件系统,然后借助环境变量 bootargs 来加载SD卡中的根文件系统,但是实际开发需要经常对文件做增删改等操作,所以将根文件系统放在SD上不大合适。 因此,最常用的做法是把根文件系统放在NFS服务端&#xff08…

Spring事务及事务传播机制

一.事务的含义:多个操作封装在一起,要么同时执行成功,一旦有一个操作执行失败,那么全部执行失败。这里给大家举个例子:比如A给B转账50元,而B没有收到这50元,此时A转账B这个操作也需要进行回滚,恢复到A给B没…

HTTP 协议的基本格式

HTTP 什么是HTTP?HTTP是应用层的一个重要协议.它定义了浏览器怎样向服务器请求文件,以及服务器怎样把文件传送给浏览器. 我们打开浏览器,手动输入一个网址:baidu.com.那么此时浏览器就会给百度的服务器发送请求.百度服务器在返回一个html的响应. 那么我们如何学习HTTP协议呢…

【系统移植】uboot 通过 NFS 加载根文件系统(二) —— 修改环境变量 bootcmd、bootargs

上一部分已经配置好了网络环境,我们要修改环境变量以保证开发板可以正常启动,uboot 环境变量中比较重要的环境变量就是 bootcmd 和 bootargs 目录 1、修改自启动命令 — bootcmd 2、修改自启动参数 —— bootargs (1) root/dev/nfs rw (2) nfsroot …

Godot引擎 4.0 文档 - 循序渐进教程 - 创建你的第一个脚本

本文为Google Translate英译中结果,DrGraph在此基础上加了一些校正。英文原版页面: Creating your first script — Godot Engine (stable) documentation in English 创建你的第一个脚本 在本课中,您将编写您的第一个脚本,使用…

Datacom-HCIE 题库 02(10月26日更新)--含解析

单选题 1.[试题编号:189785] (单选题)如图所示,VTEP1上在BD20域内开启了ARP广播抑制功能,并且VTEP1通过 BGP EVPN路由学习到了PC2的ARP信息,则PC1发送的针对PC2的ARP请求,VIEP1在转发给VIEP2时…

设备采购信息管理系统

系列文章 任务14 设备采购信息管理系统 文章目录 系列文章一、实践目的与要求1、目的2、要求 二、课题任务三、总体设计1.存储结构及数据类型定义2.程序结构3.所实现的功能函数4、程序流程图 四、小组成员及分工五、 测试界面展示添加采购信息按编号查找采购信息按设备编号查找…

vue记录鼠标拖拽划过位置并将划过位置变色

首先 我们要做一个这样的基本组件 <template><div><!--循环遍历 List数组用当前下面当做key值然后定义了 onDragStart 鼠标拖动时触发定义 onDragEnd 拖动结束后触发定义 onDragOver 记录所有鼠标拖动经过的位置--><divclass"skeleton"v-f…