import { F as FuzzyDate, P as PageInfo, E as ExternalLink, C as CacheAdapter, a as CacheOptions, b as PagedResult, A as AniListClientOptions, R as RateLimitInfo, c as ResponseMeta, d as RateLimitOptions } from './redis-ClB2nNrs.mjs'; export { e as AniListHooks, L as Logger, f as RedisCache, g as RedisCacheOptions, h as RedisLikeClient } from './redis-ClB2nNrs.mjs'; declare enum MediaListStatus { CURRENT = "CURRENT", PLANNING = "PLANNING", COMPLETED = "COMPLETED", DROPPED = "DROPPED", PAUSED = "PAUSED", REPEATING = "REPEATING" } declare enum MediaListSort { MEDIA_ID = "MEDIA_ID", MEDIA_ID_DESC = "MEDIA_ID_DESC", SCORE = "SCORE", SCORE_DESC = "SCORE_DESC", STATUS = "STATUS", STATUS_DESC = "STATUS_DESC", PROGRESS = "PROGRESS", PROGRESS_DESC = "PROGRESS_DESC", PROGRESS_VOLUMES = "PROGRESS_VOLUMES", PROGRESS_VOLUMES_DESC = "PROGRESS_VOLUMES_DESC", REPEAT = "REPEAT", REPEAT_DESC = "REPEAT_DESC", PRIORITY = "PRIORITY", PRIORITY_DESC = "PRIORITY_DESC", STARTED_ON = "STARTED_ON", STARTED_ON_DESC = "STARTED_ON_DESC", FINISHED_ON = "FINISHED_ON", FINISHED_ON_DESC = "FINISHED_ON_DESC", ADDED_TIME = "ADDED_TIME", ADDED_TIME_DESC = "ADDED_TIME_DESC", UPDATED_TIME = "UPDATED_TIME", UPDATED_TIME_DESC = "UPDATED_TIME_DESC", MEDIA_TITLE_ROMAJI = "MEDIA_TITLE_ROMAJI", MEDIA_TITLE_ROMAJI_DESC = "MEDIA_TITLE_ROMAJI_DESC", MEDIA_TITLE_ENGLISH = "MEDIA_TITLE_ENGLISH", MEDIA_TITLE_ENGLISH_DESC = "MEDIA_TITLE_ENGLISH_DESC", MEDIA_TITLE_NATIVE = "MEDIA_TITLE_NATIVE", MEDIA_TITLE_NATIVE_DESC = "MEDIA_TITLE_NATIVE_DESC", MEDIA_POPULARITY = "MEDIA_POPULARITY", MEDIA_POPULARITY_DESC = "MEDIA_POPULARITY_DESC" } interface MediaListEntry { id: number; mediaId: number; status: MediaListStatus; score: number | null; progress: number | null; progressVolumes: number | null; repeat: number | null; priority: number | null; private: boolean | null; notes: string | null; startedAt: FuzzyDate | null; completedAt: FuzzyDate | null; updatedAt: number | null; createdAt: number | null; media: Media; } interface GetUserMediaListOptions { /** User ID (provide either userId or userName) */ userId?: number; /** Username (provide either userId or userName) */ userName?: string; /** ANIME or MANGA */ type: MediaType; /** Filter by list status (CURRENT, COMPLETED, etc.) */ status?: MediaListStatus; /** Sort order */ sort?: MediaListSort[]; page?: number; perPage?: number; } declare enum StaffSort { ID = "ID", ID_DESC = "ID_DESC", ROLE = "ROLE", ROLE_DESC = "ROLE_DESC", LANGUAGE = "LANGUAGE", LANGUAGE_DESC = "LANGUAGE_DESC", SEARCH_MATCH = "SEARCH_MATCH", FAVOURITES = "FAVOURITES", FAVOURITES_DESC = "FAVOURITES_DESC", RELEVANCE = "RELEVANCE" } interface StaffName { first: string | null; middle: string | null; last: string | null; full: string | null; native: string | null; } interface StaffImage { large: string | null; medium: string | null; } /** A media node returned inside `Staff.staffMedia`. */ interface StaffMediaNode { id: number; title: MediaTitle; type: MediaType; format: MediaFormat | null; status: MediaStatus | null; coverImage: MediaCoverImage; bannerImage: string | null; genres: string[]; averageScore: number | null; meanScore: number | null; popularity: number | null; favourites: number | null; episodes: number | null; trending: number | null; hashtag: string | null; season: MediaSeason | null; seasonYear: number | null; startDate: FuzzyDate | null; endDate: FuzzyDate | null; nextAiringEpisode: { id: number; airingAt: number; episode: number; mediaId: number; timeUntilAiring: number; } | null; studios: { edges: { node: { name: string; }; }[]; } | null; siteUrl: string | null; } interface Staff { id: number; name: StaffName; language: string | null; image: StaffImage; description: string | null; primaryOccupations: string[]; gender: string | null; dateOfBirth: FuzzyDate | null; dateOfDeath: FuzzyDate | null; age: string | null; yearsActive: number[]; homeTown: string | null; bloodType: string | null; favourites: number | null; siteUrl: string | null; /** Media the staff member has worked on — only present when requested via include options. */ staffMedia?: { nodes: StaffMediaNode[]; } | null; } /** Options to include additional related data when fetching a staff member by ID. */ interface StaffIncludeOptions { /** Include character roles (voice acting) for each media the staff member worked on. */ characterRoles?: boolean; /** Raw GraphQL fields to append to the query (e.g. for custom data) */ customFields?: string; /** Include media the staff member has worked on. * `true` = 25 results sorted by popularity. Object form to customize. */ media?: boolean | { perPage?: number; sort?: boolean; }; } interface SearchStaffOptions { query?: string; sort?: StaffSort[]; page?: number; perPage?: number; } /** Compact voice actor data returned inside character edges. */ interface VoiceActor extends Pick { name: StaffName & { userPreferred: string | null; }; languageV2: string | null; } interface Studio { id: number; name: string; isAnimationStudio: boolean; siteUrl: string | null; favourites?: number | null; media?: { pageInfo: PageInfo; nodes: Pick[]; } | null; } interface StudioConnection { nodes: Studio[]; } declare enum StudioSort { ID = "ID", ID_DESC = "ID_DESC", NAME = "NAME", NAME_DESC = "NAME_DESC", SEARCH_MATCH = "SEARCH_MATCH", FAVOURITES = "FAVOURITES", FAVOURITES_DESC = "FAVOURITES_DESC" } interface SearchStudioOptions { query?: string; sort?: StudioSort[]; page?: number; perPage?: number; } /** * Options for controlling embedded media when fetching a single studio. * Pass `{ media: { perPage: 50 } }` to fetch more media per studio. */ interface StudioIncludeOptions { /** Include the media produced by this studio. */ media?: boolean | { perPage?: number; isMain?: boolean; sort?: boolean; }; /** Raw GraphQL fields to append to the query (e.g. for custom data) */ customFields?: string; } declare enum UserSort { ID = "ID", ID_DESC = "ID_DESC", USERNAME = "USERNAME", USERNAME_DESC = "USERNAME_DESC", WATCHED_TIME = "WATCHED_TIME", WATCHED_TIME_DESC = "WATCHED_TIME_DESC", CHAPTERS_READ = "CHAPTERS_READ", CHAPTERS_READ_DESC = "CHAPTERS_READ_DESC", SEARCH_MATCH = "SEARCH_MATCH" } interface UserAvatar { large: string | null; medium: string | null; } interface UserStatistics { count: number; meanScore: number; minutesWatched: number; episodesWatched: number; chaptersRead: number; volumesRead: number; } interface User { id: number; name: string; about: string | null; avatar: UserAvatar; bannerImage: string | null; isFollowing: boolean | null; isFollower: boolean | null; donatorTier: number | null; donatorBadge: string | null; createdAt: number | null; siteUrl: string | null; statistics: { anime: UserStatistics; manga: UserStatistics; } | null; } interface SearchUserOptions { query?: string; sort?: UserSort[]; page?: number; perPage?: number; } interface FavoriteMediaNode { id: number; title: MediaTitle; coverImage: Pick; type: MediaType | null; format: MediaFormat | null; siteUrl: string | null; } interface FavoriteCharacterNode { id: number; name: { full: string | null; native: string | null; }; image: { large: string | null; medium: string | null; }; siteUrl: string | null; } interface FavoriteStaffNode { id: number; name: { full: string | null; native: string | null; }; image: { large: string | null; medium: string | null; }; siteUrl: string | null; } interface FavoriteStudioNode { id: number; name: string; siteUrl: string | null; } interface UserFavorites { anime: FavoriteMediaNode[]; manga: FavoriteMediaNode[]; characters: FavoriteCharacterNode[]; staff: FavoriteStaffNode[]; studios: FavoriteStudioNode[]; } /** * Options for controlling the number of results when fetching user favorites. */ interface UserFavoritesOptions { /** Number of items per category (default: 25, max: 50). */ perPage?: number; } declare enum MediaType { ANIME = "ANIME", MANGA = "MANGA" } declare enum MediaSource { ORIGINAL = "ORIGINAL", MANGA = "MANGA", LIGHT_NOVEL = "LIGHT_NOVEL", VISUAL_NOVEL = "VISUAL_NOVEL", VIDEO_GAME = "VIDEO_GAME", OTHER = "OTHER", NOVEL = "NOVEL", DOUJINSHI = "DOUJINSHI", ANIME = "ANIME", WEB_NOVEL = "WEB_NOVEL", LIVE_ACTION = "LIVE_ACTION", GAME = "GAME", COMIC = "COMIC", MULTIMEDIA_PROJECT = "MULTIMEDIA_PROJECT", PICTURE_BOOK = "PICTURE_BOOK" } declare enum MediaFormat { TV = "TV", TV_SHORT = "TV_SHORT", MOVIE = "MOVIE", SPECIAL = "SPECIAL", OVA = "OVA", ONA = "ONA", MUSIC = "MUSIC", MANGA = "MANGA", NOVEL = "NOVEL", ONE_SHOT = "ONE_SHOT" } declare enum MediaStatus { FINISHED = "FINISHED", RELEASING = "RELEASING", NOT_YET_RELEASED = "NOT_YET_RELEASED", CANCELLED = "CANCELLED", HIATUS = "HIATUS" } declare enum MediaSeason { WINTER = "WINTER", SPRING = "SPRING", SUMMER = "SUMMER", FALL = "FALL" } declare enum MediaSort { ID = "ID", ID_DESC = "ID_DESC", TITLE_ROMAJI = "TITLE_ROMAJI", TITLE_ROMAJI_DESC = "TITLE_ROMAJI_DESC", TITLE_ENGLISH = "TITLE_ENGLISH", TITLE_ENGLISH_DESC = "TITLE_ENGLISH_DESC", TITLE_NATIVE = "TITLE_NATIVE", TITLE_NATIVE_DESC = "TITLE_NATIVE_DESC", TYPE = "TYPE", TYPE_DESC = "TYPE_DESC", FORMAT = "FORMAT", FORMAT_DESC = "FORMAT_DESC", START_DATE = "START_DATE", START_DATE_DESC = "START_DATE_DESC", END_DATE = "END_DATE", END_DATE_DESC = "END_DATE_DESC", SCORE = "SCORE", SCORE_DESC = "SCORE_DESC", POPULARITY = "POPULARITY", POPULARITY_DESC = "POPULARITY_DESC", TRENDING = "TRENDING", TRENDING_DESC = "TRENDING_DESC", EPISODES = "EPISODES", EPISODES_DESC = "EPISODES_DESC", DURATION = "DURATION", DURATION_DESC = "DURATION_DESC", STATUS = "STATUS", STATUS_DESC = "STATUS_DESC", FAVOURITES = "FAVOURITES", FAVOURITES_DESC = "FAVOURITES_DESC", UPDATED_AT = "UPDATED_AT", UPDATED_AT_DESC = "UPDATED_AT_DESC", SEARCH_MATCH = "SEARCH_MATCH" } declare enum AiringSort { ID = "ID", ID_DESC = "ID_DESC", MEDIA_ID = "MEDIA_ID", MEDIA_ID_DESC = "MEDIA_ID_DESC", TIME = "TIME", TIME_DESC = "TIME_DESC", EPISODE = "EPISODE", EPISODE_DESC = "EPISODE_DESC" } interface MediaTitle { romaji: string | null; english: string | null; native: string | null; userPreferred: string | null; } interface MediaCoverImage { extraLarge: string | null; large: string | null; medium: string | null; color: string | null; } interface MediaTrailer { id: string | null; site: string | null; thumbnail: string | null; } interface MediaTag { id: number; name: string; description: string | null; category: string | null; rank: number | null; isAdult: boolean | null; isMediaSpoiler: boolean | null; } declare enum MediaRelationType { ADAPTATION = "ADAPTATION", PREQUEL = "PREQUEL", SEQUEL = "SEQUEL", PARENT = "PARENT", SIDE_STORY = "SIDE_STORY", CHARACTER = "CHARACTER", SUMMARY = "SUMMARY", ALTERNATIVE = "ALTERNATIVE", SPIN_OFF = "SPIN_OFF", OTHER = "OTHER", SOURCE = "SOURCE", COMPILATION = "COMPILATION", CONTAINS = "CONTAINS" } interface MediaEdge { relationType: MediaRelationType; node: Pick; } interface MediaConnection { edges: MediaEdge[]; } interface MediaCharacterEdge { role: CharacterRole; node: Omit; voiceActors?: VoiceActor[]; } interface MediaCharacterConnection { edges: MediaCharacterEdge[]; } interface MediaStaffEdge { role: string; node: Staff; } interface MediaStaffConnection { edges: MediaStaffEdge[]; } interface StreamingEpisode { title: string | null; thumbnail: string | null; url: string | null; site: string | null; } interface ScoreDistribution { score: number; amount: number; } interface StatusDistribution { status: MediaListStatus; amount: number; } interface MediaStats { scoreDistribution: ScoreDistribution[]; statusDistribution: StatusDistribution[]; } interface MediaRecommendationNode { id: number; rating: number | null; mediaRecommendation: Pick; } interface NextAiringEpisode { id: number; airingAt: number; episode: number; mediaId: number; timeUntilAiring: number; } interface Media { id: number; idMal: number | null; title: MediaTitle; type: MediaType; format: MediaFormat | null; status: MediaStatus | null; description: string | null; startDate: FuzzyDate | null; endDate: FuzzyDate | null; season: MediaSeason | null; seasonYear: number | null; episodes: number | null; duration: number | null; chapters: number | null; volumes: number | null; countryOfOrigin: string | null; isLicensed: boolean | null; source: MediaSource | null; hashtag: string | null; trailer: MediaTrailer | null; coverImage: MediaCoverImage; bannerImage: string | null; genres: string[]; synonyms: string[]; averageScore: number | null; meanScore: number | null; popularity: number | null; favourites: number | null; trending: number | null; tags: MediaTag[]; studios: StudioConnection; relations: MediaConnection | null; characters?: MediaCharacterConnection; staff?: MediaStaffConnection; streamingEpisodes?: StreamingEpisode[]; externalLinks?: ExternalLink[]; stats?: MediaStats; recommendations?: { nodes: MediaRecommendationNode[]; }; nextAiringEpisode: NextAiringEpisode | null; isAdult: boolean | null; siteUrl: string | null; } interface SearchMediaOptions { /** Search Term */ query?: string; /** Filter by country code (e.g., "JP", "KR") */ countryOfOrigin?: string; /** Filter by Anime or Manga */ type?: MediaType; /** Filter by format (For multiple formats: [MediaFormat.TV]) */ format?: MediaFormat | MediaFormat[]; /** Filter by status of Media */ status?: MediaStatus; /** Filter by Season (Winter, Spring, Summer, Fall) */ season?: MediaSeason; /** Filter by Year */ seasonYear?: number; /** Single genre filter (kept for backward compat) */ genre?: string; /** Single tag filter (kept for backward compat) */ tag?: string; /** Filter by multiple genres (media must match ALL) */ genres?: string[]; /** Filter by multiple tags (media must match ALL) */ tags?: string[]; /** Exclude media with any of these genres */ genresExclude?: string[]; /** Exclude media with any of these tags */ tagsExclude?: string[]; /** Include or Exclude explicit content (default: false) */ isAdult?: boolean; /** Exclude certain media entries by ID */ idNotIn?: number[]; /** Sort order */ sort?: MediaSort[]; /** Page number */ page?: number; /** Results per page (max 50) */ perPage?: number; } interface GeneralMediaQueryOptions { /** Filter by Anime or Manga */ type?: MediaType; /** Include or Exclude explicit content (default: false) */ isAdult?: boolean; /** Exclude certain media entries by ID */ idNotIn?: number[]; /** Page number */ page?: number; /** Results per page (max 50) */ perPage?: number; } interface GetAiringOptions { /** Only show episodes that aired after this UNIX timestamp */ airingAtGreater?: number; /** Only show episodes that aired before this UNIX timestamp */ airingAtLesser?: number; /** Exclude certain media entries by ID */ idNotIn?: number[]; /** Sort order (default: TIME_DESC) */ sort?: AiringSort[]; /** Page number */ page?: number; /** Results per page (max 50) */ perPage?: number; } interface GetRecentChaptersOptions { /** Include or Exclude explicit content (default: false) */ isAdult?: boolean; /** Exclude certain media entries by ID */ idNotIn?: number[]; /** Page number (default: 1) */ page?: number; /** Results per page (default: 20, max 50) */ perPage?: number; } interface GetPlanningOptions { /** Filter by ANIME or MANGA (returns both if omitted) */ type?: MediaType; /** Include or Exclude explicit content (default: false) */ isAdult?: boolean; /** Exclude certain media entries by ID */ idNotIn?: number[]; /** Sort order (default: POPULARITY_DESC) */ sort?: MediaSort[]; /** Page number */ page?: number; /** Results per page (max 50) */ perPage?: number; } declare enum RecommendationSort { ID = "ID", ID_DESC = "ID_DESC", RATING = "RATING", RATING_DESC = "RATING_DESC" } interface Recommendation { id: number; rating: number | null; userRating: string | null; mediaRecommendation: Media; user: { id: number; name: string; avatar: UserAvatar; } | null; } interface GetRecommendationsOptions { /** The AniList media ID to get recommendations for */ mediaId: number; /** Sort order (default: RATING_DESC) */ sort?: RecommendationSort[]; /** Page number */ page?: number; /** Results per page (max 50) */ perPage?: number; } interface GetSeasonOptions { /** The season (WINTER, SPRING, SUMMER, FALL) */ season: MediaSeason; /** The year */ seasonYear: number; /** Filter by ANIME or MANGA (defaults to ANIME) */ type?: MediaType; /** Allow or disallow explicit content (defaults to False) */ isAdult?: boolean; /** Exclude certain media entries by ID */ idNotIn?: number[]; /** Sort order (default: POPULARITY_DESC) */ sort?: MediaSort[]; /** Page number */ page?: number; /** Results per page (max 50) */ perPage?: number; } /** * Options to include additional related data when fetching a media entry. * Pass `true` to include with defaults, or an object to customize. */ interface MediaIncludeOptions { /** Include characters with their roles (MAIN, SUPPORTING, BACKGROUND). * `true` = 25 results sorted by role. Object form to customize. */ characters?: boolean | { perPage?: number; sort?: boolean; voiceActors?: boolean; }; /** Include staff members with their roles. * `true` = 25 results sorted by relevance. Object form to customize. */ staff?: boolean | { perPage?: number; sort?: boolean; }; /** Include relations (default: `true` for backward compat). Set to `false` to exclude. */ relations?: boolean; /** Include streaming episode links (Crunchyroll, Funimation, etc.) */ streamingEpisodes?: boolean; /** Include external links (MAL, official site, etc.) */ externalLinks?: boolean; /** Include score & status distribution stats */ stats?: boolean; /** Include user recommendations. `true` = 10 results, or customize with `{ perPage }`. */ recommendations?: boolean | { perPage?: number; }; /** Raw GraphQL fields to append to the query (e.g. for custom data) */ customFields?: string; } interface GetMediaCharactersOptions { /** Page number */ page?: number; /** Results per page (max 50) */ perPage?: number; /** Disable default sort order */ sort?: boolean; /** Include voice actors for each character edge */ voiceActors?: boolean; } interface GetMediaStaffOptions { /** Page number */ page?: number; /** Results per page (max 50) */ perPage?: number; /** Disable default sort order */ sort?: boolean; } interface AiringSchedule { id: number; airingAt: number; timeUntilAiring: number; episode: number; mediaId: number; media: Media; } type DayOfWeek = "Monday" | "Tuesday" | "Wednesday" | "Thursday" | "Friday" | "Saturday" | "Sunday"; type WeeklySchedule = Record; declare enum CharacterSort { ID = "ID", ID_DESC = "ID_DESC", ROLE = "ROLE", ROLE_DESC = "ROLE_DESC", SEARCH_MATCH = "SEARCH_MATCH", FAVOURITES = "FAVOURITES", FAVOURITES_DESC = "FAVOURITES_DESC" } declare enum CharacterRole { MAIN = "MAIN", SUPPORTING = "SUPPORTING", BACKGROUND = "BACKGROUND" } interface CharacterName { first: string | null; middle: string | null; last: string | null; full: string | null; native: string | null; alternative: string[]; } interface CharacterImage { large: string | null; medium: string | null; } type CharacterMediaNode = Pick; interface CharacterMediaEdge { node: CharacterMediaNode; voiceActors?: VoiceActor[]; } interface Character { id: number; name: CharacterName; image: CharacterImage; description: string | null; gender: string | null; dateOfBirth: FuzzyDate | null; age: string | null; bloodType: string | null; favourites: number | null; siteUrl: string | null; media: { nodes?: CharacterMediaNode[]; edges?: CharacterMediaEdge[]; } | null; } /** Options for including extra data when fetching a character. */ interface CharacterIncludeOptions { /** Include voice actors for each media the character appears in. */ voiceActors?: boolean; /** Raw GraphQL fields to append to the query (e.g. for custom data) */ customFields?: string; } interface SearchCharacterOptions { query?: string; sort?: CharacterSort[]; page?: number; perPage?: number; /** Include voice actors for each media the character appears in. */ voiceActors?: boolean; } declare enum ReviewSort { ID = "ID", ID_DESC = "ID_DESC", SCORE = "SCORE", SCORE_DESC = "SCORE_DESC", RATING = "RATING", RATING_DESC = "RATING_DESC", CREATED_AT = "CREATED_AT", CREATED_AT_DESC = "CREATED_AT_DESC", UPDATED_AT = "UPDATED_AT", UPDATED_AT_DESC = "UPDATED_AT_DESC" } interface Review { id: number; userId: number; mediaId: number; mediaType: "ANIME" | "MANGA"; summary: string; body: string; rating: number; ratingAmount: number; userRating: "UP_VOTE" | "DOWN_VOTE" | "NO_VOTE"; score: number; private: boolean; siteUrl: string; createdAt: number; updatedAt: number; user: User; media: Media; } interface SearchReviewOptions { mediaId?: number; userId?: number; sort?: ReviewSort[]; page?: number; perPage?: number; } /** Represents a forum thread on AniList. */ interface Thread { id: number; title: string; body: string | null; userId: number; replyUserId: number | null; replyCommentId: number | null; replyCount: number; viewCount: number; isLocked: boolean; isSticky: boolean; isSubscribed: boolean; repliedAt: number | null; createdAt: number; updatedAt: number; siteUrl: string | null; user: { id: number; name: string; avatar: UserAvatar; } | null; replyUser: { id: number; name: string; avatar: UserAvatar; } | null; categories: ThreadCategory[] | null; mediaCategories: ThreadMediaCategory[] | null; likes: { id: number; name: string; }[] | null; } interface ThreadCategory { id: number; name: string; } interface ThreadMediaCategory { id: number; title: MediaTitle; type: MediaType; coverImage: Pick | null; siteUrl: string | null; } /** Sort options for thread queries. */ declare enum ThreadSort { ID = "ID", ID_DESC = "ID_DESC", TITLE = "TITLE", TITLE_DESC = "TITLE_DESC", CREATED_AT = "CREATED_AT", CREATED_AT_DESC = "CREATED_AT_DESC", UPDATED_AT = "UPDATED_AT", UPDATED_AT_DESC = "UPDATED_AT_DESC", REPLIED_AT = "REPLIED_AT", REPLIED_AT_DESC = "REPLIED_AT_DESC", REPLY_COUNT = "REPLY_COUNT", REPLY_COUNT_DESC = "REPLY_COUNT_DESC", VIEW_COUNT = "VIEW_COUNT", VIEW_COUNT_DESC = "VIEW_COUNT_DESC", IS_STICKY = "IS_STICKY", SEARCH_MATCH = "SEARCH_MATCH" } /** Options for searching/listing threads. */ interface SearchThreadOptions { /** Search query */ query?: string; /** Filter by media ID */ mediaId?: number; /** Filter by category ID */ categoryId?: number; /** Sort order */ sort?: ThreadSort[]; /** Page number */ page?: number; /** Results per page (max 50) */ perPage?: number; } /** * Normalized Cache Adapter for AniListClient. * * This cache intercepts GraphQL responses, extracts objects with `__typename` and `id`, * and stores them flat in an entity store. * This ensures data consistency across all queries (e.g., `getMedia(1)` and `searchMedia` * share the exact same `Media` object). */ declare class NormalizedCache implements CacheAdapter { private readonly ttl; private readonly maxSize; private readonly enabled; private readonly swrMs; private readonly queryStore; private readonly entityStore; private readonly refCount; private _hits; private _misses; private _stales; constructor(options?: CacheOptions); static key(query: string, variables: Record): string; /** Normalizes a GraphQL response, extracting entities and returning a tree of references. */ private normalize; /** Reconstructs a GraphQL response from references. */ private denormalize; getWithMeta(key: string): { data: T; stale: boolean; } | undefined; get(key: string): T | undefined; set(key: string, data: T): void; private deleteQueryEntry; delete(key: string): boolean; clear(): void; get size(): number; keys(): string[]; invalidate(pattern: string | RegExp): number; get stats(): CacheStats & { entitiesCount: number; }; resetStats(): void; } /** Cache performance statistics. */ interface CacheStats { /** Total cache hits. */ hits: number; /** Total cache misses. */ misses: number; /** Stale entries returned (only with stale-while-revalidate). */ stales: number; /** Hit rate as a ratio 0–1 (NaN if no requests yet). */ hitRate: number; } declare class MemoryCache implements CacheAdapter { private readonly ttl; private readonly maxSize; private readonly enabled; private readonly swrMs; private readonly store; private _hits; private _misses; private _stales; constructor(options?: CacheOptions); /** Build a deterministic cache key from a query + variables pair. */ static key(query: string, variables: Record): string; /** * Retrieve a cached value and its stale status. * With stale-while-revalidate enabled, returns stale data within the grace window * and flags it so the caller can refresh in the background. */ getWithMeta(key: string): { data: T; stale: boolean; } | undefined; get(key: string): T | undefined; /** Store a value in the cache. */ set(key: string, data: T): void; /** Remove a specific entry. */ delete(key: string): boolean; /** Clear the entire cache and reset statistics. */ clear(): void; /** Number of entries currently stored. */ get size(): number | Promise; /** Return all cache keys. */ keys(): string[]; /** * Get cache performance statistics. * * @example * ```ts * const cache = new MemoryCache(); * // ... after some usage ... * console.log(cache.stats); * // { hits: 42, misses: 8, stales: 0, hitRate: 0.84 } * ``` */ get stats(): CacheStats; /** Reset cache statistics without clearing stored data. */ resetStats(): void; /** * Remove all entries whose key matches the given pattern. * * - **String**: treated as a substring match (e.g. `"Media"` removes all keys containing `"Media"`). * - **RegExp**: tested against each key directly. * * @param pattern — A string (substring match) or RegExp. * @returns Number of entries removed. */ invalidate(pattern: string | RegExp): number; } /** * Base interface for the client context shared by all domain method modules. * Exposes only the internal request methods that domain functions need. * * @internal */ interface ClientBase { request(query: string, variables?: Record): Promise; pagedRequest(query: string, variables: Record, field: string): Promise>; paginate(fetchPage: (page: number) => Promise>, maxPages?: number): AsyncGenerator; fetchAll(fetchPage: (page: number) => Promise>, maxPages?: number): Promise; } /** * Lightweight AniList GraphQL client with built-in caching and rate limiting. * * @example * ```ts * import { AniListClient } from "ani-client"; * * const client = new AniListClient(); * const anime = await client.getMedia(1); * console.log(anime.title.romaji); * * // Custom cache & rate limit options * const client2 = new AniListClient({ * cache: { ttl: 1000 * 60 * 60 }, // 1 hour cache * rateLimit: { maxRequests: 60 }, * }); * ``` */ declare class AniListClient implements ClientBase { private readonly apiUrl; private readonly headers; private readonly cacheAdapter; private readonly rateLimiter; private readonly hooks; private readonly logger?; private readonly signal?; private readonly inFlight; private _rateLimitInfo?; private _lastRequestMeta?; private readonly mediaLoader; private readonly characterLoader; private readonly staffLoader; private readonly batchingEnabled; constructor(options?: AniListClientOptions); /** * The current rate limit information from the last API response. * Updated after every non-cached request. */ get rateLimitInfo(): RateLimitInfo | undefined; /** * Metadata about the last request (duration, cache status, rate limit info). * Useful for debugging and monitoring. */ get lastRequestMeta(): ResponseMeta | undefined; /** @internal */ request(query: string, variables?: Record): Promise; /** @internal */ private executeRequest; /** @internal */ pagedRequest(query: string, variables: Record, field: string): Promise>; /** * Fetch a single media entry by its AniList ID. * * Optionally include related data (characters, staff, relations, etc.) via the `include` parameter. * * @param id - The AniList media ID * @param include - Optional related data to include */ getMedia(id: number, include?: MediaIncludeOptions): Promise; getMediaCharacters(mediaId: number, options?: GetMediaCharactersOptions): Promise>; getMediaStaff(mediaId: number, options?: GetMediaStaffOptions): Promise>; /** * Search for anime or manga. * * @param options - Search / filter parameters * @returns Paginated results with matching media */ searchMedia(options?: SearchMediaOptions, include?: MediaIncludeOptions): Promise>; /** Get currently trending anime or manga. */ getTrending(options?: GeneralMediaQueryOptions, include?: MediaIncludeOptions): Promise>; /** Get the most popular anime or manga. */ getPopular(options?: GeneralMediaQueryOptions, include?: MediaIncludeOptions): Promise>; /** Get the highest-rated anime or manga. */ getTopRated(options?: GeneralMediaQueryOptions, include?: MediaIncludeOptions): Promise>; /** Get recently aired anime episodes. */ getAiredEpisodes(options?: GetAiringOptions): Promise>; /** * Get currently releasing manga sorted by most recently updated. * * @param options - Pagination parameters */ getRecentlyUpdatedManga(options?: GetRecentChaptersOptions, include?: MediaIncludeOptions): Promise>; /** * Fetch a media entry by its MyAnimeList (MAL) ID. * * @param malId - The MyAnimeList ID * @param type - Optional media type to disambiguate (some MAL IDs map to both ANIME and MANGA) */ getMediaByMalId(malId: number, type?: MediaType): Promise; /** Get the detailed schedule for the current week, sorted by day. */ getWeeklySchedule(date?: Date, idNotIn?: number[]): Promise; /** Get upcoming (not yet released) media. */ getPlanning(options?: GetPlanningOptions, include?: MediaIncludeOptions): Promise>; /** Get recommendations for a specific media. */ getRecommendations(mediaId: number, options?: Omit): Promise>; /** Get anime (or manga) for a specific season and year. */ getMediaBySeason(options: GetSeasonOptions, include?: MediaIncludeOptions): Promise>; /** Fetch a character by AniList ID. Pass `{ voiceActors: true }` to include VA data. */ getCharacter(id: number, include?: CharacterIncludeOptions): Promise; /** Search for characters by name. */ searchCharacters(options?: SearchCharacterOptions): Promise>; /** Fetch a staff member by AniList ID. Pass `{ media: true }` or `{ media: { perPage } }` for media credits. */ getStaff(id: number, include?: StaffIncludeOptions): Promise; /** Search for staff (voice actors, directors, etc.). */ searchStaff(options?: SearchStaffOptions): Promise>; /** * Fetch a user by AniList ID or username. * * @param idOrName - The AniList user ID (number) or username (string) */ getUser(idOrName: number | string): Promise; /** Search for users by name. */ searchUsers(options?: SearchUserOptions): Promise>; /** Get a user's anime or manga list. */ getUserMediaList(options: GetUserMediaListOptions): Promise>; /** * Fetch a user's favorite anime, manga, characters, staff, and studios. * * @param idOrName - AniList user ID (number) or username (string) * @param options - Optional pagination options (perPage per category) * @returns The user's favorites grouped by category * * @example * ```typescript * const favs = await client.getUserFavorites("AniList"); * favs.anime.forEach(a => console.log(a.title.romaji)); * * // Fetch more results per category * const moreResults = await client.getUserFavorites(1, { perPage: 50 }); * ``` */ getUserFavorites(idOrName: number | string, options?: UserFavoritesOptions): Promise; /** * Fetch a review by its AniList ID. * * @param id - The AniList review ID */ getReview(id: number): Promise; /** * Search for reviews with optional filters. * * @param options - Search and filter options * @returns Paginated results with matching reviews */ searchReviews(options?: SearchReviewOptions): Promise>; /** * Fetch a studio by its AniList ID. * Pass `include` to customise the number of media returned. * * @example * ```typescript * const studio = await client.getStudio(21, { media: { perPage: 50 } }); * ``` */ getStudio(id: number, include?: StudioIncludeOptions): Promise; /** Search for studios by name. */ searchStudios(options?: SearchStudioOptions): Promise>; /** Fetch a forum thread by its AniList ID. */ getThread(id: number): Promise; /** Get recent forum threads, optionally filtered by search, media, or category. */ getRecentThreads(options?: SearchThreadOptions): Promise>; /** Get all available genres on AniList. */ getGenres(): Promise; /** Get all available media tags on AniList. */ getTags(): Promise; /** Execute an arbitrary GraphQL query against the AniList API. */ raw(query: string, variables?: Record): Promise; /** * Auto-paginating async iterator. Yields individual items across all pages. * * @param fetchPage - A function that takes a page number and returns a `PagedResult` * @param maxPages - Maximum number of pages to fetch (default: Infinity) */ paginate(fetchPage: (page: number) => Promise>, maxPages?: number): AsyncGenerator; /** * Utility to fetch all pages of a paginated request and return them as a single array. * * @param fetchPage - A function that takes a page number and returns a `PagedResult` * @param maxPages - Maximum number of pages to fetch (default: Infinity) */ fetchAll(fetchPage: (page: number) => Promise>, maxPages?: number): Promise; /** Fetch multiple media entries in a single API request. */ getMediaBatch(ids: number[]): Promise; /** Fetch multiple characters in a single API request. */ getCharacterBatch(ids: number[]): Promise; /** Fetch multiple staff members in a single API request. */ getStaffBatch(ids: number[]): Promise; /** @internal */ private executeBatch; /** Clear the entire response cache. */ clearCache(): Promise; /** Number of entries currently in the cache. */ cacheSize(): Promise; /** Remove cache entries whose key matches the given pattern. */ invalidateCache(pattern: string | RegExp): Promise; /** Clean up resources held by the client. */ destroy(): Promise; /** * Return a scoped view of this client where every request uses the given `AbortSignal`. * The returned object shares the same cache, rate limiter, and hooks. * * @example * ```ts * const controller = new AbortController(); * const media = await client.withSignal(controller.signal).getMedia(1); * * // Cancel all in-flight requests made through the scoped view * controller.abort(); * ``` */ withSignal(signal: AbortSignal): AniListClient; } /** * Represents a location in a GraphQL query where an error occurred. */ interface GraphQLErrorLocation { line: number; column: number; } /** * Standard GraphQL error shape. */ interface GraphQLError { message: string; locations?: GraphQLErrorLocation[]; path?: (string | number)[]; extensions?: Record; [key: string]: unknown; } /** * Custom error class for AniList API errors. */ declare class AniListError extends Error { /** HTTP status code returned by the API */ readonly status: number; /** Raw error body from the API response */ readonly errors: GraphQLError[]; constructor(message: string, status: number, errors?: GraphQLError[] | unknown[]); } /** * Lightweight media fields — minimal payload for list/search contexts. * Does NOT include tags, studios, trailer, synonyms, or nextAiringEpisode. */ declare const MEDIA_FIELDS_LIGHT = "\n __typename\n id\n idMal\n title { romaji english native userPreferred }\n type\n format\n status\n coverImage { large medium color }\n bannerImage\n genres\n averageScore\n popularity\n favourites\n isAdult\n siteUrl\n season\n seasonYear\n episodes\n chapters\n nextAiringEpisode {\n id\n airingAt\n episode\n timeUntilAiring\n }\n"; /** Core media fields — always returned. Does NOT include relations (opt-in via include). */ declare const MEDIA_FIELDS_BASE = "\n __typename\n id\n idMal\n title { romaji english native userPreferred }\n type\n format\n status\n description(asHtml: false)\n startDate { year month day }\n endDate { year month day }\n season\n seasonYear\n episodes\n duration\n chapters\n volumes\n countryOfOrigin\n isLicensed\n source\n hashtag\n trailer { id site thumbnail }\n coverImage { extraLarge large medium color }\n bannerImage\n genres\n synonyms\n averageScore\n meanScore\n popularity\n favourites\n trending\n tags { id name description category rank isMediaSpoiler }\n studios { nodes { id name isAnimationStudio siteUrl } }\n isAdult\n siteUrl\n nextAiringEpisode {\n id\n airingAt\n episode\n mediaId\n timeUntilAiring\n }\n"; declare const RELATIONS_FIELDS = "\n relations {\n edges {\n relationType(version: 2)\n node {\n __typename\n id\n title { romaji english native userPreferred }\n type\n format\n status\n description(asHtml: false)\n startDate { year month day }\n endDate { year month day }\n season\n seasonYear\n episodes\n chapters\n volumes\n coverImage { extraLarge large medium color }\n genres\n averageScore\n meanScore\n studios { nodes { id name isAnimationStudio siteUrl } }\n siteUrl\n nextAiringEpisode {\n id\n airingAt\n episode\n mediaId\n timeUntilAiring\n }\n }\n }\n }\n"; /** Media Recommendation fields - used for when fetching recommendation for a specific media entry */ declare const MEDIA_RECOMMENDATION_FIELDS = "\n __typename\n id\n rating\n mediaRecommendation {\n __typename\n id\n title { romaji english native userPreferred }\n type\n format\n status\n description(asHtml: false)\n coverImage { extraLarge large medium color }\n averageScore\n meanScore\n \tepisodes\n \tchapters\n \tvolumes\n nextAiringEpisode {\n id\n airingAt\n episode\n mediaId\n timeUntilAiring\n }\n \tseason\n \tseasonYear\n \tstartDate { year month day }\n endDate { year month day }\n \tstudios { nodes { id name isAnimationStudio siteUrl } }\n \tgenres\n siteUrl\n }\n"; /** Full media fields with relations — used by existing queries for backward compat. */ declare const MEDIA_FIELDS = "\n \n __typename\n id\n idMal\n title { romaji english native userPreferred }\n type\n format\n status\n description(asHtml: false)\n startDate { year month day }\n endDate { year month day }\n season\n seasonYear\n episodes\n duration\n chapters\n volumes\n countryOfOrigin\n isLicensed\n source\n hashtag\n trailer { id site thumbnail }\n coverImage { extraLarge large medium color }\n bannerImage\n genres\n synonyms\n averageScore\n meanScore\n popularity\n favourites\n trending\n tags { id name description category rank isMediaSpoiler }\n studios { nodes { id name isAnimationStudio siteUrl } }\n isAdult\n siteUrl\n nextAiringEpisode {\n id\n airingAt\n episode\n mediaId\n timeUntilAiring\n }\n\n \n relations {\n edges {\n relationType(version: 2)\n node {\n __typename\n id\n title { romaji english native userPreferred }\n type\n format\n status\n description(asHtml: false)\n startDate { year month day }\n endDate { year month day }\n season\n seasonYear\n episodes\n chapters\n volumes\n coverImage { extraLarge large medium color }\n genres\n averageScore\n meanScore\n studios { nodes { id name isAnimationStudio siteUrl } }\n siteUrl\n nextAiringEpisode {\n id\n airingAt\n episode\n mediaId\n timeUntilAiring\n }\n }\n }\n }\n\n"; /** Character fields without back-reference to media (used when embedding characters inside a Media query). */ declare const CHARACTER_FIELDS_COMPACT = "\n __typename\n id\n name { first middle last full native alternative }\n image { large medium }\n description(asHtml: false)\n gender\n dateOfBirth { year month day }\n age\n bloodType\n favourites\n siteUrl\n"; /** Compact voice actor fields — lightweight subset for embedding inside character edges. */ declare const VOICE_ACTOR_FIELDS_COMPACT = "\n __typename\n id\n name { first middle last full native userPreferred }\n languageV2\n image { large medium }\n gender\n primaryOccupations\n siteUrl\n"; declare const CHARACTER_FIELDS = "\n \n __typename\n id\n name { first middle last full native alternative }\n image { large medium }\n description(asHtml: false)\n gender\n dateOfBirth { year month day }\n age\n bloodType\n favourites\n siteUrl\n\n \n media(perPage: 10) {\n nodes {\n __typename\n id\n title { romaji english native userPreferred }\n type\n coverImage { large medium }\n siteUrl\n }\n }\n\n"; declare const CHARACTER_FIELDS_WITH_VA = "\n \n __typename\n id\n name { first middle last full native alternative }\n image { large medium }\n description(asHtml: false)\n gender\n dateOfBirth { year month day }\n age\n bloodType\n favourites\n siteUrl\n\n \n media(perPage: 10) {\n edges {\n voiceActors {\n \n __typename\n id\n name { first middle last full native userPreferred }\n languageV2\n image { large medium }\n gender\n primaryOccupations\n siteUrl\n\n }\n node {\n __typename\n id\n title { romaji english native userPreferred }\n type\n coverImage { large medium }\n siteUrl\n }\n }\n }\n\n"; declare const STAFF_FIELDS = "\n __typename\n id\n name { first middle last full native }\n language\n image { large medium }\n description(asHtml: false)\n primaryOccupations\n gender\n dateOfBirth { year month day }\n dateOfDeath { year month day }\n age\n yearsActive\n homeTown\n bloodType\n favourites\n siteUrl\n"; declare const STAFF_MEDIA_FIELDS = "\n staffMedia(perPage: $perPage, sort: [POPULARITY_DESC]) {\n nodes {\n __typename\n id\n title { romaji english native userPreferred }\n type\n format\n status\n coverImage { extraLarge large medium color }\n bannerImage\n genres\n averageScore\n meanScore\n popularity\n favourites\n episodes\n trending\n hashtag\n season\n seasonYear\n startDate { year month day }\n endDate { year month day }\n nextAiringEpisode {\n id\n airingAt\n episode\n mediaId\n timeUntilAiring\n }\n studios {\n edges {\n node {\n name\n }\n }\n }\n siteUrl\n }\n }\n"; declare const USER_FIELDS = "\n __typename\n id\n name\n about(asHtml: false)\n avatar { large medium }\n bannerImage\n isFollowing\n isFollower\n donatorTier\n donatorBadge\n createdAt\n siteUrl\n statistics {\n anime { count meanScore minutesWatched episodesWatched chaptersRead volumesRead }\n manga { count meanScore minutesWatched episodesWatched chaptersRead volumesRead }\n }\n"; /** Favorites fragment — lightweight fields for each favorite category. */ declare const USER_FAVORITES_FIELDS = "\n favourites {\n anime(perPage: 25) {\n nodes {\n __typename\n id\n title { romaji english native userPreferred }\n coverImage { large medium }\n type\n format\n siteUrl\n }\n }\n manga(perPage: 25) {\n nodes {\n __typename\n id\n title { romaji english native userPreferred }\n coverImage { large medium }\n type\n format\n siteUrl\n }\n }\n characters(perPage: 25) {\n nodes {\n __typename\n id\n name { full native }\n image { large medium }\n siteUrl\n }\n }\n staff(perPage: 25) {\n nodes {\n __typename\n id\n name { full native }\n image { large medium }\n siteUrl\n }\n }\n studios(perPage: 25) {\n nodes {\n __typename\n id\n name\n siteUrl\n }\n }\n }\n"; declare const MEDIA_LIST_FIELDS = "\n __typename\n id\n mediaId\n status\n score(format: POINT_100)\n progress\n progressVolumes\n repeat\n priority\n private\n notes\n startedAt { year month day }\n completedAt { year month day }\n updatedAt\n createdAt\n media {\n \n __typename\n id\n idMal\n title { romaji english native userPreferred }\n type\n format\n status\n description(asHtml: false)\n startDate { year month day }\n endDate { year month day }\n season\n seasonYear\n episodes\n duration\n chapters\n volumes\n countryOfOrigin\n isLicensed\n source\n hashtag\n trailer { id site thumbnail }\n coverImage { extraLarge large medium color }\n bannerImage\n genres\n synonyms\n averageScore\n meanScore\n popularity\n favourites\n trending\n tags { id name description category rank isMediaSpoiler }\n studios { nodes { id name isAnimationStudio siteUrl } }\n isAdult\n siteUrl\n nextAiringEpisode {\n id\n airingAt\n episode\n mediaId\n timeUntilAiring\n }\n\n }\n"; declare const STUDIO_FIELDS = "\n __typename\n id\n name\n isAnimationStudio\n siteUrl\n favourites\n media(page: 1, perPage: 25, sort: POPULARITY_DESC) {\n pageInfo { total perPage currentPage lastPage hasNextPage }\n nodes {\n __typename\n id\n title { romaji english native userPreferred }\n type\n format\n coverImage { large medium }\n siteUrl\n }\n }\n"; declare const THREAD_FIELDS = "\n __typename\n id\n title\n body(asHtml: false)\n userId\n replyUserId\n replyCommentId\n replyCount\n viewCount\n isLocked\n isSticky\n isSubscribed\n repliedAt\n createdAt\n updatedAt\n siteUrl\n user {\n __typename\n id\n name\n avatar { large medium }\n }\n replyUser {\n __typename\n id\n name\n avatar { large medium }\n }\n categories {\n __typename\n id\n name\n }\n mediaCategories {\n __typename\n id\n title { romaji english native userPreferred }\n type\n coverImage { large medium }\n siteUrl\n }\n likes {\n __typename\n id\n name\n }\n"; declare const fragments_CHARACTER_FIELDS: typeof CHARACTER_FIELDS; declare const fragments_CHARACTER_FIELDS_COMPACT: typeof CHARACTER_FIELDS_COMPACT; declare const fragments_CHARACTER_FIELDS_WITH_VA: typeof CHARACTER_FIELDS_WITH_VA; declare const fragments_MEDIA_FIELDS: typeof MEDIA_FIELDS; declare const fragments_MEDIA_FIELDS_BASE: typeof MEDIA_FIELDS_BASE; declare const fragments_MEDIA_FIELDS_LIGHT: typeof MEDIA_FIELDS_LIGHT; declare const fragments_MEDIA_LIST_FIELDS: typeof MEDIA_LIST_FIELDS; declare const fragments_MEDIA_RECOMMENDATION_FIELDS: typeof MEDIA_RECOMMENDATION_FIELDS; declare const fragments_RELATIONS_FIELDS: typeof RELATIONS_FIELDS; declare const fragments_STAFF_FIELDS: typeof STAFF_FIELDS; declare const fragments_STAFF_MEDIA_FIELDS: typeof STAFF_MEDIA_FIELDS; declare const fragments_STUDIO_FIELDS: typeof STUDIO_FIELDS; declare const fragments_THREAD_FIELDS: typeof THREAD_FIELDS; declare const fragments_USER_FAVORITES_FIELDS: typeof USER_FAVORITES_FIELDS; declare const fragments_USER_FIELDS: typeof USER_FIELDS; declare const fragments_VOICE_ACTOR_FIELDS_COMPACT: typeof VOICE_ACTOR_FIELDS_COMPACT; declare namespace fragments { export { fragments_CHARACTER_FIELDS as CHARACTER_FIELDS, fragments_CHARACTER_FIELDS_COMPACT as CHARACTER_FIELDS_COMPACT, fragments_CHARACTER_FIELDS_WITH_VA as CHARACTER_FIELDS_WITH_VA, fragments_MEDIA_FIELDS as MEDIA_FIELDS, fragments_MEDIA_FIELDS_BASE as MEDIA_FIELDS_BASE, fragments_MEDIA_FIELDS_LIGHT as MEDIA_FIELDS_LIGHT, fragments_MEDIA_LIST_FIELDS as MEDIA_LIST_FIELDS, fragments_MEDIA_RECOMMENDATION_FIELDS as MEDIA_RECOMMENDATION_FIELDS, fragments_RELATIONS_FIELDS as RELATIONS_FIELDS, fragments_STAFF_FIELDS as STAFF_FIELDS, fragments_STAFF_MEDIA_FIELDS as STAFF_MEDIA_FIELDS, fragments_STUDIO_FIELDS as STUDIO_FIELDS, fragments_THREAD_FIELDS as THREAD_FIELDS, fragments_USER_FAVORITES_FIELDS as USER_FAVORITES_FIELDS, fragments_USER_FIELDS as USER_FIELDS, fragments_VOICE_ACTOR_FIELDS_COMPACT as VOICE_ACTOR_FIELDS_COMPACT }; } /** * Rate limiter with automatic retry for AniList API. * * AniList allows 30 requests per minute. * When a 429 (Too Many Requests) is received, the client * waits for the Retry-After header and retries automatically. */ declare class RateLimiter { private readonly maxRequests; private readonly windowMs; private readonly maxRetries; private readonly retryDelayMs; private readonly enabled; private readonly timeoutMs; private readonly retryOnNetworkError; private readonly retryStrategy?; /** @internal — sliding window: circular buffer of timestamps */ private readonly timestamps; private head; private count; /** @internal — active sleep timers for cleanup */ private readonly activeTimers; constructor(options?: RateLimitOptions); /** * Wait until it's safe to make a request (respects rate limit window). */ acquire(): Promise; /** * Execute a fetch with automatic retry on 429 responses and network errors. * Uses exponential backoff with jitter for retry delays. */ fetchWithRetry(url: string, init: RequestInit, hooks?: { onRetry?: (attempt: number, reason: string, delayMs: number) => void; onRateLimit?: (retryAfterMs: number) => void; }): Promise; /** @internal — Exponential backoff with jitter, capped at 30s (or custom strategy) */ private exponentialDelay; /** @internal */ private fetchWithTimeout; private sleep; /** Cancel all pending sleep timers and reset internal state. */ dispose(): void; } declare function parseAniListMarkdown(text: string): string; export { type AiringSchedule, AiringSort, AniListClient, AniListClientOptions, AniListError, CacheAdapter, CacheOptions, type CacheStats, type Character, type CharacterImage, type CharacterIncludeOptions, type CharacterMediaEdge, type CharacterName, CharacterRole, CharacterSort, type DayOfWeek, ExternalLink, type FavoriteCharacterNode, type FavoriteMediaNode, type FavoriteStaffNode, type FavoriteStudioNode, fragments as Fragments, FuzzyDate, type GetAiringOptions, type GetMediaCharactersOptions, type GetMediaStaffOptions, type GetPlanningOptions, type GetRecentChaptersOptions, type GetRecommendationsOptions, type GetSeasonOptions, type GetUserMediaListOptions, type Media, type MediaCharacterConnection, type MediaCharacterEdge, type MediaConnection, type MediaCoverImage, type MediaEdge, MediaFormat, type MediaIncludeOptions, type MediaListEntry, MediaListSort, MediaListStatus, type MediaRecommendationNode, MediaRelationType, MediaSeason, MediaSort, MediaSource, type MediaStaffConnection, type MediaStaffEdge, type MediaStats, MediaStatus, type MediaTag, type MediaTitle, type MediaTrailer, MediaType, MemoryCache, type NextAiringEpisode, NormalizedCache, PageInfo, PagedResult, RateLimitInfo, RateLimitOptions, RateLimiter, type Recommendation, RecommendationSort, ResponseMeta, type Review, ReviewSort, type ScoreDistribution, type SearchCharacterOptions, type SearchMediaOptions, type SearchReviewOptions, type SearchStaffOptions, type SearchStudioOptions, type SearchThreadOptions, type SearchUserOptions, type Staff, type StaffImage, type StaffIncludeOptions, type StaffMediaNode, type StaffName, StaffSort, type StatusDistribution, type StreamingEpisode, type Studio, type StudioConnection, type StudioIncludeOptions, StudioSort, type Thread, type ThreadCategory, type ThreadMediaCategory, ThreadSort, type User, type UserAvatar, type UserFavorites, type UserFavoritesOptions, UserSort, type UserStatistics, type VoiceActor, type WeeklySchedule, parseAniListMarkdown };