BoundaryML/baml · warning · LspError
-32803
-32803
Error message
LSP outbound sink is saturated
What it means
LspError::OutboundSaturated indicates bounded-transport backpressure: the outbound sink's buffer is full, so the server cannot immediately send a message. It maps to LSP RequestFailed error code -32803. Backpressure is a flow-control signal, not data corruption.
Solutions
- Retry the send after yielding (the sink may drain shortly); or await capacity asynchronously
- Coalesce/dedupe diagnostics so fewer messages are sent
- Increase the outbound channel capacity if the transport is legitimately undersized
Example fix
// before
sink.send(msg)?; // saturates under diagnostic bursts
// after (retry with yield)
for _ in 0..3 {
match sink.try_send(msg.clone()) {
Ok(()) => break,
Err(LspError::OutboundSaturated) => tokio::time::yield_now().await,
Err(e) => return Err(e),
}
} Defensive patterns
Strategy: retry
Type guard
fn is_saturated(e: &LspError) -> bool {
matches!(e, LspError::OutboundSaturated)
} Try / catch
loop {
match sink.try_send(msg.clone()) {
Ok(()) => break,
Err(LspError::OutboundSaturated) => tokio::time::sleep(Duration::from_millis(10)).await,
Err(e) => return Err(e),
}
} Prevention
- Coalesce diagnostics before publishing instead of sending per keystroke
- Use an async send that awaits capacity rather than try_send
- Size the outbound channel generously relative to diagnostic burst rate
When it happens
Trigger: Sending responses/notifications faster than the client drains the bounded channel; a burst of diagnostics or a large publishDiagnostics after a batch edit filling the sink capacity.
Common situations: Publishing diagnostics for every keystroke on a large project; slow or stalled client (frozen editor UI); misconfigured tiny sink buffer.
Related errors
- {0}
- all ingress capacities and the response reservation must be…
- Client closed
- combined normal and reserved capacity overflowed usize
- could not start the playground server
AI-assisted analysis of BoundaryML/baml@bd85ce9dee (2026-09-12).
Data as JSON: /api/errors/dbb1b6be7a451811.
Report an issue: GitHub.
Appendix: source
Thrown at baml_language/crates/baml_lsp/src/error.rs:25
/// Serialized to the wire exclusively through [`LspError::to_response_error`];
/// the legacy `-32001 UnknownErrorCode` is never emitted.
#[derive(Debug, thiserror::Error)]
pub enum LspError {
#[error("{0}")]
NotificationExtractError(lsp_server::ExtractError<lsp_server::Notification>),
#[error("Notification not supported: {0}")]
NotificationNotSupported(String),
#[error("{0}")]
RequestExtractError(lsp_server::ExtractError<lsp_server::Request>),
#[error("Request not supported: {0}")]
RequestNotSupported(String),
#[error("Failed to serialize request result: {0}")]
RequestSerializeError(serde_json::Error),
/// The client's sink is gone; nothing more can be delivered.
#[error("Client closed")]
ClientClosed,
/// Bounded transport backpressure (LSP `RequestFailed`, `-32803`).
#[error("LSP outbound sink is saturated")]
OutboundSaturated,
/// A frame larger than the transport limit (LSP `RequestFailed`,
/// `-32803`).
#[error("LSP outbound frame exceeds the transport limit")]
OutboundOversized,
#[error("Invalid command arguments for command: {command}: {message}")]
InvalidCommandArguments { command: String, message: String },
#[error("File not found: {}", .0.display())]
FileNotFound(PathBuf),
#[error("Path is invalid: {}: {message}", path.display())]
InvalidPath { path: PathBuf, message: String },
/// The document's path is under no known source root.
#[error("No source root contains {}", .0.display())]
NoRootForPath(PathBuf),
/// Cancellation claimed the response while the request was queued or
/// running (LSP `RequestCanceled`, `-32800`).
#[error("Request canceled: {0}")]
RequestCanceled(String),View on GitHub (pinned to bd85ce9dee)