Fork me on GitHub
#honeysql
<
2023-06-23
>
seancorfield23:06:36

A discussion I had today (elsewhere) made me wonder if I could make the quoted symbolic form of HoneySQL queries easier to use. You can write '{select * from users where (= status "approved")} today and it formats the same as the (longer) keyword version: {:select :* :from :users :where [:= :status "approved"]} -- but it's hard to use variables/parameters with the quoted form, compared to the keyword form. Sure, you can use ?name and then provide an options hash map with {:params {:name "whatever"}} but that's quite a bit of extra typing. I figured it might be nicer to have something like (sql/formatf '{select * from users where (= username ?1)} "whatever") and have it "do the right thing", i.e., construct an appropriate {:params {...}} hash map for you. I created https://github.com/seancorfield/honeysql/issues/495 for feedback/discussion and implemented a basic version of formatf, currently undocumented. You can try it out via the latest develop SHA on GitHub or as a snapshot version 2.4.9999-SNAPSHOT I guess there are two questions: • Is this actually useful enough to add at all? • How would folks expect/want to see options being passed into a variadic function like that and how/would you care about parameters that are hash maps potentially conflicting with an options hash map? The latter Q is in the issue.

seancorfield06:01:49

I continue to worry away at this particular problem (that, it seems, very few other people care about! 🙂 ) and tonight added another experimental possible solution: https://github.com/seancorfield/honeysql/blob/develop/src/honey/sql.cljc#L2104-L2131 I like formatv better because it is explicit:

... some code that sets up the user-name binding ...

(sql/formatv [user-name] '{select * from users where (= username user-name)})
This uses clojure.template/apply-template behind the scenes to replace the declared symbol (`user-name`) with its locally bound value in the DSL. format& exists too -- it replaces all locally bound symbols in the DSL which may or may not be a good idea. formatf still exists, which lets you use ?1, ?2 as positional parameters and then you provide the parameters as trailing arguments (but it doesn't support formatting options -- whereas formatv and format& do).

seancorfield06:01:49
replied to a thread:A discussion I had today (elsewhere) made me wonder if I could make the quoted symbolic form of HoneySQL queries easier to use. You can write `'{select * from users where (= status "approved")}` today and it formats the same as the (longer) keyword version: `{:select :* :from :users :where [:= :status "approved"]}` -- but it's hard to use variables/parameters with the quoted form, compared to the keyword form. Sure, you can use `?name` and then provide an options hash map with `{:params {:name "whatever"}}` but that's quite a bit of extra typing. I figured it might be nicer to have something like `(sql/formatf '{select * from users where (= username ?1)} "whatever")` and have it "do the right thing", i.e., construct an appropriate `{:params {...}}` hash map for you. I created https://github.com/seancorfield/honeysql/issues/495 for feedback/discussion and implemented a basic version of `formatf`, currently undocumented. You can try it out via the latest *develop* SHA on GitHub or as a snapshot version 2.4.9999-SNAPSHOT I guess there are two questions: • Is this actually useful enough to add at all? • How would folks expect/want to see options being passed into a variadic function like that and how/would you care about parameters that are hash maps potentially conflicting with an options hash map? The latter Q is in the issue.

I continue to worry away at this particular problem (that, it seems, very few other people care about! 🙂 ) and tonight added another experimental possible solution: https://github.com/seancorfield/honeysql/blob/develop/src/honey/sql.cljc#L2104-L2131 I like formatv better because it is explicit:

... some code that sets up the user-name binding ...

(sql/formatv [user-name] '{select * from users where (= username user-name)})
This uses clojure.template/apply-template behind the scenes to replace the declared symbol (`user-name`) with its locally bound value in the DSL. format& exists too -- it replaces all locally bound symbols in the DSL which may or may not be a good idea. formatf still exists, which lets you use ?1, ?2 as positional parameters and then you provide the parameters as trailing arguments (but it doesn't support formatting options -- whereas formatv and format& do).