The CLV1 protocol is now publicRead the spec
Browse the library

Documentation libraryIntegration

C++, C# and Python SDKs

Three native SDKs for desktop software and command-line tools. They speak the same CLV1.1 protocol as the JavaScript SDK: the machine signs every request, your app signs every answer, and offline tokens and update manifests are checked right on the machine.

3 min read

Choosing an SDK

SDKRequiresLibrariesDevice key
C++C++17, CMake, vcpkglibsodium, libcurl, nlohmann/jsonSealed with DPAPI on Windows
C#.NET 8 or laterBouncyCastleSealed with DPAPI on Windows
PythonPython 3.9 or latercryptographyStored in a file only the current user can read

All three pass the same test vectors as the server, and have a test that runs them against the real API.

Three integration steps

The app's Integration › Connect software page has sample code for each language, with your App ID and public key already filled in, and a starter project that runs as downloaded. The steps are the same everywhere:

  1. Create the client with the API address, the App ID, the app's public key, a description of the machine (default_device, ClavisDevice.Default) and a device key kept between runs.
  2. Call activate with the customer's key on first run, or login if your app uses accounts.
  3. Send a heartbeat while the software runs, waiting the seconds nextCheckIn gives between two. Sessions end after 60 minutes without one.
using ClavisAuh;

var clavis = new ClavisClient(new ClavisOptions
{
    BaseUrl = "https://api.example.com",
    AppId = "app_…",
    AppPublicKeys = ["<public key>"],
    Device = ClavisDevice.Default(),
    DeviceKey = ClavisDevice.LoadOrCreateKey("device.key"),
});
try
{
    var grant = await clavis.ActivateAsync(licenseKey);
}
catch (ClavisException e)
{
    Console.WriteLine($"Refused: {e.Code}");
}

When an answer cannot be trusted

Every answer must carry the app's signature, match the request just sent and be within 60 seconds. Otherwise the SDK raises a verification error with one of these codes:

CodeMeaning
unsigned_responseThe answer has no signature
unknown_keySigned by a key this build does not trust
invalid_response_signatureWrong signature, the content was changed
stale_responseThe answer is too old or too new

Treat these like no answer at all. After the next valid answer, the SDK reports the failures to Protect 24/7 (the forged signature signal).

Retries and heartbeat pace

The SDKs try again by themselves, with a growing random wait, two more times by default. maxRetries changes that, and 0 turns it off. fallbackUrls lists other addresses of the same server, tried in turn. These names and nextCheckIn below follow your language's spelling.

  • No answer, or an unsigned 5xx page: only calls that are safe to repeat (init, activate, login, heartbeat, variables, update checks, logout, reports). trial, register, redeem and transfer are never repeated after a lost answer, because they may already have happened.
  • A signed rate_limited, or an unsigned 429 or 503: any call, obeying Retry-After up to 30 seconds.

Only a verified signature changes license state.

nextCheckIn gives the seconds to wait before the next heartbeat: the server's signed nextCheckSeconds, plus a spread of up to a fifth that stays the same for the machine, so thousands of copies do not call at once.

Offline tokens and updates

  • On every plan, activate and heartbeat return an offline token, valid 7 days by default. On Premium the license plan sets the length. It is null only while Online-Only Mode is on. verify_offline / VerifyOffline returns its content while it is valid on this machine. A token copied to another machine, a clock turned back or a revoked license are all refused. A machine that has not heard of a revocation keeps working offline until the token ends.
  • check_updates / CheckUpdatesAsync only returns a release manifest signed by your app key and still fresh; the download helper refuses a file whose sha256 does not match.

Rotating the signing key

Pass every public key the build trusts in the key list (app_public_keys, AppPublicKeys). When you prepare a new key in the Signing keys panel, ship a build that carries both keys first, then activate the new key. See Signing keys and rotation.

How can we help?

Frequently asked

What is ClavisAUH?

A licensing and authentication service for desktop software: license keys, device binding, end-user sign-in and signed responses. All run from one dashboard

Why can't a cracker fake your server?

The SDK only trusts answers signed with your app's private key. That key never leaves our servers, so a fake server can't sign and gets rejected

What ends up in my binary?

Your app id and public key. Nothing secret, because each device makes its own key pair on first run

Does it work offline?

Yes. Every plan gets a signed offline token for 7 days, and your app checks it locally. Premium lets you choose how long. A revoked license can keep working offline for that time, unless Online-Only Mode is on

Which languages are supported?

JavaScript and TypeScript today. C++, C# and Python are next, on the same open protocol

Is Basic really free?

Yes. No time limit, no card. Move to Premium when you need more

Get in touch