@file-viewer/core 3.1.1 → 3.2.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.en.md +3 -121
- package/README.md +3 -126
- package/dist/assets.d.ts +2 -2
- package/dist/assets.js +1 -5
- package/dist/browser/controller.d.ts +1 -2
- package/dist/browser/controller.js +2 -34
- package/dist/browser.d.ts +2 -2
- package/dist/browser.js +2 -2
- package/dist/config/options.d.ts +1 -1
- package/dist/contracts/types.d.ts +30 -416
- package/dist/contracts/xml.d.ts +48 -0
- package/dist/contracts/xml.js +1 -0
- package/dist/export.d.ts +3 -10
- package/dist/export.js +2 -9
- package/dist/exportDocument.d.ts +1 -12
- package/dist/exportDocument.js +7 -31
- package/dist/features/document/dom/anchors.d.ts +1 -1
- package/dist/features/document/dom/index.d.ts +5 -5
- package/dist/features/document/dom/index.js +3 -3
- package/dist/features/document/dom/providers.d.ts +1 -1
- package/dist/features/document/events.d.ts +2 -2
- package/dist/features/document/events.js +3 -3
- package/dist/features/document/fit.d.ts +1 -1
- package/dist/features/document/fit.js +1 -1
- package/dist/features/document/model.d.ts +1 -1
- package/dist/features/document/search.d.ts +1 -1
- package/dist/features/document/search.js +2 -2
- package/dist/features/document/viewState.d.ts +1 -1
- package/dist/features/document/viewState.js +2 -2
- package/dist/features/document/zoom.d.ts +3 -2
- package/dist/features/document/zoom.js +19 -3
- package/dist/features/document/zoomGestures.d.ts +11 -0
- package/dist/features/document/zoomGestures.js +111 -0
- package/dist/features/printMask.d.ts +1 -1
- package/dist/features/printMaskDesigner.d.ts +2 -6
- package/dist/features/printMaskDesigner.js +2 -11
- package/dist/features/printMaskLoader.d.ts +1 -7
- package/dist/features/printMaskLoader.js +1 -7
- package/dist/features/watermark.d.ts +1 -1
- package/dist/headless.d.ts +29 -29
- package/dist/headless.js +16 -21
- package/dist/i18n/messages.d.ts +1 -1
- package/dist/i18n/messages.de.d.ts +1 -5
- package/dist/i18n/messages.de.js +0 -4
- package/dist/i18n/messages.ja.d.ts +1 -6
- package/dist/i18n/messages.ja.js +0 -5
- package/dist/i18n/messages.js +2 -2
- package/dist/index.d.ts +74 -73
- package/dist/index.js +37 -37
- package/dist/lifecycle/facade.d.ts +4 -4
- package/dist/lifecycle/facade.js +2 -2
- package/dist/lifecycle/operations.d.ts +4 -4
- package/dist/lifecycle/operations.js +4 -9
- package/dist/output/canvasImage.d.ts +1 -2
- package/dist/output/canvasImage.js +1 -4
- package/dist/output/export.d.ts +2 -4
- package/dist/output/export.js +133 -81
- package/dist/output/printLayout.d.ts +2 -5
- package/dist/output/printLayout.js +37 -9
- package/dist/output/snapshotDownload.d.ts +1 -2
- package/dist/output/snapshotDownload.js +2 -3
- package/dist/platform/assets.d.ts +9 -16
- package/dist/platform/assets.js +60 -17
- package/dist/platform/copiedAssets.d.ts +0 -1
- package/dist/platform/copiedAssets.js +1 -2
- package/dist/presentation/state.d.ts +1 -1
- package/dist/presentation/state.js +3 -3
- package/dist/print-mask.d.ts +2 -2
- package/dist/print-mask.js +1 -1
- package/dist/registry/capabilities.d.ts +3 -16
- package/dist/registry/capabilities.js +2 -15
- package/dist/registry/formats.d.ts +5 -5
- package/dist/registry/formats.generated.d.ts +26 -8
- package/dist/registry/formats.generated.js +36 -4
- package/dist/registry/formats.js +2 -2
- package/dist/registry/registry.d.ts +6 -15
- package/dist/registry/registry.js +24 -10
- package/dist/renderers/image.d.ts +1 -1
- package/dist/renderers/image.js +26 -5
- package/dist/renderers/index.d.ts +30 -11
- package/dist/renderers/index.js +5 -11
- package/dist/rendering/dispatcher.d.ts +1 -6
- package/dist/rendering/dispatcher.js +3 -3
- package/dist/rendering/handler.d.ts +10 -15
- package/dist/rendering/handler.js +20 -27
- package/dist/security/svgResources.d.ts +0 -10
- package/dist/security/svgResources.js +2 -11
- package/dist/source/index.d.ts +3 -3
- package/dist/source/index.js +1 -1
- package/dist/source/loading.d.ts +56 -15
- package/dist/source/loading.js +177 -87
- package/dist/source/precheck.d.ts +1 -13
- package/dist/source/precheck.js +2 -9
- package/dist/source/textEncoding.d.ts +6 -3
- package/dist/source/textEncoding.js +58 -8
- package/dist/viewer/createViewer.d.ts +1 -1
- package/dist/viewer/createViewer.js +103 -33
- package/dist/viewer/loading.d.ts +2 -6
- package/dist/viewer/loading.js +1 -9
- package/dist/viewer/operations.d.ts +3 -3
- package/dist/viewer/operations.js +6 -14
- package/dist/viewer/state.d.ts +2 -6
- package/dist/viewer/state.js +3 -8
- package/package.json +127 -19
package/dist/source/loading.js
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
import { buildFileViewerLifecycleContext, } from
|
|
2
|
-
import { resolveFileViewerPreviewMessages, } from
|
|
3
|
-
import { translateFileViewerMessage } from
|
|
4
|
-
import { DEFAULT_FILE_VIEWER_SOURCE_FILENAME, getExtension, normalizeFilename, readFileViewerBuffer, resolveFileViewerSourceFilename, wrapFileViewerFileRef, } from
|
|
1
|
+
import { buildFileViewerLifecycleContext, } from "../lifecycle/operations.js";
|
|
2
|
+
import { resolveFileViewerPreviewMessages, } from "../viewer/state.js";
|
|
3
|
+
import { translateFileViewerMessage } from "../i18n/messages.js";
|
|
4
|
+
import { DEFAULT_FILE_VIEWER_SOURCE_FILENAME, getExtension, normalizeFilename, readFileViewerBuffer, resolveFileViewerSourceFilename, wrapFileViewerFileRef, } from "./index.js";
|
|
5
5
|
export const DEFAULT_PDF_RANGE_CHUNK_SIZE = 64 * 1024;
|
|
6
6
|
export const DEFAULT_FILE_VIEWER_STREAMING_PDF_FILENAME = 'preview.pdf';
|
|
7
7
|
export const FILE_VIEWER_REMOTE_MISSING_DATA_ERROR_MESSAGE = '文件下载失败';
|
|
@@ -117,7 +117,6 @@ const encodeFileViewerUrlPathSegment = (segment) => {
|
|
|
117
117
|
decoded = decodeURIComponent(segment);
|
|
118
118
|
}
|
|
119
119
|
catch {
|
|
120
|
-
// Invalid percent escapes are treated as literal filename characters.
|
|
121
120
|
}
|
|
122
121
|
return encodeURIComponent(decoded)
|
|
123
122
|
.replace(/%3A/gi, ':')
|
|
@@ -360,9 +359,9 @@ export const commitFileViewerRenderCompleteState = ({ version, session, buildSta
|
|
|
360
359
|
onClearLoadStarted === null || onClearLoadStarted === void 0 ? void 0 : onClearLoadStarted(version);
|
|
361
360
|
return completeState;
|
|
362
361
|
};
|
|
363
|
-
export const runFileViewerReadAndRenderFile = async ({ file, version, sourceUrl, source = sourceUrl ? 'url' : 'file', fallbackFilename = '', previewTarget, isCurrent, mountRenderedContent, destroyRenderSession, buildRenderCompleteState, onSession, onActiveDocumentContext, onLifecycle, onClearLoadStarted, }) => {
|
|
362
|
+
export const runFileViewerReadAndRenderFile = async ({ file, version, signal, sourceUrl, source = sourceUrl ? 'url' : 'file', fallbackFilename = '', previewTarget, isCurrent, mountRenderedContent, destroyRenderSession, buildRenderCompleteState, onSession, onActiveDocumentContext, onLifecycle, onClearLoadStarted, }) => {
|
|
364
363
|
const buffer = await readFileViewerBuffer(file);
|
|
365
|
-
if (!isCurrent(version)) {
|
|
364
|
+
if (!isCurrent(version) || (signal === null || signal === void 0 ? void 0 : signal.aborted)) {
|
|
366
365
|
return {
|
|
367
366
|
stale: true,
|
|
368
367
|
buffer,
|
|
@@ -377,7 +376,7 @@ export const runFileViewerReadAndRenderFile = async ({ file, version, sourceUrl,
|
|
|
377
376
|
fallbackFilename,
|
|
378
377
|
}));
|
|
379
378
|
const session = await mountRenderedContent(buffer, file, version, sourceUrl);
|
|
380
|
-
if (!isCurrent(version)) {
|
|
379
|
+
if (!isCurrent(version) || (signal === null || signal === void 0 ? void 0 : signal.aborted)) {
|
|
381
380
|
destroyRenderSession === null || destroyRenderSession === void 0 ? void 0 : destroyRenderSession(session);
|
|
382
381
|
return {
|
|
383
382
|
stale: true,
|
|
@@ -408,15 +407,15 @@ export const runFileViewerReadAndRenderFile = async ({ file, version, sourceUrl,
|
|
|
408
407
|
complete,
|
|
409
408
|
};
|
|
410
409
|
};
|
|
411
|
-
export const runFileViewerStreamingPdfPreview = async ({ url, version, filename, previewTarget, isCurrent, mountRenderedContent, destroyRenderSession, buildRenderCompleteState, loadingMessage, i18n, onStartLoading, onSession, onActiveDocumentContext, onLifecycle, onClearLoadStarted, onStopLoading, onError, }) => {
|
|
410
|
+
export const runFileViewerStreamingPdfPreview = async ({ url, version, filename, previewTarget, isCurrent, mountRenderedContent, destroyRenderSession, buildRenderCompleteState, loadingMessage, signal, typeOverride, i18n, onStartLoading, onSession, onActiveDocumentContext, onLifecycle, onClearLoadStarted, onStopLoading, onError, }) => {
|
|
412
411
|
let placeholderFile = null;
|
|
413
412
|
onStartLoading === null || onStartLoading === void 0 ? void 0 : onStartLoading(loadingMessage || resolveFileViewerPreviewMessages(i18n).streamingPdf);
|
|
414
413
|
try {
|
|
415
414
|
placeholderFile = createFileViewerStreamingPdfPlaceholderFile(filename);
|
|
416
415
|
applyFileViewerPreviewSourceUrlState(previewTarget, url);
|
|
417
|
-
const session = await mountRenderedContent(new ArrayBuffer(0), placeholderFile, version, url, url);
|
|
418
|
-
if (!isCurrent(version)) {
|
|
419
|
-
destroyRenderSession === null || destroyRenderSession === void 0 ? void 0 : destroyRenderSession(session);
|
|
416
|
+
const session = await mountRenderedContent(new ArrayBuffer(0), placeholderFile, version, url, url, signal, typeOverride);
|
|
417
|
+
if (!isCurrent(version) || (signal === null || signal === void 0 ? void 0 : signal.aborted)) {
|
|
418
|
+
await (destroyRenderSession === null || destroyRenderSession === void 0 ? void 0 : destroyRenderSession(session));
|
|
420
419
|
return {
|
|
421
420
|
status: 'stale',
|
|
422
421
|
placeholderFile,
|
|
@@ -448,7 +447,7 @@ export const runFileViewerStreamingPdfPreview = async ({ url, version, filename,
|
|
|
448
447
|
};
|
|
449
448
|
}
|
|
450
449
|
catch (error) {
|
|
451
|
-
if (!isCurrent(version)) {
|
|
450
|
+
if (!isCurrent(version) || (signal === null || signal === void 0 ? void 0 : signal.aborted) || isFileViewerAbortError(error)) {
|
|
452
451
|
return {
|
|
453
452
|
status: 'stale',
|
|
454
453
|
placeholderFile,
|
|
@@ -475,7 +474,7 @@ export const runFileViewerStreamingPdfPreview = async ({ url, version, filename,
|
|
|
475
474
|
});
|
|
476
475
|
}
|
|
477
476
|
};
|
|
478
|
-
export const runFileViewerLocalFilePreview = async ({ source, version, currentFilename, fallbackFilename, previewTarget, isCurrent, mountRenderedContent, destroyRenderSession, buildLoadStartState, buildRenderCompleteState, onMarkLoadStarted, onStartLoading, onSession, onActiveDocumentContext, onLifecycle, onClearLoadStarted, onStopLoading, onError, }) => {
|
|
477
|
+
export const runFileViewerLocalFilePreview = async ({ source, version, currentFilename, fallbackFilename, shouldStreamLocalFile, requestController, previewTarget, isCurrent, mountRenderedContent, destroyRenderSession, buildLoadStartState, buildRenderCompleteState, onMarkLoadStarted, onStartLoading, onSession, onActiveDocumentContext, onLifecycle, onClearLoadStarted, onStopLoading, onError, }) => {
|
|
479
478
|
const localSource = resolveFileViewerFileRefSourcePlan({
|
|
480
479
|
source,
|
|
481
480
|
currentFilename,
|
|
@@ -495,14 +494,55 @@ export const runFileViewerLocalFilePreview = async ({ source, version, currentFi
|
|
|
495
494
|
onLifecycle,
|
|
496
495
|
onStartLoading,
|
|
497
496
|
});
|
|
497
|
+
const controller = (requestController === null || requestController === void 0 ? void 0 : requestController.createAbortController()) || null;
|
|
498
498
|
try {
|
|
499
|
+
const streamDecision = await (shouldStreamLocalFile === null || shouldStreamLocalFile === void 0 ? void 0 : shouldStreamLocalFile({
|
|
500
|
+
file,
|
|
501
|
+
filename: localSource.filename,
|
|
502
|
+
extension: getExtension(localSource.filename),
|
|
503
|
+
signal: controller === null || controller === void 0 ? void 0 : controller.signal,
|
|
504
|
+
}));
|
|
505
|
+
if (!isCurrent(version) || (controller === null || controller === void 0 ? void 0 : controller.signal.aborted)) {
|
|
506
|
+
return { status: 'stale', source: localSource, read: null, error: null };
|
|
507
|
+
}
|
|
508
|
+
if (streamDecision) {
|
|
509
|
+
const buffer = new ArrayBuffer(0);
|
|
510
|
+
const typeOverride = typeof streamDecision === 'string' ? streamDecision : undefined;
|
|
511
|
+
applyFileViewerReadPreviewState(previewTarget, createFileViewerReadPreviewState({
|
|
512
|
+
file,
|
|
513
|
+
buffer,
|
|
514
|
+
fallbackFilename: localSource.filename,
|
|
515
|
+
}));
|
|
516
|
+
const session = await mountRenderedContent(buffer, file, version, undefined, undefined, controller === null || controller === void 0 ? void 0 : controller.signal, typeOverride);
|
|
517
|
+
if (!isCurrent(version) || (controller === null || controller === void 0 ? void 0 : controller.signal.aborted)) {
|
|
518
|
+
destroyRenderSession === null || destroyRenderSession === void 0 ? void 0 : destroyRenderSession(session);
|
|
519
|
+
return { status: 'stale', source: localSource, read: null, error: null };
|
|
520
|
+
}
|
|
521
|
+
const complete = commitFileViewerRenderCompleteState({
|
|
522
|
+
version,
|
|
523
|
+
session,
|
|
524
|
+
readinessTarget: previewTarget,
|
|
525
|
+
buildState: () => buildRenderCompleteState({ version, source: 'file', file }),
|
|
526
|
+
onSession,
|
|
527
|
+
onActiveDocumentContext,
|
|
528
|
+
onLifecycle,
|
|
529
|
+
onClearLoadStarted,
|
|
530
|
+
});
|
|
531
|
+
return {
|
|
532
|
+
status: 'ready',
|
|
533
|
+
source: localSource,
|
|
534
|
+
read: { stale: false, buffer, session, complete },
|
|
535
|
+
error: null,
|
|
536
|
+
};
|
|
537
|
+
}
|
|
499
538
|
const read = await runFileViewerReadAndRenderFile({
|
|
500
539
|
file,
|
|
501
540
|
version,
|
|
541
|
+
signal: controller === null || controller === void 0 ? void 0 : controller.signal,
|
|
502
542
|
source: 'file',
|
|
503
543
|
previewTarget,
|
|
504
544
|
isCurrent,
|
|
505
|
-
mountRenderedContent,
|
|
545
|
+
mountRenderedContent: (buffer, file, version, sourceUrl) => mountRenderedContent(buffer, file, version, sourceUrl, undefined, controller === null || controller === void 0 ? void 0 : controller.signal),
|
|
506
546
|
destroyRenderSession,
|
|
507
547
|
buildRenderCompleteState: input => buildRenderCompleteState({
|
|
508
548
|
version: input.version,
|
|
@@ -530,7 +570,7 @@ export const runFileViewerLocalFilePreview = async ({ source, version, currentFi
|
|
|
530
570
|
};
|
|
531
571
|
}
|
|
532
572
|
catch (error) {
|
|
533
|
-
if (!isCurrent(version)) {
|
|
573
|
+
if (!isCurrent(version) || (controller === null || controller === void 0 ? void 0 : controller.signal.aborted)) {
|
|
534
574
|
return {
|
|
535
575
|
status: 'stale',
|
|
536
576
|
source: localSource,
|
|
@@ -547,6 +587,7 @@ export const runFileViewerLocalFilePreview = async ({ source, version, currentFi
|
|
|
547
587
|
};
|
|
548
588
|
}
|
|
549
589
|
finally {
|
|
590
|
+
requestController === null || requestController === void 0 ? void 0 : requestController.clearAbortController(controller);
|
|
550
591
|
finalizeFileViewerPreviewLoadState({
|
|
551
592
|
version,
|
|
552
593
|
isCurrent,
|
|
@@ -555,52 +596,106 @@ export const runFileViewerLocalFilePreview = async ({ source, version, currentFi
|
|
|
555
596
|
});
|
|
556
597
|
}
|
|
557
598
|
};
|
|
558
|
-
export const runFileViewerRemoteFilePreview = async ({ url, version, pageHref, streaming, previewTarget, requestController, isCurrent, downloadFile, mountRenderedContent, destroyRenderSession, buildLoadStartState, buildRenderCompleteState, i18n, onMarkLoadStarted, onStartLoading, onSetLoadingMessage, onSession, onActiveDocumentContext, onLifecycle, onClearLoadStarted, onStopLoading, onMissingData, onError, }) => {
|
|
559
|
-
|
|
599
|
+
export const runFileViewerRemoteFilePreview = async ({ url, version, pageHref, streaming, shouldStreamRemoteUrl, previewTarget, requestController, isCurrent, downloadFile, mountRenderedContent, destroyRenderSession, buildLoadStartState, buildRenderCompleteState, i18n, onMarkLoadStarted, onStartLoading, onSetLoadingMessage, onSession, onActiveDocumentContext, onLifecycle, onClearLoadStarted, onStopLoading, onMissingData, onError, }) => {
|
|
600
|
+
let remoteSource = resolveFileViewerRemoteSourcePlan({
|
|
560
601
|
pageHref,
|
|
561
602
|
streaming,
|
|
562
603
|
url,
|
|
563
604
|
});
|
|
564
605
|
const sourceUrl = remoteSource.url;
|
|
565
|
-
|
|
566
|
-
|
|
567
|
-
|
|
568
|
-
|
|
569
|
-
|
|
570
|
-
|
|
571
|
-
|
|
572
|
-
|
|
573
|
-
|
|
574
|
-
|
|
575
|
-
|
|
576
|
-
|
|
577
|
-
|
|
578
|
-
|
|
579
|
-
|
|
580
|
-
|
|
606
|
+
const controller = requestController.createAbortController();
|
|
607
|
+
let streamFinalized = false;
|
|
608
|
+
try {
|
|
609
|
+
if (!remoteSource.streamPdf && shouldStreamRemoteUrl) {
|
|
610
|
+
const streamDecision = await shouldStreamRemoteUrl({
|
|
611
|
+
url: sourceUrl,
|
|
612
|
+
filename: remoteSource.filename,
|
|
613
|
+
extension: remoteSource.extension,
|
|
614
|
+
pageHref,
|
|
615
|
+
signal: controller === null || controller === void 0 ? void 0 : controller.signal,
|
|
616
|
+
});
|
|
617
|
+
if (streamDecision) {
|
|
618
|
+
remoteSource = {
|
|
619
|
+
...remoteSource,
|
|
620
|
+
streamRenderer: true,
|
|
621
|
+
streamType: typeof streamDecision === 'string' ? streamDecision : remoteSource.extension,
|
|
622
|
+
};
|
|
623
|
+
}
|
|
624
|
+
}
|
|
625
|
+
if (!isCurrent(version) || (controller === null || controller === void 0 ? void 0 : controller.signal.aborted)) {
|
|
626
|
+
return {
|
|
627
|
+
status: 'stale',
|
|
628
|
+
remoteSource,
|
|
629
|
+
download: null,
|
|
630
|
+
read: null,
|
|
631
|
+
stream: null,
|
|
632
|
+
error: null,
|
|
633
|
+
};
|
|
634
|
+
}
|
|
635
|
+
commitFileViewerLoadStartState({
|
|
581
636
|
version,
|
|
582
637
|
filename: remoteSource.filename,
|
|
583
|
-
previewTarget,
|
|
584
|
-
|
|
585
|
-
|
|
586
|
-
destroyRenderSession,
|
|
587
|
-
buildRenderCompleteState: input => buildRenderCompleteState({
|
|
588
|
-
version: input.version,
|
|
638
|
+
filenameTarget: previewTarget,
|
|
639
|
+
buildState: () => buildLoadStartState({
|
|
640
|
+
version,
|
|
589
641
|
source: 'url',
|
|
590
642
|
sourceUrl,
|
|
591
643
|
}),
|
|
592
|
-
|
|
593
|
-
onStartLoading,
|
|
594
|
-
onSession,
|
|
595
|
-
onActiveDocumentContext,
|
|
644
|
+
onMarkLoadStarted,
|
|
596
645
|
onLifecycle,
|
|
597
|
-
|
|
598
|
-
onStopLoading,
|
|
599
|
-
onError: error => onError === null || onError === void 0 ? void 0 : onError(error, 'stream'),
|
|
646
|
+
onStartLoading,
|
|
600
647
|
});
|
|
601
|
-
if (
|
|
648
|
+
if (remoteSource.streamPdf || remoteSource.streamRenderer) {
|
|
649
|
+
const stream = await runFileViewerStreamingPdfPreview({
|
|
650
|
+
url: sourceUrl,
|
|
651
|
+
version,
|
|
652
|
+
filename: remoteSource.filename,
|
|
653
|
+
previewTarget,
|
|
654
|
+
isCurrent,
|
|
655
|
+
mountRenderedContent,
|
|
656
|
+
destroyRenderSession,
|
|
657
|
+
buildRenderCompleteState: (input) => buildRenderCompleteState({
|
|
658
|
+
version: input.version,
|
|
659
|
+
source: 'url',
|
|
660
|
+
sourceUrl,
|
|
661
|
+
}),
|
|
662
|
+
i18n,
|
|
663
|
+
loadingMessage: remoteSource.streamPdf
|
|
664
|
+
? undefined
|
|
665
|
+
: resolveFileViewerPreviewMessages(i18n).downloading,
|
|
666
|
+
signal: controller === null || controller === void 0 ? void 0 : controller.signal,
|
|
667
|
+
typeOverride: remoteSource.streamType,
|
|
668
|
+
onStartLoading,
|
|
669
|
+
onSession,
|
|
670
|
+
onActiveDocumentContext,
|
|
671
|
+
onLifecycle,
|
|
672
|
+
onClearLoadStarted,
|
|
673
|
+
onStopLoading,
|
|
674
|
+
onError: (error) => onError === null || onError === void 0 ? void 0 : onError(error, 'stream'),
|
|
675
|
+
});
|
|
676
|
+
streamFinalized = true;
|
|
677
|
+
if (stream.status === 'ready') {
|
|
678
|
+
return {
|
|
679
|
+
status: 'stream',
|
|
680
|
+
remoteSource,
|
|
681
|
+
download: null,
|
|
682
|
+
read: null,
|
|
683
|
+
stream,
|
|
684
|
+
error: null,
|
|
685
|
+
};
|
|
686
|
+
}
|
|
687
|
+
if (stream.status === 'error') {
|
|
688
|
+
return {
|
|
689
|
+
status: 'error',
|
|
690
|
+
remoteSource,
|
|
691
|
+
download: null,
|
|
692
|
+
read: null,
|
|
693
|
+
stream,
|
|
694
|
+
error: stream.error,
|
|
695
|
+
};
|
|
696
|
+
}
|
|
602
697
|
return {
|
|
603
|
-
status: '
|
|
698
|
+
status: 'stale',
|
|
604
699
|
remoteSource,
|
|
605
700
|
download: null,
|
|
606
701
|
read: null,
|
|
@@ -608,27 +703,6 @@ export const runFileViewerRemoteFilePreview = async ({ url, version, pageHref, s
|
|
|
608
703
|
error: null,
|
|
609
704
|
};
|
|
610
705
|
}
|
|
611
|
-
if (stream.status === 'error') {
|
|
612
|
-
return {
|
|
613
|
-
status: 'error',
|
|
614
|
-
remoteSource,
|
|
615
|
-
download: null,
|
|
616
|
-
read: null,
|
|
617
|
-
stream,
|
|
618
|
-
error: stream.error,
|
|
619
|
-
};
|
|
620
|
-
}
|
|
621
|
-
return {
|
|
622
|
-
status: 'stale',
|
|
623
|
-
remoteSource,
|
|
624
|
-
download: null,
|
|
625
|
-
read: null,
|
|
626
|
-
stream,
|
|
627
|
-
error: null,
|
|
628
|
-
};
|
|
629
|
-
}
|
|
630
|
-
const controller = requestController.createAbortController();
|
|
631
|
-
try {
|
|
632
706
|
const data = await downloadFile({
|
|
633
707
|
url: sourceUrl,
|
|
634
708
|
signal: controller === null || controller === void 0 ? void 0 : controller.signal,
|
|
@@ -671,7 +745,7 @@ export const runFileViewerRemoteFilePreview = async ({ url, version, pageHref, s
|
|
|
671
745
|
isCurrent,
|
|
672
746
|
mountRenderedContent,
|
|
673
747
|
destroyRenderSession,
|
|
674
|
-
buildRenderCompleteState: input => buildRenderCompleteState({
|
|
748
|
+
buildRenderCompleteState: (input) => buildRenderCompleteState({
|
|
675
749
|
version: input.version,
|
|
676
750
|
source: 'url',
|
|
677
751
|
file: input.file,
|
|
@@ -724,15 +798,17 @@ export const runFileViewerRemoteFilePreview = async ({ url, version, pageHref, s
|
|
|
724
798
|
}
|
|
725
799
|
finally {
|
|
726
800
|
requestController.clearAbortController(controller);
|
|
727
|
-
|
|
728
|
-
|
|
729
|
-
|
|
730
|
-
|
|
731
|
-
|
|
732
|
-
|
|
801
|
+
if (!streamFinalized) {
|
|
802
|
+
finalizeFileViewerPreviewLoadState({
|
|
803
|
+
version,
|
|
804
|
+
isCurrent,
|
|
805
|
+
onClearLoadStarted,
|
|
806
|
+
onStopLoading,
|
|
807
|
+
});
|
|
808
|
+
}
|
|
733
809
|
}
|
|
734
810
|
};
|
|
735
|
-
export const createFileViewerSourceLoadingActionHandlers = ({ getFile, getUrl, getCurrentFilename, getPdfStreaming, getI18n, getPageHref, previewTarget, requestController, downloadFile, mountRenderedContent, destroyRenderSession, buildLoadStartState, buildRenderCompleteState, formatErrorMessage, onMarkLoadStarted, onClearLoadStarted, onStartLoading, onSetLoadingMessage, onStopLoading, onShowError, onClearError, onResetLoading, onClearRenderedContent, onSession, onActiveDocumentContext, onLifecycle, }) => {
|
|
811
|
+
export const createFileViewerSourceLoadingActionHandlers = ({ getFile, getUrl, getCurrentFilename, shouldStreamLocalFile, getPdfStreaming, shouldStreamRemoteUrl, getI18n, getPageHref, previewTarget, requestController, downloadFile, mountRenderedContent, destroyRenderSession, buildLoadStartState, buildRenderCompleteState, formatErrorMessage, onMarkLoadStarted, onClearLoadStarted, onStartLoading, onSetLoadingMessage, onStopLoading, onShowError, onClearError, onResetLoading, onClearRenderedContent, onSession, onActiveDocumentContext, onLifecycle, }) => {
|
|
736
812
|
const isCurrentRequest = (version) => requestController.isCurrent(version);
|
|
737
813
|
const previewLocalFile = async (source, version) => {
|
|
738
814
|
var _a;
|
|
@@ -740,6 +816,8 @@ export const createFileViewerSourceLoadingActionHandlers = ({ getFile, getUrl, g
|
|
|
740
816
|
source,
|
|
741
817
|
version,
|
|
742
818
|
currentFilename: (_a = getCurrentFilename === null || getCurrentFilename === void 0 ? void 0 : getCurrentFilename()) !== null && _a !== void 0 ? _a : previewTarget.filename,
|
|
819
|
+
shouldStreamLocalFile,
|
|
820
|
+
requestController,
|
|
743
821
|
previewTarget,
|
|
744
822
|
isCurrent: isCurrentRequest,
|
|
745
823
|
mountRenderedContent,
|
|
@@ -778,6 +856,7 @@ export const createFileViewerSourceLoadingActionHandlers = ({ getFile, getUrl, g
|
|
|
778
856
|
version,
|
|
779
857
|
pageHref: getPageHref === null || getPageHref === void 0 ? void 0 : getPageHref(),
|
|
780
858
|
streaming: getPdfStreaming === null || getPdfStreaming === void 0 ? void 0 : getPdfStreaming(),
|
|
859
|
+
shouldStreamRemoteUrl,
|
|
781
860
|
i18n: getI18n === null || getI18n === void 0 ? void 0 : getI18n(),
|
|
782
861
|
previewTarget,
|
|
783
862
|
requestController,
|
|
@@ -955,22 +1034,33 @@ export const shouldStreamPdfUrl = ({ extension, pageHref, streaming, url, }) =>
|
|
|
955
1034
|
export const resolveFileViewerPageHref = (locationLike) => {
|
|
956
1035
|
return (locationLike === null || locationLike === void 0 ? void 0 : locationLike.href) || undefined;
|
|
957
1036
|
};
|
|
958
|
-
export const resolveFileViewerRemoteSourcePlan = ({ filename, fallbackFilename = DEFAULT_FILE_VIEWER_SOURCE_FILENAME, pageHref, streaming, url, }) => {
|
|
1037
|
+
export const resolveFileViewerRemoteSourcePlan = ({ filename, fallbackFilename = DEFAULT_FILE_VIEWER_SOURCE_FILENAME, pageHref, streaming, shouldStreamRemoteUrl, url, }) => {
|
|
959
1038
|
const sourceUrl = normalizeFileViewerSourceUrl(url) || url;
|
|
960
1039
|
const nextFilename = normalizeFilename(filename || url, fallbackFilename);
|
|
961
1040
|
const extension = getExtension(nextFilename);
|
|
1041
|
+
const streamPdf = pageHref
|
|
1042
|
+
? shouldStreamPdfUrl({
|
|
1043
|
+
extension,
|
|
1044
|
+
pageHref,
|
|
1045
|
+
streaming,
|
|
1046
|
+
url: sourceUrl,
|
|
1047
|
+
})
|
|
1048
|
+
: false;
|
|
1049
|
+
const streamDecision = !streamPdf
|
|
1050
|
+
? shouldStreamRemoteUrl === null || shouldStreamRemoteUrl === void 0 ? void 0 : shouldStreamRemoteUrl({
|
|
1051
|
+
url: sourceUrl,
|
|
1052
|
+
filename: nextFilename,
|
|
1053
|
+
extension,
|
|
1054
|
+
pageHref,
|
|
1055
|
+
})
|
|
1056
|
+
: false;
|
|
962
1057
|
return {
|
|
963
1058
|
url: sourceUrl,
|
|
964
1059
|
filename: nextFilename,
|
|
965
1060
|
extension,
|
|
966
|
-
streamPdf
|
|
967
|
-
|
|
968
|
-
|
|
969
|
-
pageHref,
|
|
970
|
-
streaming,
|
|
971
|
-
url: sourceUrl,
|
|
972
|
-
})
|
|
973
|
-
: false,
|
|
1061
|
+
streamPdf,
|
|
1062
|
+
streamRenderer: streamDecision === true || typeof streamDecision === 'string',
|
|
1063
|
+
streamType: typeof streamDecision === 'string' ? streamDecision : undefined,
|
|
974
1064
|
};
|
|
975
1065
|
};
|
|
976
1066
|
export const commitFileViewerRemoteDownloadState = ({ version, data, currentFilename, fallbackFilename, isCurrent, i18n, onMissingData, onSetLoadingMessage, }) => {
|
|
@@ -1,14 +1,10 @@
|
|
|
1
|
-
import type { FileViewerFileRef, FileViewerSource } from
|
|
1
|
+
import type { FileViewerFileRef, FileViewerSource } from "../contracts/types.js";
|
|
2
2
|
export type FileViewerPrecheckStatus = 'ready' | 'invalid' | 'unsupported';
|
|
3
3
|
export type FileViewerPrecheckReason = 'content-valid' | 'content-not-inspected' | 'content-inconclusive' | 'empty-structured-file' | 'signature-mismatch' | 'invalid-package' | 'missing-package-part' | 'unsupported-extension';
|
|
4
4
|
export interface FileViewerPrecheckOptions {
|
|
5
|
-
/** Filename used when a Blob or ArrayBuffer has no name. */
|
|
6
5
|
filename?: string;
|
|
7
|
-
/** Explicit extension, with or without a leading dot. */
|
|
8
6
|
type?: string;
|
|
9
|
-
/** Restricts the result to the renderers installed by the host application. */
|
|
10
7
|
supportedExtensions?: Iterable<string>;
|
|
11
|
-
/** Maximum ZIP central-directory bytes read from a Blob. Defaults to 8 MiB. */
|
|
12
8
|
maxPackageMetadataBytes?: number;
|
|
13
9
|
}
|
|
14
10
|
export interface FileViewerPrecheckResult {
|
|
@@ -17,7 +13,6 @@ export interface FileViewerPrecheckResult {
|
|
|
17
13
|
rendererId: string | null;
|
|
18
14
|
supported: boolean;
|
|
19
15
|
inspected: boolean;
|
|
20
|
-
/** `null` means the extension is supported but no structural validator exists. */
|
|
21
16
|
valid: boolean | null;
|
|
22
17
|
previewable: boolean;
|
|
23
18
|
status: FileViewerPrecheckStatus;
|
|
@@ -25,12 +20,5 @@ export interface FileViewerPrecheckResult {
|
|
|
25
20
|
missingParts: string[];
|
|
26
21
|
}
|
|
27
22
|
type FileViewerPrecheckInput = FileViewerSource | FileViewerFileRef;
|
|
28
|
-
/**
|
|
29
|
-
* Performs a cheap, renderer-free capability and structure check.
|
|
30
|
-
*
|
|
31
|
-
* This intentionally does not promise rendering fidelity. A `ready` result
|
|
32
|
-
* means the extension is available and any known container/signature checks
|
|
33
|
-
* passed; the real renderer remains the final authority for malformed content.
|
|
34
|
-
*/
|
|
35
23
|
export declare const precheckFileViewerSource: (input: FileViewerPrecheckInput, options?: FileViewerPrecheckOptions) => Promise<FileViewerPrecheckResult>;
|
|
36
24
|
export {};
|
package/dist/source/precheck.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import { DEFAULT_RENDERER_DEFINITIONS, DEFAULT_SUPPORTED_EXTENSIONS } from
|
|
2
|
-
import { getExtension, normalizeFileExtension, normalizeFilename, normalizeSource, } from
|
|
1
|
+
import { DEFAULT_RENDERER_DEFINITIONS, DEFAULT_SUPPORTED_EXTENSIONS } from "../registry/formats.js";
|
|
2
|
+
import { getExtension, normalizeFileExtension, normalizeFilename, normalizeSource, } from "./index.js";
|
|
3
3
|
const DEFAULT_MAX_PACKAGE_METADATA_BYTES = 8 * 1024 * 1024;
|
|
4
4
|
const ZIP_LOCAL_SIGNATURE = 0x04034b50;
|
|
5
5
|
const ZIP_CENTRAL_SIGNATURE = 0x02014b50;
|
|
@@ -203,13 +203,6 @@ const inspectStructuredContent = async (source, extension, maxPackageMetadataByt
|
|
|
203
203
|
}
|
|
204
204
|
return { inspected: false, valid: null, reason: 'content-not-inspected' };
|
|
205
205
|
};
|
|
206
|
-
/**
|
|
207
|
-
* Performs a cheap, renderer-free capability and structure check.
|
|
208
|
-
*
|
|
209
|
-
* This intentionally does not promise rendering fidelity. A `ready` result
|
|
210
|
-
* means the extension is available and any known container/signature checks
|
|
211
|
-
* passed; the real renderer remains the final authority for malformed content.
|
|
212
|
-
*/
|
|
213
206
|
export const precheckFileViewerSource = async (input, options = {}) => {
|
|
214
207
|
var _a;
|
|
215
208
|
const source = toSource(input, options);
|
|
@@ -1,5 +1,8 @@
|
|
|
1
|
-
export type
|
|
1
|
+
export type FileViewerSingleByteTextEncoding = 'iso-8859-1' | 'iso-8859-2' | 'iso-8859-15' | 'windows-1250' | 'windows-1251' | 'windows-1252';
|
|
2
|
+
export type FileViewerTextEncoding = 'auto' | 'utf-8' | 'utf-16le' | 'utf-16be' | 'gbk' | 'gb18030' | FileViewerSingleByteTextEncoding;
|
|
2
3
|
export type ResolvedFileViewerTextEncoding = Exclude<FileViewerTextEncoding, 'auto' | 'gbk'>;
|
|
4
|
+
export declare const DEFAULT_FILE_VIEWER_TEXT_FALLBACK_ENCODING: ResolvedFileViewerTextEncoding;
|
|
5
|
+
export declare const isSingleByteFileViewerTextEncoding: (encoding: string | undefined) => encoding is FileViewerSingleByteTextEncoding;
|
|
3
6
|
export interface DecodedFileViewerText {
|
|
4
7
|
text: string;
|
|
5
8
|
encoding: ResolvedFileViewerTextEncoding;
|
|
@@ -9,6 +12,6 @@ export interface ResolvedFileViewerTextSource {
|
|
|
9
12
|
bomLength: number;
|
|
10
13
|
}
|
|
11
14
|
export declare const isValidFileViewerUtf8: (bytes: Uint8Array) => boolean;
|
|
12
|
-
export declare const resolveFileViewerTextEncoding: (bytes: Uint8Array, encoding?: FileViewerTextEncoding | string) => ResolvedFileViewerTextSource;
|
|
15
|
+
export declare const resolveFileViewerTextEncoding: (bytes: Uint8Array, encoding?: FileViewerTextEncoding | string, fallbackEncoding?: FileViewerTextEncoding | string) => ResolvedFileViewerTextSource;
|
|
13
16
|
export declare const createFileViewerTextDecoder: (encoding: ResolvedFileViewerTextEncoding) => TextDecoder;
|
|
14
|
-
export declare const decodeFileViewerTextBuffer: (data: ArrayBuffer, encoding?: FileViewerTextEncoding | string) => DecodedFileViewerText;
|
|
17
|
+
export declare const decodeFileViewerTextBuffer: (data: ArrayBuffer, encoding?: FileViewerTextEncoding | string, fallbackEncoding?: FileViewerTextEncoding | string) => DecodedFileViewerText;
|
|
@@ -1,5 +1,44 @@
|
|
|
1
|
+
export const DEFAULT_FILE_VIEWER_TEXT_FALLBACK_ENCODING = 'gb18030';
|
|
2
|
+
const SINGLE_BYTE_ENCODING_ALIASES = new Map([
|
|
3
|
+
['iso-8859-1', 'iso-8859-1'],
|
|
4
|
+
['iso8859-1', 'iso-8859-1'],
|
|
5
|
+
['iso88591', 'iso-8859-1'],
|
|
6
|
+
['latin1', 'iso-8859-1'],
|
|
7
|
+
['latin-1', 'iso-8859-1'],
|
|
8
|
+
['l1', 'iso-8859-1'],
|
|
9
|
+
['cp819', 'iso-8859-1'],
|
|
10
|
+
['ibm819', 'iso-8859-1'],
|
|
11
|
+
['iso-8859-2', 'iso-8859-2'],
|
|
12
|
+
['iso8859-2', 'iso-8859-2'],
|
|
13
|
+
['iso88592', 'iso-8859-2'],
|
|
14
|
+
['latin2', 'iso-8859-2'],
|
|
15
|
+
['latin-2', 'iso-8859-2'],
|
|
16
|
+
['l2', 'iso-8859-2'],
|
|
17
|
+
['iso-8859-15', 'iso-8859-15'],
|
|
18
|
+
['iso8859-15', 'iso-8859-15'],
|
|
19
|
+
['iso885915', 'iso-8859-15'],
|
|
20
|
+
['latin9', 'iso-8859-15'],
|
|
21
|
+
['latin-9', 'iso-8859-15'],
|
|
22
|
+
['l9', 'iso-8859-15'],
|
|
23
|
+
['windows-1250', 'windows-1250'],
|
|
24
|
+
['windows1250', 'windows-1250'],
|
|
25
|
+
['cp1250', 'windows-1250'],
|
|
26
|
+
['x-cp1250', 'windows-1250'],
|
|
27
|
+
['windows-1251', 'windows-1251'],
|
|
28
|
+
['windows1251', 'windows-1251'],
|
|
29
|
+
['cp1251', 'windows-1251'],
|
|
30
|
+
['x-cp1251', 'windows-1251'],
|
|
31
|
+
['windows-1252', 'windows-1252'],
|
|
32
|
+
['windows1252', 'windows-1252'],
|
|
33
|
+
['cp1252', 'windows-1252'],
|
|
34
|
+
['x-cp1252', 'windows-1252']
|
|
35
|
+
]);
|
|
36
|
+
const SINGLE_BYTE_ENCODINGS = new Set(SINGLE_BYTE_ENCODING_ALIASES.values());
|
|
37
|
+
export const isSingleByteFileViewerTextEncoding = (encoding) => {
|
|
38
|
+
return encoding !== undefined && SINGLE_BYTE_ENCODINGS.has(encoding);
|
|
39
|
+
};
|
|
1
40
|
const normalizeEncoding = (encoding) => {
|
|
2
|
-
const normalized = String(encoding || 'auto').trim().toLowerCase().replace(
|
|
41
|
+
const normalized = String(encoding || 'auto').trim().toLowerCase().replace(/_/g, '-');
|
|
3
42
|
if (normalized === 'utf8' || normalized === 'utf-8') {
|
|
4
43
|
return 'utf-8';
|
|
5
44
|
}
|
|
@@ -15,13 +54,24 @@ const normalizeEncoding = (encoding) => {
|
|
|
15
54
|
if (normalized === 'gb18030') {
|
|
16
55
|
return 'gb18030';
|
|
17
56
|
}
|
|
57
|
+
const singleByte = SINGLE_BYTE_ENCODING_ALIASES.get(normalized);
|
|
58
|
+
if (singleByte) {
|
|
59
|
+
return singleByte;
|
|
60
|
+
}
|
|
18
61
|
return 'auto';
|
|
19
62
|
};
|
|
63
|
+
const toResolvedEncoding = (encoding) => {
|
|
64
|
+
return encoding === 'gbk' ? 'gb18030' : encoding;
|
|
65
|
+
};
|
|
66
|
+
const normalizeFallbackEncoding = (fallbackEncoding) => {
|
|
67
|
+
const normalized = normalizeEncoding(fallbackEncoding);
|
|
68
|
+
return normalized === 'auto'
|
|
69
|
+
? DEFAULT_FILE_VIEWER_TEXT_FALLBACK_ENCODING
|
|
70
|
+
: toResolvedEncoding(normalized);
|
|
71
|
+
};
|
|
20
72
|
const isContinuationByte = (value) => {
|
|
21
73
|
return value !== undefined && value >= 0x80 && value <= 0xbf;
|
|
22
74
|
};
|
|
23
|
-
// Validate bytes directly because older WebViews can accept the fatal option
|
|
24
|
-
// while still replacing malformed input. That would hide the GB18030 fallback.
|
|
25
75
|
export const isValidFileViewerUtf8 = (bytes) => {
|
|
26
76
|
for (let index = 0; index < bytes.length;) {
|
|
27
77
|
const first = bytes[index];
|
|
@@ -102,11 +152,11 @@ const inferBomlessUtf16 = (bytes) => {
|
|
|
102
152
|
}
|
|
103
153
|
return null;
|
|
104
154
|
};
|
|
105
|
-
export const resolveFileViewerTextEncoding = (bytes, encoding = 'auto') => {
|
|
155
|
+
export const resolveFileViewerTextEncoding = (bytes, encoding = 'auto', fallbackEncoding = DEFAULT_FILE_VIEWER_TEXT_FALLBACK_ENCODING) => {
|
|
106
156
|
const normalized = normalizeEncoding(encoding);
|
|
107
157
|
if (normalized !== 'auto') {
|
|
108
158
|
return {
|
|
109
|
-
encoding: normalized
|
|
159
|
+
encoding: toResolvedEncoding(normalized),
|
|
110
160
|
bomLength: normalized === 'utf-8' && bytes[0] === 0xef && bytes[1] === 0xbb && bytes[2] === 0xbf
|
|
111
161
|
? 3
|
|
112
162
|
: (normalized === 'utf-16le' && bytes[0] === 0xff && bytes[1] === 0xfe) ||
|
|
@@ -130,7 +180,7 @@ export const resolveFileViewerTextEncoding = (bytes, encoding = 'auto') => {
|
|
|
130
180
|
}
|
|
131
181
|
return isValidFileViewerUtf8(bytes)
|
|
132
182
|
? { encoding: 'utf-8', bomLength: 0 }
|
|
133
|
-
: { encoding:
|
|
183
|
+
: { encoding: normalizeFallbackEncoding(fallbackEncoding), bomLength: 0 };
|
|
134
184
|
};
|
|
135
185
|
export const createFileViewerTextDecoder = (encoding) => {
|
|
136
186
|
if (typeof TextDecoder === 'undefined') {
|
|
@@ -146,9 +196,9 @@ export const createFileViewerTextDecoder = (encoding) => {
|
|
|
146
196
|
throw error;
|
|
147
197
|
}
|
|
148
198
|
};
|
|
149
|
-
export const decodeFileViewerTextBuffer = (data, encoding = 'auto') => {
|
|
199
|
+
export const decodeFileViewerTextBuffer = (data, encoding = 'auto', fallbackEncoding = DEFAULT_FILE_VIEWER_TEXT_FALLBACK_ENCODING) => {
|
|
150
200
|
const bytes = new Uint8Array(data);
|
|
151
|
-
const resolved = resolveFileViewerTextEncoding(bytes, encoding);
|
|
201
|
+
const resolved = resolveFileViewerTextEncoding(bytes, encoding, fallbackEncoding);
|
|
152
202
|
return {
|
|
153
203
|
text: createFileViewerTextDecoder(resolved.encoding).decode(bytes.subarray(resolved.bomLength)),
|
|
154
204
|
encoding: resolved.encoding
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import type { FileViewerEventHandler, FileViewerInstance, FileViewerOptions, FileViewerRenderPurpose, RendererRegistry } from
|
|
1
|
+
import type { FileViewerEventHandler, FileViewerInstance, FileViewerOptions, FileViewerRenderPurpose, RendererRegistry } from "../contracts/types.js";
|
|
2
2
|
export interface CreateViewerOptions {
|
|
3
3
|
registry?: RendererRegistry;
|
|
4
4
|
options?: FileViewerOptions;
|