Glossary

A reference for the domain concepts and project-specific terms used throughout dwd-cli. The data comes from the Deutscher Wetterdienst (DWD) Warnwetter app backend (warnwetter.de); the domain is German, so this glossary gives the English term used in the CLI/API alongside the original German where one exists.

Translation table. The CLI follows these:

German English / API term
Warnung warning
Gemeinde municipality
Küste / Binnensee coast / inland lake
Vorhersage forecast
Meldung (crowd-sourced) report
Wetterstation weather station

The DWD Warnwetter source

DWD — Deutscher Wetterdienst. Germany’s national meteorological service. It operates the public weather-warning system and the Warnwetter app, whose backend this tool wraps.

Warnwetter app. DWD’s official weather-warning app for the public. Its backend serves both live station forecasts and the periodically-published warning feeds; both are open (no authentication) and read-only.

warnwetter.de. The host domain of the Warnwetter backend. The data is split across two hosts (see Live web service and Static S3 bucket).

Open / no-auth endpoints. The endpoints this client uses require no API key. They are all GET and read-only; dwd-cli never writes.


The two hosts

Live web service. https://app-prod-ws.warnwetter.de/v30 — the live backend that answers station-overview requests, queried with parameters. CLI override: --base-url (library: baseUrl); the path version segment is /v30, which the client adds, so the override is the host alone (https://app-prod-ws.warnwetter.de). A value ending in /v30 is rejected with a hint, by the CLI and the library alike.

Static S3 bucket. https://s3.eu-central-1.amazonaws.com/app-prod-static.warnwetter.de/v16 — an Amazon S3 bucket holding the periodically-published warning and crowd feeds as static JSON files. CLI override: --static-base-url; the path version segment is /v16, which the client adds, so the override is the bucket root (library: staticBaseUrl); a value ending in /v16 is rejected with a hint. S3 answers a missing file with 403, not 404.

gzip-encoded feeds. The static warning files are stored on S3 with Content-Encoding: gzip and are served compressed regardless of the request’s Accept-Encoding. The client’s transport transparently decompresses gzip/deflate/brotli bodies.


Resources & endpoints

Station overview (stationOverviewExtended). Forecasts/observations for one or more DWD weather stations, returned by the live web service. The response is an object keyed by station id; each value carries forecast1, forecast2, days, warnings and threeHourSummaries. Client: client.weather.stationOverview(ids). CLI: station-overview --id <stationId>.

Nowcast warnings (warnings_nowcast.json). Short-term (“nowcast”) weather warnings — imminent severe weather. Static-bucket feed. Client: client.warnings.nowcast(lang). CLI: warnings nowcast.

Gemeinde warnings (gemeinde_warnings_v2.json). Municipality-level weather warnings, i.e. warnings resolved to the German Gemeinde (municipality). Static feed. Client: client.warnings.gemeinde(lang). CLI: warnings gemeinde.

Coast warnings (warnings_coast.json). Coastal weather warnings, with warnings keyed by coastal zone (and inland-lake / Binnensee areas). Unlike the nowcast and Gemeinde items, coast items carry no regions geometry and no start/end. Static feed. Client: client.warnings.coast(lang). CLI: warnings coast.

Crowd overview (crowd_meldungen_overview_v2.json). An overview of crowd-sourced weather reports (Meldungen) submitted by app users. Static feed. Client: client.crowd(). CLI: crowd.


Identifiers, units & response fields

Station id. The identifier of a DWD weather station, used by the Warnwetter app — typically a 5-digit numeric id (e.g. München-Stadt = 10865). Repeatable on the CLI (--id 10865 --id 01766); a single value may also be a comma- or space-separated list (--id 10865,01766, --id "10865 01766"), and the forms are equivalent — all are sent to the web service joined by commas as stationIds=10865,01766. The client trims each id (" 10865 " is sent as 10865) and rejects a blank id, or one containing a comma, whitespace, ; or a control character (the API would answer such an id with {}, like an unknown station), before any request, for the CLI and library callers alike. An unknown id is answered with status 200 and no entry for it ({} for one id); missingStationIds(ids, overview) names such ids, and the CLI logs them as a note on stderr, an INFO record of dwd.api (exit 0 unchanged).

forecast1 / forecast2. Two forecast series carried per station in a station overview. forecast1 is hourly (timeStep 3600000) from midnight of the current day: temperature runs ten days from start, while the shorter arrays (precipitationTotal, sunshine, humidity, …) are end-aligned at start + 72 h rather than anchored at start. forecast2 continues from there in three-hour steps (timeStep 10800000); it is not an hourly copy of forecast1.

Scaled integers. The station data’s measurements come as whole numbers in tenths of their unit: temperature, temperatureMin/Max and dewPoint2m in °C, humidity in %, surfacePressure in hPa, windSpeed/windGust in km/h, windDirection in degrees, precipitation/precipitationTotal in mm and sunshine in minutes of sun in the period (97 is 9.7 °C, 10216 is 1021.6 hPa, 2700 is 270°). The CLI prints them as delivered; station-overview --decode prints them in real units, through the library’s decodeStationOverview(overview) (field list STATION_SCALED_FIELDS, factor STATION_SCALE). Decoding changes only those numbers: timestamps (epoch ms), timeStep, icon codes, isDay, the array lengths and their end-alignment stay as they are, and so do fields whose scale is not confirmed (temperatureStd, precipitationProbablity, cloudCoverTotal).

Missing-value marker (32767). The station data’s “no value”: the largest 16-bit integer, which the web service puts into a scaled-integer array where it has no value — today’s past hours at some stations (temperature, precipitationTotal, icon), and every surfacePressure value, past and future, at mountain stations (Zugspitze, Feldberg, Fichtelberg, …). Read with the ÷ 10 rule it would be 3276.7 °C, mm or hPa. The client turns it into null (STATION_MISSING_VALUE, replaceMissingValues) in forecast1, forecast2, days and threeHourSummaries, so null inside an array means “no value for this hour”, like a whole array that is null.

days. The multi-day forecast summary block of a station overview: per local date (dayDate) the min/max temperature, precipitation, wind, gust, sunrise/sunset and an icon, which matched DWD’s MOSMIX forecast when checked.

days[].sunshine. Not reliable. It is either exactly the day’s sum of the hourly (forecast1) and 3-hourly (forecast2) sunshine values, or 0 — and it was 0 on about 44 % of the future days checked (49 stations on 2026-10-05 and 06), in runs of unsettled weather, on days with up to 6–7 h of sun in the hourly data and in MOSMIX. Neither MOSMIX’s daily elements (SunD, RSunD) nor any threshold explains the zeros; the app backend’s rule is not documented. Sum the series per local day instead (the dwd-station-forecast skill has the recipe); for today the series only cover the hours from about now.

threeHourSummaries. Three-hour aggregated forecast summaries within a station overview.

warnings (station). The warnings block embedded in a station overview, i.e. warnings relevant to that station’s location.

time. The Unix-epoch timestamp (a number, milliseconds) stamped on every warning feed envelope, marking when that feed was generated. A feed without one, or with one no date can hold (beyond ±8.64e15 ms), is a malformed answer (exit 7).

staleFeed. Added by the CLI (not DWD) to every warning feed it prints: true when the feed’s time is more than 60 minutes old (STALE_FEED_MS; checked with staleFeedProblem(time)), else false. DWD republishes the feeds every few minutes (on 2026-10-06 the nowcast feed was 4 minutes old, Gemeinde and coast 10), so a stale feed misses the warnings issued since. A stale feed also gets a note on stderr (an INFO record of dwd.api).

binnenSee. Inland lake. An optional block on the nowcast/gemeinde warning envelopes carrying inland-lake (large-lake) warnings. With none active it has come back as null (nowcast) and {} (gemeinde).

meldungen. The array of crowd-sourced reports in the crowd overview. May be accompanied by start, end and highestSeverities. start/end bound the window the reports cover (12 hours when checked); the feed’s windowsSizeHours field did not match that window, so each report’s timestamp is the reliable time.

Coastal zone. The key by which coastal warnings are grouped in the coast feed (each zone maps to its own warnings object).


Enums & codes the client surfaces

Lang (de | en). The language of a warning feed. German (de, the default) feeds have no filename suffix; English (en) feeds use the _en filename suffix (e.g. warnings_nowcast_en.json). Exposed as LangValues (runtime array) and the Lang union type, and validated as the CLI --lang choice on every warnings subcommand.


Feed envelopes (typed response shapes)

StationOverview. { [stationId: string]: JsonObject } — the station-overview response keyed by station id. The DWD-specific per-station payload is exposed as a faithful raw JsonObject rather than a guessed type — except that the missing-value marker 32767 comes back as null.

WarningsFeed. The common envelope of the nowcast and gemeinde feeds: { time: number; warnings: JsonObject[]; binnenSee?: JsonValue }.

CoastWarningsFeed. The coast feed envelope: { time: number; warnings: JsonObject; vorabInformation?: JsonObject } — warnings is keyed by coastal zone (an object, not an array); vorabInformation (advance information) is keyed the same way.

CrowdOverview. The crowd feed envelope: { start?, end?, windowsSizeHours?, highestSeverities?, meldungen: JsonObject[] }.

JsonObject / JsonValue. The general JSON value types used where a payload is large and DWD-specific enough that a hand-written interface would be a guess.

Shape check. The client checks only the top level of each response: the station overview must be a JSON object, the nowcast/gemeinde feeds need a warnings array, the coast feed a warnings object and the crowd feed a meldungen array. Anything else (null, [], an error document from S3 or a proxy) raises a DwdParseError (exit 7) instead of being printed as a feed.


API & client behaviour

Rate limiting / transient errors. The backend may answer with 429 (too many requests) or 503 (service unavailable). The client retries these automatically, backing off linearly, or longer if the response’s Retry-After asks (up to 30 s; a longer one is not retried, and the error names the requested wait), but never shorter: Retry-After: 0 still waits the backoff — the number of retries is tunable with --max-retries (0–10, default 2); the base inter-attempt delay grows linearly and is an internal default, not a CLI flag. A reset connection is retried the same way; a timeout is not.

Redirects. The engine follows up to maxRedirects (default 5) HTTP redirects (301/302/303/307/308). Any other 3xx (such as 304) is not followed: it surfaces as an API error that names the target (exit 5). On a cross-origin redirect, sensitive headers (Authorization/X-API-Key/Cookie) are stripped so credentials issued for one host are never forwarded to another; a same-origin redirect (relative or absolute Location) keeps them. A base URL’s user:pw@ is sent as that Authorization header, never inside the URL, and a Location’s own userinfo is ignored.

Decompression bomb cap. maxResponseBytes (default 100 MiB; 0 = unlimited) bounds both the wire bytes and the decompressed output, so a small compressed feed cannot expand into an out-of-memory condition. Exceeding it raises a DwdNetworkError.

Content-Type guard. A 200 response whose Content-Type is clearly not JSON (e.g. a captive-portal HTML page) is reported as a DwdParseError naming the type actually returned, rather than being fed to JSON.parse.

Log record. Every diagnostic line the CLI writes to stderr: a timestamp, a level (ERROR, WARN, INFO) and a topic dwd.<area>, as text (log4j style) or with --log-format jsonl as one JSON object per line. The areas: cli (usage errors, commander’s messages, unexpected errors), api (the API’s answers: an error status, the unknown-station and stale-feed notes, and a malformed answer — bad JSON, the wrong shape or content type), http (the connection, the cleartext warning, and one WARN per retry before it waits) and output (a failed write to stdout). A record is always one line; control characters in it are escaped.


Library & internals. Terms for the TypeScript client and its internals — DwdClient, the request engine, transport, retry/backoff, error types, query builder, feed envelope types — now live in DEVELOPING.md.

View the source on GitHub →