Example of using NodeJS spawn in Lumo
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
(def child-process (js/require "child_process")) | |
(def on-exit (js/require "signal-exit")) | |
(defn -spawn | |
"Thin wrapper around NodeJS function. | |
Spawns the process in the background. Returns the created ChildProcess instance." | |
[command args options] | |
(let [name (str command " " (str/join " " args))] | |
(println "ᐅ" name) | |
(-> (.spawn child-process | |
command | |
(clj->js (sequence args)) | |
(clj->js (merge {:stdio "inherit" :shell true} options))) | |
(.on "error" (fn [err] (throw (ex-info (str "Error executing a process: " err) {})))) | |
(.on "exit" | |
(fn [code signal] | |
(when (not (= code 0)) | |
(throw (ex-info (str "Process " (pr-str name) " exited unsuccessfully. " | |
"Code = " (pr-str code) | |
", signal = " (pr-str signal) ".") {})))))))) | |
(defn spawn | |
"Spawns the process in the background. | |
Will not make app wait for process to exit. | |
Will kill the process if parent application exits. | |
Returns the created ChildProcess instance." | |
[command args options] | |
(let [process (-spawn command args options)] | |
; Do not wait for process to exit | |
(.unref process) | |
; Kill app process on exiting the parent script (otherwise, Ctrl+D will exit the parent but not the child process) | |
(on-exit (fn [_code _signal] (.kill process))) | |
process)) | |
(defn spawn-sync | |
"Spawns the process synchronously." | |
[command args options] | |
(let [name (str command " " (str/join " " args))] | |
(println "ᐅ" name) | |
(let [result (.spawnSync child-process | |
command | |
(clj->js (sequence args)) | |
(clj->js (merge {:stdio "inherit" :shell true} options)))] | |
(when (some? (.-error result)) | |
(throw (ex-info (str "Error executing a process: " (.-error result)) {}))) | |
(when (not (= (.-status result) 0)) | |
(throw (ex-info (str "Process " (pr-str name) " exited with error code. Code = " (.-status result) ".") {})))))) | |
(comment | |
; Start app in background | |
(spawn "lein" ["trampoline" "with-profile" "-dev" "run"] {:cwd "../backend"}) | |
; Run tests | |
(defn argv | |
"Returns passed CLI args. Example: | |
./run.cljs 1 2 3 | |
js/process.argv = #js [/usr/local/Cellar/lumo/1.5.0/bin/lumo nexe.js ./run.cljs 1 2 3] | |
(argv) = [1 2 3]" | |
[] | |
(subvec (js->clj (.-argv js/process)) 3)) | |
(spawn-sync "lein" (into ["test-refresh"] (argv)) {})) |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment