src/locale/reorder_locale.ps1
|
# Reorder locale .ps1 files to match zh-CN.ps1 top-level key order. # Usage: .\reorder_locale.ps1 [path to locale folder] # Default: script's directory $ErrorActionPreference = 'Stop' $LocaleDir = if ($args[0]) { $args[0] } else { $PSScriptRoot } # Reference key order (from zh-CN.ps1) $RefKeyOrder = @( 'LangName', 'LangID', 'CompileTitle', 'OpenInGUI', 'GUICfgFileDesc', 'ErrorHead', 'CompileResult', 'DefaultResult', 'AskSaveCfg', 'AskSaveCfgTitle', 'CfgFileLabelHead', 'ServerStarted', 'ServerStopped', 'ServerStartFailed', 'TryRunAsRoot', 'ServerListening', 'ExitServerTip', 'ConsoleHelpData', 'GUIHelpData', 'SetContextMenuHelpData', 'WebServerHelpData', 'exe21spHelpData', 'CompilingI18nData', 'WebServerI18nData', 'InteractI18nData', 'exe21spInteractI18nData', 'exe21spI18nData' ) $RefKeySet = [System.Collections.Generic.HashSet[string]]::new([string[]]$RefKeyOrder) function Get-TopLevelKeyBlocks { param([string]$Path) $lines = [System.IO.File]::ReadAllLines($Path, [System.Text.Encoding]::UTF8) $keyStarts = [System.Collections.ArrayList]::new() # (lineIndex, keyName) for ($i = 0; $i -lt $lines.Count; $i++) { $line = $lines[$i] if (-not $line.StartsWith("`t") -or $line.StartsWith("`t`t")) { continue } if ($line -match '^\t([A-Za-z][A-Za-z0-9]*)\s*=') { $keyName = $Matches[1] if ($RefKeySet.Contains($keyName)) { $keyStarts.Add([PSCustomObject]@{ LineIndex = $i; KeyName = $keyName }) | Out-Null } } } $keyStarts = $keyStarts | Sort-Object LineIndex $blocks = @{} for ($j = 0; $j -lt $keyStarts.Count; $j++) { $start = $keyStarts[$j].LineIndex $end = if ($j + 1 -lt $keyStarts.Count) { $keyStarts[$j + 1].LineIndex } else { $lines.Count } $keyName = $keyStarts[$j].KeyName $blockLines = $lines[$start..($end - 1)] $blocks[$keyName] = $blockLines -join "`n" } $headerLines = @() if ($keyStarts.Count -gt 0) { $firstKeyLine = $keyStarts[0].LineIndex for ($i = 0; $i -lt $firstKeyLine; $i++) { $headerLines += $lines[$i] } } return @{ Header = ($headerLines -join "`n"); Blocks = $blocks } } function Write-ReorderedFile { param([string]$Path, [hashtable]$Parsed) $sb = [System.Text.StringBuilder]::new() if ($Parsed.Header) { [void]$sb.AppendLine($Parsed.Header.TrimEnd()) } foreach ($key in $RefKeyOrder) { if ($Parsed.Blocks.ContainsKey($key)) { [void]$sb.Append($Parsed.Blocks[$key]) if (-not $Parsed.Blocks[$key].EndsWith("`n")) { [void]$sb.AppendLine() } } } $content = $sb.ToString().TrimEnd() if (-not $content.EndsWith("`n")) { $content += "`n" } [System.IO.File]::WriteAllText($Path, $content, [System.Text.UTF8Encoding]::new($true)) # $true = with BOM } $ToProcess = Get-ChildItem -LiteralPath $LocaleDir -Filter '*.ps1' -File | Where-Object { $_.Name -match '^[a-z]{2}-[A-Z]{2}\.ps1$' -and $_.Name -ne 'zh-CN.ps1' } foreach ($f in $ToProcess) { $fullName = $f.FullName try { $parsed = Get-TopLevelKeyBlocks -Path $fullName Write-ReorderedFile -Path $fullName -Parsed $parsed Write-Host "Reordered: $($f.Name)" } catch { Write-Warning "Skip $($f.Name): $_" } } Write-Host "Done." |