spicyapiDokumentacja
Przewodniki
Treść główna

Samouczek: z obrazu do wideo

Zacznij od jednego obrazu na swoim komputerze, a skończ na pobranym pliku wideo. Każdy krok pokazuje CLI, SDK dla TypeScriptu i zwykłe HTTP.

Ten samouczek bierze jeden obraz z twojego komputera i zamienia go w krótki klip wideo, który pobierasz i zachowujesz u siebie. Prowadzi przez całą drogę po kolei: wybór modelu, przesłanie obrazu, sprawdzenie ceny, uruchomienie generacji, czekanie na nią, pobranie wyniku i radzenie sobie z tym, co pójdzie nie tak. Nie musisz składać tego w całość ze stron referencyjnych.

Każdy krok pokazuje trzy sposoby na zrobienie tego samego. Wybierz jeden i trzymaj się go do końca:

SposóbWybierz go, jeśliCzego potrzebujesz
CLIChcesz wpisywać polecenia i nie pisać żadnego koduNode.js w wersji 22.13 lub nowszej
TypeScript SDKBudujesz program w Node.js i chcesz widzieć wywołania, które wykonujeNode.js w wersji 22.13 lub nowszej
HTTP (curl)Chcesz zobaczyć surowe API, na przykład żeby później użyć innego języka programowaniaTerminal bash z curl i jq (macOS, Linux albo WSL w Windows)

Wolisz po prostu poprosić o to asystenta AI? Zobacz Zrób to z pomocą asystenta AI.

Co powstanie

  • Wynik: krótki plik wideo, zwykle MP4, który zaczyna się od twojego obrazu i porusza się tak, jak opisuje to twoje zdanie.
  • Twój czas: za pierwszym razem zarezerwuj około 20 minut, głównie na czytanie. Sama generacja trwa zwykle kilka minut; przy niektórych modelach i ustawieniach dłużej.
  • Gdzie to się dzieje: w SpicyAPI. Twój komputer tylko wysyła obraz i instrukcje, a potem pobiera gotowy plik.

Ile to kosztuje i jak sprawdzić to przed zapłatą

Ceny są w dolarach amerykańskich. Zależą od wybranego modelu i od twoich ustawień, takich jak długość i rozdzielczość wideo, dlatego ta strona nie podaje konkretnej kwoty. Cenę zobaczysz w trzech miejscach i sprawdzenie jej w żadnym z nich nic nie kosztuje:

  1. Katalog na żywo (krok 1) wymienia każdy model, z którego może korzystać twoje konto, z cenami twojego konta. Wideo jest zwykle wyceniane per_second, czyli za sekundę gotowego nagrania. Gdy model ma kilka cen, każda z nich dotyczy jakiegoś ustawienia, na przykład rozdzielczości.
  2. Wycena (krok 3) podaje dokładną cenę dokładnie twojego żądania. Niczego nie uruchamia i nie blokuje żadnych środków.
  3. Potwierdzenie: CLI jeszcze raz pokazuje cenę i czeka na twoje y, zanim cokolwiek uruchomi.

Co dzieje się z twoimi pieniędzmi:

  • Kosztuje tylko krok 4, a także ponowne uruchomienie nieudanego zadania. Wyświetlanie modeli, przesyłanie, wycena, czekanie i pobieranie są bezpłatne.
  • Gdy generacja rusza, wyceniona kwota zostaje odłożona z twojego salda (to tak zwana blokada). Ta kwota to zarazem najwięcej, ile wideo może kosztować.
  • Jeśli wideo się uda, płacisz za to, co powstało, nigdy więcej niż wynosi blokada, a reszta wraca na saldo.
  • Nieudane lub wygasłe zadania zwykle zwalniają całą blokadę. Niektóre odmowy dotyczące treści są płatne według zaakceptowanej wyceny, wyłącznie gdy strona modelu wyraźnie wskazuje ten wyjątek. Sprawdź settled i cost, aby poznać ostateczną kwotę.
  • Nowe konta nie mają darmowego progu, więc najpierw potrzebujesz środków na saldzie. Zobacz Rozliczenia.

Jak to działa

twój obraz ──przesłanie──▶ adres spicy:// (ważny jeden dzień)
                                     │
twoje zdanie + ustawienia ───────────┴──▶ wycena (bezpłatna) ──▶ start zadania (blokada środków)
                                                                      │
                                           queued ──▶ running ──▶ succeeded / failed / expired
                                                                      │
                                                link do pobrania (około 20 minut) ──▶ twój plik

Zadanie to jedno zlecenie generowania. SpicyAPI wykonuje je w tle, więc uruchomienie zadania i odebranie wyniku to dwie osobne czynności. Każde zadanie ma identyfikator zaczynający się od job_; zachowaj go, bo po nim znajdziesz zadanie ponownie. Pozostałe słowa użyte na tej stronie wyjaśnia Słownik.

Zanim zaczniesz

Przygotuj konto, saldo i klucz API

Najpierw przejdź przez stronę Przygotuj konto. Na koniec będziesz mieć:

  • konto SpicyAPI ze środkami na saldzie;
  • klucz API, który zaczyna się od sk-spicy-;
  • ten klucz zapisany w zmiennej środowiskowej o nazwie SPICY_API_KEY. Zmienna środowiskowa to nazwana wartość, którą terminal przekazuje uruchamianym przez siebie programom, dzięki czemu klucz nigdy nie musi pojawić się w poleceniu ani w twoim kodzie.

Sprawdź, czy klucz jest ustawiony w oknie terminala, którego używasz – bez wypisywania całego klucza:

echo "${SPICY_API_KEY:0:9}"

Co zobaczysz: sk-spicy-. Jeśli nic się nie wypisuje albo pojawia się błąd, klucz nie jest ustawiony w tym oknie; wróć do strony Przygotuj konto.

Umieść obraz w folderze roboczym

Utwórz folder na ten samouczek i otwórz w nim terminal. Każde polecenie z tej strony uruchamiasz z tego folderu i właśnie tu trafia każdy plik, który powstaje po drodze.

mkdir -p ~/spicy-video
cd ~/spicy-video

Skopiuj obraz do tego folderu i nazwij go start-frame.jpg (albo start-frame.png, jeśli to plik PNG; wtedy używaj tej nazwy wszędzie tam, gdzie ta strona pisze start-frame.jpg).

Jaki obraz dobrze sprawdzi się na start:

  • Format i rozmiar: JPEG, PNG, WebP albo GIF, do 10 MiB (około 10 megabajtów). Model może mieć własne, ostrzejsze limity, które zobaczysz w kroku 1.
  • Plik musi naprawdę być w tym formacie. SpicyAPI sprawdza zawartość pliku, a nie tylko jego nazwę. Zdjęcia z telefonów są często w formacie HEIC, a zmiana nazwy takiego pliku na .jpg go nie konwertuje. Najpierw otwórz zdjęcie i wyeksportuj je albo zapisz jako JPEG.
  • Kształt: obraz staje się pierwszą klatką. Do poziomego wideo użyj poziomego obrazu, a do pionowego – pionowego; niektóre modele mają też ustawienie aspect_ratio.
  • Prawa: użyj obrazu, z którego masz prawo korzystać.

Przygotuj wybrane narzędzie

CLI to program o nazwie spicyapi, który uruchamiasz w terminalu. Zainstaluj go raz (pełne instrukcje, łącznie z Node.js: CLI: zanim zaczniesz):

npm install -g @spicyapi/cli
spicyapi --version

Jeśli instalacja kończy się błędem EACCES, pomiń ją i wszędzie tam, gdzie ta strona wpisuje spicyapi, wpisuj npx @spicyapi/cli.

Potem sprawdź, czy klucz działa i czy masz środki na saldzie:

spicyapi balance

Co zobaczysz: available, held i total w dolarach amerykańskich. available musi być większe od zera.

Siedem kroków

Zastąp MODEL_ID_FROM_CATALOG prawdziwym identyfikatorem modelu

MODEL_ID_FROM_CATALOG to symbol zastępczy, a nie model. W kroku 1 wybierasz prawdziwy identyfikator modelu z katalogu na żywo (spicyapi models list, listModels() w SDK albo GET /api/v1/models). Wklej go wszędzie tam, gdzie na tej stronie stoi symbol zastępczy. Wysłanie samego symbolu zastępczego zwróci tylko błąd „nie znaleziono”.

Korzystasz z Windows? Wybierz kartę CLI albo SDK

Karta HTTP jest napisana dla bash. Windows PowerShell inaczej traktuje cudzysłowy, łamanie linii (\) i $(...), więc tych poleceń nie da się tam uruchomić w takiej postaci. W Windows użyj karty CLI albo SDK albo uruchom polecenia HTTP w WSL (Windows Subsystem for Linux, czyli podsystemie Windows dla systemu Linux).

1. Wybierz model i przeczytaj jego ustawienia

Zrób to: wyświetl modele wideo z obrazu, z których może korzystać twoje konto, wybierz jeden, a potem sprawdź, jakie ustawienia przyjmuje.

Wyświetl modele:

spicyapi models list --modality video --task image-to-video --json

Co zobaczysz: listę w formacie JSON. Ta jest skrócona, a kwoty są pokazane jako …:

{
  "total": 1,
  "items": [
    {
      "model": "MODEL_ID_FROM_CATALOG",
      "displayName": "Example video model",
      "modality": "video",
      "tasks": ["image-to-video"],
      "enabled": true,
      "available": true,
      "quantityField": "duration_seconds",
      "maxOutputDurationSeconds": 10,
      "taskTimeoutSeconds": 1800,
      "pricing": [
        { "variant": "720p", "unit": "per_second", "price": "…", "currency": "USD" },
        { "variant": "1080p", "unit": "per_second", "price": "…", "currency": "USD" }
      ]
    }
  ]
}

Wybierz model, w którym zarówno enabled, jak i available mają wartość true, i skopiuj jego wartość model. Potem przeczytaj jego ustawienia:

spicyapi models get MODEL_ID_FROM_CATALOG --json

Odpowiedź ma te same pola, a do tego inputSchema (ustawienia) i examples (dane wejściowe, które serwer już sprawdził).

Na co patrzeć na liście:

PoleCo ci mówi
modelIdentyfikator modelu, którego użyjesz we wszystkich kolejnych krokach
enabled, availableKorzystaj z modelu tylko wtedy, gdy oba mają wartość true
pricingJedna pozycja na każdy poziom cenowy: variant (ustawienie, którego dotyczy, często rozdzielczość), unit (dla wideo zwykle per_second) i price w dolarach amerykańskich. Gdy obowiązuje zniżka, pojawiają się też regularPrice i offerLabel
quantityFieldUstawienie, które decyduje, za ile jednostek płacisz, zwykle duration_seconds. Puste oznacza jedną jednostkę na wideo
maxOutputDurationSecondsNajdłuższe wideo, na jakie pozwala model
taskTimeoutSecondsJak długo generacja może trwać, zanim zostanie zatrzymana ze stanem expired (i nie zostanie rozliczona)

Jak czytać ustawienia. inputSchema to lista ustawień modelu zapisana w JSON Schema:

  • required wymienia ustawienia, które musisz wysłać. W tego rodzaju modelach zawsze jest wśród nich image_url, a większość wymaga też prompt.
  • properties wymienia każde ustawienie, które model przyjmuje. Każde ma type, opis description napisany prostym angielskim, a często też enum (jedyne dozwolone wartości), minimum i maximum oraz default (wartość używana, gdy pominiesz to ustawienie).
  • W każdym ustawieniu x-ui zawiera wskazówki do wyświetlania. x-ui.affects_price: true oznacza, że zmiana tego ustawienia zmienia cenę.
  • Niektóre modele dodają na najwyższym poziomie warunki, na przykład „jeśli wysyłasz A, musisz też wysłać B”. Jak je czytać, wyjaśnia strona Spicy Schema.
  • examples zawiera kompletne dane wejściowe, które serwer już sprawdził – to bezpieczny punkt wyjścia.

Ustawienia, które spotkasz najczęściej. Nazwy są takie same we wszystkich modelach, ale każdy model przyjmuje tylko część z nich, z własnymi dozwolonymi wartościami:

UstawienieCo robiCzy zmienia cenę?
image_urlObraz startowy, użyty jako pierwsza klatka. Przyjmuje adres spicy:// z kroku 2 albo publiczny link https://Nie
promptCo ma się dziać: ruch, praca kamery, nastrój. Opisuj ruch, zamiast powtarzać to, co już widać na obrazieZwykle nie
duration_secondsDługość wideo w sekundach. Dozwolone wartości są w enum albo między minimum a maximum; niektóre modele przyjmują wartość specjalną, objaśnioną w description tego ustawieniaTak w większości modeli: wideo jest zwykle rozliczane za sekundę, więc dłuższy klip kosztuje więcej
resolutionRozmiar wyniku, na przykład 720p albo 1080pZwykle tak: wyższe rozdzielczości mają zazwyczaj własną, wyższą cenę
aspect_ratioProporcje wideo, na przykład 16:9, 9:16 albo 1:1. Niektóre modele oferują adaptive, które dopasowuje się do obrazuSprawdź x-ui.affects_price
generate_audioDodatkowo generuje ścieżkę dźwiękową pasującą do obrazuW niektórych modelach
last_image_urlObraz na ostatnią klatkę; zobacz Pierwsza i ostatnia klatkaSprawdź wyceną
negative_promptCzego wideo ma unikaćZwykle nie
seedLiczba, która ułatwia porównywanie wyników kolejnych uruchomień; nie gwarantuje identycznych filmówNie

Wysyłaj tylko ustawienia, które wymienia ten model

Każdy model ma własną listę. Ustawienie, którego nie ma w properties tego modelu, błędnie wpisana nazwa albo wartość spoza enum sprawiają, że całe żądanie zostaje odrzucone z kodem 400. Nie pobiera się wtedy żadnej opłaty, ale i tak nie kopiuj danych wejściowych z innego modelu bez sprawdzenia.

Co się właśnie stało: odczytano katalog na żywo dla twojego konta, razem z twoimi cenami. Nie pobrano żadnej opłaty. Odczyt katalogu wlicza się do limitu żądań twojego konta, więc nie trzeba go powtarzać przed każdym wideo; zrób to ponownie, gdy zmieniasz model albo dostajesz 400.

2. Prześlij obraz

Zrób to: prześlij start-frame.jpg i skopiuj adres spicy://, który dostaniesz w odpowiedzi. Przesyłanie jest bezpłatne.

spicyapi files upload start-frame.jpg

Co zobaczysz:

fileId: fil_01k3m8x9q2z4v7n5p6r8s0t1w3
status: ready
bytes: 402118
contentType: image/jpeg
sha256: a91f4c2e5b7d16809e3f2a4c8d0b61e7c4a890e5d2f71b3c609ae8427d15f0c6
uri: spicy://f/fil_01k3m8x9q2z4v7n5p6r8s0t1w3
expiresAt: 2026-09-18T09:12:11Z

Skopiuj wartość uri dokładnie tak, jak została wypisana.

Co się właśnie stało: twój obraz został zapisany prywatnie dla twojego konta, sprawdzony (jego rzeczywisty format musi zgadzać się z zadeklarowanym typem) i dostał adres spicy://. Ten adres nie jest linkiem internetowym: może go używać tylko twoje konto i tylko w danych wejściowych zadania. Można go używać przez jeden dzień (zobacz expiresAt); potem prześlij obraz ponownie.

Obraz jest już w internecie?

Jeśli obraz jest już dostępny pod publicznym adresem https://, który otwiera się bez logowania, możesz pominąć ten krok i wpisać ten adres w image_url. Adres musi pozostać osiągalny przez cały czas generowania wideo.

Jeśli przesyłanie się nie udaje:

WidziszCo to znaczyCo zrobić
Unsupported file type albo CLI lub SDK informuje, że nie potrafi rozpoznać typuPlik nie jest w formacie JPEG, PNG, WebP ani GIFPrzekonwertuj obraz albo nadaj mu nazwę z właściwym rozszerzeniem
File exceeds the 10 MB limitObraz jest większy niż 10 MiBWyeksportuj mniejszą wersję
The uploaded file does not match the upload ticketZawartość pliku jest innego typu, niż wskazuje jego nazwa albo deklaracja, na przykład to zdjęcie HEIC ze zmienioną nazwą na .jpgWyeksportuj je jako prawdziwy JPEG albo PNG i prześlij ponownie
The upload ticket has expiredMiędzy pobraniem biletu a zatwierdzeniem minęło więcej niż około 20 minutZacznij przesyłanie od nowa

3. Opisz wideo i sprawdź cenę

Zrób to: zapisz ustawienia w pliku o nazwie input.json, a potem poproś o wycenę.

Zapisz input.json. Zacznij od dwóch ustawień, które przyjmuje każdy model wideo z obrazu. W prompt wpisz własne zdanie, a wartość image_url zastąp wartością uri skopiowaną w kroku 2:

input.json
{
  "prompt": "The camera slowly pushes in while rain runs down the window and neon light flickers",
  "image_url": "spicy://f/fil_01k3m8x9q2z4v7n5p6r8s0t1w3"
}

Ustawienia, które pominiesz, dostaną wartość default modelu. Jeśli chcesz wybrać je samodzielnie, dodaj tylko takie ustawienia, które wymienia properties twojego modelu, z wartościami, na które pozwala. Na przykład jeśli twój model wymienia duration_seconds i resolution i dopuszcza takie wartości:

{
  "prompt": "The camera slowly pushes in while rain runs down the window and neon light flickers",
  "image_url": "spicy://f/fil_01k3m8x9q2z4v7n5p6r8s0t1w3",
  "duration_seconds": 5,
  "resolution": "720p"
}

Zapisz plik w folderze roboczym:

Wpisz w te linie własny tekst i uri, a potem wklej je wszystkie naraz:

cat > input.json <<'EOF'
{
  "prompt": "The camera slowly pushes in while rain runs down the window and neon light flickers",
  "image_url": "spicy://f/fil_01k3m8x9q2z4v7n5p6r8s0t1w3"
}
EOF

Używaj zwykłych, prostych cudzysłowów ("), a nie drukarskich, i nie stawiaj przecinka po ostatnim ustawieniu.

Pobierz wycenę:

spicyapi tasks quote --model MODEL_ID_FROM_CATALOG --input-file input.json

Co zobaczysz (kwoty pokazane jako …):

quoteId: eyJ2IjoxLCJtIjoi…
model: MODEL_ID_FROM_CATALOG
estimatedCost: …
maxCharge: …
currency: USD
quantity: 5
unit: per_second
expiresAt: 2026-09-17T08:05:00Z

Co się właśnie stało: SpicyAPI sprawdziło twoje dane wejściowe względem ustawień modelu i wyceniło dokładnie to żądanie. Nic nie zostało uruchomione i nie pobrano żadnej opłaty. estimatedCost to kwota, która zostanie zablokowana, jeśli uruchomisz generację teraz, a maxCharge to najwięcej, ile może to kosztować. quantity i unit pokazują, za co płacisz, na przykład za 5 sekund.

Wycena jest ważna pięć minut i tylko dla dokładnie tych danych wejściowych. Zmień długość albo rozdzielczość i wyceń ponownie, żeby porównać ceny. Wycena przeprowadza te same kontrole co uruchomienie zadania, więc problemy wychodzą na jaw tutaj, bez żadnych kosztów: 400 oznacza, że dane wejściowe nie pasują do ustawień modelu (popraw input.json według kroku 1), a 40201 – że saldo nie pokryłoby tej kwoty. Pozostałe kody wymienia krok 7.

Chcesz zrobić próbę bez własnego obrazu?

examples modelu z kroku 1 to kompletne dane wejściowe, które serwer już sprawdził. Możesz wstawić jeden z tych przykładów bez zmian do input.json, wycenić go i wygenerować, żeby zobaczyć działanie całego procesu, zanim użyjesz własnego obrazu.

4. Uruchom generację

Ten krok kosztuje

Uruchomienie generacji blokuje wycenioną kwotę na twoim saldzie. Gdy SpicyAPI przyjmie zadanie, nie da się go już anulować: wykonuje się do końca i jest rozliczane, jeśli się powiedzie. Nieudane lub wygasłe zadania zwykle zwalniają całą blokadę. Niektóre odmowy dotyczące treści są płatne według zaakceptowanej wyceny, wyłącznie gdy strona modelu wyraźnie wskazuje ten wyjątek. Sprawdź settled i cost, aby poznać ostateczną kwotę.

Klucz idempotentności, prostymi słowami. To etykieta jednego wideo, coś jak numer zamówienia. Jeśli połączenie się zerwie i nie wiesz, czy wideo ruszyło, wyślij to samo żądanie jeszcze raz z tą samą etykietą: SpicyAPI zwróci zadanie, które już uruchomiło, zamiast uruchamiać drugie i pobierać za nie opłatę. Etykieta działa przez 24 godziny z tym samym kluczem API. Do innego wideo użyj nowej etykiety: ta sama etykieta z innymi danymi wejściowymi zostanie odrzucona z kodem 409. Więcej na stronie Idempotentność.

Zrób to:

spicyapi tasks create --model MODEL_ID_FROM_CATALOG --input-file input.json

CLI jeszcze raz pobiera wycenę, pokazuje cenę i czeka na ciebie:

Estimated charge: USD …; maximum charge: USD …. Quote expires: 2026-09-17T08:05:00Z.
Idempotency-Key: 4f6755a5-0d72-4420-9f6b-9faf0e2b0241
Create a billable task with model MODEL_ID_FROM_CATALOG? … Continue? [y/N]

Wpisz y i naciśnij Enter. Każda inna odpowiedź anuluje operację i nie pobiera żadnej opłaty. Zanim odpowiesz, skopiuj gdzieś wartość Idempotency-Key: CLI przy każdym uruchomieniu tworzy nową etykietę, a właśnie ta będzie ci potrzebna, jeśli połączenie się zerwie.

Co zobaczysz:

idempotencyKey: 4f6755a5-0d72-4420-9f6b-9faf0e2b0241
taskId: job_01k3m8x9q2z4v7n5p6r8s0t1w3
state: queued
estimatedCost: …
deadlineAt: 2026-09-17T08:35:00Z

Skopiuj taskId.

Co się właśnie stało: SpicyAPI przyjęło generację, która jest teraz zadaniem, i zablokowało kwotę estimatedCost na twoim saldzie. To zarazem najwięcej, ile to wideo może kosztować. state: queued oznacza, że zadanie czeka na swoją kolej. deadlineAt to najpóźniejszy moment, w którym może się zakończyć; jeśli do tego czasu nie będzie gotowe, kończy się stanem expired i nie pobiera się za nie żadnej opłaty. deadlineAt to nie jest termin wygaśnięcia twoich plików.

Przekazanie wyceny oznacza: „przyjmij to tylko po cenie, którą mi pokazano”. Jeśli w międzyczasie zmieniła się cena albo dane wejściowe, żądanie zostanie odrzucone z kodem 40901, zamiast zablokować inną kwotę. CLI robi to za ciebie.

Jeśli połączenie zostało zerwane, a identyfikator zadania się nie pojawił, nie zaczynaj po prostu od nowa z nową etykietą – to utworzyłoby drugie wideo i pobrało za nie opłatę. Powtórz żądanie z tą samą etykietą:

  • CLI: spicyapi tasks create --model MODEL_ID_FROM_CATALOG --input-file input.json --idempotency-key <the value you copied> (zamiast <the value you copied> wklej skopiowaną wcześniej wartość Idempotency-Key). Zobacz Wróć do zadania po przerwanym czekaniu.
  • SDK: uruchom jeszcze raz node generate.mjs --yes; skrypt ponownie użyje idempotency-key.txt.
  • HTTP: uruchom jeszcze raz blok „Uruchom wideo”; on też ponownie używa idempotency-key.txt.

Jeśli krok 4 został odrzucony, nic nie zostało utworzone i nie pobrano żadnej opłaty; przyczynę i sposób naprawy znajdziesz w kroku 7.

5. Poczekaj na wideo

Zrób to: sprawdzaj zadanie, aż się zakończy. Wideo powstaje zwykle w kilka minut.

spicyapi tasks wait job_01k3m8x9q2z4v7n5p6r8s0t1w3 --wait-timeout-ms 1800000 --json

Użyj własnego identyfikatora zadania. --wait-timeout-ms 1800000 czeka do 30 minut zamiast domyślnych 10.

Co zobaczysz po zakończeniu (w skrócie):

{
  "taskId": "job_01k3m8x9q2z4v7n5p6r8s0t1w3",
  "model": "MODEL_ID_FROM_CATALOG",
  "state": "succeeded",
  "output": {
    "assets": [
      {
        "key": "tasks/2026/09/17/job_01k3m8x9q2z4v7n5p6r8s0t1w3/result.mp4",
        "url": "https://…",
        "expiresAt": "2026-09-17T08:40:00Z",
        "mime": "video/mp4",
        "durationSeconds": 5,
        "width": 1280,
        "height": 720,
        "bytes": 4839211
      }
    ]
  },
  "cost": "…",
  "settled": true
}

Następnym razem możesz połączyć kroki 4 i 5, dodając --wait do tasks create.

Co się właśnie stało: twoje narzędzie co kilka sekund pytało SpicyAPI o zadanie. Stany to queued (czeka), running (trwa generowanie), a potem jeden stan końcowy: succeeded, failed albo expired. Po powodzeniu plik jest kopiowany do własnego magazynu SpicyAPI, co zajmuje jeszcze kilka sekund; do tego czasu wynik pokazuje pending: true. Kwota cost jest ostateczna, gdy settled ma wartość true.

  • Zamknięcie terminala albo naciśnięcie Ctrl + C nie anuluje zadania. Przerywa tylko czekanie. Zachowaj identyfikator zadania i powtórz ten krok później.
  • Nie sprawdzaj częściej niż co kilka sekund. Sprawdzanie zadania korzysta z osobnego limitu odczytów konta i nie zużywa limitu uruchamiania zadań; zobacz Limity żądań.
  • W aplikacji albo na serwerze zamiast pytać, pozwól, żeby SpicyAPI samo dało znać, kiedy zadanie jest gotowe: zobacz Powiadomienie zamiast czekania.

6. Pobierz i zachowaj wideo

Zrób to: zdobądź świeży link do pobrania i zapisz plik na swoim komputerze.

Zdobądź świeży link:

spicyapi files download-url job_01k3m8x9q2z4v7n5p6r8s0t1w3
key: tasks/2026/09/17/job_01k3m8x9q2z4v7n5p6r8s0t1w3/result.mp4
url: https://…
expiresAt: 2026-09-17T08:52:00Z

Wklej url do przeglądarki, żeby pobrać plik, albo zapisz go z poziomu terminala (zachowaj cudzysłowy, bo link zawiera znaki &):

curl -L -o my-video.mp4 "PASTE_THE_URL_HERE"

W Windows PowerShell wpisz curl.exe zamiast curl. Jeśli zadanie utworzyło kilka plików, spicyapi tasks get <task-id> --json wymienia je wszystkie, a opcja --key wybiera jeden z nich.

Co się właśnie stało: każdy wynik ma bezpośredni link do pobrania. Link działa przez około 20 minut i nie wymaga klucza API; nigdy nie doklejaj do niego swojego klucza. Gdy wygaśnie, zapytaj ponownie o zadanie (albo użyj files download-url), żeby dostać nowy.

Zachowaj własną kopię

SpicyAPI przechowuje wygenerowane pliki najwyżej przez około 14 dni (krócej, jeśli twoje konto ma ustawiony krótszy okres przechowywania), a potem usuwa je na dobre. Przesłanego obrazu można używać przez jeden dzień, a tekst promptu jest domyślnie usuwany po 30 dniach. Zapis zadania i jego kosztu zostaje. Żeby wcześniej trwale usunąć pliki i prompt zakończonego zadania, użyj spicyapi tasks purge, purgeTask() albo POST /api/v1/jobs/purge; usuwa to tylko treść i nie jest zwrotem pieniędzy. Zobacz Przechowywanie i usuwanie danych.

7. Gdy coś pójdzie nie tak

Problemy są dwóch rodzajów i każdy z nich obsługuje się inaczej.

Żądanie zostaje odrzucone. Polecenie albo wywołanie od razu kończy się błędem. Nic nie zostało utworzone i nie pobrano żadnej opłaty. Komunikat mówi, dlaczego, a błąd zawiera code i identyfikator żądania (req_…), który podajesz, kontaktując się ze wsparciem.

KodCo to znaczyCo zrobić
400 albo bardziej szczegółowy kod zaczynający się od 400Dane wejściowe nie pasują do ustawień modelu: brakuje wymaganego ustawienia, jest ustawienie nieznane albo błędnie wpisane, wartość jest niedozwolona, adres spicy:// wygasł albo należy do innego konta, model nie może teraz obsłużyć takiej kombinacji ustawień albo adres callbacku jest nieprawidłowyPorównaj input.json z ustawieniami z kroku 1 i popraw plik. Jeśli adres wygasł, prześlij obraz ponownie
401Klucza API brakuje, jest błędnie wpisany albo został unieważnionySprawdź SPICY_API_KEY tak jak w sekcji Zanim zaczniesz
40201Saldo nie pokrywa kwoty, którą trzeba zablokowaćDoładuj konto w sekcji Rozliczenia w konsoli
40202Osiągnięto limit wydatków klucza (dzienny, miesięczny albo łączny)Podnieś go na stronie Klucze API albo poczekaj, aż się odnowi
403, 40301Ten klucz nie może używać tego modelu albo żądanie przyszło z miejsca, z którego nie jest dozwoloneSprawdź dozwolone modele i listę dozwolonych IP klucza na stronie Klucze API
404Twoje konto nie ma modelu o tym identyfikatorze (albo wysłano symbol zastępczy) albo ten klucz nie ma zadania o tym identyfikatorzeJeszcze raz skopiuj dokładny identyfikator; użyj tego samego klucza, którym utworzono zadanie
409Ten klucz idempotentności został już użyty do innego żądaniaDo nowego wideo użyj nowej etykiety
40901Wycena wygasła (po pięciu minutach) albo zmieniła się cenaWyceń ponownie, a potem uruchom ponownie
429Za dużo żądań w krótkim czasieOdczekaj tyle sekund, ile podaje błąd, i kontynuuj wolniej
50301Model nie może teraz przyjmować nowej pracySpróbuj ponownie później albo wybierz inny model

Zadanie kończy się niepowodzeniem. Zadanie zostało przyjęte, ale kończy się stanem failed albo expired zamiast succeeded. Zadanie pokazuje errorCode, który mówi, dlaczego tak się stało, i errorMessage z dokładniejszym opisem słownym. Nieudane lub wygasłe zadania zwykle zwalniają całą blokadę. Niektóre odmowy dotyczące treści są płatne według zaakceptowanej wyceny, wyłącznie gdy strona modelu wyraźnie wskazuje ten wyjątek. Sprawdź settled i cost, aby poznać ostateczną kwotę.

Odczytaj je:

spicyapi tasks get job_01k3m8x9q2z4v7n5p6r8s0t1w3

Spójrz na state, errorCode i errorMessage.

Potem zdecyduj, co zrobić, na podstawie errorCode, a nie brzmienia komunikatu:

errorCodeCo to znaczyCo zrobić
rate_limited, upstream_unavailable, upstream_failedGenerowanie było przeciążone albo chwilowo niedostępneUruchom zadanie ponownie po krótkiej przerwie
timeout (albo stan expired)Wideo nie zostało ukończone na czasSpróbuj jeszcze raz; jeśli to się powtórzy, wybierz krótszą długość albo niższą rozdzielczość i uruchom nowe zadanie
generation_failedGenerowanie się odbyło, ale niczego nie wytworzyłoTe same dane wejściowe zwykle zawodzą w ten sam sposób. Zmień prompt albo obraz i uruchom nowe zadanie
invalid_assetNie dało się użyć obrazu, na przykład dlatego, że przesłany plik wygasł albo nie dało się go odczytaćPrześlij obraz ponownie i uruchom nowe zadanie z nowym adresem
invalid_request, unsupported_combinationUstawienia nie zostały przyjęteZmień ustawienia i uruchom nowe zadanie
content_rejectedWybrany model odrzucił to żądanie na podstawie własnych zasadZmień prompt albo obraz albo wybierz inny model

Każdą inną wartość traktuj tak jak upstream_failed. Pełna lista jest na stronie Błędy.

Uruchom nieudane zadanie ponownie. Ponowienie tworzy nowe zadanie z tym samym modelem i tymi samymi danymi wejściowymi, po bieżącej cenie modelu. Kosztuje, tak jak krok 4, i zachowuje pierwotne dane wejściowe: jeśli korzystały one z przesłanego pliku, który już wygasł, prześlij go ponownie i zamiast ponowienia uruchom nowe zadanie.

spicyapi tasks retry job_01k3m8x9q2z4v7n5p6r8s0t1w3 --wait --wait-timeout-ms 1800000

Polecenie prosi o potwierdzenie, ale w przeciwieństwie do tasks create nie pokazuje wcześniej ceny. Żeby ją zobaczyć, uruchom polecenie tasks quote z kroku 3.

Ponowić można tylko zadania failed i expired. Jeśli chcesz inną wersję wideo, które się udało, wróć do kroku 3 z nową etykietą. Przyjętego zadania nie da się anulować. Więcej na stronie Nieodwracalność zadań i ponowienia.

Zrób to z pomocą asystenta AI

Jeśli korzystasz z asystenta AI, który obsługuje MCP, takiego jak Claude Code, Cursor czy Codex, serwer MCP SpicyAPI pozwala mu wykonać za ciebie wszystkie siedem kroków. Skonfiguruj go raz według sekcji Serwer MCP: skonfiguruj swojego klienta, a potem poproś własnymi słowami, na przykład:

Prześlij do SpicyAPI obraz /Users/me/spicy-video/start-frame.jpg. Znajdź modele wideo z obrazu, z których może korzystać mój klucz, i wyceń 5-sekundowy klip w dwóch najtańszych. Potem, gdy potwierdzę, wygeneruj wideo tańszym z nich, poczekaj na wynik i daj mi link do pobrania.

W Windows podaj ścieżkę jako C:\Users\me\spicy-video\start-frame.jpg.

Co się dzieje:

  1. spicyapi_upload_file przesyła obraz i dostaje jego adres spicy://. To nic nie kosztuje, ale plik zostaje wysłany, więc wskaż dokładnie ten plik, o który ci chodzi. Domyślnie da się odczytać tylko pliki z twojego folderu domowego; zobacz Pliki lokalne.
  2. spicyapi_models_list i spicyapi_model_get znajdują model i jego ustawienia, a spicyapi_task_quote wycenia możliwe warianty. Wszystko bezpłatnie.
  3. spicyapi_task_create zatrzymuje się i pyta ciebie, pokazując model, szacowaną i maksymalną opłatę oraz moment wygaśnięcia wyceny. Nic nie jest pobierane, dopóki nie potwierdzisz, a asystent nie może potwierdzić za ciebie.
  4. spicyapi_task_wait czeka najwyżej pięć minut naraz, więc przy dłuższym wideo asystent może czekać więcej niż raz. Potem daje ci link do pobrania, który działa przez około 20 minut.

Więcej przykładów i opis każdego narzędzia: Serwer MCP.

Co jeszcze możesz zrobić

Pierwsza i ostatnia klatka

Niektóre modele wideo z obrazu przyjmują też last_image_url, czyli drugi obraz, na którym wideo ma się skończyć. Sprawdź, czy twój model to obsługuje, szukając last_image_url w properties z kroku 1. Jeśli go tam nie ma, model tego nie obsługuje, a wysłanie tego ustawienia zostanie odrzucone z kodem 400.

Prześlij oba obrazy tak jak w kroku 2, a potem wpisz oba adresy do input.json:

{
  "prompt": "The flower slowly opens as morning light spreads across the table",
  "image_url": "spicy://f/fil_01k3m8x9q2z4v7n5p6r8s0t1w3",
  "last_image_url": "spicy://f/fil_01k3m8x9q2z4v7n5p6r8s0t1w4"
}

description tego ustawienia wyjaśnia, jak dany model wykorzystuje ostatni obraz. Przed uruchomieniem wyceń ponownie, żeby sprawdzić, czy drugi obraz zmienia cenę.

Kilka filmów

  • Używaj przesłanego pliku wielokrotnie. Jednego adresu spicy:// możesz używać w kilku zadaniach aż do jego expiresAt, chyba że przechowywanie przesłanych plików na twoim koncie jest ustawione tak, żeby usuwać je zaraz po zakończeniu zadania.
  • Jedna etykieta na jedno wideo. Nadaj każdemu wideo własny klucz idempotentności, na przykład campaign-clip-1, campaign-clip-2. Wtedy ponowne uruchomienie skryptu zwraca filmy, które już ruszyły, i nie płacisz za nie drugi raz.
  • Nie uruchamiaj wszystkiego naraz. Każde trwające zadanie ma zablokowane środki, limit wydatków odrzuca z kodem 40202 zadania, które by go przekroczyły, a każde sprawdzenie stanu wlicza się do limitu żądań. Zacznij od dwóch zadań naraz.

Gotowe skrypty: Generowanie wsadowe z ograniczoną współbieżnością (SDK) i Uruchom CLI ze skryptu.

Powiadomienie zamiast czekania

W przypadku strony internetowej albo usługi działającej w tle trzymanie uruchomionego programu tylko po to, żeby pytał „czy już gotowe?”, to marnotrawstwo. Zamiast tego podaj zadaniu adres callbacku: publiczny adres internetowy na twoim własnym serwerze, który SpicyAPI wywoła jeden raz, gdy zadanie się zakończy, przekazując te same szczegóły zadania, które pokazuje krok 5.

Czego potrzebujesz:

  • serwera osiągalnego z internetu pod adresem https://, na standardowym porcie (localhost jest odrzucany);
  • klucza podpisującego webhooki z konsoli, żeby twój serwer mógł sprawdzić, czy każde wywołanie naprawdę pochodzi od SpicyAPI;
  • kodu, który sprawdza podpis, szybko odpowiada i poprawnie obsługuje sytuację, gdy to samo powiadomienie dotrze dwa razy.

Strona Webhooki wyjaśnia format, podpis i harmonogram ponownych prób, a SDK ma minimalny odbiornik. Zostaw sobie też plan awaryjny: od czasu do czasu sprawdzaj zadania, których deadlineAt dawno minął, a powiadomienie nie przyszło.

Dodaj adres callbacku, gdy wyceniasz i uruchamiasz zadanie:

spicyapi tasks create --model MODEL_ID_FROM_CATALOG --input-file input.json --callback-url https://your-app.example.com/hooks/spicy

CLI uwzględnia ten adres we własnej wycenie, więc sprawdzenie ceny nadal się zgadza.

Co dalej

Na tej stronie