Python · Virtual Try-On API
Virtual Try-On API trong Python
Không cần pip install photta — tài liệu Photta chính thức khuyến nghị sử dụng thư viện requests. Một wrapper 30 dòng có thể tích hợp vào Django, FastAPI, Celery workers và Lambda handlers mà không cần thủ tục phức tạp nào khác.
Tóm tắt trong một câu
Cài đặt `requests`, tải `PHOTTA_API_KEY` từ môi trường, viết một wrapper `photta_request()` để gửi `Authorization: Bearer photta_live_xxx` và raise lỗi `PhottaError` có kiểu dữ liệu cho các phản hồi không phải 2xx, sau đó POST tới `/tryon/apparel` và poll `/tryon/apparel/:id` mỗi 3 giây cho đến khi `data.status == 'completed'` — thường trong vòng 1.5 đến 4 phút.
Đã cập nhật · 2026-04-19
Yêu cầu đầu tiên của bạn
import time
from photta import photta_request, PhottaError
# 1. Submit the job
created = photta_request("POST", "/tryon/apparel", json={
"product_type": "dress",
"product_images": ["https://example.com/dress.jpg"],
"mannequin_id": "mnq_athena_ts",
"pose_id": "pose_standing_front",
"resolution": "2K",
"aspect_ratio": "3:4",
})
generation_id = created["data"]["id"]
# 2. Poll every 3 seconds. Upper bound: 120 attempts ≈ 6 minutes,
# comfortably above the documented 1.5–4 minute window.
for _ in range(120):
result = photta_request("GET", f"/tryon/apparel/{generation_id}")
status = result["data"]["status"]
if status == "completed":
print("Result:", result["data"]["output_url"])
break
if status == "failed":
raise RuntimeError(result["data"]["error_message"])
time.sleep(3)Kỳ vọng gì
Typical completion
1–3min
2K / 4K credits
4 / 6
Styles
2
Batch-ready
yes
Cách hoạt động
Virtual Try-On API trong Python
Năm bước, không có thư viện phụ thuộc riêng của Photta — requests xử lý được tất cả.
- 01
Bước 1
Đăng ký và tạo key
Cùng quy trình như mọi ngôn ngữ khác: ai.photta.app → Nhà phát triển → Tạo API key. Key bắt đầu bằng `photta_live_` và hoạt động trên mọi tính năng của Photta.
- 02
Bước 2
Tải key từ env
Thiết lập `PHOTTA_API_KEY` trong môi trường và đọc nó qua `os.environ`. Trong FastAPI hoặc Django, hãy tải nó một lần khi khởi động vào một module settings. Đừng nhúng key vào mã nguồn hoặc lịch sử Git công khai.
- 03
Bước 3
Viết một requests wrapper
Một hàm `photta_request()` dài 30 dòng để xử lý base URL, Authorization header, JSON serialization và chuyển đổi lỗi. Đó là lớp trừu tượng duy nhất bạn cần cho đến khi Python SDK ra mắt.
- 04
Bước 4
Gửi yêu cầu và poll
POST tới `/tryon/apparel` để lấy ID tạo ảnh, sau đó poll `/tryon/apparel/:id` mỗi 3 giây. Trong Celery hoặc RQ, hãy chia vòng lặp poll qua các task để một tác vụ 4 phút không làm nghẽn worker.
- 05
Bước 5
Lưu trữ kết quả
Payload hoàn tất bao gồm `output_url` và `thumbnail_url`. Tải dữ liệu vào kho lưu trữ đối tượng của riêng bạn — S3, GCS, Cloudflare R2 — để sản phẩm của bạn không bị ràng buộc vào CDN của Photta cho việc hiển thị lâu dài.
Code toàn quy trình
Copy, paste, done.
Four snippets — install prerequisites, wrap the REST call, submit + poll, then handle the errors that actually happen in production.
# Photta doesn't ship an official Python SDK yet — requests is the
# recommended path in the docs. Standard library urllib works too if
# you need zero dependencies.
pip install requests
# Store your API key in env (dotenv optional but convenient)
echo "PHOTTA_API_KEY=photta_live_xxxxx" >> .env# photta.py
import os
import requests
PHOTTA_BASE_URL = "https://ai.photta.app/api/v1"
class PhottaError(Exception):
def __init__(self, status: int, code: str, message: str, retry_after: int | None = None):
super().__init__(message)
self.status = status
self.code = code
self.retry_after = retry_after
def photta_request(method: str, path: str, **kwargs):
headers = {
"Authorization": f"Bearer {os.environ['PHOTTA_API_KEY']}",
"Content-Type": "application/json",
**kwargs.pop("headers", {}),
}
response = requests.request(method, f"{PHOTTA_BASE_URL}{path}", headers=headers, **kwargs)
body = response.json()
if not response.ok:
err = body.get("error", {})
raise PhottaError(
status=response.status_code,
code=err.get("code", "unknown"),
message=err.get("message", response.reason),
retry_after=err.get("retry_after"),
)
return bodyimport time
from photta import photta_request, PhottaError
# 1. Submit the job
created = photta_request("POST", "/tryon/apparel", json={
"product_type": "dress",
"product_images": ["https://example.com/dress.jpg"],
"mannequin_id": "mnq_athena_ts",
"pose_id": "pose_standing_front",
"resolution": "2K",
"aspect_ratio": "3:4",
})
generation_id = created["data"]["id"]
# 2. Poll every 3 seconds. Upper bound: 120 attempts ≈ 6 minutes,
# comfortably above the documented 1.5–4 minute window.
for _ in range(120):
result = photta_request("GET", f"/tryon/apparel/{generation_id}")
status = result["data"]["status"]
if status == "completed":
print("Result:", result["data"]["output_url"])
break
if status == "failed":
raise RuntimeError(result["data"]["error_message"])
time.sleep(3)from photta import photta_request, PhottaError
import time
try:
photta_request("POST", "/tryon/apparel", json={ ... })
except PhottaError as err:
if err.status == 402:
# Out of credits — err.code == "insufficient_credits"
raise
elif err.status == 429:
# Rate-limited. Honour the Retry-After header.
time.sleep(err.retry_after or 30)
# then retry…
elif err.status >= 500:
# Server-side — retry with exponential backoff.
raise
else:
raiseTại sao lại có cấu trúc này
Tại sao requests là lựa chọn đúng đắn hiện nay
- Zero Photta-specific dependencies — `requests` is already in most Python projects
- Works anywhere Python runs: Django, FastAPI, Flask, Celery workers, Lambda, scripts
- The client wrapper is ~30 lines — paste it into `photta.py` and move on
- Pairs naturally with asyncio via `httpx` if you need parallel submission
Những gì nó không làm
Honest caveats
- No official @photta/python SDK yet — REST + requests is the documented pattern
- No async fetch helper shipped; swap `requests` for `httpx` when you need concurrency
- Bearer token auth only — no OAuth client credentials yet
Câu hỏi từ các nhà phát triển khác
Questions other developers ask
Có SDK Photta Python chính thức không?+
Chưa có. Lộ trình của Photta ưu tiên Python SDK khi có mười khách hàng API trả phí hoạt động. Cho đến lúc đó, lộ trình tích hợp được hỗ trợ là thư viện requests (đồng bộ) hoặc httpx (bất đồng bộ) — cả hai đều được ghi nhận trong tài liệu chính thức và hoạt động tốt với wrapper 30 dòng trên trang này.
Những phiên bản Python nào được hỗ trợ?+
Python 3.9 trở lên. Wrapper sử dụng type hints, f-strings và cú pháp `str | None`, hoạt động tốt trên 3.10+. Trên 3.9, hãy đổi `str | None` thành `Optional[str]`. Bản thân requests hỗ trợ chính thức 3.8+, nhưng 3.9+ là mức tối thiểu thực tế cho các dự án Photta hiện đại.
Nên dùng requests hay httpx?+
Sử dụng requests nếu bạn chỉ thực hiện một vài lệnh gọi tuần tự — nó đơn giản hơn và có sẵn trong hầu hết mã nguồn. Sử dụng httpx nếu bạn cần xử lý bất đồng bộ (gửi yêu cầu song song, nạp dữ liệu hàng loạt) hoặc HTTP/2. Wrapper đều rất nhỏ gọn; chỉ cần đổi `requests.request` thành `httpx.Client().request` và phần mã còn lại giữ nguyên.
Tôi có thể gọi từ Django không?+
Có. Đặt wrapper trong `services/photta.py`, import nó từ một view hoặc một Celery task. Đừng gọi API bên trong một trình xử lý yêu cầu đồng bộ nếu tác vụ kéo dài — hãy gửi yêu cầu từ view, trả về ID tạo ảnh, và poll từ một task chạy ngầm hoặc một Channels consumer.
Làm thế nào để poll từ một Celery worker?+
Gửi tác vụ từ một task, sau đó lên lịch một task tiếp theo (qua `apply_async(countdown=3)`) để thực hiện poll một lần và tự lên lịch lại cho đến khi tác vụ hoàn thành hoặc đạt ngưỡng thử lại tối đa. Điều này giúp các worker luôn rảnh và tránh các task chạy quá lâu gây ảnh hưởng đến hệ thống autoscaler.
API báo lỗi như thế nào?+
Các phản hồi không phải 2xx mang theo JSON body với đối tượng `error`: `type`, `code`, `message`, kèm theo `param` cho lỗi 400 và `retry_after` cho lỗi 429. Wrapper trên trang này raise một lỗi `PhottaError` chứa tất cả các thông tin này để bạn có thể xử lý theo mã trạng thái mà không cần tự parse body.
Python · Virtual Try-On API
Tạo tài khoản và lấy API key
Cài đặt `requests`, tải `PHOTTA_API_KEY` từ môi trường, viết một wrapper `photta_request()` để gửi `Authorization: Bearer photta_live_xxx` và raise lỗi `PhottaError` có kiểu dữ liệu cho các phản hồi không phải 2xx, sau đó POST tới `/tryon/apparel` và poll `/tryon/apparel/:id` mỗi 3 giây cho đến khi `data.status == 'completed'` — thường trong vòng 1.5 đến 4 phút.