rewrite-clj

2024-09-06T14:36:47.244819Z

there's no way to adjust the output of zip/sexpr, right?

borkdude 2024-09-06T15:22:24.380299Z

in what way? please be more specific

2024-09-06T16:10:45.240169Z

given @foo, i want (splint/deref foo) not (deref foo)

borkdude 2024-09-06T16:31:00.452589Z

actually it's a bug in rewrite-clj that the deref isn't fully qualified, it should be. that's been filed here. rewrite-clj doesn't allow rendering this different unless you override the protocol

borkdude 2024-09-06T16:31:11.939709Z

which for a library isn't recommended

borkdude 2024-09-06T16:31:23.072169Z

forgot link to issue: https://github.com/clj-commons/rewrite-clj/issues/305

lread 2024-09-06T17:56:08.932789Z

Oh right... I should finally go ahead and merge the associated PR https://github.com/clj-commons/rewrite-clj/pull/306

2024-09-06T18:01:20.057249Z

well, then my question stands: given @foo, i want (splint/deref foo) not (clojure.core/deref foo) . is that possible in rewrite-clj or do i need to write my own sexpr converter?

2024-09-06T18:10:56.360239Z

my goal is to know when a piece of code was originally written with @ and not deref/`clojure.core/deref` so i can return the code in the same style it was in when i read it

lread 2024-09-06T18:13:11.042829Z

When you use sexpr you will often lose information. Do you need to use sexpr?

borkdude 2024-09-06T18:14:35.169579Z

the workaround-ish way of doing this is to look at occurrences of clojure.core/deref / deref and then go back to the original location (if you have that on the s-expr) to see if the original was written with @. the even shorter way: if the s-expr still contains location metadata, you can even derive it from that information only, since the begin and end-location of "@" only differ in one character

👍 1
borkdude 2024-09-06T18:15:08.213749Z

and yeah, you should avoid calling sexpr if you can, it's lossy

2024-09-06T18:15:59.182899Z

#splint is written to match against clojure data structures, and the "alternative" forms that it prints are built in clojure data structures as well, so when I'm using rewrite-clj to do potential replacements, I need to convert the node to a sexpr and then convert the resulting sexpr back to a node

borkdude 2024-09-06T18:17:36.222089Z

you don't need to do it that way

😂 1
2024-09-06T18:17:47.302369Z

switching from edamame to rewrite-clj would be a dramatic loss of performance for all situations where autocorrect isn't needed (and would complicate all of the hand-built replacement code that currently expects clojure data structures)

2024-09-06T18:18:28.667089Z

if you have a suggestion for how to avoid this that doesn't involve changing roughly 110 existing splint rules, i'm all ears

borkdude 2024-09-06T18:19:41.707489Z

I'd keep the matching logic the same, but do the rewriting in terms of nodes by looking up the location of the original s-expr and then parse stuff with rewrite-clj, rewrite nodes, then use str . sexpr is sometimes handy, but can often fail

borkdude 2024-09-06T18:20:06.278269Z

all the rewriting logic in clojure-lsp is done in that way, for good reasons

lread 2024-09-06T18:20:38.867009Z

yeah, I think of sexpr as a convenience fn to use very cautiously

lread 2024-09-06T18:23:37.867319Z

I'm sure you've read the user guide on this but here it is anyway: https://cljdoc.org/d/rewrite-clj/rewrite-clj/1.1.48/doc/user-guide#sexpr-nuances

2024-09-06T18:25:31.442129Z

here's an example of the kind of code that exists: https://github.com/NoahTheDuke/splint/blob/85ac71378ae57b387fbe650aa7d133c7458fad27/src/noahtheduke/splint/rules/lint/body_unquote_splicing.clj the pattern matches the form and builds a map of matched objects {?f ... ?init-arg ...}, and then the :on-match just builds a new clojure datastructure using those objects (`(list ?f (list 'let [...] ...))`), and returns it in :replace-form

2024-09-06T18:27:42.545159Z

having worked with clj-kondo's hooks api, it's really cumbersome to write (hook/list-node [(hook/token-node ?f) (hook/list-node ...)]) and avoiding that pain was one of my big motivations for splint

borkdude 2024-09-06T18:28:30.924399Z

clj-kondo also supports :macroexpand hooks which are less cumbersome

borkdude 2024-09-06T18:28:35.779859Z

but come with trade-offs

2024-09-06T18:28:46.736169Z

right, there's trade-offs to all of these approaches lol

borkdude 2024-09-06T18:29:16.713389Z

that existed prior to splint

2024-09-06T18:29:48.552539Z

i don't mean to denigrate clj-kondo, my feelings come from "using it in anger" as they say lol. i wanted to try something new and until now it's worked well, but supporting autocorrect looks like it'll require me to make some fundamental changes

lread 2024-09-06T18:30:43.542599Z

maybe find a hammock and sleep on it a bit, you might come up with some new awesome way to achieve your goal

👍 1
lread 2024-09-06T18:31:46.150409Z

but if you have more rewrite-clj questions, you know where to find us! ❤️

lread 2024-09-06T18:32:22.540539Z

you probably didn't get the answers you wanted today, but I hope we helped to clarify things.

2024-09-06T18:37:54.056959Z

haha it's all good

2024-09-06T18:38:01.504329Z

it's all a learning journey!

2024-09-06T18:38:37.504649Z

standing on the shoulders of giants (you two) as i build this thing

lread 2024-09-06T18:45:22.081759Z

Hey, I'm no giant! Just a happy bumbler! But borkdude, well, you can stand on his shoulders (if he's ok with that).

lread 2024-09-07T00:32:05.732429Z

Or screw that @nbtheduke, we'll stand on your shoulders! Don't sell yourself short!

😂 1