Skip to content

Commit 49b00f6

Browse files
author
Gilad Naaman
committed
libtest: Json formatter now spews individiual events, not as an array
1 parent 6b97816 commit 49b00f6

File tree

1 file changed

+50
-60
lines changed

1 file changed

+50
-60
lines changed

src/libtest/formatters.rs

+50-60
Original file line numberDiff line numberDiff line change
@@ -246,127 +246,117 @@ impl<T: Write> OutputFormatter for HumanFormatter<T> {
246246
}
247247

248248
pub(crate) struct JsonFormatter<T> {
249-
out: OutputLocation<T>,
250-
had_events: bool
249+
out: OutputLocation<T>
251250
}
252251

253252
impl<T: Write> JsonFormatter<T> {
254253
pub fn new(out: OutputLocation<T>) -> Self {
255254
Self {
256-
out,
257-
had_events: false
258-
}
255+
out, }
259256
}
260257

261258
fn write_str<S: AsRef<str>>(&mut self, s: S) -> io::Result<()> {
262-
self.out.write_all(s.as_ref().as_ref())
259+
self.out.write_all(s.as_ref().as_ref())?;
260+
self.out.write_all("\n".as_ref())
263261
}
262+
}
264263

265-
fn write_event(&mut self, event: &str) -> io::Result<()> {
266-
if self.had_events {
267-
self.out.write_all(b",\n")?;
268-
}
269-
else {
270-
self.had_events = true;
271-
}
272-
273-
self.out.write_all(event.as_ref())
274-
}
264+
fn naive_json_escape(input: &str) -> String {
265+
input.replace("\\", "\\\\").replace("\"", "\\\"")
275266
}
276267

277268
impl<T: Write> OutputFormatter for JsonFormatter<T> {
278-
fn write_run_start(&mut self, _len: usize) -> io::Result<()> {
279-
self.write_str("{\n\tevents: [\n")
269+
fn write_run_start(&mut self, len: usize) -> io::Result<()> {
270+
self.write_str(
271+
&*format!(r#"{{ "type": "suite", "event": "started", "test_count": "{}" }}"#, len))
280272
}
281273

282274
fn write_test_start(&mut self,
283275
desc: &TestDesc,
284276
_align: NamePadding,
285277
_max_name_len: usize) -> io::Result<()> {
286-
self.write_event(&*format!("\t\t{{ \"test\": \"{}\", \"event\": \"started\" }}", desc.name))
278+
self.write_str(&*format!(r#"{{ "type": "test", "event": "started", "name": "{}" }}"#,
279+
desc.name))
287280
}
288281

289282
fn write_result(&mut self, desc: &TestDesc, result: &TestResult) -> io::Result<()> {
290283
let output = match *result {
291284
TrOk => {
292-
format!("\t\t{{ \"test\": \"{}\", \"event\": \"ok\" }}", desc.name)
285+
format!(r#"{{ "type": "test", "event": "ok", "name": "{}" }}"#,
286+
desc.name)
293287
},
294288

295289
TrFailed => {
296-
format!("\t\t{{ \"test\": \"{}\", \"event\": \"failed\" }}", desc.name)
290+
format!(r#"{{ "type": "test", "event": "failed", "name": "{}" }}"#,
291+
desc.name)
297292
},
298293

299294
TrFailedMsg(ref m) => {
300-
format!("\t\t{{ \"test\": \"{}\", \"event\": \"failed\", \"extra\": \"{}\" }}",
295+
format!(r#"{{ "type": "test", "event": "failed", "name": "{}", "message": "{}" }}"#,
301296
desc.name,
302-
m)
297+
naive_json_escape(m))
303298
},
304299

305300
TrIgnored => {
306-
format!("\t\t{{ \"test\": \"{}\", \"event\": \"ignored\" }}", desc.name)
301+
format!(r#"{{ "type": "test", "event": "ignored", "name": "{}" }}"#,
302+
desc.name)
307303
},
308304

309305
TrAllowedFail => {
310-
format!("\t\t{{ \"test\": \"{}\", \"event\": \"allowed_failure\" }}", desc.name)
306+
format!(r#"{{ "type": "test", "event": "allowed_failure", "name": "{}" }}"#,
307+
desc.name)
311308
},
312309

313310
TrMetrics(ref mm) => {
314-
format!("\t\t{{ \"test\": \"{}\", \"event\": \"metrics\", \"extra\": \"{}\" }}",
311+
format!(r#"{{ "type": "metrics", "name": "{}", "metrics": "{}" }}"#,
315312
desc.name,
316313
mm.fmt_metrics())
317314
},
318315

319316
TrBench(ref bs) => {
320-
format!("\t\t{{ \"test\": \"{}\", \"event\": \"bench\", \"extra\": \"{}\" }}",
317+
format!(r#"{{ "type": "bench", "name": "{}", "bench": "{}" }}"#,
321318
desc.name,
322319
fmt_bench_samples(bs))
323320
},
324321
};
325322

326-
self.write_event(&*output)
323+
self.write_str(&*output)
327324
}
328325

329326
fn write_timeout(&mut self, desc: &TestDesc) -> io::Result<()> {
330-
self.write_event(&*format!("\t{{ \"test\": \"{}\", \"event\": \"timeout\" }}", desc.name))
327+
self.write_str(&*format!(r#"{{ "type": "test", "event": "timeout", "name": "{}" }}"#,
328+
desc.name))
331329
}
332330

333331
fn write_run_finish(&mut self, state: &ConsoleTestState) -> io::Result<bool> {
334-
self.write_str("\n\t],\n\t\"summary\": {\n")?;
335332

336-
self.write_str(&*format!("\t\t\"passed\": {},\n", state.passed))?;
337-
self.write_str(&*format!("\t\t\"failed\": {},\n", state.failed + state.allowed_fail))?;
338-
self.write_str(&*format!("\t\t\"allowed_fail\": {},\n", state.allowed_fail))?;
339-
self.write_str(&*format!("\t\t\"ignored\": {},\n", state.ignored))?;
340-
self.write_str(&*format!("\t\t\"measured\": {},\n", state.measured))?;
333+
self.write_str(&*format!(r#"{{ "type": "suite",
334+
"event": "{}",
335+
"passed": {},
336+
"failed": {},
337+
"allowed_fail": {},
338+
"ignored": {},
339+
"measured": {},
340+
"filtered_out": "{}" }}"#,
341+
if state.failed == 0 { "ok" } else { "failed" },
342+
state.passed,
343+
state.failed + state.allowed_fail,
344+
state.allowed_fail,
345+
state.ignored,
346+
state.measured,
347+
state.filtered_out))?;
341348

342-
if state.failed == 0 {
343-
self.write_str(&*format!("\t\t\"filtered_out\": {}\n", state.filtered_out))?;
344-
} else {
345-
self.write_str(&*format!("\t\t\"filtered_out\": {},\n", state.filtered_out))?;
346-
self.write_str("\t\t\"failures\": [\n")?;
347-
348-
let mut has_items = false;
349-
for &(ref f, ref stdout) in &state.failures {
350-
if !stdout.is_empty() {
351-
if has_items {
352-
self.write_str(",\n")?;
353-
} else {
354-
has_items = true;
355-
}
356-
357-
let output = String::from_utf8_lossy(stdout)
358-
.replace("\\", "\\\\")
359-
.replace("\"", "\\\"");
360-
361-
self.write_str(&*format!("\t\t\t\"{}\": \"{}\"", f.name, output))?;
362-
}
363-
}
349+
for &(ref f, ref stdout) in &state.failures {
350+
if !stdout.is_empty() {
351+
let output = naive_json_escape(&*String::from_utf8_lossy(stdout));
364352

365-
self.write_str("\n\t\t]\n")?;
353+
self.write_str(
354+
&*format!(r#"{{ "type": "test_output", "name": "{}" "output": "{}" }}"#,
355+
f.name,
356+
output))?;
357+
}
366358
}
367359

368-
self.write_str("\t}\n}\n")?;
369-
370360
Ok(state.failed == 0)
371361
}
372362
}

0 commit comments

Comments
 (0)