Skip to content

Instantly share code, notes, and snippets.

@isaksky
Created October 8, 2019 16:10
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save isaksky/f693864aeedef8b54c1163342b36d788 to your computer and use it in GitHub Desktop.
Save isaksky/f693864aeedef8b54c1163342b36d788 to your computer and use it in GitHub Desktop.
Watch fancy CSS (less, scsss, etc) via shadow-cljs
(ns front.tasks.watch-css
(:require [clojure.java.io]
[clojure.java.shell :refer [sh]]
[juxt.dirwatch :refer [watch-dir]]
[clojure.core.async :as a]
[clojure.string :as str]
#_[shadow.cljs.devtools.api :refer [send-to-runtimes!]]))
(defn debounce-chan
"Taken from https://gist.github.com/xfsnowind/e15cc2e6da74df81f129"
([source msecs]
(debounce-chan (a/chan) source msecs))
([c source msecs]
(a/go-loop [state ::init
last-one nil
cs [source]]
(let [[_ threshold] cs
[v sc] (a/alts! cs)]
(condp = sc
source (condp = state
::init (recur ::debouncing
v
(conj cs (a/timeout msecs)))
::debouncing (recur state
v
(conj (pop cs) (a/timeout msecs))))
threshold (if last-one
(do (a/>! c last-one)
(recur ::init
nil
(pop cs)))
(recur ::init last-one (pop cs))))))
c))
;; Taken from: https://gist.github.com/mhuebert/ba885b5e4f07923e21d1dc4642e2f182#file-hooks-clj
(defn exec [& cmd]
(let [cmd (str/split (str/join " " (flatten cmd)) #"\s+")
_ (println (str/join " " cmd))
{:keys [exit out err]} (apply sh cmd)]
(if (zero? exit)
(when-not (str/blank? out)
(println out))
(println err))))
(defn mk-handler [build-state]
(let [msg-chan (a/chan)
handle-chan (debounce-chan msg-chan 50)
processor (a/go-loop
[m (a/<! handle-chan)]
(exec "cmd /c %CD%/scripts/build_css.bat")
(exec "cmd /c %CD%/scripts/build_dev_css.bat")
(recur (a/<! handle-chan)))]
(fn [args]
processor ;; hack - dont let him become GCed :)
(a/go (a/>! msg-chan args)))))
(defn mk-watcher [build-state]
(watch-dir
(mk-handler build-state)
(clojure.java.io/file "less-src")))
(defn hook
{:shadow.build/stage :configure}
[build-state & args]
(if (not= :dev (:shadow.build/mode build-state))
build-state
(assoc build-state
::watcher (mk-watcher build-state))))
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment