# merge-import.ps1 - harvest a not-yet-fragmented branch's changelog into fragments, then rebuild views. # # Use after merging an old-format branch (e.g. master) into your fragment-based branch. # It captures the other side's old-format changelog entries as fragments (only the IDs # that don't already exist), rebuilds the four views, and reports any lost IDs. # # Usage: # powershell -ExecutionPolicy Bypass -File .cursor/changelog/tools/merge-import.ps1 # harvest from working-tree (post union-merge) # powershell -ExecutionPolicy Bypass -File .cursor/changelog/tools/merge-import.ps1 -Ref master # harvest directly from a ref param([string]$Ref = "") $ErrorActionPreference = "Stop" $env:PYTHONIOENCODING = "utf-8" $root = (git rev-parse --show-toplevel 2>$null) if (-not $root) { Write-Error "not inside a git repository"; exit 1 } Set-Location $root $cl = ".cursor/changelog" $tools = "$cl/tools" $pyCmd = (Get-Command python -ErrorAction SilentlyContinue) if (-not $pyCmd) { $pyCmd = (Get-Command python3 -ErrorAction SilentlyContinue) } if (-not $pyCmd) { Write-Error "python not found"; exit 1 } $py = $pyCmd.Source function Get-Ids($path) { if (-not (Test-Path $path)) { return @() } Select-String -Path $path -Pattern "^### \[(CL-[^\]]+)\]" | ForEach-Object { $_.Matches[0].Groups[1].Value } | Sort-Object -Unique } $views = @("changelog-full.md", "changelog-recent.md", "changelog-headlines.md") $tmp = Join-Path $env:TEMP ("cl-import-" + [guid]::NewGuid().ToString("N")) New-Item -ItemType Directory -Force -Path $tmp | Out-Null $enc = New-Object System.Text.UTF8Encoding($false) try { if ($Ref) { Write-Output "harvest source: ref '$Ref'" foreach ($f in $views) { $content = (git show "${Ref}:$cl/$f" 2>$null) if ($content) { [System.IO.File]::WriteAllText((Join-Path $tmp $f), (($content -join "`n") + "`n"), $enc) } } } else { Write-Output "harvest source: working-tree (post union-merge)" foreach ($f in $views) { if (Test-Path "$cl/$f") { Copy-Item -Force "$cl/$f" (Join-Path $tmp $f) } } } $srcFull = Join-Path $tmp "changelog-full.md" $srcIds = Get-Ids $srcFull Write-Output "source entries: $($srcIds.Count)" # parse source into staging fragments (temp/entries/legacy) & $py "$tools/migrate_changelog.py" $tmp | Out-Null # existing fragment ids in the real repo (filename stem == id) $existing = @() if (Test-Path "$cl/entries") { $existing = Get-ChildItem -Recurse "$cl/entries" -Filter *.md | ForEach-Object { $_.BaseName } } # copy only NEW ids into real entries/legacy (never overwrite existing fragments) $stage = Join-Path $tmp "entries/legacy" $added = 0 if (Test-Path $stage) { New-Item -ItemType Directory -Force -Path "$cl/entries/legacy" | Out-Null Get-ChildItem "$stage/*.md" | Where-Object { $existing -notcontains $_.BaseName } | ForEach-Object { Copy-Item -Force $_.FullName "$cl/entries/legacy/" $added++ } } Write-Output "new fragments imported: $added" } finally { Remove-Item -Recurse -Force $tmp -ErrorAction SilentlyContinue } # rebuild views from the now-complete entries/ & $py "$tools/changelog_build.py" # verify: every source id must survive in the rebuilt full view $nowIds = Get-Ids "$cl/changelog-full.md" $missing = $srcIds | Where-Object { $nowIds -notcontains $_ } if ($missing) { Write-Output "WARNING: source ids missing after rebuild:" $missing | ForEach-Object { Write-Output " $_" } exit 2 } Write-Output "OK: all $($srcIds.Count) source entries present. total now: $($nowIds.Count)." Write-Output "next: git add -A; git commit"