;;;; Programmer: Kevin M. Rosenberg
;;;; Date Started: July 2003
;;;;
-;;;; $Id: sessions.lisp,v 1.3 2003/07/16 20:40:43 kevin Exp $
+;;;; $Id: sessions.lisp,v 1.4 2003/08/08 23:40:13 kevin Exp $
;;;;
;;;; This file and Wol are Copyright (c) 2003 by Kevin M. Rosenberg
;;;; *************************************************************************
(in-package #:wol)
-(defun make-new-session-id ()
- (random-string :length 24 :set :lower-alphanumeric))
+#||
+(awhen (and session-id (find-websession session-id ent))
+ (setf (websession-from-req req) it)
+ (setf (websession-method it) :url))
+||#
-(defun ensure-websession (key req ent method)
- "Find or make websession for key"
+(defun find-websession (key ent)
(let ((sessions (sessions (session-master (entity-project ent)))))
- ;; if sessions doesn't exist, then project is not session enabled
- (when sessions
- (cond
- ((null key)
- (make-websession req ent method))
- (t
- (maphash
- (lambda (k v)
- (declare (ignore k))
- (when (equal key (websession-key v))
- (setf (websession-lastref v) (get-universal-time))
- (return-from ensure-websession v)))
- sessions)
- (make-websession req ent method))))))
+ (maphash
+ (lambda (k v)
+ (declare (ignore k))
+ (when (equal key (websession-key v))
+ (setf (websession-lastref v) (get-universal-time))
+ (return-from find-websession v)))
+ sessions)
+ nil))
+
+(defun is-session-enabled (ent)
+ (not (null (sessions (session-master (entity-project ent))))))
-(defun make-websession (req ent method)
- (let* ((key (random-string :length 24 :set :lower-alphanumeric))
+(defun make-websession (req ent)
+ (let* ((key (random-string :length +length-session-id+
+ :set :lower-alphanumeric))
(sess (make-instance 'websession
:key key
:lastref (get-universal-time)
:lifetime (lifetime (session-master (entity-project ent)))
- :method method))
+ :method :try-cookie))
(hash (sessions (session-master (entity-project ent)))))
(when hash
(setf (gethash key hash) sess)
(setf (websession-from-req req) sess)
sess)))
-(defun compute-session (req ent)
- (awhen (and (request-plist req)
- (getf (request-plist req) :session-id))
- (setf (websession-from-req req)
- (ensure-websession it req ent :uri))))
-
+(defun compute-session (req ent)
+ (when (is-session-enabled ent)
+ (let ((key (cookie-session-key ent (request-cookies req)))
+ (has-cookie-key nil)
+ (has-url-key nil))
+ (if key
+ (setq has-cookie-key t)
+ (when (setq key (url-session-key (request-raw-uri req)))
+ (setq has-url-key t)))
+ (let* ((found-session (when key (find-websession key ent)))
+ (session (aif found-session it (make-websession req ent))))
+ (setf (websession-from-req req) session)
+ (when found-session
+ (if has-cookie-key
+ (setf (websession-method session) :cookies)
+ (when has-url-key
+ (setf (websession-method session) :url))))
+ session))))
+
;;; Reap expired sessions
(defmethod flush-expired (s)
(let ((sessions (sessions (session-master (cdr s)))))
(remhash (car s) sessions)
- (add-log-entry (cdr s) "flush expired session: key=~A" (websession-key (car s)))))
+ (add-log-entry (cdr s) "flush expired session: key=~A"
+ (websession-key (car s)))))
(defun is-session-expired (ws)
(> (get-universal-time) (+ (websession-lastref ws)
(websession-lifetime ws))))
+
+(defun is-raw-session-id (str)
+ (and (stringp str)
+ (> (length str) 2)
+ (char= #\~ (schar str 0) (schar str (1- (length str))))))
+
+(defun raw-session-id->session-id (str)
+ (subseq str 1 (1- (length str))))