Deploy project

Takes a built site live at https://<slug>.hanzo.app in one call.

POST /v1/project/{slug}/deploy

Addresshttps://api.hanzo.ai/v1/project/{slug}/deploy
MethodPOST
Operationpost_project_by_slug_deploy
AuthAuthorization: Bearer $HANZO_API_KEY

Takes a built site live at https://<slug>.hanzo.app in one call. The body is the site itself — a zip or tar.gz holding index.html at its root (or a single wrapper directory that does), sent raw or as a multipart file part. It is unpacked to the site's own storage prefix and served immediately, answering the finished deployment.

It is bounded by the edge body limit (16 MiB by default), and that bound is the whole reason the other path exists: an oversized POST is refused by the server BEFORE any handler runs and surfaces as an opaque 400 Error when parsing request that reads like a malformed payload rather than a size cap. A site too large for one archive opens a deployment with POST /v1/project/{slug}/deployments instead and writes its files straight to storage against the scoped grant that answers with — no body limit, and no bytes through this API at all.

Publishing is free: no deploy is charged, and an org with no balance can publish and republish. A site is billed for the storage its org holds past the free tier, metered hourly; an org already past the tier must be able to pay a month of that storage, or the upload is refused 402 (503 when commerce is unreachable) BEFORE anything is parsed or written. A failed upload never flips the live site, and a redeploy replaces the site's files and answers the SAME URL, because slug and apex are stable.

Scope: a validated principal is required (401 without one) and the site is resolved within that principal's org, so another tenant's slug is a 404. Object storage must be configured (503); an archive that does not walk is a 400 and one over the size cap is a 413.

Request

2 fields, body application/octet-stream.

FieldInTypeRequiredDescription
slugpathstringyes
(body)bodystring (binary)yes

Response

StatusBodyMeaning
2XXprojectsDeploymentSuccess

2XX body — 22 fields.

FieldInTypeAlwaysDescription
bucketbodystring—
bytesbodyinteger—
commitbodystring—
createdAtbodyinteger—
filesbodyinteger—
idbodystring—
liveUrlbodystring—
messagebodystring—
prefixbodystring—
projectIdbodystring—
sourcebodystring—
statusbodystring—
updatedAtbodyinteger—
uploadbodyprojectsUploadGrant—
upload.copybodyboolean—
upload.expiresAtbodyinteger—
upload.fieldsbodyobject—
upload.fields.*bodystring—
upload.maxBytesbodyinteger—
upload.prefixbodystring—
upload.urlbodystring—
versionbodyinteger—

Failure carries the platform error shape — see Errors.

Examples

hanzo project deploy <slug>
import { Configuration, ProjectApi } from 'hanzoai';

const api = new ProjectApi(new Configuration({ accessToken: process.env.HANZO_API_KEY }));
const { data } = await api.postProjectBySlugDeploy({ slug: 'slug' });
from hanzoai.cloud import ApiClient, Configuration
from hanzoai.cloud.api import ProjectApi

client = ApiClient(Configuration(access_token=os.environ["HANZO_API_KEY"]))
result = ProjectApi(client).post_project_by_slug_deploy(slug='slug')
cfg := hanzoai.NewConfiguration()
cfg.AddDefaultHeader("Authorization", "Bearer "+os.Getenv("HANZO_API_KEY"))
client := hanzoai.NewAPIClient(cfg)

resp, _, err := client.ProjectAPI.PostProjectBySlugDeploy(context.Background()).Execute()
if err != nil {
	return err
}
use hanzo_client::apis::{configuration::Configuration, project_api};

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

let result = project_api::post_project_by_slug_deploy(&cfg, Default::default()).await?;
import ai.hanzo.cloud.ApiClient;
import ai.hanzo.cloud.api.ProjectApi;

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

var result = new ProjectApi(client).postProjectBySlugDeploy();
curl -X POST https://api.hanzo.ai/v1/project/<slug>/deploy \
  -H "Authorization: Bearer $HANZO_API_KEY"

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

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_project"
         }
       }
     }'

Project API · All Hanzo APIs · Interactive reference

Was this page useful?