1 |
# Facebook |
2 |
# |
3 |
# Douglas Thrift |
4 |
# |
5 |
# $Id$ |
6 |
|
7 |
import atom |
8 |
from datetime import datetime |
9 |
import gdata.calendar |
10 |
import gdata.service |
11 |
import icalendar |
12 |
import pytz |
13 |
import re |
14 |
import urllib, urllib2 |
15 |
import warnings |
16 |
|
17 |
def main(calendar, config, debug): |
18 |
uid = re.compile(r'^e(.*)@facebook\.com$') |
19 |
pacific = pytz.timezone('US/Pacific') |
20 |
reminder = gdata.calendar.Reminder(hours = 2) |
21 |
|
22 |
with warnings.catch_warnings(): |
23 |
warnings.filterwarnings('ignore', r'object\.__init__\(\) takes no parameters', DeprecationWarning) |
24 |
|
25 |
for event in icalendar.Calendar.from_string(urllib2.urlopen('http://www.facebook.com/ical/u.php?' + urllib.urlencode({'uid': config.get('uid'), 'key': config.get('key')})).read()).walk('vevent'): |
26 |
id = uid.match(event.decoded('uid')).group(1) |
27 |
query = gdata.calendar.service.CalendarEventQuery('default', 'private', 'full', id) |
28 |
entries = calendar.CalendarQuery(query).entry |
29 |
title = event.decoded('summary') |
30 |
content = event.decoded('description') |
31 |
status = event.decoded('partstat') |
32 |
transparency = 'OPAQUE' if status == 'ACCEPTED' else 'TRANSPARENT' |
33 |
start_time = event.decoded('dtstart') |
34 |
end_time = event.decoded('dtend') |
35 |
end_time = pacific.localize(end_time) if end_time.tzinfo is None else end_time.astimezone(pacific) |
36 |
where = event.decoded('location') |
37 |
eid = re.compile(r'http://www\.facebook\.com/event\.php\?eid=%s$' % re.escape(id)) |
38 |
|
39 |
if not eid.search(content): |
40 |
content += '\n\nhttp://www.facebook.com/event.php?eid=%s' % id |
41 |
|
42 |
if not entries: |
43 |
entry = gdata.calendar.CalendarEventEntry() |
44 |
entry.title = atom.Title(text = title) |
45 |
entry.content = atom.Content(text = content) |
46 |
entry.transparency = gdata.calendar.Transparency() |
47 |
entry.transparency.value = transparency |
48 |
entry.visibility = gdata.calendar.Visibility() |
49 |
entry.visibility.value = 'CONFIDENTIAL' |
50 |
|
51 |
entry.when.append(gdata.calendar.When(start_time = start_time.isoformat(), end_time = end_time.isoformat())) |
52 |
|
53 |
if status != 'NEEDS-ACTION': |
54 |
entry.when[0].reminder.append(reminder) |
55 |
|
56 |
entry.where.append(gdata.calendar.Where(value_string = where)) |
57 |
calendar.InsertEvent(entry, '/calendar/feeds/default/private/full') |
58 |
else: |
59 |
for index, entry in enumerate(filter(lambda entry: eid.search(entry.content.text), entries)): |
60 |
if index == 0: |
61 |
entry.title.text = title |
62 |
entry.content.text = content |
63 |
entry.transparency.value = transparency |
64 |
entry.visibility.value = 'CONFIDENTIAL' |
65 |
entry.when[0].start_time = start_time.isoformat() |
66 |
entry.when[0].end_time = end_time.isoformat() |
67 |
|
68 |
if status != 'NEEDS-ACTION': |
69 |
if entry.when[0].reminder: |
70 |
entry.when[0].reminder[0] = reminder |
71 |
else: |
72 |
entry.when[0].reminder.append(reminder) |
73 |
|
74 |
# http://code.google.com/p/gdata-python-client/issues/detail?id=268 |
75 |
try: |
76 |
calendar.UpdateEvent(entry.GetEditLink().href, entry) |
77 |
except gdata.service.RequestError, error: |
78 |
print error |
79 |
else: |
80 |
calendar.DeleteEvent(entry.GetEditLink().href) |