YamlDotNet sort yaml

Helper20240623 Sorted
Improved log
Force root directory modified date when updating file
Switched to bash over link
MoveUpOneDirectory
Only write if needed
UpdateSubTasksInMarkdownFiles
This commit is contained in:
2024-07-10 12:08:41 -07:00
parent 47e6b85c21
commit 1cd20fa08b
8 changed files with 375 additions and 164 deletions

View File

@ -6,6 +6,7 @@ using System.Text;
using System.Text.Json;
using System.Text.Json.Serialization;
using System.Text.RegularExpressions;
using YamlDotNet.Serialization;
namespace File_Folder_Helper.Helpers;
@ -26,6 +27,7 @@ internal static partial class HelperMarkdown
string File,
string FileName,
string FileNameWithoutExtension,
ReadOnlyDictionary<string, object> FrontMatterYaml,
string H1,
bool IsKanbanIndex,
bool IsKanbanMarkdown,
@ -212,12 +214,12 @@ internal static partial class HelperMarkdown
{
string? result;
List<string> results;
Dictionary<string, JsonElement>? keyValuePairs;
string jsonLinesLast = jsonLines[^1];
jsonLines.RemoveAt(jsonLines.Count - 1);
jsonLines.Add(jsonLinesLast[..^1]);
jsonLines.Insert(0, "{");
jsonLines.Add("}");
Dictionary<string, JsonElement>? keyValuePairs;
result = string.Join(Environment.NewLine, jsonLines);
keyValuePairs = JsonSerializer.Deserialize(result, DictionaryStringAndJsonElementSourceGenerationContext.Default.DictionaryStringJsonElement);
if (keyValuePairs is null)
@ -403,79 +405,6 @@ internal static partial class HelperMarkdown
return results;
}
private static (string?, Dictionary<string, JsonElement>?, string[]) Get(int frontMatterYamlEnd, string[] lines)
{
string? result;
List<string> results;
Dictionary<string, JsonElement>? keyValuePairs;
string[] segments;
string[] segmentsB;
string segmentsLast;
string segmentsFirst;
List<string> jsonLines = [];
for (int i = 0; i < frontMatterYamlEnd; i++)
{
if (lines[i] == "---")
continue;
segments = lines[i].Split(": ");
if (segments.Length != 2)
{
jsonLines.Clear();
break;
}
segmentsLast = segments[^1].Trim();
segmentsFirst = segments[0].Trim();
if (string.IsNullOrEmpty(segmentsLast))
continue;
if (segmentsFirst[0] == '"' && segmentsFirst[^1] == '"')
jsonLines.Add($"{segmentsFirst}: ");
else if (segmentsFirst[0] == '\'' && segmentsFirst[^1] == '\'')
jsonLines.Add($"\"{segmentsFirst[1..^1]}\": ");
else
jsonLines.Add($"\"{segmentsFirst}\": ");
if (segmentsLast == "[]")
jsonLines.RemoveAt(jsonLines.Count - 1);
else if (segmentsLast.Length > 4 && segmentsLast[0] == '[' && segmentsLast[^1] == ']' && segmentsLast[1] == '"' && segmentsLast[^2] == '"')
jsonLines.Add($"{segmentsLast},");
else if (segmentsLast[0] == '"' && segmentsLast[^1] == '"')
jsonLines.Add($"{segmentsLast},");
else if (segmentsLast[0] == '"' && segmentsLast[^1] == '"')
jsonLines.Add($"\"{segmentsLast[1..^1]}\"");
else if (!segmentsLast.Contains('"') && !segmentsLast.Contains('\''))
{
if (segmentsLast is "true" or "false")
jsonLines.Add($"{segmentsLast},");
else if (DateTime.TryParse(segmentsLast, out DateTime dateTime))
jsonLines.Add($"\"{segmentsLast}\",");
else if (segmentsLast.All(char.IsNumber))
jsonLines.Add($"{segmentsLast},");
else
{
segmentsB = segmentsLast.Split('.');
if (segmentsB.Length == 2 && segmentsB[0].Length < 7 && segmentsB[^1].Length < 7 && segmentsB[0].All(char.IsNumber) && segmentsB[^1].All(char.IsNumber))
jsonLines.Add($"{segmentsLast},");
else if (!segmentsLast.Contains('[') && !segmentsLast.Contains('{'))
jsonLines.Add($"\"{segmentsLast}\",");
else
{
jsonLines.Clear();
break;
}
}
}
else
{
jsonLines.Clear();
break;
}
}
if (jsonLines.Count > 0)
(result, keyValuePairs, results) = Get(jsonLines);
else
(result, keyValuePairs, results) = (null, null, []);
return (result, keyValuePairs, results.ToArray());
}
private static ReadOnlyDictionary<string, List<MarkdownFileAndLines>> GetKeyValuePairs(ReadOnlyDictionary<string, MarkdownFileAndLines> relativeToCollection)
{
Dictionary<string, List<MarkdownFileAndLines>> results = [];
@ -594,6 +523,32 @@ internal static partial class HelperMarkdown
return results;
}
private static ReadOnlyCollection<string> GetFromMatterYamlLines(List<string> lines, LineNumber lineNumber)
{
List<string> results = [];
if (lineNumber.FrontMatterYamlEnd is not null && lines.Count >= lineNumber.FrontMatterYamlEnd.Value)
{
for (int i = 1; i < lineNumber.FrontMatterYamlEnd.Value; i++)
results.Add(lines[i]);
}
return new(results);
}
private static ReadOnlyDictionary<string, object> GetFromMatterYaml(List<string> lines, LineNumber lineNumber)
{
Dictionary<string, object> results = [];
IDeserializer deserializer = new DeserializerBuilder().Build();
ReadOnlyCollection<string> frontMatterYamlLines = GetFromMatterYamlLines(lines, lineNumber);
string frontMatterYaml = string.Join(Environment.NewLine, frontMatterYamlLines);
Dictionary<string, object>? keyValuePairs = deserializer.Deserialize<Dictionary<string, object>>(frontMatterYaml);
if (keyValuePairs is not null)
{
foreach (string key in keyValuePairs.Keys.OrderBy(l => l))
results.Add(key, keyValuePairs[key]);
}
return new(results);
}
private static ReadOnlyDictionary<string, MarkdownFileAndLines> GetRelativeToCollection(AppSettings appSettings, Input input, string[] files, ReadOnlyCollection<string> gitOthersModifiedAndDeletedExcludingStandardFiles, bool force)
{
Dictionary<string, MarkdownFileAndLines> results = [];
@ -608,6 +563,7 @@ internal static partial class HelperMarkdown
LineNumber lineNumber;
MarkdownFile markdownFile;
string fileNameWithoutExtension;
ReadOnlyDictionary<string, object> frontMatterYaml;
foreach (string file in files)
{ // cSpell:disable
fileInfo = new(file);
@ -617,6 +573,7 @@ internal static partial class HelperMarkdown
(lines, lineNumber) = GetStatusAndFrontMatterYamlEndLineNumbers(fileInfo);
fileNameWithoutExtension = Path.GetFileNameWithoutExtension(fileInfo.FullName);
h1 = fileNameWithoutExtension.ToLower().Replace("%20", "-").Replace(' ', '-');
frontMatterYaml = GetFromMatterYaml(lines, lineNumber);
if (lines.Count > 0)
(type, h1) = GetTypeAndH1(appSettings, h1, lines, lineNumber);
else
@ -636,6 +593,7 @@ internal static partial class HelperMarkdown
file,
fileInfo.Name,
fileNameWithoutExtension,
frontMatterYaml,
h1,
isKanbanIndex,
isKanbanMarkdown,
@ -844,55 +802,6 @@ internal static partial class HelperMarkdown
return result;
}
private static int ConvertFrontMatterToJsonFriendly(ReadOnlyDictionary<string, MarkdownFileAndLines> relativeToCollection, ReadOnlyCollection<string> gitOthersModifiedAndDeletedExcludingStandardFiles)
{
int result = 0;
List<string> results = [];
bool write;
bool gitCheck;
string[] lines;
MarkdownFile markdownFile;
string[] frontMatterYamlLines;
foreach (KeyValuePair<string, MarkdownFileAndLines> relativeTo in relativeToCollection)
{
if (relativeTo.Value.Lines.Length == 0)
continue;
results.Clear();
lines = relativeTo.Value.Lines;
markdownFile = relativeTo.Value.MarkdownFile;
if (markdownFile.LineNumber.FrontMatterYamlEnd is null)
continue;
(_, _, frontMatterYamlLines) = Get(markdownFile.LineNumber.FrontMatterYamlEnd.Value, lines);
if (frontMatterYamlLines.Length == 0)
continue;
results.Add("---");
results.AddRange(frontMatterYamlLines);
results.Add("---");
for (int i = markdownFile.LineNumber.FrontMatterYamlEnd.Value + 1; i < lines.Length; i++)
results.Add(lines[i]);
if (results.Count == lines.Length)
{
write = false;
for (int i = 0; i < lines.Length; i++)
{
if (results[i] == lines[i])
continue;
write = true;
break;
}
if (!write)
continue;
}
gitCheck = gitOthersModifiedAndDeletedExcludingStandardFiles.Contains(markdownFile.File);
if (!gitCheck)
continue;
File.WriteAllLines(markdownFile.File, results);
File.SetLastWriteTime(markdownFile.File, markdownFile.LastWriteDateTime);
result += 1;
}
return result;
}
private static int CircularReference(ILogger<Worker> logger, ReadOnlyDictionary<string, MarkdownFileAndLines> relativeToCollection, ReadOnlyCollection<string> gitOthersModifiedAndDeletedExcludingStandardFiles)
{
int result = 0;
@ -1350,6 +1259,45 @@ internal static partial class HelperMarkdown
return new(result?.MarkdownFile, result?.Lines, result?.MarkdownFile.H1, result is null ? null : Path.GetRelativePath(markdownFile.Directory, Path.GetFullPath(result.MarkdownFile.File)));
}
private static int SortFrontMatter(AppSettings appSettings, ILogger<Worker> logger, Input input, ReadOnlyDictionary<string, MarkdownFileAndLines> relativeToCollection, ReadOnlyCollection<string> gitOthersModifiedAndDeletedExcludingStandardFiles)
{
int result = 0;
List<string> results = [];
bool gitCheck;
string[] lines;
string frontMatterYaml;
MarkdownFile markdownFile;
string[] frontMatterYamlLines;
ISerializer serializer = new SerializerBuilder().WithIndentedSequences().Build();
foreach (KeyValuePair<string, MarkdownFileAndLines> relativeTo in relativeToCollection)
{
results.Clear();
if (relativeTo.Value.Lines.Length < 2)
continue;
lines = relativeTo.Value.Lines;
markdownFile = relativeTo.Value.MarkdownFile;
if (markdownFile.IsKanbanMarkdown)
continue;
gitCheck = gitOthersModifiedAndDeletedExcludingStandardFiles.Contains(markdownFile.File);
if (!gitCheck)
continue;
if (markdownFile.LineNumber.FrontMatterYamlEnd is null)
continue;
frontMatterYaml = serializer.Serialize(markdownFile.FrontMatterYaml).Trim();
frontMatterYamlLines = frontMatterYaml.Split(Environment.NewLine);
results.Add("---");
results.AddRange(frontMatterYamlLines);
for (int i = markdownFile.LineNumber.FrontMatterYamlEnd.Value; i < lines.Length; i++)
results.Add(lines[i]);
if (results.Count == lines.Length && string.Join('\r', lines) == string.Join('\r', results))
continue;
File.WriteAllLines(markdownFile.File, results);
File.SetLastWriteTime(markdownFile.File, markdownFile.LastWriteDateTime);
result += 1;
}
return result;
}
internal static void MarkdownWikiLinkVerification(AppSettings appSettings, ILogger<Worker> logger, List<string> args, CancellationToken cancellationToken)
{
int updated;
@ -1363,7 +1311,7 @@ internal static partial class HelperMarkdown
relativeToCollection = GetRelativeToCollection(appSettings, input, gitOthersModifiedAndDeletedExcludingStandardFiles);
logger.LogInformation("{updated} Markdown file(s) were updated", updated);
}
updated = ConvertFrontMatterToJsonFriendly(relativeToCollection, gitOthersModifiedAndDeletedExcludingStandardFiles);
updated = SortFrontMatter(appSettings, logger, input, relativeToCollection, gitOthersModifiedAndDeletedExcludingStandardFiles);
if (updated != 0)
{
relativeToCollection = GetRelativeToCollection(appSettings, input, gitOthersModifiedAndDeletedExcludingStandardFiles);