@omelhorsite/sdk 0.3.0 → 0.4.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.
- package/README.md +112 -130
- package/dist/index.js +1045 -1242
- package/dist/types/index.d.ts +1 -0
- package/dist/types/internal/attachments.d.ts +17 -0
- package/dist/types/internal/helpers.d.ts +9 -0
- package/dist/types/listing.d.ts +90 -0
- package/dist/types/resources/account.d.ts +5 -2
- package/dist/types/resources/admin/authorizedApplications.d.ts +133 -0
- package/dist/types/resources/admin/chests.d.ts +51 -0
- package/dist/types/resources/admin/eventAlerts.d.ts +60 -0
- package/dist/types/resources/admin/identities.d.ts +99 -0
- package/dist/types/resources/admin/index.d.ts +77 -0
- package/dist/types/resources/admin/jobs.d.ts +97 -0
- package/dist/types/resources/admin/myOauthApplications.d.ts +282 -0
- package/dist/types/resources/admin/notepads.d.ts +49 -0
- package/dist/types/resources/admin/oauthApplications.d.ts +309 -0
- package/dist/types/resources/admin/quotas.d.ts +114 -0
- package/dist/types/resources/admin/shortLinks.d.ts +201 -0
- package/dist/types/resources/admin/types.d.ts +222 -0
- package/dist/types/resources/admin/vocalSeparations.d.ts +98 -0
- package/dist/types/resources/admin.d.ts +17 -13
- package/dist/types/resources/auth/sessions.d.ts +6 -9
- package/dist/types/resources/content/analysis.d.ts +62 -0
- package/dist/types/resources/content/blogs.d.ts +471 -0
- package/dist/types/resources/content/feedbacks.d.ts +263 -0
- package/dist/types/resources/content/index.d.ts +52 -0
- package/dist/types/resources/content/intel/articles.d.ts +230 -0
- package/dist/types/resources/content/intel/config.d.ts +135 -0
- package/dist/types/resources/content/intel/index.d.ts +53 -0
- package/dist/types/resources/content/intel/items.d.ts +91 -0
- package/dist/types/resources/content/intel/reports.d.ts +108 -0
- package/dist/types/resources/content/intel/scripts.d.ts +152 -0
- package/dist/types/resources/content/intel/sources.d.ts +236 -0
- package/dist/types/resources/content/intel/stats.d.ts +105 -0
- package/dist/types/resources/content/intel/types.d.ts +86 -0
- package/dist/types/resources/content/jokes.d.ts +93 -0
- package/dist/types/resources/content/notifications.d.ts +147 -0
- package/dist/types/resources/content/serviceUsages.d.ts +73 -0
- package/dist/types/resources/content/servicesStatus.d.ts +194 -0
- package/dist/types/resources/content/siteConfig.d.ts +43 -0
- package/dist/types/resources/content/spaceInvaders.d.ts +154 -0
- package/dist/types/resources/content.d.ts +41 -236
- package/dist/types/resources/jobs.d.ts +7 -4
- package/dist/types/resources/library/annotations.d.ts +162 -0
- package/dist/types/resources/library/books.d.ts +534 -0
- package/dist/types/resources/library/chat.d.ts +259 -0
- package/dist/types/resources/library/index.d.ts +39 -0
- package/dist/types/resources/library/shelves.d.ts +237 -0
- package/dist/types/resources/library/types.d.ts +120 -0
- package/dist/types/resources/library.d.ts +20 -22
- package/dist/types/resources/movies/addons.d.ts +388 -0
- package/dist/types/resources/movies/collections.d.ts +352 -0
- package/dist/types/resources/movies/index.d.ts +29 -0
- package/dist/types/resources/movies/types.d.ts +50 -0
- package/dist/types/resources/movies/watchProgress.d.ts +277 -0
- package/dist/types/resources/movies.d.ts +27 -53
- package/dist/types/resources/music/artists.d.ts +3 -1
- package/dist/types/resources/music/imports.d.ts +9 -8
- package/dist/types/resources/music/playlists.d.ts +8 -7
- package/dist/types/resources/music/songs.d.ts +5 -21
- package/dist/types/resources/shortLinks.d.ts +5 -2
- package/dist/types/resources/social/groupChats.d.ts +458 -0
- package/dist/types/resources/social/index.d.ts +19 -0
- package/dist/types/resources/social/messages.d.ts +424 -0
- package/dist/types/resources/social/relationships.d.ts +322 -0
- package/dist/types/resources/social/types.d.ts +37 -0
- package/dist/types/resources/social.d.ts +21 -3
- package/dist/types/resources/storage.d.ts +24 -6
- package/dist/types/resources/tickets.d.ts +19 -10
- package/package.json +1 -1
|
@@ -0,0 +1,352 @@
|
|
|
1
|
+
/** The `movies.collections` area: the favourites row, the hand-made lists, and the titles filed into them. */
|
|
2
|
+
import type { ApiClient } from "../../http";
|
|
3
|
+
import { Resource } from "../../http";
|
|
4
|
+
import type { ListParams } from "../../listing";
|
|
5
|
+
import type { BaseRecord, Id, Paginated, RequestOptions } from "../../types";
|
|
6
|
+
import type { MovieType } from "./types";
|
|
7
|
+
/** The manual kind: a collection the user created and may rename or delete. */
|
|
8
|
+
export declare const MOVIE_COLLECTION_MANUAL_KIND = "manual";
|
|
9
|
+
/**
|
|
10
|
+
* The one system kind. There is exactly one favourites collection per user,
|
|
11
|
+
* enforced by a partial unique index on `(user_id, kind) WHERE kind <> 'manual'`.
|
|
12
|
+
*/
|
|
13
|
+
export declare const MOVIE_COLLECTION_FAVORITES_KIND = "favorites";
|
|
14
|
+
/** Every kind the server allows. Anything else is a `400`. */
|
|
15
|
+
export declare const MOVIE_COLLECTION_KINDS: readonly ["manual", "favorites"];
|
|
16
|
+
/** One of {@link MOVIE_COLLECTION_KINDS}. */
|
|
17
|
+
export type MovieCollectionKind = (typeof MOVIE_COLLECTION_KINDS)[number];
|
|
18
|
+
/**
|
|
19
|
+
* A user's list of titles: the auto-created favourites row, or a playlist they
|
|
20
|
+
* made by hand.
|
|
21
|
+
*/
|
|
22
|
+
export interface MovieCollection extends BaseRecord {
|
|
23
|
+
readonly user_id: Id;
|
|
24
|
+
readonly name: string;
|
|
25
|
+
readonly kind: MovieCollectionKind;
|
|
26
|
+
/**
|
|
27
|
+
* Sort key inside the sidebar. Favourites is minted at `-1` so it sorts
|
|
28
|
+
* first; manual collections start at `max + 1`.
|
|
29
|
+
*
|
|
30
|
+
* The index has NO order of its own, so this only sorts if you ask for it -
|
|
31
|
+
* pass `order: "position:asc"`.
|
|
32
|
+
*/
|
|
33
|
+
readonly position: number;
|
|
34
|
+
/**
|
|
35
|
+
* `true` for the favourites row. Mirrors `kind != "manual"`, so it is `true`
|
|
36
|
+
* for any future system kind too. Use {@link isSystemMovieCollection}.
|
|
37
|
+
*/
|
|
38
|
+
readonly system: boolean;
|
|
39
|
+
/**
|
|
40
|
+
* How many items are in it. Exact - but a snapshot, and adding an item does
|
|
41
|
+
* not refresh the collection row you are holding.
|
|
42
|
+
*/
|
|
43
|
+
readonly items_count: number;
|
|
44
|
+
}
|
|
45
|
+
/** One title filed into a collection. */
|
|
46
|
+
export interface MovieCollectionItem extends BaseRecord {
|
|
47
|
+
readonly movie_collection_id: Id;
|
|
48
|
+
/** `"movie"`, `"series"`, whatever the addon called it. */
|
|
49
|
+
readonly movie_type: MovieType;
|
|
50
|
+
/** The addon's own id for the title, e.g. an IMDb id. Not a database id. */
|
|
51
|
+
readonly movie_id: string;
|
|
52
|
+
/** Denormalised metadata, so a grid renders without hitting the addon. */
|
|
53
|
+
readonly name: string | null;
|
|
54
|
+
readonly poster: string | null;
|
|
55
|
+
readonly background: string | null;
|
|
56
|
+
readonly release_info: string | null;
|
|
57
|
+
/** Sort key inside the collection, dense from `0`. See {@link MovieCollectionsNamespace.reorder}. */
|
|
58
|
+
readonly position: number;
|
|
59
|
+
}
|
|
60
|
+
/** Arguments for {@link MovieCollectionsNamespace.create}. */
|
|
61
|
+
export interface CreateMovieCollectionInput {
|
|
62
|
+
/**
|
|
63
|
+
* Required. It is the ONLY field create reads: the owner is always the
|
|
64
|
+
* caller, `kind` is forced to `"manual"` and `position` is computed as
|
|
65
|
+
* `max(position) + 1`, so passing a kind or a position is silently ignored
|
|
66
|
+
* rather than rejected. There is no way to mint a second system collection.
|
|
67
|
+
*/
|
|
68
|
+
readonly name: string;
|
|
69
|
+
}
|
|
70
|
+
/** Arguments for {@link MovieCollectionsNamespace.update}. */
|
|
71
|
+
export interface UpdateMovieCollectionInput {
|
|
72
|
+
readonly name?: string;
|
|
73
|
+
/**
|
|
74
|
+
* Sidebar order. Nothing normalises it: two collections can hold the same
|
|
75
|
+
* position and the server will not complain, so the client owns keeping the
|
|
76
|
+
* sequence sane.
|
|
77
|
+
*/
|
|
78
|
+
readonly position?: number;
|
|
79
|
+
}
|
|
80
|
+
/**
|
|
81
|
+
* Filters for {@link MovieCollectionsNamespace.list}.
|
|
82
|
+
*
|
|
83
|
+
* Allowlist: `id`, `name`, `kind`, `created_at`, `updated_at`. Anything else is
|
|
84
|
+
* `400 "Unknown search filter: ..."`.
|
|
85
|
+
*/
|
|
86
|
+
export interface ListMovieCollectionsParams extends ListParams<(typeof MOVIE_COLLECTION_FILTER_COLUMNS)[number]> {
|
|
87
|
+
/** Exact match, or `IN (...)` when given an array. */
|
|
88
|
+
readonly id?: Id | readonly Id[];
|
|
89
|
+
/**
|
|
90
|
+
* Partial, accent-folded, case-insensitive match - the `LIKE` a search box
|
|
91
|
+
* wants. NOT equality: `"fav"` matches `"Favoritos"`.
|
|
92
|
+
*/
|
|
93
|
+
readonly name?: string;
|
|
94
|
+
/** Exact match. `"favorites"` finds the one system row. */
|
|
95
|
+
readonly kind?: MovieCollectionKind;
|
|
96
|
+
}
|
|
97
|
+
/** Filter columns of `GET /movie_collections`. */
|
|
98
|
+
export declare const MOVIE_COLLECTION_FILTER_COLUMNS: readonly ["id", "name", "kind", "created_at", "updated_at"];
|
|
99
|
+
/** Arguments for {@link MovieCollectionItemsNamespace.create}. */
|
|
100
|
+
export interface CreateMovieCollectionItemInput {
|
|
101
|
+
readonly movie_collection_id: Id;
|
|
102
|
+
readonly movie_type: MovieType;
|
|
103
|
+
/** The addon's id for the title. Required, and part of the uniqueness key. */
|
|
104
|
+
readonly movie_id: string;
|
|
105
|
+
readonly name?: string | null;
|
|
106
|
+
readonly poster?: string | null;
|
|
107
|
+
readonly background?: string | null;
|
|
108
|
+
readonly release_info?: string | null;
|
|
109
|
+
}
|
|
110
|
+
/**
|
|
111
|
+
* Filters for {@link MovieCollectionItemsNamespace.list}.
|
|
112
|
+
*
|
|
113
|
+
* Allowlist: `id`, `movie_collection_id`, `movie_type`, `movie_id`,
|
|
114
|
+
* `position`, `created_at`, `updated_at`.
|
|
115
|
+
*/
|
|
116
|
+
export interface ListMovieCollectionItemsParams extends ListParams<(typeof MOVIE_COLLECTION_ITEM_FILTER_COLUMNS)[number]> {
|
|
117
|
+
/** Exact match, or `IN (...)` when given an array. */
|
|
118
|
+
readonly id?: Id | readonly Id[];
|
|
119
|
+
/**
|
|
120
|
+
* Exact match, or `IN (...)` for several collections at once. Almost always
|
|
121
|
+
* what you want: the bare index returns the items of EVERY collection the
|
|
122
|
+
* caller owns, interleaved.
|
|
123
|
+
*/
|
|
124
|
+
readonly collectionId?: Id | readonly Id[];
|
|
125
|
+
/** Exact match. */
|
|
126
|
+
readonly movieType?: MovieType;
|
|
127
|
+
/** Exact match on the addon's title id. */
|
|
128
|
+
readonly movieId?: string;
|
|
129
|
+
/** Exact match on the sort key. */
|
|
130
|
+
readonly position?: number;
|
|
131
|
+
}
|
|
132
|
+
/** Filter columns of `GET /movie_collection_items`. */
|
|
133
|
+
export declare const MOVIE_COLLECTION_ITEM_FILTER_COLUMNS: readonly ["id", "movie_collection_id", "movie_type", "movie_id", "position", "created_at", "updated_at"];
|
|
134
|
+
/**
|
|
135
|
+
* Whether a collection is the server-managed favourites row.
|
|
136
|
+
*
|
|
137
|
+
* Prefer this over `collection.kind === "favorites"`: the server's own test is
|
|
138
|
+
* `kind != "manual"`, so a future system kind reads as system there and would
|
|
139
|
+
* read as manual in a hand-written equality check. The `system` flag already
|
|
140
|
+
* carries it; this just keeps the test in one place.
|
|
141
|
+
*/
|
|
142
|
+
export declare function isSystemMovieCollection(collection: Pick<MovieCollection, "kind">): boolean;
|
|
143
|
+
/**
|
|
144
|
+
* The `movies.collections.items` namespace: the titles filed into a collection.
|
|
145
|
+
*
|
|
146
|
+
* Index and create and delete; there is no `show` and no `update`. To change a
|
|
147
|
+
* title's stored metadata, {@link create} it again - it upserts.
|
|
148
|
+
*/
|
|
149
|
+
export declare class MovieCollectionItemsNamespace extends Resource {
|
|
150
|
+
/**
|
|
151
|
+
* `GET /movie_collection_items` - items across the caller's collections.
|
|
152
|
+
*
|
|
153
|
+
* **Pass `collectionId` unless you really mean everything.** With no filter
|
|
154
|
+
* this returns the items of EVERY collection the caller owns, and because
|
|
155
|
+
* the default order is `position:asc` they come back interleaved by position
|
|
156
|
+
* rather than grouped by collection - position 0 of each list, then
|
|
157
|
+
* position 1 of each, and so on. Grouping that back together client-side
|
|
158
|
+
* works but reads like a bug when you first see it.
|
|
159
|
+
*
|
|
160
|
+
* `collectionId` accepts an array, which becomes `IN (...)`: one request for
|
|
161
|
+
* the three lists a screen shows.
|
|
162
|
+
*
|
|
163
|
+
* The default order is `position:asc` and it is the useful one, so leave
|
|
164
|
+
* `order` alone unless you want something else. Note that passing `order`
|
|
165
|
+
* REPLACES the default, it does not add to it, so `order: "created_at:desc"`
|
|
166
|
+
* loses the position ordering entirely.
|
|
167
|
+
*
|
|
168
|
+
* @throws {OmsApiError} 400 `"Unknown search filter: ..."` outside the
|
|
169
|
+
* allowlist in {@link ListMovieCollectionItemsParams}.
|
|
170
|
+
*/
|
|
171
|
+
list(params?: ListMovieCollectionItemsParams, options?: RequestOptions): Promise<Paginated<MovieCollectionItem>>;
|
|
172
|
+
/**
|
|
173
|
+
* `POST /movie_collection_items` - adds a title to a collection, or refreshes
|
|
174
|
+
* the one already there. **`201` either way.**
|
|
175
|
+
*
|
|
176
|
+
* Adding the same title twice is a no-op-with-an-update rather than a `400`
|
|
177
|
+
* off the unique index. This is deliberate: the heart button and the "add
|
|
178
|
+
* to list" dialog both fire blind, holding only the collection they already
|
|
179
|
+
* loaded. The upshot is that this call is safe to repeat and safe to fire
|
|
180
|
+
* optimistically.
|
|
181
|
+
*
|
|
182
|
+
* Two consequences worth knowing:
|
|
183
|
+
*
|
|
184
|
+
* - `position` is only computed for a NEW row (`max(position) + 1`, starting
|
|
185
|
+
* at `0`). Re-adding an existing title keeps its place in the list rather
|
|
186
|
+
* than moving it to the end.
|
|
187
|
+
* - the denormalised metadata (`name`, `poster`, `background`,
|
|
188
|
+
* `release_info`) IS overwritten every time, so re-posting is how you
|
|
189
|
+
* refresh a poster that the addon has since changed. Sending `null` for one
|
|
190
|
+
* clears it; omitting the key leaves the stored value alone.
|
|
191
|
+
*
|
|
192
|
+
* A `movie_collection_id` that does not exist, or belongs to somebody else,
|
|
193
|
+
* is `401 "You are not authorized to create this resource"` and NOT a `404`:
|
|
194
|
+
* the ownership check fails the same way for a missing collection as for
|
|
195
|
+
* somebody else's. Do not read that `401` as "the session expired".
|
|
196
|
+
*
|
|
197
|
+
* Adding to the favourites collection is allowed - the system flag blocks
|
|
198
|
+
* renaming, reordering and deleting the COLLECTION, not writing items into
|
|
199
|
+
* it. That is how the heart button works.
|
|
200
|
+
*
|
|
201
|
+
* @throws {OmsError} `invalid_request` when the collection id, type or movie
|
|
202
|
+
* id is blank.
|
|
203
|
+
* @throws {OmsApiError} 400 `"Movie type can't be blank"` /
|
|
204
|
+
* `"Movie can't be blank"`, 401 for a collection that is not yours.
|
|
205
|
+
*/
|
|
206
|
+
create(input: CreateMovieCollectionItemInput, options?: RequestOptions): Promise<MovieCollectionItem>;
|
|
207
|
+
/**
|
|
208
|
+
* `DELETE /movie_collection_items/:id` - `204`, empty body.
|
|
209
|
+
*
|
|
210
|
+
* The id is the ITEM's primary key, not the `movie_id` the addon uses. If
|
|
211
|
+
* all you hold is a title, {@link list} it with `collectionId` and `movieId`
|
|
212
|
+
* first, or keep the item rows the collection screen already loaded.
|
|
213
|
+
*
|
|
214
|
+
* Removing leaves a gap in `position`: nothing renumbers the survivors, and
|
|
215
|
+
* the next {@link create} takes `max + 1`, so positions drift sparse over
|
|
216
|
+
* time. Only {@link MovieCollectionsNamespace.reorder} makes them dense
|
|
217
|
+
* again. Nothing depends on them being dense.
|
|
218
|
+
*
|
|
219
|
+
* @throws {OmsApiError} 404 for an item outside your collections.
|
|
220
|
+
*/
|
|
221
|
+
delete(id: Id, options?: RequestOptions): Promise<void>;
|
|
222
|
+
}
|
|
223
|
+
/**
|
|
224
|
+
* The `movies.collections` namespace: the favourites row plus whatever lists
|
|
225
|
+
* the user built by hand.
|
|
226
|
+
*/
|
|
227
|
+
export declare class MovieCollectionsNamespace extends Resource {
|
|
228
|
+
/** The titles inside a collection. */
|
|
229
|
+
readonly items: MovieCollectionItemsNamespace;
|
|
230
|
+
constructor(http: ApiClient);
|
|
231
|
+
/**
|
|
232
|
+
* `GET /movie_collections` - the caller's collections, each with its
|
|
233
|
+
* `items_count`.
|
|
234
|
+
*
|
|
235
|
+
* **This call has a side effect, and it is the only one that does.**
|
|
236
|
+
* Before anything else it finds or creates the "Favoritos" row (kind
|
|
237
|
+
* `favorites`, position `-1`). The index is the only place that knows the
|
|
238
|
+
* user has opened the movies app, so it is where the row gets minted. Two
|
|
239
|
+
* consequences: a brand new account's first listing WRITES to the database,
|
|
240
|
+
* and there is no other way to make favourites exist - a client that goes
|
|
241
|
+
* straight to the heart button without ever listing has no collection to put
|
|
242
|
+
* the title in. List first.
|
|
243
|
+
*
|
|
244
|
+
* A concurrent second tab racing the same first listing is handled: the
|
|
245
|
+
* partial unique index makes the loser read the winner's row back.
|
|
246
|
+
*
|
|
247
|
+
* `items_count` is exact here and in {@link get}. Neither is a snapshot you
|
|
248
|
+
* can trust after a write.
|
|
249
|
+
*
|
|
250
|
+
* No default order. Pass `order: "position:asc"` to get the sidebar's own
|
|
251
|
+
* order, which puts favourites first by virtue of its `-1`.
|
|
252
|
+
*
|
|
253
|
+
* @throws {OmsApiError} 401 for an anonymous caller, 403 for an OAuth token.
|
|
254
|
+
*/
|
|
255
|
+
list(params?: ListMovieCollectionsParams, options?: RequestOptions): Promise<Paginated<MovieCollection>>;
|
|
256
|
+
/**
|
|
257
|
+
* Reads the caller's favourites collection, creating it if this is the first
|
|
258
|
+
* time they have opened the app.
|
|
259
|
+
*
|
|
260
|
+
* A one-line convenience over {@link list} that exists because "get me the
|
|
261
|
+
* heart list" is the single most common reason to call the index, and
|
|
262
|
+
* because doing it by hand invites filtering on `kind` client-side after a
|
|
263
|
+
* listing that may have been paged.
|
|
264
|
+
*
|
|
265
|
+
* Resolves to `null` only if the server somehow answered without the row,
|
|
266
|
+
* which should not happen - the listing mints it.
|
|
267
|
+
*/
|
|
268
|
+
favorites(options?: RequestOptions): Promise<MovieCollection | null>;
|
|
269
|
+
/**
|
|
270
|
+
* `GET /movie_collections/:id` - one collection.
|
|
271
|
+
*
|
|
272
|
+
* The only `show` route in this whole namespace. Its payload is
|
|
273
|
+
* byte-identical to one row of the index: `show` is not a richer payload,
|
|
274
|
+
* only a single-row one.
|
|
275
|
+
*
|
|
276
|
+
* Unlike {@link list} it does NOT mint the favourites row.
|
|
277
|
+
*
|
|
278
|
+
* @throws {OmsApiError} 404 `"Resource not found"` for a collection that is
|
|
279
|
+
* not yours. Ownership is the lookup scope, so somebody else's collection
|
|
280
|
+
* and a non-existent one are indistinguishable.
|
|
281
|
+
*/
|
|
282
|
+
get(id: Id, options?: RequestOptions): Promise<MovieCollection>;
|
|
283
|
+
/**
|
|
284
|
+
* `POST /movie_collections` - a new manual list. `201`.
|
|
285
|
+
*
|
|
286
|
+
* `name` is the only field that survives: the owner is always the caller,
|
|
287
|
+
* `kind` is pinned to `"manual"` and `position` is set to
|
|
288
|
+
* `max(position) + 1`. Passing `kind: "favorites"` does not fail, it is just
|
|
289
|
+
* ignored, which is the point - there is exactly one system collection and
|
|
290
|
+
* only the listing may mint it.
|
|
291
|
+
*
|
|
292
|
+
* Names are not unique.
|
|
293
|
+
*
|
|
294
|
+
* @throws {OmsApiError} 400 `"Name can't be blank"`.
|
|
295
|
+
*/
|
|
296
|
+
create(input: CreateMovieCollectionInput | string, options?: RequestOptions): Promise<MovieCollection>;
|
|
297
|
+
/**
|
|
298
|
+
* `PATCH /movie_collections/:id` - renames or repositions. `200`.
|
|
299
|
+
*
|
|
300
|
+
* A real partial update: `name` and `position` are the only keys accepted,
|
|
301
|
+
* and an omitted key is left alone.
|
|
302
|
+
*
|
|
303
|
+
* Refused for the favourites row with
|
|
304
|
+
* `401 "You are not authorized to update this resource"` - the GENERIC
|
|
305
|
+
* message; the friendlier "The favourites collection cannot be renamed,
|
|
306
|
+
* reordered or deleted" is never reached here. Only {@link reorder}
|
|
307
|
+
* produces that sentence. Test with {@link isSystemMovieCollection} and hide
|
|
308
|
+
* the control instead.
|
|
309
|
+
*
|
|
310
|
+
* @throws {OmsApiError} 404 for a collection that is not yours, 401 for the
|
|
311
|
+
* favourites row.
|
|
312
|
+
*/
|
|
313
|
+
update(id: Id, input: UpdateMovieCollectionInput, options?: RequestOptions): Promise<MovieCollection>;
|
|
314
|
+
/**
|
|
315
|
+
* `DELETE /movie_collections/:id` - `204`, empty body.
|
|
316
|
+
*
|
|
317
|
+
* Cascades: every title in the list goes with it. Nothing is recoverable and
|
|
318
|
+
* nothing is asked.
|
|
319
|
+
*
|
|
320
|
+
* Refused for the favourites row with the same generic `401` as
|
|
321
|
+
* {@link update}, for the same reason.
|
|
322
|
+
*/
|
|
323
|
+
delete(id: Id, options?: RequestOptions): Promise<void>;
|
|
324
|
+
/**
|
|
325
|
+
* `POST /movie_collections/:id/reorder` - rewrites the order of the items
|
|
326
|
+
* inside a collection. Answers `200` with the COLLECTION, not the items.
|
|
327
|
+
*
|
|
328
|
+
* Send the full ordered list of item ids. The server keeps a stale client
|
|
329
|
+
* from losing rows: ids it recognises are laid out first in the order given,
|
|
330
|
+
* then every item you did NOT mention is appended in its existing relative
|
|
331
|
+
* order, and the whole sequence is renumbered densely from `0`. So an item
|
|
332
|
+
* added by another tab between your read and your write sinks to the bottom
|
|
333
|
+
* instead of vanishing. Ids that are not in this collection are ignored, not
|
|
334
|
+
* rejected.
|
|
335
|
+
*
|
|
336
|
+
* Positions are written inside one transaction and - the part that catches
|
|
337
|
+
* people - the write does NOT touch each item's `updated_at`. A client that
|
|
338
|
+
* syncs on `updated_at` will not see a reorder. Refetch by position.
|
|
339
|
+
*
|
|
340
|
+
* The whole rewrite is one transaction, and items already at the right
|
|
341
|
+
* position are skipped, so a reorder that changes nothing costs no writes.
|
|
342
|
+
*
|
|
343
|
+
* Refused for the favourites row with
|
|
344
|
+
* `401 "The favourites collection cannot be renamed, reordered or deleted"` -
|
|
345
|
+
* this is the one action that produces that message rather than the generic
|
|
346
|
+
* one, because the system check runs before any authorisation.
|
|
347
|
+
*
|
|
348
|
+
* @throws {OmsApiError} 404 for a collection that is not yours, 401 for the
|
|
349
|
+
* favourites row.
|
|
350
|
+
*/
|
|
351
|
+
reorder(id: Id, itemIds: readonly Id[], options?: RequestOptions): Promise<MovieCollection>;
|
|
352
|
+
}
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
/** The `movies` namespace: Stremio addons, collections and watch progress, reachable as `oms.movies`. */
|
|
2
|
+
import type { ApiClient } from "../../http";
|
|
3
|
+
import { Resource } from "../../http";
|
|
4
|
+
import { MovieAddonsNamespace } from "./addons";
|
|
5
|
+
import { MovieCollectionsNamespace } from "./collections";
|
|
6
|
+
import { MovieWatchProgressesNamespace } from "./watchProgress";
|
|
7
|
+
export * from "./types";
|
|
8
|
+
export * from "./addons";
|
|
9
|
+
export * from "./collections";
|
|
10
|
+
export * from "./watchProgress";
|
|
11
|
+
/**
|
|
12
|
+
* The `movies` namespace, reachable as `oms.movies`.
|
|
13
|
+
*
|
|
14
|
+
* Everything under it needs a session or a personal token. An OAuth access
|
|
15
|
+
* token cannot reach any of it: every route answers
|
|
16
|
+
* `403 {"error":"insufficient_scope", "message": "This endpoint is not
|
|
17
|
+
* reachable with an OAuth access token..."}` - one of the few structured error
|
|
18
|
+
* bodies the API emits. That is a deliberate gate, not an oversight to route
|
|
19
|
+
* around.
|
|
20
|
+
*/
|
|
21
|
+
export declare class MoviesNamespace extends Resource {
|
|
22
|
+
/** Installed Stremio addons, plus `.groups` and `.grants` for sharing them. */
|
|
23
|
+
readonly addons: MovieAddonsNamespace;
|
|
24
|
+
/** Favourites and hand-made lists, plus `.items` for their contents. */
|
|
25
|
+
readonly collections: MovieCollectionsNamespace;
|
|
26
|
+
/** Playback position per title or episode; "Continuar a ver". */
|
|
27
|
+
readonly watchProgress: MovieWatchProgressesNamespace;
|
|
28
|
+
constructor(http: ApiClient);
|
|
29
|
+
}
|
|
@@ -0,0 +1,50 @@
|
|
|
1
|
+
/** Shared vocabulary of the movies namespace: title types, the Stremio manifest, and the guards every area uses. */
|
|
2
|
+
/**
|
|
3
|
+
* What a title is. Stremio's own vocabulary, and the backend stores it as a
|
|
4
|
+
* free string with no inclusion validation, so an addon may invent one.
|
|
5
|
+
* Compare against this union for the cases you handle and fall through for the
|
|
6
|
+
* rest rather than assuming the list is closed.
|
|
7
|
+
*/
|
|
8
|
+
export type MovieType = "movie" | "series" | "channel" | "tv" | (string & {});
|
|
9
|
+
/** The four resource names a Stremio manifest may advertise. */
|
|
10
|
+
export type StremioResourceName = "catalog" | "meta" | "stream" | "subtitles";
|
|
11
|
+
/** One catalogue an addon offers, as declared in its manifest. */
|
|
12
|
+
export interface StremioCatalog {
|
|
13
|
+
readonly type: string;
|
|
14
|
+
readonly id: string;
|
|
15
|
+
readonly name?: string;
|
|
16
|
+
readonly extra?: ReadonlyArray<{
|
|
17
|
+
readonly name: string;
|
|
18
|
+
readonly isRequired?: boolean;
|
|
19
|
+
readonly options?: readonly string[];
|
|
20
|
+
}>;
|
|
21
|
+
}
|
|
22
|
+
/**
|
|
23
|
+
* An addon's `manifest.json`, stored verbatim in a `jsonb` column.
|
|
24
|
+
*
|
|
25
|
+
* The backend does not validate a single key of it beyond "not blank": it is
|
|
26
|
+
* written straight to the column and read straight back. So the fields below
|
|
27
|
+
* are what a well-behaved Stremio addon sends, not a contract the server
|
|
28
|
+
* enforces - `id` and `name` can be missing on a hostile or broken manifest
|
|
29
|
+
* even though they are typed as required here, and the index signature is
|
|
30
|
+
* there because whatever else the addon declared round-trips untouched.
|
|
31
|
+
*
|
|
32
|
+
* Never trust `logo`, `background` or any URL inside one without checking the
|
|
33
|
+
* origin: this blob is user-supplied content that the app renders.
|
|
34
|
+
*/
|
|
35
|
+
export interface StremioManifest {
|
|
36
|
+
readonly id: string;
|
|
37
|
+
readonly name: string;
|
|
38
|
+
readonly description?: string;
|
|
39
|
+
readonly version?: string;
|
|
40
|
+
readonly resources?: ReadonlyArray<StremioResourceName | {
|
|
41
|
+
readonly name: StremioResourceName;
|
|
42
|
+
readonly types?: readonly string[];
|
|
43
|
+
}>;
|
|
44
|
+
readonly types?: readonly string[];
|
|
45
|
+
readonly catalogs?: readonly StremioCatalog[];
|
|
46
|
+
readonly logo?: string;
|
|
47
|
+
readonly background?: string;
|
|
48
|
+
/** Anything else the manifest carried. `jsonb` keeps it all. */
|
|
49
|
+
readonly [key: string]: unknown;
|
|
50
|
+
}
|