pub struct EpubMetadataMut<'ebook> { /* private fields */ }write only.Expand description
Mutable view of EpubMetadata accessible via
Epub::metadata_mut.
Allows creation, modification, and removal of top-level (i.e., non-refining)
metadata entries (e.g., <dc:title>, <dc:creator>, <meta>).
§Refinements
To modify refinements (nested metadata), the parent must first be retrieved
(from Self::by_id_mut or similar), and then accessed via
EpubMetaEntryMut::refinements_mut.
§See Also
EpubEditorfor simple modification tasks.
Implementations§
Source§impl<'ebook> EpubMetadataMut<'ebook>
impl<'ebook> EpubMetadataMut<'ebook>
Sourcepub fn as_view(&self) -> EpubMetadata<'_>
pub fn as_view(&self) -> EpubMetadata<'_>
Returns a read-only view, useful for inspecting state before applying modifications.
Sourcepub fn push(&mut self, detached: impl Many<DetachedEpubMetaEntry>)
pub fn push(&mut self, detached: impl Many<DetachedEpubMetaEntry>)
Inserts one or more metadata entries via the Many trait.
New entries are appended to the end of the list for their specific
property.
§Examples
- Adding a new creator:
let mut epub = Epub::open("tests/ebooks/example_epub")?;
epub.metadata_mut().push(
DetachedEpubMetaEntry::creator("Jane Doe")
.id("jane")
.file_as("Doe, Jane"),
);
let mut creators = epub.metadata().creators();
// Initial creator:
let first_creator = creators.next().unwrap();
assert_eq!("John Doe", first_creator.value());
// Newly added creator:
let added_creator = creators.next().unwrap();
assert_eq!("Jane Doe", added_creator.value());
assert_eq!(Some("jane"), added_creator.id());
assert_eq!(Some("Doe, Jane"), added_creator.file_as());
assert_eq!(None, creators.next());- Adding multiple tags:
epub.metadata_mut().push([
("dc:subject", "Fiction"),
("dc:subject", "Romance"),
// Alternatively:
// DetachedEpubMetaEntry::tag("Fiction"),
// ...,
]);
let mut tags = epub.metadata().tags().map(|tag| tag.value());
// Initial tags:
assert_eq!(Some("FICTION / Occult & Supernatural"), tags.next());
assert_eq!(Some("Quests (Expeditions) -- Fiction"), tags.next());
assert_eq!(Some("Fantasy"), tags.next());
// Newly added tags:
assert_eq!(Some("Fiction"), tags.next());
assert_eq!(Some("Romance"), tags.next());
assert_eq!(None, tags.next());Sourcepub fn insert(
&mut self,
index: usize,
detached: impl Many<DetachedEpubMetaEntry>,
)
pub fn insert( &mut self, index: usize, detached: impl Many<DetachedEpubMetaEntry>, )
Inserts one or more entries at the given index via the Many trait,
within their respective property groups.
This is useful for defining the primary entry,
such as ensuring the main author appears first among dc:creator entries.
§Note
- The
indexis relative to a property group (e.g., alldc:titleentries); not all metadata. - If the
indexis greater than the current number of entries for a property, then new entries are appended to the end. - The relative order of entries inserted as a batch is preserved.
§Examples
- Setting the primary author:
let mut epub = Epub::new();
let mut metadata = epub.metadata_mut();
metadata.push(DetachedEpubMetaEntry::creator("Second Author"));
// Insert "First Author" as the first creator
metadata.insert(0, DetachedEpubMetaEntry::creator("First Author"));
let mut creators = epub.metadata().creators().map(|creator| creator.value());
assert_eq!(Some("First Author"), creators.next());
assert_eq!(Some("Second Author"), creators.next());
assert_eq!(None, creators.next());- Inserting into a new property group:
metadata.push(DetachedEpubMetaEntry::title("Awesome Title"));
// The index (0) is relative to the `dc:publisher` group (doesn't exist yet),
// so this creates a new group.
// New property groups are appended after existing ones,
// so `dc:publisher` appears last.
metadata.insert(0, DetachedEpubMetaEntry::publisher("P"));
let mut properties = epub.metadata().iter().map(|meta| meta.property().as_str());
assert_eq!(Some("dc:title"), properties.next());
assert_eq!(Some("dc:publisher"), properties.next());
assert_eq!(None, properties.next());Sourcepub fn by_id_mut(&mut self, id: &str) -> Option<EpubMetaEntryMut<'_>>
pub fn by_id_mut(&mut self, id: &str) -> Option<EpubMetaEntryMut<'_>>
Searches the metadata hierarchy, including refinements, and returns the
EpubMetaEntryMut matching the given id, or None if not found.
§See Also
EpubMetadata::by_id(immutable equivalent) for more details.Self::by_property_mutto get entries by theirproperty(e.g. all titles).
§Examples
- Updating an entry:
let mut epub = Epub::open("tests/ebooks/example_epub")?;
// Original author
let john_doe = epub.metadata().by_id("author").unwrap();
assert_eq!("John Doe", john_doe.value());
let mut metadata = epub.metadata_mut();
// `None` is returned if a non-existent `id` is given
assert!(metadata.by_id_mut("doesn't exist").is_none());
let mut author_mut = metadata.by_id_mut("author").unwrap();
author_mut.set_value("Jane Doe");
// New author
let jane_doe = epub.metadata().by_id("author").unwrap();
assert_eq!("Jane Doe", jane_doe.value());Sourcepub fn by_property_mut(
&mut self,
property: &str,
) -> impl Iterator<Item = EpubMetaEntryMut<'_>>
pub fn by_property_mut( &mut self, property: &str, ) -> impl Iterator<Item = EpubMetaEntryMut<'_>>
Returns an iterator over all mutable entries matching
the given property
(e.g., dc:title, dc:creator, dcterms:modified).
§Examples
- Making all tags uppercase:
let mut epub = Epub::open("tests/ebooks/example_epub")?;
// Original tags
let mut tags = epub.metadata().tags().map(|tag| tag.value());
assert_eq!(Some("FICTION / Occult & Supernatural"), tags.next());
assert_eq!(Some("Quests (Expeditions) -- Fiction"), tags.next());
assert_eq!(Some("Fantasy"), tags.next());
assert_eq!(0, tags.count());
// Making all tags uppercase:
for mut subject in epub.metadata_mut().by_property_mut("dc:subject") {
let old_value = subject.as_view().value().to_string();
subject.set_value(old_value.to_uppercase());
}
// Modified tags
let mut tags = epub.metadata().tags().map(|tag| tag.value());
assert_eq!(Some("FICTION / OCCULT & SUPERNATURAL"), tags.next());
assert_eq!(Some("QUESTS (EXPEDITIONS) -- FICTION"), tags.next());
assert_eq!(Some("FANTASY"), tags.next());
assert_eq!(None, tags.next());Sourcepub fn links_mut(&mut self) -> impl Iterator<Item = EpubMetaEntryMut<'_>>
pub fn links_mut(&mut self) -> impl Iterator<Item = EpubMetaEntryMut<'_>>
Returns an iterator over non-refining link entries.
§Note
This method has the same restrictions as EpubMetadata::links.
Sourcepub fn iter_mut(&mut self) -> EpubMetadataIterMut<'_> ⓘ
pub fn iter_mut(&mut self) -> EpubMetadataIterMut<'_> ⓘ
Returns an iterator over top-level (non-refining) metadata entries.
§Note
- This method has the same restrictions as
EpubMetadata::iter. - The iteration order is arbitrary between property groups, but deterministic within a specific property group (based on insertion order).
Sourcepub fn remove_by_id(&mut self, id: &str) -> Option<DetachedEpubMetaEntry>
pub fn remove_by_id(&mut self, id: &str) -> Option<DetachedEpubMetaEntry>
Searches the metadata hierarchy, including refinements, and removes the
entry matching the given id, or None if not found.
§Note
This method has the same limitations mentioned in EpubMetadata::by_id.
§Examples
- Removing an entry:
let mut epub = Epub::open("tests/ebooks/example_epub")?;
// Existing entry
let john_doe = epub.metadata().by_id("author").unwrap();
assert_eq!("John Doe", john_doe.value());
let mut metadata = epub.metadata_mut();
// `None` is returned if a non-existent `id` is given
assert_eq!(None, metadata.remove_by_id("doesn't exist"));
// Removing an entry returns it as an owned instance
let mut author = metadata.remove_by_id("author").unwrap();
assert_eq!("John Doe", author.as_view().value());
// The ebook no longer contains the entry
assert_eq!(None, epub.metadata().by_id("author"));Sourcepub fn remove_by_property(
&mut self,
property: &str,
) -> impl Iterator<Item = DetachedEpubMetaEntry>
pub fn remove_by_property( &mut self, property: &str, ) -> impl Iterator<Item = DetachedEpubMetaEntry>
Removes and returns all top-level (non-refining) entries matching the given property.
§Examples
- Clearing all creators:
let mut epub = Epub::open("tests/ebooks/example_epub")?;
// Existing creators:
assert_eq!(1, epub.metadata().creators().count());
let mut metadata = epub.metadata_mut();
// Removing all creators and collecting them into a `Vec`
let removed: Vec<_> = metadata.remove_by_property("dc:creator").collect();
assert_eq!(1, removed.len());
assert_eq!("John Doe", removed[0].as_view().value());
// The ebook no longer contains any creators
assert_eq!(0, epub.metadata().creators().count());Sourcepub fn retain(&mut self, f: impl FnMut(EpubMetaEntry<'_>) -> bool)
pub fn retain(&mut self, f: impl FnMut(EpubMetaEntry<'_>) -> bool)
Retains only top-level (non-refining) entries specified by the predicate.
If the closure returns false, the entry is retained.
Otherwise, the entry is removed.
This method operates in place and visits every entry exactly once.
§See Also
Self::extract_ifto get an iterator of the removed entries.
§Examples
- Removing legacy EPUB 2
<meta>elements:
let mut epub = Epub::open("tests/ebooks/example_epub")?;
// Checking the number of EPUB 2 meta elements
assert_eq!(
2,
epub.metadata().iter().filter(|entry| entry.kind().is_epub2_meta()).count(),
);
// Retain only entries that are not EPUB 2 meta elements
epub.metadata_mut().retain(|entry| !entry.kind().is_epub2_meta());
// The ebook no longer contains any EPUB 2 meta elements
assert_eq!(
0,
epub.metadata().iter().filter(|entry| entry.kind().is_epub2_meta()).count(),
);Sourcepub fn extract_if(
&mut self,
f: impl FnMut(EpubMetaEntry<'_>) -> bool,
) -> impl Iterator<Item = DetachedEpubMetaEntry>
pub fn extract_if( &mut self, f: impl FnMut(EpubMetaEntry<'_>) -> bool, ) -> impl Iterator<Item = DetachedEpubMetaEntry>
Removes and returns only top-level (non-refining) entries specified by the predicate.
If the closure returns true, the entry is removed and yielded.
Otherwise, the entry is retained.
§Drop
If the returned iterator is not exhausted, (e.g. dropped without iterating or iteration short-circuits), then the remaining entries are retained.
Prefer Self::retain with a negated predicate if the returned iterator is not needed.
§Examples
- Extracting all Dublin Core metadata entries:
let mut epub = Epub::open("tests/ebooks/example_epub")?;
let dublin_core: Vec<_> = epub.metadata_mut()
.extract_if(|entry| entry.kind().is_dublin_core())
.collect();
// A total of 12 entries were removed (e.g., dc:title, dc:subject, etc.)
assert_eq!(12, dublin_core.len());
// The ebook no longer contains any Dublin Core entries
assert_eq!(
0,
epub.metadata().iter().filter(|entry| entry.kind().is_dublin_core()).count(),
);Sourcepub fn drain(&mut self) -> impl Iterator<Item = DetachedEpubMetaEntry>
pub fn drain(&mut self) -> impl Iterator<Item = DetachedEpubMetaEntry>
Removes and returns all top-level (non-refining)
Sourcepub fn clear(&mut self)
pub fn clear(&mut self)
Removes all top-level (non-refining) metadata entries.
§See Also
Self::drainto get an iterator of the removed entries.
Trait Implementations§
Source§impl Debug for EpubMetadataMut<'_>
impl Debug for EpubMetadataMut<'_>
Source§impl<M> Extend<DetachedEpubMetaEntry<M>> for EpubMetadataMut<'_>
impl<M> Extend<DetachedEpubMetaEntry<M>> for EpubMetadataMut<'_>
Source§fn extend<T: IntoIterator<Item = DetachedEpubMetaEntry<M>>>(&mut self, iter: T)
fn extend<T: IntoIterator<Item = DetachedEpubMetaEntry<M>>>(&mut self, iter: T)
Source§fn extend_one(&mut self, item: T)
fn extend_one(&mut self, item: T)
extend_one)Source§fn extend_reserve(&mut self, additional: usize)
fn extend_reserve(&mut self, additional: usize)
extend_one)