aboutsummaryrefslogtreecommitdiff
path: root/src/server
diff options
context:
space:
mode:
Diffstat (limited to 'src/server')
-rw-r--r--src/server/ApiManagers/UploadManager.ts2
-rw-r--r--src/server/DashUploadUtils.ts48
-rw-r--r--src/server/SharedMediaTypes.ts38
3 files changed, 60 insertions, 28 deletions
diff --git a/src/server/ApiManagers/UploadManager.ts b/src/server/ApiManagers/UploadManager.ts
index 787e331c5..0b6e18743 100644
--- a/src/server/ApiManagers/UploadManager.ts
+++ b/src/server/ApiManagers/UploadManager.ts
@@ -86,7 +86,7 @@ export default class UploadManager extends ApiManager {
const videoId = JSON.parse(payload).videoId;
const results: Upload.FileResponse[] = [];
const result = await DashUploadUtils.uploadYoutube(videoId);
- result && !(result.result instanceof Error) && results.push(result);
+ result && results.push(result);
_success(res, results);
resolve();
});
diff --git a/src/server/DashUploadUtils.ts b/src/server/DashUploadUtils.ts
index ef7192ecc..28e26e51e 100644
--- a/src/server/DashUploadUtils.ts
+++ b/src/server/DashUploadUtils.ts
@@ -17,8 +17,6 @@ import { resolvedServerUrl } from './server_Initialization';
import { AcceptableMedia, Upload } from './SharedMediaTypes';
import request = require('request-promise');
import formidable = require('formidable');
-import { file } from 'jszip';
-import { csvParser } from './DataVizUtils';
const { exec } = require('child_process');
const parse = require('pdf-parse');
const ffmpeg = require('fluent-ffmpeg');
@@ -102,16 +100,41 @@ export namespace DashUploadUtils {
}
export function uploadYoutube(videoId: string): Promise<Upload.FileResponse> {
- console.log('UPLOAD ' + videoId);
return new Promise<Upload.FileResponse<Upload.FileInformation>>((res, rej) => {
- exec('youtube-dl -o ' + (videoId + '.mp4') + ' https://www.youtube.com/watch?v=' + videoId + ' -f "best[filesize<50M]"', (error: any, stdout: any, stderr: any) => {
- if (error) console.log(`error: ${error.message}`);
- else if (stderr) console.log(`stderr: ${stderr}`);
- else {
- console.log(`stdout: ${stdout}`);
- const data = { size: 0, path: videoId + '.mp4', name: videoId, type: 'video/mp4' };
- const file = { ...data, toJSON: () => ({ ...data, filename: data.path.replace(/.*\//, ''), mtime: null, length: 0, mime: '', toJson: () => undefined as any }) };
- res(MoveParsedFile(file, Directory.videos));
+ console.log('Uploading YouTube video: ' + videoId);
+ exec('youtube-dl -o ' + (videoId + '.mp4') + ' ' + videoId + ' -f "bestvideo[filesize<5M]+bestaudio/bestvideo+bestaudio"', (error: any, stdout: any, stderr: any) => {
+ if (error) {
+ console.log(`error: Error: ${error.message}`);
+ res({
+ source: {
+ size: 0,
+ path: videoId,
+ name: videoId,
+ type: '',
+ toJSON: () => ({ name: videoId, path: videoId }),
+ },
+ result: { name: 'failed youtube query', message: `Could not upload YouTube video (${videoId}). Error: ${error.message}` },
+ });
+ } else if (stderr) {
+ console.log(`stderr: StdError: ${stderr}`);
+ res({
+ source: {
+ size: 0,
+ path: videoId,
+ name: videoId,
+ type: '',
+ toJSON: () => ({ name: videoId, path: videoId }),
+ },
+ result: { name: 'failed youtube query', message: `Could not upload YouTube video (${videoId}). Error: ${stderr}` },
+ });
+ } else {
+ exec('youtube-dl -o ' + (videoId + '.mp4') + ' ' + videoId + ' --get-duration', (error: any, stdout: any, stderr: any) => {
+ const time = Array.from(stdout.trim().split(':')).reverse();
+ const duration = (time.length > 2 ? Number(time[2]) * 1000 * 60 : 0) + (time.length > 1 ? Number(time[1]) * 60 : 0) + (time.length > 0 ? Number(time[0]) : 0);
+ const data = { size: 0, path: videoId + '.mp4', name: videoId, type: 'video/mp4' };
+ const file = { ...data, toJSON: () => ({ ...data, filename: data.path.replace(/.*\//, ''), mtime: duration.toString(), mime: '', toJson: () => undefined as any }) };
+ res(MoveParsedFile(file, Directory.videos));
+ });
}
});
});
@@ -352,7 +375,7 @@ export namespace DashUploadUtils {
* @param suffix If the file doesn't have a suffix and you want to provide it one
* to appear in the new location
*/
- export async function MoveParsedFile(file: formidable.File, destination: Directory, suffix: string | undefined = undefined, text?: string): Promise<Upload.FileResponse> {
+ export async function MoveParsedFile(file: formidable.File, destination: Directory, suffix: string | undefined = undefined, text?: string, duration?: number): Promise<Upload.FileResponse> {
const { path: sourcePath } = file;
let name = path.basename(sourcePath);
suffix && (name += suffix);
@@ -368,6 +391,7 @@ export namespace DashUploadUtils {
agnostic: getAccessPaths(destination, name),
},
rawText: text,
+ duration,
},
});
});
diff --git a/src/server/SharedMediaTypes.ts b/src/server/SharedMediaTypes.ts
index cde95526f..7db1c2dae 100644
--- a/src/server/SharedMediaTypes.ts
+++ b/src/server/SharedMediaTypes.ts
@@ -2,36 +2,45 @@ import { ExifData } from 'exif';
import { File } from 'formidable';
export namespace AcceptableMedia {
- export const gifs = [".gif"];
- export const pngs = [".png"];
- export const jpgs = [".jpg", ".jpeg"];
- export const webps = [".webp"];
- export const tiffs = [".tiff"];
+ export const gifs = ['.gif'];
+ export const pngs = ['.png'];
+ export const jpgs = ['.jpg', '.jpeg'];
+ export const webps = ['.webp'];
+ export const tiffs = ['.tiff'];
export const imageFormats = [...pngs, ...jpgs, ...gifs, ...webps, ...tiffs];
- export const videoFormats = [".mov", ".mp4", ".quicktime", ".mkv", ".x-matroska;codecs=avc1"];
- export const applicationFormats = [".pdf"];
- export const audioFormats = [".wav", ".mp3", ".mpeg", ".flac", ".au", ".aiff", ".m4a", ".webm"];
+ export const videoFormats = ['.mov', '.mp4', '.quicktime', '.mkv', '.x-matroska;codecs=avc1'];
+ export const applicationFormats = ['.pdf'];
+ export const audioFormats = ['.wav', '.mp3', '.mpeg', '.flac', '.au', '.aiff', '.m4a', '.webm'];
}
export namespace Upload {
-
export function isImageInformation(uploadResponse: Upload.FileInformation): uploadResponse is Upload.ImageInformation {
- return "nativeWidth" in uploadResponse;
+ return 'nativeWidth' in uploadResponse;
+ }
+
+ export function isVideoInformation(uploadResponse: Upload.FileInformation): uploadResponse is Upload.VideoInformation {
+ return 'duration' in uploadResponse;
}
export interface FileInformation {
accessPaths: AccessPathInfo;
rawText?: string;
+ duration?: number;
}
- export type FileResponse<T extends FileInformation = FileInformation> = { source: File, result: T | Error };
+ export type FileResponse<T extends FileInformation = FileInformation> = { source: File; result: T | Error };
export type ImageInformation = FileInformation & InspectionResults;
+ export type VideoInformation = FileInformation & VideoResults;
+
export interface AccessPathInfo {
- [suffix: string]: { client: string, server: string };
+ [suffix: string]: { client: string; server: string };
}
+ export interface VideoResults {
+ duration: number;
+ }
export interface InspectionResults {
source: string;
requestable: string;
@@ -44,8 +53,7 @@ export namespace Upload {
}
export interface EnrichedExifData {
- data: ExifData & ExifData["gps"];
+ data: ExifData & ExifData['gps'];
error?: string;
}
-
-} \ No newline at end of file
+}