.NETAnthropicC#Tutorial

Using the Anthropic Claude API in C#

How to call Anthropic's Claude models from C#: authenticate, send a message, stream the response, and use Claude through the provider-agnostic Microsoft.Extensions.AI abstraction.

OpenAI isn’t the only game in town. Anthropic’s Claude models are a strong choice for many workloads, and calling them from C# is straightforward. This guide covers authenticating, sending a message, streaming the reply, and — importantly for .NET teams — using Claude through a provider-agnostic abstraction so you can switch models without rewriting your app.

Getting a key

Create an API key in the Anthropic Console and store it in an environment variable — never in source:

setx ANTHROPIC_API_KEY "sk-ant-..."   # reopen the terminal afterwards

Option 1: Call the API directly

Anthropic’s Messages API is a simple HTTP endpoint. If a dedicated SDK version isn’t pinned for your project, you can call it with HttpClient:

using System.Net.Http.Json;

var http = new HttpClient();
http.DefaultRequestHeaders.Add("x-api-key", Environment.GetEnvironmentVariable("ANTHROPIC_API_KEY"));
http.DefaultRequestHeaders.Add("anthropic-version", "2023-06-01");

var body = new
{
    model = "claude-sonnet-4-5",
    max_tokens = 1024,
    messages = new[] { new { role = "user", content = "Explain the actor model in two sentences." } }
};

var res = await http.PostAsJsonAsync("https://api.anthropic.com/v1/messages", body);
var json = await res.Content.ReadFromJsonAsync<JsonElement>();
Console.WriteLine(json.GetProperty("content")[0].GetProperty("text").GetString());

The key differences from OpenAI’s shape: the x-api-key header (not a bearer token), the required anthropic-version header, and an explicit max_tokens.

For real apps, go through Microsoft.Extensions.AI’s IChatClient so Claude is just one interchangeable provider behind a common interface. Then the rest of your code — and any agent built on IChatClient — doesn’t care which model it’s talking to:

// Behind IChatClient, your app code is identical whether the model is Claude, GPT, or local.
IChatClient chat = /* an Anthropic-backed IChatClient */;

var response = await chat.GetResponseAsync("Summarize dependency injection for a junior dev.");
Console.WriteLine(response);

This is the same portability argument from choosing a model: swapping providers should be a config change, not a rewrite.

Streaming

For user-facing responses, stream tokens as they arrive rather than waiting for the whole reply. Both the direct API (via server-sent events) and the IChatClient streaming method support it — the pattern mirrors streaming responses to a web UI.

System prompts and multi-turn

Claude takes a top-level system parameter for behaviour, and you continue a conversation by appending prior turns to the messages array — the same mental model as other chat APIs. Keep the system prompt focused; a tight instruction outperforms a rambling one.

Note: model names (e.g. claude-sonnet-4-5) and SDK details change over time. Verify against the Anthropic API docs for current model IDs and any official .NET SDK; the approach — key + version headers, messages array, or IChatClient for portability — is stable.

Takeaway

Calling Claude from C# is a simple HTTP request with an x-api-key and anthropic-version header — or, better, a call through Microsoft.Extensions.AI so Claude is one swappable provider behind IChatClient. Build on the abstraction and you can compare Claude, GPT, and local models on your own eval set and pick the best fit per task without touching your app code.


Have a correction or a topic you want covered? Email mani.bc72@gmail.com.