Repository navigation
fix: keep whole SIP messages out of WARN logs - #178
Merged
shenjinti merged 1 commit intoOct 7, 2026
Merged
Conversation
Some WARN records carried a whole SIP message, with the From/To/Contact URIs, display names and any body: - the dialog layer's "failed to send request" (send_prack_request and send_dialog_request) printed the full request; - the WebSocket transport's "Error parsing SIP message" printed the raw text frame; - the "bye skipped" WARN of ClientInviteDialog, InviteDialog and ServerInviteDialog printed the dialog state with Debug, which for Early, WaitAck and Confirmed includes the whole response; the returned error did the same. The send failure now logs the method at WARN and the request at DEBUG. The WebSocket parse failure logs the frame length; the frame is already logged at INFO when it is received. The BYE paths use the Display of DialogState (dialog id and state name).
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Fixes #177.
Problem
Some WARN records print a whole SIP message, with the From/To/Contact URIs, display names and the body:
DialogInner::send_prack_requestandsend_dialog_requestprint the whole request whentx.send()fails (src/dialog/dialog.rs:707,tx.originalat line 712;dialog.rs:1153,req = %tx.originalat line 1156).WebSocketConnection::serve_loopprints the raw text frame when it does not parse (src/transport/websocket.rs:343).ClientInviteDialog,InviteDialogandServerInviteDialog(client_dialog.rs:163,invite_dialog.rs:430,server_dialog.rs:357) logsstate = ?self.state(), and the returned error formats the state with{:?}.DialogState::Early,WaitAckandConfirmedhold the wholeResponse(dialog.rs:117-119), andDebugprints it.WARN usually goes to production logs, and those fields are personal data (phone numbers, user names, SDP addresses).
Fix
id,destination, the error) and addsmethod; the request is logged right after it at DEBUG ("request that failed to send", withidandreq).leninstead of the frame. The frame is already logged at INFO when it is received (websocket.rs:323), so nothing new is needed at DEBUG. This is how the binary-frame branch (websocket.rs:367) and the UDP transport (udp.rs:184, at DEBUG) already behave.DisplayofDialogState(dialog.rs:1642), which prints the dialog id and the state name (<id>(Early)) and never the embedded message.Contract / coverage
What each WARN contains now:
"failed to send request error: <error>":id(the dialog id: Call-ID, local and remote tag),destination(transport and host:port, when known),method. The Call-ID and tags were already in this WARN and are kept: they are the identifiers an operator needs to find the call, and they carry no URI or display name. The error is the transaction's ownDisplay; the in-tree send errors name an address or a transaction key, never the request (a customTargetLocatorcontrols the text of its own error)."Error parsing SIP message"(WebSocket text frame):error,src,len. The parser's error can quote the start-line token it rejected (for exampleinvalid method: NOT), as the binary-frame branch and the stream transport already log; not changed here."bye skipped: ...":dialog_id,stateas<id>(<State>).Full messages are still logged where they were, below WARN: the failed request at DEBUG next to its WARN, received WebSocket text at INFO, sent and received messages in the transports at INFO.
Behaviour change: the error returned by
bye_with_headers(andbye) on a dialog that is not confirmed readsdialog <id> cannot send BYE in state <id>(Early)instead of theDebugdump. No caller in the repository matches on it.Checked and not changed: every other
warn!/error!insrc/. None prints a message or a type whoseDebugembeds one (DialogSnapshotStateandTransactionStateare plain enums;SendError'sDebugomits its payload).Tests
New
src/dialog/tests/test_warn_logs.rs, with a small capturingtracing::Subscriber(the crate has notracing-subscriberdev-dependency;tracing-subscriberis only enabled by thebenchfeature). Each test puts a marker in the From display name and URI user part and asserts that the WARN does not contain it:test_failed_request_send_warns_without_the_request: a UAC dialog on an endpoint whoseTargetLocatoralways fails. An INFO throughdo_request(send_dialog_request) and a PRACK throughsend_prack_requesteach give one WARN withmethod=INFO/method=PRACKand without the marker, and one DEBUG record with it.test_bye_in_early_state_warns_without_the_response: the dialog inEarlywith a 180 carrying the marker;bye()onClientInviteDialog,InviteDialogandServerInviteDialogeach fails with an error that reads(Early)and has no marker, and the three WARNs have none.test_websocket_parse_failure_warns_without_the_message(websocketfeature): a WebSocket server sends one unparsable text frame toWebSocketConnection::serve_loop. The WARN haslenand no marker; the INFO record of the received frame still has it.On
main(5ef8ea6) all three fail:Checks
cargo test --features bench: 388 lib tests passed, 0 failed (385 onmainplus the three new ones), and 65 doc tests passed. Plaincargo testpasses too.cargo check --no-default-features --features platform-embassy: no warnings, as onmain.cargo clippy --features bench --all-targets: the same output as onmain, none in the changed code. (Onmainit stops at aclippy::never_looperror insrc/dialog/tests/test_refer_notify.rs:98, unrelated to this PR.)rustfmt --checkon the changed files: clean.