Programmatisches Encoding — nur für Ultra-Abonnenten. Erstellen Sie einen Schlüssel unter Konto → API-Schlüssel und fügen Sie ihn direkt in die unten stehenden Endpoint-URLs ein.
| Plan | Pro Datei max. | API-Zugang | Multipart erforderlich? |
|---|---|---|---|
| Free | 5 KB | — | — |
| Pro | 100 MB | — | Nein (einzelner PUT genügt) |
| Ultra | 300 MB | Ja | Dateien >100 MB müssen Multipart nutzen |
Cloudflare-Edge limitiert einen einzelnen Request-Body auf 100 MB. Größere Dateien müssen in 50-MB-Parts geteilt und über die Multipart-Endpoints unten gesendet werden.
POST https://webhook.binaryphp.com/upload/<api_key>
X-BPHP-Filename: plugin.php # erforderlich, Endung .php oder .zip
X-BPHP-Domain: app.example.com,*.example.com
X-BPHP-Mac: aa:bb:cc:dd:ee:ff # optional
X-BPHP-Expire: 2027-12-31 # optional
X-BPHP-Webhook: https://you.example.com/wh # optional, für asynchrone Benachrichtigung
<Datei-Binärinhalt als Request-Body>
→ 200 {
"job_id": "...",
"download_url": "https://...presigned R2 URL...",
"expires_at": "2026-05-09T...",
"size": 12345,
"license": { "domains": [...], ... }
}
curl-Einzeiler:
curl -X POST https://webhook.binaryphp.com/upload/$API_KEY \
-H "X-BPHP-Filename: plugin.php" \
-H "X-BPHP-Domain: app.example.com" \
--data-binary @plugin.php
Drei Schritte: init → einzelne PUTs für jeden Part → complete.
POST https://webhook.binaryphp.com/upload/<api_key>/init
X-BPHP-Filename: bigplugin.zip
X-BPHP-Total-Size: 200000000
→ 200 {
"job_id": "...",
"upload_id": "...", # R2-Multipart-Opaque-ID
"r2_key": "uploads/<job_id>.zip",
"part_size": 52428800, # empfohlen 50 MB pro Part
"part_count": 4,
"max_part_size": 104857600, # 100-MB-Hardlimit
"parts": [
{ "part_no": 1, "upload_url": "https://...presigned PUT..." },
{ "part_no": 2, "upload_url": "..." },
{ "part_no": 3, "upload_url": "..." },
{ "part_no": 4, "upload_url": "..." }
]
}
upload_urlDiese presigned URLs gehen direkt an R2 und verbrauchen keine
Worker-Bandbreite. Der ETag-Header jedes PUT-Response muss gesammelt
und im complete-Schritt mitgesendet werden:
PUT <upload_url>
<part_size Bytes ab Offset (part_no-1)*part_size der Datei lesen>
← 200 OK
ETag: "abc123def456..."
Jeder Part muss ≥5 MB (nur der letzte darf kleiner sein) und ≤100 MB sein.
POST https://webhook.binaryphp.com/upload/<api_key>/complete
Content-Type: application/json
{
"upload_id": "...",
"r2_key": "uploads/<job_id>.zip",
"filename": "bigplugin.zip",
"parts": [
{ "part_no": 1, "etag": "\"abc...\"" },
{ "part_no": 2, "etag": "\"def...\"" },
{ "part_no": 3, "etag": "\"ghi...\"" },
{ "part_no": 4, "etag": "\"jkl...\"" }
],
"domain": "app.example.com",
"mac": "",
"expire": "2027-12-31",
"plugin": "",
"webhook": ""
}
→ 200 { "job_id", "download_url", "expires_at", "size", "license" }
Wenn ein Part-Upload zwischendurch fehlschlägt, rufen Sie
/upload/<api_key>/abort mit { upload_id, r2_key } auf,
damit übriggebliebene Parts nicht in R2 verbleiben und Kosten verursachen.
Setzen Sie X-BPHP-Webhook (oder "webhook" im Complete-Body),
um encode.completed-Events zu erhalten. Benachrichtigungen werden von
Cloudflare-Edge-IPs gesendet, unsere Host-IP wird nicht offengelegt. Der Body wird
mit Ihrem API-Key als Shared Secret per HMAC-SHA256 signiert:
POST <Ihre Webhook-URL>
X-BinaryPHP-Signature: t=1736208000,v1=<hex>
X-BinaryPHP-Event: encode.completed
Content-Type: application/json
{
"event": "encode.completed",
"job_id": "...",
"download_url": "...",
"expires_at": "...",
"size": 12345,
"license": { ... }
}
Verifikationsbeispiel (PHP):
$sig_h = $_SERVER['HTTP_X_BINARYPHP_SIGNATURE'] ?? '';
[$tpart, $vpart] = array_pad(explode(',', $sig_h, 2), 2, '');
$ts = (int) substr($tpart, 2);
$got = substr($vpart, 3);
if (abs(time() - $ts) > 300) http_response_code(401);
$body = file_get_contents('php://input');
$expected = hash_hmac('sha256', "$ts.$body", $YOUR_API_KEY);
if (!hash_equals($expected, $got)) http_response_code(401);
ext-curl. Wählt automatisch zwischen Single- und Multipart-Flow je
nach Dateigröße; bei Fehler abortet R2-Multipart, vermeidet Restkosten.
API_KEY=bphp_live_xxx php upload.php big.zip --domain=app.example.com
requests. Ebenso automatische Erkennung + Abort-Cleanup.
| Statuscode | Bedeutung | Vorgehen |
|---|---|---|
| 401 | Falscher oder widerrufener Schlüssel | In „Konto → API-Schlüssel" neu erstellen |
| 402 | Plan unterstützt diese Operation nicht (z. B. Free + ZIP-Upload) | Plan upgraden |
| 413 | Datei / Content-Length übersteigt Plan-Limit | Auf Multipart wechseln oder Pro→Ultra (300 MB) upgraden |
| 400 | Fehlendes Feld oder Formatfehler (filename, parts etc.) | Response-Body prüfen, das fehlende Feld wird angezeigt |
| 502 | R2-Multipart-Operation fehlgeschlagen | init wiederholen; R2 schlägt gelegentlich (<1%) fehl |