diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml index d8cb5a5..61e9735 100644 --- a/.github/workflows/release.yml +++ b/.github/workflows/release.yml @@ -1,48 +1,93 @@ +# ============================================================================ +# KEEGEES AUTOMATED RELEASE WORKFLOW +# ============================================================================ +# This workflow provides comprehensive automated versioning and release +# management for the keegees GNOME keybinding management CLI tool. +# +# FEATURES: +# - Automated semantic version increments (patch-level) +# - Multi-file version synchronization (README.md, keegees.sh) +# - Comprehensive quality assurance via ShellCheck validation +# - Professional release asset generation (tar.gz, zip archives) +# - Dynamic release notes with installation instructions +# - GitHub release creation with automated asset attachment +# +# TRIGGER CONDITIONS: +# - Automatic: Push to master branch (production releases) +# - Manual: workflow_dispatch for ad-hoc releases and testing +# +# PERMISSIONS REQUIRED: +# - contents:write - Repository file modifications and tag creation +# - packages:write - Release asset publishing and management +# ============================================================================ + name: 🏷️ Auto Tag and Release -# Triggers on push to master branch (fully automated) on: push: branches: [ master ] - workflow_dispatch: # Manual trigger option + workflow_dispatch: -# Required permissions for tagging and releasing permissions: contents: write packages: write jobs: - # Job 1: Validate and Calculate Version + # ========================================================================== + # JOB 1: VALIDATION AND VERSION CALCULATION + # ========================================================================== + # Performs comprehensive quality assurance and determines the next semantic + # version number for the keegees release. This job validates shell scripts + # using ShellCheck and calculates version increments based on existing git + # tags, ensuring consistent and reliable version management. + # + # OUTPUTS: + # - version: Semantic version number (e.g., "0.0.2") + # - tag: Git tag format (e.g., "v0.0.2") + # + # DEPENDENCIES: None (entry point job) + # ========================================================================== validate-and-version: runs-on: ubuntu-latest outputs: version: ${{ steps.get_next_version.outputs.version }} tag: ${{ steps.get_next_version.outputs.tag }} steps: + # ---------------------------------------------------------------------- + # STEP: Repository Checkout with Full History + # Retrieves complete git history for accurate version calculation and + # tag analysis. Full history is required for git describe operations. + # ---------------------------------------------------------------------- - name: 🔄 Checkout Repository uses: actions/checkout@v4 with: fetch-depth: 0 token: ${{ secrets.GITHUB_TOKEN }} + # ---------------------------------------------------------------------- + # STEP: Shell Script Quality Assurance + # Validates keegees.sh and install.sh using ShellCheck to ensure + # adherence to best practices and prevent shell scripting errors. + # ---------------------------------------------------------------------- - name: 🔍 Run ShellCheck run: | shellcheck keegees.sh shellcheck install.sh + # ---------------------------------------------------------------------- + # STEP: Semantic Version Calculation + # Analyzes existing git tags to determine the next patch version. + # Implements automated semantic versioning with consistent increment logic. + # ---------------------------------------------------------------------- - name: 📊 Calculate Next Version id: get_next_version run: | - # Get latest tag or default to 0.0.0 LATEST_TAG=$(git describe --tags --abbrev=0 2>/dev/null || echo "v0.0.0") - # Extract version number (remove v prefix) CURRENT_VERSION=${LATEST_TAG#v} - # Split version into components IFS='.' read -r MAJOR MINOR PATCH <<< "$CURRENT_VERSION" - # Increment patch version (as per requirement 1.1) NEXT_PATCH=$((PATCH + 1)) NEXT_VERSION="${MAJOR}.${MINOR}.${NEXT_PATCH}" @@ -50,50 +95,76 @@ jobs: echo "tag=v$NEXT_VERSION" >> $GITHUB_OUTPUT echo "📊 Next version will be: v$NEXT_VERSION" - # Job 2: Update Version References and Create Tag + # ========================================================================== + # JOB 2: VERSION SYNCHRONIZATION AND GIT TAGGING + # ========================================================================== + # Synchronizes version references across multiple project files and creates + # annotated git tags for release tracking. Updates README.md version badges, + # CLI display versions, and keegees.sh VERSION constants to maintain + # consistency throughout the codebase. + # + # FILE UPDATES: + # - README.md: Version badges and warning text + # - keegees.sh: Internal VERSION constant + # + # GIT OPERATIONS: + # - Atomic commits with [skip ci] to prevent recursion + # - Annotated tag creation with automated messages + # - Remote repository synchronization + # + # DEPENDENCIES: validate-and-version (requires version outputs) + # ========================================================================== version-sync-and-tag: runs-on: ubuntu-latest needs: validate-and-version steps: + # ---------------------------------------------------------------------- + # STEP: Repository Checkout for File Modifications + # Retrieves repository contents for version synchronization operations. + # Full history enables proper git operations for tagging and pushing. + # ---------------------------------------------------------------------- - name: 🔄 Checkout Repository uses: actions/checkout@v4 with: fetch-depth: 0 - token: ${{ secrets.ADMIN_TOKEN || secrets.GITHUB_TOKEN }} + token: ${{ secrets.GITHUB_TOKEN }} + # ---------------------------------------------------------------------- + # STEP: Multi-File Version Synchronization + # Updates version references across README.md and keegees.sh to maintain + # consistency. Uses sed for reliable pattern matching and replacement. + # ---------------------------------------------------------------------- - name: 🔄 Synchronize Version Across Files run: | NEW_VERSION="${{ needs.validate-and-version.outputs.version }}" echo "🔄 Updating version to $NEW_VERSION across all files..." - # Update README.md version badge sed -i "s/Version-[0-9.]*/Version-$NEW_VERSION/g" README.md - # Update README.md version warning text sed -i "s/version [0-9.]*/version $NEW_VERSION/g" README.md - # Update CLI example in README.md (the "Version 1.0.0" display) sed -i "s/Version [0-9.]\+/Version $NEW_VERSION/g" README.md - # Update keegees.sh VERSION constant sed -i "s/readonly VERSION=\"[0-9.]*\"/readonly VERSION=\"$NEW_VERSION\"/g" keegees.sh - # Verify changes echo "📊 Version references updated:" echo " README.md badge: $(grep -o 'Version-[0-9.]*' README.md)" echo " README.md warning: $(grep -o 'version [0-9.]*' README.md)" echo " keegees.sh VERSION: $(grep -o 'readonly VERSION=\"[0-9.]*\"' keegees.sh)" + # ---------------------------------------------------------------------- + # STEP: Atomic Version Update Commit + # Creates atomic commit with version changes and [skip ci] tag to + # prevent recursive workflow triggers. Ensures clean git history. + # ---------------------------------------------------------------------- - name: 💾 Commit Version Updates run: | NEW_VERSION="${{ needs.validate-and-version.outputs.version }}" git config user.name "github-actions[bot]" git config user.email "41898282+github-actions[bot]@users.noreply.github.com" - # Add updated files git add README.md keegees.sh - # Check if there are changes to commit if git diff --cached --quiet; then echo "No version updates needed" else @@ -106,31 +177,62 @@ jobs: [skip ci]" fi + # ---------------------------------------------------------------------- + # STEP: Git Tag Creation and Remote Push + # Creates annotated git tag and pushes commits and tags to remote. + # Implements proper sequencing to avoid race conditions. + # ---------------------------------------------------------------------- - name: 🏷️ Create and Push Tag run: | TAG="${{ needs.validate-and-version.outputs.tag }}" git tag -a "$TAG" -m "🤖 Automated version tag: $TAG" - # Push commits first, then tag (commits have [skip ci] to prevent recursion) git push git push origin "$TAG" - # Job 3: Create Release Assets + # ========================================================================== + # JOB 3: RELEASE ASSET CREATION + # ========================================================================== + # Generates professional release archives and comprehensive release notes + # for distribution. Creates both tar.gz and zip formats with proper + # directory structures, excluding development files and maintaining + # professional packaging standards. + # + # ARCHIVE FORMATS: + # - tar.gz: Unix/Linux preferred format with directory transformation + # - zip: Windows/cross-platform compatibility format + # + # RELEASE NOTES: + # - Dynamic version warnings based on stability (pre-1.0 vs stable) + # - Installation instructions with correct download URLs + # - Filtered commit history excluding automated version updates + # - Professional formatting with requirements and feature descriptions + # + # DEPENDENCIES: validate-and-version, version-sync-and-tag + # ========================================================================== create-release-assets: runs-on: ubuntu-latest needs: [validate-and-version, version-sync-and-tag] steps: + # ---------------------------------------------------------------------- + # STEP: Repository Checkout for Asset Generation + # Retrieves repository contents for creating distribution archives. + # Full git history supports release notes generation. + # ---------------------------------------------------------------------- - name: 🔄 Checkout Repository uses: actions/checkout@v4 with: fetch-depth: 0 - token: ${{ secrets.ADMIN_TOKEN || secrets.GITHUB_TOKEN }} + token: ${{ secrets.GITHUB_TOKEN }} + # ---------------------------------------------------------------------- + # STEP: Professional Release Archive Creation + # Generates tar.gz and zip archives with proper directory structure. + # Excludes development files while maintaining distribution integrity. + # ---------------------------------------------------------------------- - name: 📦 Create Release Archives run: | - # Create release directory mkdir -p release - # Create tarball tar -czf "release/keegees-${{ needs.validate-and-version.outputs.version }}.tar.gz" \ --exclude='.git' \ --exclude='.github' \ @@ -138,14 +240,17 @@ jobs: --transform "s|^|keegees-${{ needs.validate-and-version.outputs.version }}/|" \ . - # Create zip archive zip -r "release/keegees-${{ needs.validate-and-version.outputs.version }}.zip" \ . \ -x '.git/*' '.github/*' 'release/*' + # ---------------------------------------------------------------------- + # STEP: Dynamic Release Notes Generation + # Creates comprehensive release documentation with installation + # instructions, change logs, and version-appropriate warnings. + # ---------------------------------------------------------------------- - name: 📝 Generate Release Notes run: | - # Get commits since last tag (exclude current version being created) LAST_TAG=$(git describe --tags --abbrev=0 --exclude="${{ needs.validate-and-version.outputs.tag }}" 2>/dev/null || echo "") if [ -n "$LAST_TAG" ]; then @@ -154,7 +259,6 @@ jobs: COMMITS=$(git log --oneline --no-merges | grep -v "🔄 Sync version" || true) fi - # Set dynamic version warning based on version NEW_VERSION="${{ needs.validate-and-version.outputs.version }}" MAJOR=$(echo "$NEW_VERSION" | cut -d. -f1) if [ "$MAJOR" = "0" ]; then @@ -163,7 +267,6 @@ jobs: EARLY_WARNING="**✅ Stable Release**: Ready for production use." fi - # Create release notes cat << EOF > release_notes.md ## 🚀 keegees ${{ needs.validate-and-version.outputs.tag }} @@ -176,7 +279,6 @@ jobs: ### ⚡ Quick Install \`\`\`bash - # Download and extract wget https://github.com/nutthead/keegees/releases/download/${{ needs.validate-and-version.outputs.tag }}/keegees-${{ needs.validate-and-version.outputs.version }}.tar.gz tar -xzf keegees-${{ needs.validate-and-version.outputs.version }}.tar.gz cd keegees-${{ needs.validate-and-version.outputs.version }} @@ -195,6 +297,11 @@ jobs: ${EARLY_WARNING} EOF + # ---------------------------------------------------------------------- + # STEP: Artifact Upload for Inter-Job Transfer + # Uploads generated assets and documentation for consumption by + # the GitHub release creation job using Actions artifact system. + # ---------------------------------------------------------------------- - name: 📤 Upload Release Assets uses: actions/upload-artifact@v4 with: @@ -203,16 +310,43 @@ jobs: release/ release_notes.md - # Job 4: Create GitHub Release + # ========================================================================== + # JOB 4: GITHUB RELEASE PUBLICATION + # ========================================================================== + # Publishes the final GitHub release with all generated assets and + # documentation. Downloads artifacts from previous jobs and creates a + # comprehensive release entry with professional presentation and + # accessibility. + # + # RELEASE FEATURES: + # - Automatic latest release designation + # - Professional release naming and descriptions + # - Multi-format asset attachment (tar.gz, zip) + # - Generated and custom release notes integration + # - Public accessibility for end-users + # + # DEPENDENCIES: All previous jobs (validate-and-version, + # version-sync-and-tag, create-release-assets) + # ========================================================================== create-github-release: runs-on: ubuntu-latest needs: [validate-and-version, version-sync-and-tag, create-release-assets] steps: + # ---------------------------------------------------------------------- + # STEP: Release Asset Retrieval + # Downloads artifacts generated by previous jobs including archives + # and release notes for GitHub release publication. + # ---------------------------------------------------------------------- - name: 📥 Download Release Assets uses: actions/download-artifact@v4 with: name: release-assets + # ---------------------------------------------------------------------- + # STEP: GitHub Release Publication + # Creates public GitHub release with professional presentation, + # asset attachments, and comprehensive documentation. + # ---------------------------------------------------------------------- - name: 🎉 Create GitHub Release uses: softprops/action-gh-release@v2 with: @@ -228,6 +362,11 @@ jobs: release/keegees-${{ needs.validate-and-version.outputs.version }}.zip token: ${{ secrets.GITHUB_TOKEN }} + # ---------------------------------------------------------------------- + # STEP: Release Completion Summary + # Outputs final release information including URLs and asset details + # for verification and user communication. + # ---------------------------------------------------------------------- - name: ✅ Release Summary run: | echo "🎉 Successfully created release: ${{ needs.validate-and-version.outputs.tag }}"