# Get download

URL: https://docs.hanzo.ai/docs/openapi/licensing/get-licensing-download-by-release

> Resolves a release to its artifact, gated on a valid license.

`GET /v1/licensing/download/{release}`

> [Licensing →](https://docs.hanzo.ai/docs/openapi/licensing) · [All API references →](https://docs.hanzo.ai/docs/openapi) · [Get started →](https://docs.hanzo.ai/docs/guides)

|               |                                                        |
| ------------- | ------------------------------------------------------ |
| **Address**   | `https://api.hanzo.ai/v1/licensing/download/{release}` |
| **Method**    | `GET`                                                  |
| **Operation** | `get_licensing_download_by_release`                    |
| **Auth**      | `Authorization: Bearer $HANZO_API_KEY`                 |

Resolves a release to its artifact, gated on a valid license.

The gate is the LICENSE token, not the IAM bearer: being signed in is not
permission to download a paid binary — holding a good license for it is. The
token must verify against this deployment's public key, be unrevoked, be
scoped to the release's app, and carry every feature the release requires.
Present it as the `X-License-Token` header (preferred, since a header does not
land in proxy logs) or as `?token=`.

The response pairs the artifact URL with its cosign signature so the client
verifies the binary BEFORE trusting it: a signed URL alone proves where the
bytes came from, not what they are. A yanked release is 410 Gone.

## Request

3 fields.

| Field             | In     | Type   | Required | Description |
| ----------------- | ------ | ------ | -------- | ----------- |
| `release`         | path   | string | yes      |             |
| `token`           | query  | string | —        |             |
| `X-License-Token` | header | string | —        |             |

## Response

| Status    | Body                   | Meaning |
| --------- | ---------------------- | ------- |
| `200`     | licensing.ReleaseAsset | ok      |
| `default` | problem-details        | refused |

`200` body — 16 fields.

| Field                      | In   | Type              | Always | Description                                                                                                      |
| -------------------------- | ---- | ----------------- | ------ | ---------------------------------------------------------------------------------------------------------------- |
| `cosign_cert`              | body | string            | —      |                                                                                                                  |
| `cosign_signature`         | body | string            | —      |                                                                                                                  |
| `download_url`             | body | string            | —      | DownloadURL is a short-lived signed URL to the artifact bytes.                                                   |
| `release`                  | body | licensing.Release | —      |                                                                                                                  |
| `release.app_id`           | body | string            | —      | AppID scopes the release to an app build ("hanzo" \| "lux" \| "zoo").                                            |
| `release.artifact_ref`     | body | string            | —      | ArtifactRef is where the binary lives (object-store key / OCI ref / path).                                       |
| `release.cosign_cert`      | body | string            | —      | CosignCert is the cosign/Fulcio cert (keyless) or public key ref used to verify CosignSignature.                 |
| `release.cosign_signature` | body | string            | —      | CosignSignature is the base64 cosign signature over the artifact digest.                                         |
| `release.created_at`       | body | integer (int64)   | —      |                                                                                                                  |
| `release.id`               | body | string            | —      | ID is the release identifier, e.g. "engine-rocm-0.4.2-linux-amd64".                                              |
| `release.min_features`     | body | string\[]         | —      | MinFeatures, when set, are features the license must include to download.                                        |
| `release.platform`         | body | string            | —      | Platform is "\<os>/\<arch>", e.g. "linux/amd64".                                                                 |
| `release.product`          | body | string            | —      | Product is the licensed product this artifact belongs to (commerce SKU): "engine" for every one of those builds. |
| `release.sha256`           | body | string            | —      | SHA256 is the hex digest of the artifact (integrity + cosign subject).                                           |
| `release.version`          | body | string            | —      | Version is the semantic version of the binary.                                                                   |
| `release.yanked`           | body | boolean           | —      | Yanked marks a pulled release (download refused; tokens may be revoked release-scoped too).                      |

Failure carries the platform error shape — see [Errors](https://docs.hanzo.ai/docs/errors).

## Examples

**CLI**

```bash
hanzo licensing download get <release>
```

**SDK**

**.ts**

```ts
import { Configuration, LicensingApi } from 'hanzoai';

const api = new LicensingApi(new Configuration({ accessToken: process.env.HANZO_API_KEY }));
const { data } = await api.getLicensingDownloadByRelease({ release: 'release' });
```

**.py**

```python
from hanzoai.cloud import ApiClient, Configuration
from hanzoai.cloud.api import LicensingApi

client = ApiClient(Configuration(access_token=os.environ["HANZO_API_KEY"]))
result = LicensingApi(client).get_licensing_download_by_release(release='release')
```

**.go**

```go
cfg := hanzoai.NewConfiguration()
cfg.AddDefaultHeader("Authorization", "Bearer "+os.Getenv("HANZO_API_KEY"))
client := hanzoai.NewAPIClient(cfg)

resp, _, err := client.LicensingAPI.GetLicensingDownloadByRelease(context.Background()).Execute()
if err != nil {
	return err
}
```

**.rs**

```rust
use hanzo_client::apis::{configuration::Configuration, licensing_api};

let mut cfg = Configuration::new();
cfg.bearer_access_token = std::env::var("HANZO_API_KEY").ok();

let result = licensing_api::get_licensing_download_by_release(&cfg, Default::default()).await?;
```

**.java**

```java
import ai.hanzo.cloud.ApiClient;
import ai.hanzo.cloud.api.LicensingApi;

ApiClient client = new ApiClient();
client.setBearerToken(System.getenv("HANZO_API_KEY"));

var result = new LicensingApi(client).getLicensingDownloadByRelease();
```

**HTTP**

```bash
curl https://api.hanzo.ai/v1/licensing/download/<release> \
  -H "Authorization: Bearer $HANZO_API_KEY"
```

**MCP**

MCP reaches **licensing** through the `licensing` tool, which names its 9 operations with its own verbs — this one among them, under a name only MCP declares. `describe` explains any of them:

```bash
curl -X POST https://api.hanzo.ai/v1/mcp \
  -H "Content-Type: application/json" \
  -d '{
       "jsonrpc": "2.0",
       "id": 1,
       "method": "tools/call",
       "params": {
         "name": "describe",
         "arguments": {
           "op": "get_licensing_download"
         }
       }
     }'
```

---

[Licensing API](https://docs.hanzo.ai/docs/openapi/licensing) · [All Hanzo APIs](https://docs.hanzo.ai/docs/openapi) · [Interactive reference](https://docs.hanzo.ai/docs/openapi/reference)
