1
0
mirror of https://github.com/xuthus83/pigallery2.git synced 2025-01-14 14:43:17 +08:00

implementing indexed statistic

This commit is contained in:
Patrik J. Braun 2018-12-09 23:25:39 +01:00
parent 14ef03f7fb
commit c98429a133
15 changed files with 279 additions and 55 deletions

View File

@ -3,7 +3,7 @@ import {ErrorCodes, ErrorDTO} from '../../common/entities/Error';
import {ObjectManagerRepository} from '../model/ObjectManagerRepository';
import {Logger} from '../Logger';
import {SQLConnection} from '../model/sql/SQLConnection';
import {DataBaseConfig, DatabaseType, IndexingConfig, IPrivateConfig, ThumbnailConfig} from '../../common/config/private/IPrivateConfig';
import {DataBaseConfig, DatabaseType, IndexingConfig, ThumbnailConfig} from '../../common/config/private/IPrivateConfig';
import {Config} from '../../common/config/private/Config';
import {ConfigDiagnostics} from '../model/diagnostics/ConfigDiagnostics';
import {ClientConfig} from '../../common/config/public/ConfigClass';
@ -12,12 +12,36 @@ import {OtherConfigDTO} from '../../common/entities/settings/OtherConfigDTO';
import {ProjectPath} from '../ProjectPath';
import {PrivateConfigClass} from '../../common/config/private/PrivateConfigClass';
import {IndexingDTO} from '../../common/entities/settings/IndexingDTO';
import {ISQLGalleryManager} from '../model/sql/IGalleryManager';
const LOG_TAG = '[AdminMWs]';
export class AdminMWs {
public static async loadStatistic(req: Request, res: Response, next: NextFunction) {
if (Config.Server.database.type === DatabaseType.memory) {
return next(new ErrorDTO(ErrorCodes.GENERAL_ERROR, 'Statistic is only available for indexed content'));
}
const galleryManager = <ISQLGalleryManager>ObjectManagerRepository.getInstance().GalleryManager;
try {
req.resultPipe = {
directories: await galleryManager.countDirectories(),
photos: await galleryManager.countPhotos(),
videos: await galleryManager.countVideos(),
diskUsage: await galleryManager.countMediaSize(),
};
return next();
} catch (err) {
if (err instanceof Error) {
return next(new ErrorDTO(ErrorCodes.GENERAL_ERROR, 'Error while getting statistic: ' + err.toString(), err));
}
return next(new ErrorDTO(ErrorCodes.GENERAL_ERROR, 'Error while getting statistic', err));
}
}
public static async updateDatabaseSettings(req: Request, res: Response, next: NextFunction) {
if ((typeof req.body === 'undefined') || (typeof req.body.settings === 'undefined')) {

View File

@ -365,4 +365,35 @@ export class GalleryManager implements IGalleryManager, ISQLGalleryManager {
return list;
}
async countDirectories(): Promise<number> {
const connection = await SQLConnection.getConnection();
return await connection.getRepository(DirectoryEntity)
.createQueryBuilder('directory')
.getCount();
}
async countMediaSize(): Promise<number> {
const connection = await SQLConnection.getConnection();
let {sum} = await connection.getRepository(MediaEntity)
.createQueryBuilder('media')
.select('SUM(media.metadata.fileSize)', 'sum')
.getRawOne();
return sum;
}
async countPhotos(): Promise<number> {
const connection = await SQLConnection.getConnection();
return await connection.getRepository(PhotoEntity)
.createQueryBuilder('directory')
.getCount();
}
async countVideos(): Promise<number> {
const connection = await SQLConnection.getConnection();
return await connection.getRepository(VideoEntity)
.createQueryBuilder('directory')
.getCount();
}
}

View File

@ -8,4 +8,11 @@ export interface ISQLGalleryManager extends IGalleryManager {
indexDirectory(relativeDirectoryName: string): Promise<DirectoryDTO>;
countDirectories(): Promise<number>;
countPhotos(): Promise<number>;
countVideos(): Promise<number>;
countMediaSize(): Promise<number>;
}

View File

@ -7,10 +7,19 @@ import {Express} from 'express';
export class AdminRouter {
public static route(app: Express) {
this.addGetStatistic(app);
this.addIndexGallery(app);
this.addSettings(app);
}
private static addGetStatistic(app: Express) {
app.get('/api/admin/statistic',
AuthenticationMWs.authenticate,
AuthenticationMWs.authorise(UserRoles.Admin),
AdminMWs.loadStatistic,
RenderingMWs.renderResult
);
}
private static addIndexGallery(app: Express) {
app.get('/api/admin/indexes/job/progress',

View File

@ -0,0 +1,6 @@
export interface StatisticDTO {
directories: number;
photos: number;
videos: number;
diskUsage: number;
}

View File

@ -73,9 +73,9 @@ import {FixOrientationPipe} from './gallery/FixOrientationPipe';
import {VideoSettingsComponent} from './settings/video/video.settings.component';
import {DurationPipe} from './pipes/DurationPipe';
import {MapService} from './gallery/map/map.service';
import {Icon} from 'leaflet';
import {MetaFileSettingsComponent} from './settings/metafiles/metafile.settings.component';
import {ThumbnailLoaderService} from './gallery/thumbnailLoader.service';
import {FileSizePipe} from './pipes/FileSizePipe';
@Injectable()
@ -166,7 +166,8 @@ export function translationsFactory(locale: string) {
IconizeSortingMethod,
StringifySortingMethod,
FixOrientationPipe,
DurationPipe
DurationPipe,
FileSizePipe
],
providers: [
{provide: UrlSerializer, useClass: CustomUrlSerializer},

View File

@ -18,7 +18,7 @@
<div class="details-sub row">
<div class="col-4">{{media.metadata.size.width}} x {{media.metadata.size.height}}</div>
<div class="col-4" *ngIf="isPhoto()">{{calcMpx()}}MP</div>
<div class="col-4" *ngIf="media.metadata.fileSize">{{calcSize(media.metadata.fileSize)}}</div>
<div class="col-4" *ngIf="media.metadata.fileSize">{{media.metadata.fileSize | fileSize}}</div>
</div>
</div>
</div>

View File

@ -40,15 +40,7 @@ export class InfoPanelLightboxComponent {
}
calcSize(size: number) {
const postFixes = ['B', 'KB', 'MB', 'GB', 'TB'];
let index = 0;
while (size > 1000 && index < postFixes.length - 1) {
size /= 1000;
index++;
}
return size.toFixed(2) + postFixes[index];
}
isThisYear() {
return (new Date()).getFullYear() ===

View File

@ -0,0 +1,19 @@
import {Pipe, PipeTransform} from '@angular/core';
import {I18n} from '@ngx-translate/i18n-polyfill';
@Pipe({name: 'fileSize'})
export class FileSizePipe implements PipeTransform {
transform(size: number): string {
const postFixes = ['B', 'KB', 'MB', 'GB', 'TB'];
let index = 0;
while (size > 1000 && index < postFixes.length - 1) {
size /= 1000;
index++;
}
return size.toFixed(2) + postFixes[index];
}
}

View File

@ -0,0 +1,8 @@
.buttons-row {
margin-top: 10px;
margin-bottom: 20px;
}
.statics span.oi {
margin-right: 3px;
}

View File

@ -79,31 +79,59 @@
aria-valuemax="100"
style="min-width: 2em;"
[style.width.%]="(_settingsService.progress.value.indexed/(_settingsService.progress.value.left+_settingsService.progress.value.indexed))*100">
{{_settingsService.progress.value.indexed}}/{{_settingsService.progress.value.indexed+_settingsService.progress.value.left}}
{{_settingsService.progress.value.indexed}}
/{{_settingsService.progress.value.indexed + _settingsService.progress.value.left}}
</div>
</div>
</div>
<div class="row justify-content-center">
<div class="row justify-content-center buttons-row">
<button class="btn btn-success"
*ngIf="_settingsService.progress.value == null"
[disabled]="inProgress"
title="Indexes the folders"
i18n-title
(click)="index(false)" i18n>Index</button>
(click)="index(false)" i18n>Index
</button>
<button class="btn btn-primary"
title="Indexes the folders and also creates the thumbnails"
i18n-title
*ngIf="_settingsService.progress.value == null"
[disabled]="inProgress"
(click)="index(true)" i18n>Index with Thumbnails</button>
(click)="index(true)" i18n>Index with Thumbnails
</button>
<button class="btn btn-default"
*ngIf="_settingsService.progress.value != null"
[disabled]="inProgress"
(click)="cancelIndexing()" i18n>Cancel</button>
(click)="cancelIndexing()" i18n>Cancel
</button>
<button class="btn btn-danger"
[disabled]="inProgress"
(click)="resetDatabase()" i18n>Reset Indexes</button>
(click)="resetDatabase()" i18n>Reset Indexes
</button>
</div>
<hr/>
<div class="row statics">
<div class="col-md-4 col-12" i18n>
Statistic:
</div>
<div class="col-md-2 col-6">
<span class="oi oi-folder" title="Folders" i18n-title aria-hidden="true"> </span>
{{statistic ? statistic.directories : '...'}}
</div>
<div class="col-md-2 col-6">
<span class="oi oi-camera-slr" title="Photos" i18n-title aria-hidden="true"> </span>
{{statistic ? statistic.photos : '...'}}
</div>
<div class="col-md-2 col-6">
<span class="oi oi-video" title="Videos" i18n-title aria-hidden="true"> </span>
{{statistic ? statistic.videos : '...'}}
</div>
<div class="col-md-2 col-6">
<span class="oi oi-pie-chart" title="Size" i18n-title aria-hidden="true"> </span>
{{statistic ? (statistic.diskUsage | fileSize) : '...'}}
</div>
</div>
</div>
</div>

View File

@ -9,6 +9,7 @@ import {IndexingConfig, ReIndexingSensitivity} from '../../../../common/config/p
import {SettingsComponent} from '../_abstract/abstract.settings.component';
import {Utils} from '../../../../common/Utils';
import {I18n} from '@ngx-translate/i18n-polyfill';
import {StatisticDTO} from '../../../../common/entities/settings/StatisticDTO';
@Component({
selector: 'app-settings-indexing',
@ -26,6 +27,7 @@ export class IndexingSettingsComponent extends SettingsComponent<IndexingConfig,
timer: null,
settings: null
};
statistic: StatisticDTO;
private $counter: Observable<number> = null;
updateProgress = async () => {
try {
@ -82,6 +84,7 @@ export class IndexingSettingsComponent extends SettingsComponent<IndexingConfig,
}
});
this.updateProgress();
this.statistic = await this._settingsService.getStatistic();
}
ngOnDestroy() {

View File

@ -6,6 +6,7 @@ import {DatabaseType, IndexingConfig} from '../../../../common/config/private/IP
import {IndexingProgressDTO} from '../../../../common/entities/settings/IndexingProgressDTO';
import {BehaviorSubject} from 'rxjs';
import {IndexingDTO} from '../../../../common/entities/settings/IndexingDTO';
import {StatisticDTO} from '../../../../common/entities/settings/StatisticDTO';
@Injectable()
export class IndexingSettingsService extends AbstractSettingsService<IndexingConfig> {
@ -45,4 +46,7 @@ export class IndexingSettingsService extends AbstractSettingsService<IndexingCon
}
getStatistic() {
return this._networkService.getJson<StatisticDTO>('/admin/statistic');
}
}

View File

@ -1353,11 +1353,12 @@
</context-group>
<target>Note: search only works among the indexed directories</target>
</trans-unit>
<trans-unit id="170f7de02b14690fb9c1999a16926c0044bfd5c1" datatype="html">
<source>Index</source>
<trans-unit id="32cc8ef8dc6f4f239b7f637ac8adaecc55b8e1d8" datatype="html">
<source>Index
</source>
<context-group purpose="location">
<context context-type="sourcefile">app/settings/indexing/indexing.settings.component.html</context>
<context context-type="linenumber">93</context>
<context context-type="linenumber">94</context>
</context-group>
<target>Index</target>
</trans-unit>
@ -1365,15 +1366,16 @@
<source>Indexes the folders</source>
<context-group purpose="location">
<context context-type="sourcefile">app/settings/indexing/indexing.settings.component.html</context>
<context context-type="linenumber">91</context>
<context context-type="linenumber">92</context>
</context-group>
<target>Indexes the folders</target>
</trans-unit>
<trans-unit id="7e546cd01e4ee4cb0571fe34ce9c96ad760f31f7" datatype="html">
<source>Index with Thumbnails</source>
<trans-unit id="2cf5bad5f694098d6eb9ce70f687cc469e60c697" datatype="html">
<source>Index with Thumbnails
</source>
<context-group purpose="location">
<context context-type="sourcefile">app/settings/indexing/indexing.settings.component.html</context>
<context context-type="linenumber">99</context>
<context context-type="linenumber">101</context>
</context-group>
<target>Index with Thumbnails</target>
</trans-unit>
@ -1381,26 +1383,70 @@
<source>Indexes the folders and also creates the thumbnails</source>
<context-group purpose="location">
<context context-type="sourcefile">app/settings/indexing/indexing.settings.component.html</context>
<context context-type="linenumber">95</context>
<context context-type="linenumber">97</context>
</context-group>
<target>Indexes the folders and also creates the thumbnails</target>
</trans-unit>
<trans-unit id="d7b35c384aecd25a516200d6921836374613dfe7" datatype="html">
<source>Cancel</source>
<context-group purpose="location">
<context context-type="sourcefile">app/settings/indexing/indexing.settings.component.html</context>
<context context-type="linenumber">103</context>
</context-group>
<target>Cancel</target>
</trans-unit>
<trans-unit id="6ea6ba32bbd2333f0df2a888252f82e42c8bbe7a" datatype="html">
<source>Reset Indexes</source>
<trans-unit id="e7e43ec575247424aa179da55b338fd740e8aa7f" datatype="html">
<source>Cancel
</source>
<context-group purpose="location">
<context context-type="sourcefile">app/settings/indexing/indexing.settings.component.html</context>
<context context-type="linenumber">106</context>
</context-group>
<target>Cancel</target>
</trans-unit>
<trans-unit id="d68e02eaea0b78b12fceb483b2183a3f5b70d969" datatype="html">
<source>Reset Indexes
</source>
<context-group purpose="location">
<context context-type="sourcefile">app/settings/indexing/indexing.settings.component.html</context>
<context context-type="linenumber">110</context>
</context-group>
<target>Reset Indexes</target>
</trans-unit>
<trans-unit id="fed617f53bda7660e3f3cf4e7c62fa6d39e2ca16" datatype="html">
<source>
Statistic:
</source>
<context-group purpose="location">
<context context-type="sourcefile">app/settings/indexing/indexing.settings.component.html</context>
<context context-type="linenumber">115</context>
</context-group>
<target>Statistic:</target>
</trans-unit>
<trans-unit id="3fde556358b58d910adc30abaaff2433f0bb5f6c" datatype="html">
<source>Folders</source>
<context-group purpose="location">
<context context-type="sourcefile">app/settings/indexing/indexing.settings.component.html</context>
<context context-type="linenumber">119</context>
</context-group>
<target>Folders</target>
</trans-unit>
<trans-unit id="f84ece8c3bbbf088cb70cf95792ae14dfe51bf96" datatype="html">
<source>Photos</source>
<context-group purpose="location">
<context context-type="sourcefile">app/settings/indexing/indexing.settings.component.html</context>
<context context-type="linenumber">123</context>
</context-group>
<target>Photos</target>
</trans-unit>
<trans-unit id="a52dae09be10ca3a65da918533ced3d3f4992238" datatype="html">
<source>Videos</source>
<context-group purpose="location">
<context context-type="sourcefile">app/settings/indexing/indexing.settings.component.html</context>
<context context-type="linenumber">127</context>
</context-group>
<target>Videos</target>
</trans-unit>
<trans-unit id="7faaaa08f56427999f3be41df1093ce4089bbd75" datatype="html">
<source>Size</source>
<context-group purpose="location">
<context context-type="sourcefile">app/settings/indexing/indexing.settings.component.html</context>
<context context-type="linenumber">132</context>
</context-group>
<target>Size</target>
</trans-unit>
<trans-unit id="bc2e854e111ecf2bd7db170da5e3c2ed08181d88" datatype="html">
<source>Advanced</source>
<context-group purpose="location">

View File

@ -1353,11 +1353,12 @@
</context-group>
<target>Megjegyzés: csak az indexelt könyvtárak között működik a keresés</target>
</trans-unit>
<trans-unit id="170f7de02b14690fb9c1999a16926c0044bfd5c1" datatype="html">
<source>Index</source>
<trans-unit id="32cc8ef8dc6f4f239b7f637ac8adaecc55b8e1d8" datatype="html">
<source>Index
</source>
<context-group purpose="location">
<context context-type="sourcefile">app/settings/indexing/indexing.settings.component.html</context>
<context context-type="linenumber">93</context>
<context context-type="linenumber">94</context>
</context-group>
<target>Index</target>
</trans-unit>
@ -1365,15 +1366,16 @@
<source>Indexes the folders</source>
<context-group purpose="location">
<context context-type="sourcefile">app/settings/indexing/indexing.settings.component.html</context>
<context context-type="linenumber">91</context>
<context context-type="linenumber">92</context>
</context-group>
<target>Indexeli a mappákat</target>
</trans-unit>
<trans-unit id="7e546cd01e4ee4cb0571fe34ce9c96ad760f31f7" datatype="html">
<source>Index with Thumbnails</source>
<trans-unit id="2cf5bad5f694098d6eb9ce70f687cc469e60c697" datatype="html">
<source>Index with Thumbnails
</source>
<context-group purpose="location">
<context context-type="sourcefile">app/settings/indexing/indexing.settings.component.html</context>
<context context-type="linenumber">99</context>
<context context-type="linenumber">101</context>
</context-group>
<target>Index thumbnail-el</target>
</trans-unit>
@ -1381,26 +1383,70 @@
<source>Indexes the folders and also creates the thumbnails</source>
<context-group purpose="location">
<context context-type="sourcefile">app/settings/indexing/indexing.settings.component.html</context>
<context context-type="linenumber">95</context>
<context context-type="linenumber">97</context>
</context-group>
<target>Indexeli a mappákat és legenerálja a thumbnaileket is</target>
</trans-unit>
<trans-unit id="d7b35c384aecd25a516200d6921836374613dfe7" datatype="html">
<source>Cancel</source>
<context-group purpose="location">
<context context-type="sourcefile">app/settings/indexing/indexing.settings.component.html</context>
<context context-type="linenumber">103</context>
</context-group>
<target>Mégse</target>
</trans-unit>
<trans-unit id="6ea6ba32bbd2333f0df2a888252f82e42c8bbe7a" datatype="html">
<source>Reset Indexes</source>
<trans-unit id="e7e43ec575247424aa179da55b338fd740e8aa7f" datatype="html">
<source>Cancel
</source>
<context-group purpose="location">
<context context-type="sourcefile">app/settings/indexing/indexing.settings.component.html</context>
<context context-type="linenumber">106</context>
</context-group>
<target>Mégse</target>
</trans-unit>
<trans-unit id="d68e02eaea0b78b12fceb483b2183a3f5b70d969" datatype="html">
<source>Reset Indexes
</source>
<context-group purpose="location">
<context context-type="sourcefile">app/settings/indexing/indexing.settings.component.html</context>
<context context-type="linenumber">110</context>
</context-group>
<target>Indexek visszaállítása</target>
</trans-unit>
<trans-unit id="fed617f53bda7660e3f3cf4e7c62fa6d39e2ca16" datatype="html">
<source>
Statistic:
</source>
<context-group purpose="location">
<context context-type="sourcefile">app/settings/indexing/indexing.settings.component.html</context>
<context context-type="linenumber">115</context>
</context-group>
<target>Statisztika:</target>
</trans-unit>
<trans-unit id="3fde556358b58d910adc30abaaff2433f0bb5f6c" datatype="html">
<source>Folders</source>
<context-group purpose="location">
<context context-type="sourcefile">app/settings/indexing/indexing.settings.component.html</context>
<context context-type="linenumber">119</context>
</context-group>
<target>Mappák</target>
</trans-unit>
<trans-unit id="f84ece8c3bbbf088cb70cf95792ae14dfe51bf96" datatype="html">
<source>Photos</source>
<context-group purpose="location">
<context context-type="sourcefile">app/settings/indexing/indexing.settings.component.html</context>
<context context-type="linenumber">123</context>
</context-group>
<target>Fotók</target>
</trans-unit>
<trans-unit id="a52dae09be10ca3a65da918533ced3d3f4992238" datatype="html">
<source>Videos</source>
<context-group purpose="location">
<context context-type="sourcefile">app/settings/indexing/indexing.settings.component.html</context>
<context context-type="linenumber">127</context>
</context-group>
<target>Videók</target>
</trans-unit>
<trans-unit id="7faaaa08f56427999f3be41df1093ce4089bbd75" datatype="html">
<source>Size</source>
<context-group purpose="location">
<context context-type="sourcefile">app/settings/indexing/indexing.settings.component.html</context>
<context context-type="linenumber">132</context>
</context-group>
<target>Méret</target>
</trans-unit>
<trans-unit id="bc2e854e111ecf2bd7db170da5e3c2ed08181d88" datatype="html">
<source>Advanced</source>
<context-group purpose="location">