shadow-cljs

michihuber 2025-06-17T07:21:54.129559Z

I want to move some of my app's UI components into a library. these will depend on some npm packages, as well as a compiled package (to remove some js features unsupported by goog) that I pull in via {:js-package-dirs ["vendor" "node_modules"]} . what's the most user-friendly way to package this? should I move the vendor contents to the src dir? will library users have to add npm deps to their package.json themselves?

thheller 2025-06-17T07:22:54.300469Z

is that app's UI components code CLJS?

thheller 2025-06-17T07:24:09.896189Z

there is no supported way to bundle JS code in .jars

michihuber 2025-06-17T07:42:13.441539Z

yes, it is wrapping some npm js components with some added features, as well as some vendored js, as well as some js in the src dir. so basically, the installation will be adding my lib, then running npm install <list of deps>, correct? if I moved the contents of vendor to src and removed the :js-package-dir config, should it work the same?

thheller 2025-06-17T07:45:17.422129Z

no, none of that will work

thheller 2025-06-17T07:45:34.830979Z

first of all you cannot compile some CLJS and then include that compiled code in another CLJS build

thheller 2025-06-17T07:46:04.027299Z

then, as I said, you cannot bundle precompiled JS code in .jars and consume those as-if they were npm packages

thheller 2025-06-17T07:46:11.700809Z

you can publish it to npm, then sure

thheller 2025-06-17T07:46:53.342089Z

kinda hard to guess what you are trying to achieve without seeing any code

michihuber 2025-06-17T07:56:13.805029Z

gotcha, so I'd need to publish an npm package that had all the npm deps in its package.json, as well as the vendored code and my own js code. the user would need to install that into via npm. then I could package my cljs code (uncompiled) and the user would add this to their deps.edn is that roughly correct?

thheller 2025-06-17T07:57:06.742629Z

yes, kinda have to be careful how the JS code is bundled though

thheller 2025-06-17T07:57:45.594529Z

the cljs code can include a deps.cljs file with {:npm-deps {"your-stuff" "1.1.0"}}, which automates the user having to run npm install your-stuff@1.1.0

michihuber 2025-06-17T07:58:31.278559Z

oh, cool

michihuber 2025-06-17T07:58:40.131979Z

thanks!

Priyankaa 2025-06-17T07:31:06.205589Z

We have a use case where we’re migrating our ClojureScript application to anhttps://developer.atlassian.com/platform/forge/. Forge doesn’t directly support ClojureScript, but I believe shadow-cljs is responsible for compiling ClojureScript to JavaScript. We’re considering using that compiled JavaScript file as the entry point for Forge. My questions are: 1. Is it possible to compile and generate JavaScript output for a specific piece of code or a single readable javascript file instead of compiling the entire application in an single file? 2. Are there any tools or methods that can convert Clojure code directly into human-readable or reusable JavaScript code? This would help us reuse some of our existing functionality during the migration.

thheller 2025-06-17T07:36:13.007419Z

2) maybe https://github.com/squint-cljs/squint

thheller 2025-06-17T07:37:06.975379Z

1) any CLJS build will require at least a single namespace and will include all the dependencies it has, so the implicit cljs.core and closure library bits. readable is not a goal during compilation, so a no there

1
Priyankaa 2025-06-17T12:12:29.156579Z

Is it possible to use Atlassian forge framework dependencies directly in clojurescript project - "@forge/api": "^4.0.0", "@forge/bridge": "^4.1.0", "@forge/react": "^10.6.1", "@forge/resolver": "^1.6.0" \

Priyankaa 2025-06-18T05:17:52.948129Z

any inputs will really help me pls

thheller 2025-06-18T06:17:30.227209Z

sorry, I know absolutely nothing about the forge stuff. I'd assume you use those dependencies like any other npm dependency

Priyankaa 2025-06-18T06:19:10.980729Z

yes

Priyankaa 2025-06-18T06:33:55.408019Z

@forge/react is UI and rest all for back end so my doubt was is it recommended to use this directly in clojure .. officially they just support JS

thheller 2025-06-18T06:35:33.343909Z

CLJS compiles to JS so thats fine. https://shadow-cljs.github.io/docs/UsersGuide.html#_using_npm_packages

thheller 2025-06-18T06:36:30.733199Z

I cannot walk you through any detail blindly, so you either show me some code of what you have tried or you are on your own

👀 1
valerauko 2025-06-17T07:42:14.190069Z

I'm trying to set up shadow-cljs with webpack and in dev mode I run into Uncaught TypeError: Cannot set properties of undefined (setting 'NodeType') (the build works fine in release mode) I feel like I've seen similar errors talked about here but I can't for my life find it

thheller 2025-06-17T07:43:04.147879Z

if why "with webpack" you mean the shadow-cljs output it running through webpack entirely then only a few targets support this

valerauko 2025-06-17T07:43:25.691879Z

Config

{,,,
 :js-options
 {:js-provider :import}
 
 :builds
 {:target :esm
  :runtime :browser

thheller 2025-06-17T07:43:38.048349Z

ok for esm it should be fine

thheller 2025-06-17T07:44:23.162589Z

NodeType is usually goog.dom, so if that doesn't exist something is fundamentally broken 😛

valerauko 2025-06-17T07:45:11.456439Z

I'm confused because it works with the release/prod config I looked at the generated code and it seems that webpack pulls in goog.dom.dom after goog.dom.nodetype which might be causing it?

thheller 2025-06-17T07:52:23.914999Z

release builds are optimized and collapse the "namespace" structure completely, they are also a single file, so basically anything that may confuse webpack is removed

thheller 2025-06-17T07:52:43.133549Z

dev builds obviously do not do that as that would make things like hot-reload or REPLs impossible

thheller 2025-06-17T07:53:13.147329Z

:esm should make the code look like something webpack supports, and I have seen people do that successfully

thheller 2025-06-17T07:53:29.348049Z

impossible for me to guess why it wouldn't work in your case without seeing any code

thheller 2025-06-17T07:54:06.732759Z

usually best to study the JS webpack generates. that isn't exactly easy but the most direct path.

valerauko 2025-06-17T12:19:09.946679Z

I managed to get it to work but tbf I have no idea why it wouldn't work in the first place...

thheller 2025-06-17T17:22:27.986989Z

what was it?

valerauko 2025-06-17T17:56:12.228849Z

I really don't know. Probably some pollution in webpack's node_modules cache? It kept breaking in seemingly unrelated ways at different points during attempts I got it working based on the config from https://deh.li/2022/11/04/shadow-cljs-webpack.html

valerauko 2025-06-17T12:19:35.087419Z

Is it possible to write a macro for a require?

valerauko 2025-06-17T12:27:24.718719Z

To get webpack to deal with my images I require them like this

(ns foo
  (:require ["images/icons/login_active.png$default" :as LoginActive]))
Like this LoginActive will be = the uri of the image asset. But writing this all over the place is repetitive and long and gets messy with variants. Can I write a macro that does this for me?
(asset/uri "icons/login" :active)
;; "images/icons/login_active.png"
I first tried just putting a (require '["images/foo.jpg" :as Foo]) in the top level of a ns (outside of the ns form) but it complained about it being outside of the ns form. Hoped to do something like below
(defmacro uri
  ([item] (uri item :default))
  ([item variant]
   (let [import-name (gensym)]
     `(do
        (require '[~(str "images/" item "$default") :as ~import-name])
        ~import-name)))

thheller 2025-06-17T17:31:28.367309Z

no, macros creating require calls is not supported. that is a special form reserved for the REPL in CLJS