Skip to content

[Repo Assist] Use HttpClient with SocketsHttpHandler on .NET 8+ to avoid socket exhaustion#1667

Closed
github-actions[bot] wants to merge 2 commits intomainfrom
repo-assist/fix-issue-1392-httpclient-net8-99e87a498347caf7
Closed

[Repo Assist] Use HttpClient with SocketsHttpHandler on .NET 8+ to avoid socket exhaustion#1667
github-actions[bot] wants to merge 2 commits intomainfrom
repo-assist/fix-issue-1392-httpclient-net8-99e87a498347caf7

Conversation

@github-actions
Copy link
Contributor

🤖 This is an automated pull request from Repo Assist, an AI assistant for this repository.

Implements @dsyme's request from #1392 — use System.Net.Http.HttpClient on .NET 8+ to address socket exhaustion and modernise the HTTP implementation.

Closes #1392

What changed

FSharp.Data.Http now multi-targets netstandard2.0;net8.0. On the net8.0 target, all Http.Request* / Http.AsyncRequest* calls go through a shared HttpClient backed by a SocketsHttpHandler:

Setting Value Reason
PooledConnectionLifetime 2 minutes Avoids stale DNS entries while reusing connections
AutomaticDecompression GZip + Deflate + Brotli Same as before, plus Brotli support
UseCookies false Cookies are managed manually (existing CookieContainer logic reused)
AllowAutoRedirect true Matches existing behaviour

The HttpWebRequest path is fully preserved for:

  • netstandard2.0 (unchanged)
  • Any .NET 8+ call that supplies customizeHttpRequest (backwards-compatible fallback)

Backward-compatibility notes

  • customizeHttpRequest: HttpWebRequest -> HttpWebRequest still works on all TFMs (falls back to HttpWebRequest on .NET 8+)
  • Timeout exceptions are wrapped as WebException(Status=Timeout) on the HttpClient path
  • Duplicate-header validation is preserved on the HttpClient path
  • Cookie handling is equivalent: cookies from CookieContainer and explicit cookies parameter are combined into a Cookie header

Test status

All existing tests pass — 2846/2847 (1 pre-existing network-blocked test unrelated to this change).

Build: netstandard2.0 ✅ · net8.0

Generated by Repo Assist

To install this agentic workflow, run

gh aw add githubnext/agentics/workflows/repo-assist.md@69c1ee19e39e6aaba35519aafefb5cbf314de323

Warning

⚠️ Firewall blocked 1 domain

The following domain was blocked by the firewall during workflow execution:

  • www.google.com

…austion

On .NET 8+, Http.Request and friends now use a shared System.Net.Http.HttpClient
backed by a SocketsHttpHandler with:
- PooledConnectionLifetime = 2 minutes (to handle DNS changes)
- AutomaticDecompression = GZip | Deflate | Brotli
- UseCookies = false (cookies handled manually, matching existing behaviour)
- AllowAutoRedirect = true

The HttpWebRequest path is preserved for netstandard2.0 and for any .NET 8+
call that provides customizeHttpRequest (for backward compatibility).

Timeout exceptions are wrapped as WebException(Status=Timeout) for compat.
Duplicate-header checking is preserved on the new code path.

Closes #1392

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
@dsyme dsyme marked this pull request as ready for review February 26, 2026 14:00
@dsyme
Copy link
Contributor

dsyme commented Feb 26, 2026

Closing as seems too invasive for now

@dsyme dsyme closed this Feb 26, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Use System.Net.Http.HttpClient

1 participant