Fork me on GitHub
#shadow-cljs
<
2022-07-02
>
john17:07:58

I'm exploring making a library that allows you to programmatically spawn webworkers in CLJS. To do this, I need to craft a JS script to inject into the worker that will correctly import/require things in a way that works within webworkers. I'm focusing on non-advanced compile mode right now. I've got a thing that works with cljs.main cli and figwheel, but I haven't got it to work yet in shadow:

(defn create-worker-body [require-ns afn value tid]
  (println :require-ns require-ns)
  (let [pre-loads
        (str "var CLOSURE_UNCOMPILED_DEFINES = {\"cljs.core._STAR_target_STAR_\":\"webworker\"};"
             "var quarkpreload = {};\n"
             "quarkpreload.fn = `" afn "`;\n"
             "quarkpreload.args = `" value "`;\n"
             "quarkpreload.tid = `" tid "`;\n")]
    (if (empty? goog/basePath)
      (str pre-loads
           "importScripts('" (last (scripts-src)) "');\n")
      (str pre-loads
           "CLOSURE_BASE_PATH = '" goog/basePath "';\n"
           "this.CLOSURE_IMPORT_SCRIPT = (function(global) {\n"
           "    return function(src) {\n"
           "        global['importScripts'](src);\n"
           "        return true;\n"
           "    };\n"
           "})(this);\n"
           "if(typeof goog == 'undefined') importScripts(CLOSURE_BASE_PATH + 'base.js');\n"
           "importScripts(CLOSURE_BASE_PATH + 'deps.js');\n"
           "importScripts(CLOSURE_BASE_PATH + '../cljs_deps.js');\n"
           "goog.require('process.env');\n"
           "goog.require('" require-ns "');\n"))))
In shadow, I get Error: browser bootstrap used in incorrect target because goog.global.document isn't available:
var doc = goog.global.document;

  if (!doc) {
    throw new Error("browser bootstrap used in incorrect target");
  }
Any pointers here?

john17:07:26

I'm trying to make a minimal script that will work across shadow, figwheel and cljs.main

john17:07:21

If I need a special version for shadow, I could potentially make a thing to detect which build environment I'm in, and spit out the correct one

john17:07:00

In the long run, maybe it'd be good for cljs.main/figwheel/shadow to all expose a out/webworker.js file that CLJS users can know they can always pass to new Worker(... and know that the given build system will handle setup the way it wants to.

john17:07:21

Nevermind I just followed the directions!!!

john17:07:47

lol, and it worked... :web-worker true

john17:07:03

lots of sourcemap errors, with my script

john17:07:00

unsupported protocol for sourcemap request blob:.... But this is sweet progress

souenzzo17:07:25

Is possible to define ^:export 'ed functions at shadow-cljs.edn? I have two builds and I want to export a different set of functions in the same ns

thheller17:07:07

@john the web-worker output is supposed to be loaded as a regular file (ie. new Worker("/js/worker.js")) not as a blob. then source maps will also work

👀 1
thheller17:07:57

@souenzzo no, but you can skip export completely and instead create 2 different entry namespace

thheller18:07:11

so (ns your.build.a) and (ns your.build.b) (each with the appropriate requires of course)

thheller18:07:35

they can each call (js/goog.exportSymbol "whatever.name.you.like" the-cljs/def)

thheller18:07:09

all ^:export does is adding that exportSymbol call basically

thheller18:07:21

but you can do it manually with more control

👌 1