Google App Engine Sessions and Cookies ae-09-session .

63
Google App Engine Sessions and Cookies ae-09-session www.appenginelearn.com

Transcript of Google App Engine Sessions and Cookies ae-09-session .

Page 1: Google App Engine Sessions and Cookies ae-09-session .

Google App Engine Sessions and Cookies

ae-09-session

www.appenginelearn.com

Page 2: Google App Engine Sessions and Cookies ae-09-session .

Cookies and SessionsMaintaining State in HTTP

Page 3: Google App Engine Sessions and Cookies ae-09-session .

High Level Summary

•The web is “stateless”

•The browser does not maintain a connection to the server while you are looking at a page.

•You may never come back to the same server

•Or it may be a long time

•Or it may be one second later

Page 4: Google App Engine Sessions and Cookies ae-09-session .

High Level Summary

•The web is “stateless”

•So we need a way for servers to know “which browser is this?”

•In the browser, state is stored in “Cookies”

•In the server, state is stored in “Sessions”

Page 5: Google App Engine Sessions and Cookies ae-09-session .

Some Web sites always seem to want to know who you are!

Page 6: Google App Engine Sessions and Cookies ae-09-session .

Other Web sites always seem to know who you are!

Page 7: Google App Engine Sessions and Cookies ae-09-session .

Browser

Server

GET

WholePage

GET

WholePage

Draw Draw

You watch the YouTube videofor an 30 seconds

How you see YouTube...

ClickClick

Page 8: Google App Engine Sessions and Cookies ae-09-session .

Browser

Server

GET

WholePage

GET

WholePage

How YouTube sees you...

Draw DrawClickClick

Page 9: Google App Engine Sessions and Cookies ae-09-session .

Multi-User•When a server is interacting with many different

browsers at the same time, the server needs to know *which* browser a particular request came from

•Request / Response initially was stateless

•All browsers looked identical

•This was was fine for static web pages

•But it was really really bad for "webapps"

• Those simple days did not last very long at all.

Page 10: Google App Engine Sessions and Cookies ae-09-session .

Web Cookies to the Rescue

http://en.wikipedia.org/wiki/HTTP_cookie

Technically, cookies are arbitrary pieces of data chosen by the Web server and sent to the

browser. The browser returns them unchanged to the server, introducing a state (memory of

previous events) into otherwise stateless HTTP transactions. Without cookies, each retrieval of a

Web page or component of a Web page is an isolated event, mostly unrelated to all other

views of the pages of the same site.

Page 11: Google App Engine Sessions and Cookies ae-09-session .

http://en.wikipedia.org/wiki/HTTP_cookie

Page 12: Google App Engine Sessions and Cookies ae-09-session .

Cookies In the Browser•Cookies contain markers indicating the web

addresses they come from

•The browser only sends a cookie to the web server that originally set it

•Cookies have an expiration date

•Some last for years

•Others are short-term and go away as soon as the browser is closed

Page 13: Google App Engine Sessions and Cookies ae-09-session .

Playing with Cookies

•Firefox's WebDeveloper plugin has a set of cookie features

•Other browsers have a way to view or change cookies

Page 14: Google App Engine Sessions and Cookies ae-09-session .
Page 15: Google App Engine Sessions and Cookies ae-09-session .

Cookies

•Identifying individual users across requests

•Making the web seem not to be stateless

Page 16: Google App Engine Sessions and Cookies ae-09-session .

Request / Response Again!

Page 17: Google App Engine Sessions and Cookies ae-09-session .

HTTP Request / Response Cycle

http://www.oreilly.com/openbook/cgi/ch04_02.html

Browser

Web Server

HTTPRequest

HTTPResponse

Internet Explorer, FireFox, Safari,

etc.

(Review)

Page 18: Google App Engine Sessions and Cookies ae-09-session .

HTTP Request / Response Cycle

GET /index.html HTTP/1.1Accept: www/sourceAccept: text/htmlUser-Agent: Lynx/2.4

http://www.oreilly.com/openbook/cgi/ch04_02.html

Browser

Web Server

HTTPRequest

We do our initialGET to a server.

The server checks to see if

we have a cookie with a particular

name set.Since this is our first interaction,

we have no cookies set for

this host.

Page 19: Google App Engine Sessions and Cookies ae-09-session .

HTTP Request / Response Cycle

http://www.oreilly.com/openbook/cgi/ch04_02.html

Browser

Web Server

HTTPResponse

HTTP/1.1 200 OKContent-type: text/htmlSet-Cookie: sessid=123

<head> .. </head><body><h1>Welcome ....

host: sessid=123

Along with the rest of the

response, the server sets a

cookie with some name (sessid) and sends it

back along with the rest of the

response.

Page 20: Google App Engine Sessions and Cookies ae-09-session .

HTTP Request / Response Cycle

GET /index.html HTTP/1.1Accept: www/sourceAccept: text/htmlCookie: sessid=123User-Agent: Lynx/2.4

http://www.oreilly.com/openbook/cgi/ch04_02.html

Browser

Web Server

HTTPRequest

host: sessid=123

From that point forward, each

time we send a GET or POST to the server, we

include any cookies which

were set by that host.

Page 21: Google App Engine Sessions and Cookies ae-09-session .

HTTP Request / Response Cycle

http://www.oreilly.com/openbook/cgi/ch04_02.html

Browser

Web Server

HTTPResponse

HTTP/1.1 200 OKContent-type: text/htmlSet-Cookie: name=chuck

<head> .. </head><body><h1>Welcome ....

host: sessid=123host:name=chuck

On each response, the

server can change a cookie

value. Or add another cookie.

Page 22: Google App Engine Sessions and Cookies ae-09-session .

HTTP Request / Response Cycle

GET /index.html HTTP/1.1Accept: www/sourceAccept: text/htmlCookie: sessid=123,name=ChuckUser-Agent: Lynx/2.4

http://www.oreilly.com/openbook/cgi/ch04_02.html

Browser

Web Server

HTTPRequest

From that point forward, each

time we send a GET or POST to the server, we include all the cookies which

were set by that host.host: sessid=123

host:name=chuck

Page 23: Google App Engine Sessions and Cookies ae-09-session .

Security

•We ony send cookies back to the host that originally set the cookie

•The browser has *lots* of cookies for lots of hosts

•To see all Cookies:

Firefox -> Preferences -> Privacy -> Show Cookies

Page 24: Google App Engine Sessions and Cookies ae-09-session .

The Firefox Web Developer Plugin Shows

Cookies for the Current Host.

Page 25: Google App Engine Sessions and Cookies ae-09-session .

Two Kinds of Cookies

•Long-lived - who you are - account name - last access time

•You can close and reopen your browser and it is still there

•Temporary - used to identify your session

•It goes away when you close the browser

Page 26: Google App Engine Sessions and Cookies ae-09-session .
Page 27: Google App Engine Sessions and Cookies ae-09-session .

Using Cookies to Support Sessions and Login /

Logout

Page 28: Google App Engine Sessions and Cookies ae-09-session .

Some Web sites always seem to want to know who you are!

Page 29: Google App Engine Sessions and Cookies ae-09-session .

In The Server - Sessions

•In most server applications, as soon as we meet a new browser we create a session

•We set a session cookie to be stored in the browser which indicates the session id in use

•The creation and destruction of sessions is generally handled by a web framework or some utility code that we just use to manage the sessions

Page 30: Google App Engine Sessions and Cookies ae-09-session .

Session Identifier•A large, random number that we place in a browser

cookie the first time we encounter a browser.

•This number is used to pick from the many sessions that the server has active at any one time.

•Server software stores data in the session which it wants to have from one request to another from the same browser.

•Shopping cart or login information is stored in the session in the server

Page 31: Google App Engine Sessions and Cookies ae-09-session .

ServerServer

Session 97Session 97

Browser CBrowser C

cook=97cook=97

Request

Response

index:index:

““PleasePleaselog in”log in”cook=97

CreateSession

Page 32: Google App Engine Sessions and Cookies ae-09-session .

ServerServer

Session 97Session 97

Browser CBrowser C

cook=97cook=97

Typing

We now have a session

establishedbut are not yet

logged in.

Page 33: Google App Engine Sessions and Cookies ae-09-session .

Login / Logout•Having a session is not the same as being logged in.

•Generally you have a session the instant you connect to a web site

•The Session ID cookie is set when the first page is delivered

•Login puts user information in the session (stored in the server)

•Logout removes user information from the session

Page 34: Google App Engine Sessions and Cookies ae-09-session .

ServerServer

Session 97Session 97

Browser CBrowser C

cook=97cook=97

Request

login:login:

if good:if good:set userset user

Click

cook=97cook=97

Page 35: Google App Engine Sessions and Cookies ae-09-session .

ServerServer

Session 97Session 97

user=philuser=phil

Browser CBrowser C

cook=97cook=97

Request

login:login:

if good:if good:set userset user

Click

Response

cook=97cook=97

Page 36: Google App Engine Sessions and Cookies ae-09-session .

ServerServer

Session 97Session 97

user=philuser=phil

Browser CBrowser C

cook=97cook=97

Page 37: Google App Engine Sessions and Cookies ae-09-session .

Using Sessions for Other Stuff

Page 38: Google App Engine Sessions and Cookies ae-09-session .

ServerServerBrowser ABrowser A

cook=10cook=10

Browser BBrowser B

cook=46cook=46

Session 10Session 10

user=chucuser=chuckk

bal=$100bal=$10000

Session 46Session 46

user=januser=janbal=$400bal=$400

Page 39: Google App Engine Sessions and Cookies ae-09-session .

ServerServer

Session 10Session 10

user=chucuser=chuckk

bal=$100bal=$10000

Session 46Session 46

user=januser=janbal=$500bal=$500

Browser ABrowser A

cook=10cook=10

Browser BBrowser B

cook=46cook=46

withdraw:withdraw:

bal=bal-bal=bal-100100

Page 40: Google App Engine Sessions and Cookies ae-09-session .

ServerServer

Session 10Session 10

user=chucuser=chuckk

bal=$100bal=$10000

Session 46Session 46

user=januser=janbal=$500bal=$500

Browser ABrowser A

cook=10cook=10

Browser BBrowser B

cook=46cook=46

withdraw:withdraw:

bal=bal-bal=bal-100100

Click

Page 41: Google App Engine Sessions and Cookies ae-09-session .

ServerServer

Session 10Session 10

user=chucuser=chuckk

bal=$100bal=$10000

Session 46Session 46

user=januser=janbal=$500bal=$500

Browser ABrowser A

cook=10cook=10

Browser BBrowser B

cook=46cook=46

cook=46cook=46

withdraw:withdraw:

bal=bal-bal=bal-100100

Page 42: Google App Engine Sessions and Cookies ae-09-session .

ServerServer

Session 10Session 10

user=chucuser=chuckk

bal=$100bal=$10000

Session 46Session 46

user=januser=janbal=$400bal=$400

Browser ABrowser A

cook=10cook=10

Browser BBrowser B

cook=46cook=46

cook=46cook=46

withdraw:withdraw:

bal=bal-bal=bal-100100

Response

Request

Page 43: Google App Engine Sessions and Cookies ae-09-session .

Review...

Page 44: Google App Engine Sessions and Cookies ae-09-session .

High Level Summary

•The web is “stateless” - the browser does not maintain a connection to the server while you are looking at a page. Yu may never come back to the same server - or it may be a long time - or it may be one second later

•So we need a way for servers to know “which browser is this?”

•In the browser state is stored in “Cookies”

•In the server state is stored in “Sessions”

Page 45: Google App Engine Sessions and Cookies ae-09-session .

Browser

Server

GET

WholePage

GET

WholePage

Draw Draw

You watch the YouTube videofor an 30 seconds

How you see YouTube...

ClickClick

Page 46: Google App Engine Sessions and Cookies ae-09-session .

Browser

Server

Draw DrawClickClick

GET

WholePage

GET

WholePage

Page 47: Google App Engine Sessions and Cookies ae-09-session .

Browser

Server

Draw DrawClickClick

GET

WholePage

GET

WholePage

Session 42Session 42

cook=

42

cook=

42

cook=

42

cook=

42

Session 42Session 42

Page 48: Google App Engine Sessions and Cookies ae-09-session .

Cookie/Session Summary•Cookies take the stateless web and allow servers to store

small “breadcrumbs” in each browser.

•Session IDs are large random numbers stored in a cookie and used to maintain a session on the server for each of the browsers connecting to the server

•Server software stores sessions *somewhere* - each time a request comes back in, the right session is retrieved based on the cookie

•Server uses the session as a scratch space for little things

Page 49: Google App Engine Sessions and Cookies ae-09-session .

Programming and Sessions

Page 50: Google App Engine Sessions and Cookies ae-09-session .

First Look: Sessions are Magic!

•Sessions are usually part of the built-in web application framework

•Ruby on Rails

•Java Web Applications

•PHP

•The framework does all the cookie setting and data finding

Page 51: Google App Engine Sessions and Cookies ae-09-session .

First Look: Sessions are Magic!

•In our controller code we simply ask to create and/or access a session

•We treat the session like a dictionary storing whatever we like in the session under a set of string keys that we choose

Page 52: Google App Engine Sessions and Cookies ae-09-session .

Session Rules•Keep them small - we don’t want to put too much in

the session or we start taxing memory and other storage resources and slowing down our application

•Focus on data that is used on nearly every incoming request - the lookup key of the current user - the email address of the current user

•Sessions generally go away when the user closes their browser (cookie is lost) or after a period of inactivity (1-3 hours)

Page 53: Google App Engine Sessions and Cookies ae-09-session .

Session Uses

•Indication of the current user - management of the login and log out process

•Shopping cart - items / quantities

Page 54: Google App Engine Sessions and Cookies ae-09-session .

Our Magic - sessions.py•Since the Google Application Engine does

not provide a session capability, we need to add one - extending our application

•Download from

http://www.appenginelearn.com/downloads/util.zip

•Install in your application in the directory util to make it available in your application

Page 55: Google App Engine Sessions and Cookies ae-09-session .

Using the Session

from util.sessions import Session

class LogoutHandler(webapp.RequestHandler): def get(self): self.session = Session() self.session.delete('username') doRender(self, 'index.htm')

The Session() call either establishes a session or accesses the current session.

Page 56: Google App Engine Sessions and Cookies ae-09-session .

Inside the Session() call

•We use a session cookie to look up our session

•If the cookie exists and the session exists, return that session

•If not pick a large random number as the session key, make a session and set a temporary cookie with the session key as its value

Page 57: Google App Engine Sessions and Cookies ae-09-session .

The Login/Logout Pattern

•We use a key named ‘username’ in the session to indicate that the user is logged in

•If the key is missing the user is logged out

•If the key is present, its value is the account of the logged in user (e.g. “csev”)

Page 58: Google App Engine Sessions and Cookies ae-09-session .

def post(self): self.session = Session() acct = self.request.get('account') pw = self.request.get('password') logging.info("Checking account="+acct+" pw="+pw)

self.session.delete('username')

if pw == "" or acct == "": doRender(self,"login.htm",{'error' : 'Please specify Acct/PW'} ) elif pw == "secret": self.session['username'] = acct doRender(self,"index.htm",{ } ) else: doRender(self,"login.htm",{'error' : 'Incorrect password'} )

Get the Session

Log out previous user

Log in new user

Page 59: Google App Engine Sessions and Cookies ae-09-session .

Logout

from util.sessions import Session

class LogoutHandler(webapp.RequestHandler): def get(self): self.session = Session() self.session.delete('username') doRender(self, 'index.htm')

Get the Session

Log out previous user

Page 60: Google App Engine Sessions and Cookies ae-09-session .

Navigation

•We want to have the Login / Logout button flip when we log in or out and we want to see the name of the current logged in user.

Page 61: Google App Engine Sessions and Cookies ae-09-session .

<li><a href="topics.htm" {% ifequal path '/topics.htm' %} class="selected" {% endifequal %} >Topics</a></li> {% ifequal username None %} <li><a href="/login" {% ifequal path '/login' %} class="selected" {% endifequal %} >Login</a></li> {% else %} <li><a href="/logout">Logout ({{username}})</a></li> {% endifequal %}

In the view template, we send an additional

context variable to the template called

“username” if the user is logged in. We use logic in

the template to either generate the Login link or

the Logout + account name link.

_base.htm

Page 62: Google App Engine Sessions and Cookies ae-09-session .

def doRender(self, tname = "index.htm", values = { }): logging.info(tname) temp = os.path.join(os.path.dirname(__file__),'templates/'+tname) if not os.path.exists(temp): return False

# Make a copy of the dictionary and add basic values newval = dict(values) if not 'path' in newval: path = self.request.path newval['path'] = self.request.path

if not 'username' in newval: self.session = Session() if 'username' in self.session: newval['username'] = self.session["username"]

outstr = template.render(temp, newval) self.response.out.write(outstr) return True

We check to see if the username is in the

session and if username is in the

session we add it to the context variables to be

passed into the template.

Page 63: Google App Engine Sessions and Cookies ae-09-session .

Summary

•The Cookies and Session work together to give us a relatively simply way to programmatically stash data associated with a particular user/browser

•While the mechanisms are a bit complex, the session pattern turns out to be pretty simple to use in our applications

•The Google Application Engine does not provide us with a Session feature - so we need to write or borrow some code

•Clever use of session is important to application performance