v7 is a full rewrite. The package name on npm is still themeparks, but the
import surface has changed. This guide walks through the common patterns.
If you are blocked on a migration detail not covered here, please open an issue: https://github.com/ThemeParks/ThemeParks_JavaScript/issues
- Replace the default/namespace import with a named
ThemeParksimport. - One client object;
tp.destinations,tp.entity(...), andtp.raw.*replace the per-resource classes. - All response types are real TypeScript types — no more
any. - Ad-hoc
{ body, response, status }error shapes are replaced with typedApiError/RateLimitError/NetworkError/TimeoutError.
const Themeparks = require('themeparks');
// or: import Themeparks from 'themeparks';
const destinationsApi = new Themeparks.DestinationsApi();
const entitiesApi = new Themeparks.EntitiesApi();import { ThemeParks } from 'themeparks';
const tp = new ThemeParks();
// tp.destinations, tp.entity(...), tp.raw.*One client, fully typed.
const response = await destinationsApi.getDestinations();
for (const d of response.destinations) {
console.log(d.id, d.name);
}// Ergonomic
const resp = await tp.destinations.list();
for (const d of resp.destinations ?? []) {
console.log(d.id, d.name);
}
// Or raw (same return type)
const resp2 = await tp.raw.getDestinations();const entity = await entitiesApi.getEntity(entityId);
console.log(entity.name, entity.entityType);const entity = await tp.entity(entityId).get(); // ergonomic
const entityRaw = await tp.raw.getEntity(entityId); // raw
console.log(entity.name, entity.entityType);price.amount is number | null. null means the queue costs money but the
provider does not publish a price; 0 means it is genuinely free. Before this,
both cases arrived as 0, so an unknown price was indistinguishable from a
free one — Tokyo Disney Resort's Premier Access rows are the current example.
price.formatted is optional and may be absent when the amount is unknown, so
do not rely on it alone to detect the case.
const paid = live.liveData[0].queue?.PAID_RETURN_TIME;
if (paid) {
const { amount, currency } = paid.price;
console.log(amount === null ? `${currency}: price not published` : `${currency} ${amount / 100}`);
}Queue fields are now correctly typed end-to-end. Null waitTime is
number | null rather than an untyped surprise.
import { ThemeParks, currentWaitTime } from 'themeparks';
const tp = new ThemeParks();
const live = await tp.entity(parkId).live();
for (const item of live.liveData ?? []) {
const wait = currentWaitTime(item);
if (wait === null) {
console.log(`${item.name}: closed / no data`);
} else {
console.log(`${item.name}: ${wait} min`);
}
}try {
await entitiesApi.getEntity(entityId);
} catch (err) {
// ad-hoc shape — { body, response, status } or a raw superagent error
console.log(err.status, err.body);
}import { ApiError, RateLimitError, NetworkError, TimeoutError } from 'themeparks';
try {
await tp.entity(entityId).get();
} catch (err) {
if (err instanceof RateLimitError) {
// 429: err.retryAfterMs is set if the server sent a Retry-After header
} else if (err instanceof ApiError) {
console.log(err.status, err.url, err.body);
} else if (err instanceof NetworkError || err instanceof TimeoutError) {
// transport failure
} else {
throw err;
}
}All four inherit from ThemeParksError if you want a single catch-all.
tp.entity(id).walk()— async iterator over every descendant in a single API call (the/childrenendpoint already returns the full subtree).tp.entity(id).schedule.range(start, end)— stitches monthly schedule responses into a sorted, filtered list across a date range.tp.destinations.find(query)— case-insensitive lookup by slug or name.currentWaitTime(entry)— null-safe standby-wait accessor.narrowQueues(queue)— typed discriminated-union iterator over populated queue variants.- Default-on response caching with per-endpoint TTLs (see README).
- Automatic 429
Retry-Afterhandling. - First-class TypeScript types generated from the upstream OpenAPI spec.