- Rust 100%
| src |
Switch to where syntax
|
|
| tests | trust clippy and rustfmt | |
| .gitignore | Add .gitignore file. | |
| .travis.yml | prevent travis from building with features that are not available | |
| Cargo.toml | bump version | |
| LICENSE.md | add license | |
| README.md | Simplify example in README | |
notmuch-rs
This is not much more than a wrapper for the notmuch C api.
Build Status Crate version Download statistics License
Building
notmuch-rs expects libnotmuch development files to be installed on your system.
Using
Add this to your Cargo.toml:
[dependencies]
notmuch = "*"
and this to your crate root:
externcratenotmuch;Example
externcratenotmuch;usenotmuch::StreamingIterator;fn main(){letmutmail_path=std::env::home_dir().unwrap();mail_path.push(".mail");letdb=notmuch::Database::open(&mail_path,notmuch::DatabaseMode::ReadOnly).unwrap();letquery=db.create_query("").unwrap();letmutthreads=query.search_threads().unwrap();whileletSome(thread)=threads.next(){println!("thread {:?}{:?}",thread.subject(),thread.authors());}}Concurrency
Notmuch makes no claims regarding thread safety. It does not seem to use any
thread locals, but I did not spot any locks. So, as far as I am concerned, it is
not thread safe.
So why do all structs implement Send and Sync? Well, it is safe to
access pointers from different threads (as long as you know what you are doing :) ).
Up till now I haven't done a lot of multithreaded stuff with notmuch-rs. If you
feel this is too permissive, let me know.
Lifetime
All structs are strictly linked together with their lifetime. The root of the
tree is Database, which has a lifetime that must outlive any child
objects, for instance Query. The Threads iterator that you can get
from a Query is always outlived by the parent query. Threads in its
turn must have a longer life than Thread, which in turn must outlive
Messages and so on. Each structure keeps a PhantomData marker of its
owner.
Using this in an application poses significant difficulties in satisfying these
lifetime requirements. To alleviate this, notmuch-rs makes use of the
excellent Supercow, so you don't have to
use crates like owningref or rental to get around this.
This way, you get to choose your own container type, and even keep the parent
object alive so you don't have to juggle lifetimes. To use this, most types
are accompagnied with an *Ext trait, that accepts Rc, Arc or
comparable.
usestd::sync::Arc;usenotmuch::{DatabaseExt};letquery={letdbr=Arc::new(db);<DatabaseasDatabaseExt>::create_query(dbr.clone(),&"".to_string()).unwrap()};Iterators
Since the lifetime of a Thread or a Message is dependent on the
Threads and Messages iterator respectively, using the regular rust
Iterator trait proved impossible. As such, notmuch-rs includes a
StreamingIterator (and additional StreamingIteratorExt) trait that
is used to iterate while satisfying the lifetime constraints.
Acknowledgements
notmuch-rs started out from the following projects:
- https://github.com/Stebalien/notmuch-sys/blob/master/src/lib.rs
- https://github.com/cmhamill/rust-notmuch
Any contributions are welcome!