Publish to npm #9
Workflow file for this run
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| name: Publish to npm | |
| on: | |
| # 任意分支 push 时发布测试包(依赖 CI 测试通过) | |
| push: | |
| branches: | |
| - '**' | |
| # GitHub Release 触发正式发布 | |
| release: | |
| types: [published] | |
| # 手动触发 | |
| workflow_dispatch: | |
| inputs: | |
| publish_type: | |
| description: '发布类型 / Publish type' | |
| required: true | |
| default: 'test' | |
| type: choice | |
| options: | |
| - official # 正式发布 | |
| - test # 测试发布 | |
| version: | |
| description: '版本号(留空则自动递增)/ Version (leave empty for auto-increment)' | |
| required: false | |
| type: string | |
| version_bump: | |
| description: '版本递增类型(仅自动递增时有效)/ Version bump type (only for auto-increment)' | |
| required: false | |
| default: 'patch' | |
| type: choice | |
| options: | |
| - patch # 0.0.1 -> 0.0.2 | |
| - minor # 0.0.1 -> 0.1.0 | |
| - major # 0.0.1 -> 1.0.0 | |
| jobs: | |
| # 等待 CI 测试通过(仅 push 触发时) | |
| wait-for-ci: | |
| name: Wait for CI | |
| runs-on: ubuntu-latest | |
| if: github.event_name == 'push' | |
| steps: | |
| - name: Wait for CI workflow (Node 18.x) | |
| uses: lewagon/[email protected] | |
| with: | |
| ref: ${{ github.sha }} | |
| check-name: 'build (18.x)' | |
| repo-token: ${{ secrets.GITHUB_TOKEN }} | |
| wait-interval: 10 | |
| allowed-conclusions: success | |
| - name: Wait for CI workflow (Node 20.x) | |
| uses: lewagon/[email protected] | |
| with: | |
| ref: ${{ github.sha }} | |
| check-name: 'build (20.x)' | |
| repo-token: ${{ secrets.GITHUB_TOKEN }} | |
| wait-interval: 10 | |
| allowed-conclusions: success | |
| - name: Wait for CI workflow (Node 22.x) | |
| uses: lewagon/[email protected] | |
| with: | |
| ref: ${{ github.sha }} | |
| check-name: 'build (22.x)' | |
| repo-token: ${{ secrets.GITHUB_TOKEN }} | |
| wait-interval: 10 | |
| allowed-conclusions: success | |
| # 测试包发布(push 触发) | |
| publish-test: | |
| name: Publish Test Package | |
| runs-on: ubuntu-latest | |
| needs: wait-for-ci | |
| if: github.event_name == 'push' | |
| permissions: | |
| contents: read | |
| id-token: write | |
| steps: | |
| - name: Checkout | |
| uses: actions/checkout@v4 | |
| with: | |
| fetch-depth: 0 | |
| - name: Setup Node.js | |
| uses: actions/setup-node@v4 | |
| with: | |
| node-version: '20' | |
| registry-url: 'https://registry.npmjs.org' | |
| - name: Upgrade npm for Trusted Publishers | |
| run: | | |
| npm --version | |
| npm install -g npm@latest | |
| npm --version | |
| - name: Determine test version | |
| id: version | |
| run: | | |
| # 获取包名 | |
| PACKAGE_NAME=$(node -p "require('./package.json').name") | |
| echo "PACKAGE_NAME=${PACKAGE_NAME}" >> $GITHUB_OUTPUT | |
| # 获取基础版本号 | |
| BASE_VERSION=$(node -p "require('./package.json').version") | |
| # 生成唯一标识符:优先使用 run_id,否则使用时间戳 | |
| if [ -n "${{ github.run_id }}" ]; then | |
| UNIQUE_ID="${{ github.run_id }}" | |
| else | |
| UNIQUE_ID=$(date +%Y%m%d%H%M%S) | |
| fi | |
| # 生成 prerelease 版本号 | |
| VERSION="${BASE_VERSION}-test.${UNIQUE_ID}" | |
| echo "VERSION=${VERSION}" >> $GITHUB_OUTPUT | |
| echo "Test version: ${VERSION}" | |
| - name: Update package.json version | |
| run: | | |
| VERSION="${{ steps.version.outputs.VERSION }}" | |
| node -e " | |
| const fs = require('fs'); | |
| const pkg = JSON.parse(fs.readFileSync('package.json', 'utf8')); | |
| pkg.version = process.env.VERSION; | |
| fs.writeFileSync('package.json', JSON.stringify(pkg, null, 2) + '\n'); | |
| " | |
| echo "Updated package.json:" | |
| cat package.json | head -5 | |
| env: | |
| VERSION: ${{ steps.version.outputs.VERSION }} | |
| - name: Clean and install dependencies | |
| run: | | |
| rm -rf node_modules package-lock.json | |
| npm install | |
| - name: Build | |
| run: npm run build | |
| - name: Publish test package (Trusted Publishers - no token needed) | |
| run: | | |
| PACKAGE_NAME="${{ steps.version.outputs.PACKAGE_NAME }}" | |
| VERSION="${{ steps.version.outputs.VERSION }}" | |
| echo "Publishing ${PACKAGE_NAME}@${VERSION} with tag=test" | |
| # Remove any .npmrc that might interfere with OIDC | |
| rm -f ~/.npmrc | |
| rm -f .npmrc | |
| rm -f /home/runner/work/_temp/.npmrc | |
| # Publish using Trusted Publishers (OIDC) | |
| npm publish --tag test --access public --provenance | |
| env: | |
| # Clear the environment variables that might interfere with OIDC | |
| NPM_CONFIG_USERCONFIG: '' | |
| NODE_AUTH_TOKEN: '' | |
| - name: Summary | |
| run: | | |
| PACKAGE_NAME="${{ steps.version.outputs.PACKAGE_NAME }}" | |
| VERSION="${{ steps.version.outputs.VERSION }}" | |
| echo "## 🧪 Test Package Published!" >> $GITHUB_STEP_SUMMARY | |
| echo "" >> $GITHUB_STEP_SUMMARY | |
| echo "- **Package:** ${PACKAGE_NAME}@${VERSION}" >> $GITHUB_STEP_SUMMARY | |
| echo "- **Branch:** ${{ github.ref_name }}" >> $GITHUB_STEP_SUMMARY | |
| echo "- **Commit:** ${{ github.sha }}" >> $GITHUB_STEP_SUMMARY | |
| echo "" >> $GITHUB_STEP_SUMMARY | |
| echo "Install with:" >> $GITHUB_STEP_SUMMARY | |
| echo "\`\`\`bash" >> $GITHUB_STEP_SUMMARY | |
| echo "npm install ${PACKAGE_NAME}@${VERSION}" >> $GITHUB_STEP_SUMMARY | |
| echo "# or install latest test version" >> $GITHUB_STEP_SUMMARY | |
| echo "npm install ${PACKAGE_NAME}@test" >> $GITHUB_STEP_SUMMARY | |
| echo "\`\`\`" >> $GITHUB_STEP_SUMMARY | |
| # 正式发布(release 或手动触发) | |
| publish-official: | |
| name: Publish Official Package | |
| runs-on: ubuntu-latest | |
| if: github.event_name == 'release' || (github.event_name == 'workflow_dispatch' && inputs.publish_type == 'official') | |
| permissions: | |
| contents: write | |
| id-token: write | |
| steps: | |
| - name: Checkout | |
| uses: actions/checkout@v4 | |
| with: | |
| ssh-key: ${{ secrets.DEPLOY_KEY }} | |
| ref: main | |
| fetch-depth: 0 | |
| - name: Setup Node.js | |
| uses: actions/setup-node@v4 | |
| with: | |
| node-version: '20' | |
| registry-url: 'https://registry.npmjs.org' | |
| - name: Upgrade npm for Trusted Publishers | |
| run: | | |
| npm --version | |
| npm install -g npm@latest | |
| npm --version | |
| - name: Determine version | |
| id: config | |
| run: | | |
| PACKAGE_NAME=$(node -p "require('./package.json').name") | |
| echo "PACKAGE_NAME=${PACKAGE_NAME}" >> $GITHUB_OUTPUT | |
| # 确定版本号 | |
| if [ "${{ github.event_name }}" = "release" ]; then | |
| VERSION="${{ github.event.release.tag_name }}" | |
| VERSION="${VERSION#v}" # 移除 v 前缀 | |
| echo "Triggered by release: $VERSION" | |
| else | |
| VERSION="${{ inputs.version }}" | |
| if [ -z "$VERSION" ]; then | |
| # 自动递增版本号 | |
| NPM_RESPONSE=$(npm view "$PACKAGE_NAME" version 2>/dev/null || echo "") | |
| if [ -z "$NPM_RESPONSE" ]; then | |
| CURRENT_VERSION="0.0.0" | |
| else | |
| CURRENT_VERSION="$NPM_RESPONSE" | |
| fi | |
| IFS='.' read -r MAJOR MINOR PATCH <<< "$CURRENT_VERSION" | |
| BUMP_TYPE="${{ inputs.version_bump }}" | |
| if [ -z "$BUMP_TYPE" ]; then | |
| BUMP_TYPE="patch" | |
| fi | |
| case "$BUMP_TYPE" in | |
| major) | |
| MAJOR=$((MAJOR + 1)) | |
| MINOR=0 | |
| PATCH=0 | |
| ;; | |
| minor) | |
| MINOR=$((MINOR + 1)) | |
| PATCH=0 | |
| ;; | |
| patch) | |
| PATCH=$((PATCH + 1)) | |
| ;; | |
| esac | |
| VERSION="${MAJOR}.${MINOR}.${PATCH}" | |
| fi | |
| fi | |
| echo "VERSION=${VERSION}" >> $GITHUB_OUTPUT | |
| echo "Official version: ${VERSION}" | |
| - name: Update package.json | |
| run: | | |
| VERSION="${{ steps.config.outputs.VERSION }}" | |
| node -e " | |
| const fs = require('fs'); | |
| const pkg = JSON.parse(fs.readFileSync('package.json', 'utf8')); | |
| pkg.version = process.env.VERSION; | |
| fs.writeFileSync('package.json', JSON.stringify(pkg, null, 2) + '\n'); | |
| " | |
| echo "Updated package.json:" | |
| cat package.json | head -5 | |
| env: | |
| VERSION: ${{ steps.config.outputs.VERSION }} | |
| - name: Commit version changes | |
| run: | | |
| git config --local user.email "[email protected]" | |
| git config --local user.name "GitHub Action" | |
| git add package.json | |
| if git diff --staged --quiet; then | |
| echo "No version changes to commit" | |
| else | |
| git commit -m "chore: bump version to ${{ steps.config.outputs.VERSION }}" | |
| git push | |
| fi | |
| - name: Clean and install dependencies | |
| run: | | |
| rm -rf node_modules package-lock.json | |
| npm install | |
| - name: Build | |
| run: npm run build | |
| - name: Publish to npm (Trusted Publishers - no token needed) | |
| run: | | |
| PACKAGE_NAME="${{ steps.config.outputs.PACKAGE_NAME }}" | |
| VERSION="${{ steps.config.outputs.VERSION }}" | |
| echo "Publishing ${PACKAGE_NAME}@${VERSION} with tag=latest" | |
| # Remove any .npmrc that might interfere with OIDC | |
| rm -f ~/.npmrc | |
| rm -f .npmrc | |
| rm -f /home/runner/work/_temp/.npmrc | |
| # Publish using Trusted Publishers (OIDC) | |
| npm publish --tag latest --access public --provenance | |
| env: | |
| # Clear the environment variables that might interfere with OIDC | |
| NPM_CONFIG_USERCONFIG: '' | |
| NODE_AUTH_TOKEN: '' | |
| - name: Summary | |
| run: | | |
| PACKAGE_NAME="${{ steps.config.outputs.PACKAGE_NAME }}" | |
| VERSION="${{ steps.config.outputs.VERSION }}" | |
| echo "## 🚀 Official Package Released!" >> $GITHUB_STEP_SUMMARY | |
| echo "" >> $GITHUB_STEP_SUMMARY | |
| echo "- **Package Name:** ${PACKAGE_NAME}" >> $GITHUB_STEP_SUMMARY | |
| echo "- **Version:** ${VERSION}" >> $GITHUB_STEP_SUMMARY | |
| echo "- **NPM Tag:** latest" >> $GITHUB_STEP_SUMMARY | |
| echo "- **Commit:** ${{ github.sha }}" >> $GITHUB_STEP_SUMMARY | |
| echo "" >> $GITHUB_STEP_SUMMARY | |
| echo "Install with:" >> $GITHUB_STEP_SUMMARY | |
| echo "\`\`\`bash" >> $GITHUB_STEP_SUMMARY | |
| echo "npm install ${PACKAGE_NAME}@${VERSION}" >> $GITHUB_STEP_SUMMARY | |
| echo "\`\`\`" >> $GITHUB_STEP_SUMMARY | |
| # 手动触发测试发布 | |
| publish-test-manual: | |
| name: Publish Test Package (Manual) | |
| runs-on: ubuntu-latest | |
| if: github.event_name == 'workflow_dispatch' && inputs.publish_type == 'test' | |
| permissions: | |
| contents: read | |
| id-token: write | |
| steps: | |
| - name: Checkout | |
| uses: actions/checkout@v4 | |
| with: | |
| fetch-depth: 0 | |
| - name: Setup Node.js | |
| uses: actions/setup-node@v4 | |
| with: | |
| node-version: '20' | |
| registry-url: 'https://registry.npmjs.org' | |
| - name: Upgrade npm for Trusted Publishers | |
| run: | | |
| npm --version | |
| npm install -g npm@latest | |
| npm --version | |
| - name: Determine version | |
| id: version | |
| run: | | |
| PACKAGE_NAME=$(node -p "require('./package.json').name") | |
| echo "PACKAGE_NAME=${PACKAGE_NAME}" >> $GITHUB_OUTPUT | |
| VERSION="${{ inputs.version }}" | |
| if [ -z "$VERSION" ]; then | |
| # 自动生成测试版本号 | |
| BASE_VERSION=$(node -p "require('./package.json').version") | |
| # 生成唯一标识符:优先使用 run_id,否则使用时间戳 | |
| if [ -n "${{ github.run_id }}" ]; then | |
| UNIQUE_ID="${{ github.run_id }}" | |
| else | |
| UNIQUE_ID=$(date +%Y%m%d%H%M%S) | |
| fi | |
| VERSION="${BASE_VERSION}-test.${UNIQUE_ID}" | |
| fi | |
| echo "VERSION=${VERSION}" >> $GITHUB_OUTPUT | |
| echo "Test version: ${VERSION}" | |
| - name: Update package.json version | |
| run: | | |
| VERSION="${{ steps.version.outputs.VERSION }}" | |
| node -e " | |
| const fs = require('fs'); | |
| const pkg = JSON.parse(fs.readFileSync('package.json', 'utf8')); | |
| pkg.version = process.env.VERSION; | |
| fs.writeFileSync('package.json', JSON.stringify(pkg, null, 2) + '\n'); | |
| " | |
| env: | |
| VERSION: ${{ steps.version.outputs.VERSION }} | |
| - name: Clean and install dependencies | |
| run: | | |
| rm -rf node_modules package-lock.json | |
| npm install | |
| - name: Build | |
| run: npm run build | |
| - name: Publish test package (Trusted Publishers - no token needed) | |
| run: | | |
| PACKAGE_NAME="${{ steps.version.outputs.PACKAGE_NAME }}" | |
| VERSION="${{ steps.version.outputs.VERSION }}" | |
| echo "Publishing ${PACKAGE_NAME}@${VERSION} with tag=test" | |
| # Remove any .npmrc that might interfere with OIDC | |
| rm -f ~/.npmrc | |
| rm -f .npmrc | |
| rm -f /home/runner/work/_temp/.npmrc | |
| # Publish using Trusted Publishers (OIDC) | |
| npm publish --tag test --access public --provenance | |
| env: | |
| # Clear the environment variables that might interfere with OIDC | |
| NPM_CONFIG_USERCONFIG: '' | |
| NODE_AUTH_TOKEN: '' | |
| - name: Summary | |
| run: | | |
| PACKAGE_NAME="${{ steps.version.outputs.PACKAGE_NAME }}" | |
| VERSION="${{ steps.version.outputs.VERSION }}" | |
| echo "## 🧪 Test Package Published (Manual)!" >> $GITHUB_STEP_SUMMARY | |
| echo "" >> $GITHUB_STEP_SUMMARY | |
| echo "- **Package:** ${PACKAGE_NAME}@${VERSION}" >> $GITHUB_STEP_SUMMARY | |
| echo "- **Commit:** ${{ github.sha }}" >> $GITHUB_STEP_SUMMARY | |
| echo "" >> $GITHUB_STEP_SUMMARY | |
| echo "Install with:" >> $GITHUB_STEP_SUMMARY | |
| echo "\`\`\`bash" >> $GITHUB_STEP_SUMMARY | |
| echo "npm install ${PACKAGE_NAME}@${VERSION}" >> $GITHUB_STEP_SUMMARY | |
| echo "\`\`\`" >> $GITHUB_STEP_SUMMARY |