Release v3.25.2-rc3: Installer improvements and automated changelog enhancements (#133)

* feat: dramatically improve automated changelog generation

- Add detailed analysis logging and error handling
- Clean up commit messages by removing prefixes (feat:, fix:, etc.)
- Group changes by type with proper emoji categories
- Include version progression info (v3.25.2 → v3.25.3)
- Add installation instructions and Docker commands
- Filter out technical/automated commits from user-facing changelog
- Provide enhanced fallback using git log if analysis fails
- Include release statistics and change counts

This replaces the generic 'Automated stable release' message with
comprehensive, user-friendly changelogs.

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>

* chore: bump version to 3.25.2-rc3 for RC release

* fix: improve installer resilience against GitHub API rate limits

Add fallback mechanism in check_release_exists() to verify release existence
by attempting direct tarball download when GitHub API is rate limited.
This prevents installation failures when the API quota is exceeded.

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>

* chore: bump version to 3.25.2-rc4 for RC release

---------

Co-authored-by: rcourtman <dev@pulse.local>
Co-authored-by: Claude <noreply@anthropic.com>
Co-authored-by: GitHub Action <action@github.com>
This commit is contained in:
rcourtman
2025-06-13 17:45:06 +01:00
committed by GitHub
parent 63c51e5ff0
commit 02b56b7691
3 changed files with 82 additions and 14 deletions
+69 -12
View File
@@ -195,16 +195,32 @@ jobs:
node -e "
const { execSync } = require('child_process');
const { analyzeCommitsForVersionBump } = require('./server/versionUtils');
const fs = require('fs');
try {
console.log('🔍 Starting changelog generation...');
const analysis = analyzeCommitsForVersionBump();
console.log('📊 Analysis results:', {
currentStable: analysis.currentStableVersion,
suggested: analysis.suggestedVersion,
bumpType: analysis.bumpType,
totalCommits: analysis.totalCommits,
breaking: analysis.analysis.breaking.length,
features: analysis.analysis.features.length,
fixes: analysis.analysis.fixes.length,
other: analysis.analysis.other.length
});
// Generate meaningful changelog based on actual commits
let changelog = '## What\\'s Changed\\n\\n';
// Add version summary
changelog += '**' + analysis.bumpType.charAt(0).toUpperCase() + analysis.bumpType.slice(1) + ' release** with ' + analysis.totalCommits + ' commit' + (analysis.totalCommits !== 1 ? 's' : '') + ' since v' + analysis.currentStableVersion + '\\n\\n';
if (analysis.analysis.breaking.length > 0) {
changelog += '### 💥 Breaking Changes\\n';
analysis.analysis.breaking.forEach(commit => {
changelog += '- ' + commit + '\\n';
changelog += '- ' + commit.replace(/^(fix|feat|docs|style|refactor|test|chore)!?:\\s*/, '') + '\\n';
});
changelog += '\\n';
}
@@ -212,7 +228,7 @@ jobs:
if (analysis.analysis.features.length > 0) {
changelog += '### ✨ New Features\\n';
analysis.analysis.features.forEach(commit => {
changelog += '- ' + commit + '\\n';
changelog += '- ' + commit.replace(/^feat:\\s*/, '') + '\\n';
});
changelog += '\\n';
}
@@ -220,7 +236,7 @@ jobs:
if (analysis.analysis.fixes.length > 0) {
changelog += '### 🐛 Bug Fixes\\n';
analysis.analysis.fixes.forEach(commit => {
changelog += '- ' + commit + '\\n';
changelog += '- ' + commit.replace(/^fix:\\s*/, '') + '\\n';
});
changelog += '\\n';
}
@@ -228,33 +244,74 @@ jobs:
if (analysis.analysis.other.length > 0) {
changelog += '### 🔧 Other Changes\\n';
analysis.analysis.other.forEach(commit => {
changelog += '- ' + commit + '\\n';
let cleanCommit = commit.replace(/^(docs|style|refactor|test|chore):\\s*/, '');
// Skip very technical commits that aren't user-facing
if (!cleanCommit.includes('🤖 Generated with') && !cleanCommit.includes('resolve:') && cleanCommit.length > 10) {
changelog += '- ' + cleanCommit + '\\n';
}
});
changelog += '\\n';
}
changelog += '### 📊 Release Statistics\\n';
changelog += '- **Version bump**: ' + analysis.bumpType + '\\n';
changelog += '- **Total commits**: ' + analysis.totalCommits + '\\n';
changelog += '### 📊 Release Information\\n';
changelog += '- **Release type**: ' + analysis.bumpType + ' (v' + analysis.currentStableVersion + ' → v' + analysis.suggestedVersion + ')\\n';
changelog += '- **Total changes**: ' + analysis.totalCommits + ' commits\\n';
changelog += '- **Breaking changes**: ' + analysis.analysis.breaking.length + '\\n';
changelog += '- **New features**: ' + analysis.analysis.features.length + '\\n';
changelog += '- **Bug fixes**: ' + analysis.analysis.fixes.length + '\\n';
changelog += '\\n';
changelog += '### 🐳 Docker\\n';
changelog += '\\`\\`\\`bash\\n';
changelog += '# Latest stable release\\n';
changelog += 'docker pull rcourtman/pulse:v' + analysis.suggestedVersion + '\\n';
changelog += 'docker pull rcourtman/pulse:latest\\n';
changelog += '\\`\\`\\`\\n';
changelog += '\\n';
changelog += '🤖 *This release was automatically created from the develop branch*';
console.log(changelog);
changelog += '### 📥 Installation\\n';
changelog += '\\`\\`\\`bash\\n';
changelog += '# Automated installer (recommended)\\n';
changelog += 'curl -sL https://raw.githubusercontent.com/rcourtman/Pulse/main/scripts/install-pulse.sh | bash\\n';
changelog += '\\n';
changelog += '# Or download and extract tarball manually\\n';
changelog += 'wget https://github.com/rcourtman/Pulse/releases/download/v' + analysis.suggestedVersion + '/pulse-v' + analysis.suggestedVersion + '.tar.gz\\n';
changelog += '\\`\\`\\`\\n';
changelog += '\\n';
changelog += '🤖 *This release was automatically generated from the develop branch*';
console.log('✅ Generated changelog with', changelog.split('\\n').length, 'lines');
// Write to file for GitHub release
require('fs').writeFileSync('CHANGELOG.md', changelog);
fs.writeFileSync('CHANGELOG.md', changelog);
console.log('📝 Changelog written to CHANGELOG.md');
} catch (error) {
console.error('Error generating changelog:', error);
require('fs').writeFileSync('CHANGELOG.md', 'Automated stable release\\n\\nSee commit history for details.');
console.error('❌ Error generating changelog:', error);
console.error('Stack trace:', error.stack);
// Enhanced fallback with basic git log
let fallbackChangelog = '## Release v$NEW_VERSION\\n\\n';
try {
const gitLog = execSync('git log $(git describe --tags --abbrev=0)..HEAD --oneline --no-merges', { encoding: 'utf8' });
if (gitLog.trim()) {
fallbackChangelog += '### Changes since last release:\\n';
gitLog.trim().split('\\n').forEach(line => {
if (line.trim() && !line.includes('🤖 Generated with')) {
fallbackChangelog += '- ' + line.replace(/^[a-f0-9]+\\s+/, '') + '\\n';
}
});
} else {
fallbackChangelog += 'See commit history for details.\\n';
}
} catch (gitError) {
fallbackChangelog += 'See commit history for details.\\n';
}
fallbackChangelog += '\\n🤖 *Automated release - detailed changelog generation failed*';
fs.writeFileSync('CHANGELOG.md', fallbackChangelog);
console.log('📝 Fallback changelog written');
}
"