---
title: "List all ski resorts"
method: GET
path: "/api/v1/resorts"
tags: ["Resorts"]
---

# List all ski resorts

`GET /api/v1/resorts`

## Request

- Base URL: `https://www.snowsure.ai`
- URL: `https://www.snowsure.ai/api/v1/resorts`
- Auth: none declared

Returns ski resorts with current conditions and SnowSure scores. Use for: browse or filter by region/country; best resorts in Europe, Asia, or North America; sort by score, snowfall, or forecast. Example: ?region=asia&sort=score&limit=20

**Forecast entitlement (SS-W-318).** Days 1–7 and the blended total are public. Days 8–14 and the per-model series (`models`, `byModel`, `comparableWindow`, `modelCoverageDays`) require an entitled caller: SnowSure Pro, or a signed-in free reader asking about a resort in their My Mountains. An unauthenticated request receives the free window — `forecast.daily` cut to seven days, `total14dCm` equal to the total of those days, and `forecastHorizonDays: 7` stating the span. The field keeps its name so existing consumers keep reading a number; read `forecastHorizonDays` to know what it covers. There is no partner key: every caller follows the same rule.

## Query parameters

- `limit` integer
- `region` 'europe' | 'north-america' | 'asia' | 'oceania' | 'south-america'
- `country` string
- `sort` 'score' | 'snowfall' | 'forecast' | 'name'
- `slugs` string
- `cursor` string
- `include` string

## Response `200`

Successful response

- ResortsResponse
  - `meta` object
    - `source` string
    - `timestamp` string, date-time
    - `total` integer: Resorts matching the query across every page, not the rows in this response (see count). With no filters this is the size of the fleet.
    - `count` integer: Rows in this response.
    - `region` string: Region filter applied
  - `data` object[]
    - `name` string: Resort name
    - `slug` string: URL-friendly identifier
    - `aliases` string[]: Alternate slugs that resolve to this resort on /api/v1/resorts/{slug}. The list emits only canonical slugs, so match against slug AND aliases before concluding a resort is absent.
    - `country` string: Country where the resort is located
    - `region` string: Geographic region
    - `coordinates` object
      - `lat` number: Latitude
      - `lng` number: Longitude
    - `elevation` object
      - `summit` integer: Summit elevation in meters
      - `base` integer: Base elevation in meters
      - `vertical` integer: Vertical drop in meters
    - `stats` object
      - `runs` integer: Number of ski runs
      - `lifts` integer: Number of lifts
      - `skiableAcres` integer: Skiable terrain in acres
      - `pisteKm` number, nullable: Total marked piste length in km, as the resort publishes it. A length, never an area. Null when unknown. Detail response only.
      - `annualSnowfall` string: Average annual snowfall
    - `conditions` object
      - `snowDepthCm` number: Current BASE-band snow depth in centimeters — the value sort=depth ranks on. A measured mid/summit headline is on /resorts/{slug} only, so the board stays like-for-like.
      - `snowDepthElevationBand` 'base' | 'null', nullable: Always base when snowDepthCm is set (SS-W-201 ranking rule).
      - `snowfall24hCm` number: Snowfall in last 24 hours (cm)
      - `snowfall7dCm` number: Snowfall in the PAST 7 days (cm). Not to be confused with forecast7dCm, which is the week ahead.
      - `forecast7dCm` number, nullable: FORWARD 7-day blended snowfall forecast (cm) — the industry comparison window, and the field sort=forecast7d ranks on. Equals the sum of the first 7 daily rows from the forecast endpoint, to 0.1cm. null (never 0) when the blend has no data for this resort; 0 means a forecast of no snow.
      - `forecastPeak` object, nullable: The single biggest snowfall day inside the forward 7-day window — forecast7dCm's window, NOT forecast14dCm's. null when no snow is forecast. Since SS-W-207 the object carries windowDays so the pair can never be read against the wrong total.
        - `date` string, date
        - `cm` number
        - `windowDays` integer: How many forward days this peak was the biggest of. Always 7 on this object. For the biggest day of a 14-day total, read forecast.peak on /api/v1/resorts/{slug}, which is chosen from the daily rows that endpoint serves and carries its own windowDays.
      - `forecastHorizonDays` 7 | 14: How many forward days `forecast14dCm` covers for THIS caller (SS-W-318, SS-W-378). 14 for an entitled caller — SnowSure Pro, or a resort in a signed-in reader's My Mountains; 7 otherwise, and then `forecast14dCm` holds the seven-day total, the same figure as `forecast7dCm`. Read this before naming the number: a seven-day total must never be labelled as a fortnight.
      - `forecast14dCm` number, nullable: Sum over the forecast horizon the caller is entitled to; equals `forecast7dCm` when `forecastHorizonDays` is 7 (anonymous and free callers). Read `forecastHorizonDays` before calling this a 14-day total (SS-W-1460). The blended forecast total (cm, 1 dp) over the window `forecastHorizonDays` states: the forward 14 days for an entitled caller, or the free seven days — equal to `forecast7dCm` — for one without the fortnight. The key keeps its name so existing consumers keep reading a number. For an entitled caller it is the same value as forecast.total14dCm on /api/v1/resorts/{slug}. A per-day blend over the models covering each day, so it can sit outside the per-model totals, which each cover only their own model's horizon. null (never 0) when the blend has no data.
      - `temperature` number: Current temperature in Celsius
      - `weatherConditions` string: Current weather description
      - `seasonTotalCm` number, nullable: Season-to-date snowfall (cm): the operator-reported season total when present, otherwise the modelled season sum, floored at the base depth for an open resort. The same arithmetic as snow.seasonTotalCm on /api/v1/resorts/{slug}. null when unknown.
      - `lastUpdated` string, date-time, nullable: When the data behind this row was captured: the later of the weather snapshot's capture time and its lift-data update time. Never the request time and never a time in the future. Equal to currentConditions.lastUpdated on /api/v1/resorts/{slug} for the same resort. null when the resort has no snapshot or the snapshot carries neither time.
    - `snowSure` object
      - `score` integer: SnowSure Score (0-100)
      - `rating` 'Outstanding' | 'Superb' | 'Excellent' | 'Good' | 'Solid' | 'Fair' | 'Limited' | 'null', nullable: Rating label for `score`, from SnowSure's score bands. null when the resort is unscored, or when the rating is withheld because the resort is not operating today.
      - `ratingColor` '#0ea5e9' | '#22c55e' | '#10b981' | '#14b8a6' | '#0d9488' | '#f59e0b' | '#94a3b8' | 'null', nullable: Hex colour of `rating`'s band, from the same SnowSure score bands as the label. Every band has its own colour: Outstanding #0ea5e9 · Superb #22c55e · Excellent #10b981 · Good #14b8a6 · Solid #0d9488 · Fair #f59e0b · Limited #94a3b8 (each is at least 4.5:1 against a slate-900 #0f172a background). Render this colour rather than mapping labels to colours yourself, so a change to the bands reaches every partner at once. null exactly when `rating` is null.
      - `tagline` string, nullable: SnowSure's published condition summary. On /api/v1/resorts it is the same value as snowSure.tagline on /api/v1/resorts/{slug}, and null when the detail publishes no snowSure block (closed, pre-season or post-season).
      - `trend` 'improving' | 'stable' | 'declining' | 'null', nullable: SnowSure's published trend. On /api/v1/resorts it is the same value as snowSure.trend on /api/v1/resorts/{slug}; null when that detail block is null.
    - `links` object: Official resort links. Every field except `snowsure` is nullable: a value is only returned when it validates as a real URL, so absence means "not known" rather than "not applicable". Coverage of 445 resorts as of 2026-07-28 — website 429, instagram 364, trailMap 429, webcamPage 413, trailMapPdf 10.
      - `website` string, uri, nullable: Resort official website
      - `instagram` string, uri, nullable: Canonical profile URL, always in the form https://instagram.com/<handle> regardless of how it is stored
      - `trailMap` string, uri, nullable: Trail map image or page URL
      - `trailMapPdf` string, uri, nullable: Trail map PDF, when one is published separately from trailMap
      - `trailMaps` object[], nullable: Additional named trail maps, when the resort publishes more than one
        - `title` string
        - `url` string, uri
      - `webcamPage` string, uri, nullable: Resort webcam landing page
      - `snowsure` string, uri: SnowSure resort page URL
    - `apresSki` object: Après-ski editorial. Generated prose, not a measured fact — deliberately separate from `links` and from `stats`.
      - `top` string, nullable: Leading après-ski venue and a short description of it
    - `heroImage` string, uri: Resort hero image URL
    - `isOpen` boolean: True if the resort is currently open for skiing today. Year-round glacier resorts (Matterhorn Ski Paradise, Saas-Fee, Hintertux, Cervinia) always return true regardless of seasonClosingDate.
    - `status` string, nullable: Editorial status from CMS: typically 'Live', 'Active', 'Data Collection', or 'Archived'. Anything other than the first three is treated as closed.
    - `seasonClosingDate` string, date, nullable: Scheduled or operator-confirmed end-of-season date (YYYY-MM-DD). Resorts past this date are treated as closed unless flagged as year-round.
    - `closure` object, nullable: Closure metadata, null when the resort is open. /api/v1/resorts serves the same object as /api/v1/resorts/{slug}: isClosed true for a closed season, false (with a reason and label) for a resort that is not open but not season-ended.
      - `isClosed` boolean
      - `reason` 'editorial' | 'season-end' | 'pre-season' | 'out-of-season' | 'not-operating' | 'unknown' | 'null', nullable: Why the resort is not open. 'season-end' = past seasonClosingDate; 'pre-season' = before its opening; 'editorial' = status not operational; 'out-of-season' = hemisphere off-season; 'not-operating' = in its window but not operating; 'unknown' = no season dates and no operating signal.
      - `label` string, nullable: Human-readable close label, e.g. 'Closed for the season since May 3'.
    - `operations` object, nullable: Live lift and run counts. Counts are null when the resort is closed for the season.
      - `liftsOpen` integer, nullable
      - `liftsTotal` integer, nullable
      - `runsOpen` integer, nullable
      - `runsTotal` integer, nullable
      - `liftPercentOpen` integer, nullable: Percentage of lifts open (0-100), rounded, the same value as operations.liftPercentOpen on /api/v1/resorts/{slug}. null when the resort is not in season, is on a closed hold, or reports no lift counts. Render it; do not derive it from liftsOpen / liftsTotal.
    - `dailyForecast` object, nullable: Only present with include=dailyForecast. null when SnowSure has no forecast snapshot for the resort; never an estimated series.
      - `daily` object[]
        - `date` string, date: Resort-local calendar date.
        - `snowfall` number, nullable: Blended snowfall for the day (cm): the mean over the models covering it, else the stored day's value. Equal to forecast.daily[].snowfall on /api/v1/resorts/{slug}.
      - `next48hCm` number, nullable: Snowfall forecast for resort-local today plus tomorrow (cm, 1 dp): the sum of the first two `daily` rows. null when neither day has a value.
  - `nextCursor` string, nullable: Opaque cursor for the next page; null when no further pages. Only present when the request used the cursor or limit query parameter.

## Other responses

- `500`: Server error

---

[API](https://skmtc.dev/snowsure/apis/snowsure-api.md) · [All operations](https://skmtc.dev/snowsure/apis/snowsure-api/llms.txt) · [OpenAPI document](https://skmtc.dev/snowsure/apis/snowsure-api/revisions/dcbcdbb3df50?raw)
