mirror of
https://github.com/yusufipk/OpenFrame.git
synced 2026-09-11 09:36:08 +00:00
feat: bulk video uploads and S3 asset video support (#18)
Add multi-file drag-and-drop queues for project videos and the assets pane, and route asset video uploads through S3/R2 when direct Bunny uploads are disabled.
This commit is contained in:
@@ -8,8 +8,10 @@ import { db } from '@/lib/db';
|
||||
import {
|
||||
extractImageFileNameFromProxyUrl,
|
||||
extractAudioFileNameFromProxyUrl,
|
||||
extractVideoFileNameFromProxyUrl,
|
||||
getVideoAssetAccessContext,
|
||||
} from '@/lib/video-assets';
|
||||
import { buildVideoObjectKey } from '@/lib/video-upload-validation';
|
||||
import { logError } from '@/lib/logger';
|
||||
|
||||
type RouteParams = { params: Promise<{ videoId: string; assetId: string }> };
|
||||
@@ -35,6 +37,16 @@ const AUDIO_CONTENT_TYPE_BY_EXTENSION: Record<string, string> = {
|
||||
};
|
||||
const BUNNY_ALLOWED_QUALITIES = new Set([2160, 1440, 1080, 720, 480, 360, 240]);
|
||||
|
||||
const VIDEO_CONTENT_TYPE_BY_EXTENSION: Record<string, string> = {
|
||||
mp4: 'video/mp4',
|
||||
webm: 'video/webm',
|
||||
ogg: 'video/ogg',
|
||||
mov: 'video/quicktime',
|
||||
m4v: 'video/mp4',
|
||||
mkv: 'video/x-matroska',
|
||||
avi: 'video/x-msvideo',
|
||||
};
|
||||
|
||||
function sanitizeFileName(value: string): string {
|
||||
const sanitized = value
|
||||
.replace(/[<>:"/\\|?*\u0000-\u001F]/g, '-')
|
||||
@@ -137,6 +149,29 @@ export async function GET(request: NextRequest, { params }: RouteParams) {
|
||||
});
|
||||
}
|
||||
|
||||
if (asset.provider === VideoAssetProvider.R2_VIDEO) {
|
||||
const fileName = extractVideoFileNameFromProxyUrl(asset.sourceUrl);
|
||||
if (!fileName) return apiErrors.badRequest('Invalid video asset URL');
|
||||
const key = buildVideoObjectKey(fileName);
|
||||
const ext = fileName.includes('.') ? fileName.slice(fileName.lastIndexOf('.')) : '.mp4';
|
||||
const downloadName = `${sanitizeFileName(asset.displayName)}${ext}`;
|
||||
const contentDisposition = buildContentDisposition(downloadName);
|
||||
const extKey = ext.replace('.', '');
|
||||
const contentType = VIDEO_CONTENT_TYPE_BY_EXTENSION[extKey] || 'video/mp4';
|
||||
|
||||
return proxyR2MediaObject({
|
||||
request,
|
||||
key,
|
||||
fallbackContentType: contentType,
|
||||
cacheControl: 'private, no-store',
|
||||
extraHeaders: {
|
||||
'Content-Disposition': contentDisposition,
|
||||
'X-Content-Type-Options': 'nosniff',
|
||||
},
|
||||
internalErrorMessage: 'Failed to retrieve video',
|
||||
});
|
||||
}
|
||||
|
||||
const sourceParam = request.nextUrl.searchParams.get('source');
|
||||
const rawQuality = request.nextUrl.searchParams.get('quality');
|
||||
const isPrepareOnly = request.nextUrl.searchParams.get('prepare') === '1';
|
||||
|
||||
Reference in New Issue
Block a user