summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/datalayer.clj106
-rw-r--r--src/site.clj18
2 files changed, 85 insertions, 39 deletions
diff --git a/src/datalayer.clj b/src/datalayer.clj
index 8590a7d..c74315a 100644
--- a/src/datalayer.clj
+++ b/src/datalayer.clj
@@ -5,6 +5,7 @@
(:use clojure.contrib.sql
clojure.contrib.json.write
clojure.contrib.json.read
+ multikey-cache
config
jedis
message
@@ -69,14 +70,28 @@ WHERE u.nick = ANY(?)"
(do-select [(recent-posts-nick-query nil)
(sql-array "text" nicks)]))
+(defn fetch-messages-by-id-uncached [m-ids]
+ (when-not (empty? m-ids)
+ (let [query "SELECT m.message_id, m.content, m.created_on, m.user_id,
+ m.is_image, u.nick, u.avatar, r.key, r.admin_only
+ FROM messages m, users u, rooms r
+ WHERE m.user_id = u.user_id
+ AND r.room_id = m.room_id
+ AND m.message_id = ANY(?)"
+ res (do-select [query
+ (sql-array "int" m-ids)])]
+ (sort-by-index-in res m-ids :message_id))))
+
+(def message-cache-size 50000)
+(def message-cache (multikey-lru-cache
+ fetch-messages-by-id-uncached
+ message-cache-size))
+
+(defn fetch-messages-by-id [m-ids]
+ (get-keys message-cache m-ids))
+
(defn fetch-message-by-id [m-id]
- (let [query "SELECT m.message_id, m.content, m.created_on, m.user_id,
- m.is_image, u.nick, u.avatar, r.key, r.admin_only
- FROM messages m, users u, rooms r
- WHERE m.user_id = u.user_id
- AND r.room_id = m.room_id
- AND m.message_id = ?"]
- (first (do-select [query (maybe-parse-int m-id -1)]))))
+ (get-key message-cache m-id))
;;;; Popular Posts
@@ -95,7 +110,18 @@ WHERE u.nick = ANY(?)"
(tags/fetch-dumps-by-ids msg-ids viewer-nick)))))
-;;;; Redis Favscores
+;;;; Redis Favscores and Hall
+
+(def redis-hall-key "hall")
+
+(defn fetch-redis-hall [viewer-nick]
+ (let [ids (map maybe-parse-int
+ (redis/with-server redis-server
+ (redis/zrevrange redis-hall-key 0 (dec num-hall-dumps))))]
+ (if-not (empty? ids)
+ (sort-by
+ #(* -1 (:count %))
+ (tags/fetch-dumps-by-ids ids viewer-nick)))))
(def score-piece-map
(zipmap
@@ -115,15 +141,34 @@ WHERE u.nick = ANY(?)"
(def redis-favscores-key "favscores")
+(defn redis-daily-hall-key [date-str]
+ (str "hall:daily:" date-str))
+
+(defn fetch-redis-zset [key symbol offset num]
+ (for [t (with-jedis
+ #(.zrevrangeWithScores %
+ key
+ offset
+ (+ offset num 1)))
+ :when (> (int (.getScore t)) 0)]
+ {symbol (.getElement t)
+ :score (int (.getScore t))}))
+
+(defn fetch-redis-daily-hall [date-str offset num]
+ (let [msg-ids (fetch-redis-zset (redis-daily-hall-key date-str)
+ :message_id
+ offset
+ num)
+ full-msgs (fetch-messages-by-id (map :message_id msg-ids))]
+ (for [[info full] (map list msg-ids full-msgs)]
+ (assoc full :score (:score info)))))
+
(defn fetch-redis-directory [page num]
(vec
- (for [t (with-jedis
- #(.zrevrangeWithScores %
- redis-favscores-key
- (* page num)
- (dec (* (inc page) num))))]
- {:nick (.getElement t)
- :score (int (.getScore t))})))
+ (fetch-redis-zset redis-favscores-key
+ :nick
+ (* page num)
+ (dec (* (inc page) num)))))
(defn fetch-redis-favscore [nick]
(if (= (lower-case nick) "scottbot")
@@ -133,29 +178,20 @@ WHERE u.nick = ANY(?)"
(redis/zscore "favscores" (lower-case nick)))
0)))
-(defn incrby-redis-favscore! [nick msg-id inc is-image]
- (let [msg-id (str msg-id)
- inc (double inc)]
+(defn incrby-redis-favscore! [msg incr]
+ (let [msg-id (str (:message_id msg))
+ is-image? (:is_image msg)
+ nick (lower-case (:nick msg))
+ incr (double incr)]
(with-jedis
#(do
- (.zincrby % "favscores" inc (lower-case nick))
- (when is-image
- (.zincrby % (str "popular:" nick) inc msg-id)
- (.zincrby % "hall" inc msg-id))))))
-
-
-;;;; Redis Hall of Fame
+ (.zincrby % "favscores" incr nick)
+ (when is-image?
+ (let [date-str (format-yyyymmdd (:created_on msg))]
+ (.zincrby % (redis-daily-hall-key date-str) incr msg-id)
+ (.zincrby % (redis-popular-key nick) incr msg-id)
+ (.zincrby % redis-hall-key incr msg-id)))))))
-(def redis-hall-key "hall")
-
-(defn fetch-redis-hall [viewer-nick]
- (let [ids (map maybe-parse-int
- (redis/with-server redis-server
- (redis/zrevrange redis-hall-key 0 (dec num-hall-dumps))))]
- (if-not (empty? ids)
- (sort-by
- #(* -1 (:count %))
- (tags/fetch-dumps-by-ids ids viewer-nick)))))
;;;; Message insertion
diff --git a/src/site.clj b/src/site.clj
index 90db5dc..43e7f9a 100644
--- a/src/site.clj
+++ b/src/site.clj
@@ -192,8 +192,18 @@
;; Landing
+(defn front-page [session]
+ (let [st (fetch-template "frontpage" session)
+ date-str (format-yyyymmdd (Date.))
+ dumps (map process-message-for-output
+ (fetch-redis-daily-hall date-str 0 100))]
+ (.setAttribute st "dumps" dumps)
+ (.toString st)))
+
(defn landing [session]
- (redirect-to "/chat"))
+ (if (is-vip? session)
+ (front-page session)
+ (redirect-to "/chat")))
(defn log-login [user_id ip]
;; i'm using do-cmds here because update-values can't deal with stuff like 'last_login = now()'
@@ -763,7 +773,7 @@ WHERE user_id IN
(when (and (= tag "favorite")
(not (= (msg :nick) (:nick user))))
(if-not (or (:admin_only msg) (= (:user_id user) (:user_id msg)))
- (incrby-redis-favscore! (:nick msg) (:message_id msg) 1 (:is_image msg)))
+ (incrby-redis-favscore! msg 1))
(insert-fav-notification! (msg :nick)
(user :nick)
(user :avatar)
@@ -801,7 +811,7 @@ WHERE user_id IN
(if-not (zero? rows-deleted)
(do
(if-not (or (:admin_only msg) (= user-id (:user_id msg)))
- (incrby-redis-favscore! (:nick msg) msg-id -1 (:is_image msg)))
+ (incrby-redis-favscore! msg -1))
(resp-success "OK"))
(resp-error "NO_TAG")))))
@@ -1126,7 +1136,7 @@ WHERE user_id IN
(.setAttribute st "dumps" (map process-message-for-output msgs))
(.toString st)))
-;; MGMT logic
+;; MGMT
(def mgmt-pw "idontgetit")