Page Menu
Home
c4science
Search
Configure Global Search
Log In
Files
F90855148
websession.py
No One
Temporary
Actions
Download File
Edit File
Delete File
View Transforms
Subscribe
Mute Notifications
Award Token
Subscribers
None
File Metadata
Details
File Info
Storage
Attached
Created
Tue, Nov 5, 09:18
Size
6 KB
Mime Type
text/x-python
Expires
Thu, Nov 7, 09:18 (2 d)
Engine
blob
Format
Raw Data
Handle
22147133
Attached To
R3600 invenio-infoscience
websession.py
View Options
## $Id$
## CDS Invenio Web Session utilities, implementing persistence.
## This file is part of CDS Invenio.
## Copyright (C) 2002, 2003, 2004, 2005, 2006 CERN.
##
## CDS Invenio is free software; you can redistribute it and/or
## modify it under the terms of the GNU General Public License as
## published by the Free Software Foundation; either version 2 of the
## License, or (at your option) any later version.
##
## CDS Invenio is distributed in the hope that it will be useful, but
## WITHOUT ANY WARRANTY; without even the implied warranty of
## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
## General Public License for more details.
##
## You should have received a copy of the GNU General Public License
## along with CDS Invenio; if not, write to the Free Software Foundation, Inc.,
## 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA.
"""
Classes necessary for using in CDS Invenio, as a complement of session, which adds persistence to sessions
by using a MySQL table. Consists of the following classes:
- SessionNotInDb: Exception to be raised when a session doesn't exit
- pSession(Session): Specialisation of the class Session which adds persistence to session
- pSessionMapping: Implements only the necessary methods to make it work with the session manager
"""
import
cPickle
import
time
from
UserDict
import
UserDict
from
invenio.dbquery
import
run_sql
,
blob_to_string
,
OperationalError
,
IntegrityError
from
invenio.session
import
Session
class
SessionNotInDb
(
Exception
):
"""Exception to be raised when a requested session doesn't exist in the DB
"""
pass
class
pSession
(
Session
):
"""Specialisation of the class Session which adds persistence to sessions
by using a database table (it pickles itself into the corresponding row of
the table). The class provides methods to save and retrieve an instance
to/from the DB and to access the main session attributes (uid). The
table in the DB must have the following structure:
session_key - text - unique
uid - int
session_object - blob
Attributes:
__tableName -- (string) name of the table in the DB where the
sessions are going to be stored
__uid -- (int) user identifier who initiated the session
__dirty -- (bool) flag indicating whether the session has been
modified (and therefore needs to be saved back to the DB) or not
"""
__tableName
=
"session"
__ExpireTime
=
1050043127
def
__init__
(
self
,
request
,
id
,
uid
=-
1
):
Session
.
__init__
(
self
,
request
,
id
)
self
.
__uid
=
uid
self
.
__dirty
=
0
def
is_dirty
(
self
):
return
self
.
__dirty
def
getUid
(
self
):
return
self
.
__uid
def
setUid
(
self
,
newUid
):
if
newUid
:
self
.
__uid
=
int
(
newUid
)
self
.
__dirty
=
1
else
:
# something bad happened, e.g. database down, so return user id -1
self
.
__uid
=
-
1
self
.
__dirty
=
1
def
retrieve
(
cls
,
sessionId
):
"""method for retrieving a session from the DB for the given id. If the
id has no corresponding session an exception is raised
"""
sql
=
"select session_object from
%s
where session_key='
%s
'"
%
(
cls
.
__tableName
,
sessionId
)
try
:
res
=
run_sql
(
sql
)
except
OperationalError
:
raise
SessionNotInDb
(
"Session
%s
doesn't exist"
%
sessionId
)
if
len
(
res
)
==
0
:
raise
SessionNotInDb
(
"Session
%s
doesn't exist"
%
sessionId
)
s
=
cPickle
.
loads
(
blob_to_string
(
res
[
0
][
0
]))
return
s
retrieve
=
classmethod
(
retrieve
)
def
__getRepr
(
self
):
return
cPickle
.
dumps
(
self
)
def
save
(
self
):
"""method that tries to insert the session as NEW in the DB. If this
fails (giving an integrity error) it means the session already
exists there and it must be updated, so it performs the
corresponding SQL update
"""
repr
=
self
.
__getRepr
()
.
replace
(
"'"
,
"
\\\'
"
)
repr
=
repr
.
replace
(
'"'
,
'
\\\"
'
)
try
:
sql
=
'INSERT INTO
%s
(session_key, session_expiry, session_object, uid) values ("
%s
","
%s
","
%s
","
%s
")'
%
\
(
self
.
__class__
.
__tableName
,
self
.
id
,
self
.
get_access_time
()
+
60
*
60
*
24
*
2
,
repr
,
int
(
self
.
getUid
()))
res
=
run_sql
(
sql
)
except
IntegrityError
:
try
:
sql
=
'UPDATE
%s
SET uid=
%s
, session_expiry=
%s
, session_object="
%s
" WHERE session_key="
%s
"'
%
\
(
self
.
__class__
.
__tableName
,
int
(
self
.
getUid
()),
self
.
get_access_time
()
+
60
*
60
*
24
*
2
,
repr
,
self
.
id
)
res
=
run_sql
(
sql
)
except
OperationalError
:
pass
self
.
__dirty
=
0
except
OperationalError
:
self
.
__dirty
=
0
class
pSessionMapping
(
UserDict
):
"""Only the necessary methods to make it work with the session manager
have been implemented.
"""
def
__includeItemFromDB
(
self
,
key
):
if
key
not
in
self
.
data
.
keys
():
try
:
s
=
pSession
.
retrieve
(
key
)
self
.
data
[
key
]
=
s
except
SessionNotInDb
,
e
:
pass
def
__setitem__
(
self
,
key
,
v
):
"""when a session is added or updated in the dictionary it means it
must be updated within the DB
"""
v
.
save
()
UserDict
.
__setitem__
(
self
,
key
,
v
)
def
__getitem__
(
self
,
key
):
"""in order not to have to load all the sessions in the dictionary
(normally only a single session is needed on each web request) when
a session is requested the object looks to see if it is in the
dictionary (memory) and if not it tries to retrieve it from the
DB, puts it in the dictionary and returns the requested item. If
the session doesn't exist a normal KeyError exception is raised
"""
self
.
__includeItemFromDB
(
key
)
return
UserDict
.
__getitem__
(
self
,
key
)
def
has_key
(
self
,
key
):
"""same as for "__getitem__": it checks whether the session exist in the
local dictionary or in the DB.
"""
self
.
__includeItemFromDB
(
key
)
return
UserDict
.
has_key
(
self
,
key
)
Event Timeline
Log In to Comment