Skip to content

Instantly share code, notes, and snippets.

@metametadata
Last active January 9, 2020 07:06
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 metametadata/bb00917e09463f6ce04f0e50ccc0740a to your computer and use it in GitHub Desktop.
Save metametadata/bb00917e09463f6ce04f0e50ccc0740a to your computer and use it in GitHub Desktop.
ClojureScript compilation-time project configuration using external-config

Example of providing custom compilation-time configuration option :debug in ClojureScript project. It's a better alternative to goog defines.

project.clj:

,,,

:cljsbuild {:builds [{:id           "dev"
                      :source-paths ["src"]
                      :compiler     {:main            app.core
                                     ,,,
                                      
                                     ; Using :myapp "namespace" to reduce a chance of conflict with other tools using :external-config.
                                     :external-config {:myapp {:debug? true}}}}

                     {:id           "test"
                      :source-paths ["src" "test"]
                      :compiler     {:main            unit.runner
                                     ,,,

                                     :external-config {:myapp {:debug? true}}}}

                     {:id           "min"
                      :source-paths ["src"]
                      :compiler     {:main            app.core
                                     :output-to       "resources/public/js/compiled/frontend.js"
                                     :optimizations   :advanced
                                     ,,,

                                     :external-config {:myapp {:debug? false}}}}]}
,,,

config.clj:

(ns app.config
  "Compilation time app configuration."
  (:require [cljs.env :as env]))

(defn -config
  []
  (when (some? env/*compiler*)
    (get-in @env/*compiler* [:options :external-config :myapp])))

(defmacro if-debug
  "Emits expression based on the value of debug flag in project's compiler options."
  ([then]
   `(if-debug ~then nil))
  ([then else]
   (if (:debug? (-config))
     then
     else)))

(defmacro when-debug
  [& body]
  `(if-debug (do ~@body)))

Usage:

(ns app.core
  (:require [schema.core :as schema])
  (:require-macros [app.config :as app-config]))

(defn main
  []
  (app-config/when-debug
   ; This code will not be compiled on :min build:
   (.warn js/console "App debug mode is ON.")
   (schema/set-fn-validation! true))

  ,,,)
@smoes
Copy link

smoes commented Jan 9, 2020

Awesome, exactly what I was looking for 👍

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment