Do call after login only if there was a previous call

--- src/discuss/communication/auth.cljs
+++ src/discuss/communication/auth.cljs
@@ -7,14 +7,16 @@
 (defn- success-login
   "Callback function when login was successful. Set attributes of user."
   [response]
-  (let [{:keys [nickname uid token]} (lib/process-response response)]
+  (let [{:keys [nickname uid token]} (lib/process-response response)
+        last-api-call (lib/get-last-api)]
      (lib/store-multiple-values-to-app-state!
      [['user/nickname nickname]
       ['user/token token]
       ['user/id uid]
       ['user/logged-in? true]
       ['layout/view :default]])
-    (comlib/ajax-get (lib/get-last-api))))
+     (when (seq last-api-call)
+       (comlib/ajax-get last-api-call))))

 (defn- wrong-login
   "Callback function for invalid credentials."


remove unneeded ":remote true" and pass true to :api instead of ast


always show likes when exist

always show likes when exist

--- iwaswhere-web/src/cljs/iwaswhere_web/ui/entry.cljs
+++ iwaswhere-web/src/cljs/iwaswhere_web/ui/entry.cljs
@@ -134,7 +134,7 @@
          [:span.fa.toggle
           {:on-click (upvote-fn inc)
            :class    (if (pos? upvotes) "fa-thumbs-up" "fa-thumbs-o-up")}]
-         (when (pos? upvotes) [:span.upvotes " " upvotes])
+         (when (pos? upvotes) [:span.upvotes upvotes])
          (when (pos? upvotes)
            [:span.fa.fa-thumbs-down.toggle {:on-click (upvote-fn dec)}])
          (when map? [:span.fa.fa-map-o.toggle {:on-click toggle-map}])
@@ -261,7 +261,12 @@
      [m/image-view entry]
      [m/videoplayer-view entry]
      (when-let [measurements (:measurements entry)]
-       [:pre [:code (with-out-str (pp/pprint measurements))]])]))
+       [:pre [:code (with-out-str (pp/pprint measurements))]])
+     (when-let [upvotes (:upvotes entry)]
+       (when (pos? upvotes)
+         [:div
+          [:span.fa.fa-thumbs-up]
+          [:span.upvotes upvotes]]))]))

 (defn thumbnails
   "Renders thumbnails of photos in linked entries. Respects private entries."


Write energy-as

Write energy-as

Previous commits ...

This commit ...

--- src/test_utils/fracture_diagnostics.cljc
+++ src/test_utils/fracture_diagnostics.cljc
@@ -87,6 +87,7 @@
 (defn density-as [[from-magnitude from-unit substance] to-unit]
   (let [[target-magnitude _] ((as-f :lb-per-cu-ft :kg-per-m3 16.0185) [from-magnitude from-unit] to-unit)]
     [target-magnitude to-unit substance]))
+(def energy-as (as-f :ft-lb :J 1.35582))
 (def force-as (as-f :lbf :N 4.44822))
 (def power-as (as-f :hp :W 745.69987158227022))
 (def proppant-concentration-as (as-f :lb-per-gal :kg-per-m3 119.826))
@@ -660,4 +661,5 @@
         measurement (generate-measurement-f unit)]
     [measurement (measurement-as-f measurement (first (remove (partial = unit) units)))]))

-(generate-pair #{:lb-per-cu-ft :kg-per-m3} rand-density-unit typical-density density-as)
+(generate-pair #{:ft-lb :J} rand-energy-unit typical-total-pump-energy energy-as)
+;; => [[7.045024884133696E10 :ft-lb] [9.551785638406148E10 :J]]


Bug fix: render page regardless of which data resource loads first

--- src-cljs/acfe/core.cljs
+++ src-cljs/acfe/core.cljs
@@ -99,7 +99,8 @@
   [response]
   (reset! places (read-string response))
   (render/create-map)
-  (render/create-markers @places on-place-click))
+  (render/create-markers @places on-place-click)
+  (update-and-render))

 (defn on-areas-load


Update watcher to use console runner and nested reporter

--- src/main/clojure/lazytest/watch.clj
+++ src/main/clojure/lazytest/watch.clj
@@ -1,20 +1,15 @@
 (ns lazytest.watch
   (:gen-class)
-  (:use	[lazytest.find :only (find-tests)]
-	[clojure.contrib.find-namespaces
+  (:use	[clojure.contrib.find-namespaces
 	 :only (find-clojure-sources-in-dir
 		read-file-ns-decl)]
 	[clojure.java.io :only (file)]
 	[clojure.string :only (split join)])
+  (:require lazytest.runner.console
+	    lazytest.report.nested)
   (:import (java.util.concurrent ScheduledThreadPoolExecutor TimeUnit)
 	   (java.util.regex Pattern)
 	   (java.io File)))
-
-(defn report [& args]
-  (println "report function not implemented"))
-
-(defn run-tests [& args]
-  (println "run-tests function not implmented"))

 (defn find-sources
   [dirs]
@@ -42,7 +37,7 @@
 	(doseq [n names] (remove-ns n))
 	(doseq [n names] (require n :reload))
 	(println "Running examples at" (java.util.Date.))
-	(reporter (mapcat run-tests (mapcat find-tests (all-ns))))
+	(reporter (apply lazytest.runner.console/run-tests (all-ns)))
 	(println "\nDone.")))
     (catch Throwable t
       (println "ERROR:" t)
@@ -50,7 +45,8 @@

 (defn start [dirs & options]
   (let [dirs (map file dirs)
-	{:keys [reporter delay], :or {delay 500, reporter report}} options
+	{:keys [reporter delay],
+	 :or {delay 500, reporter lazytest.report.nested/report}} options
 	last-run-timestamp (atom 0)
 	runner #(reload-and-run dirs last-run-timestamp reporter)]
     (doto (ScheduledThreadPoolExecutor. 1)


Add test for no-op start/stop.

Add test for no-op start/stop.

--- test/com/stuartsierra/component_test.clj
+++ test/com/stuartsierra/component_test.clj
@@ -249,3 +249,10 @@
                 :e {:n 50}}
         system (component/system-using system dependency-map)]
     (assert-increments (increment-all-components system))))
+
+(defrecord ComponentWithoutLifecycle [state])
+
+(deftest component-without-lifecycle
+  (let [c (->ComponentWithoutLifecycle nil)]
+    (is (= c (component/start c)))
+    (is (= c (component/stop c)))))


Updated example on factor analysis

Updated example on factor analysis

Signed-off-by: Daniel Borchmann <25857343a15bf1edafebc2912e82ecf775c585c1@mailbox.tu-dresden.de>

--- doc/examples/factor-analysis.clj
+++ doc/examples/factor-analysis.clj
@@ -34,17 +34,19 @@

 (defvar- fuzzy-ctx (make-fuzzy-context [1 2 3 4]
                                        [1 2 3 4]
-                                       [0.1 0.2 0.3 0.4,
-                                        0.5 0.6 0.7 0.8,
-                                        0.9 1.0 0.9 0.8,
-                                        0.7 0.6 0.5 0.4]))
+                                       [1/10 2/10 3/10 4/10,
+                                        5/10 6/10 7/10 8/10,
+                                        9/10 1    9/10 8/10,
+                                        7/10 6/10 5/10 4/10]))

 ;; and then call factorize-context with the parameter :fuzzy. Note
 ;; that you need to wrap this call in with-fuzzy-logic to determine
 ;; the logic to use. Also see the example for fuzzy FCA for "more" details.

 (with-fuzzy-logic :goedel
-  (factorize-context :fuzzy fuzzy-ctx))
+  (factorize-context :fuzzy
+                     fuzzy-ctx
+                     #{0 1/10 2/10 3/10 4/10 5/10 6/10 7/10 8/10 9/10 1}))

 ;;;


Delete some debugging code

Delete some debugging code

--- src/midje/ideas/rerunning_facts.clj
+++ src/midje/ideas/rerunning_facts.clj
@@ -77,10 +77,6 @@
   (compendium/namespace-facts @compendium namespace))

 (defn record-fact-existence [fact-function]
-  (when (:check-only-at-load-time (meta fact-function))
-    (prn "WELL! I shall not save this:")
-    (pprint (macroexpand-1 (:midje/source (meta fact-function)))))
-
   (when-not (:check-only-at-load-time (meta fact-function))
     (if-let [previous (compendium/previous-version @compendium fact-function)]
       (swap! compendium compendium/remove-from previous))


Make the file-type property as an optional value since sometimes files have no mime type.

--- src/oc/storage/resources/common.clj
+++ src/oc/storage/resources/common.clj
@@ -23,7 +23,7 @@

 (def Attachment {
   :file-name lib-schema/NonBlankStr
-  :file-type lib-schema/NonBlankStr
+  :file-type (schema/maybe schema/Str)
   :file-size schema/Num
   :file-url lib-schema/NonBlankStr
   :created-at lib-schema/ISO8601})


Use a better name for the board flag.

Use a better name for the board flag.

--- src/oc/storage/resources/common.clj
+++ src/oc/storage/resources/common.clj
@@ -58,7 +58,7 @@
   (schema/optional-key :draft) schema/Bool
   :created-at lib-schema/ISO8601
   :updated-at lib-schema/ISO8601
-  (schema/optional-key :personal) schema/Bool})
+  (schema/optional-key :publisher-board) schema/Bool})

 (def ContentVisibility {
   (schema/optional-key :disallow-secure-links) schema/Bool


handle bad numbers in carbon handler

handle bad numbers in carbon handler

--- src/org/spootnik/cyanite/carbon.clj
+++ src/org/spootnik/cyanite/carbon.clj
@@ -8,12 +8,23 @@
             [gloss.core                 :refer [string]]
             [lamina.core                :refer [receive-all map* siphon]]))

+(defn parse-num
+  "parse a number into the given value, return the
+  default value if it fails"
+  [parse default number]
+  (try (parse number)
+    (catch NumberFormatException e
+      (debug "got an invalid number" number (.getMessage e))
+      default)))
+
 (defn formatter
   "Split each line on whitespace, discard nan metric lines
    and format correct lines for each resolution"
   [index rollups input]
-  (let [[path metric time] (s/split (.trim input) #" ")]
-    (when (not= metric "nan")
+  (let [[path metric time] (s/split (.trim input) #" ")
+        metric (parse-num #(Double/parseDouble %) "nan" metric)
+        time (parse-num #(Long/parseLong %) "nan" time)]
+    (when (and (not= metric "nan") (not= time "nan"))
       ;; hardcode empty tenant for now
       (when index (path/register index "" path))
       (for [{:keys [rollup period rollup-to]} rollups]
@@ -21,8 +32,8 @@
          :rollup rollup
          :period period
          :ttl    (* period rollup)
-         :time   (rollup-to (Long/parseLong time))
-         :metric (Double/parseDouble metric)}))))
+         :time   (rollup-to time)
+         :metric metric}))))

 (defn handler
   "Send each metric over to the cassandra store"


fix has-output?

fix has-output?

--- frontend/models/action.cljs
+++ frontend/models/action.cljs
@@ -15,7 +15,7 @@
 (defn has-content? [action]
   (or (:has_output action)
       (:bash_command action)
-      (seq (:final-out action))))
+      (:output action)))

 (defn duration [{:keys [start_time stop_time] :as action}]
   (cond (:run_time_millis action) (datetime/as-duration (:run_time_millis action))


add more content to output of (defn spec-info [spec])

--- src/babel/generate.cljc
+++ src/babel/generate.cljc
@@ -271,6 +271,14 @@
       {:pred pred})
     (if-let [agr (get-in spec [:synsem :agr])]
       {:agr agr})
+    (if-let [pronoun (get-in spec [:synsem :pronoun])]
+      {:pronoun pronoun})
+    ;; :synsem/:sem/:mod is sometimes used with nil explicitly, so need to have a special test for it
+    (let [mod (get-in spec [:synsem :sem :mod] :not-found-by-spec-info)]
+      (if (not (= :not-found-by-spec-info mod))
+        {:mod mod}))
+    (if-let [modified (get-in spec [:modified])]
+      {:modified modified})
     (if-let [subcat1 (if (not (empty? (get-in spec [:synsem :subcat])))
                       (get-in spec [:synsem :subcat :1 :cat]))]
       {:subcat/:1/:cat subcat1


more cleanup

more cleanup

--- src/babel/generate.cljc
+++ src/babel/generate.cljc
@@ -92,15 +92,14 @@
       (if (empty? comp-paths)
         [bolt] ;; done: we've added all the comps to the bolt, so just return the bolt as a singleton vector.
         ;; else, more comp-paths to go.
-        (lazy-seq
-         (flatten
-          (mapfn #(add-comps % model
-                             (rest comp-paths)
-                             (rest bolts-at-paths)
-                             depth max-depth top-bolt truncate? take-n)
-                 (add-bolts-to-path
-                  (first comp-paths) (first bolts-at-paths)
-                  bolt top-bolt model depth max-depth truncate? take-n))))))))
+        (flatten
+         (mapfn #(add-comps % model
+                            (rest comp-paths)
+                            (rest bolts-at-paths)
+                            depth max-depth top-bolt truncate? take-n)
+                (add-bolts-to-path
+                 (first comp-paths) (first bolts-at-paths)
+                 bolt top-bolt model depth max-depth truncate? take-n)))))))

 (defn add-bolt-at [top-bolt bolt path bolt-at model depth max-depth truncate? & [take-n]]
   (mapfn #(do-defaults % model)
@@ -108,27 +107,21 @@
                comp-bolts
                (mapfn #(comp-path-to-bolts bolt-at % model (+ 1 depth) max-depth)
                       comp-paths)]
-           (log/trace (str "add-bolt-at:" ((:morph-ps model) bolt-at) "; comp-paths: " (string/join "," comp-paths)))
            (when (not (some empty? comp-bolts))
              (filter #(not (= :fail %))
                      (mapfn #(let [assoc (if (empty? path) %
                                              (assoc-in bolt path %))]
                                assoc)
-                            (filter (fn [with-comps]
-                                      (do
-                                        (log/debug (str "add-bolt-at: added all comps to bolt: '" ((:morph model)
-                                                                                with-comps)
-                                                        "'"))
-                                        with-comps))
-                                    (add-comps bolt-at
-                                               model
-                                               comp-paths
-                                               comp-bolts
-                                               (+ 1 depth)
-                                               max-depth
-                                               top-bolt
-                                               truncate?
-                                               take-n))))))))
+                            (lazy-seq
+                             (add-comps bolt-at
+                                        model
+                                        comp-paths
+                                        comp-bolts
+                                        (+ 1 depth)
+                                        max-depth
+                                        top-bolt
+                                        truncate?
+                                        take-n))))))))
 (defn generate
   "Return one (by default) or _n_ (using :take _n_) expressions matching spec _spec_ given the model _model_."
   [spec language-model


+(log/debug)

+(log/debug)

--- src/babel/generate.cljc
+++ src/babel/generate.cljc
@@ -135,6 +135,7 @@
                           depth max-depth top-bolt path-from-top)
               (let [path (first comp-paths)
                     bolts-at (first bolts-at-paths)]
+                (log/debug (str "add-comps to: " ((:morph-ps model) bolt) "@" path))
                 (flatten
                  (mapfn
                   (fn [bolt-at]


more logging

more logging

--- src/babel/generate.cljc
+++ src/babel/generate.cljc
@@ -134,7 +134,11 @@
                           depth max-depth top-bolt path-from-top)
               (let [path (first comp-paths)
                     bolts-at (first bolts-at-paths)]
-                (log/debug (str "add-comps to: " ((:morph-ps model) bolt) "@" path))
+                (log/debug (str "add-comps to: "
+                                (if (not (= bolt top-bolt))
+                                  (str ((:morph-ps model) top-bolt)
+                                       "/"))
+                                ((:morph-ps model) bolt) "@" path))
                 (flatten
                  (mapfn
                   (fn [bolt-at]


Add tests for with-optional-tail

Add tests for with-optional-tail

--- test/cljs/comic_reader/ui/base_test.cljs
+++ test/cljs/comic_reader/ui/base_test.cljs
@@ -28,3 +28,10 @@
                                (:content el)])
                             [{:url "a" :content "A"}
                              {:url "b" :content "B"}]))))
+
+(deftest test-with-optional-tail
+  (is (= [:div]
+         (sut/with-optional-tail [:div] nil)))
+
+  (is (= [:div [1 2 3]]
+         (sut/with-optional-tail [:div] [1 2 3]))))


CMR-1399: Keep RabbitMQ connections alive by sending a heartbeat request every 2 minutes

--- message-queue-lib/src/cmr/message_queue/config.clj
+++ message-queue-lib/src/cmr/message_queue/config.clj
@@ -35,4 +35,5 @@
    :port (rabbit-mq-port)
    :admin-port (rabbit-mq-admin-port)
    :username (rabbit-mq-user)
-   :password (rabbit-mq-password)})+   :password (rabbit-mq-password)
+   :requested-heartbeat 120})


Unify hash low level api to the mac one.

--- src/buddy/core/hash.clj
+++ src/buddy/core/hash.clj
@@ -41,6 +41,34 @@
    :sha3-384 #(SHA3Digest. 284)
    :sha3-512 #(SHA3Digest. 512)})

+;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
+;; Protocol definitions (abstractions)
+;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
+
+(defprotocol IDigest
+  (^:private digest* [input algorithm] "Low level interface, always returns bytes"))
+
+(defprotocol IHash
+  "Mac engine common interface definition."
+  (^:private update [_ bytes offset length] "Update bytes in a current instance.")
+  (^:private end [_] "Return the computed mac and reset the engine."))
+
+;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
+;; Low level api
+;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
+
+(defn update!
+  ([engine input]
+   (update engine input 0 (count input)))
+  ([engine input offset]
+   (update engine input offset (count input)))
+  ([engine input offset length]
+   (update engine input offset length)))
+
+(defn end!
+  [engine]
+  (end engine))
+
 (defn resolve-digest
   "Helper function for make Digest instances
   from algorithm parameter."
@@ -51,46 +79,68 @@
    (instance? IFn alg) (alg)
    (instance? Digest alg) alg))

-(defprotocol IDigest
-  (^:private digest* [input algorithm] "Low level interface, always returns bytes"))
+(defn hash-engine
+  "Create a hash engine instance."
+  [^Keyword alg]
+  (let [engine (resolve-digest alg)]
+    (reify
+      IHash
+      (update [_ input offset length]
+        (.update engine input offset length))
+      (end [_]
+        (let [buffer (byte-array (.getDigestSize engine))]
+          (.doFinal engine buffer 0)
+          buffer)))))
+
+;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
+;; Implementation details for different data types.
+;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
+
+(defn- hash-plain-data
+  [^bytes input ^Keyword alg]
+  (let [engine (hash-engine alg)]
+    (update! engine input)
+    (end! engine)))
+
+(defn- hash-stream-data
+  [^java.io.InputStream input ^Keyword alg]
+  (let [engine (hash-engine alg)
+        buffer (byte-array 5120)]
+    (loop []
+      (let [readed (.read input buffer 0 5120)]
+        (when-not (= readed -1)
+          (update! engine buffer 0 readed)
+          (recur))))
+    (end! engine)))

 (extend-protocol IDigest
   (Class/forName "[B")
   (digest* [^bytes input ^Keyword alg]
-    (let [digest (resolve-digest alg)
-          buffer (byte-array (.getDigestSize digest))]
-      (.update digest input 0 (count input))
-      (.doFinal digest buffer 0)
-      buffer))
+    (hash-plain-data input alg))

   String
   (digest* [^String input ^Keyword alg]
-    (digest* (str->bytes input) alg))
+    (hash-plain-data (str->bytes input) alg))

   java.io.InputStream
   (digest* [^java.io.InputStream input ^Keyword alg]
-    (let [digest  (resolve-digest alg)
-          buffer1 (byte-array 5120)
-          buffer2 (byte-array (.getDigestSize digest))]
-      (loop []
-        (let [readed (.read input buffer1 0 5120)]
-          (when-not (= readed -1)
-            (.update digest buffer1 0 readed)
-            (recur))))
-      (.doFinal digest buffer2 0)
-      buffer2))
+    (hash-stream-data input alg))

   java.io.File
   (digest* [^java.io.File input ^Keyword alg]
-    (digest* (io/input-stream input) alg))
+    (hash-stream-data (io/input-stream input) alg))

   java.net.URL
   (digest* [^java.net.URL input ^Keyword alg]
-    (digest* (io/input-stream input) alg))
+    (hash-stream-data (io/input-stream input) alg))

   java.net.URI
   (digest* [^java.net.URI input ^Keyword alg]
-    (digest* (io/input-stream input) alg)))
+    (hash-stream-data (io/input-stream input) alg)))
+
+;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
+;; High level public api.
+;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;

 (defn digest
   "Generic function for create cryptographic hash."
@@ -105,4 +155,3 @@
 (def sha3-512 #(digest % :sha3-512))
 (def sha1 #(digest % :sha1))
 (def md5 #(digest % :md5))
-


Refactored and improved get-css fn to handle nested hiccup structures

--- src/clojurescript_css_modules_demo/js/core.cljs
+++ src/clojurescript_css_modules_demo/js/core.cljs
@@ -3,25 +3,33 @@
             [reagent.core :as r]
             [clojure.string :as string]
             [cljs.reader :as reader]
+            [clojure.walk :refer [prewalk]]
             ))

 (enable-console-print!)

 (println "CSS Modules:" js/cssModules)

+(defn ^:private populate-css-module-classes [e]
+  (prewalk (fn [x]
+             (let [key (if (keyword? x) (str (name x)))
+                   class-lookup (if (some? key) (re-find #"(?:CSS>)[^\s][a-zA-Z>-]+" key))
+                   tree (if (some? key) (rest (string/split class-lookup #">")))
+                   class-names (or (if (not (empty? tree)) (apply aget (js* "cssModules") tree)) ".")
+                   joined-class-names (string/replace-all class-names #" " ".")
+                   new-key (if (some? key) (keyword (string/replace-first key #"(?:CSS>)[^\s][a-zA-Z>-]+" joined-class-names)))
+                   ]
+
+               (if (some? key) new-key x)
+               )
+             ) e)
+  )
+
 (defn get-css
   "Helper fn that takes Reagent's hiccup syntax and replaces .CSS>x classes with their respective CSS module name(s). See usage in header below."
-  [i]
-  (let [stringified (str i)
-        class-lookup (re-find #"(?:CSS>)[^\s][a-zA-Z>-]+" stringified)
-        tree (rest (string/split class-lookup #">"))
-        class-names (or (apply aget (js* "cssModules") tree) ".")
-        joined-class-names (string/replace-all class-names #" " ".")
-        output (reader/read-string (string/replace-first stringified #"(?:CSS>)[^\s][a-zA-Z>-]+" joined-class-names))
-        finished? (nil? (re-find #"(?:CSS>)[^\s][a-zA-Z>-]+" (str output)))]
-    (if finished?
-      output
-      (recur output))))
+  [v]
+  (into [] (map #(populate-css-module-classes %) v))
+  )

 (defn header []
   (get-css


keep enrolled_betas as a set

keep enrolled_betas as a set

--- src-cljs/frontend/components/account.cljs
+++ src-cljs/frontend/components/account.cljs
@@ -169,7 +169,7 @@
   (raise! owner [:preferences-updated {state/user-betas-key
                                        (if value
                                          (conj (set betas) id)
-                                         (remove #{id} (set betas)))}]))
+                                         (disj (set betas) id))}]))

 (defn beta-programs [app owner]
   (reify


don't draw multiple signup buttons

don't draw multiple signup buttons

--- src-cljs/frontend/components/drawing.cljs
+++ src-cljs/frontend/components/drawing.cljs
@@ -214,15 +214,20 @@
     (-> {:tick-ms 16
          :ticks {}}
       (move-mouse {:start-tick 10 :end-tick 45 :start-x vw :end-x rect-start-x :start-y 0 :end-y rect-start-y})
-      (draw-shape {:doc-id (:db/id document) :tool :rect :start-tick 50 :end-tick 100 :start-x rect-start-x :end-x rect-end-x
+      (draw-shape {:doc-id (:db/id document) :tool :rect :start-tick 50 :end-tick 100
+                   :start-x rect-start-x :end-x rect-end-x
                    :start-y rect-start-y :end-y rect-end-y
+                   :source "signup-animation"
                    :props {;; look into this later, right now it interfers with signup action
                            ;; :layer/ui-target "/signup"
                            :layer/signup-button true}})
-      (move-mouse {:tool :text :start-tick 100 :end-tick 120 :start-x rect-end-x :end-x text-start-x
+      (move-mouse {:tool :text :start-tick 100 :end-tick 120
+                   :start-x rect-end-x :end-x text-start-x
                    :start-y rect-end-y :end-y (- text-start-y (/ text-height 2))})
-      (draw-text {:text text :doc-id (:db/id document) :start-tick 120 :end-tick 200 :start-x text-start-x
-                  :end-x (+ text-start-x text-width) :start-y text-start-y :end-y (- text-start-y text-height)
+      (draw-text {:text text :doc-id (:db/id document) :start-tick 120 :end-tick 200
+                  :start-x text-start-x :end-x (+ text-start-x text-width)
+                  :start-y text-start-y :end-y (- text-start-y text-height)
+                  :source "signup-animation"
                   :props {;; look into this later, right now it interfers with signup action
                           ;;:layer/ui-target "/signup"
                           :layer/signup-button true}})
@@ -235,7 +240,8 @@
     (did-mount [_]
       ;; TODO: would be nice to get this a different way :(
       (let [vw (:width (utils/canvas-size))]
-        (when (< 640 vw) ;; only if not on mobile
+        (when (and (< 640 vw) ;; only if not on mobile
+                   (empty? (d/datoms @(om/get-shared owner :db) :avet :layer/source "signup-animation")))
           (run-animation owner (signup-animation document vw)))))
     om/IWillUnmount
     (will-unmount [_]


mix up fake emails in features art to seem real

--- src-cljs/frontend/components/landing.cljs
+++ src-cljs/frontend/components/landing.cljs
@@ -199,50 +199,50 @@
       [:div.access-avatar
        [:div.access-avatar-img]]
       [:div.access-details
-       [:span "danny@precursorapp.com"]
+       [:span "soren@prcr.sr"]
        [:span.access-status "Was granted access yesterday."]]]

      [:div.access-card
       [:div.access-avatar
        [:div.access-avatar-img]]
       [:div.access-details
-       [:span "danny@precursorapp.com"]
+       [:span "niobe@prcr.sr"]
        [:span.access-status "Was granted access yesterday."]]]

      [:div.access-card
       [:div.access-avatar
        [:div.access-avatar-img]]
       [:div.access-details
-       [:span "danny@precursorapp.com"]
+       [:span "ballard@prcr.sr"]
        [:span.access-status "Was granted access yesterday."]]]

      [:div.access-card.requesting
       [:div.access-avatar
        [:div.access-avatar-img]]
       [:div.access-details
-       [:span "danny@precursorapp.com"]
-       [:span.access-status "Requested access on just now."]]]
-
-     [:div.access-card
-      [:div.access-avatar
-       [:div.access-avatar-img]]
-      [:div.access-details
-       [:span "danny@precursorapp.com"]
-       [:span.access-status "Was granted access yesterday."]]]
-
-     [:div.access-card
-      [:div.access-avatar
-       [:div.access-avatar-img]]
-      [:div.access-details
-       [:span "danny@precursorapp.com"]
-       [:span.access-status "Was granted access yesterday."]]]
-
-     [:div.access-card
-      [:div.access-avatar
-       [:div.access-avatar-img]]
-      [:div.access-details
-       [:span "danny@precursorapp.com"]
-       [:span.access-status "Was granted access yesterday."]]]]]])
+       [:span "anderson@prcrsr.com"]
+       [:span.access-status "Requested access yesterday."]]]
+
+     [:div.access-card
+      [:div.access-avatar
+       [:div.access-avatar-img]]
+      [:div.access-details
+       [:span "smith@precursorapp.com"]
+       [:span.access-status "Was denied access yesterday."]]]
+
+     [:div.access-card
+      [:div.access-avatar
+       [:div.access-avatar-img]]
+      [:div.access-details
+       [:span "roland@prcr.sr"]
+       [:span.access-status "Was granted access today."]]]
+
+     [:div.access-card
+      [:div.access-avatar
+       [:div.access-avatar-img]]
+      [:div.access-details
+       [:span "morpheus@prcrsr.com"]
+       [:span.access-status "Was granted access today."]]]]]])

 (defn the-how [app owner]
   (reify


AB + CW | 100 | use new renderer design for current-password blur and input

--- src-cljs/stonecutter/change_password.cljs
+++ src-cljs/stonecutter/change_password.cljs
@@ -1,7 +1,8 @@
 (ns stonecutter.change-password
   (:require [dommy.core :as d]
             [stonecutter.validation :as v]
-            [stonecutter.renderer.change-password :as r])
+            [stonecutter.renderer.change-password :as r]
+            [stonecutter.controller.change-password :as c])
   (:require-macros [dommy.core :as dm]))

 (def current-password-input :#current-password)
@@ -70,12 +71,25 @@
   (when-let [e (dm/sel1 selector)]
     (d/listen! e event function)))

+(def change-password-form-state (atom {}))
+
+(defn update-state-input! [field]
+  (let [new-input-value (field (field-values))]
+    (swap! change-password-form-state #(assoc-in % [field :value] new-input-value))))
+
+(defn update-state-and-render [field controller-fn]
+  (update-state-input! field)
+  (swap! change-password-form-state controller-fn)
+  (r/render! @change-password-form-state))
+
 (defn start []
-  (setup-listener current-password-input :input update-current-password!)
+
+  (setup-listener current-password-input :input #(update-state-and-render :current-password (partial c/update-current-password-input)))
   (setup-listener new-password-input :input update-new-password!)
   (setup-listener current-password-input :input update-new-password!)
-  (setup-listener current-password-input :blur check-current-password!)
+  (setup-listener current-password-input :blur #(update-state-and-render :current-password (partial c/update-current-password-blur)))
   (setup-listener new-password-input :blur check-new-password!)
+
   (setup-listener change-password-form :submit block-invalid-submit))

 (set! (.-onload js/window) start)


Add long information for example.

Add long information for example.

--- src/cli4clj/example.clj
+++ src/cli4clj/example.clj
@@ -60,7 +60,8 @@
 ;;;                      The following simple example command is used to illustrate that arbitrary Clojure data types can be used.
 ;;;                      The command is intended to take a seq (e.g., a list or vector) which it converts into a CSV string.
                          :to-csv {:fn (fn [data] (reduce (fn [s d] (str s "," d)) (str (first data)) (rest data)))
-                                  :short-info "Seq to CSV"}
+                                  :short-info "Seq to CSV"
+                                  :long-info "E.g.: \"to-csv [1 2 3]\"}
                         }
                  }]
 ;;;  Last but not least, the CLI is started using the options defined above.


Move up for compile fix

Move up for compile fix

--- src/clj/shale/nodes.clj
+++ src/clj/shale/nodes.clj
@@ -131,6 +131,14 @@
         (car/return (modify-node pool id {:url url
                                           :tags tags
                                           :max-sessions max-sessions}))))))
+
+(s/defn ^:always-validate raw-sessions-with-node [pool    :- NodePool
+                                                  node-id :- s/Str]
+  (let [redis-conn (:redis-conn pool)]
+    (->> (redis/models redis-conn
+                       redis/SessionInRedis
+                       :include-soft-deleted? true)
+         (filter #(= node-id (:node-id %))))))

 (s/defn ^:always-validate destroy-node
   [pool :- NodePool
@@ -188,14 +196,6 @@
     :and [(s/recursive #'NodeRequirement)]
     :or  [(s/recursive #'NodeRequirement)]))

-(s/defn ^:always-validate raw-sessions-with-node [pool    :- NodePool
-                                                  node-id :- s/Str]
-  (let [redis-conn (:redis-conn pool)]
-    (->> (redis/models redis-conn
-                       redis/SessionInRedis
-                       :include-soft-deleted? true)
-         (filter #(= node-id (:node-id %))))))
-
 (s/defn ^:always-validate raw-session-count [pool    :- NodePool
                                              node-id :- s/Str]
   (count (raw-sessions-with-node pool node-id)))


Replace Joke API

Replace Joke API

--- src/cljs/app/jokes.cljs
+++ src/cljs/app/jokes.cljs
@@ -6,8 +6,8 @@
    [app.json :as json :refer [fetch-json]]
    [goog.string :as gstring]))

-(def endpoint {:url "http://api.icndb.com/jokes/random"
-               :extract #(get-in % ["value" "joke"]) })
+(def endpoint {:url "https://api.chucknorris.io/jokes/random"
+               :extract #(get-in % ["value"]) })

 (defn fresh-jokes
   "Channel buffering collections of n jokes from The Internet Chuck Norris Database"


add experimental support for converting ES6 iterators into seqs

--- src/cljs/cljs/core.cljs
+++ src/cljs/cljs/core.cljs
@@ -708,6 +708,22 @@

 (defn es6-iterator [coll]
   (ES6Iterator. (seq coll)))
+
+(declare es6-iterator-seq)
+
+(deftype ES6IteratorSeq [value iter]
+  ISeqable
+  (-seq [this] this)
+  ISeq
+  (-first [_] value)
+  (-rest [_]
+    (es6-iterator-seq iter)))
+
+(defn es6-iterator-seq [iter]
+  (let [v (.next iter)]
+    (if (.-done v)
+      ()
+      (ES6IteratorSeq. (.-value v) iter))))

 ;;;;;;;;;;;;;;;;;;; Murmur3 Helpers ;;;;;;;;;;;;;;;;

@@ -8221,6 +8237,9 @@
   (-pr-writer [coll writer opts] (pr-sequential-writer writer pr-writer "#{" " " "}" opts coll))

   Range
+  (-pr-writer [coll writer opts] (pr-sequential-writer writer pr-writer "(" " " ")" opts coll))
+
+  ES6IteratorSeq
   (-pr-writer [coll writer opts] (pr-sequential-writer writer pr-writer "(" " " ")" opts coll))

   Atom


Added neg? per #34

Added neg? per #34


whoops forgot to put in timer

whoops forgot to put in timer

--- src/cljs/demo/core.cljs
+++ src/cljs/demo/core.cljs
@@ -22,7 +22,7 @@
 (defonce timer (atom  (js/Date.)))
 (defonce state (r/atom "state"))

-#_(def time-updater (js/setInterval
+(def time-updater (js/setInterval
                    #(swap!
                      circle-state
                      (fn [data]


session management

session management

--- src/clojure2d/utils.clj
+++ src/clojure2d/utils.clj
@@ -1,35 +1,17 @@
 (ns clojure2d.utils
   (:require [clojure.string :as s]
-            [clojure2d.math :as m]))
+            [clojure2d.math :as m]
+            [clojure.java.io :as io]))

 (set! *warn-on-reflection* true)
 (set! *unchecked-math* true)

-(defn repeat-val
-  "Repeats given value num times and return String"
-  [v cnt]
-  (s/join (repeat cnt v)))
-
-(defn pad-left
-  "Pad string with given char(s)"
-  ([string cnt]
-   (pad-left string cnt \space))
-  ([string cnt padchr]
-   (let [c (count string)]
-     (if (< c cnt)
-       (str (repeat-val padchr (- cnt c)) string)
-       string))))
-
 (defn to-hex
   "return hex value of given number, padded with leading zeroes if given length"
   ([n]
-   (s/upper-case
-    (cond
-      (instance? Byte n) (Integer/toHexString (unchecked-byte n))
-      (instance? Integer n) (Integer/toHexString (unchecked-int n))
-      :else (Long/toHexString (unchecked-long n)))))
+   (format "%X" n))
   ([n pad]
-   (pad-left (to-hex n) pad \0)))
+   (format (str "%0" pad "X") n)))

 (defmacro time-with-name
   "Evaluates expr and prints the time it took.  Returns the value of
@@ -47,9 +29,6 @@
   [f ^ints array idx]
   (let [v (aget array idx)]
     (aset array idx ^int (f v))))
-
-(def ainc! (partial array-mutate! inc))
-(def adec! (partial array-mutate! dec))

 (defmacro amap!
   "Mutating version of amap"
@@ -86,3 +65,80 @@
   (let [tick (atom (dec v))]
     #(swap! tick inc)))

+(defn make-session-name
+  ""
+  ([]
+   (let [^java.text.SimpleDateFormat sdf (java.text.SimpleDateFormat. "yyyyMMddHHmmss")
+         date (java.util.Date.)]
+     [(.format sdf date) (to-hex (hash date))])))
+
+(def ^:dynamic *log-to-file* false)
+
+(let [session-name (atom nil) ; store session name as a current date
+      session-file (agent nil) ; logger Writer, created and used when *log-to-file* is true
+      session-cnt (atom nil) ; counter for next filename fn
+      ^java.text.SimpleDateFormat sdf (java.text.SimpleDateFormat. "yyyy-MM-dd HH:mm:ss")
+      nilfn (fn [_] nil)]
+
+  (defn close-session
+    ""
+    []
+    (when-not (nil? @session-file)
+      (send session-file (fn [^java.io.Writer o]
+                           (.flush o)
+                           (.close o)
+                           nil)))
+    (swap! session-name nilfn)
+    (swap! session-cnt nilfn))
+
+  (defn make-session
+    ""
+    []
+    (let [nname (make-session-name)]
+      (swap! session-name (fn [_] nname))
+
+      (when *log-to-file*
+        (let [fname (str "log/" (first nname) ".log")]
+          (io/make-parents fname)
+          (send session-file (fn [^java.io.Writer o]
+                               (do
+                                 (when-not (nil? o)
+                                   (.flush o)
+                                   (.close o))
+                                 (let [^java.io.Writer no (io/writer fname :append true)]
+                                   (.write no (str "Session id: " (second nname) "\n"))
+                                   no))))))
+
+      (swap! session-cnt (fn [_] (make-counter 0)))))
+
+  (defn log
+    ""
+    [s]
+    (when *log-to-file*
+      (if (nil? @session-file)
+        (do
+          (make-session)
+          (log s))
+        (let [to-log (str (.format sdf (java.util.Date.)) ": " s "\n")]
+          (send session-file (fn [^java.io.Writer o]
+                               (.write o to-log)
+                               (.flush o)
+                               o)))))
+    true)
+
+  (defn next-filename
+    ""
+    [prefix]
+    (if (nil? @session-name)
+      (do
+        (make-session)
+        (next-filename prefix))
+      (str prefix (second @session-name) "_" (format "%06d" (@session-cnt)))))
+
+  (defn get-session-name
+    ""
+    []
+    @session-name)
+
+
+)


CMR-5195 Addresses PR comments. Adds estimation for netcdf4.

--- src/cmr/sizing/core.clj
+++ src/cmr/sizing/core.clj
@@ -22,6 +22,13 @@
 ;;; Note that all internal operations for estimating size are performed
 ;;; assuming bytes as the units.

+(defn- read-number
+  "If value is string, read-string.  Otherwise ignore."
+  [value]
+  (if (string? value)
+    (read-string value)
+    value))
+
 (defn- get-measurement
   [variable]
   (let [dims (get-in variable [:umm :Dimensions])
@@ -32,21 +39,27 @@

 (defn- get-avg-gran-size
   "Gets SizeEstimation value for AverageSizeOfGranulesSampled and parses it to a number."
-  [vars]
-  (let [value (get-in (first vars) [:umm :SizeEstimation :AverageSizeOfGranulesSampled])]
-    (if (string? value)
-      (read-string value)
-      value)))
-
-(defn- get-avg-compression-rate
+  [variable]
+  (-> variable
+      (get-in [:umm :SizeEstimation :AverageSizeOfGranulesSampled])
+      read-number))
+
+(defn- get-avg-compression-rate-ascii
   "Gets SizeEstimation value for AvgCompressionRateASCII and parses it to a number."
-  [vars]
-  (let [value (get-in (first vars) [:umm :SizeEstimation :AvgCompressionRateASCII])]
-    (if (string? value)
-      (read-string value)
-      value)))
+  [variable]
+  (-> variable
+      (get-in [:umm :SizeEstimation :AvgCompressionRateASCII])
+      read-number))
+
+(defn- get-avg-compression-rate-netcdf4
+  "Gets SizeEstimation value for AvgCompressionRateNetCDF4 and parses it to a number."
+  [variable]
+  (-> variable
+      (get-in [:umm :SizeEstimation :AvgCompressionRateNetCDF4])
+      read-number))

 (defn estimate-dods-size
+  "Calculates the estimated size for DODS format."
   [granule-count variables]
   (let [compression 1
         metadata 0 ; included here for symmetry
@@ -54,27 +67,36 @@
     (+ (* granule-count compression measurements) metadata)))

 (defn- estimate-netcdf3-size
+  "Calculates the estimated size for NETCDF3 format."
   [granule-count variables metadata]
   (let [compression 1
         measurements (reduce + (map get-measurement variables))]
     (+ (* granule-count compression measurements) metadata)))

-(defn- estimate-ascii-size
-  "Calculates the estimated size for ASCII format."
-  [granule-count variables params]
-  (let [metadata 0
-        avg-gran-size (get-avg-gran-size variables)
-        edsc-size-estimate (read-string (:edsc-size-estimate params))
-        avg-compression-rate (get-avg-compression-rate variables)
-        measurements (reduce + (map get-measurement variables))]
-    (* edsc-size-estimate (+ (* (/ (/ edsc-size-estimate granule-count) avg-gran-size) avg-compression-rate) metadata))))
+(defn- estimate-netcdf4-or-ascii-size
+  "Calculates the estimated size for ASCII or NETCDF4 format.
+   total-granule-input-bytes is a value given by the client in the size estimate request."
+  [granule-count variables params fmt]
+  (reduce (fn [total-estimate variable]
+            (let [avg-gran-size (get-avg-gran-size variable)
+                  total-granule-input-bytes (read-string (:total-granule-input-bytes params))
+                  avg-compression-rate (if (= fmt :nc4)
+                                         (get-avg-compression-rate-netcdf4 variable)
+                                         (get-avg-compression-rate-ascii variable))]
+              (+ total-estimate
+                 (* total-granule-input-bytes
+                    (* (/ (/ total-granule-input-bytes granule-count) avg-gran-size
+                          avg-compression-rate))))))
+          0
+          variables))

 (defn- -estimate-size
   [fmt granule-count vars granule-metadata-size params]
   (case (keyword (string/lower-case fmt))
     :dods (estimate-dods-size granule-count vars)
     :nc (estimate-netcdf3-size granule-count vars granule-metadata-size)
-    :ascii (estimate-ascii-size granule-count vars params)
+    :nc4 (estimate-netcdf4-or-ascii-size granule-count vars params fmt)
+    :ascii (estimate-netcdf4-or-ascii-size granule-count vars params fmt)
     (do
       (log/errorf "Cannot estimate size for %s (not implemented)." fmt)
       {:errors ["not-implemented"]})))
@@ -165,14 +187,14 @@
               {:errors (errors/check
                         [not data-files metadata-errors/empty-gnl-data-files])})

-        params (assoc params :edsc-size-estimate (:edsc-size-estimate raw-params))
+        params (assoc params :total-granule-input-bytes (:total-granule-input-bytes raw-params))
         fmt (:format params)]
     (log/trace "raw-params:" raw-params)
     (log/debug "Got format:" fmt)
     (log/debug "Got data-files:" (vec data-files))
     (log/debug "Got services:" services)
     (log/debug "Got vars:" vars)
-    (log/debug "Got edsc-size-estimate:" (:edsc-size-estimate raw-params))
+    (log/debug "Got total-granule-input-bytes:" (:total-granule-input-bytes raw-params))
     (process-results
       {:params params
        :data-files data-files


reverting back from (reduce concat) to (mapcat) because speed seems worse with the latter; also remove some local variables for concision

--- src/babel/generate.cljc
+++ src/babel/generate.cljc
@@ -66,21 +66,16 @@
      ;; The result is a trellis for each bolt, and a path through this
      ;; trellis is a generated expression, with one complement for
      ;; each complement position.
-     (map (fn [each-bolt-and-comps]
-            (let [paths-to-comps (keys each-bolt-and-comps)
-                  vals (vals each-bolt-and-comps)]
-              ;; TODO: further flatten this into the overall ->> pipeline
-              (map (fn [each-path-through-trellis]
-                     (zipmap paths-to-comps each-path-through-trellis))
-                   (apply combo/cartesian-product vals)))))
-
-     (reduce concat)
+     (mapcat (fn [each-bolt-and-comps]
+               ;; TODO: further flatten this into the overall ->> pipeline
+               (map (fn [each-path-through-trellis]
+                      (zipmap (keys each-bolt-and-comps) each-path-through-trellis))
+                    (apply combo/cartesian-product (vals each-bolt-and-comps)))))

      ;; for each such path through a trellis, unify the bolt with all of its complements to create a final expression tree.
      (map (fn [bolt-and-comps]
             (let [bolt (get bolt-and-comps [])
-                  paths-and-comps (dissoc bolt-and-comps [])
-                  paths-to-comps (keys paths-and-comps)]
+                  paths-and-comps (dissoc bolt-and-comps [])]
               ;; TODO: further flatten this into the overall ->> pipeline
               (reduce (fn [a b]
                         (let [result
@@ -94,7 +89,7 @@
                             (map (fn [path-to-comp]
                                    (let [complement (get paths-and-comps path-to-comp)]
                                      (assoc-in bolt path-to-comp complement)))
-                                 paths-to-comps))))))
+                                 (keys paths-and-comps)))))))

      (map #(do-defaults % model)) ;; for each tree, run model defaults.


improve readability: move use of index closer to where it is used

--- src/babel/generate.cljc
+++ src/babel/generate.cljc
@@ -157,18 +157,14 @@
                                       truncate-children true}}]
   (log/trace (str "add-complement-to-bolt: " (show-bolt bolt language-model)
                   "@[" (string/join " " path) "]" "^" total-depth))
-  (let [index (:index language-model)
-        lexicon (or (-> :generate :lexicon language-model)
+  (let [lexicon (or (-> :generate :lexicon language-model)
                     (:lexicon language-model))
         from-bolt bolt ;; so we can show what (add-complement-to-bolt) did to the input bolt, for logging.
         spec (get-in bolt path)
         immediate-parent (get-in bolt (butlast path))
         complement-candidate-lexemes
-        (if (not (= true
-                    (get-in bolt (concat path [:phrasal]))))
-          (let [indexed (if index
-                          (get-lex immediate-parent :comp index))
-                pred (get-in spec [:synsem :sem :pred])
+        (if (not (= true (get-in bolt (concat path [:phrasal]))))
+          (let [pred (get-in spec [:synsem :sem :pred])
                 cat (get-in spec [:synsem :cat])
                 pred-set (if (and (:pred2lex language-model)
                                   (not (= :top pred)))
@@ -185,14 +181,14 @@
                       (intersection-with-identity pred-set cat-set))]
             (if (not (empty? subset))
               subset
-              (if (not (empty? indexed))
-                indexed
-                (do
-                  (log/warn (str "no candidate lexemes were found."))
-                  nil)))))
-
+              (let [index (:index language-model)
+                    indexed (if index (get-lex immediate-parent :comp index))]
+                (if (not (empty? indexed))
+                  indexed
+                  (do
+                    (log/warn (str "no candidate lexemes were found."))
+                    nil))))))
         bolt-child-synsem (strip-refs (get-in bolt (concat path [:synsem]) :top))
-
         lexical-complements (lazy-shuffle
                              (filter (fn [lexeme]
                                        (and (not-fail? (unify (strip-refs (get-in lexeme [:synsem] :top))


more cleanup

more cleanup

--- src/babel/generate.cljc
+++ src/babel/generate.cljc
@@ -160,18 +160,13 @@
 bolt, from deepest and working upward to the top. Return a lazy
 sequence of having added all possible complements at each node in the
 bolt."
-  (let [bolt-groups
-        (filter #(not (empty? %))
-                bolt-groups)
-        bolts (reduce concat bolt-groups)]
-    (when (not (empty? bolt-groups))
-      (lazy-mapcat
-       (fn [bolt]
-         (log/trace (str "add-all-comps: adding comps to bolt: " (show-bolt bolt language-model)))
-         (add-all-comps-with-paths [bolt] language-model total-depth
-                                   (find-comp-paths-in (bolt-depth bolt))
-                                   truncate-children max-total-depth))
-       bolts))))
+  (let [bolts (reduce concat bolt-groups)]
+    (lazy-mapcat
+     (fn [bolt]
+       (add-all-comps-with-paths [bolt] language-model total-depth
+                                 (find-comp-paths-in (bolt-depth bolt))
+                                 truncate-children max-total-depth))
+     bolts)))

 ;; TODO: make this non-recursive by using mapcat.
 (defn add-all-comps-with-paths [bolts language-model total-depth comp-paths truncate-children max-total-depth]


whitespace

whitespace

--- src/babel/italiano.cljc
+++ src/babel/italiano.cljc
@@ -198,4 +198,3 @@
   (load "babel/italiano")
   (in-ns 'babel.italiano)
   (test-cm))
-


fix spelling

fix spelling

--- src/overtone/sc/machinery/server/connection.clj
+++ src/overtone/sc/machinery/server/connection.clj
@@ -55,7 +55,7 @@
   (server-snd "/notify" 1))

 (defn- logged-sh
-  "Run a shell command an log any errors. Returns stdout."
+  "Run a shell command and log any errors. Returns stdout."
   [cmd & args]
   (let [res (apply sh cmd args)]
     (when-not (zero? (:exit res))


routing: remove Safari double dispatch hack because it breaks the back navigation sometimes

--- examples/_common/middleware/routing.cljs
+++ examples/_common/middleware/routing.cljs
@@ -44,15 +44,6 @@
 (defn new-history
   []
   (let [history (Html5History.)]
-    ; prevent firing initial event in Safari, source;
-    ; http://anmonteiro.com/2015/09/solving-closure-librarys-html5history-double-event-dispatch/
-    (when (.-useFragment_ history)
-      (goog.events/unlisten (.-window_ history)
-                            goog.events.EventType.POPSTATE
-                            (.-onHistoryEvent_ history)
-                            false
-                            history))
-
     (.setEnabled history true)
     (->History history)))


Update Hello world version.

Update Hello world version.

--- examples/hello-world/project.clj
+++ examples/hello-world/project.clj
@@ -1,8 +1,8 @@
-(defproject hello-world "0.37.0"
+(defproject hello-world "0.38.0"
   :license {:name "Eclipse Public License"
             :url "http://www.eclipse.org/legal/epl-v10.html"}
   :dependencies [[org.clojure/clojure "1.10.1"]
-                 [uncomplicate/neanderthal "0.37.0"]
+                 [uncomplicate/neanderthal "0.38.0"]
                  ;;Optional. If bytedeco is not present, a system-wide MKL is used.
                  [org.bytedeco/mkl-platform-redist "2020.3-1.5.4"]]
   ;; If on Java 9+, you have to uncomment the following JVM option.


Fixes filename too long that comes up in conjunction with macro expanding (#77)

--- src/pigeon_backend/services/message_service.clj
+++ src/pigeon_backend/services/message_service.clj
@@ -87,8 +87,9 @@
                                             (for [entry send-limit-rules
                                                   :let [messages-counted-by-recipient
                                                           (into {}
-                                                            (for [[k v] (group-by :recipient (:messages entry))]
-                                                              {k (count v)}))]]
+                                                            (mapv
+                                                              (fn [[k v]] {k (count v)})
+                                                              (group-by :recipient (:messages entry))))]]
                                               (>= (get messages-counted-by-recipient recipient 0) (:value entry))))
           shared-send-limit-rules (->> send-limits
                                        (filter #(and (= (:from_node %) sender)


fixed issue of not string

fixed issue of not string

--- src/clj_social/core.clj
+++ src/clj_social/core.clj
@@ -61,10 +61,10 @@
     (if (= :wechat (keyword type))
       (let [token (.getAccessToken this verifier)]
         ;; bind openid to secret
-        [(.getToken token) (.getSecret token)])
+        [(.getToken token) (str (.getSecret token))])
       (let [access-token (getAccessToken this verifier)
             id (getId this access-token)]
-        [(.getToken access-token) id])))
+        [(.getToken access-token) (str id)])))
   (getUserInfo [this access-token id]
     (let [params (build-params this {:access-token access-token :id id})
           req (OAuthRequest. Verb/GET ((spec type) :user-url))


Adapt `binary` and `unbinary` for cljs. Since not provided by p5js implementing in javascript.

--- src/cljc/quil/core.cljc
+++ src/cljc/quil/core.cljc
@@ -694,10 +694,10 @@
   the number of digits used."
   ([val]
    #?(:clj (PApplet/binary (int val))
-      :cljs (.binary (ap/current-applet) val)))
+      :cljs (.toString val 2)))
   ([val num-digits]
    #?(:clj (PApplet/binary (int val) (int num-digits))
-      :cljs (.binary (ap/current-applet) val num-digits))))
+      :cljs (subs (.toString val 2) 0 num-digits))))

 (defn
   ^{:requires-bindings true
@@ -4378,7 +4378,7 @@
   integers to strings."
   [str-val]
   #?(:clj (PApplet/unbinary (str str-val))
-     :cljs (.unbinary (ap/current-applet) (str str-val))))
+     :cljs (js/parseInt str-val 2)))

 (defn
   ^{:require-binding false


extending protocols to nil, updated API fns to reflect that. refs #23

--- src/cljs/cljs/core.cljs
+++ src/cljs/cljs/core.cljs
@@ -198,8 +198,7 @@
   "Returns a possibly empty seq of the items after the first. Calls seq on its
   argument."
   [coll]
-  (when-let [s (seq coll)]
-    (-rest s)))
+  (-rest (seq coll)))

 (defn next
   "Returns a seq of the items after the first. Calls seq on its
@@ -465,14 +464,7 @@
   "Returns the number of items in the collection. (count nil) returns
   0.  Also works on strings, arrays, and Maps"
   [coll]
-  (if (not (nil? coll))
-    (if (satisfies? ICounted coll)
-      (-count coll)
-      (loop [s (seq coll) n 0]
-	(if s
-	  (recur (next s) (inc n))
-	  n)))
-    0))
+  (-count coll))

 (defn nth
   "Returns the value at the index. get returns nil if index out of
@@ -480,22 +472,16 @@
   also works for strings, arrays, regex Matchers and Lists, and,
   in O(n) time, for sequences."
   ([coll n]
-     (when-not (nil? coll)
-       (-nth coll n)))
+     (-nth coll n))
   ([coll n not-found]
-     (if (nil? coll)
-       not-found
-       (-nth coll n not-found))))
+     (-nth coll n not-found)))

 (defn get
   "Returns the value mapped to key, not-found or nil if key not present."
   ([o k]
-     (when-not (nil? o)
-       (-lookup o k)))
+     (-lookup o k))
   ([o k not-found]
-     (if (nil? o)
-       not-found
-       (-lookup o k not-found))))
+     (-lookup o k not-found)))

 (defn assoc
   "assoc[iate]. When applied to a map, returns a new map of the
@@ -503,8 +489,7 @@
    val(s). When applied to a vector, returns a new vector that
    contains val at index. Note - index must be <= (count vector)."
   [coll k v]
-  (when-not (nil? coll)
-    (-assoc coll k v)))
+  (-assoc coll k v))

 (defn zipmap
   "Returns a map with the keys mapped to the corresponding vals."
@@ -522,25 +507,24 @@
   "dissoc[iate]. Returns a new map of the same (hashed/sorted) type,
   that does not contain a mapping for key(s)."
   [coll k]
-  (when-not (nil? coll)
-    (-dissoc coll k)))
+  (-dissoc coll k))

 (defn with-meta
   "Returns an object of the same type and value as obj, with
   map m as its metadata."
   [o meta]
-  (when-not (nil? o) (-with-meta o meta)))
+  (-with-meta o meta))

 (defn meta
   "Returns the metadata of obj, returns nil if there is no metadata."
   [o]
-  (when-not (nil? o) (-meta o)))
+  (-meta o))

 (defn peek
   "For a list or queue, same as first, for a vector, same as, but much
   more efficient than, last. If the collection is empty, returns nil."
   [coll]
-  (when-not (nil? coll) (-peek coll)))
+  (-peek coll))

 (defn pop
   "For a list or queue, returns a new list/queue without the first
@@ -548,7 +532,7 @@
   the collection is empty, throws an exception.  Note - not the same
   as next/butlast."
   [coll]
-  (when-not (nil? coll) (-pop coll)))
+  (-pop coll))

 (defn contains?
   "Returns true if key is present in the given collection, otherwise
@@ -557,13 +541,13 @@
   range of indexes. 'contains?' operates constant or logarithmic time;
   it will not perform a linear search for a value.  See also 'some'."
   [coll v]
-  (if (nil? coll) false (-contains? coll v)))
+  (-contains? coll v))

 (defn disj
   "disj[oin]. Returns a new set of the same (hashed/sorted) type, that
   does not contain key(s)."
   [coll v]
-  (when-not (nil? coll) (-disjoin coll v)))
+  (-disjoin coll v))

 (defn empty?
   "Returns true if coll has no items - same as (not (seq coll)).
@@ -725,6 +709,58 @@
          (if (< n (-count cicoll))
            (recur (f val (-nth cicoll n)) (inc n))
            val))))
+
+(extend-type nil
+  ICounted
+  (-count [coll] 0)
+
+  IEmptyableCollection
+  (-empty [coll] nil)
+
+  ICollection
+  (-conj [coll o] (list o))
+
+  IIndexed
+  (-nth
+   ([coll n] nil)
+   ([coll n not-found] not-found))
+
+  ISeq
+  (-first [coll] nil)
+  (-rest [coll] (list))
+
+  ILookup
+  (-lookup
+   ([o k] nil)
+   ([o k not-found] not-found))
+
+  IAssociative
+  (-assoc [coll k v] (hash-map k v))
+
+  IMap
+  (-dissoc [coll k] nil)
+
+  ISet
+  (-contains? [coll v] false)
+  (-disjoin [coll v] nil)
+
+  IStack
+  (-peek [coll] nil)
+  (-pop [coll] nil)
+
+  IMeta
+  (-meta [o] nil)
+
+  IWithMeta
+  (-with-meta [o meta] nil))
+
+(extend-type default
+  ICounted
+  (-count [coll]
+    (loop [s (seq coll) n 0]
+      (if s
+	(recur (next s) (inc n))
+	n))))

 (extend-type goog.global.Date
   IEquiv
@@ -1321,6 +1357,7 @@
      (if xs
        (recur (conj coll x) (first xs) (next xs))
        (conj coll x))))
+

 ;;; Math - variadic forms will not work until the following implemented:
 ;;; first, next, reduce


Avoid unlimited-use.

Avoid unlimited-use.

--- src/clojournal/repl.clj
+++ src/clojournal/repl.clj
@@ -1,10 +1,10 @@
 (ns clojournal.repl
-  (:use clojournal.handler
-        ring.server.standalone
+  (:use [clojournal.handler :refer [app init destroy]]
+        [ring.server.standalone :refer [serve]]
         [ring.middleware
-         [file :only [wrap-file]]
-         [content-type :only [wrap-content-type]]
-         [not-modified :only [wrap-not-modified]]]))
+         [file :refer [wrap-file]]
+         [content-type :refer [wrap-content-type]]
+         [not-modified :refer [wrap-not-modified]]]))

 (defonce server (atom nil))


Fixed issue #29: Logging should be race condition-free.

--- src/clouseau/server.clj
+++ src/clouseau/server.clj
@@ -80,6 +80,12 @@
      :subname     "changes.db"
     })

+(defn println-and-flush
+    "Original (println) has problem with syncing when it's called from more threads. This function is a bit better."
+    [& more]
+    (.write *out* (str (clojure.string/join " " more) "\n"))
+    (flush))
+
 (defn get-calendar
     "Gets a calendar using the default time zone and locale."
     []
@@ -143,7 +149,7 @@
     (if (and (not-empty-parameter? package) (not-empty-parameter? description))
         (let [date (format-date-time (get-calendar))]
             (jdbc/insert! changes-db :changes {:date_time date :user_name user-name :package package :description description})
-            (println date user-name package)
+            (println-and-flush date user-name package)
         )))

 (defn render-html-header
@@ -286,11 +292,11 @@

 (defn log-request-information
     [request]
-    (println "time:        " (.toString (new java.util.Date)))
-    (println "addr:        " (request :remote-addr))
-    (println "params:      " (request :params))
-    (println "user-agent:  " ((request :headers) "user-agent"))
-    (println ""))
+    (println-and-flush "time:        " (.toString (new java.util.Date)))
+    (println-and-flush "addr:        " (request :remote-addr))
+    (println-and-flush "params:      " (request :params))
+    (println-and-flush "user-agent:  " ((request :headers) "user-agent"))
+    (println-and-flush ""))

 (defn get-products-without-descriptions
     [products package-descriptions]
@@ -346,9 +352,9 @@
           new-description     (get params "new-description")
           new-user-name       (get params "user-name")
           old-user-name       (get (get cookies "user-name") :value)]
-          (println "Incoming cookies: " cookies)
+          (println-and-flush "Incoming cookies: " cookies)
           (let [response (process package new-description format new-user-name old-user-name)]
-              (println "Outgoing cookies: " (get response :cookies))
+              (println-and-flush "Outgoing cookies: " (get response :cookies))
               response
           )))

@@ -357,22 +363,22 @@
     [request]
     (let [descriptions (read-all-descriptions)
           user-name    (get (get (request :cookies) "user-name") :value)]
-        ;(println descriptions)
+        ;(println-and-flush descriptions)
         (-> (http-response/response (html-renderer-descriptions descriptions user-name))
             (http-response/content-type "text/html"))))

 (defn return-file
     [file-name content-type]
     (let [file (new java.io.File "www" file-name)]
-        (println "Returning file " (.getAbsolutePath file))
-        (println "")
+        (println-and-flush "Returning file " (.getAbsolutePath file))
+        (println-and-flush "")
         (-> (http-response/response file)
             (http-response/content-type content-type))))

 (defn handler
     "Handler that is called by Ring for all requests received from user(s)."
     [request]
-    (println "request URI: " (request :uri))
+    (println-and-flush "request URI: " (request :uri))
     (let [uri (request :uri)]
         (condp = uri
             "/favicon.ico"       (return-file "favicon.ico" "image/x-icon")


review changes pt 2

review changes pt 2

--- src/clj/org/openforis/ceo/db/projects.clj
+++ src/clj/org/openforis/ceo/db/projects.clj
@@ -496,7 +496,7 @@
                                                         samples-per-plot
                                                         sample-resolution))
                              "Error adding plot file with generated samples."))
-        ;; The SQL function only checks against plots with external tables.
+          ;; The SQL function only checks against plots with external tables.
           (when (not allow-drawn-samples?)
             (let [bad-plots (map :plot_id (call-sql "plots_missing_samples" project-id))]
               (when (seq bad-plots)
@@ -518,7 +518,7 @@
                              "none"    1.0)
                            200.0
                            50000.0)
-      ;; TODO use bulk insert, or use postGIS to generate points.
+        ;; TODO use bulk insert, or use postGIS to generate points.
         (doseq [plot-center (if (= "gridded" plot-distribution)
                               (create-gridded-points-in-bounds left bottom right top plot-spacing)
                               (create-random-points-in-bounds left bottom right top num-plots))]
@@ -922,7 +922,7 @@
   [project-id]
   (->> (call-sql "get_plot_headers" project-id)
        (map :column_names)
-       (remove #(#{"GID", "GEOM", "PLOT_GEOM", "LAT", "LON"} (str/upper-case %)))
+       (remove #(#{"GID" "GEOM" "PLOT_GEOM" "LAT" "LON"} (str/upper-case %)))
        (mapv #(str "pl_" %))))

 (def plot-key-names {:lon        :center_lon
@@ -985,7 +985,7 @@
   [project-id]
   (->> (call-sql "get_sample_headers" project-id)
        (map :column_names)
-       (remove #(#{"GID", "GEOM", "LAT", "LON", "SAMPLE_GEOM"} (str/upper-case %)))
+       (remove #(#{"GID" "GEOM" "LAT" "LON" "SAMPLE_GEOM"} (str/upper-case %)))
        (map #(str "smpl_" %))))

 (defn- extract-answers [value sample-value-trans]


Cleanup

Cleanup

--- src/cljs/gtfve/components/controller.cljs
+++ src/cljs/gtfve/components/controller.cljs
@@ -44,7 +44,7 @@
           (async/untap controls-mult controls-tap))))
     om/IWillUnmount
     (will-unmount [_]
-      (let [{:keys [kill-ch controls-tap]} (om/get-state owner)]
+      (let [{:keys [kill-ch]} (om/get-state owner)]
         (when kill-ch (put! kill-ch (js/Date.)))))
     om/IRender
     (render [_]


Make stop search results a component

Make stop search results a component

--- src/cljs/gtfve/components/side_panel.cljs
+++ src/cljs/gtfve/components/side_panel.cljs
@@ -26,18 +26,45 @@
          (when active? "active")
          (when in? "in")]))

+(defn stop-search-results [data owner]
+  (reify
+    om/IDisplayName (display-name [_] "Stop Search Results")
+    om/IRender
+    (render [_]
+      (html
+       (let [{:keys [query]} (om/get-state owner)]
+         (cond
+           (empty? query) nil
+           (empty? data) [:div.alert.alert-danger
+                          [:p "No stops found matching "
+                           [:i query]]]
+           :else (into [:div.list-group]
+                       (map (fn [stop]
+                              [:a.list-group-item {:key (:db/id stop)
+                                                   :href "#"}
+                               [:h5.list-group-item-heading (:stop/name stop)]
+                               [:p.list-group-item-text (str (:stop/latitude stop)
+                                                             "/"
+                                                             (:stop/longitude stop))]])
+                            data))))))))
+
 (defn stop-panel [{:keys [panel data active? in?]} owner]
   (reify
     om/IDisplayName (display-name [_] "Stop Panel")
+    om/IInitState
+    (init-state [_]
+      {:current-query (:stops-query panel)})
     om/IRender
     (render [_]
       (let [tab (:tab panel)
-            query (:stops-query panel)]
+            query (:stops-query panel)
+            {:keys [current-query]} (om/get-state owner)]
         (html
          [:div {:className (tab-class active? in?)}
           [:div.tab-content-wrapper
            [:form.form-horizontal
             {:on-submit #(do
+                           (om/set-state! owner :current-query query)
                            (raise! owner [:stops-search-submitted {:query query}])
                            (.preventDefault %))}
             [:fieldset
@@ -49,15 +76,7 @@
                  :placeholder "Search"
                  :value query
                  :on-change #(utils/edit-input owner :input-stops-search %)}]]]]]
-           (into [:div.list-group]
-                 (map (fn [stop]
-                        [:a.list-group-item {:key (:db/id stop)
-                                             :href "#"}
-                         [:h5.list-group-item-heading (:stop/name stop)]
-                         [:p.list-group-item-text (str (:stop/latitude stop)
-                                                       "/"
-                                                       (:stop/longitude stop))]])
-                      data))
+           (om/build stop-search-results data {:state {:query current-query}})
            [:button.btn.btn-default.btn-block {:href "#"} "Load More"]]])))))

 (defn route-panel [{:keys [panel data active? in?]} owner]


adds keystore file hot-reload support (#1274)

--- waiter/project.clj
+++ waiter/project.clj
@@ -45,7 +45,7 @@
                  [io.grpc/grpc-core "1.20.0"
                   :exclusions [com.google.guava/guava]
                   :scope "test"]
-                 [twosigma/jet "0.7.10-20200801_013034-g6cffb81"
+                 [twosigma/jet "0.7.10-20210126_171807-gea4b804"
                   :exclusions [org.mortbay.jetty.alpn/alpn-boot]]
                  [twosigma/clj-http "1.0.2-20180124_201819-gcdf23e5"
                   :exclusions [commons-codec commons-io org.clojure/tools.reader potemkin slingshot]]


Add docstring for find-free-vars

Add docstring for find-free-vars

--- src/desdemona/query.clj
+++ src/desdemona/query.clj
@@ -88,5 +88,10 @@
               (comp nil? namespace)))

 (defn ^:private find-free-vars
+  "Finds all the free logic variables in a given logic query.
+
+  This takes advantage of the fact that function references for goal
+  functions/macros (conde, featurec...) will be fully qualified, but free
+  variables will be unadorned by a namespace."
   [logic-query]
   #{})


make the return to app link stay a link

make the return to app link stay a link

--- frontend/components/landing.cljs
+++ frontend/components/landing.cljs
@@ -180,7 +180,7 @@
                                         ; "What is Continuous Integration?"
          "Learn how we support Docker."]
         (if logged-in?
-          [:a.login {:href "/"} "Return to App"]
+          [:a.return {:href "/"} "Return to App"]
           [:a.login {:href (auth-url)
                      :on-click #(raise! owner [:track-external-link-clicked
                                                {:event "Auth GitHub"
@@ -190,7 +190,7 @@
         [:a.logo-circleci {:on-click #(raise! owner [:home-scroll-logo-clicked])}
          [:figure circle-logo]]
         (if logged-in?
-          [:a.action {:href "/"} "Return to App"]
+          [:a.return {:href "/"} "Return to App"]
           [:a.action {:href (auth-url)
                       :role "button"
                       :on-click #(raise! owner [:track-external-link-clicked


p011: moving tests form midje back to clj.test


Fix CLJS tests

Fix CLJS tests

--- test/expound/alpha_test.cljc
+++ test/expound/alpha_test.cljc
@@ -2162,44 +2162,44 @@
                                                               ::s/invalid))
                                               keyword?))
     (testing "coercion"
-      (is (= "-- Spec failed --------------------
+      (is (= (pf "-- Spec failed --------------------

   nil

 should satisfy

-  (clojure.spec.alpha/conformer
+  (pf.spec.alpha/conformer
    (fn
-    [%]
+    [%%]
     (if
-     (string? %)
-     (keyword %)
-     :clojure.spec.alpha/invalid)))
+     (string? %%)
+     (keyword %%)
+     :pf.spec.alpha/invalid)))

 -------------------------
 Detected 1 error
-"
+")
              (binding [s/*explain-out* (expound/custom-printer {:print-specs? false})]
                (s/explain-str :conformers-test/coerced-kw nil))))

-      (is (= "-- Spec failed --------------------
+      (is (= (pf "-- Spec failed --------------------

   [... ... ... 0]
                ^

 should satisfy

-  (clojure.spec.alpha/conformer
+  (pf.spec.alpha/conformer
    (fn
-    [%]
+    [%%]
     (if
-     (string? %)
-     (keyword %)
-     :clojure.spec.alpha/invalid)))
+     (string? %%)
+     (keyword %%)
+     :pf.spec.alpha/invalid)))

 -------------------------
 Detected 1 error
-"
+")
              (binding [s/*explain-out* (expound/custom-printer {:print-specs? false})]
                (s/explain-str (s/coll-of :conformers-test/coerced-kw) ["a" "b" "c" 0])))))
     ;; Also not recommended
@@ -2208,44 +2208,44 @@
                                                            ::s/invalid)
                                                         name) keyword?))
     (testing "coercion with unformer"
-      (is (= "-- Spec failed --------------------
+      (is (= (pf "-- Spec failed --------------------

   nil

 should satisfy

-  (clojure.spec.alpha/conformer
+  (pf.spec.alpha/conformer
    (fn
-    [%]
+    [%%]
     (if
-     (string? %)
-     (keyword %)
-     :clojure.spec.alpha/invalid)))
+     (string? %%)
+     (keyword %%)
+     :pf.spec.alpha/invalid)))

 -------------------------
 Detected 1 error
-"
+")
              (binding [s/*explain-out* (expound/custom-printer {:print-specs? false})]
                (s/explain-str :conformers-test/coerced-kw nil))))

-      (is (= "-- Spec failed --------------------
+      (is (= (pf "-- Spec failed --------------------

   [... ... ... 0]
                ^

 should satisfy

-  (clojure.spec.alpha/conformer
+  (pf.spec.alpha/conformer
    (fn
-    [%]
+    [%%]
     (if
-     (string? %)
-     (keyword %)
-     :clojure.spec.alpha/invalid)))
+     (string? %%)
+     (keyword %%)
+     :pf.spec.alpha/invalid)))

 -------------------------
 Detected 1 error
-"
+")
              (binding [s/*explain-out* (expound/custom-printer {:print-specs? false})]
                (s/explain-str (s/coll-of :conformers-test/coerced-kw) ["a" "b" "c" 0])))))

@@ -2272,7 +2272,7 @@
                (s/explain-str :conformers-test/person [:age 30 :name :Stan])))))

     (testing "ambiguous value"
-      (is (= "-- Spec failed --------------------
+      (is (= (pf "-- Spec failed --------------------

   {[0 1] ..., [1 0] ...}
               ^^^^^
@@ -2283,13 +2283,15 @@

 should satisfy

-  (fn
-   [%]
-   (< (-> % :x) (-> % :y)))
+  %s

 -------------------------
 Detected 1 error
 "
+                 #?(:cljs "(fn [%] (< (-> % :x) (-> % :y)))"
+                    :clj "(fn
+   [%]
+   (< (-> % :x) (-> % :y)))"))
              (binding [s/*explain-out* (expound/custom-printer {:print-specs? false})]
                (s/explain-str (s/map-of :conformers-test/sorted-pair any?) {[0 1] [1 0]
                                                                             [1 0] [1 0]})))))))


Fix incorrect user list path

Fix incorrect user list path

--- common/clojure/nightweb/constants.clj
+++ common/clojure/nightweb/constants.clj
@@ -29,13 +29,11 @@
 (def priv-key "private.key")
 (def pub-key "public.key")
 (def profile "user.profile")
-(def user-list "user.list")

 (def torrent-ext ".torrent")
 (def link-ext ".link")

-(def priv-key-file (str nw-dir slash priv-key))
-(def pub-key-file (str nw-dir slash pub-key))
+(def user-list-file (str nw-dir slash "user.list"))
 (def priv-node-key-file (str nw-dir slash "private.node.key"))
 (def pub-node-key-file (str nw-dir slash "public.node.key"))
 (def db-file (str nw-dir slash "main"))
@@ -43,7 +41,7 @@

 (defn get-user-list-file
   []
-  (str base-dir slash user-list))
+  (str base-dir user-list-file))

 (defn get-user-dir
   ([] (str base-dir user-dir))
@@ -57,7 +55,7 @@
   [user-hash]
   (if user-hash
     (str (get-user-dir user-hash) slash pub-key)
-    (str base-dir pub-key-file)))
+    (str base-dir nw-dir slash pub-key)))

 (defn get-meta-dir
   [user-hash]


Remove prepl cruft and update lein plugins

--- stow/lein-nubank/.lein/profiles.clj
+++ stow/lein-nubank/.lein/profiles.clj
@@ -15,33 +15,14 @@
                         [venantius/ultra "0.6.0"]
                         [lein-ancient "0.6.15"]
                         [lein-auto "0.1.3"]
-                        [com.jakemccrary/lein-test-refresh "0.24.1"]]
-
-  :repl-options {:prompt (constantly "user profile yeah=>")
-                 :init (do (println "Starting Propel...")
-                           (require 'propel.core)
-                           (let [prepl (propel.core/start-prepl! {:port-file? true})]
-                             (println "pREPL server started on port"
-                                      (:port prepl)
-                                      "on host"
-                                      (:address prepl))))}}
+                        [com.jakemccrary/lein-test-refresh "0.24.1"]]}

  :repl
- {:plugins      [[cider/cider-nrepl "0.21.1"]
+ {:plugins      [[cider/cider-nrepl "0.24.0"]
                  [refactor-nrepl "2.4.0"]
                  [lein-cljfmt "0.6.4"]]

   :dependencies [[org.clojure/tools.namespace "0.3.1"]
                  [nrepl "0.6.0"]
                  [olical/propel "1.3.0"]
-                 [mvxcvi/puget "1.1.1"]]}
-
- :propel
- {:repl-options {:prompt (constantly "CHIDDDDY=>")
-                 :init (do (println "Starting Propel...")
-                           (require 'propel.core)
-                           (let [prepl (propel.core/start-prepl! {:port-file? true})]
-                             (println "pREPL server started on port"
-                                      (:port prepl)
-                                      "on host"
-                                      (:address prepl))))}}}
+                 [mvxcvi/puget "1.1.1"]]}}


(PDB-4656) command: rm store report special case; don't wrap retries

Don't wrap command retries in a parent connection/transaction,
i.e. treat all commands like store report and get a new connection for
each retry.

--- src/puppetlabs/puppetdb/command.clj
+++ src/puppetlabs/puppetdb/command.clj
@@ -290,11 +290,13 @@
    (assoc command :payload (cat/parse-catalog payload version received))))

 (defn exec-replace-catalog
-  [{:keys [version id received payload]} start-time db]
+  [{:keys [version id received payload]} start-time db conn-status]
   (let [{producer-timestamp :producer_timestamp certname :certname :as catalog} payload]
-    (jdbc/with-transacted-connection' db :repeatable-read
-      (scf-storage/maybe-activate-node! certname producer-timestamp)
-      (scf-storage/replace-catalog! catalog received))
+    (jdbc/retry-with-monitored-connection
+     db conn-status :repeatable-read
+     (fn []
+       (scf-storage/maybe-activate-node! certname producer-timestamp)
+       (scf-storage/replace-catalog! catalog received)))
     (log-command-processed-messsage id received start-time :replace-catalog certname)))

 ;; Catalog input replacement
@@ -302,13 +304,15 @@
 (defn prep-replace-catalog-inputs [command]
   (update-in command [:payload :producer_timestamp] #(or % (now))))

-(defn exec-replace-catalog-inputs [{:keys [id received payload]} start-time db]
+(defn exec-replace-catalog-inputs [{:keys [id received payload]} start-time db conn-status]
   (let [{:keys [certname inputs catalog_uuid]
          stamp :producer_timestamp} payload]
     (when (seq inputs)
-      (jdbc/with-transacted-connection' db :repeatable-read
-        (scf-storage/maybe-activate-node! certname stamp)
-        (scf-storage/replace-catalog-inputs! certname catalog_uuid inputs stamp))
+      (jdbc/retry-with-monitored-connection
+       db conn-status :repeatable-read
+       (fn []
+         (scf-storage/maybe-activate-node! certname stamp)
+         (scf-storage/replace-catalog-inputs! certname catalog_uuid inputs stamp)))
       (log-command-processed-messsage id received start-time
                                       :replace-catalog-inputs certname))))

@@ -335,11 +339,13 @@
                 (seq package_inventory) (update :package_inventory distinct))))))

 (defn exec-replace-facts
-  [{:keys [payload id received] :as command} start-time db]
+  [{:keys [payload id received] :as command} start-time db conn-status]
   (let [{:keys [certname producer_timestamp]} payload]
-    (jdbc/with-transacted-connection' db :repeatable-read
-      (scf-storage/maybe-activate-node! certname producer_timestamp)
-      (scf-storage/replace-facts! payload))
+    (jdbc/retry-with-monitored-connection
+     db conn-status :repeatable-read
+     (fn []
+       (scf-storage/maybe-activate-node! certname producer_timestamp)
+       (scf-storage/replace-facts! payload)))
     (log-command-processed-messsage id received start-time :replace-facts certname)))

 ;; Node deactivation
@@ -364,12 +370,14 @@

 ;; FIXME: was to-timestamp redundant here and in store-report? others don't have it...

-(defn exec-deactivate-node [{:keys [id received payload]} start-time db]
+(defn exec-deactivate-node [{:keys [id received payload]} start-time db conn-status]
   (let [{:keys [certname producer_timestamp]} payload]
-    (jdbc/with-transacted-connection db
-      (when-not (scf-storage/certname-exists? certname)
-        (scf-storage/add-certname! certname))
-      (scf-storage/deactivate-node! certname producer_timestamp))
+    (jdbc/retry-with-monitored-connection
+     db conn-status :read-committed
+     (fn []
+       (when-not (scf-storage/certname-exists? certname)
+         (scf-storage/add-certname! certname))
+       (scf-storage/deactivate-node! certname producer_timestamp)))
     (log-command-processed-messsage id received start-time :deactivate-node certname)))

 ;; Report submission
@@ -403,13 +411,15 @@
        (update :payload #(s/validate nodes/configure-expiration-wireformat-schema %))
        (update-in [:payload :producer_timestamp] #(or % (now))))))

-(defn exec-configure-expiration [{:keys [id received payload]} start-time db]
+(defn exec-configure-expiration [{:keys [id received payload]} start-time db conn-status]
   (let [{:keys [certname producer_timestamp]} payload
         expire-facts? (get-in payload [:expire :facts])]
     (when-not (nil? expire-facts?)
-      (jdbc/with-transacted-connection db
-        (scf-storage/maybe-activate-node! certname producer_timestamp)
-        (scf-storage/set-certname-facts-expiration certname expire-facts? producer_timestamp))
+      (jdbc/retry-with-monitored-connection
+       db conn-status :read-committed
+       (fn []
+         (scf-storage/maybe-activate-node! certname producer_timestamp)
+         (scf-storage/set-certname-facts-expiration certname expire-facts? producer_timestamp)))
       (log-command-processed-messsage id received start-time
                                       :configure-expiration certname))))

@@ -424,29 +434,24 @@
     "configure expiration" (prep-configure-expiration cmd)
     "replace catalog inputs" (prep-replace-catalog-inputs cmd)))

-(def supported-command?
-  (comp (kitchensink/valset command-names) :command))
-
-(defn supported-version? [command version]
-  (contains? (get supported-command-versions command #{}) version))
-
-(defn supported-command-version? [command-name [received-command-name received-version]]
-  (boolean
-   (and (= command-name received-command-name)
-        (supported-version? command-name received-version))))
+(defn supported-command? [{:keys [command version] :as cmd}]
+  (some-> (supported-command-versions command) (get version)))

 (defn exec-command
   "Takes a command object and processes it to completion. Dispatch is
    based on the command's name and version information"
-  [{command-name :command version :version delete? :delete? :as command}
-   db conn-status start]
-  (condp supported-command-version? [command-name version]
-    "replace catalog" (exec-replace-catalog command start db)
-    "replace facts" (exec-replace-facts command start db)
-    "store report" (exec-store-report command start db conn-status)
-    "deactivate node" (exec-deactivate-node command start db)
-    "configure expiration" (exec-configure-expiration command start db)
-    "replace catalog inputs" (exec-replace-catalog-inputs command start db)))
+  [{:keys [command version] :as cmd} db conn-status start]
+  (when-not (supported-command? cmd)
+    (throw (ex-info (trs "Unsupported command {0} version {1}" command version)
+                    {:kind ::fatal-processing-error})))
+  (let [exec (case command
+               "replace catalog" exec-replace-catalog
+               "replace facts" exec-replace-facts
+               "store report" exec-store-report
+               "deactivate node" exec-deactivate-node
+               "configure expiration" exec-configure-expiration
+               "replace catalog inputs" exec-replace-catalog-inputs)]
+    (exec cmd start db conn-status)))

 (defn process-command!
   ;; only used by testing...
@@ -569,13 +574,7 @@
         not-exception? #(not (instance? Throwable %))
         attempt-exec (fn [db status]
                        (try
-                         ;; FIXME: huge hack...
-                         (if (= command "store report")
-                           (attempt-exec-command cmd db status
-                                                 response-chan stats)
-                           (jdbc/with-monitored-db-connection db status
-                             (attempt-exec-command cmd jdbc/*db* status
-                                                   response-chan stats)))
+                         (attempt-exec-command cmd db status response-chan stats)
                          nil
                          (catch Throwable ex
                            ex)))]


(PDB-3993) command-service: return correct context from stop method

--- src/puppetlabs/puppetdb/command.clj
+++ src/puppetlabs/puppetdb/command.clj
@@ -660,8 +660,8 @@
     (async/untap-all (:response-mult context))
     (async/close! (:response-chan-for-pub context))
     (async/close! (:response-chan context))
-    (dissoc context :response-pub :response-chan :response-chan-for-pub :response-mult)
-    context)
+    (dissoc context
+            :response-pub :response-chan :response-chan-for-pub :response-mult))

   (stats [this]
     @(:stats (service-context this)))


Add tests for all hashes.

Add tests for all hashes.

--- test/buddy/core/hash_tests.clj
+++ test/buddy/core/hash_tests.clj
@@ -14,6 +14,7 @@

 (ns buddy.core.hash-tests
   (:require [clojure.test :refer :all]
+            [clojure.string :as str]
             [buddy.core.codecs :as codecs :refer :all]
             [buddy.core.bytes :as bytes]
             [buddy.core.keys :refer :all]
@@ -21,12 +22,64 @@
             [clojure.java.io :as io]))

 (deftest buddy-core-hash
-  (testing "SHA3 support test"
-    (let [plain-text "FooBar"
-          hashed     (-> (hash/sha3-256 plain-text)
-                         (bytes->hex))]
-      (is (= hashed "3007b60101d12b393d3f78d92aa573809b769b7ba05806657c3028bd11e7265f"))))
+  (testing "SHA3 256"
+    (let [hashed (hash/sha3-256 "")]
+      (is (= (bytes->hex hashed)
+             (str "a7ffc6f8bf1ed76651c14756a061d662"
+                  "f580ff4de43b49fa82d80a4b80f8434a")))))
+
+  (testing "SHA3 384"
+    (let [hashed (hash/sha3-384 "")]
+      (is (= (bytes->hex hashed)
+             (str "0c63a75b845e4f7d01107d852e4c2485"
+                  "c51a50aaaa94fc61995e71bbee983a2a"
+                  "c3713831264adb47fb6bd1e058d5f004")))))
+
+  (testing "SHA3 512"
+    (let [hashed (hash/sha3-512 "")]
+      (is (= (bytes->hex hashed)
+             (str "a69f73cca23a9ac5c8b567dc185a756e"
+                  "97c982164fe25859e0d1dcc1475c80a6"
+                  "15b2123af1f5f94c11e3e9402c3ac558"
+                  "f500199d95b6d3e301758586281dcd26")))))
+
+  (testing "SHA2 256"
+    (let [hashed (hash/sha256 "")]
+      (is (= (bytes->hex hashed)
+             (str "e3b0c44298fc1c149afbf4c8996fb924"
+                  "27ae41e4649b934ca495991b7852b855")))))
+
+  (testing "SHA2 384"
+    (let [hashed (hash/sha384 "")]
+      (is (= (bytes->hex hashed)
+             (str "38b060a751ac96384cd9327eb1b1e36a"
+                  "21fdb71114be07434c0cc7bf63f6e1da"
+                  "274edebfe76f65fbd51ad2f14898b95b")))))
+
+  (testing "SHA2 512"
+    (let [hashed (hash/sha512 "")]
+      (is (= (bytes->hex hashed)
+             (str "cf83e1357eefb8bdf1542850d66d8007"
+                  "d620e4050b5715dc83f4a921d36ce9ce"
+                  "47d0d13c5d85f2b0ff8318d2877eec2f"
+                  "63b931bd47417a81a538327af927da3e")))))
+
+  (testing "blake2 512"
+    (let [hashed (hash/blake2b-512 "")]
+      (is (= (str/upper-case (bytes->hex hashed))
+             (str "786A02F742015903C6C6FD852552D272"
+                  "912F4740E15847618A86E217F71F5419"
+                  "D25E1031AFEE585313896444934EB04B"
+                  "903A685B1448B755D56F701AFE9BE2CE")))))
+
+  (testing "sha1"
+    (let [hashed (hash/sha1 "")]
+      (is (= (bytes->hex hashed)
+             "da39a3ee5e6b4b0d3255bfef95601890afd80709"))))
+
   (testing "File hashing"
-    (let [path       "test/_files/pubkey.ecdsa.pem"
-          valid-hash "7aa01e35e65701c9a9d8f71c4cbf056acddc9be17fdff06b4c7af1b0b34ddc29"]
-      (is (= (bytes->hex (hash/sha256 (io/input-stream path))) valid-hash)))))
+    (let [path "test/_files/pubkey.ecdsa.pem"
+          stream (io/input-stream path)]
+      (is (= (bytes->hex (hash/sha256 stream))
+             (str "7aa01e35e65701c9a9d8f71c4cbf056a"
+                  "cddc9be17fdff06b4c7af1b0b34ddc29"))))))


check dates

check dates

--- test/clojento/magento/t_db.clj
+++ test/clojento/magento/t_db.clj
@@ -239,8 +239,8 @@
                                                           :type          "simple"
                                                           :sku           "sku-1"
                                                           :attribute-set 4
-                                                          :date-created  anything
-                                                          :date-updated  anything
+                                                          :date-created  (t/date-time 2011 11 21 22 02 58)
+                                                          :date-updated  (t/date-time 2013 11 14 18 17 49)
                                                           ; :websites      (just ["website_1" "website_2"] :in-any-order)
                                                           }]))
       (fact "has meta"


Use 4 threads and set queue size to 300 000 in clojure-http-kit implementation

--- clojure-http-kit/src/sse_server/core.clj
+++ clojure-http-kit/src/sse_server/core.clj
@@ -52,6 +52,6 @@
 (defn -main
   [& args]
   (let [port (parse-port args)]
-    (run-server app {:port port})
+    (run-server app {:port port :thread 4 :queue-size 300000})
     (start-timer)
     (print (str "Listening on http://127.0.0.1:" port))))


Adjust params test of sequentialness.

Adjust params test of sequentialness.

--- test/onyx/peer/params_test.clj
+++ test/onyx/peer/params_test.clj
@@ -66,7 +66,7 @@
     :onyx/ident :hornetq/read-segments
     :onyx/type :input
     :onyx/medium :hornetq
-    :onyx/consumption :concurrent
+    :onyx/consumption :sequential
     :hornetq/queue-name in-queue
     :hornetq/host hornetq-host
     :hornetq/port hornetq-port
@@ -75,14 +75,14 @@
    {:onyx/name :add
     :onyx/fn :onyx.peer.params-test/my-adder
     :onyx/type :transformer
-    :onyx/consumption :concurrent
+    :onyx/consumption :sequential
     :onyx/batch-size batch-size}

    {:onyx/name :out
     :onyx/ident :hornetq/write-segments
     :onyx/type :output
     :onyx/medium :hornetq
-    :onyx/consumption :concurrent
+    :onyx/consumption :sequential
     :hornetq/queue-name out-queue
     :hornetq/host hornetq-host
     :hornetq/port hornetq-port


added combine doc

added combine doc

--- src/datasplash/core.clj
+++ src/datasplash/core.clj
@@ -1294,9 +1294,18 @@
    base-schema
    base-combine-schema
    {:as-singleton-view {:docstr "The transform returns a PCollectionView whose elements are the result of combining elements per-window in the input PCollection."
-                        :action (fn [transform b] (when b (.asSingletonView transform)))}}))
+                        :action (fn [transform b] (when b (.asSingletonView transform)))}
+    :scope {:docstr "Specifies the combiner scope of application"
+            :enum [:global :per-key]
+            :default :global}}))

 (defn combine
+  {:doc (with-opts-docstr
+          "Applies a CombineFn or a Clojure function with equivalent arities to the PCollection.
+
+See https://cloud.google.com/dataflow/java-sdk/JavaDoc/com/google/cloud/dataflow/sdk/transforms/Combine"
+          combine-schema)
+   :added "0.1.0"}
   ([f {:keys [coder key-coder value-coder] :as options} ^PCollection pcoll]
    (let [scope (or (:scope options) :global)
          opts (assoc options


Fixed web ref bug

Fixed web ref bug

--- src/demogorgon/core.clj
+++ src/demogorgon/core.clj
@@ -27,7 +27,7 @@
      (irc-hooks/add-message-hook *connection* #"\.lasturl ?(.*)?" #'last-dump-hook)
      (irc/connect *connection*)
      (dosync
-      (alter *web* (start-web))))
+      (ref-set *web* (start-web))))
    (catch Exception e
      (pst e))))


Code golf

Code golf

--- src/desdemona/query.clj
+++ src/desdemona/query.clj
@@ -69,17 +69,13 @@
   (m/match [dsl-query]
     [(('= & terms) :seq)]
     (let [{literals true attr-terms false} (group-by dsl-literal? terms)
-          featurec-term (fn [value [attr lvar]]
-                          (let [lvar (free-sym lvar)]
-                            `(l/featurec ~lvar {~attr ~value})))
-          literal-featurec-term (partial featurec-term (first literals))]
+          feature (fn [value [attr lvar]]
+                    `(l/featurec ~(free-sym lvar) {~attr ~value}))]
       (m/match [(count literals) (count attr-terms)]
-        [1 1] (literal-featurec-term (first attr-terms))
-        [1 _] (let [logic-terms (map literal-featurec-term attr-terms)]
-                `(l/all ~@logic-terms))
-        [0 _] (let [u (gensym)
-                    logic-terms (map (partial featurec-term u) attr-terms)]
-                `(l/fresh [~u] ~@logic-terms))))
+        [1 1] (feature (first literals) (first attr-terms))
+        [1 _] `(l/all ~@(map (partial feature (first literals)) attr-terms))
+        [0 _] (let [u (gensym)]
+                `(l/fresh [~u] ~@(map (partial feature u) attr-terms)))))

     [(('and & terms) :seq)]
     (let [logic-terms (map dsl->logic terms)]


Improve project.clj

Improve project.clj


fix manifest generation

fix manifest generation

--- src/main/shadow/build/targets/browser.clj
+++ src/main/shadow/build/targets/browser.clj
@@ -266,9 +266,11 @@
   (spit
     (data/output-file state "manifest.json")
     (let [data
-          (->> (:build-modules state)
-               (map (fn [{:keys [name output-name entries depends-on sources foreign-files] :as mod}]
-                      {:name name
+          (->> (or (::closure/modules state)
+                   (:build-modules state))
+               (map (fn [{:keys [module-id output-name entries depends-on sources foreign-files] :as mod}]
+                      {:module-id module-id
+                       :name module-id
                        :output-name output-name
                        ;; FIXME: this is old, should always use :output-name
                        :js-name output-name
@@ -278,12 +280,6 @@
                        (->> sources
                             (map #(get-in state [:sources %]))
                             (map :resource-name)
-                            (into []))
-                       :js-modules
-                       (->> sources
-                            (map #(get-in state [:sources %]))
-                            (map :js-module)
-                            (remove nil?)
                             (into []))}
                       )))]
       (with-out-str


provider validations

provider validations

--- src/gce/validations.clj
+++ src/gce/validations.clj
@@ -15,7 +15,7 @@
     [celestial.model :refer (check-validity)]
     [celestial.provider :refer (mappings)]
     [clojure.core.strint :refer (<<)]
-    [subs.core :refer (validate! combine validation when-not-nil every-v)]
+    [subs.core :refer (validate! combine validation when-not-nil every-v every-kv)]
     ))

 (def machine-entity
@@ -34,6 +34,18 @@
 (defmethod check-validity [:gce :entity] [spec]
   (validate! spec (combine machine-entity gce-entity) :error ::invalid-system))

-(defn validate-provider [spec]
-  )
+(validation :params {:sourceImage #{:required :String}})

+(validation :disk {:initializeParams #{:required :Map}})
+
+(validation :disk* (every-v #{:disk}))
+
+(def gce-provider {
+   :name #{:required :String}
+   :machineType #{:required :String}
+   :disks #{:required :disk*}
+   })
+
+(defn validate-provider [gce spec]
+   (validate! gce gce-provider :error ::invalid-gce-instance))
+