File: SessionFactory.py

package info (click to toggle)
mobyle 1.5.5%2Bdfsg-6
  • links: PTS, VCS
  • area: main
  • in suites: buster
  • size: 8,288 kB
  • sloc: python: 22,709; makefile: 35; sh: 33; ansic: 10; xml: 6
file content (190 lines) | stat: -rw-r--r-- 8,404 bytes parent folder | download | duplicates (4)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
########################################################################################
#                                                                                      #
#   Author: Bertrand Neron,                                                            #
#   Organization:'Biological Software and Databases' Group, Institut Pasteur, Paris.   #  
#   Distributed under GPLv2 Licence. Please refer to the COPYING.LIB document.         #
#                                                                                      #
########################################################################################

import os 
from hashlib import md5

from Mobyle.AnonymousSession import AnonymousSession
from Mobyle.AuthenticatedSession import AuthenticatedSession
from Mobyle.MobyleError import SessionError , AuthenticationError 
from logging import getLogger

class SessionFactory( object ):
    """
    This class defines a session, that stores all the information
    about a user that should be persistent on the server
    @organization: Institut Pasteur
    @contact:mobyle@pasteur.fr
    """
    __ref = None


    def __new__( cls , cfg ):
        if cls.__ref is  None:
            self = super( SessionFactory , cls ).__new__( cls )
            self.log = getLogger( 'Mobyle.Session.SessionFactory' )
            self.cfg = cfg
            self.__sessions = {}
            cls.__ref = self

        return cls.__ref

    #OPENID, call by openid , do not check password
    def getOpenIdAuthenticatedSession( self , userEmailAddr , ticket_id=None ):
        """
        @return: an already existing openid authenticated session.
        @param userEmailAddr: the user email
        @type userEmailAddr: a Mobyle.Net.EmailAddress instance
        @raise AuthenticationError: the session doesn't already exists
        """
        mymd5 = md5()
        mymd5.update( str( userEmailAddr ) )
        key = mymd5.hexdigest()
        try:
            session = self.__sessions[ key ]
            return session
        except KeyError:
            sessionDir = os.path.normpath( os.path.join( self.cfg.user_sessions_path() , AuthenticatedSession.DIRNAME , key  ) )

            if os.path.exists( sessionDir ):
                session = AuthenticatedSession( self.cfg , userEmailAddr , passwd=None, ticket_id=ticket_id )
                self.__sessions[ session.getKey() ] = session
                return session
            else:
                raise AuthenticationError , "There is no user with this email"



    def getAuthenticatedSession( self , userEmailAddr , passwd=None, ticket_id=None ):
        """
        @return: an already existing authenticated session.
        @param userEmailAddr: the user email
        @type userEmailAddr: a Mobyle.Net.EmailAddress instance
        @param passwd: the session pass word 
        @type passwd: string
        @raise AuthenticationError: if the passwd doesn't match the session passwd
        @raise AuthenticationError: the session doesn't already exists
        """
        mymd5 = md5()
        mymd5.update( str( userEmailAddr ) )
        key = mymd5.hexdigest()

        try:
            session = self.__sessions[ key ]
            if session.checkPasswd( passwd ):
                return session
            else:
                raise AuthenticationError , "There is no user with this email and password"
       
        except KeyError: 
            sessionDir = os.path.normpath( os.path.join( self.cfg.user_sessions_path() , AuthenticatedSession.DIRNAME , key ) )
          
            if os.path.exists( sessionDir ):
                session = AuthenticatedSession( self.cfg , userEmailAddr , passwd=passwd, ticket_id=ticket_id )
                self.__sessions[ session.getKey() ] = session  
                return session
            else: 
                raise AuthenticationError , "There is no user with this email" 



    def getAnonymousSession( self , key = None ):
        """
        @return: an anonymous session. If key is None create a new anonymous session
        @rtype: Session object
        @param key: the key to identify a anonymous session
        @type key: string
        @raise SessionError: if key is specified and doesn't match any session.
        """
        anonymousSessionAllowed = self.cfg.anonymousSession()
        if anonymousSessionAllowed== 'no':
            self.log.error("SessionFactory/can't create anonymous session ANONYMOUS_SESSION is set to \"no\" in Local/Config/Config.py")          
            raise SessionError , "can't create anonymous session: permission denied"
        try:
            session = self.__sessions[ key ]
        except KeyError: 
            if key :
                sessionDir = self.__getSessionDir( key )
                
                if os.path.exists( sessionDir ):
                    self.log.debug( "SessionFactory.getAnonymousSession( key= %s )/ the dir exist I 'll return this session" % key)
                    session = AnonymousSession( self.cfg , key )
                else: 
                    self.log.error( "can't retrieve anonymous session, the Key: %s doesn't match with any Session" % key )
                    raise SessionError , "wrong Key: %s" % key
                   
            else: #new session
                session = AnonymousSession( self.cfg )
                self.log.debug( "SessionFactory.getAnonymousSession( key= %s ) / a new anonymous has been created . I 'll return this session" % key)
                
            self.__sessions[session.getKey()] = session  
            
        self.log.debug( "SessionFactory.getAnonymousSession( key= %s ) I return this anonymous session :key=" + str( session.getKey() )) 
        return session
   

    def createAuthenticatedSession( self , userEmailAddr , passwd ):
        """
        create an authenticated session with email as login and passwd as pass word
        @param userEmailAddr: the user email
        @type userEmailAddr: a Mobyle.Net.EmailAddress object
        @param passwd: the user password
        @type passwd: string
        @return: a new authenticated session
        @rtype: session instance
        @raise AuthenticationError: if there is already a session with this email, or the email is not allowed on this server
        """
        authenticatedSessionAllowed = self.cfg.authenticatedSession()
      
        if authenticatedSessionAllowed == 'no':
            self.log.error("can't create  session AUTHENTICATED_SESSION is set to \"no\" in Local/Config/Config.py")          
            raise SessionError , "can't create  authenticated session: permission denied"

        mymd5 = md5()
        mymd5.update( str( userEmailAddr ) )
        key = mymd5.hexdigest()

        if self.__sessions.has_key( key ) : 
            msg = "Try to create a new Session with email %s, the %s Session already exist" % ( userEmailAddr , key)
            self.log.error( msg )        
            raise AuthenticationError , "user with the email you specify already exist" 
       
        else:  
            sessionDir = os.path.normpath( os.path.join( self.cfg.user_sessions_path() , AuthenticatedSession.DIRNAME , key ) )
          
            if os.path.exists( sessionDir ):
                msg = "Try to create a new Session with email %s, the %s Session already exist" % ( userEmailAddr , key)
                self.log.error( msg )
                raise AuthenticationError , "user with the email you specify already exist" 
                
            session = AuthenticatedSession( self.cfg , userEmailAddr , passwd )
            self.__sessions[ session.getKey() ] = session   
            return session
  

    def removeSession( self , key ):
        sessionDir = self.__getSessionDir(  key )
       
        for File in os.listdir( sessionDir ):
            os.unlink( os.path.join( sessionDir , File ) )
        os.rmdir( sessionDir )
        del self.__sessions[ key ]


    def __getSessionDir( self , key ) :
 
        if  len ( key ) == 32  :
            #a md5 value is always encode in 32 char
            return os.path.normpath( os.path.join( self.cfg.user_sessions_path() , AuthenticatedSession.DIRNAME , key  ) )
        else:
            ##the anonymous key have 15 char length
            return os.path.normpath( os.path.join( self.cfg.user_sessions_path() , AnonymousSession.DIRNAME , key ) )