Licenses
The Licenses API endpoints helps you manage licenses purchased through your store.
License instances are part of a license key. Each license key can be linked to multiple instances. Whenever you activate a license key, you create a new instance of the license key.
The license key model
The license key model represents a single license key purchased by a customer.
Properties
- Name
id- Type
- integer
- Description
(read-only) The unique identifier for the license key.
- Name
key- Type
- string
- Description
(read-only) The actual license key string
- Name
limit- Type
- integer | null
- Description
The maximum number of instances this key can be activated on.
nullmeans unlimited activations.
- Name
active- Type
- boolean
- Description
Whether the license key is currently active which you can modify via the API and which is unrelated to the status. Inactive keys cannot be activated or validated successfully.
- Name
status- Type
- string
- Description
(read-only) The status of the license key, one of:
ACTIVE,INACTIVE,EXPIRED
- Name
expires_at- Type
- timestamp | null
- Description
The timestamp when the license key expires.
nullmeans the license will never expire.
- Name
is_expired- Type
- boolean
- Description
Whether the license key is expired.
- Name
store_id- Type
- integer
- Description
(read-only) The ID of the store this license key belongs to.
- Name
order_id- Type
- integer | null
- Description
(read-only) The ID of the order associated with this license key.
- Name
invoice_id- Type
- integer | null
- Description
(read-only) The ID of the associated invoice V2, if applicable.
- Name
product_id- Type
- integer
- Description
(read-only) The ID of the product this license is for.
- Name
variant_id- Type
- integer
- Description
(read-only) The ID of the specific product variant this license is for.
- Name
customer_id- Type
- integer
- Description
(read-only) The ID of the customer that purchased this license key.
- Name
subscription_id- Type
- integer | null
- Description
(read-only) The ID of the associated subscription, if applicable.
- Name
created_at- Type
- timestamp
- Description
(read-only) Time at which the license key was created.
- Name
updated_at- Type
- timestamp
- Description
(read-only) Time at which the license key was last updated.
The license instance model
The license instance model represents a single activation of a license key on a specific device or identifier.
Properties
- Name
id- Type
- string (uuid)
- Description
(read-only) The unique identifier (UUID) of the license instance. This is the
instance_idused for validation.
- Name
license_key_id- Type
- integer
- Description
(read-only) The unique identifier for the parent license key which this instance is linked to.
- Name
name- Type
- string
- Description
(read-only) The name provided during activation, which you can use to identify this instance (e.g., the customer's email or HWID).
- Name
store_id- Type
- integer
- Description
(read-only) The ID of the store this instance belongs to.
- Name
created_at- Type
- timestamp
- Description
(read-only) Time at which the instance was created (activation time).
- Name
updated_at- Type
- timestamp
- Description
(read-only) Time at which the instance was last updated.
Activate a license key
This endpoint activates a given license key and creates an instance of the license key. Activation registers a unique identifier (instance name) against the license key. If the activation is successful, it returns the details of the newly created LicenseKeyInstance, including its unique id which should be stored by the client/application for future validation.
Activation can fail if:
- The license key does not exist.
- The license key is inactive (
activeis false). - The license key has expired (
expires_atis in the past). - The activation limit (
limit) has been reached.
Required attributes
- Name
license_key- Type
- string
- Description
The license key string to activate.
- Name
instance_name- Type
- string
- Description
A unique name or identifier for this instance (e.g., user email, HWID, server hostname). This name helps you identify this instance.
Request
$request = new HttpRequest();
$request->setUrl('https://sell.app/api/v2/licenses/activate');
$request->setMethod(HTTP_METH_POST);
$request->setHeaders([
'Content-Type' => 'application/json',
'accept' => 'application/json',
'Authorization' => 'Bearer YOUR_API_TOKEN'
]);
$request->setBody(json_encode([
'license_key' => '01965f1d-f038-7116-b57f-9e7ecb4e7b8f',
'instance_name' => 'zezima@osrs.com'
]));
try {
$response = $request->send();
echo $response->getBody();
} catch (HttpException $ex) {
echo $ex;
}
Response (Success 200)
{
"name": "zezima@osrs.com",
"store_id": 1,
"license_key_id": 1,
"id": "9ebd2de0-61fb-4966-a319-2a75b27f5ddf", // Instance ID to store
"updated_at": "2025-04-22T20:08:39.000000Z",
"created_at": "2025-04-22T20:08:39.000000Z"
}
Response (Error 422)
{
"message": "This license key has reached its activation limit.",
"license_key": {
"id": 1,
"status": "ACTIVE", // Current status
"expired_at": "2025-01-01T00:00:00.000000Z" // Expiration date
}
}
On successful activation, store the returned instance id. You'll need it for validation.
Validate a license key
Checks if a given license key and instance ID pair represents a valid, active license activation. This is the primary endpoint to use within your application to verify a user's license status periodically.
Validation checks if:
- The license key exists.
- The license key is currently
active. - The license key has not expired (
expires_at). - The provided
instance_idmatches an existing activation for that license key.
Required attributes
- Name
license_key- Type
- string
- Description
The license key string to validate.
- Name
instance_id- Type
- string
- Description
The unique ID of the instance that was returned upon successful activation.
Request
$request = new HttpRequest();
$request->setUrl('https://sell.app/api/v2/licenses/validate');
$request->setMethod(HTTP_METH_POST);
$request->setHeaders([
'Content-Type' => 'application/json',
'accept' => 'application/json',
'Authorization' => 'Bearer YOUR_API_TOKEN'
]);
$request->setBody(json_encode([
'license_key' => '01965f1d-f038-7116-b57f-9e7ecb4e7b8f',
'instance_id' => '9ebd3be0-de72-4da7-805e-bc99d1ac1186'
]));
try {
$response = $request->send();
echo $response->getBody();
} catch (HttpException $ex) {
echo $ex;
}
Response (Success 200)
{
"valid": true,
"license_key": {
"id": 1,
"key": "01965f1d-f038-7116-b57f-9e7ecb4e7b8f",
"limit": 4,
"active": 1,
"status": "ACTIVE",
"expires_at": "2025-05-22T20:08:39.000000Z",
"is_expired": 0,
"store_id": 1,
"order_id": 1,
"invoice_id": 1,
"product_id": 218,
"variant_id": 228,
"customer_id": 1,
"subscription_id": null,
"created_at": "2025-04-22T20:08:39.000000Z",
"updated_at": "2025-04-22T20:08:39.000000Z",
"instances_count": 4
},
"instance": {
"id": "9ebd3be0-de72-4da7-805e-bc99d1ac1186",
"license_key_id": 1,
"name": "zezima@osrs.com",
"store_id": 1,
"created_at": "2025-04-22T21:05:06.000000Z",
"updated_at": "2025-04-22T21:05:06.000000Z"
}
}
Response (Invalid 422)
{
"message": "License key not found"
}
The primary check should be the valid boolean field in the response. If true, the application can proceed. If false, access should be restricted. The license_key and instance objects provide additional context.
List all license keys
Retrieves a paginated list of all license keys associated with your store. Standard pagination parameters (limit, page) can be used.
Refer to the license key model section for details on the returned object structure.
Optional Query Parameters
- Name
limit- Type
- integer
- Description
Limit the number of license keys returned per page.
- Name
page- Type
- integer
- Description
The page number to retrieve.
Request
$request = new HttpRequest();
$request->setUrl('https://sell.app/api/v2/license-keys'); // Add ?limit=10&page=2 for pagination
$request->setMethod(HTTP_METH_GET);
$request->setHeaders([
'accept' => 'application/json',
'Authorization' => 'Bearer YOUR_API_TOKEN'
]);
try {
$response = $request->send();
echo $response->getBody();
} catch (HttpException $ex) {
echo $ex;
}
Response
{
"data": [
{
"id": 1,
"key": "01965f1d-f038-7116-b57f-9e7ecb4e7b8f",
"limit": 4,
"active": 1,
"status": "ACTIVE",
"expires_at": "2025-05-22T20:08:39.000000Z",
"is_expired": 0,
"store_id": 1,
"order_id": 1,
"invoice_id": 1,
"product_id": 1,
"variant_id": 1,
"customer_id": 1,
"subscription_id": null,
"created_at": "2025-04-22T20:08:39.000000Z",
"updated_at": "2025-04-22T20:08:39.000000Z"
}
]
}
Retrieve a license key
Retrieves the details of a specific license key by its unique ID (not key!)
Refer to the license key model section for details on the returned object structure.
Required attributes
- Name
id- Type
- integer
- Description
The ID of the license key to retrieve.
Request
$request = new HttpRequest();
$request->setUrl('https://sell.app/api/v2/license-keys/1');
$request->setMethod(HTTP_METH_GET);
$request->setHeaders([
'accept' => 'application/json',
'Authorization' => 'Bearer YOUR_API_TOKEN'
]);
try {
$response = $request->send();
echo $response->getBody();
} catch (HttpException $ex) {
echo $ex;
}
Response
{
"data": {
"id": 1,
"key": "01965f1d-f038-7116-b57f-9e7ecb4e7b8f",
"limit": 4,
"active": 1,
"status": "ACTIVE",
"expires_at": "2025-05-22T20:08:39.000000Z",
"is_expired": 0,
"store_id": 1,
"order_id": 1,
"invoice_id": 1,
"product_id": 1,
"variant_id": 1,
"customer_id": 1,
"subscription_id": null,
"created_at": "2025-04-22T20:08:39.000000Z",
"updated_at": "2025-04-22T20:08:39.000000Z"
}
}
Update a license key
Updates specific properties of a license key. You can modify the activation limit, expiration date, and active status.
If you decrease the limit to a value lower than the current instances_count, the oldest instances will be automatically deleted to match the new limit.
Required attributes
- Name
id- Type
- integer
- Description
The ID of the license key to update.
Optional attributes
- Name
limit- Type
- integer | null
- Description
New activation limit (minimum 1). Set to
nullfor unlimited.
- Name
expires_at- Type
- timestamp | null
- Description
New expiration date (must be in the future). Set to
nullfor no expiration. Format:YYYY-MM-DD HH:MM:SS.
- Name
active- Type
- boolean
- Description
Set to
trueto activate orfalseto deactivate the license key and its instances.
Request
$request = new HttpRequest();
$request->setUrl('https://sell.app/api/v2/license-keys/1');
$request->setMethod(HTTP_METH_PATCH); // Use PATCH
$request->setHeaders([
'Content-Type' => 'application/json',
'accept' => 'application/json',
'Authorization' => 'Bearer YOUR_API_TOKEN'
]);
$request->setBody(json_encode([
'limit' => 10,
'expires_at' => '2025-05-03 20:00:00',
'active' => false
]));
try {
$response = $request->send();
echo $response->getBody();
} catch (HttpException $ex) {
echo $ex;
}
Response
{
"data": {
"id": 1,
"key": "01965f1d-f038-7116-b57f-9e7ecb4e7b8f",
"limit": 10,
"active": 0,
"status": "ACTIVE",
"expires_at": "2025-05-03T20:00:00.000000Z",
"is_expired": 0,
"store_id": 1,
"order_id": 1,
"invoice_id": 1,
"product_id": 1,
"variant_id": 1,
"customer_id": 1,
"subscription_id": null,
"created_at": "2025-04-22T20:08:39.000000Z",
"updated_at": "2025-04-22T21:20:51.000000Z",
"instances_count": 4
}
}