# API dei video e dei trailer

> Gli endpoint dei video elencano trailer, teaser, clip e featurette collegati a un film o a una serie. Ogni voce dà il nome dell'host, una chiave del video, un tipo, un flag ufficiale, una dimensione e una data di pubblicazione. I percorsi di stagioni ed episodi esistono ma non restituiscono video. Filtra per lingua e tipo nel tuo codice.

## Endpoint

`GET /3/movie/{movie_id}/videos`

```bash
curl "https://api.amodb.dev/3/movie/550/videos" \
  -H "Authorization: Bearer $AMODB_KEY"
```

Risposta:

```json
{
  "id": 550,
  "results": [
    {
      "iso_639_1": "en",
      "iso_3166_1": "US",
      "name": "Theatrical Trailer (HD Fan Remaster)",
      "key": "6JnN1DmbqoU",
      "site": "YouTube",
      "size": 1080,
      "type": "Trailer",
      "official": false,
      "published_at": "2015-02-26T03:19:25Z",
      "id": "6JnN1DmbqoU"
    },
    {
      "iso_639_1": "en",
      "iso_3166_1": "US",
      "name": "#TBT Trailer",
      "key": "BdJKm16Co6M",
      "site": "YouTube",
      "size": 1080,
      "type": "Trailer",
      "official": true,
      "published_at": "2014-10-02T19:20:22Z",
      "id": "BdJKm16Co6M"
    },
    {
      "iso_639_1": "en",
      "iso_3166_1": "US",
      "name": "20th Anniversary Trailer",
      "key": "dfeUzm6KF4g",
      "site": "YouTube",
      "size": 1080,
      "type": "Trailer",
      "official": true,
      "published_at": "2019-10-15T18:59:47Z",
      "id": "dfeUzm6KF4g"
    }
  ]
}
```

## Ottenere i video di un film

`GET /3/movie/{movie_id}/videos` restituisce i record video collegati a un film. Un record contiene solo metadati: un nome, l'host che serve il video, la chiave del video su quell'host, un tipo e qualche flag. amodb non restituisce file video.

L'esempio stampa il primo trailer ufficiale in inglese, ripiegando su un qualsiasi trailer in inglese.

```bash
curl -s "https://api.amodb.dev/3/movie/550/videos" \
  -H "Authorization: Bearer $AMODB_KEY"
```

```js
const url = 'https://api.amodb.dev/3/movie/550/videos';
const res = await fetch(url, { headers: { Authorization: `Bearer ${process.env.AMODB_KEY}` } });
if (!res.ok) throw new Error(`amodb returned ${res.status}`);
const { results } = await res.json();
const trailers = results.filter((v) => v.type === 'Trailer' && v.iso_639_1 === 'en');
const pick = trailers.find((v) => v.official) ?? trailers[0];
console.log(pick ? `${pick.name} (${pick.site}, key ${pick.key})` : 'no trailer');
```

```python
import os
import requests

r = requests.get(
    "https://api.amodb.dev/3/movie/550/videos",
    headers={"Authorization": f"Bearer {os.environ['AMODB_KEY']}"},
    timeout=10,
)
r.raise_for_status()
trailers = [v for v in r.json()["results"] if v["type"] == "Trailer" and v["iso_639_1"] == "en"]
official = [v for v in trailers if v["official"]]
pick = (official or trailers or [None])[0]
print(f"{pick['name']} ({pick['site']}, key {pick['key']})" if pick else "no trailer")
```

```php
<?php
$url = 'https://api.amodb.dev/3/movie/550/videos';
$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");
}
$trailers = array_values(array_filter(
    json_decode($body, true)['results'],
    fn($v) => $v['type'] === 'Trailer' && $v['iso_639_1'] === 'en'
));
$official = array_values(array_filter($trailers, fn($v) => $v['official']));
$pick = $official[0] ?? $trailers[0] ?? null;
echo $pick ? "{$pick['name']} ({$pick['site']}, key {$pick['key']})" : 'no trailer', PHP_EOL;
```

```go
package main

import (
	"encoding/json"
	"fmt"
	"net/http"
	"os"
	"time"
)

type Videos struct {
	Results []struct {
		Name     string `json:"name"`
		Key      string `json:"key"`
		Site     string `json:"site"`
		Type     string `json:"type"`
		Language string `json:"iso_639_1"`
		Official bool   `json:"official"`
	} `json:"results"`
}

func main() {
	url := "https://api.amodb.dev/3/movie/550/videos"
	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 v Videos
	if err := json.NewDecoder(res.Body).Decode(&v); err != nil {
		panic(err)
	}
	for _, r := range v.Results {
		if r.Type == "Trailer" && r.Language == "en" && r.Official {
			fmt.Printf("%s (%s, key %s)\n", r.Name, r.Site, r.Key)
			return
		}
	}
	fmt.Println("no official trailer")
}
```

### Parametri

| Parametro                            | In       | Obbligatorio | Descrizione                                                                                                         |
| ------------------------------------ | -------- | ------------ | ------------------------------------------------------------------------------------------------------------------- |
| `movie_id`                           | percorso | sì           | ID numerico del film, per esempio `550`.                                                                            |
| `api_key`                            | query    | uno dei due  | La tua chiave. Usa questa o l'header `Authorization: Bearer`.                                                       |
| `language`, `include_video_language` | query    | no           | Accettati ma ignorati. La risposta contiene sempre tutti i video del titolo. Filtra per `iso_639_1` nel tuo codice. |

### Campi della risposta

| Campo                                         | Tipo     | Note                                                                                                     |
| --------------------------------------------- | -------- | -------------------------------------------------------------------------------------------------------- |
| `id`                                          | intero   | ID del film.                                                                                             |
| `results`                                     | array    | Record video, non ordinati per tipo o data. Vuoto quando non se ne conosce nessuno.                      |
| `results[].iso_639_1`, `results[].iso_3166_1` | stringa  | Lingua e paese del video, per esempio `en` e `US`.                                                       |
| `results[].name`                              | stringa  | Titolo del video, per esempio `#TBT Trailer`.                                                            |
| `results[].key`                               | stringa  | ID del video su quell'host.                                                                              |
| `results[].site`                              | stringa  | Nome dell'host del video. Oggi sempre `YouTube`.                                                         |
| `results[].size`                              | intero   | Risoluzione verticale. Oggi sempre `1080`.                                                               |
| `results[].type`                              | stringa  | `Trailer`, `Teaser`, `Clip`, `Featurette`, `Behind the Scenes`, `Bloopers`, `Opening Credits` o `Recap`. |
| `results[].official`                          | booleano | Vero quando lo studio o il titolare dei diritti l'ha pubblicato.                                         |
| `results[].published_at`                      | stringa  | Timestamp ISO 8601, con o senza millisecondi.                                                            |
| `results[].id`                                | stringa  | ID del record video. Uguale a `key`.                                                                     |

### Risposta di esempio

Sono mostrati tre dei 19 record del film 550.

```json
{
  "id": 550,
  "results": [
    {
      "iso_639_1": "en",
      "iso_3166_1": "US",
      "name": "Theatrical Trailer (HD Fan Remaster)",
      "key": "6JnN1DmbqoU",
      "site": "YouTube",
      "size": 1080,
      "type": "Trailer",
      "official": false,
      "published_at": "2015-02-26T03:19:25Z",
      "id": "6JnN1DmbqoU"
    },
    {
      "iso_639_1": "en",
      "iso_3166_1": "US",
      "name": "#TBT Trailer",
      "key": "BdJKm16Co6M",
      "site": "YouTube",
      "size": 1080,
      "type": "Trailer",
      "official": true,
      "published_at": "2014-10-02T19:20:22Z",
      "id": "BdJKm16Co6M"
    },
    {
      "iso_639_1": "en",
      "iso_3166_1": "US",
      "name": "Mark Kermode introduces Fight Club | Film4 Interview",
      "key": "tiWCNtGDGEY",
      "site": "YouTube",
      "size": 1080,
      "type": "Featurette",
      "official": true,
      "published_at": "2015-05-08T15:59:05Z",
      "id": "tiWCNtGDGEY"
    }
  ]
}
```

## Tipi di video

Il campo `type` ti dice cos'è un video. Confrontalo in modo esatto, con le maiuscole indicate.

| Tipo                | Da usare per                                              |
| ------------------- | --------------------------------------------------------- |
| `Trailer`           | La promo principale. Mostralo in una pagina di dettaglio. |
| `Teaser`            | Un breve annuncio che precede il trailer.                 |
| `Clip`              | Una scena presa dal film o dall'episodio finito.          |
| `Featurette`        | Un breve pezzo su come è stato realizzato il titolo.      |
| `Behind the Scenes` | Riprese sul set e interviste.                             |
| `Bloopers`          | Scene fuori onda e gag.                                   |
| `Opening Credits`   | La sigla di apertura di una serie.                        |
| `Recap`             | Un riassunto degli episodi precedenti.                    |

Col tempo possono comparire altri valori, quindi tratta un `type` sconosciuto come un extra generico e non far fallire il codice.

## Scegliere il video giusto

Usa lo stesso ordine per ogni titolo. Prova le tue lingue in ordine. All'interno di una lingua vengono prima i trailer ufficiali, poi un trailer qualsiasi, poi i teaser, poi le clip. All'interno di un gruppo ordina per `published_at`: crescente dà il primo trailer, decrescente dà il più recente.

```js
function pickVideo(results, langs = ['en']) {
  const order = ['Trailer', 'Teaser', 'Clip'];
  for (const lang of langs) {
    for (const type of order) {
      const group = results
        .filter((v) => v.iso_639_1 === lang && v.type === type)
        .sort((a, b) => Number(b.official) - Number(a.official) || Date.parse(a.published_at) - Date.parse(b.published_at));
      if (group.length > 0) return group[0];
    }
  }
  return null;
}

// Russian first, English as the fallback.
// const video = pickVideo(results, ['ru', 'en']);
```

## Lingue

`language` e `include_video_language` non cambiano la risposta, quindi una sola chiamata dà tutti i video del titolo. Ogni record porta `iso_639_1` e `iso_3166_1`. Il film 550 ha video etichettati `fr`, `en`, `es`, `pt`, `it`, `cs`, `pl` e `ru`. Filtra per `iso_639_1` nel tuo codice come mostrato sopra, poi indica all'utente in che lingua sta per ascoltare. Un titolo può non avere alcun video nella lingua che vuoi, quindi tieni un ripiego sull'inglese o su una lingua qualsiasi. Le 14 lingue servite sono elencate nella pagina [lingue](https://amodb.dev/it/languages/).

## Altri endpoint dei video

I percorsi qui sotto restituiscono la stessa struttura `id` e `results`.

| Metodo e percorso                                                            | Restituisce                      |
| ---------------------------------------------------------------------------- | -------------------------------- |
| `GET /tv/{series_id}/videos`                                                 | Video di una serie.              |
| `GET /tv/{series_id}/season/{season_number}/videos`                          | Sempre un array `results` vuoto. |
| `GET /tv/{series_id}/season/{season_number}/episode/{episode_number}/videos` | Sempre un array `results` vuoto. |

Puoi anche aggiungere `append_to_response=videos` a una chiamata di dettagli di film o serie. Il blocco aggiunto contiene `results` e nessun `id`. Le pagine di serie e stagioni sono descritte in [serie TV](https://amodb.dev/it/tv-series/) e [stagioni ed episodi](https://amodb.dev/it/tv-seasons-episodes/).

## Errori

| HTTP | status_code | Quando                                                                   |
| ---- | ----------- | ------------------------------------------------------------------------ |
| 401  | 7           | La chiave manca o è sbagliata.                                           |
| 402  | 36          | Il periodo del piano è terminato.                                        |
| 404  | 34          | Nessuna stagione o episodio con quell'ID, o un ID che non è un numero.   |
| 405  | 37          | Hai usato un metodo di scrittura su un percorso di video.                |
| 429  | 25          | Hai superato le richieste al minuto. Attendi i secondi di `Retry-After`. |

Un ID di film o serie che non esiste non è un errore qui: il percorso dei video risponde 200 con `"results": []`, come per un titolo noto senza video. Il percorso dei dettagli risponde 404 per un ID sconosciuto. Altro nelle pagine [errori](https://amodb.dev/it/errors/) e [limiti di richieste](https://amodb.dev/it/rate-limits/).

## Note pratiche

- Salva `site` e `key` scelti insieme al titolo, non un indirizzo completo, così potrai cambiare player più avanti.
- Le liste dei video seguono la cache dei dettagli di 6 ore sull'edge. Una cache client di poche ore corrisponde.
- `size` oggi è 1080 per ogni record, quindi non ti dice quale clip sia leggera. Lascia che sia il player a scegliere la qualità.
- Non contare sull'esistenza di un solo trailer. Nascondi il pulsante di riproduzione quando la tua funzione di scelta restituisce null.
- L'ordine di `results` non ha alcun significato. Ordina nel tuo codice.
- Per i file di locandine e sfondi vedi [immagini](https://amodb.dev/it/images-api/). Per la vista per caso d'uso, vedi l'[API per i trailer](https://amodb.dev/it/movie-trailer-api/).

## Domande e risposte

### Come ottengo solo il trailer ufficiale?

Filtra l'array results per type uguale a Trailer e official uguale a true. Se ne restano diversi, ordina per published_at per prendere il più vecchio o il più recente.

### Come ottengo i video nella mia lingua?

L'endpoint restituisce tutti i video del titolo e ignora language e include_video_language. Filtra results per iso_639_1 nel tuo codice, per esempio prima ru e en come ripiego. Molti titoli non hanno alcun video in una data lingua.

### Come riproduco un video dalla risposta?

Usa il campo site per scegliere il player e il campo key come ID del video su quell'host. Nei dati serviti oggi site è sempre YouTube. Costruisci l'indirizzo di incorporamento o di visione con il modello proprio di quell'host. amodb restituisce metadati, non file video.

### Episodi e stagioni hanno video propri?

No. I percorsi dei video di stagioni ed episodi rispondono 200 con un array results vuoto. Solo film e serie portano record video.

## Pagine correlate

- [API dei dettagli del film](https://amodb.dev/it/movies/): API dettagli film con gli stessi percorsi e JSON di TMDB v3. Ottieni un film per ID, aggiungi crediti, valutazioni e mood con append_to_response, in 14 lingue.
- [API delle serie TV](https://amodb.dev/it/tv-series/): API serie TV con gli stessi percorsi e JSON di TMDB v3. Ottieni una serie per ID con stagioni, emittenti e prossimo episodio, più classificazioni e piattaforme.
- [API di stagioni ed episodi delle serie TV](https://amodb.dev/it/tv-seasons-episodes/): API stagioni ed episodi con gli stessi percorsi e JSON di TMDB v3. Leggi una stagione con tutti gli episodi, o un episodio con data, durata e immagine.
- [API per i trailer dei film](https://amodb.dev/it/movie-trailer-api/): API trailer sull'endpoint videos di TMDB v3. Ordina trailer, teaser e clip per tipo, flag ufficiale e codice lingua, con una richiesta per titolo.
- [API delle immagini e host delle immagini](https://amodb.dev/it/images-api/): API immagini dei film con percorsi TMDB v3: elenca locandine, sfondi, loghi e fermi immagine di ogni titolo e caricali da img.amodb.dev in 10 dimensioni.
- [Avvio rapido](https://amodb.dev/it/quickstart/): Fai la prima chiamata ad amodb: ottieni una chiave, richiedi i dettagli di un film in curl, JavaScript, Python, PHP o Go, carica la locandina. Meno di 2 minuti.

Aggiornato: 2026-10-18. Source: https://amodb.dev/it/videos-trailers/
