From cffdf3b92a97b1af3aedec624a9fb43db1c60ef8 Mon Sep 17 00:00:00 2001 From: Craig Jennings Date: Sun, 10 May 2026 13:42:11 -0500 Subject: refactor(dirvish): extract cj/--html-file-p; match HTML case-insensitively `cj/dirvish-open-html-in-eww' inlined a `string-match-p' against `\.html?\=' to decide whether to hand a file to eww. The check was case-sensitive, so `.HTML' fell through to the "Not an HTML file" message even though every browser treats it as HTML. Lift the predicate into `cj/--html-file-p' and bind `case-fold-search' to t so uppercase and mixed-case extensions match. The trailing-`\=' anchor stays so files like `html-thing.org' still don't match. Seven Normal/Boundary/Error tests cover lowercase `.html', `.htm', uppercase `.HTML', mixed-case `.Html', embedded `html' (no match), non-html extensions (no match), and no-extension files (no match). --- modules/dirvish-config.el | 11 ++++++- tests/test-dirvish-config-html-file-p.el | 53 ++++++++++++++++++++++++++++++++ 2 files changed, 63 insertions(+), 1 deletion(-) create mode 100644 tests/test-dirvish-config-html-file-p.el diff --git a/modules/dirvish-config.el b/modules/dirvish-config.el index 86ecfd2d..ad2227e8 100644 --- a/modules/dirvish-config.el +++ b/modules/dirvish-config.el @@ -161,11 +161,20 @@ Filters for audio files, prompts for the playlist name, and saves the resulting ;;; --------------------------- Dired Open HTML In EWW -------------------------- +(defun cj/--html-file-p (file) + "Return non-nil when FILE has a `.html' or `.htm' extension. + +Match is case-insensitive (`.HTML' counts) and anchored at end so +embedded `html' in the middle of a name doesn't match. Pure helper +used by `cj/dirvish-open-html-in-eww'." + (let ((case-fold-search t)) + (and (string-match-p "\\.html?\\'" file) t))) + (defun cj/dirvish-open-html-in-eww () "Open HTML file at point in dired/dirvish using eww." (interactive) (let ((file (dired-get-file-for-visit))) - (if (string-match-p "\\.html?\\'" file) + (if (cj/--html-file-p file) (eww-open-file file) (message "Not an HTML file: %s" file)))) diff --git a/tests/test-dirvish-config-html-file-p.el b/tests/test-dirvish-config-html-file-p.el new file mode 100644 index 00000000..dd18edaf --- /dev/null +++ b/tests/test-dirvish-config-html-file-p.el @@ -0,0 +1,53 @@ +;;; test-dirvish-config-html-file-p.el --- Tests for the html-file predicate -*- lexical-binding: t; -*- + +;;; Commentary: +;; `cj/--html-file-p' is the predicate behind `cj/dirvish-open-html-in-eww'. +;; The earlier inline regex was case-sensitive (`.html?\='), but most +;; browsers treat `.HTML' as HTML too, so the helper is case-insensitive. +;; The predicate also anchors on the trailing extension so files with +;; "html" embedded in the middle of the name don't match. + +;;; Code: + +(require 'ert) +(require 'package) + +(setq package-user-dir (expand-file-name "elpa" user-emacs-directory)) +(package-initialize) +(add-to-list 'load-path (expand-file-name "modules" user-emacs-directory)) +(add-to-list 'load-path (expand-file-name "elpa/dirvish-2.3.0/extensions" + user-emacs-directory)) +(require 'user-constants) +(require 'keybindings) +(require 'dirvish-config) + +(ert-deftest test-cj--html-file-p-html-extension-matches () + "Normal: `.html' extension matches." + (should (cj/--html-file-p "/tmp/index.html"))) + +(ert-deftest test-cj--html-file-p-htm-extension-matches () + "Normal: `.htm' extension matches (legacy 8.3 form)." + (should (cj/--html-file-p "/tmp/page.htm"))) + +(ert-deftest test-cj--html-file-p-uppercase-html-matches () + "Boundary: `.HTML' (uppercase) matches -- match is case-insensitive." + (should (cj/--html-file-p "/tmp/index.HTML"))) + +(ert-deftest test-cj--html-file-p-mixed-case-html-matches () + "Boundary: mixed case (`.Html') matches." + (should (cj/--html-file-p "/tmp/index.Html"))) + +(ert-deftest test-cj--html-file-p-embedded-html-does-not-match () + "Boundary: `html' in the middle of the name doesn't match (anchor at end)." + (should-not (cj/--html-file-p "/tmp/html-thing.org"))) + +(ert-deftest test-cj--html-file-p-non-html-extension-does-not-match () + "Error: a non-html file returns nil." + (should-not (cj/--html-file-p "/tmp/notes.txt"))) + +(ert-deftest test-cj--html-file-p-no-extension-does-not-match () + "Boundary: a file without an extension does not match." + (should-not (cj/--html-file-p "/tmp/README"))) + +(provide 'test-dirvish-config-html-file-p) +;;; test-dirvish-config-html-file-p.el ends here -- cgit v1.2.3