1 import org.maemo.hermes.engine.service
3 from org.maemo.hermes.engine.names import canonical
4 from org.maemo.hermes.engine.friend import Friend
6 class Service(org.maemo.hermes.engine.service.Service):
7 """Facebook backend for Hermes.
9 Copyright (c) Andrew Flegg <andrew@bleb.org> 2010.
10 Copyright (c) Fredrik Wendt <fredrik@wendt.se> 2010.
11 Released under the Artistic Licence."""
13 attrs = ['uid', 'name', 'pic_big', 'birthday_date', 'profile_url', 'first_name', 'last_name', 'website']
16 # -----------------------------------------------------------------------
17 def __init__(self, facebook, autocreate=False, gui_callback=None):
18 """Initialise the Facebook service, finding Facebook API keys in gconf and
19 having a gui_callback available."""
21 self._gui = gui_callback
22 self._autocreate = autocreate
25 self._friends_by_name = {}
26 self._friends_by_url = {}
27 self._friends_by_contact = {}
28 self._contacts_by_friend = {}
29 self._friends_without_contact = set()
30 self._known_urls = set()
33 # -----------------------------------------------------------------------
38 # -----------------------------------------------------------------------
39 def get_friends(self):
40 return self._contacts_by_friend.keys()
43 def get_contacts_with_match(self):
44 return self._friends_by_contact
46 def get_unmatched_friends(self):
47 return self._friends_by_name.values()
50 # -----------------------------------------------------------------------
51 def pre_process_contact(self, contact):
52 """Registers URLs of all previous mappings, and makes sure that any Friends with those
53 URLs don't get match by name."""
54 for url in contact.get_urls():
55 self._known_urls.add(url)
58 # -----------------------------------------------------------------------
59 def process_friends(self):
61 def if_defined(data, key, callback):
62 if key in data and data[key]:
65 friends_data = self._get_friends_data()
66 for data in friends_data:
67 key = canonical(data['name']) # FIXME: deal with name collision
68 friend = self._create_friend(data['name'])
70 if 'profile_url' not in data:
71 data['profile_url'] = "http://www.facebook.com/profile.php?id=" + str(data['uid'])
73 if_defined(data, 'website', friend.add_url)
74 if_defined(data, 'profile_url', friend.add_url)
75 if_defined(data, 'birthday_date', friend.set_birthday_date)
77 if_defined(data, 'pic_big', friend.set_photo_url)
79 if friend.has_birthday_date(): # FIXME: remove this, either you want to add your contacts or not?
80 self._friends_without_contact.add(friend)
81 url = data['profile_url']
82 self._friends_by_url[url] = friend
84 if url not in self._known_urls:
85 self._friends_by_name[key] = friend
88 # -----------------------------------------------------------------------
89 def process_contact(self, contact):
90 if self._friends_by_contact.has_key(contact):
94 # we might get a hit if the friend has setup a URL with another service,
95 # such as putting the id link to Facebook on the Twitter account's profile
96 for url in contact.get_urls():
97 if url in self._friends_by_url:
98 matched_friend = self._friends_by_url[url]
99 self._register_match(contact, matched_friend)
100 print contact.get_name(), " -> match by url -> ", matched_friend
103 if not matched_friend:
104 for id in contact.get_identifiers():
105 if id in self._friends_by_name:
106 matched_friend = self._friends_by_name.pop(id)
107 self._register_match(contact, matched_friend)
108 print contact.get_name(), " -> match by name -> ", matched_friend
112 # -----------------------------------------------------------------------
113 def _register_match(self, contact, friend):
114 self._friends_without_contact.discard(friend)
115 self._friends_by_contact[contact] = friend
116 self._contacts_by_friend[friend] = contact
118 # -----------------------------------------------------------------------
119 def _get_friends_data(self):
120 """Returns a list of dicts, where each dict represents a friend/contact"""
122 return self.fb.users.getInfo(self.fb.friends.get(), Service.attrs)