Remove unused code

Remove unused code

--- modules/menu/src/modular/menu.clj
+++ modules/menu/src/modular/menu.clj
@@ -9,24 +9,8 @@
    ;;[cylon.core :refer (allowed-handler?)]
    [schema.core :as s]))

-#_(defn show-menu-item?
-  "This is an example of how useful it is to wrap handlers in records
-  that implement the AuthorizedHandler protocol. In this case, we can
-  call authorized-handler? on any given handler to see whether it would
-  be authorized with this request. We use this result to avoid
-  displaying menu-items that are not available. We could alternatively
-  use this information to disable or grey-out the menu-item."
-  [req {:keys [handler label]}]
-  (allowed-handler? handler req))
-
 (defprotocol MenuItems
   (menu-items [_]))
-
-;; If there is a protection system... see accounting2 eae2f02 src/juxt/accounting/menu.clj
-#_(when-let [{:keys [handlers]} (-> this :protection-system :login-form)]
-                  [(if-not (:cylon.core/session req)
-                     {:label "Login" :order "Z" :handler (:login handlers)}
-                     {:label "Logout" :order "Z" :handler (:logout handlers)})])

 (defrecord MenuIndex []
   MenuItems


(TK-333) Improve comments and assertion in test

This rewords a comment to make it more obvious what is happening in
the test, and tweaks the test to make it less likely to yield a
false positive.

--- test/clj/puppetlabs/trapperkeeper/services/webserver/jetty9_service_test.clj
+++ test/clj/puppetlabs/trapperkeeper/services/webserver/jetty9_service_test.clj
@@ -757,12 +757,12 @@
                    {:webserver {:port 8080}})]
           (tk-app/stop app)
           (tk-app/stop app)))
-      ;; if we try to unregister the mbeans more than once Jetty will log a bunch
-      ;; of very loud and terrifying InstanceNotFoundExceptions
-      (let [log-event-filter #(and (= :warn (:level %))
-                                   (not (nil? (:exception %)))
-                                   (re-find #"InstanceNotFoundException"
-                                            (.getClassName (:exception %))))
+      ;; we previously had a bug where we could try to unregister mbeans multiple
+      ;; times if our tk-j9 stop lifecycle function was called more than once.
+      ;; in that case, Jetty would log tons of nasty exceptions at warning level.
+      ;; this test just validates that that is not happening.
+      (let [log-event-filter #(or (= :warn (:level %))
+                                  (= :error (:level %)))
             mbean-err-logs (->> @log-messages
                                 (map tk-log-testutils/event->map)
                                 (filter log-event-filter))]


Cause :protocol-impl-recur-with-target to be non-fatal

--- planck-cljs/script/build.clj
+++ planck-cljs/script/build.clj
@@ -11,13 +11,16 @@
     (transit/write writer cache)
     (spit (io/file out-path) (.toString out))))

+(def non-fatal-warnings #{:protocol-impl-recur-with-target})
+
 (cljs.analyzer/with-warning-handlers
   [(fn [warning-type env extra]
      (when (warning-type cljs.analyzer/*cljs-warnings*)
        (when-let [s (cljs.analyzer/error-message warning-type extra)]
          (binding [*out* *err*]
            (println "WARNING:" (cljs.analyzer/message env s)))
-         (System/exit 1))))]
+         (when-not (warning-type non-fatal-warnings)
+           (System/exit 1)))))]
   (api/build (api/inputs "src")
     {:output-dir         "out"
      :output-to          "out/main.js"


Better clojure testing

Better clojure testing

- Fast fails!
- Prints timing when successful

--- frameworks/clojure/clojure/test/codewars.clj
+++ frameworks/clojure/clojure/test/codewars.clj
@@ -1,24 +1,27 @@
 (ns clojure.test.codewars
+  (:refer-clojure :exclude [time])
   (:require
-   [clojure.test :refer :all]
+   [clojure.test :refer :all :exclude [run-all-tests]]
    [clojure.stacktrace :as stack]))

 (defmulti codewars-report :type)

 (defmethod codewars-report :pass [m]
-  (with-test-out
+  (with-test-out
     (when (seq *testing-contexts*)
       (->> (testing-contexts-str) (str "<IT::>") println))
     (-> "<PASSED::>Test Passed" println with-test-out)))

 (defmethod codewars-report :fail [m]
-  (with-test-out
+  (with-test-out
     (when (seq *testing-contexts*)
       (->> (testing-contexts-str) (str "<IT::>") println))
     (print "<FAILED::>")
     (when-let [message (:message m)] (print message "- "))
     (print "expected:" (pr-str (:expected m)))
-    (println " actual:" (pr-str (:actual m)))))
+    (println " actual:" (pr-str (:actual m))))
+  (flush)
+  (System/exit 1))

 (defmethod codewars-report :error [m]
   (with-test-out
@@ -31,14 +34,32 @@
     (let [actual (:actual m)]
       (if (instance? Throwable actual)
         (stack/print-cause-trace actual *stack-trace-depth*)
-        (prn actual)))))
+        (prn actual))))
+  (flush)
+  (System/exit 1))

 (defmethod codewars-report :begin-test-ns [_])
 (defmethod codewars-report :end-test-ns [_])

 (defmethod codewars-report :begin-test-var [m]
-  (with-test-out
+  (with-test-out
     (print "<DESCRIBE::>")
     (-> m :var (. sym) println)))
 (defmethod codewars-report :end-test-var [_])
+
 (defmethod codewars-report :summary [_])
+
+(defmacro time
+  "Evaluates expr and prints the time it took.  Returns the value of expr."
+  [expr]
+  `(let [start# (System/nanoTime)
+         ret# ~expr]
+     (println (str "<COMPLETEDIN::>"
+                   (/ (double (- (System/nanoTime) start#)) 1000000.0)
+                   " msecs"))
+     ret#))
+
+(defmacro run-all-tests []
+  (binding [clojure.test/report
+            clojure.test.codewars/codewars-report]
+    (time (clojure.test/run-all-tests))))


refine morphological rules

refine morphological rules

--- src/babel/english/morphology.cljc
+++ src/babel/english/morphology.cljc
@@ -50,22 +50,26 @@

 (defn present-participle-of [stem]
   (cond
+
     (re-find #"ie$" stem)
     (str (replace stem #"..$" "y") "ing")

     (re-find #"..e$" stem) ;; "..": avoid matching two-letter word "be"
     (str (replace stem #"e$" "") "ing")

-    (re-find #"m$" stem)
+    (re-find #"[eu]m$" stem)
     (str (replace stem #"m$" "mm") "ing")
+
+    (re-find #"[ou]p$" stem)
+    (str (replace stem #"p$" "pp") "ing")

-    (re-find #"up$" stem)
-    (str (replace stem #"up$" "upp") "ing")
-
-    (re-find #"n$" stem)
+    (re-find #"[a]n$" stem)
     (str (replace stem #"n$" "nn") "ing")

-    (re-find #"t$" stem)
+    (re-find #"[ou]b$" stem)
+    (str (replace stem #"b$" "bb") "ing")
+
+    (re-find #"[eou]t$" stem)
     (str (replace stem #"t$" "tt") "ing")

     true


fix docstring indentation in doc gen

fix docstring indentation in doc gen

--- get-symbol-metadata/src/core.clj
+++ get-symbol-metadata/src/core.clj
@@ -81,6 +81,36 @@
   (get-forms-from-file (get-repo-path ns- repo file)))

 ;;------------------------------------------------------------
+;; Docstring Indentation Fix
+;;------------------------------------------------------------
+
+(defn get-docstring-indent
+  [docstring]
+  (let [lines (split-lines docstring)]
+    (if (> (count lines) 1)
+      (let [[first-line & indented-lines] lines
+            get-indent-length #(count (re-find #"^ *" %))
+            has-content? #(pos? (count (trim %)))]
+        (->> indented-lines
+             (filter has-content?)
+             (map get-indent-length)
+             (apply min 3)))
+      0)))
+
+(defn fix-docstring
+  [docstring]
+  (let [indent-length (get-docstring-indent docstring)]
+    (if (zero? indent-length)
+      docstring
+      (let [[first-line & indented-lines] (split-lines docstring)
+            indent (re-pattern (str "^ {" indent-length "}"))
+            remove-indent #(replace % indent "")]
+        (->> indented-lines
+             (map remove-indent)
+             (cons first-line)
+             (join "\n"))))))
+
+;;------------------------------------------------------------
 ;; Form Parsing
 ;;------------------------------------------------------------

@@ -89,7 +119,8 @@
   (let [fn-or-macro ({'defn "function" 'defmacro "macro"} (first form))
         docstring (when fn-or-macro
                     (let [ds (nth form 2)]
-                      (when (string? ds) ds)))
+                      (when (string? ds)
+                        (fix-docstring ds))))
         m (meta form)
         lines [(:line m) (:end-line m)]
         num-lines (inc (- (:end-line m) (:line m)))


day 05

day 05

--- 2019/src/day05.clj
+++ 2019/src/day05.clj
@@ -3,3 +3,87 @@
             [clojure.java.io :as io]))

 (def input (into [] (map read-string (str/split (slurp (io/file (io/resource "day5.txt"))) #","))))
+
+(defn get-val [state pos mode]
+  (if (= mode "0")
+    (get state (get state pos) :not-found)
+    (get state pos :not-found)))
+
+(defn parse-instruction [s]
+  (let [[_ m3 m2 m1 op] (re-find #"(\d)(\d)(\d)(\d\d)" (format "%05d" s))]
+    {:op    op
+     :mode1 m1
+     :mode2 m2
+     :mode3 m3}))
+
+
+(defn run-program [init-state input debug?]
+  (loop [state init-state
+         pos 0]
+    (let [{:keys [op mode1 mode2 mode3]} (parse-instruction (get state pos))]
+      (when debug?
+        (println (list state
+                       pos
+                       op
+                       (get-val state (+ pos 1) "1")
+                       (get-val state (+ pos 1) mode1)
+                       (get-val state (+ pos 2) "1")
+                       (get-val state (+ pos 2) mode2)
+                       (get-val state (+ pos 3) "1")
+                       (get-val state (+ pos 3) mode3))))
+
+      (case op
+        "99" (get state 0)
+        ;; add
+        "01" (recur (assoc state (get state (+ pos 3))
+                                 (+ (get-val state (+ pos 1) mode1) (get-val state (+ pos 2) mode2)))
+                    (+ pos 4))
+        ;; multiply
+        "02" (recur (assoc state (get state (+ pos 3))
+                                 (* (get-val state (+ pos 1) mode1) (get-val state (+ pos 2) mode2)))
+                    (+ pos 4))
+        ;; read input
+        "03" (recur (assoc state (get state (+ pos 1)) input)
+                    (+ pos 2))
+        ;; print
+        "04" (do
+              (println (get-val state (+ pos 1) mode1))
+              (recur state (+ pos 2)))
+        ;; jump-if-true
+        "05" (recur state
+                    (if (zero? (get-val state (+ pos 1) mode1))
+                      (+ pos 3)
+                      (get-val state (+ pos 2) mode2)))
+        ;; jump-if-false
+        "06" (recur state
+                    (if (zero? (get-val state (+ pos 1) mode1))
+                      (get-val state (+ pos 2) mode2)
+                      (+ pos 3)))
+        ;; less than
+        "07" (recur (assoc state (get state (+ pos 3))
+                                 (if (< (get-val state (+ pos 1) mode1)
+                                        (get-val state (+ pos 2) mode2))
+                                   1
+                                   0))
+                    (+ pos 4))
+        ;; equals
+        "08" (recur (assoc state (get state (+ pos 3))
+                                 (if (= (get-val state (+ pos 1) mode1)
+                                        (get-val state (+ pos 2) mode2))
+                                   1
+                                   0))
+                    (+ pos 4))))))
+
+
+; (println (run-program [1101 100 -1 4 0 99] 1))
+; (run-program [3,9,8,9,10,9,4,9,99,-1,8] 8) ;; 1
+; (run-program [3,9,8,9,10,9,4,9,99,-1,8] 1) ;; 0
+; (run-program [3,12,6,12,15,1,13,14,13,4,13,99,-1,0,1,9] 0 true) ;; 0
+; (run-program [3,12,6,12,15,1,13,14,13,4,13,99,-1,0,1,9] 2 true) ;; 1
+; (run-program [3,3,1105,-1,9,1101,0,0,12,4,12,99,1] 0 true) ;; 0
+; (run-program [3,3,1105,-1,9,1101,0,0,12,4,12,99,1] 3 true) ;; 1
+
+;; part 1
+(run-program input 1 false)
+;; part 2
+(run-program input 5 false)


add note about original-obj

add note about original-obj

--- src/clj/com/rpl/specter/impl.cljc
+++ src/clj/com/rpl/specter/impl.cljc
@@ -603,6 +603,9 @@
 (defn dynamic-var? [v]
   (-> v meta :dynamic))

+;; original-obj stuff is done to avoid using functions with metadata on them
+;; clojure's implementation of function metadata causes the function to do an
+;; apply for every invocation
 (defn direct-nav-obj [o]
   (vary-meta o merge {:direct-nav true :original-obj o}))


Extracts spectating check function.

Extracts spectating check function.

--- src/cljs/netrunner/gameboard.cljs
+++ src/cljs/netrunner/gameboard.cljs
@@ -64,6 +64,9 @@
 (defn send [msg]
   (.emit socket "netrunner" (clj->js msg)))

+(defn not-spectator? [game-state app-state]
+  (#{(get-in @game-state [:corp :user]) (get-in @game-state [:runner :user])} (:user @app-state)))
+
 (defn send-command
   ([command] (send-command command nil))
   ([command args]
@@ -109,7 +112,7 @@
 (defn handle-card-click [{:keys [type zone counter advance-counter advancementcost advanceable
                                  root] :as card} owner]
   (let [side (:side @game-state)]
-    (when (#{(get-in @game-state [:corp :user]) (get-in @game-state [:runner :user])} (:user @app-state))
+    (when (not-spectator? game-state app-state)
       (if (= (get-in @game-state [side :prompt 0 :prompt-type]) "select")
         (send-command "select" {:card card})
         (if (and (= (:type card) "Identity") (= side (keyword (.toLowerCase (:side card)))))
@@ -277,7 +280,7 @@
      (sab/html
       [:div.card-frame
        [:div.blue-shade.card {:class (when selected "selected")
-                              :draggable (when (#{(get-in @game-state [:corp :user]) (get-in @game-state [:runner :user])} (:user @app-state)) true)
+                              :draggable (when (not-spectator? game-state app-state) true)
                               :on-drag-start #(handle-dragstart % cursor)
                               :on-drag-end #(-> % .-target js/$ (.removeClass "dragged"))
                               :on-mouse-enter #(when (or (not (or flipped facedown))
@@ -654,8 +657,7 @@
                [:div
                 (om/build rfg-view {:cards (:rfg opponent) :name "Removed from the game"})
                 (om/build rfg-view {:cards (:rfg me) :name "Removed from the game"})
-                (when (#{(get-in @game-state [:corp :user]) (get-in @game-state [:runner :user])} (:user @app-state))
-                  (om/build rfg-view {:cards (:play-area me)}))
+                (when (not-spectator? game-state app-state) (om/build rfg-view {:cards (:play-area me)}))
                 (om/build rfg-view {:cards (:current opponent) :name "Current"})
                 (om/build rfg-view {:cards (:current me) :name "Current"})]
                (when-not (= side :spectator)


Netrunner symbols support in prompt buttons

--- src/cljs/netrunner/gameboard.cljs
+++ src/cljs/netrunner/gameboard.cljs
@@ -506,7 +506,8 @@
                      [:h4 {:dangerouslySetInnerHTML #js {:__html (add-symbols (:msg prompt))}}]
                      (for [c (:choices prompt)]
                        (if (string? c)
-                         [:button {:on-click #(send-command "choice" {:choice c})} c]
+                         [:button {:on-click #(send-command "choice" {:choice c})
+                                   :dangerouslySetInnerHTML #js {:__html (add-symbols c)}}]
                          [:button {:on-click #(send-command "choice" {:card @c})} (:title c)]))]
                     (if run
                       (let [s (:server run)


factorize count

factorize count

--- stuf/src/sandbox/4clojure.clj
+++ stuf/src/sandbox/4clojure.clj
@@ -1300,5 +1300,6 @@

 ;;152 Latin Square Slicing
 (defn lsqr? [sq]
-  (and (= (count sq) (count (first sq)))
-       (= (count sq) (count (reduce into #{} sq)))))
+  (let [cnt (count sq)]
+    (and (= cnt (count (first sq)))
+         (= cnt (count (reduce into #{} sq))))))


rm emacs tmp file

rm emacs tmp file


Fix undo issue

Fix undo issue

--- src/clojure/nightcode/editors.clj
+++ src/clojure/nightcode/editors.clj
@@ -396,11 +396,13 @@
                          (.getKeyCode e))
               (mwm/update-cursor-position! edit-history (get-cursor-position text-area))

-              (not (or (contains? #{KeyEvent/VK_SHIFT KeyEvent/VK_CONTROL
-                                    KeyEvent/VK_ALT KeyEvent/VK_META}
-                                  (.getKeyCode e))
-                       (.isControlDown e)
-                       (.isMetaDown e)))
+              (and (or (.isControlDown e) (.isMetaDown e))
+                (= (.getKeyCode e) KeyEvent/VK_V))
+              (->> (get-parinfer-state text-area true)
+                   (refresh-content! text-area)
+                   (mwm/update-edit-history! edit-history))
+
+              :else
               (->> (cond
                      (= (.getKeyCode e) KeyEvent/VK_ENTER)
                      (get-normal-state text-area)
@@ -408,12 +410,6 @@
                      (get-indent-state text-area (.isShiftDown e))
                      :else
                      (get-parinfer-state text-area false))
-                   (refresh-content! text-area)
-                   (mwm/update-edit-history! edit-history))
-
-              (and (or (.isControlDown e) (.isMetaDown e))
-                (= (.getKeyCode e) KeyEvent/VK_V))
-              (->> (get-parinfer-state text-area true)
                    (refresh-content! text-area)
                    (mwm/update-edit-history! edit-history))))
           (keyTyped [this e] nil)


Improve `wrap-sink` docstring.

Improve `wrap-sink` docstring.

--- src/clojure/parkour/mapreduce.clj
+++ src/clojure/parkour/mapreduce.clj
@@ -158,7 +158,11 @@

 (defn wrap-sink
   "Return new tuple sink which wraps keys and values as the types
-`ckey` and `cval` respectively."
+`ckey` and `cval` respectively, which should be compatible with the
+key and value type of `sink`.  Where they are not compatible, the type
+of the `sink` will be used instead.  Returns a new tuple sink which
+wraps any sunk keys and values which are not already of the correct
+type then sinks them to `sink`."
   [ckey cval sink]
   (let [conf (conf/ig sink)
         ckey (wrapper-class ckey (key-class sink)),


Two tests in test-calendar module

Two tests in test-calendar module

--- test/clouseau/test_calendar.clj
+++ test/clouseau/test_calendar.clj
@@ -160,10 +160,24 @@
             (is (= "2000-02-01 10:20"  (format-date-using-desired-format calendar "yyyy-MM-dd hh:mm")))
             (is (= "2000-02-01 10:20:30"  (format-date-using-desired-format calendar "yyyy-MM-dd hh:mm:ss"))))))

-(deftest test-format-date-time
+(deftest test-format-date-time-1
     "Check the function clouseau.calendar/format-date-time"
     (testing "the function clouseau.calendar/format-date-time"
         (let [calendar (get-calendar)]
             (.set calendar 2000 01 01 10 20 30)
             (is (= "2000-02-01 10:20:30" (format-date-time calendar))))))

+(deftest test-format-date-time-2
+    "Check the function clouseau.calendar/format-date-time"
+    (testing "the function clouseau.calendar/format-date-time"
+        (let [calendar (get-calendar)]
+            (.set calendar 2000 00 01 10 20 30)
+            (is (= "2000-01-01 10:20:30" (format-date-time calendar))))))
+
+(deftest test-format-date-time-3
+    "Check the function clouseau.calendar/format-date-time"
+    (testing "the function clouseau.calendar/format-date-time"
+        (let [calendar (get-calendar)]
+            (.set calendar 2000 00 31 10 20 30)
+            (is (= "2000-01-31 10:20:30" (format-date-time calendar))))))
+


Fixed build failure.

Fixed build failure.

--- test/cmr/spatial/test/point.clj
+++ test/cmr/spatial/test/point.clj
@@ -205,7 +205,7 @@
     (let [[l1 l2] (p/order-longitudes lon1 lon2)]
       (and
         ;; should have original values
-        (= #{l1 l2} #{lon1 lon2})
+        (= (hash-set l1 l2) (hash-set lon1 lon2))
         ;; should stay in order
         (= [l1 l2] (p/order-longitudes l1 l2))
         ;; should be put back in the right order


benutzer pass geloescht...

benutzer pass geloescht...

--- src/hello_world/core.clj
+++ src/hello_world/core.clj
@@ -37,12 +37,12 @@
            :subname (str "//" db-host ":" db-port "/" db-name)
            ; Any additional keys are passed to the driver
            ; as driver-specific properties.
-           :user "johorst"
-           :password "666jojojo"}))
+           :user ""
+           :password ""}))
 ;geht:
-(j/insert! mysql-db :konten
-           {:Kontonummer 11 :Kontostand 31}
-           {:Kontonummer 12 :Kontostand 11})
+;(j/insert! mysql-db :konten
+;           {:Kontonummer 11 :Kontostand 31}
+;           {:Kontonummer 12 :Kontostand 11})

 (run-jetty app {:port 8080})


Fix test name

Fix test name

--- test/onyx/metrics/send_test.clj
+++ test/onyx/metrics/send_test.clj
@@ -1,4 +1,4 @@
-(ns onyx.metrics.throughput-test
+(ns onyx.metrics.send-test
   (:require [clojure.core.async :refer [chan >!! <!! close! sliding-buffer]]
             [clojure.test :refer [deftest is testing]]
             [onyx.plugin.core-async :refer [take-segments!]]
@@ -98,7 +98,7 @@
                                :riemann/address "localhost"
                                :riemann/port 12201
                                :metrics/sender-fn sender
-                               :lifecycle/doc "Instruments a task's throughput metrics"}
+                               :lifecycle/doc "Instruments a task's metrics"}

                               {:lifecycle/task :out
                                :lifecycle/calls ::out-calls}


Commenting testing behavior.

Commenting testing behavior.

--- test/poky/kv/jdbc/util_test.clj
+++ test/poky/kv/jdbc/util_test.clj
@@ -24,7 +24,12 @@
          (jdbc-set @@S bucket "key" "value") => (contains {:result "updated"})
          (jdbc-set @@S bucket "key" "value"
                    (tc/to-sql-date (t/plus (t/now) (t/days 1)))) => (contains {:result "updated"})
+
+         ; unconditionally accept a set without a modified
          (jdbc-set @@S bucket "key" "value") => (contains {:result "updated"})
+
+         ; the modified_at should be 1 day in the future. this should be
+         ; rejected
          (jdbc-set @@S bucket "key" "value"
                    (tc/to-sql-date (t/now))) => (contains {:result "rejected"}))


[scamp] remove unused destructuring

[scamp] remove unused destructuring

--- modules/scamp/src/scamp/core.clj
+++ modules/scamp/src/scamp/core.clj
@@ -456,7 +456,7 @@
   2.2.1 Subscription: Algorithm 1"
   [_message-type :- MessageTypesSchema
    {:keys [logging connection-redundancy] :as cluster-config}
-   {:keys [downstream] :as node} :- NetworkedNodeSchema
+   node :- NetworkedNodeSchema
    subscription :- SubscriptionSchema
    _envelope-id :- MessageEnvelopeIdSchema]
   (timbre/log* logging :trace


[scamp] add TODO for handling unknown message types in future

--- modules/scamp/src/scamp/core.clj
+++ modules/scamp/src/scamp/core.clj
@@ -217,6 +217,8 @@
   [& args]
   (let [[_message-type {:keys [logging]} & _rest] args]
     (if logging
+      ;; TODO: If an unknown message type is received, gracefully shut
+      ;; down to allow restart with an upgrade?
       (timbre/log* logging :error
                    :receive-msg-unknown-message-type
                    :args args)


Tweak autogenerated docstrs for defsetting :page_facing_up:

--- src/metabase/models/setting.clj
+++ src/metabase/models/setting.clj
@@ -143,7 +143,9 @@
                (s/upper-case (s/replace (name symb) #"-" "_")))
        "Clear its value by calling\n\n"
        (format "    (%s nil)\n\n" symb)
-       (format "Its default value is `%s`." default-value)))
+       (format "Its default value is `%s`." (if (nil? default-value)
+                                              "nil"
+                                              default-value))))

 (defmacro defsetting
   "Defines a new `Setting` that will be added to the DB at some point in the future.


Removes println

Removes println

--- src/hundred_pushups/ios/core.cljs
+++ src/hundred_pushups/ios/core.cljs
@@ -147,7 +147,6 @@
          :do-pushup-test [do-pushup-test]
          :do-plank-test [do-plank-test]
          :show-day (let [day @(subscribe [:days-exercise])]
-                     (prn "day ------------" day)
                      (if (= day :exr/do-test)
                        [do-pushup-test]
                        [show-day day]))


Fix crash in test scenario.

Fix crash in test scenario.

--- src/hypernova/activities/test.clj
+++ src/hypernova/activities/test.clj
@@ -13,7 +13,7 @@
 (defn station-destroyed []
   "called when the artifact station is destroyed"
   (cond
-   (active? @invaders)
+   (and @invaders (active? @invaders))
    (do
      (message "$@%# invaders!")
      (add-destruct-handler @invaders


Extract vol.

Extract vol.

--- src/klangmeister/instruments.cljs
+++ src/klangmeister/instruments.cljs
@@ -2,7 +2,6 @@
   (:require [klangmeister.music :as music]))

 (defonce context (js/window.AudioContext.))
-

 (defn perc [at attack decay]
   (let [node (.createGain context)]
@@ -11,6 +10,15 @@
       (.linearRampToValueAtTime 1 (+ at attack))
       (.linearRampToValueAtTime 0 (+ at attack decay)))
     node))
+
+(defn connect [& [a b & nodes]]
+  (when b
+    (.connect a b)
+    (apply connect (cons b nodes))))
+
+(defn vol [x]
+  (doto (.createGain context)
+    (-> .-gain .-value (set! x))))

 (defn bell! [midi start dur]
   (let [freq (music/equal-temperament midi)
@@ -36,11 +44,6 @@
     (harmonic 4.1 0.25)
     (harmonic 5.2 0.2)))

-(defn connect [& [a b & nodes]]
-  (when b
-    (.connect a b)
-    (apply connect (cons b nodes))))
-
 (defn fuzz! [midi start dur]
   (let [freq (music/equal-temperament midi)
         start (+ start (.-currentTime context))
@@ -51,4 +54,4 @@
       (-> .-type  (set! "sawtooth"))
       (.start start)
       (.stop (+ start 1.5))
-      (connect envelope (.-destination context)))))
+      (connect (vol 0.8) envelope (.-destination context)))))


Add test for show-help in interactive mode

--- test/app/test/interactive.clj
+++ test/app/test/interactive.clj
@@ -12,6 +12,16 @@
                (verify-call-times-for println 1)
                (verify-first-call-args-for println "Exit...")))))

+(deftest shows-help
+  (let [command-sequence ["help" "quit"]
+        input-string (clojure.string/join "\r" command-sequence)]
+    (with-in-str
+      input-string
+      (mocking [println print flush]
+               (interactive [])
+               (verify-call-times-for println 2)
+               (verify-first-call-args-for println help-message)))))
+
 (deftest list-shows-error-if-no-classes-loaded
   (let [command-sequence ["list" "quit"]
         input-string (clojure.string/join "\r" command-sequence)]


latest few tests

latest few tests

--- test/cljs/cljs/core_test.cljs
+++ test/cljs/cljs/core_test.cljs
@@ -2370,6 +2370,37 @@
   (assert (= (sequence (flatmap reverse) [[3 2 1 0] [6 5 4] [9 8 7]])
              (range 10)))
   (assert (= (seq (iteration (map inc) [1 2 3])) '(2 3 4)))
+  (assert (= (sequence (partition-by #{:split}) [1 2 3 :split 4 5 6])
+             '([1 2 3] [:split] [4 5 6])))
+  (assert (= (sequence (partition-all 3) '(1 2 3 4 5))
+             '([1 2 3] [4 5])))
+  (assert (= (sequence (keep identity) [1 nil 2 nil 3])
+             '(1 2 3)))
+  (assert (= (keep-indexed identity [:foo nil :bar nil :baz])
+             (sequence (keep-indexed identity) [:foo nil :bar nil :baz])))
+
+  (def xform
+    (comp (map inc)
+      (filter even?)
+      (dedupe)
+      (flatmap range)
+      (partition-all 3)
+      (partition-by #(< (apply + %) 7))
+      (flatmap flatten)
+      (random-sample 1.0)
+      (take-nth 1)
+      (keep #(when (odd? %) (* % %)))
+      (keep-indexed #(when (even? %1) (* %1 %2)))
+      (replace {2 "two" 6 "six" 18 "eighteen"})
+      (take 11)
+      (take-while #(not= 300 %))
+      (drop 1)
+      (drop-while string?)
+      (remove string?)))
+  (def data (vec (interleave (range 18) (range 20))))
+
+  (assert (= (sequence xform data)
+             '(36 200 10)))

   :ok
   )


a bunch more cljs test impls

a bunch more cljs test impls

--- test/deferst/system_test.cljc
+++ test/deferst/system_test.cljc
@@ -230,29 +230,41 @@
                               [:a ff {:a-arg [:foo]}]])
         sys (s/start-system! sb {:foo 10})
         sysmap (s/system-map sys)
-        stop-sys (s/stop-system! sys)]
+        stop-sys (s/stop-system! sys)
+        x-sysmap {:foo 10 :a {:a-arg 10} :b {:b-arg 10}}
+        x-dvals [{:b-arg 10} {:a-arg 10}]]

     (testing "dependent items are created"
       #?(:clj
-         (is (= @(s/system-map sys)
-                {:foo 10
-                 :a {:a-arg 10}
-                 :b {:b-arg 10}}))))
+         (is (= @sysmap x-sysmap))
+
+         :cljs
+         (t/async
+          done
+          (p/then
+           sysmap
+           (fn [v] (is (= v x-sysmap))
+             (done))))))

     (testing "dependent items were destroyed"
       #?(:clj
-         (is (= @destructor-vals
-                [{:b-arg 10}
-                 {:a-arg 10}]))))))
+         (is (= @destructor-vals x-dvals))
+
+         :cljs
+         (t/async
+          done
+          (p/then
+           stop-sys
+           (fn [_] (is (= @destructor-vals x-dvals))
+             (done))))))))

 (deftest dependent-item-system-with-circular-deps
   (let [ff (fn [v] v)]
-    #?(:clj
-       (is (thrown-with-msg?
-            clojure.lang.ExceptionInfo
-            #"circular dependency"
-            (s/system-builder [[:a ff {:a-arg [:b :b-arg]}]
-                               [:b ff {:b-arg [:a :a-arg]}]]))))))
+    (is (thrown-with-msg?
+         #?(:clj clojure.lang.ExceptionInfo :cljs :default)
+         #"circular dependency"
+         (s/system-builder [[:a ff {:a-arg [:b :b-arg]}]
+                            [:b ff {:b-arg [:a :a-arg]}]])))))

 (deftest dependent-item-system-with-vector-arg-specs
   (let [destructor-vals (atom [])
@@ -261,20 +273,34 @@
                               [:b ff {:b-arg [:a]}]])
         sys (s/start-system! sb {:foo 10})
         sysmap (s/system-map sys)
-        stop-sys (s/stop-system! sys)]
+        stop-sys (s/stop-system! sys)
+        x-sysmap {:foo 10 :a 10 :b {:b-arg 10}}
+        x-dvals [{:b-arg 10} 10]]

     (testing "dependent items are created"
       #?(:clj
-         (is (= @(s/system-map sys)
-                {:foo 10
-                 :a 10
-                 :b {:b-arg 10}}))))
+         (is (= @sysmap
+                x-sysmap))
+
+         :cljs
+         (t/async
+          done
+          (p/then
+           sysmap
+           (fn [v] (is (= v x-sysmap))
+             (done))))))

     (testing "dependent items were destroyed"
       #?(:clj
-         (is (= @destructor-vals
-                [{:b-arg 10}
-                 10]))))))
+         (is (= @destructor-vals x-dvals))
+
+         :cljs
+         (t/async
+          done
+          (p/then
+           stop-sys
+           (fn [_] (is (= @destructor-vals x-dvals))
+             (done))))))))

 (deftest dependent-item-system-with-mixed-destructors
   (let [destructor-vals (atom [])
@@ -283,19 +309,33 @@
                               [:b ff {:b-arg [:a :a-arg]}]])
         sys (s/start-system! sb {:foo 10})
         sysmap (s/system-map sys)
-        stop-sys (s/stop-system! sys)]
+        stop-sys (s/stop-system! sys)
+        x-sysmap {:foo 10 :a {:a-arg 10} :b {:b-arg 10}}
+        x-dvals [{:b-arg 10}]]

     (testing "dependent items are created"
       #?(:clj
-         (is (= @(s/system-map sys)
-                {:foo 10
-                 :a {:a-arg 10}
-                 :b {:b-arg 10}}))))
+         (is (= @sysmap x-sysmap))
+
+         :cljs
+         (t/async
+          done
+          (p/then
+           sysmap
+           (fn [v] (is (= v x-sysmap))
+             (done))))))

     (testing "dependent items were destroyed"
       #?(:clj
-         (is (= @destructor-vals
-                [{:b-arg 10}]))))))
+         (is (= @destructor-vals x-dvals))
+
+         :cljs
+         (t/async
+          done
+          (p/then
+           stop-sys
+           (fn [_] (is (= @destructor-vals x-dvals))
+             (done))))))))

 (deftest composed-builders
   (let [destructor-vals (atom [])


Streamlined tf-by-doc. Cleaned up other cruft.

--- test/flambo/example/tfidf.clj
+++ test/flambo/example/tfidf.clj
@@ -10,27 +10,21 @@
 (def stopwords #{"a" "all" "and" "any" "are" "is" "in" "of" "on"
                  "or" "our" "so" "this" "the" "that" "to" "we"})

-;; Returns a seq of (doc_id, term) tuples
-(f/defsparkfn gen-docid-term-tuples [x]
-  (let [[doc-id content] x
-        terms (clojure.string/split content #" ")]
-    (map (fn [term] [doc-id term]) terms)))
+;; Returns a stopword filtered seq of
+;; [doc-id term term-frequency doc-terms-count] tuples
+(f/defsparkfn gen-docid-term-tuples [doc-tuple]
+  (let [[doc-id content] doc-tuple
+        terms (filter #(not (contains? stopwords %))
+                      (clojure.string/split content #" "))
+        doc-terms-count (count terms)
+        term-frequencies (frequencies terms)]
+    (map (fn [term] [doc-id term (term-frequencies term) doc-terms-count])
+         (distinct terms))))

-;; Filters (doc_id, term) tuples if term is a stopword
-(f/defsparkfn filter-stopwords
-  [[_ term]]
-  (not (contains? stopwords term)))
-
-;; Returns a seq of term-frequency tuples: (term, (doc_id, tf))
-(f/defsparkfn term-freq-per-doc
-  [[doc-id term-freq-seq]]
-  (let [terms-count (reduce (fn [accum [_ term-freq]]
-                              (+ accum term-freq))
-                            0
-                            term-freq-seq)]
-    (map (fn [[term term-freq]]
-           [term [doc-id (double (/ term-freq terms-count))]])
-         term-freq-seq)))
+(defn calc-idf [doc-count]
+  (f/fn [[term tuple-seq]]
+    (let [df (count tuple-seq)]
+      [term (Math/log (/ doc-count (+ 1.0 df)))])))

 (defn -main [& args]
   (try
@@ -50,19 +44,16 @@

           doc-data (f/parallelize sc documents)

-          ;; stopword filtered RDD of (document_id, term) tuples
+          ;; stopword filtered RDD of [doc-id term term-freq doc-terms-count] tuples
           doc-term-seq (-> doc-data
                            (f/flat-map gen-docid-term-tuples)
-                           (f/filter filter-stopwords)
                            f/cache)

-          ;; tf per document, that is, tf(term, document)
+          ;; RDD of term-frequency tuples: [term [doc-id tf]]
+          ;; where tf is per document, that is, tf(term, document)
           tf-by-doc (-> doc-term-seq
-                        (f/group-by (f/fn [[doc-id term]] [doc-id term]))
-                        ;; (raw) number of times a term appears in a document
-                        (f/map (f/fn [[[doc-id term] val-seq]] [doc-id [term (count val-seq)]]))
-                        f/group-by-key
-                        (f/flat-map term-freq-per-doc)
+                        (f/map (f/fn [[doc-id term term-freq doc-terms-count]]
+                                     [term [doc-id (double (/ term-freq doc-terms-count))]]))
                         f/cache)

           ;; total number of documents in corpus
@@ -70,20 +61,20 @@

           ;; idf of terms, that is, idf(term)
           idf-by-term (-> doc-term-seq
-                          f/distinct
-                          (f/group-by (f/fn [[_ term]] term))
-                          (f/map (f/fn [[term doc-seq]] [term (count doc-seq)])) ;; num of docs with a given term in it
-                          (f/map (f/fn [[term df]] [term [(Math/log (/ num-docs (+ 1.0 df)))]]))
+                          (f/group-by (f/fn [[_ term _ _]] term))
+                          (f/map (calc-idf num-docs))
                           f/cache)

           ;; tf-idf of terms, that is, tf(term, document) x idf(term)
           tfidf-by-term (-> (f/join tf-by-doc idf-by-term)
-                            (f/map (f/fn [[term [[doc-id tf] [idf]]]]
+                            (f/map (f/fn [[term [[doc-id tf] idf]]]
                                          [doc-id term (* tf idf)]))
                             f/cache)
           ]
-      (-> tfidf-by-term
-          f/collect
-          clojure.pprint/pprint))
+      (->> tfidf-by-term
+           f/collect
+           ((partial sort-by last >))
+           (take 10)
+           clojure.pprint/pprint))
     (catch Exception e
       (println (.printStackTrace e)))))


Fixed code to return joint angles. Added function to get joint limits and store them in robot map. Rewrote arms code to use map from joint name to value. Snapshot of motion task code that converts from joint descriptions to calls to ALMotion

--- src/main/clojure/naojure/core.clj
+++ src/main/clojure/naojure/core.clj
@@ -112,6 +112,14 @@
      (.call (get-proxy robot proxy-sym) operation
             (into-array Object params))))

+(defn post-service
+  "Call an operation asynchronously on a service"
+  ([robot proxy-sym operation]
+     (.post (get-proxy robot proxy-sym) operation
+            (into-array Object [])))
+  ([robot proxy-sym operation params]
+     (.post (get-proxy robot proxy-sym) operation
+            (into-array Object params))))

 ;; event handling
 (defn- event-dispatcher
@@ -220,17 +228,23 @@
 (defn get-installed-behaviours
   "Return list of behaviours installed on robot"
   [robot]
-  (call-service robot :behaviour-manager "getInstalledBehaviors" ))
+  (->
+   (call-service robot :behaviour-manager "getInstalledBehaviors" )
+   (.get)))

 (defn get-running-behaviours
   "Get list of running behaviours"
   [robot]
-  (call-service robot :behaviour-manager "getRunningBehaviors"))
+  (->
+   (call-service robot :behaviour-manager "getRunningBehaviors")
+   (.get)))

 (defn get-default-behaviours
   "Get list of default behaviours (behaviours set to run automatically)"
   [robot]
-  (call-service robot :behaviour-manager "getDefaultBehaviors" ))
+  (->
+   (call-service robot :behaviour-manager "getDefaultBehaviors" )
+   (.get)))

 (defn add-default-behaviour
   "Make the named behaviour auto run on robot boot"
@@ -250,12 +264,18 @@
 (defn behaviour-present
   "Is the named behaviour present?"
   [robot behaviour-name]
-  (call-service robot :behaviour-manager "isBehaviorPresent" [behaviour-name]))
+  (->
+   (call-service robot :behaviour-manager "isBehaviorPresent"
+                 [behaviour-name])
+   (.get)))

 (defn behaviour-running
   "Is the named behaviour running"
   [robot behaviour-name]
-  (call-service robot :behaviour-manager "isBehaviorRunning"  [behaviour-name]))
+  (->
+   (call-service robot :behaviour-manager "isBehaviorRunning"
+                 [behaviour-name])
+   (.get)))

 ; memory
 (defn get-memory-keys
@@ -377,13 +397,16 @@
   [robot x y theta]
   (call-service robot :motion "moveTo" [x y theta]))

-(defn get-joint-angles
+(defn- get-joint-angles-internal
   "Return a map of the current joint angles for a robot"
-  [robot]
-  (-> (call-service robot :motion "getAngles"
-                    ["Body" Boolean/TRUE])
+  [robot useSensors]
+  (->> (call-service robot :motion "getAngles" ["Body" useSensors])
       (.get)
       (zipmap joint-names)))
+
+(defn get-joint-angles
+  ([robot] (get-joint-angles-internal robot Boolean/TRUE))
+  ([robot useSensors] (get-joint-angles-internal useSensors)))

 (defn get-body-names
   "Return names of joints in the specified chain"
@@ -391,6 +414,26 @@
   (->
    (call-service robot :motion "getBodyNames"  [name])
    (.get)))
+
+(defn get-joint-limits
+  "Get the minAngle (rad), maxAngle (rad), maxVelocity (rad.s-1) and maxTorque (N.m). for a given joint or actuator in the body."
+  [robot]
+  (->>
+   (call-service robot :motion "getLimits" ["Body"])
+   (.get)
+   (zipmap joint-names)))
+
+(defn save-joint-limits
+  "Get joint limit information and save it in robot structure"
+  [robot]
+  (assoc robot :joint-limits (get-joint-limits robot)))
+
+(defn load-joint-limits
+  "Get joint limits from robot map or retrieve them from NAOqi"
+  [robot]
+  (if-let [limits (:joint-limits robot)]
+    limits
+    (get-joint-limits robot)))

 ;; broken - can't construct variant holding array of values
 (defn set-joint-angles
@@ -460,97 +503,86 @@
   (call-service robot :tts "setVolume" [(float vol)]))

 ;; motion
-(defn- concat-joints
-  [a b]
-  (let [{an :names av :values} a
-        {bn :names bv :values} b]
-    {:names (concat an bn) :values (concat av bv)}))
+(defn- combine-joint-fns
+  [params & fns]
+  {:joints (->> fns
+                (map #(:joints ( % params)))
+                (apply merge))})

 (defn- arms_left_forward [params]
   (let [angle1 (get params 0 0)
         angle2 (get params 1 0)]
-    {:joints {:names [ "LShoulderPitch" "LShoulderRoll"]
-              :values [ (- angle1) angle2]}}))
+    {:joints {"LShoulderPitch" (- angle1)
+              "LShoulderRoll" angle2}}))

 (defn- arms_right_forward [params]
   (let [angle1 (get params 0 0)
         angle2 (get params 1 0)]
-    {:joints {:names [ "RShoulderPitch"  "RShoulderRoll"]
-              :values [ (- angle1) (- angle2)]}}))
+    {:joints {"RShoulderPitch" (- angle1)
+              "RShoulderRoll" (- angle2)}}))

 (defn- arms_forward [params]
-  (concat-joints
-   (:joints (arms_left_forward params))
-   (:joints (arms_right_forward params))))
-
+  (combine-joint-fns params arms_left_forward arms_right_forward))

 (defn- arms_left_out [params]
   (let [angle1 (get params 0 0)
         angle2 (get params 1 0)]
-    {:joints {:names ["LShoulderPitch" "LShoulderRoll"]
-              :values [(- angle1) (+ 90 angle2)]}}))
+    {:joints {"LShoulderPitch" (- angle1)
+              "LShoulderRoll" (+ 90 angle2)}}))

 (defn- arms_right_out [params]
   (let [angle1 (get params 0 0)
         angle2 (get params 1 0)]
-    {:joints {:names ["RShoulderPitch"  "RShoulderRoll"]
-              :values [ (- angle1) (- -90 angle2)]}}))
+    {:joints {"RShoulderPitch" (- angle1)
+              "RShoulderRoll" (- -90 angle2)}}))

 (defn- arms_out [params]
-  (concat-joints
-   (:joints (arms_left_out params))
-   (:joints (arms_right_out params))))
+  (combine-joint-fns params arms_left_out arms_right_out))

 (defn- arms_left_up [params]
   (let [angle1 (get params 0 0)
         angle2 (get params 1 0)]
-    {:joints {:names ["LShoulderPitch" "LShoulderRoll"]
-              :values [(- -90 angle1) angle2]}}))
+    {:joints {"LShoulderPitch" (- -90 angle1)
+              "LShoulderRoll" angle2}}))

 (defn- arms_right_up [params]
   (let [angle1 (get params 0 0)
         angle2 (get params 1 0)]
-    {:joints {:names ["RShoulderPitch"  "RShoulderRoll"]
-              :values [(- -90 angle1) (- angle2)]}}))
+    {:joints {"RShoulderPitch" (- -90 angle1)
+              "RShoulderRoll" (- angle2)}}))

 (defn- arms_up [params]
-  (concat-joints
-   (:joints (arms_left_up params))
-   (:joints (arms_right_up params))))
+  (combine-joint-fns params arms_left_up arms_right_up))

 (defn- arms_left_down [params]
   (let [angle1 (get params 0 0)
         angle2 (get params 1 0)]
-    {:joints {:names ["LShoulderPitch" "LShoulderRoll"]
-              :values [ (- 90 angle1) angle2]}}))
+    {:joints {"LShoulderPitch" (- 90 angle1)
+              "LShoulderRoll" angle2}}))

 (defn- arms_right_down [params]
   (let [angle1 (get params 0 0)
         angle2 (get params 1 0)]
-    {:joints {:names ["RShoulderPitch"  "RShoulderRoll"]
-              :values [ (- 90 angle1) (- angle2)]}}))
+    {:joints {"RShoulderPitch" (- 90 angle1)
+              "RShoulderRoll" (- angle2)}}))

 (defn- arms_down [params]
-  (concat-joints
-   (:joints (arms_left_down params))
-   (:joints (arms_right_down params))))
+  (combine-joint-fns params arms_left_down arms_right_down))

 (defn- arms_left_back [params]
   (let [angle1 (get params 0 0)
         angle2 (get params 1 0)]
-    {:joints {:names ["LShoulderPitch" "LShoulderRoll"]
-              :values [ (- 119.5 angle1) angle2]}}))
+    {:joints {"LShoulderPitch" (- 119.5 angle1)
+              "LShoulderRoll" angle2}}))

 (defn- arms_right_back [params]
   (let [angle1 (get params 0 0)
         angle2 (get params 1 0)]
-    {:joints {:names ["RShoulderPitch"  "RShoulderRoll"]
-              :values [ (- 119.5 angle1) (- angle2)]}}))
+    {:joints {"RShoulderPitch" (- 119.5 angle1)
+              "RShoulderRoll" (- angle2)}}))

 (defn- arms_back [params]
-  (concat-joints
-   (:joints (arms_left_back params))
-   (:joints (arms_right_back params))))
+  (combine-joint-fns params arms_left_back arms_right_back))

 (defn arms
   [action & params]
@@ -576,20 +608,49 @@
   [actions]
   (->> actions
        (map :joints)
-       (filter identity)))
-
-(defn do-joints
-  "Make action for joint changes if any"
-  [joint-lists duration]
-  (if-let [{:keys [names values]}
-           (cond
-            (> 1 (count joints)) (reduce concat_joints joints)
-            (= 1 (count joints)) joints)]
-    ))
+       (filter identity)
+       (apply merge)))
+
+(defn- clip
+  [value min max]
+  (cond
+   (> value max) max
+   (< value min) min
+   :else value))
+
+(defn- compute-joint-speed
+  "Compute fraction of max speed for joint movement in radians"
+  [execution-time-seconds cur-pos-rad desired-pos-rad limits]
+  (let [max-change (limits 2)
+        desired-change (Math/abs (- cur-pos-rad desired-pos-rad))
+        speed (/ desired-change (* max-change execution-time-seconds))]
+    (clip speed 0.01 1.0)))
+
+(defn- motion-task
+  [robot joint-name joint-pos-deg execution-time-seconds cur-joints limits]
+  (let [pos-rad (Math/toRadians joint-pos-deg)
+        speed-fraction (compute-joint-speed execution-time-seconds
+                                            (cur-joints joint-name)
+                                            pos-rad
+                                            (limits joint-name))]
+    (call-service robot :motion "angleInterpolationWithSpeed"
+                  [joint-name
+                   (into-array Object [(Float. pos-rad)])
+                   (Float. speed-fraction)])))
+
+(defn- do-joints
+  "Takes a map of joint changes and a duration and builds a motion task for each joint with the appropriate speed"
+  [robot duration joint-changes]
+  (if (seq joint-changes)
+    (let [cur-joints (get-joint-angles-internal robot Boolean/FALSE)
+          limits (load-joint-limits robot)]
+      (map (fn [[j v]] (motion-task robot j v duration cur-joints limits))
+           joint-changes))))

 ;; TODO make the duration and channel params optional
 (defn donao
   "Accepts a number of parameters specifying robot actions and executes them"
   [robot duration chan & actions]
-  (let [joint-changes (only-joint-actions actions)]
+  (let [joint-changes (only-joint-actions actions)
+        joint-tasks (do-joints robot duration joint-changes)]
     ))


more edits

more edits

--- src/main/clojure/dojo/solutions.clj
+++ src/main/clojure/dojo/solutions.clj
@@ -1,13 +1,11 @@
 (ns dojo.solutions
   (:use clojure.core.matrix)
+  (:use clojure.core.matrix.operators)
   (:use clojure.repl)
   (:use dojo.data))

 ;; There is no right answer.....
 ;; But here are some suggested ideas / solutions for the challenge
-
- ;; the list of teams. We'll use this to structure most results
-(def TEAMS dojo.data/TEAMS)

 ;; a map of column names -> column data
 (def COLS (zipmap HEADINGS (for [h HEADINGS] (get-column RESULTS (COL-NUMS h)))))
@@ -27,7 +25,10 @@
 (esum (add HWINS AWINS DRAWS))
 ;; => 380

-(def HOME-WINS (mapv esum (slices (mul HWINS HOME-GAMES))))
-(def AWAY-WINS (mapv esum (slices (mul AWINS AWAY-GAMES))))
-(def DRAW-RESULTS (mapv esum (slices (add (mul DRAWS AWAY-GAMES) (mul DRAWS HOME-GAMES)))))
+;; add up results by team
+(def HOME-WINS (mapv esum (slices (* HWINS HOME-GAMES))))
+(def AWAY-WINS (mapv esum (slices (* AWINS AWAY-GAMES))))
+(def DRAW-RESULTS (mapv esum (slices (add (* DRAWS AWAY-GAMES) (* DRAWS HOME-GAMES)))))

+;; percentages
+(def HOME-WIN-PERCENTAGE (/ HOME-WINS 19.0)) ;; note: division of vector by a scalar


slightly improve error message for malformed configs

sometimes bad characters cause weird issues

--- src/main/shadow/cljs/npm/cli.cljs
+++ src/main/shadow/cljs/npm/cli.cljs
@@ -119,7 +119,7 @@

 (defn ensure-config []
   (loop [root (path/resolve)]
-    (let [config (path/resolve root "shadow-cljs.edn")]
+    (let [config (path/resolve root "tmp" "bad.edn" #_"shadow-cljs.edn")]
       (cond
         (fs/existsSync config)
         config
@@ -249,13 +249,9 @@
           ))))

 (defn print-error [ex]
-  (let [{:keys [tag] :as data}
-        (ex-data ex)]
-
-    (js/console.warn "===== ERROR =================")
-    (js/console.warn (.-message ex))
-    (js/console.warn "=============================")
-    ))
+  (js/console.warn "===== ERROR =================")
+  (js/console.warn (.-message ex))
+  (js/console.warn "============================="))

 (defn get-shared-home []
   (path/resolve (os/homedir) ".shadow-cljs" jar-version))
@@ -561,9 +557,17 @@
           (util/slurp config-path)

           rdr
-          (rt/source-logging-push-back-reader config-txt)]
-
-      (edn/read reader-opts rdr))
+          (rt/source-logging-push-back-reader config-txt)
+
+          res
+          (edn/read reader-opts rdr)]
+
+      (when-not (map? res)
+        (throw (ex-info
+                 (str "Malformed config file, expected a map but got: " (pr-str res))
+                 {:x res})))
+
+      res)

     (catch :default ex
       (throw (ex-info


Fix a format of require-macros docstring

Former-commit-id: cd8ab47ce8f08337c0fd025b062a63c3fb512f51

--- planck-cljs/src/planck/core.cljs
+++ planck-cljs/src/planck/core.cljs
@@ -47,8 +47,7 @@
     require        {:arglists ([& args])
                     :doc      "Loads libs, skipping any that are already loaded."}
     require-macros {:arglists ([& args])
-                    :doc      "Similar to the require REPL special function but
-                    only for macros."}
+                    :doc      "Similar to the require REPL special function but\n  only for macros."}
     doc            {:arglists ([name])
                     :doc      "Prints documentation for a var or special form given its name"}})


Starts some validation clean up.

Starts some validation clean up.

--- test/onyx/validation_test.clj
+++ test/onyx/validation_test.clj
@@ -1,7 +1,5 @@
 (ns onyx.validation-test
-  (:require [com.stuartsierra.component :as component]
-            [onyx.system :refer [onyx-development-env]]
-            [onyx.peer.pipeline-extensions :as p-ext]
+  (:require [onyx.peer.pipeline-extensions :as p-ext]
             [onyx.peer.task-lifecycle-extensions :as l-ext]
             [midje.sweet :refer :all]
             [onyx.queue.hornetq-utils :as hq-util]
@@ -39,9 +37,7 @@
    :onyx.peer/outbox-capacity (:outbox-capacity (:peer config))
    :onyx.peer/job-scheduler :onyx.job-scheduler/round-robin})

-(def dev (onyx-development-env env-config))
-
-(def env (component/start dev))
+(def env (onyx.api/start-env env-config))

 (def workflow {:in-bootstrapped {:inc :out}})


Remove `slack-thread` from entries when adding them to an update.

--- src/oc/storage/resources/update.clj
+++ src/oc/storage/resources/update.clj
@@ -44,7 +44,7 @@
   (let [topic-slug (:topic-slug entry)
         timestamp (:created-at entry)]
     (if-let [entry (entry-res/get-entry conn org-uuid topic-slug timestamp)]
-      (dissoc entry :org-uuid :board-uuid :body-placeholder)
+      (dissoc entry :org-uuid :board-uuid :body-placeholder :slack-thread)
       (throw (ex-info "Invalid entry." {:org-uuid org-uuid :topic-slug topic-slug :created-at timestamp})))))

 ;; ----- Update Slug -----


Change eval-supporting atoms to volatiles

--- planck-cljs/src/planck/repl.cljs
+++ planck-cljs/src/planck/repl.cljs
@@ -1687,23 +1687,23 @@
               (process-execute-source source-text expression-form opts))))))))

-;; The following atoms and fns set up a scheme to
+;; The following volatiles and fns set up a scheme to
 ;; emit function values into JavaScript as numeric
 ;; references that are looked up.

-(defonce ^:private fn-index (atom 0))
-(defonce ^:private fn-refs (atom {}))
+(defonce ^:private fn-index (volatile! 0))
+(defonce ^:private fn-refs (volatile! {}))

 (defn- clear-fns!
   "Clears saved functions."
   []
-  (reset! fn-refs {}))
+  (vreset! fn-refs {}))

 (defn- put-fn
   "Saves a function, returning a numeric representation."
   [f]
-  (let [n (swap! fn-index inc)]
-    (swap! fn-refs assoc n f)
+  (let [n (vswap! fn-index inc)]
+    (vswap! fn-refs assoc n f)
     n))

 (defn- get-fn


Change direction to hold

Change direction to hold

--- src/re_natal_esp32control_app/views/ble_control/magnetometer.cljs
+++ src/re_natal_esp32control_app/views/ble_control/magnetometer.cljs
@@ -46,7 +46,7 @@
         joystick-direction (-> (.atan2 js/Math x (- y))
                               (* 180)
                               (/ (.-PI js/Math)))
-        direction (in-pi-roop (+ mag-direction joystick-direction))
+        direction (in-pi-roop (- joystick-direction mag-direction))
         speed (-> (.sqrt js/Math (+ (* x x) (* y y)))
                   (min 1)
                   (* 255))]


CMR-6288: Increase timeout of elastic startup.

--- elastic-utils-lib/src/cmr/elastic_utils/embedded_elastic_server.clj
+++ elastic-utils-lib/src/cmr/elastic_utils/embedded_elastic_server.clj
@@ -7,6 +7,7 @@
    [cmr.common.log :as log :refer [debug info warn error]]
    [cmr.common.util :as util])
   (:import
+   (java.time Duration)
    (org.testcontainers.containers FixedHostPortGenericContainer)
    (org.testcontainers.containers.wait Wait)
    (org.testcontainers.images.builder ImageFromDockerfile)))
@@ -48,6 +49,7 @@
           (.withEnv "node.name" "embedded-elastic")
           (.withFileSystemBind data-dir "/usr/share/elasticsearch/data")
           (.withFixedExposedPort (int http-port) 9200)
+          (.withStartupTimeout (Duration/ofSeconds 120))
           (.waitingFor
            (.forStatusCode (Wait/forHttp "/_cat/health?v&pretty") 200)))))


will use legacy guid or concept-id properly

--- access-control-app/src/cmr/access_control/services/auth_util.clj
+++ access-control-app/src/cmr/access_control/services/auth_util.clj
@@ -63,15 +63,18 @@
                 (get-provider-level-group-acls context permission))))))

 (defn- get-instance-acls
- "Returns any ACLs that grant the given permission to the context user on a specific group by its :legacy-guid."
+ "Returns any ACLs that grant the given permission to the context user on a specific group by its concept-id or legacy-guid."
  [context action-description permission group]
- (when-let [target-guid (or (:concept-id group) (:legacy-guid group))]
-   (let [permissions (cond (= action-description "update") :update
-                           (= action-description "read") [:update :delete]
-                           (= action-description "delete") :delete
-                           :else permission)]
+ (let [concept-id (:concept-id group)
+       legacy-guid (:legacy-guid group)
+       permissions (cond (= action-description "update") :update
+                         (= action-description "read") [:update :delete]
+                         (= action-description "delete") :delete
+                         :else permission)]
+   (when (or legacy-guid concept-id)
      (doseq [permission permissions]
-       (filter #(= target-guid (-> % :single-instance-object-identity :target-guid))
+       (filter #(or (= concept-id (-> % :single-instance-object-identity :target-guid))
+                    (= legacy-guid (-> % :single-instance-object-identity :target-guid)))
                (acl/get-permitting-acls context
                                         :single-instance-object "GROUP_MANAGEMENT" permission))))))
 (defn- describe-group


resolve tilde in audio-file helper

resolve tilde in audio-file helper

--- src/overtone/helpers/audio_file.clj
+++ src/overtone/helpers/audio_file.clj
@@ -2,7 +2,8 @@
     ^{:doc "Audio file encoding functions"
       :author "Sam Aaron"}
   overtone.helpers.audio-file
-  (:use [overtone.sc.buffer :only [buffer-data]])
+  (:use [overtone.sc.buffer :only [buffer-data]]
+        [overtone.helpers.file :only [resolve-tilde-path]])
   (:import [javax.sound.sampled AudioFormat AudioFileFormat AudioFormat$Encoding
                                 AudioFileFormat$Type AudioInputStream AudioSystem]
            [java.io File ByteArrayInputStream]
@@ -26,7 +27,8 @@
   [data path frame-rate n-channels]
   (when (some #(or (< % -1) (> % 1)) data)
     (throw (Exception. (str "Unable to write audio file with this data as it contains sample points either less than -1 or greater than 1."))))
-  (let [frame-rate   (float frame-rate)
+  (let [path         (resolve-tilde-path)
+        frame-rate   (float frame-rate)
         n-channels   (int n-channels)
         sample-bytes (/ Short/SIZE 8)
         frame-bytes  (* sample-bytes n-channels)


stop accepting user in the payload of a login message

--- src/puppetlabs/cthun/validation.clj
+++ src/puppetlabs/cthun/validation.clj
@@ -27,8 +27,7 @@
 ; Server message data types
 (def LoginMessageData
   "Defines the data field in a login message body"
-  {(s/required-key :type) s/Str
-   (s/required-key :user) s/Str})
+  {(s/required-key :type) s/Str})

 (defn check-schema
   "Check if the JSON matches the ClientMessage schema.


Removing the special case polygons from the general spatial search test.


Fix imports in r.m.file-info.

Fix imports in r.m.file-info.

--- ring-core/src/ring/middleware/file_info.clj
+++ ring-core/src/ring/middleware/file_info.clj
@@ -1,8 +1,8 @@
 (ns ring.middleware.file-info
   "Augment Ring File responses."
-  (:use ring.util.response)
+  (:require [ring.util.response :as res])
   (:import java.io.File
-           [java.util Date Locale TimeZone]
+           (java.util Date Locale TimeZone)
            java.text.SimpleDateFormat))

 (def ^{:private true} base-mime-types
@@ -103,12 +103,12 @@
                 file-length (.length ^File body)
                 lmodified   (Date. (.lastModified ^File body))
                 response    (-> response
-                              (content-type file-type)
-                              (header "Last-Modified"
+                              (res/content-type file-type)
+                              (res/header "Last-Modified"
                                       (.format (make-http-format) lmodified)))]
             (if (not-modified-since? req lmodified)
-              (-> response (status 304)
-                           (header "Content-Length" 0)
+              (-> response (res/status 304)
+                           (res/header "Content-Length" 0)
                            (assoc :body ""))
-              (-> response (header "Content-Length" file-length))))
+              (-> response (res/header "Content-Length" file-length))))
           response)))))


Force US locale for parsing HTTP dates

Force US locale for parsing HTTP dates

--- ring-core/src/ring/middleware/file_info.clj
+++ ring-core/src/ring/middleware/file_info.clj
@@ -3,8 +3,7 @@
   (:use [clojure.contrib.def :only (defvar-)]
         ring.util.response)
   (:import java.io.File
-           java.util.Date
-           java.util.TimeZone
+           [java.util Date Locale TimeZone]
            java.text.SimpleDateFormat))

 (defvar- base-mime-types
@@ -78,7 +77,7 @@
   "Formats or parses dates into HTTP date format (RFC 822/1123)."
   []
   ;; SimpleDateFormat is not threadsafe, so return a new instance each time
-  (doto (SimpleDateFormat. "EEE, dd MMM yyyy HH:mm:ss ZZZ")
+  (doto (SimpleDateFormat. "EEE, dd MMM yyyy HH:mm:ss ZZZ" Locale/US)
     (.setTimeZone (TimeZone/getTimeZone "UTC"))))

 (defn- not-modified-since?


CMR-1980: Fix cache test failure

CMR-1980: Fix cache test failure

--- system-int-test/test/cmr/system_int_test/admin/cache_api_test.clj
+++ system-int-test/test/cmr/system_int_test/admin/cache_api_test.clj
@@ -81,7 +81,8 @@
                                          "index-names"
                                          "token-imp"
                                          "token-sid"
-                                         "xsl-transformer-templates"])
+                                         "xsl-transformer-templates"
+                                         "kms"])
       (s/only-with-real-database
         (testing "list caches for bootstrap"
           (let [response (list-caches-for-app (url/bootstrap-read-caches-url) admin-read-token)]


log shortcut

log shortcut

--- src-cljs/flatride/frontend.cljs
+++ src-cljs/flatride/frontend.cljs
@@ -4,6 +4,9 @@
     (:require
         [dommy.core :as dommy]
         [flatride.core :as core]))
+
+(defn log [stuff]
+  (.log js/console stuff))

 (def gautocomplete-from nil)
 (def gautocomplete-to nil)


Format slack pastes as code

Format slack pastes as code

--- src/yetibot/core/adapters/slack.clj
+++ src/yetibot/core/adapters/slack.clj
@@ -54,7 +54,7 @@
                            {:unfurl_media "true" :as_user "true"}))

 (defn send-paste [msg]
-  (send-msg msg))
+  (send-msg (str "```" msg "```")))

 (def messaging-fns
   {:msg send-msg


Memoize functions reading keys

Memoize functions reading keys

--- auth/src/com/sixsq/slipstream/auth/sign.clj
+++ auth/src/com/sixsq/slipstream/auth/sign.clj
@@ -25,7 +25,7 @@
       co/bytes->hex
       clojure.string/upper-case))

-(defn private-key
+(defn- read-private-key
   [private-key-pem]
   (let [passphrase (cf/property-value :passphrase)
         privkey (io/resource private-key-pem)]
@@ -33,12 +33,16 @@
       (ks/private-key privkey passphrase)
       (throw (IllegalStateException. "Passphrase not defined or private key not accessible (must be in the classpath).")))))

-(defn- public-key
+(defn- read-public-key
   [public-key-pem]
   (let [pubkey (io/resource public-key-pem)]
     (if pubkey
       (ks/public-key pubkey)
       (throw (IllegalStateException. "Public key not accessible (must be in the classpath).")))))
+
+(def public-key (memoize read-public-key))
+
+(def private-key (memoize read-private-key))

 (defn sign-claims
   [claims]


CMR-687: Added test for using AND with facets.

--- test/cmr/system_int_test/search/collection_facets_search_test.clj
+++ test/cmr/system_int_test/search/collection_facets_search_test.clj
@@ -254,6 +254,42 @@
           (is (= expected-facets
                  (:facets (search/find-refs :collection {:include-facets true
                                                          :project "PROJ2"}))))))
+
+      (testing "AND conditions narrow facets via AND not OR"
+        (let [expected-facets [{:field "project" :value-counts [["PROJ2" 1] ["proj3" 1]]}
+                               {:field "platform" :value-counts [["B-p0" 1] ["B-p1" 1]]}
+                               {:field "instrument"
+                                :value-counts [["B-p0-i0" 1]
+                                               ["B-p0-i1" 1]
+                                               ["B-p1-i0" 1]
+                                               ["B-p1-i1" 1]]}
+                               {:field "sensor"
+                                :value-counts [["B-p0-i0-s0" 1]
+                                               ["B-p0-i1-s0" 1]
+                                               ["B-p1-i0-s0" 1]
+                                               ["B-p1-i1-s0" 1]]}
+                               {:field "two_d_coordinate_system_name" :value-counts []}
+                               {:field "processing_level_id" :value-counts [["pl1" 1]]}
+                               {:field "category" :value-counts [["Cat1" 1] ["Hurricane" 1]]}
+                               {:field "topic" :value-counts [["Popular" 1] ["Topic1" 1]]}
+                               {:field "term" :value-counts [["Extreme" 1]
+                                                             ["Term1" 1]
+                                                             ["UNIVERSAL" 1]]}
+                               {:field "variable_level_1":value-counts [["Level1-1" 1]
+                                                                        ["Level2-1" 1]]}
+                               {:field "variable_level_2" :value-counts [["Level1-2" 1]
+                                                                         ["Level2-2" 1]]}
+                               {:field "variable_level_3" :value-counts [["Level1-3" 1]
+                                                                         ["Level2-3" 1]]}
+                               {:field "detailed_variable" :value-counts [["Detail1" 1]
+                                                                          ["UNIVERSAL" 1]]}]]
+
+
+          (is (= expected-facets
+                 (:facets (search/find-refs :collection {:include-facets true
+                                                        :project ["PROJ2" "proj3"]
+                                                        "options[project][and]" true}))))))
+
       (testing "search finding one document"
         (let [expected-facets [{:field "project" :value-counts []}
                                {:field "platform" :value-counts []}


Test return values

Test return values

--- modules/scheduling/src/test/clojure/wunderboss/scheduling_tests.clj
+++ modules/scheduling/src/test/clojure/wunderboss/scheduling_tests.clj
@@ -53,7 +53,8 @@
     (with-job #(swap! q inc) {:every 100}
       (Thread/sleep 500)
       (is (> @q 0))
-      (.unschedule default "a-job")
+      (is (.unschedule default "a-job"))
+      (is (not (.unschedule default "a-job")))
       (Thread/sleep 500)
       (let [curr @q]
         (Thread/sleep 500)


Maybe some sleep will help this test on CI.

--- modules/scheduling/src/test/clojure/wunderboss/scheduling_tests.clj
+++ modules/scheduling/src/test/clojure/wunderboss/scheduling_tests.clj
@@ -236,6 +236,7 @@
                                (deliver p :success)))))
     (.schedule default id #() {})
     (is (= :success (deref p 1000 :failure)))
+    (Thread/sleep 100)
     (is (false? (.unschedule default id)))
     (is (empty? (.scheduledJobs default)))
     (-> (.scheduler default)


logging

logging

--- src/babel/italiano/grammar.cljc
+++ src/babel/italiano/grammar.cljc
@@ -831,7 +831,7 @@
                                             (get aux2lex (get-in spec [:synsem :aux] ::undefined))
                                             (get cat2lex (get-in spec [:synsem :cat] ::undefined))
                                             ]))]
-                       (log/debug (str "intersection size: " (count result)))
+                       (log/debug (str "indexed size returned: " (count result)))
                        result)))

      :language "it"


~(defn aux-is-head-feature): adopt square-brackets convention

--- src/babel/italiano/grammar.cljc
+++ src/babel/italiano/grammar.cljc
@@ -567,7 +567,7 @@
                                        :rule "s-modified-modifier-last"}))))

 (defn aux-is-head-feature [phrase]
-  (cond (= :verb (get-in phrase '(:synsem :cat)))
+  (cond (= :verb (get-in phrase [:synsem :cat]))
         (unify phrase
                (let [ref (atom :top)]
                  {:synsem {:aux ref}


Refactor

Refactor

--- src/buildviz/analyse/builds.clj
+++ src/buildviz/analyse/builds.clj
@@ -1,13 +1,13 @@
 (ns buildviz.analyse.builds
-  (:require [buildviz.data.build-schema :as schema]
+  (:require [buildviz.data.build-schema :refer [build-with-outcome? failed-build?]]
             [buildviz.util.math :as math]
             [clj-time
              [coerce :as tc]
              [core :as t]
              [format :as tf]]))

-(defn builds-with-outcome [build-data-entries]
-  (filter schema/build-with-outcome? build-data-entries))
+(defn builds-with-outcome [builds]
+  (filter build-with-outcome? builds))

 (defn builds-grouped-by-same-inputs [builds]
@@ -18,46 +18,45 @@

 ;; flaky builds

-(defn- outcomes-for-builds-grouped-by-input [build-data-entries]
-  (->> build-data-entries
+(defn- outcomes-for-builds-grouped-by-input [builds]
+  (->> builds
        builds-grouped-by-same-inputs
        (map #(map :outcome %))
        (map distinct)))

-(defn flaky-build-count [build-data-entries]
-  (->> (outcomes-for-builds-grouped-by-input build-data-entries)
+(defn flaky-build-count [builds]
+  (->> (outcomes-for-builds-grouped-by-input builds)
        (map count)
        (filter #(< 1 %))
        count))

 ;; avg runtime

-(defn- runtime-for [build]
-  (when (contains? build :end)
-    (- (build :end) (build :start))))
+(defn- runtime-for [{:keys [start end]}]
+  (- end start))

-(defn- build-runtime [build-data-entries]
-  (filter some?
-          (map runtime-for build-data-entries)))
+(defn- build-runtimes [builds]
+  (map runtime-for (filter :end builds)))

-(defn average-runtime [build-data-entries]
-  (when-let [runtimes (seq (build-runtime build-data-entries))]
+(defn average-runtime [builds]
+  (when-let [runtimes (seq (build-runtimes builds))]
     (math/avg runtimes)))

 (def date-only-formatter (tf/formatter "yyyy-MM-dd" (t/default-time-zone)))

 (defn- date-for [{end :end}]
-  (when (some? end)
+  (when end
     (tf/unparse date-only-formatter (tc/from-long (long end)))))

-(defn average-runtime-by-day [build-data-entries]
-  (->> (group-by date-for build-data-entries)
+(defn average-runtime-by-day [builds]
+  (->> builds
+       (filter :end)
+       (group-by date-for)
        (map (fn [[date builds]] [date (average-runtime builds)]))
-       (filter second)
        (into {})))

 ;; error count

-(defn fail-count [build-data-entries]
-  (count (filter schema/failed-build? build-data-entries)))
+(defn fail-count [builds]
+  (count (filter failed-build? builds)))


fix auth error callback

fix auth error callback

--- src/chat/client/dispatcher.cljs
+++ src/chat/client/dispatcher.cljs
@@ -181,7 +181,7 @@
                      :csrf-token (:csrf-token @sync/chsk-state)}
             :on-complete (fn [data]
                            (sync/reconnect!))
-            :on-error (fn [data]
+            :on-error (fn [_]
                         (when-let [cb (data :on-error)]
                           (cb)))}))


Add missing test.check namespaces necessary for testing CLJS

--- test/cljc/spectrace/trace_test.cljc
+++ test/cljc/spectrace/trace_test.cljc
@@ -1,6 +1,9 @@
 (ns spectrace.trace-test
   (:require [clojure.spec.alpha :as s]
             [clojure.test :refer [deftest is are]]
+            #?@(:cljs ([clojure.test.check]
+                       [clojure.test.check.generators]
+                       [clojure.test.check.properties]))
             [spectrace.trace :as trace]))

 (s/def ::x integer?)


Faster routing

Faster routing

--- src/clj/salava/core/handler.clj
+++ src/clj/salava/core/handler.clj
@@ -52,6 +52,7 @@

 (defn handler [ctx]
+  (let [main-routes (resolve-routes ctx)]
     (wrap-middlewares
       ctx
       (api
@@ -70,10 +71,10 @@
                                {:name "page", :description "plugin"}
                                {:name "translator", :description "plugin"}
                                {:name "user", :description "plugin"}]})
-        (context (get-base-path ctx) []
-                 (resolve-routes ctx))
+
+        (context (get-base-path ctx) [] main-routes)

         (legacy-routes ctx)

-        (route/not-found "404 Not found"))))
+        (route/not-found "404 Not found")))))


Try to prevent player from spawning inside volcano

--- src/cljc/robinson/worldgen.cljc
+++ src/cljc/robinson/worldgen.cljc
@@ -138,7 +138,7 @@
             points  (rlos/line-segment [0 0] [x y])
             samples points #_(take-nth 2 points)
             n       (rn/create-noise (rr/create-random seed))
-            _ (log/info "find-starting-pos samples" (vec samples))]
+            #_#__ (log/info "find-starting-pos samples" (vec samples))]
         (if (= :ocean (apply sample-island n (last samples)))
           (let [spans (partition-by (fn [[x y]]
                                       (let [s (sample-island n x y)
@@ -148,7 +148,8 @@
                                         (every? (partial contains? #{:surf}) adj-types)))
                                     samples)
                 [sx sy] (-> spans first last)]
-            (if (and sx sy)
+            (log/info "spans" (vec spans))
+            (if (and sx sy (rc/farther-than? (rc/xy->pos 0 0) (rc/xy->pos sx sy) 20))
               (recur (rc/xy->pos sx sy))
               (recur nil)))
           (recur nil))))))


Enable sharing short url by email

Enable sharing short url by email

Several changes in this patch:
- We change the `SHORTENING-IN-PROGRESS` var from a set to a
  hash of url -> set of actions. This allows us to perform the set of
  actions when the url has been shortened. Currently, only the `:email`
  action is supported
- Add the `add-url-and-action-to-shortening-in-progress` function
  used for adding a url and an associated action to the
  `SHORTENING-IN-PROGRESS` hash
- Add `do-action-after-url-shortening` function to perform an action
  associated with a short url. Currently, only the `:email` action is
  supported
- Modify the `make-request-to-get-short-url` function to perform the
  actions associated with the url to be shortened after shortening is
  successful
- Modify the `get-short-url-jq-evt-handler-maker` function to take in
  an optional `actionAfterDone` arg, which is the action to be performed
  after url shortening
- Modify `get-short-url-jq-evt-handler-maker` to add new actions to a
  url that is currently being shortened but whose ajax call has not been
  completed. This allows multiple actions to be associated with a url to
  be shortened.

Signed-off-by: Pang Yan Han <22594c345857f664c61cd411f607c4d40a9d4af9@gmail.com>

--- src/cljs/cljs_nusmods/main.cljs
+++ src/cljs/cljs_nusmods/main.cljs
@@ -402,16 +402,41 @@
         (initialize-exhibit3 (aget js/window "MODULES")
                              (aget js/window "AUXMODULES")))))

-(def ^{:doc     "The set of urls that have been sent for shortening, but whose
-                 ajax requests have not yet completed"
-       :private true}
-  SHORTENING-IN-PROGRESS #{})
+(def ^{:doc     "A map of urls that have been sent for shortening, but whose
+                 ajax requests have not yet completed.
+
+                 Values are a set of actions to be performed after the url
+                 shortening has been done; refer to the
+                 `action-after-url-shortening` function for more details on the
+                 actions."
+       :private true}
+  SHORTENING-IN-PROGRESS {})
+
+(defn- add-url-and-action-to-shortening-in-progress
+  "Adds a url and its associated action to `SHORTENING-IN-PROGRESS`"
+  [url action]
+  (set! SHORTENING-IN-PROGRESS
+        (update-in SHORTENING-IN-PROGRESS [url]
+                   (fn [actionSet]
+                     (if (nil? actionSet)
+                         #{action}
+                         (conj actionSet action))))))
+
+(defn- do-action-after-url-shortening
+  "Performs an action after url shortening"
+  [shortUrl action]
+  (case action
+        :email   (aset js/window
+                       "location"
+                       (str "mailto:?"
+                            "subject=My%20cljs-nusmods%20timetable&body="
+                            "&body=" (js/encodeURI shortUrl)))
+        :twitter nil
+        nil      nil))

 (defn- make-request-to-get-short-url
   "Makes the ajax request to the server to obtain a short url"
-  [currentUrl $urlShortenerInput localStorage localStorageKey]
-  (set! SHORTENING-IN-PROGRESS
-        (conj SHORTENING-IN-PROGRESS currentUrl))
+  [currentUrl actionAfterDone $urlShortenerInput localStorage localStorageKey]
   (ajax "/shorten"
         {:data     {:url (js/encodeURI currentUrl)}
          :dataType "json"
@@ -421,8 +446,13 @@
            (if (= (aget data "status") 200)
                (let [shortUrl (aget data "shortUrl")]
                  (.val $urlShortenerInput shortUrl)
+                 ; perform actions before setting in localStorage
+                 (doseq [action (get SHORTENING-IN-PROGRESS currentUrl)]
+                   (do-action-after-url-shortening shortUrl action))
                  (.setItem localStorage localStorageKey
                            shortUrl))
+
+               ; else status != 200
                (.val $urlShortenerInput
                      (aget data "message"))))

@@ -432,13 +462,13 @@

          :complete (fn []
                      (set! SHORTENING-IN-PROGRESS
-                           (disj SHORTENING-IN-PROGRESS currentUrl)))}))
+                           (dissoc SHORTENING-IN-PROGRESS currentUrl)))}))

 (defn- get-short-url-jq-evt-handler-maker
   "Returns a function suitable for a jQuery event handler; the returned function
    tries to obtain a short url and sets the result in the #url-shortener
    <input>"
-  [$urlShortenerInput localStorage]
+  [$urlShortenerInput localStorage & [actionAfterDone]]
   (fn []
     (let [currentUrl (aget js/document "URL")
           localStorageKey (str "shortUrl-" currentUrl)
@@ -446,11 +476,27 @@
           mbShortUrl (and localStorage
                           (.getItem localStorage localStorageKey))]
       (cond mbShortUrl
-            (.val $urlShortenerInput mbShortUrl)
+            ; the set! on `SHORTENING-IN-PROGRESS` is carried out to clear away
+            ; any actions that may have been added by the :else part of this
+            ; `cond` after the url has been shortened
+            (do (set! SHORTENING-IN-PROGRESS
+                      (dissoc SHORTENING-IN-PROGRESS currentUrl))
+                (.val $urlShortenerInput mbShortUrl)
+                (if actionAfterDone
+                    (do-action-after-url-shortening mbShortUrl actionAfterDone)))

             (not (contains? SHORTENING-IN-PROGRESS currentUrl))
-            (make-request-to-get-short-url currentUrl $urlShortenerInput
-                                           localStorage localStorageKey)))))
+            (do (add-url-and-action-to-shortening-in-progress currentUrl
+                                                              actionAfterDone)
+                (make-request-to-get-short-url currentUrl actionAfterDone
+                                               $urlShortenerInput localStorage
+                                               localStorageKey))
+
+            ; currentUrl in `SHORTENING-IN-PROGRESS`.
+            ; add `actionAfterDone` to the set of actions to perform
+            :else
+            (add-url-and-action-to-shortening-in-progress currentUrl
+                                                          actionAfterDone)))))

 (defn- qtip-for-sharing-button
   "Add qtip for social sharing buttons"
@@ -484,6 +530,7 @@
         localStorage        (aget js/window "localStorage")
         zcbClient           (ZeroClipboard. $copy-to-clipboard)
         $urlShortenerInput  ($ :#url-shortener)
+        $share-by-email     ($ :#share-by-email)
         get-url-evt-handler (get-short-url-jq-evt-handler-maker
                               $urlShortenerInput localStorage)
         qtipOrgCopyText     "Copy to Clipboard"
@@ -506,8 +553,12 @@
     (.mouseenter $copy-to-clipboard get-url-evt-handler)
     ; Change text of qtip when user clicks the copy-to-clipboard <button>
     (.on zcbClient "copy" (fn [] (.set qtipApi "content.text" "Copied!")))
-    (qtip-for-sharing-button ($ :#share-by-email) "Share via Email")
-    (qtip-for-sharing-button ($ :#share-on-twitter) "Share via Twitter")))
+    (qtip-for-sharing-button $share-by-email  "Share via Email")
+    (qtip-for-sharing-button ($ :#share-on-twitter) "Share via Twitter")
+    (.click $share-by-email
+            (get-short-url-jq-evt-handler-maker $urlShortenerInput
+                                                localStorage
+                                                :email))))

 ; Main entry point of the program
 (defn ^:export init [acad-year sem]


Adding card expension

Adding card expension

--- src/cljs/clojure_rest/core.cljs
+++ src/cljs/clojure_rest/core.cljs
@@ -71,18 +71,27 @@
   ])

 (defn render-card
-  [card]
-  [:div.card
-   [:div.card__title (:title card)]
-   [:div.card__details (:description card)]
-   [render-tasks (:tasks card)]
-  ])
+  []
+  (let [is-show-details (r/atom false)
+        show-details #(swap! is-show-details not)]
+    (fn [card]
+      [:div.card
+       [:div.card__title {:on-click show-details} (:title card)]
+       (when @is-show-details
+         [:div ;TODO - If there is not div here, it does not work
+          [:div.card__details (:description card)]
+          [render-tasks (:tasks card)]])
+      ])
+    ))

 (defn render-list
   [status cards]
   [:div.list
    [:h1 (status->str status)]
-   (map render-card (filter-by-status status cards))
+   (for [c (filter-by-status status cards)]
+     [render-card c])
+   ; (map render-card (filter-by-status status cards))
+   ; TODO - Investigate why if you use map it does not work...
   ])

 (defn render-board


Add missing on-add-card

Add missing on-add-card

--- src/cljs/clojure_rest/core.cljs
+++ src/cljs/clojure_rest/core.cljs
@@ -112,8 +112,8 @@

 (def-multi-reducer app-reducer
   ; TODO - Try to use multi-methods instead
-  {:on-toggle-all (fn [store _]
-                    (toggle-all-cards store))
+  {:on-add-card (fn [store _] (js/alert "TODO") store)
+   :on-toggle-all (fn [store _] (toggle-all-cards store))
    :on-toggle-card (fn [store card-id]
                      (update-in store [card-id :show-details] not))
    :on-remove-task (fn [store card-id task-id]


Add a null handler for :navigate

Add a null handler for :navigate

--- src/cljs/comic_reader/main.cljs
+++ src/cljs/comic_reader/main.cljs
@@ -10,9 +10,13 @@

 (rf/register-handler
  :initialize
- (fn
-   [db _]
+ (fn [db _]
    (merge db initial-state)))
+
+(rf/register-handler
+ :navigate
+ (fn [db [_ page]]
+   db))

 (rf/register-sub
  :page


Adds option for the user to draw the initial state

User can use mouse to set the cells for the initial setup
Makes the board larger


async/merge shadowing map merge

async/merge shadowing map merge

--- src/cljs/hacker_agent/core.cljs
+++ src/cljs/hacker_agent/core.cljs
@@ -5,7 +5,7 @@
             [goog.events :as events]
             [goog.history.EventType :as EventType]
             [weasel.repl :as ws-repl]
-            [cljs.core.async :as async :refer [put! chan <! >! close! merge]]
+            [cljs.core.async :as async :refer [put! chan <! >! close!]]
             [hacker-agent.hacker-base :as base]
             [hacker-agent.time :as t]
             [hacker-agent.utils :as utils])


Minor English language fixes

Minor English language fixes

--- src/cljs/subman/components.cljs
+++ src/cljs/subman/components.cljs
@@ -59,7 +59,7 @@
    (or (= @counter 0)
        (= (count @query) 0)) [:div.container.col-xs-12.info-box.form-inline
                               [:h2 "Welcome to subman!"]
-                              [:p "We indexing "
+                              [:p "We index "
                                [:a {:href "http://www.addic7ed.com/"
                                     :target "_blank"} "addic7ed.com"]
                                ", "
@@ -75,9 +75,9 @@
                                [:a {:href "http://notabenoid.com/"
                                     :target "_blank"} "notabenoid.com"]
                                "."]
-                              [:p "In query you can specifie language with "
+                              [:p "You can specify subtitle language in your query using "
                                [:code ":lang name"]
-                               ", by default used: "
+                               ". Default language used: "
                                (edit-option options :languages :current-language)]
                               [:p "And source using "
                                [:code ":source name"]


do the stupid thing so we can type hint to remove reflection

--- src/clojure/flambo/function.clj
+++ src/clojure/flambo/function.clj
@@ -51,7 +51,7 @@
        (defn ~wrapper-name [f#]
          (new ~new-class-sym
               (if (serfn? f#) (binding [sfn/*serialize* kryo/serialize]
-                                (serialize-fn f#)) f#))))))
+                                (serialize-fn f#)) f#)) assoc :tag ~new-class-sym))))

 (gen-function Function function)
 (gen-function Function2 function2)
@@ -61,30 +61,118 @@
 (gen-function FlatMapFunction2 flat-map-function2)
 (gen-function PairFlatMapFunction pair-flat-map-function)
 (gen-function PairFunction pair-function)
+(gen-function DoubleFunction double-function)
+(gen-function DoubleFlatMapFunction double-flat-map-function)

-;; Replaces the PairFunction-call and PairFlatMapFunction-call defined by the gen-function macro.
-;; (defmulti PairFunction-call (fn [_ x] (class x)))
+;; This sucks, but I need to do it to type hint the call to .state
+;; and I don't think I can do that from the generic -call I used above.

-;; (defmethod PairFunction-call Tuple2
-;;   [this x]
-;;   (log/trace "PAIRFUNCTION-CALL TUPLE2")
-;;   (-call this x))
+(defn Function-call [^flambo.function.Function this & xs]
+  (let [fn-or-serfn (.state this)
+        f (if (instance? array-of-bytes-type fn-or-serfn)
+            (binding [sfn/*deserialize* kryo/deserialize]
+              (deserialize-fn fn-or-serfn))
+            fn-or-serfn)]
+    (log/trace "CLASS" (type this))
+    (log/trace "META" (meta f))
+    (log/trace "XS" xs)
+    (apply f xs)))

-;; (defmethod PairFunction-call :default
-;;   [this x]
-;;   (log/trace "PAIRFUNCTION-CALL DEFAULT")
-;;   (let [[a b] (-call this x)]
-;;     (Tuple2. a b)))
+(defn Function2-call [^flambo.function.Function2 this & xs]
+  (let [fn-or-serfn (.state this)
+        f (if (instance? array-of-bytes-type fn-or-serfn)
+            (binding [sfn/*deserialize* kryo/deserialize]
+              (deserialize-fn fn-or-serfn))
+            fn-or-serfn)]
+    (log/trace "CLASS" (type this))
+    (log/trace "META" (meta f))
+    (log/trace "XS" xs)
+    (apply f xs)))

-;; (defmulti PairFlatMapFunction-call (fn [_ x] (class x)))
+(defn Function3-call [^flambo.function.Function2 this & xs]
+  (let [fn-or-serfn (.state this)
+        f (if (instance? array-of-bytes-type fn-or-serfn)
+            (binding [sfn/*deserialize* kryo/deserialize]
+              (deserialize-fn fn-or-serfn))
+            fn-or-serfn)]
+    (log/trace "CLASS" (type this))
+    (log/trace "META" (meta f))
+    (log/trace "XS" xs)
+    (apply f xs)))

-;; (defmethod PairFlatMapFunction-call Tuple2
-;;   [this x]
-;;   (-call this x))
+(defn VoidFunction-call [^flambo.function.VoidFunction this & xs]
+  (let [fn-or-serfn (.state this)
+        f (if (instance? array-of-bytes-type fn-or-serfn)
+            (binding [sfn/*deserialize* kryo/deserialize]
+              (deserialize-fn fn-or-serfn))
+            fn-or-serfn)]
+    (log/trace "CLASS" (type this))
+    (log/trace "META" (meta f))
+    (log/trace "XS" xs)
+    (apply f xs)))

-;; (defmethod PairFlatMapFunction-call :default
-;;   [this x]
-;;   (let [ret (-call this x)]
-;;     (for [v ret
-;;           :let [[a b] v]]
-;;       (Tuple2. a b))))
+(defn FlatMapFunction-call [^flambo.function.FlatMapFunction this & xs]
+  (let [fn-or-serfn (.state this)
+        f (if (instance? array-of-bytes-type fn-or-serfn)
+            (binding [sfn/*deserialize* kryo/deserialize]
+              (deserialize-fn fn-or-serfn))
+            fn-or-serfn)]
+    (log/trace "CLASS" (type this))
+    (log/trace "META" (meta f))
+    (log/trace "XS" xs)
+    (apply f xs)))
+
+(defn FlatMapFunction2-call [^flambo.function.FlatMapFunction2 this & xs]
+  (let [fn-or-serfn (.state this)
+        f (if (instance? array-of-bytes-type fn-or-serfn)
+            (binding [sfn/*deserialize* kryo/deserialize]
+              (deserialize-fn fn-or-serfn))
+            fn-or-serfn)]
+    (log/trace "CLASS" (type this))
+    (log/trace "META" (meta f))
+    (log/trace "XS" xs)
+    (apply f xs)))
+
+(defn PairFlatMapFunction-call [^flambo.function.PairFlatMapFunction this & xs]
+  (let [fn-or-serfn (.state this)
+        f (if (instance? array-of-bytes-type fn-or-serfn)
+            (binding [sfn/*deserialize* kryo/deserialize]
+              (deserialize-fn fn-or-serfn))
+            fn-or-serfn)]
+    (log/trace "CLASS" (type this))
+    (log/trace "META" (meta f))
+    (log/trace "XS" xs)
+    (apply f xs)))
+
+(defn PairFunction-call [^flambo.function.PairFunction this & xs]
+  (let [fn-or-serfn (.state this)
+        f (if (instance? array-of-bytes-type fn-or-serfn)
+            (binding [sfn/*deserialize* kryo/deserialize]
+              (deserialize-fn fn-or-serfn))
+            fn-or-serfn)]
+    (log/trace "CLASS" (type this))
+    (log/trace "META" (meta f))
+    (log/trace "XS" xs)
+    (apply f xs)))
+
+(defn DoubleFunction-call [^flambo.function.DoubleFunction this & xs]
+  (let [fn-or-serfn (.state this)
+        f (if (instance? array-of-bytes-type fn-or-serfn)
+            (binding [sfn/*deserialize* kryo/deserialize]
+              (deserialize-fn fn-or-serfn))
+            fn-or-serfn)]
+    (log/trace "CLASS" (type this))
+    (log/trace "META" (meta f))
+    (log/trace "XS" xs)
+    (apply f xs)))
+
+(defn DoubleFlatMapFunction-call [^flambo.function.DoubleFlatMapFunction this & xs]
+  (let [fn-or-serfn (.state this)
+        f (if (instance? array-of-bytes-type fn-or-serfn)
+            (binding [sfn/*deserialize* kryo/deserialize]
+              (deserialize-fn fn-or-serfn))
+            fn-or-serfn)]
+    (log/trace "CLASS" (type this))
+    (log/trace "META" (meta f))
+    (log/trace "XS" xs)
+    (apply f xs)))


Removed js mixins incompatible with :advanced compilation

--- src/clojure/freactive/core.cljc
+++ src/clojure/freactive/core.cljc
@@ -568,7 +568,7 @@
             (fn [this f & args]
               (swap! parent
                      (fn [x] (setter x (apply f (getter x) args)))))
-            (fn [] (throw (ex-info "Cursor is read-only"))))
+            (fn [] (throw (ex-info "Cursor is read-only" {}))))
           (fn [this]
             ((.-add-watch binding-info) parent id
              (fn [k r o n] (.updateCursor this (getter n) *change-ks*))))
@@ -604,36 +604,6 @@

      (def ^:dynamic *trace-capture* nil)

-     (defn apply-js-mixin [the-type mixin]
-       (let [ptype (.-prototype the-type)]
-         (goog.object/forEach
-          mixin
-          (fn [val key obj]
-            (aset ptype key val)))))
-
-     (def fwatch-mixin
-       #js {:addFWatch
-            (fn addFWatch [key f]
-              (this-as this
-                       (when-not (aget (.-fwatches this) key)
-                         (set! (.-watchers this) (inc (.-watchers this)))
-                         (aset (.-fwatches this) key f))))
-            :removeFWatch
-            (fn removeFWatch [key]
-              (this-as this
-                       (when (aget (.-fwatches this) key)
-                         (set! (.-watchers this) (dec (.-watchers this)))
-                         (js-delete (.-fwatches this) key))))
-            :notifyFWatches
-            (fn notifyFWatches [oldVal newVal]
-              (this-as this
-                       (goog.object/forEach
-                        (.-fwatches this)
-                        (fn [f key _]
-                          (f key this oldVal newVal)))
-                       (doseq [[key f] (.-watches this)]
-                         (f key this oldVal newVal))))})
-
      (defn- make-register-dep [rx]
        (fn do-register-dep [dep id binding-info]
          (when *trace-capture* (*trace-capture* dep))
@@ -645,65 +615,13 @@
             (js-delete (.-deps rx) id)
             (.invalidate rx)))))

-     (def invalidates-mixin
-       #js {:notifyInvalidationWatches
-            (fn notifyInvalidationWatches []
-              (this-as this
-                       (goog.object/forEach
-                        (.-invalidation-watches this)
-                        (fn [f key _]
-                          (f key this)))))
-            :addInvalidationWatch
-            (fn addInvalidationWatch [key f]
-              (this-as this
-                       (when-not (aget (.-invalidation-watches this) key)
-                         (set! (.-iwatchers this) (inc (.-iwatchers this)))
-                         (aset (.-invalidation-watches this) key f))
-                       this))
-            :removeInvalidationWatch
-            (fn removeInvalidationWatch [key]
-              (this-as this
-                       (when (aget (.-invalidation-watches this) key)
-                         (set! (.-iwatchers this) (dec (.-iwatchers this)))
-                         (js-delete (.-invalidation-watches this) key))
-                       this))
-            :invalidate
-            (fn invalidate []
-              (this-as this
-                       (when-not (.-dirty this)
-                         (set! (.-dirty this) true)
-                         (if (> (.-watchers this) 0)
-                           ;; updates state and notifies watches
-                           (when (.compute this)
-                             (.notifyInvalidationWatches this))
-                           ;; updates only invalidation watches
-                           (.notifyInvalidationWatches this))
-                         (.clean this)
-                         )))})
-
      (def invalidates-binding-info
        (BindingInfo.
         #(.rawDeref %)
         #(.addInvalidationWatch % %2 %3)
         #(.removeInvalidationWatch % %2)
         #(.clean %)))
-
-     (def rx-mixin
-       #js
-       {:reactiveDeref (fn reactiveDeref []
-                         (this-as this
-                                  (if (.-lazy this)
-                                    (register-dep this (.-id this) invalidates-binding-info)
-                                    (register-dep this (.-id this) fwatch-binding-info))
-                                  (when (.-dirty this) (.compute this))
-                                  (.-state this)))
-        :rawDeref (fn rawDeref []
-                    (this-as this
-                             (when (.-dirty this)
-                               (binding [*register-dep* nil]
-                                 (.compute this)))
-                             (.-state this)))})
-
+
      (deftype ReactiveExpression [id ^:mutable state ^:mutable dirty f deps meta watches fwatches watchers
                                   invalidation-watches iwatchers
                                   register-dep-fn lazy trace-captures]
@@ -735,6 +653,58 @@
                                   (js-delete obj key)))
            (set! (.-dirty this) true)))
        (dispose [this] (.clean this))
+       (addFWatch [this key f]
+         (when-not (aget (.-fwatches this) key)
+           (set! (.-watchers this) (inc (.-watchers this)))
+           (aset (.-fwatches this) key f)))
+       (removeFWatch [this key]
+         (when (aget (.-fwatches this) key)
+           (set! (.-watchers this) (dec (.-watchers this)))
+           (js-delete (.-fwatches this) key)))
+       (notifyFWatches [this oldVal newVal]
+         (goog.object/forEach
+          (.-fwatches this)
+          (fn [f key _]
+            (f key this oldVal newVal)))
+         (doseq [[key f] (.-watches this)]
+           (f key this oldVal newVal)))
+
+       (notifyInvalidationWatches [this]
+         (goog.object/forEach
+          (.-invalidation-watches this)
+          (fn [f key _]
+            (f key this))))
+       (addInvalidationWatch [this key f]
+         (when-not (aget (.-invalidation-watches this) key)
+           (set! (.-iwatchers this) (inc (.-iwatchers this)))
+           (aset (.-invalidation-watches this) key f))
+         this)
+       (removeInvalidationWatch [this key]
+         (when (aget (.-invalidation-watches this) key)
+           (set! (.-iwatchers this) (dec (.-iwatchers this)))
+           (js-delete (.-invalidation-watches this) key))
+         this)
+       (invalidate [this]
+         (when-not (.-dirty this)
+           (set! (.-dirty this) true)
+           (if (> (.-watchers this) 0)
+             ;; updates state and notifies watches
+             (when (.compute this)
+               (.notifyInvalidationWatches this))
+             ;; updates only invalidation watches
+             (.notifyInvalidationWatches this))
+           (.clean this)))
+       (reactiveDeref [this]
+         (if (.-lazy this)
+           (register-dep this (.-id this) invalidates-binding-info)
+           (register-dep this (.-id this) fwatch-binding-info))
+         (when (.-dirty this) (.compute this))
+         (.-state this))
+       (rawDeref [this]
+         (when (.-dirty this)
+           (binding [*register-dep* nil]
+             (.compute this)))
+         (.-state this))

        IReactive
        (-get-binding-fns [this]
@@ -769,10 +739,6 @@

        IHash
        (-hash [this] (goog/getUid this)))
-
-     (apply-js-mixin ReactiveExpression fwatch-mixin)
-     (apply-js-mixin ReactiveExpression invalidates-mixin)
-     (apply-js-mixin ReactiveExpression rx-mixin)

      (defn rx*
        ([f] (rx* f true))


Use fancy destructuring

Use fancy destructuring

--- test/icecap/handlers/delay_test.clj
+++ test/icecap/handlers/delay_test.clj
@@ -33,7 +33,7 @@
 (defn fake-timeout
   "Create a test double for core.async/timeout."
   []
-  (let [{advance :advance add-waiter :add-waiter} (fake-clock)
+  (let [{:keys [advance add-waiter]} (fake-clock)
         timeout (fn [^long ms]
                   (let [c (chan)]
                     (add-waiter ms false (fn []


Fix clojure test

Fix clojure test

--- language-adaptors/rxjava-clojure/src/test/clojure/rx/lang/clojure/blocking_test.clj
+++ language-adaptors/rxjava-clojure/src/test/clojure/rx/lang/clojure/blocking_test.clj
@@ -36,7 +36,7 @@
   (testing "returns one element"
     (is (= 1 (b/single (rx/return 1)))))
   (testing "throw if empty"
-    (is (thrown? java.lang.IllegalArgumentException (b/single (rx/empty)))))
+    (is (thrown? java.util.NoSuchElementException (b/single (rx/empty)))))
   (testing "throw if many"
     (is (thrown? java.lang.IllegalArgumentException (b/single (rx/seq->o [1 2])))))
   (testing "rethrows errors"