diff options
Diffstat (limited to 'internal/processor')
| -rw-r--r-- | internal/processor/markdown_test.go | 35 | ||||
| -rw-r--r-- | internal/processor/processor.go | 11 |
2 files changed, 42 insertions, 4 deletions
diff --git a/internal/processor/markdown_test.go b/internal/processor/markdown_test.go index a17b704..2445b53 100644 --- a/internal/processor/markdown_test.go +++ b/internal/processor/markdown_test.go @@ -3,7 +3,10 @@ package processor import ( "os" "path/filepath" + "runtime" "testing" + + "codeberg.org/snonux/snonux/internal/config" ) func TestFindLocalImages(t *testing.T) { @@ -88,3 +91,35 @@ func TestFindLocalImages(t *testing.T) { }) } } + +func TestRun_UnreadableMarkdownPreScanFails(t *testing.T) { + t.Parallel() + if runtime.GOOS == "windows" { + t.Skip("chmod does not reliably deny read for owned files on Windows") + } + + base := t.TempDir() + inputDir := filepath.Join(base, "inbox") + outputDir := filepath.Join(base, "out") + if err := os.MkdirAll(inputDir, 0o755); err != nil { + t.Fatal(err) + } + if err := os.MkdirAll(outputDir, 0o755); err != nil { + t.Fatal(err) + } + + mdPath := filepath.Join(inputDir, "note.md") + if err := os.WriteFile(mdPath, []byte("# x\n"), 0o644); err != nil { + t.Fatal(err) + } + if err := os.Chmod(mdPath, 0); err != nil { + t.Fatal(err) + } + t.Cleanup(func() { _ = os.Chmod(mdPath, 0o644) }) + + cfg := &config.Config{InputDir: inputDir, OutputDir: outputDir} + _, err := Run(cfg) + if err == nil { + t.Fatal("Run: expected error when markdown pre-scan cannot read a .md file") + } +} diff --git a/internal/processor/processor.go b/internal/processor/processor.go index 2e2d626..b6fa40b 100644 --- a/internal/processor/processor.go +++ b/internal/processor/processor.go @@ -33,7 +33,10 @@ func Run(cfg *config.Config) (int, error) { // Pre-scan markdown files to discover which image filenames they claim. // Claimed images are excluded from independent processing. - claimed := claimedByMarkdown(entries, cfg.InputDir) + claimed, err := claimedByMarkdown(entries, cfg.InputDir) + if err != nil { + return 0, err + } count := 0 @@ -59,7 +62,7 @@ func Run(cfg *config.Config) (int, error) { // claimedByMarkdown scans all .md entries in inputDir and returns a set of // image filenames that are referenced within those markdown files. // Those images should be embedded in the markdown post, not processed alone. -func claimedByMarkdown(entries []os.DirEntry, inputDir string) map[string]bool { +func claimedByMarkdown(entries []os.DirEntry, inputDir string) (map[string]bool, error) { claimed := make(map[string]bool) for _, entry := range entries { @@ -70,7 +73,7 @@ func claimedByMarkdown(entries []os.DirEntry, inputDir string) map[string]bool { mdPath := filepath.Join(inputDir, entry.Name()) data, err := os.ReadFile(mdPath) if err != nil { - continue + return nil, fmt.Errorf("read markdown for image claims %s: %w", entry.Name(), err) } for _, imgName := range findLocalImages(string(data), inputDir) { @@ -78,7 +81,7 @@ func claimedByMarkdown(entries []os.DirEntry, inputDir string) map[string]bool { } } - return claimed + return claimed, nil } // processFile processes a single input file into a new post directory. |
