Test + Style

This commit is contained in:
Izuco 2021-10-28 19:32:34 +02:00
parent 255574df1b
commit 2c07f51f54
No known key found for this signature in database
GPG key ID: 41DFCB1835A5695E
14 changed files with 1560 additions and 1494 deletions

2
.eslintignore Normal file
View file

@ -0,0 +1,2 @@
lib
/videos/*.ts

View file

@ -1,23 +0,0 @@
name: eslint
on:
push:
branches: [ master ]
pull_request:
branches: [ master ]
jobs:
build:
runs-on: ubuntu-latest
strategy:
matrix:
node-version: [14.x]
steps:
- uses: actions/checkout@v2
- name: Use Node.js ${{ matrix.node-version }}
uses: actions/setup-node@v2
with:
node-version: ${{ matrix.node-version }}
cache: 'npm'
- run: npm i
- run: npx eslint .

33
.github/workflows/test.yml vendored Normal file
View file

@ -0,0 +1,33 @@
name: eslint
on:
push:
branches: [ master ]
pull_request:
branches: [ master ]
jobs:
eslint:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v2
- name: Use Node.js 14
uses: actions/setup-node@v2
with:
node-version: 14
cache: 'npm'
- run: npm i
- run: npx eslint .
test:
needs: eslint
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v2
- name: Use Node.js 14
uses: actions/setup-node@v2
with:
node-version: 14
cache: 'npm'
- run: npm i
- run: npm run test

39
@types/episode.d.ts vendored
View file

@ -59,20 +59,20 @@ export interface Value {
}
export enum Label {
Rating = "Rating",
RatingSystem = "Rating System",
ReleaseDate = "Release Date",
Synopsis = "Synopsis",
SynopsisType = "Synopsis Type",
Rating = 'Rating',
RatingSystem = 'Rating System',
ReleaseDate = 'Release Date',
Synopsis = 'Synopsis',
SynopsisType = 'Synopsis Type',
}
export enum MetaType {
Rating = "rating",
RatingSystemType = "RatingSystemType",
ReleaseDate = "release-date",
Synopsis = "synopsis",
Synopsistype = "synopsistype",
VideoRatingType = "VideoRatingType",
Rating = 'rating',
RatingSystemType = 'RatingSystemType',
ReleaseDate = 'release-date',
Synopsis = 'synopsis',
Synopsistype = 'synopsistype',
VideoRatingType = 'VideoRatingType',
}
export interface HistoricalSelections {
@ -87,8 +87,8 @@ export interface EpisodeDataIDS {
}
export enum TitleElement {
Empty = "",
English = "English",
Empty = '',
English = 'English',
}
export interface Media {
@ -194,8 +194,7 @@ export interface AvailIDS {
externalAlphaId: string;
}
export interface Next {
}
export type Next = Record<string, unknown>
export interface LanguageClass {
code: string;
@ -299,7 +298,7 @@ export interface CatalogParent {
}
export enum Source {
Dbb = "dbb",
Dbb = 'dbb',
}
export interface MetaItems {
@ -313,10 +312,10 @@ export interface Filters {
}
export interface Items {
"release-date": AnimationProductionStudio;
'release-date': AnimationProductionStudio;
rating: AnimationProductionStudio;
synopsis: AnimationProductionStudio;
"animation-production-studio": AnimationProductionStudio;
'animation-production-studio': AnimationProductionStudio;
}
export interface AnimationProductionStudio {
@ -366,8 +365,8 @@ export interface PreviousSeasonEpisode {
}
export enum Type {
Episode = "episode",
Ova = "ova",
Episode = 'episode',
Ova = 'ova',
}
export interface Quality {

View file

@ -2,7 +2,7 @@ declare module 'hls-download' {
export default class hlsDownload {
constructor(options: {
m3u8json: {
segments: {}[],
segments: Record<string, unknown>[],
mediaSequence?: number,
},
output?: string,

23
@types/items.d.ts vendored
View file

@ -39,8 +39,8 @@ export interface Item {
}
export enum ContentType {
Episode = "episode",
Ova = "ova",
Episode = 'episode',
Ova = 'ova',
}
export interface IDs {
@ -110,19 +110,18 @@ export interface MostRecentAvodIDS {
}
export enum Purchase {
AVOD = "A-VOD",
Dfov = "DFOV",
Est = "EST",
Svod = "SVOD",
AVOD = 'A-VOD',
Dfov = 'DFOV',
Est = 'EST',
Svod = 'SVOD',
}
export enum Version {
Simulcast = "Simulcast",
Uncut = "Uncut",
Simulcast = 'Simulcast',
Uncut = 'Uncut',
}
export interface MostRecentSvodJpnUs {
}
export type MostRecentSvodJpnUs = Record<string, any>
export interface QualityClass {
quality: QualityQuality;
@ -130,8 +129,8 @@ export interface QualityClass {
}
export enum QualityQuality {
HD = "HD",
SD = "SD",
HD = 'HD',
SD = 'SD',
}
export interface TitleImages {

View file

@ -32,17 +32,17 @@ declare module 'm3u8-parsed' {
uri: string,
timeline: number,
attributes: {
"CLOSED-CAPTIONS": string,
"AUDIO": string,
"FRAME-RATE": number,
"RESOLUTION": {
'CLOSED-CAPTIONS': string,
'AUDIO': string,
'FRAME-RATE': number,
'RESOLUTION': {
width: number,
height: number
},
"CODECS": string,
"AVERAGE-BANDWIDTH": string,
"BANDWIDTH": number
'CODECS': string,
'AVERAGE-BANDWIDTH': string,
'BANDWIDTH': number
}
}[],
}
};
}

1332
funi.ts

File diff suppressed because it is too large Load diff

View file

@ -5,69 +5,70 @@ import fs from 'fs-extra';
import pkg from '../package.json';
import modulesCleanup from 'removeNPMAbsolutePaths';
import { exec } from 'pkg';
import { execSync } from 'child_process';
const buildsDir = './_builds';
const nodeVer = 'node14-';
// main
(async function(){
const buildStr = `${pkg.name}-${pkg.version}`;
const acceptableBuilds = ['win64','linux64','macos64'];
const buildType = process.argv[2];
if(!acceptableBuilds.includes(buildType)){
console.error('[ERROR] unknown build type!');
process.exit(1);
}
await modulesCleanup('.');
if(!fs.existsSync(buildsDir)){
fs.mkdirSync(buildsDir);
}
const buildFull = `${buildStr}-${buildType}`;
const buildDir = `${buildsDir}/${buildFull}`;
if(fs.existsSync(buildDir)){
fs.removeSync(buildDir);
}
fs.mkdirSync(buildDir);
const buildConfig = [
pkg.main,
'--target', nodeVer + getTarget(buildType),
'--output', `${buildDir}/${pkg.short_name}`,
];
console.log(`[Build] Build configuration: ${buildFull}`);
try {
await exec(buildConfig);
}
catch(e){
console.log(e);
process.exit(1);
}
fs.mkdirSync(`${buildDir}/bin`);
fs.mkdirSync(`${buildDir}/config`);
fs.mkdirSync(`${buildDir}/videos`);
fs.copySync('./bin/', `${buildDir}/bin/`);
fs.copySync('./config/bin-path.yml', `${buildDir}/config/bin-path.yml`);
fs.copySync('./config/cli-defaults.yml', `${buildDir}/config/cli-defaults.yml`);
fs.copySync('./config/dir-path.yml', `${buildDir}/config/dir-path.yml`);
fs.copySync('./modules/cmd-here.bat', `${buildDir}/cmd-here.bat`);
fs.copySync('./modules/NotoSans-Regular.ttf', `${buildDir}/NotoSans-Regular.ttf`);
fs.copySync('./package.json', `${buildDir}/package.json`)
fs.copySync('./docs/', `${buildDir}/docs/`);
fs.copySync('./LICENSE.md', `${buildDir}/docs/LICENSE.md`);
if(fs.existsSync(`${buildsDir}/${buildFull}.7z`)){
fs.removeSync(`${buildsDir}/${buildFull}.7z`);
}
require('child_process').execSync(`7z a -t7z "${buildsDir}/${buildFull}.7z" "${buildDir}"`,{stdio:[0,1,2]});
const buildStr = `${pkg.name}-${pkg.version}`;
const acceptableBuilds = ['win64','linux64','macos64'];
const buildType = process.argv[2];
if(!acceptableBuilds.includes(buildType)){
console.error('[ERROR] unknown build type!');
process.exit(1);
}
await modulesCleanup('.');
if(!fs.existsSync(buildsDir)){
fs.mkdirSync(buildsDir);
}
const buildFull = `${buildStr}-${buildType}`;
const buildDir = `${buildsDir}/${buildFull}`;
if(fs.existsSync(buildDir)){
fs.removeSync(buildDir);
}
fs.mkdirSync(buildDir);
const buildConfig = [
pkg.main,
'--target', nodeVer + getTarget(buildType),
'--output', `${buildDir}/${pkg.short_name}`,
];
console.log(`[Build] Build configuration: ${buildFull}`);
try {
await exec(buildConfig);
}
catch(e){
console.log(e);
process.exit(1);
}
fs.mkdirSync(`${buildDir}/bin`);
fs.mkdirSync(`${buildDir}/config`);
fs.mkdirSync(`${buildDir}/videos`);
fs.copySync('./bin/', `${buildDir}/bin/`);
fs.copySync('./config/bin-path.yml', `${buildDir}/config/bin-path.yml`);
fs.copySync('./config/cli-defaults.yml', `${buildDir}/config/cli-defaults.yml`);
fs.copySync('./config/dir-path.yml', `${buildDir}/config/dir-path.yml`);
fs.copySync('./modules/cmd-here.bat', `${buildDir}/cmd-here.bat`);
fs.copySync('./modules/NotoSans-Regular.ttf', `${buildDir}/NotoSans-Regular.ttf`);
fs.copySync('./package.json', `${buildDir}/package.json`);
fs.copySync('./docs/', `${buildDir}/docs/`);
fs.copySync('./LICENSE.md', `${buildDir}/docs/LICENSE.md`);
if(fs.existsSync(`${buildsDir}/${buildFull}.7z`)){
fs.removeSync(`${buildsDir}/${buildFull}.7z`);
}
execSync(`7z a -t7z "${buildsDir}/${buildFull}.7z" "${buildDir}"`,{stdio:[0,1,2]});
}());
function getTarget(bt: string) : string {
switch(bt){
case 'win64':
return 'windows-x64';
case 'linux64':
return 'linux-x64';
case 'macos64':
return 'macos-x64';
default:
return 'windows-x64';
}
switch(bt){
case 'win64':
return 'windows-x64';
case 'linux64':
return 'linux-x64';
case 'macos64':
return 'macos-x64';
default:
return 'windows-x64';
}
}

View file

@ -1,12 +1,12 @@
import yargs from 'yargs';
const availableFilenameVars = [
'title',
'episode',
'showTitle',
'season',
'width',
'height'
'title',
'episode',
'showTitle',
'season',
'width',
'height'
];
export type possibleDubs = (
@ -22,241 +22,241 @@ const dubLang: possibleDubs = ['enUS', 'esLA', 'ptBR', 'zhMN', 'jaJP'];
const appArgv = (cfg: {
[key: string]: unknown
}) => {
// init
const parseDefault = <T = unknown>(key: string, _default: T) : T=> {
if (Object.prototype.hasOwnProperty.call(cfg, key)) {
return cfg[key] as T;
} else
return _default;
};
const argv = yargs.parserConfiguration({
'duplicate-arguments-array': true,
'camel-case-expansion': false
// init
const parseDefault = <T = unknown>(key: string, _default: T) : T=> {
if (Object.prototype.hasOwnProperty.call(cfg, key)) {
return cfg[key] as T;
} else
return _default;
};
const argv = yargs.parserConfiguration({
'duplicate-arguments-array': true,
'camel-case-expansion': false
})
// main
.wrap(Math.min(120)) // yargs.terminalWidth()
.help(false).version(false)
.usage('Usage: $0 [options]')
// auth
.option('auth', {
group: 'Authentication:',
describe: 'Enter authentication mode',
type: 'boolean',
})
// main
.wrap(Math.min(120)) // yargs.terminalWidth()
.help(false).version(false)
.usage('Usage: $0 [options]')
// auth
.option('auth', {
group: 'Authentication:',
describe: 'Enter authentication mode',
type: 'boolean',
})
// search
.option('search', {
alias: 'f',
group: 'Search:',
describe: 'Search show ids',
type: 'string',
})
// select show and eps
.option('s', {
group: 'Downloading:',
describe: 'Sets the show id',
type: 'number',
})
.option('e', {
group: 'Downloading:',
describe: 'Select episode ids (comma-separated, hyphen-sequence)',
type: 'string',
})
.option('all', {
group: 'Downloading:',
describe: 'Used to download all episodes from the show',
type: 'boolean',
default: parseDefault<boolean>('all', false)
})
.option('partsize', {
group: 'Downloading:',
describe: 'The amount of parts that should be downloaded in paralell',
type: 'number',
default: parseDefault<number>('partsize', 10)
})
// quality
.option('q', {
group: 'Downloading:',
describe: 'Select video layer (0 is max)',
choices: [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10],
default: parseDefault<number>('videoLayer', 7),
type: 'number',
})
// alt listing
.option('alt', {
group: 'Downloading:',
describe: 'Alternative episode listing (if available)',
default: parseDefault<boolean>('altList', false),
type: 'boolean',
})
// switch to subs
.option('dub', {
group: 'Downloading:',
describe: 'Download non-Japanese Dub (English Dub mode by default)',
choices: dubLang,
default: parseDefault<possibleDubs>('dub', ['enUS']),
type: 'array',
})
.option('subLang', {
group: 'Downloading:',
describe: 'Set the subtitle language (English is default and fallback)',
default: parseDefault<possibleSubs>('subLang', ['enUS']),
choices: subLang,
type: 'array'
})
.option('fontSize', {
group: 'Downloading:',
describe: 'Used to set the fontsize of the subtitles',
default: parseDefault<number>('fontSize', 55),
type: 'number'
})
.option('allSubs', {
group: 'Downloading:',
describe: 'If set to true, all available subs will get downloaded',
default: false,
type: 'boolean'
})
.option('allDubs', {
group: 'Downloading:',
describe: 'If set to true, all available dubs will get downloaded',
default: false,
type: 'boolean'
})
// simulcast
.option('simul', {
group: 'Downloading:',
describe: 'Force downloading simulcast ver. instead of uncut ver. (if uncut ver. available)',
default: parseDefault<boolean>('forceSimul', false),
type: 'boolean',
})
// server number
.option('x', {
alias: 'server',
group: 'Downloading:',
describe: 'Select server',
choices: [1, 2, 3, 4],
default: parseDefault<number>('nServer', 1),
type: 'number',
})
// skip
.option('noaudio', {
group: 'Downloading:',
describe: 'Skip downloading audio',
type: 'boolean'
})
.option('novids', {
group: 'Downloading:',
alias: 'skipdl',
describe: 'Skip downloading video',
type: 'boolean',
})
.option('nosubs', {
group: 'Downloading:',
describe: 'Skip downloading subtitles for English Dub (if available)',
type: 'boolean',
default: false
})
// proxy
.option('proxy', {
group: 'Proxy:',
describe: 'Set http(s)/socks proxy WHATWG url',
default: parseDefault<boolean>('proxy', false),
hidden: true,
})
.option('proxy-auth', {
group: 'Proxy:',
describe: 'Colon-separated username and password for proxy',
default: parseDefault<string|boolean>('proxy_auth', false),
hidden: true,
})
.option('ssp', {
group: 'Proxy:',
describe: 'Don\'t use proxy for stream and subtitles downloading',
default: parseDefault<boolean>('proxy_ssp', false),
hidden: true,
type: 'boolean',
})
// muxing
.option('skipmux', {
group: 'Muxing:',
describe: 'Skip muxing video and subtitles',
type: 'boolean',
})
.option('mp4', {
group: 'Muxing:',
describe: 'Mux into mp4',
default: parseDefault<boolean>('mp4mux', false),
type: 'boolean'
})
// filenaming
.option('fileName', {
group: 'Filename Template:',
describe: `Set the filename template. Use \${variable_name} to insert variables.\nYou may use ${availableFilenameVars
.map(a => `'${a}'`).join(', ')} as variables.`,
type: 'string',
default: parseDefault<string>('fileName', '[Funimation] ${showTitle} - ${episode} [${height}p]')
})
.option('numbers', {
group: 'Filename Template:',
describe: `Set how long a number in the title should be at least.\n${[[3, 5, '005'], [2, 1, '01'], [1, 20, '20']]
.map(val => `Set in config: ${val[0]}; Episode number: ${val[1]}; Output: ${val[2]}`).join('\n')}`,
type: 'number',
default: parseDefault<number>('numbers', 2)
})
// util
.option('nocleanup', {
group: 'Utilities:',
describe: 'Dont\'t delete the input files after muxing',
default: parseDefault<boolean>('noCleanUp', false),
type: 'boolean'
})
.option('timeout', {
group: 'Downloading:',
describe: 'Set the timeout of all download reqests. Set in millisecods',
type: 'number',
default: parseDefault('timeout', 60 * 1000)
})
.option('debug', {
group: 'Utilities:',
describe: 'Used to enter debug mode. Please use this flag when opening an issue to get more information'
// search
.option('search', {
alias: 'f',
group: 'Search:',
describe: 'Search show ids',
type: 'string',
})
// select show and eps
.option('s', {
group: 'Downloading:',
describe: 'Sets the show id',
type: 'number',
})
.option('e', {
group: 'Downloading:',
describe: 'Select episode ids (comma-separated, hyphen-sequence)',
type: 'string',
})
.option('all', {
group: 'Downloading:',
describe: 'Used to download all episodes from the show',
type: 'boolean',
default: parseDefault<boolean>('all', false)
})
.option('partsize', {
group: 'Downloading:',
describe: 'The amount of parts that should be downloaded in paralell',
type: 'number',
default: parseDefault<number>('partsize', 10)
})
// quality
.option('q', {
group: 'Downloading:',
describe: 'Select video layer (0 is max)',
choices: [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10],
default: parseDefault<number>('videoLayer', 7),
type: 'number',
})
// alt listing
.option('alt', {
group: 'Downloading:',
describe: 'Alternative episode listing (if available)',
default: parseDefault<boolean>('altList', false),
type: 'boolean',
})
// switch to subs
.option('dub', {
group: 'Downloading:',
describe: 'Download non-Japanese Dub (English Dub mode by default)',
choices: dubLang,
default: parseDefault<possibleDubs>('dub', ['enUS']),
type: 'array',
})
.option('subLang', {
group: 'Downloading:',
describe: 'Set the subtitle language (English is default and fallback)',
default: parseDefault<possibleSubs>('subLang', ['enUS']),
choices: subLang,
type: 'array'
})
.option('fontSize', {
group: 'Downloading:',
describe: 'Used to set the fontsize of the subtitles',
default: parseDefault<number>('fontSize', 55),
type: 'number'
})
.option('allSubs', {
group: 'Downloading:',
describe: 'If set to true, all available subs will get downloaded',
default: false,
type: 'boolean'
})
.option('allDubs', {
group: 'Downloading:',
describe: 'If set to true, all available dubs will get downloaded',
default: false,
type: 'boolean'
})
// simulcast
.option('simul', {
group: 'Downloading:',
describe: 'Force downloading simulcast ver. instead of uncut ver. (if uncut ver. available)',
default: parseDefault<boolean>('forceSimul', false),
type: 'boolean',
})
// server number
.option('x', {
alias: 'server',
group: 'Downloading:',
describe: 'Select server',
choices: [1, 2, 3, 4],
default: parseDefault<number>('nServer', 1),
type: 'number',
})
// skip
.option('noaudio', {
group: 'Downloading:',
describe: 'Skip downloading audio',
type: 'boolean'
})
.option('novids', {
group: 'Downloading:',
alias: 'skipdl',
describe: 'Skip downloading video',
type: 'boolean',
})
.option('nosubs', {
group: 'Downloading:',
describe: 'Skip downloading subtitles for English Dub (if available)',
type: 'boolean',
default: false
})
// proxy
.option('proxy', {
group: 'Proxy:',
describe: 'Set http(s)/socks proxy WHATWG url',
default: parseDefault<boolean>('proxy', false),
hidden: true,
})
.option('proxy-auth', {
group: 'Proxy:',
describe: 'Colon-separated username and password for proxy',
default: parseDefault<string|boolean>('proxy_auth', false),
hidden: true,
})
.option('ssp', {
group: 'Proxy:',
describe: 'Don\'t use proxy for stream and subtitles downloading',
default: parseDefault<boolean>('proxy_ssp', false),
hidden: true,
type: 'boolean',
})
// muxing
.option('skipmux', {
group: 'Muxing:',
describe: 'Skip muxing video and subtitles',
type: 'boolean',
})
.option('mp4', {
group: 'Muxing:',
describe: 'Mux into mp4',
default: parseDefault<boolean>('mp4mux', false),
type: 'boolean'
})
// filenaming
.option('fileName', {
group: 'Filename Template:',
describe: `Set the filename template. Use \${variable_name} to insert variables.\nYou may use ${availableFilenameVars
.map(a => `'${a}'`).join(', ')} as variables.`,
type: 'string',
default: parseDefault<string>('fileName', '[Funimation] ${showTitle} - ${episode} [${height}p]')
})
.option('numbers', {
group: 'Filename Template:',
describe: `Set how long a number in the title should be at least.\n${[[3, 5, '005'], [2, 1, '01'], [1, 20, '20']]
.map(val => `Set in config: ${val[0]}; Episode number: ${val[1]}; Output: ${val[2]}`).join('\n')}`,
type: 'number',
default: parseDefault<number>('numbers', 2)
})
// util
.option('nocleanup', {
group: 'Utilities:',
describe: 'Dont\'t delete the input files after muxing',
default: parseDefault<boolean>('noCleanUp', false),
type: 'boolean'
})
.option('timeout', {
group: 'Downloading:',
describe: 'Set the timeout of all download reqests. Set in millisecods',
type: 'number',
default: parseDefault('timeout', 60 * 1000)
})
.option('debug', {
group: 'Utilities:',
describe: 'Used to enter debug mode. Please use this flag when opening an issue to get more information'
+ '\n!Be careful! - Your token might be exposed so make sure to delete it!',
type: 'boolean',
default: false
})
// help
.option('help', {
alias: 'h',
group: 'Help:',
describe: 'Show this help',
type: 'boolean'
})
// usage
.example([
['$0 --search "My Hero"', 'search "My Hero" in title'],
['$0 -s 124389 -e 1,2,3', 'download episodes 1-3 from show with id 124389'],
['$0 -s 124389 -e 1-3,2-7,s1-2', 'download episodes 1-7 and "S"-episodes 1-2 from show with id 124389'],
])
type: 'boolean',
default: false
})
// help
.option('help', {
alias: 'h',
group: 'Help:',
describe: 'Show this help',
type: 'boolean'
})
// usage
.example([
['$0 --search "My Hero"', 'search "My Hero" in title'],
['$0 -s 124389 -e 1,2,3', 'download episodes 1-3 from show with id 124389'],
['$0 -s 124389 -e 1-3,2-7,s1-2', 'download episodes 1-7 and "S"-episodes 1-2 from show with id 124389'],
])
// --
.parseSync();
// --
.parseSync();
// Resolve unwanted arrays
if (argv.allDubs)
argv.dub = dubLang;
if (argv.allSubs)
argv.subLang = subLang;
for (let key in argv) {
if (argv[key] instanceof Array && !(key === 'subLang' || key === 'dub')) {
argv[key] = (argv[key] as Array<unknown>).pop();
}
if (argv.allDubs)
argv.dub = dubLang;
if (argv.allSubs)
argv.subLang = subLang;
for (const key in argv) {
if (argv[key] instanceof Array && !(key === 'subLang' || key === 'dub')) {
argv[key] = (argv[key] as Array<unknown>).pop();
}
return argv;
}
return argv;
};
const showHelp = yargs.showHelp;
export {
appArgv,
showHelp,
availableFilenameVars,
dubLang,
subLang
appArgv,
showHelp,
availableFilenameVars,
dubLang,
subLang
};

View file

@ -185,16 +185,16 @@ class Merger {
MKVmerge: undefined|string|false,
FFmpeg: undefined|string|false
} = {
MKVmerge: bin.mkvmerge,
FFmpeg: bin.ffmpeg,
MKVmerge: bin.mkvmerge,
FFmpeg: bin.ffmpeg,
};
if( !useMP4format && !merger.MKVmerge ){
console.log('[WARN] MKVMerge not found, skip using this...');
merger.MKVmerge = false;
console.log('[WARN] MKVMerge not found, skip using this...');
merger.MKVmerge = false;
}
if( !merger.MKVmerge && !merger.FFmpeg || useMP4format && !merger.FFmpeg ){
console.log('[WARN] FFmpeg not found, skip using this...');
merger.FFmpeg = false;
console.log('[WARN] FFmpeg not found, skip using this...');
merger.FFmpeg = false;
}
return merger;

953
package-lock.json generated

File diff suppressed because it is too large Load diff

View file

@ -1,7 +1,7 @@
{
"name": "funimation-downloader-nx",
"short_name": "funi",
"version": "4.12.5",
"version": "5.0.0",
"description": "Download videos from Funimation via cli.",
"keywords": [
"download",
@ -57,6 +57,8 @@
"build-macos64": "cd lib && node modules/build macos64",
"eslint": "eslint *.js modules",
"eslint-fix": "eslint *.js modules --fix",
"test": "echo \"Error: no test specified\" && exit 1"
"pretest": "npm run tsc",
"test": "cd lib && node modules/build win64 && node modules/build linux64 && node modules/build macos64"
}
}

32
tsc.ts
View file

@ -1,7 +1,7 @@
import { exec } from "child_process";
import fs from "fs";
import path from "path";
import { removeSync, copyFileSync } from "fs-extra";
import { exec } from 'child_process';
import fs from 'fs';
import path from 'path';
import { removeSync, copyFileSync } from 'fs-extra';
const ignore = [
'.git',
@ -13,29 +13,29 @@ const ignore = [
(async () => {
removeSync('lib');
const tsc = exec('npx tsc');
tsc.stdout?.on("data", console.log);
tsc.stderr?.on("data", console.log);
tsc.stdout?.on('data', console.log);
tsc.stderr?.on('data', console.log);
tsc.on("close", () => {
tsc.on('close', () => {
const files = readDir(__dirname);
const filtered = files.filter(a => {
if (a.stats.isFile()) {
return a.path.split('.').pop() !== 'ts';
} else {
return true
return true;
}
})
});
filtered.forEach(item => {
const itemPath = path.join(__dirname, 'lib', item.path.replace(__dirname, ''));
if (item.stats.isDirectory()) {
if (!fs.existsSync(itemPath))
fs.mkdirSync(itemPath)
fs.mkdirSync(itemPath);
} else {
copyFileSync(item.path, itemPath)
copyFileSync(item.path, itemPath);
}
})
})
})()
});
});
})();
const readDir = (dir: string) : {
path: string,
@ -56,8 +56,8 @@ const readDir = (dir: string) : {
stats
});
if (stats.isDirectory()) {
items.push(...readDir(itemPath))
items.push(...readDir(itemPath));
}
}
return items;
}
};