@ctrl/plex 1.5.3 → 2.0.0

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 (68) hide show
  1. package/README.md +3 -2
  2. package/dist/src/alert.d.ts +12 -0
  3. package/dist/src/alert.js +29 -0
  4. package/dist/src/alert.types.d.ts +59 -0
  5. package/dist/src/alert.types.js +1 -0
  6. package/dist/{base → src/base}/partialPlexObject.d.ts +18 -12
  7. package/dist/{base → src/base}/partialPlexObject.js +29 -23
  8. package/dist/{base → src/base}/playable.d.ts +2 -2
  9. package/dist/src/base/playable.js +8 -0
  10. package/dist/{base → src/base}/plexObject.d.ts +8 -1
  11. package/dist/{base → src/base}/plexObject.js +21 -18
  12. package/dist/{baseFunctionality.d.ts → src/baseFunctionality.d.ts} +17 -1
  13. package/dist/{baseFunctionality.js → src/baseFunctionality.js} +7 -15
  14. package/dist/{client.d.ts → src/client.d.ts} +2 -2
  15. package/dist/{client.js → src/client.js} +12 -20
  16. package/dist/src/client.types.js +1 -0
  17. package/dist/src/config.js +35 -0
  18. package/dist/src/exceptions.d.ts +20 -0
  19. package/dist/src/exceptions.js +40 -0
  20. package/dist/src/index.d.ts +12 -0
  21. package/dist/src/index.js +11 -0
  22. package/dist/{library.d.ts → src/library.d.ts} +207 -21
  23. package/dist/{library.js → src/library.js} +348 -132
  24. package/dist/{library.types.d.ts → src/library.types.d.ts} +59 -1
  25. package/dist/src/library.types.js +1 -0
  26. package/dist/{media.d.ts → src/media.d.ts} +16 -4
  27. package/dist/{media.js → src/media.js} +42 -49
  28. package/dist/src/media.types.d.ts +7 -0
  29. package/dist/src/media.types.js +1 -0
  30. package/dist/{myplex.d.ts → src/myplex.d.ts} +16 -6
  31. package/dist/{myplex.js → src/myplex.js} +71 -57
  32. package/dist/src/myplex.types.js +10 -0
  33. package/dist/src/playlist.d.ts +75 -0
  34. package/dist/src/playlist.js +142 -0
  35. package/dist/src/playlist.types.d.ts +17 -0
  36. package/dist/src/playlist.types.js +1 -0
  37. package/dist/{search.d.ts → src/search.d.ts} +4 -3
  38. package/dist/{search.js → src/search.js} +13 -19
  39. package/dist/src/search.types.js +1 -0
  40. package/dist/{server.d.ts → src/server.d.ts} +22 -10
  41. package/dist/{server.js → src/server.js} +65 -50
  42. package/dist/src/server.types.js +1 -0
  43. package/dist/src/settings.d.ts +79 -0
  44. package/dist/src/settings.js +160 -0
  45. package/dist/{util.d.ts → src/util.d.ts} +2 -1
  46. package/dist/{util.js → src/util.js} +8 -12
  47. package/dist/{video.d.ts → src/video.d.ts} +38 -60
  48. package/dist/{video.js → src/video.js} +109 -92
  49. package/dist/{video.types.d.ts → src/video.types.d.ts} +1 -1
  50. package/dist/src/video.types.js +6 -0
  51. package/package.json +46 -44
  52. package/dist/base/playable.js +0 -12
  53. package/dist/client.types.js +0 -2
  54. package/dist/config.js +0 -41
  55. package/dist/index.d.ts +0 -8
  56. package/dist/index.js +0 -23
  57. package/dist/library.types.js +0 -2
  58. package/dist/myplex.types.js +0 -13
  59. package/dist/playlist.d.ts +0 -7
  60. package/dist/playlist.js +0 -19
  61. package/dist/search.types.js +0 -2
  62. package/dist/server.types.js +0 -2
  63. package/dist/video.types.js +0 -9
  64. /package/dist/{client.types.d.ts → src/client.types.d.ts} +0 -0
  65. /package/dist/{config.d.ts → src/config.d.ts} +0 -0
  66. /package/dist/{myplex.types.d.ts → src/myplex.types.d.ts} +0 -0
  67. /package/dist/{search.types.d.ts → src/search.types.d.ts} +0 -0
  68. /package/dist/{server.types.d.ts → src/server.types.d.ts} +0 -0
@@ -0,0 +1,20 @@
1
+ export declare class BadRequest extends Error {
2
+ message: string;
3
+ constructor(message: string);
4
+ }
5
+ export declare class NotFound extends Error {
6
+ message: string;
7
+ constructor(message: string);
8
+ }
9
+ export declare class UnknownType extends Error {
10
+ message: string;
11
+ constructor(message: string);
12
+ }
13
+ export declare class Unsupported extends Error {
14
+ message: string;
15
+ constructor(message: string);
16
+ }
17
+ export declare class Unauthorized extends Error {
18
+ message: string;
19
+ constructor(message: string);
20
+ }
@@ -0,0 +1,40 @@
1
+ export class BadRequest extends Error {
2
+ constructor(message) {
3
+ super(message);
4
+ this.message = 'An invalid request, generally a user error.';
5
+ this.name = 'BadRequest';
6
+ this.message = message;
7
+ }
8
+ }
9
+ export class NotFound extends Error {
10
+ constructor(message) {
11
+ super(message);
12
+ this.message = 'Request media item or device is not found.';
13
+ this.name = 'NotFound';
14
+ this.message = message;
15
+ }
16
+ }
17
+ export class UnknownType extends Error {
18
+ constructor(message) {
19
+ super(message);
20
+ this.message = 'Unknown library type.';
21
+ this.name = 'UnknownType';
22
+ this.message = message;
23
+ }
24
+ }
25
+ export class Unsupported extends Error {
26
+ constructor(message) {
27
+ super(message);
28
+ this.message = 'Unsupported client request.';
29
+ this.name = 'Unsupported';
30
+ this.message = message;
31
+ }
32
+ }
33
+ export class Unauthorized extends Error {
34
+ constructor(message) {
35
+ super(message);
36
+ this.message = 'Invalid username or password.';
37
+ this.name = 'Unauthorized';
38
+ this.message = message;
39
+ }
40
+ }
@@ -0,0 +1,12 @@
1
+ export * from './alert.js';
2
+ export type { AlertTypes } from './alert.types.js';
3
+ export * from './client.js';
4
+ export * from './exceptions.js';
5
+ export * from './library.js';
6
+ export * from './media.js';
7
+ export * from './myplex.js';
8
+ export * from './playlist.js';
9
+ export * from './server.js';
10
+ export * from './video.js';
11
+ export { X_PLEX_IDENTIFIER } from './config.js';
12
+ export { SearchResult, Agent, SEARCHTYPES } from './search.js';
@@ -0,0 +1,11 @@
1
+ export * from './alert.js';
2
+ export * from './client.js';
3
+ export * from './exceptions.js';
4
+ export * from './library.js';
5
+ export * from './media.js';
6
+ export * from './myplex.js';
7
+ export * from './playlist.js';
8
+ export * from './server.js';
9
+ export * from './video.js';
10
+ export { X_PLEX_IDENTIFIER } from './config.js';
11
+ export { SearchResult, Agent, SEARCHTYPES } from './search.js';
@@ -1,13 +1,13 @@
1
1
  import { Class } from 'type-fest';
2
- import type { PlexServer } from './server';
3
- import { LibraryRootResponse, SectionsDirectory, Location, CollectionData } from './library.types';
4
- import { PlexObject } from './base/plexObject';
5
- import { Movie, VideoType, Show } from './video';
6
- import { SearchResult } from './search.types';
7
- import { Agent, SEARCHTYPES } from './search';
8
- import { Playlist } from './playlist';
9
- import { PartialPlexObject } from './base/partialPlexObject';
10
- export declare type Section = MovieSection | ShowSection;
2
+ import { PartialPlexObject } from './base/partialPlexObject.js';
3
+ import { PlexObject } from './base/plexObject.js';
4
+ import { CollectionData, LibraryRootResponse, Location, SectionsDirectory } from './library.types.js';
5
+ import { Playlist } from './playlist.js';
6
+ import { Agent, SEARCHTYPES } from './search.js';
7
+ import { SearchResult } from './search.types.js';
8
+ import type { PlexServer } from './server.js';
9
+ import { Movie, Show, VideoType } from './video.js';
10
+ export type Section = MovieSection | ShowSection;
11
11
  export declare class Library {
12
12
  private readonly server;
13
13
  static key: string;
@@ -186,8 +186,38 @@ export declare class Library {
186
186
  * library, you may like to optimize the database.
187
187
  */
188
188
  optimize(): Promise<void>;
189
+ /**
190
+ * Validates a filter field and values are available as a custom filter for the library.
191
+ * Returns the validated field and values as a URL encoded parameter string.
192
+ */
193
+ /**
194
+ * Returns the validated and formatted search query API key
195
+ * (``/library/sections/<sectionKey>/all?<params>``).
196
+ */
189
197
  protected _loadData(data: LibraryRootResponse): void;
190
198
  }
199
+ type Libtype = keyof typeof SEARCHTYPES;
200
+ interface SearchArgs {
201
+ [key: string]: number | string | boolean | string[];
202
+ /** General string query to search for. Partial string matches are allowed. */
203
+ title: string;
204
+ /** A string of comma separated sort fields or a list of sort fields in the format ``column:dir``. */
205
+ sort: string | string[];
206
+ /** Only return the specified number of results. */
207
+ maxresults: number;
208
+ /** Default 0 */
209
+ container_start: number;
210
+ /** Default 100 (X_PLEX_CONTAINER_SIZE) */
211
+ container_size: number;
212
+ /** Limit the number of results from the filter. */
213
+ limit: number;
214
+ /**
215
+ * Return results of a specific type (movie, show, season, episode,
216
+ * artist, album, track, photoalbum, photo, collection) (e.g. ``libtype='movie'`` will only
217
+ * return {@link Movie} objects)
218
+ */
219
+ libtype: Libtype;
220
+ }
191
221
  /**
192
222
  * Base class for a single library section.
193
223
  */
@@ -205,8 +235,6 @@ export declare abstract class LibrarySection<SectionVideoType = VideoType> exten
205
235
  composite: string;
206
236
  /** Unknown */
207
237
  filters: boolean;
208
- /** Key (or ID) of this library section. */
209
- key: string;
210
238
  /** Language represented in this section (en, xn, etc). */
211
239
  language: string;
212
240
  /** Paths on disk where section content is stored. */
@@ -230,6 +258,8 @@ export declare abstract class LibrarySection<SectionVideoType = VideoType> exten
230
258
  uuid: string;
231
259
  CONTENT_TYPE: string;
232
260
  readonly VIDEO_TYPE: Class<SectionVideoType>;
261
+ _filterTypes?: FilteringType[];
262
+ _fieldTypes?: FilteringFieldType[];
233
263
  all(sort?: string): Promise<any[]>;
234
264
  agents(): Promise<Agent[]>;
235
265
  /**
@@ -238,16 +268,51 @@ export declare abstract class LibrarySection<SectionVideoType = VideoType> exten
238
268
  */
239
269
  get(title: string): Promise<SectionVideoType>;
240
270
  /**
241
- * Searching within a library section is much more powerful. It seems certain
242
- * attributes on the media objects can be targeted to filter this search down
243
- * a bit, but I havent found the documentation for it.
271
+ * Returns the media item with the specified external IMDB, TMDB, or TVDB ID.
272
+ * Note: This search uses a PlexAPI operator so performance may be slow. All items from the
273
+ * entire Plex library need to be retrieved for each guid search. It is recommended to create
274
+ * your own lookup dictionary if you are searching for a lot of external guids.
275
+ *
276
+ * @param guid The external guid of the item to return.
277
+ * Examples: IMDB ``imdb://tt0944947``, TMDB ``tmdb://1399``, TVDB ``tvdb://121361``.
278
+ *
279
+ *
280
+ * Example:
281
+ *
282
+ * .. code-block:: python
283
+ *
284
+ * # This will retrieve all items in the entire library 3 times
285
+ * result1 = library.getGuid('imdb://tt0944947')
286
+ * result2 = library.getGuid('tmdb://1399')
287
+ * result3 = library.getGuid('tvdb://121361')
288
+ *
289
+ * # This will only retrieve all items in the library once to create a lookup dictionary
290
+ * guidLookup = {guid.id: item for item in library.all() for guid in item.guids}
291
+ * result1 = guidLookup['imdb://tt0944947']
292
+ * result2 = guidLookup['tmdb://1399']
293
+ * result3 = guidLookup['tvdb://121361']
294
+ */
295
+ getGuid(guid: string): Promise<SectionVideoType>;
296
+ /**
297
+ * Returns the Plex Web URL for the library.
298
+ *
299
+ * @param base The base URL before the fragment (``#!``).
300
+ * Default is https://app.plex.tv/desktop.
301
+ * @param tab The library tab (recommended, library, collections, playlists, timeline).
302
+ * @param key A hub key.
303
+ */
304
+ getWebURL(base?: string, tab?: string, key?: string): string;
305
+ /**
306
+ * Search the library. The http requests will be batched in container_size. If you are only looking for the
307
+ * first <num> results, it would be wise to set the maxresults option to that amount so the search doesn't iterate
308
+ * over all results on the server.
244
309
  *
245
310
  * Example: "studio=Comedy%20Central" or "year=1999" "title=Kung Fu" all work. Other items
246
311
  * such as actor=<id> seem to work, but require you already know the id of the actor.
247
312
  * TLDR: This is untested but seems to work. Use library section search when you can.
248
313
  * @param args Search using a number of different attributes
249
314
  */
250
- search<T = SectionVideoType>(args?: Record<string, number | string | boolean>, libtype?: keyof typeof SEARCHTYPES, Cls?: any): Promise<T[]>;
315
+ search<T = SectionVideoType>(args?: Partial<SearchArgs>, Cls?: any): Promise<T[]>;
251
316
  /**
252
317
  * Run an analysis on all of the items in this library section.
253
318
  * See :func:`~plexapi.base.PlexPartialObject.analyze` for more details.
@@ -297,7 +362,37 @@ export declare abstract class LibrarySection<SectionVideoType = VideoType> exten
297
362
  * Returns a list of available Folders for this library section.
298
363
  */
299
364
  folders(): Promise<Folder[]>;
365
+ genres(): Promise<FilterChoice[]>;
366
+ /**
367
+ * Returns a list of available {@link FilteringFields} for a specified libtype.
368
+ * This is the list of options in the custom filter dropdown menu
369
+ */
370
+ listFields(libtype?: Libtype): Promise<FilteringField[]>;
371
+ getFilterType(libtype?: Libtype): Promise<FilteringType>;
372
+ /**
373
+ * @param fieldType The data type for the field (tag, integer, string, boolean, date,
374
+ subtitleLanguage, audioLanguage, resolution).
375
+ */
376
+ getFieldType(fieldType: string): Promise<FilteringFieldType>;
377
+ /**
378
+ * @param libtype The library type to filter (movie, show, season, episode,
379
+ * artist, album, track, photoalbum, photo, collection).
380
+ *
381
+ * @example
382
+ * ```ts
383
+ * const availableFilters = (await library.listFilters()).map(f => f.filter)
384
+ * ```
385
+ */
386
+ listFilters(libtype?: Libtype): Promise<FilteringFilter[]>;
387
+ /**
388
+ * @param fieldType The data type for the field (tag, integer, string, boolean, date,
389
+ * subtitleLanguage, audioLanguage, resolution).
390
+ */
391
+ listOperators(fieldType: string): Promise<FilteringOperator[]>;
392
+ filterTypes(): Promise<FilteringType[]>;
393
+ fieldTypes(): Promise<FilteringFieldType[]>;
300
394
  protected _loadData(data: SectionsDirectory): void;
395
+ private _loadFilters;
301
396
  }
302
397
  export declare class MovieSection extends LibrarySection<Movie> {
303
398
  static TYPE: string;
@@ -339,7 +434,6 @@ export declare class Hub extends PlexObject {
339
434
  * Represents a Folder inside a library.
340
435
  */
341
436
  export declare class Folder extends PlexObject {
342
- key: string;
343
437
  title: string;
344
438
  /**
345
439
  * Returns a list of available Folders for this folder.
@@ -351,12 +445,8 @@ export declare class Folder extends PlexObject {
351
445
  export declare class Collections<CollectionVideoType = VideoType> extends PartialPlexObject {
352
446
  static TAG: string;
353
447
  TYPE: string;
354
- ratingKey: string;
355
448
  guid: string;
356
- type: string;
357
- title: string;
358
449
  librarySectionTitle: string;
359
- librarySectionID: number;
360
450
  librarySectionKey: string;
361
451
  contentRating: string;
362
452
  subtype: string;
@@ -375,6 +465,102 @@ export declare class Collections<CollectionVideoType = VideoType> extends Partia
375
465
  * Returns a list of all items in the collection.
376
466
  */
377
467
  items(): Promise<CollectionVideoType[]>;
378
- protected _loadData(data: CollectionData): void;
379
468
  protected _loadFullData(data: any): void;
469
+ protected _loadData(data: CollectionData): void;
470
+ }
471
+ export declare class FilterChoice extends PlexObject {
472
+ static TAG: string;
473
+ /**
474
+ * API URL path to quickly list all items with this filter choice.
475
+ * (/library/sections/<section>/all?genre=<key>)
476
+ */
477
+ fastKey: string;
478
+ /** Thumbnail URL for the filter choice. */
479
+ thumb?: string;
480
+ /** The title of the filter choice. */
481
+ title: string;
482
+ /** The filter type (genre, contentRating, etc). */
483
+ type: string;
484
+ protected _loadData(data: CollectionData): void;
485
+ }
486
+ export declare class FilteringType extends PlexObject {
487
+ static TAG: string;
488
+ /** The libtype for the filter. */
489
+ type: string;
490
+ /** True if this filter type is currently active. */
491
+ active: boolean;
492
+ fields: FilteringField[];
493
+ filters: FilteringFilter[];
494
+ /** List of sort objects. */
495
+ sorts: any;
496
+ /** The title for the libtype filter. */
497
+ title: string;
498
+ _loadData(data: any): void;
499
+ }
500
+ /**
501
+ * Represents a single Filter object for a {@link FilteringType}
502
+ */
503
+ export declare class FilteringFilter extends PlexObject {
504
+ static TAG: string;
505
+ /** The key for the filter. */
506
+ filter: string;
507
+ /** The :class:`~plexapi.library.FilteringFieldType` type (string, boolean, integer, date, etc). */
508
+ filterType: string;
509
+ /** The title of the filter. */
510
+ title: string;
511
+ /** 'filter' */
512
+ type: string;
513
+ _loadData(data: any): void;
514
+ }
515
+ /**
516
+ * Represents a single Sort object for a {@link FilteringType}
517
+ */
518
+ export declare class FilteringSort extends PlexObject {
519
+ static TAG: string;
520
+ /** True if the sort is currently active. */
521
+ active: boolean;
522
+ /** The currently active sorting direction. */
523
+ activeDirection: string;
524
+ /** The currently active default sorting direction. */
525
+ default: string;
526
+ /** The default sorting direction. */
527
+ defaultDirection: string;
528
+ /** The URL key for sorting with desc. */
529
+ descKey: string;
530
+ /** API URL path for first character endpoint. */
531
+ firstCharacterKey: string;
532
+ /** The title of the sorting. */
533
+ title: string;
534
+ _loadData(data: any): void;
535
+ }
536
+ /**
537
+ * Represents a single Field object for a {@link FilteringType}
538
+ */
539
+ export declare class FilteringField extends PlexObject {
540
+ static TAG: string;
541
+ type: string;
542
+ title: string;
543
+ /** The subtype of the filter (decade, rating, etc) */
544
+ subType: string;
545
+ _loadData(data: any): void;
546
+ }
547
+ /**
548
+ * Represents a single FieldType for library filtering.
549
+ */
550
+ export declare class FilteringFieldType extends PlexObject {
551
+ static TAG: string;
552
+ /** The filtering data type (string, boolean, integer, date, etc). */
553
+ type: string;
554
+ operators: FilteringOperator[];
555
+ _loadData(data: any): void;
556
+ }
557
+ /**
558
+ * Represents a single FilterChoice for library filtering.
559
+ */
560
+ export declare class FilteringOperator extends PlexObject {
561
+ static TAG: string;
562
+ /** The libtype for the filter. */
563
+ type: string;
564
+ _loadData(data: any): void;
380
565
  }
566
+ export {};