SMS Quickstart

The fastest way to get started with ClickSend API in your preferred coding language.

This guide is for the current version of the C# SDK.

Looking for v1? See our Quickstart guide for our C# v1 SDK.

Send your first SMS with the official ClickSend .NET SDK (ClickSend on NuGet) in under 5 minutes.

1. Prerequisites

Before you start, make sure you have:

Requirement

Details

A ClickSend account

Sign up free if you don't have one. New accounts get free credit to test with.

API credentials

Your username and API key, both on the API Credentials page of the dashboard. You'll authenticate with these, not your dashboard login password.

.NET 10.0 or newer

This SDK targets net10.0. Check with dotnet --version.

Account credit

Sending SMS consumes credit. Free trial credit is enough for this guide; top up on the Billing page if you get an INSUFFICIENT_CREDIT error later.

2. Install

dotnet add package ClickSend

Or add it directly to your .csproj:

<PackageReference Include="ClickSend" Version="6.0.2" />

3. Configure the client

The SDK is wired up through Microsoft.Extensions.Hosting dependency injection rather than a standalone client object. Authentication uses HTTP Basic auth via a BasicToken built from your ClickSend username and API key. Never hard-code real credentials — load them from environment variables:

export CLICKSEND_USERNAME="your-clicksend-username"
export CLICKSEND_API_KEY="your-clicksend-api-key"

using ClickSend.Client;
using ClickSend.Api;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Hosting;

var host = Host.CreateDefaultBuilder(args)
    .ConfigureApi((context, services, options) =>
    {
        BasicToken token = new(
            Environment.GetEnvironmentVariable("CLICKSEND_USERNAME"), // placeholder: your ClickSend username
            Environment.GetEnvironmentVariable("CLICKSEND_API_KEY")); // placeholder: your ClickSend API key
        options.AddTokens(token);
    })
    .Build();

var smsApi = host.Services.GetRequiredService<ISmsApi>();

smsApi is now an authenticated client for every SMS endpoint (send, history, templates, delivery receipts, etc.). Every other ClickSend resource has its own interface resolvable from the same host.Services (e.g. IMmsApi, IManagementApi, IContactsApi).

4. Send your first SMS

This is a complete, runnable example. Set the two environment variables from step 3, replace the to number with a real one, and run it.

using ClickSend.Client;
using ClickSend.Api;
using ClickSend.Model;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Hosting;

var host = Host.CreateDefaultBuilder(args)
    .ConfigureApi((context, services, options) =>
    {
        BasicToken token = new(
            Environment.GetEnvironmentVariable("CLICKSEND_USERNAME"),
            Environment.GetEnvironmentVariable("CLICKSEND_API_KEY"));
        options.AddTokens(token);
    })
    .Build();

var smsApi = host.Services.GetRequiredService<ISmsApi>();

var sendSmsRequest = new SendSmsRequest(messages: new List<SendSmsRequestMessagesInner>
{
    new(
        source: "sdk",
        from: "YOUR_SENDER_ID",       // placeholder: e.g. a ClickSend number, or omit to use your default sender
        body: "Hello from ClickSend!",
        to: "+61411111111")           // placeholder: recipient in E.164 format
});

var response = await smsApi.SendSmsAsync(sendSmsRequest: sendSmsRequest);

if (response.IsSuccessStatusCode)
{
    var result = response.Ok();
    Console.WriteLine(result);
}
else
{
    Console.WriteLine($"Failed to send SMS: {response.StatusCode} {response.RawContent}");
}

5. Understand the response

smsApi.SendSmsAsync(...) returns an ISendSmsApiResponse. Call .Ok() to get the typed SendSms payload once you've confirmed IsSuccessStatusCode:

{
  "http_code": 200,
  "response_code": "SUCCESS",
  "response_msg": "Messages queued for delivery.",
  "data": {
    "total_price": 0.0388,
    "total_count": 1,
    "queued_count": 1,
    "blocked_count": 0,
    "messages": [
      {
        "to": "+61411111111",
        "body": "Hello from ClickSend!",
        "from": "SENDERID",
        "message_id": "6811A5CE-E374-5D26-82F5-1D9E52FA9AB3",
        "message_parts": 1,
        "message_price": "0.0388",
        "status": "SUCCESS",
        "date": 1758434400
      }
    ]
  }
}

The fields you'll use most, via the generated (PascalCase) properties:

Field

Where

Meaning

Message ID

result.Data.Messages[0].MessageId

The unique ID for this message. Quote this when contacting support or looking up delivery receipts.

Status

result.Data.Messages[0].Status

The outcome for this specific message (SUCCESS, INVALID_RECIPIENT, ...). Check this per message — a batch send can succeed overall while individual messages fail (see §6).

Cost

result.Data.Messages[0].MessagePrice

Cost of this one message. result.Data.TotalPrice is the sum across every message in the request.

var message = result.Data.Messages[0];
Console.WriteLine($"Message ID: {message.MessageId}");
Console.WriteLine($"Status: {message.Status}");
Console.WriteLine($"Cost: {message.MessagePrice}");

6. Common errors

Unlike most other ClickSend SDKs, this one does not throw an exception on a non-2xx HTTP response — SendSmsAsync always completes successfully, and you inspect response.IsSuccessStatusCode / response.StatusCode / response.RawContent yourself. ClickSend also reports some failures — like an invalid recipient in an otherwise-valid batch — inside a 200 OK response, which is a separate check again. Always check both the HTTP-level status and each message's own Status.

var response = await smsApi.SendSmsAsync(sendSmsRequest: sendSmsRequest);

if (!response.IsSuccessStatusCode)
{
    Console.WriteLine($"HTTP error: {response.StatusCode} {response.RawContent}");
    return;
}

var result = response.Ok();
foreach (var message in result.Data.Messages)
{
    if (message.Status != "SUCCESS")
    {
        Console.WriteLine($"Message to {message.To} failed: {message.Status}");
    }
}

Error

How it shows up

What it means

Fix

Authentication failure

response.StatusCode == HttpStatusCode.Unauthorized (401) — IsSuccessStatusCode is false, no exception thrown. response.RawContent's response_code is MISSING_CREDENTIALS (no username/API key sent) or INVALID_CREDENTIALS (wrong username/API key).

Your BasicToken username/password doesn't match a valid ClickSend account, or an env var wasn't set.

Double-check CLICKSEND_USERNAME/CLICKSEND_API_KEY are set and copied exactly from the API Credentials page — use the API key, not your dashboard password.

Invalid recipient

Request usually still returns HTTP 200 (IsSuccessStatusCode is true, response_code: SUCCESS at the top level) — the failure is on the individual message: message.Status is INVALID_RECIPIENT. This does not fail the HTTP call — you must check the status yourself.

The destination mobile number isn't a valid, deliverable number (bad format, wrong country, disconnected, etc).

Validate/normalize numbers to E.164 (e.g. +61411111111) before sending, and surface per-message status values to your own logs or users.

Insufficient balance

response_code (or a message's Status) is INSUFFICIENT_CREDIT, typically alongside response.StatusCode == HttpStatusCode.BadRequest (400) when it blocks the whole request.

Your account has run out of message credit.

Top up credit on the Billing page, or check balance first with IManagementApi.ViewAccountDetailsAsync().

Next steps

Start sprinting with our API docs

Get all the detail you'll ever need in our full API docs. Learn how to launch your own features or integrate with others.