fix: Address security audit findings - #369
Conversation
use() on a catch-all was skipped for the prefix itself, so /api bypassed the middleware that /api/keys ran.
The unanchored regexes backtracked quadratically, wedging the isolate on a long value. Text between auth-params is now rejected, not skipped.
Sections were materialised before the response returned, and the count was unbounded, so a short request could ask for many times the file size.
Random().nextInt(1000000) gave ~20 bits, so boundaries repeated within a few thousand responses.
Returning the future from inside the try skipped the catch, so a failed response write left the connection open and the client waiting.
Rejects CR, LF and NUL where every header write funnels, so the defence is Relic own rather than inherited from dart:io.
No such check exists. The page now says every file in the directory is served, including dot files.
The host was only segment 0 of a flat string, so a path resolving upwards could pop it and select another virtual host.
Decoding first turned %2F into a separator no upstream proxy ever saw. NormalizedPath.fromUri names the safe conversion.
Refuse a mismatched Origin with 403; opt out with allowAnyOrigin. Only the host is compared, since a TLS-terminating proxy changes scheme and port. Breaking for apps relying on cross-origin sockets.
Emitted through ParameterValue, so a quote in a filename can no longer end the value and append a filename*. Parsing is now quote-aware too, or Relic could not read its own output.
An unescaped realm could close its value and graft a second challenge onto the response.
io.ContentType takes the parts separately, so they bypassed the CR/LF check dart:io applies to ordinary header values.
|
Important Review skippedAuto reviews are disabled on this repository. Please check the settings in the CodeRabbit UI or the ⚙️ Run configurationConfiguration used: Repository UI Review profile: CHILL Plan: Pro Plus Run ID: You can disable this status message by setting the Use the checkbox below for a quick retry:
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
Codecov Report❌ Patch coverage is Additional details and impacted files@@ Coverage Diff @@
## main #369 +/- ##
==========================================
- Coverage 92.53% 92.35% -0.19%
==========================================
Files 108 109 +1
Lines 4544 4655 +111
Branches 2310 2355 +45
==========================================
+ Hits 4205 4299 +94
- Misses 339 356 +17
Flags with carried forward coverage won't be shown. Click here to find out more. ☔ View full report in Codecov by Harness. 🚀 New features to boost your workflow:
|
Hijacking and upgrading detach the connection from the underlying server, which then reports and closes nothing, so a hijacked socket survived close(force: true) and connectionsInfo() could not show it. Track them in the adapter: a forced close destroys them, a graceful close drains, sends 1001 to WebSocket peers, then closes the rest after a bounded wait. 40 hijack cycles ignoring the socket leaked 80 sockets before, none after.
The teardown closed with a 5s timeout and, on timeout, retried close with none, so a shutdown that could not complete hung the suite instead of reporting it. Close forcefully once: this test deliberately leaves the hijacked connection open. The timeout expectation was also never awaited, so it raced the teardown.
b904b85 to
4e72de3
Compare
No description provided.