import strategy for error module
This commit is contained in:
parent
d37797d2ec
commit
2315c9cd2e
10 changed files with 63 additions and 67 deletions
|
|
@ -6,7 +6,6 @@ use log::{debug, warn};
|
||||||
use crate::{
|
use crate::{
|
||||||
cachefile::CacheFile,
|
cachefile::CacheFile,
|
||||||
cli::Cli,
|
cli::Cli,
|
||||||
error,
|
|
||||||
file::{Chunk, FileTrait},
|
file::{Chunk, FileTrait},
|
||||||
output::new_progressbar,
|
output::new_progressbar,
|
||||||
sharry::Client,
|
sharry::Client,
|
||||||
|
|
@ -33,7 +32,7 @@ fn new_http(args: &Cli) -> ureq::Agent {
|
||||||
.into()
|
.into()
|
||||||
}
|
}
|
||||||
|
|
||||||
fn new_share(args: &Cli) -> error::Result<String> {
|
fn new_share(args: &Cli) -> crate::Result<String> {
|
||||||
new_http(args).share_create(&args.get_uri(), &args.alias, args.get_share_request())
|
new_http(args).share_create(&args.get_uri(), &args.alias, args.get_share_request())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -46,11 +45,11 @@ impl AppState {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn try_resume(args: &Cli) -> error::Result<Self> {
|
pub fn try_resume(args: &Cli) -> crate::Result<Self> {
|
||||||
Ok(Self::new(new_http(args), CacheFile::try_resume(args)?))
|
Ok(Self::new(new_http(args), CacheFile::try_resume(args)?))
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn from_args(args: &Cli) -> error::Result<Self> {
|
pub fn from_args(args: &Cli) -> crate::Result<Self> {
|
||||||
Ok(Self::new(
|
Ok(Self::new(
|
||||||
new_http(args),
|
new_http(args),
|
||||||
CacheFile::from_args(args, new_share)?,
|
CacheFile::from_args(args, new_share)?,
|
||||||
|
|
@ -87,7 +86,7 @@ impl AppState {
|
||||||
self.with_progressbar(f, true);
|
self.with_progressbar(f, true);
|
||||||
}
|
}
|
||||||
|
|
||||||
fn next_chunk<'t>(&mut self, buffer: &'t mut [u8]) -> error::Result<Option<Chunk<'t>>> {
|
fn next_chunk<'t>(&mut self, buffer: &'t mut [u8]) -> crate::Result<Option<Chunk<'t>>> {
|
||||||
if self.inner.get_uploading(&self.http)?.is_none() {
|
if self.inner.get_uploading(&self.http)?.is_none() {
|
||||||
return Ok(None);
|
return Ok(None);
|
||||||
}
|
}
|
||||||
|
|
@ -103,7 +102,7 @@ impl AppState {
|
||||||
Ok(Some(chunk))
|
Ok(Some(chunk))
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn upload_chunk(&mut self, buffer: &mut [u8]) -> error::Result<bool> {
|
pub fn upload_chunk(&mut self, buffer: &mut [u8]) -> crate::Result<bool> {
|
||||||
let Some(chunk) = self.next_chunk(buffer)? else {
|
let Some(chunk) = self.next_chunk(buffer)? else {
|
||||||
self.inner
|
self.inner
|
||||||
.share_notify(&self.http)
|
.share_notify(&self.http)
|
||||||
|
|
@ -136,7 +135,7 @@ impl AppState {
|
||||||
self.drop_progressbar(ProgressBar::abandon);
|
self.drop_progressbar(ProgressBar::abandon);
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn rebuild_share(self, args: &Cli) -> error::Result<Self> {
|
pub fn rebuild_share(self, args: &Cli) -> crate::Result<Self> {
|
||||||
Ok(Self::new(self.http, CacheFile::from_args(args, new_share)?))
|
Ok(Self::new(self.http, CacheFile::from_args(args, new_share)?))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -11,7 +11,7 @@ use console::{StyledObject, style};
|
||||||
use log::{info, trace};
|
use log::{info, trace};
|
||||||
|
|
||||||
use shrupl::{
|
use shrupl::{
|
||||||
AppState, Cli, error,
|
AppState, Cli,
|
||||||
output::{self, Log, SHRUPL},
|
output::{self, Log, SHRUPL},
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
@ -86,16 +86,16 @@ fn main() {
|
||||||
Err(e) => {
|
Err(e) => {
|
||||||
Log::handle(&e);
|
Log::handle(&e);
|
||||||
|
|
||||||
if let error::Error::InvalidParameter(p) = e {
|
if let shrupl::Error::InvalidParameter(p) = e {
|
||||||
match p {
|
match p {
|
||||||
// Error 404 (File not found)
|
// Error 404 (File not found)
|
||||||
error::Parameter::FileID(fid) => {
|
shrupl::Parameter::FileID(fid) => {
|
||||||
info!("retrying file {fid:?}");
|
info!("retrying file {fid:?}");
|
||||||
|
|
||||||
state.abort_upload();
|
state.abort_upload();
|
||||||
}
|
}
|
||||||
// Error 404 (Share not found)
|
// Error 404 (Share not found)
|
||||||
error::Parameter::ShareID(sid) => {
|
shrupl::Parameter::ShareID(sid) => {
|
||||||
output::prompt_rebuild_share();
|
output::prompt_rebuild_share();
|
||||||
info!("rebuilding share {sid:?}");
|
info!("rebuilding share {sid:?}");
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -12,7 +12,6 @@ use serde::{Deserialize, Serialize};
|
||||||
|
|
||||||
use crate::{
|
use crate::{
|
||||||
cli::Cli,
|
cli::Cli,
|
||||||
error,
|
|
||||||
file::{self, Chunk, FileTrait},
|
file::{self, Chunk, FileTrait},
|
||||||
output::new_progressbar,
|
output::new_progressbar,
|
||||||
sharry::{Client, Uri},
|
sharry::{Client, Uri},
|
||||||
|
|
@ -48,7 +47,7 @@ impl CacheFile {
|
||||||
file_name
|
file_name
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn try_resume(args: &Cli) -> error::Result<Self> {
|
pub fn try_resume(args: &Cli) -> crate::Result<Self> {
|
||||||
let file_name = Self::cache_file(args);
|
let file_name = Self::cache_file(args);
|
||||||
|
|
||||||
let state: Self = {
|
let state: Self = {
|
||||||
|
|
@ -61,7 +60,7 @@ impl CacheFile {
|
||||||
fn check_hash<'a>(
|
fn check_hash<'a>(
|
||||||
file: &'a impl FileTrait<'a>,
|
file: &'a impl FileTrait<'a>,
|
||||||
bar: &ProgressBar,
|
bar: &ProgressBar,
|
||||||
) -> error::Result<()> {
|
) -> crate::Result<()> {
|
||||||
bar.set_message(format!("checking {:?}", file.get_name()));
|
bar.set_message(format!("checking {:?}", file.get_name()));
|
||||||
file.check_hash(|bytes| bar.inc(bytes))
|
file.check_hash(|bytes| bar.inc(bytes))
|
||||||
}
|
}
|
||||||
|
|
@ -98,8 +97,8 @@ impl CacheFile {
|
||||||
|
|
||||||
pub fn from_args(
|
pub fn from_args(
|
||||||
args: &Cli,
|
args: &Cli,
|
||||||
new_share: impl FnOnce(&Cli) -> error::Result<String>,
|
new_share: impl FnOnce(&Cli) -> crate::Result<String>,
|
||||||
) -> error::Result<Self> {
|
) -> crate::Result<Self> {
|
||||||
let mut files = args.files.clone();
|
let mut files = args.files.clone();
|
||||||
|
|
||||||
if args.should_hash() {
|
if args.should_hash() {
|
||||||
|
|
@ -135,7 +134,7 @@ impl CacheFile {
|
||||||
pub fn get_uploading(
|
pub fn get_uploading(
|
||||||
&mut self,
|
&mut self,
|
||||||
client: &impl Client,
|
client: &impl Client,
|
||||||
) -> error::Result<Option<&mut file::Uploading>> {
|
) -> crate::Result<Option<&mut file::Uploading>> {
|
||||||
if self.uploading.is_some() {
|
if self.uploading.is_some() {
|
||||||
Ok(self.uploading.as_mut())
|
Ok(self.uploading.as_mut())
|
||||||
} else if let Some(chk) = self.files.pop_front() {
|
} else if let Some(chk) = self.files.pop_front() {
|
||||||
|
|
@ -189,11 +188,11 @@ impl CacheFile {
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn share_notify(&self, client: &impl Client) -> error::Result<()> {
|
pub fn share_notify(&self, client: &impl Client) -> crate::Result<()> {
|
||||||
client.share_notify(&self.uri, &self.alias_id, &self.share_id)
|
client.share_notify(&self.uri, &self.alias_id, &self.share_id)
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn file_patch(&self, client: &impl Client, chunk: &Chunk) -> error::Result<()> {
|
pub fn file_patch(&self, client: &impl Client, chunk: &Chunk) -> crate::Result<()> {
|
||||||
client.file_patch(&self.uri, &self.alias_id, &self.share_id, chunk)
|
client.file_patch(&self.uri, &self.alias_id, &self.share_id, chunk)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -5,7 +5,7 @@ use std::{
|
||||||
|
|
||||||
use serde::{Deserialize, Serialize};
|
use serde::{Deserialize, Serialize};
|
||||||
|
|
||||||
use crate::{error, sharry};
|
use crate::sharry;
|
||||||
|
|
||||||
use super::{FileTrait, Uploading};
|
use super::{FileTrait, Uploading};
|
||||||
|
|
||||||
|
|
@ -53,9 +53,9 @@ impl Checked {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn hash(&mut self, f: impl Fn(u64)) -> error::Result<()> {
|
pub fn hash(&mut self, f: impl Fn(u64)) -> crate::Result<()> {
|
||||||
if self.hash.is_some() {
|
if self.hash.is_some() {
|
||||||
return Err(error::Error::mismatch("unhashed file", self.path.display()));
|
return Err(crate::Error::mismatch("unhashed file", self.path.display()));
|
||||||
}
|
}
|
||||||
|
|
||||||
self.hash = Some(super::compute_file_hash(&self.path, self.size, f)?);
|
self.hash = Some(super::compute_file_hash(&self.path, self.size, f)?);
|
||||||
|
|
@ -78,7 +78,7 @@ impl Checked {
|
||||||
uri: &sharry::Uri,
|
uri: &sharry::Uri,
|
||||||
alias_id: &str,
|
alias_id: &str,
|
||||||
share_id: &str,
|
share_id: &str,
|
||||||
) -> error::Result<Uploading> {
|
) -> crate::Result<Uploading> {
|
||||||
let file_id = client.file_create(uri, alias_id, share_id, &self)?;
|
let file_id = client.file_create(uri, alias_id, share_id, &self)?;
|
||||||
|
|
||||||
Ok(Uploading::new(self.path, self.size, self.hash, file_id))
|
Ok(Uploading::new(self.path, self.size, self.hash, file_id))
|
||||||
|
|
@ -98,7 +98,7 @@ impl<'t> FileTrait<'t> for Checked {
|
||||||
self.size
|
self.size
|
||||||
}
|
}
|
||||||
|
|
||||||
fn check_hash(&self, on_progress: impl Fn(u64)) -> error::Result<()> {
|
fn check_hash(&self, on_progress: impl Fn(u64)) -> crate::Result<()> {
|
||||||
super::check_file_hash(&self.path, self.size, self.hash.as_ref(), on_progress)
|
super::check_file_hash(&self.path, self.size, self.hash.as_ref(), on_progress)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -12,9 +12,8 @@ pub use chunk::Chunk;
|
||||||
use log::{debug, warn};
|
use log::{debug, warn};
|
||||||
pub use uploading::Uploading;
|
pub use uploading::Uploading;
|
||||||
|
|
||||||
use crate::error;
|
|
||||||
|
|
||||||
fn compute_file_hash(path: &Path, size: u64, on_progress: impl Fn(u64)) -> error::Result<String> {
|
fn compute_file_hash(path: &Path, size: u64, on_progress: impl Fn(u64)) -> crate::Result<String> {
|
||||||
let mut file = fs::File::open(path)?;
|
let mut file = fs::File::open(path)?;
|
||||||
let mut hasher = Blake2b::new().hash_length(64).to_state();
|
let mut hasher = Blake2b::new().hash_length(64).to_state();
|
||||||
|
|
||||||
|
|
@ -33,7 +32,7 @@ fn compute_file_hash(path: &Path, size: u64, on_progress: impl Fn(u64)) -> error
|
||||||
}
|
}
|
||||||
|
|
||||||
if bytes_read != size {
|
if bytes_read != size {
|
||||||
return Err(error::Error::mismatch(size, bytes_read));
|
return Err(crate::Error::mismatch(size, bytes_read));
|
||||||
}
|
}
|
||||||
|
|
||||||
let result = Base64::encode_string(hasher.finalize().as_bytes());
|
let result = Base64::encode_string(hasher.finalize().as_bytes());
|
||||||
|
|
@ -46,9 +45,9 @@ fn check_file_hash(
|
||||||
size: u64,
|
size: u64,
|
||||||
hash: Option<&String>,
|
hash: Option<&String>,
|
||||||
on_progress: impl Fn(u64),
|
on_progress: impl Fn(u64),
|
||||||
) -> error::Result<()> {
|
) -> crate::Result<()> {
|
||||||
let Some(expected) = hash else {
|
let Some(expected) = hash else {
|
||||||
return Err(error::Error::mismatch("hash", path.display()));
|
return Err(crate::Error::mismatch("hash", path.display()));
|
||||||
};
|
};
|
||||||
|
|
||||||
let actual = &compute_file_hash(path, size, on_progress)?;
|
let actual = &compute_file_hash(path, size, on_progress)?;
|
||||||
|
|
@ -58,7 +57,7 @@ fn check_file_hash(
|
||||||
Ok(())
|
Ok(())
|
||||||
} else {
|
} else {
|
||||||
warn!("hash mismatch for file {:?}", path.display());
|
warn!("hash mismatch for file {:?}", path.display());
|
||||||
Err(error::Error::mismatch(expected, actual))
|
Err(crate::Error::mismatch(expected, actual))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -80,5 +79,5 @@ pub trait FileTrait<'t> {
|
||||||
/// get the file's size
|
/// get the file's size
|
||||||
fn get_size(&self) -> u64;
|
fn get_size(&self) -> u64;
|
||||||
|
|
||||||
fn check_hash(&self, on_progress: impl Fn(u64)) -> error::Result<()>;
|
fn check_hash(&self, on_progress: impl Fn(u64)) -> crate::Result<()>;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -7,7 +7,6 @@ use std::{
|
||||||
use log::warn;
|
use log::warn;
|
||||||
use serde::{Deserialize, Serialize};
|
use serde::{Deserialize, Serialize};
|
||||||
|
|
||||||
use crate::error;
|
|
||||||
|
|
||||||
use super::{Checked, Chunk, FileTrait};
|
use super::{Checked, Chunk, FileTrait};
|
||||||
|
|
||||||
|
|
@ -103,7 +102,7 @@ impl<'t> FileTrait<'t> for Uploading {
|
||||||
self.size
|
self.size
|
||||||
}
|
}
|
||||||
|
|
||||||
fn check_hash(&self, on_progress: impl Fn(u64)) -> error::Result<()> {
|
fn check_hash(&self, on_progress: impl Fn(u64)) -> crate::Result<()> {
|
||||||
super::check_file_hash(&self.path, self.size, self.hash.as_ref(), on_progress)
|
super::check_file_hash(&self.path, self.size, self.hash.as_ref(), on_progress)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -1,7 +1,6 @@
|
||||||
use log::{debug, trace};
|
use log::{debug, trace};
|
||||||
|
|
||||||
use crate::{
|
use crate::{
|
||||||
error,
|
|
||||||
file::{self, FileTrait},
|
file::{self, FileTrait},
|
||||||
sharry::{self, Uri},
|
sharry::{self, Uri},
|
||||||
};
|
};
|
||||||
|
|
@ -11,22 +10,22 @@ fn find_cause(
|
||||||
alias_id: &str,
|
alias_id: &str,
|
||||||
share_id: Option<&str>,
|
share_id: Option<&str>,
|
||||||
file_id: Option<&str>,
|
file_id: Option<&str>,
|
||||||
) -> impl FnOnce(ureq::Error) -> error::Error {
|
) -> impl FnOnce(ureq::Error) -> crate::Error {
|
||||||
move |error| match error {
|
move |error| match error {
|
||||||
ureq::Error::StatusCode(403) => {
|
ureq::Error::StatusCode(403) => {
|
||||||
trace!("HTTP Error 403: Alias not found!");
|
trace!("HTTP Error 403: Alias not found!");
|
||||||
|
|
||||||
error::Error::InvalidParameter(error::Parameter::AliasID(alias_id.to_owned()))
|
crate::Error::InvalidParameter(crate::Parameter::AliasID(alias_id.to_owned()))
|
||||||
}
|
}
|
||||||
ureq::Error::StatusCode(404) => {
|
ureq::Error::StatusCode(404) => {
|
||||||
trace!("HTTP Error 404: Share and/or file may have been deleted!");
|
trace!("HTTP Error 404: Share and/or file may have been deleted!");
|
||||||
|
|
||||||
if let Some(file_id) = file_id {
|
if let Some(file_id) = file_id {
|
||||||
error::Error::InvalidParameter(error::Parameter::FileID(file_id.to_owned()))
|
crate::Error::InvalidParameter(crate::Parameter::FileID(file_id.to_owned()))
|
||||||
} else if let Some(share_id) = share_id {
|
} else if let Some(share_id) = share_id {
|
||||||
error::Error::InvalidParameter(error::Parameter::ShareID(share_id.to_owned()))
|
crate::Error::InvalidParameter(crate::Parameter::ShareID(share_id.to_owned()))
|
||||||
} else {
|
} else {
|
||||||
error::Error::InvalidParameter(error::Parameter::Uri(uri.to_string()))
|
crate::Error::InvalidParameter(crate::Parameter::Uri(uri.to_string()))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
ureq::Error::Io(error) => {
|
ureq::Error::Io(error) => {
|
||||||
|
|
@ -34,7 +33,7 @@ fn find_cause(
|
||||||
|
|
||||||
if let Some(msg) = error.get_ref().map(ToString::to_string) {
|
if let Some(msg) = error.get_ref().map(ToString::to_string) {
|
||||||
if msg.starts_with("failed to lookup address information") {
|
if msg.starts_with("failed to lookup address information") {
|
||||||
error::Error::InvalidParameter(error::Parameter::Uri(uri.to_string()))
|
crate::Error::InvalidParameter(crate::Parameter::Uri(uri.to_string()))
|
||||||
} else {
|
} else {
|
||||||
error.into()
|
error.into()
|
||||||
}
|
}
|
||||||
|
|
@ -42,7 +41,7 @@ fn find_cause(
|
||||||
error.into()
|
error.into()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
error => error::Error::Unknown(error.to_string()),
|
error => crate::Error::Unknown(error.to_string()),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -52,7 +51,7 @@ impl sharry::Client for ureq::Agent {
|
||||||
uri: &Uri,
|
uri: &Uri,
|
||||||
alias_id: &str,
|
alias_id: &str,
|
||||||
data: sharry::NewShareRequest,
|
data: sharry::NewShareRequest,
|
||||||
) -> error::Result<String> {
|
) -> crate::Result<String> {
|
||||||
let res = {
|
let res = {
|
||||||
let endpoint = uri.share_create();
|
let endpoint = uri.share_create();
|
||||||
|
|
||||||
|
|
@ -63,11 +62,11 @@ impl sharry::Client for ureq::Agent {
|
||||||
.map_err(find_cause(uri, alias_id, None, None))?;
|
.map_err(find_cause(uri, alias_id, None, None))?;
|
||||||
|
|
||||||
trace!("{endpoint:?} response: {res:?}");
|
trace!("{endpoint:?} response: {res:?}");
|
||||||
error::Error::res_status_check(res.status(), ureq::http::StatusCode::OK)?;
|
crate::Error::res_status_check(res.status(), ureq::http::StatusCode::OK)?;
|
||||||
|
|
||||||
res.body_mut()
|
res.body_mut()
|
||||||
.read_json::<sharry::NewShareResponse>()
|
.read_json::<sharry::NewShareResponse>()
|
||||||
.map_err(error::Error::response)?
|
.map_err(crate::Error::response)?
|
||||||
};
|
};
|
||||||
|
|
||||||
debug!("{res:?}");
|
debug!("{res:?}");
|
||||||
|
|
@ -77,11 +76,11 @@ impl sharry::Client for ureq::Agent {
|
||||||
|
|
||||||
Ok(res.id)
|
Ok(res.id)
|
||||||
} else {
|
} else {
|
||||||
Err(error::Error::response(format!("{res:?}")))
|
Err(crate::Error::response(format!("{res:?}")))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn share_notify(&self, uri: &Uri, alias_id: &str, share_id: &str) -> error::Result<()> {
|
fn share_notify(&self, uri: &Uri, alias_id: &str, share_id: &str) -> crate::Result<()> {
|
||||||
let res = {
|
let res = {
|
||||||
let endpoint = uri.share_notify(share_id);
|
let endpoint = uri.share_notify(share_id);
|
||||||
|
|
||||||
|
|
@ -92,11 +91,11 @@ impl sharry::Client for ureq::Agent {
|
||||||
.map_err(find_cause(uri, alias_id, Some(share_id), None))?;
|
.map_err(find_cause(uri, alias_id, Some(share_id), None))?;
|
||||||
|
|
||||||
trace!("{endpoint:?} response: {res:?}");
|
trace!("{endpoint:?} response: {res:?}");
|
||||||
error::Error::res_status_check(res.status(), ureq::http::StatusCode::OK)?;
|
crate::Error::res_status_check(res.status(), ureq::http::StatusCode::OK)?;
|
||||||
|
|
||||||
res.body_mut()
|
res.body_mut()
|
||||||
.read_json::<sharry::NotifyShareResponse>()
|
.read_json::<sharry::NotifyShareResponse>()
|
||||||
.map_err(error::Error::response)?
|
.map_err(crate::Error::response)?
|
||||||
};
|
};
|
||||||
|
|
||||||
debug!("{res:?}");
|
debug!("{res:?}");
|
||||||
|
|
@ -110,7 +109,7 @@ impl sharry::Client for ureq::Agent {
|
||||||
alias_id: &str,
|
alias_id: &str,
|
||||||
share_id: &str,
|
share_id: &str,
|
||||||
file: &file::Checked,
|
file: &file::Checked,
|
||||||
) -> error::Result<String> {
|
) -> crate::Result<String> {
|
||||||
let res = {
|
let res = {
|
||||||
let endpoint = uri.file_create(share_id);
|
let endpoint = uri.file_create(share_id);
|
||||||
|
|
||||||
|
|
@ -123,14 +122,14 @@ impl sharry::Client for ureq::Agent {
|
||||||
.map_err(find_cause(uri, alias_id, Some(share_id), None))?;
|
.map_err(find_cause(uri, alias_id, Some(share_id), None))?;
|
||||||
|
|
||||||
trace!("{endpoint:?} response: {res:?}");
|
trace!("{endpoint:?} response: {res:?}");
|
||||||
error::Error::res_status_check(res.status(), ureq::http::StatusCode::CREATED)?;
|
crate::Error::res_status_check(res.status(), ureq::http::StatusCode::CREATED)?;
|
||||||
res
|
res
|
||||||
};
|
};
|
||||||
|
|
||||||
let location = (res.headers().get("Location"))
|
let location = (res.headers().get("Location"))
|
||||||
.ok_or_else(|| error::Error::response("Location header not found"))?
|
.ok_or_else(|| crate::Error::response("Location header not found"))?
|
||||||
.to_str()
|
.to_str()
|
||||||
.map_err(error::Error::response)?
|
.map_err(crate::Error::response)?
|
||||||
.to_string();
|
.to_string();
|
||||||
|
|
||||||
let file_id = Self::get_file_id(&location)?;
|
let file_id = Self::get_file_id(&location)?;
|
||||||
|
|
@ -146,7 +145,7 @@ impl sharry::Client for ureq::Agent {
|
||||||
alias_id: &str,
|
alias_id: &str,
|
||||||
share_id: &str,
|
share_id: &str,
|
||||||
chunk: &file::Chunk,
|
chunk: &file::Chunk,
|
||||||
) -> error::Result<()> {
|
) -> crate::Result<()> {
|
||||||
let res = {
|
let res = {
|
||||||
let endpoint = uri.file_patch(share_id, chunk.get_file_id());
|
let endpoint = uri.file_patch(share_id, chunk.get_file_id());
|
||||||
|
|
||||||
|
|
@ -163,21 +162,21 @@ impl sharry::Client for ureq::Agent {
|
||||||
))?;
|
))?;
|
||||||
|
|
||||||
trace!("{endpoint:?} response: {res:?}");
|
trace!("{endpoint:?} response: {res:?}");
|
||||||
error::Error::res_status_check(res.status(), ureq::http::StatusCode::NO_CONTENT)?;
|
crate::Error::res_status_check(res.status(), ureq::http::StatusCode::NO_CONTENT)?;
|
||||||
res
|
res
|
||||||
};
|
};
|
||||||
|
|
||||||
let res_offset = (res.headers().get("Upload-Offset"))
|
let res_offset = (res.headers().get("Upload-Offset"))
|
||||||
.ok_or_else(|| error::Error::response("Upload-Offset header not found"))?
|
.ok_or_else(|| crate::Error::response("Upload-Offset header not found"))?
|
||||||
.to_str()
|
.to_str()
|
||||||
.map_err(error::Error::response)?
|
.map_err(crate::Error::response)?
|
||||||
.parse::<u64>()
|
.parse::<u64>()
|
||||||
.map_err(error::Error::response)?;
|
.map_err(crate::Error::response)?;
|
||||||
|
|
||||||
if chunk.get_behind() == res_offset {
|
if chunk.get_behind() == res_offset {
|
||||||
Ok(())
|
Ok(())
|
||||||
} else {
|
} else {
|
||||||
Err(error::Error::response(format!(
|
Err(crate::Error::response(format!(
|
||||||
"Unexpected Upload-Offset: {} (expected {})",
|
"Unexpected Upload-Offset: {} (expected {})",
|
||||||
res_offset,
|
res_offset,
|
||||||
chunk.get_behind()
|
chunk.get_behind()
|
||||||
|
|
|
||||||
|
|
@ -4,7 +4,7 @@
|
||||||
mod appstate;
|
mod appstate;
|
||||||
mod cachefile;
|
mod cachefile;
|
||||||
mod cli;
|
mod cli;
|
||||||
pub mod error;
|
mod error;
|
||||||
mod file;
|
mod file;
|
||||||
mod impl_ureq;
|
mod impl_ureq;
|
||||||
pub mod output;
|
pub mod output;
|
||||||
|
|
@ -12,3 +12,4 @@ mod sharry;
|
||||||
|
|
||||||
pub use appstate::AppState;
|
pub use appstate::AppState;
|
||||||
pub use cli::Cli;
|
pub use cli::Cli;
|
||||||
|
pub use error::{Error, Parameter, Result};
|
||||||
|
|
|
||||||
|
|
@ -92,7 +92,7 @@ impl Log {
|
||||||
process::exit(1);
|
process::exit(1);
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn handle(e: &crate::error::Error) {
|
pub fn handle(e: &crate::Error) {
|
||||||
if e.is_fatal() {
|
if e.is_fatal() {
|
||||||
// react to fatal error
|
// react to fatal error
|
||||||
warn!("fatal error: {e:?}");
|
warn!("fatal error: {e:?}");
|
||||||
|
|
|
||||||
|
|
@ -3,12 +3,12 @@ use std::sync::LazyLock;
|
||||||
use log::trace;
|
use log::trace;
|
||||||
use regex::Regex;
|
use regex::Regex;
|
||||||
|
|
||||||
use crate::{error, file};
|
use crate::file;
|
||||||
|
|
||||||
use super::api::{NewShareRequest, Uri};
|
use super::api::{NewShareRequest, Uri};
|
||||||
|
|
||||||
pub trait Client {
|
pub trait Client {
|
||||||
fn get_file_id(uri: &str) -> error::Result<&str> {
|
fn get_file_id(uri: &str) -> crate::Result<&str> {
|
||||||
/// Pattern breakdown:
|
/// Pattern breakdown:
|
||||||
/// - `^([^:/?#]+)://` – scheme (anything but `:/?#`) + `"://"`
|
/// - `^([^:/?#]+)://` – scheme (anything but `:/?#`) + `"://"`
|
||||||
/// - `([^/?#]+)` – authority/host (anything but `/?#`)
|
/// - `([^/?#]+)` – authority/host (anything but `/?#`)
|
||||||
|
|
@ -32,7 +32,7 @@ pub trait Client {
|
||||||
{
|
{
|
||||||
Ok(fid)
|
Ok(fid)
|
||||||
} else {
|
} else {
|
||||||
Err(error::Error::mismatch(
|
Err(crate::Error::mismatch(
|
||||||
"<proto>://<base>/api/v2/alias/upload/<share>/files/tus/<file>",
|
"<proto>://<base>/api/v2/alias/upload/<share>/files/tus/<file>",
|
||||||
uri,
|
uri,
|
||||||
))
|
))
|
||||||
|
|
@ -44,9 +44,9 @@ pub trait Client {
|
||||||
uri: &Uri,
|
uri: &Uri,
|
||||||
alias_id: &str,
|
alias_id: &str,
|
||||||
data: NewShareRequest,
|
data: NewShareRequest,
|
||||||
) -> error::Result<String>;
|
) -> crate::Result<String>;
|
||||||
|
|
||||||
fn share_notify(&self, uri: &Uri, alias_id: &str, share_id: &str) -> error::Result<()>;
|
fn share_notify(&self, uri: &Uri, alias_id: &str, share_id: &str) -> crate::Result<()>;
|
||||||
|
|
||||||
fn file_create(
|
fn file_create(
|
||||||
&self,
|
&self,
|
||||||
|
|
@ -54,7 +54,7 @@ pub trait Client {
|
||||||
alias_id: &str,
|
alias_id: &str,
|
||||||
share_id: &str,
|
share_id: &str,
|
||||||
file: &file::Checked,
|
file: &file::Checked,
|
||||||
) -> error::Result<String>;
|
) -> crate::Result<String>;
|
||||||
|
|
||||||
fn file_patch(
|
fn file_patch(
|
||||||
&self,
|
&self,
|
||||||
|
|
@ -62,7 +62,7 @@ pub trait Client {
|
||||||
alias_id: &str,
|
alias_id: &str,
|
||||||
share_id: &str,
|
share_id: &str,
|
||||||
chunk: &file::Chunk,
|
chunk: &file::Chunk,
|
||||||
) -> error::Result<()>;
|
) -> crate::Result<()>;
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO move into tests subdir
|
// TODO move into tests subdir
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue