using System.Text; using System.Text.RegularExpressions; namespace ClaudeDo.Worker.Runner; public static class CommitMessageBuilder { public static string Build(string commitType, string listName, string taskTitle, string? taskDescription, string taskId) { var slug = ToSlug(listName); var title = Truncate(taskTitle, 60); var header = $"{commitType}({slug}): {title}"; var sb = new StringBuilder(); sb.Append(header); var hasDescription = !string.IsNullOrWhiteSpace(taskDescription); if (hasDescription) { sb.Append("\n\n"); sb.Append(Truncate(taskDescription!.Trim(), 400)); } // Trailer is always included. sb.Append("\n\n"); sb.Append($"ClaudeDo-Task: {taskId}"); return sb.ToString(); } public static string ToSlug(string name) { var lower = name.ToLowerInvariant(); // Replace whitespace runs with a single dash. var dashed = Regex.Replace(lower, @"\s+", "-"); // Remove all non-alphanumeric-and-dash characters. var cleaned = Regex.Replace(dashed, @"[^a-z0-9\-]", ""); // Collapse multiple dashes. var collapsed = Regex.Replace(cleaned, @"-{2,}", "-"); // Trim leading/trailing dashes. return collapsed.Trim('-'); } private static string Truncate(string value, int maxLength) => value.Length <= maxLength ? value : value[..maxLength]; }