summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMatthias Beyer <mail@beyermatthias.de>2017-10-12 23:47:15 +0200
committerGitHub <noreply@github.com>2017-10-12 23:47:15 +0200
commita24baca779d8ab609fa313e001b331c16d7e4c5f (patch)
treecc5439b861bfc4bd75548caad35a64ea800d96fc
parentdde343965a8f72f4494fd33c27ee847ed2fb5bb4 (diff)
parentd4633d466eae2632ec3928954cbdec263be91657 (diff)
downloadimag-a24baca779d8ab609fa313e001b331c16d7e4c5f.zip
imag-a24baca779d8ab609fa313e001b331c16d7e4c5f.tar.gz
Merge pull request #1129 from matthiasbeyer/libimagentryannotation/not-based-on-libimagnotes
Libimagentryannotation/not based on libimagnotes
-rw-r--r--doc/src/09020-changelog.md5
-rw-r--r--lib/entry/libimagentryannotation/Cargo.toml1
-rw-r--r--lib/entry/libimagentryannotation/src/annotateable.rs63
-rw-r--r--lib/entry/libimagentryannotation/src/annotation_fetcher.rs83
-rw-r--r--lib/entry/libimagentryannotation/src/error.rs9
-rw-r--r--lib/entry/libimagentryannotation/src/iter.rs65
-rw-r--r--lib/entry/libimagentryannotation/src/lib.rs6
7 files changed, 132 insertions, 100 deletions
diff --git a/doc/src/09020-changelog.md b/doc/src/09020-changelog.md
index 8ab0270..7f4aace 100644
--- a/doc/src/09020-changelog.md
+++ b/doc/src/09020-changelog.md
@@ -29,6 +29,11 @@ This section contains the changelog from the last release to the next release.
stderr)
* `imag-store` can dump all storeids now
+* Minor changes
+ * `libimagentryannotation` got a rewrite, is not based on `libimagnotes`
+ anymore. This is minor because `libimagentryanntation` is not yet used by
+ any other crate.
+
## 0.4.0
* Major changes
diff --git a/lib/entry/libimagentryannotation/Cargo.toml b/lib/entry/libimagentryannotation/Cargo.toml
index bc738f4..430c509 100644
--- a/lib/entry/libimagentryannotation/Cargo.toml
+++ b/lib/entry/libimagentryannotation/Cargo.toml
@@ -17,5 +17,4 @@ error-chain = "0.11"
libimagstore = { version = "0.5.0", path = "../../../lib/core/libimagstore" }
libimagerror = { version = "0.5.0", path = "../../../lib/core/libimagerror" }
-libimagnotes = { version = "0.5.0", path = "../../../lib/domain/libimagnotes" }
libimagentrylink = { version = "0.5.0", path = "../../../lib/entry/libimagentrylink" }
diff --git a/lib/entry/libimagentryannotation/src/annotateable.rs b/lib/entry/libimagentryannotation/src/annotateable.rs
index d51380c..bc2aaa4 100644
--- a/lib/entry/libimagentryannotation/src/annotateable.rs
+++ b/lib/entry/libimagentryannotation/src/annotateable.rs
@@ -17,13 +17,13 @@
// Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
//
-use std::path::PathBuf;
-
use toml::Value;
use libimagstore::store::Entry;
use libimagstore::store::FileLockEntry;
use libimagstore::store::Store;
+use libimagstore::storeid::IntoStoreId;
+use libimagstore::storeid::StoreIdIterator;
use libimagentrylink::internal::InternalLinker;
use toml_query::read::TomlValueReadExt;
@@ -34,29 +34,29 @@ use error::AnnotationErrorKind as AEK;
use error::AnnotationError as AE;
use error::ResultExt;
-pub trait Annotateable {
+use iter::*;
- /// Add an annotation to `Self`, that is a `FileLockEntry` which is linked to `Self` (link as in
- /// libimagentrylink).
- ///
- /// A new annotation also has the field `annotation.is_annotation` set to `true`.
+pub trait Annotateable {
fn annotate<'a>(&mut self, store: &'a Store, ann_name: &str) -> Result<FileLockEntry<'a>>;
-
- /// Check whether an entry is an annotation
+ fn denotate<'a>(&mut self, store: &'a Store, ann_name: &str) -> Result<Option<FileLockEntry<'a>>>;
+ fn annotations<'a>(&self, store: &'a Store) -> Result<AnnotationIter<'a>>;
fn is_annotation(&self) -> Result<bool>;
-
}
impl Annotateable for Entry {
+ /// Annotate an entry, returns the new entry which is used to annotate
fn annotate<'a>(&mut self, store: &'a Store, ann_name: &str) -> Result<FileLockEntry<'a>> {
- store.retrieve(PathBuf::from(ann_name))
- .chain_err(|| AEK::StoreWriteError)
+ use module_path::ModuleEntryPath;
+ store.retrieve(try!(ModuleEntryPath::new(ann_name).into_storeid()))
+ .map_err(From::from)
.and_then(|mut anno| {
- anno.get_header_mut()
- .insert("annotation.is_annotation", Value::Boolean(true))
- .chain_err(|| AEK::HeaderWriteError)
- .map(|_| anno)
+ {
+ let header = anno.get_header_mut();
+ try!(header.insert("annotation.is_annotation", Value::Boolean(true)));
+ try!(header.insert("annotation.name", Value::String(String::from(ann_name))));
+ }
+ Ok(anno)
})
.and_then(|mut anno| {
anno.add_internal_link(self)
@@ -65,10 +65,39 @@ impl Annotateable for Entry {
})
}
+ /// Checks the current entry for all annotations and removes the one where the name is
+ /// `ann_name`, which is then returned
+ fn denotate<'a>(&mut self, store: &'a Store, ann_name: &str) -> Result<Option<FileLockEntry<'a>>> {
+ for annotation in self.annotations(store)? {
+ let mut anno = try!(annotation);
+ let name = match anno.get_header().read("annotation.name")? {
+ None => continue,
+ Some(val) => match *val {
+ Value::String(ref name) => name.clone(),
+ _ => return Err(AE::from_kind(AEK::HeaderTypeError)),
+ },
+ };
+
+ if name == ann_name {
+ let _ = try!(self.remove_internal_link(&mut anno));
+ }
+ }
+
+ Ok(None)
+ }
+
+ /// Get all annotations of an entry
+ fn annotations<'a>(&self, store: &'a Store) -> Result<AnnotationIter<'a>> {
+ self.get_internal_links()
+ .map_err(From::from)
+ .map(|iter| StoreIdIterator::new(Box::new(iter.map(|e| e.get_store_id().clone()))))
+ .map(|i| AnnotationIter::new(i, store))
+ }
+
fn is_annotation(&self) -> Result<bool> {
self.get_header()
.read("annotation.is_annotation")
- .chain_err(|| AEK::StoreReadError)
+ .map_err(From::from)
.and_then(|res| match res {
Some(&Value::Boolean(b)) => Ok(b),
None => Ok(false),
diff --git a/lib/entry/libimagentryannotation/src/annotation_fetcher.rs b/lib/entry/libimagentryannotation/src/annotation_fetcher.rs
index afdec88..a19b6cc 100644
--- a/lib/entry/libimagentryannotation/src/annotation_fetcher.rs
+++ b/lib/entry/libimagentryannotation/src/annotation_fetcher.rs
@@ -17,100 +17,23 @@
// Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
//
-use libimagstore::store::Entry;
use libimagstore::store::Store;
-use libimagentrylink::internal::InternalLinker;
-use libimagnotes::notestore::NoteStore;
-use libimagnotes::iter::NoteIterator;
-use libimagstore::storeid::StoreIdIterator;
use error::Result;
-use error::AnnotationErrorKind as AEK;
-use error::ResultExt;
-
-use self::iter::*;
+use iter::*;
pub trait AnnotationFetcher<'a> {
fn all_annotations(&'a self) -> Result<AnnotationIter<'a>>;
- fn annotations_for_entry(&'a self, entry: &Entry) -> Result<AnnotationIter<'a>>;
-
}
impl<'a> AnnotationFetcher<'a> for Store {
- /// Wrapper around `Note::all_notes()` of `libimagnotes` which filters out normal notes and
- /// leaves only annotations in the iterator.
fn all_annotations(&'a self) -> Result<AnnotationIter<'a>> {
- NoteStore::all_notes(self)
+ self.retrieve_for_module("annotations")
.map(|iter| AnnotationIter::new(iter, self))
- .chain_err(|| AEK::StoreReadError)
- }
-
- /// Get all annotations (in an iterator) for an entry
- ///
- /// Internally, this fetches the links of the entry, fetches all the entries behind the links
- /// and filters them for annotations.
- ///
- /// This might result in some heavy IO operations if a lot of stuff is linked to a single
- /// entry, but should normally be not that heavy.
- fn annotations_for_entry(&'a self, entry: &Entry) -> Result<AnnotationIter<'a>> {
- entry.get_internal_links()
- .chain_err(|| AEK::StoreReadError)
- .map(|iter| StoreIdIterator::new(Box::new(iter.map(|e| e.get_store_id().clone()))))
- .map(NoteIterator::new)
- .map(|i| AnnotationIter::new(i, self))
- }
-
-}
-
-pub mod iter {
- use toml::Value;
-
- use toml_query::read::TomlValueReadExt;
-
- use libimagnotes::iter::NoteIterator;
- use libimagstore::store::Store;
- use libimagstore::store::FileLockEntry;
-
- use error::Result;
- use error::AnnotationErrorKind as AEK;
- use error::AnnotationError as AE;
- use error::ResultExt;
-
- #[derive(Debug)]
- pub struct AnnotationIter<'a>(NoteIterator, &'a Store);
-
- impl<'a> AnnotationIter<'a> {
-
- pub fn new(noteiter: NoteIterator, store: &'a Store) -> AnnotationIter<'a> {
- AnnotationIter(noteiter, store)
- }
-
- }
-
- impl<'a> Iterator for AnnotationIter<'a> {
- type Item = Result<FileLockEntry<'a>>;
-
- fn next(&mut self) -> Option<Self::Item> {
- loop {
- match self.0.next().map(|id| self.1.get(id)) {
- Some(Ok(Some(note))) => {
- match note.get_header().read("annotation.is_annotation") {
- Ok(None) => continue, // not an annotation
- Ok(Some(&Value::Boolean(true))) => return Some(Ok(note)),
- Ok(Some(_)) => return Some(Err(AE::from_kind(AEK::HeaderTypeError))),
- Err(e) => return Some(Err(e).chain_err(|| AEK::HeaderReadError)),
- }
- },
- Some(Ok(None)) => continue,
- Some(Err(e)) => return Some(Err(e).chain_err(|| AEK::StoreReadError)),
- None => return None, // iterator consumed
- }
- }
- }
-
+ .map_err(Into::into)
}
}
diff --git a/lib/entry/libimagentryannotation/src/error.rs b/lib/entry/libimagentryannotation/src/error.rs
index 8a349b7..8e25004 100644
--- a/lib/entry/libimagentryannotation/src/error.rs
+++ b/lib/entry/libimagentryannotation/src/error.rs
@@ -22,6 +22,15 @@ error_chain! {
AnnotationError, AnnotationErrorKind, ResultExt, Result;
}
+ links {
+ StoreError(::libimagstore::error::StoreError, ::libimagstore::error::StoreErrorKind);
+ LinkError(::libimagentrylink::error::LinkError, ::libimagentrylink::error::LinkErrorKind);
+ }
+
+ foreign_links {
+ TomlQueryError(::toml_query::error::Error);
+ }
+
errors {
StoreReadError {
description("Store read error")
diff --git a/lib/entry/libimagentryannotation/src/iter.rs b/lib/entry/libimagentryannotation/src/iter.rs
new file mode 100644
index 0000000..04dc8e2
--- /dev/null
+++ b/lib/entry/libimagentryannotation/src/iter.rs
@@ -0,0 +1,65 @@
+//
+// imag - the personal information management suite for the commandline
+// Copyright (C) 2015, 2016 Matthias Beyer <mail@beyermatthias.de> and contributors
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; version
+// 2.1 of the License.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
+//
+
+use toml::Value;
+use toml_query::read::TomlValueReadExt;
+
+use libimagstore::store::Store;
+use libimagstore::store::FileLockEntry;
+use libimagstore::storeid::StoreIdIterator;
+
+use error::Result;
+use error::AnnotationErrorKind as AEK;
+use error::AnnotationError as AE;
+use error::ResultExt;
+
+#[derive(Debug)]
+pub struct AnnotationIter<'a>(StoreIdIterator, &'a Store);
+
+impl<'a> AnnotationIter<'a> {
+
+ pub fn new(iter: StoreIdIterator, store: &'a Store) -> AnnotationIter<'a> {
+ AnnotationIter(iter, store)
+ }
+
+}
+
+impl<'a> Iterator for AnnotationIter<'a> {
+ type Item = Result<FileLockEntry<'a>>;
+
+ fn next(&mut self) -> Option<Self::Item> {
+ loop {
+ match self.0.next().map(|id| self.1.get(id)) {
+ Some(Ok(Some(entry))) => {
+ match entry.get_header().read("annotation.is_annotation") {
+ Ok(None) => continue, // not an annotation
+ Ok(Some(&Value::Boolean(true))) => return Some(Ok(entry)),
+ Ok(Some(_)) => return Some(Err(AE::from_kind(AEK::HeaderTypeError))),
+ Err(e) => return Some(Err(e).chain_err(|| AEK::HeaderReadError)),
+ }
+ },
+ Some(Ok(None)) => continue,
+ Some(Err(e)) => return Some(Err(e).chain_err(|| AEK::StoreReadError)),
+ None => return None, // iterator consumed
+ }
+ }
+ }
+
+}
+
diff --git a/lib/entry/libimagentryannotation/src/lib.rs b/lib/entry/libimagentryannotation/src/lib.rs
index bd1e9ed..3bc5ad4 100644
--- a/lib/entry/libimagentryannotation/src/lib.rs
+++ b/lib/entry/libimagentryannotation/src/lib.rs
@@ -39,12 +39,14 @@ extern crate toml;
extern crate toml_query;
#[macro_use] extern crate error_chain;
+#[macro_use] extern crate libimagstore;
extern crate libimagerror;
-extern crate libimagstore;
extern crate libimagentrylink;
-extern crate libimagnotes;
+
+module_entry_path_mod!("annotations");
pub mod annotateable;
pub mod annotation_fetcher;
pub mod error;
+pub mod iter;