summaryrefslogtreecommitdiff
path: root/alot/addressbooks.py
blob: 16818a3924a722fbb6b29db4de6afae8e3f004f0 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
import re
import os

from alot.settings.utils import read_config
from helper import call_cmd
from alot.helper import split_commandstring


class AddressBook(object):
    """can look up email addresses and realnames for contacts.

    .. note::

        This is an abstract class that leaves :meth:`get_contacts`
        unspecified. See :class:`AbookAddressBook` and
        :class:`MatchSdtoutAddressbook` for implementations.
    """

    def get_contacts(self):
        """list all contacts tuples in this abook as (name, email) tuples"""
        return []

    def lookup(self, prefix=''):
        """looks up all contacts with given prefix (in name or address)"""
        res = []
        for name, email in self.get_contacts():
            if name.startswith(prefix) or email.startswith(prefix):
                res.append((name, email))
        return res


class AbookAddressBook(AddressBook):
    """:class:`AddressBook` that parses abook's config/database files"""
    def __init__(self, path='~/.abook/addressbook'):
        """
        :param path: path to theme file
        :type path: str
        """
        DEFAULTSPATH = os.path.join(os.path.dirname(__file__), 'defaults')
        self._spec = os.path.join(DEFAULTSPATH, 'abook_contacts.spec')
        path = os.path.expanduser(path)
        self._config = read_config(path, self._spec)
        del(self._config['format'])

    def get_contacts(self):
        c = self._config
        res = []
        for id in c.sections:
            for email in c[id]['email']:
                if email: res.append((c[id]['name'], email))
        return res


class MatchSdtoutAddressbook(AddressBook):
    """:class:`AddressBook` that parses a shell command's output for lookups"""
    def __init__(self, command, match=None):
        """
        :param command: lookup command
        :type command: str
        :param match: regular expression used to match contacts in `commands`
                      output to stdout. Must define subparts named "email" and
                      "name".  Defaults to
                      :regexp:`^(?P<email>[^@]+@[^\t]+)\t+(?P<name>[^\t]+)`.
        :type match: str
        """
        self.command = command
        if not match:
            self.match = '^(?P<email>[^@]+@[^\t]+)\t+(?P<name>[^\t]+)'
        else:
            self.match = match

    def get_contacts(self):
        return self.lookup('\'\'')

    def lookup(self, prefix):
        cmdlist = split_commandstring(self.command)
        resultstring, errmsg, retval = call_cmd(cmdlist + [prefix])
        if not resultstring:
            return []
        lines = resultstring.splitlines()
        res = []
        for l in lines:
            m = re.match(self.match, l)
            if m:
                info = m.groupdict()
                email = info['email'].strip()
                name = info['name']
                res.append((name, email))
        return res