Scott Chapman
scottie at mischko.com
Mon Mar 28 13:48:15 EST 2005
Here's my uberServlet which demonstrates this "interesting" behavior. If I use the external redirect and comment out the internal redirect, everything works perfectly. Note that I have changed mpservlets to call prep BEFORE auth. This makes better sense to me. uberServlet: > from mod_python.servlet import Servlet > from mod_python import apache,util > from pages import Pages > import data_object > > class uberservlet(Servlet): > use_session = True > > def prep(self): > Servlet.prep(self) > > def auth(self): > pages=Pages() > > methodName=self.req.uri[:len(self.req.uri)-len(self.req.path_info)][1:] > self.req.log_error('AUTH - methodName: ' + methodName) > if methodName in ['login','doLogin','logout']: > return > method=getattr(pages,methodName,None) > if method: > self.req.log_error('AUTH - method found') > > # Check to see if the page requires user to be logged in > requiresLogin = data_object.requires_login(methodName) > > if requiresLogin == 'unknown': > self.req.log_error('AUTH - page: %s not found in pages > table' % methodName) > raise apache.SERVER_RETURN, apache.HTTP_NOT_FOUND > > if not requiresLogin: > self.req.log_error('AUTH - page: %s does not require > login' % methodName) > return > > if requiresLogin: > self.req.log_error('AUTH - page: %s requires login' % > methodName) > userName = self.session.get('username', None) > # Check to see if the user is logged in > if userName: > self.req.log_error('AUTH - user already logged in: > %s' % userName) > # Check that the user has access to the page. > access_ok = > data_object.check_access(methodName,userName) > if access_ok: > return > else: > raise apache.SERVER_RETURN, apache.HTTP_FORBIDDEN > else: > self.req.log_error('AUTH - user not logged in') > self.session['returnto'] = self.req.unparsed_uri > self.req.log_error('AUTH - sid when returnto set: > ' + str(self.session.id())) > self.req.log_error('AUTH - returnto: ' + > self.session['returnto']) > self.req.log_error('AUTH - internal redirect to > login') > #Tried doing an internal redirect here but > #things don't go well. Code is executed after the > internal redirect. > #The cookie with the session info is not sent to > the client here so the returnto is lost. > self.session.save() > self.session.unlock() > self.req.internal_redirect('/login') > > #util.redirect(self.req,'/login') > > #The next line should never be reached. > #It is reached when internal redirect is done, not > when external is done. > self.req.log_error('AUTH - logging after redirect > - should never happen!') > else: > self.req.log_error('AUTH - method not found') > raise apache.SERVER_RETURN, apache.HTTP_NOT_FOUND > return > > def respond(self): > > methodName=self.req.uri[:len(self.req.uri)-len(self.req.path_info)][1:] > self.req.log_error ('UBERSERVLET RESPOND - method name: %s' % > methodName) > pages=Pages() > method=getattr(pages,methodName,None) > if method: > self.req.log_error('UBERSERVLET RESPOND - calling method') > if self.form.list: > self.write(method(self,self.form)) > else: > self.write(method(self)) > return True > else: > self.req.log_error('UBERSERVLET RESPOND - method not found') > return False > Here's the "pages" contents: > from mod_python import util, apache > import data_object > import templates > import table_builder > > class Pages: > def login(self,uberServlet): > center=templates.login_template > return templates.site_template(2,center=center,menu=False) > > > def doLogin(self,uberServlet, form): > login = form.getfirst('login') > password = form.getfirst('password') > if data_object.checkLoginAndPassword(login, password): > uberServlet.session['username'] = login > uberServlet.req.log_error('DOLOGIN - username and password > confirmed') > uberServlet.req.log_error('DOLOGIN - sid: ' + > str(uberServlet.session.id())) > return_to = uberServlet.session.pop('returnto','/index') > uberServlet.req.log_error('DOLOGIN - return_to' + return_to) > util.redirect(uberServlet.req,return_to) > else: > return self.login() > > def table(self,uberServlet): > return .... Here's my log of the session, using internal redirect with code above: > --- session cookies cleared in browser and request for /table > submitted ---- > HANDLER-calling prep > HANDLER-calling auth > AUTH - methodName: table > AUTH - method found > AUTH - page: table requires login > AUTH - user not logged in > AUTH - sid when returnto set: 01e782d539e43cf4d490196e104bd257 > AUTH - returnto: /table > AUTH - internal redirect to login > HANDLER-calling prep > HANDLER-calling auth > AUTH - methodName: login > HANDLER-calling respond > UBERSERVLET RESPOND - method name: login > UBERSERVLET RESPOND - calling method > HANDLER-calling wrapup > AUTH - logging after redirect - should never happen! > HANDLER-calling respond > UBERSERVLET RESPOND - method name: table > UBERSERVLET RESPOND - calling method > HANDLER-calling wrapup > ---- login screen in browser ---- > HANDLER-calling prep, referer: http://nsnserver/table > HANDLER-calling auth, referer: http://nsnserver/table > AUTH - methodName: doLogin, referer: http://nsnserver/table > HANDLER-calling respond, referer: http://nsnserver/table > UBERSERVLET RESPOND - method name: doLogin, referer: > http://nsnserver/table > UBERSERVLET RESPOND - calling method, referer: http://nsnserver/table > DOLOGIN - username and password confirmed, referer: http://nsnserver/table > DOLOGIN - sid: b8efe481dabadabdba61b7301de32f98, referer: > http://nsnserver/table > DOLOGIN - return_to/index, referer: http://nsnserver/table > ---- table contents shows up in browser as text (no headers sent back > to browser) followed by redirect Here's what showed in the browser (not view source): <-snip-> </tr> </tbody> </table> </body> </html> HTTP/1.1 302 Found Date: Mon, 28 Mar 2005 18:41:40 GMT Server: Apache/2.0.53 (Unix) mod_ssl/2.0.53 OpenSSL/0.9.7d mod_python/3.1.4 Python/2.4.1c2 Location: /index Keep-Alive: timeout=15, max=99 Connection: Keep-Alive Transfer-Encoding: chunked Content-Type: text/plain 38 <p>The document has moved <a href="/index">here</a></p> 0 Cordially, Scott
|