Implemented step 3

Implemented step 3

--- src/cljs/reagent_phonecat/core.cljs
+++ src/cljs/reagent_phonecat/core.cljs
@@ -1,23 +1,42 @@
 (ns reagent-phonecat.core
     (:require [reagent.core :as rc :refer [atom]]
+              [clojure.string :as str]
               )
     )

 ;; -------------------------
+;; Logic
+
+(defn matches-query? "Emulates Angular's 'filter:query' filter.
+Checks that any string value of the 'data' map matches the 'query' string."
+  [query data]
+  (let [qp (-> query str/lower-case re-pattern)]
+    (->> (vals data)
+         (filter string?) (map str/lower-case)
+         (some #(re-find qp %))
+         )))
+
+;; -------------------------
 ;; State

-(def phones "The list of phones. It is an atom so that you can modify it live."
-  (rc/atom
-   [{:name "Nexus S"
-     :snippet "Fast just got faster with Nexus S."}
-    {:name "Motorola XOOM™ with Wi-Fi"
-     :snippet "The Next, Next Generation tablet."}
-    {:name "MOTOROLA XOOM™"
-     :snippet "The Next, Next Generation tablet."}]
-   ))
+(def state
+  (rc/atom
+   {:phones [{:name "Nexus S"
+              :snippet "Fast just got faster with Nexus S."}
+             {:name "Motorola XOOM™ with Wi-Fi"
+              :snippet "The Next, Next Generation tablet."}
+             {:name "MOTOROLA XOOM™"
+              :snippet "The Next, Next Generation tablet."}]
+    :query ""
+    }))

 ;; -------------------------
 ;; Views
+
+(defn query-input []
+  [:input {:type text
+           :value (:query @state)
+           :on-change #(swap! state assoc :query (-> % .-target .-value))}])

 (defn phone-component "component showing details about one phone"
   [{:keys [name snippet] :as phone}]
@@ -26,46 +45,26 @@
    [:p snippet]]
   )

-(defn phones-list "Component displaying the list of phones" []
+(defn phones-list "Component displaying the list of phones" [query phones]
   [:ul
-   (for [phone @phones]
+   (for [phone (filter (partial matches-query? query) phones)]
      [phone-component phone])])

-;; experiments
-(def name (rc/atom "World"))
-(defn hello-cpnt []
-  [:p (str "Hello, " @name "!")])

-(defn simple-table []
-  [:table
-   [:tr [:th "row number"]]
-   (for [i (range 8)]
-     [:tr [:td (inc i)]])
+(defn top-cpnt []
+  [:div.container-fluid
+   [:div.row
+    [:div.col-md-2
+     ;; sidebar content
+     "Search : " [query-input]
+     ]
+    [:div.col-md-10
+     ;; body content
+     [phones-list (:query @state) (:phones @state)]
+     ]]
    ])
-
-(defn less-simple-table []
-  [:table
-   (for [i (range 8)]
-     [:tr (for [j (range 8)]
-            [:td (inc i) (inc j)])])
-   ])
-
 ;; -------------------------
 ;; Initialize app
-(defn top-cpnt []
-  [:div
-   [phones-list]
-
-   [:h2 "Experiments"]
-   [:h4 "Hello World"]
-   [hello-cpnt]
-
-   [:h4 "Simple table"]
-   [simple-table]
-
-   [:h4 "Less simple table"]
-   [less-simple-table]
-   ])

 (defn init! []
   (rc/render-component [top-cpnt] (.getElementById js/document "app")))
@@ -73,7 +72,4 @@

 ;; -------------------------
 ;; Playground
-(comment
-  ;; live coding: change the list of phones by eval-ing this form. Notice the change is immediately reflected in the browser, without reloading the page.
-  (swap! phones #(drop 1 %))
-  )
+


Cleanup generators docstrings

Cleanup generators docstrings

--- src/main/clojure/clojure/test/check/generators.cljc
+++ src/main/clojure/clojure/test/check/generators.cljc
@@ -74,6 +74,7 @@

   Given a random number generator, returns an infinite lazy sequence
   of random number generators."
+  {:no-doc true}
   [rr]
   (lazy-seq
    (core/let [[r1 r2] (random/split rr)]
@@ -103,7 +104,7 @@
   (gen-fmap #(rose/fmap f %) gen))

 (defn return
-  "Create a generator that always returns `value`,
+  "Creates a generator that always returns `value`,
   and never shrinks. You can think of this as
   the `constantly` of generators. E.g.:

@@ -122,7 +123,7 @@
                             rose))))))

 (defn bind
-  "Create a new generator that passes the result of `gen` into function
+  "Creates a new generator that passes the result of `gen` into function
   `f`. `f` should return a new generator. This allows you to create new
   generators that depend on the value of other generators. For example,
   to create a generator of permutations which first generates a
@@ -150,7 +151,10 @@
   (cycle (range 0 max-size)))

 (defn sample-seq
-  "Return a sequence of realized values from `generator`."
+  "Returns an infinite sequence of realized values from `generator`.
+
+  Note that this function is a dev helper and is not meant to be used
+  to build other generators."
   ([generator] (sample-seq generator 200))
   ([generator max-size]
    (core/let [r (random/make-random)
@@ -245,11 +249,25 @@
   (calc-long (random/rand-double rnd) lower upper))

 (defn sized
-  "Create a generator that depends on the size parameter.
+  "Creates a generator that depends on the size parameter.
   `sized-gen` is a function that takes an integer and returns
   a generator.

-      TODO: example"
+  Examples:
+
+      ;; generates vectors of booleans where the length always exactly
+      ;; matches the `size` parameter
+      (gen/sample (gen/sized (fn [size] (gen/vector gen/boolean size))))
+      => ([]
+          [false]
+          [true true]
+          [false true false]
+          [false true true true]
+          [false false true true false]
+          [false true false true true false]
+          [true false true true true false false]
+          [true true false false false true false false]
+          [false false false true true false true false true])"
   [sized-gen]
   (make-gen
    (fn [rnd size]
@@ -260,7 +278,7 @@
 ;; ---------------------------------------------------------------------------

 (defn resize
-  "Create a new generator with `size` always bound to `n`.
+  "Creates a new generator with `size` always bound to `n`.

       (gen/sample (gen/set (gen/resize 200 gen/double)))
       => (#{}
@@ -282,7 +300,7 @@
        (gen rnd n)))))

 (defn scale
-  "Create a new generator that modifies the size parameter by the
+  "Creates a new generator that modifies the size parameter by the
   given function. Intended to support generators with sizes that need
   to grow at different rates compared to the normal linear scaling.

@@ -297,15 +315,15 @@

 (defn choose
   #?(:clj
-     "Create a generator that returns long integers in the range
+     "Creates a generator that generates integers uniformly in the range
      `lower` to `upper`, inclusive.

          (gen/sample (gen/choose 200 800))
          => (331 241 593 339 643 718 688 473 247 694)"

      :cljs
-     "Create a generator that returns integer numbers in the range
-     `lower` to `upper`, inclusive.
+     "Creates a generator that generates integer numbers uniformly in
+     the range `lower` to `upper`, inclusive.

          (gen/sample (gen/choose 200 800))
          => (331 241 593 339 643 718 688 473 247 694)")
@@ -325,7 +343,7 @@
           (int-rose-tree value)))))))

 (defn one-of
-  "Create a generator that randomly chooses a value from the list of
+  "Creates a generator that randomly chooses a value from the list of
   provided generators. Shrinks toward choosing an earlier generator,
   as well as shrinking the value generated by the chosen generator.

@@ -349,7 +367,7 @@
        (count)))

 (defn frequency
-  "Create a generator that chooses a generator from `pairs` based on the
+  "Creates a generator that chooses a generator from `pairs` based on the
   provided likelihoods. The likelihood of a given generator being chosen is
   its likelihood divided by the sum of all likelihoods. Shrinks toward
   choosing an earlier generator, as well as shrinking the value generated
@@ -388,7 +406,7 @@
         rnd size)))))

 (defn elements
-  "Create a generator that randomly chooses an element from `coll`.
+  "Creates a generator that randomly chooses an element from `coll`.

       (gen/sample (gen/elements [:foo :bar :baz]))
       => (:foo :baz :baz :bar :foo :foo :bar :bar :foo :bar)"
@@ -420,7 +438,7 @@
    :max-tries 10})

 (defn such-that
-  "Create a generator that generates values from `gen` that satisfy predicate
+  "Creates a generator that generates values from `gen` that satisfy predicate
   `pred`. Care is needed to ensure there is a high chance `gen` will satisfy
   `pred`. By default, `such-that` will try 10 times to generate a value that
   satisfies the predicate. If no value passes this predicate after this number
@@ -481,7 +499,7 @@
   (such-that core/not-empty gen))

 (defn no-shrink
-  "Create a new generator that is just like `gen`, except does not shrink
+  "Creates a new generator that is just like `gen`, except does not shrink
   at all. This can be useful when shrinking is taking a long time or is not
   applicable to the domain."
   [gen]
@@ -491,7 +509,7 @@
             gen))

 (defn shrink-2
-  "Create a new generator like `gen`, but will consider nodes for shrinking
+  "Creates a new generator like `gen`, but will consider nodes for shrinking
   even if their parent passes the test (up to one additional level)."
   [gen]
   (assert (generator? gen) "Arg to shrink-2 must be a generator")
@@ -502,9 +520,9 @@
   (elements [false true]))

 (defn tuple
-  "Create a generator that returns a vector, whose elements are chosen
+  "Creates a generator that returns a vector, whose elements are chosen
   from the generators in the same position. The individual elements shrink
-  according to their generator, but the value will never shrink in count.
+  according to their generator, but the vector will never shrink in count.

   Examples:

@@ -530,23 +548,23 @@
   (fmap #(Math/abs (long %)) int))

 (def pos-int
-  "Generate positive integers bounded by the generator's `size` parameter."
+  "Generates positive integers bounded by the generator's `size` parameter."
   nat)

 (def neg-int
-  "Generate negative integers bounded by the generator's `size` parameter."
+  "Generates negative integers bounded by the generator's `size` parameter."
   (fmap #(* -1 %) nat))

 (def s-pos-int
-  "Generate strictly positive integers bounded by the generator's `size` + 1"
+  "Generates strictly positive integers bounded by the generator's `size` + 1"
   (fmap inc nat))

 (def s-neg-int
-  "Generate strictly negative integers bounded by the generator's `size` + 1"
+  "Generates strictly negative integers bounded by the generator's `size` + 1"
   (fmap dec neg-int))

 (defn vector
-  "Create a generator of vectors whose elements are chosen from
+  "Creates a generator of vectors whose elements are chosen from
   `generator`. The count of the vector will be bounded by the `size`
   generator parameter."
   ([generator]
@@ -595,7 +613,7 @@
 (defn
   ^{:added "0.6.0"}
   shuffle
-  "Create a generator that generates random permutations of
+  "Creates a generator that generates random permutations of
   `coll`. Shrinks toward the original collection: `coll`. `coll` will
   be coerced to a vector."
   [coll]
@@ -920,7 +938,7 @@
    (coll-distinct-by (core/sorted-set) identity false false gen opts)))

 (defn map
-  "Create a generator that generates maps, with keys chosen from
+  "Creates a generator that generates maps, with keys chosen from
   `key-gen` and values chosen from `val-gen`.

   If the key generator cannot or is unlikely to produce enough distinct
@@ -1264,11 +1282,11 @@
   (fmap core/char (choose 0 255)))

 (def char-ascii
-  "Generate only ascii character."
+  "Generates only ascii characters."
   (fmap core/char (choose 32 126)))

 (def char-alphanumeric
-  "Generate alphanumeric characters."
+  "Generates alphanumeric characters."
   (fmap core/char
         (one-of [(choose 48 57)
                  (choose 65 90)
@@ -1278,47 +1296,47 @@
   char-alpha-numeric
   "Deprecated - use char-alphanumeric instead.

-  Generate alphanumeric characters."
+  Generates alphanumeric characters."
   char-alphanumeric)

 (def char-alpha
-  "Generate alpha characters."
+  "Generates alpha characters."
   (fmap core/char
         (one-of [(choose 65 90)
                  (choose 97 122)])))

 (def ^:private char-symbol-special
-  "Generate non-alphanumeric characters that can be in a symbol."
+  "Generates non-alphanumeric characters that can be in a symbol."
   (elements [\* \+ \! \- \_ \? \.]))

 (def ^:private char-symbol-noninitial
-  "Generate characters that can be the char following first of a keyword or symbol."
+  "Generates characters that can be the char following first of a keyword or symbol."
   (frequency [[14 char-alphanumeric]
               [7 char-symbol-special]
               [1 (return \:)]]))

 (def ^:private char-symbol-initial
-  "Generate characters that can be the first char of a keyword or symbol."
+  "Generates characters that can be the first char of a keyword or symbol."
   (frequency [[2 char-alpha]
               [1 char-symbol-special]]))

 (def string
-  "Generate strings. May generate unprintable characters."
+  "Generates strings. May generate unprintable characters."
   (fmap clojure.string/join (vector char)))

 (def string-ascii
-  "Generate ascii strings."
+  "Generates ascii strings."
   (fmap clojure.string/join (vector char-ascii)))

 (def string-alphanumeric
-  "Generate alphanumeric strings."
+  "Generates alphanumeric strings."
   (fmap clojure.string/join (vector char-alphanumeric)))

 (def ^{:deprecated "0.6.0"}
   string-alpha-numeric
   "Deprecated - use string-alphanumeric instead.

-  Generate alphanumeric strings."
+  Generates alphanumeric strings."
   string-alphanumeric)

 (defn- digit?
@@ -1355,7 +1373,7 @@
   (scale #(long (Math/pow % 0.60)) g))

 (def keyword
-  "Generate keywords without namespaces."
+  "Generates keywords without namespaces."
   (frequency [[100
                (->> symbol-name-or-namespace
                     (fmap core/keyword)
@@ -1365,13 +1383,13 @@
 (def
   ^{:added "0.5.9"}
   keyword-ns
-  "Generate keywords with namespaces."
+  "Generates keywords with namespaces."
   (->> (tuple symbol-name-or-namespace symbol-name-or-namespace)
        (fmap (fn [[ns name]] (core/keyword ns name)))
        (resize-symbolish-generator)))

 (def symbol
-  "Generate symbols without namespaces."
+  "Generates symbols without namespaces."
   (frequency [[100
                (->> symbol-name-or-namespace
                     (fmap core/symbol)
@@ -1381,7 +1399,7 @@
 (def
   ^{:added "0.5.9"}
   symbol-ns
-  "Generate symbols with namespaces."
+  "Generates symbols with namespaces."
   (->> (tuple symbol-name-or-namespace symbol-name-or-namespace)
        (fmap (fn [[ns name]] (core/symbol ns name)))
        (resize-symbolish-generator)))
@@ -1430,10 +1448,12 @@
             (vector (choose 0 15) 31)))))

 (def simple-type
+  "Generates a variety of scalar types."
   (one-of [int large-integer double char string ratio boolean keyword
            keyword-ns symbol symbol-ns uuid]))

 (def simple-type-printable
+  "Generates a variety of scalar types, with printable strings."
   (one-of [int large-integer double char-ascii string-ascii ratio boolean
            keyword keyword-ns symbol symbol-ns uuid]))


Rewrite of if refactoring to use rewrite-cljs

--- src/lt/plugins/cljrefactor/form_refactor.cljs
+++ src/lt/plugins/cljrefactor/form_refactor.cljs
@@ -1,41 +1,76 @@
 (ns lt.plugins.cljrefactor.form-refactor
   (:require [lt.plugins.cljrefactor.parser :as p]
             [lt.plugins.cljrefactor.util :as u]
+            [rewrite-clj.zip :as z]
+            [rewrite-clj.zip.whitespace :as ws]
+            [rewrite-clj.node :as nd]
+            [rewrite-clj.zip.utils :as zu]
+            [clojure.zip :as zz]
             [lt.object :as object]
             [lt.objs.editor.pool :as pool]
             [lt.objs.editor :as editor]
             [lt.objs.command :as cmd]
-            [lt.plugins.paredit :as pe]
-            [lt.plugins.clojure :as cp]
-            [clojure.zip :as z]
             [clojure.string :as s])
   (:require-macros [lt.macros :refer [behavior]]))

-(defn top [zipnode]
-  (loop [n zipnode]
-    (if-not (z/up n)
-      n
-      (recur (z/up n)))))

-(defn if-node? [loc]
-  (when (and (seq loc) (list? (z/node loc)))
-    (-> loc z/down z/node  ((fn [s] (some #{s} ['if 'if-not]))))))
+(defn-  nodes-by-dir
+  ([zloc f] (nodes-by-dir zloc f constantly))
+  ([zloc f p?]
+   (->> zloc
+        (iterate f)
+        (take-while identity)
+        (take-while p?)
+        (map z/node))))

-(defn swap-if-nodes [loc]
-  (let [move (-> loc z/down z/right z/right z/node)]
-    (-> loc z/down z/right z/right z/remove top (z/append-child move))))
+(defn- an-if? [zloc]
+  (some #{"if" "if-not"} [(z/string zloc)]))

-(defn cycle-if [form-str]
-  (let [root (p/str->seq-zip form-str)
-        if-node (if-node? root)]
-    (when if-node
-      (-> root
-          swap-if-nodes
-          z/down
-          (z/replace (if (= if-node 'if) 'if-not 'if))
-          p/zip->str))))
+
+(defn- find-if [zloc]
+  (when zloc
+     (if-let [an-if (-> zloc z/leftmost an-if?)]
+       [an-if (z/leftmost zloc)]
+       (recur (z/up zloc)))))
+
+
+(defn- right-lb-or-nl [zloc]
+  (->> (-> zloc
+           zz/right
+           (nodes-by-dir zz/right ws/whitespace-or-comment?))
+       (filter #(or (nd/linebreak? %) (nd/comment? %)))))
+
+(defn shift-left [zloc]
+  (let [preserves-right (right-lb-or-nl zloc)
+        maybe-trim-ws (fn [l]
+                        (if (and (z/rightmost? l)
+                                 (not (->> l right-lb-or-nl (filter nd/comment?) seq)))
+                          (zu/remove-right-while l ws/whitespace?)
+                          l))
+        maybe-add-lb (fn [l]
+                       (if (and (not (seq preserves-right))
+                                (-> zloc z/left right-lb-or-nl seq))
+                         (z/insert-left l (nd/newlines 1))
+                         l))]
+    (-> zloc
+        (zu/remove-right-while ws/whitespace-or-comment?)
+        zu/remove-and-move-left
+        z/left
+        maybe-trim-ws
+        (z/insert-left (z/node zloc))
+        ((partial reduce z/insert-left) preserves-right)
+        maybe-add-lb)))
+
+
+(defn cycle-if [zloc]
+  (when-let [[an-if cand] (find-if zloc)]
+    (-> cand
+        z/rightmost
+        shift-left
+        z/leftmost
+        (z/replace (symbol (if (= an-if "if") "if-not" "if"))))))

 (defn cycle-col [form-str]
@@ -49,44 +84,6 @@
        (= (.substr form-str 0 2) "#{") (wrap-in "(" ")" 2)
        :else nil))))

-
-(defn find-node [start candidate-str]
-  (loop [cur start]
-    (cond
-     (= (-> cur z/node str) candidate-str) cur
-     (not (z/end? cur)) (recur (z/next cur))
-    :else nil)))
-
-
-
-(defn move-up [form-str candidate-str]
-  (let [root (p/str->seq-zip form-str)
-        loc? (when (seq root) (find-node root candidate-str))]
-    (when (and loc? (z/node (z/remove loc?)))
-      (z/root (z/insert-left (z/remove loc?) (z/node loc?))))))
-
-;;(move-up "(+ 1 (\"__jalla__\" \"dill\"))" "__jalla__")
-
-;;(move-up "(\"__jalla__\")" "__jalla__")
-
-
-;; DOH no negative lookbehind in JS
-;;"(?<!if|\bif-not\b)\s\(" "\n("
-(defn inject-nl[form-str]
-  (let [idx-a (.indexOf form-str "if (")
-        idx-b (.indexOf form-str "if-not (")]
-    (cond
-     (= -1 idx-a idx-b) (s/replace form-str #"\s\(" "\n(")
-     (> idx-a idx-b) (str (.substr form-str 0 (+ idx-a 4))
-                          (inject-nl (.substr form-str (+ idx-a 4))))
-     :else (str (.substr form-str 0 (+ idx-b 8))
-                (inject-nl (.substr form-str (+ idx-b 8)))))))
-
-
-;; Silly simplistic...
-(defn format-form [form-str]
-  (-> form-str
-      inject-nl))

 (defn replace-cmd [ed replace-fn & {:keys [fmt]}]
@@ -105,12 +102,25 @@
           (editor/move-cursor ed p))))))

+(defn cycle-if* [ed]
+  (let [pos (editor/->cursor ed)
+        form (u/get-top-level-form ed pos)
+        zloc (some-> form
+                     :form-str
+                     z/of-string
+                     (z/find-last-by-pos (u/->zipper-pos-start pos form)))]
+
+    (when-let [res (some-> zloc cycle-if z/root-string)]
+      (editor/replace ed (:start form) (:end form) res)
+      (editor/move-cursor ed pos)
+      (u/format-keep-pos ed))))
+

 (behavior ::cycle-if!
           :triggers #{:refactor.cycle-if!}
           :reaction (fn [ed]
-                      (replace-cmd ed cycle-if :fmt true)))
+                      (cycle-if* ed)))

 (behavior ::cycle-col!
           :triggers #{:refactor.cycle-col!}
@@ -131,25 +141,3 @@
               :exec (fn []
                       (when-let [ed (pool/last-active)]
                         (object/raise ed :refactor.cycle-col!)))})
-
-
-;; (cmd/command {:command ::move-up
-;;              :desc "Clojure refactor: Move node up"
-;;              :exec (fn []
-;;                      (let [ed (pool/last-active)
-;;                            pos (editor/->cursor ed)
-;;                            token (cp/find-symbol-at-cursor ed)
-;;                            move-node (:string token)
-;;                            top-form (u/get-top-level-form ed pos)]
-
-;;                        (when-let [moved (move-up (u/replace-token (:form-str top-form)
-;;                                                                   {:line (- (:line pos) (:line (:start top-form)))
-;;                                                                    :start (:start token)
-;;                                                                    :end (:end token)}
-;;                                                                   "__move-node__")
-;;                                                  "__move-node__")]
-
-;;                          (let [bounds (u/find-token-bounds moved "__move-node__")
-;;                                replaced (u/replace-token moved bounds move-node)]
-;;                           (editor/replace ed (:start top-form) (:end top-form) replaced)
-;;                            ))))})


Correct null pointer in reconciler

Correct null pointer in reconciler

Signed-off-by: Wil <41c73e1c187a64e501bf473cfef5419e8eb5a640@twosigma.com>

--- scheduler/src/cook/mesos/scheduler.clj
+++ scheduler/src/cook/mesos/scheduler.clj
@@ -450,6 +450,7 @@
 (histograms/defhistogram [cook-mesos scheduler offer-size-mem])
 (histograms/defhistogram [cook-mesos scheduler offer-size-cpus])
 (histograms/defhistogram [cook-mesos scheduler number-tasks-matched])
+(histograms/defhistogram [cook-mesos-scheduler number-offers-matched])
 (meters/defmeter [cook-mesos scheduler scheduler-offer-matched])
 (meters/defmeter [cook-mesos scheduler handle-resource-offer!-errors])
 (meters/defmeter [cook-mesos scheduler matched-tasks])
@@ -471,7 +472,7 @@

 (defn process-matches-for-backfill
   "This computes some sets:
-
+
    fully-processed: this is a set of job uuids that should be removed from the list scheduler jobs. These are not backfilled
    upgrade-backfill: this is a set of instance datomic ids that should be upgraded to non-backfill
    backfill-jobs: this is a set of job uuids for jobs that were matched, but are in the backfill QoS class
@@ -620,7 +621,7 @@
                    (vec (apply concat upgrade-txns task-txns)))
                 (log/info "Launching" (count task-txns) "tasks")
                 (log/info "Upgrading" (count (:upgrade-backfill processed-matches)) "tasks from backfilled to proper")
-                (log/debug "Matched tasks" task-txns)
+                (log/info "Matched tasks" task-txns)
                 ;; This launch-tasks MUST happen after the above transaction in
                 ;; order to allow a transaction failure (due to failed preconditions)
                 ;; to block the launch
@@ -629,6 +630,11 @@
                                    (mapcat (comp :id :offer :leases))
                                    (distinct)
                                    (count)))
+                (histograms/update! number-offers-matched
+                                    (->> matches
+                                         (mapcat (comp :id :offer :leases))
+                                         (distinct)
+                                         (count)))
                 (meters/mark! matched-tasks (count task-txns))
                 (meters/mark! matched-tasks-cpus (:cpus match-resource-requirements))
                 (meters/mark! matched-tasks-mem (:mem match-resource-requirements))
@@ -774,7 +780,7 @@
     (when (seq running-tasks)
       (log/info "Preparing to reconcile" (count running-tasks) "tasks")
       (doseq [[task-id] running-tasks
-              :let [task-ent (d/entity db task-id)
+              :let [task-ent (d/entity db [:instance/task-id task-id])
                     hostname (:instance/hostname task-ent)
                     job (:job/_instance task-ent)]]
         (.. fenzo


add TODOs about imperfect and (or .. stem)

--- src/babel/francais/morphology/verbs.clj
+++ src/babel/francais/morphology/verbs.clj
@@ -202,24 +202,28 @@
      (get-in word [:imperfect number-and-person])
      (get-in word [:imperfect number-and-person])

+     ;; TODO: this seems wrong: 'stem' is never false
      (and (= person :1st) (= number :sing) (or er-type stem))
      (str stem "ais")

      (and (= person :1st) (= number :sing) ir-type)
      (str stem "issais")

+     ;; TODO: this seems wrong: 'stem' is never false
      (and (= person :2nd) (= number :sing) (or er-type stem))
      (str stem "ais")

      (and (= person :2nd) (= number :sing) ir-type)
      (str stem "issais")

+     ;; TODO: this seems wrong: 'stem' is never false
      (and (= person :3rd) (= number :sing) (or er-type stem))
      (str stem "ait")

      (and (= person :3rd) (= number :sing) ir-type)
      (str stem "issait")
-
+
+     ;; TODO: this seems wrong: 'stem' is never false
      (and (= person :1st) (= number :plur) (or er-type stem))
      (str stem "ions")

@@ -227,7 +231,8 @@
      (str stem "issions")

      ;; <second person plural imperfecto>
-
+
+     ;; TODO: this seems wrong: 'stem' is never false
      (and (= person :2nd) (= number :plur) (or er-type stem))
      (str stem "iez")

@@ -237,6 +242,7 @@
      ;; </second person plural imperfecto>

      ;; <third person plural imperfecto>
+     ;; TODO: this seems wrong: 'stem' is never false
      (and (= person :3rd) (= number :plur) (or er-type stem))
      (str stem "aient")


Format log properly.

Format log properly.

--- src/clojure/my/stuff/fitlogger/main.clj
+++ src/clojure/my/stuff/fitlogger/main.clj
@@ -35,20 +35,21 @@
 (defn set-elmt [activity elmt s]
   (on-ui (config (find-view activity elmt) :text s)))

-(defn format-events [events]
+(defn trim-keyword [k]
+  (apply str (rest (drop-while #(not= % \/) (str k)))))
+
+(defn format-measurements [m]
   (->>
-   (map (fn [[location event]]
-            (format "%s - %s\n" location event))
-          events)
-   (join "                        ")))
+   (map (fn [[k v]]
+            (format "%s: %s" (trim-keyword k) v))
+          m)
+   (join ", ")))

-;; (defn format-listing [lst]
-;;   (->> (map (fn [[date events]]
-;;             (format "%s - %s" date (format-events events)))
-;;           lst)
-;;      join))
-
-(defn format-listing [lst] lst)
+(defn format-listing [lst]
+  (->> (map (fn [[_ measurements]]
+            (format "%s" (format-measurements measurements)))
+          lst)
+     (join "\n")))

 (def listing (atom {}))

@@ -65,7 +66,7 @@
                    (catch RuntimeException e "Date string is empty!"))]
     (when (number? date-key)
       (swap! listing
-             #(reduce (fn [l k] (assoc-in l [date-key k] (get-elmt activity k)))
+             #(reduce (fn [l k] (assoc-in l [date-key k] (read-string (get-elmt activity k))))
                       %
                       [::date ::weight ::bf ::water ::muscle]))
       (update-ui activity))))


Don't generated nested repeated outputs for resolvers

--- src/com/wsscode/pathom/connect/gen.cljc
+++ src/com/wsscode/pathom/connect/gen.cljc
@@ -7,6 +7,9 @@
 (defn gen-connect-index [attrs]
   {::attrs
    attrs
+
+   ::p/path
+   []

    ::s.query/gen-property
    (fn gen-property [{::keys [attrs]}] (gen/elements attrs))
@@ -22,12 +25,20 @@
                      [6 (gen-join env)]]))

    ::s.query/gen-join-key
-   (fn gen-join-key [{::s.query/keys [gen-property] :as env}]
-     (gen-property env))
+   (fn gen-join-key [{::s.query/keys [gen-property]
+                      ::p/keys       [path]
+                      :as            env}]
+     (gen-property (update env ::attrs #(remove (set path) %))))

    ::s.query/gen-join-query
    (fn gen-join-query [{::s.query/keys [gen-query] :as env}]
      (gen-query env))
+
+   ::s.query/gen-join
+   (fn gen-join [{::s.query/keys [gen-join-key gen-query] :as env}]
+     (gen/let [key   (gen-join-key env)
+               query (gen-query (update env ::p/path conj key))]
+       {key query}))

    ::s.query/gen-query
    (fn gen-query [{::s.query/keys [gen-property gen-query-expr gen-max-depth] :as env}]
@@ -57,15 +68,18 @@
                    index
                    (pc/add index sym resolver))) {} resolvers)))})

+(defn merge-resolvers [resolvers]
+  (reduce (fn [index {::pc/keys [sym] :as resolver}]
+            (if (contains? (::pc/index-resolvers index) sym)
+              index
+              (pc/add index sym resolver))) {} resolvers))
+
 (defn clean-nil [s]
   (into [] (filter identity) s))

 (defn gen-connect-query [{::pc/keys [indexes]}]
   {::pc/indexes
-   indexes
-
-   ::pc/cache
-   (atom {})
+   (assoc indexes ::pc/cache (atom {}))

    ::p/path
    []


[#12556] Black font color of community categories in dark mode

Signed-off-by: andrey <b713972e59b8e606e23253c4a13e948139fea4d1@gmail.com>

--- src/status_im/ui/screens/communities/community.cljs
+++ src/status_im/ui/screens/communities/community.cljs
@@ -166,7 +166,7 @@
                      [rn/touchable-opacity {:on-press #(>evt [:delete-community-category community-id id])}
                       [icons/icon :main-icons/delete-circle {:no-color true}]]
                      [icons/icon :main-icons/channel-category {:color colors/gray}])
-                   [rn/text {:style {:font-size 17 :margin-left 10}} name]]
+                   [rn/text {:style {:font-size 17 :margin-left 10 :color colors/black}} name]]
         :content  [rn/view
                    (for [chat (get chats id)]
                      (if edit


Docstring for expected got lost.

Docstring for expected got lost.

--- src/structural_typing/assist/predicate_defining.clj
+++ src/structural_typing/assist/predicate_defining.clj
@@ -18,7 +18,17 @@

 (def exactly-format "%s should be exactly `%s`; it is `%s`")

-(defn exactly [expected]
+(defn exactly
+  "A predicate that succeeds exactly when its argument is `=` to expected.
+
+        (built-like? even? even?) ;=> false
+        (built-like? (exactly even?) even?) ;=> true
+
+  Note: except for vectors, maps, and functions, `exactly` is added implicitly:
+
+        (built-like {[ALL :a] 1} [{:a 1} {:a 2}]) ;=> [1 :a] should be exactly `1`; it is `2`
+"
+  [expected]
   (compose-predicate
    (format "(exactly %s)" (readable/value-string expected))
    (partial = expected)


Added graphite function mostDeviant

Added graphite function mostDeviant

--- src/de/otto/oscillator/graphite/dsl.clj
+++ src/de/otto/oscillator/graphite/dsl.clj
@@ -12,6 +12,9 @@

 (defn group [& targets]
   (str "group(" (cs/join "," targets) ")"))
+
+(defn most-deviant [& targets]
+  (str "mostDeviant(" (cs/join "," targets) ")"))

 (defn summarize [target, timespan]
   (str "summarize(" target ",\"" timespan "\",\"avg\")"))


Allow for deleted files by removing the asset from the cache before refreshing it from downstream

--- src/io/aviso/twixt/memory_cache.clj
+++ src/io/aviso/twixt/memory_cache.clj
@@ -53,11 +53,12 @@
   A cached asset is invalid if any of its dependencies has changed (based on modified-at timestamp)."
   [handler]
   (let [cache (atom {})]
-    (fn development-cache [asset-path]
+    (fn invalidating-cache [asset-path]
       (let [asset (get @cache asset-path)]
         (if (is-valid? asset)
           asset
           (do
+            (swap! cache dissoc asset-path)
             (when-let [asset (handler asset-path)]
               (swap! cache assoc asset-path asset)
               asset)))))))


Minor alignment fix

Minor alignment fix

--- src/com/akr/ez_patcher/core.clj
+++ src/com/akr/ez_patcher/core.clj
@@ -136,8 +136,8 @@
                  [_ 'java.lang.Integer 'java.lang.Byte      _]   (byte value)
                  [_ 'java.lang.Integer 'java.lang.Short     _]   (short value)
                  [_ 'java.lang.String  'java.lang.Character _]   (first value)
-                 [_ 'java.lang.String  _               true]   (let [klass (get-class-by-name property-type)]
-                                                                 (Reflector/invokeStaticMethod klass "valueOf" (to-array [value])))
+                 [_ 'java.lang.String  _                 true]   (let [klass (get-class-by-name property-type)]
+                                                                   (Reflector/invokeStaticMethod klass "valueOf" (to-array [value])))
                  :else (-> property-type
                              (resolve)
                              (cast value)))]


Tweaks.

Tweaks.

--- src/eu/cassiel/reveal_js_render_clj.clj
+++ src/eu/cassiel/reveal_js_render_clj.clj
@@ -49,11 +49,13 @@

 (def image (partial image-h 480))

-(defn video [f]
-  [:video {:height 480
+(defn video-h [h f]
+  [:video {:height h
            :controls 1
            :data-autoplay 1}
-   [:source {:src (str (File. "media" f))}]])
+   [:source {:src (str ASSET-ROOT-URL f)}]])
+
+(def video (partial video-h 480))

 (defn github [stem text]
   [:a {:href (str "https://github.com/" stem)} text])
@@ -96,6 +98,36 @@
                     (p/include-css (format "css/theme/%s.css" (name theme))))
    :body-part (html [:div.reveal
                      (vec (cons :div.slides slides))])})
+
+;; This machinery is for rendering directly from a project containing a
+;; presentation file which we want to be able to evaluate immediately.
+;; It renders into our SSI-enabled Apache document area.
+
+(def INCLUDE-ROOT (-> (File. (System/getProperty "user.home"))
+                      (File. "Sites")
+                      (File. "reveal.js")
+                      (File. "_included")))
+(def ASSET-ROOT-URL "../reveal-media/")
+
+(defn render1 [& {:keys [head body]}]
+  (.mkdir INCLUDE-ROOT)
+  (spit (str (File. INCLUDE-ROOT "head.html")) head)
+  (spit (str (File. INCLUDE-ROOT "content.html")) body))
+
+(defn render-me [& {:keys [theme title author slides]}]
+  (render1
+   :head (html [:title title]
+               [:meta {:name "description" :content title}]
+               [:meta {:name "author" :content author}]
+               [:link#theme {:rel "stylesheet"
+                             :href (format "css/theme/%s.css" (name theme))}])
+   :body (html [:div.reveal
+                (vec (cons :div.slides slides))])))
+
+;; This machinery is for "batch" rendering from a .clj to a .html, without
+;; needing any server machinery. Upside: result is a single vanilla HTML file
+;; (plus copied reveal.js assets). Downside: `render-main` needs to be
+;; explicitly called with all file arguments to do the work (see `from-repl.clj`).

 (def REVEAL-ROOT (File. "/Users/nick/GITHUB/cassiel/reveal.js"))


Swith to dsl

Swith to dsl

--- test/clojure/clojurewerkz/cassaforte/test_helper.clj
+++ test/clojure/clojurewerkz/cassaforte/test_helper.clj
@@ -2,7 +2,7 @@
   (:refer-clojure :exclude [update])
   (:require [clojurewerkz.cassaforte.client :as client]
             [clojurewerkz.cassaforte.cql :refer :all]
-            [clojurewerkz.cassaforte.query :refer :all]))
+            [clojurewerkz.cassaforte.query.dsl :refer :all]))

 (declare ___test-session)


Added overrideable handlers to table widget

--- src/conexp/gui/editors/util.clj
+++ src/conexp/gui/editors/util.clj
@@ -178,6 +178,28 @@
   "Takes a java-array and turns it into a list"
   [array]
   (map (rho aget array) (range (alength array))))
+
+(defmacro !!
+  "Takes a map, a key and arbitrary additional parameters and calls
+   the function that is the value of the map under the key with
+   the given additional parameters"
+  [map key & parameters]
+  `((~map ~key) ~@parameters))
+
+(defmacro !!!
+  "Takes a map, a key and arbitrary additional parameters and calls
+   the function that is the value of that map, which is the map under
+   the key :handler, under the key with the given additional parameters"
+  [map key & parameters]
+  `(((~map :handler) ~key) ~@parameters))
+
+(defmacro !!!!
+  "Takes a widget, a key and arbitrary additional parameters and calls
+   the handler function of the widget that is associated with the key
+   with the widget as first parameter and the given additional parameters"
+  [map key & parameters]
+  `(((~map :handler) ~key) ~map ~@parameters))
+

 ;;;
 ;;; java & swing utils
@@ -414,10 +436,10 @@
         (one-by-one lns (fn [r]
                           (one-by-one (range (count (cells r)))
                             (fn [c]
-                              (.setValueAt control
-                                ((cells r) c)
+                              (!!!! obj :set-cell-value
                                 (+ starty r)
-                                (+ startx c))))))))))
+                                (+ startx c)
+                                ((cells r) c))))))))))

 (defn-swing-threads* table-to-clipboard!
   "Takes a table widget as parameter and copies the current
@@ -462,6 +484,33 @@
          :widget   pane
          :control  table
          :model    model
+         :handler  (ref {})
+
+         :set-handler
+         (fn-doc "Set the widgets handler function.
+
+  Parameters:
+    key        _a key that identifies the handler
+    handler    _the new handler function"
+           [key handler]
+           (let [ widget @self
+                  handler-map (widget :handler) ]
+             (dosync (commute handler-map conj {key handler}))))
+
+         :set-handler-and-wait
+         (fn-doc "Set the widgets handler function,
+  and waits for the completion of the setup.
+
+  Parameters:
+    key        _a key that identifies the handler
+    handler    _the new handler function"
+           [key handler]
+           (let [ widget @self
+                  handler-map (widget :handler)
+                  dowaitfor (promise)]
+             (dosync (commute handler-map conj {key handler})
+               (deliver dowaitfor nil))
+             @dowaitfor))

          :register-keyboard-action
          (fn-swing-threads*-doc "Registers a keyboard action on the table.
@@ -537,7 +586,31 @@
                     [:register-keyboard-action
                       clipboard-to-table!
                       "Paste" keystroke-paste :focus]
-                    ]]
+                    [:set-handler :set-cell-value
+                      (fn-swing-threads*-doc "Sets the value of a cell in the table.
+  Parameters:
+    widget     _the widget object
+    row        _integer identifying a row
+    column     _integer identifying a column
+    contents   _the new contents"
+                        [widget row column contents]
+                        (.setValueAt (get-control widget)
+                          (!!!! widget :set-cell-value-hook row column contents)
+                          row column))]
+                    [:set-handler :set-cell-value-hook
+                      (fn-doc "This hook takes requested contents and turns them into
+  allowed contents.
+
+  Parameters:
+    widget     _the widget object
+    row        _integer identifying a row
+    column     _integer identifying a column
+    contents   _the desired new contents
+
+  Returns the new allowed contents for the cell (as string)."
+                        [widget row column contents]
+                        (str contents))
+                    ]]]
     (do
       (deliver self widget)
       (one-by-one defaults unroll-parameters-fn-map widget)


remove peer-group-manager-gen-test for now as it's

not pure, causing timeouts in circle. This will be replaced
with a pure one with ABS

--- test/onyx/peer/peer_group_manager_gen_test.clj
+++ test/onyx/peer/peer_group_manager_gen_test.clj
@@ -1,65 +0,0 @@
-(ns onyx.peer.peer-group-manager-gen-test
-  (:require [clojure.core.async :refer [>!! <!! alts!! promise-chan close! chan thread poll!]]
-            [com.stuartsierra.component :as component]
-            [taoensso.timbre :refer [info error warn fatal]]
-            [onyx.log.entry :refer [create-log-entry]]
-            [onyx.static.logging-configuration :as logging-config]
-            [onyx.test-helper :refer [load-config with-test-env playback-log]]
-            [onyx.log.zookeeper :refer [zookeeper]]
-            [onyx.extensions :as extensions]
-            [onyx.system :as system]
-            [onyx.static.default-vals :refer [arg-or-default]]
-            [clojure.test :refer [deftest is]]
-            [clojure.test.check :as tc]
-            [clojure.test.check.generators :as gen]
-            [clojure.test.check.properties :as prop]
-            [com.gfredericks.test.chuck :refer [times]]
-            [com.gfredericks.test.chuck.clojure-test :refer [checking]]))
-
-(def add-peer-gen
-  (gen/fmap (fn [oid]
-              [:add-peer (keyword (str "po" oid))])
-            (gen/resize 20 gen/pos-int)))
-
-(def remove-peer-gen
-  (gen/fmap (fn [oid]
-              [:remove-peer (keyword (str "po" oid))])
-            (gen/resize 20 gen/pos-int)))
-
-(def restart-peer-group-gen
-  (gen/return [:restart-peer-group]))
-
-(def break-conn
-  (gen/return [:break-conn]))
-
-(deftest peergroup-gen-test
-  (checking
-    "Checking percentages allocation causes peers to be evenly split"
-    (times 5)
-    [n-commands (gen/fmap #(+ 10 %) gen/pos-int)
-     commands (gen/vector (gen/one-of [add-peer-gen remove-peer-gen break-conn restart-peer-group-gen]) n-commands)]
-    (let [onyx-id (java.util.UUID/randomUUID)
-          config (load-config)
-          env-config (assoc (:env-config config) :onyx/tenancy-id onyx-id)
-          peer-config (assoc (:peer-config config) :onyx/tenancy-id onyx-id)
-          env (onyx.api/start-env env-config)
-          peer-group (onyx.api/start-peer-group peer-config)
-          group-ch (:group-ch (:peer-group-manager peer-group))
-          ch (chan 10000)]
-      (try
-       (run! (partial >!! group-ch) commands)
-       (let [final-replica (playback-log (:log env) (extensions/subscribe-to-log (:log env) ch) ch 6000)
-             model (reduce (fn [model [cmd & args]]
-                             (case cmd
-                               :add-peer
-                               (update model :peers conj (first args))
-                               :remove-peer
-                               (update model :peers disj (first args))
-                               model))
-                           {:peers #{}}
-                           commands)]
-         (is (= 1 (count (:groups final-replica))))
-         (is (= (count (:peers final-replica)) (count (:peers model)))))
-       (finally
-        (onyx.api/shutdown-peer-group peer-group)
-        (onyx.api/shutdown-env env))))))


print formatted namelist from map, not tree

--- src/nml/core.clj
+++ src/nml/core.clj
@@ -7,8 +7,6 @@
 (declare nml-get nml-name nml-parse nml-set nml-str)

 ;; defs
-
-(def debug false)

 (def msgs
   {
@@ -58,12 +56,19 @@
     (let [val (nml-get tree nml key)]
       (println (if no-prefix val (str nml ":" key "=" val))))))

+;;(defn- nml-map [tree]
+;; (let [q  #(str "\"" % "\"")
+;;       f0 (fn [& nvsubseqs   ] (into {} nvsubseqs))
+;;       f1 (fn [dataref values] { (q (nml-str dataref)) (q (nml-str values)) })
+;;       f2 (fn [& stmts       ] (into {} stmts))
+;;       f3 (fn [name nvseq    ] { (q (nml-str name)) nvseq })]
+;;   (insta/transform {:nvseq f0 :nvsubseq f1 :s f2 :stmt f3 } tree)))
+
 (defn- nml-map [tree]
-  (let [q  #(str "\"" % "\"")
-        f0 (fn [& nvsubseqs   ] (into {} nvsubseqs))
-        f1 (fn [dataref values] { (q (nml-str dataref)) (q (nml-str values)) })
+  (let [f0 (fn [& nvsubseqs   ] (into {} nvsubseqs))
+        f1 (fn [dataref values] { (nml-str dataref) (nml-str values) })
         f2 (fn [& stmts       ] (into {} stmts))
-        f3 (fn [name nvseq    ] { (q (nml-str name)) nvseq })]
+        f3 (fn [name nvseq    ] { (nml-str name) nvseq })]
     (insta/transform {:nvseq f0 :nvsubseq f1 :s f2 :stmt f3 } tree)))

 (defn- nml-name [x]
@@ -95,9 +100,8 @@
         list2str #(apply str (map nml-str %))
         strfirst #(nml-str (first %))
         strlast  #(nml-str (last %))]
-    (if debug (println (str "key=" key " val=" val)))
     (apply str (case key
-                 :s        (delesort val)
+                 :s        (string/join "\n" (delesort val))
                  :array    [(strfirst val) (strlast val)]
                  :c        (strfirst val)
                  :colon    ":"
@@ -113,8 +117,8 @@
                  :junk     ""
                  :logical  (strfirst val)
                  :name     (map string/lower-case val)
-                 :nvseq    (delesort val)
-                 :nvsubseq ["  " (strfirst val) "=" (strlast val) "\n"]
+                 :nvseq    (string/join " " (delesort val))
+                 :nvsubseq [(strfirst val) "=" (strlast val)]
                  :partref  (strfirst val)
                  :percent  "%"
                  :r        (strfirst val)
@@ -124,7 +128,7 @@
                  :sign     val
                  :slash    val
                  :star     "*"
-                 :stmt     ["&" (strfirst val) "\n" (list2str (rest val)) "/\n"]
+                 :stmt     ["&" (strfirst val) " " (list2str (rest val)) " /"]
                  :string   val
                  :true     "t"
                  :uint     val
@@ -204,6 +208,13 @@
         child :nvseq
         f     (fn [& v] (into [child] (nml-uniq v)))]
       (insta/transform {child f} tree)))
+
+;; formatting
+
+(defn- fmt-namelist [nls-map]
+  (let [f0 #(str "  " (first %) "=" (last %) "\n")
+        f1 (fn [x] (str "&" (first x) "\n" (apply str (map f0 (sort (last x)))) "/\n"))]
+    (string/trim (apply str (map f1 (sort nls-map))))))

 ;; main

@@ -226,8 +237,8 @@
                   ""
                   (try (slurp in)
                        (catch Exception e
-                         (fail (str "Could not read from '" in "'."))))))]
-      (if debug (println tree))
+                         (fail (str "Could not read from '" in "'."))))))
+          nls-map (nml-map tree)]
       (cond gets  (nml-gets tree gets (:no-prefix options))
             sets  (let [s (nml-str (nml-sets tree sets))]
                     (if (= out *out*)
@@ -235,4 +246,4 @@
                       (try (spit out s)
                            (catch Exception e
                              (fail (str "Could not write to '" out "'."))))))
-            :else (println (string/trim (nml-str tree)))))))
+            :else (println (fmt-namelist nls-map))))))


Revert "Validate Java version when booting up the env."

This reverts commit 6a6558e5a9710285e922285f5b5fae3987d1f24d.

--- src/onyx/api.clj
+++ src/onyx/api.clj
@@ -336,7 +336,6 @@
   ([env-config]
    (start-env env-config {:monitoring :no-op}))
   ([env-config monitoring-config]
-   (validator/validate-java-version)
    (validator/validate-env-config env-config)
    (component/start (system/onyx-development-env env-config monitoring-config))))


End planet loop if there are problems with ws connection

--- src/flux_challenge_re_frame/core.cljs
+++ src/flux_challenge_re_frame/core.cljs
@@ -36,13 +36,18 @@
   (go
     (let [{:keys [ws-channel error]} (<! (ws-ch "ws://localhost:4000" {:format :json}))]
       (if-not error
-        (while true
+        (loop []
+          ; If the websocket server gets closed, the ws-channel gets closed too and the response will be nil.
           (let [response (<! ws-channel)
                 error (:error response)
                 planet (keywordize-keys (:message response))]
-            (if-not error
-              (swap! app-state assoc :planet planet)
-              (println (str "Error while receiving message: " error)))))
+            (if planet
+              (do
+                (swap! app-state assoc :planet planet)
+                (recur))
+              (if error
+                (println (str "Error while receiving message: " error))
+                (println "Websocket connection closed unexpectedly")))))
         (println (str "Error while connecting: " error))))))

 (defn get-jedi


Adding project settings and moving cancel button for v2 build header.

--- src-cljs/frontend/components/build_head.cljs
+++ src-cljs/frontend/components/build_head.cljs
@@ -1220,46 +1220,52 @@
             has-write-settings? (:write-settings
                                   (get-in data state/project-scopes-path))]
         (html
-          [:div.build-actions
-           (when has-write-settings?
-             [:div.btn-group
-              (forms/managed-button
-                [:button.btn
-                 {:data-loading-text "Rebuilding",
-                  :title "Retry the same tests",
-                  :on-click #(raise! owner [:retry-build-clicked {:build-id build-id
-                                                                  :vcs-url vcs-url
-                                                                  :build-num build-num
-                                                                  :no-cache? false}])}
-                 "Rebuild"])
-              [:button.btn.dropdown-toggle {:data-toggle "dropdown"} [:span.caret]]
-              [:ul.dropdown-menu
-               ;; XXX Temporarily remove the ssh button for OSX builds
-               (when (not (feature/enabled-for-project? project :osx))
-                 [:li (forms/managed-button
-                        [:a.ssh_build
-                         {:data-loading-text "Rebuilding",
-                          :title "Retry with SSH in VM",
-                          :on-click #(raise! owner [:ssh-build-clicked {:build-id build-id
-                                                                        :vcs-url vcs-url
-                                                                        :build-num build-num}])}
-                         "with ssh"])])
-               [:li (forms/managed-button
-                      [:a
-                       {:data-loading-text "Rebuilding",
-                        :title "Retry without cache",
-                        :on-click #(raise! owner [:retry-build-clicked {:build-id build-id
-                                                                        :vcs-url vcs-url
-                                                                        :build-num build-num
-                                                                        :no-cache? true}])}
-                       "without cache"])]]])
-           [:div.actions
-            (when (and (build-model/can-cancel? build) has-write-settings?)
-              (forms/managed-button
-               [:button.cancel_build
-                {:data-loading-text "Canceling",
-                 :title "Cancel this build",
-                 :on-click #(raise! owner [:cancel-build-clicked {:build-id build-id
-                                                                  :vcs-url vcs-url
-                                                                  :build-num build-num}])}
-                "Cancel"]))]])))))
+          [:div
+           [:div.build-actions
+            [:div.actions
+             (when (and (build-model/can-cancel? build) has-write-settings?)
+               (forms/managed-button
+                 [:a
+                  {:data-loading-text "Canceling",
+                   :title             "Cancel this build",
+                   :on-click #(raise! owner [:cancel-build-clicked {:build-id build-id
+                                                                    :vcs-url vcs-url
+                                                                    :build-num build-num}])}
+                  "Cancel Build"]))
+            (when has-write-settings?
+              [:div.btn-group
+               (forms/managed-button
+                 [:button.btn
+                  {:data-loading-text "Rebuilding",
+                   :title             "Retry the same tests",
+                   :on-click #(raise! owner [:retry-build-clicked {:build-id build-id
+                                                                   :vcs-url vcs-url
+                                                                   :build-num build-num
+                                                                   :no-cache? false}])}
+                  "Rebuild"])
+               [:button.btn.dropdown-toggle {:data-toggle "dropdown"} [:span.caret]]
+               [:ul.dropdown-menu
+                ;; XXX Temporarily remove the ssh button for OSX builds
+                (when (not (feature/enabled-for-project? project :osx))
+                  [:li (forms/managed-button
+                         [:a.ssh_build
+                          {:data-loading-text "Rebuilding",
+                           :title             "Retry with SSH in VM",
+                           :on-click #(raise! owner [:ssh-build-clicked {:build-id build-id
+                                                                         :vcs-url vcs-url
+                                                                         :build-num build-num}])}
+                          "with ssh"])])
+                [:li (forms/managed-button
+                       [:a
+                        {:data-loading-text "Rebuilding",
+                         :title             "Retry without cache",
+                         :on-click #(raise! owner [:retry-build-clicked {:build-id build-id
+                                                                         :vcs-url vcs-url
+                                                                         :build-num build-num
+                                                                         :no-cache? true}])}
+                        "without cache"])]]])
+            [:a
+             {:href (routes/v1-project-settings {:org  (get-in data (conj state/project-plan-path :org_name))
+                                                 :repo (get-in data (conj state/project-path :reponame))})}
+             [:img.dashboard-icon {:src (common/icon-path "QuickLink-Settings")}]
+             "Project Settings"]]]])))))


1_2_6


Don't respond with garbled data.

Don't respond with garbled data.

--- src/forces_assemble/handler.clj
+++ src/forces_assemble/handler.clj
@@ -130,7 +130,8 @@
   :known-content-type? #(check-content-type % [application-json])
   :malformed? #(parse-json % ::data)
   :post! (fn [context]
-           (add-event-to-channel channel-id (::data context))))
+           (add-event-to-channel channel-id (::data context))
+           nil))

 (defresource channel-subscribers [channel-id]
   :allowed-methods [:post]


Integerate with the values from the UI

Integerate with the values from the UI

--- src/clj/collect_earth_online/db/projects.clj
+++ src/clj/collect_earth_online/db/projects.clj
@@ -213,16 +213,18 @@

 (defn- assign-qaqc
   "Assigns additional plots to users based on QA/QC method.  The two options are:
-   {:qaqc-method \"overlap\"
-    :percent     50}
+   {:qaqcMethod \"overlap\"
+    :percent    50}
    and
-   {:qaqc-method \"sme\"
-    :percent     100
-    :smes        [2 5]}"
+   {:qaqcMethod \"sme\"
+    :percent    100
+    :smes       [2 5]}"
   [assigned-plots design-settings]
   (when (seq assigned-plots)
-    (let [{:keys [qaqc-method percent smes]} (:qaqc-assignment design-settings)
-          {:keys [users]}                    (:user-assignment design-settings)]
+    (let [{qaqc-method :qaqcMethod
+           percent    :percent
+           smes       :smes} (:qaqcAssignment design-settings)
+          {:keys [users]}    (:userAssignment design-settings)]
       (concat assigned-plots
               (->> assigned-plots
                    (group-by :user_rid)


- additional changes to winning screen

- additional changes to winning screen

--- src/app/cljs/one/sample/animation.cljs
+++ src/app/cljs/one/sample/animation.cljs
@@ -579,27 +579,78 @@
                     (.setFrameTime (.time director) duration)
                     (.setValues 1 0)))))

-(defn fall! [target director & {:keys [duration] :or {duration 2000}}]
-  (let [cpX (+ (.x target) (- (rand-int 200) 100))
-        cpY (+ (.y target) (- (rand-int 200) 100))
-        nX (+ (.x target) (* 2 (- cpX (.x target))))
-        nY (+ (.height director) 10)]
-    (doto target
-      (.setDiscardable true)
-      (.addBehavior (doto (CAAT/PathBehavior.)
-                      (.setFrameTime (.time director) duration)
-                      (.setPath (doto (CAAT/Path.)
-                                  (.beginPath (.x target) (.y target))
-                                  (.addQuadricTo cpX cpY nX nY)
-                                  (. (endPath))))
-                      (.addListener
-                       (clj->js
-                        {:behaviorExpired
-                         (fn [bh t a]
-                           (.setExpired target true))})))))))
-
-(defn gen-winning-screen [director]
-  (let [mask (doto (CAAT/ShapeActor.)
+(let [auto-expire-listener
+      (clj->js
+       {:behaviorExpired
+        (fn [bh t a]
+          (.setExpired a true))})]
+  (defn fall! [target director & {:keys [duration] :or {duration 2000}}]
+    (let [cpX (+ (.x target) (- (rand-int 200) 100))
+          cpY (+ (.y target) (- (rand-int 200) 100))
+          nX (+ (.x target) (* 2 (- cpX (.x target))))
+          nY (+ (.height director) 10)]
+      (doto target
+        (.setDiscardable true)
+        (.addBehavior (doto (CAAT/PathBehavior.)
+                        (.setFrameTime (.time director) duration)
+                        (.setPath (doto (CAAT/Path.)
+                                    (.beginPath (.x target) (.y target))
+                                    (.addQuadricTo cpX cpY nX nY)
+                                    (. (endPath))))
+                        (.addListener auto-expire-listener)))))))
+
+(defn director-of [what]
+  (cond (instance? CAAT.Scene what) (.parent what)
+        (instance? CAAT.ActorContainer what) (director-of (.parent what))
+        (instance? CAAT.Actor what) (director-of (.parent what))
+        true nil))
+
+(defn scene-of [what]
+  (cond (instance? CAAT.Scene what) what
+        (instance? CAAT.ActorContainer what) (scene-of (.parent what))
+        (instance? CAAT.Actor what) (scene-of (.parent what))
+        true nil))
+
+(defn repeatedly-create-stars [target scene &
+                               {:keys [start-time start-position batch-count repeat-interval]
+                                :as kw
+                                :or {start-time 0 batch-count 30 start-position [400 50] repeat-interval 2000}}]
+  (let [director (director-of scene)]
+    (.createTimer
+     scene
+     (.time scene)
+     start-time
+     (fn [scene-time timer-time timetask]
+       (dotimes [x batch-count]
+         (let [rotation-direction (if (< (Math/random) 0.5) -1 1)
+               star (doto (gen-star :radius (rand-nth [12 14 16 18 20])
+                                    :color (rand-nth ["yellow" "chartreuse" "orange" "red" "powderblue" "magenta" "cyan"]))
+                      (.enableEvents false)
+                      (.setLocation (+ (x-of start-position) (* x 10)) (+ (y-of start-position) (rand-int 30)))
+                      ;; (. (cacheAsBitmap))
+                      (.addBehavior
+                       (gen-rotate-behavior :from 0 :to (* rotation-direction (+ 180 (* (* (rand-int 2) -1) (rand-int 180))))
+                                            :time [scene-time 3000]))
+                      ;; TODO: why is the following not working? (rotation stops after some seconds)
+                      ;; (animate [:rotate [:from 0 :to (+ 180 (* (* (rand-int 2) -1) (rand-int 180)))
+                      ;;                    :time [scene-time 3000]]])
+                      (fall! director :duration (+ 2000 (rand-int 1000)))
+                      (fade! director :duration (+ 3000 (rand-int 1000))))]
+           (add! target star)
+           ;; randomize the star z
+           (.setZOrder target star (- (rand-int batch-count) (/ batch-count 2)))
+           ))
+       (repeatedly-create-stars target scene
+              :start-time repeat-interval
+              :start-position start-position
+              :batch-count batch-count
+              :repeat-interval repeat-interval)
+       )
+     (fn []) (fn []))))
+
+(defn gen-winning-screen [scene]
+  (let [director (director-of scene)
+        mask (doto (CAAT/ShapeActor.)
                (.setShape CAAT.ShapeActor.prototype.SHAPE_RECTANGLE)
                (.setBounds 0 0 (.width director) (.height director))
                (.setFillStyle "#000000")
@@ -614,19 +665,32 @@
                (.centerAt (/ (.width director) 2) (/ (.height director) 2)))
         container (doto (CAAT/ActorContainer.)
                     (add! mask)
-                    (add! text))]
+                    (add! text)
+                    (.setZOrder text 8)
+                    (.enableEvents false))]
     (m/wrap text.paint [director time default]
             (let [ctx (.ctx director)]
               (set! ctx.shadowColor "yellow")
               (set! ctx.shadowBlur 20)
               (default text director time)))
-    (dotimes [x 40]
-      (add! container (doto (gen-star :radius (rand-nth [12 14 16 18 20])
-                                      :color (rand-nth ["yellow" "green" "orange" "red" "blue"]))
-                        (.setLocation (+ 200 (* x 10)) (+ 170 (rand-int 30)))
-                        (. (cacheAsBitmap))
-                        (fall! director :duration (+ 2000 (rand-int 1000)))
-                        (fade! director :duration (+ 3000 (rand-int 1000))))))
+    (let [animate-text
+          (fn animate-text []
+            (let [r1 (+ 1 (rand-int 4))
+                  r2 (- (+ 1 (rand-int 4)))]
+              (animate text
+                       [:rotate [:from 0 :to r1 :time 1000]]
+                       [:rotate [:from r1 :to r2 :time 1000]]
+                       [:rotate [:from r2 :to 0 :time 1000]]
+                       (fn [t] (animate-text)))))]
+      (animate-text))
+    (dotimes [i 6]
+      (repeatedly-create-stars
+       container scene
+       :start-time (* i 150)
+       :repeat-interval 2000
+       :batch-count 10
+       :start-position [(* 100 (+ 1 i))
+                        (+ 50 (* (mod i 2) 50))]))
     container))

 (defn initialize-views
@@ -682,4 +746,5 @@

          (doseq [object objects]
            (add! scene object))
-         (add! scene (gen-winning-screen director)))))))
+         ;; (add! scene (gen-winning-screen scene))
+         )))))


use paragraphs in the email, prevent Gmail from trimming

--- src/pc/email.clj
+++ src/pc/email.clj
@@ -1,5 +1,7 @@
 (ns pc.email
   (:require [clojure.string :as str]
+            [clj-time.core :as time]
+            [clj-time.format]
             [hiccup.core :as hiccup]
             [pc.mailgun :as mailgun]))

@@ -7,18 +9,23 @@
   (hiccup/html
    [:html
     [:body
-     [:div "Hey there,"]
-     [:div
+     [:p "Hey there,"]
+     [:p
       "Come draw with me on Precursor: "
       [:a {:href (str "https://prcrsr.com/document/" doc-id)}
        (str "https://prcrsr.com/document/" doc-id)]]
-     [:div
+     [:p
       [:a {:href (str "https://prcrsr.com/document/" doc-id)}
        [:img {:width 256
               :src (str "https://prcrsr.com/document/" doc-id ".png?printer-friendly=false")}]]]
-     [:div {:style "font-size: 12px"}
+     [:p {:style "font-size: 12px"}
       "If you think this message was an error, let us know: "
-      [:a {:href "mailto:info@prcrsr.com"} "info@prcrsr.com"] "."]]]))
+      [:a {:href "mailto:info@prcrsr.com"} "info@prcrsr.com"] "."
+      ;; Add some hidden text so that Google doesn't try to trim these.
+      [:span {:style "display: none; max-height: 0px; font-size: 0px; overflow: hidden;"}
+       " Sent at "
+       (clj-time.format/unparse (clj-time.format/formatters :rfc822) (time/now))
+       "."]]]]))

 (defn send-chat-invite [{:keys [cust to-email doc-id]}]
   (mailgun/send-message {:from "Precursor <draw@prcrsr.com>"


add migration #332

add migration
#332

--- src/clj/swarmpit/couchdb/migration.clj
+++ src/clj/swarmpit/couchdb/migration.clj
@@ -20,9 +20,18 @@
   (db/create-sns-global-changes)
   (println "Single node setup finished"))

+(defn change-reg-types
+  []
+  (doseq [dockeruser (db/find-docs "dockeruser")]
+    (db/update-doc dockeruser :type "dockerhub"))
+  (doseq [registry (db/find-docs "registry")]
+    (db/update-doc registry :type "v2"))
+  (println "Change reg types finished"))
+
 (def migrations
   {:single-node-setup single-node-setup
-   :initial           verify-initial-data})
+   :initial           verify-initial-data
+   :change-reg-types  change-reg-types})

 (defn migrate
   []


small fix

small fix

--- src/cljs/salava/core/ui/page_grid.cljs
+++ src/cljs/salava/core/ui/page_grid.cljs
@@ -84,7 +84,8 @@
       "pickable" [:div.media.grid-container
                   [:a {:href "#" :on-click #(do
                                               (.preventDefault %)
-                                              (reset! (:atom element-data) (conj @(:atom element-data) {:name name :id id :visibility visibility}))) :style {:text-decoration "none"}
+                                              (when-not (some (fn [page] (= id (:id page))) @(:atom element-data))
+                                               (reset! (:atom element-data) (conj @(:atom element-data) {:name name :id id :visibility visibility})))) :style {:text-decoration "none"}
                        :data-dismiss "modal"}
                    [:div.media-content
                     [:div.media-body


Fix: make-client :default dispatch had wrong args;

--- src/herald/services/clients.clj
+++ src/herald/services/clients.clj
@@ -151,7 +151,7 @@
     (GithubClient. api-url auth client-opts_ )))

-(defmethod make-client :default [client-type]
+(defmethod make-client :default [client-type _ _]
   (throw (IllegalArgumentException.
            (str "Unsupported client type: " client-type))))


Destructure peer-config, env-config

Destructure peer-config, env-config

--- src/desdemona/launcher/launch_prod_peers.clj
+++ src/desdemona/launcher/launch_prod_peers.clj
@@ -24,9 +24,9 @@

 (defn -main [n & args]
   (let [n-peers (Integer/parseInt n)
-        config (read-config!)
+        {:keys [peer-config env-config]} (read-config!)
         peer-config (assoc
-                     (:peer-config config)
+                     peer-config
                      :onyx.log/config
                      {:appenders
                       {:stdout
@@ -35,7 +35,7 @@
                         :output-fn t/default-output-fn,
                         :fn stdout-logger}}})
         peer-group (onyx.api/start-peer-group peer-config)
-        env (onyx.api/start-env (:env-config config))
+        env (onyx.api/start-env env-config)
         peers (onyx.api/start-peers n-peers peer-group)]
     (println "Attempting to connect to Zookeeper: " (:zookeeper/address peer-config))
     (.addShutdownHook (Runtime/getRuntime)


Made string helper arrays start at zero size

--- src/longshi/fressian/utils.cljs
+++ src/longshi/fressian/utils.cljs
@@ -67,7 +67,7 @@
 (defn make-string-writer
   "Convience method for making a string writer"
   []
-  (StringWriter. (make-array 16384) (js/Uint8Array. 65536)))
+  (StringWriter. (array) (js/Uint8Array. 65536)))

 (deftype
   ^{:doc
@@ -138,7 +138,7 @@

 (defn make-string-reader []
   "Convience method for making a string reader"
-  (StringReader. (js/Uint8Array. 65536) (make-array 21846)))
+  (StringReader. (js/Uint8Array. 65536) (array)))

 (def ^{:doc "Marker for the endianess of bytestreams"}
   little-endian false)


wrap handler maps in a container to discourage modification

We considered implementing Associative and related interfaces on
the HandlerMapContainer to support interrogation while suppressing
modification, but this is simpler and we don't have a real use
case yet for doing anything with the handler maps other than
passing them off to reader and writer fns.

--- src/cognitect/transit.clj
+++ src/cognitect/transit.clj
@@ -22,6 +22,13 @@
            [com.cognitect.transit.impl ReadHandlerMap WriteHandlerMap]
            [com.cognitect.transit.SPI ReaderSPI]
            [java.io InputStream OutputStream]))
+
+(defprotocol HandlerMapProvider
+  (handler-map [this]))
+
+(deftype HandlerMapContainer [m]
+  HandlerMapProvider
+  (handler-map [this] m))

 ;; writing

@@ -130,7 +137,9 @@
   ([out type] (writer out type {}))
   ([^OutputStream out type {:keys [handlers]}]
      (if (#{:json :json-verbose :msgpack} type)
-       (let [handler-map (if (instance? WriteHandlerMap handlers) handlers (merge default-write-handlers handlers))]
+       (let [handler-map (if (instance? HandlerMapContainer handlers)
+                           (handler-map handlers)
+                           (merge default-write-handlers handlers))]
          (Writer. (TransitFactory/writer (transit-format type) out handler-map)))
        (throw (ex-info "Type must be :json, :json-verbose or :msgpack" {:type type})))))

@@ -269,7 +278,9 @@
   ([in type] (reader in type {}))
   ([^InputStream in type {:keys [handlers default-handler]}]
      (if (#{:json :json-verbose :msgpack} type)
-       (let [handler-map (if (instance? ReadHandlerMap handlers) handlers (merge default-read-handlers handlers))
+       (let [handler-map (if (instance? HandlerMapContainer handlers)
+                           (handler-map handlers)
+                           (merge default-read-handlers handlers))
              reader (TransitFactory/reader (transit-format type)
                                            in
                                            handler-map
@@ -318,12 +329,26 @@
           types))

 (defn read-handler-map
+  "Returns a HandlerMapContainer containing a ReadHandlerMap
+  containing all the default handlers for Clojure and Java and any
+  custom handlers that you supply, letting you store the return value
+  and pass it to multiple invocations of reader.  This can be more
+  efficient than repeatedly handing the same raw map of tags -> custom
+  handlers to reader."
   [custom-handlers]
-  (TransitFactory/readHandlerMap (merge default-read-handlers custom-handlers)))
+  (HandlerMapContainer.
+   (TransitFactory/readHandlerMap (merge default-read-handlers custom-handlers))))

 (defn write-handler-map
+  "Returns a HandlerMapContainer containing a WriteHandlerMap
+  containing all the default handlers for Clojure and Java and any
+  custom handlers that you supply, letting you store the return value
+  and pass it to multiple invocations of writer.  This can be more
+  efficient than repeatedly handing the same raw map of types -> custom
+  handlers to writer."
   [custom-handlers]
-  (TransitFactory/writeHandlerMap (merge default-write-handlers custom-handlers)))
+  (HandlerMapContainer.
+   (TransitFactory/writeHandlerMap (merge default-write-handlers custom-handlers))))

 (comment


Use the nightcode window listener

Use the nightcode window listener


Improve Android start time significantly

--- minicraft/desktop/src-common/minicraft/entities.clj
+++ minicraft/desktop/src-common/minicraft/entities.clj
@@ -85,10 +85,11 @@
   [screen {:keys [width height] :as entity} entities]
   (->> (for [tile-x (range 0 (- u/map-width width))
              tile-y (range 0 (- u/map-height height))]
-         (assoc entity :x tile-x :y tile-y))
+         {:x tile-x :y tile-y})
        shuffle
-       (drop-while #(u/is-invalid-location? screen % entities))
-       first))
+       (drop-while #(u/is-invalid-location? screen (merge entity %) entities))
+       first
+       (merge entity)))

 (defn ^:private prevent-move
   [{:keys [x y x-change y-change] :as entity} entities]


update versions

update versions

--- clj-tcp/project.clj
+++ clj-tcp/project.clj
@@ -1,16 +1,16 @@
-(defproject clj-tcp "0.4.9"
+(defproject clj-tcp "1.0.1"
   :description "Fast clojure tcp library based on netty"
   :url "https://github.com/gerritjvv/clj-tcp"
   :license {:name "Eclipse Public License"
             :url "http://www.eclipse.org/legal/epl-v10.html"}
   :dependencies [
-                  [org.clojure/tools.logging "0.2.3"]
-		          [midje "1.6-alpha2" :scope "test"]
+                  [org.clojure/tools.logging "0.3.1"]
+		              [midje "1.8.3" :scope "test"]

-                  [io.netty/netty-all "4.0.24.Final"]
-                  [com.taoensso/nippy "2.5.2"]
-                  [org.clojure/core.async "0.1.267.0-0d7780-alpha"]
-                  [org.clojure/clojure "1.5.1"]]
+                  [io.netty/netty-all "4.0.36.Final"]
+                  [com.taoensso/nippy "2.11.1"]
+                  [org.clojure/core.async "0.2.374"]
+                  [org.clojure/clojure "1.8.0"]]

  :javac-options ["-target" "1.6" "-source" "1.6" "-Xlint:-options"]
  :java-source-paths ["java"]


Default min peers lookup to 1.

Default min peers lookup to 1.

--- src/onyx/scheduling/common_job_scheduler.clj
+++ src/onyx/scheduling/common_job_scheduler.clj
@@ -207,7 +207,7 @@
      (let [tasks (get-in replica [:tasks job])]
        (if (every? (fn [t]
                      (>= (count (get-in result [:allocations job t]))
-                         (get-in result [:min-required-peers job t])))
+                         (get-in result [:min-required-peers job t] 1)))
                    tasks)
          result
          (update-in result [:allocations] dissoc job))))


be more explicit about kw to pass

be more explicit about kw to pass

--- src/open_company/representations/company.clj
+++ src/open_company/representations/company.clj
@@ -36,7 +36,7 @@

 (defn- company-links*
   "Return a list of links specified via the `links` argument.
-   If all possible links should be returned pass the namespaced `::all-links` keyword"
+   If all possible links should be returned pass `:open-company.representations.company/all-links`"
   [company links]
   {:pre [(or (sequential? links) (set? links) (= links ::all-links))]}
   (let [recognized-links #{:self :update :partial-update :delete :section-list}]


Moving Query functions to ReadTx

Moving Query functions to ReadTx

--- src/org/libraryweasel/ligature/core.clj
+++ src/org/libraryweasel/ligature/core.clj
@@ -33,10 +33,6 @@
     "Returns a ReadTx.")
   (write [this f]
     "Returns a ReadTx/WriteTx."))
-;  (sparql-query [this query]
-;    "")
-;  (wander-query [this query]
-;    ""))

 (defprotocol ReadTx
   (all-statements [this]
@@ -48,7 +44,13 @@
   (match-rules [this pattern]
     "Is passed a pattern and returns a channel with all matching rules.")
   (cancel [this]
-    "Cancels this transaction."))
+    "Cancels this transaction.")
+  (sparql-query [this query]
+    "Runs a SPARQL query in this transaction.
+    If a write is attempted in a read-only transaction and error will occur.")
+  (wander-query [this query]
+    "Runs a Wander query in this transaction.
+    If a write is attempted in a read-only transaction and error will occur."))

 (defprotocol WriteTx
   (new-identifier [this]


(PDB-2206) indexes not getting used for hash/uuid queries

Without this patch, equality queries on our bytea fields trigger full table
scans because we're doing type coercion on the left hand side of the
comparison. This adds expression indexes for those coercions to enable fast
queries.

--- src/puppetlabs/puppetdb/scf/migrate.clj
+++ src/puppetlabs/puppetdb/scf/migrate.clj
@@ -1464,6 +1464,29 @@
       (format "ALTER TABLE reports ADD COLUMN metrics %s DEFAULT NULL" jsonb-type)
       (format "ALTER TABLE reports ADD COLUMN logs %s DEFAULT NULL" jsonb-type)
       (format "ALTER TABLE reports ADD COLUMN resources %s DEFAULT NULL" jsonb-type))))
+
+(defn add-expression-indexes-for-bytea-queries
+  []
+  (if (sutils/postgres?)
+    (jdbc/do-commands
+      "CREATE UNIQUE INDEX reports_hash_expr_idx ON reports(trim(leading '\\x' from hash::text))"
+      "ALTER TABLE REPORTS DROP CONSTRAINT reports_hash_key"
+      "DROP INDEX reports_transaction_uuid_idx"
+      "CREATE INDEX reports_tx_uuid_expr_idx ON reports(CAST(transaction_uuid AS text))"
+
+      ;; leave the existing resources/rpc indices for resources-query join
+      "CREATE INDEX resources_hash_expr_idx ON catalog_resources(trim(leading '\\x' from resource::text))"
+      "CREATE INDEX rpc_hash_expr_idx ON resource_params_cache(trim(leading '\\x' from resource::text))"
+      "CREATE INDEX resource_params_hash_expr_idx ON resource_params(trim(leading '\\x' from resource::text))"
+
+      "CREATE UNIQUE INDEX catalogs_hash_expr_idx ON catalogs(trim(leading '\\x' from hash::text))"
+      "ALTER TABLE catalogs DROP CONSTRAINT catalogs_hash_key"
+      "DROP INDEX idx_catalogs_transaction_uuid"
+      "CREATE INDEX catalogs_tx_uuid_expr_idx ON catalogs(CAST(transaction_uuid AS text))"
+
+      "CREATE UNIQUE INDEX factsets_hash_expr_idx ON factsets(trim(leading '\\x' from hash::text))"
+      "ALTER TABLE factsets DROP CONSTRAINT factsets_hash_key")
+    nil))

 (def migrations
   "The available migrations, as a map from migration version to migration function."
@@ -1508,7 +1531,7 @@
    36 rename-environments-name-to-environment
    37 add-jsonb-columns-for-metrics-and-logs
    38 add-code-id-to-catalogs
-   })
+   39 add-expression-indexes-for-bytea-queries})

 (def desired-schema-version (apply max (keys migrations)))


(PDB-4895) Compute, store, and check catalog inputs hash

[rlb@puppet.com: augment commit message; speed up hashing a bit]

--- src/puppetlabs/puppetdb/scf/storage.clj
+++ src/puppetlabs/puppetdb/scf/storage.clj
@@ -870,17 +870,31 @@
                                   inputs)))

 (defn update-catalog-input-metadata!
-  [certid catalog-uuid last-updated]
+  [certid catalog-uuid last-updated inputs-hash]
   (jdbc/update! :certnames
-                {:catalog_inputs_uuid catalog-uuid :catalog_inputs_timestamp last-updated}
+                {:catalog_inputs_uuid catalog-uuid
+                 :catalog_inputs_timestamp last-updated
+                 :catalog_inputs_hash inputs-hash}
                 ["id = ?" certid]))

-(defn certname-id-and-timestamp [certname]
+(defn catalog-inputs-metadata [certname]
   (-> (jdbc/query (hcore/format
-                    {:select [:id :catalog_inputs_timestamp]
+                    {:select [:id :catalog_inputs_timestamp :catalog_inputs_hash]
                      :from [:certnames]
                      :where [:= :certname certname]}))
       first))
+
+(defn catalog-inputs-hash
+  [^String certname inputs]
+  (let [digest (MessageDigest/getInstance "SHA-1")]
+    (.update digest (.getBytes certname "UTF-8"))
+    (.update digest (byte 0))
+    (doseq [[^String type ^String name] inputs]
+      (.update digest (.getBytes type "UTF-8"))
+      (.update digest (byte 0))
+      (.update digest (.getBytes name "UTF-8"))
+      (.update digest (byte 0)))
+    (.digest digest)))

 (pls/defn-validated replace-catalog-inputs!
   [certname :- s/Str
@@ -890,12 +904,17 @@
   (jdbc/with-db-transaction []
     (let [updated (to-timestamp updated)
           catalog-uuid (sutils/munge-uuid-for-storage catalog_uuid)
-          {certid :id old-ts :catalog_inputs_timestamp} (certname-id-and-timestamp certname)]
+          {certid :id
+           old-ts :catalog_inputs_timestamp
+           ^bytes old-hash :catalog_inputs_hash} (catalog-inputs-metadata certname)]
       (when (or (nil? old-ts)
                 (before? (from-sql-date old-ts) (from-sql-date updated)))
-        (delete-catalog-inputs! certid)
-        (store-catalog-inputs! certid inputs)
-        (update-catalog-input-metadata! certid catalog-uuid updated)))))
+        (let [inputs (apply sorted-set inputs)
+              ^bytes new-hash (catalog-inputs-hash certname inputs)]
+          (when (not (Arrays/equals old-hash new-hash))
+            (delete-catalog-inputs! certid)
+            (store-catalog-inputs! certid inputs))
+          (update-catalog-input-metadata! certid catalog-uuid updated new-hash))))))

 ;; ## Database compaction


[FIX #2530] Create `catalog` variable on client-side.

Signed-off-by: Oskar Thoren <aeed71d78dc09e4764ceac69b111eee9b50cfdd0@oskarthoren.com>

--- src/status_im/native_module/impl/module.cljs
+++ src/status_im/native_module/impl/module.cljs
@@ -132,9 +132,15 @@
   (when status
     (call-module #(.discardTransaction status id))))

+(defn- append-catalog-init [js]
+    (str js "\n" "var catalog = JSON.stringify(_status_catalog); catalog;"))
+
 (defn parse-jail [bot-id file callback]
   (when status
-    (call-module #(.parseJail status bot-id file callback))))
+    (call-module #(.parseJail status
+                              bot-id
+                              (append-catalog-init file)
+                              callback))))

 (defn execute-call [{:keys [jail-id path params callback]}]
   (when status


Test multiple result display.

Test multiple result display.

--- test/ahnentafel/server/pages/search_test.clj
+++ test/ahnentafel/server/pages/search_test.clj
@@ -30,6 +30,23 @@
        "John /Doe"
        "(1 Jan 1970 - 1 Jan 2000)"))))

-(deftest multiple-results)
+(deftest multiple-results
+  (with-redefs [query/search
+                (fn [data query]
+                  [{:xref "@I1@"
+                    :name ["John /Doe"]
+                    :birth {:date "1 Jan 1970"}
+                    :death {:date "1 Jan 2000"}}
+                   {:xref "@I2@"
+                    :name ["Jane /Doe"]
+                    :birth {:date "2 Jan 1970"}
+                    :death {:date "2 Jan 2000"}}]
+                  )]
+    (let [page (get-page search "/Doe")]
+      (are-on-page
+       "2 records found for"
+       "John /Doe"
+       "Jane /Doe"))))
+
 (deftest result-with-multiple-names)
 (deftest with-missing-dates)


Adjust start value type check for threads endpoint and pass in the full read items list instead of only the list of read items.

--- src/oc/storage/api/activity.clj
+++ src/oc/storage/api/activity.clj
@@ -105,10 +105,10 @@
         follow-data (when follow?
                       (follow-parameters-map user-id (:slug org) following))
         read-data (when user-id
-                    (map :item-id (read/retrieve-by-user-org config/dynamodb-opts (:uuid org) user-id)))
+                    (read/retrieve-by-user-org config/dynamodb-opts (:uuid org) user-id))
         threads (entry-res/paginated-threads conn (:uuid org) allowed-boards user-id follow-data read-data order start direction config/default-activity-limit {})
         entries (entry-res/entries-list conn (:uuid org) (map :resource-uuid threads))
-        total-count (entry-res/paginated-threads conn (:uuid org) allowed-boards user-id follow-data [] :asc (c/to-long (t/now)) :before 0 {:count true})
+        total-count (entry-res/paginated-threads conn (:uuid org) allowed-boards user-id follow-data [] :asc (* (c/to-long (t/now)) 1000) :before 0 {:count true})
         result {:next-count (count threads)
                 :direction direction
                 :total-count total-count
@@ -319,7 +319,7 @@
   ;; Check the request
   :malformed? (fn [ctx] (let [ctx-params (keywordize-keys (-> ctx :request :params))
                               start (:start ctx-params)
-                              valid-start? (if start (try (Integer. start) (catch java.lang.NumberFormatException e false)) true)
+                              valid-start? (if start (try (Long. start) (catch java.lang.NumberFormatException e false)) true)
                               direction (keyword (:direction ctx-params))
                               ;; no direction is OK, but if specified it's from the allowed enumeration of options
                               valid-direction? (if direction (#{:before :after} direction) true)
@@ -344,7 +344,7 @@
                              org (:existing-org ctx)
                              org-id (:uuid org)
                              ctx-params (keywordize-keys (-> ctx :request :params))
-                             start-params (update ctx-params :start #(if % (Integer. %) (c/to-long (t/now)))) ; default is now
+                             start-params (update ctx-params :start #(if % (Long. %) (* (c/to-long (t/now)) 1000))) ; default is now
                              direction (or (#{:after} (keyword (:direction ctx-params))) :before) ; default is before
                              params (merge start-params {:direction direction})
                              boards (board-res/list-boards-by-org conn org-id board-props)


The completed delay seems unnecessary with further testing.

--- src/hatti/ona/stream.cljs
+++ src/hatti/ona/stream.cljs
@@ -4,7 +4,6 @@
             [cljsjs.oboe]))

 (def small-delay 10)
-(def big-delay 1000)

 (defn process-aggregated-data!
   "Calls callback on aggregated data that come via messages in channel.
@@ -17,8 +16,7 @@
        (when data (callback data completed?))
        ;; Timeout so browser can do some rendering before parsing again.
        (<! (timeout small-delay))
-       (when completed?
-         (close! agg-data-channel))))))
+       (when completed? (close! agg-data-channel))))))

 (defn read-next-chunk!
   "On each step of data, increment read-count atom, and put data in a list agg.


Removed spurious colon character

Removed spurious colon character

--- src/alfresco_technical_validation/source_validation.clj
+++ src/alfresco_technical_validation/source_validation.clj
@@ -46,7 +46,7 @@
                        content-index
                        :api05
                        "API05"
-                       "Bean injections other than ServiceRegistry:"
+                       "Bean injections other than ServiceRegistry"
                        true
                        "The technology does not perform bean injection."
                        #(if (empty? %) true nil)))


Updated unit test

Updated unit test

--- test/pe_apptxn_restsupport/resource_test.clj
+++ test/pe_apptxn_restsupport/resource_test.clj
@@ -129,7 +129,8 @@
               (is (= (:apptxn/user-agent-device-make apptxn-ent) "x86_64"))
               (is (= (:apptxn/user-agent-device-os apptxn-ent) "iPhone OS"))
               (is (= (:apptxn/user-agent-device-os-version apptxn-ent) "8.1"))
-              (let [apptxnlogs (apptxncore/apptxnlogs-for-apptxnid @conn apptxn-id)]
+              (let [apptxnlogs (apptxncore/apptxnlogs-for-apptxnid @conn apptxn-id)
+                    apptxnlogs (sort-by :apptxnlog/timestamp apptxnlogs)]
                 (is (= 2 (count apptxnlogs)))
                 (let [apptxnlog-entid (ffirst apptxnlogs)
                       apptxnlog-ent (d/entity (d/db @conn) apptxnlog-entid)]


(PDB-3282) Increase timeouts in threadpool_test

Try to work around CI slowness

--- test/puppetlabs/puppetdb/threadpool_test.clj
+++ test/puppetlabs/puppetdb/threadpool_test.clj
@@ -34,7 +34,7 @@
           (is (= [:done :a] (async/<!! out-chan)))
           (is (= 1 @counter))
           (async/close! in-chan)
-          (is (not= ::timed-out (deref fut 1000 ::timed-out)))
+          (is (not= ::timed-out (deref fut tu/default-timeout-ms ::timed-out)))
           (is (true? (future-done? fut)))))))

   (testing "message in-flight shutdown"
@@ -62,7 +62,7 @@

           (is (= [:done 1] (async/<!! out-chan)))

-          (is (not= ::timed-out (deref fut 1000 ::timed-out)))
+          (is (not= ::timed-out (deref fut tu/default-timeout-ms ::timed-out)))
           (is (true? (future-done? fut)))))))

   (testing "blocking put on gated threadpool"
@@ -90,10 +90,10 @@
                     (dochan gtp worker-fn in-chan))]

           (async/>!! in-chan {:id :a})
-          (is (= true (deref (:a in-flight-promises) 100 ::not-found)))
+          (is (= true (deref (:a in-flight-promises) tu/default-timeout-ms ::not-found)))

           (async/>!! in-chan {:id :b})
-          (is (= true (deref (:b in-flight-promises) 100 ::not-found)))
+          (is (= true (deref (:b in-flight-promises) tu/default-timeout-ms ::not-found)))

           (async/>!! in-chan {:id :c})
           (async/close! in-chan)
@@ -104,7 +104,7 @@
           (deliver (get stop-here :a) true)

           (is (= [:done :a] (async/<!! out-chan)))
-          (is (= true (deref (:c in-flight-promises) 100 ::not-found)))
+          (is (= true (deref (:c in-flight-promises) tu/default-timeout-ms ::not-found)))
           (is (= [:a :b :c] @seen))

           (deliver (get stop-here :b) true)
@@ -113,7 +113,7 @@
           (deliver (get stop-here :c) true)
           (is (= [:done :c] (async/<!! out-chan)))

-          (is (not= ::timed-out (deref fut 1000 ::timed-out)))
+          (is (not= ::timed-out (deref fut tu/default-timeout-ms ::timed-out)))
           (is (true? (future-done? fut))))))))


Change tests to use byte buffers

Change tests to use byte buffers

--- test/caesium/crypto/scalarmult_test.clj
+++ test/caesium/crypto/scalarmult_test.clj
@@ -2,6 +2,7 @@
   (:require [caesium.crypto.scalarmult :as s]
             [caesium.test-utils :refer [const-test]]
             [caesium.util :as u]
+            [caesium.byte-bufs :as bb]
             [clojure.test :refer [are deftest is testing]]))

 (const-test
@@ -39,7 +40,7 @@

 (deftest scalarmult-tests
   (testing "-to-buf! and regular API work identically"
-    (let [q (byte-array s/bytes)
+    (let [q (bb/alloc s/bytes)
           r (s/scalarmult scalar-1)]
       (s/scalarmult-to-buf! scalar-1 q)
       (is (u/array-eq r q))))


Removed SQL plugin

Removed SQL plugin


Put comment about docker / rlwrap bug back in

...with an update that it still exists even though the linked issue is closed.


bump blueprints dependency

bump blueprints dependency


Update figwheel

Update figwheel


Bump commons dep.

Bump commons dep.


lein-release plugin: bumped version from 0.114 to 0.115-SNAPSHOT for next development cycle


Add doc string to victorian/rude?.

Add doc string to victorian/rude?.

--- src/manners/victorian.clj
+++ src/manners/victorian.clj
@@ -34,7 +34,9 @@
   [etiquette value]
   (empty? (bad-manners etiquette value)))

-(def rude? (complement proper?))
+(def rude?
+  "The complement of manners.victorian/proper?"
+  (complement proper?))

 (defn falter
   "Throw an AssertionError when there are bad manners."


Simplify artifact_input component by passing owner object instead of callbacks.

--- src/cljs/hatnik/web/client/form/artifact_input.cljs
+++ src/cljs/hatnik/web/client/form/artifact_input.cljs
@@ -5,23 +5,27 @@
             [hatnik.schema :as schm]
             [schema.core :as s]))

-(defn library-check-handler [reply callback]
-  (let [resp (js->clj reply)]
-    (if (= "ok" (get resp "result"))
-      (callback "has-success" (get resp "version") nil)
-      (callback "has-error" nil nil))))
+(defn set-state [owner status version in-progress?]
+  (om/set-state! owner :form-status status)
+  (om/set-state! owner :version version)
+  (om/set-state! owner :request-in-progress? in-progress?))

-(defn check-input-value [data-handler check-handler started-handler timer new-val]
+(defn library-check-handler [reply owner]
+  (let [resp (js->clj reply)
+        status (if (= "ok" (get resp "result"))
+                 "has-success"
+                 "has-error")]
+    (set-state owner status (get resp "version") false)))
+
+(defn check-library-exists [owner timer library]
   (js/clearTimeout timer)
-  (check-handler
-   "has-warning"
-   nil
-   (js/setTimeout
-    (fn []
-      (started-handler)
-      (action/get-library new-val #(library-check-handler % check-handler)))
-    1000))
-  (data-handler new-val))
+  (set-state owner "has-warning" nil false)
+  (let [timer (js/setTimeout
+               (fn []
+                 (om/set-state! owner :request-in-progress? true)
+                 (action/get-library library #(library-check-handler % owner)))
+               1000)]
+    (om/set-state! owner :timer timer)))

 (defn artifact-input-component [data owner]
   (reify
@@ -45,17 +49,9 @@
                         :id "artifact-input"
                         :className "form-control"
                         :placeholder "e.g. org.clojure/clojure"
-                        :onChange #(check-input-value
-                                    (:handler data)
-                                    (fn [result version timer]
-                                      (om/set-state! owner :form-status result)
-                                      (om/set-state! owner :version version)
-                                      (om/set-state! owner :timer timer)
-                                      (om/set-state! owner :request-in-progress? false))
-                                    (fn []
-                                      (om/set-state! owner :request-in-progress? true))
-                                    (:timer state)
-                                    (.. % -target -value))
+                        :onChange #(let [library (.. % -target -value)]
+                                     (check-library-exists owner (:timer state) library)
+                                     ((:handler data) library))
                         :value (:value data)})
                (dom/span #js {:className "form-control-feedback"}
                  (cond (= (:form-status state) "has-error") "Not found"


Fix bug in parse-ns

Fix bug in parse-ns

foo.bar.baz is a perfectly valid libspec and can safely be filtered out
when looking for aliases

--- src/refactor_nrepl/analyzer.clj
+++ src/refactor_nrepl/analyzer.clj
@@ -25,7 +25,8 @@
                      (filter list?)
                      (some #(when (#{:require} (first %)) %))
                      rest
-                     (filter #(contains? (into #{} %) :as))
+                     (remove symbol?)
+                     (filter #(contains? (set %) :as))
                      (#(zipmap (map (partial get-alias nil) %)
                                (map first %))))]
     [(second ns-decl) aliases]))
@@ -35,7 +36,8 @@

 (defn- get-ast-from-cache
   [ns file-content]
-  (-> (get @ast-cache ns)
+  (-> @ast-cache
+      (get ns)
       (get (hash file-content))))

 (defn- update-ast-cache


replace deprecated s/either with s/if

replace deprecated s/either with s/if

--- src/io/sarnowski/swagger1st/schemas/swagger_2_0.clj
+++ src/io/sarnowski/swagger1st/schemas/swagger_2_0.clj
@@ -10,6 +10,9 @@

 (defn extension? [^String k]
   (.startsWith "x-" k))
+
+(defn ref? [x]
+  (get x "$ref"))

 (def primitives
   {"integer" s-long
@@ -140,8 +143,8 @@
   {s-string [s-string]})

 (def responses-object
-  {(s/optional-key "default")           (s/either response-object reference-object)
-   (s/either s-long s-string)               (s/either response-object reference-object)
+  {(s/optional-key "default")           (s/if ref? reference-object response-object)
+   (s/cond-pre s-long s-string)         (s/if ref? reference-object response-object)
    (s/optional-key (s/pred extension?)) s/Any})

 (def operation-object
@@ -153,7 +156,7 @@
    (s/optional-key "externalDocs")      external-documentation-object
    (s/optional-key "consumes")          [s-string]
    (s/optional-key "produces")          [s-string]
-   (s/optional-key "parameters")        [(s/either parameter-object reference-object)]
+   (s/optional-key "parameters")        [(s/if ref? reference-object parameter-object)]
    (s/optional-key "schemes")           [s-string]
    (s/optional-key "deprecated")        s-boolean
    (s/optional-key "security")          [security-requirement-object]
@@ -168,7 +171,7 @@
    (s/optional-key "options")           operation-object
    (s/optional-key "head")              operation-object
    (s/optional-key "patch")             operation-object
-   (s/optional-key "parameters")        [(s/either parameter-object reference-object)]
+   (s/optional-key "parameters")        [(s/if ref? reference-object parameter-object)]
    (s/optional-key (s/pred extension?)) s/Any})

 (def paths-object


Инверсия меню навигатора

Инверсия меню навигатора

--- radiolamp-6P3S/src/r6p3s/ui/nav.cljs
+++ radiolamp-6P3S/src/r6p3s/ui/nav.cljs
@@ -3,8 +3,9 @@

 (defn render [{:keys [brand
-                      brand-href]
-               :or   {brand      "IX"
+                      brand-href
+                      inverse?]
+               :or   {brand      "6П3С"
                       brand-href "#/"}}
               & body]
   (dom/nav #js {:className "navbar navbar-default navbar-fixed-top"}
@@ -24,5 +25,7 @@

                     (apply dom/div #js {:id        "navbar-collapse-1"
-                                        :className "collapse navbar-collapse"}
+                                        :className (if inverse?
+                                                     "collapse navbar-inverse-collapse"
+                                                     "collapse navbar-collapse")}
                            body))))