Skip to content

Follow comma style when arranging a Cabal section #1098

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Jan 21, 2016
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
57 changes: 47 additions & 10 deletions haskell-cabal.el
Original file line number Diff line number Diff line change
Expand Up @@ -569,13 +569,28 @@ resulting buffer-content"
(haskell-cabal-add-indentation (- ,old-l1-indent
,new-l1-indent))))))))

(defun haskell-cabal-comma-separatorp (pos)
"Return non-nil when the char at POS is a comma separator.
Characters that are not a comma, or commas inside a commment or
string, are not comma separators."
(when (eq (char-after pos) ?,)
(let ((ss (syntax-ppss pos)))
(not
(or
;; inside a string
(nth 3 ss)
;; inside a comment
(nth 4 ss))))))


(defun haskell-cabal-strip-list ()
"strip commas from comma-seperated list"
"Strip commas from a comma-separated list."
(goto-char (point-min))
;; split list items on single line
;; split list items on single line
(while (re-search-forward
"\\([^ \t,\n]\\)[ \t]*,[ \t]*\\([^ \t,\n]\\)" nil t)
(replace-match "\\1\n\\2" nil nil))
"\\([^ \t,\n]\\)[ \t]*\\(,\\)[ \t]*\\([^ \t,\n]\\)" nil t)
(when (haskell-cabal-comma-separatorp (match-beginning 2))
(replace-match "\\1\n\\3" nil nil)))
(goto-char (point-min))
(while (re-search-forward "^\\([ \t]*\\),\\([ \t]*\\)" nil t)
(replace-match "" nil nil))
Expand All @@ -586,7 +601,7 @@ resulting buffer-content"
(haskell-cabal-each-line (haskell-cabal-chomp-line)))

(defun haskell-cabal-listify ()
"Add commas so that buffer contains a comma-seperated list"
"Add commas so that the buffer contains a comma-seperated list"
(cl-case haskell-cabal-list-comma-position
('before
(goto-char (point-min))
Expand All @@ -605,14 +620,36 @@ resulting buffer-content"
(insert ",")
(beginning-of-line))))))

(defun haskell-cabal-comma-separatedp ()
"Return non-nil when the current buffer contains a comma-separated list.
When the buffer contains at least one comma separator (checked
with `haskell-cabal-comma-separatorp'), the buffer is considered
to be a comma-separated list."
(let ((comma-separatedp nil))
(goto-char (point-min))
(while (and (not comma-separatedp)
(search-forward "," (point-max) t))
(when (haskell-cabal-comma-separatorp (match-beginning 0))
(setq comma-separatedp t))
;; Make sure we don't find the same comma every time
(forward-char 1))
comma-separatedp))


(defmacro haskell-cabal-with-cs-list (&rest funs)
"format buffer so that each line contains a list element "
`(progn
(save-excursion (haskell-cabal-strip-list))
(unwind-protect (progn ,@funs)
(haskell-cabal-listify))))
"Format the buffer so that each line contains a list element.
Keep the lines comma-separated if and only if they were in the
first place."
(let ((comma-separatedp (make-symbol "comma-separatedp")))
`(let ((,comma-separatedp
(save-excursion
(prog1
(haskell-cabal-comma-separatedp)
(haskell-cabal-strip-list)))))
(unwind-protect (progn ,@funs)
;; Only reinsert commas when it already was comma-separated.
(when ,comma-separatedp
(haskell-cabal-listify))))))


(defun haskell-cabal-sort-lines-key-fun ()
Expand Down
118 changes: 118 additions & 0 deletions tests/haskell-cabal-tests.el
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,124 @@
(haskell-cabal-previous-subsection)
(haskell-cabal-previous-section))))

(ert-deftest haskell-cabal-subsection-arrange-lines-keep-commas ()
(should (with-temp-buffer
(insert "Executable bin-1
Main-Is: TestParsing.hs
Build-Depends: base,
bytestring,
directory,
filepath,
text
Ghc-Options: -O -Wall
")
(haskell-cabal-mode)
(goto-char (point-min))
(search-forward "Build-Depends:")
(haskell-cabal-subsection-arrange-lines)
(string= (buffer-string)
"Executable bin-1
Main-Is: TestParsing.hs
Build-Depends: base
, bytestring
, directory
, filepath
, text
Ghc-Options: -O -Wall
"))))

(ert-deftest haskell-cabal-subsection-arrange-lines-no-commas ()
(should (with-temp-buffer
(insert "Executable bin-1
Main-Is: TestParsing.hs
Other-Modules: Some.Module
Some.Other.Other.Module
Some.Other.Module
")
(haskell-cabal-mode)
(goto-char (point-min))
(search-forward "Other-Modules:")
(haskell-cabal-subsection-arrange-lines)
(string= (buffer-string)
"Executable bin-1
Main-Is: TestParsing.hs
Other-Modules: Some.Module
Some.Other.Module
Some.Other.Other.Module
"))))


(ert-deftest haskell-cabal-subsection-arrange-lines-quoted-items ()
(should (with-temp-buffer
(insert "Executable bin-1
Main-Is: TestParsing.hs
GHC-Options: -fprof-auto \"-with-rtsopts=-N -p -s -h -i0.1\"
")
(haskell-cabal-mode)
(goto-char (point-min))
(search-forward "GHC-Options:")
(haskell-cabal-subsection-arrange-lines)
(string= (buffer-string)
"Executable bin-1
Main-Is: TestParsing.hs
GHC-Options: -fprof-auto \"-with-rtsopts=-N -p -s -h -i0.1\"
"))))

(ert-deftest haskell-cabal-subsection-arrange-lines-no-commas-quoted-comma ()
(should (with-temp-buffer
(insert "Executable bin-1
Main-Is: TestParsing.hs
GHC-Options: -Wall -fprof-auto \"foo, bar\"
")
(haskell-cabal-mode)
(goto-char (point-min))
(search-forward "GHC-Options:")
(haskell-cabal-subsection-arrange-lines)
(string= (buffer-string)
"Executable bin-1
Main-Is: TestParsing.hs
GHC-Options: -Wall -fprof-auto \"foo, bar\"
"))))

(ert-deftest haskell-cabal-subsection-arrange-lines-commas-quoted-comma ()
(should (with-temp-buffer
(insert "Executable bin-1
Main-Is: TestParsing.hs
GHC-Options: -Wall, -fprof-auto \"foo, bar\"
")
(haskell-cabal-mode)
(goto-char (point-min))
(search-forward "GHC-Options:")
(haskell-cabal-subsection-arrange-lines)
(string= (buffer-string)
"Executable bin-1
Main-Is: TestParsing.hs
GHC-Options: -Wall
, -fprof-auto \"foo, bar\"
"))))

(ert-deftest haskell-cabal-subsection-arrange-lines-comma-in-commment ()
(should (with-temp-buffer
(insert "Executable bin-1
Main-Is: TestParsing.hs
Other-Modules: Some.Module
Some.Other.Other.Module
Some.Other.Module
-- Foo, bar
")
(haskell-cabal-mode)
(goto-char (point-min))
(search-forward "Other-Modules:")
(haskell-cabal-subsection-arrange-lines)
(string= (buffer-string)
"Executable bin-1
Main-Is: TestParsing.hs
Other-Modules: Some.Module
Some.Other.Module
Some.Other.Other.Module
-- Foo, bar
"))))

(provide 'haskell-cabal-tests)

;;; haskell-cabal-tests.el ends here