Permalink
Browse files

Separate out the business logic from the stuff that depends on it

  • Loading branch information...
1 parent aa6be05 commit befd48c621651c41512600ddfbb64982e12b75c4 @paul-lshift paul-lshift committed Jan 14, 2013
@@ -1,7 +1,7 @@
(ns eventframework.app
(:use
[eventframework.commands :only [valid-position? put-command! get-all-commands set-commands!]]
- [eventframework.business :only [listen-events!]]
+ [eventframework.apply-business :only [listen-events!]]
[compojure.core :only [defroutes context GET PUT POST]])
(:require
[clojure.tools.logging :as log]
@@ -0,0 +1,45 @@
+(ns eventframework.apply-business
+ (:use [eventframework.business :only [initial-state update-state gen-events]])
+ (:require eventframework.commands
+ [clojure.tools.logging :as log]))
+
+(defrecord CommandResult
+ [new-state events])
+
+(defn reduce-non-nil
+ "Like reduce, but skipping over values for which f yields nil.
+
+ (nil results are logged as errors)"
+ [f & args]
+ (apply reduce
+ (fn [x y] (if-let [x' (f x y)]
+ x'
+ (do (log/errorf "Fn ~s returned nil on ~s, keeping ~s"
+ f y x)
+ x)))
+ args))
+
+(defn state-before [position]
+ (reduce-non-nil update-state initial-state
+ (eventframework.commands/get-commands-before position)))
+
+(defn apply-commands [user state commands]
+ (let [apply-command
+ (fn [{state :new-state events :events} command]
+ (when-let [new-state (update-state state command)]
+ (CommandResult. new-state (into events (gen-events user state command)))))]
+ (reduce-non-nil apply-command
+ (CommandResult. state [])
+ commands)))
+
+(defn listen-events!
+ ([user position callback]
+ (listen-events! user position callback (state-before position)))
+ ([user position callback state]
+ (eventframework.commands/apply-or-enqueue-listener!
+ position
+ (fn [new-pos commands]
+ (let [{:keys [new-state events]} (apply-commands user state commands)]
+ (if (not-empty events)
+ (callback new-pos events)
+ (listen-events! user new-pos callback new-state)))))))
@@ -1,15 +1,9 @@
(ns eventframework.business
- (:require eventframework.commands
- [clojure.tools.logging :as log]))
-
-;; --------- Business logic
+ (:require [clojure.tools.logging :as log]))
(defrecord ThreadsAndSubscriptions
[threads subscriptions])
-(defrecord CommandResult
- [new-state events])
-
(def initial-state (ThreadsAndSubscriptions. {} {}))
(defn update-state [state command]
@@ -47,43 +41,3 @@
[]))
(do (log/warn "Ignoring unknown command type" type "while gen. events")
[]))))
-
-(defn reduce-non-nil
- "Like reduce, but skipping over values for which f yields nil.
-
- (nil results are logged as errors)"
- [f & args]
- (apply reduce
- (fn [x y] (if-let [x' (f x y)]
- x'
- (do (log/errorf "Fn ~s returned nil on ~s, keeping ~s"
- f y x)
- x)))
- args))
-
-;; ----------- Generic stuff not dependent on exact business logic
-
-(defn state-before [position]
- (reduce-non-nil update-state initial-state
- (eventframework.commands/get-commands-before position)))
-
-(defn apply-commands [user state commands]
- (let [apply-command
- (fn [{state :new-state events :events} command]
- (when-let [new-state (update-state state command)]
- (CommandResult. new-state (into events (gen-events user state command)))))]
- (reduce-non-nil apply-command
- (CommandResult. state [])
- commands)))
-
-(defn listen-events!
- ([user position callback]
- (listen-events! user position callback (state-before position)))
- ([user position callback state]
- (eventframework.commands/apply-or-enqueue-listener!
- position
- (fn [new-pos commands]
- (let [{:keys [new-state events]} (apply-commands user state commands)]
- (if (not-empty events)
- (callback new-pos events)
- (listen-events! user new-pos callback new-state)))))))
@@ -1,6 +1,7 @@
(ns eventframework.business-test
(:use
eventframework.business
+ eventframework.apply-business
clojure.test
midje.sweet))

0 comments on commit befd48c

Please sign in to comment.