aeb8de58b93c8efe688f7da15a928cba637fd7c3
[theonering] / src / gvoice / addressbook.py
1 #!/usr/bin/python
2
3
4 import logging
5
6 import util.coroutines as coroutines
7
8
9 _moduleLogger = logging.getLogger("gvoice.addressbook")
10
11
12 class Addressbook(object):
13
14         def __init__(self, backend):
15                 self._backend = backend
16                 self._contacts = {}
17                 self._addedContacts = set()
18                 self._removedContacts = set()
19                 self._changedContacts = set()
20
21                 self.updateSignalHandler = coroutines.CoTee()
22
23         def update(self):
24                 oldContacts = self._contacts
25                 oldContactIds = set(self.get_contacts())
26
27                 self._contacts = {}
28                 self._populate_contacts()
29                 newContactIds = set(self.get_contacts())
30
31                 self._addedContacts = newContactIds - oldContactIds
32                 self._removedContacts = oldContactIds - newContactIds
33                 self._changedContacts = set(
34                         contactId
35                         for contactId in newContactIds.intersection(oldContactIds)
36                         if self._has_contact_changed(contactId, oldContacts)
37                 )
38
39                 message = self, self._addedContacts, self._removedContacts, self._changedContacts
40                 self.updateSignalHandler.send(message)
41
42         def get_contacts(self):
43                 return self._contacts.iterkeys()
44
45         def get_contact_name(self, contactId):
46                 return self._contacts[contactId][0]
47
48         def get_contact_details(self, contactId):
49                 self._populate_contact_details(contactId)
50                 return self._get_contact_details(contactId)
51
52         def _populate_contacts(self):
53                 if self._contacts:
54                         return
55                 contacts = self._backend.get_contacts()
56                 for contactId, contactName in contacts:
57                         self._contacts[contactId] = (contactName, {})
58
59         def _populate_contact_details(self, contactId):
60                 if self._get_contact_details(contactId):
61                         return
62                 self._get_contact_details(contactId).update(
63                         self._backend.get_contact_details(contactId)
64                 )
65
66         def _get_contact_details(self, contactId):
67                 return self._contacts[contactId][1]
68
69         def _has_contact_changed(self, contactId, oldContacts):
70                 oldContact = oldContacts[contactId]
71                 oldContactName = oldContact[0]
72                 oldContactDetails = oldContact[1]
73                 if oldContactName != self.get_contact_name(contactId):
74                         return True
75                 if not oldContactDetails[1]:
76                         return False
77                 # if its already in the old cache, purposefully add it into the new cache
78                 return oldContactDetails != self.get_contact_details(contactId)