Skip to main content

发布 Node.js 包

您可以将 Node.js 包发布到注册表,作为持续集成 (CI) 工作流程的一部分。

简介

本指南介绍如何创建一个工作流程,以在持续集成 (CI) 测试通过后将 Node.js 包发布到 GitHub Packages 和 npm 注册表。

先决条件

建议基本了解工作流程配置选项和如何创建工作流程文件。 有关详细信息,请参阅“写入工作流”。

有关为 Node.js 项目创建 CI 工作流的详细信息,请参阅“构建和测试 Node.js”。

你可能还发现基本了解以下内容是有帮助的:

关于包配置

package.json 文件中的 nameversion 字段创建一个唯一标识符,注册表使用该标识符将包链接到注册表。 可以通过在 package.json 文件中包含一个 description 字段来添加软件包列表页面的摘要。 有关详细信息,请参阅 npm 文档中的“创建 package.json 文件”和“创建 Node.js 模块”。

当本地 .npmrc 文件存在并指定了 registry 值时,npm publish 命令将使用在 .npmrc 文件中配置的注册表。 可使用 setup-node 操作在运行器上创建本地 .npmrc 文件以配置默认注册表和范围。 setup-node 操作也接受身份验证令牌作为输入,用于访问私人注册表或发布节点包。 有关详细信息,请参阅 setup-node

可以使用 setup-node 操作指定运行器上安装的 Node.js 版本。

如果在工作流中添加步骤来配置 package.json 文件中的 publishConfig 字段,则无需使用 setup-node 操作指定 registry-url,但是只能将包发布到一个注册表。 有关详细信息,请参阅 npm 文档中的“publishConfig”。

发布包到 npm 注册表

每次发布新版本时,都可以触发工作流来发布包。 触发类型 published 的版本事件时,执行下例中的过程。 如果 CI 测试通过,该过程会将包上传到 npm 注册表。 有关详细信息,请参阅“管理仓库中的发行版”。

要根据工作流程中的 npm 注册表执行经过身份验证的操作,您需要将 npm 身份验证令牌作存储为密码。 例如,创建名为 NPM_TOKEN 的存储库机密。 有关详细信息,请参阅“在 GitHub Actions 中使用机密”。

默认情况下,npm 使用 package.json 文件的 name 字段来确定已发布包的名称。 当发布到全局命名空间时,您只需要包含包名称。 例如,将名为 my-package 的包发布到 https://www.npmjs.com/package/my-package

如果要发布包含范围前缀的包,请在 package.json 文件的名称中包含范围。 例如,如果 npm 范围前缀是“octocat”并且包名称是“hello-world”,那么 package.json 文件中的 name 应为 @octocat/hello-world。 如果 npm 包使用范围前缀并且包是公共的,则需要使用选项 npm publish --access public。 这是 npm 需要用来防止有人无意中发布私有包的选项。

如果要发布具有证明的包,请将 --provenance 标志包含在命令 npm publish 中。 这样,你就可以公开且可验证地确定包的生成位置和方式,从而增加使用包的人员的供应链安全性。 有关详细信息,请参阅 npm 文档中的生成来源语句

此示例将 NPM_TOKEN 机密存储在 NODE_AUTH_TOKEN 环境变量中。 当 setup-node 操作创建 .npmrc 文件时,会引用来自 NODE_AUTH_TOKEN 环境变量的令牌。

YAML
name: Publish Package to npmjs
on:
  release:
    types: [published]
jobs:
  build:
    runs-on: ubuntu-latest
    permissions:
      contents: read
      id-token: write
    steps:
      - uses: actions/checkout@v4
      # Setup .npmrc file to publish to npm
      - uses: actions/setup-node@v4
        with:
          node-version: '20.x'
          registry-url: 'https://registry.npmjs.org'
      - run: npm ci
      - run: npm publish --provenance --access public
        env:
          NODE_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }}

在上面的示例中,setup-node 操作在运行器上创建了一个具有以下内容的 .npmrc 文件:

//registry.npmjs.org/:_authToken=${NODE_AUTH_TOKEN}
registry=https://registry.npmjs.org/
always-auth=true

请注意,需要在 setup-node 中将 registry-url 设置为 https://registry.npmjs.org/ 才能正确配置凭据。

发布包到 GitHub Packages

每次发布新版本时,都可以触发工作流来发布包。 触发类型 published 的版本事件时,执行下例中的过程。 如果 CI 测试通过,该过程会将包上传到 GitHub Packages。 有关详细信息,请参阅“管理仓库中的发行版”。

配置目标仓库

使用 repository 键将包链接到 GitHub Packages 是可选操作。 如果你选择不在 package.json 文件中提供 repository 密钥,则你的包在发布时不会链接到存储库,但你可以选择稍后将包连接到存储库。

但是,如果在 package.json 文件中提供了 repository 密钥,则该密钥中的存储库将用作 GitHub Packages 的目标 npm 注册表。 例如,发布以下 package.json 结果将导致名为 my-package 的包发布到 octocat/my-other-repo GitHub 存储库。

{
  "name": "@octocat/my-package",
  "repository": {
    "type": "git",
    "url": "https://github.com/octocat/my-other-repo.git"
  },

向目标仓库验证

要在工作流中对 GitHub Packages 注册表执行经过身份验证的操作,可以使用 GITHUB_TOKEN。 每当工作流中的作业开始时,GITHUB_TOKEN 机密都会设置为存储库的访问令牌。 应在工作流文件中设置此访问令牌的权限,以授予 contents 权限的读取访问权限,并授予 packages 权限的写入访问权限。 有关详细信息,请参阅“自动令牌身份验证”。

如果要将包发布到其他存储库,必须使用对目标存储库中的包具有写入权限的 personal access token (classic)。 有关详细信息,请参阅 管理个人访问令牌在 GitHub Actions 中使用机密

示例工作流

此示例将 GITHUB_TOKEN 机密存储在 NODE_AUTH_TOKEN 环境变量中。 当 setup-node 操作创建 .npmrc 文件时,会引用来自 NODE_AUTH_TOKEN 环境变量的令牌。

YAML
name: Publish package to GitHub Packages
on:
  release:
    types: [published]
jobs:
  build:
    runs-on: ubuntu-latest
    permissions:
      contents: read
      packages: write
    steps:
      - uses: actions/checkout@v4
      # Setup .npmrc file to publish to GitHub Packages
      - uses: actions/setup-node@v4
        with:
          node-version: '20.x'
          registry-url: 'https://npm.pkg.github.com'
          # Defaults to the user or organization that owns the workflow file
          scope: '@octocat'
      - run: npm ci
      - run: npm publish
        env:
          NODE_AUTH_TOKEN: ${{ secrets.GITHUB_TOKEN }}

setup-node 操作在运行器上创建一个 .npmrc 文件。 当对 setup-node 操作使用 scope 输入时,.npmrc 文件包含范围前缀。 默认情况下,setup-node 操作会将 .npmrc 文件中的范围设置为包含该工作流文件的帐户。

//npm.pkg.github.com/:_authToken=${NODE_AUTH_TOKEN}
@octocat:registry=https://npm.pkg.github.com
always-auth=true

使用 Yarn 发布包

如果您使用 Yarn 包管理器,可以使用 Yarn 安装和发布包。

YAML
name: Publish Package to npmjs
on:
  release:
    types: [published]
jobs:
  build:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v4
      # Setup .npmrc file to publish to npm
      - uses: actions/setup-node@v4
        with:
          node-version: '20.x'
          registry-url: 'https://registry.npmjs.org'
          # Defaults to the user or organization that owns the workflow file
          scope: '@octocat'
      - run: yarn
      - run: yarn npm publish // for Yarn version 1, use `yarn publish` instead
        env:
          NODE_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }}

要在发布期间进行注册表身份验证,请确保在 yarnrc.yml 文件中也定义了你的身份验证令牌。 有关详细信息,请参阅 Yarn 文档中的设置一文。