@@ -0,0 +1,91 @@
|
|||||||
|
use page::Page;
|
||||||
|
use serde::Deserialize;
|
||||||
|
|
||||||
|
/// Abstracts away the `next_page` logic into a single stream of items
|
||||||
|
///
|
||||||
|
/// ```no_run
|
||||||
|
/// # extern crate mammut;
|
||||||
|
/// # use mammut::{Data, Mastodon};
|
||||||
|
/// # use std::error::Error;
|
||||||
|
/// # fn main() -> Result<(), Box<Error>> {
|
||||||
|
/// # let data = Data {
|
||||||
|
/// # base: "".into(),
|
||||||
|
/// # client_id: "".into(),
|
||||||
|
/// # client_secret: "".into(),
|
||||||
|
/// # redirect: "".into(),
|
||||||
|
/// # token: "".into(),
|
||||||
|
/// # };
|
||||||
|
/// let client = Mastodon::from_data(data);
|
||||||
|
/// let statuses = client.statuses("user-id", None)?;
|
||||||
|
/// for status in statuses.items_iter() {
|
||||||
|
/// // do something with `status`
|
||||||
|
/// }
|
||||||
|
/// # Ok(())
|
||||||
|
/// # }
|
||||||
|
/// ```
|
||||||
|
pub struct ItemsIter<'a, T: Clone + for<'de> Deserialize<'de>> {
|
||||||
|
page: Page<'a, T>,
|
||||||
|
buffer: Vec<T>,
|
||||||
|
cur_idx: usize,
|
||||||
|
use_initial: bool,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<'a, T: Clone + for<'de> Deserialize<'de>> ItemsIter<'a, T> {
|
||||||
|
pub(crate) fn new(page: Page<'a, T>) -> ItemsIter<'a, T> {
|
||||||
|
ItemsIter {
|
||||||
|
page: page,
|
||||||
|
buffer: vec![],
|
||||||
|
cur_idx: 0,
|
||||||
|
use_initial: true,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn need_next_page(&self) -> bool {
|
||||||
|
self.buffer.is_empty() ||
|
||||||
|
self.cur_idx == self.buffer.len()
|
||||||
|
}
|
||||||
|
|
||||||
|
fn fill_next_page(&mut self) -> Option<()> {
|
||||||
|
let items = if let Ok(items) = self.page.next_page() {
|
||||||
|
items
|
||||||
|
} else {
|
||||||
|
return None;
|
||||||
|
};
|
||||||
|
if let Some(items) = items {
|
||||||
|
self.buffer = items;
|
||||||
|
self.cur_idx = 0;
|
||||||
|
Some(())
|
||||||
|
} else {
|
||||||
|
None
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<'a, T: Clone+ for<'de> Deserialize<'de>> Iterator for ItemsIter<'a, T> {
|
||||||
|
type Item = T;
|
||||||
|
|
||||||
|
fn next(&mut self) -> Option<Self::Item> {
|
||||||
|
if self.use_initial {
|
||||||
|
if self.page.initial_items.is_empty() {
|
||||||
|
return None;
|
||||||
|
}
|
||||||
|
let idx = self.cur_idx;
|
||||||
|
if self.cur_idx == self.page.initial_items.len() - 1 {
|
||||||
|
self.cur_idx = 0;
|
||||||
|
self.use_initial = false;
|
||||||
|
} else {
|
||||||
|
self.cur_idx += 1;
|
||||||
|
}
|
||||||
|
Some(self.page.initial_items[idx].clone())
|
||||||
|
} else {
|
||||||
|
if self.need_next_page() {
|
||||||
|
if self.fill_next_page().is_none() {
|
||||||
|
return None;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
let idx = self.cur_idx;
|
||||||
|
self.cur_idx += 1;
|
||||||
|
Some(self.buffer[idx].clone())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -6,6 +6,7 @@ pub mod instance;
|
|||||||
pub mod list;
|
pub mod list;
|
||||||
pub mod mention;
|
pub mod mention;
|
||||||
pub mod notification;
|
pub mod notification;
|
||||||
|
pub(crate) mod itemsiter;
|
||||||
pub mod relationship;
|
pub mod relationship;
|
||||||
pub mod report;
|
pub mod report;
|
||||||
pub mod search_result;
|
pub mod search_result;
|
||||||
|
|||||||
+28
-2
@@ -587,16 +587,42 @@ impl Mastodon {
|
|||||||
///
|
///
|
||||||
/// # Example
|
/// # Example
|
||||||
///
|
///
|
||||||
/// ```ignore
|
/// ```no_run
|
||||||
|
/// # extern crate mammut;
|
||||||
|
/// # use mammut::{Data, Mastodon};
|
||||||
|
/// # use std::error::Error;
|
||||||
|
/// # fn main() -> Result<(), Box<Error>> {
|
||||||
|
/// # let data = Data {
|
||||||
|
/// # base: "".into(),
|
||||||
|
/// # client_id: "".into(),
|
||||||
|
/// # client_secret: "".into(),
|
||||||
|
/// # redirect: "".into(),
|
||||||
|
/// # token: "".into(),
|
||||||
|
/// # };
|
||||||
/// let client = Mastodon::from_data(data);
|
/// let client = Mastodon::from_data(data);
|
||||||
/// let statuses = client.statuses("user-id", None)?;
|
/// let statuses = client.statuses("user-id", None)?;
|
||||||
|
/// # Ok(())
|
||||||
|
/// # }
|
||||||
/// ```
|
/// ```
|
||||||
///
|
///
|
||||||
/// ```ignore
|
/// ```no_run
|
||||||
|
/// # extern crate mammut;
|
||||||
|
/// # use mammut::{Data, Mastodon, StatusesRequest};
|
||||||
|
/// # use std::error::Error;
|
||||||
|
/// # fn main() -> Result<(), Box<Error>> {
|
||||||
|
/// # let data = Data {
|
||||||
|
/// # base: "".into(),
|
||||||
|
/// # client_id: "".into(),
|
||||||
|
/// # client_secret: "".into(),
|
||||||
|
/// # redirect: "".into(),
|
||||||
|
/// # token: "".into(),
|
||||||
|
/// # };
|
||||||
/// let client = Mastodon::from_data(data);
|
/// let client = Mastodon::from_data(data);
|
||||||
/// let request = StatusesRequest::default()
|
/// let request = StatusesRequest::default()
|
||||||
/// .only_media();
|
/// .only_media();
|
||||||
/// let statuses = client.statuses("user-id", request)?;
|
/// let statuses = client.statuses("user-id", request)?;
|
||||||
|
/// # Ok(())
|
||||||
|
/// # }
|
||||||
/// ```
|
/// ```
|
||||||
pub fn statuses<'a, S>(&self, id: &str, request: S) -> Result<Page<Status>>
|
pub fn statuses<'a, S>(&self, id: &str, request: S) -> Result<Page<Status>>
|
||||||
where S: Into<Option<StatusesRequest<'a>>>
|
where S: Into<Option<StatusesRequest<'a>>>
|
||||||
|
|||||||
@@ -3,6 +3,7 @@ use reqwest::Response;
|
|||||||
use reqwest::header::{Link, RelationType};
|
use reqwest::header::{Link, RelationType};
|
||||||
use serde::Deserialize;
|
use serde::Deserialize;
|
||||||
use url::Url;
|
use url::Url;
|
||||||
|
use entities::itemsiter::ItemsIter;
|
||||||
|
|
||||||
pub struct Page<'a, T: for<'de> Deserialize<'de>> {
|
pub struct Page<'a, T: for<'de> Deserialize<'de>> {
|
||||||
mastodon: &'a Mastodon,
|
mastodon: &'a Mastodon,
|
||||||
@@ -53,6 +54,13 @@ impl<'a, T: for<'de> Deserialize<'de>> Page<'a, T> {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
impl<'a, T: Clone + for<'de> Deserialize<'de>> Page<'a, T> {
|
||||||
|
pub fn items_iter(self) -> impl Iterator<Item = T> + 'a
|
||||||
|
where T: 'a
|
||||||
|
{
|
||||||
|
ItemsIter::new(self)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
fn get_links(response: &Response) -> Result<(Option<Url>, Option<Url>)> {
|
fn get_links(response: &Response) -> Result<(Option<Url>, Option<Url>)> {
|
||||||
let mut prev = None;
|
let mut prev = None;
|
||||||
|
|||||||
Reference in New Issue
Block a user