# API de vídeos e trailers

> Os endpoints de vídeos listam os trailers, teasers, clipes e featurettes ligados a um filme ou série. Cada entrada traz o nome do host, a chave do vídeo, o tipo, um sinalizador oficial, o tamanho e a data de publicação. Os caminhos de temporada e episódio não retornam vídeos. Filtre por idioma e tipo no seu próprio código.

## Endpoint

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

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

Resposta:

```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"
    }
  ]
}
```

## Obter os vídeos de um filme

`GET /3/movie/{movie_id}/videos` retorna os registros de vídeo ligados a um filme. Um registro tem só metadados: um nome, o host que serve o vídeo, a chave do vídeo nesse host, um tipo e alguns sinalizadores. O amodb não retorna arquivos de vídeo.

O exemplo imprime o primeiro trailer oficial em inglês e, se não houver, qualquer trailer em inglês.

```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")
}
```

### Parâmetros

| Parâmetro                            | Em       | Obrigatório | Descrição                                                                                                       |
| ------------------------------------ | -------- | ----------- | --------------------------------------------------------------------------------------------------------------- |
| `movie_id`                           | caminho  | sim         | Id numérico do filme, por exemplo `550`.                                                                        |
| `api_key`                            | consulta | um dos dois | Sua chave. Use este parâmetro ou o header `Authorization: Bearer`.                                              |
| `language`, `include_video_language` | consulta | não         | Aceitos, mas ignorados. A resposta sempre traz todos os vídeos do título. Filtre por `iso_639_1` no seu código. |

### Campos da resposta

| Campo                                         | Tipo     | Observações                                                                                               |
| --------------------------------------------- | -------- | --------------------------------------------------------------------------------------------------------- |
| `id`                                          | inteiro  | O id do filme.                                                                                            |
| `results`                                     | array    | Registros de vídeo, sem ordenação por tipo ou data. Vazio quando nenhum é conhecido.                      |
| `results[].iso_639_1`, `results[].iso_3166_1` | string   | Idioma e país do vídeo, por exemplo `en` e `US`.                                                          |
| `results[].name`                              | string   | Título do vídeo, por exemplo `#TBT Trailer`.                                                              |
| `results[].key`                               | string   | Id do vídeo nesse host.                                                                                   |
| `results[].site`                              | string   | Nome do host do vídeo. Hoje é sempre `YouTube`.                                                           |
| `results[].size`                              | inteiro  | Resolução vertical. Hoje é sempre `1080`.                                                                 |
| `results[].type`                              | string   | `Trailer`, `Teaser`, `Clip`, `Featurette`, `Behind the Scenes`, `Bloopers`, `Opening Credits` ou `Recap`. |
| `results[].official`                          | booleano | Verdadeiro quando o estúdio ou o detentor dos direitos o publicou.                                        |
| `results[].published_at`                      | string   | Timestamp ISO 8601, com ou sem milissegundos.                                                             |
| `results[].id`                                | string   | Id do registro de vídeo. Igual a `key`.                                                                   |

### Exemplo de resposta

Três dos 19 registros do filme 550 são mostrados.

```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"
    }
  ]
}
```

## Tipos de vídeo

O campo `type` diz o que um vídeo é. Compare exatamente, com as maiúsculas mostradas.

| Tipo                | Para que serve                                           |
| ------------------- | -------------------------------------------------------- |
| `Trailer`           | A promoção principal. Mostre este na página de detalhes. |
| `Teaser`            | Um anúncio curto que vem antes do trailer.               |
| `Clip`              | Uma cena tirada do filme ou do episódio finalizado.      |
| `Featurette`        | Um vídeo curto sobre como o título foi feito.            |
| `Behind the Scenes` | Imagens de set e entrevistas.                            |
| `Bloopers`          | Cenas cortadas e erros de gravação.                      |
| `Opening Credits`   | A abertura de uma série.                                 |
| `Recap`             | Um resumo dos episódios anteriores.                      |

Outros valores podem aparecer com o tempo, então trate um `type` desconhecido como um extra genérico e não falhe por causa dele.

## Escolher o vídeo certo

Use a mesma ordem para todo título. Tente seus idiomas em ordem. Dentro de um idioma, os trailers oficiais vêm primeiro, depois qualquer trailer, depois teasers, depois clipes. Dentro de um grupo, ordene por `published_at`: crescente dá o primeiro trailer, decrescente dá o mais 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']);
```

## Idiomas

`language` e `include_video_language` não mudam a resposta, então uma chamada traz todos os vídeos do título. Cada registro tem `iso_639_1` e `iso_3166_1`. O filme 550 tem vídeos marcados como `fr`, `en`, `es`, `pt`, `it`, `cs`, `pl` e `ru`. Filtre por `iso_639_1` no seu código, como mostrado acima, e depois avise ao usuário em que idioma ele vai ouvir o vídeo. Um título pode não ter vídeo no idioma que você quer, então mantenha um fallback em inglês ou em qualquer idioma. Os 14 idiomas atendidos estão listados em [idiomas](https://amodb.dev/pt/languages/).

## Outros endpoints de vídeos

Os caminhos abaixo retornam o mesmo formato com `id` e `results`.

| Método e caminho                                                             | Retorna                          |
| ---------------------------------------------------------------------------- | -------------------------------- |
| `GET /tv/{series_id}/videos`                                                 | Vídeos de uma série.             |
| `GET /tv/{series_id}/season/{season_number}/videos`                          | Sempre um array `results` vazio. |
| `GET /tv/{series_id}/season/{season_number}/episode/{episode_number}/videos` | Sempre um array `results` vazio. |

Você também pode usar `append_to_response=videos` em uma chamada de detalhes de filme ou de série. O bloco acrescentado traz `results` e não tem `id`. As páginas de séries e de temporadas estão descritas em [séries de TV](https://amodb.dev/pt/tv-series/) e [temporadas e episódios](https://amodb.dev/pt/tv-seasons-episodes/).

## Erros

| HTTP | status_code | Quando                                                                                              |
| ---- | ----------- | --------------------------------------------------------------------------------------------------- |
| 401  | 7           | A chave está ausente ou incorreta.                                                                  |
| 402  | 36          | O período do plano terminou.                                                                        |
| 404  | 34          | Nenhuma temporada ou episódio com esse id, ou um id que não é um número.                            |
| 405  | 37          | Você usou um método de escrita em um caminho de vídeos.                                             |
| 429  | 25          | Você passou do seu limite de requisições por minuto. Espere os segundos indicados em `Retry-After`. |

Um id de filme ou de série que não existe não é um erro aqui: o caminho de vídeos responde 200 com `"results": []`, igual a um título conhecido sem vídeos. O caminho de detalhes responde 404 para um id desconhecido. Mais em [erros](https://amodb.dev/pt/errors/) e [limites de requisições](https://amodb.dev/pt/rate-limits/).

## Notas práticas

- Guarde o `site` e a `key` escolhidos junto do título, não um endereço completo, para poder trocar o player depois.
- As listas de vídeos seguem o cache de detalhes de 6 horas na borda. Um cache de cliente de poucas horas acompanha isso.
- `size` é 1080 em todo registro hoje, então não diz qual clipe é mais leve. Deixe o player escolher a qualidade.
- Não conte com a existência de um trailer. Esconda o botão de reproduzir quando sua função de escolha retornar null.
- A ordem de `results` não tem significado. Ordene no seu código.
- Para arquivos de pôster e de imagem de fundo (backdrop), veja [imagens](https://amodb.dev/pt/images-api/). Para a visão do caso de uso, veja [API de trailers de filmes](https://amodb.dev/pt/movie-trailer-api/).

## Perguntas e respostas

### Como pego só o trailer oficial?

Filtre o array results por type igual a Trailer e official igual a true. Se sobrar mais de um, ordene por published_at para pegar o mais antigo ou o mais recente.

### Como pego vídeos no meu idioma?

O endpoint retorna todos os vídeos do título e ignora language e include_video_language. Filtre results por iso_639_1 no seu código, por exemplo pt primeiro e en como fallback. Muitos títulos não têm vídeo em um idioma específico.

### Como reproduzo um vídeo da resposta?

Use o campo site para escolher o player e o campo key como o id do vídeo nesse host. Nos dados servidos hoje, site é sempre YouTube. Monte o endereço de incorporação ou de exibição com o padrão do próprio host. O amodb retorna metadados, não arquivos de vídeo.

### Episódios e temporadas têm vídeos próprios?

Não. Os caminhos de vídeos de temporada e de episódio respondem 200 com um array results vazio. Só filmes e séries têm registros de vídeo.

## Páginas relacionadas

- [API de detalhes de filmes](https://amodb.dev/pt/movies/): API de detalhes de filmes com caminhos e JSON do TMDB v3. Busque um filme por id e junte créditos, avaliações e moods com append_to_response, em 14 idiomas.
- [API de séries de TV](https://amodb.dev/pt/tv-series/): API de séries de TV com os mesmos caminhos e JSON do TMDB v3. Busque uma série por id com temporadas, emissoras, próximo episódio e classificações.
- [API de temporadas e episódios de séries](https://amodb.dev/pt/tv-seasons-episodes/): API de temporadas e episódios com os mesmos caminhos e JSON do TMDB v3. Leia uma temporada com todos os episódios, ou um episódio com data, duração e still.
- [API de trailers de filmes](https://amodb.dev/pt/movie-trailer-api/): API de trailers de filmes no endpoint videos do TMDB v3. Classifique trailers, teasers e clipes por tipo, flag oficial e idioma, com uma requisição por filme.
- [API de imagens e host de imagens](https://amodb.dev/pt/images-api/): API de imagens de filmes com caminhos do TMDB v3: liste pôsteres, backdrops, logos e stills por título e carregue-os de img.amodb.dev em 10 tamanhos, sem chave.
- [Início rápido](https://amodb.dev/pt/quickstart/): Faça sua primeira chamada ao amodb: obtenha uma chave, peça um filme em curl, JavaScript, Python, PHP ou Go e carregue o pôster. Menos de 2 minutos.

Atualizado: 2026-10-18. Source: https://amodb.dev/pt/videos-trailers/
