Best Practices
Here we combine best practices for writing HTTP load tests, along with useful links and important considerations. All the practices mentioned below are also applicable to RestSharp.
Blog posts
Choose the right workload
Please make sure to choose the right workload for your load tests. We recommend reviewing the following documentation:
Using HttpClient correctly
Using HttpClient (or RestSharp client) properly is crucial for performance, reliability, and avoiding resource exhaustion. Here are best practices when working with HttpClient. All the practices mentioned below are also applicable to RestSharp.
Reuse HttpClient instance
Avoid creating a new instance per request. Creating and disposing HttpClient frequently can exhaust available sockets under heavy load. You can read more about this problem in this article: You are using HttpClient wrong. The basic recommendations are:
- Avoid creating a new instance per request.
- It is a good practice to reuse a single HttpClient instance per Scenario.
- If you need a separate HttpClient per virtual user (e.g., for cookie management), consider attaching it to the scenario instance via
context.ScenarioInstanceData
. We describe this approach in Dedicated HttpClient Per User Session. - Avoid disposing of HttpClient frequently, as it's a costly operation and can lead to socket exhaustion issues. It’s better not to dispose of it during the load test.
Example of incorrect usage: Creating a new HttpClient for each request and disposing it afterward can exhaust available sockets under high load, leading to degraded performance or even failures.
var scenario = Scenario.Create("my scenario", async context =>
{
using var httpClient = Http.CreateDefaultClient();
var request = Http.CreateRequest("GET", "https://nbomber.com")
var response = await Http.Send(httpClient, request);
...
});
Example of correct usage: Reuse a shared HttpClient instance for all requests. This approach creates a single HttpClient and reuses it for all concurrent requests within one scenario.
var httpClient = Http.CreateDefaultClient();
var scenario = Scenario.Create("my scenario", async context =>
{
var request = Http.CreateRequest("GET", "https://nbomber.com")
var response = await Http.Send(httpClient, request);
...
});
Dedicated HttpClient Per User Session
There may be cases where you need to create a separate HttpClient instance for each user session — such as when managing cookies, authentication headers, or maintaining session-specific state.
In such cases, we recommend attaching the created HttpClient instance to the scenario's ScenarioInstanceData
, which represents the current user session.
var scenario = Scenario.Create("cookies_management_scenario", async context =>
{
HttpClient myClient = null;
context.ScenarioInstanceData.TryGetValue("my_http_client", out var httpClient);
if (httpClient is null)
{
myClient = Http.CreateDefaultClient();
var login = await Step.Run("login", context, async () =>
{
// WebAppSimulator address
var request = Http.CreateRequest("POST", "https://localhost:65385/api/CookiesAuthentication")
.WithJsonBody(new StringContent("""{"login": "morpheus","password": "leader"}"""));
var response = await Http.Send(myClient, request);
return response;
});
context.ScenarioInstanceData["my_http_client"] = myClient;
}
else
myClient = (HttpClient)httpClient;
var getData = await Step.Run("get_data", context, async () =>
{
var request = Http.CreateRequest("GET", "https://localhost:65385/api/CookiesAuthentication");
var response = await Http.Send(myClient, request);
return response;
});
return Response.Ok();
})
You can find the complete example by this link.