Seanse kinowe
GET /3/movie/{movie_id}/showtimes?country=RU zwraca kina, które grają film w jednym kraju, z datowanymi seansami w każdym. Bez country zwraca tylko liczby według krajów w liście countries. Pokrycie zależy od kraju i tytułu, a pusta tablica results oznacza, że dla tej pary nic nie wiadomo.
Pobieranie seansów filmu
GET / zwraca kina, które grają film w jednym kraju, z datowanymi seansami w każdym. Parametr country przyjmuje dwuliterowy kod, wielkimi lub małymi literami. Pokrycie zależy od kraju i tytułu, więc dane są obecne tam, gdzie są znane, a brakuje ich tam, gdzie nie. Zwracane są tylko dni od dziś.
Przykład prosi o Fight Club w Rosji i obsługuje pustą odpowiedź.
curl -sf "https://api.amodb.dev/3/movie/550/showtimes?country=RU" \
-H "Authorization: Bearer $AMODB_KEY"const url = 'https://api.amodb.dev/3/movie/550/showtimes?country=RU';
const res = await fetch(url, { headers: { Authorization: `Bearer ${process.env.AMODB_KEY}` } });
if (!res.ok) throw new Error(`amodb returned ${res.status}`);
const data = await res.json();
if (data.results.length === 0) console.log('no showtimes known');
for (const venue of data.results) {
for (const s of venue.showtimes) {
console.log(venue.name, venue.city, s.start, s.formats.join(','), s.booking_url);
}
}import os
import requests
r = requests.get(
"https://api.amodb.dev/3/movie/550/showtimes",
params={"country": "RU"},
headers={"Authorization": f"Bearer {os.environ['AMODB_KEY']}"},
timeout=10,
)
r.raise_for_status()
results = r.json()["results"]
if not results:
print("no showtimes known")
for venue in results:
for s in venue["showtimes"]:
print(venue["name"], venue["city"], s["start"], ",".join(s["formats"]))<?php
$url = 'https://api.amodb.dev/3/movie/550/showtimes?country=RU';
$ch = curl_init($url);
curl_setopt_array($ch, [
CURLOPT_RETURNTRANSFER => true,
CURLOPT_TIMEOUT => 10,
CURLOPT_HTTPHEADER => ['Authorization: Bearer ' . getenv('AMODB_KEY')],
]);
$body = curl_exec($ch);
$status = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);
if ($status !== 200) {
throw new RuntimeException("amodb returned $status");
}
$results = json_decode($body, true)['results'];
if (!$results) {
echo 'no showtimes known', PHP_EOL;
}
foreach ($results as $venue) {
foreach ($venue['showtimes'] as $s) {
echo $venue['name'], ' ', $s['start'], ' ', implode(',', $s['formats']), PHP_EOL;
}
}package main
import (
"encoding/json"
"fmt"
"net/http"
"os"
"strings"
"time"
)
type Venue struct {
Name string `json:"name"`
City string `json:"city"`
Showtimes []struct {
Start string `json:"start"`
Formats []string `json:"formats"`
BookingURL string `json:"booking_url"`
} `json:"showtimes"`
}
func main() {
url := "https://api.amodb.dev/3/movie/550/showtimes?country=RU"
req, _ := http.NewRequest("GET", url, nil)
req.Header.Set("Authorization", "Bearer "+os.Getenv("AMODB_KEY"))
client := &http.Client{Timeout: 10 * time.Second}
res, err := client.Do(req)
if err != nil {
panic(err)
}
defer res.Body.Close()
if res.StatusCode != http.StatusOK {
panic(res.Status)
}
var body struct {
Results []Venue `json:"results"`
}
if err := json.NewDecoder(res.Body).Decode(&body); err != nil {
panic(err)
}
if len(body.Results) == 0 {
fmt.Println("no showtimes known")
}
for _, v := range body.Results {
for _, s := range v.Showtimes {
fmt.Println(v.Name, v.City, s.Start, strings.Join(s.Formats, ","))
}
}
}Parametry
movie_idpathwymaganyNumeryczne ID filmu, na przykład550.countryqueryDwuliterowy kod kraju, na przykładRU. Bez niego dostajesz tylko podsumowanie według krajów.regionjest aliasem.api_keyqueryjeden z dwóchTwój klucz. Użyj go albo nagłówkaAuthorization: Bearer.
Pola odpowiedzi
| Pole | Typ | Uwagi |
|---|---|---|
id | integer | ID filmu. |
country | string lub null | Kod wielkimi literami, o który prosisz, albo null, gdy country brakuje lub nie ma dwóch liter. |
results | array | Jeden obiekt na kino, uporządkowane według kina. Puste, gdy nic nie wiadomo lub nie wysłano kraju. Łącznie najwyżej 1500 seansów. |
results[].id | integer | ID kina. |
results[].name | string | Nazwa kina. |
results[].chain | object | key to klucz sieci, name to nazwa sieci albo null. |
results[].city | string lub null | Miasto. |
results[].region | string lub null | Region. |
results[].address | string lub null | Adres ulicy. |
results[].postal_code | string lub null | Kod pocztowy. |
results[].country | string | Kod kraju kina. |
results[].timezone | string lub null | Strefa czasowa IANA, na przykład Europe/Moscow. |
results[].latitude, results[].longitude | number lub null | Pozycja kina. |
results[].phone | string lub null | Numer telefonu. |
results[].url | string lub null | Strona kina. |
results[].showtimes | array | Seanse w tym kinie, uporządkowane według początku. |
results[].showtimes[].date | string | Dzień jako 2026-10-18. |
results[].showtimes[].start | string | Początek w czasie lokalnym kina, na przykład 2026-10-18T21:40, bez przesunięcia UTC. |
results[].showtimes[].end | string lub null | Koniec w czasie lokalnym kina. |
results[].showtimes[].auditorium | string lub null | Nazwa sali. |
results[].showtimes[].formats | array of strings | Formaty, na przykład 2D. |
results[].showtimes[].tags | array of strings | Dodatkowe etykiety. Często puste. |
results[].showtimes[].audio, subtitles, language | string lub null | Szczegóły dźwięku, napisów i języka, gdy znane. |
results[].showtimes[].price | number lub null | Cena biletu. |
results[].showtimes[].currency | string lub null | Waluta price. |
results[].showtimes[].prices | any lub null | Szczegóły cen, gdy kino ma kilka. |
results[].showtimes[].booking_ | string lub null | Link do rezerwacji miejsca. |
results[].showtimes[].sold_ | boolean | true, gdy seans jest wyprzedany. |
countries | array | Podsumowanie według krajów, zobacz niżej. |
Klucze, których używasz, czytaj po nazwie i pomijaj dodatkowe klucze wewnątrz obiektu kina lub seansu. Wiele pól ma dziś wartość null, bo nie każde kino je wysyła.
Przykładowa odpowiedź
{
"id": 550,
"country": "RU",
"results": [
{
"id": 1114,
"name": "Мираж Синема НА БОЛЬШОМ",
"chain": {
"key": "mirage-ru",
"name": "Мираж Синема"
},
"city": "Санкт-Петербург",
"region": null,
"address": "Большой пр. П.С., д. 35А",
"postal_code": null,
"country": "RU",
"timezone": "Europe/Moscow",
"latitude": null,
"longitude": null,
"phone": null,
"url": "https://www.mirage.ru/spb/cinema/1/",
"showtimes": [
{
"date": "2026-10-18",
"start": "2026-10-18T21:40",
"end": null,
"auditorium": null,
"formats": ["2D"],
"tags": [],
"audio": null,
"subtitles": null,
"language": null,
"price": null,
"currency": null,
"prices": null,
"booking_url": "https://www.mirage.ru/ticket_new/aca7b114-d587-4fc5-9df6-28568e8fa9b3/",
"sold_out": false
},
{
"date": "2026-10-19",
"start": "2026-10-19T22:20",
"end": null,
"auditorium": "Зал №4",
"formats": ["2D"],
"tags": [],
"audio": null,
"subtitles": null,
"language": null,
"price": null,
"currency": null,
"prices": null,
"booking_url": "https://www.mirage.ru/ticket_new/0c32e190-890a-4c81-a754-3300fefc4d5e/",
"sold_out": false
}
]
}
],
"countries": [
{
"country": "RU",
"name": "Russia",
"venues": 2,
"cities": 1,
"showtimes": 7,
"first_day": "2026-10-18",
"last_day": "2026-10-21"
}
]
}Lista jest przycięta do 1 z 2 kin i 2 z 4 seansów. Seanse istnieją tylko dla dni, które jeszcze nie minęły, więc ta odpowiedź zmienia się codziennie.
Pobieranie podsumowania według krajów
Pomiń country, a odpowiedź zawiera tylko liczby. results pozostaje puste, a country ma wartość null. Tablica countries wymienia do 60 krajów, które mają jeszcze jakiś seans, na początku ten z największą liczbą seansów. Użyj jej, by dowiedzieć się, gdzie tytuł jest w kinach, zanim poprosisz o kina.
curl -sf "https://api.amodb.dev/3/movie/550/showtimes" \
-H "Authorization: Bearer $AMODB_KEY"{
"id": 550,
"country": null,
"results": [],
"countries": [
{
"country": "RU",
"name": "Russia",
"venues": 2,
"cities": 1,
"showtimes": 7,
"first_day": "2026-10-18",
"last_day": "2026-10-21"
}
]
}| Pole | Typ | Uwagi |
|---|---|---|
countries[].country | string | Dwuliterowy kod, gotowy do użycia jako parametr country. |
countries[].name | string | Angielska nazwa kraju. |
countries[].venues | integer | Kina z seansem. |
countries[].cities | integer | Miasta z seansem. |
countries[].showtimes | integer | Seanse od dziś. |
countries[].first_day, countries[].last_day | string | Pierwszy i ostatni dzień z seansem. |
Kod kraju bez danych, taki jak country=US dla tego filmu, odpowiada country jako US, pustym results i tą samą listą countries. Tytuł bez seansów nigdzie, taki jak serial 1396, ma "countries": [].
Dołączanie seansów do wywołania szczegółów
append_ scala ten sam blok z odpowiedzią szczegółów pod kluczem showtimes. Kod country wyślij w tym samym żądaniu. Blok zachowuje własne klucze id, country, results i countries.
| Żądanie | Wynik |
|---|---|
/ | Rekord filmu plus blok showtimes dla Rosji |
/ | Dodaje obsadę do tego samego wywołania |
Liczy się jako jedno żądanie, więc strona filmu pokazująca obsadę i seanse potrzebuje jednego wywołania. Ten sam endpoint istnieje dla seriali jako GET /.
Łączenie z now_playing i region
Lista now playing daje tytuły. Endpoint seansów daje seanse jednego tytułu. Połącz je w swoim kodzie.
| Krok | Żądanie | Wynik |
|---|---|---|
| 1 | GET / | Do 20 filmów na stronę, w cache przez 30 minut |
| 2 | GET / dla każdego ID | Kina i godziny, gdzie znane |
Poniższa pętla ponawia próbę raz lub dwa razy, gdy zostanie osiągnięty limit planu, czekając liczbę sekund z Retry-After.
const base = 'https://api.amodb.dev/3';
const headers = { Authorization: `Bearer ${process.env.AMODB_KEY}` };
async function get(path, retries = 2) {
const res = await fetch(base + path, { headers });
if (res.status === 429 && retries > 0) {
const wait = Number(res.headers.get('Retry-After') ?? 60);
await new Promise((resolve) => setTimeout(resolve, wait * 1000));
return get(path, retries - 1);
}
if (!res.ok) throw new Error(`amodb returned ${res.status} for ${path}`);
return res.json();
}
const playing = await get('/movie/now_playing?region=RU&page=1');
for (const movie of playing.results) {
const data = await get(`/movie/${movie.id}/showtimes?country=RU`);
if (data.results.length > 0) console.log(movie.title, data.results.length, 'venues');
}Strona z 20 tytułami to 20 żądań o seanse. W planie z 20 żądaniami na minutę zużywa to całe okno, więc zapisz wynik w cache u siebie. Parametry list zobacz w trendy i listy.
Błędy
Treść błędu odpowiada TMDB: success, status_code i status_message. Zły klucz pokazuje status_code 7.
| HTTP | status_code | Kiedy |
|---|---|---|
| 401 | 7 | Brakuje klucza lub jest błędny. |
| 402 | 36 | Okres planu dobiegł końca. |
| 404 | 34 | Brak filmu o tym ID. |
| 429 | 25 | Przekroczono limit żądań na minutę. Poczekaj tyle sekund, ile podaje Retry-After. |
Brak seansów to nie błąd: spodziewaj się statusu 200 i pustej tablicy results. Brakujące lub nieprawidłowe country też nie jest błędem. Zobacz błędy i limity żądań.
Praktyczne uwagi
- Pokrycie zależy od kraju i tytułu. Pustą tablicę
resultstraktuj jako nieznane, a nie jako film nie jest grany. - Pokaż
startdokładnie tak, jak przyszło. To czas lokalny kina bez przesunięcia UTC, a zegar kina jest tym, czego oczekują odwiedzający. - Seanse są w cache na edge przez 30 minut. Nie żądaj ich przy każdym wyświetleniu strony i trzymaj własny cache krótko.
- Użyj jednej listy now playing dla wszystkich odwiedzających w regionie. Na edge też jest w cache przez 30 minut.
- Użyj
booking_url, by wysłać odwiedzającego na stronę rezerwacji kina. Ma wartośćnull, gdy kino nie podaje linku. - Przegląd zastosowania zobacz w API seansów kinowych, a inne dane filmu w filmy.