Skip to content

fix(uat): align CLI config versions to v2.3.0 #2

fix(uat): align CLI config versions to v2.3.0

fix(uat): align CLI config versions to v2.3.0 #2

Workflow file for this run

name: Create Release
on:
push:
tags:
- 'v*'
permissions:
contents: write
id-token: write # Required for Sigstore signing
jobs:
# Run quality gate checks before allowing release
quality-gate:
name: Quality Gate
uses: ./.github/workflows/quality-gate.yml
release:
name: Create Release
runs-on: ubuntu-latest
# Only run release if quality gate passes
needs: [quality-gate]
steps:
- name: Checkout code
uses: actions/checkout@34e114876b0b11c390a56381ad16ebd13914f8d5 # v4.3.1
with:
fetch-depth: 0 # Full history for changelog
- name: Setup Node.js
uses: actions/setup-node@49933ea5288caeca8642d1e84afbd3f7d6820020 # v4.4.0
with:
node-version: '20'
- name: Get version from tag
id: version
run: echo "VERSION=${GITHUB_REF#refs/tags/}" >> $GITHUB_OUTPUT
- name: Set reproducible build timestamp
id: build_time
run: |
# Use SOURCE_DATE_EPOCH for reproducible builds (VAL-09-005)
export SOURCE_DATE_EPOCH=$(date +%s)
echo "SOURCE_DATE_EPOCH=${SOURCE_DATE_EPOCH}" >> $GITHUB_ENV
echo "build_date=$(date -u -d @${SOURCE_DATE_EPOCH} +%Y-%m-%dT%H:%M:%SZ 2>/dev/null || date -u -r ${SOURCE_DATE_EPOCH} +%Y-%m-%dT%H:%M:%SZ)" >> $GITHUB_OUTPUT
- name: Create version.json
run: |
mkdir -p _bmad
echo "{\"version\": \"${{ steps.version.outputs.VERSION }}\", \"buildDate\": \"${{ steps.build_time.outputs.build_date }}\", \"reproducible\": true}" > _bmad/version.json
- name: Create tarball
run: |
VERSION=${{ steps.version.outputs.VERSION }}
# Create a staging directory
STAGING_DIR="bmad-cyber-${VERSION}"
mkdir -p "${STAGING_DIR}"
# Copy included files/directories
# Core framework
if [ -d "_bmad" ]; then
cp -r _bmad "${STAGING_DIR}/"
fi
# Claude configuration
if [ -d ".claude" ]; then
cp -r .claude "${STAGING_DIR}/"
fi
# Utility tools
if [ -d "src/utility/tools" ]; then
mkdir -p "${STAGING_DIR}/src/utility"
cp -r src/utility/tools "${STAGING_DIR}/src/utility/"
fi
# Root files
[ -f "CLAUDE.md" ] && cp CLAUDE.md "${STAGING_DIR}/"
[ -f "package.json" ] && cp package.json "${STAGING_DIR}/"
[ -f "tsconfig.json" ] && cp tsconfig.json "${STAGING_DIR}/"
[ -f "README.md" ] && cp README.md "${STAGING_DIR}/"
# Remove excluded patterns from staging
find "${STAGING_DIR}" -name "node_modules" -type d -exec rm -rf {} + 2>/dev/null || true
find "${STAGING_DIR}" -name ".git" -type d -exec rm -rf {} + 2>/dev/null || true
find "${STAGING_DIR}" -name ".github" -type d -exec rm -rf {} + 2>/dev/null || true
find "${STAGING_DIR}" -name "*.test.js" -delete 2>/dev/null || true
find "${STAGING_DIR}" -name "*.test.ts" -delete 2>/dev/null || true
find "${STAGING_DIR}" -name "*.spec.js" -delete 2>/dev/null || true
find "${STAGING_DIR}" -name "*.spec.ts" -delete 2>/dev/null || true
find "${STAGING_DIR}" -name "coverage" -type d -exec rm -rf {} + 2>/dev/null || true
find "${STAGING_DIR}" -name ".nyc_output" -type d -exec rm -rf {} + 2>/dev/null || true
find "${STAGING_DIR}" -name "__tests__" -type d -exec rm -rf {} + 2>/dev/null || true
find "${STAGING_DIR}" -name ".env" -delete 2>/dev/null || true
find "${STAGING_DIR}" -name ".env.local" -delete 2>/dev/null || true
# Create tarball from staging directory
tar -czvf "bmad-cyber-${VERSION}.tar.gz" "${STAGING_DIR}"
# Cleanup staging
rm -rf "${STAGING_DIR}"
echo "Created bmad-cyber-${VERSION}.tar.gz"
ls -la bmad-cyber-${VERSION}.tar.gz
- name: Generate checksum
run: |
VERSION=${{ steps.version.outputs.VERSION }}
sha256sum "bmad-cyber-${VERSION}.tar.gz" > "bmad-cyber-${VERSION}.tar.gz.sha256"
cat "bmad-cyber-${VERSION}.tar.gz.sha256"
- name: Generate SBOM (VAL-09-008-002)
run: |
VERSION=${{ steps.version.outputs.VERSION }}
# Install cyclonedx for SBOM generation
npm install -g @cyclonedx/cyclonedx-npm 2>/dev/null || true
# Generate SBOM if package.json exists
if [ -f "package.json" ]; then
npx @cyclonedx/cyclonedx-npm --output-format JSON --output-file "bmad-cyber-${VERSION}.sbom.json" 2>/dev/null || \
echo '{"bomFormat":"CycloneDX","specVersion":"1.4","version":1,"metadata":{"component":{"name":"bmad-cyber","version":"'"${VERSION}"'"}},"components":[]}' > "bmad-cyber-${VERSION}.sbom.json"
else
echo '{"bomFormat":"CycloneDX","specVersion":"1.4","version":1,"metadata":{"component":{"name":"bmad-cyber","version":"'"${VERSION}"'"}},"components":[]}' > "bmad-cyber-${VERSION}.sbom.json"
fi
echo "SBOM generated: bmad-cyber-${VERSION}.sbom.json"
- name: Sign artifacts with Sigstore (VAL-09-008-001)
uses: sigstore/gh-action-sigstore-python@a5caf349bc536fbef3668a10ed7f5cd309a4b53d # v3.2.0
with:
inputs: |
bmad-cyber-${{ steps.version.outputs.VERSION }}.tar.gz
bmad-cyber-${{ steps.version.outputs.VERSION }}.tar.gz.sha256
bmad-cyber-${{ steps.version.outputs.VERSION }}.sbom.json
- name: Generate changelog
id: changelog
run: |
# Get previous tag
PREV_TAG=$(git describe --tags --abbrev=0 HEAD^ 2>/dev/null || echo "")
if [ -n "$PREV_TAG" ]; then
echo "Generating changelog from $PREV_TAG to ${{ steps.version.outputs.VERSION }}"
CHANGELOG=$(git log --pretty=format:"- %s (%h)" "$PREV_TAG"..HEAD)
else
echo "First release, using recent commits"
CHANGELOG=$(git log --pretty=format:"- %s (%h)" -10)
fi
# Save to file for multiline output
echo "$CHANGELOG" > CHANGELOG.txt
echo "changelog_file=CHANGELOG.txt" >> $GITHUB_OUTPUT
- name: Determine pre-release status
id: prerelease
run: |
VERSION=${{ steps.version.outputs.VERSION }}
if [[ "$VERSION" == *"-alpha"* ]] || [[ "$VERSION" == *"-beta"* ]] || [[ "$VERSION" == *"-rc"* ]]; then
echo "is_prerelease=true" >> $GITHUB_OUTPUT
else
echo "is_prerelease=false" >> $GITHUB_OUTPUT
fi
- name: Create Release
uses: softprops/action-gh-release@a06a81a03ee405af7f2048a818ed3f03bbf83c7b # v2.5.0
with:
files: |
bmad-cyber-${{ steps.version.outputs.VERSION }}.tar.gz
bmad-cyber-${{ steps.version.outputs.VERSION }}.tar.gz.sha256
bmad-cyber-${{ steps.version.outputs.VERSION }}.sbom.json
bmad-cyber-${{ steps.version.outputs.VERSION }}.tar.gz.sigstore.json
bmad-cyber-${{ steps.version.outputs.VERSION }}.tar.gz.sha256.sigstore.json
bmad-cyber-${{ steps.version.outputs.VERSION }}.sbom.json.sigstore.json
body_path: CHANGELOG.txt
prerelease: ${{ steps.prerelease.outputs.is_prerelease }}
generate_release_notes: true
fail_on_unmatched_files: false
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
- name: Notify on success (optional)
if: success() && vars.DISCORD_WEBHOOK_URL != ''
run: |
curl -X POST "${{ vars.DISCORD_WEBHOOK_URL }}" \
-H "Content-Type: application/json" \
-d "{\"content\": \"New BMAD-CYBER release: ${{ steps.version.outputs.VERSION }}\"}"