@devultur/convex 1.4.3 → 1.5.1

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/dist/react.d.ts CHANGED
@@ -1,59 +1,16 @@
1
1
  import React from 'react';
2
- import { DevulturMedia, MediaUrlOptions, Visibility, ProcessingPhase, FailureReason, MediaStatusValue } from '@devultur/core';
3
- import { BakeOutputFormat, MediaUploadState, MediaUploadError, UploadProgress } from '@devultur/react';
2
+ import { V as VideoProps, a as ViewerTokenAction, b as ViewerTokenArgs, D as DevulturApi } from './hooks-uqpBd5UF.js';
3
+ export { c as DevulturApiContext, d as DevulturContext, e as DevulturContextValue, f as DevulturProgressContext, g as DevulturProgressContextValue, T as TokenStatus, U as UploadOptions, h as UploadedMedia, i as ViewerTokenResult, u as useDevultur, j as useDevulturApi, k as useDevulturOptional, l as useDevulturProgress, m as useMediaUrl, n as useVideoProps } from './hooks-uqpBd5UF.js';
4
+ import { BakeOutputFormat, MediaUploadState, MediaUploadError } from '@devultur/react';
4
5
  export { MediaUploadError, MediaUploadState, UploadProgress } from '@devultur/react';
5
- import { FunctionReference } from 'convex/server';
6
- import { A as AttachmentLabels, M as MediaLibraryLabels, P as PreviewLabels, a as MediaPickerLabels, b as MediaFetchError } from './preview-labels-B7HNa7Va.js';
7
- export { c as AttachmentKind, d as MediaFetchErrorCode, e as defaultAttachmentLabels, f as defaultMediaLibraryLabels, g as defaultMediaPickerLabels, h as defaultPreviewLabels, i as formatDuration, j as formatFileSize } from './preview-labels-B7HNa7Va.js';
8
- import { Value } from 'convex/values';
9
- import { M as MediaRecord } from './types-DZxN6Eij.js';
6
+ import { A as AttachmentLabels, b as MediaFetchError, M as MediaLibraryLabels, P as PreviewLabels, a as MediaPickerLabels } from './preview-labels-C2nUUY_f.js';
7
+ export { c as AttachmentKind, d as MediaFetchErrorCode, e as defaultAttachmentLabels, f as defaultMediaLibraryLabels, g as defaultMediaPickerLabels, h as defaultPreviewLabels, i as formatDuration, j as formatFileSize } from './preview-labels-C2nUUY_f.js';
8
+ import { Visibility, DevulturMedia, MediaUrlOptions, MediaStatusValue, ProcessingPhase, FailureReason } from '@devultur/core';
9
+ import { M as MediaRecord } from './types-C0ruHUcu.js';
10
10
  import { P as PdfjsLoader } from './pdf-render-BwJGagvz.js';
11
11
  export { a as PdfjsModule } from './pdf-render-BwJGagvz.js';
12
-
13
- /** What a viewer token action returns: the token with its lifetime, or the bare token (default lifetime). */
14
- type ViewerTokenResult = {
15
- token: string;
16
- expiresIn: number;
17
- } | string;
18
- /** Extra arguments sent with `sessionSecret` to the viewer token action. */
19
- type ViewerTokenArgs = Record<string, Value>;
20
- /**
21
- * Where the viewer token for the current `tokenArgs` stands: not requested yet, being issued (no token yet), held, or
22
- * failed (the action threw or returned no token). A renewal in flight, or one that failed, keeps `"ready"`.
23
- */
24
- type TokenStatus = "idle" | "loading" | "ready" | "error";
25
-
26
- /** Transform/delivery options for media URLs (without `token`, which the context injects). */
27
- type MediaRenderOptions = Omit<MediaUrlOptions, "token">;
28
- /**
29
- * The viewer token action: the component's `issueViewerToken` (as `defineDevulturFunctions` or `exposeApi` export it,
30
- * where `sessionSecret` is optional) or an app's own, which may require it. The providers always send it.
31
- */
32
- type ViewerTokenAction = FunctionReference<"action", "public", {
33
- sessionSecret?: string;
34
- }>;
35
- interface MediaSession {
36
- token: string | null;
37
- /** Where the viewer token stands; `"error"` makes private previews fail fast with `token_unavailable`. */
38
- tokenStatus: TokenStatus;
39
- /** Why the last issuance failed (the action threw or returned no token), while `tokenStatus` is `"error"`. */
40
- tokenError: Error | null;
41
- /** Issues the viewer token again (after a failure, for example). Resolves to the new token, or `null`. */
42
- retryToken: () => Promise<string | null>;
43
- baseUrl: string | null;
44
- /** Browser session secret → sent in `${SESSION_HEADER}` on every private delivery. */
45
- sessionSecret: string;
46
- /** Delivery URL from a reference (non-hook → usable in handlers and `.map`). Token-transparent. */
47
- url: (media: DevulturMedia, options?: MediaRenderOptions) => string;
48
- /** Downloads a video's subtitle text for a locale (auth-transparent). */
49
- getCaptionsText: (media: DevulturMedia, locale: string) => Promise<string>;
50
- /**
51
- * Re-issues the viewer token (new session fingerprint with the current UA/IP) and updates the context.
52
- * Single-flight: concurrent calls share the same issuance. Returns the new token (or null if it
53
- * failed). The render uses it to transparently recover from a 401 `session_mismatch`.
54
- */
55
- reissueToken: () => Promise<string | null>;
56
- }
12
+ import 'convex/server';
13
+ import 'convex/values';
57
14
 
58
15
  /** What `useDevultur()` can do only under a `<DevulturProvider>` given the matching actions. */
59
16
  type DevulturCapability = "upload" | "uploadUrl" | "deleteMedia" | "api";
@@ -159,6 +116,27 @@ interface AttachmentCardProps extends Omit<React.HTMLAttributes<HTMLElement>, "c
159
116
  */
160
117
  declare function AttachmentCard({ media, contentType, onOpen, preview, headingLevel, locale, labels, ...articleProps }: AttachmentCardProps): React.JSX.Element | null;
161
118
 
119
+ interface DownloadLinkProps extends Omit<React.AnchorHTMLAttributes<HTMLAnchorElement>, "href" | "download" | "media"> {
120
+ media: DevulturMedia | null | undefined;
121
+ /** Name it downloads as. Without this it uses the upload's original name. */
122
+ filename?: string;
123
+ /**
124
+ * A private download that failed: `token_unavailable` right away when the viewer token couldn't be issued
125
+ * (`useDevultur().retryToken()` tries again), `http_error` when the delivery refused it.
126
+ */
127
+ onDownloadError?: (error: MediaFetchError) => void;
128
+ children: React.ReactNode;
129
+ }
130
+ /**
131
+ * `<a>` that downloads a media with its original name (token-transparent). The worker serves it with
132
+ * `Content-Disposition: attachment`, so a click downloads the file instead of opening it in a tab.
133
+ *
134
+ * Private: an `<a download>` NAVIGATES, and a navigation can't send `${SESSION_HEADER}` → with session
135
+ * binding the gate gives a 401. So, for private media, we intercept the click, blob-fetch with the header
136
+ * (like private `<Image>`) and trigger the download from the object URL. Public keeps native navigation.
137
+ */
138
+ declare function DownloadLink({ media, filename, onDownloadError, children, ...anchorProps }: DownloadLinkProps): React.JSX.Element | null;
139
+
162
140
  /** An explicit `srcSet` is passed through to the `<img>` as is, and wins over the one `widths` builds. */
163
141
  interface ImageProps extends Omit<React.ImgHTMLAttributes<HTMLImageElement>, "src" | "width" | "height"> {
164
142
  /** Typed reference. `null`/`undefined` → renders `fallback` (or `externalFallback`). Its `alt` is the default `alt`. */
@@ -200,6 +178,68 @@ interface ImageProps extends Omit<React.ImgHTMLAttributes<HTMLImageElement>, "sr
200
178
  */
201
179
  declare function Image({ media, width, height, fit, format, quality, widths, sizes, fallback, externalFallback, render, alt, onLoadError, ...imgProps }: ImageProps): React.JSX.Element;
202
180
 
181
+ interface MediaStatusReturn {
182
+ status: MediaStatusValue;
183
+ /** Typed progress: `phase` is the pipeline step (no `as any`). */
184
+ progress: {
185
+ current: number;
186
+ total: number;
187
+ percent: number;
188
+ phase?: ProcessingPhase;
189
+ } | null;
190
+ error: string | null;
191
+ /** Categorized failure reason (null if it didn't fail). */
192
+ failureReason: FailureReason | null;
193
+ /** Whether the failure is retriable (null if it didn't fail). */
194
+ retriable: boolean | null;
195
+ isQueued: boolean;
196
+ isTranscoding: boolean;
197
+ isCaptioning: boolean;
198
+ isReady: boolean;
199
+ isFailed: boolean;
200
+ playlistUrl: string | null;
201
+ thumbnailKey: string | null;
202
+ captionLocales: string[];
203
+ duration: number | null;
204
+ isLoading: boolean;
205
+ }
206
+ declare function useDevulturMedia(key: string | null | undefined): MediaStatusReturn;
207
+ interface CaptionTrack {
208
+ locale: string;
209
+ label: string;
210
+ src: string;
211
+ }
212
+ /**
213
+ * A video's pipeline state as a **discriminated union** on `phase`: the render is an exhaustive
214
+ * `switch` (no boolean ordering or `as any`), and adding a new phase is a compile error until it's
215
+ * handled. `processing` carries typed `step`/`percent`; `ready` carries the ref + props ready for
216
+ * `<VideoPlayer>` (token-transparent); `failed` carries a categorized `reason` + `retriable`.
217
+ */
218
+ type VideoState = {
219
+ phase: "idle";
220
+ } | {
221
+ phase: "queued";
222
+ } | {
223
+ phase: "processing";
224
+ step: ProcessingPhase;
225
+ percent: number;
226
+ } | {
227
+ phase: "ready";
228
+ media: DevulturMedia;
229
+ playlist: string;
230
+ duration: number;
231
+ captions: CaptionTrack[];
232
+ playerProps: VideoProps;
233
+ } | {
234
+ phase: "failed";
235
+ reason: FailureReason;
236
+ message: string;
237
+ retriable: boolean;
238
+ };
239
+ declare function useVideoState(media: DevulturMedia | null | undefined, options?: {
240
+ locales?: string[];
241
+ }): VideoState;
242
+
203
243
  /** What `renderItem` gets besides the record. */
204
244
  interface MediaLibraryItemState {
205
245
  /** The record's reference (`mediaFromRecord`), `null` for a record without a visibility. */
@@ -528,6 +568,11 @@ interface PreviewProps {
528
568
  pdfWorkerSrc?: string;
529
569
  /** Overrides any string shown or announced; wins over `PdfPreviewProvider`'s `labels`. English by default. */
530
570
  labels?: Partial<PreviewLabels>;
571
+ /**
572
+ * A video's playback metrics (`<VideoPlayer metrics>`): anonymous, no cookies, sent to the media host. On by
573
+ * default; `false` turns them off.
574
+ */
575
+ metrics?: boolean;
531
576
  }
532
577
  /**
533
578
  * Renders a media inline by its content type: images in an `<img>`, PDFs on `<canvas>` pages with pdf.js under a
@@ -538,7 +583,7 @@ interface PreviewProps {
538
583
  * @example
539
584
  * <Preview media={document.file} maxBytes={20_000_000} className="h-[80vh] w-full" />
540
585
  */
541
- declare function Preview({ media, contentType, fallback, loading, labels, ...viewProps }: PreviewProps): React.JSX.Element | null;
586
+ declare function Preview({ media, contentType, fallback, loading, labels, metrics, ...viewProps }: PreviewProps): React.JSX.Element | null;
542
587
 
543
588
  /** How a content type renders inline: `<img>`, a PDF view (pdf.js canvases or `<iframe>`), `<audio>` or `<pre>`. */
544
589
  type PreviewKind = "image" | "pdf" | "audio" | "text";
@@ -577,228 +622,8 @@ interface MediaLibraryState {
577
622
  */
578
623
  declare function useMediaLibrary(options?: UseMediaLibraryOptions): MediaLibraryState;
579
624
 
580
- type AnyAction = FunctionReference<"action">;
581
- type AnyMutation = FunctionReference<"mutation">;
582
- type AnyQuery = FunctionReference<"query">;
583
- interface DevulturApi {
584
- issueViewerToken: AnyAction;
585
- createUploadUrl: AnyAction;
586
- /** Records an upload in the component after its PUT, so it shows in `listMedia`. Optional (uploads still work). */
587
- confirmUpload?: AnyAction;
588
- deleteMedia: AnyAction;
589
- /** Deletes the full folder of a video (raw/hls/thumbnails/captions). Required to delete videos. */
590
- deleteVideo?: AnyAction;
591
- /** Requests the transcode of an uploaded video. Required by `useMediaUpload` for auto-process. */
592
- processVideo?: AnyAction;
593
- getMedia?: AnyQuery;
594
- /** The library, newest first. Required by `useMediaLibrary` and `<MediaLibrary>`. */
595
- listMediaPage?: AnyQuery;
596
- /** The library matching a search. Required by `useMediaLibrary` and `<MediaLibrary>` to search. */
597
- searchMedia?: AnyQuery;
598
- saveProgress?: AnyMutation;
599
- loadProgress?: AnyQuery;
600
- markComplete?: AnyMutation;
601
- resetProgress?: AnyMutation;
602
- }
603
- interface UploadOptions {
604
- /** Visibility override for this resource. Omitted → inherits the router's default by type. */
605
- visibility?: Visibility;
606
- /** Progress of the PUT: bytes sent, total bytes and their fraction (0 to 1). */
607
- onProgress?: (progress: UploadProgress) => void;
608
- /** Aborts the PUT → `upload()` rejects with an `AbortError`. */
609
- signal?: AbortSignal;
610
- /** A PDF's page count to record with it, a hint (`countPdfPages` from `@devultur/convex/pdfjs` counts it). */
611
- pageCount?: number;
612
- }
613
- /**
614
- * The reference `upload()` resolves to: a `DevulturMedia` whose `key` is always set (the uploaded object's key; a
615
- * video's raw file, what `processVideo` takes). It stores as-is in a `dv.media()` field.
616
- */
617
- type UploadedMedia = DevulturMedia & {
618
- readonly key: string;
619
- };
620
- /**
621
- * What `useDevultur()` returns. Under a `<DevulturViewerProvider>`, `uploadUrl`, `upload` and `deleteMedia` throw a
622
- * `DevulturCapabilityError` (`capability_unavailable`).
623
- */
624
- interface DevulturContextValue extends MediaSession {
625
- uploadUrl: (file: File) => Promise<{
626
- url: string;
627
- key: string;
628
- }>;
629
- /** Uploads a file (reporting progress), records it in the component, and returns the reference ready to save. */
630
- upload: (file: File, options?: UploadOptions) => Promise<UploadedMedia>;
631
- /** Deletes a media by reference: video → full folder; image/file → the object. */
632
- deleteMedia: (media: DevulturMedia) => void;
633
- }
634
- interface ProgressContextValue {
635
- save: (videoId: string, position: number) => Promise<void>;
636
- load: (videoId: string) => Promise<{
637
- lastPosition: number;
638
- completedAt: Date | null;
639
- } | null>;
640
- markComplete: (videoId: string) => Promise<void>;
641
- reset: (videoId: string) => Promise<void>;
642
- }
643
- interface DevulturProviderProps {
644
- api: DevulturApi;
645
- /** Media worker base (e.g. `https://media.your-domain.com`). Required for `useMediaUrl`. */
646
- baseUrl?: string;
647
- /**
648
- * Extra arguments sent with `sessionSecret` on every viewer token issuance (first, renewal and re-issue), for
649
- * example `{ workspaceId }`. Compared by value: when they change, the current token is dropped and a new one is
650
- * issued. The component's own `issueViewerToken` accepts only `sessionSecret`, so pass your own action in
651
- * `issueViewerToken` that takes these arguments.
652
- */
653
- tokenArgs?: ViewerTokenArgs;
654
- /**
655
- * Your own viewer token action, used instead of `api.issueViewerToken`. It receives `{ sessionSecret, ...tokenArgs }`
656
- * and returns what the component's `issueViewerToken` returns.
657
- */
658
- issueViewerToken?: ViewerTokenAction;
659
- children: React.ReactNode;
660
- }
661
- declare function DevulturProvider({ api, baseUrl, tokenArgs, issueViewerToken, children }: DevulturProviderProps): React.JSX.Element;
662
- declare function useDevultur(): DevulturContextValue;
663
- /**
664
- * The `api` passed to `<DevulturProvider>`: your app's exported Devultur functions. Under a `<DevulturViewerProvider>`
665
- * it throws a `DevulturCapabilityError`.
666
- */
667
- declare function useDevulturApi(): DevulturApi;
668
- interface DevulturViewerProviderProps {
669
- /** Media worker base (e.g. `https://media.your-domain.com`). */
670
- baseUrl: string;
671
- /** Your viewer token action. It receives `{ sessionSecret, ...tokenArgs }`, like `<DevulturProvider>`'s. */
672
- issueViewerToken: ViewerTokenAction;
673
- /** Extra arguments for `issueViewerToken`, compared by value (see `<DevulturProvider tokenArgs>`). */
674
- tokenArgs?: ViewerTokenArgs;
675
- children: React.ReactNode;
676
- }
677
- /**
678
- * A provider for apps that only display media: it issues and renews the viewer token, so `<Image>`, `<Preview>`,
679
- * `<DownloadLink>`, `useMediaObjectUrl` and the video hooks work, and it needs no upload or delete actions. `upload`,
680
- * `uploadUrl` and `deleteMedia` throw a `DevulturCapabilityError`, as do the hooks that need the `api`
681
- * (`useMediaUpload`, `useDevulturApi`, `<MediaLibrary>`, `<MediaPicker>`).
682
- *
683
- * @example
684
- * <DevulturViewerProvider baseUrl={MEDIA_URL} issueViewerToken={api.admin.issueViewerToken} tokenArgs={{ workspaceId }}>
685
- * <Preview media={document.file} />
686
- * </DevulturViewerProvider>
687
- */
688
- declare function DevulturViewerProvider({ baseUrl, issueViewerToken, tokenArgs, children, }: DevulturViewerProviderProps): React.JSX.Element;
689
- declare function useDevulturProgress(): ProgressContextValue;
690
- /**
691
- * Ready-to-use delivery URL for a key, with the context's viewer token already injected. The consumer
692
- * never touches the token or the query — it only declares what it wants (download, resize, etc.).
693
- *
694
- * @example
695
- * <img src={useMediaUrl(key)} />
696
- * <a href={useMediaUrl(key, { download: true })} download>Download</a>
697
- * <img src={useMediaUrl(key, { width: 512, format: "webp" })} />
698
- */
699
- declare function useMediaUrl(key: string | null | undefined, options?: MediaRenderOptions): string | null;
700
- interface VideoProps {
701
- src: string;
702
- token: string | undefined;
703
- captions: {
704
- locale: string;
705
- label: string;
706
- src: string;
707
- }[];
708
- /** Session secret → `<VideoPlayer>` sends it in `${SESSION_HEADER}` on hls.js/captions requests. */
709
- sessionSecret?: string;
710
- }
711
- /**
712
- * Token-transparent props for `<VideoPlayer>` from a video reference: builds the HLS playlist `src`,
713
- * the viewer `token` (only if private), and the `captions` for the requested locales.
714
- * The consumer just does `<VideoPlayer {...useVideoProps(lesson.video, { locales })} />`.
715
- */
716
- declare function useVideoProps(media: DevulturMedia | null | undefined, options?: {
717
- locales?: string[];
718
- }): VideoProps | null;
719
- interface DownloadLinkProps extends Omit<React.AnchorHTMLAttributes<HTMLAnchorElement>, "href" | "download" | "media"> {
720
- media: DevulturMedia | null | undefined;
721
- /** Name it downloads as. Without this it uses the upload's original name. */
722
- filename?: string;
723
- /**
724
- * A private download that failed: `token_unavailable` right away when the viewer token couldn't be issued
725
- * (`useDevultur().retryToken()` tries again), `http_error` when the delivery refused it.
726
- */
727
- onDownloadError?: (error: MediaFetchError) => void;
728
- children: React.ReactNode;
729
- }
730
- /**
731
- * `<a>` that downloads a media with its original name (token-transparent). The worker serves it with
732
- * `Content-Disposition: attachment`, so a click downloads the file instead of opening it in a tab.
733
- *
734
- * Private: an `<a download>` NAVIGATES, and a navigation can't send `${SESSION_HEADER}` → with session
735
- * binding the gate gives a 401. So, for private media, we intercept the click, blob-fetch with the header
736
- * (like private `<Image>`) and trigger the download from the object URL. Public keeps native navigation.
737
- */
738
- declare function DownloadLink({ media, filename, onDownloadError, children, ...anchorProps }: DownloadLinkProps): React.JSX.Element | null;
739
- interface MediaStatusReturn {
740
- status: MediaStatusValue;
741
- /** Typed progress: `phase` is the pipeline step (no `as any`). */
742
- progress: {
743
- current: number;
744
- total: number;
745
- percent: number;
746
- phase?: ProcessingPhase;
747
- } | null;
748
- error: string | null;
749
- /** Categorized failure reason (null if it didn't fail). */
750
- failureReason: FailureReason | null;
751
- /** Whether the failure is retriable (null if it didn't fail). */
752
- retriable: boolean | null;
753
- isQueued: boolean;
754
- isTranscoding: boolean;
755
- isCaptioning: boolean;
756
- isReady: boolean;
757
- isFailed: boolean;
758
- playlistUrl: string | null;
759
- thumbnailKey: string | null;
760
- captionLocales: string[];
761
- duration: number | null;
762
- isLoading: boolean;
763
- }
764
- declare function useDevulturMedia(key: string | null | undefined): MediaStatusReturn;
765
- interface CaptionTrack {
766
- locale: string;
767
- label: string;
768
- src: string;
769
- }
770
- /**
771
- * A video's pipeline state as a **discriminated union** on `phase`: the render is an exhaustive
772
- * `switch` (no boolean ordering or `as any`), and adding a new phase is a compile error until it's
773
- * handled. `processing` carries typed `step`/`percent`; `ready` carries the ref + props ready for
774
- * `<VideoPlayer>` (token-transparent); `failed` carries a categorized `reason` + `retriable`.
775
- */
776
- type VideoState = {
777
- phase: "idle";
778
- } | {
779
- phase: "queued";
780
- } | {
781
- phase: "processing";
782
- step: ProcessingPhase;
783
- percent: number;
784
- } | {
785
- phase: "ready";
786
- media: DevulturMedia;
787
- playlist: string;
788
- duration: number;
789
- captions: CaptionTrack[];
790
- playerProps: VideoProps;
791
- } | {
792
- phase: "failed";
793
- reason: FailureReason;
794
- message: string;
795
- retriable: boolean;
796
- };
797
- declare function useVideoState(media: DevulturMedia | null | undefined, options?: {
798
- locales?: string[];
799
- }): VideoState;
800
625
  interface UseMediaUploadOptions {
801
- /** Resource visibility. Omitted → config default → private (secure-by-default). */
626
+ /** Resource visibility. Omitted → `config.upload.visibility`, else the Worker's default by type. Your guard can rewrite it. */
802
627
  visibility?: Visibility;
803
628
  /** Fires ONCE, at the persistence point (PUT done + transcode requested). */
804
629
  onComplete?: (media: DevulturMedia) => void;
@@ -829,4 +654,61 @@ interface UseMediaUploadReturn {
829
654
  */
830
655
  declare function useMediaUpload(options?: UseMediaUploadOptions): UseMediaUploadReturn;
831
656
 
832
- export { AttachmentCard, type AttachmentCardProps, AttachmentLabels, type CaptionTrack, CropUpload, type CropUploadLabels, type CropUploadProps, type CropUploadRenderProps, type DevulturApi, type DevulturCapability, DevulturCapabilityError, DevulturProvider, DevulturViewerProvider, DocumentLink, type DocumentLinkProps, DownloadLink, Image, type ImageProps, MediaFetchError, MediaLibrary, type MediaLibraryItemState, MediaLibraryLabels, type MediaLibraryPart, type MediaLibraryProps, type MediaLibraryState, type MediaLibraryStatus, type MediaObjectUrl, MediaPicker, MediaPickerLabels, type MediaPickerLibraryProps, type MediaPickerProps, type MediaPickerSelectionProps, type MediaPickerState, type MediaPickerUpload$1 as MediaPickerUpload, type MediaPickerUploadProps, type MediaPickerUploads, type PdfPreviewConfig, PdfPreviewProvider, PdfThumbnail, type PdfThumbnailProps, PdfjsLoader, Preview, type PreviewKind, PreviewLabels, type PreviewProps, type TokenStatus, type UploadedMedia, type UseMediaLibraryOptions, type UseMediaObjectUrlOptions, type UseMediaUploadOptions, type UseMediaUploadReturn, type VideoProps, type VideoState, type ViewerTokenArgs, type ViewerTokenResult, matchesAccept, useDevultur, useDevulturApi, useDevulturMedia, useDevulturProgress, useMediaLibrary, useMediaObjectUrl, useMediaPicker, useMediaUpload, useMediaUrl, useVideoProps, useVideoState };
657
+ interface DevulturViewerProviderProps {
658
+ /** Media worker base (e.g. `https://media.your-domain.com`). */
659
+ baseUrl: string;
660
+ /**
661
+ * Your viewer token action. It receives `{ sessionSecret, ...tokenArgs }`, like `<DevulturProvider>`'s. Leave it
662
+ * out when every media is public: the provider then needs no Convex client, issues nothing, and a private media
663
+ * fails with `token_unavailable`.
664
+ */
665
+ issueViewerToken?: ViewerTokenAction;
666
+ /**
667
+ * `true` → the token is issued only once a private media is shown (and renewed from then on), so a page of public
668
+ * media calls nothing. Code that reads `token` itself then calls `requestToken()` first. Default `false`: issued
669
+ * as soon as the provider mounts.
670
+ */
671
+ lazyToken?: boolean;
672
+ /** Extra arguments for `issueViewerToken`, compared by value (see `<DevulturProvider tokenArgs>`). */
673
+ tokenArgs?: ViewerTokenArgs;
674
+ children: React.ReactNode;
675
+ }
676
+ /**
677
+ * A provider for apps that only display media: `<Image>`, `<Preview>`, `<DownloadLink>`, `useMediaObjectUrl` and the
678
+ * video hooks work, and it needs no upload or delete actions. It issues and renews the viewer token (with `lazyToken`,
679
+ * only once a private media is shown). Without `issueViewerToken` it needs no Convex client at all. `upload`, `uploadUrl` and `deleteMedia` throw a `DevulturCapabilityError`, as do the hooks that
680
+ * need the `api` (`useMediaUpload`, `useDevulturApi`, `<MediaLibrary>`, `<MediaPicker>`).
681
+ *
682
+ * @example
683
+ * <DevulturViewerProvider baseUrl={MEDIA_URL} issueViewerToken={api.admin.issueViewerToken} tokenArgs={{ workspaceId }}>
684
+ * <Preview media={document.file} />
685
+ * </DevulturViewerProvider>
686
+ *
687
+ * // Only public media: no token action, no Convex client.
688
+ * <DevulturViewerProvider baseUrl={MEDIA_URL}>
689
+ * <Image media={post.cover} alt="" />
690
+ * </DevulturViewerProvider>
691
+ */
692
+ declare function DevulturViewerProvider({ issueViewerToken, ...props }: DevulturViewerProviderProps): React.JSX.Element;
693
+
694
+ interface DevulturProviderProps {
695
+ api: DevulturApi;
696
+ /** Media worker base (e.g. `https://media.your-domain.com`). Required for `useMediaUrl`. */
697
+ baseUrl?: string;
698
+ /**
699
+ * Extra arguments sent with `sessionSecret` on every viewer token issuance (first, renewal and re-issue), for
700
+ * example `{ workspaceId }`. Compared by value: when they change, the current token is dropped and a new one is
701
+ * issued. The component's own `issueViewerToken` accepts only `sessionSecret`, so pass your own action in
702
+ * `issueViewerToken` that takes these arguments.
703
+ */
704
+ tokenArgs?: ViewerTokenArgs;
705
+ /**
706
+ * Your own viewer token action, used instead of `api.issueViewerToken`. It receives `{ sessionSecret, ...tokenArgs }`
707
+ * and returns what the component's `issueViewerToken` returns.
708
+ */
709
+ issueViewerToken?: ViewerTokenAction;
710
+ children: React.ReactNode;
711
+ }
712
+ declare function DevulturProvider({ api, baseUrl, tokenArgs, issueViewerToken, children }: DevulturProviderProps): React.JSX.Element;
713
+
714
+ export { AttachmentCard, type AttachmentCardProps, AttachmentLabels, type CaptionTrack, CropUpload, type CropUploadLabels, type CropUploadProps, type CropUploadRenderProps, DevulturApi, type DevulturCapability, DevulturCapabilityError, DevulturProvider, DevulturViewerProvider, type DevulturViewerProviderProps, DocumentLink, type DocumentLinkProps, DownloadLink, type DownloadLinkProps, Image, type ImageProps, MediaFetchError, MediaLibrary, type MediaLibraryItemState, MediaLibraryLabels, type MediaLibraryPart, type MediaLibraryProps, type MediaLibraryState, type MediaLibraryStatus, type MediaObjectUrl, MediaPicker, MediaPickerLabels, type MediaPickerLibraryProps, type MediaPickerProps, type MediaPickerSelectionProps, type MediaPickerState, type MediaPickerUpload$1 as MediaPickerUpload, type MediaPickerUploadProps, type MediaPickerUploads, type MediaStatusReturn, type PdfPreviewConfig, PdfPreviewProvider, PdfThumbnail, type PdfThumbnailProps, PdfjsLoader, Preview, type PreviewKind, PreviewLabels, type PreviewProps, type UseMediaLibraryOptions, type UseMediaObjectUrlOptions, type UseMediaUploadOptions, type UseMediaUploadReturn, VideoProps, type VideoState, ViewerTokenArgs, matchesAccept, useDevulturMedia, useMediaLibrary, useMediaObjectUrl, useMediaPicker, useMediaUpload, useVideoState };