Rather than returning simply strings and having to guess their encoding,
return explicit unicode() strings for the tags. Xapian stores UTF8, so
we know that they come as UTF8 encoded string.
Note: I tried to directly use the c_wchar_p type of the ctypes library
which translates directly into an unicode type, but that did not work
out so well, so we take c_char_p and .decode() them manually.
Signed-off-by: Sebastian Spaeth <Sebastian@SSpaeth.de>
If we pass in an unicode instance as query string, we would probably get
weird behavior (and indeed do so, see mail
id:"20110707113700.GA16347@megatron"). If a unicode instance is passed
in, make sure we encode it properly to an utf-8 encoded byte string.
Signed-off-by: Sebastian Spaeth <Sebastian@SSpaeth.de>
A stupid typo was preventing this from ever working and it was not
detected until now. Patrick noted the typo and proposed the fix in mail
id:"20110704203926.GA20238@brick.lan".
Patch-by: Patrick Totzke <patricktotzke@googlemail.com>
Signed-off-by: Sebastian Spaeth <Sebastian@SSpaeth.de>
In order to remain consistent with the underlying C API, we do not
automatically synchronize notmuch tags and maildir flags anymore.
The underlying functions Message.maildir_flags_to_tags and
Message.tags_to_maildir_flags still exist and are available to the user.
Signed-off-by: Sebastian Spaeth <Sebastian@SSpaeth.de>
We were still using len(self.get_replies()) for the __str__ summary of a
mail, but 1) len(Messages()) has just gone away 2) the number of replies
can not be retrieved when we got the message via search_messages()
anyway, and 3) it is likely quite expensive to pull all replies for all
messages that we display a summary of.
So we fix this by simplifying str(Message()) to omit the number of replies.
Signed-off-by: Sebastian Spaeth <Sebastian@SSpaeth.de>
libnotmuch (and python) crashed when I accidently passed in an invalid
value as path argument to the Database() instantiation.
Therefore, we now check via assert that the handed in path is actually a
real string (or None).
Signed-off-by: Sebastian Spaeth <Sebastian@SSpaeth.de>
and also maildir_flags_to_tags. The methods will be invoked by
db.add_message() and also (if not overridden via function parameter) by
add|remove_tag and remove_all_tags. Documentation on the usage has been
updated.
Signed-off-by: Sebastian Spaeth <Sebastian@SSpaeth.de>
Improve the documentation with regard to the new __cmp__ and __hash__
methods and the implications of doing set arithmetic with Messages()
objects.
Signed-off-by: Sebastian Spaeth <Sebastian@SSpaeth.de>
We can now do: if msg1 == msg2, and we can use set arithmetic on
Messages():
s1, s2= msgs1, msgs2
s1.union(s2)
s2 -= s1
Signed-off-by: Sebastian Spaeth <Sebastian@SSpaeth.de>
Messages.__len__() exhausted the iterator and list() inherently calls
len(), so we could not invoke list(msgs) without getting errors. Fix
this by implementing __nonzero__ but removing __len__ on Messages.
Use Query.count_messages() or len(list(msgs)) if you need to know the
number.
Signed-off-by: Sebastian Spaeth <Sebastian@SSpaeth.de>
To match the upcoming release, and with the updated API to match the
current libnotmuch, bump the python version number (notmuch.__VERSION__)
to 0.6.
Signed-off-by: Sebastian Spaeth <Sebastian@SSpaeth.de>
Analog to Threads.__nonzero__ this allows us to perform list() on a Threads() object and to repeatedly call "if Tags():" or "bool(Tags())" without implicitly invoking len(), thus exhausting our iterator.
While touching this code, I added a small micro-optimization to the Tag next() function. There is no need to explicitly check _is_valid, as _get implicitly does check for validness and returns None, if there is no more Tag to fetch. This avoids some roundtrips into the library when iterating through Tags.
Signed-off-by: Sebastian Spaeth <Sebastian@SSpaeth.de>
__nonzero__ checks if Threads() contains at least one more valid thread
The existence of this function makes 'if Threads(): foo' work, as that
previously implicitely called len() exhausting the iterator. This
function makes `bool(Threads())` work repeatedly.
For further info, see http://docs.python.org/reference/datamodel.html.
Credits for the hint go to Brian May.
Signed-off-by: Sebastian Spaeth <Sebastian@SSpaeth.de>
Message().get_filenames() will return a generator that allows to
iterator over the recorded filenames for a certain Message. Do ntoe that
as all generators, these are one-time use only. You will have to reget
them to perform various actions. So this works::
len(Message().get_filenames())
list(Message().get_filenames())
for n in Message().get_filenames():
print n
But this won't::
names = Message().get_filenames()
len(names) #uses up the iterator
list(names) #outch, already used up...
Signed-off-by: Sebastian Spaeth <Sebastian@SSpaeth.de>
Convert the meta information to point to the notmuchmail.org repository, rather
than the old cnotmuch location. I will delete the "cnotmuch" package
from http://pypi.python.org/pypi/cnotmuch and create a new "notmuch"
package there that contains the current versions.
Also bump the version number to 0.4. I will need to upgrade the API
first before I can release the 0.5 of the bindings, there are still some
methods missing.
Signed-off-by: Sebastian Spaeth <Sebastian@SSpaeth.de>
Database.find_message() used to be able to reliably indicate whether a
message exists or not (in which case it returns None). However, the
recent API change of the notmuch library means we will return None
even for all Xapian exceptions, which happens e.g. when the current
Database has been modified by another project. Therefore the return
value of None cannot be reliably be used to indicate whether a message
exists or not. Make the docs state that explicitely.
Signed-off-by: Sebastian Spaeth <Sebastian@SSpaeth.de>