1
0
mirror of https://github.com/bpatrik/pigallery2.git synced 2025-05-31 23:09:48 +02:00

improving logging and configs

This commit is contained in:
Braun Patrik 2017-06-04 15:25:08 +02:00
parent 98681322f5
commit 7e56ef1111
36 changed files with 279 additions and 326 deletions

View File

@ -7,8 +7,7 @@ declare module 'winston' {
}
}
export const Logger = new winston.Logger({
export const winstonSettings = {
transports: [
new winston.transports.Console({
level: 'silly',
@ -29,4 +28,6 @@ export const Logger = new winston.Logger({
})
],
exitOnError: false
});
};
export const Logger = new winston.Logger(winstonSettings);

View File

@ -1,5 +1,5 @@
import * as path from "path";
import {Config} from "./config/Config";
import {Config} from "../common/config/private/Config";
class ProjectPathClass {
public Root: string;

View File

@ -1,28 +0,0 @@
import {ConfigLoader} from "./ConfigLoader";
import * as path from "path";
import {ConfigClass, DatabaseType} from "../../common/config/Config";
export let Config = new ConfigClass();
Config.Server = {
port: 80,
imagesFolder: "demo/images",
thumbnail: {
folder: "demo/TEMP",
hardwareAcceleration: true
},
database: {
type: DatabaseType.mysql,
mysql: {
host: "localhost",
username: "root",
password: "root",
database: "pigallery2"
}
}
};
ConfigLoader.init(Config, path.join(__dirname, './../../config.json'), [["PORT", "Server-port"]]);

View File

@ -1,116 +0,0 @@
import * as fs from "fs";
import * as optimist from "optimist";
export class ConfigLoader {
static init(configObject: any, configFilePath?: string, envAlias: Array<Array<string>> = []) {
this.processConfigFile(configFilePath, configObject);
this.processArguments(configObject);
this.processEnvVariables(configObject, envAlias);
}
private static processEnvVariables(configObject: any, envAlias: Array<Array<string>>) {
let varAliases = {};
envAlias.forEach((alias) => {
if (process.env[alias[0]]) {
varAliases[alias[1]] = process.env[alias[0]];
}
});
this.processHierarchyVar(configObject, varAliases);
this.processHierarchyVar(configObject, process.env);
};
private static processArguments(configObject: any) {
let argv = optimist.argv;
delete(argv._);
delete(argv.$0);
this.processHierarchyVar(configObject, argv);
};
private static processHierarchyVar(configObject: any, vars: any) {
let config = {};
Object.keys(vars).forEach((key) => {
let keyArray = key.split("-");
let value = vars[key];
//recursive settings
let setObject = (object: any, keyArray: Array<string>, value: any): void => {
let key = keyArray.shift();
object[key] = object[key] || {};
if (keyArray.length == 0) {
//convert to boolean
if (value.toLowerCase && value.toLowerCase() === "false") {
value = false;
}
if (value.toLowerCase && value.toLowerCase() === "true") {
value = true;
}
object[key] = value;
return;
}
return setObject(object[key], keyArray, value);
};
setObject(config, keyArray, value);
});
this.loadObject(configObject, config);
}
private static processConfigFile(configFilePath: string, configObject: any) {
if (typeof configFilePath !== 'undefined') {
if (ConfigLoader.loadConfigFile(configFilePath, configObject) === false) {
ConfigLoader.saveConfigFile(configFilePath, configObject);
}
}
};
private static loadConfigFile(configFilePath: string, configObject: any): boolean {
if (fs.existsSync(configFilePath) === false) {
return false;
}
try {
let config = JSON.parse(fs.readFileSync(configFilePath, 'utf8'));
this.loadObject(configObject, config);
return true;
} catch (err) {
}
return false;
}
private static saveConfigFile(configFilePath: string, configObject: any) {
try {
fs.writeFileSync(configFilePath, JSON.stringify(configObject, null, 4));
} catch (err) {
}
}
private static loadObject(targetObject, sourceObject) {
Object.keys(sourceObject).forEach((key) => {
if (typeof targetObject[key] === "undefined") {
return;
}
if (Array.isArray(targetObject[key])) {
return targetObject[key] = sourceObject[key];
}
if (typeof targetObject[key] === "object") {
return this.loadObject(targetObject[key], sourceObject[key]);
}
targetObject[key] = sourceObject[key];
});
}
}

View File

@ -8,9 +8,9 @@ import {AutoCompleteItem, SearchTypes} from "../../common/entities/AutoCompleteI
import {ContentWrapper} from "../../common/entities/ConentWrapper";
import {SearchResultDTO} from "../../common/entities/SearchResult";
import {PhotoDTO} from "../../common/entities/PhotoDTO";
import {Config} from "../config/Config";
import {ProjectPath} from "../ProjectPath";
import {Logger} from "../Logger";
import {Config} from "../../common/config/private/Config";
const LOG_TAG = "[GalleryMWs]";

View File

@ -5,12 +5,12 @@ import * as fs from "fs";
import * as os from "os";
import {NextFunction, Request, Response} from "express";
import {Error, ErrorCodes} from "../../../common/entities/Error";
import {Config} from "../../config/Config";
import {ContentWrapper} from "../../../common/entities/ConentWrapper";
import {DirectoryDTO} from "../../../common/entities/DirectoryDTO";
import {ProjectPath} from "../../ProjectPath";
import {PhotoDTO} from "../../../common/entities/PhotoDTO";
import {hardwareRenderer, softwareRenderer} from "./THRenderers";
import {Config} from "../../../common/config/private/Config";
Config.Client.concurrentThumbnailGenerations = Math.max(1, os.cpus().length - 1);
@ -18,14 +18,21 @@ Config.Client.concurrentThumbnailGenerations = Math.max(1, os.cpus().length - 1)
const Pool = require('threads').Pool;
const pool = new Pool(Config.Client.concurrentThumbnailGenerations);
if (Config.Server.thumbnail.hardwareAcceleration == true) {
pool.run(hardwareRenderer);
} else {
pool.run(softwareRenderer);
}
export class ThumbnailGeneratorMWs {
private static poolsInited = false;
private static initPools() {
if (this.poolsInited == true) {
return
}
if (Config.Server.thumbnail.hardwareAcceleration == true) {
pool.run(hardwareRenderer);
} else {
pool.run(softwareRenderer);
}
this.poolsInited = true;
}
private static addThInfoTODir(directory: DirectoryDTO) {
if (typeof directory.photos == "undefined") {
@ -111,6 +118,7 @@ export class ThumbnailGeneratorMWs {
}
private static generateImage(imagePath: string, size: number, makeSquare: boolean, req: Request, res: Response, next: NextFunction) {
//generate thumbnail path
@ -129,6 +137,7 @@ export class ThumbnailGeneratorMWs {
fs.mkdirSync(ProjectPath.ThumbnailFolder);
}
this.initPools();
//run on other thread
pool.send({imagePath: imagePath, size: size, thPath: thPath, makeSquare: makeSquare, __dirname: __dirname})
.on('done', (out) => {

View File

@ -1,9 +1,9 @@
///<reference path="../customtypings/ExtendedRequest.d.ts"/>
import {NextFunction, Request, Response} from "express";
import {Error, ErrorCodes} from "../../../common/entities/Error";
import {UserRoles, UserDTO} from "../../../common/entities/UserDTO";
import {UserDTO, UserRoles} from "../../../common/entities/UserDTO";
import {ObjectManagerRepository} from "../../model/ObjectManagerRepository";
import {Config} from "../../config/Config";
import {Config} from "../../../common/config/private/Config";
export class AuthenticationMWs {

View File

@ -2,8 +2,8 @@ import {NextFunction, Request, Response} from "express";
import {Error, ErrorCodes} from "../../../common/entities/Error";
import {ObjectManagerRepository} from "../../model/ObjectManagerRepository";
import {UserDTO} from "../../../common/entities/UserDTO";
import {Config} from "../../config/Config";
import {Utils} from "../../../common/Utils";
import {Config} from "../../../common/config/private/Config";
export class UserMWs {

View File

@ -138,7 +138,6 @@ pool.run(
try {
for (let i = 0; i < list.length; i++) {
let file = list[i];
console.log(list[i]);
let fullFilePath = path.normalize(path.resolve(directoryInfo.absoluteDirectoryName, file));
if (photosOnly == false && fs.statSync(fullFilePath).isDirectory()) {
let promise = parseDir({
@ -195,7 +194,7 @@ pool.run(
export class DiskManager {
public static scanDirectory(relativeDirectoryName: string, cb: (error: any, result: DirectoryDTO) => void) {
Logger.silly(LOG_TAG, "scanDirectory");
Logger.silly(LOG_TAG, "scanning directory:", relativeDirectoryName);
let directoryName = path.basename(relativeDirectoryName);
let directoryParent = path.join(path.dirname(relativeDirectoryName), path.sep);
let absoluteDirectoryName = path.join(ProjectPath.ImageFolder, relativeDirectoryName);

View File

@ -1,10 +1,10 @@
import "reflect-metadata";
import {createConnection, Connection} from "typeorm";
import {Config} from "../../config/Config";
import {Connection, createConnection} from "typeorm";
import {UserEntity} from "./enitites/UserEntity";
import {UserRoles} from "../../../common/entities/UserDTO";
import {PhotoEntity, PhotoMetadataEntity} from "./enitites/PhotoEntity";
import {DirectoryEntity} from "./enitites/DirectoryEntity";
import {Config} from "../../../common/config/private/Config";
export class MySQLConnection {

View File

@ -2,22 +2,22 @@ import {AuthenticationMWs} from "../middlewares/user/AuthenticationMWs";
import {UserRoles} from "../../common/entities/UserDTO";
export class AdminRouter {
constructor(private app: any) {
public static route(app: any) {
this.addResetDB();
this.addIndexGallery();
this.addResetDB(app);
this.addIndexGallery(app);
}
private addResetDB() {
this.app.post("/api/admin/db/reset",
private static addResetDB(app) {
app.post("/api/admin/db/reset",
AuthenticationMWs.authenticate,
AuthenticationMWs.authorise(UserRoles.Admin)
//TODO: implement
);
};
private addIndexGallery() {
this.app.post("/api/admin/gallery/index",
private static addIndexGallery(app) {
app.post("/api/admin/gallery/index",
AuthenticationMWs.authenticate,
AuthenticationMWs.authorise(UserRoles.Admin)
//TODO: implement

View File

@ -1,26 +1,27 @@
import {RenderingMWs} from "../middlewares/RenderingMWs";
import {Error, ErrorCodes} from "../../common/entities/Error";
import {Logger} from "../Logger";
import Request = Express.Request;
import Response = Express.Response;
export class ErrorRouter {
constructor(private app: any) {
public static route(app: any) {
this.addApiErrorHandler();
this.addGenericHandler();
this.addApiErrorHandler(app);
this.addGenericHandler(app);
}
private addApiErrorHandler() {
this.app.use("/api/*",
private static addApiErrorHandler(app) {
app.use("/api/*",
RenderingMWs.renderError
);
};
private addGenericHandler() {
this.app.use((err: any, req: Request, res: Response, next: Function) => {
private static addGenericHandler(app) {
app.use((err: any, req: Request, res: Response, next: Function) => {
//Flush out the stack to the console
console.error(err.stack);
Logger.error(err);
next(new Error(ErrorCodes.SERVER_ERROR, "Unknown server side error"));
},
RenderingMWs.renderError

View File

@ -4,20 +4,20 @@ import {RenderingMWs} from "../middlewares/RenderingMWs";
import {ThumbnailGeneratorMWs} from "../middlewares/thumbnail/ThumbnailGeneratorMWs";
export class GalleryRouter {
constructor(private app: any) {
public static route(app: any) {
this.addGetImageIcon();
this.addGetImageThumbnail();
this.addGetImage();
this.addDirectoryList();
this.addGetImageIcon(app);
this.addGetImageThumbnail(app);
this.addGetImage(app);
this.addDirectoryList(app);
this.addSearch();
this.addInstantSearch();
this.addAutoComplete();
this.addSearch(app);
this.addInstantSearch(app);
this.addAutoComplete(app);
}
private addDirectoryList() {
this.app.get(["/api/gallery/content/:directory(*)", "/api/gallery/", "/api/gallery//"],
private static addDirectoryList(app) {
app.get(["/api/gallery/content/:directory(*)", "/api/gallery/", "/api/gallery//"],
AuthenticationMWs.authenticate,
GalleryMWs.listDirectory,
ThumbnailGeneratorMWs.addThumbnailInformation,
@ -27,16 +27,16 @@ export class GalleryRouter {
};
private addGetImage() {
this.app.get(["/api/gallery/content/:imagePath(*\.(jpg|bmp|png|gif|jpeg))"],
private static addGetImage(app) {
app.get(["/api/gallery/content/:imagePath(*\.(jpg|bmp|png|gif|jpeg))"],
AuthenticationMWs.authenticate,
GalleryMWs.loadImage,
RenderingMWs.renderFile
);
};
private addGetImageThumbnail() {
this.app.get("/api/gallery/content/:imagePath(*\.(jpg|bmp|png|gif|jpeg))/thumbnail/:size?",
private static addGetImageThumbnail(app) {
app.get("/api/gallery/content/:imagePath(*\.(jpg|bmp|png|gif|jpeg))/thumbnail/:size?",
AuthenticationMWs.authenticate,
GalleryMWs.loadImage,
ThumbnailGeneratorMWs.generateThumbnail,
@ -44,8 +44,8 @@ export class GalleryRouter {
);
};
private addGetImageIcon() {
this.app.get("/api/gallery/content/:imagePath(*\.(jpg|bmp|png|gif|jpeg))/icon",
private static addGetImageIcon(app) {
app.get("/api/gallery/content/:imagePath(*\.(jpg|bmp|png|gif|jpeg))/icon",
AuthenticationMWs.authenticate,
GalleryMWs.loadImage,
ThumbnailGeneratorMWs.generateIcon,
@ -53,8 +53,8 @@ export class GalleryRouter {
);
};
private addSearch() {
this.app.get("/api/search/:text",
private static addSearch(app) {
app.get("/api/search/:text",
AuthenticationMWs.authenticate,
GalleryMWs.search,
ThumbnailGeneratorMWs.addThumbnailInformation,
@ -63,8 +63,8 @@ export class GalleryRouter {
);
};
private addInstantSearch() {
this.app.get("/api/instant-search/:text",
private static addInstantSearch(app) {
app.get("/api/instant-search/:text",
AuthenticationMWs.authenticate,
GalleryMWs.instantSearch,
ThumbnailGeneratorMWs.addThumbnailInformation,
@ -73,8 +73,8 @@ export class GalleryRouter {
);
};
private addAutoComplete() {
this.app.get("/api/autocomplete/:text",
private static addAutoComplete(app) {
app.get("/api/autocomplete/:text",
AuthenticationMWs.authenticate,
GalleryMWs.autocomplete,
RenderingMWs.renderResult

View File

@ -2,11 +2,12 @@ import * as _express from "express";
import {NextFunction, Request, Response} from "express";
import * as _path from "path";
import {Utils} from "../../common/Utils";
import {Config} from "../config/Config";
import {Config} from "../../common/config/private/Config";
export class PublicRouter {
constructor(private app) {
this.app.use((req:Request, res:Response, next:NextFunction) => {
public static route(app) {
app.use((req: Request, res: Response, next: NextFunction) => {
res.tpl = {};
res.tpl.user = null;
@ -20,15 +21,15 @@ export class PublicRouter {
return next();
});
this.app.use(_express.static(_path.resolve(__dirname, './../../frontend')));
this.app.use('/node_modules', _express.static(_path.resolve(__dirname, './../../node_modules')));
this.app.use('/common', _express.static(_path.resolve(__dirname, './../../common')));
app.use(_express.static(_path.resolve(__dirname, './../../frontend')));
app.use('/node_modules', _express.static(_path.resolve(__dirname, './../../node_modules')));
app.use('/common', _express.static(_path.resolve(__dirname, './../../common')));
const renderIndex = (req: Request, res: Response) => {
res.render(_path.resolve(__dirname, './../../frontend/index.ejs'), res.tpl);
};
this.app.get(['/', '/login', "/gallery*", "/admin", "/search*"], renderIndex);
app.get(['/', '/login', "/gallery*", "/admin", "/search*"], renderIndex);
}

View File

@ -2,22 +2,22 @@ import {AuthenticationMWs} from "../middlewares/user/AuthenticationMWs";
import {UserRoles} from "../../common/entities/UserDTO";
export class SharingRouter {
constructor(private app: any) {
public static route(app: any) {
this.addGetSharing();
this.addUpdateSharing();
this.addGetSharing(app);
this.addUpdateSharing(app);
}
private addGetSharing() {
this.app.get("/api/share/:directory",
private static addGetSharing(app) {
app.get("/api/share/:directory",
AuthenticationMWs.authenticate,
AuthenticationMWs.authorise(UserRoles.User)
//TODO: implement
);
};
private addUpdateSharing() {
this.app.post("/api/share/:directory",
private static addUpdateSharing(app) {
app.post("/api/share/:directory",
AuthenticationMWs.authenticate,
AuthenticationMWs.authorise(UserRoles.User)
//TODO: implement

View File

@ -5,29 +5,29 @@ import {UserRequestConstrainsMWs} from "../middlewares/user/UserRequestConstrain
import {RenderingMWs} from "../middlewares/RenderingMWs";
export class UserRouter {
constructor(private app) {
this.addLogin();
this.addLogout();
this.addGetSessionUser();
this.addChangePassword();
public static route(app) {
this.addLogin(app);
this.addLogout(app);
this.addGetSessionUser(app);
this.addChangePassword(app);
this.addCreateUser();
this.addDeleteUser();
this.addListUsers();
this.addChangeRole();
this.addCreateUser(app);
this.addDeleteUser(app);
this.addListUsers(app);
this.addChangeRole(app);
}
private addLogin() {
this.app.post("/api/user/login",
private static addLogin(app) {
app.post("/api/user/login",
AuthenticationMWs.inverseAuthenticate,
AuthenticationMWs.login,
RenderingMWs.renderSessionUser
);
};
private addLogout() {
this.app.post("/api/user/logout",
private static addLogout(app) {
app.post("/api/user/logout",
AuthenticationMWs.authenticate,
AuthenticationMWs.logout,
RenderingMWs.renderOK
@ -35,16 +35,16 @@ export class UserRouter {
};
private addGetSessionUser() {
this.app.get("/api/user/login",
private static addGetSessionUser(app) {
app.get("/api/user/login",
AuthenticationMWs.authenticate,
RenderingMWs.renderSessionUser
);
};
private addChangePassword() {
this.app.post("/api/user/:id/password",
private static addChangePassword(app) {
app.post("/api/user/:id/password",
AuthenticationMWs.authenticate,
UserRequestConstrainsMWs.forceSelfRequest,
UserMWs.changePassword,
@ -53,8 +53,8 @@ export class UserRouter {
};
private addCreateUser() {
this.app.put("/api/user",
private static addCreateUser(app) {
app.put("/api/user",
AuthenticationMWs.authenticate,
AuthenticationMWs.authorise(UserRoles.Admin),
UserMWs.createUser,
@ -62,8 +62,8 @@ export class UserRouter {
);
};
private addDeleteUser() {
this.app.delete("/api/user/:id",
private static addDeleteUser(app) {
app.delete("/api/user/:id",
AuthenticationMWs.authenticate,
AuthenticationMWs.authorise(UserRoles.Admin),
UserRequestConstrainsMWs.notSelfRequest,
@ -73,8 +73,8 @@ export class UserRouter {
};
private addListUsers() {
this.app.get("/api/user/list",
private static addListUsers(app) {
app.get("/api/user/list",
AuthenticationMWs.authenticate,
AuthenticationMWs.authorise(UserRoles.Admin),
UserMWs.listUsers,
@ -82,8 +82,8 @@ export class UserRouter {
);
};
private addChangeRole() {
this.app.post("/api/user/:id/role",
private static addChangeRole(app) {
app.post("/api/user/:id/role",
AuthenticationMWs.authenticate,
AuthenticationMWs.authorise(UserRoles.Admin),
UserRequestConstrainsMWs.notSelfRequestOr2Admins,

View File

@ -1,18 +1,19 @@
import * as _express from "express";
import * as _session from "express-session";
import * as _bodyParser from "body-parser";
import * as _debug from "debug";
import * as _http from "http";
import * as winston from "winston";
import * as expressWinston from "express-winston";
import {PublicRouter} from "./routes/PublicRouter";
import {UserRouter} from "./routes/UserRouter";
import {GalleryRouter} from "./routes/GalleryRouter";
import {AdminRouter} from "./routes/AdminRouter";
import {ErrorRouter} from "./routes/ErrorRouter";
import {SharingRouter} from "./routes/SharingRouter";
import {DatabaseType} from "../common/config/Config";
import {ObjectManagerRepository} from "./model/ObjectManagerRepository";
import {Config} from "./config/Config";
import {Logger} from "./Logger";
import {Config} from "../common/config/private/Config";
import {DatabaseType} from "../common/config/private/IPrivateConfig";
const LOG_TAG = "[server]";
export class Server {
@ -22,18 +23,46 @@ export class Server {
private server: any;
constructor() {
this.init();
}
async init() {
Logger.info(LOG_TAG, "config:");
Logger.info(LOG_TAG, JSON.stringify(Config, null, '\t'));
this.debug = _debug("PiGallery2:server");
this.app = _express();
this.app.set('view engine', 'ejs');
this.app.use(expressWinston.logger({
transports: [
new winston.transports.Console({
level: 'silly',
json: false,
colorize: true,
timestamp: function () {
return (new Date()).toLocaleString();
},
formatter: (options) => {
// Return string will be passed to logger.
return options.timestamp() + '[' + winston['config']['colorize'](options.level, options.level.toUpperCase()) + '] ' +
(undefined !== options.message ? options.message : '') +
(options.meta && Object.keys(options.meta).length ? '\n\t' + JSON.stringify(options.meta) : '' );
},
debugStdout: true
})
],
meta: false, // optional: control whether you want to log the meta data about the request (default to true)
msg: "HTTP {{req.method}} {{req.url}}", // optional: customize the default logging message. E.g. "{{res.statusCode}} {{req.method}} {{res.responseTime}}ms {{req.url}}"
expressFormat: true, // Use the default Express/morgan request formatting. Enabling this will override any msg if true. Will only output colors with colorize set to true
colorize: true, // Color the text and status code, using the Express/morgan color palette (text: gray, status: default green, 3XX cyan, 4XX yellow, 5XX red).
level: (req) => {
if (req.url.indexOf("/api/") !== -1) {
return "verbose";
}
return req.url.indexOf("node_modules") !== -1 ? "silly" : "debug"
}
}));
if (process.env.DEBUG) {
let _morgan = require('morgan');
this.app.use(_morgan('dev'));
}
this.app.set('view engine', 'ejs');
/**
@ -57,19 +86,26 @@ export class Server {
this.app.use(_bodyParser.json());
if (Config.Server.database.type == DatabaseType.mysql) {
ObjectManagerRepository.InitMySQLManagers().catch((err) => {
Logger.warn(LOG_TAG, "Error during initailizing mysql falling back to memory DB", err);
try {
await ObjectManagerRepository.InitMySQLManagers();
} catch (err) {
Logger.warn(LOG_TAG, "[MYSQL error]", err);
Logger.warn(LOG_TAG, "Error during initializing mysql falling back to memory DB");
Config.setDatabaseType(DatabaseType.memory);
ObjectManagerRepository.InitMemoryManagers();
});
await ObjectManagerRepository.InitMemoryManagers();
}
} else {
ObjectManagerRepository.InitMemoryManagers();
await ObjectManagerRepository.InitMemoryManagers();
}
if (Config.Server.thumbnail.hardwareAcceleration == true) {
try {
const sharp = require.resolve("sharp");
const sharp = require("sharp");
sharp();
} catch (err) {
Logger.warn(LOG_TAG, "[Thumbnail hardware acceleration] sharp module error: ", err);
Logger.warn(LOG_TAG, "Thumbnail hardware acceleration is not possible." +
" 'Sharp' node module is not found." +
" Falling back to JS based thumbnail generation");
@ -77,14 +113,14 @@ export class Server {
}
}
new PublicRouter(this.app);
PublicRouter.route(this.app);
new UserRouter(this.app);
new GalleryRouter(this.app);
new SharingRouter(this.app);
new AdminRouter(this.app);
UserRouter.route(this.app);
GalleryRouter.route(this.app);
SharingRouter.route(this.app);
AdminRouter.route(this.app);
new ErrorRouter(this.app);
ErrorRouter.route(this.app);
// Get PORT from environment and store in Express.
@ -138,7 +174,7 @@ export class Server {
const bind = typeof addr === 'string'
? 'pipe ' + addr
: 'port ' + addr.port;
Logger.debug(LOG_TAG, 'Listening on ' + bind);
Logger.info(LOG_TAG, 'Listening on ' + bind);
};
}

View File

@ -0,0 +1,12 @@
import * as path from "path";
import {PrivateConfigClass} from "./PrivateConfigClass";
import {ConfigLoader} from "typeconfig";
export let Config = new PrivateConfigClass();
ConfigLoader.loadBackendConfig(Config,
path.join(__dirname, './../../../config.json'),
[["PORT", "Server-port"]]);

View File

@ -0,0 +1,28 @@
export enum DatabaseType{
memory = 0, mysql = 1
}
export enum LogLevel {
error, warn, info, debug, verbose
}
export interface MySQLConfig {
host: string;
database: string;
username: string;
password: string;
}
export interface DataBaseConfig {
type: DatabaseType;
mysql?: MySQLConfig;
}
export interface ThumbnailConfig {
folder: string;
hardwareAcceleration: boolean;
}
export interface ServerConfig {
port: number;
imagesFolder: string;
thumbnail: ThumbnailConfig;
database: DataBaseConfig;
}

View File

@ -0,0 +1,39 @@
import {PublicConfigClass} from "../public/ConfigClass";
import {DatabaseType, ServerConfig} from "./IPrivateConfig";
/**
* This configuration will be only at backend
*/
export class PrivateConfigClass extends PublicConfigClass {
public Server: ServerConfig = {
port: 80,
imagesFolder: "demo/images",
thumbnail: {
folder: "demo/TEMP",
hardwareAcceleration: true
},
database: {
type: DatabaseType.mysql,
mysql: {
host: "localhost",
username: "root",
password: "root",
database: "pigallery2"
}
}
};
public setDatabaseType(type: DatabaseType) {
this.Server.database.type = type;
if (type === DatabaseType.memory) {
this.Client.Search.searchEnabled = false;
this.Client.Search.instantSearchEnabled = false;
this.Client.Search.autocompleteEnabled = false;
}
}
}

View File

@ -0,0 +1,15 @@
import {PublicConfigClass} from "./ConfigClass";
import {WebConfigLoader} from "typeconfig/src/WebConfigLoader";
declare module ServerInject {
export const ConfigInject;
}
export let Config = new PublicConfigClass();
if (typeof ServerInject !== "undefined" && typeof ServerInject.ConfigInject !== "undefined") {
WebConfigLoader.loadFrontendConfig(Config.Client, ServerInject.ConfigInject);
}

View File

@ -1,29 +1,3 @@
export enum DatabaseType{
memory = 0, mysql = 1
}
interface MySQLConfig {
host: string;
database: string;
username: string;
password: string;
}
interface DataBaseConfig {
type: DatabaseType;
mysql?: MySQLConfig;
}
interface ThumbnailConfig {
folder: string;
hardwareAcceleration: boolean;
}
interface ServerConfig {
port: number;
imagesFolder: string;
thumbnail: ThumbnailConfig;
database: DataBaseConfig;
}
interface SearchConfig {
searchEnabled: boolean
instantSearchEnabled: boolean
@ -41,9 +15,11 @@ interface ClientConfig {
authenticationRequired: boolean;
googleApiKey: string;
}
export class ConfigClass {
public Server: ServerConfig = null;
/**
* These configuration will be available at frontend and backend too
*/
export class PublicConfigClass {
public Client: ClientConfig = {
thumbnailSizes: [200, 400, 600],
@ -61,14 +37,5 @@ export class ConfigClass {
googleApiKey: ""
};
public setDatabaseType(type: DatabaseType) {
this.Server.database.type = type;
if (type === DatabaseType.memory) {
this.Client.Search.searchEnabled = false;
this.Client.Search.instantSearchEnabled = false;
this.Client.Search.autocompleteEnabled = false;
}
}
}

View File

@ -2,7 +2,7 @@ import {Component, OnInit} from "@angular/core";
import {AuthenticationService} from "../model/network/authentication.service";
import {Router} from "@angular/router";
import {UserRoles} from "../../../common/entities/UserDTO";
import {Config} from "../config/Config";
import {Config} from "../../../common/config/public/Config";
@Component({
selector: 'admin',
templateUrl: 'app/admin/admin.component.html',

View File

@ -26,11 +26,11 @@ import {LoginComponent} from "./login/login.component";
import {AdminComponent} from "./admin/admin.component";
import {GalleryComponent} from "./gallery/gallery.component";
import {StringifyRole} from "./pipes/StringifyRolePipe";
import {Config} from "./config/Config";
import {GalleryMapComponent} from "./gallery/map/map.gallery.component";
import {GalleryMapLightboxComponent} from "./gallery/map/lightbox/lightbox.map.gallery.component";
import {ThumbnailManagerService} from "./gallery/thumnailManager.service";
import {OverlayService} from "./gallery/overlay.service";
import {Config} from "../../common/config/public/Config";
@NgModule({
imports: [

View File

@ -1,12 +0,0 @@
import {ConfigClass} from "../../../common/config/Config";
import {Utils} from "../../../common/Utils";
declare module ServerInject {
export let ConfigInject: ConfigClass;
}
export let Config = new ConfigClass();
if (typeof ServerInject !== "undefined" && typeof ServerInject.ConfigInject !== "undefined") {
Utils.updateKeys(Config.Client, ServerInject.ConfigInject);
}

View File

@ -2,7 +2,7 @@ import {Component, ViewEncapsulation} from "@angular/core";
import {RouterLink} from "@angular/router";
import {AuthenticationService} from "../model/network/authentication.service";
import {UserDTO} from "../../../common/entities/UserDTO";
import {Config} from "../config/Config";
import {Config} from "../../../common/config/public/Config";
@Component({
selector: 'app-frame',

View File

@ -1,7 +1,7 @@
import {PhotoDTO} from "../../../common/entities/PhotoDTO";
import {Utils} from "../../../common/Utils";
import {Config} from "../config/Config";
import {IconPhoto} from "./IconPhoto";
import {Config} from "../../../common/config/public/Config";
export class Photo extends IconPhoto {

View File

@ -2,7 +2,7 @@ import {Injectable} from "@angular/core";
import {PhotoDTO} from "../../../common/entities/PhotoDTO";
import {DirectoryDTO} from "../../../common/entities/DirectoryDTO";
import {Utils} from "../../../common/Utils";
import {Config} from "../config/Config";
import {Config} from "../../../common/config/public/Config";
@Injectable()
export class GalleryCacheService {

View File

@ -1,11 +1,11 @@
import {Component, OnInit, ViewChild} from "@angular/core";
import {AuthenticationService} from "../model/network/authentication.service";
import {Router, ActivatedRoute, Params} from "@angular/router";
import {ActivatedRoute, Params, Router} from "@angular/router";
import {GalleryService} from "./gallery.service";
import {GalleryGridComponent} from "./grid/grid.gallery.component";
import {GallerySearchComponent} from "./search/search.gallery.component";
import {Config} from "../config/Config";
import {SearchTypes} from "../../../common/entities/AutoCompleteItem";
import {Config} from "../../../common/config/public/Config";
@Component({
selector: 'gallery',

View File

@ -15,8 +15,8 @@ import {GridRowBuilder} from "./GridRowBuilder";
import {GalleryLightboxComponent} from "../lightbox/lightbox.gallery.component";
import {GridPhoto} from "./GridPhoto";
import {GalleryPhotoComponent} from "./photo/photo.grid.gallery.component";
import {Config} from "../../config/Config";
import {OverlayService} from "../overlay.service";
import {Config} from "../../../../common/config/public/Config";
@Component({
selector: 'gallery-grid',

View File

@ -1,10 +1,10 @@
import {Component, Input, ElementRef, ViewChild, OnInit, OnDestroy} from "@angular/core";
import {IRenderable, Dimension} from "../../../model/IRenderable";
import {Component, ElementRef, Input, OnDestroy, OnInit, ViewChild} from "@angular/core";
import {Dimension, IRenderable} from "../../../model/IRenderable";
import {GridPhoto} from "../GridPhoto";
import {SearchTypes} from "../../../../../common/entities/AutoCompleteItem";
import {RouterLink} from "@angular/router";
import {Config} from "../../../config/Config";
import {Thumbnail, ThumbnailManagerService} from "../../thumnailManager.service";
import {Config} from "../../../../../common/config/public/Config";
@Component({
selector: 'gallery-grid-photo',

View File

@ -1,10 +1,10 @@
import {Component} from "@angular/core";
import {AutoCompleteService} from "./autocomplete.service";
import {AutoCompleteItem, SearchTypes} from "../../../../common/entities/AutoCompleteItem";
import {RouterLink, ActivatedRoute, Params} from "@angular/router";
import {ActivatedRoute, Params, RouterLink} from "@angular/router";
import {Message} from "../../../../common/entities/Message";
import {GalleryService} from "../gallery.service";
import {Config} from "../../config/Config";
import {Config} from "../../../../common/config/public/Config";
@Component({
selector: 'gallery-search',

View File

@ -1,9 +1,9 @@
import {Injectable} from "@angular/core";
import {Config} from "../config/Config";
import {GalleryCacheService} from "./cache.gallery.service";
import {Photo} from "./Photo";
import {IconPhoto} from "./IconPhoto";
import {PhotoDTO} from "../../../common/entities/PhotoDTO";
import {Config} from "../../../common/config/public/Config";
export enum ThumbnailLoadingPriority{
high, medium, low

View File

@ -6,7 +6,7 @@ import {LoginCredential} from "../../../../common/entities/LoginCredential";
import {Message} from "../../../../common/entities/Message";
import {Cookie} from "ng2-cookies";
import {ErrorCodes} from "../../../../common/entities/Error";
import {Config} from "../../config/Config";
import {Config} from "../../../../common/config/public/Config";
declare module ServerInject {
export let user: UserDTO;

View File

@ -27,7 +27,8 @@
'rxjs': 'npm:rxjs',
'@agm/core': 'npm:@agm/core/core.umd.js',
'ng2-cookies': 'npm:ng2-cookies/ng2-cookies'
'ng2-cookies': 'npm:ng2-cookies/ng2-cookies',
'typeconfig': 'npm:typeconfig'
},
// packages tells the System loader how to load when no filename and/or no extension
packages: {

View File

@ -4,7 +4,7 @@ import {Error, ErrorCodes} from "../../../../../common/entities/Error";
import {UserRoles} from "../../../../../common/entities/UserDTO";
import {ObjectManagerRepository} from "../../../../../backend/model/ObjectManagerRepository";
import {UserManager} from "../../../../../backend/model/memory/UserManager";
import {Config} from "../../../../../backend/config/Config";
import {Config} from "../../../../../common/config/private/Config";
describe('Authentication middleware', () => {