1use std::error;
4use std::io;
5
6use termcolor::{ColorSpec, WriteColor};
7
8use crate::prelude::*;
9
10pub fn format_repl_trace_into<W, E>(mut error: W, interp: &mut Artichoke, exc: &E) -> Result<(), Box<dyn error::Error>>
38where
39 W: io::Write + WriteColor,
40 E: RubyException,
41{
42 error.reset()?;
44
45 if let Some(backtrace) = exc.vm_backtrace(interp) {
47 error.set_color(ColorSpec::new().set_bold(true))?;
48 write!(error, "Traceback")?;
49 error.reset()?;
50 writeln!(error, " (most recent call last):")?;
51 for (num, frame) in backtrace.into_iter().enumerate().rev() {
52 write!(error, "\t{}: from ", num + 1)?;
53 error.write_all(frame.as_slice())?;
54 writeln!(error)?;
55 }
56 }
57
58 error.set_color(ColorSpec::new().set_bold(true))?;
60 write!(error, "{} (", exc.name())?;
61 error.set_color(ColorSpec::new().set_bold(true).set_underline(true))?;
62 error.write_all(&exc.message())?;
63 error.set_color(ColorSpec::new().set_bold(true))?;
64 writeln!(error, ")")?;
65
66 error.reset()?;
68
69 Ok(())
70}
71
72pub fn format_cli_trace_into<W, E>(mut error: W, interp: &mut Artichoke, exc: &E) -> Result<(), Box<dyn error::Error>>
99where
100 W: io::Write + WriteColor,
101 E: RubyException,
102{
103 error.reset()?;
105
106 let mut top = None;
107
108 if let Some(backtrace) = exc.vm_backtrace(interp) {
110 error.set_color(ColorSpec::new().set_bold(true))?;
111 write!(error, "Traceback")?;
112 error.reset()?;
113 writeln!(error, " (most recent call last):")?;
114 let mut iter = backtrace.into_iter().enumerate();
115 top = iter.next();
116 for (num, frame) in iter.rev() {
117 write!(error, "\t{}: from ", num + 1)?;
118 error.write_all(frame.as_slice())?;
119 writeln!(error)?;
120 }
121 }
122
123 if let Some((_, frame)) = top {
124 error.write_all(frame.as_slice())?;
125 write!(error, ": ")?;
126 }
127
128 error.set_color(ColorSpec::new().set_bold(true))?;
130 error.write_all(&exc.message())?;
131 error.set_color(ColorSpec::new().set_bold(true))?;
132 write!(error, " (")?;
133 error.set_color(ColorSpec::new().set_bold(true).set_underline(true))?;
134 write!(error, "{}", exc.name())?;
135 error.set_color(ColorSpec::new().set_bold(true))?;
136 writeln!(error, ")")?;
137
138 error.reset()?;
140
141 Ok(())
142}