rust / expert
Snippet
Isolierte Panic-Erfassung und Hook-Testen
Das Testen von Panic-Verhalten in Standard-Rust erfordert das Abfangen des Output-Hooks und das sichere Einbetten der Ausführung in std::panic::catch_unwind.
snippet.rs
rust
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
use std::panic::{catch_unwind, set_hook, take_hook, AssertUnwindSafe};use std::sync::atomic::{AtomicBool, Ordering};use std::sync::Arc;pub fn test_panic_resilience<F>(f: F) -> Result<(), String>whereF: FnOnce() + Send + 'static,{let hook_called = Arc::new(AtomicBool::new(false));let hook_flag = Arc::clone(&hook_called);let prev_hook = take_hook();set_hook(Box::new(move |_info| {hook_flag.store(true, Ordering::SeqCst);}));let result = catch_unwind(AssertUnwindSafe(f));set_hook(prev_hook);if result.is_err() && hook_called.load(Ordering::SeqCst) {Ok(())} else {Err("Expected thread panic was not triggered or caught".to_string())}}
Erklärung
1
pub fn test_panic_resilience<F>(f: F) -> Result<(), String>
Test-Runner höherer Ordnung, der eine Closure akzeptiert, um Panic-Auslösung zu validieren.
2
let prev_hook = take_hook();
Speichert den bestehenden globalen Panic-Handler vor der Registrierung des eigenen Hooks.
3
let result = catch_unwind(AssertUnwindSafe(f));
Führt Closure aus und fängt Unwinding-Thread-Panics ohne Prozessabbruch ab.
4
set_hook(prev_hook);
Stellt den ursprünglichen globalen Panic-Hook wieder her, um einen sauberen Zustand zu wahren.