]> git.eshelyaron.com Git - emacs.git/commitdiff
Improve indentation of some shell script forms
authorLars Ingebrigtsen <larsi@gnus.org>
Mon, 7 Feb 2022 08:13:46 +0000 (09:13 +0100)
committerLars Ingebrigtsen <larsi@gnus.org>
Mon, 7 Feb 2022 08:13:54 +0000 (09:13 +0100)
* lisp/progmodes/sh-script.el (sh-smie--default-backward-token):
Don't skip past things like "true;then" (bug#53817).

lisp/progmodes/sh-script.el
test/lisp/progmodes/sh-script-resources/sh-indents.erts [new file with mode: 0644]
test/lisp/progmodes/sh-script-tests.el

index 0a2ec348c1ac6dc5bb6a9c5f80d47493e42a6350..8dc55621438c5cea1654f1e4ea21f77ea9352502 100644 (file)
@@ -1774,21 +1774,27 @@ Does not preserve point."
         (n (skip-syntax-backward ".")))
     (if (or (zerop n)
             (and (eq n -1)
+                 ;; Skip past quoted white space.
                  (let ((p (point)))
                    (if (eq -1 (% (skip-syntax-backward "\\") 2))
                        t
                      (goto-char p)
                      nil))))
         (while
-            (progn (skip-syntax-backward ".w_'")
-                   (or (not (zerop (skip-syntax-backward "\\")))
-                       (when (eq ?\\ (char-before (1- (point))))
-                         (let ((p (point)))
-                           (forward-char -1)
-                           (if (eq -1 (% (skip-syntax-backward "\\") 2))
-                               t
-                             (goto-char p)
-                             nil))))))
+            (progn
+              ;; Skip past words, but stop at semicolons.
+              (while (and (not (zerop (skip-syntax-backward "w_'")))
+                          (not (eq (char-before (point)) ?\;))
+                          (skip-syntax-backward ".")))
+              (or (not (zerop (skip-syntax-backward "\\")))
+                  ;; Skip past quoted white space.
+                  (when (eq ?\\ (char-before (1- (point))))
+                    (let ((p (point)))
+                      (forward-char -1)
+                      (if (eq -1 (% (skip-syntax-backward "\\") 2))
+                          t
+                        (goto-char p)
+                        nil))))))
       (goto-char (- (point) (% (skip-syntax-backward "\\") 2))))
     (buffer-substring-no-properties (point) pos)))
 
diff --git a/test/lisp/progmodes/sh-script-resources/sh-indents.erts b/test/lisp/progmodes/sh-script-resources/sh-indents.erts
new file mode 100644 (file)
index 0000000..1f92610
--- /dev/null
@@ -0,0 +1,40 @@
+Code:
+  (lambda ()
+    (shell-script-mode)
+    (indent-region (point-min) (point-max)))
+
+Name: sh-indents1
+
+=-=
+if test;then
+    something
+fi
+other
+=-=-=
+
+Name: sh-indents2
+
+=-=
+if test; then
+    something
+fi
+other
+=-=-=
+
+Name: sh-indents3
+
+=-=
+if test ; then
+    something
+fi
+other
+=-=-=
+
+Name: sh-indents4
+
+=-=
+if test ;then
+    something
+fi
+other
+=-=-=
index ebd26ab42956df4ce4d78edce7b46e827a1e9cf9..5d01cc1c2266a7c24dc12c9a4034fec040bffc59 100644 (file)
@@ -23,6 +23,7 @@
 
 (require 'sh-script)
 (require 'ert)
+(require 'ert-x)
 
 (ert-deftest test-sh-script-indentation ()
   (with-temp-buffer
 }
 "))))
 
+(ert-deftest test-indentation ()
+  (ert-test-erts-file (ert-resource-file "sh-indents.erts")))
+
+(defun test-sh-back (string &optional pos)
+  (with-temp-buffer
+    (shell-script-mode)
+    (insert string)
+    (sh-smie--default-backward-token)
+    (= (point) (or pos 1))))
+
+(ert-deftest test-backward-token ()
+  (should (test-sh-back "foo"))
+  (should (test-sh-back "foo.bar"))
+  (should (test-sh-back "foo\\1bar"))
+  (should (test-sh-back "foo\\\nbar"))
+  (should (test-sh-back "foo\\\n\\\n\\\nbar"))
+  (should (test-sh-back "foo"))
+  (should-not (test-sh-back "foo;bar"))
+  (should (test-sh-back "foo#zot")))
+
 ;;; sh-script-tests.el ends here