Persistence of gsessionids
Posted on
May 8th, 2008 by
yesteray
I’ve read this paragraph many times, but somehow the full meaning just became apparent to me.
Just like in the previous example, Calendar may return an HTTP 302 redirect; if so, then the redirect URL has a new parameter,
gsessionid, appended to it. If you received the redirect, then send the samePOSTrequest again, with the same Authorization header and the same content, but with thegsessionidparameter appended. The response may also include aScookie, which you should store and send this cookie with future requests as appropriate. Please see the knowledge base for more information on handling sessions with the Calendar data API. Please note: if a session ID indicated in a cookie header conflicts
with the session ID passed as a gsessionid URL parameter, you will get caught in a redirect loop.
The introductory clause obscures important information. Having read the previous example, I thought that there wasn’t much to be gained by reading this paragraph in detail. Just do the same thing as before, “So after you’ve sent the GET request, you have to read the HTTP headers of the response to find the URL with the session ID appended; then you need to send another GET request with that new URL.”
Really, I didn’t think too much. The gsessionid is a persistent session id. You can send it with any future request and if you do, and the session id matches the auth token your request will be accepted without redirect. Moreover you can grab the S cookie and stick it in your headers and not need to worry about it.This is documented here.
Here’s an example in action:
# get_feed is from a project I'm working on irb:01:0> require 'get_feed' => true # it provides an authorization method that also sets @headers and creates @http object irb:02:0> get_auth('me@gmail.com','top_secret') => {"Authorization"=>"GoogleLogin auth=DQAAAIQAAABECsmTToeu0o97DoPQ8v9lXDkqFYQY4tOC4QmkItA9jb1J2GfEql69SifsFF7TJJ6_lbAST3iuc-aZQUIvY3qDfPj4pNpo9_XAsCEphd9jRdqeqengYDnpTOEJJedw9jRV738b4x-EluyDKDPBw0f46fFDto0o8zkgY_bUChKK0T6j8A5PgedYRRJzQJm_oSY", "Content-Type"=>"application/atom+xml", "Service"=>"67central.com--get-feed-0.0.1"} irb:03:0> @headers => {"Authorization"=>"GoogleLogin auth=DQAAAIQAAABECsmTToeu0o97DoPQ8v9lXDkqFYQY4tOC4QmkItA9jb1J2GfEql69SifsFF7TJJ6_lbAST3iuc-aZQUIvY3qDfPj4pNpo9_XAsCEphd9jRdqeqengYDnpTOEJJedw9jRV738b4x-EluyDKDPBw0f46fFDto0o8zkgY_bUChKK0T6j8A5PgedYRRJzQJm_oSY", "Content-Type"=>"application/atom+xml", "Service"=>"67central.com--get-feed-0.0.1"} # User's default calendar and own calendars feeds irb:04:0> default = '/calendar/feeds/default' => "/calendar/feeds/default" irb:05:0> all = '/calendar/feeds/default/owncalendars/full' => "/calendar/feeds/default/owncalendars/full" # Request for feeds are redirected irb:06:0> @http.get(default,@headers) => #<Net::HTTPFound 302 Moved Temporarily readbody=true> irb:07:0> response = @http.get(all,@headers) => #<Net::HTTPFound 302 Moved Temporarily readbody=true> # All calendars feed to this location, note the gsessionid irb:08:0> response['Location'] => "https://www.google.com:443/calendar/feeds/default/owncalendars/full?gsessionid=uVGhyT0F60BtaKPNVsOeig" # Also returns this cookie irb:09:0> response['set-cookie'] => "S=calendar=uVGhyT0F60BtaKPNVsOeig;Expires=Fri, 08-May-2009 20:54:31 GMT" irb:10:0> s_cookie = response["set-cookie"].split(';').first => "S=calendar=uVGhyT0F60BtaKPNVsOeig" irb:11:0> all_redirect = "/calendar/feeds/default/owncalendars/full?gsessionid=uVGhyT0F60BtaKPNVsOeig" => "/calendar/feeds/default/owncalendars/full?gsessionid=uVGhyT0F60BtaKPNVsOeig" # With the gsessionid, request succeeds irb:12:0> response = @http.get(all_redirect,@headers) => #<Net::HTTPOK 200 OK readbody=true> irb:13:0> default_with_redirect = default + "?gsessionid=uVGhyT0F60BtaKPNVsOeig" => "/calendar/feeds/default?gsessionid=uVGhyT0F60BtaKPNVsOeig" # So does this one irb:14:0> response = @http.get(default_with_redirect,@headers) => #<Net::HTTPOK 200 OK readbody=true> # Set the cookie irb:15:0> @headers['Cookie'] = s_cookie => "S=calendar=uVGhyT0F60BtaKPNVsOeig" # And both request succeed without gsessionid irb:16:0> response = @http.get(all,@headers) => #<Net::HTTPOK 200 OK readbody=true> irb:17:0> response = @http.get(default,@headers) => #<Net::HTTPOK 200 OK readbody=true>
I hope that is useful to some one. There is a claim in the documentation (I’ve temporarily lost it) that the API libraries will handle these session ids and cookies automatically. Good to know.
Leave a Reply
Search:
Recent Posts
- Running Multiple Versions of Firefox
- Adding Events to Secondary Google Calendars in Python
- Q & A - Sharing Calendars
- Adding Events to Secondary Google Calendars
- Link Elements in GCalendar Calendar Feeds
Categories
Relevant Links
AtomPub
- Getting to know the Atom Publishing Protocol, Part 1: Create and edit Web resources with the Atom Publishing Protocol
- Getting to know the Atom Publishing Protocol, Part 2: Put the Atom Publishing Protocol (APP) to work
Date and Time
GCalendar
- Articles and Tutorials
- Bugs and Enhancements
- Calendar API FAQ
- Calendar Feeds
- Developer’s Guide
- Google Calendar Data API Group
- Reference Guide
GData
- Authentication
- Batch Processing
- Client Libraries
- Common Elements
- Issues
- libgcal
- Overview
- Protocol Basics
- Protocol Reference
- Reference
- Samples
- Zend Documentation
iCalendar Tools
Online Calendars
- 30 Boxes
- CalendarHub - Web Calendars
- Google Calendar
- LuckyCal.com
- Online calendar publishing: Google Calendar
- Online calendar publishing: iCal
- Online calendar publishing: Outlook
- RSSCalendar
- The Human Calendar
- Yahoo! Calendar
