hey all, I'm wondering if it's possible to check the build configuration (target) when expanding a macro. Maybe this is also the wrong approach to solving my problem (more context in the thread).
I'm trying to create one Clojurescript codebase for both web and mobile (using react-native). The app initialization logic varies between targets, so my idea was to create a macro to render the root component depending on the build target.
don't do that
instead create a dedicated namespace per target, so your.app.web and your.app.native or something
then one build for each using the dedicated namespace, not including the other at all
could do something like this if you want to abstract it further https://gist.github.com/thheller/fa044450a6470fdd1afdbcf3f37a65e3
ok, thank you
Hi there! For the first time in a long long time, I'm getting the infamous "x(...).yy is not a function" error in advanced compilation when calling some (but not all) functions from an external library. Any hints on where to start debugging this?
the relevant portion of my shadow-cljs.edn file looks something like this:
:js-options
{:js-provider :external
:external-index "target/libs.js"
:external-index-format :esm}
did you properly handle all extern inference warnings?
best way to quickly identify what .yy was is using npx shadow-cljs release the-build --pseudo-names
I think so, in the sense that I had none.
that'll make that propery something like .$something$ when it was .something origninally. usually that is pretty distinct and should lead you to the problem quickly
I'm now trying to figure out what's changed in the library 🙃
a-ha, thanks for that one liner, I'll check immediately
hm, the "missing" method has been there for a while...
I wonder if I anything changed in vite (that's what orchestrates the bundling), but it's code I haven't touched in ages
if you updated the dependencies it is very common for JS libs to just change their api randomly
but the vite parts have absolutely zero to do with externs issues?
yeah, I learned that the hard way one time too many 🙂 regarding vite... ok I may be looking at this from the wrong angle then
I'm assuming that you actually get a renamed reference. since you mentioned x(...).yy is not a function. so the advanced compiled bits renamed the function access, but vite still only provides the actual old name
so there is a mismatch and the name cannot be found. only way to fix it is to have the advanced compile not rename that property. normally externs inference should have warned you about it.
why is it all so clear when you explain it? 🙂
the object I'm trying to call that function from lives in an atom. Can that explain the lack of warnings?
not without some code. atom part is pretty much irrelevant
that's what I thought
dunno which shadow-cljs version you are using. maybe try upgrading. there have been a couple tweaks for externs inference of the years
yeah, I'm on the latest. The thing that surprises me the most is that method is not special at all. There are plenty like that one that I call elsewhere in the app 🤔 having said that, I'll actually verify this assumption next
did you identify the actual name? via --pseudo-names? don't assume, verify before doing anything else. extern issues can be tricky to track down when following from the wrong start 😉
yes, I have the name
https://shadow-cljs.github.io/docs/UsersGuide.html#infer-externs
uuuh... there is one thing that's special: it's one of a bunch of methods that are added to the object by another class (to give you minimal context, it's a modular editor of sorts, each module enriches the main View object)
none of that matters
great
it is literally only that there is a x.something but the advanced code is looking for x.yy. it doesnt matter what it comes from
of course, apologies for mixing things up. I'll re-read the user guide section
it's definitely all type hinted though 😕
this is the line that fails:
(defn get-match-index [] ^number (.findGetActiveMatchIndex ^js @view))
hmm try moving the deref out, not entirely sure this typehint transfers correctly for the @. I assume it does, just not sure
hang on...
(let [^js x @view] (.findGetActiveMatchIndex x))
It looks like it's the ^number hint! If I remove it works
hmm odd
I'll do some more tests
(defn get-match-index ^number [] (.findGetActiveMatchIndex ^js @view)) should be ok with the same effect
yes, that works 🎉
thanks aplenty. Time to look for other similarly misplaced hints 👋