This changelog is loose. Versions are not semantic, they are incremental. Splint is not meant to be infrastructure, so don't rely on it like infrastructure; it is a helpful development tool.
-v
and --version
cli flags to print the current version.--config TYPE
cli flag to print the diff
, local
, or full
configuration.splint.rules.helpers.parse-defn
when trying to parse ill-formed function definitions.#(do [%1 %2])
in style/useless-do
, add docstring note about it.naming/single-segment-namespace
: Prefer (ns foo.bar)
to (ns foo)
.lint/prefer-require-over-use
: Prefer (:require [clojure.string ...])
to (:use clojure.string)
. Accepts different styles in the replacement form: :as
, :refer [...]
and :refer :all
.naming/conventional-aliases
: Prefer idiomatic aliases for core libraries ([clojure.string :as str]
to [clojure.string :as string]
).naming/lisp-case
: Prefer kebab-case over other cases for top-level definitions. Relies on camel-snake-kebab.style/multiple-arity-order
: Function definitions should have multiple arities sorted fewest arguments to most: (defn foo ([a] 1) ([a b] 2) ([a b & more] 3))
lint/fn-wrapper
introduced in v1.2.3.*warn-on-reflection*
to all rules and rule template.:spat/import-ns
metadata as way to track when a symbol has been imported.noahtheduke.spat.pattern/simple-type
for performance.volatile
instead of atom
for bindings in noahtheduke.spat.pattern
.keep
to reduce
to avoid seq and laziness manipulation.some->
where appropriate for short-circuiting.&&.
rest args and parsed lists in :on-match
handlers by attaching :noahtheduke.spat.pattern/rest
metadata to bound rest args.edamame
to v1.3.21 to handle #:: {:a 1}
auto-resolved namespaced maps with spaces between the colons and the map literal.lint/thread-macro-one-arg
supports :inline
and :avoid-collections
styles.:updated
field in configuration edn, show in rule docs.:guide-ref
for style/prefer-clj-math
.<hr>
between each rule's docs.lint/dorun-map
.deploy
justfile recipe.markdown
output: Same text as full
but with a fancy horizontal bar, header, and code blocks.:chosen-style
allows for rules to have configuration and different "styles". The first supported is lint/not-empty?
showing either seq
or not-empty
.ctx
is no longer an atom, but a plain map. The :diagnostics
entry is now the atom.splint.runner/check-form
returns the entire updated ctx
object instead of just the diagnostics. (I'm not entirely sure that's reasonable, but it's easily changed.)lint
to style
genre:
apply-str
apply-str-interpose
apply-str-reverse
assoc-assoc
conj-vector
eq-false
eq-nil
eq-true
eq-zero
filter-complement
filter-vec-filterv
first-first
first-next
let-do
mapcat-apply-apply
mapcat-concat-map
minus-one
minus-zero
multiply-by-one
multiply-by-zero
neg-checks
nested-addition
nested-multiply
next-first
next-next
not-eq
not-nil
not-some-pred
plus-one
plus-zero
pos-checks
tostring
update-in-assoc
useless-do
when-do
when-not-call
when-not-do
when-not-empty
when-not-not
ctx
as first argument to :on-match
functions to pass in config to rules. Update functions in splint.runner
as necessary.noahtheduke.spat.pattern
functions.:spat/lit
metadata to treat special symbols in pattern DSL as their literal values.clojure.core
, then in noahtheduke.splint.rules.helpers
.:var
to :binding
.style/def-fn
: Prefer (let [z f] (defn x [y] (z y)))
over (def x (let [z f] (fn [y] (z y))))
lint/try-splicing
: Prefer (try (do ~@body) (finally ...))
over (try ~@body (finally ...))
.lint/body-unquote-splicing
: Prefer (binding [max mymax] (let [res# (do ~@body)] res#))
over (binding [max mymax] ~@body)
.--parallel
and --no-parallel
for running splint in parallel or not. Defaults to true
.:uneval
config option for :splint/disable
.build.clj
to resources/SPLINT_VERSION
.naming/record-name
: Add :message
.style/prefer-condp
: Only runs if given more than 1 predicate branch.style/set-literal-as-fn
: Allow quoted symbols in sets.Actually wrote out something of a changelog.
:new-rule
task now creates a test stub in the correct test directory.#_:splint/disable
is treated as metadata on the following form and disables all rules. #_{:splint/disable []}
can take genres of rules ([lint]
) and/or specific rules ([lint/loop-do]
) and disables those rules. See below (Thoughts and Followup) for discussion and Configuration for more details.lint/duplicate-field-name
: (defrecord Foo [a b a])
naming/conversion-functions
: Should use x->y
instead of x-to-y
.style/set-literal-as-fn
: Should use (case elem (a b) true false)
instead of (#{'a 'b} elem)
defrule
now requires the provided rule-name to be fully qualified, and doesn't perform any *ns*
magic to derive the genre.:init-type
in defrule
to handle symbol matching.:dispatch
reader macros provided by Edamame now wrap their sexps in the appropriate (splint/X sexp)
form, to distinguish them from the symbol forms. Aka #(inc %)
is now rendered as (splint/fn [%1] (inc %1))
, vs the original (fn* ...)
, or #'x
is now (splint/var x)
vs (var x)
. This allows for writing rules targeting the literal form instead of the symbol form, and requires that rule patterns rely on functions in noahtheduke.splint.rules.helpers
to cover these alternates.noahtheduke.splint.rules.helpers
as an autoresolving namespace so rules can use predicates defined within it without importing or qualifying.violation
to diagnostic
.lint/duplicate-field-name
wasn't checking that ?fields
was a vector before calling count
on it.I want another parser because I want access to comments. Without comments, I can't parse magic comments, meaning I can't enable or disable rules inline, only globally. That's annoying and not ideal. However, every solution I've dreamed up has some deep issue.
Edamame is our current parser and it's extremely fast (40ms to parse clojure/core.clj
) but it drops comments. I've forked it to try to add them, but that would mean handling them in every other part of the parser, such as syntax-quote and maps and sets, making dealing with those objects really hard. :sob:
Rewrite-clj only exposes comments in the zip api, meaning I have to operate on the zipper objects with zipper functions (horrible and slow). It's nice to rely on Clojure built-ins instead of (loop [zloc zloc] (z/next* ...))
nonsense.
clj-kondo is faster than rewrite-clj and has a nicer api, but the resulting tree isn't as easy to work with as Edamame and it's slower. Originally built Spat in it and found it to be annoying to use.
parcera looked promising, but the pre-processing in parcera/ast
is slow and operating on the Java directly is deeply cumbersome. The included grammar also makes some odd choices and I don't know ANTLR4 well enough to know how to fix them (such as including the :
in keyword strings). Additionally, if I were to switch, I would have to update/touch every existing rule.
After tinkering with Edamame for a bit, I've found a solution that requires no changes to edamame to support: #_:splint/disable
. This style of directive applies metadata to the following form: #_{:splint/disable [lint/plus-one]} (+ 1 x)
. Edamame normally discard #_
/discarded forms, so on Borkdude's recommendation, I use str/replace
to convert it at parse-time to metadata. This uses an existing convention and handles the issue of disabling multiple items or disabling for only a certain portion of the file.
Update readme with some better writing.
dev/sorted-rules-require
for internal use only:no-doc
.lint/cond-else
to style/cond-else
.Renamed to Splint! Things are really coming together now.
-M:gen-docs
for rule documentation generation and formatting.-M:new-rule
task to generate a new rule file from a template.-M:deploy
task to push to clojars.lint/assoc-in-one-arg
lint/update-in-one-arg
naming/predicate
naming/record-name
style/let-if
style/let-when
style/new-object
style/prefer-boolean
style/prefer-condp
style/redundant-let
style/single-key-in
lint/with-meta-vary-meta
to style/prefer-vary-meta
.lint/thread-macro-no-arg
to lint/redundant-call
.Initial release of spat
, announcement on Clojurian Slack and bbin installation set up. Contains working pattern matching system, a bunch of rules, and a simple runner.
Can you improve this documentation?Edit on GitHub
cljdoc is a website building & hosting documentation for Clojure/Script libraries
× close