Fork me on GitHub
#clj-kondo
<
2023-01-06
>
phronmophobic21:01:37

I'm using clj-kondo to statically analyze projects for dewey. I'm interested in adding custom analyzers. It seems like there's no way to add additional analyzers. Is that right? I see that it's possible to add hooks and that hooks can emit findings, but it doesn't seem like there's a way to emit analyses? Maybe there's not much of a difference between "findings" and "analysis results"? As an example, I'm interested in extracting all the spec definitions within a project.

borkdude22:01:52

I think clojure.spec more runtime oriented than amenable to static analysis. I've tried to cross that bridge here a bit: https://github.com/clj-kondo/inspector

borkdude22:01:02

We could make the SCI environment pluggable so you can do anything you need in your hooks, e.g. spit out stuff to a database or whatever. But you could experiment with this in a fork to start, I think

👍 2
phronmophobic22:01:54

I think it would be valuable just to have the keyword for each spec and the definition form

borkdude22:01:39

we do have those keywords for clojure.spec already, I think there's a defined-by clojure.spec.alpha key on them in the keywords analysis or so

phronmophobic22:01:41

and doc strings once there’s support

borkdude22:01:50

but there is no definition yet

phronmophobic22:01:29

I’m generally interested in custom analyzers. The spec defs is just an example

borkdude22:01:54

there is some custom analysis available, you can add :context to something and this could be anything - I'd have to look this up how it works exactly

phronmophobic22:01:52

cool! so I would create a hook and return some data in a :context key?

borkdude22:01:53

yes. you would add to the keyword some :context {:my-thing "blob"} and if you then request analysis with {:content [:my-thing]} or {:context true} , the keyword will appear with that data in the analysis

borkdude22:01:17

this was more a way to add arbitrary properties to existing analysis, but I think we could also allow inserting whatever analysis you like to see

lread18:01:49

This reminds me of my wip experiment of switching to clj-kondo data analysis for MrAnderson, the library inliner tool. I think kondo analysis data has got all I might need for namespace renames but I was less sure about import renames. Nice to remember that I might use :context if I need it.

phronmophobic19:03:16

Finally getting a chance to play with clj-kondo's hooks for static analysis. I just forked clj-kondo to add support for using functions as hooks to help with programmatic support, https://github.com/clj-kondo/clj-kondo/compare/master...phronmophobic:clj-kondo:master Usage

(defn my-def-hook [o]
  (prn "hi")
  o)

(defn analyze-project [paths]
  (let [config {:cache false
                :lint paths
                :config {:analysis {:locals true
                                    :keywords true
                                    :arglists true
                                    :protocol-impls true
                                    :var-definitions {:meta true}
                                    :namespace-definitions {:meta true}}
                         :hooks
                         {:analyze-call
                          {'clojure.core/def my-def-hook}}
                         :linters (default-linters-off)}}]
    (clj-kondo/run! config)))
Is this something clj-kondo would be interested in. Should I start a pull request?

borkdude19:03:30

I'm not exactly sure what you're trying to do. JVM functions vs SCI interpreter functions? Maybe you can describe a problem instead of a solution?

phronmophobic19:03:00

Sure, dewey is a project that tries to collect information on all the clojure projects on github. As part of that, I run clj-kondo's static analysis to collect information, https://blog.phronemophobic.com/dewey-analysis.html. Currently, the analysis relies on the built in options that clj-kondo offers. I'd like to expand the analysis to include things like all of the spec definitions for every project.

phronmophobic19:03:20

Based off the previous answers in this thread, it seemed like the best way to do that was to write custom hooks to return extra context.

borkdude19:03:16

Sure, this seems like a small innocent change, so PR welcome. You may want to include a test so we don't accidentally break it later. You may also be able to do this without this change and use the :context option, to include extra information on the spec-ed keyword, which will end up in the analysis data

👍 2
phronmophobic19:03:09

Right, collecting specs is just an example.

borkdude19:03:34

in fact, I think keywords that are "defined by" spec already have this data

phronmophobic19:03:14

Does it include the spec definition?

borkdude19:03:53

since clojure-lsp uses this for navigating to the definition and usages of a spec (by keyword). no. what would you do with the definition?

phronmophobic19:03:33

Specs are meant to be global. having a global of db specs makes sense to me

phronmophobic19:03:43

Part of collecting this information is to find out how specs are being used so part of the answer will be easier to answer once I have the data.

👍 2
borkdude19:03:06

PR welcome btw, I think it makes sense to be able to do your own thing for such purposes

phronmophobic19:03:33

Is there a way to write hooks for host interop (js or java)? One of the topics that comes up in #C053AK3F9 is figuring what parts of Java are worth learning. One way to approach that question is to figure which host interop clojure programs are currently using.

borkdude19:03:34

This is a good question. This is the issue: https://github.com/clj-kondo/clj-kondo/issues/1603 I'm not sure if we want to re-use :analyze-call for this or have another kind of hook

👍 2
phronmophobic19:03:12

Awesome. I can also prototype some ideas locally.

borkdude19:03:21

for one-off questions, I also use https://github.com/borkdude/grasp a lot

👍 2
phronmophobic19:03:24

Also, not sure if you saw this. Visualizations of all the clojure namespaces and their requires. gray is just the edges and the dots are the namespaces.

🤯 2
borkdude19:03:41

is the red area clojure itself?

phronmophobic19:03:53

Working on a more detailed write up

borkdude19:03:07

cool stuff :)

phronmophobic00:03:34

Just saw this! https://github.com/clj-kondo/clj-kondo/commit/d4bce65db2284c2c288e94795ebc9b1d713dad12 This is awesome. Going to try this in a dewey analysis soon!

phronmophobic19:03:16

Finally getting a chance to play with clj-kondo's hooks for static analysis. I just forked clj-kondo to add support for using functions as hooks to help with programmatic support, https://github.com/clj-kondo/clj-kondo/compare/master...phronmophobic:clj-kondo:master Usage

(defn my-def-hook [o]
  (prn "hi")
  o)

(defn analyze-project [paths]
  (let [config {:cache false
                :lint paths
                :config {:analysis {:locals true
                                    :keywords true
                                    :arglists true
                                    :protocol-impls true
                                    :var-definitions {:meta true}
                                    :namespace-definitions {:meta true}}
                         :hooks
                         {:analyze-call
                          {'clojure.core/def my-def-hook}}
                         :linters (default-linters-off)}}]
    (clj-kondo/run! config)))
Is this something clj-kondo would be interested in. Should I start a pull request?