diff --git a/services/web/frontend/js/features/pdf-preview/components/pdf-js-viewer.tsx b/services/web/frontend/js/features/pdf-preview/components/pdf-js-viewer.tsx index b0fbb4cf93..e237ca3877 100644 --- a/services/web/frontend/js/features/pdf-preview/components/pdf-js-viewer.tsx +++ b/services/web/frontend/js/features/pdf-preview/components/pdf-js-viewer.tsx @@ -15,11 +15,10 @@ import { usePdfPreviewContext } from '@/features/pdf-preview/components/pdf-prev import usePresentationMode from '../hooks/use-presentation-mode' import useMouseWheelZoom from '../hooks/use-mouse-wheel-zoom' import { PDFJS } from '../util/pdf-js' -import { PDFFile } from '@ol-types/compile' type PdfJsViewerProps = { url: string - pdfFile: PDFFile + pdfFile: Record } function PdfJsViewer({ url, pdfFile }: PdfJsViewerProps) { diff --git a/services/web/frontend/js/features/pdf-preview/util/pdf-caching-transport.ts b/services/web/frontend/js/features/pdf-preview/util/pdf-caching-transport.js similarity index 83% rename from services/web/frontend/js/features/pdf-preview/util/pdf-caching-transport.ts rename to services/web/frontend/js/features/pdf-preview/util/pdf-caching-transport.js index ea1a137abb..f568c634a4 100644 --- a/services/web/frontend/js/features/pdf-preview/util/pdf-caching-transport.ts +++ b/services/web/frontend/js/features/pdf-preview/util/pdf-caching-transport.js @@ -15,7 +15,6 @@ import { debugConsole } from '@/utils/debugging' import { PDFJS } from './pdf-js' import { sendMB } from '@/infrastructure/event-tracking' import getMeta from '@/utils/meta' -import { PDFFile, PDFRange } from '@ol-types/compile' // 30 seconds: The shutdown grace period of a clsi pre-emp instance. const STALE_OUTPUT_REQUEST_THRESHOLD_MS = 30 * 1000 @@ -52,26 +51,7 @@ export function generatePdfCachingTransportFactory() { new URLSearchParams(window.location.search).get('verify_chunks') === 'true' class PDFDataRangeTransport extends PDFJS.PDFDataRangeTransport { - url: string - pdfFile: PDFFile - abortController: AbortController - leanPdfRanges: PDFRange[] - handleFetchError: (error: any) => void - startTime: number - sentEventFallbackToClsiCache: boolean - queryForChunks: string - - constructor({ - url, - pdfFile, - abortController, - handleFetchError, - }: { - url: string - pdfFile: PDFFile - abortController: AbortController - handleFetchError: (error: any) => void - }) { + constructor({ url, pdfFile, abortController, handleFetchError }) { super(pdfFile.size, new Uint8Array()) this.url = url pdfFile.ranges = pdfFile.ranges || [] @@ -95,7 +75,7 @@ export function generatePdfCachingTransportFactory() { this.abortController.abort() } - requestDataRange(start: number, end: number) { + requestDataRange(start, end) { let recordFallbackToClsiCache = false const abortSignal = this.abortController.signal const getDebugInfo = () => ({ @@ -115,12 +95,9 @@ export function generatePdfCachingTransportFactory() { const isStaleOutputRequest = () => performance.now() - this.startTime > STALE_OUTPUT_REQUEST_THRESHOLD_MS - const is404 = (err: any) => - (OError.getFullInfo(err) as { statusCode: number }).statusCode === 404 - const isFromOutputPDFRequest = (err: any) => - (OError.getFullInfo(err) as { url?: string }).url?.includes?.( - '/output.pdf' - ) === true + const is404 = err => OError.getFullInfo(err).statusCode === 404 + const isFromOutputPDFRequest = err => + OError.getFullInfo(err).url?.includes?.('/output.pdf') === true // Do not consider "expected 404s" and network errors as pdf caching // failures. @@ -129,11 +106,11 @@ export function generatePdfCachingTransportFactory() { // Example: The user returns to a browser tab after 1h and scrolls. // - requests for the main output.pdf file // A fallback request would not be able to retrieve the PDF either. - const isExpectedError = (err: any) => + const isExpectedError = err => (is404(err) || isNetworkError(err)) && (isStaleOutputRequest() || isFromOutputPDFRequest(err)) - const usesCache = (url: string) => { + const usesCache = url => { if (!url) return false const u = new URL(url) return ( @@ -144,10 +121,10 @@ export function generatePdfCachingTransportFactory() { u.searchParams.get('clsiserverid')?.startsWith('clsi-cache-')) ) } - const canTryFromCache = (err: any) => { + const canTryFromCache = err => { if (!fallBackToClsiCache) return false if (!is404(err)) return false - return !usesCache((OError.getFullInfo(err) as { url: string }).url) + return !usesCache(OError.getFullInfo(err).url) } const getOutputPDFURLFromCache = () => { if (usesCache(this.url)) return this.url @@ -180,10 +157,7 @@ export function generatePdfCachingTransportFactory() { return blob }) .catch(err => { - const { statusCode, url } = OError.getFullInfo(err) as { - statusCode: number - url: string - } + const { statusCode, url } = OError.getFullInfo(err) throw OError.tag( new PDFJS.ResponseException(undefined, statusCode, true), 'cache-fallback', @@ -192,8 +166,6 @@ export function generatePdfCachingTransportFactory() { }) } - // @ts-ignore is incorrectly inferring the type of fetchRange. - // Remove this when we convert pdf-caching.js to typescript. fetchRange({ url: this.url, start, @@ -225,10 +197,7 @@ export function generatePdfCachingTransportFactory() { metrics.failedCount++ metrics.failedOnce = true } - const { statusCode, url } = OError.getFullInfo(err) as { - statusCode: number - url: string - } + const { statusCode, url } = OError.getFullInfo(err) throw OError.tag( new PDFJS.ResponseException(undefined, statusCode, true), 'caching', @@ -257,10 +226,7 @@ export function generatePdfCachingTransportFactory() { }).catch(err => { if (canTryFromCache(err)) return fetchFromCache() if (isExpectedError(err)) { - const { statusCode, url } = OError.getFullInfo(err) as { - statusCode: number - url: string - } + const { statusCode, url } = OError.getFullInfo(err) throw OError.tag( new PDFJS.ResponseException(undefined, statusCode, true), 'fallback', @@ -280,7 +246,7 @@ export function generatePdfCachingTransportFactory() { ageMS: Math.ceil(performance.now() - this.startTime), }) } - this.onDataRange(start, blob ?? null) + this.onDataRange(start, blob) }) .catch(err => { if (abortSignal.aborted) return @@ -300,17 +266,7 @@ export function generatePdfCachingTransportFactory() { } } - return function ({ - url, - pdfFile, - abortController, - handleFetchError, - }: { - url: string - pdfFile: PDFFile - abortController: AbortController - handleFetchError: (error: any) => void - }) { + return function ({ url, pdfFile, abortController, handleFetchError }) { if (metrics.failedOnce) { // Disable pdf caching once any fetch request failed. // Be trigger-happy here until we reached a stable state of the feature. diff --git a/services/web/frontend/js/features/pdf-preview/util/pdf-caching.js b/services/web/frontend/js/features/pdf-preview/util/pdf-caching.js index 3e4b4607be..c3dba41d8b 100644 --- a/services/web/frontend/js/features/pdf-preview/util/pdf-caching.js +++ b/services/web/frontend/js/features/pdf-preview/util/pdf-caching.js @@ -516,7 +516,7 @@ export async function fallbackRequest({ file, url, start, end, abortSignal }) { const init = getDynamicChunkInit({ file, start, end, signal: abortSignal }) const response = await fetchWithBrowserCacheFallback(url, init) checkChunkResponse(response, end - start, init) - return await response.bytes() + return await response.arrayBuffer() } catch (e) { throw OError.tag(e, 'fallback request failed', { url, start, end }) } diff --git a/services/web/frontend/js/features/pdf-preview/util/pdf-js-wrapper.ts b/services/web/frontend/js/features/pdf-preview/util/pdf-js-wrapper.ts index 5c73bee2b9..9f6ba7316a 100644 --- a/services/web/frontend/js/features/pdf-preview/util/pdf-js-wrapper.ts +++ b/services/web/frontend/js/features/pdf-preview/util/pdf-js-wrapper.ts @@ -9,7 +9,6 @@ import { } from 'pdfjs-dist/web/pdf_viewer.mjs' import 'pdfjs-dist/web/pdf_viewer.css' import browser from '@/features/source-editor/extensions/browser' -import { PDFFile } from '@ol-types/compile' const DEFAULT_RANGE_CHUNK_SIZE = 128 * 1024 // 128K chunks @@ -56,7 +55,7 @@ export default class PDFJSWrapper { handleFetchError, }: { url: string - pdfFile: PDFFile + pdfFile: Record abortController: AbortController handleFetchError: (error: any) => void }) { diff --git a/services/web/types/compile.ts b/services/web/types/compile.ts index 469695d292..35a294756c 100644 --- a/services/web/types/compile.ts +++ b/services/web/types/compile.ts @@ -1,38 +1,22 @@ -export type PDFRange = { - objectId: Uint8Array - end: number - hash: string - size: number - start: number - totalUsage: number -} - -type OutputFileBase = { +export type CompileOutputFile = { path: string url: string + downloadURL?: string type: string build: string - downloadURL: string + ranges?: { + start: number + end: number + hash: string + objectId: string + }[] + contentId?: string + size?: number // assigned by buildFileList in frontend main?: boolean } -export type PDFFile = OutputFileBase & { - clsiCacheShard: string - contentId: string - createdAt: Date - editorId: string - pdfDownloadURL: string - pdfURL: string - prefetched: any[] - preprocessed: boolean - ranges: PDFRange[] - size: number -} - -export type CompileOutputFile = OutputFileBase | PDFFile - export type CompileResponseData = { fromCache?: boolean status: string