From 0551602b198ca50650f9853d23fd970f3655842a Mon Sep 17 00:00:00 2001
From: Dmitri Vereshchagin <dmitri.vereshchagin@gmail.com>
Date: Sun, 29 Dec 2024 07:55:43 +0300
Subject: [PATCH] Add erlfmt fixer to the registry and use it with stdin
 (#4868)

* Add erlfmt fixer to the registry

Without this, the fixer will not appear in the list of suggested tools
and cannot be used without additional configuration.

* Handle stdin in the erlfmt fixer command

Previously, the full path to the file being edited was used, which
resulted in the loss of unsaved changes.

* Add executable selection tests for erlfmt fixer
---
 autoload/ale/fix/registry.vim                 |  5 +++
 autoload/ale/fixers/erlfmt.vim                |  6 +--
 test/fixers/test_erlfmt_fixer_callback.vader  | 43 +++++++++++--------
 test/test-files/erlang/app_with_erlfmt/erlfmt |  0
 4 files changed, 33 insertions(+), 21 deletions(-)
 create mode 100755 test/test-files/erlang/app_with_erlfmt/erlfmt

diff --git a/autoload/ale/fix/registry.vim b/autoload/ale/fix/registry.vim
index 1ab569789d..b00218151c 100644
--- a/autoload/ale/fix/registry.vim
+++ b/autoload/ale/fix/registry.vim
@@ -109,6 +109,11 @@ let s:default_registry = {
 \       'description': 'Indent with the Erlang mode for Emacs',
 \       'aliases': ['erlang-mode'],
 \   },
+\   'erlfmt': {
+\       'function': 'ale#fixers#erlfmt#Fix',
+\       'suggested_filetypes': ['erlang'],
+\       'description': 'Format Erlang code with erlfmt',
+\   },
 \   'fecs': {
 \       'function': 'ale#fixers#fecs#Fix',
 \       'suggested_filetypes': ['javascript', 'css', 'html'],
diff --git a/autoload/ale/fixers/erlfmt.vim b/autoload/ale/fixers/erlfmt.vim
index f9951e9dd3..06cb17046d 100644
--- a/autoload/ale/fixers/erlfmt.vim
+++ b/autoload/ale/fixers/erlfmt.vim
@@ -13,9 +13,7 @@ function! ale#fixers#erlfmt#Fix(buffer) abort
     let l:options = ale#Var(a:buffer, 'erlang_erlfmt_options')
     let l:executable = ale#fixers#erlfmt#GetExecutable(a:buffer)
 
-    let l:command = ale#Escape(l:executable) . (empty(l:options) ? '' : ' ' . l:options) . ' %s'
+    let l:command = ale#Escape(l:executable) . ale#Pad(l:options) . ' -'
 
-    return {
-    \   'command': l:command
-    \}
+    return {'command': l:command}
 endfunction
diff --git a/test/fixers/test_erlfmt_fixer_callback.vader b/test/fixers/test_erlfmt_fixer_callback.vader
index 132cd6eefe..21e252e6ff 100644
--- a/test/fixers/test_erlfmt_fixer_callback.vader
+++ b/test/fixers/test_erlfmt_fixer_callback.vader
@@ -1,25 +1,34 @@
 Before:
-  Save b:ale_elm_format_executable
-  Save b:ale_elm_format_options
-
-  let b:ale_elm_format_executable = 'erlfmt'
-  let b:ale_elm_format_options = ''
+  call ale#assert#SetUpFixerTest('erlang', 'erlfmt')
 
 After:
-  Restore
+  unlet! b:root
+
+  call ale#assert#TearDownFixerTest()
+
+Execute(The local erlfmt executable should be used by default):
+  " Not sure if this is a good default though.  It seems to imply
+  " that the executable is committed to the repository.
+
+  let b:root = '../test-files/erlang/app_with_erlfmt'
+
+  call ale#test#SetFilename(b:root . '/src/app.erl')
+  AssertFixer {
+  \ 'command': ale#Escape(ale#test#GetFilename(b:root . '/erlfmt')) . ' -',
+  \}
+
+Execute(The global erlfmt executable should be configurable):
+  let b:root = '../test-files/erlang/app_with_erlfmt'
+
+  let b:ale_erlang_erlfmt_executable = '/path/to/erlfmt'
+  let b:ale_erlang_erlfmt_use_global = 1
+
+  call ale#test#SetFilename(b:root . '/src/app.erl')
+  AssertFixer {'command': ale#Escape('/path/to/erlfmt') . ' -'}
 
 Execute(The erlfmt command should handle empty options):
-  AssertEqual
-  \ {
-  \   'command': ale#Escape('erlfmt') . ' %s'
-  \ },
-  \ ale#fixers#erlfmt#Fix(bufnr(''))
+  AssertFixer {'command': ale#Escape('erlfmt') . ' -'}
 
 Execute(The erlfmt command should handle custom options):
   let b:ale_erlang_erlfmt_options = '--insert-pragma'
-
-  AssertEqual
-  \ {
-  \   'command': ale#Escape('erlfmt') . ' --insert-pragma %s'
-  \ },
-  \ ale#fixers#erlfmt#Fix(bufnr(''))
+  AssertFixer {'command': ale#Escape('erlfmt') . ' --insert-pragma -'}
diff --git a/test/test-files/erlang/app_with_erlfmt/erlfmt b/test/test-files/erlang/app_with_erlfmt/erlfmt
new file mode 100755
index 0000000000..e69de29bb2