New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add elixir support via dogma #969

Merged
merged 1 commit into from Aug 31, 2016

Conversation

Projects
None yet
5 participants
@kthelgason
Member

kthelgason commented May 17, 2016

This PR adds support for the Elixir language (as discussed in #877).
This relies on dogma for syntax checking, and so does not execute the code being checked as elixirc would.

Edit (@lunaryorn): Connects to #877

TODO:

  • Add predicate to make sure checker is not loaded when mix dogma is not available.
  • Parse dogma's JSON output format.
  • Tests for JSON parsing
flycheck.el Outdated
(message) line-end))
:modes elixir-mode)

This comment has been minimized.

@lunaryorn

lunaryorn May 17, 2016

Contributor

Please remove this blank line :)

@kthelgason kthelgason force-pushed the kthelgason:elixir-support branch from 05e3894 to 1fbb610 May 17, 2016

@kthelgason

This comment has been minimized.

Member

kthelgason commented May 17, 2016

@lunaryorn removed blank line and force-pushed :) thanks for taking a look.

flycheck.el Outdated
"An Elixir syntax checker using the Dogma analysis tool.
See URL `https://github.com/lpil/dogma/'."
:command ("mix" "dogma" "--format=flycheck" source-inplace)

This comment has been minimized.

@lunaryorn

lunaryorn May 17, 2016

Contributor

--format=flycheck?! 😊

dogma seems to support JSON output, though, and we generally prefer to parse structured output formats, which tend to be less fragile than plain text.

Would you mind to update this pull request to use an :error-parser that parses the JSON output of dogma?

This comment has been minimized.

@lunaryorn

lunaryorn May 17, 2016

Contributor

By the way how does mix know that dogma is available? Can we somehow test that to make sure that we don't enable this syntax checker when mix is there but dogma is not?

This comment has been minimized.

@lunaryorn

lunaryorn May 17, 2016

Contributor

And last but not least, do we need source-inplace, or can we feed the buffer contents to dogma via standard input?

@lunaryorn

This comment has been minimized.

Contributor

lunaryorn commented May 17, 2016

@kthelgason Thank you very much! It's great news to have Elixir back in, thanks for your work!

I've left a couple of comments on the diff, would you take a look?

@kthelgason

This comment has been minimized.

Member

kthelgason commented May 17, 2016

Thanks for the review @lunaryorn! As for your comments:

Would you mind to update this pull request to use an :error-parser that parses the JSON output of dogma?

I can do this, but it will involve more code and be more complicated. Here is an example of the JSON output:

{
  "metadata": {
    "dogma_version": "0.3.0",
    "elixir_version": "1.0.5",
    "erlang_version": "Erlang/OTP 10 [erts-7.0.3] [64-bit]",
    "system_architecture": "x86_64-apple-darwin14.5.0"
  },
  "files": [{
      "path": "lib/foo.ex",
      "errors": []
   }, {
      "path": "lib/bar.ex",
      "errors": [{
          "line": 1,
          "rule": "ModuleDoc",
          "message": "Module without @moduledoc detected"
       }, {
          "line": 14,
          "rule": "ComparisonToBoolean",
          "message": "Comparison to a boolean is useless"
       }
      ]
  }],
  "summary": {
    "error_count": 2,
    "inspected_file_count": 2
  }
}

It's up to you wether you think it's worth it :)

By the way how does mix know that dogma is available? Can we somehow test that to make sure that we don't enable this syntax checker when mix is there but dogma is not?

This is an excellent point, and I don't really have a good answer, perhaps you have some ideas as to how to accomplish this?

And last but not least, do we need source-inplace, or can we feed the buffer contents to dogma via standard input?

Unfortunately dogma does not currently support reading the source from stdin, but there is an open PR that implements that functionality. I can keep an eye on it and submit another PR when it lands.

@lunaryorn

This comment has been minimized.

Contributor

lunaryorn commented May 17, 2016

@kthelgason

It's up to you wether you think it's worth it :)

Yes, I do. Take a look at the tslint checker to see an example for JSON parsing. And—if you've a little more time to spare—maybe also take a look at test/specs/languages/test-typescript.el to see a test case for JSON parsing, and probably add a test case for parsing dogma errors? 😊

This is an excellent point, and I don't really have a good answer, perhaps you have some ideas as to how to accomplish this?

Flycheck checkers can supply a :predicate to add additional checks. Take a look at the go-vet syntax checker when looks at the installed Go tools to find out whether vet is available. Can we do something similar for mix? Is there a mix commands or similar which lists all available mix commands?

Unfortunately dogma does not currently support reading the source from stdin, but there is an open PR that implements that functionality. I can keep an eye on it and submit another PR when it lands.

Would you mind to link this PR here so that we can track its process, too?

Meanwhile, would source instead of source-inplace work? We generally prefer the former because it keeps temporary files out of the source tree…

@kthelgason

This comment has been minimized.

Member

kthelgason commented May 17, 2016

Certainly, I'll find some time to work on this in the coming days and ping you when I have something. Thanks for the suggestions!

Flycheck checkers can supply a :predicate to add additional checks. Take a look at the go-vet syntax checker when looks at the installed Go tools to find out whether vet is available. Can we do something similar for mix? Is there a mix commands or similar which lists all available mix commands?

Yup, this would totally work.

Would you mind to link this PR here so that we can track its process, too?

lpil/dogma#194

Meanwhile, would source instead of source-inplace work? We generally prefer the former because it keeps temporary files out of the source tree…

Yes, that should definitely work as well. I'll change that.

@lunaryorn

This comment has been minimized.

Contributor

lunaryorn commented May 17, 2016

@kthelgason Great, thank you very much 👍

@kthelgason

This comment has been minimized.

Member

kthelgason commented May 28, 2016

Update:
I'm pretty much done rewriting the checker to use dogma's json format. I ran into some issues with the checker itself and I'm working to get them upstreamed. I'm still waiting to resolve some issues before I can fully test the code I've written here. Will update again when I've gotten this resolved.

@kthelgason kthelgason force-pushed the kthelgason:elixir-support branch from 1fbb610 to eab7432 May 28, 2016

@kthelgason kthelgason force-pushed the kthelgason:elixir-support branch from eab7432 to 55ddf2a Jun 9, 2016

@kthelgason

This comment has been minimized.

Member

kthelgason commented Jun 9, 2016

Update:

There were some issues with using dogma as a mix command so I've added support for running dogma standalone. I'm going to submit a PR to dogma to get those changes in. Meanwhile I've updated this PR to work with that version of dogma. I've been running it in this configuration for a while and it seems to work well.

I apologise in advance if I'm doing something stupid in this PR, this is the first real code I write in elisp.

cc @lunaryorn

@lunaryorn

This comment has been minimized.

Contributor

lunaryorn commented Jul 15, 2016

@kthelgason May I ask what's the status of this? Is the change to dogma already submitted? Is this PR ready for being merged?

@kthelgason

This comment has been minimized.

Member

kthelgason commented Jul 17, 2016

@lunaryorn Absolutely. The change has been pulled into dogma, so the code in this PR works with the current version. As for whether it's ready to be merged, you tell me 😄 from my perspective it's done.

@kthelgason

This comment has been minimized.

Member

kthelgason commented Aug 18, 2016

I screwed up some settings and had to to battle with the CLA bot, luckily I won 😄 I cherry-picked @sergv's commit and tested it, I can confirm that the checker works brilliantly.

Also refactored according to the review, thanks for that @lunaryorn, great comments as usual!

@lunaryorn

This comment has been minimized.

Contributor

lunaryorn commented Aug 19, 2016

@kthelgason Awesome, great news. It's ready to be merged then.

But please remove @sergv's commit from this PR again, as we'll merge it separately n #1040 before merging this one. Finally please squash all commits into a single one.

Sorry for being such a nuisance to you 😌

@kthelgason kthelgason force-pushed the kthelgason:elixir-support branch from a90d8e5 to e1f3d58 Aug 22, 2016

@kthelgason

This comment has been minimized.

Member

kthelgason commented Aug 22, 2016

@lunaryorn Done and done! Thanks for helping me out with this @lunaryorn and @sergv

flycheck.el Outdated
"Come up with a suitable default directory to run CHECKER in.
This will either be the directory that contains `mix.exs' or,
if no such file is found in the directory hierarchy, ths directory

This comment has been minimized.

@cpitclaudel

cpitclaudel Aug 25, 2016

Member

ths → the?

flycheck.el Outdated
(defun flycheck-elixir--parse-dogma-json (output checker buffer)
"Parse dogma errors from JSON OUTPUT.
CHECKER and BUFFER denoted the CHECKER that returned OUTPUT and

This comment has been minimized.

@cpitclaudel

cpitclaudel Aug 25, 2016

Member

denoted → denote?

Check by parsing the output of `mix help'.
Used as a predicate for enabling the checker."
(let ((mix (flycheck-checker-executable 'elixir-dogma)))
(seq-find (lambda (l) (string-match-p "dogma" l))

This comment has been minimized.

@cpitclaudel

cpitclaudel Aug 25, 2016

Member

This lambda could be written with apply-partially (I don't know if it would actually be better)

This comment has been minimized.

@kthelgason

kthelgason Aug 25, 2016

Member

I feel that would only serve to make it less clear in this case.

flycheck.el Outdated
default-directory))
(defun flycheck-elixir--parse-dogma-json (output checker buffer)
"Parse dogma errors from JSON OUTPUT.

This comment has been minimized.

@cpitclaudel

cpitclaudel Aug 25, 2016

Member

dogma → Dogma?

@@ -6262,6 +6263,63 @@ Requires DMD 2.066 or newer. See URL `http://dlang.org/'."
(one-or-more " ") (message) line-end))
:modes d-mode)
(defun flycheck-elixir--find-default-directory (_checker)
"Come up with a suitable default directory to run CHECKER in.

This comment has been minimized.

@cpitclaudel

cpitclaudel Aug 25, 2016

Member

This could say "to run Dogma in", since _checker is in fact ignored.

This comment has been minimized.

@kthelgason

kthelgason Aug 25, 2016

Member

As with the names, I'd prefer to keep the functions that can be reused checker-agnostic.

@cpitclaudel

This comment has been minimized.

Member

cpitclaudel commented Aug 25, 2016

This looks very good. I commented on the diff about a few typos.
Question: why are the functions called flycheck-elixir rather than flycheck-dogma? (this could be a convention that I'm just not aware of :)

@kthelgason

This comment has been minimized.

Member

kthelgason commented Aug 25, 2016

@cpitclaudel I'll try to address your comments later today or tomorrow, thanks for looking over the PR.
The reason I went with that naming (inspired by some other checker, can't recall which now) was that I hope to add support for more elixir checkers (credo) soon, in which case functions such as flycheck-elixir--find-default-directory could be shared.

@lunaryorn

This comment has been minimized.

Contributor

lunaryorn commented Aug 25, 2016

I don't mind the name; these functions looks sufficiently generic imho to be named after the language.

@cpitclaudel

This comment has been minimized.

Member

cpitclaudel commented Aug 25, 2016

Thanks for the clarification (and for your efforts!). Everything LGTM modulo the small typos :)

@kthelgason kthelgason force-pushed the kthelgason:elixir-support branch from e1f3d58 to ca035a3 Aug 25, 2016

@kthelgason

This comment has been minimized.

Member

kthelgason commented Aug 25, 2016

I fixed the typos and tried to come up with excuses for the comments I ignored 😄
Please give this one last look, Thanks!

@cpitclaudel

This comment has been minimized.

Member

cpitclaudel commented Aug 25, 2016

Looks perfect. @lunaryorn?

@lunaryorn

This comment has been minimized.

Contributor

lunaryorn commented Aug 30, 2016

Uh, sh**, I knew I had forgotten a pull request for the last release 😢

LGTM, but unfortunately CHANGES.rst is now out of date as we're now heading towards Flycheck 30. 😞

@kthelgason I'm so sorry to bother you again but could you just update CHANGES.rst to note the change under Flycheck 30 before you merge? I'm sorry for all the nuisance 😞

@kthelgason kthelgason force-pushed the kthelgason:elixir-support branch from ca035a3 to 2ee668d Aug 30, 2016

@kthelgason

This comment has been minimized.

Member

kthelgason commented Aug 30, 2016

Don't worry about it! I fixed CHANGES.rst (I think) and pushed. 😄

@lunaryorn

This comment has been minimized.

Contributor

lunaryorn commented Aug 31, 2016

Feel free to merge then 😊

@kthelgason kthelgason merged commit e10f40c into flycheck:master Aug 31, 2016

3 checks passed

approvals/lgtm this commit looks good
continuous-integration/travis-ci/pr The Travis CI build passed
Details
licence/cla Contributor License Agreement is signed.
Details

@kthelgason kthelgason deleted the kthelgason:elixir-support branch Aug 31, 2016

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment