diff --git a/ale_linters/erlang/elp.vim b/ale_linters/erlang/elp.vim new file mode 100644 index 0000000000..b09a3dffda --- /dev/null +++ b/ale_linters/erlang/elp.vim @@ -0,0 +1,36 @@ +" Author: Ivan Stone +" Description: LSP linter for Erlang files using erlang-language-platform + +call ale#Set('erlang_elp_executable', 'elp') + +function! s:FindProjectRoot(buffer) abort + let l:markers = [ + \ '_checkouts/', + \ '_build/', + \ 'deps/', + \ 'rebar.config', + \ 'rebar.lock', + \ 'erlang.mk', + \ '.kerl_config', + \] + + for l:marker in l:markers + let l:path = l:marker[-1:] is# '/' + \ ? ale#path#FindNearestDirectory(a:buffer, l:marker) + \ : ale#path#FindNearestFile(a:buffer, l:marker) + + if !empty(l:path) + return ale#path#Dirname(l:path) + endif + endfor + + return '' +endfunction + +call ale#linter#Define('erlang', { +\ 'name': 'elp', +\ 'lsp': 'stdio', +\ 'executable': {b -> ale#Var(b, 'erlang_elp_executable')}, +\ 'command': '%e server', +\ 'project_root': function('s:FindProjectRoot'), +\}) diff --git a/doc/ale-erlang.txt b/doc/ale-erlang.txt index 388f80adcc..363aa4749f 100644 --- a/doc/ale-erlang.txt +++ b/doc/ale-erlang.txt @@ -64,6 +64,20 @@ g:ale_erlang_elvis_executable This variable can be changed to specify the elvis executable. +=============================================================================== +elp *ale-erlang-elp* + + *ale-options.erlang_elp_executable* + *g:ale_erlang_elp_executable* + *b:ale_erlang_elp_executable* +erlang_elp_executable +g:ale_erlang_elp_executable + Type: |String| + Default: `'elp'` + + This variable can be changed to specify the elp executable. + + =============================================================================== erlang-mode *ale-erlang-erlang-mode* diff --git a/doc/ale-supported-languages-and-tools.txt b/doc/ale-supported-languages-and-tools.txt index 8cb95b569a..dbc32e49da 100644 --- a/doc/ale-supported-languages-and-tools.txt +++ b/doc/ale-supported-languages-and-tools.txt @@ -198,6 +198,7 @@ Notes: * Erlang * `SyntaxErl` * `dialyzer`!! + * `elp` * `elvis`!! * `erlang-mode` (The Erlang mode for Emacs) * `erlang_ls` diff --git a/doc/ale.txt b/doc/ale.txt index 380914bc5c..65b2de2228 100644 --- a/doc/ale.txt +++ b/doc/ale.txt @@ -3544,6 +3544,7 @@ documented in additional help files. elm-make..............................|ale-elm-elm-make| erlang..................................|ale-erlang-options| dialyzer..............................|ale-erlang-dialyzer| + elp...................................|ale-erlang-elp| elvis.................................|ale-erlang-elvis| erlang-mode...........................|ale-erlang-erlang-mode| erlang_ls.............................|ale-erlang-erlang_ls| diff --git a/supported-tools.md b/supported-tools.md index a038acbdeb..f47ac9dc8c 100644 --- a/supported-tools.md +++ b/supported-tools.md @@ -208,6 +208,7 @@ formatting. * Erlang * [SyntaxErl](https://github.com/ten0s/syntaxerl) * [dialyzer](http://erlang.org/doc/man/dialyzer.html) :floppy_disk: + * [elp](https://github.com/WhatsApp/erlang-language-platform) :speech_balloon: * [elvis](https://github.com/inaka/elvis) :floppy_disk: * [erlang-mode](https://www.erlang.org/doc/apps/tools/erlang_mode_chapter.html) (The Erlang mode for Emacs) :speech_balloon: * [erlang_ls](https://github.com/erlang-ls/erlang_ls) :speech_balloon: diff --git a/test/linter/test_erlang_elp.vader b/test/linter/test_erlang_elp.vader new file mode 100644 index 0000000000..81899b49d2 --- /dev/null +++ b/test/linter/test_erlang_elp.vader @@ -0,0 +1,42 @@ +Before: + call ale#assert#SetUpLinterTest('erlang', 'elp') + +After: + unlet! b:root + + call ale#assert#TearDownLinterTest() + +Execute(The default command should be correct): + AssertLinter 'elp', ale#Escape('elp') . ' server' + +Execute(Executable should be configurable): + let b:ale_erlang_elp_executable = '/path/to/elp' + + AssertLinter '/path/to/elp', ale#Escape('/path/to/elp') . ' server' + +Execute(Root of Rebar3 project should be detected): + let b:root = '../test-files/erlang/rebar3_app' + + call ale#test#SetFilename(b:root . '/src/app.erl') + AssertLSPProject ale#test#GetFilename(b:root) + + call ale#test#SetFilename(b:root . '/_build/default/lib/dep/src/dep.erl') + AssertLSPProject ale#test#GetFilename(b:root) + + call ale#test#SetFilename(b:root . '/_checkouts/dep/src/dep.erl') + AssertLSPProject ale#test#GetFilename(b:root) + +Execute(Root of Erlang.mk project should be detected): + let b:root = '../test-files/erlang/erlang_mk_app' + + call ale#test#SetFilename(b:root . '/src/app.erl') + AssertLSPProject ale#test#GetFilename(b:root) + + call ale#test#SetFilename(b:root . '/deps/dep/src/dep.erl') + AssertLSPProject ale#test#GetFilename(b:root) + +Execute(Root of kerl managed Erlang/OTP installation should be detected): + let b:root = '../test-files/erlang/kerl_otp_root' + + call ale#test#SetFilename(b:root . '/lib/stdlib-4.1.1/array.erl') + AssertLSPProject ale#test#GetFilename(b:root)