Created
May 29, 2011 02:04
-
-
Save leandrosilva/997393 to your computer and use it in GitHub Desktop.
Playing with Clojure, Redis, Compojure, and Jedis library
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
As always, I'm just playing with interesting things to relax a little bit. Just it. | |
== 1. Dependencies | |
I tried to use redis-clojure but it sucks and I shifted to Jedis which rocks. So if you want to try | |
as well, this little joke (ops! I mean...) program depends on: | |
* org.clojure/clojure "1.2.0" | |
* org.clojure/clojure-contrib "1.2.0" | |
* redis.clients/jedis "1.5.2" | |
* commons-pool/commons-pool "1.4" | |
I suggest use Leiningen to get these. ;) | |
== 2. Improvements | |
In this program, I'm playing with Redis set, list, and key-value to implement a primitive queue. But | |
y'know, it's not too idiomatic Clojure because I'm using a Java library directly. I think that It | |
can be improved a lot. If you try, let me know please. | |
== 3. Output | |
So if you run in a `lein repl` instance: | |
user=> (do (load-file "src/qdis/queue.clj") (qdis.queue/run-tests)) | |
...you should see something like that: | |
::: running test functions ::: | |
TEST 1 (enqueue 'padoca' 'panguan') = qdis:queue:padoca:uuid:272 | |
TEST 2 (dequeue 'padocax') = :queue-not-found-or-is-empty | |
TEST 3 (dequeue 'padoca') = {:item-uuid qdis:queue:padoca:uuid:272, :item panguan} | |
TEST 4.1 (enqueue 'padoca' 'panguan1') = qdis:queue:padoca:uuid:273 | |
TEST 4.2 (enqueue 'padoca' 'panguan2') = qdis:queue:padoca:uuid:274 | |
TEST 4.3 (enqueue 'padoca' 'panguan3') = qdis:queue:padoca:uuid:275 | |
TEST 4.4 (dequeue 'padoca') = {:item-uuid qdis:queue:padoca:uuid:273, :item panguan1} | |
TEST 4.5 (dequeue 'padoca') = {:item-uuid qdis:queue:padoca:uuid:274, :item panguan2} | |
TEST 4.6 (dequeue 'padoca') = {:item-uuid qdis:queue:padoca:uuid:275, :item panguan3} | |
:ok |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
(ns qdis.jedis | |
(:import [redis.clients.jedis Jedis JedisPool])) | |
;; use a jedis connection pool to be thread safe | |
(def ^{:private true} *jedis-pool* (ref nil)) | |
(defn initialize-pool [redis-config] | |
(dosync | |
(ref-set *jedis-pool* (JedisPool. (:host redis-config) (:port redis-config))))) | |
(defn finalize-pool [] | |
(.destroy @*jedis-pool*)) | |
(defn connect [] | |
(let [jedis (.getResource @*jedis-pool*)] | |
(.select jedis 0) | |
jedis)) | |
(defn disconnect [jedis] | |
(.returnResource @*jedis-pool* jedis)) | |
;; redis-like api | |
(def jedis) | |
(defmacro with-jedis [& exprs] | |
`(do | |
(binding [jedis (connect)] | |
(let [result# ~@exprs] | |
(disconnect jedis) | |
result#)))) | |
(defn -set | |
([jedis* key value] (.set jedis* key value)) | |
([key value] (-set jedis key value))) | |
(defn -get | |
([jedis* key] (.get jedis* key)) | |
([key] (-get jedis key))) | |
(defn -del | |
([jedis* key] (.del jedis* (into-array [key]))) | |
([key] (-del jedis key))) | |
(defn -sadd | |
([jedis* set-key value] (.sadd jedis* set-key value)) | |
([set-key value] (.sadd jedis set-key value))) | |
(defn -incr | |
([jedis* key] (.incr jedis* key)) | |
([key] (.incr jedis key))) | |
(defn -lpush | |
([jedis* list-key value] (.lpush jedis* list-key value)) | |
([list-key value] (.lpush jedis list-key value))) | |
(defn -rpop | |
([jedis* list-key] (.rpop jedis* list-key)) | |
([list-key] (.rpop jedis list-key))) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
(ns qdis.queue | |
(:use qdis.jedis)) | |
;; settings | |
(def ^{:private true} queue-set "qdis:queueset") | |
(def ^{:private true} queue-uuid "qdis:uuid") | |
(def ^{:private true} qdis-tag "qdis:") | |
(def ^{:private true} queue-tag "queue:") | |
(def ^{:private true} uuid-tag ":uuid:") | |
(defn- which-queue-name-for [queue] | |
(str qdis-tag queue-tag queue)) | |
(defn- which-item-uuid-for [queue-name uuid] | |
(str queue-name uuid-tag uuid)) | |
;; api | |
(defn enqueue [queue item] | |
(with-jedis | |
(do | |
(let [queue-name (which-queue-name-for queue)] | |
;; create the queue (if it doesn't exists) | |
(qdis.jedis/-sadd queue-set queue-name) | |
;; get a uuid to received item | |
(let [item-uuid (which-item-uuid-for queue-name (qdis.jedis/-incr queue-uuid))] | |
;; bind this uuid to item's value | |
(qdis.jedis/-set item-uuid item) | |
;; and finally push item's uuid to queue | |
(qdis.jedis/-lpush queue-name item-uuid) | |
item-uuid))))) | |
(defn dequeue [queue] | |
(with-jedis | |
(do | |
(let [result (let [queue-name (which-queue-name-for queue)] | |
;; get item's uuid from queue | |
(let [item-uuid (qdis.jedis/-rpop queue-name)] | |
(if (nil? item-uuid) | |
;; being nil, it means that this queue doesn't exists or is empty | |
:queue-not-found-or-is-empty | |
;; or since queue exists, get and del the item | |
(let [item (qdis.jedis/-get item-uuid)] | |
(qdis.jedis/-del item-uuid) | |
{:item-uuid item-uuid :item item}))))] | |
result)))) | |
;; tests | |
(defn run-tests [] | |
(qdis.jedis/initialize-pool {:host "127.0.0.1" :port 6379}) | |
(println "\n::: running test functions :::\n") | |
(println "TEST 1 (enqueue 'padoca' 'panguan') =" (enqueue "padoca" "panguan")) | |
(println "TEST 2 (dequeue 'padocax') =" (dequeue "padocax")) | |
(println "TEST 3 (dequeue 'padoca') =" (dequeue "padoca")) | |
(println) | |
(println "TEST 4.1 (enqueue 'padoca' 'panguan1') =" (enqueue "padoca" "panguan1")) | |
(println "TEST 4.2 (enqueue 'padoca' 'panguan2') =" (enqueue "padoca" "panguan2")) | |
(println "TEST 4.3 (enqueue 'padoca' 'panguan3') =" (enqueue "padoca" "panguan3")) | |
(println "TEST 4.4 (dequeue 'padoca') =" (dequeue "padoca")) | |
(println "TEST 4.5 (dequeue 'padoca') =" (dequeue "padoca")) | |
(println "TEST 4.6 (dequeue 'padoca') =" (dequeue "padoca")) | |
(println) | |
(qdis.jedis/finalize-pool) | |
:ok) |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment