Skip to content

Commit 33b0a1f

Browse files
committed
Better errors when importing AutoYaST profiles
1 parent 82ed652 commit 33b0a1f

File tree

2 files changed

+40
-21
lines changed

2 files changed

+40
-21
lines changed

rust/agama-lib/src/profile.rs

Lines changed: 24 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -26,35 +26,49 @@ use std::{fs, io::Write, path::Path, process::Command};
2626
use tempfile::{tempdir, TempDir};
2727
use url::Url;
2828

29+
#[derive(thiserror::Error, Debug)]
30+
pub enum AutoyastError {
31+
#[error("I/O error: {0}")]
32+
IO(#[from] std::io::Error),
33+
#[error("Failed to run the agama-autoyast script: {0}")]
34+
Execute(#[source] std::io::Error),
35+
#[error("Failed to convert the AutoYaST profile: {0}")]
36+
Evaluation(String),
37+
#[error("Unsupported AutoYaST format at {0}")]
38+
UnsupportedFormat(Url),
39+
}
40+
2941
/// Downloads and converts autoyast profile.
3042
pub struct AutoyastProfileImporter {
3143
pub content: String,
3244
}
3345

3446
impl AutoyastProfileImporter {
35-
pub async fn read(url: &Url) -> anyhow::Result<Self> {
47+
pub async fn read(url: &Url) -> Result<Self, AutoyastError> {
3648
let path = url.path();
3749
if !path.ends_with(".xml") && !path.ends_with(".erb") && !path.ends_with('/') {
38-
let msg = format!("Unsupported AutoYaST format at {}", url);
39-
return Err(anyhow::Error::msg(msg));
50+
return Err(AutoyastError::UnsupportedFormat(url.clone()));
4051
}
4152

4253
const TMP_DIR_PREFIX: &str = "autoyast";
4354
const AUTOINST_JSON: &str = "autoinst.json";
4455

4556
let tmp_dir = TempDir::with_prefix(TMP_DIR_PREFIX)?;
46-
tokio::process::Command::new("agama-autoyast")
57+
let result = tokio::process::Command::new("agama-autoyast")
4758
.env("YAST_SKIP_PROFILE_FETCH_ERROR", "1")
4859
.args([url.as_str(), &tmp_dir.path().to_string_lossy()])
49-
.status()
60+
.output()
5061
.await
51-
.context("Failed to run agama-autoyast")?;
62+
.map_err(AutoyastError::Execute)?;
63+
64+
if !result.status.success() {
65+
return Err(AutoyastError::Evaluation(
66+
String::from_utf8_lossy(&result.stderr).to_string(),
67+
));
68+
}
5269

5370
let autoinst_json = tmp_dir.path().join(AUTOINST_JSON);
54-
let content = fs::read_to_string(&autoinst_json).context(format!(
55-
"agama-autoyast did not produce {:?}",
56-
autoinst_json
57-
))?;
71+
let content = fs::read_to_string(&autoinst_json)?;
5872
Ok(Self { content })
5973
}
6074
}

rust/agama-server/src/profile/web.rs

Lines changed: 16 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@
1818
// To contact SUSE LLC about this file by physical or electronic mail, you may
1919
// find current contact information at www.suse.com.
2020

21+
use agama_lib::profile::AutoyastError;
2122
use anyhow::Context;
2223

2324
use agama_lib::utils::Transfer;
@@ -50,6 +51,19 @@ impl std::fmt::Display for ProfileServiceError {
5051
}
5152
}
5253

54+
impl From<AutoyastError> for ProfileServiceError {
55+
fn from(e: AutoyastError) -> Self {
56+
let http_status = match e {
57+
AutoyastError::Execute(..) => StatusCode::INTERNAL_SERVER_ERROR,
58+
_ => StatusCode::BAD_REQUEST,
59+
};
60+
Self {
61+
source: e.into(),
62+
http_status,
63+
}
64+
}
65+
}
66+
5367
// Make a 400 response
5468
// ```
5569
// let r: Result<T, anyhow::Error> = foo();
@@ -221,15 +235,6 @@ async fn autoyast(
221235
}
222236

223237
let url = Url::parse(query.url.as_ref().unwrap()).map_err(anyhow::Error::new)?;
224-
let importer_res = AutoyastProfileImporter::read(&url).await;
225-
match importer_res {
226-
Ok(importer) => Ok(importer.content),
227-
Err(error) => {
228-
// anyhow can be only displayed, not so nice
229-
if format!("{}", error).contains("Failed to run") {
230-
return Err(make_internal(error));
231-
}
232-
Err(error.into())
233-
}
234-
}
238+
let importer = AutoyastProfileImporter::read(&url).await?;
239+
Ok(importer.content)
235240
}

0 commit comments

Comments
 (0)