Skip to the content.

curl PUT, DELETE and PATCH requests in C#

To send curl PUT, DELETE and PATCH requests in C#, pass -X <METHOD> in the command string to Curl.ExecuteAsync, with -d for the body where the method takes one. Every verb curl accepts works the same way, so the command from an API’s documentation can be used as-is.

PUT - replace a resource

using CurlDotNet;

var result = await Curl.ExecuteAsync(@"
    curl -X PUT https://httpbin.org/put \
         -H 'Content-Type: application/json' \
         -d '{""name"":""Ada"",""role"":""admin""}'");

Console.WriteLine(result.StatusCode);   // 200

PATCH - partial update

var result = await Curl.ExecuteAsync(@"
    curl -X PATCH https://httpbin.org/patch \
         -H 'Content-Type: application/json' \
         -d '{""role"":""editor""}'");

Console.WriteLine(result.Body);

DELETE

var result = await Curl.ExecuteAsync("curl -X DELETE https://httpbin.org/delete");

Console.WriteLine(result.IsSuccess ? "deleted" : $"HTTP {result.StatusCode}");

Many APIs answer DELETE with 204 No Content; IsSuccess is true for any 2xx and Body is empty.

Builder style

using CurlDotNet.Core;

var put = await CurlRequestBuilder.Put("https://httpbin.org/put")
    .WithJson(new { name = "Ada", role = "admin" })
    .ExecuteAsync();

var patch = await CurlRequestBuilder.Patch("https://httpbin.org/patch")
    .WithJson(new { role = "editor" })
    .ExecuteAsync();

var del = await CurlRequestBuilder.Delete("https://httpbin.org/delete").ExecuteAsync();
Console.WriteLine($"{put.StatusCode} {patch.StatusCode} {del.StatusCode}");

WithJson serialises the object and sets Content-Type: application/json. For a raw string body use WithData("..."), and for any other verb CurlRequestBuilder.Request("OPTIONS", url).

Reusable client

using CurlDotNet.Lib;

using var api = new LibCurl()
    .WithBearerToken(Environment.GetEnvironmentVariable("API_TOKEN"))
    .WithTimeout(TimeSpan.FromSeconds(15));

await api.PutAsync("https://httpbin.org/put", new { name = "Ada" });
await api.PatchAsync("https://httpbin.org/patch", new { role = "editor" });
var deleted = await api.DeleteAsync("https://httpbin.org/delete");
Console.WriteLine(deleted.StatusCode);

Object bodies on PutAsync/PatchAsync are sent as JSON.

Check the outcome

var result = await Curl.ExecuteAsync("curl -X DELETE https://httpbin.org/status/404");

if (!result.IsSuccess)
    Console.WriteLine($"Delete failed: {result.StatusCode} {result.Body}");

Without -f, HTTP errors are returned, not thrown. Call result.EnsureSuccess() if you prefer an exception, or add -f / --fail-with-body to the command to get CurlHttpReturnedErrorException (curl exit code 22).

Gotchas