Skip to content

Commit 4083288

Browse files
committed
Improve report I/O error message with filename.
1 parent 60838fe commit 4083288

8 files changed

Lines changed: 68 additions & 143 deletions

File tree

packages/hurl/src/report/curl.rs

Lines changed: 8 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -32,28 +32,27 @@ pub fn write_curl(
3232
filename: &Path,
3333
secrets: &[&str],
3434
) -> Result<(), ReportError> {
35-
if let Err(err) = create_dir_all(filename) {
36-
return Err(ReportError::from_error(
37-
err,
38-
filename,
39-
"Issue creating curl export",
40-
));
41-
}
35+
create_dir_all(filename)
36+
.map_err(|e| ReportError::from_io_error(&e, filename, "Issue creating curl export"))?;
4237

4338
let mut file = OpenOptions::new()
4439
.create(true)
4540
.truncate(true)
4641
.write(true)
4742
.append(false)
48-
.open(filename)?;
43+
.open(filename)
44+
.map_err(|e| ReportError::from_io_error(&e, filename, "Issue creating curl export"))?;
45+
4946
let mut cmds = hurl_results
5047
.iter()
5148
.flat_map(|h| &h.entries)
5249
.map(|e| e.curl_cmd.to_string().redact(secrets))
5350
.collect::<Vec<_>>()
5451
.join("\n");
5552
cmds.push('\n');
56-
file.write_all(cmds.as_bytes())?;
53+
54+
file.write_all(cmds.as_bytes())
55+
.map_err(|e| ReportError::from_io_error(&e, filename, "Issue writing curl export"))?;
5756

5857
Ok(())
5958
}

packages/hurl/src/report/error.rs

Lines changed: 3 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,7 @@ use std::{fmt, io};
2121
#[derive(Debug)]
2222
pub enum ReportError {
2323
IO {
24-
inner: io::Error,
24+
inner: io::ErrorKind,
2525
file: PathBuf,
2626
message: String,
2727
},
@@ -35,9 +35,9 @@ impl ReportError {
3535
}
3636

3737
/// Creates a new error instance.
38-
pub fn from_error(error: io::Error, file: &Path, message: &str) -> Self {
38+
pub fn from_io_error(error: &io::Error, file: &Path, message: &str) -> Self {
3939
ReportError::IO {
40-
inner: error,
40+
inner: error.kind(),
4141
file: file.to_path_buf(),
4242
message: message.to_string(),
4343
}
@@ -56,9 +56,3 @@ impl fmt::Display for ReportError {
5656
}
5757
}
5858
}
59-
60-
impl From<io::Error> for ReportError {
61-
fn from(e: io::Error) -> Self {
62-
ReportError::from_string(&e.to_string())
63-
}
64-
}

packages/hurl/src/report/html/report.rs

Lines changed: 9 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -37,23 +37,10 @@ pub fn write_report(dir_path: &Path, testcases: &[Testcase]) -> Result<(), Repor
3737
let s = create_html_index(&now.to_rfc2822(), &results);
3838

3939
let file_path = index_path;
40-
let mut file = match std::fs::File::create(&file_path) {
41-
Err(err) => {
42-
return Err(ReportError::from_error(
43-
err,
44-
&file_path,
45-
"Issue writing HTML report",
46-
))
47-
}
48-
Ok(file) => file,
49-
};
50-
if let Err(err) = file.write_all(s.as_bytes()) {
51-
return Err(ReportError::from_error(
52-
err,
53-
&file_path,
54-
"Issue writing HTML report",
55-
));
56-
}
40+
let mut file = std::fs::File::create(&file_path)
41+
.map_err(|e| ReportError::from_io_error(&e, &file_path, "Issue writing HTML report"))?;
42+
file.write_all(s.as_bytes())
43+
.map_err(|e| ReportError::from_io_error(&e, &file_path, "Issue writing HTML report"))?;
5744
Ok(())
5845
}
5946

@@ -84,21 +71,12 @@ fn create_html_index(now: &str, hurl_results: &[HTMLResult]) -> String {
8471
}
8572

8673
fn parse_html(path: &Path) -> Result<Vec<HTMLResult>, ReportError> {
87-
if path.exists() {
88-
let s = match std::fs::read_to_string(path) {
89-
Ok(s) => s,
90-
Err(e) => {
91-
return Err(ReportError::from_error(
92-
e,
93-
path,
94-
"Issue reading HTML report",
95-
))
96-
}
97-
};
98-
Ok(parse_html_report(&s))
99-
} else {
100-
Ok(vec![])
74+
if !path.exists() {
75+
return Ok(vec![]);
10176
}
77+
let s = std::fs::read_to_string(path)
78+
.map_err(|e| ReportError::from_io_error(&e, path, "Issue reading HTML report"))?;
79+
Ok(parse_html_report(&s))
10280
}
10381

10482
/// Parses the HTML report `html` an returns a list of [`HTMLResult`].

packages/hurl/src/report/html/testcase.rs

Lines changed: 12 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -18,13 +18,13 @@
1818
use std::fs;
1919
use std::path::Path;
2020

21+
use crate::report::ReportError;
22+
use crate::runner::{EntryResult, HurlResult, RunnerError};
2123
use hurl_core::ast::SourceInfo;
2224
use hurl_core::input::Input;
2325
use hurl_core::parser;
2426
use uuid::Uuid;
2527

26-
use crate::runner::{EntryResult, HurlResult, RunnerError};
27-
2828
#[derive(Clone, Debug, PartialEq, Eq)]
2929
pub struct Testcase {
3030
/// Unique identifier of this testcase.
@@ -71,7 +71,7 @@ impl Testcase {
7171
entries: &[EntryResult],
7272
dir: &Path,
7373
secrets: &[&str],
74-
) -> Result<(), crate::report::ReportError> {
74+
) -> Result<(), ReportError> {
7575
// We parse the content as we'll reuse the AST to construct the HTML source file, and
7676
// the waterfall.
7777
// TODO: for the moment, we can only have parseable file.
@@ -80,17 +80,23 @@ impl Testcase {
8080
// We create the timeline view.
8181
let output_file = dir.join(self.timeline_filename());
8282
let html = self.get_timeline_html(&hurl_file, content, entries, secrets);
83-
fs::write(output_file, html.as_bytes())?;
83+
fs::write(&output_file, html.as_bytes()).map_err(|e| {
84+
ReportError::from_io_error(&e, &output_file, "Issue writing HTML report")
85+
})?;
8486

8587
// Then create the run view.
8688
let output_file = dir.join(self.run_filename());
8789
let html = self.get_run_html(&hurl_file, content, entries, secrets);
88-
fs::write(output_file, html.as_bytes())?;
90+
fs::write(&output_file, html.as_bytes()).map_err(|e| {
91+
ReportError::from_io_error(&e, &output_file, "Issue writing HTML report")
92+
})?;
8993

9094
// And create the source view.
9195
let output_file = dir.join(self.source_filename());
9296
let html = self.get_source_html(&hurl_file, content, secrets);
93-
fs::write(output_file, html.as_bytes())?;
97+
fs::write(&output_file, html.as_bytes()).map_err(|e| {
98+
ReportError::from_io_error(&e, &output_file, "Issue writing HTML report")
99+
})?;
94100

95101
Ok(())
96102
}

packages/hurl/src/report/json/deserialize.rs

Lines changed: 3 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -33,16 +33,9 @@ pub fn parse_json_report(filename: &Path) -> Result<Vec<Value>, ReportError> {
3333
if !filename.exists() {
3434
return Ok(vec![]);
3535
}
36-
let s = match fs::read_to_string(filename) {
37-
Ok(s) => s,
38-
Err(e) => {
39-
return Err(ReportError::from_error(
40-
e,
41-
filename,
42-
"Issue reading JSON report",
43-
))
44-
}
45-
};
36+
let s = fs::read_to_string(filename)
37+
.map_err(|e| ReportError::from_io_error(&e, filename, "Issue reading JSON report"))?;
38+
4639
// TODO: if the existing JSON report is not valid, we consider that there is no
4740
// existing report to append, without displaying any error or warning. Maybe a better option
4841
// would be to raise an error here and ask the user to explicitly deal with this error.

packages/hurl/src/report/json/mod.rs

Lines changed: 8 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -60,21 +60,19 @@ pub fn write_report(
6060
let json = testcases
6161
.iter()
6262
.map(|t| t.to_json(response_dir, secrets))
63-
.collect::<Result<Vec<_>, _>>()?;
63+
.collect::<Result<Vec<_>, _>>()
64+
.map_err(|e| ReportError::from_io_error(&e, filename, "Issue creating JSON report"))?;
6465
report.extend(json);
6566

6667
let serialized = serde_json::to_string(&report)?;
6768
let bytes = format!("{serialized}\n");
6869
let bytes = bytes.into_bytes();
69-
let mut file_out = File::create(filename)?;
70-
match file_out.write_all(&bytes) {
71-
Ok(_) => Ok(()),
72-
Err(e) => Err(ReportError::from_error(
73-
e,
74-
filename,
75-
"Issue writing JSON report",
76-
)),
77-
}
70+
let mut file_out = File::create(filename)
71+
.map_err(|e| ReportError::from_io_error(&e, filename, "Issue creating JSON report"))?;
72+
file_out
73+
.write_all(&bytes)
74+
.map_err(|e| ReportError::from_io_error(&e, filename, "Issue writing JSON report"))?;
75+
Ok(())
7876
}
7977

8078
#[derive(Clone, Debug, PartialEq, Eq)]

packages/hurl/src/report/junit/mod.rs

Lines changed: 14 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -73,26 +73,13 @@ pub fn write_report(
7373
testcases: &[Testcase],
7474
secrets: &[&str],
7575
) -> Result<(), ReportError> {
76-
if let Err(err) = create_dir_all(filename) {
77-
return Err(ReportError::from_error(
78-
err,
79-
filename,
80-
"Issue writing JUnit report",
81-
));
82-
}
76+
create_dir_all(filename)
77+
.map_err(|e| ReportError::from_io_error(&e, filename, "Issue writing JUnit report"))?;
8378

8479
// If there is an existing JUnit report, we parse it to insert a new testsuite.
8580
let mut root = if filename.exists() {
86-
let file = match File::open(filename) {
87-
Ok(s) => s,
88-
Err(e) => {
89-
return Err(ReportError::from_error(
90-
e,
91-
filename,
92-
"Issue reading JUnit report",
93-
))
94-
}
95-
};
81+
let file = File::open(filename)
82+
.map_err(|e| ReportError::from_io_error(&e, filename, "Issue reading JUnit report"))?;
9683
let doc = XmlDocument::parse(file).unwrap();
9784
doc.root.unwrap()
9885
} else {
@@ -103,22 +90,16 @@ pub fn write_report(
10390
root = root.add_child(testsuite);
10491

10592
let doc = XmlDocument::new(root);
106-
let file = match File::create(filename) {
107-
Ok(f) => f,
108-
Err(e) => {
109-
return Err(ReportError::from_error(
110-
e,
111-
filename,
112-
"Issue writing JUnit report",
113-
))
114-
}
115-
};
116-
match doc.write(file) {
117-
Ok(_) => Ok(()),
118-
Err(e) => Err(ReportError::from_string(&format!(
119-
"Failed to produce Junit report: {e:?}"
120-
))),
121-
}
93+
let file = File::create(filename)
94+
.map_err(|e| ReportError::from_io_error(&e, filename, "Issue writing JUnit report"))?;
95+
96+
doc.write(file).map_err(|e| {
97+
ReportError::from_string(&format!(
98+
"Issue writing JUnit report {} {e}",
99+
filename.display()
100+
))
101+
})?;
102+
Ok(())
122103
}
123104

124105
/// Returns a testsuite as a XML object, from a list of `testcases`.

packages/hurl/src/report/tap/report.rs

Lines changed: 11 additions & 35 deletions
Original file line numberDiff line numberDiff line change
@@ -45,23 +45,12 @@ pub fn write_report(filename: &Path, testcases: &[Testcase]) -> Result<(), Repor
4545

4646
/// Creates a Tap from a list of `testcases`.
4747
fn write_tap_file(filename: &Path, testcases: &[&Testcase]) -> Result<(), ReportError> {
48-
if let Err(err) = create_dir_all(filename) {
49-
return Err(ReportError::from_error(
50-
err,
51-
filename,
52-
"Issue writing TAP report",
53-
));
54-
}
55-
let mut file = match File::create(filename) {
56-
Ok(f) => f,
57-
Err(e) => {
58-
return Err(ReportError::from_error(
59-
e,
60-
filename,
61-
"Issue writing TAP report",
62-
))
63-
}
64-
};
48+
create_dir_all(filename)
49+
.map_err(|e| ReportError::from_io_error(&e, filename, "Issue writing TAP report"))?;
50+
51+
let mut file = File::create(filename)
52+
.map_err(|e| ReportError::from_io_error(&e, filename, "Issue writing TAP report"))?;
53+
6554
let start = 1;
6655
let end = testcases.len();
6756

@@ -74,31 +63,18 @@ fn write_tap_file(filename: &Path, testcases: &[&Testcase]) -> Result<(), Report
7463
let description = &testcase.description;
7564
s.push_str(format!("{state} {number} - {description}\n").as_str());
7665
}
77-
match file.write_all(s.as_bytes()) {
78-
Ok(_) => Ok(()),
79-
Err(e) => Err(ReportError::from_error(
80-
e,
81-
filename,
82-
"Issue writing TAP report",
83-
)),
84-
}
66+
file.write_all(s.as_bytes())
67+
.map_err(|e| ReportError::from_io_error(&e, filename, "Issue writing TAP report"))?;
68+
Ok(())
8569
}
8670

8771
/// Parse Tap report file
8872
fn parse_tap_file(filename: &Path) -> Result<Vec<Testcase>, ReportError> {
8973
if !filename.exists() {
9074
return Ok(vec![]);
9175
}
92-
let s = match std::fs::read_to_string(filename) {
93-
Ok(s) => s,
94-
Err(e) => {
95-
return Err(ReportError::from_error(
96-
e,
97-
filename,
98-
"Issue reading TAP report",
99-
))
100-
}
101-
};
76+
let s = std::fs::read_to_string(filename)
77+
.map_err(|e| ReportError::from_io_error(&e, filename, "Issue reading TAP report"))?;
10278
parse_tap_report(&s)
10379
}
10480

0 commit comments

Comments
 (0)