diff --git a/backend/middlewares/AdminMWs.ts b/backend/middlewares/AdminMWs.ts index 694f8924..e1a5b8ad 100644 --- a/backend/middlewares/AdminMWs.ts +++ b/backend/middlewares/AdminMWs.ts @@ -103,6 +103,29 @@ export class AdminMWs { } } + public static async updateMetaFileSettings(req: Request, res: Response, next: NextFunction) { + if ((typeof req.body === 'undefined') || (typeof req.body.settings === 'undefined')) { + return next(new ErrorDTO(ErrorCodes.INPUT_ERROR, 'settings is needed')); + } + + try { + const original = Config.original(); + await ConfigDiagnostics.testMetaFileConfig(req.body.settings, original); + + Config.Client.MetaFile = req.body.settings; + // only updating explicitly set config (not saving config set by the diagnostics) + + original.Client.MetaFile = req.body.settings; + original.save(); + await ConfigDiagnostics.runDiagnostics(); + Logger.info(LOG_TAG, 'new config:'); + Logger.info(LOG_TAG, JSON.stringify(Config, null, '\t')); + return next(); + } catch (err) { + return next(new ErrorDTO(ErrorCodes.SETTINGS_ERROR, 'Settings error: ' + err.toString(), err)); + } + } + public static async updateShareSettings(req: Request, res: Response, next: NextFunction) { if ((typeof req.body === 'undefined') || (typeof req.body.settings === 'undefined')) { return next(new ErrorDTO(ErrorCodes.INPUT_ERROR, 'settings is needed')); diff --git a/backend/model/diagnostics/ConfigDiagnostics.ts b/backend/model/diagnostics/ConfigDiagnostics.ts index 0fe6e6ab..92d3a96b 100644 --- a/backend/model/diagnostics/ConfigDiagnostics.ts +++ b/backend/model/diagnostics/ConfigDiagnostics.ts @@ -14,6 +14,7 @@ import * as fs from 'fs'; import {ClientConfig} from '../../../common/config/public/ConfigClass'; import VideoConfig = ClientConfig.VideoConfig; import {FFmpegFactory} from '../FFmpegFactory'; +import MetaFileConfig = ClientConfig.MetaFileConfig; const LOG_TAG = '[ConfigDiagnostics]'; @@ -26,6 +27,14 @@ export class ConfigDiagnostics { } + static async testMetaFileConfig(metaFileConfig: MetaFileConfig, config: IPrivateConfig) { + if (metaFileConfig.enabled === true && + config.Client.Map.enabled === false) { + throw new Error('*.gpx meta files are not supported without MAP'); + } + } + + static testVideoConfig(videoConfig: VideoConfig) { return new Promise((resolve, reject) => { try { @@ -200,6 +209,15 @@ export class ConfigDiagnostics { Config.Client.Video.enabled = false; } + try { + await ConfigDiagnostics.testMetaFileConfig(Config.Client.MetaFile, Config); + } catch (ex) { + const err: Error = ex; + NotificationManager.warning('Meta file support error, switching off..', err.toString()); + Logger.warn(LOG_TAG, 'Meta file support error, switching off..', err.toString()); + Config.Client.MetaFile.enabled = false; + } + try { await ConfigDiagnostics.testImageFolder(Config.Server.imagesFolder); diff --git a/backend/model/threading/DiskMangerWorker.ts b/backend/model/threading/DiskMangerWorker.ts index c9b435e7..aa7dae15 100644 --- a/backend/model/threading/DiskMangerWorker.ts +++ b/backend/model/threading/DiskMangerWorker.ts @@ -182,7 +182,7 @@ export class DiskMangerWorker { return new Promise((resolve, reject) => { const fd = fs.openSync(fullPath, 'r'); - const data = new Buffer(65535); + const data = Buffer.allocUnsafe(65535); fs.read(fd, data, 0, 65535, 0, (err) => { // fs.readFile(fullPath, (err, data) => { if (err) { diff --git a/backend/routes/AdminRouter.ts b/backend/routes/AdminRouter.ts index af401374..83e9963d 100644 --- a/backend/routes/AdminRouter.ts +++ b/backend/routes/AdminRouter.ts @@ -66,6 +66,12 @@ export class AdminRouter { AdminMWs.updateVideoSettings, RenderingMWs.renderOK ); + app.put('/api/settings/metafile', + AuthenticationMWs.authenticate, + AuthenticationMWs.authorise(UserRoles.Admin), + AdminMWs.updateMetaFileSettings, + RenderingMWs.renderOK + ); app.put('/api/settings/authentication', AuthenticationMWs.authenticate, diff --git a/frontend/app/admin/admin.component.html b/frontend/app/admin/admin.component.html index b5c98c01..dbe3dc1c 100644 --- a/frontend/app/admin/admin.component.html +++ b/frontend/app/admin/admin.component.html @@ -50,10 +50,11 @@ - + + diff --git a/frontend/app/app.module.ts b/frontend/app/app.module.ts index 64f5fadc..02a1031c 100644 --- a/frontend/app/app.module.ts +++ b/frontend/app/app.module.ts @@ -76,6 +76,7 @@ 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 {MetaFileSettingsComponent} from './settings/metafiles/metafile.settings.component'; @Injectable() export class GoogleMapsConfig { @@ -163,6 +164,7 @@ export function translationsFactory(locale: string) { MapSettingsComponent, ThumbnailSettingsComponent, VideoSettingsComponent, + MetaFileSettingsComponent, SearchSettingsComponent, ShareSettingsComponent, RandomPhotoSettingsComponent, diff --git a/frontend/app/settings/metafiles/metafile.settings.component.css b/frontend/app/settings/metafiles/metafile.settings.component.css new file mode 100644 index 00000000..e69de29b diff --git a/frontend/app/settings/metafiles/metafile.settings.component.html b/frontend/app/settings/metafiles/metafile.settings.component.html new file mode 100644 index 00000000..9ae70f7b --- /dev/null +++ b/frontend/app/settings/metafiles/metafile.settings.component.html @@ -0,0 +1,36 @@ +
+
+
+ Meta file settings +
+ + +
+
+
+ + + Reads and show *.gpx files on the map  + + + + +
+
+ +
diff --git a/frontend/app/settings/metafiles/metafile.settings.component.ts b/frontend/app/settings/metafiles/metafile.settings.component.ts new file mode 100644 index 00000000..351cfe67 --- /dev/null +++ b/frontend/app/settings/metafiles/metafile.settings.component.ts @@ -0,0 +1,32 @@ +import {Component} from '@angular/core'; +import {MetaFileSettingsService} from './metafile.settings.service'; +import {SettingsComponent} from '../_abstract/abstract.settings.component'; +import {AuthenticationService} from '../../model/network/authentication.service'; +import {NavigationService} from '../../model/navigation.service'; +import {NotificationService} from '../../model/notification.service'; +import {ClientConfig} from '../../../../common/config/public/ConfigClass'; +import {I18n} from '@ngx-translate/i18n-polyfill'; + + +@Component({ + selector: 'app-settings-meta-file', + templateUrl: './metafile.settings.component.html', + styleUrls: ['./metafile.settings.component.css', + './../_abstract/abstract.settings.component.css'], + providers: [MetaFileSettingsService], +}) +export class MetaFileSettingsComponent extends SettingsComponent { + + constructor(_authService: AuthenticationService, + _navigation: NavigationService, + _settingsService: MetaFileSettingsService, + notification: NotificationService, + i18n: I18n) { + super(i18n('Meta file'), _authService, _navigation, _settingsService, notification, i18n, s => s.Client.MetaFile); + } + + +} + + + diff --git a/frontend/app/settings/metafiles/metafile.settings.service.ts b/frontend/app/settings/metafiles/metafile.settings.service.ts new file mode 100644 index 00000000..78ae8969 --- /dev/null +++ b/frontend/app/settings/metafiles/metafile.settings.service.ts @@ -0,0 +1,24 @@ +import {Injectable} from '@angular/core'; +import {NetworkService} from '../../model/network/network.service'; +import {ClientConfig} from '../../../../common/config/public/ConfigClass'; +import {SettingsService} from '../settings.service'; +import {AbstractSettingsService} from '../_abstract/abstract.settings.service'; + +@Injectable() +export class MetaFileSettingsService extends AbstractSettingsService { + constructor(private _networkService: NetworkService, + _settingsService: SettingsService) { + super(_settingsService); + + } + + public isSupported(): boolean { + return this._settingsService.settings.value.Client.Map.enabled === true; + } + + + public updateSettings(settings: ClientConfig.MetaFileConfig): Promise { + return this._networkService.putJson('/settings/metafile', {settings: settings}); + } + +} diff --git a/frontend/translate/messages.en.xlf b/frontend/translate/messages.en.xlf index 5b0fdba6..08ac8abe 100644 --- a/frontend/translate/messages.en.xlf +++ b/frontend/translate/messages.en.xlf @@ -182,7 +182,7 @@ app/gallery/gallery.component.html - 44 + 46 Too many results to show. Refine your search. @@ -190,7 +190,7 @@ Searching for: app/gallery/gallery.component.html - 49 + 51 Searching for: @@ -627,6 +627,10 @@ app/settings/video/video.settings.component.html 28 + + app/settings/metafiles/metafile.settings.component.html + 28 + app/settings/search/search.settings.component.html 73 @@ -664,6 +668,10 @@ app/settings/video/video.settings.component.html 31 + + app/settings/metafiles/metafile.settings.component.html + 31 + app/settings/search/search.settings.component.html 76 @@ -836,6 +844,22 @@ Video support uses ffmpeg. ffmpeg and ffprobe binaries need to be available in the PATH or the @ffmpeg-installer/ffmpeg and @ffprobe-installer/ffprobe optional node packages need to be installed. + + Meta file settings + + app/settings/metafiles/metafile.settings.component.html + 4 + + Meta file settings + + + Reads and show *.gpx files on the map + + app/settings/metafiles/metafile.settings.component.html + 23 + + Reads and show *.gpx files on the map + Search settings @@ -1671,6 +1695,14 @@ Map + + Meta files + + frontend/app/settings/metafiles/metafile.settings.component.ts + 1 + + Meta files + Other diff --git a/frontend/translate/messages.hu.xlf b/frontend/translate/messages.hu.xlf index 8d721058..3fb86901 100644 --- a/frontend/translate/messages.hu.xlf +++ b/frontend/translate/messages.hu.xlf @@ -182,7 +182,7 @@ app/gallery/gallery.component.html - 44 + 46 Túl sok eredmény jelenik meg. Pontosítsa a keresést. @@ -190,7 +190,7 @@ Searching for: app/gallery/gallery.component.html - 49 + 51 Keresés: @@ -627,6 +627,10 @@ app/settings/video/video.settings.component.html 28 + + app/settings/metafiles/metafile.settings.component.html + 28 + app/settings/search/search.settings.component.html 73 @@ -664,6 +668,10 @@ app/settings/video/video.settings.component.html 31 + + app/settings/metafiles/metafile.settings.component.html + 31 + app/settings/search/search.settings.component.html 76 @@ -836,6 +844,22 @@ A videó lejátszához az ffmpeg szükséges. Az ffmpeg és az ffprobe binárisoknak rendelkezésre kell állniuk a PATH-ban vagy az @ffmpeg-installer/ffmpeg és @ffprobe-installer/ffprobe opcionális node csomagokat kell telepíteni. + + Meta file settings + + app/settings/metafiles/metafile.settings.component.html + 4 + + Meta fájl beállítások + + + Reads and show *.gpx files on the map + + app/settings/metafiles/metafile.settings.component.html + 23 + + Megjeleníti a *.gpx fájlokat a térképen + Search settings @@ -1671,6 +1695,14 @@ Térkép + + Meta files + + frontend/app/settings/metafiles/metafile.settings.component.ts + 1 + + Metafájlok + Other diff --git a/test/backend/unit/model/sql/GalleryManager.ts b/test/backend/unit/model/sql/GalleryManager.ts index ed41e400..6eb2290d 100644 --- a/test/backend/unit/model/sql/GalleryManager.ts +++ b/test/backend/unit/model/sql/GalleryManager.ts @@ -113,6 +113,26 @@ describe('GalleryManager', () => { }); + it('should skip meta files', async () => { + const gm = new GalleryManagerTest(); + const parent = TestHelper.getRandomizedDirectoryEntry(); + const p1 = TestHelper.getRandomizedPhotoEntry(parent, 'Photo1'); + const p2 = TestHelper.getRandomizedPhotoEntry(parent, 'Photo2'); + const gpx = TestHelper.getRandomizedGPXEntry(parent, 'GPX1'); + DirectoryDTO.removeReferences(parent); + Config.Client.MetaFile.enabled = true; + await gm.saveToDB(Utils.clone(parent)); + + Config.Client.MetaFile.enabled = false; + const conn = await SQLConnection.getConnection(); + const selected = await gm.selectParentDir(conn, parent.name, parent.path); + await gm.fillParentDir(conn, selected); + + delete parent.metaFile; + DirectoryDTO.removeReferences(selected); + removeIds(selected); + expect(Utils.clone(selected)).to.deep.equal(Utils.clone(parent)); + }); it('should update sub directory', async () => { const gm = new GalleryManagerTest();