sharepoint_cli/graph/
download.rs1use futures_util::StreamExt;
8use reqwest::Method;
9use tokio::io::{AsyncWrite, AsyncWriteExt};
10
11use super::GraphClient;
12use crate::error::{CliError, Result};
13
14pub async fn download_to_writer<W: AsyncWrite + Unpin>(
16 graph: &GraphClient,
17 drive_id: &str,
18 path: &str,
19 writer: &mut W,
20) -> Result<u64> {
21 let trimmed = path.trim_start_matches('/');
22 if trimmed.is_empty() {
23 return Err(CliError::Input("cannot download the drive root".into()));
24 }
25 let encoded = super::drives::encode_path_segments(trimmed);
26 let api_path = format!("/drives/{drive_id}/root:/{encoded}:/content");
27 let resp = graph.send(Method::GET, &api_path, None).await?;
28 let mut total: u64 = 0;
29 let mut stream = resp.bytes_stream();
30 while let Some(chunk) = stream.next().await {
31 let bytes = chunk.map_err(|e| CliError::Http(format!("download stream: {e}")))?;
32 writer
33 .write_all(&bytes)
34 .await
35 .map_err(|e| CliError::Other(format!("write download: {e}")))?;
36 total += bytes.len() as u64;
37 }
38 writer
39 .flush()
40 .await
41 .map_err(|e| CliError::Other(format!("flush download: {e}")))?;
42 Ok(total)
43}