yoto-nodejs-client 0.0.1 → 0.0.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (37) hide show
  1. package/bin/lib/cli-helpers.d.ts +32 -0
  2. package/bin/lib/cli-helpers.d.ts.map +1 -1
  3. package/bin/lib/token-helpers.d.ts +32 -0
  4. package/bin/lib/token-helpers.d.ts.map +1 -1
  5. package/index.d.ts +368 -0
  6. package/index.d.ts.map +1 -1
  7. package/lib/api-endpoints/auth.d.ts +85 -0
  8. package/lib/api-endpoints/auth.d.ts.map +1 -1
  9. package/lib/api-endpoints/constants.d.ts +22 -0
  10. package/lib/api-endpoints/constants.d.ts.map +1 -1
  11. package/lib/api-endpoints/content.d.ts +760 -0
  12. package/lib/api-endpoints/content.d.ts.map +1 -1
  13. package/lib/api-endpoints/devices.d.ts +581 -0
  14. package/lib/api-endpoints/devices.d.ts.map +1 -1
  15. package/lib/api-endpoints/family-library-groups.d.ts +187 -0
  16. package/lib/api-endpoints/family-library-groups.d.ts.map +1 -1
  17. package/lib/api-endpoints/family.d.ts +88 -0
  18. package/lib/api-endpoints/family.d.ts.map +1 -1
  19. package/lib/api-endpoints/helpers.d.ts +37 -3
  20. package/lib/api-endpoints/helpers.d.ts.map +1 -1
  21. package/lib/api-endpoints/icons.d.ts +196 -0
  22. package/lib/api-endpoints/icons.d.ts.map +1 -1
  23. package/lib/api-endpoints/media.d.ts +83 -0
  24. package/lib/api-endpoints/media.d.ts.map +1 -1
  25. package/lib/api-endpoints/test-helpers.d.ts +21 -0
  26. package/lib/api-endpoints/test-helpers.d.ts.map +1 -1
  27. package/lib/mqtt/client.d.ts +277 -0
  28. package/lib/mqtt/client.d.ts.map +1 -1
  29. package/lib/mqtt/commands.d.ts +195 -0
  30. package/lib/mqtt/commands.d.ts.map +1 -1
  31. package/lib/mqtt/factory.d.ts +43 -0
  32. package/lib/mqtt/factory.d.ts.map +1 -1
  33. package/lib/mqtt/topics.d.ts +157 -0
  34. package/lib/mqtt/topics.d.ts.map +1 -1
  35. package/lib/token.d.ts +88 -0
  36. package/lib/token.d.ts.map +1 -1
  37. package/package.json +1 -1
@@ -1,5 +1,20 @@
1
+ /**
2
+ * Get common CLI option definitions shared across all tools
3
+ * @returns {ArgscloptsParseArgsOptionsConfig}
4
+ */
1
5
  export function getCommonOptions(): ArgscloptsParseArgsOptionsConfig;
6
+ /**
7
+ * Load .env file from specified path or default to .env in cwd
8
+ * @param {string} [envFile] - Optional path to .env file
9
+ * @returns {string} The path that was loaded (or attempted)
10
+ */
2
11
  export function loadEnvFile(envFile?: string): string;
12
+ /**
13
+ * Load and validate tokens from environment
14
+ * @param {{ values: Record<string, string | boolean | undefined> }} args - Parsed arguments from parseArgs
15
+ * @returns {{ clientId: string, refreshToken: string, accessToken: string, envFile: string }}
16
+ * @throws Exits process if tokens are missing
17
+ */
3
18
  export function loadTokensFromEnv(args: {
4
19
  values: Record<string, string | boolean | undefined>;
5
20
  }): {
@@ -8,13 +23,30 @@ export function loadTokensFromEnv(args: {
8
23
  accessToken: string;
9
24
  envFile: string;
10
25
  };
26
+ /**
27
+ * Create YotoClient with standard token persistence callbacks
28
+ * @param {object} options
29
+ * @param {string} options.clientId - OAuth client ID
30
+ * @param {string} options.refreshToken - OAuth refresh token
31
+ * @param {string} options.accessToken - OAuth access token
32
+ * @param {string} [options.outputFile='.env'] - File to save refreshed tokens to
33
+ * @returns {YotoClient}
34
+ */
11
35
  export function createYotoClient({ clientId, refreshToken, accessToken, outputFile }: {
12
36
  clientId: string;
13
37
  refreshToken: string;
14
38
  accessToken: string;
15
39
  outputFile?: string | undefined;
16
40
  }): YotoClient;
41
+ /**
42
+ * Standard error handler for CLI tools
43
+ * @param {any} error
44
+ */
17
45
  export function handleCliError(error: any): void;
46
+ /**
47
+ * Print CLI tool header with title
48
+ * @param {string} title - The title to display
49
+ */
18
50
  export function printHeader(title: string): void;
19
51
  import type { ArgscloptsParseArgsOptionsConfig } from 'argsclopts';
20
52
  import { YotoClient } from '../../index.js';
@@ -1 +1 @@
1
- {"version":3,"file":"cli-helpers.d.ts","sourceRoot":"","sources":["cli-helpers.js"],"names":[],"mappings":"AAYA,oCAFa,gCAAgC,CAoB5C;AAOD,sCAHW,MAAM,GACJ,MAAM,CAUlB;AAQD,wCAJW;IAAE,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,GAAG,OAAO,GAAG,SAAS,CAAC,CAAA;CAAE,GACtD;IAAE,QAAQ,EAAE,MAAM,CAAC;IAAC,YAAY,EAAE,MAAM,CAAC;IAAC,WAAW,EAAE,MAAM,CAAC;IAAC,OAAO,EAAE,MAAM,CAAA;CAAE,CAoB5F;AAWD,sFANG;IAAwB,QAAQ,EAAxB,MAAM;IACU,YAAY,EAA5B,MAAM;IACU,WAAW,EAA3B,MAAM;IACW,UAAU;CACnC,GAAU,UAAU,CAsBtB;AAMD,sCAFW,GAAG,QAyBb;AAMD,mCAFW,MAAM,QAKhB;sDA1IoD,YAAY;2BAGtC,gBAAgB"}
1
+ {"version":3,"file":"cli-helpers.d.ts","sourceRoot":"","sources":["cli-helpers.js"],"names":[],"mappings":"AAQA;;;GAGG;AACH,oCAFa,gCAAgC,CAoB5C;AAED;;;;GAIG;AACH,sCAHW,MAAM,GACJ,MAAM,CAUlB;AAED;;;;;GAKG;AACH,wCAJW;IAAE,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,GAAG,OAAO,GAAG,SAAS,CAAC,CAAA;CAAE,GACtD;IAAE,QAAQ,EAAE,MAAM,CAAC;IAAC,YAAY,EAAE,MAAM,CAAC;IAAC,WAAW,EAAE,MAAM,CAAC;IAAC,OAAO,EAAE,MAAM,CAAA;CAAE,CAoB5F;AAED;;;;;;;;GAQG;AACH,sFANG;IAAwB,QAAQ,EAAxB,MAAM;IACU,YAAY,EAA5B,MAAM;IACU,WAAW,EAA3B,MAAM;IACW,UAAU;CACnC,GAAU,UAAU,CAsBtB;AAED;;;GAGG;AACH,sCAFW,GAAG,QAyBb;AAED;;;GAGG;AACH,mCAFW,MAAM,QAKhB;sDA1IoD,YAAY;2BAGtC,gBAAgB"}
@@ -1,14 +1,46 @@
1
+ /**
2
+ * Format timestamp
3
+ * @param {number} timestamp
4
+ * @returns {string}
5
+ */
1
6
  export function formatTimestamp(timestamp: number): string;
7
+ /**
8
+ * Check if token is expired
9
+ * @param {number} exp
10
+ * @param {number} bufferSeconds
11
+ * @returns {{expired: boolean, message: string}}
12
+ */
2
13
  export function checkExpiration(exp: number, bufferSeconds?: number): {
3
14
  expired: boolean;
4
15
  message: string;
5
16
  };
17
+ /**
18
+ * Check if a JWT token is expired or about to expire
19
+ * @param {string} token - JWT token to check
20
+ * @param {number} bufferSeconds - Seconds before expiration to consider expired
21
+ * @returns {{expired: boolean, message: string}}
22
+ */
6
23
  export function checkTokenExpiration(token: string, bufferSeconds?: number): {
7
24
  expired: boolean;
8
25
  message: string;
9
26
  };
27
+ /**
28
+ * Decode a JWT token without verification
29
+ * @param {string} token
30
+ * @returns {any}
31
+ */
10
32
  export function decodeJwt(token: string): any;
33
+ /**
34
+ * Save tokens to .env file
35
+ * @param {string} filename
36
+ * @param {YotoTokenResponse} tokens
37
+ * @param {string} clientId
38
+ */
11
39
  export function saveTokensToEnv(filename: string, tokens: YotoTokenResponse, clientId: string): Promise<void>;
40
+ /**
41
+ * Sleep for a specified number of milliseconds
42
+ * @param {number} ms
43
+ */
12
44
  export function sleep(ms: number): Promise<any>;
13
45
  import type { YotoTokenResponse } from '../../lib/api-endpoints/auth.js';
14
46
  //# sourceMappingURL=token-helpers.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"token-helpers.d.ts","sourceRoot":"","sources":["token-helpers.js"],"names":[],"mappings":"AAaA,2CAHW,MAAM,GACJ,MAAM,CAKlB;AAQD,qCAJW,MAAM,kBACN,MAAM,GACJ;IAAC,OAAO,EAAE,OAAO,CAAC;IAAC,OAAO,EAAE,MAAM,CAAA;CAAC,CAmB/C;AAQD,4CAJW,MAAM,kBACN,MAAM,GACJ;IAAC,OAAO,EAAE,OAAO,CAAC;IAAC,OAAO,EAAE,MAAM,CAAA;CAAC,CAa/C;AAOD,iCAHW,MAAM,GACJ,GAAG,CASf;AAQD,0CAJW,MAAM,UACN,iBAAiB,YACjB,MAAM,iBA8DhB;AAMD,0BAFW,MAAM,gBAIhB;uCArJmC,iCAAiC"}
1
+ {"version":3,"file":"token-helpers.d.ts","sourceRoot":"","sources":["token-helpers.js"],"names":[],"mappings":"AAQA;;;;GAIG;AACH,2CAHW,MAAM,GACJ,MAAM,CAKlB;AAED;;;;;GAKG;AACH,qCAJW,MAAM,kBACN,MAAM,GACJ;IAAC,OAAO,EAAE,OAAO,CAAC;IAAC,OAAO,EAAE,MAAM,CAAA;CAAC,CAmB/C;AAED;;;;;GAKG;AACH,4CAJW,MAAM,kBACN,MAAM,GACJ;IAAC,OAAO,EAAE,OAAO,CAAC;IAAC,OAAO,EAAE,MAAM,CAAA;CAAC,CAa/C;AAED;;;;GAIG;AACH,iCAHW,MAAM,GACJ,GAAG,CASf;AAED;;;;;GAKG;AACH,0CAJW,MAAM,UACN,iBAAiB,YACjB,MAAM,iBA8DhB;AAED;;;GAGG;AACH,0BAFW,MAAM,gBAIhB;uCArJmC,iCAAiC"}
package/index.d.ts CHANGED
@@ -1,4 +1,44 @@
1
+ /**
2
+ * @typedef {Object} RefreshSuccessEvent
3
+ * @property {string} clientId - The OAuth client ID
4
+ * @property {string} accessToken - The new access token
5
+ * @property {string} refreshToken - The refresh token (may be updated)
6
+ * @property {number} expiresAt - Unix timestamp in seconds when token expires
7
+ */
8
+ /**
9
+ * @typedef {Object} YotoClientConstructorOptions
10
+ * @property {string} clientId - OAuth client ID
11
+ * @property {string} refreshToken - OAuth refresh token
12
+ * @property {string} accessToken - Initial OAuth access token (JWT)
13
+ * @property {(event: RefreshSuccessEvent) => void | Promise<void>} onTokenRefresh - **REQUIRED** Callback invoked when tokens are refreshed. You MUST persist these tokens (to file, database, etc.) as the refresh can happen at any time during API calls. The refresh token may be rotated by the auth server. **DO NOT STUB THIS CALLBACK** - always implement proper persistence logic.
14
+ * @property {number} [bufferSeconds=30] - Seconds before expiration to consider token expired
15
+ * @property {() => void | Promise<void>} [onRefreshStart] - Optional callback invoked when token refresh starts. Defaults to console.log.
16
+ * @property {(error: Error) => void | Promise<void>} [onRefreshError] - Optional callback invoked when token refresh fails with a transient error. Defaults to console.warn.
17
+ * @property {(error: Error) => void | Promise<void>} [onInvalid] - Optional callback invoked when refresh token is permanently invalid. Defaults to console.error.
18
+ * @property {string} [userAgent] - Optional user agent string to identify your application
19
+ * @property {RequestOptions} [defaultRequestOptions] - Default undici request options for all requests (dispatcher, timeouts, etc.)
20
+ */
21
+ /**
22
+ * Yoto API Client with automatic token refresh
23
+ */
1
24
  export class YotoClient {
25
+ /**
26
+ * Get authorization URL for browser-based OAuth flow
27
+ * @see https://yoto.dev/api/get-authorize/
28
+ * @param {object} params
29
+ * @param {string} params.clientId - OAuth client ID
30
+ * @param {string} params.redirectUri - Redirect URI after authorization
31
+ * @param {'code' | 'token' | 'id_token' | 'code token' | 'code id_token' | 'token id_token' | 'code token id_token'} params.responseType - OAuth response type
32
+ * @param {string} params.state - State parameter for CSRF protection
33
+ * @param {string} [params.audience] - Audience for the token
34
+ * @param {string} [params.scope] - Requested scopes
35
+ * @param {string} [params.nonce] - Nonce for replay attack prevention
36
+ * @param {'none' | 'login' | 'consent' | 'select_account'} [params.prompt] - Authorization prompt behavior
37
+ * @param {number} [params.maxAge] - Maximum authentication age in seconds
38
+ * @param {string} [params.codeChallenge] - PKCE code challenge
39
+ * @param {'S256' | 'plain'} [params.codeChallengeMethod] - PKCE code challenge method
40
+ * @returns {string} Authorization URL
41
+ */
2
42
  static getAuthorizeUrl(params: {
3
43
  clientId: string;
4
44
  redirectUri: string;
@@ -12,6 +52,22 @@ export class YotoClient {
12
52
  codeChallenge?: string | undefined;
13
53
  codeChallengeMethod?: "S256" | "plain" | undefined;
14
54
  }): string;
55
+ /**
56
+ * Exchange authorization code or refresh token for access tokens
57
+ * @see https://yoto.dev/api/post-oauth-token/
58
+ * @param {object} params
59
+ * @param {'authorization_code' | 'refresh_token' | 'client_credentials' | 'urn:ietf:params:oauth:grant-type:device_code'} params.grantType - OAuth grant type
60
+ * @param {string} [params.code] - Authorization code (required for authorization_code grant)
61
+ * @param {string} [params.redirectUri] - Redirect URI (required for authorization_code grant if used in authorize request)
62
+ * @param {string} [params.refreshToken] - Refresh token (required for refresh_token grant)
63
+ * @param {string} [params.clientId] - OAuth client ID
64
+ * @param {string} [params.clientSecret] - OAuth client secret
65
+ * @param {string} [params.scope] - Requested scope
66
+ * @param {string} [params.codeVerifier] - PKCE code verifier
67
+ * @param {string} [params.deviceCode] - Device code (required for device_code grant)
68
+ * @param {string} [params.audience] - Audience for the token
69
+ * @returns {Promise<YotoTokenResponse>}
70
+ */
15
71
  static exchangeToken(params: {
16
72
  grantType: "authorization_code" | "refresh_token" | "client_credentials" | "urn:ietf:params:oauth:grant-type:device_code";
17
73
  code?: string | undefined;
@@ -24,13 +80,41 @@ export class YotoClient {
24
80
  deviceCode?: string | undefined;
25
81
  audience?: string | undefined;
26
82
  }): Promise<Auth.YotoTokenResponse>;
83
+ /**
84
+ * Request device code for device authorization flow
85
+ * @see https://yoto.dev/api/post-oauth-device-code/
86
+ * @param {object} params
87
+ * @param {string} params.clientId - OAuth client ID
88
+ * @param {string} [params.scope] - Requested scopes
89
+ * @param {string} [params.audience] - Audience for the token
90
+ * @returns {Promise<YotoDeviceCodeResponse>}
91
+ */
27
92
  static requestDeviceCode(params: {
28
93
  clientId: string;
29
94
  scope?: string | undefined;
30
95
  audience?: string | undefined;
31
96
  }): Promise<Auth.YotoDeviceCodeResponse>;
97
+ /**
98
+ * Create a new Yoto API client
99
+ * @param {YotoClientConstructorOptions} options
100
+ */
32
101
  constructor({ clientId, refreshToken, accessToken, onTokenRefresh, bufferSeconds, onRefreshStart, onRefreshError, onInvalid, userAgent, defaultRequestOptions }: YotoClientConstructorOptions);
102
+ /**
103
+ * Get the underlying RefreshableToken instance
104
+ * @returns {RefreshableToken}
105
+ */
33
106
  get token(): RefreshableToken;
107
+ /**
108
+ * Get content/card details
109
+ * @see https://yoto.dev/api/getcontent/
110
+ * @param {object} params
111
+ * @param {string} params.cardId - The card/content ID
112
+ * @param {string} [params.timezone] - Timezone for schedule-based content
113
+ * @param {'full' | 'pre'} [params.signingType] - Type of URL signing
114
+ * @param {boolean} [params.playable] - Whether to include playback URLs
115
+ * @param {RequestOptions} [params.requestOptions] - Request options that override defaults
116
+ * @returns {Promise<YotoContentResponse>}
117
+ */
34
118
  getContent({ cardId, timezone, signingType, playable, requestOptions }: {
35
119
  cardId: string;
36
120
  timezone?: string | undefined;
@@ -40,41 +124,97 @@ export class YotoClient {
40
124
  dispatcher?: import("undici").Dispatcher;
41
125
  } & Omit<import("undici").Dispatcher.RequestOptions<unknown>, "origin" | "path" | "method"> & Partial<Pick<import("undici").Dispatcher.RequestOptions<null>, "method">>) | undefined;
42
126
  }): Promise<Content.YotoContentResponse>;
127
+ /**
128
+ * Get user's MYO (Make Your Own) content
129
+ * @see https://yoto.dev/api/getusersmyocontent/
130
+ * @param {object} [params]
131
+ * @param {boolean} [params.showDeleted=false] - Include deleted content
132
+ * @param {RequestOptions} [params.requestOptions] - Request options that override defaults
133
+ * @returns {Promise<YotoMyoContentResponse>}
134
+ */
43
135
  getUserMyoContent({ showDeleted, requestOptions }?: {
44
136
  showDeleted?: boolean | undefined;
45
137
  requestOptions?: ({
46
138
  dispatcher?: import("undici").Dispatcher;
47
139
  } & Omit<import("undici").Dispatcher.RequestOptions<unknown>, "origin" | "path" | "method"> & Partial<Pick<import("undici").Dispatcher.RequestOptions<null>, "method">>) | undefined;
48
140
  }): Promise<Content.YotoMyoContentResponse>;
141
+ /**
142
+ * Create or update content/card
143
+ * @see https://yoto.dev/api/createorupdatecontent/
144
+ * @param {object} params
145
+ * @param {YotoCreateOrUpdateContentRequest} params.content - Content data to create/update
146
+ * @param {RequestOptions} [params.requestOptions] - Request options that override defaults
147
+ * @returns {Promise<YotoCreateOrUpdateContentResponse>}
148
+ */
49
149
  createOrUpdateContent({ content, requestOptions }: {
50
150
  content: Content.YotoCreateOrUpdateContentRequest;
51
151
  requestOptions?: ({
52
152
  dispatcher?: import("undici").Dispatcher;
53
153
  } & Omit<import("undici").Dispatcher.RequestOptions<unknown>, "origin" | "path" | "method"> & Partial<Pick<import("undici").Dispatcher.RequestOptions<null>, "method">>) | undefined;
54
154
  }): Promise<Content.YotoCreateOrUpdateContentResponse>;
155
+ /**
156
+ * Delete content/card
157
+ * @see https://yoto.dev/api/deletecontent/
158
+ * @param {object} params
159
+ * @param {string} params.cardId - The card/content ID to delete
160
+ * @param {RequestOptions} [params.requestOptions] - Request options that override defaults
161
+ * @returns {Promise<YotoDeleteContentResponse>}
162
+ */
55
163
  deleteContent({ cardId, requestOptions }: {
56
164
  cardId: string;
57
165
  requestOptions?: ({
58
166
  dispatcher?: import("undici").Dispatcher;
59
167
  } & Omit<import("undici").Dispatcher.RequestOptions<unknown>, "origin" | "path" | "method"> & Partial<Pick<import("undici").Dispatcher.RequestOptions<null>, "method">>) | undefined;
60
168
  }): Promise<Content.YotoDeleteContentResponse>;
169
+ /**
170
+ * Get all devices for authenticated user
171
+ * @see https://yoto.dev/api/getdevices/
172
+ * @param {object} [params]
173
+ * @param {RequestOptions} [params.requestOptions] - Request options that override defaults
174
+ * @returns {Promise<YotoDevicesResponse>}
175
+ */
61
176
  getDevices({ requestOptions }?: {
62
177
  requestOptions?: ({
63
178
  dispatcher?: import("undici").Dispatcher;
64
179
  } & Omit<import("undici").Dispatcher.RequestOptions<unknown>, "origin" | "path" | "method"> & Partial<Pick<import("undici").Dispatcher.RequestOptions<null>, "method">>) | undefined;
65
180
  }): Promise<Devices.YotoDevicesResponse>;
181
+ /**
182
+ * Get device status
183
+ * @see https://yoto.dev/api/getdevicestatus/
184
+ * @param {object} params
185
+ * @param {string} params.deviceId - Device ID
186
+ * @param {RequestOptions} [params.requestOptions] - Request options that override defaults
187
+ * @returns {Promise<YotoDeviceStatusResponse>}
188
+ */
66
189
  getDeviceStatus({ deviceId, requestOptions }: {
67
190
  deviceId: string;
68
191
  requestOptions?: ({
69
192
  dispatcher?: import("undici").Dispatcher;
70
193
  } & Omit<import("undici").Dispatcher.RequestOptions<unknown>, "origin" | "path" | "method"> & Partial<Pick<import("undici").Dispatcher.RequestOptions<null>, "method">>) | undefined;
71
194
  }): Promise<Devices.YotoDeviceStatusResponse>;
195
+ /**
196
+ * Get device configuration
197
+ * @see https://yoto.dev/api/getdeviceconfig/
198
+ * @param {object} params
199
+ * @param {string} params.deviceId - Device ID
200
+ * @param {RequestOptions} [params.requestOptions] - Request options that override defaults
201
+ * @returns {Promise<YotoDeviceConfigResponse>}
202
+ */
72
203
  getDeviceConfig({ deviceId, requestOptions }: {
73
204
  deviceId: string;
74
205
  requestOptions?: ({
75
206
  dispatcher?: import("undici").Dispatcher;
76
207
  } & Omit<import("undici").Dispatcher.RequestOptions<unknown>, "origin" | "path" | "method"> & Partial<Pick<import("undici").Dispatcher.RequestOptions<null>, "method">>) | undefined;
77
208
  }): Promise<Devices.YotoDeviceConfigResponse>;
209
+ /**
210
+ * Update device configuration
211
+ * @see https://yoto.dev/api/updatedeviceconfig/
212
+ * @param {object} params
213
+ * @param {string} params.deviceId - Device ID
214
+ * @param {YotoUpdateDeviceConfigRequest} params.configUpdate - Config updates
215
+ * @param {RequestOptions} [params.requestOptions] - Request options that override defaults
216
+ * @returns {Promise<YotoUpdateDeviceConfigResponse>}
217
+ */
78
218
  updateDeviceConfig({ deviceId, configUpdate, requestOptions }: {
79
219
  deviceId: string;
80
220
  configUpdate: Devices.YotoUpdateDeviceConfigRequest;
@@ -82,6 +222,15 @@ export class YotoClient {
82
222
  dispatcher?: import("undici").Dispatcher;
83
223
  } & Omit<import("undici").Dispatcher.RequestOptions<unknown>, "origin" | "path" | "method"> & Partial<Pick<import("undici").Dispatcher.RequestOptions<null>, "method">>) | undefined;
84
224
  }): Promise<Devices.YotoUpdateDeviceConfigResponse>;
225
+ /**
226
+ * Update device shortcuts
227
+ * @see https://yoto.dev/api/updateshortcutsbeta/
228
+ * @param {object} params
229
+ * @param {string} params.deviceId - Device ID
230
+ * @param {YotoUpdateShortcutsRequest} params.shortcutsUpdate - Shortcuts config
231
+ * @param {RequestOptions} [params.requestOptions] - Request options that override defaults
232
+ * @returns {Promise<YotoUpdateShortcutsResponse>}
233
+ */
85
234
  updateDeviceShortcuts({ deviceId, shortcutsUpdate, requestOptions }: {
86
235
  deviceId: string;
87
236
  shortcutsUpdate: Devices.YotoUpdateShortcutsRequest;
@@ -89,6 +238,16 @@ export class YotoClient {
89
238
  dispatcher?: import("undici").Dispatcher;
90
239
  } & Omit<import("undici").Dispatcher.RequestOptions<unknown>, "origin" | "path" | "method"> & Partial<Pick<import("undici").Dispatcher.RequestOptions<null>, "method">>) | undefined;
91
240
  }): Promise<Devices.YotoUpdateShortcutsResponse>;
241
+ /**
242
+ * Send command to device
243
+ * @see https://yoto.dev/api/senddevicecommand/
244
+ * @see https://yoto.dev/players-mqtt/mqtt-docs/
245
+ * @param {object} params
246
+ * @param {string} params.deviceId - Device ID
247
+ * @param {YotoDeviceCommand} params.command - Command to send
248
+ * @param {RequestOptions} [params.requestOptions] - Request options that override defaults
249
+ * @returns {Promise<YotoDeviceCommandResponse>}
250
+ */
92
251
  sendDeviceCommand({ deviceId, command, requestOptions }: {
93
252
  deviceId: string;
94
253
  command: Devices.YotoDeviceCommand;
@@ -96,23 +255,55 @@ export class YotoClient {
96
255
  dispatcher?: import("undici").Dispatcher;
97
256
  } & Omit<import("undici").Dispatcher.RequestOptions<unknown>, "origin" | "path" | "method"> & Partial<Pick<import("undici").Dispatcher.RequestOptions<null>, "method">>) | undefined;
98
257
  }): Promise<Devices.YotoDeviceCommandResponse>;
258
+ /**
259
+ * Get all family library groups
260
+ * @see https://yoto.dev/api/getgroups/
261
+ * @param {object} [params]
262
+ * @param {RequestOptions} [params.requestOptions] - Request options that override defaults
263
+ * @returns {Promise<YotoGroup[]>}
264
+ */
99
265
  getGroups({ requestOptions }?: {
100
266
  requestOptions?: ({
101
267
  dispatcher?: import("undici").Dispatcher;
102
268
  } & Omit<import("undici").Dispatcher.RequestOptions<unknown>, "origin" | "path" | "method"> & Partial<Pick<import("undici").Dispatcher.RequestOptions<null>, "method">>) | undefined;
103
269
  }): Promise<FamilyLibraryGroups.YotoGroup[]>;
270
+ /**
271
+ * Create a family library group
272
+ * @see https://yoto.dev/api/createagroup/
273
+ * @param {object} params
274
+ * @param {YotoCreateGroupRequest} params.group - Group data
275
+ * @param {RequestOptions} [params.requestOptions] - Request options that override defaults
276
+ * @returns {Promise<YotoGroup>}
277
+ */
104
278
  createGroup({ group, requestOptions }: {
105
279
  group: FamilyLibraryGroups.YotoCreateGroupRequest;
106
280
  requestOptions?: ({
107
281
  dispatcher?: import("undici").Dispatcher;
108
282
  } & Omit<import("undici").Dispatcher.RequestOptions<unknown>, "origin" | "path" | "method"> & Partial<Pick<import("undici").Dispatcher.RequestOptions<null>, "method">>) | undefined;
109
283
  }): Promise<FamilyLibraryGroups.YotoGroup>;
284
+ /**
285
+ * Get a specific family library group
286
+ * @see https://yoto.dev/api/getgroup/
287
+ * @param {object} params
288
+ * @param {string} params.groupId - Group ID
289
+ * @param {RequestOptions} [params.requestOptions] - Request options that override defaults
290
+ * @returns {Promise<YotoGroup>}
291
+ */
110
292
  getGroup({ groupId, requestOptions }: {
111
293
  groupId: string;
112
294
  requestOptions?: ({
113
295
  dispatcher?: import("undici").Dispatcher;
114
296
  } & Omit<import("undici").Dispatcher.RequestOptions<unknown>, "origin" | "path" | "method"> & Partial<Pick<import("undici").Dispatcher.RequestOptions<null>, "method">>) | undefined;
115
297
  }): Promise<FamilyLibraryGroups.YotoGroup>;
298
+ /**
299
+ * Update a family library group
300
+ * @see https://yoto.dev/api/updateagroup/
301
+ * @param {object} params
302
+ * @param {string} params.groupId - Group ID
303
+ * @param {YotoUpdateGroupRequest} params.group - Updated group data
304
+ * @param {RequestOptions} [params.requestOptions] - Request options that override defaults
305
+ * @returns {Promise<YotoGroup>}
306
+ */
116
307
  updateGroup({ groupId, group, requestOptions }: {
117
308
  groupId: string;
118
309
  group: FamilyLibraryGroups.YotoUpdateGroupRequest;
@@ -120,17 +311,41 @@ export class YotoClient {
120
311
  dispatcher?: import("undici").Dispatcher;
121
312
  } & Omit<import("undici").Dispatcher.RequestOptions<unknown>, "origin" | "path" | "method"> & Partial<Pick<import("undici").Dispatcher.RequestOptions<null>, "method">>) | undefined;
122
313
  }): Promise<FamilyLibraryGroups.YotoGroup>;
314
+ /**
315
+ * Delete a family library group
316
+ * @see https://yoto.dev/api/deleteagroup/
317
+ * @param {object} params
318
+ * @param {string} params.groupId - Group ID
319
+ * @param {RequestOptions} [params.requestOptions] - Request options that override defaults
320
+ * @returns {Promise<YotoDeleteGroupResponse>}
321
+ */
123
322
  deleteGroup({ groupId, requestOptions }: {
124
323
  groupId: string;
125
324
  requestOptions?: ({
126
325
  dispatcher?: import("undici").Dispatcher;
127
326
  } & Omit<import("undici").Dispatcher.RequestOptions<unknown>, "origin" | "path" | "method"> & Partial<Pick<import("undici").Dispatcher.RequestOptions<null>, "method">>) | undefined;
128
327
  }): Promise<FamilyLibraryGroups.YotoDeleteGroupResponse>;
328
+ /**
329
+ * Get all family images
330
+ * @see https://yoto.dev/api/getfamilyimages/
331
+ * @param {object} [params]
332
+ * @param {RequestOptions} [params.requestOptions] - Request options that override defaults
333
+ * @returns {Promise<YotoFamilyImagesResponse>}
334
+ */
129
335
  getFamilyImages({ requestOptions }?: {
130
336
  requestOptions?: ({
131
337
  dispatcher?: import("undici").Dispatcher;
132
338
  } & Omit<import("undici").Dispatcher.RequestOptions<unknown>, "origin" | "path" | "method"> & Partial<Pick<import("undici").Dispatcher.RequestOptions<null>, "method">>) | undefined;
133
339
  }): Promise<Family.YotoFamilyImagesResponse>;
340
+ /**
341
+ * Get a specific family image
342
+ * @see https://yoto.dev/api/getafamilyimage/
343
+ * @param {object} params
344
+ * @param {string} params.imageId - Image ID
345
+ * @param {'640x480' | '320x320'} params.size - Image size
346
+ * @param {RequestOptions} [params.requestOptions] - Request options that override defaults
347
+ * @returns {Promise<YotoFamilyImageResponse>}
348
+ */
134
349
  getAFamilyImage({ imageId, size, requestOptions }: {
135
350
  imageId: string;
136
351
  size: "640x480" | "320x320";
@@ -138,22 +353,54 @@ export class YotoClient {
138
353
  dispatcher?: import("undici").Dispatcher;
139
354
  } & Omit<import("undici").Dispatcher.RequestOptions<unknown>, "origin" | "path" | "method"> & Partial<Pick<import("undici").Dispatcher.RequestOptions<null>, "method">>) | undefined;
140
355
  }): Promise<Family.YotoFamilyImageResponse>;
356
+ /**
357
+ * Upload a family image
358
+ * @see https://yoto.dev/api/uploadafamilyimage/
359
+ * @param {object} params
360
+ * @param {Buffer} params.imageData - Image binary data
361
+ * @param {RequestOptions} [params.requestOptions] - Request options that override defaults
362
+ * @returns {Promise<YotoUploadFamilyImageResponse>}
363
+ */
141
364
  uploadAFamilyImage({ imageData, requestOptions }: {
142
365
  imageData: Buffer;
143
366
  requestOptions?: ({
144
367
  dispatcher?: import("undici").Dispatcher;
145
368
  } & Omit<import("undici").Dispatcher.RequestOptions<unknown>, "origin" | "path" | "method"> & Partial<Pick<import("undici").Dispatcher.RequestOptions<null>, "method">>) | undefined;
146
369
  }): Promise<Family.YotoUploadFamilyImageResponse>;
370
+ /**
371
+ * Get public Yoto icons
372
+ * @see https://yoto.dev/api/getpublicicons/
373
+ * @param {object} [params]
374
+ * @param {RequestOptions} [params.requestOptions] - Request options that override defaults
375
+ * @returns {Promise<YotoPublicIconsResponse>}
376
+ */
147
377
  getPublicIcons({ requestOptions }?: {
148
378
  requestOptions?: ({
149
379
  dispatcher?: import("undici").Dispatcher;
150
380
  } & Omit<import("undici").Dispatcher.RequestOptions<unknown>, "origin" | "path" | "method"> & Partial<Pick<import("undici").Dispatcher.RequestOptions<null>, "method">>) | undefined;
151
381
  }): Promise<Icons.YotoPublicIconsResponse>;
382
+ /**
383
+ * Get user's custom icons
384
+ * @see https://yoto.dev/api/getusericons/
385
+ * @param {object} [params]
386
+ * @param {RequestOptions} [params.requestOptions] - Request options that override defaults
387
+ * @returns {Promise<YotoUserIconsResponse>}
388
+ */
152
389
  getUserIcons({ requestOptions }?: {
153
390
  requestOptions?: ({
154
391
  dispatcher?: import("undici").Dispatcher;
155
392
  } & Omit<import("undici").Dispatcher.RequestOptions<unknown>, "origin" | "path" | "method"> & Partial<Pick<import("undici").Dispatcher.RequestOptions<null>, "method">>) | undefined;
156
393
  }): Promise<Icons.YotoUserIconsResponse>;
394
+ /**
395
+ * Upload a custom icon
396
+ * @see https://yoto.dev/api/uploadicon/
397
+ * @param {object} params
398
+ * @param {Buffer} params.imageData - Image binary data
399
+ * @param {boolean} [params.autoConvert=true] - Auto-convert to proper format
400
+ * @param {string} [params.filename] - Optional filename
401
+ * @param {RequestOptions} [params.requestOptions] - Request options that override defaults
402
+ * @returns {Promise<YotoUploadIconResponse>}
403
+ */
157
404
  uploadIcon({ imageData, autoConvert, filename, requestOptions }: {
158
405
  imageData: Buffer;
159
406
  autoConvert?: boolean | undefined;
@@ -162,6 +409,15 @@ export class YotoClient {
162
409
  dispatcher?: import("undici").Dispatcher;
163
410
  } & Omit<import("undici").Dispatcher.RequestOptions<unknown>, "origin" | "path" | "method"> & Partial<Pick<import("undici").Dispatcher.RequestOptions<null>, "method">>) | undefined;
164
411
  }): Promise<Icons.YotoUploadIconResponse>;
412
+ /**
413
+ * Get audio upload URL
414
+ * @see https://yoto.dev/api/getaudiouploadurl/
415
+ * @param {object} params
416
+ * @param {string} params.sha256 - SHA256 hash of audio file
417
+ * @param {string} [params.filename] - Optional filename
418
+ * @param {RequestOptions} [params.requestOptions] - Request options that override defaults
419
+ * @returns {Promise<YotoAudioUploadUrlResponse>}
420
+ */
165
421
  getAudioUploadUrl({ sha256, filename, requestOptions }: {
166
422
  sha256: string;
167
423
  filename?: string | undefined;
@@ -169,6 +425,18 @@ export class YotoClient {
169
425
  dispatcher?: import("undici").Dispatcher;
170
426
  } & Omit<import("undici").Dispatcher.RequestOptions<unknown>, "origin" | "path" | "method"> & Partial<Pick<import("undici").Dispatcher.RequestOptions<null>, "method">>) | undefined;
171
427
  }): Promise<Media.YotoAudioUploadUrlResponse>;
428
+ /**
429
+ * Upload a cover image
430
+ * @see https://yoto.dev/api/uploadcoverimage/
431
+ * @param {object} params
432
+ * @param {Buffer} [params.imageData] - Image binary data
433
+ * @param {string} [params.imageUrl] - URL to image
434
+ * @param {boolean} [params.autoConvert] - Auto-convert to proper format
435
+ * @param {YotoCoverType} [params.coverType] - Cover image type
436
+ * @param {string} [params.filename] - Optional filename
437
+ * @param {RequestOptions} [params.requestOptions] - Request options that override defaults
438
+ * @returns {Promise<YotoUploadCoverImageResponse>}
439
+ */
172
440
  uploadCoverImage({ imageData, imageUrl, autoConvert, coverType, filename, requestOptions }: {
173
441
  imageData?: Buffer<ArrayBufferLike> | undefined;
174
442
  imageUrl?: string | undefined;
@@ -179,6 +447,64 @@ export class YotoClient {
179
447
  dispatcher?: import("undici").Dispatcher;
180
448
  } & Omit<import("undici").Dispatcher.RequestOptions<unknown>, "origin" | "path" | "method"> & Partial<Pick<import("undici").Dispatcher.RequestOptions<null>, "method">>) | undefined;
181
449
  }): Promise<Media.YotoUploadCoverImageResponse>;
450
+ /**
451
+ * Create an MQTT client for a specific device
452
+ *
453
+ * The MQTT client provides real-time communication with Yoto devices:
454
+ * - Subscribe to device events (playback, volume, card changes)
455
+ * - Subscribe to device status (battery, temperature, network)
456
+ * - Send commands (volume, card playback, ambient lights, etc.)
457
+ *
458
+ * @see https://yoto.dev/players-mqtt/
459
+ * @param {object} params
460
+ * @param {string} params.deviceId - The device ID to connect to
461
+ * @param {object} [params.options] - MQTT client options
462
+ * @param {boolean} [params.options.autoSubscribe=true] - Auto-subscribe to device topics on connect
463
+ * @returns {Promise<YotoMqttClient>} MQTT client instance
464
+ *
465
+ * @example
466
+ * // Create YotoClient with token refresh callback
467
+ * const client = new YotoClient({
468
+ * clientId: 'your-client-id',
469
+ * refreshToken: 'your-refresh-token',
470
+ * accessToken: 'your-access-token',
471
+ * onTokenRefresh: async (event) => {
472
+ * // Save tokens to file/database
473
+ * await saveTokens(event.accessToken, event.refreshToken)
474
+ * }
475
+ * })
476
+ *
477
+ * // Get an online device
478
+ * const devices = await client.getDevices()
479
+ * const device = devices.devices.find(d => d.online)
480
+ *
481
+ * // Create MQTT client for the device
482
+ * const mqttClient = await client.createMqttClient({ deviceId: device.deviceId })
483
+ *
484
+ * // Setup event handlers
485
+ * mqttClient.on('events', (message) => {
486
+ * console.log('Playback event:', message.playbackStatus)
487
+ * console.log('Volume:', message.volume)
488
+ * })
489
+ *
490
+ * mqttClient.on('status', (message) => {
491
+ * console.log('Battery:', message.status.batteryLevel)
492
+ * console.log('Temperature:', message.status.temp)
493
+ * })
494
+ *
495
+ * mqttClient.on('response', (message) => {
496
+ * console.log('Command acknowledged:', message.status)
497
+ * })
498
+ *
499
+ * // Connect and send commands
500
+ * await mqttClient.connect()
501
+ * await mqttClient.requestStatus()
502
+ * await mqttClient.setVolume(50)
503
+ * await mqttClient.startCard({ uri: 'https://yoto.io/cardId123' })
504
+ *
505
+ * // Cleanup
506
+ * await mqttClient.disconnect()
507
+ */
182
508
  createMqttClient({ deviceId, options }: {
183
509
  deviceId: string;
184
510
  options?: {
@@ -188,21 +514,63 @@ export class YotoClient {
188
514
  #private;
189
515
  }
190
516
  export type RefreshSuccessEvent = {
517
+ /**
518
+ * - The OAuth client ID
519
+ */
191
520
  clientId: string;
521
+ /**
522
+ * - The new access token
523
+ */
192
524
  accessToken: string;
525
+ /**
526
+ * - The refresh token (may be updated)
527
+ */
193
528
  refreshToken: string;
529
+ /**
530
+ * - Unix timestamp in seconds when token expires
531
+ */
194
532
  expiresAt: number;
195
533
  };
196
534
  export type YotoClientConstructorOptions = {
535
+ /**
536
+ * - OAuth client ID
537
+ */
197
538
  clientId: string;
539
+ /**
540
+ * - OAuth refresh token
541
+ */
198
542
  refreshToken: string;
543
+ /**
544
+ * - Initial OAuth access token (JWT)
545
+ */
199
546
  accessToken: string;
547
+ /**
548
+ * - **REQUIRED** Callback invoked when tokens are refreshed. You MUST persist these tokens (to file, database, etc.) as the refresh can happen at any time during API calls. The refresh token may be rotated by the auth server. **DO NOT STUB THIS CALLBACK** - always implement proper persistence logic.
549
+ */
200
550
  onTokenRefresh: (event: RefreshSuccessEvent) => void | Promise<void>;
551
+ /**
552
+ * - Seconds before expiration to consider token expired
553
+ */
201
554
  bufferSeconds?: number;
555
+ /**
556
+ * - Optional callback invoked when token refresh starts. Defaults to console.log.
557
+ */
202
558
  onRefreshStart?: () => void | Promise<void>;
559
+ /**
560
+ * - Optional callback invoked when token refresh fails with a transient error. Defaults to console.warn.
561
+ */
203
562
  onRefreshError?: (error: Error) => void | Promise<void>;
563
+ /**
564
+ * - Optional callback invoked when refresh token is permanently invalid. Defaults to console.error.
565
+ */
204
566
  onInvalid?: (error: Error) => void | Promise<void>;
567
+ /**
568
+ * - Optional user agent string to identify your application
569
+ */
205
570
  userAgent?: string;
571
+ /**
572
+ * - Default undici request options for all requests (dispatcher, timeouts, etc.)
573
+ */
206
574
  defaultRequestOptions?: RequestOptions;
207
575
  };
208
576
  import { RefreshableToken } from './lib/token.js';