package notmuch
/*
+#cgo LDFLAGS: -lnotmuch
+
#include <stdlib.h>
#include <string.h>
#include <time.h>
// Status codes used for the return values of most functions
type Status C.notmuch_status_t
+
const (
STATUS_SUCCESS Status = iota
STATUS_OUT_OF_MEMORY
- STATUS_READ_ONLY_DATABASE
- STATUS_XAPIAN_EXCEPTION
- STATUS_FILE_ERROR
- STATUS_FILE_NOT_EMAIL
- STATUS_DUPLICATE_MESSAGE_ID
- STATUS_NULL_POINTER
- STATUS_TAG_TOO_LONG
- STATUS_UNBALANCED_FREEZE_THAW
- STATUS_UNBALANCED_ATOMIC
-
- STATUS_LAST_STATUS
+ STATUS_READ_ONLY_DATABASE
+ STATUS_XAPIAN_EXCEPTION
+ STATUS_FILE_ERROR
+ STATUS_FILE_NOT_EMAIL
+ STATUS_DUPLICATE_MESSAGE_ID
+ STATUS_NULL_POINTER
+ STATUS_TAG_TOO_LONG
+ STATUS_UNBALANCED_FREEZE_THAW
+ STATUS_UNBALANCED_ATOMIC
+
+ STATUS_LAST_STATUS
)
func (self Status) String() string {
var p *C.char
-
+
// p is read-only
p = C.notmuch_status_to_string(C.notmuch_status_t(self))
if p != nil {
}
type DatabaseMode C.notmuch_database_mode_t
+
const (
- DATABASE_MODE_READ_ONLY DatabaseMode = 0
- DATABASE_MODE_READ_WRITE
+ DATABASE_MODE_READ_ONLY DatabaseMode = 0
+ DATABASE_MODE_READ_WRITE
)
// Create a new, empty notmuch database located at 'path'
return nil, STATUS_OUT_OF_MEMORY
}
- self := &Database{db:nil}
+ self := &Database{db: nil}
st := Status(C.notmuch_database_create(c_path, &self.db))
if st != STATUS_SUCCESS {
return nil, st
return nil, STATUS_OUT_OF_MEMORY
}
- self := &Database{db:nil}
+ self := &Database{db: nil}
st := Status(C.notmuch_database_open(c_path, C.notmuch_database_mode_t(mode), &self.db))
if st != STATUS_SUCCESS {
return nil, st
/* Close the given notmuch database, freeing all associated
* resources. See notmuch_database_open. */
-func (self *Database) Close() {
- C.notmuch_database_destroy(self.db)
+func (self *Database) Close() Status {
+ return Status(C.notmuch_database_destroy(self.db))
}
/* Return the database path of the given database.
*/
func (self *Database) GetPath() string {
-
- /* The return value is a string owned by notmuch so should not be
- * modified nor freed by the caller. */
+
+ /* The return value is a string owned by notmuch so should not be
+ * modified nor freed by the caller. */
var p *C.char = C.notmuch_database_get_path(self.db)
if p != nil {
s := C.GoString(p)
// TODO: notmuch_database_upgrade
-
/* Retrieve a directory object from the database for 'path'.
*
* Here, 'path' should be a path relative to the path of 'database'
*
* Can return NULL if a Xapian exception occurs.
*/
-func (self *Database) GetDirectory(path string) *Directory {
+func (self *Database) GetDirectory(path string) (*Directory, Status) {
var c_path *C.char = C.CString(path)
defer C.free(unsafe.Pointer(c_path))
if c_path == nil {
- return nil
+ return nil, STATUS_OUT_OF_MEMORY
}
- c_dir := C.notmuch_database_get_directory(self.db, c_path)
- if c_dir == nil {
- return nil
+ var c_dir *C.notmuch_directory_t
+ st := Status(C.notmuch_database_get_directory(self.db, c_path, &c_dir))
+ if st != STATUS_SUCCESS || c_dir == nil {
+ return nil, st
}
- return &Directory{dir:c_dir}
+ return &Directory{dir: c_dir}, st
}
/* Add a new message to the given notmuch database.
* NOTMUCH_STATUS_READ_ONLY_DATABASE: Database was opened in read-only
* mode so no message can be added.
*/
-func
-(self *Database) AddMessage(fname string) (*Message, Status) {
+func (self *Database) AddMessage(fname string) (*Message, Status) {
var c_fname *C.char = C.CString(fname)
defer C.free(unsafe.Pointer(c_fname))
var c_msg *C.notmuch_message_t = new(C.notmuch_message_t)
st := Status(C.notmuch_database_add_message(self.db, c_fname, &c_msg))
- return &Message{message:c_msg}, st
+ return &Message{message: c_msg}, st
}
/* Remove a message from the given notmuch database.
* mode so no message can be removed.
*/
func (self *Database) RemoveMessage(fname string) Status {
-
+
var c_fname *C.char = C.CString(fname)
defer C.free(unsafe.Pointer(c_fname))
* * A Xapian exception occurs
*/
func (self *Database) FindMessage(message_id string) (*Message, Status) {
-
+
var c_msg_id *C.char = C.CString(message_id)
defer C.free(unsafe.Pointer(c_msg_id))
return nil, STATUS_OUT_OF_MEMORY
}
- msg := &Message{message:nil}
+ msg := &Message{message: nil}
st := Status(C.notmuch_database_find_message(self.db, c_msg_id, &msg.message))
if st != STATUS_SUCCESS {
return nil, st
if tags == nil {
return nil
}
- return &Tags{tags:tags}
+ return &Tags{tags: tags}
}
/* Create a new query for 'database'.
* Will return NULL if insufficient memory is available.
*/
func (self *Database) CreateQuery(query string) *Query {
-
+
var c_query *C.char = C.CString(query)
defer C.free(unsafe.Pointer(c_query))
if q == nil {
return nil
}
- return &Query{query:q}
+ return &Query{query: q}
}
/* Sort values for notmuch_query_set_sort */
type Sort C.notmuch_sort_t
+
const (
SORT_OLDEST_FIRST Sort = 0
SORT_NEWEST_FIRST
// FIXME: do we own 'q' or not ?
q := C.notmuch_query_get_query_string(self.query)
//defer C.free(unsafe.Pointer(q))
-
+
if q != nil {
s := C.GoString(q)
return s
if threads == nil {
return nil
}
- return &Threads{threads:threads}
+ return &Threads{threads: threads}
}
/* Execute a query for messages, returning a notmuch_messages_t object
if msgs == nil {
return nil
}
- return &Messages{messages:msgs}
+ return &Messages{messages: msgs}
}
/* Destroy a notmuch_query_t along with any associated resources.
if msg == nil {
return nil
}
- return &Message{message:msg}
+ return &Message{message: msg}
}
/* Move the 'messages' iterator to the next message.
if tags == nil {
return nil
}
- return &Tags{tags:tags}
+ return &Tags{tags: tags}
}
/* Get the message ID of 'message'.
* message belongs to a single thread.
*/
func (self *Message) GetThreadId() string {
-
+
if self.message == nil {
return ""
}
id := C.notmuch_message_get_thread_id(self.message)
// we dont own id
// defer C.free(unsafe.Pointer(id))
-
+
if id == nil {
return ""
}
if msgs == nil {
return nil
}
- return &Messages{messages:msgs}
+ return &Messages{messages: msgs}
}
/* Get a filename for the email corresponding to 'message'.
fname := C.notmuch_message_get_filename(self.message)
// we dont own fname
// defer C.free(unsafe.Pointer(fname))
-
+
if fname == nil {
return ""
}
}
type Flag C.notmuch_message_flag_t
+
const (
MESSAGE_FLAG_MATCH Flag = 0
)
C.notmuch_message_set_flag(self.message, C.notmuch_message_flag_t(flag), v)
}
-// TODO: wrap notmuch_message_get_date
+/* Get the timestamp (seconds since the epoch) of 'message'.
+ *
+ * Return status:
+ *
+ * NOTMUCH_STATUS_SUCCESS: Timestamp successfully retrieved
+ *
+ * NOTMUCH_STATUS_NULL_POINTER: The 'message' argument is NULL
+ *
+ */
+func (self *Message) GetDate() (int64, Status) {
+ if self.message == nil {
+ return -1, STATUS_NULL_POINTER
+ }
+ timestamp := C.notmuch_message_get_date(self.message)
+ return int64(timestamp), STATUS_SUCCESS
+}
/* Get the value of the specified header from 'message'.
*
if self.message == nil {
return ""
}
-
+
var c_header *C.char = C.CString(header)
defer C.free(unsafe.Pointer(c_header))
-
+
/* we dont own value */
value := C.notmuch_message_get_header(self.message, c_header)
if value == nil {
return ""
}
-
+
return C.GoString(value)
}
if tags == nil {
return nil
}
- return &Tags{tags:tags}
+ return &Tags{tags: tags}
}
/* The longest possible tag value. */
}
C.notmuch_filenames_destroy(self.fnames)
}
+
/* EOF */