1
Fork 0

Don’t make conf errors fatal errors

This commit is contained in:
mcarton 2016-03-06 15:48:56 +01:00
parent d118b27abb
commit 95e582a338
2 changed files with 40 additions and 23 deletions

View file

@ -111,24 +111,30 @@ mod reexport {
#[plugin_registrar] #[plugin_registrar]
#[cfg_attr(rustfmt, rustfmt_skip)] #[cfg_attr(rustfmt, rustfmt_skip)]
pub fn plugin_registrar(reg: &mut Registry) { pub fn plugin_registrar(reg: &mut Registry) {
let conferr = match utils::conf::conf_file(reg.args()) { let conf = match utils::conf::conf_file(reg.args()) {
Ok(Some(file_name)) => { Ok(file_name) => {
utils::conf::read_conf(&file_name, true) // if the user specified a file, it must exist, otherwise default to `Clippy.toml` but
} // do not require the file to exist
Ok(None) => { let (ref file_name, must_exist) = if let Some(ref file_name) = file_name {
utils::conf::read_conf("Clippy.toml", false) (&**file_name, true)
} else {
("Clippy.toml", false)
};
let (conf, errors) = utils::conf::read_conf(&file_name, must_exist);
// all conf errors are non-fatal, we just use the default conf in case of error
for error in errors {
reg.sess.struct_err(&format!("error reading Clippy's configuration file: {}", error)).emit();
}
conf
} }
Err((err, span)) => { Err((err, span)) => {
reg.sess.struct_span_err(span, err).emit(); reg.sess.struct_span_err(span, err)
return; .span_note(span, "Clippy will use defaulf configuration")
} .emit();
}; utils::conf::Conf::default()
let conf = match conferr {
Ok(conf) => conf,
Err(err) => {
reg.sess.struct_err(&format!("error reading Clippy's configuration file: {}", err)).emit();
return;
} }
}; };

View file

@ -157,20 +157,28 @@ define_Conf! {
/// Read the `toml` configuration file. The function will ignore “File not found” errors iif /// Read the `toml` configuration file. The function will ignore “File not found” errors iif
/// `!must_exist`, in which case, it will return the default configuration. /// `!must_exist`, in which case, it will return the default configuration.
pub fn read_conf(path: &str, must_exist: bool) -> Result<Conf, ConfError> { /// In case of error, the function tries to continue as much as possible.
pub fn read_conf(path: &str, must_exist: bool) -> (Conf, Vec<ConfError>) {
let mut conf = Conf::default(); let mut conf = Conf::default();
let mut errors = Vec::new();
let file = match fs::File::open(path) { let file = match fs::File::open(path) {
Ok(mut file) => { Ok(mut file) => {
let mut buf = String::new(); let mut buf = String::new();
try!(file.read_to_string(&mut buf));
if let Err(err) = file.read_to_string(&mut buf) {
errors.push(err.into());
return (conf, errors);
}
buf buf
} }
Err(ref err) if !must_exist && err.kind() == io::ErrorKind::NotFound => { Err(ref err) if !must_exist && err.kind() == io::ErrorKind::NotFound => {
return Ok(conf); return (conf, errors);
} }
Err(err) => { Err(err) => {
return Err(err.into()); errors.push(err.into());
return (conf, errors);
} }
}; };
@ -178,12 +186,15 @@ pub fn read_conf(path: &str, must_exist: bool) -> Result<Conf, ConfError> {
let toml = if let Some(toml) = parser.parse() { let toml = if let Some(toml) = parser.parse() {
toml toml
} else { } else {
return Err(ConfError::TomlError(parser.errors)); errors.push(ConfError::TomlError(parser.errors));
return (conf, errors);
}; };
for (key, value) in toml { for (key, value) in toml {
try!(conf.set(key, value)); if let Err(err) = conf.set(key, value) {
errors.push(err);
}
} }
Ok(conf) (conf, errors)
} }