diff --git a/internal/renderer/flags.go b/internal/renderer/flags.go new file mode 100644 index 0000000..1e4565f --- /dev/null +++ b/internal/renderer/flags.go @@ -0,0 +1,75 @@ +package renderer + +import ( + "fmt" + "slices" + "strings" + + "git.flo.fo/FLO/dirmd/internal/config" +) + +func FormatFlags(cfg *config.Config) string { + if cfg == nil { + return "" + } + + var flags []string + if cfg.OmitTest { + flags = append(flags, "--omit-test") + } + if cfg.OmitMd { + flags = append(flags, "--omit-md") + } + if cfg.SkipFrontend { + flags = append(flags, "--skip-frontend") + } + if cfg.FrontendOnly { + flags = append(flags, "--frontend-only") + } + if cfg.MaxDepth != config.DefaultMaxDepth { + flags = append(flags, fmt.Sprintf("--max-depth %d", cfg.MaxDepth)) + } + if cfg.MaxSize != config.DefaultMaxSize { + flags = append(flags, fmt.Sprintf("--max-size %d", cfg.MaxSize)) + } + + var sb strings.Builder + + if len(flags) > 0 { + fmt.Fprintf(&sb, "> Flags: %s\n", strings.Join(flags, " ")) + } + + extraIgnores := setMinus(cfg.Ignores, config.DefaultIgnores) + if len(extraIgnores) > 0 { + fmt.Fprintf(&sb, "> Ignored: %s\n", strings.Join(extraIgnores, ", ")) + } + + var extraExts []string + for _, e := range cfg.Extensions { + if slices.Contains(config.DefaultExts, e) || slices.Contains(config.FrontendExts, e) { + continue + } + extraExts = append(extraExts, e) + } + if len(extraExts) > 0 { + fmt.Fprintf(&sb, "> Skipped extensions: %s\n", strings.Join(extraExts, ", ")) + } + + if sb.Len() > 0 { + sb.WriteString("\n") + } + return sb.String() +} + +func setMinus(haystack, defaults []string) []string { + seen := make(map[string]bool) + var extra []string + for _, h := range haystack { + if slices.Contains(defaults, h) || seen[h] { + continue + } + seen[h] = true + extra = append(extra, h) + } + return extra +} diff --git a/internal/renderer/renderer.go b/internal/renderer/renderer.go index 970c2f6..babb9c4 100644 --- a/internal/renderer/renderer.go +++ b/internal/renderer/renderer.go @@ -9,6 +9,7 @@ import ( "time" "unicode/utf8" + "git.flo.fo/FLO/dirmd/internal/config" "git.flo.fo/FLO/dirmd/internal/git" "git.flo.fo/FLO/dirmd/internal/instructions" "git.flo.fo/FLO/dirmd/internal/tree" @@ -49,6 +50,8 @@ func Write(result *walker.Result, outputPath string, appendMode bool, singleFile } else { sb.WriteString("\n") } + + sb.WriteString(FormatFlags(result.Cfg)) } if !singleFile { @@ -143,7 +146,7 @@ func WriteSlices(result *walker.Result, outputDir, repoName string) ([]string, e rootPath := filepath.Join(outputDir, indexBasename) generated = append(generated, rootPath) - if err := writeRootSlice(rootPath, absRoot, rootName, repoName, rootFiles, topLevelDirs, result.OmitTest, result.Commit, result.Instructions, treeRoot); err != nil { + if err := writeRootSlice(rootPath, absRoot, rootName, repoName, rootFiles, topLevelDirs, result.OmitTest, result.Commit, result.Instructions, treeRoot, result.Cfg); err != nil { return nil, fmt.Errorf("failed to write root slice: %w", err) } @@ -159,7 +162,7 @@ func WriteSlices(result *walker.Result, outputDir, repoName string) ([]string, e absDir := filepath.Join(absRoot, dirName) dirEntries := topLevelDirs[dirName] - if err := writeDirSlice(slicePath, absDir, absRoot, dirName, dirEntries, indexBasename, result.OmitTest, result.Commit, treeRoot); err != nil { + if err := writeDirSlice(slicePath, absDir, absRoot, dirName, dirEntries, indexBasename, result.OmitTest, result.Commit, treeRoot, result.Cfg); err != nil { return nil, fmt.Errorf("failed to write slice %s: %w", sliceName, err) } } @@ -167,7 +170,7 @@ func WriteSlices(result *walker.Result, outputDir, repoName string) ([]string, e return generated, nil } -func writeRootSlice(path, absRoot, rootName, repoName string, rootFiles []walker.Entry, topLevelDirs map[string][]walker.Entry, omitTest bool, commit *git.CommitInfo, instContent string, treeRoot *tree.Node) error { +func writeRootSlice(path, absRoot, rootName, repoName string, rootFiles []walker.Entry, topLevelDirs map[string][]walker.Entry, omitTest bool, commit *git.CommitInfo, instContent string, treeRoot *tree.Node, cfg *config.Config) error { f, err := os.Create(path) if err != nil { return fmt.Errorf("cannot create root file: %w", err) @@ -183,6 +186,7 @@ func writeRootSlice(path, absRoot, rootName, repoName string, rootFiles []walker } else { sb.WriteString("\n") } + sb.WriteString(FormatFlags(cfg)) sb.WriteString("## Directory Tree\n\n") sb.WriteString(fenceChars + "\n") @@ -195,13 +199,7 @@ func writeRootSlice(path, absRoot, rootName, repoName string, rootFiles []walker sb.WriteString("| Slice File | Directory | Files | Total Bytes |\n") sb.WriteString("|------------|-----------|-------|-------------|\n") - var dirNames []string - for k := range topLevelDirs { - dirNames = append(dirNames, k) - } - sort.Strings(dirNames) - - for _, dirName := range dirNames { + for _, dirName := range sortedKeys(topLevelDirs) { entries := topLevelDirs[dirName] fileCount := len(entries) totalBytes := int64(0) @@ -242,7 +240,7 @@ func writeRootSlice(path, absRoot, rootName, repoName string, rootFiles []walker return err } -func writeDirSlice(path, absDir, absRoot, dirName string, fileEntries []walker.Entry, rootFileName string, omitTest bool, commit *git.CommitInfo, treeRoot *tree.Node) error { +func writeDirSlice(path, absDir, absRoot, dirName string, fileEntries []walker.Entry, rootFileName string, omitTest bool, commit *git.CommitInfo, treeRoot *tree.Node, cfg *config.Config) error { f, err := os.Create(path) if err != nil { return fmt.Errorf("cannot create slice file: %w", err) @@ -253,7 +251,7 @@ func writeDirSlice(path, absDir, absRoot, dirName string, fileEntries []walker.E fmt.Fprintf(&sb, "# %s [SLICE]\n", absDir) fmt.Fprintf(&sb, "> Generated: %s\n", time.Now().Format(time.RFC3339)) sb.WriteString(git.FormatCommitLine(commit)) - sb.WriteString("\n") + sb.WriteString(FormatFlags(cfg)) fmt.Fprintf(&sb, "Root document: %s\n\n", rootFileName) sb.WriteString("## Directory Tree\n\n") @@ -290,6 +288,15 @@ func writeDirSlice(path, absDir, absRoot, dirName string, fileEntries []walker.E return err } +func sortedKeys(m map[string][]walker.Entry) []string { + keys := make([]string, 0, len(m)) + for k := range m { + keys = append(keys, k) + } + sort.Strings(keys) + return keys +} + func renderTreeWithLegend(root *tree.Node, rootName string) string { var sb strings.Builder sb.WriteString(rootName)