Fork me on GitHub
#shadow-cljs
<
2024-04-24
>
hifumi12301:04:11

Another exports question: is the case of a vector value supported? For instance

"./*": ["./dist/src/*", "./dist/src/*.js"]
The intent is that ./foo causes a search for ./dist/src/foo first then ./dist/src/foo.js

hifumi12302:04:20

Looking at the shadow-cljs source, it seems the answer is "no"

thheller06:04:57

the array syntax is supported as it is widely used

thheller07:04:09

but I believe it is not allowed for wildcards?

thheller07:04:41

could also be broken. I don't think I have seen this in the wild

hifumi12307:04:32

I am trying to work around an issue where I am using a javascript library that inconsistently uses fake paths, sometimes without .js extensions, other times with a .js extension. 😛

hifumi12307:04:24

The interesting part is that every bundler I have tried handles it gracefully, but shadow doesn’t. Not shadow’s fault, though. There is next to zero documentation on how this exports key should work anyway

thheller07:04:13

so the library INTERNALLY has lookups that rely on exports?

thheller07:04:32

exports are usually only used for external lookups, i.e. requests from outside the package?

hifumi12307:04:41

Ok, so there are two libraries at play. Library A has exports

{"./*": "./dist/src/*.js",
 "./*.js": "./dist/src/*.js"}
Library B depends on library A. Some files in library B use
import { thing } from "@A/foo";
Some files in library B instead use
import { thing } from "@A/foo.js";

hifumi12307:04:14

Library A has an invalid exports entry, based on the explanation youve provided me in an earlier thread. So I decided to experiment using the array syntax at the start of this thread, in attempt to “fix” the exports declared in library A’s package.json

hifumi12307:04:19

At the moment, I decided to bite the bullet and manually refactor library B so that it consistently refers to files without extension. Now shadow can locate the files. (Just barely tested npx shadow-cljs compile app and it succeeded after refactoring about two dozen imports in library B)

thheller07:04:59

maybe it is allowed that wildcard is other places, not just at the end

thheller07:04:13

I never verified that assumption. Just seemed so from the webpack docs

thheller07:04:36

if its a package on npm I can take a look and fix it

thheller07:04:45

just haven't seen other examples of that in the wild so far

thheller07:04:06

(I also didn't check a whole lot of package, basically only those users reported not working)

hifumi12307:04:46

Unfortunately these libraries are company-internal libraries, but I can easily make a minimal project reproducing this issue I’ve faced. It’s just a matter of whether its worth supporting or not (probably not, since this is the first time I’ve ran into a JS library with huge inconsistencies in imports)

thheller07:04:30

I mean I wasn't sure when I wrote it and changing that to str/includes? is not a big deal

thheller07:04:54

my take is that if there are package on npm using that it should be supported

thheller07:04:09

if its company-internal relying-on-webpack-only that is a bit sketch 😛

thheller07:04:03

well, I guess that answers this

thheller07:04:10

the node docs even use that pattern

thheller07:04:16

so I guess its supposed to be supported

hifumi12307:04:47

oh these two libraries in question are some of the messiest typescript Ive ever seen

hifumi12307:04:29

to make things play nicely with shadow I went and set up bundlers since they are doing all sorts of crazy things, like importing JSON files with an assert keyword that google-closure doesnt support

hifumi12307:04:08

originally they simply ran tsc and the outputted JS didnt even work in Node.js or Chrome… let alone shadow and gcc. the tsconfigs have references and path aliases all over the place.

hifumi12307:04:27

in any case, I managed to solve the problem I was facing — shadow’s existing functionality is sufficient for my needs

thheller07:04:42

yeah people never pick up any discipline when webpack basically allow all sorts of random combinations 😛

thheller07:04:15

I'm happy to fix it. its not a big deal

thheller07:04:13

the array thing will not work I believe

thheller07:04:11

what did you test this with? I mean on the JS side that that actually works?

thheller07:04:49

or did you just try that because

{"./*": "./dist/src/*.js",
 "./*.js": "./dist/src/*.js"}
didn't work?

thheller07:04:03

"./*": ["./dist/src/*", "./dist/src/*.js"] I mean?

hifumi12307:04:54

The array idea didn't work indeed. Even tsc got confused by the array exports

hifumi12307:04:38

But tsc, tsup, rollup, vite, etc. all handle

{"./*": "./dist/src/*.js",
 "./*.js": "./dist/src/*.js"}
gracefully

thheller07:04:49

shadow will now too I think 😛

gratitude 1
thheller07:04:56

can you give it a quick test? Just paste this into your REPL and let shadow compile?

hifumi12307:04:14

sure, one moment

thheller07:04:27

I mean I wrote a test, so should be fine but never hurts to test twice 😉

hifumi12307:04:03

do i need to restart shadow if i forgot to npm install in a subproject?

hifumi12307:04:07

I copy-pasted the code youve sent into my REPL, same error

hifumi12307:04:26

package A had exports, but could not resolve ./foo.js
{:package #object[java.io.File 0x12f76ddf "/Users/****/Desktop/repro/packages/B/node_modules/A"], :require-from [:shadow.build.npm/resource "node_modules/B/src/two.js"], :rel-require "./foo.js"}
ExceptionInfo: package A had exports, but could not resolve ./foo.js
	shadow.build.npm/find-resource-in-package (NO_SOURCE_FILE:907)
	shadow.build.npm/find-resource-in-package (NO_SOURCE_FILE:888)
	shadow.build.npm/find-resource (NO_SOURCE_FILE:1027)
	shadow.build.npm/find-resource (NO_SOURCE_FILE:951)
	shadow.build.resolve/find-npm-resource (resolve.clj:123)
	shadow.build.resolve/find-npm-resource (resolve.clj:94)

thheller07:04:52

and did you have the proper exports definition? not the array one?

hifumi12308:04:19

this is what’s being used

hifumi12308:04:21

not the array one

hifumi12308:04:42

this is part of the file structure of the project

src
└── repro
    └── demo.cljs
packages
├── A
│   ├── dist
│   │   └── foo.js
│   ├── package-lock.json
│   └── package.json
└── B
    ├── node_modules
    │   └── A -> ../../A
    ├── package-lock.json
    ├── package.json
    └── src
        ├── one.js
        └── two.js

thheller08:04:13

works for me?

thheller08:04:32

I don't know what this nested link business is about though?

hifumi12308:04:31

ah thats just what npm does when “installing” local file as a package

hifumi12308:04:09

Okay I found something interesting

hifumi12308:04:16

For some reason shadow can build the project successfully now

hifumi12308:04:25

I was triggering compilation with the Shadow CLJS web UI

hifumi12308:04:43

When I clicked “Stop” in the middle of a compile then clicked “Compile” again, now the exports are being parsed properly

hifumi12308:04:26

OK it looks like the issue is indeed fixed. watch, compile, and release work on my end now

thheller08:04:37

did you maybe run a compile before the change? the package.json is cached, so maybe it just had the old one

thheller08:04:48

(that wasn't parsed properly, i.e. without the change)

hifumi12308:04:02

I did run compile before sending the new shadow.build.npm code to the REPL

thheller08:04:19

yeah that won't work then

hifumi12308:04:24

In any case, it works now. A sequence of “stop” and “compile” somehow evicted that cache

hifumi12308:04:47

I can test it one more time without a compile, to be doubly sure

hifumi12308:04:56

But as far as I can tell, the patch youve sent me works

👍 1
hifumi12308:04:45

Restarted shadow-cljs in REPL, this time making sure to not compile before patching shadow.build.npm. It indeed works

thheller08:04:13

let me see if I can squeeze in another unrelated change

thheller08:04:31

I'll make a proper release in a bit regardless

thheller09:04:07

2.28.4 is out

🎉 1
danielneal18:04:13

I’m trying to install Swiper Element … I think I’ve followed the shadow-cljs npm module guide, but something is wrong somewhere.. My ns declaration:

(ns qrart.homepage
  (:require [qrart.qr :as qr]
            [uix.core :as uix :refer [defui $]]
            #?(:cljs [uix.dom])
            #?(:cljs ["swiper/element/bundle" :refer [register]])
            [shadow.css :refer [css]]))
The error:
The required JS dependency "swiper/element/bundle" is not available, it was required by "qrart/homepage.cljc".

Dependency Trace:
	qrart/preload.cljs
	qrart/homepage.cljc

Searched for npm packages in:
	/Users/danielneal/development/qrart/node_modules

The docs for Swiper say to do this:
// import function to register Swiper custom elements import { register } from ‘swiper/element/bundle’; // register Swiper custom elements register(); ` I’ve done the npm install swiper step. Have I mistranslated the import?

thheller18:04:03

first check: does /Users/danielneal/development/qrart/node_modules/swiper/package.json exist?

thheller18:04:19

2nd check: which shadow-cljs version do you use?

danielneal18:04:05

Yep the node_modules/package.json exists

danielneal18:04:33

thheller/shadow-cljs {:mvn/version “2.19.1”} is my shadow-cljs version

thheller18:04:28

that is too old. proper support for exports was added way later and that package uses exports

danielneal18:04:48

ah great, I’ll update

danielneal18:04:17

Sorry for the noise!

danielneal18:04:22

swiper-element-bundle is a .mjs file - is that a factor?

danielneal18:04:04

I find the js modules space tricky to wrap my head around

paul.​legato20:04:20

Hello. I’m new to CLJS and re-frame (but not to Clojure.) My first re-frame-template project was going well, until I quit the shadow-cljs REPL within Emacs. When I restart it (using M-x cider-jack-in-cljs), it appears to start up normally within Emacs, but the browser has a red banner that says Stale output! Your loaded JS was not produced by the running shadow-cljs instance. Is the watch for this build running? and indeed no changes I make in the source files appear in the browser. I’ve tried restarting, emptying cache and hard reloading. Anyone know what might be going on?

thheller21:04:05

well. Is the watch for this build running? Is it?

thheller21:04:39

jack-in is an extremely complex setup and I do not know if you have configured that correctly, nor would I know how that looks

thheller21:04:34

normally you'd have a npx shadow-cljs watch app or whatever task running

thheller21:04:48

with jack-in that is handled elsewhere and I cannot help you debug that

paul.​legato21:04:43

I do not know if the watch for this build is running. I did not do that manually the first time, when it worked. That was somehow spawned by cider-jack-in-cljs. Whatever it did the first time did not happen the second time. Perhaps someone more familiar with cider-jack-in-cljs can add some insight.

thheller21:04:20

you can open http://localhost:9630 for the shadow-cljs UI

thheller21:04:27

it'll show if the watch is running or not

thheller21:04:47

for cider help ask in #C0617A8PQ

thheller21:04:00

or you know ... skip the entire jack-in nonsense

thheller21:04:19

run shadow-cljs as the docs suggest, i.e. npx shadow-cljs watch app manually

thheller21:04:26

and then cider-connect instead

thheller21:04:38

but again .. can't really help you with that either. I do not use emacs

paul.​legato21:04:47

The docs clearly indicate that cider-jack-in-cljs is supported and valid: https://shadow-cljs.github.io/docs/UsersGuide.html#cider

thheller21:04:22

I cannot verify that. I assume it works but I couldn't tell you 1bit of how

paul.​legato21:04:39

That’s OK. Thanks for the info. Perhaps someone else will be more familiar with the jack-in command

paul.​legato21:04:16

It works now. I deleted the .dir-locals.el file (which the same above linked docs suggest setting up in section 15.2.2 as a means of storing defaults). I killed the existing session, and restarted with cider-jack-in-cljs, and it just worked as expected after that. I have no information beyond that, but I leave this here for future searchers who might encounter this issue.