Ich versuche das Iron-Framework zu verwenden, um ein einfaches Backend in Rust zu erstellen. Dieser Handler soll nur den Inhalt einer bestimmten Datei zurückgeben, und ich kann es mit unwrap()
richtig funktionieren lassen, aber ich möchte versuchen, eine ordnungsgemäße Fehlerbehandlung zu tun. Dies ist, wie ich könnte mir vorstellen, es aussehen würde:Wenn ein Ergebnis Err (_) zurückgibt, möchte ich, dass die gesamte Funktion einen HTTP-Anforderungsfehler zurückgibt.
fn get_content(res: &mut Request) -> IronResult<Response> {
let mut id = String::new();
res.body.read_to_string(&mut id).unwrap();
let file_path_string = &("../content/".to_string() + &id + ".rdt");
// TODO: Error handling
match File::open(file_path_string) {
Ok(f) => {
let mut s = String::new();
f.read_to_string(&mut s);
Ok(Response::with(((status::Ok), s)))
}
Err(err) => Err(Response::with(((status::InternalServerError), "File not found")))
};
}
not all control paths return a value [E0269]
, dies führt den Fehler, der in Ordnung ist. Aber wenn ich eine Antwort nach dem Spiel Teil hinzufügen:
match File::open(file_path_string) {
Ok(f) => {
let mut s = String::new();
f.read_to_string(&mut s);
Ok(Response::with(((status::Ok), s)))
}
Err(err) => Err(Response::with(((status::InternalServerError), "File not found")))
};
Err(Response::with(((status::InternalServerError), "File not found")))
ich stattdessen die Fehlermeldung:
expected `iron::error::IronError`,
found `iron::response::Response`
(expected struct `iron::error::IronError`,
found struct `iron::response::Response`) [E0308]
src/main.rs:95
Err(Response::with(((status::InternalServerError), "File not found")))
Ich denke, das Problem ist die Kollision zwischen Rust Err und Eisen Err? Ich bin mir nicht sicher. Und ich habe in der Vergangenheit nicht viel Web-Entwicklung (oder Rust in der Tat) gemacht, also wird jede Rückmeldung über den Code auch geschätzt!
UPDATE: Ich denke, das ist mehr "The Rust Way", es zu tun? Aber ich bin nicht sicher,
fn get_content(res: &mut Request) -> IronResult<Response> {
let mut id = String::new();
res.body.read_to_string(&mut id).unwrap();
let file_path_string = &("../content/".to_string() + &id + ".rdt");
// TODO: Error handling
let f;
match File::open(file_path_string) {
Ok(file) => f = file,
Err(err) => Err(HttpError::Io(err))
};
let mut s = String::new();
f.read_to_string(&mut s);
Ok(Response::with(((status::Ok), s)))
}
den Code Nachdem innerhalb der Fehlerbehandlung seltsam scheint, als read_to_string
muss auch gesorgt werden, und das würde eine verschachtelte Chaos der Fehlerbehandlung erstellen? Diese passenden Arme sind jedoch offensichtlich inkompatibel, also wird es nicht funktionieren ... irgendwelche Vorschläge?
Ist es idiomatisch korrekt den Rest des Codes Teil innerhalb der Fehlerbehandlung zu tun? Wenn ich bedenke, dass ich mit dem Ergebnis von '' read_to_string''' umgehen muss, wird es nicht zu einer verschachtelten Fehlerbehandlung kommen? – mnordber
Was idiomatisch wäre, denke ich, ist zuerst zu sehen, ob das 'try!' - Makro anwendbar ist (ich weiß nicht, ob es mit Iron's-Error-Typen und/oder der Signatur Ihrer Funktion ist.) Wenn nicht, ein guter Workaround wäre wie folgt zu strukturieren: 'let what_you_want = passt zu ... {...}' und 1. lasse den Ok-Zweig mit what_you_want 2. früh-Rückkehr vom Err-Zweig enden. Auf diese Weise können Sie weiter unten ohne Nesting weitermachen. Eigentlich ist das die Philosophie hinter "try!". – mdup
Ja, zuerst habe ich versucht, 'try!' Zu verwenden, aber es gab eine Art Kollision mit dem Iron-Paket.Ist die Lösung einfach "Versuch" zu verlassen oder kannst du das umgehen? Ich habe auch den Ansatz "let what_you_want = match" ausprobiert, endete aber in einem Durcheinander von Armen, die keine passenden Typen hatten. Was ist eine frühe Rückkehr? Summiert es einfach die Rendite? 'return Err (HttpError :: Io (err))'? Weil das Problem, das ich dann bekomme, ist, dass ich einen 'hyper :: error: Error' zurückgebe, aber es erwartet einen 'iron :: error :: IronError' ... – mnordber