991807da55ff

Moar.
[view raw] [browse files]
author Steve Losh <steve@stevelosh.com>
date Mon, 03 Oct 2011 19:52:37 -0400
parents 8fce5bbfe1d3
children fb4c1da11613
branches/tags (none)
files project.clj resources/public/css/style.less src/newseasons/middleware/session/redis.clj src/newseasons/models/shows.clj src/newseasons/models/users.clj src/newseasons/server.clj src/newseasons/templates/main.clj src/newseasons/views/main.clj

Changes

--- a/project.clj	Thu Sep 29 23:28:26 2011 -0400
+++ b/project.clj	Mon Oct 03 19:52:37 2011 -0400
@@ -2,7 +2,8 @@
             :description "FIXME: write this!"
             :dependencies [[org.clojure/clojure "1.2.1"]
                            [org.clojure/clojure-contrib "1.2.0"]
-                           [noir "1.1.0"]
+                           [noir "1.2.0"]
+                           [postmark "1.0.0"]
                            [cheshire "2.0.2"]
                            [clj-http "0.2.1"]
                            [aleph "0.2.0-beta2"]]
--- a/resources/public/css/style.less	Thu Sep 29 23:28:26 2011 -0400
+++ b/resources/public/css/style.less	Mon Oct 03 19:52:37 2011 -0400
@@ -81,8 +81,8 @@
 }
 section.message {
     border-bottom: 2px solid #ddd;
-    margin-top: -12px;
-    margin-bottom: 32px;
+    margin-top: -26px;
+    margin-bottom: 44px;
 }
 .page-title {
     position: relative;
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/newseasons/middleware/session/redis.clj	Mon Oct 03 19:52:37 2011 -0400
@@ -0,0 +1,29 @@
+(ns newseasons.middleware.session.redis
+  "Redis session storage."
+  (:use ring.middleware.session.store)
+  (:use [cheshire.core :only (generate-string parse-string)])
+  (:use [aleph.redis :only (redis-client)])
+  (:import java.util.UUID))
+
+
+(deftype RedisStore [r]
+  SessionStore
+
+  (read-session [_ key]
+    (parse-string (or @(r [:get key]) "{}")))
+
+  (write-session [_ key data]
+    (let [key (or key (str (UUID/randomUUID)))]
+      @(r [:set key (generate-string data)])
+      (r [:expire key (* 60 60 24 30)])
+      key))
+
+  (delete-session [_ key]
+    @(r [:del key])
+    nil))
+
+(defn redis-store
+  "Creates a Redis-backed storage engine."
+  [host password] (RedisStore. (redis-client {:host host :password password})))
+
+
--- a/src/newseasons/models/shows.clj	Thu Sep 29 23:28:26 2011 -0400
+++ b/src/newseasons/models/shows.clj	Mon Oct 03 19:52:37 2011 -0400
@@ -10,6 +10,7 @@
 ; Shows are stored as hashes.
 ;
 ; shows:<iTunes artist ID> = {
+;     id: show id
 ;     title: show tile
 ;     image: url to show's image
 ;     url: url to view the show on iTunes
@@ -18,7 +19,15 @@
 ; Code ------------------------------------------------------------------------
 
 (defn show-get [id]
-  (apply hash-map @(r [:hgetall (key-show id)])))
+  (let [show (apply hash-map @(r [:hgetall (key-show id)]))]
+    (when (not (empty? show))
+      {:id (show "id")
+       :title (show "title")
+       :image (show "image")
+       :url (show "url")})))
+
+(defn show-set-id! [id new-id]
+  @(r [:hset (key-show id) "id" new-id]))
 
 (defn show-set-title! [id new-title]
   @(r [:hset (key-show id) "title" new-title]))
--- a/src/newseasons/models/users.clj	Thu Sep 29 23:28:26 2011 -0400
+++ b/src/newseasons/models/users.clj	Mon Oct 03 19:52:37 2011 -0400
@@ -1,5 +1,6 @@
 (ns newseasons.models.users
   (:use newseasons.models.keys)
+  (:use [newseasons.models.shows :only (show-get)])
   (:require [noir.util.crypt :as crypt])
   (:use [aleph.redis :only (redis-client)]))
 
@@ -25,7 +26,7 @@
   (let [user (apply hash-map @(r [:hgetall (key-user email)]))]
     (when (not (empty? user))
       (merge {:email (user "email") :pass (user "pass")}
-             {:shows @(r [:smembers (key-user-shows email)])}))))
+             {:shows (map show-get @(r [:smembers (key-user-shows email)]))}))))
 
 (defn user-set-email! [email new-email]
   @(r [:hset (key-user email) "email" new-email]))
--- a/src/newseasons/server.clj	Thu Sep 29 23:28:26 2011 -0400
+++ b/src/newseasons/server.clj	Mon Oct 03 19:52:37 2011 -0400
@@ -1,4 +1,5 @@
 (ns newseasons.server
+  (:use [newseasons.middleware.session.redis :only (redis-store)])
   (:require [noir.server :as server]))
 
 (server/load-views "src/newseasons/views/")
@@ -7,5 +8,6 @@
   (let [mode (keyword (or (first m) :dev))
         port (Integer. (get (System/getenv) "PORT" "8000"))]
     (server/start port {:mode mode
-                        :ns 'newseasons})))
+                        :ns 'newseasons
+                        :session-store (redis-store "localhost" "devpass")})))
 
--- a/src/newseasons/templates/main.clj	Thu Sep 29 23:28:26 2011 -0400
+++ b/src/newseasons/templates/main.clj	Mon Oct 03 19:52:37 2011 -0400
@@ -14,6 +14,12 @@
   (list [:label {:for (str "id_" field-name)} label]
         (fieldfn field-name)))
 
+(defn pluralize
+  ([coll] (pluralize coll "s"))
+  ([coll plural-suffix] (if (= 1 (count coll))
+                         ""
+                         plural-suffix)))
+
 
 ; Layout ----------------------------------------------------------------------
 (defpartial base [& content]
@@ -67,8 +73,17 @@
                [:p "New Seasons will notify you when your favorite TV "
                    "shows have new seasons on iTunes.  That's it."]]))
 
-(defpartial user [email]
-            (inner (str "Hello, " email)
+
+(defpartial user-show [show]
+            [:li.show.group
+             [:img {:src (show :image)}]
+             [:h3 (link-to (show :url) (show :title))]
+             (form-to [:post "/rem"]
+                      [:input {:type "hidden" :name "artist-id" :value (show :id)}]
+                      (submit-button "Remove"))])
+
+(defpartial user [user]
+            (inner (str "Hello, " (:email user))
                    [:div.eight.columns
                     [:form {:action "/search"}
                      (field text-field
@@ -76,7 +91,17 @@
                             "Which show do you want to keep track of?")
                      (submit-button "Search")]]
                    [:div.eight.columns
-                    [:p "You're not currently waiting for any shows."]]))
+                    (let [shows (:shows user)]
+                      (if (empty? shows)
+                        [:p "You're not currently watching any shows."]
+                        (list
+                          [:p
+                           "You're watching "
+                           (count shows)
+                           " show"
+                           (pluralize shows)
+                           "."]
+                          [:ul (map user-show shows)])))]))
 
 
 (defpartial result [r]
--- a/src/newseasons/views/main.clj	Thu Sep 29 23:28:26 2011 -0400
+++ b/src/newseasons/views/main.clj	Mon Oct 03 19:52:37 2011 -0400
@@ -117,12 +117,14 @@
          (login-required
            (if (not= email (sess/get :email))
              (force-login)
-             (t/user email))))
+             (let [user (users/user-get email)]
+               (t/user user)))))
 
 
 ; Search ----------------------------------------------------------------------
 (defn store-show [show]
   (let [id (show "artistId")]
+    (shows/show-set-id! id id)
     (shows/show-set-title! id (show "artistName"))
     (shows/show-set-image! id (show "artworkUrl100"))
     (shows/show-set-url! id (show "artistViewUrl"))))
@@ -146,6 +148,14 @@
            (resp/redirect "/")))
 
 
+; Remove ----------------------------------------------------------------------
+(defpage [:post "/rem"] {:keys [artist-id]}
+         (login-required
+           (users/user-rem-show! (sess/get :email) artist-id)
+           (flash! "Removed a show from your list.")
+           (resp/redirect "/")))
+
+
 ; Change Password -------------------------------------------------------------
 (defpage [:get "/password"] []
          (login-required