Guide to setting up and maintaining changelog for the Open Source Site Tracking platform.
The changelog is a critical component of the Open Source Site Tracking platform, providing users with clear information about changes, improvements, and fixes in each release. This guide covers the format, maintenance, and automation of the changelog.
# Changelog Format
## [Version] - [Date]
### ✨ New Features
- Feature description with details
- Another feature with implementation notes
### 🐛 Bug Fixes
- Bug description and fix details
- Another bug with resolution information
### 🔒 Security Improvements
- Security enhancement description
- Another security improvement
### ⚠️ Breaking Changes
- Breaking change description with migration guide
- Another breaking change with impact assessment
### 📚 Documentation
- Documentation improvement
- New guide or tutorial added
### 🛠️ Internal Changes
- Internal improvement or refactoring
- Development tool update
We follow Semantic Versioning (SemVer) with the format:
MAJOR.MINOR.PATCH
Examples:
1.0.0 - Major release with breaking changes
1.1.0 - Minor release with new features
1.1.1 - Patch release with bug fixes
# Changelog automation script
import subprocess
from datetime import datetime
from typing import List, Dict
class ChangelogGenerator:
def __init__(self):
self.git = GitInterface()
self.github = GitHubInterface()
self.template_engine = TemplateEngine()
def generate_changelog(self, version: str, since_tag: str = None):
"""Generate changelog for version"""
# Get commits since last tag
commits = self.get_commits_since_tag(since_tag)
# Categorize changes
categorized_changes = self.categorize_commits(commits)
# Generate changelog content
changelog = self.generate_changelog_content(version, categorized_changes)
return changelog
def categorize_commits(self, commits: List[Dict]) -> Dict[str, List]:
"""Categorize commits by type"""
categories = {
'features': [],
'bug_fixes': [],
'security': [],
'breaking': [],
'documentation': [],
'internal': []
}
for commit in commits:
category = self.determine_category(commit)
categories[category].append(commit)
return categories
def determine_category(self, commit: Dict) -> str:
"""Determine commit category based on message and labels"""
message = commit['message'].lower()
labels = commit.get('labels', [])
# Check for breaking changes
if 'breaking' in labels or '!' in message.split(':')[0]:
return 'breaking'
# Check for security
if 'security' in labels or any(keyword in message for keyword in ['security', 'vulnerability', 'cve']):
return 'security'
# Check for features
if 'feature' in labels or any(keyword in message for keyword in ['feat', 'add', 'new']):
return 'features'
# Check for bug fixes
if 'bug' in labels or any(keyword in message for keyword in ['fix', 'bug', 'issue']):
return 'bug_fixes'
# Check for documentation
if 'documentation' in labels or any(keyword in message for keyword in ['docs', 'readme']):
return 'documentation'
# Default to internal
return 'internal'
def generate_changelog_content(self, version: str, changes: Dict) -> str:
"""Generate changelog content"""
template = self.template_engine.get_template('changelog')
context = {
'version': version,
'date': datetime.now().strftime('%Y-%m-%d'),
'features': changes['features'],
'bug_fixes': changes['bug_fixes'],
'security': changes['security'],
'breaking': changes['breaking'],
'documentation': changes['documentation'],
'internal': changes['internal']
}
return template.render(context)
# GitHub Actions workflow
name: Generate Changelog
on:
push:
tags:
- 'v*'
jobs:
generate-changelog:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v3
with:
fetch-depth: 0
- name: Setup Python
uses: actions/setup-python@v4
with:
python-version: '3.9'
- name: Install dependencies
run: pip install -r requirements.txt
- name: Generate changelog
run: python scripts/generate_changelog.py
- name: Update changelog
run: |
git config --local user.email "action@github.com"
git config --local user.name "GitHub Action"
git add CHANGELOG.md
git commit -m "Update changelog for ${{ github.ref_name }}"
git push