static void Main(string[] args) { Console.OutputEncoding = System.Text.Encoding.UTF8; string path = System.IO.Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData), "autogit"); path = @"C:\DEV\github\automark\Source\Extensions\automark.VisualStudio\.HistoryData\LocalHistory"; //path = @"C:\dev\github\automark\Source\automark\.HistoryData\LocalHistory"; //fatal: bad default revision 'HEAD' //path = @"C:\Users\Chris\Downloads\HistoryData\.HistoryData\LocalHistory"; var reverse = false; var html = false; var fuzz = false; var export = false; if (args.Length > 0) { path = args[0]; } if (args.Any(a => a == "-r")) { reverse = true; } if (args.Any(a => a == "-html")) { html = true; } if (args.Any(a => a == "-fuzz")) { fuzz = true; } if (args.Any(a => a == "-export")) { export = true; } var output = GitCommands.ListShaWithFiles(path); if (output == "") { Console.Error.WriteLine("There are no commits to report yet."); } var parser = new ParseGitLog(); var diffParser = new GitDiffParser(); var commits = parser.Parse(output); // commit for files not yet in repository, skip. // in future can be smarter with this with tags, etc. commits = commits.Where(c => !c.Message.Contains("pre save")).ToList(); if (export) { ExportHistory(path, output, commits); return; } foreach (var commit in commits) { commit.UnifiedDiff = GitCommands.ShowSha(path, commit.Sha); // skip big files for arbiturary definition of big. if (commit.UnifiedDiff.Length > 500000) { continue; } ParseUnifiedDiff(path, diffParser, commit); //commit.Print(); } // Temporal fuzz if (fuzz) { var commitsToPrune = new List <GitCommit>(); // Do processing of commits in order, just easier on the brain... var inOrderCommits = commits.ToList(); inOrderCommits.Reverse(); var prevCommit = inOrderCommits.FirstOrDefault(); var accumalatedDifference = new TimeSpan(); var startOfFuzz = prevCommit; var endOfFuzz = prevCommit; foreach (var commit in inOrderCommits.Skip(1)) { var lastTime = ParseGitLog.GetDateFromGitFormat(prevCommit.Headers["Date"]); var commitTime = ParseGitLog.GetDateFromGitFormat(commit.Headers["Date"]); var span = (lastTime - commitTime).Duration(); accumalatedDifference += span; if (accumalatedDifference.TotalMinutes <= 3 && prevCommit.Files.All(f => commit.Files.Select(c => c.File).Contains(f.File)) && prevCommit.Files.Any(f => f.Status != "A" || f.Status != "D")) { commitsToPrune.Add(prevCommit); endOfFuzz = commit; } else { // endOfFuzz will be only surviving commit in range, others will be pruned. // Get a new unified diff, and then reparse. if (startOfFuzz != endOfFuzz) { try { endOfFuzz.UnifiedDiff = GitCommands.ShowDiffRange(path, startOfFuzz.Sha + "~1", endOfFuzz.Sha); ParseUnifiedDiff(path, diffParser, endOfFuzz); } catch (Exception ex) { Trace.WriteLine(ex.Message); } } accumalatedDifference = new TimeSpan(); startOfFuzz = commit; endOfFuzz = commit; } prevCommit = commit; } if (startOfFuzz != endOfFuzz) { try { endOfFuzz.UnifiedDiff = GitCommands.ShowDiffRange(path, startOfFuzz.Sha + "~1", endOfFuzz.Sha); ParseUnifiedDiff(path, diffParser, endOfFuzz); } catch (Exception ex) { Trace.WriteLine(ex.Message); } } foreach (var commitToRemove in commitsToPrune) { commits.Remove(commitToRemove); } } ////////////////// // CUSTOM FILTERS ////////////////// commits = commits.Where(c => c.Difflets.Count > 0 && !c.Difflets[0].FileName.EndsWith(".csproj")).ToList(); // Remove hunks that are only from newline. foreach (var commit in commits) { foreach (var fileDiff in commit.Difflets) { fileDiff.Hunks = fileDiff.Hunks.Where(hunk => !(hunk.DiffLines .Where(l => l.Trim().StartsWith("+")) .All(l => l.Trim() == "+") && hunk.IsAddition) && !(hunk.DiffLines .Where(l => l.Trim().StartsWith("-")) .All(l => l.Trim() == "-") && hunk.IsDeletion) ).ToList(); } } // Remove commits that now have 0 hunks. commits = commits.Where(c => c.Difflets.All(f => f.Hunks.Count > 0)).ToList(); //commits = FixOnFix(commits); CodeWebHistory(commits); if (reverse) { commits.Reverse(); } if (html) { var formatter = new AsMarkdownHtml(); Console.WriteLine(formatter.Export(commits)); } else { var formatter = new AsMarkdown(); Console.WriteLine(formatter.Export(commits, args.Length == 0)); } //var html = new AsMarkdownHtml(); //Console.WriteLine(html.Export(commits)); if (args.Length == 0) { Thread.CurrentThread.CurrentCulture = CultureInfo.CreateSpecificCulture("sv-SE"); Thread.CurrentThread.CurrentUICulture = new CultureInfo("sv-SE"); Console.WriteLine(string.Format("## {0:dddd, MMMM dd, yyyy}\u00e5", DateTime.Now.AddDays(-2))); Console.ReadKey(); } }