1 Return-Path: <teythoon@jade-hamburg.de>
\r
2 X-Original-To: notmuch@notmuchmail.org
\r
3 Delivered-To: notmuch@notmuchmail.org
\r
4 Received: from localhost (localhost [127.0.0.1])
\r
5 by olra.theworths.org (Postfix) with ESMTP id C0C7E429E25
\r
6 for <notmuch@notmuchmail.org>; Sun, 9 Oct 2011 15:13:45 -0700 (PDT)
\r
7 X-Virus-Scanned: Debian amavisd-new at olra.theworths.org
\r
11 X-Spam-Status: No, score=0.001 tagged_above=-999 required=5
\r
12 tests=[UNPARSEABLE_RELAY=0.001] autolearn=disabled
\r
13 Received: from olra.theworths.org ([127.0.0.1])
\r
14 by localhost (olra.theworths.org [127.0.0.1]) (amavisd-new, port 10024)
\r
15 with ESMTP id KcPOLsTVLwUh for <notmuch@notmuchmail.org>;
\r
16 Sun, 9 Oct 2011 15:13:43 -0700 (PDT)
\r
17 Received: from mail.cryptobitch.de (cryptobitch.de [88.198.7.68])
\r
18 (using TLSv1 with cipher ADH-AES256-SHA (256/256 bits))
\r
19 (No client certificate requested)
\r
20 by olra.theworths.org (Postfix) with ESMTPS id 344A8431FB6
\r
21 for <notmuch@notmuchmail.org>; Sun, 9 Oct 2011 15:13:43 -0700 (PDT)
\r
22 Received: from mail.jade-hamburg.de (unknown [85.183.11.228])
\r
23 (using TLSv1 with cipher ADH-AES256-SHA (256/256 bits))
\r
24 (No client certificate requested)
\r
25 by mail.cryptobitch.de (Postfix) with ESMTPSA id E1747509367
\r
26 for <notmuch@notmuchmail.org>; Mon, 10 Oct 2011 00:13:41 +0200 (CEST)
\r
27 Received: by mail.jade-hamburg.de (Postfix, from userid 401)
\r
28 id 60011DF2A1; Mon, 10 Oct 2011 00:13:41 +0200 (CEST)
\r
29 Received: from thinkbox.jade-hamburg.de (unknown
\r
30 [IPv6:fe80::216:d3ff:fe3e:5058%br0])
\r
31 (using TLSv1 with cipher AES256-SHA (256/256 bits))
\r
32 (No client certificate requested) (Authenticated sender: teythoon)
\r
33 by mail.jade-hamburg.de (Postfix) with ESMTPSA id 680C2DF29F;
\r
34 Mon, 10 Oct 2011 00:13:22 +0200 (CEST)
\r
35 Received: from teythoon by thinkbox.jade-hamburg.de with local (Exim 4.76)
\r
36 (envelope-from <teythoon@thinkbox.jade-hamburg.de>)
\r
37 id 1RD1cX-0000HM-JH; Mon, 10 Oct 2011 00:13:21 +0200
\r
38 From: Justus Winter <4winter@informatik.uni-hamburg.de>
\r
39 To: notmuch@notmuchmail.org
\r
40 Subject: [PATCH 2/2] python: annotate all calls into libnotmuch with types
\r
41 Date: Mon, 10 Oct 2011 00:12:54 +0200
\r
43 <1318198374-926-2-git-send-email-4winter@informatik.uni-hamburg.de>
\r
44 X-Mailer: git-send-email 1.7.6.3
\r
46 <1318198374-926-1-git-send-email-4winter@informatik.uni-hamburg.de>
\r
48 <1318198374-926-1-git-send-email-4winter@informatik.uni-hamburg.de>
\r
49 X-BeenThere: notmuch@notmuchmail.org
\r
50 X-Mailman-Version: 2.1.13
\r
52 List-Id: "Use and development of the notmuch mail system."
\r
53 <notmuch.notmuchmail.org>
\r
54 List-Unsubscribe: <http://notmuchmail.org/mailman/options/notmuch>,
\r
55 <mailto:notmuch-request@notmuchmail.org?subject=unsubscribe>
\r
56 List-Archive: <http://notmuchmail.org/pipermail/notmuch>
\r
57 List-Post: <mailto:notmuch@notmuchmail.org>
\r
58 List-Help: <mailto:notmuch-request@notmuchmail.org?subject=help>
\r
59 List-Subscribe: <http://notmuchmail.org/mailman/listinfo/notmuch>,
\r
60 <mailto:notmuch-request@notmuchmail.org?subject=subscribe>
\r
61 X-List-Received-Date: Sun, 09 Oct 2011 22:13:45 -0000
\r
63 Add type information to the ctypes._FuncPtr wrappers and
\r
64 use the wrapper classes instead of c_void_p for pointers
\r
67 This enables the ctypes library to type check parameters
\r
68 being handed to functions from the notmuch library.
\r
70 Signed-off-by: Justus Winter <4winter@informatik.uni-hamburg.de>
\r
72 bindings/python/notmuch/database.py | 127 ++++++++++++++++++++++++++--------
\r
73 bindings/python/notmuch/filename.py | 22 +++++-
\r
74 bindings/python/notmuch/message.py | 91 ++++++++++++++++++++-----
\r
75 bindings/python/notmuch/tag.py | 23 +++++--
\r
76 bindings/python/notmuch/thread.py | 63 +++++++++++++----
\r
77 5 files changed, 255 insertions(+), 71 deletions(-)
\r
79 diff --git a/bindings/python/notmuch/database.py b/bindings/python/notmuch/database.py
\r
80 index f4bc53e..25b4b1b 100644
\r
81 --- a/bindings/python/notmuch/database.py
\r
82 +++ b/bindings/python/notmuch/database.py
\r
83 @@ -18,9 +18,11 @@ Copyright 2010 Sebastian Spaeth <Sebastian@SSpaeth.de>'
\r
87 -from ctypes import c_int, c_char_p, c_void_p, c_uint, c_long, byref
\r
88 +from ctypes import c_int, c_char_p, c_void_p, c_uint, c_long, byref, POINTER
\r
89 from notmuch.globals import (nmlib, STATUS, NotmuchError, NotInitializedError,
\r
90 - NullPointerError, OutOfMemoryError, XapianError, Enum, _str)
\r
91 + NullPointerError, OutOfMemoryError, XapianError, Enum, _str,
\r
92 + NotmuchDatabaseP, NotmuchDirectoryP, NotmuchMessageP, NotmuchTagsP,
\r
93 + NotmuchQueryP, NotmuchMessagesP, NotmuchThreadsP, NotmuchFilenamesP)
\r
94 from notmuch.thread import Threads
\r
95 from notmuch.message import Messages, Message
\r
96 from notmuch.tag import Tags
\r
97 @@ -56,37 +58,48 @@ class Database(object):
\r
99 """notmuch_database_get_directory"""
\r
100 _get_directory = nmlib.notmuch_database_get_directory
\r
101 - _get_directory.restype = c_void_p
\r
102 + _get_directory.argtypes = [NotmuchDatabaseP, c_char_p]
\r
103 + _get_directory.restype = NotmuchDirectoryP
\r
105 """notmuch_database_get_path"""
\r
106 _get_path = nmlib.notmuch_database_get_path
\r
107 + _get_path.argtypes = [NotmuchDatabaseP]
\r
108 _get_path.restype = c_char_p
\r
110 """notmuch_database_get_version"""
\r
111 _get_version = nmlib.notmuch_database_get_version
\r
112 + _get_version.argtypes = [NotmuchDatabaseP]
\r
113 _get_version.restype = c_uint
\r
115 """notmuch_database_open"""
\r
116 _open = nmlib.notmuch_database_open
\r
117 - _open.restype = c_void_p
\r
118 + _open.argtypes = [c_char_p, c_uint]
\r
119 + _open.restype = NotmuchDatabaseP
\r
121 """notmuch_database_upgrade"""
\r
122 _upgrade = nmlib.notmuch_database_upgrade
\r
123 - _upgrade.argtypes = [c_void_p, c_void_p, c_void_p]
\r
124 + _upgrade.argtypes = [NotmuchDatabaseP, c_void_p, c_void_p]
\r
125 + _upgrade.restype = c_uint
\r
127 """ notmuch_database_find_message"""
\r
128 _find_message = nmlib.notmuch_database_find_message
\r
129 + _find_message.argtypes = [NotmuchDatabaseP, c_char_p, POINTER(NotmuchMessageP)]
\r
130 + _find_message.restype = c_uint
\r
132 """notmuch_database_find_message_by_filename"""
\r
133 _find_message_by_filename = nmlib.notmuch_database_find_message_by_filename
\r
134 + _find_message_by_filename.argtypes = [NotmuchDatabaseP, c_char_p, POINTER(NotmuchMessageP)]
\r
135 + _find_message_by_filename.restype = c_uint
\r
137 """notmuch_database_get_all_tags"""
\r
138 _get_all_tags = nmlib.notmuch_database_get_all_tags
\r
139 - _get_all_tags.restype = c_void_p
\r
140 + _get_all_tags.argtypes = [NotmuchDatabaseP]
\r
141 + _get_all_tags.restype = NotmuchTagsP
\r
143 """notmuch_database_create"""
\r
144 _create = nmlib.notmuch_database_create
\r
145 - _create.restype = c_void_p
\r
146 + _create.argtypes = [c_char_p]
\r
147 + _create.restype = NotmuchDatabaseP
\r
149 def __init__(self, path=None, create=False, mode=0):
\r
150 """If *path* is `None`, we will try to read a users notmuch
\r
151 @@ -186,6 +199,10 @@ class Database(object):
\r
152 self._assert_db_is_initialized()
\r
153 return Database._get_version(self._db)
\r
155 + _needs_upgrade = nmlib.notmuch_database_needs_upgrade
\r
156 + _needs_upgrade.argtypes = [NotmuchDatabaseP]
\r
157 + _needs_upgrade.restype = bool
\r
159 def needs_upgrade(self):
\r
160 """Does this database need to be upgraded before writing to it?
\r
162 @@ -197,7 +214,7 @@ class Database(object):
\r
163 :returns: `True` or `False`
\r
165 self._assert_db_is_initialized()
\r
166 - return nmlib.notmuch_database_needs_upgrade(self._db)
\r
167 + return self._needs_upgrade(self._db)
\r
170 """Upgrades the current database
\r
171 @@ -219,6 +236,10 @@ class Database(object):
\r
172 #TODO: catch exceptions, document return values and etc
\r
175 + _begin_atomic = nmlib.notmuch_database_begin_atomic
\r
176 + _begin_atomic.argtypes = [NotmuchDatabaseP]
\r
177 + _begin_atomic.restype = c_uint
\r
179 def begin_atomic(self):
\r
180 """Begin an atomic database operation
\r
182 @@ -236,11 +257,15 @@ class Database(object):
\r
184 *Added in notmuch 0.9*"""
\r
185 self._assert_db_is_initialized()
\r
186 - status = nmlib.notmuch_database_begin_atomic(self._db)
\r
187 + status = self._begin_atomic(self._db)
\r
188 if status != STATUS.SUCCESS:
\r
189 raise NotmuchError(status)
\r
192 + _end_atomic = nmlib.notmuch_database_end_atomic
\r
193 + _end_atomic.argtypes = [NotmuchDatabaseP]
\r
194 + _end_atomic.restype = c_uint
\r
196 def end_atomic(self):
\r
197 """Indicate the end of an atomic database operation
\r
199 @@ -258,7 +283,7 @@ class Database(object):
\r
201 *Added in notmuch 0.9*"""
\r
202 self._assert_db_is_initialized()
\r
203 - status = nmlib.notmuch_database_end_atomic(self._db)
\r
204 + status = self._end_atomic(self._db)
\r
205 if status != STATUS.SUCCESS:
\r
206 raise NotmuchError(status)
\r
208 @@ -299,6 +324,10 @@ class Database(object):
\r
209 # return the Directory, init it with the absolute path
\r
210 return Directory(_str(abs_dirpath), dir_p, self)
\r
212 + _add_message = nmlib.notmuch_database_add_message
\r
213 + _add_message.argtypes = [NotmuchDatabaseP, c_char_p, POINTER(NotmuchMessageP)]
\r
214 + _add_message.restype = c_uint
\r
216 def add_message(self, filename, sync_maildir_flags=False):
\r
217 """Adds a new message to the database
\r
219 @@ -350,9 +379,7 @@ class Database(object):
\r
221 self._assert_db_is_initialized()
\r
223 - status = nmlib.notmuch_database_add_message(self._db,
\r
226 + status = self._add_message(self._db, _str(filename), byref(msg_p))
\r
228 if not status in [STATUS.SUCCESS, STATUS.DUPLICATE_MESSAGE_ID]:
\r
229 raise NotmuchError(status)
\r
230 @@ -364,6 +391,10 @@ class Database(object):
\r
231 msg.maildir_flags_to_tags()
\r
232 return (msg, status)
\r
234 + _remove_message = nmlib.notmuch_database_remove_message
\r
235 + _remove_message.argtypes = [NotmuchDatabaseP, c_char_p]
\r
236 + _remove_message.restype = c_uint
\r
238 def remove_message(self, filename):
\r
239 """Removes a message (filename) from the given notmuch database
\r
241 @@ -392,8 +423,7 @@ class Database(object):
\r
244 self._assert_db_is_initialized()
\r
245 - return nmlib.notmuch_database_remove_message(self._db,
\r
247 + return self._remove_message(self._db, filename)
\r
249 def find_message(self, msgid):
\r
250 """Returns a :class:`Message` as identified by its message ID
\r
251 @@ -491,10 +521,14 @@ class Database(object):
\r
252 def __repr__(self):
\r
253 return "'Notmuch DB " + self.get_path() + "'"
\r
255 + _close = nmlib.notmuch_database_close
\r
256 + _close.argtypes = [NotmuchDatabaseP]
\r
257 + _close.restype = None
\r
260 """Close and free the notmuch database if needed"""
\r
261 if self._db is not None:
\r
262 - nmlib.notmuch_database_close(self._db)
\r
263 + self._close(self._db)
\r
265 def _get_user_default_db(self):
\r
266 """ Reads a user's notmuch config and returns his db location
\r
267 @@ -545,18 +579,22 @@ class Query(object):
\r
269 """notmuch_query_create"""
\r
270 _create = nmlib.notmuch_query_create
\r
271 - _create.restype = c_void_p
\r
272 + _create.argtypes = [NotmuchDatabaseP, c_char_p]
\r
273 + _create.restype = NotmuchQueryP
\r
275 """notmuch_query_search_threads"""
\r
276 _search_threads = nmlib.notmuch_query_search_threads
\r
277 - _search_threads.restype = c_void_p
\r
278 + _search_threads.argtypes = [NotmuchQueryP]
\r
279 + _search_threads.restype = NotmuchThreadsP
\r
281 """notmuch_query_search_messages"""
\r
282 _search_messages = nmlib.notmuch_query_search_messages
\r
283 - _search_messages.restype = c_void_p
\r
284 + _search_messages.argtypes = [NotmuchQueryP]
\r
285 + _search_messages.restype = NotmuchMessagesP
\r
287 """notmuch_query_count_messages"""
\r
288 _count_messages = nmlib.notmuch_query_count_messages
\r
289 + _count_messages.argtypes = [NotmuchQueryP]
\r
290 _count_messages.restype = c_uint
\r
292 def __init__(self, db, querystr):
\r
293 @@ -602,6 +640,10 @@ class Query(object):
\r
294 raise NullPointerError
\r
295 self._query = query_p
\r
297 + _set_sort = nmlib.notmuch_query_set_sort
\r
298 + _set_sort.argtypes = [NotmuchQueryP, c_uint]
\r
299 + _set_sort.argtypes = None
\r
301 def set_sort(self, sort):
\r
302 """Set the sort order future results will be delivered in
\r
304 @@ -609,7 +651,7 @@ class Query(object):
\r
306 self._assert_query_is_initialized()
\r
308 - nmlib.notmuch_query_set_sort(self._query, sort)
\r
309 + self._set_sort(self._query, sort)
\r
311 def search_threads(self):
\r
312 """Execute a query for threads
\r
313 @@ -661,10 +703,14 @@ class Query(object):
\r
314 self._assert_query_is_initialized()
\r
315 return Query._count_messages(self._query)
\r
317 + _destroy = nmlib.notmuch_query_destroy
\r
318 + _destroy.argtypes = [NotmuchQueryP]
\r
319 + _destroy.restype = None
\r
322 """Close and free the Query"""
\r
323 if self._query is not None:
\r
324 - nmlib.notmuch_query_destroy(self._query)
\r
325 + self._destroy(self._query)
\r
328 class Directory(object):
\r
329 @@ -683,19 +729,23 @@ class Directory(object):
\r
331 """notmuch_directory_get_mtime"""
\r
332 _get_mtime = nmlib.notmuch_directory_get_mtime
\r
333 + _get_mtime.argtypes = [NotmuchDirectoryP]
\r
334 _get_mtime.restype = c_long
\r
336 """notmuch_directory_set_mtime"""
\r
337 _set_mtime = nmlib.notmuch_directory_set_mtime
\r
338 - _set_mtime.argtypes = [c_char_p, c_long]
\r
339 + _set_mtime.argtypes = [NotmuchDirectoryP, c_long]
\r
340 + _set_mtime.restype = c_uint
\r
342 """notmuch_directory_get_child_files"""
\r
343 _get_child_files = nmlib.notmuch_directory_get_child_files
\r
344 - _get_child_files.restype = c_void_p
\r
345 + _get_child_files.argtypes = [NotmuchDirectoryP]
\r
346 + _get_child_files.restype = NotmuchFilenamesP
\r
348 """notmuch_directory_get_child_directories"""
\r
349 _get_child_directories = nmlib.notmuch_directory_get_child_directories
\r
350 - _get_child_directories.restype = c_void_p
\r
351 + _get_child_directories.argtypes = [NotmuchDirectoryP]
\r
352 + _get_child_directories.restype = NotmuchFilenamesP
\r
354 def _assert_dir_is_initialized(self):
\r
355 """Raises a NotmuchError(:attr:`STATUS`.NOT_INITIALIZED) if dir_p is None"""
\r
356 @@ -815,10 +865,14 @@ class Directory(object):
\r
357 """Object representation"""
\r
358 return "<notmuch Directory object '%s'>" % self._path
\r
360 + _destroy = nmlib.notmuch_directory_destroy
\r
361 + _destroy.argtypes = [NotmuchDirectoryP]
\r
362 + _destroy.argtypes = None
\r
365 """Close and free the Directory"""
\r
366 if self._dir_p is not None:
\r
367 - nmlib.notmuch_directory_destroy(self._dir_p)
\r
368 + self._destroy(self._dir_p)
\r
371 class Filenames(object):
\r
372 @@ -826,6 +880,7 @@ class Filenames(object):
\r
374 #notmuch_filenames_get
\r
375 _get = nmlib.notmuch_filenames_get
\r
376 + _get.argtypes = [NotmuchFilenamesP]
\r
377 _get.restype = c_char_p
\r
379 def __init__(self, files_p, parent):
\r
380 @@ -844,16 +899,24 @@ class Filenames(object):
\r
381 """ Make Filenames an iterator """
\r
384 + _valid = nmlib.notmuch_filenames_valid
\r
385 + _valid.argtypes = [NotmuchFilenamesP]
\r
386 + _valid.restype = bool
\r
388 + _move_to_next = nmlib.notmuch_filenames_move_to_next
\r
389 + _move_to_next.argtypes = [NotmuchFilenamesP]
\r
390 + _move_to_next.restype = None
\r
393 if self._files_p is None:
\r
394 raise NotmuchError(STATUS.NOT_INITIALIZED)
\r
396 - if not nmlib.notmuch_filenames_valid(self._files_p):
\r
397 + if not self._valid(self._files_p):
\r
398 self._files_p = None
\r
399 raise StopIteration
\r
401 file = Filenames._get(self._files_p)
\r
402 - nmlib.notmuch_filenames_move_to_next(self._files_p)
\r
403 + self._move_to_next(self._files_p)
\r
407 @@ -872,13 +935,17 @@ class Filenames(object):
\r
408 raise NotmuchError(STATUS.NOT_INITIALIZED)
\r
411 - while nmlib.notmuch_filenames_valid(self._files_p):
\r
412 - nmlib.notmuch_filenames_move_to_next(self._files_p)
\r
413 + while self._valid(self._files_p):
\r
414 + self._move_to_next(self._files_p)
\r
416 self._files_p = None
\r
419 + _destroy = nmlib.notmuch_filenames_destroy
\r
420 + _destroy.argtypes = [NotmuchFilenamesP]
\r
421 + _destroy.restype = None
\r
424 """Close and free Filenames"""
\r
425 if self._files_p is not None:
\r
426 - nmlib.notmuch_filenames_destroy(self._files_p)
\r
427 + self._destroy(self._files_p)
\r
428 diff --git a/bindings/python/notmuch/filename.py b/bindings/python/notmuch/filename.py
\r
429 index de4d785..077754e 100644
\r
430 --- a/bindings/python/notmuch/filename.py
\r
431 +++ b/bindings/python/notmuch/filename.py
\r
432 @@ -17,7 +17,8 @@ along with notmuch. If not, see <http://www.gnu.org/licenses/>.
\r
433 Copyright 2010 Sebastian Spaeth <Sebastian@SSpaeth.de>'
\r
435 from ctypes import c_char_p
\r
436 -from notmuch.globals import nmlib, STATUS, NotmuchError
\r
437 +from notmuch.globals import (nmlib, STATUS, NotmuchError,
\r
438 + NotmuchFilenamesP, NotmuchMessagesP, NotmuchMessageP)
\r
441 class Filenames(object):
\r
442 @@ -50,6 +51,7 @@ class Filenames(object):
\r
444 #notmuch_filenames_get
\r
445 _get = nmlib.notmuch_filenames_get
\r
446 + _get.argtypes = [NotmuchFilenamesP]
\r
447 _get.restype = c_char_p
\r
449 def __init__(self, files_p, parent):
\r
450 @@ -74,6 +76,14 @@ class Filenames(object):
\r
451 #save reference to parent object so we keep it alive
\r
452 self._parent = parent
\r
454 + _valid = nmlib.notmuch_filenames_valid
\r
455 + _valid.argtypes = [NotmuchFilenamesP]
\r
456 + _valid.restype = bool
\r
458 + _move_to_next = nmlib.notmuch_filenames_move_to_next
\r
459 + _move_to_next.argtypes = [NotmuchFilenamesP]
\r
460 + _move_to_next.restype = None
\r
462 def as_generator(self):
\r
463 """Return generator of Filenames
\r
465 @@ -82,9 +92,9 @@ class Filenames(object):
\r
466 if self._files is None:
\r
467 raise NotmuchError(STATUS.NOT_INITIALIZED)
\r
469 - while nmlib.notmuch_filenames_valid(self._files):
\r
470 + while self._valid(self._files):
\r
471 yield Filenames._get(self._files)
\r
472 - nmlib.notmuch_filenames_move_to_next(self._files)
\r
473 + self._move_to_next(self._files)
\r
477 @@ -101,7 +111,11 @@ class Filenames(object):
\r
479 return "\n".join(self)
\r
481 + _destroy = nmlib.notmuch_filenames_destroy
\r
482 + _destroy.argtypes = [NotmuchMessageP]
\r
483 + _destroy.restype = None
\r
486 """Close and free the notmuch filenames"""
\r
487 if self._files is not None:
\r
488 - nmlib.notmuch_filenames_destroy(self._files)
\r
489 + self._destroy(self._files)
\r
490 diff --git a/bindings/python/notmuch/message.py b/bindings/python/notmuch/message.py
\r
491 index 4bf90c2..e0c7eda 100644
\r
492 --- a/bindings/python/notmuch/message.py
\r
493 +++ b/bindings/python/notmuch/message.py
\r
494 @@ -21,7 +21,8 @@ Copyright 2010 Sebastian Spaeth <Sebastian@SSpaeth.de>'
\r
496 from ctypes import c_char_p, c_void_p, c_long, c_uint, c_int
\r
497 from datetime import date
\r
498 -from notmuch.globals import nmlib, STATUS, NotmuchError, Enum, _str
\r
499 +from notmuch.globals import (nmlib, STATUS, NotmuchError, Enum, _str,
\r
500 + NotmuchTagsP, NotmuchMessagesP, NotmuchMessageP, NotmuchFilenamesP)
\r
501 from notmuch.tag import Tags
\r
502 from notmuch.filename import Filenames
\r
504 @@ -92,10 +93,12 @@ class Messages(object):
\r
506 #notmuch_messages_get
\r
507 _get = nmlib.notmuch_messages_get
\r
508 - _get.restype = c_void_p
\r
509 + _get.argtypes = [NotmuchMessagesP]
\r
510 + _get.restype = NotmuchMessageP
\r
512 _collect_tags = nmlib.notmuch_messages_collect_tags
\r
513 - _collect_tags.restype = c_void_p
\r
514 + _collect_tags.argtypes = [NotmuchMessagesP]
\r
515 + _collect_tags.restype = NotmuchTagsP
\r
517 def __init__(self, msgs_p, parent=None):
\r
519 @@ -146,16 +149,24 @@ class Messages(object):
\r
520 """ Make Messages an iterator """
\r
523 + _valid = nmlib.notmuch_messages_valid
\r
524 + _valid.argtypes = [NotmuchMessagesP]
\r
525 + _valid.restype = bool
\r
527 + _move_to_next = nmlib.notmuch_messages_move_to_next
\r
528 + _move_to_next.argtypes = [NotmuchMessagesP]
\r
529 + _move_to_next.restype = None
\r
532 if self._msgs is None:
\r
533 raise NotmuchError(STATUS.NOT_INITIALIZED)
\r
535 - if not nmlib.notmuch_messages_valid(self._msgs):
\r
536 + if not self._valid(self._msgs):
\r
538 raise StopIteration
\r
540 msg = Message(Messages._get(self._msgs), self)
\r
541 - nmlib.notmuch_messages_move_to_next(self._msgs)
\r
542 + self._move_to_next(self._msgs)
\r
545 def __nonzero__(self):
\r
546 @@ -163,12 +174,16 @@ class Messages(object):
\r
547 :return: True if there is at least one more thread in the
\r
548 Iterator, False if not."""
\r
549 return self._msgs is not None and \
\r
550 - nmlib.notmuch_messages_valid(self._msgs) > 0
\r
551 + self._valid(self._msgs) > 0
\r
553 + _destroy = nmlib.notmuch_messages_destroy
\r
554 + _destroy.argtypes = [NotmuchMessagesP]
\r
555 + _destroy.restype = None
\r
558 """Close and free the notmuch Messages"""
\r
559 if self._msgs is not None:
\r
560 - nmlib.notmuch_messages_destroy(self._msgs)
\r
561 + self._destroy(self._msgs)
\r
563 def print_messages(self, format, indent=0, entire_thread=False):
\r
564 """Outputs messages as needed for 'notmuch show' to sys.stdout
\r
565 @@ -235,44 +250,60 @@ class Message(object):
\r
567 """notmuch_message_get_filename (notmuch_message_t *message)"""
\r
568 _get_filename = nmlib.notmuch_message_get_filename
\r
569 + _get_filename.argtypes = [NotmuchMessageP]
\r
570 _get_filename.restype = c_char_p
\r
572 """return all filenames for a message"""
\r
573 _get_filenames = nmlib.notmuch_message_get_filenames
\r
574 - _get_filenames.restype = c_void_p
\r
575 + _get_filenames.argtypes = [NotmuchMessageP]
\r
576 + _get_filenames.restype = NotmuchFilenamesP
\r
578 """notmuch_message_get_flag"""
\r
579 _get_flag = nmlib.notmuch_message_get_flag
\r
580 - _get_flag.restype = c_uint
\r
581 + _get_flag.argtypes = [NotmuchMessageP, c_uint]
\r
582 + _get_flag.restype = bool
\r
584 + """notmuch_message_set_flag"""
\r
585 + _set_flag = nmlib.notmuch_message_set_flag
\r
586 + _set_flag.argtypes = [NotmuchMessageP, c_uint, c_int]
\r
587 + _set_flag.restype = None
\r
589 """notmuch_message_get_message_id (notmuch_message_t *message)"""
\r
590 _get_message_id = nmlib.notmuch_message_get_message_id
\r
591 + _get_message_id.argtypes = [NotmuchMessageP]
\r
592 _get_message_id.restype = c_char_p
\r
594 """notmuch_message_get_thread_id"""
\r
595 _get_thread_id = nmlib.notmuch_message_get_thread_id
\r
596 + _get_thread_id.argtypes = [NotmuchMessageP]
\r
597 _get_thread_id.restype = c_char_p
\r
599 """notmuch_message_get_replies"""
\r
600 _get_replies = nmlib.notmuch_message_get_replies
\r
601 - _get_replies.restype = c_void_p
\r
602 + _get_replies.argtypes = [NotmuchMessageP]
\r
603 + _get_replies.restype = NotmuchMessagesP
\r
605 """notmuch_message_get_tags (notmuch_message_t *message)"""
\r
606 _get_tags = nmlib.notmuch_message_get_tags
\r
607 - _get_tags.restype = c_void_p
\r
608 + _get_tags.argtypes = [NotmuchMessageP]
\r
609 + _get_tags.restype = NotmuchTagsP
\r
611 _get_date = nmlib.notmuch_message_get_date
\r
612 + _get_date.argtypes = [NotmuchMessageP]
\r
613 _get_date.restype = c_long
\r
615 _get_header = nmlib.notmuch_message_get_header
\r
616 + _get_header.argtypes = [NotmuchMessageP, c_char_p]
\r
617 _get_header.restype = c_char_p
\r
619 """notmuch_status_t ..._maildir_flags_to_tags (notmuch_message_t *)"""
\r
620 _tags_to_maildir_flags = nmlib.notmuch_message_tags_to_maildir_flags
\r
621 + _tags_to_maildir_flags.argtypes = [NotmuchMessageP]
\r
622 _tags_to_maildir_flags.restype = c_int
\r
624 """notmuch_status_t ..._tags_to_maildir_flags (notmuch_message_t *)"""
\r
625 _maildir_flags_to_tags = nmlib.notmuch_message_maildir_flags_to_tags
\r
626 + _maildir_flags_to_tags.argtypes = [NotmuchMessageP]
\r
627 _maildir_flags_to_tags.restype = c_int
\r
629 #Constants: Flags that can be set/get with set_flag
\r
630 @@ -450,7 +481,7 @@ class Message(object):
\r
632 if self._msg is None:
\r
633 raise NotmuchError(STATUS.NOT_INITIALIZED)
\r
634 - nmlib.notmuch_message_set_flag(self._msg, flag, value)
\r
635 + self._set_flag(self._msg, flag, value)
\r
637 def get_tags(self):
\r
638 """Returns the message tags
\r
639 @@ -470,6 +501,10 @@ class Message(object):
\r
640 raise NotmuchError(STATUS.NULL_POINTER)
\r
641 return Tags(tags_p, self)
\r
643 + _add_tag = nmlib.notmuch_message_add_tag
\r
644 + _add_tag.argtypes = [NotmuchMessageP, c_char_p]
\r
645 + _add_tag.restype = c_uint
\r
647 def add_tag(self, tag, sync_maildir_flags=False):
\r
648 """Adds a tag to the given message
\r
650 @@ -504,7 +539,7 @@ class Message(object):
\r
651 if self._msg is None:
\r
652 raise NotmuchError(STATUS.NOT_INITIALIZED)
\r
654 - status = nmlib.notmuch_message_add_tag(self._msg, _str(tag))
\r
655 + status = self._add_tag(self._msg, _str(tag))
\r
657 # bail out on failure
\r
658 if status != STATUS.SUCCESS:
\r
659 @@ -514,6 +549,10 @@ class Message(object):
\r
660 self.tags_to_maildir_flags()
\r
661 return STATUS.SUCCESS
\r
663 + _remove_tag = nmlib.notmuch_message_remove_tag
\r
664 + _remove_tag.argtypes = [NotmuchMessageP, c_char_p]
\r
665 + _remove_tag.restype = c_uint
\r
667 def remove_tag(self, tag, sync_maildir_flags=False):
\r
668 """Removes a tag from the given message
\r
670 @@ -548,7 +587,7 @@ class Message(object):
\r
671 if self._msg is None:
\r
672 raise NotmuchError(STATUS.NOT_INITIALIZED)
\r
674 - status = nmlib.notmuch_message_remove_tag(self._msg, _str(tag))
\r
675 + status = self._remove_tag(self._msg, _str(tag))
\r
676 # bail out on error
\r
677 if status != STATUS.SUCCESS:
\r
678 raise NotmuchError(status)
\r
679 @@ -557,6 +596,10 @@ class Message(object):
\r
680 self.tags_to_maildir_flags()
\r
681 return STATUS.SUCCESS
\r
683 + _remove_all_tags = nmlib.notmuch_message_remove_all_tags
\r
684 + _remove_all_tags.argtypes = [NotmuchMessageP]
\r
685 + _remove_all_tags.restype = c_uint
\r
687 def remove_all_tags(self, sync_maildir_flags=False):
\r
688 """Removes all tags from the given message.
\r
690 @@ -585,7 +628,7 @@ class Message(object):
\r
691 if self._msg is None:
\r
692 raise NotmuchError(STATUS.NOT_INITIALIZED)
\r
694 - status = nmlib.notmuch_message_remove_all_tags(self._msg)
\r
695 + status = self._remove_all_tags(self._msg)
\r
697 # bail out on error
\r
698 if status != STATUS.SUCCESS:
\r
699 @@ -595,6 +638,10 @@ class Message(object):
\r
700 self.tags_to_maildir_flags()
\r
701 return STATUS.SUCCESS
\r
703 + _freeze = nmlib.notmuch_message_freeze
\r
704 + _freeze.argtypes = [NotmuchMessageP]
\r
705 + _freeze.restype = c_uint
\r
708 """Freezes the current state of 'message' within the database
\r
710 @@ -639,7 +686,7 @@ class Message(object):
\r
711 if self._msg is None:
\r
712 raise NotmuchError(STATUS.NOT_INITIALIZED)
\r
714 - status = nmlib.notmuch_message_freeze(self._msg)
\r
715 + status = self._freeze(self._msg)
\r
717 if STATUS.SUCCESS == status:
\r
718 # return on success
\r
719 @@ -647,6 +694,10 @@ class Message(object):
\r
721 raise NotmuchError(status)
\r
723 + _thaw = nmlib.notmuch_message_thaw
\r
724 + _thaw.argtypes = [NotmuchMessageP]
\r
725 + _thaw.restype = c_uint
\r
728 """Thaws the current 'message'
\r
730 @@ -674,7 +725,7 @@ class Message(object):
\r
731 if self._msg is None:
\r
732 raise NotmuchError(STATUS.NOT_INITIALIZED)
\r
734 - status = nmlib.notmuch_message_thaw(self._msg)
\r
735 + status = self._thaw(self._msg)
\r
737 if STATUS.SUCCESS == status:
\r
738 # return on success
\r
739 @@ -896,7 +947,11 @@ class Message(object):
\r
740 res = cmp(list(self.get_filenames()), list(other.get_filenames()))
\r
743 + _destroy = nmlib.notmuch_message_destroy
\r
744 + _destroy.argtypes = [NotmuchMessageP]
\r
745 + _destroy.restype = None
\r
748 """Close and free the notmuch Message"""
\r
749 if self._msg is not None:
\r
750 - nmlib.notmuch_message_destroy(self._msg)
\r
751 + self._destroy(self._msg)
\r
752 diff --git a/bindings/python/notmuch/tag.py b/bindings/python/notmuch/tag.py
\r
753 index 50e3686..f3a3d27 100644
\r
754 --- a/bindings/python/notmuch/tag.py
\r
755 +++ b/bindings/python/notmuch/tag.py
\r
756 @@ -17,7 +17,7 @@ along with notmuch. If not, see <http://www.gnu.org/licenses/>.
\r
757 Copyright 2010 Sebastian Spaeth <Sebastian@SSpaeth.de>'
\r
759 from ctypes import c_char_p
\r
760 -from notmuch.globals import nmlib, STATUS, NotmuchError
\r
761 +from notmuch.globals import nmlib, STATUS, NotmuchError, NotmuchTagsP
\r
764 class Tags(object):
\r
765 @@ -50,6 +50,7 @@ class Tags(object):
\r
768 _get = nmlib.notmuch_tags_get
\r
769 + _get.argtypes = [NotmuchTagsP]
\r
770 _get.restype = c_char_p
\r
772 def __init__(self, tags_p, parent=None):
\r
773 @@ -80,14 +81,22 @@ class Tags(object):
\r
774 """ Make Tags an iterator """
\r
777 + _valid = nmlib.notmuch_tags_valid
\r
778 + _valid.argtypes = [NotmuchTagsP]
\r
779 + _valid.restype = bool
\r
781 + _move_to_next = nmlib.notmuch_tags_move_to_next
\r
782 + _move_to_next.argtypes = [NotmuchTagsP]
\r
783 + _move_to_next.restype = None
\r
786 if self._tags is None:
\r
787 raise NotmuchError(STATUS.NOT_INITIALIZED)
\r
788 - if not nmlib.notmuch_tags_valid(self._tags):
\r
789 + if not self._valid(self._tags):
\r
791 raise StopIteration
\r
792 tag = Tags._get(self._tags).decode('UTF-8')
\r
793 - nmlib.notmuch_tags_move_to_next(self._tags)
\r
794 + self._move_to_next(self._tags)
\r
797 def __nonzero__(self):
\r
798 @@ -99,7 +108,7 @@ class Tags(object):
\r
800 :returns: True if the Tags() iterator has at least one more Tag
\r
802 - return nmlib.notmuch_tags_valid(self._tags) > 0
\r
803 + return self._valid(self._tags) > 0
\r
806 """The str() representation of Tags() is a space separated list of tags
\r
807 @@ -112,7 +121,11 @@ class Tags(object):
\r
809 return " ".join(self)
\r
811 + _destroy = nmlib.notmuch_tags_destroy
\r
812 + _destroy.argtypes = [NotmuchTagsP]
\r
813 + _destroy.restype = None
\r
816 """Close and free the notmuch tags"""
\r
817 if self._tags is not None:
\r
818 - nmlib.notmuch_tags_destroy(self._tags)
\r
819 + self._destroy(self._tags)
\r
820 diff --git a/bindings/python/notmuch/thread.py b/bindings/python/notmuch/thread.py
\r
821 index 5e08eb3..d903c76 100644
\r
822 --- a/bindings/python/notmuch/thread.py
\r
823 +++ b/bindings/python/notmuch/thread.py
\r
824 @@ -17,8 +17,10 @@ along with notmuch. If not, see <http://www.gnu.org/licenses/>.
\r
825 Copyright 2010 Sebastian Spaeth <Sebastian@SSpaeth.de>'
\r
828 -from ctypes import c_char_p, c_void_p, c_long
\r
829 -from notmuch.globals import nmlib, STATUS, NotmuchError
\r
830 +from ctypes import c_char_p, c_void_p, c_long, c_int
\r
831 +from notmuch.globals import (nmlib, STATUS,
\r
832 + NotmuchError, NotmuchThreadP, NotmuchThreadsP, NotmuchMessagesP,
\r
834 from notmuch.message import Messages
\r
835 from notmuch.tag import Tags
\r
836 from datetime import date
\r
837 @@ -75,7 +77,8 @@ class Threads(object):
\r
839 #notmuch_threads_get
\r
840 _get = nmlib.notmuch_threads_get
\r
841 - _get.restype = c_void_p
\r
842 + _get.argtypes = [NotmuchThreadsP]
\r
843 + _get.restype = NotmuchThreadP
\r
845 def __init__(self, threads_p, parent=None):
\r
847 @@ -105,16 +108,24 @@ class Threads(object):
\r
848 """ Make Threads an iterator """
\r
851 + _valid = nmlib.notmuch_threads_valid
\r
852 + _valid.argtypes = [NotmuchThreadsP]
\r
853 + _valid.restype = bool
\r
855 + _move_to_next = nmlib.notmuch_threads_move_to_next
\r
856 + _move_to_next.argtypes = [NotmuchThreadsP]
\r
857 + _move_to_next.restype = None
\r
860 if self._threads is None:
\r
861 raise NotmuchError(STATUS.NOT_INITIALIZED)
\r
863 - if not nmlib.notmuch_threads_valid(self._threads):
\r
864 + if not self._valid(self._threads):
\r
865 self._threads = None
\r
866 raise StopIteration
\r
868 thread = Thread(Threads._get(self._threads), self)
\r
869 - nmlib.notmuch_threads_move_to_next(self._threads)
\r
870 + self._move_to_next(self._threads)
\r
874 @@ -134,8 +145,8 @@ class Threads(object):
\r
877 # returns 'bool'. On out-of-memory it returns None
\r
878 - while nmlib.notmuch_threads_valid(self._threads):
\r
879 - nmlib.notmuch_threads_move_to_next(self._threads)
\r
880 + while self._valid(self._threads):
\r
881 + self._move_to_next(self._threads)
\r
883 # reset self._threads to mark as "exhausted"
\r
884 self._threads = None
\r
885 @@ -153,12 +164,16 @@ class Threads(object):
\r
886 Iterator, False if not. None on a "Out-of-memory" error.
\r
888 return self._threads is not None and \
\r
889 - nmlib.notmuch_threads_valid(self._threads) > 0
\r
890 + self._valid(self._threads) > 0
\r
892 + _destroy = nmlib.notmuch_threads_destroy
\r
893 + _destroy.argtypes = [NotmuchThreadsP]
\r
894 + _destroy.argtypes = None
\r
897 """Close and free the notmuch Threads"""
\r
898 if self._threads is not None:
\r
899 - nmlib.notmuch_messages_destroy(self._threads)
\r
900 + self._destroy(self._threads)
\r
903 class Thread(object):
\r
904 @@ -166,29 +181,36 @@ class Thread(object):
\r
906 """notmuch_thread_get_thread_id"""
\r
907 _get_thread_id = nmlib.notmuch_thread_get_thread_id
\r
908 + _get_thread_id.argtypes = [NotmuchThreadP]
\r
909 _get_thread_id.restype = c_char_p
\r
911 """notmuch_thread_get_authors"""
\r
912 _get_authors = nmlib.notmuch_thread_get_authors
\r
913 + _get_authors.argtypes = [NotmuchThreadP]
\r
914 _get_authors.restype = c_char_p
\r
916 """notmuch_thread_get_subject"""
\r
917 _get_subject = nmlib.notmuch_thread_get_subject
\r
918 + _get_subject.argtypes = [NotmuchThreadP]
\r
919 _get_subject.restype = c_char_p
\r
921 """notmuch_thread_get_toplevel_messages"""
\r
922 _get_toplevel_messages = nmlib.notmuch_thread_get_toplevel_messages
\r
923 - _get_toplevel_messages.restype = c_void_p
\r
924 + _get_toplevel_messages.argtypes = [NotmuchThreadP]
\r
925 + _get_toplevel_messages.restype = NotmuchMessagesP
\r
927 _get_newest_date = nmlib.notmuch_thread_get_newest_date
\r
928 + _get_newest_date.argtypes = [NotmuchThreadP]
\r
929 _get_newest_date.restype = c_long
\r
931 _get_oldest_date = nmlib.notmuch_thread_get_oldest_date
\r
932 + _get_oldest_date.argtypes = [NotmuchThreadP]
\r
933 _get_oldest_date.restype = c_long
\r
935 """notmuch_thread_get_tags"""
\r
936 _get_tags = nmlib.notmuch_thread_get_tags
\r
937 - _get_tags.restype = c_void_p
\r
938 + _get_tags.argtypes = [NotmuchThreadP]
\r
939 + _get_tags.restype = NotmuchTagsP
\r
941 def __init__(self, thread_p, parent=None):
\r
943 @@ -225,6 +247,11 @@ class Thread(object):
\r
944 raise NotmuchError(STATUS.NOT_INITIALIZED)
\r
945 return Thread._get_thread_id(self._thread)
\r
948 + _get_total_messages = nmlib.notmuch_thread_get_total_messages
\r
949 + _get_total_messages.argtypes = [NotmuchThreadP]
\r
950 + _get_total_messages.restype = c_int
\r
952 def get_total_messages(self):
\r
953 """Get the total number of messages in 'thread'
\r
955 @@ -236,7 +263,7 @@ class Thread(object):
\r
957 if self._thread is None:
\r
958 raise NotmuchError(STATUS.NOT_INITIALIZED)
\r
959 - return nmlib.notmuch_thread_get_total_messages(self._thread)
\r
960 + return self._get_total_messages(self._thread)
\r
962 def get_toplevel_messages(self):
\r
963 """Returns a :class:`Messages` iterator for the top-level messages in
\r
964 @@ -267,6 +294,10 @@ class Thread(object):
\r
966 return Messages(msgs_p, self)
\r
968 + _get_matched_messages = nmlib.notmuch_thread_get_matched_messages
\r
969 + _get_matched_messages.argtypes = [NotmuchThreadP]
\r
970 + _get_matched_messages.restype = c_int
\r
972 def get_matched_messages(self):
\r
973 """Returns the number of messages in 'thread' that matched the query
\r
975 @@ -278,7 +309,7 @@ class Thread(object):
\r
977 if self._thread is None:
\r
978 raise NotmuchError(STATUS.NOT_INITIALIZED)
\r
979 - return nmlib.notmuch_thread_get_matched_messages(self._thread)
\r
980 + return self._get_matched_messages(self._thread)
\r
982 def get_authors(self):
\r
983 """Returns the authors of 'thread'
\r
984 @@ -387,7 +418,11 @@ class Thread(object):
\r
988 + _destroy = nmlib.notmuch_thread_destroy
\r
989 + _destroy.argtypes = [NotmuchThreadP]
\r
990 + _destroy.restype = None
\r
993 """Close and free the notmuch Thread"""
\r
994 if self._thread is not None:
\r
995 - nmlib.notmuch_thread_destroy(self._thread)
\r
996 + self._destroy(self._thread)
\r