avoid_throw_in_catch_block
v0.4.0 Warning Fix Control Flow
Warns when a throw expression is used inside a catch block. Throwing a new exception (or re-throwing the caught one with throw e) discards the original stack trace, making debugging significantly harder. Use rethrow or Error.throwWithStackTrace() instead.
Why use this rule
Section titled “Why use this rule”When you use throw inside a catch block, the original stack trace is lost. This means error reports and logs will point to the catch block instead of the actual source of the error. Using rethrow preserves the full stack trace, and Error.throwWithStackTrace() lets you throw a different exception while keeping the original stack trace attached.
See also: Exceptions
void bad() { // throw loses original stack trace try { networkDataProvider(); } on Object { throw RepositoryException(); }
// throw with caught exception still loses stack trace try { networkDataProvider(); } catch (e) { throw e; }
// throw with logic before it try { networkDataProvider(); } catch (e) { print(e); throw RepositoryException('failed'); }}void good() { // Use Error.throwWithStackTrace to preserve the stack trace try { networkDataProvider(); } catch (_, stack) { Error.throwWithStackTrace(RepositoryException(), stack); }
// Use rethrow to re-throw the original exception try { networkDataProvider(); } catch (e) { print(e); rethrow; }
// Throw inside a closure is fine — it's not in the catch scope try { networkDataProvider(); } catch (e) { final callback = () { throw RepositoryException(); }; callback(); }}Configuration
Section titled “Configuration”To disable this rule:
plugins: many_lints: diagnostics: avoid_throw_in_catch_block: false