Code Monkey home page Code Monkey logo

diagnosticls-configs-nvim's Introduction

diagnosticls-configs-nvim

Configs on dotfyle

An unofficial collection of linter and formatter configurations for diagnostic-languageserver to work with builtin nvim-lsp. Works only for Neovim >= 0.5.

Supported linters and formatters

Check out supported-linters-and-formatters.md

Features

  • Intelligently detect tools installed project-wide or system-wide - works only for node/npm, php/composer and ruby/bundler, additional support for other build tools coming soon.
  • Use :checkhealth to see any missing tools.
  • Customize configs for your project needs.

Installation

Requirements

You will need to install diagnostic-languageserver and nvim-lspconfig before using this plugin.

Packer.nvim

use {
    'creativenull/diagnosticls-configs-nvim',
    tag = 'v0.1.8', -- `tag` is optional
    requires = 'neovim/nvim-lspconfig',
}

Vim-plug

Plug 'neovim/nvim-lspconfig'
Plug 'creativenull/diagnosticls-configs-nvim', { 'tag': 'v0.1.8' } " tag is optional

Setup

First you need to initialize the plugin, this is where you can pass your own LSP options:

-- Lua file
local function on_attach(client)
  print('Attached to ' .. client.name)
end

local dlsconfig = require 'diagnosticls-configs'

dlsconfig.init {
  -- Your custom attach function
  on_attach = on_attach,
}

Finally, setup the linters/formatters according to the filetype, here is an example for running eslint and prettier for javascript and javascriptreact filetype:

-- Lua file
local eslint = require 'diagnosticls-configs.linters.eslint'
local standard = require 'diagnosticls-configs.linters.standard'
local prettier = require 'diagnosticls-configs.formatters.prettier'
local prettier_standard = require 'diagnosticls-configs.formatters.prettier_standard'
dlsconfig.setup {
  ['javascript'] = {
    linter = eslint,
    formatter = prettier
  },
  ['javascriptreact'] = {
    -- Add multiple linters
    linter = { eslint, standard },
    -- Add multiple formatters
    formatter = { prettier, prettier_standard }
  }
}

Default configuration

A default configuration for the supported filetypes is provided but not activated by default.

To activate the default configuration you can pass the default_config flag as true in the init function. Below are the default values for init:

-- Lua file
dlsconfig.init {
  -- Use a list of default configurations
  -- set by this plugin
  -- (Default: false)
  default_config = false,

  -- Set to false if formatting is not needed at all,
  -- any formatter provided will be ignored
  -- (Default: true)
  format = true,
}

dlsconfig.setup()

You will still need to call the setup() after init() for the changes to take effect. You can still pass your custom configurations to setup() as show in the Setup section and it will override any default configuration set by default_config if it's for the same filetype.

NOTE: For format option it does not imply that it will "format on save". You still need to setup that in your lsp on_attach handler.

Advanced Configuration

If default configurations of a linter/formatter do not work for your use-case, or there are additional configuration that needs to be added which is not provided by default. Then you can extend the built-in configurations with your own modifications. The API is the same as diagnostic-languageserver Initialization Options on linter/formatter structure. You can use vim.tbl_extend() to extend these tables:

-- Lua file
local eslint = require 'diagnosticls-configs.linter.eslint'

-- ESLint Extented Config
eslint = vim.tbl_extend('force', eslint, {

  -- REQUIRED: if `default_config` is enabled, separate name from original sourceName
  sourceName = 'eslint_extended',

  args = { 'extra', 'args' },
  rootPatterns = { '.git' }
})

dlsconfig.setup {
  javascript = {
    linter = eslint
  }
}

NOTE: If you have default_config enabled, then sourceName needs to be a different name to the provided name, you can just add _extended or any other unique name to the extended configuration will work. This is because other defaults might use the same linter of the same sourceName and would default to use that instead of your own extended configuration.

TODO

  • Tests with busted/vusted or plenary - using plenary test_harness
  • Use :checkhealth to display status of linters/formatters registered with plugin
  • Add ability to override args, root patterns, etc
  • Add vim docs
  • Add contributing content
  • Add feature to allow multiple linters/formatters: see ref

Contributing

First of all, thank you for your contribution ๐Ÿ™‚!

To help create configurations start with the diagnostic-languageserver API to know how the object is structured for a linter or a formatter. Also check out the wiki to see some examples. Finally, check out the configurations created in the lua/diagnosticls-configs/linters and lua/diagnosticls-configs/formatters and see how they are implemented.

Tools required for linting and formatting for this project (which are also supported by this plugin):

For testing, add the relevant test logic in tests/diagnosticls-configs and then run:

make test

Credits

Credits goes to the following repos for inspiration:

  • Diagnostic Language Server - for example configs in json format
  • ale - for a vibrate list of supported linters/formatters to look through and implement

diagnosticls-configs-nvim's People

Contributors

academo avatar bentilley avatar creativenull avatar danielloney avatar dirtyhabits97 avatar euclio avatar vianney-g avatar whoissethdaniel avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar

diagnosticls-configs-nvim's Issues

Create formatting config for `eslint_d`

Hi, thanks for this plugin, it works very well and abstracts a lot of config.

Only the eslint formatting didn't work me, but I don't have eslint globally installed so that might be it. I think it might be good to have a config for formatting with eslint_d as it's much faster than eslint. Might also be good to write a note about that as people might not be aware.

Currently achieving it like so:

local eslint_fmt = require 'diagnosticls-configs.formatters.eslint_fmt'
local fs = require 'diagnosticls-configs.fs'

-- Use eslint_d deamon instead of eslint
local eslint_fix = vim.tbl_extend('force', eslint_fmt, {
  sourceName = 'eslint_d',
  command = fs.get_executable('eslint_d', 'node'),
})

Unifying init() and setup() function into one

Hi,

I would like to figure out why are init() and setup() functions separate? I'm thinking that simplifying it and using only a setup() function would be more straightforward. Something like this:

require 'diagnosticls-configs'.setup({
  default_config = false,
  format = false,
  on_attach = on_attach,
  filetypes = {}, -- same what current setup() accepts
})

I was creating a project specific setup and ran into this issue where I need to call both init() and setup() to override the functionality. In my init.vim I have default_config = true, but for one of my projects, I need to have specific settings, which I had to override with an init({ default_config = false }) call. It wasn't fully clear to me at first that I need to do that.
I'm assuming this is done for a reason, but I can't figure out which one.

Generally, plugin works great, and thank you for building it. My diagnosticls setup started to grow over time and this cleaned it up tremendously.

Fix global fallback in fs.lua

I'd suggest doing the following in fs.lua.

  if vim.fn.filereadable(binpath) == 0 then
-   add_checkhealth_error(name)
+   return ''
  end
    if local_binpath == '' then
      return get_global_exec(name)
    end
+   add_checkhealth_error(name)

    return local_binpath

The reason for this is that you probably want to check the PATH if there is no ~/node_modules for example. I have many Node-based linters and formatters installed globally through my system package manager and they're in /usr/bin instead of ./node_modules/.bin and patching the files as described made everything work. This will likely fix system/user global NPM packages too.

Please give me thoughts on this idea.

Per-project linter config

Is there a way to set up per-project diagnostic configurations? I'm using AutoSource to allow me to load a custom configuration per-project, so for example one project uses tabs and the other spaces.

I have one project using the WordPress PHP standards for phpcs, and another that uses PSR2. Currently, I'm hand-editing the diagnostic config file whenever I switch projects which is not ideal.

luacheck only lints on write

Copy/pasted the luacheck config, I have luacheck installed, and it gives no diagnostics. There's no errors in ~/.cache/nvim/lsp.log

> luacheck --version
Luacheck: 0.23.0
Lua: PUC-Rio Lua 5.4
Argparse: 0.7.1
LuaFileSystem: 1.8.0
LuaLanes: Not found

Ability to extend the linter/formatter config

Users should be able to extend the config and add their own mix, if default configs don't work, or if some linters/formatters depend on the CLI for settings instead of a project config file.

We don't want to be breaking anything on the user side.

The API for this can take many forms, the one I was heavily leaning on was the following:

-- default config
local eslint = require 'diagnosticls-configs.linters.eslint'

-- config extended and overwritten with the table provided
local eslint = require 'diagnosticls-configs.linters.eslint'.extend {
  args = {'some', 'args'}
}

Another one was to create and extend the config:

local extend = require 'diagnosticls-configs.util'.extend
local eslint = require 'diagnosticls-configs.linters.eslint'

eslint = extend(eslint, {
  args = {'some', 'args'}
})

Finally, we can just direct the user to use vim.tbl_extend to make use of the same interface:

local eslint = require 'diagnosticls-configs.linters.eslint'

eslint = vim.tbl_extend('force', eslint, {
  args = {'some', 'args'}
})

diagnosticls-nvim/init.lua:77: bad argument #1 to 'pairs'

Error

Failed to load my/plugin/lspconfig
...r/start/diagnosticls-nvim/lua/diagnosticls-nvim/init.lua:77: bad argument #1 to 'pairs' (table expected, got function)

My config

require'diagnosticls-nvim'.setup{
  on_attach = attacher,
  ['ruby'] = { linter = require'diagnosticls-nvim.linters.rubocop' },
  ['vim'] = { linter = require'diagnosticls-nvim.linters.vint' }
}

Simplify setup code

Omit init() and setup() just like it was done in creativenull/efmls-configs-nvim#30.

The reason being that having two separate functions to have the user setup is not very friendly, the preference would be to keep setup code as minimal as possible, at the same time, provide more flexibility to the user if in case they might want to adjust some settings.

But since the API is different in diagnostic-languageserver compared to efm-langserver, I'm thinking of creating a wrapper to generate the LSP config and then have the user merge them on lspconfig.diagnosticls.setup().

New proposal example:

local eslint = require('diagnosticls-configs.linters.eslint')
local prettier = require('diagnosticls-configs.formatters.prettier')

local diagnosticls_config = require('diagnosticls-configs').create({
  javascript = {
    linters = { eslint },
    formatters = { prettier },
  },
  typescript = {
    linters = { eslint },
    formatters = { prettier },
  },
})

require('lspconfig').diagnosticls.setup(vim.tbl_extend('force', diagnosticls_config, {
  on_attach = on_attach,
  capabilities = capabilities,
})

For defaults:

local diagnosticls_config = require('diagnosticls-configs').defaults()

To add additional languages or to overrides defaults, just pass the same table structure as in create():

local diagnosticls_config = require('diagnosticls-configs').defaults({
  javascript = {
    linters = { eslint },
    formatters = { prettier },
  },
})

Override phpcs args

Hi,

Is it possible to override the args settings for phpcs?

from
args = {'--standard=PSR2', '--report=emacs', '-s', '-'},

to
args = {'--standard=PSR12'}

eslint security configuration is not passed to language server properly

From looking at my language server logs, I see that the eslint security configuration is getting passed as securities = { "warning", "error" }, when it should be passed as securities = { "1" = "warning", "2" = "error" }. I'm not sure where things are going wrong, but it seems like something (neovim, nvim-lspconfig, this plugin?) can't distinguish between a map and an array here.

Linting files in directories without '.git'

How to reproduce

  1. Create a *.sh file in a folder without .git
  2. Open the file with neovim

What happens?

The plugin doesn't get attached:

Screen Shot 2021-09-18 at 15 54 24

I expected the plugin to be attached with shellcheck as the linter.
When I attach it inside a git repo it works:

Screen Shot 2021-09-18 at 15 56 53


My config

local dlsconfig = require 'diagnosticls-configs'
local shellcheck = require 'diagnosticls-configs.linters.shellcheck'
local swiftlint = require 'diagnosticls-configs.linters.swiftlint'

swiftlint = vim.tbl_extend('force', swiftlint, {
  rootPatterns = {'Package.swift', '.git'}
})

dlsconfig.setup {
  ['sh'] = {
    linter = shellcheck
  },
  ['swift'] = {
    linter = swiftlint
  },
}

The same thing happens with swiftlint. Notice how in my config I specify {'Package.swift', '.git'} as the root pattern.
In my folder's root I have a Package.swift file, but the plugin doesn't attach:

Screen Shot 2021-09-18 at 16 00 20


I noticed that this is the only place where root_dir is referenced.

root_dir = require'lspconfig'.util.root_pattern('.git'),

To make SwiftLint work, I changed it to:

root_dir = require'lspconfig'.util.root_pattern('Package.swift', '.git'), 

To make shellcheck work, I changed it to:

root_dir = function(fname)
  return util.root_pattern '.git'(fname) or util.path.dirname(fname)
end,
``

Change plugin name

diagnosticls-nvim sounds too vague and makes no sense as to what the plugin does, until a user reads the README. Suggested plugin names below.

Namely prefixed with one of:

  • dls
  • diagnosticls
  • diagnostic-languageserver

Then suffixed with one of (the - can be replaced with .):

  • config-nvim
  • settings-nvim
  • options-nvim

For example, with the combination above, we can construct the name like: diagnosticls-config-nvim or diagnosticls-config.nvim

I guess something short would be nice, will be looking toward more nvim plugins for naming conventions.

Black formatter defaults to writing to disk instead of using available stdio

Here's this repo's config for black:

local fs = require('diagnosticls-configs.fs')

return {
  sourceName = 'black',
  command = fs.executable('black'),
  args = { '%filepath' },
  doesWriteToFile = true,
  rootPatterns = {
    '.git',
    'pyproject.toml',
    'setup.py',
  },

This command writes to disk (doesWriteToFile = true). Isn't it more natural for a language server formatter to use stdio? This is also the default behavior for formatters in diagnosticls. Does this repo have a differetn philosophy about default behavior for formatters? To change black to use stdio by default, one could use this:

local fs = require('diagnosticls-configs.fs')

return {
  sourceName = 'black',
  command = fs.executable('black'),
  args = { '-' },
  rootPatterns = {
    '.git',
    'pyproject.toml',
    'setup.py',
  },

Adding swiftlint

Hey @creativenull,

I'm trying to add swiftlint to diagnosticls-nvim, however, it doesn't seem to be working as expected.

In my init.lua I had the following

require'diagnosticls-nvim'.init{}
require'diagnosticls-nvim'.setup{
  ['swift'] = {
    linter = {
      sourceName = 'swiftlint',
      command = "swiftlint",
      debounce = 100,
      args = {
        'lint',
        '--use-stdin',
        "--quiet",
        "--reporter",
        "json",
      },
      rootPatterns = {
        '.git',
      }
    }
  }
}

I tried to draw inspeeration from existing plugins in other editors like vscode: https://github.com/vknabel/vscode-swiftlint/blob/master/src/lint.ts

It would be awesome if you can point out why it didn't work for me or what I missed.

Thanks

Error on startup

Error detected while processing /Users/sam/.config/nvim/init.lua:
E5113: Error while calling lua chunk: ...ker/opt/diagnosticls-nvim/lua/diagnosticls-nvim/init.lua:93: table index is nil

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.