linebender/druid · error
Application is already running
Error message
Application is already running
What it means
`Application::run` panics if called on an `Application` instance that has already been run. The application tracks a `running` flag in a `RefCell`; calling `run` twice on the same instance would start a second platform event loop, which is invalid.
Solutions
- Create a fresh `Application` for each run instead of reusing the previous instance
- Restructure the code so `run` is called exactly once, from one code path
- If a restart is needed, spawn a new process rather than re-running the same `Application`
Example fix
// before let app = Application::new().unwrap(); app.run(None); app.run(None); // panics // after let app = Application::new().unwrap(); app.run(None); // once; make a new Application to run again
Defensive patterns
Strategy: type-guard
Validate before calling
// Track run state in the caller:
let mut has_run = false;
if !has_run { app.run(None); has_run = true; } Type guard
fn can_run(running: bool) -> bool { !running } Try / catch
// Rust panics are not catchable here by design; guard the call site:
if !app_has_run() { app.run(handler); } Prevention
- Call `Application::run` exactly once from the program entry point
- Never store and re-invoke the same `Application` for restarts
- Route restarts through spawning a new process or a fresh `Application`
When it happens
Trigger: Calling `app.run(handler)` a second time on the same `Application` value (or a clone/reborrow of it) after the first `run` set `state.running = true`.
Common situations: Restarting the app from a menu/callback by calling `run` again instead of creating a new `Application`; calling run in both a setup path and a main path.
Understand the failure class
Background: "Invalid state transition" errors: "status must be X, actually Y", "already rejected/charging/uninstalled", "cannot ... while running" — what they mean when a library rejects your call — this error's family across 31 libraries.
Related errors
- There is no globally active Application
- Application state already borrowed
- Tried to build a window without setting the handler
- Unwrap named called on unnamed FieldIdent
- unexpected wayland event
AI-assisted analysis of linebender/druid@0f8b1195e4 (2026-09-10).
Data as JSON: /api/errors/8f28d766fae576b4.
Report an issue: GitHub.
Appendix: source
Thrown at druid-shell/src/application.rs:131
util::assert_main_thread_or_main_unclaimed();
GLOBAL_APP.with(|global_app| global_app.borrow().clone())
}
/// Start the `Application` runloop.
///
/// The provided `handler` will be used to inform of events.
///
/// This will consume the `Application` and block the current thread
/// until the `Application` has finished executing.
///
/// # Panics
///
/// Panics if the `Application` is already running.
pub fn run(self, handler: Option<Box<dyn AppHandler>>) {
// Make sure this application hasn't run() yet.
if let Ok(mut state) = self.state.try_borrow_mut() {
if state.running {
panic!("Application is already running");
}
state.running = true;
} else {
panic!("Application state already borrowed");
}
// Run the platform application
self.backend_app.run(handler);
// This application is no longer active, so clear the global reference
GLOBAL_APP.with(|global_app| {
*global_app.borrow_mut() = None;
});
// .. and release the main thread
util::release_main_thread();
// .. and mark as done so a new sequence can start
APPLICATION_CREATED
.compare_exchange(true, false, Ordering::AcqRel, Ordering::Acquire)View on GitHub (pinned to 0f8b1195e4)