Looking for the overview — what this API returns, what it costs, and a call you can run without a key? See the Letterboxd API page →
Media, Film & Knowledge

Letterboxd API & Scraper

The Letterboxd API returns film details, ratings and user data as clean JSON.

11 actionsLive JSON1,000 free credits$0.67–$1.50 / 1,000 creditsMCP-ready
Get a free keyOpen in playground

🤖 Using an AI assistant? Copy this link into ChatGPT / Claude / Cursor — it reads every endpoint and parameter instantly and tells you if this API fits your use case.

The primary film endpoint returns a film's title, year, directors, cast, genres, runtime, poster, IMDb/TMDb ids, average rating and rating count, and you can pull a user, their films, diary and lists, film reviews, browse, similar films and popular lists. It is built for film apps, recommendation engines and media research that need Letterboxd data without a scraper. One ReefAPI key, one shared credit pool, the standard envelope.

Reference

Slugs, the star scale and the page sizes Letterboxd fixes for you

Letterboxd has no numeric film id in its public pages, so everything here is addressed by slug. The numbers below are from live calls on Parasite, on a member diary, and on a one-minute 1920 documentary, which is what shows you where the nulls are.

Field or parameterMeasured valueWhat to know
film slugparasite-2019, the-housemaidthe id for every film action. Usually title-year, but a title with no collision has no year suffix. A full film URL is also accepted and parsed down to the slug.
avg_rating4.52the community mean on Letterboxd's 5-star scale, two decimals. Not out of 10.
user_rating, diary rating3.5, 4.0, 4.5half-star granularity from 0.5 to 5.0. null when the member logged the film without rating it: 6 of 72 rows in one member's film list, 16 of 50 in the diary.
watch_count, rating_count7,471,960 and 5,774,276two separate counters. More people log a film than rate it, so watch_count is always the larger of the pair.
like_count, list_count3,859,986 and 884,440likes are the heart, list_count is how many member lists include the film.
imdb_id, tmdb_idtt6751668 and 496243both are strings. tmdb_id is bare digits with no prefix, imdb_id keeps the tt.
year on the film actionnullthe film record does not carry a release year. Read it off the slug suffix, or off imdb_id / tmdb_id in another catalog.
per_pagefilms 72, diary 100, reviews 12, browse 72a hint only. Letterboxd fixes the page size per view and the value it actually used is echoed in meta.per_page. Walk pages with meta.has_more.

Community counters are published only once a film has enough activity. A measured film action on kino-the-girl-of-colour, a one-minute 1920 documentary, returned a title, runtime_minutes 1, genres, a poster, imdb_id tt3307880 and tmdb_id 360370, with avg_rating, rating_count, watch_count, like_count and list_count all null.

Live example

Real request and response JSON

Captured from the indexed primary action, film, on .

Captured request
{
  "method": "POST",
  "url": "https://api.reefapi.com/letterboxd/v1/film",
  "headers": {
    "x-api-key": "$REEF_KEY",
    "content-type": "application/json"
  },
  "body": {
    "film": "parasite-2019"
  }
}
Captured response
{
  "ok": true,
  "meta": {
    "api": "letterboxd",
    "endpoint": "film",
    "mode": "live",
    "latency_ms": 1792.1,
    "record_count": 1,
    "bytes": 322776,
    "cache_hit": false,
    "method": "public_html_json_ld"
  },
  "data": {
    "film": {
      "slug": "parasite-2019",
      "title": "Parasite",
      "name": "Parasite",
      "year": null,
      "tagline": "Act like you own the place.",
      "description": "All unemployed, Ki-taek's family takes peculiar interest in the wealthy and glamorous Parks for their livelihood until they get entangled in an unexpected incident.",
      "poster_url": "https://a.ltrbxd.com/resized/film-poster/4/2/6/4/0/6/426406-parasite-[redacted-phone]-crop.jpg?v=8f5653f710",
      "runtime_minutes": 133,
      "directors": [
        "Bong Joon Ho"
      ],
      "director": "Bong Joon Ho",
      "cast": [
        {
          "name": "[redacted-name]",
          "role": "Kim Ki-taek"
        },
        {
          "name": "[redacted-name]",
          "role": "Park Dong-ik"
        },
        {
          "name": "[redacted-name]",
          "role": "Yeon-kyo"
        }
      ],
      "crew": {
        "producer": [
          "Jang Young-hwan",
          "Kwak Sin-ae",
          "Moon Yang-kwon"
        ],
        "writer": [
          "Kim Dae-hwan",
          "Bong Joon Ho",
          "Han Jin-won"
        ],
        "story": [
          "Bong Joon Ho"
        ],
        "editor": [
          "Yang Jin-mo"
        ],
        "cinematography": [
          "Hong Kyung-pyo"
        ],
        "assistant_director": [
          "Kim Seong-sik",
          "Yoon Young-woo"
        ],
        "executive_producer": [
          "Miky Lee",
          "Heo Min-heoi",
          "Lim Myeong-gyun"
        ],
        "production_design": [
          "Lee Ha-jun"
        ],
        "art_direction": [
          "Mo So-ra"
        ],
        "set_decoration": [
          "Noh Seung-goog",
          "Song Suk-ki",
          "Cho Won-woo"
        ],
        "visual_effects": [
          "Hong Jeong-ho",
          "Peter Ahn",
          "Ha Jae-gu"
        ],
        "stunts": [
          "Yoo Mi-jin",
          "Kwon Ji-hoon",
          "Kang Gyeong-su"
        ],
        "composer": [
          "Jung Jae-il"
        ],
        "sound": [
          "Choi Tae-young",
          "Eun Hee-soo",
          "Kim Byung-in"
        ],
        "costume_design": [
          "Choi Se-yeon"
        ],
        "makeup": [
          "Kim Ho-sik",
          "Kwak Tae-yong",
          "Hwang Hyo-kyun"
        ]
      },
      "writers": [
        "Kim Dae-hwan",
        "Bong Joon Ho",
        "Han Jin-won"
      ],
      "cinematography": [
        "Hong Kyung-pyo"
      ],
      "editors": [
        "Yang Jin-mo"
      ],
      "composers": [
        "Jung Jae-il"
      ],
      "producers": [
        "Jang Young-hwan",
        "Kwak Sin-ae",
        "Moon Yang-kwon"
      ],
      "genres": [
        "Thriller",
        "Comedy",
        "Drama"
      ],
      "tags": [
        "Thriller",
        "Comedy",
        "Drama"
      ],
      "themes": [
        "Intense violence and sexual transgression",
        "Humanity and the world around us",
        "Moving relationship stories"
      ],
      "alternative_titles": [
        "ชนชั้นปรสิต",
        "パラサイト 半地下の家族:2019",
        "Parazit"
      ],
      "similar_films": [
        {
          "slug": "no-other-choice-2025",
          "name": null,
          "url": "https://letterboxd.com/film/no-other-choice-2025/",
          "user_rating": null
        },
        {
          "slug": "the-housemaid",
          "name": null,
          "url": "https://letterboxd.com/film/the-housemaid/",
          "user_rating": null
        },
        {
          "slug": "saltburn",
          "name": null,
          "url": "https://letterboxd.com/film/saltburn/",
          "user_rating": null
        }
      ],
      "countries": [
        "South Korea"
      ],
      "languages": [
        "English",
        "German",
        "Korean"
      ],
      "production_companies": [
        "Barunson E&A"
      ],
      "imdb_id": "tt6751668",
      "tmdb_id": "496243",
      "imdb_url": "https://www.imdb.com/title/tt6751668/",
      "tmdb_url": "https://www.themoviedb.org/movie/496243/",
      "url": "https://letterboxd.com/film/parasite-2019/",
      "avg_rating": 4.52,
      "rating_count": 5578743,
      "review_count": 744252,
      "watch_count": 7231524,
      "like_count": 3759340,
      "list_count": 865763,
      "watches": 7231524,
      "lists": 865763,
      "likes": 3759340,
      "fans": null
    }
  }
}
Actions

What the Letterboxd API does

ActionDescriptionConcrete use caseKey params
filmFull Letterboxd film detail by film slug or URL: title, year, directors, cast, genres, runtime, poster, IMDb/TMDb IDs, average rating, total ratings, watch count, like count, and list appearances.Content platforms call film to get full Letterboxd film detail by film slug or URL.film, film_slug, url
userPublic Letterboxd member profile and stats by username: display name, avatar, bio, film/list/follower counts, and the member's favourite films.Research tools call user to get public Letterboxd member profile and stats by username.user
user_filmsPaginated list of films a Letterboxd member has watched and rated, with their personal star rating for each.Community analysts call user_films to get paginated list of films a Letterboxd member has watched and rated, with their personal star r….user, page, per_page
user_diaryPaginated diary entries for a Letterboxd member: film slug, name, watch date, and star rating for each viewing.Media monitors call user_diary to get paginated diary entries for a Letterboxd member.user, page, per_page
listA public Letterboxd curated film list: title, description, and the paginated film entries with user ratings.Content platforms call list to get a public Letterboxd curated film list.user, list, page, per_page
film_reviewsPaginated public reviews for a Letterboxd film: reviewer username, display name, star rating, review text, and like count.Research tools call film_reviews to get paginated public reviews for a Letterboxd film.film, film_slug, url, page, per_page
browseBrowse Letterboxd films with optional genre / decade / year filters, ordered by popularity, rating, release date, or runtime (paginated): slug, name, URL, and average rating.Community analysts call browse to get browse Letterboxd films with optional genre / decade / year filters, ordered by popularity, r….sort, genre, decade, year, page, ...
film_similarFilms Letterboxd shows as similar/related to a given film: slug, name, URL — useful for recommendation and discovery off a single seed film.Media monitors call film_similar to get films Letterboxd shows as similar/related to a given film.film, film_slug, url
lists_popularBrowse Letterboxd's most popular member-curated film lists for a time window (week/month/year/all): list title, owner username, list slug+URL, and a preview of the first films.Content platforms call lists_popular to get browse Letterboxd's most popular member-curated film lists for a time window (week/month/year….period, page, per_page
user_listsThe public film lists a Letterboxd member has created (paginated): list title, slug+URL, and a preview of the first films in each list.Research tools call user_lists to get the public film lists a Letterboxd member has created (paginated).user, page, per_page
searchSearch Letterboxd for films, members, or curated lists by keyword — returns matching results with ratings and links.Community analysts call search to search Letterboxd for films, members, or curated lists by keyword.query, type, page, per_page
Code samples

Call film from your stack

curl -X POST https://api.reefapi.com/letterboxd/v1/film \
  -H "x-api-key: $REEF_KEY" \
  -H "content-type: application/json" \
  -d '{"film":"parasite-2019"}'
MCP one-liner
Ask your MCP-connected assistant: call reefapi.letterboxd.film with {"film":"parasite-2019"}.
Use cases

Who uses this API and why

  • Film apps call film to enrich a title with rating, cast and cross-links to IMDb and TMDb.
  • Recommendation engines use film_similar and lists_popular to surface related films.
  • Media research uses user_films and film_reviews to study taste and sentiment.
FAQ

Questions developers ask before integrating

Why is year null even though the slug ends in a year?

The film action does not return a release year. Measured on parasite-2019, the-sheep-detectives and kino-the-girl-of-colour, year came back null every time while runtime_minutes, genres and the external ids were populated. The year in a slug is a disambiguator Letterboxd adds when two films share a title, not a data field, and plenty of slugs have no year at all. If you need a reliable year, take imdb_id or tmdb_id from the same record and resolve it elsewhere.

Why does an obscure film come back with no rating at all?

Letterboxd only publishes a rating histogram once a film has accumulated enough ratings, and below that threshold the page carries no numbers to read. A live call on kino-the-girl-of-colour returned a complete identity block, with title, runtime, genre, poster, tt3307880 and tmdb 360370, and null for avg_rating, rating_count, watch_count, like_count and list_count together. All five going null at once is the signal that the film is below the threshold, not that the call failed.

How does the half-star rating come back in the JSON?

As a float, not as stars or a string. Letterboxd's scale runs from half a star to five in half-star steps, and the API mirrors that exactly: a measured diary page returned 4.0, 3.5, 4.5, 2.5 and 2.0, and never a value like 3.7. Multiply by two if you need integer buckets. A member who logged a film without rating it produces null, which is different from a zero and should not be averaged in.

Why is watch_count higher than rating_count on every film?

They count different actions. watch_count is how many members marked the film as watched, rating_count is how many attached a star rating, and marking watched does not require rating. On Parasite the gap was 7,471,960 watches against 5,774,276 ratings, with 3,859,986 likes and 884,440 list appearances on top. If you are ranking by popularity, watch_count is the broader signal and rating_count is the one avg_rating is actually computed over.

What does this give me that the imdb or movies-tv engines do not?

The community layer. IMDb gives you a 10-point rating and a vote count, TMDB gives you a 10-point rating and popularity, and neither of them knows how many people put a film in a list or logged it in a diary. This engine returns the Letterboxd 5-star average, the watch, like and list counters, per-member diary entries with watch dates, member film lists with each member's own rating, and curated lists ranked by period. It also returns Letterboxd's editorial themes, which are phrases such as Intense violence and sexual transgression rather than genre labels.

Can I control how many rows a page returns?

No. per_page is accepted but treated as a hint, because Letterboxd fixes the page size per view server side. Measured: user_films returned 72 rows, user_diary returned 50 rows on a page reported as per_page 100, film_reviews returned 12, and browse returned 72. The value actually used comes back in meta.per_page and meta.has_more tells you whether to ask for the next page. Budget your calls off those two, not off a number you sent.

Why do user_films rows have a null name?

That view is a poster grid, so the only identity on the page is the film slug and its link. A measured page for one member returned rows of slug, url, user_rating and name null. Treat slug as the join key, which is what every other action in this engine takes anyway, and call film only for the slugs you actually need to display. user_diary is the richer sibling: its rows carry both slug and a name that includes the year, such as Spider-Man: No Way Home (2021).

What is the difference between genres, tags and themes?

genres is the conventional list, Thriller, Comedy, Drama on Parasite. tags came back identical to genres on the films measured, so do not treat it as a second signal. themes is the one that is genuinely different: it is Letterboxd's own editorial clustering and returns phrases such as Humanity and the world around us or Moving relationship stories, eight of them on Parasite. There is no numeric id on any of the three, so they join on the string.

What is the Letterboxd API?

Letterboxd API is a ReefAPI endpoint group for letterboxd It returns live JSON through POST requests under /letterboxd/v1.

Is the Letterboxd API free to try?

Yes. ReefAPI starts with 1,000 free credits, no card required. Letterboxd calls use the same shared credit balance as every other ReefAPI engine.

Do I need a Letterboxd login or account?

No login to Letterboxd is needed for the API response. You call ReefAPI with your x-api-key header, and the playground can run live examples before you create a production key.

How fresh is the Letterboxd data?

The page example is captured from a live film call, and production requests fetch live data through ReefAPI rather than a static sample.

How many credits does the Letterboxd API use?

Letterboxd actions currently cost 1 credit per successful call. Failed or blocked calls are free, and all APIs draw from one credit pool.

Can I call Letterboxd from an AI assistant or MCP client?

Yes. Connect ReefAPI once through MCP and your assistant can call letterboxd actions with the same key, credit pool and JSON envelope used by normal REST requests.

docs / letterboxd

Letterboxd

Letterboxd

base /letterboxd/v111 endpoints
post/letterboxd/v1/film1 credit

Full Letterboxd film detail by film slug or URL: title, year, directors, cast, genres, runtime, poster, IMDb/TMDb IDs, average rating, total ratings, watch count, like count, and list appearances.

ParameterAllowed / rangeDescription
filmoptionalLetterboxd film slug, OR a full film URL (https://letterboxd.com/film/parasite-2019/) — the path is parsed to the slug.
Try in playground →
post/letterboxd/v1/user1 credit

Public Letterboxd member profile and stats by username: display name, avatar, bio, film/list/follower counts, and the member's favourite films.

ParameterAllowed / rangeDescription
userrequiredLetterboxd username (the handle in a profile URL), OR a profile URL.
Try in playground →
post/letterboxd/v1/user_films1 credit

Paginated list of films a Letterboxd member has watched and rated, with their personal star rating for each.

ParameterAllowed / rangeDescription
userrequiredLetterboxd username (the handle in a profile URL), OR a profile URL.
page = 1optional1–1-based page number. Use meta.has_more to know when to stop; values < 1 clamp to 1.
per_pageoptionalHint only — Letterboxd fixes the page size per view (films 72, reviews 12, diary/list 100); reported back in meta.per_page.
Try in playground →
post/letterboxd/v1/user_diary1 credit

Paginated diary entries for a Letterboxd member: film slug, name, watch date, and star rating for each viewing.

ParameterAllowed / rangeDescription
userrequiredLetterboxd username (the handle in a profile URL), OR a profile URL.
page = 1optional1–1-based page number. Use meta.has_more to know when to stop; values < 1 clamp to 1.
per_pageoptionalHint only — Letterboxd fixes the page size per view (films 72, reviews 12, diary/list 100); reported back in meta.per_page.
Try in playground →
post/letterboxd/v1/list1 credit

A public Letterboxd curated film list: title, description, and the paginated film entries with user ratings.

ParameterAllowed / rangeDescription
userrequiredLetterboxd username (the handle in a profile URL), OR a profile URL.
listrequiredList slug (the segment after /list/ in a list URL).
page = 1optional1–1-based page number. Use meta.has_more to know when to stop; values < 1 clamp to 1.
per_pageoptionalHint only — Letterboxd fixes the page size per view (films 72, reviews 12, diary/list 100); reported back in meta.per_page.
Try in playground →
post/letterboxd/v1/film_reviews1 credit

Paginated public reviews for a Letterboxd film: reviewer username, display name, star rating, review text, and like count.

ParameterAllowed / rangeDescription
filmoptionalLetterboxd film slug, OR a full film URL (https://letterboxd.com/film/parasite-2019/) — the path is parsed to the slug.
page = 1optional1–1-based page number. Use meta.has_more to know when to stop; values < 1 clamp to 1.
per_pageoptionalHint only — Letterboxd fixes the page size per view (films 72, reviews 12, diary/list 100); reported back in meta.per_page.
Try in playground →
post/letterboxd/v1/browse1 credit

Browse Letterboxd films with optional genre / decade / year filters, ordered by popularity, rating, release date, or runtime (paginated): slug, name, URL, and average rating.

ParameterAllowed / rangeDescription
sort = popularoptionalpopular · rating · release · shortest · longestOrdering for the films browser.
genreoptionalaction · adventure · animation · comedy · crime · documentary · drama · family · fantasy · history · horror · music · mystery · romance · science-fiction · thriller · tv-movie · war · westernOptional genre filter for the films browser (e.g. horror, science-fiction). Combine with sort to get e.g. highest-rated horror.
decadeoptionalOptional decade filter, e.g. '1990s', '2010s'. Combine with sort and/or genre.
yearoptionalOptional release-year filter, e.g. 2019. Combine with sort and/or genre.
page = 1optional1–1-based page number. Use meta.has_more to know when to stop; values < 1 clamp to 1.
per_pageoptionalHint only — Letterboxd fixes the page size per view (films 72, reviews 12, diary/list 100); reported back in meta.per_page.
Try in playground →
post/letterboxd/v1/film_similar1 credit

Films Letterboxd shows as similar/related to a given film: slug, name, URL — useful for recommendation and discovery off a single seed film.

ParameterAllowed / rangeDescription
filmoptionalLetterboxd film slug, OR a full film URL (https://letterboxd.com/film/parasite-2019/) — the path is parsed to the slug.
Try in playground →
post/letterboxd/v1/user_lists1 credit

The public film lists a Letterboxd member has created (paginated): list title, slug+URL, and a preview of the first films in each list.

ParameterAllowed / rangeDescription
userrequiredLetterboxd username (the handle in a profile URL), OR a profile URL.
page = 1optional1–1-based page number. Use meta.has_more to know when to stop; values < 1 clamp to 1.
per_pageoptionalHint only — Letterboxd fixes the page size per view (films 72, reviews 12, diary/list 100); reported back in meta.per_page.
Try in playground →