# Deepgram .NET SDK
[](https://www.nuget.org/packages/Deepgram)
[](https://github.com/deepgram-devs/deepgram-dotnet-sdk/actions?query=CI)
[](./.github/CODE_OF_CONDUCT.md)
[](https://discord.gg/deepgram)
Official .NET SDK for [Deepgram](https://www.deepgram.com/).
Power your apps with world-class speech and Language AI models.
- [Deepgram .NET SDK](#deepgram-net-sdk)
- [Documentation](#documentation)
- [Requirements](#requirements)
- [Installation](#installation)
- [Getting an API Key](#getting-an-api-key)
- [Initialization](#initialization)
- [Pre-Recorded (Synchronous)](#pre-recorded-synchronous)
- [Remote Files (Synchronous)](#remote-files-synchronous)
- [Local Files (Synchronous)](#local-files-synchronous)
- [Pre-Recorded (Asynchronous / Callbacks)](#pre-recorded-asynchronous--callbacks)
- [Remote Files (Asynchronous)](#remote-files-asynchronous)
- [Local Files (Asynchronous)](#local-files-asynchronous)
- [Streaming Audio](#streaming-audio)
- [Flux - Conversational Speech Recognition (Preview)](#flux---conversational-speech-recognition-preview)
- [Flux Text to Speech](#flux-text-to-speech)
- [Voice Agent](#voice-agent)
- [Text to Speech REST](#text-to-speech-rest)
- [Text to Speech Streaming](#text-to-speech-streaming)
- [Text Intelligence](#text-intelligence)
- [Authentication](#authentication)
- [Grant Token](#grant-token)
- [Projects](#projects)
- [Get Projects](#get-projects)
- [Get Project](#get-project)
- [Update Project](#update-project)
- [Delete Project](#delete-project)
- [Keys](#keys)
- [List Keys](#list-keys)
- [Get Key](#get-key)
- [Create Key](#create-key)
- [Delete Key](#delete-key)
- [Members](#members)
- [Get Members](#get-members)
- [Remove Member](#remove-member)
- [Scopes](#scopes)
- [Get Member Scopes](#get-member-scopes)
- [Update Scope](#update-scope)
- [Invitations](#invitations)
- [List Invites](#list-invites)
- [Send Invite](#send-invite)
- [Delete Invite](#delete-invite)
- [Leave Project](#leave-project)
- [Usage](#usage)
- [Get All Requests](#get-all-requests)
- [Get Request](#get-request)
- [Get Fields](#get-fields)
- [Get Usage Breakdown](#get-usage-breakdown)
- [Billing](#billing)
- [Get All Balances](#get-all-balances)
- [Get Balance](#get-balance)
- [Models](#models)
- [Get All Project Models](#get-all-project-models)
- [Get Model](#get-model)
- [Self-Hosted Distribution Credentials](#self-hosted-distribution-credentials)
- [Logging](#logging)
- [Backwards Compatibility](#backwards-compatibility)
- [Development and Contributing](#development-and-contributing)
- [Getting Help](#getting-help)
## Documentation
You can learn more about the Deepgram API at [developers.deepgram.com](https://developers.deepgram.com/docs).
The repository's maintained [code documentation corpus](docs/codedocs/README.md) covers the current SDK surface used by Context7.
## Requirements
This SDK supports the following versions:
- .NET 8.0
- .NET Standard 2.0
## Installation
To install the latest version of the .NET SDK using [NuGet](https://www.nuget.org/),
run the following command from your terminal in your project's directory:
```bash
dotnet add package Deepgram
```
Or use the [NuGet package Manager](https://learn.microsoft.com/en-us/nuget/consume-packages/install-use-packages-visual-studio).
Right click on project and select manage NuGet packages.
## Getting an API Key
🔑 To access the Deepgram API, you will need a
[free Deepgram API Key](https://console.deepgram.com/signup?jump=keys).
## Initialization
All of the examples below will require initializing the Deepgram client
and inclusion of imports.
```csharp
using Deepgram;
using Deepgram.Models.Listen.v1.REST;
using Deepgram.Models.Speak.v1.REST;
using Deepgram.Models.Analyze.v1;
using Deepgram.Models.Manage.v1;
using Deepgram.Models.Authenticate.v1;
// Initialize Library with default logging
Library.Initialize();
// Create client using the client factory
var deepgramClient = ClientFactory.CreateListenRESTClient();
```
## Pre-Recorded (Synchronous)
### Remote Files (Synchronous)
Transcribe audio from a URL.
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var deepgramClient = ClientFactory.CreateListenRESTClient();
// Define Deepgram Options
var response = await deepgramClient.TranscribeUrl(
new UrlSource("https://static.deepgram.com/examples/Bueller-Life-moves-pretty-fast.wav"),
new PreRecordedSchema()
{
Model = "nova-3",
});
// Writes to Console
Console.WriteLine($"Transcript: {response.Results.Channels[0].Alternatives[0].Transcript}");
```
[See our API reference for more info](https://developers.deepgram.com/reference/speech-to-text-api/listen).
[See the Example for more info](./examples/speech-to-text/rest/url/).
### Local Files (Synchronous)
Transcribe audio from a file.
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var deepgramClient = ClientFactory.CreateListenRESTClient();
// Check if file exists
if (!File.Exists("audio.wav"))
{
Console.WriteLine("Error: File 'audio.wav' not found.");
return;
}
// Define Deepgram Options
var audioData = File.ReadAllBytes("audio.wav");
var response = await deepgramClient.TranscribeFile(
audioData,
new PreRecordedSchema()
{
Model = "nova-3",
});
// Writes to Console
Console.WriteLine($"Transcript: {response.Results.Channels[0].Alternatives[0].Transcript}");
```
[See our API reference for more info](https://developers.deepgram.com/reference/speech-to-text-api/listen).
[See the Example for more info](./examples/speech-to-text/rest/file/).
## Pre-Recorded (Asynchronous / Callbacks)
### Remote Files (Asynchronous)
Transcribe audio from a URL with callback.
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var deepgramClient = ClientFactory.CreateListenRESTClient();
// Define Deepgram Options
var response = await deepgramClient.TranscribeUrl(
new UrlSource("https://static.deepgram.com/examples/Bueller-Life-moves-pretty-fast.wav"),
new PreRecordedSchema()
{
Model = "nova-3",
CallBack = "https://your-callback-url.com/webhook",
});
// Writes to Console
Console.WriteLine($"Request ID: {response.RequestId}");
```
[See our API reference for more info](https://developers.deepgram.com/reference/speech-to-text-api/listen).
### Local Files (Asynchronous)
Transcribe audio from a file with callback.
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var deepgramClient = ClientFactory.CreateListenRESTClient();
var audioData = File.ReadAllBytes("audio.wav");
var response = await deepgramClient.TranscribeFile(
audioData,
new PreRecordedSchema()
{
Model = "nova-3",
CallBack = "https://your-callback-url.com/webhook",
});
Console.WriteLine($"Request ID: {response.RequestId}");
```
[See our API reference for more info](https://developers.deepgram.com/reference/speech-to-text-api/listen).
### Callback method compatibility
`PreRecordedSchema.CallbackMethod` is a legacy Boolean property, so it cannot name an HTTP
method: setting it sends `callback_method=true` or `callback_method=false`. Leave it unset to
get the default `POST` callback.
## Streaming Audio
Transcribe streaming audio.
```csharp
using Deepgram;
using Deepgram.Models.Listen.v2.WebSocket;
using Deepgram.Models.Speak.v2.WebSocket;
using Deepgram.Models.Agent.v2.WebSocket;
// Initialize Library with default logging
Library.Initialize();
// Create WebSocket client
var liveClient = ClientFactory.CreateListenWebSocketClient();
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
// Subscribe to transcription results
await liveClient.Subscribe(new EventHandler<ResultResponse>((sender, e) =>
{
if (!string.IsNullOrEmpty(e.Channel.Alternatives[0].Transcript))
{
Console.WriteLine($"Transcript: {e.Channel.Alternatives[0].Transcript}");
}
}));
// Print every server Error, including rejected Configure updates.
await liveClient.Subscribe(
new EventHandler<Deepgram.Models.Listen.v2.WebSocket.ErrorResponse>((sender, e) =>
{
Console.Error.WriteLine($"{e.Variant} {e.Code}: {e.Description}");
}));
// Connect to Deepgram
var liveSchema = new LiveSchema()
{
Model = "nova-3",
};
await liveClient.Connect(liveSchema);
// Update keyterms or features on an open stream without reconnecting. Keyterm updates work on
// Nova-3 on api.deepgram.com, not yet on the EU, Australia, or India hosts. Keyterms replace the
// active list; an empty list clears it. Keep each update under 500 tokens: an over-limit update
// returns no Error, transcription stops, and the stream closes with 1011 (NET-0000).
// Success has no acknowledgement; most rejections arrive as an Error. Details:
// https://developers.deepgram.com/docs/configure
await liveClient.SendConfigure(new ConfigureSchema
{
Keyterms = new List<string> { "Deepgram" },
Features = new Dictionary<string, bool> { ["numerals"] = true },
});
// Stream audio data to Deepgram
byte[] audioData = GetAudioData(); // Your audio source
liveClient.Send(audioData);
// Keep connection alive while streaming
await Task.Delay(TimeSpan.FromSeconds(30));
// Stop the connection
await liveClient.Stop();
```
### WebSocket handshake errors
Set `ThrowDeepgramWebSocketExceptions` to `true` on `DeepgramWsClientOptions` to receive a
`DeepgramWebSocketException`, with the original `WebSocketException` as its inner exception and
an inspectable `HttpStatusCode`, when a WebSocket upgrade is rejected with an HTTP response. This
flag defaults to `false` in 7.x, so `Connect` keeps throwing the raw `WebSocketException` unless
you opt in; the default changes in the next major version.
```csharp
using System.Net;
using Deepgram;
using Deepgram.Models.Authenticate.v1;
using Deepgram.Models.Exceptions.v1;
using Deepgram.Models.Listen.v2.WebSocket;
var options = new DeepgramWsClientOptions
{
ThrowDeepgramWebSocketExceptions = true,
};
var liveClient = ClientFactory.CreateListenWebSocketClient(options: options);
var liveSchema = new LiveSchema
{
Model = "nova-3",
};
try
{
await liveClient.Connect(liveSchema);
}
catch (DeepgramWebSocketException exception)
when (exception.HttpStatusCode == HttpStatusCode.TooManyRequests)
{
// Back off or reduce concurrent self-hosted requests.
}
```
[See our API reference for more info](https://developers.deepgram.com/reference/speech-to-text-api/listen-streaming).
[See the Examples for more info](./examples/speech-to-text/websocket/).
## Flux - Conversational Speech Recognition (Preview)
> Flux support is currently in preview. The API surface may change in a future release.
Transcribe conversational audio with contextual turn detection using [Deepgram Flux](https://developers.deepgram.com/docs/flux/quickstart). Instead of interim/final results, Flux delivers `TurnInfo` events that track the turn lifecycle (`StartOfTurn`, `Update`, `EagerEndOfTurn`, `TurnResumed`, `EndOfTurn`) — ideal for voice agents that need to know when a speaker is done talking.
Flux accepts only three control messages (`CloseStream`, `Configure`, and `ForceEndTurn`); the classic streaming `KeepAlive`/`Finalize` messages do not apply. Send `ForceEndTurn` (via `SendForceEndTurn()` on the concrete `FluxWebSocketClient`) to end the current turn on your own signal — the resulting `EndOfTurn` carries `Trigger` = `"manual"` — and set `EotThreshold` to `1.0` to [bring your own turn detection](https://developers.deepgram.com/docs/flux/own-turn-detection).
```csharp
using Deepgram;
using Deepgram.Models.Flux.WebSocket;
// Initialize Library with default logging
Library.Initialize();
// Create Flux WebSocket client. The concrete type (rather than
// ClientFactory.CreateFluxWebSocketClient(), which returns IFluxWebSocketClient) is used here
// because SendForceEndTurn lives on the concrete client only until the 8.0 interface revision.
var fluxClient = new FluxWebSocketClient();
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
// Subscribe to TurnInfo events
await fluxClient.Subscribe(new EventHandler<TurnInfoResponse>((sender, e) =>
{
if (e.EventType == TurnEvent.EndOfTurn)
{
Console.WriteLine($"Speaker finished: {e.Transcript}");
}
}));
// Connect to Deepgram Flux (model is required)
var fluxSchema = new FluxSchema()
{
Model = "flux-general-en",
Encoding = "linear16",
SampleRate = 16000,
EotThreshold = 0.7,
Redact = "numbers", // Flux STT supports numbers or aggressive_numbers only; each redacted number becomes *
};
await fluxClient.Connect(fluxSchema);
// Turn numeral formatting on or off for future transcripts without reconnecting.
await fluxClient.SendConfigure(new ConfigureSchema { Numerals = true });
// Stream audio to Deepgram in ~80ms chunks (2560 bytes at 16kHz linear16)
byte[] audioChunk = GetAudioChunk(); // Your audio source
fluxClient.Send(audioChunk);
// Optional: end the current turn on your own signal (push-to-talk release, DTMF,
// your own VAD). The resulting EndOfTurn carries Trigger = "manual".
// SendForceEndTurn first flushes any audio still queued by Send(), so the turn always
// ends on the audio you actually sent — no extra ordering work is needed here.
await fluxClient.SendForceEndTurn();
// Stop the connection (sends CloseStream and waits for the final results)
await fluxClient.Stop();
```
[See our API reference for more info](https://developers.deepgram.com/reference/speech-to-text/listen-flux).
[See the Examples for more info](./examples/speech-to-text/websocket/flux/) - including a [bring-your-own-turn-detection version](./examples/speech-to-text/websocket/flux-force-end-turn/) and a [raw WebSocket version](./examples/speech-to-text/websocket/flux-raw/) that uses no SDK at all.
### `SendForceEndTurn` availability (7.1.0)
`SendForceEndTurn` shipped in 7.1.0 (it is not in 7.0.0).
It lives on the concrete `FluxWebSocketClient` class only — it is intentionally **not** on the
`IFluxWebSocketClient` interface, because adding an interface member would source-break any
third-party class implementing that interface in a 7.x release. The member will be added to the
interface in 8.0. Until then, create the client as `new FluxWebSocketClient(...)` (or cast the
`ClientFactory.CreateFluxWebSocketClient()` result to `FluxWebSocketClient`) to call it. No
existing interface member was renamed, removed, or changed.
## Flux Text to Speech
Synthesize speech with [Deepgram Flux TTS](https://developers.deepgram.com/docs/flux-tts/overview), available on two transports. Stream text in and receive synthesized audio out turn by turn over a WebSocket (built for voice agents), or generate a complete block of audio in a single batch (REST) request. Models are `flux-{voice}-{language}` (e.g. `flux-alexis-en`); an Aura model on this endpoint is rejected — use the classic Speak client for Aura voices.
`FluxSpeakTextControls.Pronunciation(word, ipa)` formats Early Access IPA markers for Flux TTS REST or WebSocket text. `FluxSpeakTextControls.Pause(duration)` formats batch REST-only pauses from 500 to 3000 ms in 100 ms increments. Do not combine pronunciation with non-default speed or with a pause in the same request; Flux TTS rejects those combinations.
Streaming sends five client messages — `Speak`, `Flush`, `Interrupt`, `Configure`, and `Close` (note: `Close`, not the listen client's `CloseStream`). Audio arrives as interleaved binary chunks alongside JSON control messages (`Connected`, `SpeechStarted`, `SpeechMetadata`, `SpeechInterrupted`, `Flushed`, `ConfigureSuccess`/`ConfigureFailure`, `SessionMetadata`, `Warning`, `Error`).
```csharp
using Deepgram;
using Deepgram.Models.Flux.Speak.WebSocket;
// Initialize Library with default logging
Library.Initialize();
// Create Flux TTS WebSocket client
var speakClient = ClientFactory.CreateFluxSpeakWebSocketClient();
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
// Subscribe to synthesized audio chunks (raw bytes in the requested encoding)
await speakClient.Subscribe(new EventHandler<AudioResponse>((sender, e) =>
{
if (e.Stream is not null) { /* play or persist e.Stream */ }
}));
// Connect to Deepgram Flux TTS (model is required)
var schema = new SpeakSchema()
{
Model = "flux-alexis-en",
Encoding = "linear16",
SampleRate = 24000,
Speed = 1.0, // optional: 0.85–1.15 in 0.05 steps
// Expressivity = 1, // optional (beta): -2 (calmer) to 2 (more animated)
};
await speakClient.Connect(schema);
// Stream text into the active turn, then flush to mark the end of the turn.
// The turn's SpeechMetadata (billing, timing) is your end-of-turn signal.
await speakClient.SendText("Sure, I can help you cancel your subscription.");
await speakClient.SendFlush();
// Stop the connection (sends Close and waits for the server to drain the audio)
await speakClient.Stop();
```
### Barge-in and mid-stream controls
When the user speaks over the agent, stop your local playback immediately — don't wait for the server — then send `Interrupt` with how many milliseconds of audio the user actually heard. The server cancels the active turn and answers with `SpeechInterrupted`, splitting the turn's text into what was spoken and what wasn't, so you can feed exactly what the user heard back into your LLM context.
```csharp
await speakClient.Subscribe(new EventHandler<SpeechInterruptedResponse>((sender, e) =>
{
Console.WriteLine($"Heard: {e.TextSpoken}");
Console.WriteLine($"Unsaid: {e.TextRemaining}");
}));
// The offset is cumulative across the whole session (not per turn), and each
// interrupt must advance past the previous one. Report your audio player's
// actual position — not bytes received, which arrive much faster than realtime.
await speakClient.SendInterrupt(playbackOffsetMs);
```
Omit the offset (`SendInterrupt()`) and the turn still stops, but the server can't compute the split — `TextSpoken`/`TextRemaining` come back empty.
`Configure` changes the speaking rate mid-session without reconnecting. The server acknowledges with `ConfigureSuccess`, or rejects with a typed `ConfigureFailure` — the SDK does not range-check `speed` locally, so an out-of-range value comes back as `SPEED_OUT_OF_RANGE` rather than throwing.
```csharp
await speakClient.SendConfigure(new ConfigureSchema() { Speed = 1.05 });
```
For batch (REST) synthesis of a complete block of text:
```csharp
using Deepgram;
using Deepgram.Models.Flux.Speak.REST;
var speakClient = ClientFactory.CreateFluxSpeakRESTClient();
// Synchronous: get the audio back and write it to a file
await speakClient.ToFile(
new TextSource("Your appointment is confirmed for 3pm tomorrow."),
"output.mp3",
new SpeakSchema() { Model = "flux-alexis-en", Encoding = "mp3", BitRate = 48000, Speed = 1.05 });
// Asynchronous: supply a callback URL and receive a request_id ack; the audio is
// delivered to your callback
// await speakClient.StreamCallBack(new TextSource("..."), "https://example.com/webhook",
// new SpeakSchema() { Model = "flux-alexis-en" });
```
[See our API reference for more info](https://developers.deepgram.com/reference/text-to-speech/speak-flux).
[See the Examples for more info](./examples/text-to-speech/websocket/flux/) - and the [batch (REST) example](./examples/text-to-speech/rest/flux/).
### Upgrading from 6.x (`IFluxSpeakWebSocketClient` interface members)
Version 7.0 adds the GA barge-in/mid-stream controls above directly to the
`IFluxSpeakWebSocketClient` interface: `SendInterrupt` (two overloads), `SendConfigure`, and
`Subscribe` overloads for `SpeechInterruptedResponse`, `ConfigureSuccessResponse`, and
`ConfigureFailureResponse`. If you use `FluxSpeakWebSocketClient`/`ClientFactory` as shipped, or a
mocking framework (NSubstitute, Moq) to fake this interface in tests, nothing changes for you.
This is a breaking change only if you have your own concrete class implementing
`IFluxSpeakWebSocketClient` directly — add the six new members to keep it compiling. There is no
old-API-to-new-API migration here (nothing was renamed or removed); it is a pure addition.
## Voice Agent
Configure a Voice Agent.
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var agentClient = ClientFactory.CreateAgentWebSocketClient();
// Subscribe to key events
await agentClient.Subscribe(new EventHandler<ConversationTextResponse>
((sender, e) =>
{
Console.WriteLine($"Agent: {e.Text}");
}));
await agentClient.Subscribe(new EventHandler<AudioResponse>((sender, e) =>
{
// Handle agent's audio response
Console.WriteLine("Agent speaking...");
}));
// Configure agent settings
var settings = new SettingsSchema()
{
Language = "en",
Agent = new AgentSchema()
{
Think = new ThinkSchema()
{
Provider = new ProviderSchema()
{
Type = "open_ai",
Model = "gpt-4o-mini",
},
Prompt = "You are a helpful AI assistant.",
},
Listen = new ListenSchema()
{
Provider = new ProviderSchema()
{
Type = "deepgram",
Model = "nova-3",
},
},
// Option 1: Single Provider (Backward Compatibility)
Speak = new SpeakSchema()
{
Provider = new ProviderSchema()
{
Type = "deepgram",
Model = "aura-2-thalia-en",
},
},
// Option 2: Multiple Providers with Fallback Support
// Uncomment the section below and comment out the single provider above
// to use multiple TTS providers for enhanced reliability
/*
Speak = new SpeakSchema()
{
SpeakProviders = new List<SpeakProviderConfig>
{
// Primary provider: Deepgram
new SpeakProviderConfig
{
Provider = new ProviderSchema()
{
Type = "deepgram",
Model = "aura-2-zeus-en",
}
},
// Fallback provider: OpenAI
new SpeakProviderConfig
{
Provider = new ProviderSchema()
{
Type = "open_ai",
Model = "tts-1",
Voice = "shimmer",
},
Endpoint = new EndpointSchema()
{
URL = "https://api.openai.com/v1/audio/speech",
Headers = new Dictionary<string, string>
{
{ "authorization", "Bearer {{OPENAI_API_KEY}}" }
}
}
}
}
},
*/
},
Greeting = "Hello, I'm your AI assistant.",
};
// Connect to Deepgram Voice Agent
await agentClient.Connect(settings);
// Keep connection alive
await Task.Delay(TimeSpan.FromSeconds(30));
// Cleanup
await agentClient.Stop();
```
This example demonstrates:
- Setting up a WebSocket connection for Voice Agent
- Configuring the agent with speech, language, and audio settings
- Handling various agent events (speech, transcripts, audio)
- Sending audio data and keeping the connection alive
For a complete implementation, you would need to:
1. Add your audio input source (e.g., microphone)
2. Implement audio playback for the agent's responses
3. Handle any function calls if your agent uses them
4. Add proper error handling and connection management
### Defining function-call parameters
`Function.Parameters` is a JSON Schema expressed as a `Dictionary<string, object>`, so a function
can declare **any number of parameters** with custom names — set `properties` to a dictionary keyed
by each parameter name:
```csharp
var function = new Function
{
Name = "get_weather",
Description = "Get the weather for a city on a date",
Parameters = new Dictionary<string, object>
{
["type"] = "object",
["properties"] = new Dictionary<string, object>
{
["city"] = new Dictionary<string, object> { ["type"] = "string", ["description"] = "City name" },
["date"] = new Dictionary<string, object> { ["type"] = "string", ["description"] = "ISO 8601 date" },
["units"] = new Dictionary<string, object> { ["type"] = "string", ["description"] = "metric or imperial" },
},
["required"] = new List<string> { "city", "date" },
},
};
```
### Current session controls and function safety
Use `CreateAgentProtocolClient()` when you need typed subscriptions for current Voice Agent
protocol events. `FunctionCallCancelled` means the named client-side calls must not receive a
response.
```csharp
var agentClient = ClientFactory.CreateAgentProtocolClient();
await agentClient.Subscribe(new EventHandler<FunctionCallCancelledResponse>((_, e) =>
{
foreach (var function in e.Functions ?? new List<CancelledFunctionCall>())
{
Console.WriteLine($"Cancelled: {function.Id} ({function.Name})");
// Do not send AgentFunctionCallResponseSchema for this ID.
}
}));
var chargeCard = new Function
{
Name = "charge_card",
DeferUntilEot = true, // Wait for a confirmed user turn before an irreversible action.
};
settings.Agent.Think.Functions = new List<Function> { chargeCard };
// Connect settings before sending any session control message.
await agentClient.Connect(settings);
await agentClient.SendUpdatePrompt(new AgentUpdatePromptSchema
{
Prompt = "Keep answers concise and confirm before charging a card.",
});
await agentClient.SendForceEndTurn(); // Requires a Flux STT listen provider and IAgentProtocolClient.
```
### Custom Think providers
Experimental custom Think provider messages require a `wss://` endpoint in
`settings.Agent.Think.Endpoint.Url`. The SDK forwards `JsonElement` content unchanged, including
objects, arrays, scalar values, and JSON `null`.
```csharp
await agentClient.Subscribe(new EventHandler<CustomFromThinkProviderResponse>((_, e) =>
{
Console.WriteLine(e.Content.GetRawText());
}));
using var document = JsonDocument.Parse("""{"action":"continue"}""");
await agentClient.SendCustomToThinkProvider(new AgentCustomToThinkProviderSchema
{
Content = document.RootElement.Clone(),
});
```
### Available Think models
Read the current Voice Agent Think-model catalog before configuring a session. The catalog is
read-only, public, and does not require a project ID or credentials.
```csharp
using Deepgram.Models.Agent.v1.REST;
var catalogClient = ClientFactory.CreateAgentCatalogClient();
var catalog = await catalogClient.GetThinkModels();
foreach (var model in catalog.Models ?? new List<AgentThinkModel>())
{
Console.WriteLine($"{model.Provider}: {model.Id} ({model.Name})");
}
```
[See the runnable example](./examples/agent/rest/think_models/).
### Reusable Agent Configurations
Store the `agent` block of a Settings message with Deepgram and reference it by UUID instead of
repeating the full configuration, with optional template variables (`DG_*`) for values shared
across configurations. A variable is referenced inside the JSON-encoded config as a bare,
unquoted `DG_<VARIABLE_NAME>` token (e.g. `"greeting": DG_GREETING` — no quotes, no braces);
the service substitutes the variable's JSON value when the configuration is used. Managed via
REST with the `AgentManageClient`:
```csharp
using Deepgram.Models.AgentManage.v1;
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var agentManageClient = ClientFactory.CreateAgentManageClient();
// projectId: read it from DEEPGRAM_PROJECT_ID. Use a DISPOSABLE test project while experimenting:
// these calls create and delete real resources, and a deleted variable's name stays reserved in
// its project forever.
var projectId = Environment.GetEnvironmentVariable("DEEPGRAM_PROJECT_ID")!;
// Create a template variable first (DG_* key, any JSON value) so configurations can
// reference it.
var variable = await agentManageClient.CreateAgentVariable(projectId,
new AgentVariableSchema { Key = "DG_GREETING", Value = "Hello! How can I help you today?" });
await agentManageClient.UpdateAgentVariable(projectId, variable.VariableId!,
new UpdateAgentVariableSchema { Value = "Welcome back!" });
// Create a reusable agent configuration (Config is a JSON-encoded string). The bare
// DG_GREETING token references the template variable created above; it comes back
// uninterpolated when you fetch the configuration.
var created = await agentManageClient.CreateAgent(projectId, new AgentConfigurationSchema
{
Config = """{"language":"en","listen":{"provider":{"type":"deepgram","model":"nova-3"}},"think":{"provider":{"type":"open_ai","model":"gpt-4o-mini"},"prompt":"You are a helpful agent."},"greeting":DG_GREETING,"speak":{"provider":{"type":"deepgram","version":"v2","model":"flux-kit-en"}}}""",
Metadata = new Dictionary<string, string> { ["name"] = "customer-service-agent" },
});
Console.WriteLine($"Agent ID: {created.AgentId}"); // pass this in place of the agent object in Settings
// List / get / update metadata / delete
var agents = await agentManageClient.GetAgents(projectId);
var agent = await agentManageClient.GetAgent(projectId, created.AgentId!);
await agentManageClient.UpdateAgentMetadata(projectId, created.AgentId!,
new AgentMetadataSchema { Metadata = new Dictionary<string, string> { ["environment"] = "production" } });
await agentManageClient.DeleteAgent(projectId, created.AgentId!);
await agentManageClient.DeleteAgentVariable(projectId, variable.VariableId!);
```
> Note: the live API currently reserves a deleted variable's name forever within a project —
> re-creating `DG_GREETING` after deleting it fails with "This project already has a variable
> with that name". Use a fresh key per experiment (the runnable examples add a per-run suffix).
[See our docs for more info](https://developers.deepgram.com/docs/reusable-agent-configurations).
[See the Examples for more info](./examples/agent/manage/configurations/) - and the [template variables example](./examples/agent/manage/variables/).
## Text to Speech REST
Convert text into speech using the REST API.
Aura REST requests also accept `Speed`, one or more `Tag` values, and `MipOptOut`:
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var speakClient = ClientFactory.CreateSpeakRESTClient();
var response = await speakClient.ToFile(
new Deepgram.Models.Speak.v1.REST.TextSource("Hello world!"),
"output.wav",
new SpeakSchema()
{
Model = "aura-2-thalia-en",
Speed = 1.1,
Tag = new List<string> { "release", "voice" },
// Opts this request out of the Model Improvement Program; see
// https://developers.deepgram.com/docs/the-deepgram-model-improvement-partnership-program
// for pricing and data-retention effects.
// MipOptOut = true,
});
Console.WriteLine($"Audio saved to: output.wav");
```
[See our API reference for more info](https://developers.deepgram.com/reference/text-to-speech-api/speak).
[See the Example for more info](./examples/text-to-speech/rest/).
## Text to Speech Streaming
Convert streaming text into speech using a WebSocket.
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var speakClient = ClientFactory.CreateSpeakWebSocketClient();
// Subscribe to audio responses
await speakClient.Subscribe(new EventHandler<AudioResponse>((sender, e) =>
{
// Handle the generated audio data
Console.WriteLine("Received audio data");
}));
// Configure speak options
var speakSchema = new SpeakSchema()
{
Model = "aura-2-thalia-en",
Encoding = "linear16",
SampleRate = 16000,
};
// Connect to Deepgram
await speakClient.Connect(speakSchema);
// Send text to convert to speech
await speakClient.SendText("Hello, this is a text to speech example.");
await speakClient.Flush();
// Wait for completion and cleanup
await speakClient.WaitForComplete();
await speakClient.Stop();
```
[See our API reference for more info](https://developers.deepgram.com/reference/text-to-speech-api/speak-streaming).
[See the Examples for more info](./examples/text-to-speech/websocket/).
## Text Intelligence
Analyze text.
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var analyzeClient = ClientFactory.CreateAnalyzeClient();
// Check if file exists
if (!File.Exists("text_to_analyze.txt"))
{
Console.WriteLine("Error: File 'text_to_analyze.txt' not found.");
return;
}
var textData = File.ReadAllBytes("text_to_analyze.txt");
var response = await analyzeClient.AnalyzeFile(
textData,
new AnalyzeSchema()
{
Model = "nova-3"
// Configure Read Options
});
Console.WriteLine($"Analysis Results: {response}");
```
[See our API reference for more info](https://developers.deepgram.com/reference/text-intelligence-api/text-read).
[See the Examples for more info](./examples/analyze/).
## Authentication
### Grant Token
Creates a temporary token with a 30-second TTL.
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var authClient = ClientFactory.CreateAuthClient();
var response = await authClient.GrantToken();
Console.WriteLine($"Token: {response.AccessToken}");
```
[See our API reference for more info](https://developers.deepgram.com/reference/token-based-auth-api/grant-token).
[See the Examples for more info](./examples/auth/grant-token).
## Projects
### Get Projects
Returns all projects accessible by the API key.
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var manageClient = ClientFactory.CreateManageClient();
var response = await manageClient.GetProjects();
Console.WriteLine($"Projects: {response.Projects}");
```
[See our API reference for more info](https://developers.deepgram.com/reference/management-api/projects/list).
[See the Example for more info](./examples/manage/projects/).
### Get Project
Retrieves a specific project based on the provided project_id.
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var manageClient = ClientFactory.CreateManageClient();
var response = await manageClient.GetProject(projectId);
Console.WriteLine($"Project: {response.Project}");
```
[See our API reference for more info](https://developers.deepgram.com/reference/management-api/projects/get).
[See the Example for more info](./examples/manage/projects/).
### Update Project
Update a project.
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var manageClient = ClientFactory.CreateManageClient();
var updateOptions = new ProjectSchema()
{
Name = "Updated Project Name",
};
var response = await manageClient.UpdateProject(projectId, updateOptions);
Console.WriteLine($"Update result: {response.Message}");
```
[See our API reference for more info](https://developers.deepgram.com/reference/management-api/projects/update).
[See the Example for more info](./examples/manage/projects/).
### Delete Project
Delete a project.
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var manageClient = ClientFactory.CreateManageClient();
var response = await manageClient.DeleteProject(projectId);
Console.WriteLine($"Delete result: {response.Message}");
```
[See our API reference for more info](https://developers.deepgram.com/reference/management-api/projects/delete).
[See the Example for more info](./examples/manage/projects/).
## Keys
### List Keys
Retrieves all keys associated with the provided project_id.
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var manageClient = ClientFactory.CreateManageClient();
var response = await manageClient.GetKeys(projectId);
Console.WriteLine($"Keys: {response.APIKeys}");
```
[See our API reference for more info](https://developers.deepgram.com/reference/management-api/keys/list).
[See the Example for more info](./examples/manage/keys/).
### Get Key
Retrieves a specific key associated with the provided project_id.
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var manageClient = ClientFactory.CreateManageClient();
var response = await manageClient.GetKey(projectId, keyId);
Console.WriteLine($"Key: {response.APIKey}");
```
[See our API reference for more info](https://developers.deepgram.com/reference/management-api/keys/get).
[See the Example for more info](./examples/manage/keys/).
### Create Key
Creates an API key with the provided scopes.
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var manageClient = ClientFactory.CreateManageClient();
var createOptions = new KeySchema()
{
Comment = "My API Key",
Scopes = new List<string> { "admin" },
};
var response = await manageClient.CreateKey(projectId, createOptions);
Console.WriteLine($"Created key: {response.APIKeyID}");
```
[See our API reference for more info](https://developers.deepgram.com/reference/management-api/keys/create).
[See the Example for more info](./examples/manage/keys/).
### Delete Key
Deletes a specific key associated with the provided project_id.
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var manageClient = ClientFactory.CreateManageClient();
var response = await manageClient.DeleteKey(projectId, keyId);
Console.WriteLine($"Delete result: {response.Message}");
```
[See our API reference for more info](https://developers.deepgram.com/reference/management-api/keys/delete).
[See the Example for more info](./examples/manage/keys/).
## Members
### Get Members
Retrieves account objects for all of the accounts in the specified project_id.
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var manageClient = ClientFactory.CreateManageClient();
var response = await manageClient.GetMembers(projectId);
Console.WriteLine($"Members: {response.Members}");
```
[See our API reference for more info](https://developers.deepgram.com/reference/management-api/members/list).
[See the Example for more info](./examples/manage/members/).
### Remove Member
Removes member account for specified member_id.
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var manageClient = ClientFactory.CreateManageClient();
var response = await manageClient.RemoveMember(projectId, memberId);
Console.WriteLine($"Remove result: {response.Message}");
```
[See our API reference for more info](https://developers.deepgram.com/reference/management-api/members/delete).
[See the Example for more info](./examples/manage/members/).
## Scopes
### Get Member Scopes
Retrieves scopes of the specified member in the specified project.
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var manageClient = ClientFactory.CreateManageClient();
var response = await manageClient.GetMemberScopes(projectId, memberId);
Console.WriteLine($"Scopes: {response.Scopes}");
```
[See our API reference for more info](https://developers.deepgram.com/reference/management-api/scopes/list).
[See the Example for more info](./examples/manage/scopes/).
### Update Scope
Updates the scope for the specified member in the specified project.
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var manageClient = ClientFactory.CreateManageClient();
var updateOptions = new ScopeSchema()
{
Scope = "admin",
};
var response = await manageClient.UpdateMemberScopes(projectId, memberId, updateOptions);
Console.WriteLine($"Update result: {response.Message}");
```
[See our API reference for more info](https://developers.deepgram.com/reference/management-api/scopes/update).
[See the Example for more info](./examples/manage/scopes/).
## Invitations
### List Invites
Retrieves all invitations associated with the provided project_id.
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var manageClient = ClientFactory.CreateManageClient();
var response = await manageClient.GetInvitations(projectId);
Console.WriteLine($"Invitations: {response.Invites}");
```
[See our API reference for more info](https://developers.deepgram.com/reference/management-api/invitations/list).
[See the Example for more info](./examples/manage/invitations/).
### Send Invite
Sends an invitation to the provided email address.
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var manageClient = ClientFactory.CreateManageClient();
var inviteOptions = new InvitationSchema()
{
Email = "user@example.com",
Scope = "admin",
};
var response = await manageClient.SendInvitation(projectId, inviteOptions);
Console.WriteLine($"Invitation sent: {response.Message}");
```
[See our API reference for more info](https://developers.deepgram.com/reference/management-api/invitations/create).
[See the Example for more info](./examples/manage/invitations/).
### Delete Invite
Removes the specified invitation from the project.
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var manageClient = ClientFactory.CreateManageClient();
var response = await manageClient.DeleteInvitation(projectId, email);
Console.WriteLine($"Delete result: {response.Message}");
```
[See our API reference for more info](https://developers.deepgram.com/reference/management-api/invitations/delete).
[See the Example for more info](./examples/manage/invitations/).
### Leave Project
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var manageClient = ClientFactory.CreateManageClient();
var response = await manageClient.LeaveProject(projectId);
Console.WriteLine($"Leave result: {response.Message}");
```
[See our API reference for more info](https://developers.deepgram.com/reference/management-api/invitations/leave).
[See the Example for more info](./examples/manage/invitations/).
## Usage
### Get All Requests
Retrieves all requests associated with the provided project_id
based on the provided options.
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var manageClient = ClientFactory.CreateManageClient();
var response = await manageClient.GetUsageRequests(projectId);
Console.WriteLine($"Requests: {response.Requests}");
```
[See our API reference for more info](https://developers.deepgram.com/reference/management-api/usage/list-requests).
[See the Example for more info](./examples/manage/usage/).
### Get Request
Retrieves a specific request associated with the provided project_id.
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var manageClient = ClientFactory.CreateManageClient();
var response = await manageClient.GetUsageRequest(projectId, requestId);
Console.WriteLine($"Request: {response.Request}");
```
[See our API reference for more info](https://developers.deepgram.com/reference/management-api/usage/get-request).
[See the Example for more info](./examples/manage/usage/).
### Get Fields
Lists the features, models, tags, languages, and processing method
used for requests in the specified project.
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var manageClient = ClientFactory.CreateManageClient();
var response = await manageClient.GetUsageFields(projectId, new UsageFieldsSchema());
Console.WriteLine($"Fields: {response.Fields}");
```
[See our API reference for more info](https://developers.deepgram.com/reference/management-api/usage/list-fields).
[See the Example for more info](./examples/manage/usage/).
### Get Usage Breakdown
Retrieves current usage totals grouped by a reporting dimension. Prefer this endpoint for new
reporting integrations; `GetUsageSummary` remains available on `ManageClient` for compatibility.
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var reportingClient = ClientFactory.CreateManagementReportingClient();
var response = await reportingClient.GetUsageBreakdown(projectId, new UsageBreakdownSchema
{
Start = DateTime.UtcNow.Date.AddDays(-7),
End = DateTime.UtcNow.Date,
Grouping = "models",
});
Console.WriteLine($"Usage groups: {response.Results?.Count ?? 0}");
```
[See our API reference for more info](https://developers.deepgram.com/reference/manage/usage/breakdown/get).
[See the Example for more info](./examples/manage/usage/).
## Billing
Balances are read through `ManageClient`. For billing reports, use the reporting client from
`ClientFactory.CreateManagementReportingClient()`: `GetBillingBreakdown` returns dollar totals that you
can group by one or more of `accessor`, `deployment`, `line_item`, or `tags`, `GetBillingFields` lists the accessors,
deployments, tags, and line items you can filter that breakdown by, and `GetPurchases` lists the
project's purchase orders. See the
[ManagementReportingClient reference](./docs/codedocs/api-reference/management-reporting-client.md).
### Get All Balances
Retrieves the list of balance info for the specified project.
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var manageClient = ClientFactory.CreateManageClient();
var response = await manageClient.GetBalances(projectId);
Console.WriteLine($"Balances: {response.Balances}");
```
[See our API reference for more info](https://developers.deepgram.com/reference/management-api/balances/list).
[See the Example for more info](./examples/manage/balances/).
### Get Balance
Retrieves the balance info for the specified project and balance_id.
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var manageClient = ClientFactory.CreateManageClient();
var response = await manageClient.GetBalance(projectId, balanceId);
Console.WriteLine($"Balance: {response.Balance}");
```
[See our API reference for more info](https://developers.deepgram.com/reference/management-api/balances/get).
[See the Example for more info](./examples/manage/balances/).
## Models
### Get All Project Models
Retrieves all models available for a given project.
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var manageClient = ClientFactory.CreateManageClient();
var response = await manageClient.GetProjectModels(projectId);
Console.WriteLine($"Models: {response}");
```
[See our API reference for more info](https://developers.deepgram.com/reference/management-api/projects/list-models).
[See the Example for more info](./examples/manage/models/).
### Get Model
Retrieves details of a specific model.
```csharp
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key
var manageClient = ClientFactory.CreateManageClient();
var response = await manageClient.GetProjectModel(projectId, modelId);
Console.WriteLine($"Model: {response.Model}");
```
[See our API reference for more info](https://developers.deepgram.com/reference/management-api/projects/get-model).
[See the Example for more info](./examples/manage/models/).
## Self-Hosted Distribution Credentials
Use `CreateSelfHostedDistributionCredentialsClient()` for the current
`/v1/projects/{project_id}/self-hosted/distribution/credentials` API. The request body contains
only the optional comment; provider and scopes are query options.
```csharp
using Deepgram.Models.SelfHosted.v1;
// Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key.
var selfHostedClient = ClientFactory.CreateSelfHostedDistributionCredentialsClient();
var credential = await selfHostedClient.CreateDistributionCredentials(
projectId,
new DistributionCredentialsCreateSchema
{
Comment = "Credential for the staging cluster",
},
new DistributionCredentialsCreateOptions
{
Provider = "quay",
Scopes = new List<string>
{
"self-hosted:product:api",
"self-hosted:product:engine",
},
});
Console.WriteLine($"Created credentials: {credential.DistributionCredentials?.DistributionCredentialsId}");
```
The client also provides `ListDistributionCredentials`, `GetDistributionCredentials`, and
`DeleteDistributionCredentials`.
`CreateSelfHostedClient()` and the `SelfHostedClient` it returns are obsolete. `SelfHostedClient`
calls the older `onprem/distribution/credentials` route, which still responds but no longer appears
in the API reference. Use `CreateSelfHostedDistributionCredentialsClient()` for new code.
[See our API reference for more info](https://developers.deepgram.com/reference/self-hosted/distribution-credentials/list).
## Logging
This SDK logs through [`Microsoft.Extensions.Logging`](https://learn.microsoft.com/en-us/dotnet/core/extensions/logging),
the standard .NET logging abstraction. By default it writes to the console at
`Information` level and higher (ie `Warning`, `Error`, etc.) when you initialize the
library as follows:
```csharp
// Default logging level is "Information"
Library.Initialize();
```
To increase the logging output/verbosity for debug or troubleshooting purposes,
set the `Debug` level:
```csharp
Library.Initialize(LogLevel.Debug);
```
### Upgrading from 6.x (Serilog → Microsoft.Extensions.Logging)
Version 7.0 replaces Serilog with `Microsoft.Extensions.Logging`. Most code is
unaffected — `Library.Initialize()`, `Library.Initialize(LogLevel.Debug)`, and the
`Deepgram.Logger.LogLevel` enum (member names *and* values) are unchanged. The
following Serilog-coupled members on `Deepgram.Logger.Log` are the only breaking
changes:
| 6.x (Serilog) | 7.0 replacement |
| --- | --- |
| `Log.Initialize(Serilog.ILogger)` | `Library.Configure(ILoggerFactory)` — see below. To keep using Serilog, register it as a provider (`builder.AddSerilog(...)`). |
| `Log.GetLogger()` returning `Serilog.ILogger` | now returns `Microsoft.Extensions.Logging.ILogger` |
| `Log.Initialize(LogLevel, string?)` returning `Serilog.ILogger` | now returns `Microsoft.Extensions.Logging.ILogger` |
If you previously handed the SDK a Serilog logger, route it through an
`ILoggerFactory` instead (Serilog remains fully usable as an MEL provider):
```csharp
using Microsoft.Extensions.Logging;
using Serilog;
var serilog = new LoggerConfiguration().WriteTo.Console().CreateLogger();
var factory = LoggerFactory.Create(b => b.AddSerilog(serilog, dispose: true));
Library.Configure(factory);
```
### Using your own logger
Because the SDK uses `Microsoft.Extensions.Logging`, you can route SDK logs through
your own logging pipeline (Serilog, NLog, OpenTelemetry, JSON for Kibana, etc.) by
supplying your own `ILoggerFactory`. The SDK only consumes the factory you give it —
it never reconfigures your application's global logging.
```csharp
using Microsoft.Extensions.Logging;
// Any ILoggerFactory you already build in your app
var factory = LoggerFactory.Create(builder =>
{
builder.SetMinimumLevel(LogLevel.Debug);
builder.AddJsonConsole(); // or AddSerilog(), AddOpenTelemetry(), etc.
});
Library.Configure(factory); // route SDK logs through your factory
```
Each SDK component logs under its own category (for example `"ListenWSClient"` or
`"ManageClient"`), so you can filter and format SDK logs per category with your own
provider.
If you use dependency injection, register logging and hand the SDK the container's
factory once the provider is built:
```csharp
using Microsoft.Extensions.DependencyInjection;
services.AddDeepgramLogging(); // ensures an ILoggerFactory is available
// ... after building the provider ...
serviceProvider.UseDeepgramLogging(); // routes SDK logs through it
```
### Correlating logs for a connection
For WebSocket clients, every log entry emitted for a single connection carries a
generated `dg.connection_id` (via a logging scope), so you can group all of a
connection's log entries together and later tie them back to the server's
`request_id`. Enable scope output in your provider (for example
`options.IncludeScopes = true` on the console logger) to surface it.
## Testing
### Unit Tests
Run:
```bash
dotnet test Deepgram.Tests/Deepgram.Tests.csproj
```
### Integration Tests
See the [tests](./tests/) directory for integration tests and edge case validation
beyond the unit tests.
### Examples
See the [examples](./examples/) directory for working code samples for different
Deepgram SDK features.
## Backwards Compatibility
We follow semantic versioning (semver) to ensure a smooth upgrade experience.
Within a major version (like `6.*`), we will maintain backward compatibility
so your code will continue to work without breaking changes.
When we release a new major version (like moving from `5.*` to `6.*`),
we may introduce breaking changes to improve the SDK.
We'll always document these changes clearly in our release notes to help you
upgrade smoothly.
Older SDK versions will receive Priority 1 (P1) bug support only.
Security issues, both in our code and dependencies, are promptly addressed.
Significant bugs without clear workarounds are also given priority attention.
## Development and Contributing
Interested in contributing? We ❤️ pull requests!
To make sure our community is safe for all, be sure to review and agree to our
[Code of Conduct](.github/CODE_OF_CONDUCT.md).
Then see the [Contribution](.github/CONTRIBUTING.md) guidelines for more information.
### Getting Help
We love to hear from you, so if you have questions, comments or find a bug in
the project, please let us know! You can either:
- [Open an issue in this repository](https://github.com/deepgram/deepgram-dotnet-sdk/issues/new)
- [Join the Deepgram Github Discussions Community](https://github.com/orgs/deepgram/discussions)
- [Join the Deepgram Discord Community](https://discord.gg/xWRaCDBtW4)