--- /dev/null
+" Asynchronous pylint utility call
+" Maintainer: Sergey Matveev <stargrave@stargrave.org>
+" License: GNU General Public License version 3 of the License or later
+"
+" This plugin allows you to asynchronously call pylint.
+"
+" * Press <F6> to start pylint on current file
+" * Press <S-F6> to open quickfix window with messages from pylint
+" * All lines with corresponding pylint existing warning will be highlighted
+" * If no warning and errors occurred, "pylint is clean" message will be shown
+" * If existing quickfix window is found, then it won't be overwritten.
+" Start pylint manually (<F6>) to force its filling
+" * After Python file is saved, pylint is automatically started
+
+function! python#lint#status()
+ if exists("b:pylint_job") && job_status(b:pylint_job) == "run" | return "LN" | endif
+ return ""
+endfunction
+
+function! s:qffill(ch) abort
+ let msgs = []
+ while ch_status(a:ch) == 'buffered'
+ let msgs = add(msgs, ch_read(a:ch))
+ endwhile
+ cgetexpr msgs
+endfunction
+
+sign define LN text=LN texthl=Error
+
+function! python#lint#finish(ch) abort
+ let l:errorformat_bak = &errorformat
+ set errorformat=%f:%l:\ [%t]%m,%f:%l:%m
+ call s:qffill(a:ch)
+ let &errorformat=l:errorformat_bak
+ sign unplace *
+ let l:id = 2
+ for item in getqflist()
+ if item.lnum == 0 | continue | endif
+ execute(':sign place '.l:id.' name=LN line='.l:item.lnum.' buffer='.l:item.bufnr)
+ let l:id = l:id + 2
+ endfor
+ redraw!
+ if l:id == 2
+ echohl MoreMsg | echomsg "pylint is clean" | echohl None
+ cclose
+ endif
+endfunction
+
+function! python#lint#start() abort
+ if exists("g:pylint_disable") ||
+ \ (exists("b:pylint_job") &&
+ \ job_status(b:pylint_job) == "run")
+ return
+ endif
+ let ignores = [
+ \"locally-disabled",
+ \"no-init",
+ \"no-self-use",
+ \"too-few-public-methods",
+ \"missing-docstring",
+ \"too-many-instance-attributes",
+ \"invalid-name",
+ \"too-many-arguments",
+ \"too-many-locals",
+ \"too-many-public-methods",
+ \"no-value-for-parameter",
+ \]
+ let linter = get(g:, "pylint_linter", "pylint")
+ if linter == "flake8"
+ let cmdline = [
+ \"flake8",
+ \"--ignore=E501",
+ \"--format=%(path)s:%(row)d: [%(code)s] %(text)s",
+ \"--max-line-length=90",
+ \expand("%p")
+ \]
+ elseif linter == "pylint"
+ let cmdline = [
+ \"pylint",
+ \"--jobs=4",
+ \"--reports=n",
+ \"--msg-template={path}:{line}: [{msg_id}({symbol}), {obj}] {msg}",
+ \"--disable=" . join(ignores, ","),
+ \"--persistent=n",
+ \"--score=no",
+ \expand("%p")
+ \]
+ else
+ echohl WarningMsg | echomsg "Unknown linter specified" | echohl None
+ return
+ endif
+ let b:pylint_job = job_start(cmdline,
+ \ {"in_mode": "nl", "err_io": "null", "close_cb": "python#lint#finish"})
+endfunction