Skip to content

Commit

Permalink
ensure proper cache invalidation for JS sources
Browse files Browse the repository at this point in the history
  • Loading branch information
thheller committed Mar 23, 2018
1 parent 68c4124 commit d403fa1
Show file tree
Hide file tree
Showing 9 changed files with 40 additions and 12 deletions.
2 changes: 1 addition & 1 deletion src/main/shadow/build/classpath.clj
Expand Up @@ -376,7 +376,7 @@
(-> result
(conj! {:resource-id [::resource name]
:resource-name (rc/normalize-name name)
:cache-key last-modified
:cache-key [last-modified]
:last-modified last-modified
:url url
:from-jar true})
Expand Down
35 changes: 31 additions & 4 deletions src/main/shadow/build/compiler.clj
Expand Up @@ -856,17 +856,44 @@
(map #(update % :sources remove-fn))
(into [])))))))

;; when requiring a JS dependency the chosen ns symbol might change because it is based on the filename
;; but cache would still have the old name so we need to ensure that a changed dep will also
;; invalidate the cache

;; For CLJS this was already ensured but the caching for JS is much less strict so it wouldn't recompiled
;; when a custom :resolve config was used. doing this here now so it works for every source

;; import ... from \"react\"
;; would result in something like
;; module$node_modules$react$index
;; being chosen as the variable name
;; :resolve {\"react\" {:target :npm :require \"preact\"}}
;; would result in
;; module$node_modules$preact$dist$index
;; but the cache wouldn't invalidate because the file itself didn't change

(defn ensure-cache-invalidation-on-resolve-changes
"populates :cache-key of the resource with the resolved symbols of its deps
to ensure recompilation when their names change"
[state resource-id]
(let [rc (data/get-source-by-id state resource-id)
deps-syms (data/deps->syms state rc)]
(update-in state [:sources resource-id :cache-key] into deps-syms)))

(defn compile-all
([{:keys [build-sources] :as state}]
(compile-all state build-sources))
([{:keys [executor last-progress-ref] :as state} source-ids]
"compile a list of sources by id,
requires that the ids are in dependency order
requires that ALL of the dependencies NOT listed are already compiled
eg. you cannot just compile clojure.string as it requires other files to be compiled first"
" compile a list of sources by id,
requires that the ids are in dependency order
requires that ALL of the dependencies NOT listed are already compiled
eg. you cannot just compile clojure.string as it requires other files to be compiled first "
(let [js-provider
(get-in state [:js-options :js-provider])

state
(reduce ensure-cache-invalidation-on-resolve-changes state source-ids)

sources
(into [] (map #(data/get-source-by-id state %)) source-ids)

Expand Down
2 changes: 1 addition & 1 deletion src/main/shadow/build/macros.clj
Expand Up @@ -156,7 +156,7 @@
(if (nil? url)
info
(let [^URLConnection con (.openConnection url)]
(assoc info :cache-key (.getLastModified con)))
(assoc info :cache-key [(.getLastModified con)]))
)))
;; get file (if not in jar)
(map (fn [{:keys [^URL url] :as info}]
Expand Down
2 changes: 1 addition & 1 deletion src/main/shadow/build/modules.clj
Expand Up @@ -172,7 +172,7 @@
rc
{:resource-id resource-id
:type :goog
:cache-key resource-id
:cache-key [resource-id]
:last-modified 0
:resource-name resource-name
:output-name (util/flat-filename resource-name)
Expand Down
3 changes: 2 additions & 1 deletion src/main/shadow/build/resource.clj
Expand Up @@ -46,7 +46,8 @@
;; this is more reliable to use for cljs caching since some inputs
;; may have more than one files they reference (ie. :foreign)
;; they must invalidate the cache for every entry not just one
(s/def ::cache-key some?)
(s/def ::cache-key-entry some?)
(s/def ::cache-key (s/coll-of ::cache-key-entry :kind vector?))

(s/def ::resource
(s/keys
Expand Down
2 changes: 1 addition & 1 deletion src/main/shadow/build/targets/bootstrap.clj
Expand Up @@ -37,7 +37,7 @@
:type :cljs
:url rc-url
:last-modified last-mod
:cache-key last-mod
:cache-key [last-mod]
:macros-ns true
:output-name (str macro-ns "$macros.js")
:source (slurp rc-url)}
Expand Down
2 changes: 1 addition & 1 deletion src/main/shadow/build/targets/node_library.clj
Expand Up @@ -78,7 +78,7 @@
:source [`(~'ns ~'shadow.umd-helper
(:require ~@(mapv vector entries)))
`(defn ~(with-meta 'get-exports {:export true}) [] ~get-exports)]
:cache-key (System/currentTimeMillis)
:cache-key [(System/currentTimeMillis)]
:last-modified (System/currentTimeMillis)
:virtual true}

Expand Down
2 changes: 1 addition & 1 deletion src/main/shadow/build/test.clj
Expand Up @@ -38,7 +38,7 @@
~@(for [it test-namespaces]
`(quote ~it))))]
:last-modified cache-key
:cache-key cache-key
:cache-key [cache-key]
:virtual true}]

(-> state
Expand Down
2 changes: 1 addition & 1 deletion src/main/shadow/cljs/repl.clj
Expand Up @@ -86,7 +86,7 @@
(into (-> ns-info :use-macros vals)))
:deps deps
:last-modified (System/currentTimeMillis)
:cache-key (System/currentTimeMillis)
:cache-key [(System/currentTimeMillis)]
)))

(defn setup [state]
Expand Down

0 comments on commit d403fa1

Please sign in to comment.