shadow-cljs 2025-08-07

김태희(taehee kim) 2025-08-07T05:47:10.240369Z

Can we provide build specific env for macros (.clj files) like closure-defines ?

김태희(taehee kim) 2025-08-07T05:52:06.687859Z

Usage scenario we have builds dev, test, and storybook we have several test specific macros. (codegen, build time optimization, etc...) we are using System/getenv in macro .clj files, goog-define + closure-defines in cljs files we want to disable the macro according to the env. but we can't use goog-define in macro files. but when the builds share single server, we can't provide different process environment variables

do these macros also target clojure? I mean generate code running in clojure? or do they only generate code that gets converted to JS?

김태희(taehee kim) 2025-08-07T06:14:51.435419Z

> do they only generate code that gets converted to JS?

you can get any options from the build config in the macro, but those won't be available during "normal" CLJ compilation, so wouldn't be available there

👀 1

that lib looks like a bad idea IMHO

😂 1
김태희(taehee kim) 2025-08-07T06:16:36.802469Z

how can we get build config from macro?

just to be clear you are looking for something like this

(defmacro a-macro [& body]
  (case (get-desired-target)
    :storybook
    `(foo :storybook)
    :test
    `(test :test)
    ;; default
    `(normal :cljs)))

👀 1

and want the (get-desired-target) thing?

김태희(taehee kim) 2025-08-07T06:18:29.987239Z

yes. exactly

김태희(taehee kim) 2025-08-07T06:19:00.584319Z

i want to get current :shadow.build/build-id

ok, so what you are looking for is the cljs.env/*compiler* atom

🙌 1

basically the entire compiler state is in there and you can get most things. some are more nested than others though

the convention is to use the :compiler-options {:external-config {:foo "bar"}} map

which you could get via (get-in @cljs.env/*compiler* [:options :external-config :foo])

김태희(taehee kim) 2025-08-07T06:24:57.228189Z

I see. Thank you for helping us!

if you want the build-id you can get that via (get-in @cljs.env/*compiler* [:shadow.build.cljs-bridge/state :shadow.build/build-id])

👀 1

:shadow.build.cljs-bridge/state contains basically all the shadow-cljs build state. instead of :shadow.build/build-id you can also get :shadow.build/config which is the entire config

be aware that you cannot just use everything from that map though

only some options are respected when it comes to caching

so just adding things randomly may lead to the compiler not knowing about them and not taking them into account for caching

which can lead to stale caches

✅ 1

:compiler-options {:external-config {:foo "bar"}} is generally recommended place, since the compiler knows about this and any changes made to the :external-config map will invalidate the caches

🙌 1