mirror of
https://github.com/xuthus83/pigallery2.git
synced 2025-01-14 14:43:17 +08:00
improving benchmark
This commit is contained in:
parent
d2cdc32c68
commit
03789ecaf8
39
benchmark/BMConfig.ts
Normal file
39
benchmark/BMConfig.ts
Normal file
@ -0,0 +1,39 @@
|
||||
/* tslint:disable:no-inferrable-types */
|
||||
import * as path from 'path';
|
||||
import {ConfigClass, ConfigClassBuilder} from 'typeconfig/node';
|
||||
import {ConfigProperty} from 'typeconfig/common';
|
||||
|
||||
|
||||
@ConfigClass({
|
||||
configPath: path.join(__dirname, './../bm_config.json'),
|
||||
saveIfNotExist: true,
|
||||
attachDescription: true,
|
||||
enumsAsString: true,
|
||||
softReadonly: true,
|
||||
cli: {
|
||||
enable: {
|
||||
configPath: true,
|
||||
attachState: true,
|
||||
attachDescription: true,
|
||||
rewriteCLIConfig: true,
|
||||
rewriteENVConfig: true,
|
||||
enumsAsString: true,
|
||||
saveIfNotExist: true,
|
||||
exitOnConfig: true
|
||||
},
|
||||
defaults: {
|
||||
enabled: true
|
||||
}
|
||||
}
|
||||
})
|
||||
export class PrivateConfigClass {
|
||||
@ConfigProperty({description: 'Images are loaded from this folder (read permission required)'})
|
||||
path: string = 'demo/images';
|
||||
@ConfigProperty({description: 'Describe your system setup'})
|
||||
system: string = '';
|
||||
|
||||
|
||||
}
|
||||
|
||||
export const BMConfig = ConfigClassBuilder.attachInterface(new PrivateConfigClass());
|
||||
BMConfig.loadSync();
|
@ -11,6 +11,9 @@ import {Utils} from '../src/common/Utils';
|
||||
import {GalleryManager} from '../src/backend/model/database/sql/GalleryManager';
|
||||
import {DirectoryDTO} from '../src/common/entities/DirectoryDTO';
|
||||
import {ServerConfig} from '../src/common/config/private/PrivateConfig';
|
||||
import {ProjectPath} from '../src/backend/ProjectPath';
|
||||
import {PersonMWs} from '../src/backend/middlewares/PersonMWs';
|
||||
import {ThumbnailGeneratorMWs} from '../src/backend/middlewares/thumbnail/ThumbnailGeneratorMWs';
|
||||
|
||||
const rimrafPR = util.promisify(rimraf);
|
||||
|
||||
@ -30,7 +33,7 @@ export class BMIndexingManager extends IndexingManager {
|
||||
|
||||
export class Benchmarks {
|
||||
|
||||
constructor(public RUNS: number, public dbFolder: string) {
|
||||
constructor(public RUNS: number) {
|
||||
|
||||
}
|
||||
|
||||
@ -52,6 +55,20 @@ export class Benchmarks {
|
||||
return await this.benchmark(() => gm.listDirectory('./'));
|
||||
}
|
||||
|
||||
async bmListPersons(): Promise<BenchmarkResult> {
|
||||
await this.setupDB();
|
||||
Config.Server.Indexing.reIndexingSensitivity = ServerConfig.ReIndexingSensitivity.low;
|
||||
return await this.benchmark(async () => {
|
||||
await ObjectManagers.reset();
|
||||
const req = {resultPipe: <any>null};
|
||||
await this.nextToPromise(PersonMWs.listPersons, req, null);
|
||||
await this.nextToPromise(PersonMWs.addSamplePhotoForAll, req, null);
|
||||
await this.nextToPromise(ThumbnailGeneratorMWs.addThumbnailInfoForPersons, req, null);
|
||||
await this.nextToPromise(PersonMWs.removeSamplePhotoForAll, req, null);
|
||||
return req.resultPipe;
|
||||
});
|
||||
}
|
||||
|
||||
async bmAllSearch(text: string): Promise<{ result: BenchmarkResult, searchType: SearchTypes }[]> {
|
||||
await this.setupDB();
|
||||
const types = Utils.enumToArray(SearchTypes).map(a => a.key).concat([null]);
|
||||
@ -75,6 +92,16 @@ export class Benchmarks {
|
||||
return await this.benchmark(() => sm.autocomplete(text));
|
||||
}
|
||||
|
||||
private nextToPromise(fn: (req: any, res: any, next: Function) => void, request: any, response: any) {
|
||||
return new Promise<void>((resolve, reject) => {
|
||||
fn(request, resolve, (err?: any) => {
|
||||
if (err) {
|
||||
return reject(err);
|
||||
}
|
||||
resolve();
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
private async benchmark(fn: () => Promise<{ media: any[], directories: any[] } | any[] | void>,
|
||||
beforeEach: () => Promise<any> = null,
|
||||
@ -122,9 +149,8 @@ export class Benchmarks {
|
||||
|
||||
private resetDB = async () => {
|
||||
await SQLConnection.close();
|
||||
await rimrafPR(this.dbFolder);
|
||||
await rimrafPR(ProjectPath.DBFolder);
|
||||
Config.Server.Database.type = ServerConfig.DatabaseType.sqlite;
|
||||
Config.Server.Database.dbFolder = this.dbFolder;
|
||||
await ObjectManagers.InitSQLManagers();
|
||||
};
|
||||
|
||||
|
@ -5,10 +5,12 @@ import {BenchmarkResult, Benchmarks} from './Benchmarks';
|
||||
import {SearchTypes} from '../src/common/entities/AutoCompleteItem';
|
||||
import {Utils} from '../src/common/Utils';
|
||||
import {DiskMangerWorker} from '../src/backend/model/threading/DiskMangerWorker';
|
||||
import {BMConfig} from './BMConfig';
|
||||
import {GalleryManager} from '../src/backend/model/database/sql/GalleryManager';
|
||||
|
||||
const config: { path: string, system: string } = require(path.join(__dirname, 'config.json'));
|
||||
Config.Server.Media.folder = config.path;
|
||||
const dbFolder = __dirname;
|
||||
|
||||
Config.Server.Media.folder = BMConfig.path;
|
||||
const dbFolder = path.join(__dirname, './../');
|
||||
ProjectPath.reset();
|
||||
const RUNS = 50;
|
||||
|
||||
@ -23,8 +25,9 @@ const printHeader = async () => {
|
||||
', ' + Utils.zeroPrefix(dt.getDate(), 2) +
|
||||
'.' + Utils.zeroPrefix(dt.getMonth() + 1, 2) +
|
||||
'.' + dt.getFullYear());
|
||||
printLine('**System**: ' + config.system);
|
||||
printLine('**System**: ' + BMConfig.system);
|
||||
const dir = await DiskMangerWorker.scanDirectory('./');
|
||||
const gm = new GalleryManager();
|
||||
printLine('**Gallery**: directories: ' +
|
||||
dir.directories.length +
|
||||
' media: ' + dir.media.length +
|
||||
@ -52,7 +55,7 @@ const printResult = (result: BenchmarkResult, action: string, actionDetails: str
|
||||
|
||||
const run = async () => {
|
||||
const start = Date.now();
|
||||
const bm = new Benchmarks(RUNS, dbFolder);
|
||||
const bm = new Benchmarks(RUNS);
|
||||
|
||||
// header
|
||||
await printHeader();
|
||||
@ -60,6 +63,7 @@ const run = async () => {
|
||||
printResult(await bm.bmScanDirectory(), 'Scanning directory');
|
||||
printResult(await bm.bmSaveDirectory(), 'Saving directory');
|
||||
printResult(await bm.bmListDirectory(), 'Listing Directory');
|
||||
printResult(await bm.bmListPersons(), 'Listing Faces');
|
||||
(await bm.bmAllSearch('a')).forEach(res => {
|
||||
if (res.searchType !== null) {
|
||||
printResult(res.result, 'searching', '`a` as `' + SearchTypes[res.searchType] + '`');
|
||||
|
@ -146,7 +146,7 @@
|
||||
"@ffprobe-installer/ffprobe": "1.1.0",
|
||||
"bcrypt": "5.0.0",
|
||||
"mysql": "2.18.1",
|
||||
"sharp": "0.27.0"
|
||||
"sharp": "0.23.4"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=10.17 <15.0"
|
||||
|
@ -9,6 +9,7 @@ class ProjectPathClass {
|
||||
public TranscodedFolder: string;
|
||||
public FacesFolder: string;
|
||||
public FrontendFolder: string;
|
||||
public DBFolder: string;
|
||||
|
||||
constructor() {
|
||||
this.reset();
|
||||
@ -33,6 +34,7 @@ class ProjectPathClass {
|
||||
this.TempFolder = this.getAbsolutePath(Config.Server.Media.tempFolder);
|
||||
this.TranscodedFolder = path.join(this.TempFolder, 'tc');
|
||||
this.FacesFolder = path.join(this.TempFolder, 'f');
|
||||
this.DBFolder = this.getAbsolutePath(Config.Server.Database.dbFolder);
|
||||
|
||||
// create thumbnail folder if not exist
|
||||
if (!fs.existsSync(this.TempFolder)) {
|
||||
|
@ -97,6 +97,6 @@ export class PersonMWs {
|
||||
}
|
||||
|
||||
|
||||
export interface PersonWithPhoto extends PersonDTO {
|
||||
export interface PersonWithPhoto extends PersonDTO {
|
||||
samplePhoto: PhotoDTO;
|
||||
}
|
||||
|
@ -14,7 +14,7 @@ export class UserManager implements IUserManager {
|
||||
|
||||
|
||||
constructor() {
|
||||
this.dbPath = path.join(ProjectPath.getAbsolutePath(Config.Server.Database.dbFolder), 'users.db');
|
||||
this.dbPath = path.join(ProjectPath.DBFolder, 'users.db');
|
||||
if (fs.existsSync(this.dbPath)) {
|
||||
this.loadDB();
|
||||
}
|
||||
|
@ -183,7 +183,7 @@ export class SQLConnection {
|
||||
} else if (config.type === ServerConfig.DatabaseType.sqlite) {
|
||||
driver = {
|
||||
type: 'sqlite',
|
||||
database: path.join(ProjectPath.getAbsolutePath(config.dbFolder), 'sqlite.db')
|
||||
database: path.join(ProjectPath.getAbsolutePath(config.dbFolder), config.sqlite.DBFileName)
|
||||
};
|
||||
}
|
||||
return driver;
|
||||
|
@ -17,7 +17,7 @@ export class JobProgressManager {
|
||||
private timer: NodeJS.Timeout = null;
|
||||
|
||||
constructor() {
|
||||
this.dbPath = path.join(ProjectPath.getAbsolutePath(Config.Server.Database.dbFolder), 'jobs.db');
|
||||
this.dbPath = path.join(ProjectPath.DBFolder, 'jobs.db');
|
||||
this.loadDB().catch(console.error);
|
||||
}
|
||||
|
||||
|
@ -53,6 +53,13 @@ export module ServerConfig {
|
||||
}
|
||||
|
||||
|
||||
@SubConfigClass()
|
||||
export class SQLiteConfig {
|
||||
@ConfigProperty()
|
||||
DBFileName: string = 'sqlite.db';
|
||||
}
|
||||
|
||||
|
||||
@SubConfigClass()
|
||||
export class DataBaseConfig {
|
||||
@ConfigProperty<DatabaseType, IPrivateConfig>({
|
||||
@ -69,6 +76,9 @@ export module ServerConfig {
|
||||
@ConfigProperty()
|
||||
dbFolder: string = 'db';
|
||||
|
||||
@ConfigProperty()
|
||||
sqlite?: SQLiteConfig = new SQLiteConfig();
|
||||
|
||||
@ConfigProperty()
|
||||
mysql?: MySQLConfig = new MySQLConfig();
|
||||
}
|
||||
|
@ -4,6 +4,7 @@ import * as util from 'util';
|
||||
import * as rimraf from 'rimraf';
|
||||
import {SQLConnection} from '../../src/backend/model/database/sql/SQLConnection';
|
||||
import {ServerConfig} from '../../src/common/config/private/PrivateConfig';
|
||||
import {ProjectPath} from '../../src/backend/ProjectPath';
|
||||
|
||||
declare let describe: any;
|
||||
const savedDescribe = describe;
|
||||
@ -63,6 +64,7 @@ export class SQLTestHelper {
|
||||
|
||||
Config.Server.Database.type = ServerConfig.DatabaseType.sqlite;
|
||||
Config.Server.Database.dbFolder = this.tempDir;
|
||||
ProjectPath.reset();
|
||||
}
|
||||
|
||||
private async initMySQL() {
|
||||
|
@ -18,6 +18,7 @@ import {
|
||||
import {MediaDimensionEntity} from '../../../../../src/backend/model/database/sql/enitites/MediaEntity';
|
||||
import {VersionEntity} from '../../../../../src/backend/model/database/sql/enitites/VersionEntity';
|
||||
import {ServerConfig} from '../../../../../src/common/config/private/PrivateConfig';
|
||||
import {ProjectPath} from '../../../../../src/backend/ProjectPath';
|
||||
|
||||
|
||||
const rimrafPR = util.promisify(rimraf);
|
||||
@ -31,6 +32,7 @@ describe('Typeorm integration', () => {
|
||||
|
||||
Config.Server.Database.type = ServerConfig.DatabaseType.sqlite;
|
||||
Config.Server.Database.dbFolder = tempDir;
|
||||
ProjectPath.reset();
|
||||
|
||||
};
|
||||
|
||||
|
@ -30,6 +30,7 @@ describe('GalleryRouter', () => {
|
||||
Config.Server.Database.dbFolder = tempDir;
|
||||
ProjectPath.ImageFolder = path.join(__dirname, '../../assets');
|
||||
ProjectPath.TempFolder = tempDir;
|
||||
ProjectPath.reset();
|
||||
|
||||
server = new Server();
|
||||
await server.onStarted.wait();
|
||||
|
@ -13,6 +13,7 @@ import {SuperAgentStatic} from 'superagent';
|
||||
import {RouteTestingHelper} from './RouteTestingHelper';
|
||||
import {ErrorCodes} from '../../../../src/common/entities/Error';
|
||||
import {ServerConfig} from '../../../../src/common/config/private/PrivateConfig';
|
||||
import {ProjectPath} from '../../../../src/backend/ProjectPath';
|
||||
|
||||
|
||||
process.env.NODE_ENV = 'test';
|
||||
@ -39,6 +40,7 @@ describe('UserRouter', () => {
|
||||
Config.Server.Threading.enabled = false;
|
||||
Config.Server.Database.type = ServerConfig.DatabaseType.sqlite;
|
||||
Config.Server.Database.dbFolder = tempDir;
|
||||
ProjectPath.reset();
|
||||
|
||||
|
||||
server = new Server();
|
||||
|
@ -5,6 +5,7 @@ import {Config} from '../../../../../src/common/config/private/Config';
|
||||
import {SQLConnection} from '../../../../../src/backend/model/database/sql/SQLConnection';
|
||||
import {Server} from '../../../../../src/backend/server';
|
||||
import {ServerConfig} from '../../../../../src/common/config/private/PrivateConfig';
|
||||
import {ProjectPath} from '../../../../../src/backend/ProjectPath';
|
||||
|
||||
process.env.NODE_ENV = 'test';
|
||||
const chai: any = require('chai');
|
||||
@ -21,6 +22,7 @@ describe('SettingsRouter', () => {
|
||||
Config.Server.Threading.enabled = false;
|
||||
Config.Server.Database.type = ServerConfig.DatabaseType.sqlite;
|
||||
Config.Server.Database.dbFolder = tempDir;
|
||||
ProjectPath.reset();
|
||||
});
|
||||
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user