> For the complete documentation index, see [llms.txt](https://docs.licensespring.com/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.licensespring.com/license-api/license-activation-and-deactivation/activate-license-offline-method.md).

# Activate License (Offline Method)

{% hint style="info" %}
Currently we support trial, perpetual and consumption license types for offline activation purposes
{% endhint %}

### Endpoint

* Method: `POST`
* Path: `/api/v4/activate_offline`
* Description: Activates a license using the offline activation flow (base64 payload).

### Authentication

See [License API Authorization](/license-api/license-api-authorization.md).

#### Required headers

* `Date` (string) — RFC7231 GMT date string
* `Authorization` (string) — signature or bearer token

#### Recommended headers

* `Accept: application/json`

### Request

#### Body

The request body is a **base64-encoded, stringified JSON object**.

{% hint style="danger" %}
If using `multipart/form-data`, the `file` form parameter is mandatory.
{% endhint %}

### Schema

The request body is a string representing a base64-encoded JSON object containing all the required activation data.

<details>

<summary><strong>Request body schema (TypeScript + JSON Schema)</strong></summary>

**TypeScript**

```typescript
type LicenseOfflineActivationObject = ({

  // for key-based licenses:
  license_key: string

} | {

  // for user-based licenses:
  username: string
  password: string

}) & {

  // required properties:
  hardware_id: string
  product: string
  signature: string
  date: string

} & ({
  api_key: string // for API key authorization
} | {
  client_id: string // for OAuth authorization
}) & {

  // optional properties:
  request?: string | undefined
  request_id?: string | undefined
  bundle_code?: string | undefined
  license_id?: number | undefined
  is_vm?: boolean | undefined
  vm_info?: string | undefined
  os_ver?: string | undefined
  hostname?: string | undefined
  os_hostname?: string | undefined
  ip?: string | undefined
  ip_local?: string | undefined
  app_ver?: string | undefined
  app_name?: string | undefined
  sdk_ver?: string | undefined
  mac_address?: string | undefined
  include_metadata_string?: boolean | undefined
  variables?: { [key: string]: string } | undefined
}
```

**JSON Schema**

```json
{
  "$schema": "https://json-schema.org/draft/2020-12/schema",
  "type": "object",
  "allOf": [
    {
      "oneOf": [
        {
          "type": "object",
          "properties": {
            "license_key": { "type": "string" }
          },
          "required": ["license_key"],
          "additionalProperties": false
        },
        {
          "type": "object",
          "properties": {
            "username": { "type": "string" },
            "password": { "type": "string" }
          },
          "required": ["username", "password"],
          "additionalProperties": false
        }
      ]
    },
    {
      "type": "object",
      "properties": {
        "api_key": { "type": "string" },
        "client_id": { "type": "string" },
        "request": { "type": "string" },
        "request_id": { "type": "string" },
        "date": { "type": "string" },
        "signature": { "type": "string" },
        "hardware_id": { "type": "string" },
        "product": { "type": "string" },
        "bundle_code": { "type": "string" },
        "license_id": { "type": "number" },
        "is_vm": { "type": "boolean" },
        "vm_info": { "type": "string" },
        "os_ver": { "type": "string" },
        "hostname": { "type": "string" },
        "os_hostname": { "type": "string" },
        "ip": { "type": "string" },
        "ip_local": { "type": "string" },
        "app_ver": { "type": "string" },
        "app_name": { "type": "string" },
        "sdk_ver": { "type": "string" },
        "mac_address": { "type": "string" },
        "include_metadata_string": { "type": "string" },
        "variables": {
          "type": "object",
          "additionalProperties": { "type": "string" }
        }
      },
      "allOf": [
        { "anyOf": [{ "required": ["api_key"] }, { "required": ["client_id"] }] },
        { "anyOf": [{ "required": ["license_key"] }, { "required": ["username", "password"] }] }
      ],
      "required": ["hardware_id", "product", "date", "signature"],
      "additionalProperties": false
    }
  ]
}
```

</details>

### Signature

The request `signature` is constructed and signed with HMAC-SHA256 using the company shared key (or client secret for OAuth). Steps to construct the signing string:

{% stepper %}
{% step %}

### Build the signing string — part 1

Start with:

* The literal string: licenseSpring
* Then a newline
  {% endstep %}

{% step %}

### Build the signing string — part 2

Append:

* The string "date: " plus the date value from the license payload, then a newline
  {% endstep %}

{% step %}

### Build the signing string — part 3

Append:

* Either the license\_key or username value from the payload (whichever is present), then a newline
  {% endstep %}

{% step %}

### Build the signing string — part 4

Append:

* The hardware\_id value from the payload, then a newline
  {% endstep %}

{% step %}

### Build the signing string — part 5

Append:

* The api\_key (or client\_id) value from the payload

Encrypt the complete string using HMAC-SHA256 with the signing key (Shared Key for API key auth, Client Secret for OAuth). Example (Node.js):

```javascript
import crypto from 'node:crypto';

const activationPayload = {
  // ...payload content...
};

// api_key or client_id depending on authorization type used:
const key = (activationPayload.api_key || activationPayload.client_id);

// if using API key authorization: the signing key is the Shared Key
// if using OAuth: the signing key is the Client Secret
const signingKey = '...';

const signingString =
  'licenseSpring\n' +
  'date: ' + activationPayload.date + '\n' +
  (activationPayload.license_key || activationPayload.username) + '\n' +
  activationPayload.hardware_id + '\n' +
  key;

const signature = crypto
  .createHmac('sha256', signingKey)
  .update(signingString)
  .digest('base64');
```

{% endstep %}
{% endstepper %}

### Finalized payload

Stringify the activation object and encode it to base64.

{% tabs %}
{% tab title="JS Browser" %}

```javascript
const activationPayload = {
  // ...payload content...
};
const requestBody = btoa(JSON.stringify(activationPayload));
```

{% endtab %}

{% tab title="nodeJS" %}

```javascript
const activationPayload = {
  // ...payload content...
};
const requestBody = Buffer.from(JSON.stringify(activationPayload)).toString('base64');
```

{% endtab %}
{% endtabs %}

### Examples

Send the base64 payload as the request body. Set the Date and Authorization headers.

{% tabs %}
{% tab title="curl" %}

```bash
curl --location --request POST '/api/v4/activate_offline' \
--header 'Accept: application/json' \
--header 'Date: string' \
--header 'Authorization: string' \
--data-raw '_BASE64_PAYLOAD_HERE_'
```

{% endtab %}

{% tab title="nodejs" %}

```javascript
var request = require('request');
var options = {
  method: 'POST',
  url: '/api/v4/activate_offline',
  headers: {
    'Accept': 'application/json',
    'Date': 'string',
    'Authorization': 'string'
  },
  body: Buffer.from(JSON.stringify(offline_payload)).toString('base64')
};

request(options, function (error, response) {
  if (error) throw new Error(error);
  console.log(response.body);
});
```

{% endtab %}

{% tab title="javascript (fetch)" %}

```javascript
var myHeaders = new Headers();
myHeaders.append("Accept", "application/json");
myHeaders.append("Date", "string");
myHeaders.append("Authorization", "string");

var requestOptions = {
  method: 'POST',
  headers: myHeaders,
  body: btoa(JSON.stringify(offline_payload)),
  redirect: 'follow'
};

fetch("/api/v4/activate_offline", requestOptions)
  .then(response => response.text())
  .then(result => console.log(result))
  .catch(error => console.log('error', error));
```

{% endtab %}

{% tab title="python" %}

```python
import requests

url = "/api/v4/activate_offline"

payload = "_BASE64_PAYLOAD_HERE_"
headers = {
  'Accept': 'application/json',
  'Date': 'string',
  'Authorization': 'string'
}

response = requests.request("POST", url, headers=headers, data=payload)

print(response.text)
```

{% endtab %}

{% tab title="ruby" %}

```ruby
require "uri"
require "net/http"

url = URI("/api/v4/activate_offline")

http = Net::HTTP.new(url.host, url.port)
request = Net::HTTP::Post.new(url)
request["Accept"] = "application/json"
request["Date"] = "string"
request["Authorization"] = "string"
request.body = "_BASE64_PAYLOAD_HERE_"

response = http.request(request)
puts response.read_body
```

{% endtab %}
{% endtabs %}

### Response

<details>

<summary><strong>Response schema (TypeScript + JSON Schema)</strong></summary>

**TypeScript**

```typescript
type InstallationFile = {
  id: number,
  channel: string,
  environment: string,
  version: string,
  installation_file: string,
  hash_md5: string,
  eula_link: string,
  release_date: string | null,
  requires_version: string,
  size: string,
  release_notes_link: string,
};

type LicenseActivationResponseBody = {
  id: number,
  request: string,
  active: boolean,
  allow_grace_period: boolean,
  allow_overages: boolean,
  allow_unlimited_activations: boolean,
  allow_offline_activation: boolean,
  can_borrow: boolean,
  device_id: number,
  hardware_id: string,
  enable_maintenance_period: boolean,
  floating_timeout: number,
  grace_period: number,
  installation_file: InstallationFile,
  is_air_gapped: boolean,
  is_expired: boolean,
  is_floating_cloud: boolean,
  is_floating: boolean,
  is_hardware_key_auth: boolean,
  is_trial: boolean,
  license_signature: string,
  license_signature_v2: string,
  offline_signature: string,
  license_type: string,
  license_template_id: number | null,
  maintenance_period: string | null,
  max_activations: number,
  max_borrow_time: number,
  max_license_users: number,
  max_overages: number,
  max_transfers: number,
  order_store_id: string | null,
  prevent_vm: boolean,
  start_date: string | null,
  times_activated: number,
  transfer_count: number,
  validity_period: string | null,
  is_bundle: boolean | null,
  bundle_license_id: number | null,
  company: { id: number },
  
  product_features: ({
    id: number,
    code: string,
    name?: string,
    product_feature_id: number,
    expiry_date: string | null,
    valid_duration: string | null,
    is_expired: boolean,
    is_global?: boolean,
    metadata: JSON,
    metadata_string?: string,
    can_borrow: boolean,
    max_borrow_time: number,
    feature_type: 'activation' | 'consumption',
    is_floating: boolean,
    is_floating_cloud: boolean,

    // the following properties are only present if is_floating=true or is_floating_cloud=true
    floating_users?: number,
    floating_timeout?: number,

    // the following properties are only present if feature_type=consumption
    max_consumption: number,
    allow_negative_consumptions: boolean,
    allow_unlimited_consumptions: boolean,
    total_consumptions: number,
    allow_overages: boolean,
    max_overages: number,
    reset_consumption: boolean,
    consumption_period: 'daily' | 'weekly' | 'monthly' | 'annually',
  })[],
  
  custom_fields: ({
    name: string,
    data_type: 'number' | 'text' | 'date/time',
    value: string,
  })[],
  
  customer: {
    email: string,
    company_name: string,
    reference: string,
    phone: string,
    first_name: string,
    last_name: string,
    city: string,
    postcode: string,
    state: string,
    country: string,
    address: string,
    customer_account: {
      id: number,
      name: string,
      code: string
    } | null,
    metadata: JSON,
    metadata_string?: string
  },
  
  product_details: {
    product_id: number,
    product_name: string,
    short_code: string,
    authorization_method: 'license-key' | 'user',
    metadata: JSON,
    metadata_string?: string
  },
  
  variables: {
    value: string,
    device_id: number,
    variable: string,
    created_at: string | null,
  }[],
  
  metadata: JSON,
  
  // the following property is only present if is_trial=true
  trial_days: number,
  
  // the following property is only present when is_floating_cloud=true
  floating_in_use: boolean,
  
  // the following properties are only present if is_floating=true or is_floating_cloud=true
  floating_in_use_devices: number,
  floating_users: number,
  
  // the following properties are only present if license_type='consumption'
  max_consumptions: number,
  total_consumptions: number,
  allow_unlimited_consumptions: boolean,
  allow_negative_consumptions: boolean,
  reset_consumption: boolean,
  consumption_period: string | null,
} & ({
  license_key: string,
} | {
  user: {
    id: number,
    email: string,
    first_name: string,
    last_name: string,
    phone_number: string,
    is_initial_password: boolean,
    max_activations: number,
    allow_unlimited_activations: boolean,
    total_activations: number
  }
});
```

**JSON Schema**

```json
{
  "$schema": "https://json-schema.org/draft/2020-12/schema",
  "type": "object",
  "properties": {
    "id": { "type": "number" },
    "request": { "type": "string" },
    "active": { "type": "boolean" },
    "allow_grace_period": { "type": "boolean" },
    "allow_overages": { "type": "boolean" },
    "allow_unlimited_activations": { "type": "boolean" },
    "allow_offline_activation": { "type": "boolean" },
    "can_borrow": { "type": "boolean" },
    "device_id": { "type": "number" },
    "hardware_id": { "type": "string" },
    "enable_maintenance_period": { "type": "boolean" },
    "floating_timeout": { "type": "number" },
    "grace_period": { "type": "number" },

    "installation_file": {
      "type": "object",
      "properties": {
        "id": { "type": "number" },
        "channel": { "type": "string" },
        "environment": { "type": "string" },
        "version": { "type": "string" },
        "installation_file": { "type": "string" },
        "hash_md5": { "type": "string" },
        "eula_link": { "type": "string" },
        "release_date": { "type": ["string", "null"] },
        "requires_version": { "type": "string" },
        "size": { "type": "string" },
        "release_notes_link": { "type": "string" }
      }
    },

    "is_air_gapped": { "type": "boolean" },
    "is_expired": { "type": "boolean" },
    "is_floating_cloud": { "type": "boolean" },
    "is_floating": { "type": "boolean" },
    "is_hardware_key_auth": { "type": "boolean" },
    "is_trial": { "type": "boolean" },

    "license_signature": { "type": "string" },
    "license_signature_v2": { "type": "string" },
    "offline_signature": { "type": "string" },
    "license_type": { "type": "string" },

    "license_template_id": { "type": ["number", "null"] },
    "maintenance_period": { "type": ["string", "null"] },

    "max_activations": { "type": "number" },
    "max_borrow_time": { "type": "number" },
    "max_license_users": { "type": "number" },
    "max_overages": { "type": "number" },
    "max_transfers": { "type": "number" },

    "order_store_id": { "type": ["string", "null"] },
    "prevent_vm": { "type": "boolean" },
    "start_date": { "type": ["string", "null"] },

    "times_activated": { "type": "number" },
    "transfer_count": { "type": "number" },
    "validity_period": { "type": ["string", "null"] },

    "is_bundle": { "type": ["boolean", "null"] },
    "bundle_license_id": { "type": ["number", "null"] },

    "company": {
      "type": "object",
      "properties": {
        "id": { "type": "number" }
      }
    },

    "product_features": {
      "type": "array",
      "items": {
        "type": "object",
        "properties": {
          "id": { "type": "number" },
          "code": { "type": "string" },
          "name": { "type": "string" },
          "product_feature_id": { "type": "number" },
          "expiry_date": { "type": ["string", "null"] },
          "valid_duration": { "type": ["string", "null"] },
          "is_expired": { "type": "boolean" },
          "is_global": { "type": "boolean" },
          "metadata": {},
          "metadata_string": { "type": "string" },
          "can_borrow": { "type": "boolean" },
          "max_borrow_time": { "type": "number" },
          "feature_type": {
            "type": "string",
            "enum": ["activation", "consumption"]
          },
          "is_floating": { "type": "boolean" },
          "is_floating_cloud": { "type": "boolean" },

          "floating_users": { "type": "number" },
          "floating_timeout": { "type": "number" },

          "max_consumption": { "type": "number" },
          "allow_negative_consumptions": { "type": "boolean" },
          "allow_unlimited_consumptions": { "type": "boolean" },
          "total_consumptions": { "type": "number" },
          "allow_overages": { "type": "boolean" },
          "max_overages": { "type": "number" },
          "reset_consumption": { "type": "boolean" },
          "consumption_period": {
            "type": "string",
            "enum": ["daily", "weekly", "monthly", "annually"]
          }
        }
      }
    },

    "custom_fields": {
      "type": "array",
      "items": {
        "type": "object",
        "properties": {
          "name": { "type": "string" },
          "data_type": {
            "type": "string",
            "enum": ["number", "text", "date/time"]
          },
          "value": { "type": "string" }
        }
      }
    },

    "customer": {
      "type": "object",
      "properties": {
        "email": { "type": "string" },
        "company_name": { "type": "string" },
        "reference": { "type": "string" },
        "phone": { "type": "string" },
        "first_name": { "type": "string" },
        "last_name": { "type": "string" },
        "city": { "type": "string" },
        "postcode": { "type": "string" },
        "state": { "type": "string" },
        "country": { "type": "string" },
        "address": { "type": "string" },

        "customer_account": {
          "type": ["object", "null"],
          "properties": {
            "id": { "type": "number" },
            "name": { "type": "string" },
            "code": { "type": "string" }
          }
        },

        "metadata": {},
        "metadata_string": { "type": "string" }
      }
    },

    "product_details": {
      "type": "object",
      "properties": {
        "product_id": { "type": "number" },
        "product_name": { "type": "string" },
        "short_code": { "type": "string" },
        "authorization_method": {
          "type": "string",
          "enum": ["license-key", "user"]
        },
        "metadata": {},
        "metadata_string": { "type": "string" }
      }
    },

    "variables": {
      "type": "array",
      "items": {
        "type": "object",
        "properties": {
          "value": { "type": "string" },
          "device_id": { "type": "number" },
          "variable": { "type": "string" },
          "created_at": { "type": ["string", "null"] }
        }
      }
    },

    "metadata": {},

    "trial_days": { "type": "number" },
    "floating_in_use": { "type": "boolean" },
    "floating_in_use_devices": { "type": "number" },
    "floating_users": { "type": "number" },

    "max_consumptions": { "type": "number" },
    "total_consumptions": { "type": "number" },
    "allow_unlimited_consumptions": { "type": "boolean" },
    "allow_negative_consumptions": { "type": "boolean" },
    "reset_consumption": { "type": "boolean" },
    "consumption_period": { "type": ["string", "null"] }
  },

  "oneOf": [
    {
      "properties": {
        "license_key": { "type": "string" }
      }
    },
    {
      "properties": {
        "user": {
          "type": "object",
          "properties": {
            "id": { "type": "number" },
            "email": { "type": "string" },
            "first_name": { "type": "string" },
            "last_name": { "type": "string" },
            "phone_number": { "type": "string" },
            "is_initial_password": { "type": "boolean" },
            "max_activations": { "type": "number" },
            "allow_unlimited_activations": { "type": "boolean" },
            "total_activations": { "type": "number" }
          }
        }
      }
    }
  ]
}
```

</details>

### Response signatures

The response contains two digital signatures:

* license\_signature: HMAC-SHA256 signature explained in [Response Signature](/license-api/license-api-authorization/response-signature.md).
* offline\_signature: HMAC-SHA256 signature specific to this endpoint, constructed identically to the request `signature` generation but using the response `date` value.

### Errors

If an error occurs, the response will have an HTTP status code of 400 or higher, and the response body will contain an error description in the following format:

```typescript
{
  status: number,
  code: string,
  message: string
}
```

JSON Schema

```json
{
  "$schema": "https://json-schema.org/draft/2020-12/schema",
  "type": "object",
  "properties": {
    "status": { "type": "number" },
    "code": { "type": "string" },
    "message": { "type": "string" }
  },
  "required": [
    "status",
    "code",
    "message"
  ],
  "additionalProperties": false
}
```

List of exceptions

* missing\_headers (400): some headers are missing
  * when missing authorization or date headers
* missing\_parameters (400): some parameters are missing in the request
  * when no request body at all or no file found in request body
* authorization\_missing\_params (400): some parameters are missing in authorization
  * when request body is not properly base64 encoded
  * when file is missing in request body (multipart case)
  * when license\_key or hardware\_id body parameters are missing
  * when data body parameter is missing
  * when api\_key parameter is missing

{% hint style="info" %}
If you want to use this API endpoint directly, instead of using an SDK (which does most of the heavy lifting for you), please contact us for additional instructions.
{% endhint %}

### Guide on offline licensing

If any aspect of the offline licensing model remains unclear or raises questions, see: [Offline License Activation](/license-entitlements/license-activation-types/offline-license-activation.md).


---

# Agent Instructions
This documentation is published with GitBook. GitBook is the documentation platform designed so that both humans and AI agents can read, navigate, and reason over technical content effectively. Learn more at gitbook.com.

## Querying This Documentation
If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://docs.licensespring.com/license-api/license-activation-and-deactivation/activate-license-offline-method.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
