vercel/turborepo · warning
File watcher still initializing after {}s, likely a large fi
Error message
File watcher still initializing after {}s, likely a large file is slowing the initial hash.{}\nRetrying... What it means
Emitted by `turbo run --watch` while waiting for the file watcher's initial hashing pass to finish. If hashing has not completed after STARTUP_ATTEMPT seconds, turbo logs this warning (once) including a slowest_files_hint from the hash watcher, then keeps retrying until startup_cap elapses, at which point the run fails with Error::FileWatchingTimeout. It indicates large or slow-to-hash files in the watched tree, not a watcher crash. A broadcast lag during watching instead surfaces Error::PackageChangeLagged.
Source
Thrown at crates/turborepo-lib/src/run/watch.rs:448
let initial_event = loop {
match tokio::time::timeout(STARTUP_ATTEMPT, events.recv()).await {
Ok(Ok(event)) => break event,
Ok(Err(broadcast::error::RecvError::Closed)) => {
return Err(Error::PackageChangeClosed)
}
Ok(Err(broadcast::error::RecvError::Lagged(_))) => {
return Err(Error::PackageChangeLagged)
}
Err(_) => {
if started.elapsed() >= startup_cap {
return Err(Error::FileWatchingTimeout(
startup_cap.as_secs(),
slowest_files_hint(&self._watching.hash_watcher.slowest_files()),
));
}
if !warned {
warned = true;
turborepo_log::warn(
turborepo_log::Source::turbo(turborepo_log::Subsystem::Run),
format!(
"File watcher still initializing after {}s, likely a large file \
is slowing the initial hash.{}\nRetrying...",
STARTUP_ATTEMPT.as_secs(),
slowest_files_hint(&self._watching.hash_watcher.slowest_files())
),
)
.emit();
}
}
}
};
let signal_subscriber = self.handler.subscribe().ok_or(Error::NoSignalHandler)?;
let pending_changes = Mutex::new(ChangedPackages::default());
let notify_run = Arc::new(Notify::new());View on GitHub (pinned to f9245100cf)
Solutions
- Check the slowest-files hint printed with the warning and add those files/directories to .gitignore (or .turboignore / turbo.json `inputs`) so the watcher skips them
- Move or shrink large generated artifacts out of the watched tree
- Wait it out: turbo retries automatically and only aborts once startup_cap elapses
- Run watch mode on a local filesystem instead of network storage
Example fix
# before: .gitignore does not exclude heavy artifacts # (assets/*.psd hashed at startup, watcher lags) # after: .gitignore *.psd *.mp4 dist-artifacts/
Defensive patterns
Strategy: retry
Validate before calling
# Before starting watch mode, find files likely to slow the initial hash: find . -type f -size +50M -not -path './node_modules/*' -not -path './.git/*' -not -path '*/.turbo/*' # gitignore or move whatever shows up before running `turbo run --watch`
Type guard
// Rust (embedding the turbo crates):
fn is_file_watching_timeout(e: &turborepo_lib::Error) -> bool {
matches!(e, turborepo_lib::Error::FileWatchingTimeout(_, _))
} Try / catch
// Rust: surface the slow-file hint, let the operator fix ignores, retry once
match result {
Err(Error::FileWatchingTimeout(secs, hint)) => {
eprintln!("watch startup timed out after {secs}s: {hint}");
// add offenders to .gitignore, then retry the run
}
Err(Error::PackageChangeLagged) => { /* watcher fell behind; restart watch mode */ }
other => other?,
} Prevention
- Keep large binaries and generated artifacts out of the repo (gitignore them) so the watcher never hashes them
- Prefer local SSD-backed filesystems for --watch; network mounts drastically slow hashing
- Scope task `inputs` in turbo.json so huge directories are not part of the hashed set
- Act on the slowest-files hint immediately — after startup_cap the warning becomes a hard FileWatchingTimeout error
When it happens
Trigger: Running `turbo <tasks> --watch` when the initial hash of watched files exceeds STARTUP_ATTEMPT seconds: very large files (binaries, media, bundled assets), directories not excluded by .gitignore, or slow filesystems (network mounts, containers). The warning fires on the Err(_) arm of the watcher readiness select loop before the startup_cap deadline turns into a hard FileWatchingTimeout error.
Common situations: Monorepos with committed build artifacts or media; watch runs inside Docker or on NFS; the first watch after cloning a big repo; generated directories that turbo hashes because they are not gitignored.
Related errors
- {message}
- Found both turbo.json and turbo.jsonc in the same directory:
- Found both turbo.json and turbo.jsonc in the same directory:
- refusing to write structured log to symlink: {}
- error creating log file directory: {err:?}
AI-assisted analysis of vercel/turborepo@f9245100cf (2026-08-17).
Data as JSON: /api/errors/afb9b7d7591319cc.
Report an issue: GitHub.