diff --git a/.gitignore b/.gitignore index de5cb2f5f42e..1ab527632162 100644 --- a/.gitignore +++ b/.gitignore @@ -182,3 +182,6 @@ tsp_client_metadata.yaml # Common toolchain intermediate files temp +debug_analysis.py +__pycache__/ +analysis_output.txt diff --git a/CHANGELOG_ANALYSIS_README.md b/CHANGELOG_ANALYSIS_README.md new file mode 100644 index 000000000000..78cfb121c2cf --- /dev/null +++ b/CHANGELOG_ANALYSIS_README.md @@ -0,0 +1,89 @@ +# CHANGELOG Version Change Analysis Tool + +## Purpose + +This tool analyzes CHANGELOG.md files across the Azure SDK repository to track how many times unreleased package versions changed before being released. + +## Background + +SDK packages maintain a CHANGELOG.md file with version entries in the format: +- `## 1.0.0-beta.1 (Unreleased)` - Version is being actively developed +- `## 1.0.0-beta.1 (2025-11-10)` - Version was released on the specified date + +The tool tracks the evolution of version numbers to understand how frequently version numbers change while in an unreleased state. + +## Usage + +### Basic Usage + +Run the analysis on a sample of 10 CHANGELOG files: + +```bash +python3 analyze_changelog_versions.py +``` + +### Configuration + +Edit the script to adjust: +- **Time period**: Modify `three_months_ago` calculation in `main()` function +- **File limit**: Change the `limit` parameter in `find_changelog_files()` call +- **File selection**: Modify the `find_changelog_files()` function to target specific directories + +### Output + +The tool generates: +1. **Console output**: Summary statistics and per-file analysis +2. **CSV file**: `changelog_version_analysis.csv` with columns: + - `changelog_path`: Relative path to the CHANGELOG.md file + - `version`: The released version number + - `changes_before_release`: Count of version number changes while unreleased + - `release_date`: Date the version was released + - `avg_changes_per_file`: Average changes per release for this file + +## How It Works + +1. **Find CHANGELOGs**: Locates all CHANGELOG.md files under the `sdk/` directory +2. **Retrieve Git History**: Gets full commit history for each file (requires unshallow clone) +3. **Parse Versions**: Extracts version headers and determines if they're released or unreleased +4. **Track Evolution**: Follows the chronological sequence of version numbers +5. **Count Changes**: For each release, counts how many distinct version numbers appeared while unreleased +6. **Calculate Statistics**: Computes per-file and overall averages + +## Example Scenarios + +### Scenario 1: No version changes before release +``` +Commit 1: ## 1.0.0-beta.1 (Unreleased) +Commit 2: ## 1.0.0-beta.1 (Unreleased) <- Same version, multiple commits +Commit 3: ## 1.0.0-beta.1 (2025-11-10) <- Released +Result: 0 changes before release +``` + +### Scenario 2: Version changes before release +``` +Commit 1: ## 1.0.0-beta.1 (Unreleased) +Commit 2: ## 1.0.0-beta.2 (Unreleased) <- Version changed (1 change) +Commit 3: ## 1.0.0-beta.3 (Unreleased) <- Version changed again (2 changes) +Commit 4: ## 1.0.0 (2025-11-10) <- Released +Result: 2 changes before release +``` + +### Scenario 3: Multiple releases per file +``` +Release 1: beta.1 → beta.2 → released (1 change) +Release 2: 1.1.0-beta.1 → 1.1.0 (0 changes) +Average: 0.5 changes per release for this file +``` + +## Requirements + +- Python 3.7+ +- Git repository with full history (run `git fetch --unshallow` if needed) +- Standard library only (no external dependencies) + +## Notes + +- The tool looks back 3 months from the current date by default +- Only released versions (with dates) are included in the analysis +- The analysis is based on the "top" version in each commit (first version header in the CHANGELOG) +- Files with no releases in the time period are skipped in the output diff --git a/analyze_changelog_versions.py b/analyze_changelog_versions.py new file mode 100644 index 000000000000..a5d11408a4f0 --- /dev/null +++ b/analyze_changelog_versions.py @@ -0,0 +1,360 @@ +#!/usr/bin/env python3 +""" +Analyze CHANGELOG.md files to track version changes before release. + +This script: +1. Finds CHANGELOG.md files in the repository +2. Tracks version changes through git history +3. Counts how many times a version changed while unreleased +4. Calculates statistics per file and overall +5. Outputs results to CSV + +Example: + 1.0.0-beta.1 (Unreleased) -> 1.0.0-beta.2 (Unreleased) -> 1.0.0 (2025-11-10) + This counts as 2 version changes before release. +""" + +import re +import subprocess +import csv +from datetime import datetime, timedelta +from pathlib import Path +from collections import defaultdict +from typing import List, Dict, Tuple, Optional + + +def run_git_command(cmd: List[str], cwd: str) -> str: + """Run a git command and return output.""" + result = subprocess.run( + cmd, + cwd=cwd, + capture_output=True, + text=True, + check=True + ) + return result.stdout + + +def find_changelog_files(repo_root: str, limit: Optional[int] = None) -> List[Path]: + """Find all CHANGELOG.md files in the repository.""" + changelogs = [] + sdk_dir = Path(repo_root) / "sdk" + + if sdk_dir.exists(): + for changelog in sdk_dir.rglob("CHANGELOG.md"): + changelogs.append(changelog) + if limit and len(changelogs) >= limit: + break + + return sorted(changelogs) + + +def parse_version_line(line: str) -> Optional[Tuple[str, Optional[str]]]: + """ + Parse a version line from CHANGELOG.md. + + Returns: (version, date) or None + Examples: + "## 1.0.0 (2025-11-10)" -> ("1.0.0", "2025-11-10") + "## 1.0.0-beta.1 (Unreleased)" -> ("1.0.0-beta.1", None) + """ + # Match version headers like ## 1.0.0 (2025-11-10) or ## 1.0.0-beta.1 (Unreleased) + pattern = r'^##\s+([\d.]+(?:-[a-zA-Z0-9.]+)?)\s+\(([^)]+)\)' + match = re.match(pattern, line.strip()) + + if match: + version = match.group(1) + date_str = match.group(2).strip() + + # Check if it's unreleased + if date_str.lower() == "unreleased": + return (version, None) + + # Try to parse as date + try: + datetime.strptime(date_str, "%Y-%m-%d") + return (version, date_str) + except ValueError: + return (version, None) + + return None + + +def get_git_history_for_file(repo_root: str, filepath: str, since_date: str) -> List[Tuple[str, str, str]]: + """ + Get git history for a specific file. + + Returns: List of (commit_hash, date, content) tuples + """ + rel_path = Path(filepath).relative_to(repo_root) + + try: + # Get commits that modified this file since the given date + log_cmd = [ + "git", "--no-pager", "log", + "--follow", + "--since", since_date, + "--format=%H|%ci", + "--", str(rel_path) + ] + log_output = run_git_command(log_cmd, repo_root) + + if not log_output.strip(): + return [] + + commits = [] + for line in log_output.strip().split('\n'): + if '|' in line: + commit_hash, commit_date = line.split('|', 1) + # Get file content at this commit + try: + show_cmd = ["git", "--no-pager", "show", f"{commit_hash}:{rel_path}"] + content = run_git_command(show_cmd, repo_root) + commits.append((commit_hash, commit_date, content)) + except subprocess.CalledProcessError: + # File might not exist at this commit + continue + + return commits + except subprocess.CalledProcessError: + return [] + + +def extract_versions_from_changelog(content: str) -> List[Tuple[str, Optional[str]]]: + """ + Extract all version entries from changelog content. + + Returns: List of (version, release_date) tuples in order they appear + """ + versions = [] + for line in content.split('\n'): + parsed = parse_version_line(line) + if parsed: + versions.append(parsed) + + return versions + + +def analyze_version_changes(repo_root: str, changelog_path: str, since_date: str) -> Dict: + """ + Analyze version changes for a single CHANGELOG.md file. + + Algorithm: + 1. Read the current CHANGELOG content and extract ALL releases + 2. Filter releases by date range + 3. For each release in range, check git history to count version changes while unreleased + 4. If no git history exists (file was regenerated), assume 0 changes + + Example: + - Commit 1: ## 1.0.0-beta.1 (Unreleased) <- Start tracking + - Commit 2: ## 1.0.0-beta.2 (Unreleased) <- Version changed (1 change) + - Commit 3: ## 1.0.0 (2025-11-10) <- Released (1 total change before release) + + Returns: Dictionary with analysis results + """ + # First, read the current CHANGELOG to get all releases + try: + with open(changelog_path, 'r') as f: + current_content = f.read() + except FileNotFoundError: + return { + "path": changelog_path, + "releases": [], + "total_changes": 0, + "avg_changes": 0.0 + } + + # Extract all versions from current changelog + all_versions = extract_versions_from_changelog(current_content) + + # Filter to only released versions within date range + cutoff_dt = datetime.strptime(since_date, "%Y-%m-%d") + releases_in_range = [] + + for version, release_date in all_versions: + if release_date: # Only released versions + try: + release_dt = datetime.strptime(release_date, "%Y-%m-%d") + if release_dt >= cutoff_dt: + releases_in_range.append((version, release_date)) + except ValueError: + pass + + if not releases_in_range: + return { + "path": changelog_path, + "releases": [], + "total_changes": 0, + "avg_changes": 0.0 + } + + # Now get git history to track version changes + history = get_git_history_for_file(repo_root, changelog_path, since_date) + + # Build sequence of top versions commit by commit + commit_sequence = [] + if history: + # Process commits in chronological order (oldest first) + for commit_hash, commit_date, content in reversed(history): + versions = extract_versions_from_changelog(content) + + if versions: + top_version, top_release_date = versions[0] + commit_sequence.append({ + "commit": commit_hash[:7], + "date": commit_date.split()[0], + "version": top_version, + "released": top_release_date is not None, + "release_date": top_release_date + }) + + # For each release in range, count version changes + releases = [] + + for version, release_date in releases_in_range: + # Try to find this release in commit history + num_changes = 0 + + if commit_sequence: + # Find the release event in commit sequence + release_idx = None + for i, commit in enumerate(commit_sequence): + if commit["version"] == version and commit["released"]: + release_idx = i + break + + if release_idx is not None: + # Count distinct unreleased versions that came before this release + unreleased_versions = set() + + # Go back through commits to find unreleased versions leading to this + j = release_idx - 1 + while j >= 0: + prev_commit = commit_sequence[j] + + # Stop when we hit another release + if prev_commit["released"]: + break + + # Add this unreleased version + unreleased_versions.add(prev_commit["version"]) + j -= 1 + + # Check if the released version itself appeared as unreleased + for k in range(max(0, release_idx - 10), release_idx): + if (commit_sequence[k]["version"] == version and + not commit_sequence[k]["released"]): + unreleased_versions.add(version) + break + + # Number of changes = distinct versions - 1 (first doesn't count as change) + num_changes = max(0, len(unreleased_versions) - 1) if unreleased_versions else 0 + + releases.append({ + "version": version, + "changes": num_changes, + "release_date": release_date + }) + + total_changes = sum(r["changes"] for r in releases) + avg_changes = total_changes / len(releases) if releases else 0.0 + + return { + "path": changelog_path, + "releases": releases, + "total_changes": total_changes, + "avg_changes": avg_changes + } + + +def main(): + """Main analysis function.""" + repo_root = "/home/runner/work/azure-sdk-for-net/azure-sdk-for-net" + + # Calculate date 6 months ago + six_months_ago = datetime.now() - timedelta(days=180) + since_date = six_months_ago.strftime("%Y-%m-%d") + + print(f"Analyzing CHANGELOG.md files...") + print(f"Looking for releases since: {since_date}") + print() + + # Find all changelog files + changelog_files = find_changelog_files(repo_root, limit=None) + print(f"Found {len(changelog_files)} CHANGELOG.md files to analyze") + print() + + # Analyze each file + results = [] + for i, changelog_path in enumerate(changelog_files, 1): + rel_path = str(changelog_path.relative_to(repo_root)) + print(f"[{i}/{len(changelog_files)}] Analyzing {rel_path}...") + + analysis = analyze_version_changes(repo_root, str(changelog_path), since_date) + + if analysis["releases"]: + results.append(analysis) + print(f" Found {len(analysis['releases'])} release(s) with {analysis['total_changes']} total changes (avg: {analysis['avg_changes']:.2f})") + else: + print(f" No releases found in date range") + print() + + # Write results to CSV + output_file = Path(repo_root) / "changelog_version_analysis.csv" + + with open(output_file, 'w', newline='') as csvfile: + fieldnames = ['changelog_path', 'version', 'changes_before_release', 'release_date', 'avg_changes_per_file'] + writer = csv.DictWriter(csvfile, fieldnames=fieldnames) + + writer.writeheader() + + for result in results: + rel_path = str(Path(result["path"]).relative_to(repo_root)) + + if result["releases"]: + for release in result["releases"]: + writer.writerow({ + 'changelog_path': rel_path, + 'version': release['version'], + 'changes_before_release': release['changes'], + 'release_date': release['release_date'], + 'avg_changes_per_file': f"{result['avg_changes']:.2f}" + }) + else: + writer.writerow({ + 'changelog_path': rel_path, + 'version': 'N/A', + 'changes_before_release': 0, + 'release_date': 'N/A', + 'avg_changes_per_file': '0.00' + }) + + # Print summary + print("=" * 80) + print("SUMMARY") + print("=" * 80) + print(f"Files analyzed: {len(changelog_files)}") + print(f"Files with releases in date range: {len(results)}") + + if results: + total_releases = sum(len(r["releases"]) for r in results) + total_changes = sum(r["total_changes"] for r in results) + overall_avg = total_changes / total_releases if total_releases > 0 else 0 + + print(f"Total releases found: {total_releases}") + print(f"Total version changes before release: {total_changes}") + print(f"Overall average changes per release: {overall_avg:.2f}") + + # Print per-file averages + print() + print("Per-file averages:") + for result in results: + rel_path = str(Path(result["path"]).relative_to(repo_root)) + print(f" {rel_path}: {result['avg_changes']:.2f}") + + print() + print(f"Results written to: {output_file}") + + +if __name__ == "__main__": + main() diff --git a/changelog_version_analysis.csv b/changelog_version_analysis.csv new file mode 100644 index 000000000000..932e9981a8b9 --- /dev/null +++ b/changelog_version_analysis.csv @@ -0,0 +1,360 @@ +changelog_path,version,changes_before_release,release_date,avg_changes_per_file +sdk/agentserver/Azure.AI.AgentServer.AgentFramework/CHANGELOG.md,1.0.0-beta.1,0,2025-11-07,0.00 +sdk/agentserver/Azure.AI.AgentServer.Contracts/CHANGELOG.md,1.0.0-beta.1,0,2025-11-07,0.00 +sdk/agentserver/Azure.AI.AgentServer.Core/CHANGELOG.md,1.0.0-beta.1,0,2025-11-07,0.00 +sdk/ai/Azure.AI.Agents.Persistent/CHANGELOG.md,1.2.0-beta.7,0,2025-10-28,0.00 +sdk/ai/Azure.AI.Agents.Persistent/CHANGELOG.md,1.2.0-beta.6,0,2025-10-10,0.00 +sdk/ai/Azure.AI.Agents.Persistent/CHANGELOG.md,1.2.0-beta.5,0,2025-09-18,0.00 +sdk/ai/Azure.AI.Agents.Persistent/CHANGELOG.md,1.2.0-beta.4,0,2025-09-05,0.00 +sdk/ai/Azure.AI.Agents.Persistent/CHANGELOG.md,1.2.0-beta.3,0,2025-08-22,0.00 +sdk/ai/Azure.AI.Agents.Persistent/CHANGELOG.md,1.2.0-beta.2,0,2025-08-13,0.00 +sdk/ai/Azure.AI.Agents.Persistent/CHANGELOG.md,1.2.0-beta.1,0,2025-07-25,0.00 +sdk/ai/Azure.AI.Agents.Persistent/CHANGELOG.md,1.1.0-beta.4,0,2025-07-11,0.00 +sdk/ai/Azure.AI.Agents.Persistent/CHANGELOG.md,1.1.0-beta.3,0,2025-06-27,0.00 +sdk/ai/Azure.AI.Agents.Persistent/CHANGELOG.md,1.1.0-beta.2,0,2025-06-04,0.00 +sdk/ai/Azure.AI.Agents.Persistent/CHANGELOG.md,1.1.0-beta.1,0,2025-05-21,0.00 +sdk/ai/Azure.AI.Agents.Persistent/CHANGELOG.md,1.0.0,0,2025-05-15,0.00 +sdk/ai/Azure.AI.Agents.Persistent/CHANGELOG.md,1.0.0-beta.2,0,2025-05-14,0.00 +sdk/ai/Azure.AI.Inference/CHANGELOG.md,1.0.0-beta.5,0,2025-05-14,0.00 +sdk/ai/Azure.AI.Projects/CHANGELOG.md,1.1.0,0,2025-11-03,0.00 +sdk/ai/Azure.AI.Projects/CHANGELOG.md,1.0.0,0,2025-10-01,0.00 +sdk/ai/Azure.AI.Projects/CHANGELOG.md,1.0.0-beta.11,0,2025-08-20,0.00 +sdk/ai/Azure.AI.Projects/CHANGELOG.md,1.0.0-beta.10,0,2025-07-11,0.00 +sdk/ai/Azure.AI.Projects/CHANGELOG.md,1.0.0-beta.9,0,2025-05-16,0.00 +sdk/ai/Azure.AI.VoiceLive/CHANGELOG.md,1.0.0,0,2025-10-01,0.00 +sdk/ai/Azure.AI.VoiceLive/CHANGELOG.md,1.0.0-beta.4,0,2025-09-30,0.00 +sdk/ai/Azure.AI.VoiceLive/CHANGELOG.md,1.0.0-beta.3,0,2025-09-26,0.00 +sdk/ai/Azure.AI.VoiceLive/CHANGELOG.md,1.0.0-beta.2,0,2025-09-22,0.00 +sdk/ai/Azure.AI.VoiceLive/CHANGELOG.md,1.0.0-beta.1,0,2025-09-16,0.00 +sdk/apicenter/Azure.ResourceManager.ApiCenter/CHANGELOG.md,1.0.0,0,2025-06-06,0.00 +sdk/apimanagement/Azure.ResourceManager.ApiManagement/CHANGELOG.md,1.3.0,0,2025-05-21,0.00 +sdk/appconfiguration/Azure.Data.AppConfiguration/CHANGELOG.md,1.7.0,0,2025-11-07,0.00 +sdk/appconfiguration/Azure.ResourceManager.AppConfiguration/CHANGELOG.md,1.4.1,0,2025-07-28,0.00 +sdk/applicationinsights/Azure.ResourceManager.ApplicationInsights/CHANGELOG.md,1.1.0-beta.1,0,2025-08-04,0.00 +sdk/arizeaiobservabilityeval/Azure.ResourceManager.ArizeAIObservabilityEval/CHANGELOG.md,1.0.0,0,2025-07-07,0.00 +sdk/authorization/Azure.ResourceManager.Authorization/CHANGELOG.md,1.1.6,0,2025-11-09,0.00 +sdk/authorization/Azure.ResourceManager.Authorization/CHANGELOG.md,1.1.5,0,2025-07-28,0.00 +sdk/avs/Azure.ResourceManager.Avs/CHANGELOG.md,1.5.0,0,2025-07-02,0.00 +sdk/azurestackhci/Azure.ResourceManager.Hci.Vm/CHANGELOG.md,1.0.0-beta.1,0,2025-09-19,0.00 +sdk/batch/Azure.Compute.Batch/CHANGELOG.md,1.0.0-beta.3,0,2025-06-19,0.00 +sdk/carbon/Azure.ResourceManager.CarbonOptimization/CHANGELOG.md,1.0.0,0,2025-07-04,0.00 +sdk/carbon/Azure.ResourceManager.CarbonOptimization/CHANGELOG.md,1.0.0-beta.1,0,2025-05-15,0.00 +sdk/cdn/Azure.ResourceManager.Cdn/CHANGELOG.md,1.5.0,0,2025-08-08,0.00 +sdk/chaos/Azure.ResourceManager.Chaos/CHANGELOG.md,1.1.0,0,2025-05-22,0.00 +sdk/cloudhealth/Azure.ResourceManager.CloudHealth/CHANGELOG.md,1.0.0-beta.1,0,2025-06-20,0.00 +sdk/cognitivelanguage/Azure.AI.Language.Conversations/CHANGELOG.md,2.0.0-beta.4,0,2025-09-18,0.00 +sdk/cognitivelanguage/Azure.AI.Language.Conversations/CHANGELOG.md,2.0.0-beta.3,0,2025-06-23,0.00 +sdk/cognitivelanguage/Azure.AI.Language.Conversations.Authoring/CHANGELOG.md,1.0.0-beta.2,0,2025-07-24,0.00 +sdk/cognitivelanguage/Azure.AI.Language.Text/CHANGELOG.md,1.0.0-beta.3,0,2025-06-23,0.00 +sdk/cognitivelanguage/Azure.AI.Language.Text.Authoring/CHANGELOG.md,1.0.0-beta.2,0,2025-07-24,0.00 +sdk/cognitiveservices/Azure.ResourceManager.CognitiveServices/CHANGELOG.md,1.5.2,0,2025-11-11,0.00 +sdk/cognitiveservices/Azure.ResourceManager.CognitiveServices/CHANGELOG.md,1.5.1,0,2025-07-28,0.00 +sdk/cognitiveservices/Azure.ResourceManager.CognitiveServices/CHANGELOG.md,1.5.0,0,2025-06-15,0.00 +sdk/cognitiveservices/Azure.ResourceManager.CognitiveServices/CHANGELOG.md,1.5.0-beta.1,0,2025-05-30,0.00 +sdk/communication/Azure.Communication.CallAutomation/CHANGELOG.md,1.5.0,0,2025-08-25,0.00 +sdk/communication/Azure.Communication.CallAutomation/CHANGELOG.md,1.4.0,0,2025-06-04,0.00 +sdk/communication/Azure.Communication.CallAutomation/CHANGELOG.md,1.5.0-beta.1,0,2025-05-16,0.00 +sdk/communication/Azure.Communication.Chat/CHANGELOG.md,1.4.0,0,2025-06-17,0.00 +sdk/communication/Azure.Communication.Common/CHANGELOG.md,1.4.0,0,2025-06-04,0.00 +sdk/communication/Azure.Communication.Email/CHANGELOG.md,1.1.0,0,2025-10-01,0.00 +sdk/communication/Azure.Communication.Identity/CHANGELOG.md,1.4.0-beta.1,0,2025-06-09,0.00 +sdk/communication/Azure.Communication.Messages/CHANGELOG.md,1.3.0-beta.2,0,2025-10-01,0.00 +sdk/communication/Azure.Communication.PhoneNumbers/CHANGELOG.md,1.5.0,0,2025-08-28,0.00 +sdk/communication/Azure.Communication.PhoneNumbers/CHANGELOG.md,1.5.0-beta.1,0,2025-07-22,0.00 +sdk/communication/Azure.Communication.PhoneNumbers/CHANGELOG.md,1.4.0,0,2025-06-20,0.00 +sdk/communication/Azure.Communication.PhoneNumbers/CHANGELOG.md,1.4.0-beta.1,0,2025-05-21,0.00 +sdk/communication/Azure.Communication.Sms/CHANGELOG.md,1.1.0-beta.3,0,2025-06-12,0.00 +sdk/compute/Azure.ResourceManager.Compute/CHANGELOG.md,1.12.0,0,2025-09-26,0.00 +sdk/compute/Azure.ResourceManager.Compute/CHANGELOG.md,1.11.0,0,2025-08-12,0.00 +sdk/compute/Azure.ResourceManager.Compute/CHANGELOG.md,1.10.0,0,2025-06-30,0.00 +sdk/computerecommender/Azure.ResourceManager.Compute.Recommender/CHANGELOG.md,1.0.0-beta.2,0,2025-11-03,0.00 +sdk/computerecommender/Azure.ResourceManager.Compute.Recommender/CHANGELOG.md,1.0.0-beta.1,0,2025-09-30,0.00 +sdk/computeschedule/Azure.ResourceManager.ComputeSchedule/CHANGELOG.md,1.2.0-beta.1,0,2025-09-12,0.00 +sdk/computeschedule/Azure.ResourceManager.ComputeSchedule/CHANGELOG.md,1.1.0,0,2025-09-12,0.00 +sdk/confidentialledger/Azure.Security.CodeTransparency/CHANGELOG.md,1.0.0-beta.5,0,2025-10-20,0.00 +sdk/connectedcache/Azure.ResourceManager.ConnectedCache/CHANGELOG.md,1.0.0-beta.1,0,2025-06-20,0.00 +sdk/containerapps/Azure.ResourceManager.AppContainers/CHANGELOG.md,1.5.0,0,2025-10-09,0.00 +sdk/containerapps/Azure.ResourceManager.AppContainers/CHANGELOG.md,1.4.1,0,2025-08-11,0.00 +sdk/containerapps/Azure.ResourceManager.AppContainers/CHANGELOG.md,1.4.0,0,2025-05-22,0.00 +sdk/containerinstance/Azure.ResourceManager.ContainerInstance/CHANGELOG.md,1.3.0,0,2025-09-29,0.00 +sdk/containerinstance/Azure.ResourceManager.ContainerInstance/CHANGELOG.md,1.3.0-beta.4,0,2025-09-16,0.00 +sdk/containerinstance/Azure.ResourceManager.ContainerInstance/CHANGELOG.md,1.3.0-beta.3,0,2025-08-11,0.00 +sdk/containerinstance/Azure.ResourceManager.ContainerInstance/CHANGELOG.md,1.3.0-beta.2,0,2025-06-13,0.00 +sdk/containerregistry/Azure.ResourceManager.ContainerRegistry/CHANGELOG.md,1.4.0,0,2025-11-05,0.00 +sdk/containerregistry/Azure.ResourceManager.ContainerRegistry/CHANGELOG.md,1.3.1,0,2025-08-11,0.00 +sdk/containerservice/Azure.ResourceManager.ContainerService/CHANGELOG.md,1.2.5,0,2025-07-28,0.00 +sdk/containerservice/Azure.ResourceManager.ContainerService/CHANGELOG.md,1.2.4,0,2025-06-24,0.00 +sdk/core/Azure.Core/CHANGELOG.md,1.50.0,0,2025-11-05,0.00 +sdk/core/Azure.Core/CHANGELOG.md,1.49.0,0,2025-09-22,0.00 +sdk/core/Azure.Core/CHANGELOG.md,1.48.0,0,2025-09-09,0.00 +sdk/core/Azure.Core/CHANGELOG.md,1.47.3,0,2025-08-20,0.00 +sdk/core/Azure.Core/CHANGELOG.md,1.47.2,0,2025-08-11,0.00 +sdk/core/Azure.Core/CHANGELOG.md,1.47.1,0,2025-07-15,0.00 +sdk/core/Azure.Core/CHANGELOG.md,1.47.0,0,2025-07-09,0.00 +sdk/core/Azure.Core/CHANGELOG.md,1.46.2,0,2025-06-05,0.00 +sdk/core/System.ClientModel/CHANGELOG.md,1.8.0,0,2025-10-31,0.00 +sdk/core/System.ClientModel/CHANGELOG.md,1.7.0,0,2025-09-22,0.00 +sdk/core/System.ClientModel/CHANGELOG.md,1.6.1,0,2025-08-20,0.00 +sdk/core/System.ClientModel/CHANGELOG.md,1.6.0,0,2025-08-11,0.00 +sdk/core/System.ClientModel/CHANGELOG.md,1.5.1,0,2025-07-14,0.00 +sdk/core/System.ClientModel/CHANGELOG.md,1.5.0,0,2025-07-07,0.00 +sdk/core/System.ClientModel/CHANGELOG.md,1.5.0-beta.1,0,2025-06-13,0.00 +sdk/core/System.ClientModel/CHANGELOG.md,1.4.2,0,2025-06-05,0.00 +sdk/cosmosdb/Azure.ResourceManager.CosmosDB/CHANGELOG.md,1.4.0-beta.13,0,2025-08-04,0.00 +sdk/datadog/Azure.ResourceManager.Datadog/CHANGELOG.md,1.0.0-beta.6,0,2025-08-04,0.00 +sdk/datafactory/Azure.ResourceManager.DataFactory/CHANGELOG.md,1.10.0,0,2025-09-03,0.00 +sdk/datafactory/Azure.ResourceManager.DataFactory/CHANGELOG.md,1.9.0,0,2025-06-13,0.00 +sdk/datamigration/Azure.ResourceManager.DataMigration/CHANGELOG.md,1.0.0,0,2025-09-25,0.00 +sdk/datamigration/Azure.ResourceManager.DataMigration/CHANGELOG.md,1.0.0-beta.6,0,2025-08-04,0.00 +sdk/dataprotection/Azure.ResourceManager.DataProtectionBackup/CHANGELOG.md,1.7.0,0,2025-09-25,0.00 +sdk/dependencymap/Azure.ResourceManager.DependencyMap/CHANGELOG.md,1.0.0-beta.1,0,2025-05-14,0.00 +sdk/desktopvirtualization/Azure.ResourceManager.DesktopVirtualization/CHANGELOG.md,1.3.2,0,2025-08-11,0.00 +sdk/deviceprovisioningservices/Azure.ResourceManager.DeviceProvisioningServices/CHANGELOG.md,1.3.0-beta.1,0,2025-10-13,0.00 +sdk/deviceregistry/Azure.ResourceManager.DeviceRegistry/CHANGELOG.md,1.1.0-beta.1,0,2025-10-23,0.00 +sdk/digitaltwins/Azure.DigitalTwins.Core/CHANGELOG.md,1.6.0,0,2025-06-10,0.00 +sdk/disconnectedoperations/Azure.ResourceManager.DisconnectedOperations/CHANGELOG.md,1.0.0-beta.1,0,2025-09-24,0.00 +sdk/dnsresolver/Azure.ResourceManager.DnsResolver/CHANGELOG.md,1.2.0,0,2025-06-10,0.00 +sdk/durabletask/Azure.ResourceManager.DurableTask/CHANGELOG.md,1.0.0,0,2025-11-03,0.00 +sdk/entra/Microsoft.Azure.WebJobs.Extensions.AuthenticationEvents/CHANGELOG.md,1.1.0,0,2025-07-29,0.00 +sdk/eventgrid/Azure.Messaging.EventGrid/CHANGELOG.md,5.0.0,0,2025-06-26,0.00 +sdk/eventgrid/Azure.Messaging.EventGrid/CHANGELOG.md,5.0.0-beta.1,0,2025-06-04,0.00 +sdk/eventgrid/Azure.Messaging.EventGrid/CHANGELOG.md,4.31.0,0,2025-05-19,0.00 +sdk/eventgrid/Azure.Messaging.EventGrid.SystemEvents/CHANGELOG.md,1.0.0,0,2025-06-23,0.00 +sdk/eventgrid/Azure.Messaging.EventGrid.SystemEvents/CHANGELOG.md,1.0.0-beta.5,0,2025-06-04,0.00 +sdk/eventgrid/Azure.Messaging.EventGrid.SystemEvents/CHANGELOG.md,1.0.0-beta.4,0,2025-06-03,0.00 +sdk/eventgrid/Azure.Messaging.EventGrid.SystemEvents/CHANGELOG.md,1.0.0-beta.3,0,2025-05-19,0.00 +sdk/eventgrid/Azure.ResourceManager.EventGrid/CHANGELOG.md,1.2.0-beta.2,0,2025-09-03,0.00 +sdk/eventgrid/Azure.ResourceManager.EventGrid/CHANGELOG.md,1.2.0-beta.1,0,2025-06-05,0.00 +sdk/eventgrid/Microsoft.Azure.WebJobs.Extensions.EventGrid/CHANGELOG.md,3.5.0,0,2025-06-20,0.00 +sdk/eventhub/Azure.Messaging.EventHubs/CHANGELOG.md,5.12.2,0,2025-06-12,0.00 +sdk/eventhub/Azure.Messaging.EventHubs.Processor/CHANGELOG.md,5.12.2,0,2025-06-12,0.00 +sdk/eventhub/Azure.ResourceManager.EventHubs/CHANGELOG.md,1.2.1,0,2025-09-23,0.00 +sdk/eventhub/Azure.ResourceManager.EventHubs/CHANGELOG.md,1.2.0,0,2025-06-13,0.00 +sdk/eventhub/Microsoft.Azure.WebJobs.Extensions.EventHubs/CHANGELOG.md,6.5.3,0,2025-10-20,0.00 +sdk/eventhub/Microsoft.Azure.WebJobs.Extensions.EventHubs/CHANGELOG.md,6.5.2,0,2025-06-16,0.00 +sdk/extensions/Azure.Extensions.AspNetCore.DataProtection.Blobs/CHANGELOG.md,1.5.1,0,2025-06-23,0.00 +sdk/extensions/Azure.Extensions.AspNetCore.DataProtection.Keys/CHANGELOG.md,1.6.1,0,2025-06-23,0.00 +sdk/extensions/Azure.Extensions.AspNetCore.DataProtection.Keys/CHANGELOG.md,1.6.0,0,2025-05-19,0.00 +sdk/extensions/Microsoft.Extensions.Azure/CHANGELOG.md,1.13.0,0,2025-09-22,0.00 +sdk/extensions/Microsoft.Extensions.Azure/CHANGELOG.md,1.12.0,0,2025-06-12,0.00 +sdk/fabric/Azure.ResourceManager.Fabric/CHANGELOG.md,1.0.0,0,2025-09-05,0.00 +sdk/fleet/Azure.ResourceManager.ContainerServiceFleet/CHANGELOG.md,1.2.0-beta.1,0,2025-08-12,0.00 +sdk/frontdoor/Azure.ResourceManager.FrontDoor/CHANGELOG.md,1.4.1,0,2025-10-15,0.00 +sdk/grafana/Azure.ResourceManager.Grafana/CHANGELOG.md,1.2.0-beta.3,0,2025-08-07,0.00 +sdk/grafana/Azure.ResourceManager.Grafana/CHANGELOG.md,1.2.0-beta.2,0,2025-08-04,0.00 +sdk/grafana/Azure.ResourceManager.Grafana/CHANGELOG.md,1.2.0-beta.1,0,2025-06-24,0.00 +sdk/hardwaresecuritymodules/Azure.ResourceManager.HardwareSecurityModules/CHANGELOG.md,1.0.0,0,2025-07-15,0.00 +sdk/hdinsight/Azure.ResourceManager.HDInsight/CHANGELOG.md,1.2.0-beta.5,0,2025-10-15,0.00 +sdk/healthbot/Azure.ResourceManager.HealthBot/CHANGELOG.md,1.2.0,0,2025-10-22,0.00 +sdk/healthdataaiservices/Azure.Health.Deidentification/CHANGELOG.md,1.1.0-beta.1,0,2025-09-30,0.00 +sdk/healthinsights/Azure.Health.Insights.RadiologyInsights/CHANGELOG.md,1.1.0,0,2025-06-13,0.00 +sdk/identity/Azure.Identity/CHANGELOG.md,1.17.0,0,2025-10-07,0.00 +sdk/identity/Azure.Identity/CHANGELOG.md,1.16.0,0,2025-09-09,0.00 +sdk/identity/Azure.Identity/CHANGELOG.md,1.15.0,0,2025-08-11,0.00 +sdk/identity/Azure.Identity/CHANGELOG.md,1.15.0-beta.1,0,2025-07-17,0.00 +sdk/identity/Azure.Identity/CHANGELOG.md,1.14.2,0,2025-07-10,0.00 +sdk/identity/Azure.Identity/CHANGELOG.md,1.14.1,0,2025-06-24,0.00 +sdk/identity/Azure.Identity.Broker/CHANGELOG.md,1.3.0,0,2025-09-04,0.00 +sdk/identity/Azure.Identity.Broker/CHANGELOG.md,1.3.0-beta.4,0,2025-07-11,0.00 +sdk/identity/Azure.Identity.Broker/CHANGELOG.md,1.2.1,0,2025-07-11,0.00 +sdk/identity/Azure.Identity.Broker/CHANGELOG.md,1.3.0-beta.3,0,2025-06-10,0.00 +sdk/impactreporting/Azure.ResourceManager.ImpactReporting/CHANGELOG.md,1.0.0-beta.1,0,2025-10-23,0.00 +sdk/iot/Azure.ResourceManager.IotFirmwareDefense/CHANGELOG.md,1.1.0,0,2025-09-15,0.00 +sdk/iot/Azure.ResourceManager.IotFirmwareDefense/CHANGELOG.md,1.1.0-beta.1,0,2025-06-02,0.00 +sdk/iothub/Azure.ResourceManager.IotHub/CHANGELOG.md,1.2.0-beta.2,0,2025-10-29,0.00 +sdk/iotoperations/Azure.ResourceManager.IotOperations/CHANGELOG.md,1.1.0-beta.1,0,2025-09-09,0.00 +sdk/keyvault/Azure.ResourceManager.KeyVault/CHANGELOG.md,1.3.3,0,2025-09-15,0.00 +sdk/keyvault/Azure.Security.KeyVault.Administration/CHANGELOG.md,4.6.0,0,2025-06-16,0.00 +sdk/keyvault/Azure.Security.KeyVault.Certificates/CHANGELOG.md,4.8.0,0,2025-06-16,0.00 +sdk/keyvault/Azure.Security.KeyVault.Keys/CHANGELOG.md,4.8.0,0,2025-06-27,0.00 +sdk/keyvault/Azure.Security.KeyVault.Secrets/CHANGELOG.md,4.8.0,0,2025-06-13,0.00 +sdk/kusto/Azure.ResourceManager.Kusto/CHANGELOG.md,1.6.2,0,2025-09-04,0.00 +sdk/kusto/Azure.ResourceManager.Kusto/CHANGELOG.md,1.6.1,0,2025-07-28,0.00 +sdk/lambdatesthyperexecute/Azure.ResourceManager.LambdaTestHyperExecute/CHANGELOG.md,1.0.0,0,2025-07-07,0.00 +sdk/loadtestservice/Azure.Developer.Playwright/CHANGELOG.md,1.0.0,0,2025-08-29,0.00 +sdk/loadtestservice/Azure.Developer.Playwright/CHANGELOG.md,1.0.0-beta.2,0,2025-08-06,0.00 +sdk/loadtestservice/Azure.Developer.Playwright/CHANGELOG.md,1.0.0-beta.1,0,2025-07-01,0.00 +sdk/loadtestservice/Azure.Developer.Playwright.NUnit/CHANGELOG.md,1.0.0,0,2025-08-29,0.00 +sdk/loadtestservice/Azure.Developer.Playwright.NUnit/CHANGELOG.md,1.0.0-beta.2,0,2025-08-06,0.00 +sdk/loadtestservice/Azure.Developer.Playwright.NUnit/CHANGELOG.md,1.0.0-beta.1,0,2025-07-01,0.00 +sdk/loadtestservice/Azure.ResourceManager.LoadTesting/CHANGELOG.md,1.1.2,0,2025-07-28,0.00 +sdk/machinelearningservices/Azure.ResourceManager.MachineLearning/CHANGELOG.md,1.2.3,0,2025-08-11,0.00 +sdk/managedserviceidentity/Azure.ResourceManager.ManagedServiceIdentities/CHANGELOG.md,1.4.0,0,2025-07-11,0.00 +sdk/managedserviceidentity/Azure.ResourceManager.ManagedServiceIdentities/CHANGELOG.md,1.3.0,0,2025-06-13,0.00 +sdk/mongocluster/Azure.ResourceManager.MongoCluster/CHANGELOG.md,1.0.0,0,2025-10-30,0.00 +sdk/mongodbatlas/Azure.ResourceManager.MongoDBAtlas/CHANGELOG.md,1.0.0,0,2025-07-03,0.00 +sdk/mongodbatlas/Azure.ResourceManager.MongoDBAtlas/CHANGELOG.md,1.0.0-beta.1,0,2025-05-29,0.00 +sdk/monitor/Azure.Monitor.Ingestion/CHANGELOG.md,1.2.0,0,2025-08-05,0.00 +sdk/monitor/Azure.Monitor.OpenTelemetry.AspNetCore/CHANGELOG.md,1.4.0-beta.1,0,2025-10-21,0.00 +sdk/monitor/Azure.Monitor.OpenTelemetry.Exporter/CHANGELOG.md,1.5.0-beta.1,0,2025-10-16,0.00 +sdk/monitor/Azure.Monitor.Query.Logs/CHANGELOG.md,1.0.0,0,2025-10-15,0.00 +sdk/monitor/Azure.Monitor.Query.Metrics/CHANGELOG.md,1.0.0,0,2025-10-15,0.00 +sdk/mysql/Azure.ResourceManager.MySql/CHANGELOG.md,1.2.0,0,2025-10-31,0.00 +sdk/mysql/Azure.ResourceManager.MySql/CHANGELOG.md,1.1.2,0,2025-08-11,0.00 +sdk/neonpostgres/Azure.ResourceManager.NeonPostgres/CHANGELOG.md,1.0.0,0,2025-05-22,0.00 +sdk/netapp/Azure.ResourceManager.NetApp/CHANGELOG.md,1.13.0-beta.1,0,2025-10-22,0.00 +sdk/netapp/Azure.ResourceManager.NetApp/CHANGELOG.md,1.12.0,0,2025-08-25,0.00 +sdk/netapp/Azure.ResourceManager.NetApp/CHANGELOG.md,1.11.0,0,2025-07-25,0.00 +sdk/network/Azure.ResourceManager.Network/CHANGELOG.md,1.13.0,0,2025-10-24,0.00 +sdk/network/Azure.ResourceManager.Network/CHANGELOG.md,1.12.0,0,2025-09-19,0.00 +sdk/network/Azure.ResourceManager.Network/CHANGELOG.md,1.11.3,0,2025-08-21,0.00 +sdk/network/Azure.ResourceManager.Network/CHANGELOG.md,1.11.2,0,2025-08-11,0.00 +sdk/network/Azure.ResourceManager.Network/CHANGELOG.md,1.11.1,0,2025-07-01,0.00 +sdk/network/Azure.ResourceManager.Network/CHANGELOG.md,1.11.0,0,2025-05-22,0.00 +sdk/network/Azure.ResourceManager.Network/CHANGELOG.md,1.11.0-beta.2,0,2025-05-15,0.00 +sdk/networkcloud/Azure.ResourceManager.NetworkCloud/CHANGELOG.md,1.2.0,0,2025-06-25,0.00 +sdk/newrelicobservability/Azure.ResourceManager.NewRelicObservability/CHANGELOG.md,1.2.0-beta.1,0,2025-11-05,0.00 +sdk/onlineexperimentation/Azure.Analytics.OnlineExperimentation/CHANGELOG.md,1.0.0-beta.1,0,2025-06-10,0.00 +sdk/onlineexperimentation/Azure.ResourceManager.OnlineExperimentation/CHANGELOG.md,1.0.0-beta.1,0,2025-05-23,0.00 +sdk/openai/Azure.AI.OpenAI/CHANGELOG.md,2.5.0-beta.1,0,2025-10-03,0.00 +sdk/openai/Azure.AI.OpenAI/CHANGELOG.md,2.3.0-beta.2,0,2025-08-21,0.00 +sdk/openai/Azure.AI.OpenAI/CHANGELOG.md,2.3.0-beta.1,0,2025-08-07,0.00 +sdk/openai/Azure.AI.OpenAI/CHANGELOG.md,2.2.0-beta.5,0,2025-07-11,0.00 +sdk/operationalinsights/Azure.ResourceManager.OperationalInsights/CHANGELOG.md,1.3.1,0,2025-07-28,0.00 +sdk/oracle/Azure.ResourceManager.OracleDatabase/CHANGELOG.md,1.2.0,0,2025-09-30,0.00 +sdk/oracle/Azure.ResourceManager.OracleDatabase/CHANGELOG.md,1.1.0,0,2025-06-26,0.00 +sdk/planetarycomputer/Azure.ResourceManager.PlanetaryComputer/CHANGELOG.md,1.0.0-beta.1,0,2025-07-11,0.00 +sdk/playwright/Azure.ResourceManager.Playwright/CHANGELOG.md,1.0.0,0,2025-09-05,0.00 +sdk/playwright/Azure.ResourceManager.Playwright/CHANGELOG.md,1.0.0-beta.1,0,2025-07-30,0.00 +sdk/policyinsights/Azure.ResourceManager.PolicyInsights/CHANGELOG.md,1.3.0,0,2025-10-22,0.00 +sdk/postgresql/Azure.ResourceManager.PostgreSql/CHANGELOG.md,1.3.1,0,2025-08-06,0.00 +sdk/postgresql/Azure.ResourceManager.PostgreSql/CHANGELOG.md,1.3.0,0,2025-06-25,0.00 +sdk/providerhub/Azure.ResourceManager.ProviderHub/CHANGELOG.md,1.2.0,0,2025-10-21,0.00 +sdk/provisioning/Azure.Provisioning/CHANGELOG.md,1.4.0-beta.1,0,2025-09-03,0.00 +sdk/provisioning/Azure.Provisioning/CHANGELOG.md,1.3.0,0,2025-08-01,0.00 +sdk/provisioning/Azure.Provisioning/CHANGELOG.md,1.2.1,0,2025-07-09,0.00 +sdk/provisioning/Azure.Provisioning/CHANGELOG.md,1.2.0,0,2025-07-02,0.00 +sdk/provisioning/Azure.Provisioning/CHANGELOG.md,1.1.0,0,2025-06-16,0.00 +sdk/provisioning/Azure.Provisioning/CHANGELOG.md,1.0.1,0,2025-05-30,0.00 +sdk/provisioning/Azure.Provisioning.AppConfiguration/CHANGELOG.md,1.1.0,0,2025-06-16,0.00 +sdk/provisioning/Azure.Provisioning.AppService/CHANGELOG.md,1.3.0-beta.1,0,2025-11-07,0.00 +sdk/provisioning/Azure.Provisioning.AppService/CHANGELOG.md,1.2.0,0,2025-06-26,0.00 +sdk/provisioning/Azure.Provisioning.AppService/CHANGELOG.md,1.1.1,0,2025-06-25,0.00 +sdk/provisioning/Azure.Provisioning.AppService/CHANGELOG.md,1.1.0,0,2025-06-16,0.00 +sdk/provisioning/Azure.Provisioning.ApplicationInsights/CHANGELOG.md,1.1.0,0,2025-06-16,0.00 +sdk/provisioning/Azure.Provisioning.CognitiveServices/CHANGELOG.md,1.1.0,0,2025-06-16,0.00 +sdk/provisioning/Azure.Provisioning.CosmosDB/CHANGELOG.md,1.1.0-beta.1,0,2025-06-16,0.00 +sdk/provisioning/Azure.Provisioning.Dns/CHANGELOG.md,1.0.0-beta.1,0,2025-11-07,0.00 +sdk/provisioning/Azure.Provisioning.EventHubs/CHANGELOG.md,1.1.0,0,2025-06-16,0.00 +sdk/provisioning/Azure.Provisioning.FrontDoor/CHANGELOG.md,1.0.0-beta.1,0,2025-10-17,0.00 +sdk/provisioning/Azure.Provisioning.KeyVault/CHANGELOG.md,1.1.0,0,2025-06-16,0.00 +sdk/provisioning/Azure.Provisioning.OperationalInsights/CHANGELOG.md,1.1.0,0,2025-06-17,0.00 +sdk/provisioning/Azure.Provisioning.PostgreSql/CHANGELOG.md,1.1.1,0,2025-06-25,0.00 +sdk/provisioning/Azure.Provisioning.PostgreSql/CHANGELOG.md,1.1.0,0,2025-06-16,0.00 +sdk/provisioning/Azure.Provisioning.Redis/CHANGELOG.md,1.1.0,0,2025-06-16,0.00 +sdk/provisioning/Azure.Provisioning.Search/CHANGELOG.md,1.1.0-beta.1,0,2025-06-16,0.00 +sdk/provisioning/Azure.Provisioning.ServiceBus/CHANGELOG.md,1.1.0,0,2025-06-16,0.00 +sdk/provisioning/Azure.Provisioning.SignalR/CHANGELOG.md,1.1.0,0,2025-06-16,0.00 +sdk/provisioning/Azure.Provisioning.Sql/CHANGELOG.md,1.1.0,0,2025-06-16,0.00 +sdk/provisioning/Azure.Provisioning.Storage/CHANGELOG.md,1.1.2,0,2025-07-15,0.00 +sdk/provisioning/Azure.Provisioning.Storage/CHANGELOG.md,1.1.1,0,2025-06-25,0.00 +sdk/provisioning/Azure.Provisioning.Storage/CHANGELOG.md,1.1.0,0,2025-06-16,0.00 +sdk/provisioning/Azure.Provisioning.Storage/CHANGELOG.md,1.0.1,0,2025-05-15,0.00 +sdk/provisioning/Azure.Provisioning.WebPubSub/CHANGELOG.md,1.1.0,0,2025-06-16,0.00 +sdk/purestorageblock/Azure.ResourceManager.PureStorageBlock/CHANGELOG.md,1.0.0,0,2025-06-26,0.00 +sdk/purestorageblock/Azure.ResourceManager.PureStorageBlock/CHANGELOG.md,1.0.0-beta.1,0,2025-05-19,0.00 +sdk/qumulo/Azure.ResourceManager.Qumulo/CHANGELOG.md,1.2.0,0,2025-10-22,0.00 +sdk/quota/Azure.ResourceManager.Quota/CHANGELOG.md,1.2.0,0,2025-09-25,0.00 +sdk/quota/Azure.ResourceManager.Quota/CHANGELOG.md,1.2.0-beta.1,0,2025-09-17,0.00 +sdk/redis/Azure.ResourceManager.Redis/CHANGELOG.md,1.5.1,0,2025-07-28,0.00 +sdk/redisenterprise/Azure.ResourceManager.RedisEnterprise/CHANGELOG.md,1.3.0,0,2025-11-10,0.00 +sdk/redisenterprise/Azure.ResourceManager.RedisEnterprise/CHANGELOG.md,1.2.1,0,2025-07-25,0.00 +sdk/redisenterprise/Azure.ResourceManager.RedisEnterprise/CHANGELOG.md,1.2.0,0,2025-07-23,0.00 +sdk/resourcegraph/Azure.ResourceManager.ResourceGraph/CHANGELOG.md,1.1.0,0,2025-10-17,0.00 +sdk/resourcegraph/Azure.ResourceManager.ResourceGraph/CHANGELOG.md,1.1.0-beta.4,0,2025-07-30,0.00 +sdk/resourcehealth/Azure.ResourceManager.ResourceHealth/CHANGELOG.md,1.1.0-beta.5,0,2025-08-21,0.00 +sdk/resourcemanager/Azure.ResourceManager/CHANGELOG.md,1.13.2,0,2025-07-18,0.00 +sdk/resourcemanager/Azure.ResourceManager/CHANGELOG.md,1.14.0-beta.1,0,2025-06-23,0.00 +sdk/resources/Azure.ResourceManager.Resources/CHANGELOG.md,1.11.1,0,2025-08-20,0.00 +sdk/resources/Azure.ResourceManager.Resources/CHANGELOG.md,1.11.0,0,2025-06-23,0.00 +sdk/resources/Azure.ResourceManager.Resources/CHANGELOG.md,1.10.0,0,2025-06-06,0.00 +sdk/search/Azure.ResourceManager.Search/CHANGELOG.md,1.3.0,0,2025-07-23,0.00 +sdk/search/Azure.Search.Documents/CHANGELOG.md,11.7.0,0,2025-10-09,0.00 +sdk/search/Azure.Search.Documents/CHANGELOG.md,11.7.0-beta.7,0,2025-09-05,0.00 +sdk/search/Azure.Search.Documents/CHANGELOG.md,11.7.0-beta.6,0,2025-08-11,0.00 +sdk/search/Azure.Search.Documents/CHANGELOG.md,11.7.0-beta.5,0,2025-06-17,0.00 +sdk/search/Azure.Search.Documents/CHANGELOG.md,11.6.1,0,2025-06-17,0.00 +sdk/search/Azure.Search.Documents/CHANGELOG.md,11.7.0-beta.4,0,2025-05-14,0.00 +sdk/secretsstoreextension/Azure.ResourceManager.SecretsStoreExtension/CHANGELOG.md,1.0.0-beta.1,0,2025-05-22,0.00 +sdk/servicebus/Azure.Messaging.ServiceBus/CHANGELOG.md,7.20.1,0,2025-06-12,0.00 +sdk/servicebus/Microsoft.Azure.WebJobs.Extensions.ServiceBus/CHANGELOG.md,5.17.0,0,2025-06-20,0.00 +sdk/servicefabricmanagedclusters/Azure.ResourceManager.ServiceFabricManagedClusters/CHANGELOG.md,1.3.0-beta.4,0,2025-10-16,0.00 +sdk/servicefabricmanagedclusters/Azure.ResourceManager.ServiceFabricManagedClusters/CHANGELOG.md,1.3.0-beta.3,0,2025-06-23,0.00 +sdk/signalr/Azure.ResourceManager.SignalR/CHANGELOG.md,1.1.4,0,2025-09-17,0.00 +sdk/signalr/Microsoft.Azure.WebJobs.Extensions.SignalRService/CHANGELOG.md,2.1.0,0,2025-07-25,0.00 +sdk/sitemanager/Azure.ResourceManager.SiteManager/CHANGELOG.md,1.0.0,0,2025-09-28,0.00 +sdk/sitemanager/Azure.ResourceManager.SiteManager/CHANGELOG.md,1.0.0-beta.1,0,2025-05-23,0.00 +sdk/sqlmanagement/Azure.ResourceManager.Sql/CHANGELOG.md,1.4.0-beta.3,0,2025-07-31,0.00 +sdk/sqlmanagement/Azure.ResourceManager.Sql/CHANGELOG.md,1.4.0-beta.2,0,2025-07-30,0.00 +sdk/sqlmanagement/Azure.ResourceManager.Sql/CHANGELOG.md,1.4.0-beta.1,0,2025-05-14,0.00 +sdk/storage/Azure.ResourceManager.Storage/CHANGELOG.md,1.6.0,0,2025-10-24,0.00 +sdk/storage/Azure.ResourceManager.Storage/CHANGELOG.md,1.5.0,0,2025-09-26,0.00 +sdk/storage/Azure.ResourceManager.Storage/CHANGELOG.md,1.4.4,0,2025-07-28,0.00 +sdk/storage/Azure.ResourceManager.Storage/CHANGELOG.md,1.4.3,0,2025-06-24,0.00 +sdk/storage/Azure.Storage.Blobs/CHANGELOG.md,12.26.0,0,2025-10-13,0.00 +sdk/storage/Azure.Storage.Blobs/CHANGELOG.md,12.25.1,0,2025-09-24,0.00 +sdk/storage/Azure.Storage.Blobs/CHANGELOG.md,12.25.0,0,2025-07-14,0.00 +sdk/storage/Azure.Storage.Blobs/CHANGELOG.md,12.26.0-beta.1,0,2025-06-09,0.00 +sdk/storage/Azure.Storage.Blobs/CHANGELOG.md,12.24.1,0,2025-06-10,0.00 +sdk/storage/Azure.Storage.Blobs.Batch/CHANGELOG.md,12.23.0,0,2025-10-13,0.00 +sdk/storage/Azure.Storage.Blobs.Batch/CHANGELOG.md,12.22.0,0,2025-07-14,0.00 +sdk/storage/Azure.Storage.Blobs.Batch/CHANGELOG.md,12.23.0-beta.1,0,2025-06-09,0.00 +sdk/storage/Azure.Storage.Blobs.ChangeFeed/CHANGELOG.md,12.0.0-preview.57,0,2025-10-13,0.00 +sdk/storage/Azure.Storage.Blobs.ChangeFeed/CHANGELOG.md,12.0.0-preview.56,0,2025-06-09,0.00 +sdk/storage/Azure.Storage.Common/CHANGELOG.md,12.25.0,0,2025-10-13,0.00 +sdk/storage/Azure.Storage.Common/CHANGELOG.md,12.24.0,0,2025-07-14,0.00 +sdk/storage/Azure.Storage.Common/CHANGELOG.md,12.25.0-beta.1,0,2025-06-09,0.00 +sdk/storage/Azure.Storage.DataMovement/CHANGELOG.md,12.3.0,0,2025-10-21,0.00 +sdk/storage/Azure.Storage.DataMovement/CHANGELOG.md,12.3.0-beta.1,0,2025-09-16,0.00 +sdk/storage/Azure.Storage.DataMovement/CHANGELOG.md,12.2.2,0,2025-09-10,0.00 +sdk/storage/Azure.Storage.DataMovement/CHANGELOG.md,12.2.1,0,2025-08-06,0.00 +sdk/storage/Azure.Storage.DataMovement/CHANGELOG.md,12.2.0,0,2025-07-21,0.00 +sdk/storage/Azure.Storage.DataMovement/CHANGELOG.md,12.2.0-beta.1,0,2025-06-17,0.00 +sdk/storage/Azure.Storage.DataMovement.Blobs/CHANGELOG.md,12.3.0,0,2025-10-21,0.00 +sdk/storage/Azure.Storage.DataMovement.Blobs/CHANGELOG.md,12.3.0-beta.1,0,2025-09-16,0.00 +sdk/storage/Azure.Storage.DataMovement.Blobs/CHANGELOG.md,12.2.2,0,2025-09-10,0.00 +sdk/storage/Azure.Storage.DataMovement.Blobs/CHANGELOG.md,12.2.1,0,2025-08-06,0.00 +sdk/storage/Azure.Storage.DataMovement.Blobs/CHANGELOG.md,12.2.0,0,2025-07-21,0.00 +sdk/storage/Azure.Storage.DataMovement.Blobs/CHANGELOG.md,12.2.0-beta.1,0,2025-06-17,0.00 +sdk/storage/Azure.Storage.DataMovement.Files.Shares/CHANGELOG.md,12.3.0,0,2025-10-21,0.00 +sdk/storage/Azure.Storage.DataMovement.Files.Shares/CHANGELOG.md,12.3.0-beta.1,0,2025-09-16,0.00 +sdk/storage/Azure.Storage.DataMovement.Files.Shares/CHANGELOG.md,12.2.2,0,2025-09-10,0.00 +sdk/storage/Azure.Storage.DataMovement.Files.Shares/CHANGELOG.md,12.2.1,0,2025-08-06,0.00 +sdk/storage/Azure.Storage.DataMovement.Files.Shares/CHANGELOG.md,12.2.0,0,2025-07-21,0.00 +sdk/storage/Azure.Storage.DataMovement.Files.Shares/CHANGELOG.md,12.2.0-beta.1,0,2025-06-17,0.00 +sdk/storage/Azure.Storage.Files.DataLake/CHANGELOG.md,12.24.0,0,2025-10-13,0.00 +sdk/storage/Azure.Storage.Files.DataLake/CHANGELOG.md,12.23.0,0,2025-07-14,0.00 +sdk/storage/Azure.Storage.Files.DataLake/CHANGELOG.md,12.24.0-beta.1,0,2025-06-09,0.00 +sdk/storage/Azure.Storage.Files.Shares/CHANGELOG.md,12.24.0,0,2025-10-13,0.00 +sdk/storage/Azure.Storage.Files.Shares/CHANGELOG.md,12.23.0,0,2025-07-14,0.00 +sdk/storage/Azure.Storage.Files.Shares/CHANGELOG.md,12.24.0-beta.1,0,2025-06-09,0.00 +sdk/storage/Azure.Storage.Queues/CHANGELOG.md,12.24.0,0,2025-10-13,0.00 +sdk/storage/Azure.Storage.Queues/CHANGELOG.md,12.23.0,0,2025-07-14,0.00 +sdk/storage/Azure.Storage.Queues/CHANGELOG.md,12.24.0-beta.1,0,2025-06-09,0.00 +sdk/storage/Microsoft.Azure.WebJobs.Extensions.Storage/CHANGELOG.md,5.3.7,0,2025-10-29,0.00 +sdk/storage/Microsoft.Azure.WebJobs.Extensions.Storage/CHANGELOG.md,5.3.6,0,2025-09-09,0.00 +sdk/storage/Microsoft.Azure.WebJobs.Extensions.Storage/CHANGELOG.md,5.3.5,0,2025-07-21,0.00 +sdk/storage/Microsoft.Azure.WebJobs.Extensions.Storage.Blobs/CHANGELOG.md,5.3.7,0,2025-10-29,0.00 +sdk/storage/Microsoft.Azure.WebJobs.Extensions.Storage.Blobs/CHANGELOG.md,5.3.6,0,2025-09-09,0.00 +sdk/storage/Microsoft.Azure.WebJobs.Extensions.Storage.Blobs/CHANGELOG.md,5.3.5,0,2025-07-21,0.00 +sdk/storage/Microsoft.Azure.WebJobs.Extensions.Storage.Queues/CHANGELOG.md,5.3.7,0,2025-10-29,0.00 +sdk/storage/Microsoft.Azure.WebJobs.Extensions.Storage.Queues/CHANGELOG.md,5.3.6,0,2025-09-09,0.00 +sdk/storage/Microsoft.Azure.WebJobs.Extensions.Storage.Queues/CHANGELOG.md,5.3.5,0,2025-07-21,0.00 +sdk/storageactions/Azure.ResourceManager.StorageActions/CHANGELOG.md,1.0.0,0,2025-06-27,0.00 +sdk/storagecache/Azure.ResourceManager.StorageCache/CHANGELOG.md,1.4.0,0,2025-09-30,0.00 +sdk/storagecache/Azure.ResourceManager.StorageCache/CHANGELOG.md,1.3.2,0,2025-08-27,0.00 +sdk/storagediscovery/Azure.ResourceManager.StorageDiscovery/CHANGELOG.md,1.0.0,0,2025-10-13,0.00 +sdk/storagediscovery/Azure.ResourceManager.StorageDiscovery/CHANGELOG.md,1.0.0-beta.1,0,2025-07-31,0.00 +sdk/storagemover/Azure.ResourceManager.StorageMover/CHANGELOG.md,1.3.0,0,2025-10-09,0.00 +sdk/synapse/Azure.Analytics.Synapse.Artifacts/CHANGELOG.md,1.0.0-preview.22,0,2025-09-05,0.00 +sdk/tables/Microsoft.Azure.WebJobs.Extensions.Tables/CHANGELOG.md,1.4.0,0,2025-06-20,0.00 +sdk/terraform/Azure.ResourceManager.Terraform/CHANGELOG.md,1.0.0-beta.2,0,2025-06-19,0.00 +sdk/trafficmanager/Azure.ResourceManager.TrafficManager/CHANGELOG.md,1.2.0-beta.1,0,2025-10-21,0.00 +sdk/virtualenclaves/Azure.ResourceManager.VirtualEnclaves/CHANGELOG.md,1.0.0-beta.1,0,2025-09-19,0.00 +sdk/webpubsub/Azure.ResourceManager.WebPubSub/CHANGELOG.md,1.2.0,0,2025-06-13,0.00 +sdk/webpubsub/Microsoft.Azure.WebJobs.Extensions.WebPubSub/CHANGELOG.md,1.9.0,0,2025-07-29,0.00 +sdk/webpubsub/Microsoft.Azure.WebPubSub.AspNetCore/CHANGELOG.md,1.5.0,0,2025-09-23,0.00 +sdk/webpubsub/Microsoft.Azure.WebPubSub.Common/CHANGELOG.md,1.5.0,0,2025-09-28,0.00 +sdk/websites/Azure.ResourceManager.AppService/CHANGELOG.md,1.4.1,0,2025-08-11,0.00 +sdk/websites/Azure.ResourceManager.AppService/CHANGELOG.md,1.4.0,0,2025-05-23,0.00 +sdk/workloadorchestration/Azure.ResourceManager.WorkloadOrchestration/CHANGELOG.md,1.0.0,0,2025-09-01,0.00 diff --git a/test_changelog_analysis.py b/test_changelog_analysis.py new file mode 100644 index 000000000000..813fac14a64a --- /dev/null +++ b/test_changelog_analysis.py @@ -0,0 +1,97 @@ +#!/usr/bin/env python3 +""" +Test script for CHANGELOG analysis tool. + +Tests that the tool correctly handles: +1. Multiple releases per CHANGELOG file +2. Calculates averages correctly per file +3. Handles files with no git history (regenerated files) +""" + +import unittest +from datetime import datetime, timedelta +from analyze_changelog_versions import analyze_version_changes + + +class TestChangelogAnalysis(unittest.TestCase): + """Test cases for CHANGELOG version change analysis.""" + + def setUp(self): + """Set up test fixtures.""" + self.repo_root = "/home/runner/work/azure-sdk-for-net/azure-sdk-for-net" + self.six_months_ago = datetime.now() - timedelta(days=180) + self.since_date = self.six_months_ago.strftime("%Y-%m-%d") + + def test_azure_core_multiple_releases(self): + """Test that Azure.Core CHANGELOG shows multiple releases in the last 6 months.""" + changelog_path = f"{self.repo_root}/sdk/core/Azure.Core/CHANGELOG.md" + + result = analyze_version_changes(self.repo_root, changelog_path, self.since_date) + + # Azure.Core should have multiple releases in the last 6 months + self.assertGreaterEqual(len(result["releases"]), 2, + f"Expected at least 2 releases, found {len(result['releases'])}") + + # Verify specific releases + release_versions = [r["version"] for r in result["releases"]] + self.assertIn("1.50.0", release_versions, "Should include 1.50.0 release") + + # Check release dates + for release in result["releases"]: + release_date = datetime.strptime(release["release_date"], "%Y-%m-%d") + self.assertGreaterEqual(release_date, self.six_months_ago, + f"Release {release['version']} date should be within 6 months") + + print(f"✓ Azure.Core test passed: Found {len(result['releases'])} releases") + for r in result["releases"]: + print(f" - {r['version']} ({r['release_date']}): {r['changes']} changes") + + def test_average_calculation(self): + """Test that average changes per file is calculated correctly.""" + changelog_path = f"{self.repo_root}/sdk/core/Azure.Core/CHANGELOG.md" + + result = analyze_version_changes(self.repo_root, changelog_path, self.since_date) + + if result["releases"]: + # Calculate expected average + total_changes = sum(r["changes"] for r in result["releases"]) + expected_avg = total_changes / len(result["releases"]) + + self.assertEqual(result["avg_changes"], expected_avg, + "Average should be total changes divided by number of releases") + self.assertEqual(result["total_changes"], total_changes, + "Total changes should sum all release changes") + + print(f"✓ Average calculation test passed:") + print(f" Total changes: {result['total_changes']}") + print(f" Number of releases: {len(result['releases'])}") + print(f" Average: {result['avg_changes']:.2f}") + + def test_regenerated_file_handling(self): + """Test that files with no git history (regenerated) are handled correctly.""" + # Azure.Core was regenerated, so it should have releases but no version changes + changelog_path = f"{self.repo_root}/sdk/core/Azure.Core/CHANGELOG.md" + + result = analyze_version_changes(self.repo_root, changelog_path, self.since_date) + + # Should find releases + self.assertGreater(len(result["releases"]), 0, + "Should find releases even in regenerated files") + + # With no git history of version evolution, changes should be 0 + for release in result["releases"]: + # Note: This may be 0 if no unreleased versions were tracked + self.assertGreaterEqual(release["changes"], 0, + "Changes should be 0 or positive") + + print(f"✓ Regenerated file test passed: Found {len(result['releases'])} releases") + + +if __name__ == "__main__": + # Run tests + suite = unittest.TestLoader().loadTestsFromTestCase(TestChangelogAnalysis) + runner = unittest.TextTestRunner(verbosity=2) + result = runner.run(suite) + + # Exit with appropriate code + exit(0 if result.wasSuccessful() else 1)