{"id":13481902,"url":"https://github.com/mattn/efm-langserver","last_synced_at":"2025-05-14T02:06:58.654Z","repository":{"id":37774077,"uuid":"169221755","full_name":"mattn/efm-langserver","owner":"mattn","description":"General purpose Language Server","archived":false,"fork":false,"pushed_at":"2025-04-29T12:21:31.000Z","size":466,"stargazers_count":1446,"open_issues_count":63,"forks_count":64,"subscribers_count":8,"default_branch":"master","last_synced_at":"2025-05-10T15:53:46.330Z","etag":null,"topics":["go","golang","langserver","language-server"],"latest_commit_sha":null,"homepage":"","language":"Go","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/mattn.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":".github/FUNDING.yml","license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null},"funding":{"github":"mattn","patreon":null,"open_collective":null,"ko_fi":null,"tidelift":null,"community_bridge":null,"liberapay":null,"issuehunt":null,"otechie":null,"custom":null}},"created_at":"2019-02-05T10:16:46.000Z","updated_at":"2025-05-10T08:50:19.000Z","dependencies_parsed_at":"2024-03-18T14:48:10.296Z","dependency_job_id":"cdd4388b-2373-4309-9a3f-580a1dc5bb8d","html_url":"https://github.com/mattn/efm-langserver","commit_stats":{"total_commits":330,"total_committers":47,"mean_commits":"7.0212765957446805","dds":"0.40303030303030307","last_synced_commit":"bad115b56bd96f517e25d66ca660d5f194af629e"},"previous_names":[],"tags_count":52,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mattn%2Fefm-langserver","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mattn%2Fefm-langserver/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mattn%2Fefm-langserver/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mattn%2Fefm-langserver/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/mattn","download_url":"https://codeload.github.com/mattn/efm-langserver/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":254052730,"owners_count":22006716,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["go","golang","langserver","language-server"],"created_at":"2024-07-31T17:00:57.276Z","updated_at":"2025-05-14T02:06:53.636Z","avatar_url":"https://github.com/mattn.png","language":"Go","funding_links":["https://github.com/sponsors/mattn"],"categories":["Go","Linting \u0026 Formatters","Repositories"],"sub_categories":[],"readme":"# efm-langserver\n\n[![Actions Status](https://github.com/mattn/efm-langserver/workflows/CI/badge.svg)](https://github.com/mattn/efm-langserver/actions)\n\nGeneral purpose Language Server that can use specified error message format\ngenerated from specified command. This is useful for editing code with linter.\n\n![efm](https://raw.githubusercontent.com/mattn/efm-langserver/master/screenshot.png)\n\n* [Installation](#installation)\n* [Usage](#usage)\n  + [Configuration](#configuration)\n    - [InitializeParams](#initializeparams)\n  + [Example for config.yaml](#example-for-configyaml)\n  + [Example for DidChangeConfiguration notification](#example-for-didchangeconfiguration-notification)\n* [Client Setup](#client-setup)\n  + [Configuration for vim-lsp](#configuration-for-vim-lsp)\n  + [Configuration for coc.nvim](#configuration-for-cocnvim)\n  + [Configuration for Eglot (Emacs)](#configuration-for-eglot)\n  + [Configuration for neovim builtin LSP with nvim-lspconfig](#configuration-for-neovim-builtin-lsp-with-nvim-lspconfig)\n  + [Configuration for Helix](#configuration-for-helix)\n  + [Configuration for VSCode](#configuration-for-vscode)\n* [License](#license)\n* [Author](#author)\n\n## Installation\n\n```console\ngo install github.com/mattn/efm-langserver@latest\n```\n\nor via [Homebrew](https://brew.sh/):\n```console\nbrew install efm-langserver\n```\n\n## Usage\n\n```text\nUsage of efm-langserver:\n  -c string\n        path to config.yaml\n  -d    dump configuration\n  -logfile string\n        logfile\n  -loglevel int\n        loglevel (default 1)\n  -q    Run quieter\n  -v    Print the version\n```\n\n### Configuration\n\nConfiguration can be done with either a `config.yaml` file, or through\na [DidChangeConfiguration](https://microsoft.github.io/language-server-protocol/specification.html#workspace_didChangeConfiguration)\nnotification from the client.\n`DidChangeConfiguration` can be called any time and will overwrite only provided\nproperties.\n\n`DidChangeConfiguration` only supports V2 configuration and cannot set `LogFile`.\n\n`efm-langserver` does not include formatters/linters for any languages, you must install these manually,\ne.g.\n - lua: [LuaFormatter](https://github.com/Koihik/LuaFormatter)\n - python: [yapf](https://github.com/google/yapf) [isort](https://github.com/PyCQA/isort)\n - [vint](https://github.com/Kuniwak/vint) for Vim script\n - [markdownlint-cli](https://github.com/igorshubovych/markdownlint-cli) for Markdown\n - etc...\n\n#### InitializeParams\n\nBecause the configuration can be updated on the fly, capabilities might change\nthroughout the lifetime of the server. To enable support for capabilities that will\nbe available later, set them in the [InitializeParams](https://microsoft.github.io/language-server-protocol/specification.html#initialize)\n\nExample\n```json\n{\n    \"initializationOptions\": {\n        \"documentFormatting\": true,\n        \"documentRangeFormatting\": true,\n        \"hover\": true,\n        \"documentSymbol\": true,\n        \"codeAction\": true,\n        \"completion\": true\n    }\n}\n```\n\n### Example for config.yaml\n\nLocation of config.yaml is:\n\n* UNIX: `$XDG_CONFIG_HOME/efm-langserver/config.yaml` or `$HOME/.config/efm-langserver/config.yaml`\n* Windows: `%APPDATA%\\efm-langserver\\config.yaml`\n\nBelow is example for `config.yaml` for Windows. Please see [schema.md](schema.md) for full documentation of the available options.\n\n```yaml\nversion: 2\nroot-markers:\n  - .git/\nlint-debounce: 1s\ncommands:\n  - command: notepad\n    arguments:\n      - ${INPUT}\n    title: メモ帳\n\ntools:\n  any-excitetranslate: \u0026any-excitetranslate\n    hover-command: 'excitetranslate'\n    hover-stdin: true\n\n  blade-blade-formatter: \u0026blade-blade-formatter\n    format-command: 'blade-formatter --stdin'\n    format-stdin: true\n\n  css-prettier: \u0026css-prettier\n    format-command: './node_modules/.bin/prettier ${--tab-width:tabWidth} ${--single-quote:singleQuote} --parser css'\n\n  csv-csvlint: \u0026csv-csvlint\n    lint-command: 'csvlint'\n\n  dockerfile-hadolint: \u0026dockerfile-hadolint\n    lint-command: 'hadolint'\n    lint-formats:\n      - '%f:%l %m'\n\n  eruby-erb: \u0026eruby-erb\n    lint-debounce: 2s\n    lint-command: 'erb -x -T - | ruby -c'\n    lint-stdin: true\n    lint-offset: 1\n    format-stdin: true\n    format-command: htmlbeautifier\n\n  gitcommit-gitlint: \u0026gitcommit-gitlint\n    lint-command: 'gitlint'\n    lint-stdin: true\n    lint-formats:\n      - '%l: %m: \"%r\"'\n      - '%l: %m'\n\n  html-prettier: \u0026html-prettier\n    format-command: './node_modules/.bin/prettier ${--tab-width:tabWidth} ${--single-quote:singleQuote} --parser html'\n\n  javascript-eslint: \u0026javascript-eslint\n    lint-command: 'eslint -f visualstudio --stdin --stdin-filename ${INPUT}'\n    lint-ignore-exit-code: true\n    lint-stdin: true\n    lint-formats:\n      - \"%f(%l,%c): %tarning %m\"\n      - \"%f(%l,%c): %rror %m\"\n\n  json-fixjson: \u0026json-fixjson\n    format-command: 'fixjson'\n\n  json-jq: \u0026json-jq\n    lint-command: 'jq .'\n\n  json-prettier: \u0026json-prettier\n    format-command: './node_modules/.bin/prettier ${--tab-width:tabWidth} --parser json'\n\n  lua-lua-format: \u0026lua-lua-format\n    format-command: 'lua-format -i'\n    format-stdin: true\n\n  make-checkmake: \u0026make-checkmake\n    lint-command: 'checkmake'\n    lint-stdin: true\n\n  markdown-markdownlint: \u0026markdown-markdownlint\n    lint-command: 'markdownlint -s -c %USERPROFILE%\\.markdownlintrc'\n    lint-stdin: true\n    lint-formats:\n      - '%f:%l %m'\n      - '%f:%l:%c %m'\n      - '%f: %l: %m'\n\n  markdown-pandoc: \u0026markdown-pandoc\n    format-command: 'pandoc -f markdown -t gfm -sp --tab-stop=2'\n\n  mix_credo: \u0026mix_credo\n    lint-command: \"mix credo suggest --format=flycheck --read-from-stdin ${INPUT}\"\n    lint-stdin: true\n    lint-formats:\n      - '%f:%l:%c: %t: %m'\n      - '%f:%l: %t: %m'\n    root-markers:\n      - mix.lock\n      - mix.exs\n\n  perl-perlcritic: \u0026perl-perlcritic\n    lint-command: 'perlcritic --nocolor -3 --verbose \"%l:%c %m\\n\"'\n    lint-ignore-exit-code: true\n    lint-formats:\n      - '%l:%c %m'\n\n  perl-perltidy: \u0026perl-perltidy\n    format-command: \"perltidy -b\"\n    format-stdin: true\n\n  php-phpstan: \u0026php-phpstan\n    lint-command: './vendor/bin/phpstan analyze --error-format raw --no-progress'\n\n  php-psalm: \u0026php-psalm\n    lint-command: './vendor/bin/psalm --output-format=emacs --no-progress'\n    lint-formats:\n      - '%f:%l:%c:%trror - %m'\n      - '%f:%l:%c:%tarning - %m'\n\n  prettierd: \u0026prettierd\n    format-command: \u003e\n      prettierd ${INPUT} ${--range-start=charStart} ${--range-end=charEnd} \\\n        ${--tab-width=tabSize}\n    format-stdin: true\n    root-markers:\n      - .prettierrc\n      - .prettierrc.json\n      - .prettierrc.js\n      - .prettierrc.yml\n      - .prettierrc.yaml\n      - .prettierrc.json5\n      - .prettierrc.mjs\n      - .prettierrc.cjs\n      - .prettierrc.toml\n\n  python-autopep8: \u0026python-autopep8\n    format-command: 'autopep8 -'\n    format-stdin: true\n\n  python-black: \u0026python-black\n    format-command: 'black --quiet -'\n    format-stdin: true\n\n  python-flake8: \u0026python-flake8\n    lint-command: 'flake8 --stdin-display-name ${INPUT} -'\n    lint-stdin: true\n    lint-formats:\n      - '%f:%l:%c: %m'\n\n  python-isort: \u0026python-isort\n    format-command: 'isort --quiet -'\n    format-stdin: true\n\n  python-mypy: \u0026python-mypy\n    lint-command: 'mypy --show-column-numbers'\n    lint-formats:\n      - '%f:%l:%c: %trror: %m'\n      - '%f:%l:%c: %tarning: %m'\n      - '%f:%l:%c: %tote: %m'\n\n  python-pylint: \u0026python-pylint\n    lint-command: 'pylint --output-format text --score no --msg-template {path}:{line}:{column}:{C}:{msg} ${INPUT}'\n    lint-stdin: false\n    lint-formats:\n      - '%f:%l:%c:%t:%m'\n    lint-offset-columns: 1\n    lint-category-map:\n      I: H\n      R: I\n      C: I\n      W: W\n      E: E\n      F: E\n\n  python-yapf: \u0026python-yapf\n    format-command: 'yapf --quiet'\n    format-stdin: true\n\n  rst-lint: \u0026rst-lint\n    lint-command: 'rst-lint'\n    lint-formats:\n      - '%tNFO %f:%l %m'\n      - '%tARNING %f:%l %m'\n      - '%tRROR %f:%l %m'\n      - '%tEVERE %f:%l %m'\n\n  rst-pandoc: \u0026rst-pandoc\n    format-command: 'pandoc -f rst -t rst -s --columns=79'\n\n  sh-shellcheck: \u0026sh-shellcheck\n    lint-command: 'shellcheck -f gcc -x'\n    lint-source: 'shellcheck'\n    lint-formats:\n      - '%f:%l:%c: %trror: %m'\n      - '%f:%l:%c: %tarning: %m'\n      - '%f:%l:%c: %tote: %m'\n\n  sh-shfmt: \u0026sh-shfmt\n    format-command: 'shfmt -ci -s -bn'\n    format-stdin: true\n\n  vim-vint: \u0026vim-vint\n    lint-command: 'vint -'\n    lint-stdin: true\n    lint-formats:\n      - '%f:%l:%c: %m'\n\n  yaml-yamllint: \u0026yaml-yamllint\n    lint-command: 'yamllint -f parsable -'\n    lint-stdin: true\n\nlanguages:\n  blade:\n    - \u003c\u003c: *blade-blade-formatter\n\n  css:\n    - \u003c\u003c: *css-prettier\n\n  csv:\n    - \u003c\u003c: *csv-csvlint\n\n  dockerfile:\n    - \u003c\u003c: *dockerfile-hadolint\n\n  elixir:\n    - \u003c\u003c: *mix_credo\n\n  eruby:\n    - \u003c\u003c: *eruby-erb\n\n  gitcommit:\n    - \u003c\u003c: *gitcommit-gitlint\n\n  html:\n    - \u003c\u003c: *html-prettier\n\n  javascript:\n    - \u003c\u003c: *javascript-eslint\n    - \u003c\u003c: *prettierd\n\n  json:\n    - \u003c\u003c: *json-fixjson\n    - \u003c\u003c: *json-jq\n    # - \u003c\u003c: *json-prettier\n\n  lua:\n    - \u003c\u003c: *lua-lua-format\n\n  make:\n    - \u003c\u003c: *make-checkmake\n\n  markdown:\n    - \u003c\u003c: *markdown-markdownlint\n    - \u003c\u003c: *markdown-pandoc\n\n  perl:\n    - \u003c\u003c: *perl-perltidy\n    - \u003c\u003c: *perl-perlcritic\n\n  php:\n    - \u003c\u003c: *php-phpstan\n    - \u003c\u003c: *php-psalm\n\n  python:\n    - \u003c\u003c: *python-black\n    - \u003c\u003c: *python-flake8\n    - \u003c\u003c: *python-isort\n    - \u003c\u003c: *python-mypy\n    # - \u003c\u003c: *python-autopep8\n    # - \u003c\u003c: *python-yapf\n\n  rst:\n    - \u003c\u003c: *rst-lint\n    - \u003c\u003c: *rst-pandoc\n\n  sh:\n    - \u003c\u003c: *sh-shellcheck\n    - \u003c\u003c: *sh-shfmt\n\n  vim:\n    - \u003c\u003c: *vim-vint\n\n  yaml:\n    - \u003c\u003c: *yaml-yamllint\n\n  =:\n    - \u003c\u003c: *any-excitetranslate\n```\n\nIf you want to debug output of commands:\n\n```yaml\nversion: 2\nlog-file: /path/to/output.log\nlog-level: 1\n```\n\n### Example for DidChangeConfiguration notification\n\n```json\n{\n    \"settings\": {\n        \"rootMarkers\": [\".git/\"],\n        \"languages\": {\n            \"lua\": {\n                \"formatCommand\": \"lua-format -i\",\n                \"formatStdin\": true\n            }\n        }\n    }\n}\n```\n\n## Client Setup\n\n### Configuration for [vim-lsp](https://github.com/prabirshrestha/vim-lsp/)\n\n```vim\naugroup LspEFM\n  au!\n  autocmd User lsp_setup call lsp#register_server({\n      \\ 'name': 'efm-langserver',\n      \\ 'cmd': {server_info-\u003e['efm-langserver', '-c=/path/to/your/config.yaml']},\n      \\ 'allowlist': ['vim', 'eruby', 'markdown', 'yaml'],\n      \\ })\naugroup END\n```\n\n[vim-lsp-settings](https://github.com/mattn/vim-lsp-settings) provide installer for efm-langserver.\n\n### Configuration for [coc.nvim](https://github.com/neoclide/coc.nvim)\n\ncoc-settings.json\n\n```jsonc\n  // languageserver\n  \"languageserver\": {\n    \"efm\": {\n      \"command\": \"efm-langserver\",\n      \"args\": [],\n      // custom config path\n      // \"args\": [\"-c\", \"/path/to/your/config.yaml\"],\n      \"filetypes\": [\"vim\", \"eruby\", \"markdown\", \"yaml\"]\n    }\n  },\n```\n\n### Configuration for [Eglot](https://github.com/joaotavora/eglot) (Emacs)\n\nAdd to eglot-server-programs with major mode you want.\n\n```lisp\n(with-eval-after-load 'eglot\n  (add-to-list 'eglot-server-programs\n    `(markdown-mode . (\"efm-langserver\"))))\n```\n\n### Configuration for [neovim builtin LSP](https://neovim.io/doc/user/lsp.html) with [nvim-lspconfig](https://github.com/neovim/nvim-lspconfig)\n\nNeovim's built-in LSP client sends `DidChangeConfiguration`, so `config.yaml` is optional.\n\n`init.lua` example (`settings` follows [`schema.md`](schema.md)):\n\n```lua\nrequire \"lspconfig\".efm.setup {\n    init_options = {documentFormatting = true},\n    settings = {\n        rootMarkers = {\".git/\"},\n        languages = {\n            lua = {\n                {formatCommand = \"lua-format -i\", formatStdin = true}\n            }\n        }\n    }\n}\n```\n\nYou can get premade tool definitions from [`creativenull/efmls-configs-nvim`](https://github.com/creativenull/efmls-configs-nvim):\n```lua\nlua = {\n  require('efmls-configs.linters.luacheck'),\n  require('efmls-configs.formatters.stylua'),\n}\n```\n\nIf you define your own, make sure to define as table:\n\n```lua\nlua = {\n    {formatCommand = \"lua-format -i\", formatStdin = true}\n}\n-- NOT\nlua = {\n    formatCommand = \"lua-format -i\", formatStdin = true\n}\n\n-- and for multiple formatters, add to the table\nlua = {\n    {formatCommand = \"lua-format -i\", formatStdin = true},\n    {formatCommand = \"lua-pretty -i\"}\n}\n```\n\n### Configuration for [Helix](https://github.com/helix-editor/helix)\n`~/.config/helix/languages.toml`\n```toml\n[language-server.efm]\ncommand = \"efm-langserver\"\n\n[[language]]\nname = \"typescript\"\nlanguage-servers = [\n  { name = \"efm\", only-features = [ \"diagnostics\", \"format\" ] },\n  { name = \"typescript-language-server\", except-features = [ \"format\" ] }\n]\n```\n\n### Configuration for [VSCode](https://github.com/microsoft/vscode)\n[Generic LSP Client for VSCode](https://github.com/llllvvuu/vscode-glspc)\n\nExample `settings.json` (change to fit your local installs):\n```json\n{\n  \"glspc.languageId\": \"lua\",\n  \"glspc.serverCommand\": \"/Users/me/.local/share/nvim/mason/bin/efm-langserver\",\n  \"glspc.pathPrepend\": \"/Users/me/.local/share/rtx/installs/python/3.11.4/bin:/Users/me/.local/share/rtx/installs/node/20.3.1/bin\",\n}\n```\n\n## License\n\nMIT\n\n## Author\n\nYasuhiro Matsumoto (a.k.a. mattn)\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fmattn%2Fefm-langserver","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fmattn%2Fefm-langserver","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fmattn%2Fefm-langserver/lists"}