
This article was written in 2021. Versions, tools and recommendations may have changed since then. Newer posts are collected under .NET.
While analyzing nearly 120 million requests, we noticed that one thing was dragging down our performance: parsing user agents for detecting bots and search engines.
For this task, we used the UA Parser library, which is quite widely used. Unfortunately, it is quite outdated, generates a lot of allocations and lowers our performance in its implementation.
1| Method | Mean | Error | StdDev | Gen 0 | Gen 1 | Gen 2 | Allocated |
2|-------------------- |-------------|-----------|-----------|---------|--------|-------|-----------|
3| 'UA Parser' | 3,238.59 us | 27.435 us | 25.663 us | 7.8125 | - | - | 168225 B |Since the alternatives are not really better, we decided to build our own parser: mycsharp/HttpUserAgentParser
During implementation, we paid special attention to the fact that this component could be part of a hot path of the application and therefore invested a lot in optimized performance. And our implementation lives up to this expectation in comparison!
1| Method | Mean | Error | StdDev | Gen 0 | Gen 1 | Gen 2 | Allocated |
2|-------------------- |-------------|-----------|-----------|---------|--------|-------|-----------|
3| 'UA Parser' | 3,238.59 us | 27.435 us | 25.663 us | 7.8125 | - | - | 168225 B |
4| UserAgentService | 391.11 us | 5.126 us | 4.795 us | 35.1563 | 3.4180 | - | 589664 B |
5| HttpUserAgentParser | 67.07 us | 0.740 us | 0.693 us | - | - | - | 848 B |As can be seen, we generate minimal allocations, but as the only implementation no GenX load at all!
Besides the implementation itself, we also created a caching component that checks respective browser agent strings for equality and thus very widely used agents only need to be parsed once.
We also provide a Dependency Injection registration for ASP.NET Core directly.
Related articles

- 11 min read
Containerizing .NET in 2026 Without a Dockerfile
Most .NET Dockerfiles repeat the same five steps: restore, publish, select the matching Microsoft runtime image, copy the output and start …

- 12 min read
Problem Details in ASP.NET Core and .NET 11
builder.Services.AddProblemDetails() registers infrastructure. It does not create an error contract. An ASP.NET Core request can fail during …

- 11 min read
Resilience in .NET with Microsoft.Extensions.Resilience
Retries are the most visible resilience strategy and the easiest one to misuse. Repeating a failing call can recover from a short network …
Let's Work Together
Looking for an experienced Platform Architect or Engineer for your next project? Whether it's cloud migration, platform modernization or building new solutions from scratch - I'm here to help you succeed.
