fix: various fixes to sentry-reported errors and more
This commit is contained in:
@@ -169,20 +169,21 @@ export function DownloadController(routes: Hono<HonoEnv>): void {
|
||||
operationId: 'download_file',
|
||||
summary: 'Download file',
|
||||
responseSchema: null,
|
||||
statusCode: 200,
|
||||
statusCode: 302,
|
||||
security: [],
|
||||
tags: ['Downloads'],
|
||||
description: 'Downloads files from the download service with support for range requests and caching.',
|
||||
description: 'Redirects to a presigned URL for the requested file.',
|
||||
}),
|
||||
async (ctx) => {
|
||||
const response = await ctx.get('downloadService').streamDownload({
|
||||
const url = await ctx.get('downloadService').resolveDownloadRedirect({
|
||||
path: ctx.req.path,
|
||||
rangeHeader: ctx.req.header('range'),
|
||||
});
|
||||
if (!response) {
|
||||
if (!url) {
|
||||
return ctx.text('Not Found', 404);
|
||||
}
|
||||
return response;
|
||||
const res = ctx.redirect(url, 302);
|
||||
res.headers.set('Cache-Control', 'public, max-age=300');
|
||||
return res;
|
||||
},
|
||||
);
|
||||
}
|
||||
|
||||
@@ -415,7 +415,7 @@ export class DownloadService {
|
||||
return null;
|
||||
}
|
||||
|
||||
async streamDownload(params: {path: string; rangeHeader?: string | null}): Promise<Response | null> {
|
||||
async resolveDownloadRedirect(params: {path: string}): Promise<string | null> {
|
||||
const key = this.buildKeyFromPath(params.path);
|
||||
if (!key) {
|
||||
return null;
|
||||
@@ -429,20 +429,13 @@ export class DownloadService {
|
||||
|
||||
for (const candidateKey of keysToTry) {
|
||||
try {
|
||||
const streamResult = await this.storageService.streamObject({
|
||||
bucket: Config.s3.buckets.downloads,
|
||||
key: candidateKey,
|
||||
range: params.rangeHeader ?? undefined,
|
||||
});
|
||||
|
||||
if (!streamResult) {
|
||||
continue;
|
||||
const metadata = await this.storageService.getObjectMetadata(Config.s3.buckets.downloads, candidateKey);
|
||||
if (metadata) {
|
||||
return this.storageService.getPresignedDownloadURL({
|
||||
bucket: Config.s3.buckets.downloads,
|
||||
key: candidateKey,
|
||||
});
|
||||
}
|
||||
|
||||
const headers = this.buildDownloadHeaders(streamResult);
|
||||
const status = streamResult.contentRange ? 206 : 200;
|
||||
const body = Readable.toWeb(streamResult.body);
|
||||
return new Response(body as ReadableStream, {headers, status});
|
||||
} catch (error) {
|
||||
if (error instanceof S3ServiceException && (error.name === 'NoSuchKey' || error.name === 'NotFound')) {
|
||||
continue;
|
||||
@@ -681,26 +674,4 @@ export class DownloadService {
|
||||
const [, prefix, , , arch, suffix] = match;
|
||||
return `${prefix}/${arch}${suffix}`;
|
||||
}
|
||||
|
||||
private buildDownloadHeaders(metadata: {
|
||||
contentLength: number;
|
||||
contentType?: string | null;
|
||||
contentRange?: string | null;
|
||||
}): Headers {
|
||||
const headers = new Headers();
|
||||
if (metadata.contentType) {
|
||||
headers.set('Content-Type', metadata.contentType);
|
||||
} else {
|
||||
headers.set('Content-Type', 'application/octet-stream');
|
||||
}
|
||||
headers.set('Content-Length', metadata.contentLength.toString());
|
||||
if (metadata.contentRange) {
|
||||
headers.set('Content-Range', metadata.contentRange);
|
||||
headers.set('Accept-Ranges', 'bytes');
|
||||
} else {
|
||||
headers.set('Accept-Ranges', 'bytes');
|
||||
}
|
||||
headers.set('Cache-Control', 'public, max-age=86400');
|
||||
return headers;
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user