Apply eslint automatic fix

pull/32/head
HardiReady 2018-03-12 09:26:44 +01:00
parent c78651a703
commit 7b9d23d1b1
57 changed files with 753 additions and 840 deletions

View File

@ -17,5 +17,5 @@ module.exports = {
signUp: rootRoute + '/authenticate/signup',
squads: rootRoute + '/squads',
users: rootRoute + '/users',
wars: rootRoute + '/wars'
wars: rootRoute + '/wars',
};

View File

@ -7,17 +7,17 @@ module.exports = {
},
prod: {
env: 'production'
env: 'production',
},
dev: {
env: 'dev'
env: 'dev',
},
test: {
port: 3001,
db: 'cc-test',
env: 'test'
}
env: 'test',
},
};

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
const cron = require('cron');
const async = require('async');
@ -19,8 +19,8 @@ const createAllSignatures = () => {
// mock response
const res = {
locals: {
items: {}
}
items: {},
},
};
// re-create signature image for each active user
@ -29,21 +29,21 @@ const createAllSignatures = () => {
// mock next to execute callback
const next = (err) => {
if (!err || (err && err.message.startsWith('Fraction not defined'))) {
callback()
callback();
} else {
error('\x1b[41m%s\x1b[0m', new Date().toLocaleString()
+ ': Error in execution - UPDATE SIGNATURES: ' + err.message)
+ ': Error in execution - UPDATE SIGNATURES: ' + err.message);
}
};
signatureTool(user._id, res, next)
signatureTool(user._id, res, next);
}, () => {
if (err) {
error('\x1b[41m%s\x1b[0m', new Date().toLocaleString()
+ ': Error in execution - UPDATE SIGNATURES: ' + err.message)
+ ': Error in execution - UPDATE SIGNATURES: ' + err.message);
}
logger('\x1b[35m%s\x1b[0m', new Date().toLocaleString()
+ ': finished successful - UPDATE SIGNATURES');
})
});
});
};
@ -57,7 +57,7 @@ const createBackup = () => {
logger('\x1b[32m%s\x1b[0m', stderr);
logger('\x1b[35m%s\x1b[0m', new Date().toLocaleString()
+ ': cron job finished - CREATE BACKUP');
})
});
};
// Execute daily @ 02:30 AM
@ -69,5 +69,5 @@ const cronJobBackup = cron.job('00 00 04 * * mon,thu,sat', createBackup);
module.exports = {
cronJobSignature: cronJobSignature,
cronJobBackup: cronJobBackup,
createAllSignatures: createAllSignatures
createAllSignatures: createAllSignatures,
};

View File

@ -1,17 +1,15 @@
"use strict";
'use strict';
const jwt = require('jsonwebtoken');
const config = require('../config/config');
const AppUser = require('../models/app-user');
const apiAuthentication = (req, res, next) => {
// check header or url parameters or post parameters for token
const token = req.body.token || req.query.token || req.headers['x-access-token'];
// decode token
if (token) {
const secret = process.env.NODE_ENV === config.prod.env ? process.env.JWS_SECRET : 'dev-secret';
// verifies secret and checks exp
@ -25,7 +23,7 @@ const apiAuthentication = (req, res, next) => {
if (err) {
return res.status(403).send({
success: false,
message: 'token is not associated to any actual user'
message: 'token is not associated to any actual user',
});
}
req.user = item;
@ -33,16 +31,13 @@ const apiAuthentication = (req, res, next) => {
});
}
});
} else {
// if there is no token
// return an error
return res.status(403).send({
success: false,
message: 'No token provided.'
message: 'No token provided.',
});
}
};

View File

@ -1,43 +1,43 @@
/** This module provides middleware to respond with proper JSON error objects
* using NODE_ENV setting to production or development. In dev mode it send the stacktrace.
*
* You call the returned function with an app instance
*
* @author Johannes Konert
* @licence CC BY-SA 4.0
*
*
* @module restapi/error-response
* @type {Function}
*/
"use strict";
const logger = require('debug')('me2:error-response');
module.exports = (app) => {
// development error handler
// will print stacktrace as JSON response
if (app.get('env') === 'development') {
app.use(function (err, req, res, next) {
logger('Internal Error: ', err.stack);
res.status(err.status || 500);
res.json({
error: {
message: err.message,
error: err.stack
}
});
});
} else {
// production error handler
// no stacktraces leaked to user
app.use(function (err, req, res, next) {
res.status(err.status || 500);
res.json({
error: {
message: err.message,
error: {}
}
});
});
}
};
/** This module provides middleware to respond with proper JSON error objects
* using NODE_ENV setting to production or development. In dev mode it send the stacktrace.
*
* You call the returned function with an app instance
*
* @author Johannes Konert
* @licence CC BY-SA 4.0
*
*
* @module restapi/error-response
* @type {Function}
*/
'use strict';
const logger = require('debug')('me2:error-response');
module.exports = (app) => {
// development error handler
// will print stacktrace as JSON response
if (app.get('env') === 'development') {
app.use(function(err, req, res, next) {
logger('Internal Error: ', err.stack);
res.status(err.status || 500);
res.json({
error: {
message: err.message,
error: err.stack,
},
});
});
} else {
// production error handler
// no stacktraces leaked to user
app.use(function(err, req, res, next) {
res.status(err.status || 500);
res.json({
error: {
message: err.message,
error: {},
},
});
});
}
};

View File

@ -1,104 +1,104 @@
/** This module defines a express.Router() instance
* - supporting filter=key1,key2
* - it sets res.locals.filter to a string "key1 key2"
* - calls next with error if a filter=key is given, but key does not exist (not raised on empty item arrays!)
*
* Note: it expects to be called before any data is fetched from DB
* Note: it sets an Error-Object to next with error.status set to HTTP status code 400
*
* @author Johannes Konert
* @licence CC BY-SA 4.0
*
* @module restapi/filter-middleware-mongo
* @type {Factory function returning an Router}
* @param Schema {Object} a MongooseSchema.path value or similar object with attributes representing the valid keys
* @param suppressId {Boolean} if true, the _id is not returned implicitly
*/
// remember: in modules you have 3 variables given by CommonJS
// 1.) require() function
// 2.) module.exports
// 3.) exports (which is module.exports)
"use strict";
const express = require('express');
const logger = require('debug')('middleware:filterware');
/**
* private helper function to filter Objects by given keys
* @param keys {Array} the keys from GET parameter filter
* @param schema [Object} containing the keys as attributes that are allowed
* @returns {Object or Error} either the filtered items or an Error object
*/
const limitFilterToSchema = (keys, schema) => {
if (!keys || !schema) { // empty arrays evaluate to false
return undefined; // means no filter at all
}
let error = null;
const result = [];
// now for each given filter=key1,key2in the array check that the schema allows this key and store it in result
keys.forEach((key) => {
if (schema.hasOwnProperty(key)) {
result.push(key);
} else {
error = new Error('given key for filter does not exist in ressource: ' + key);
}
});
return error ? error : result
};
/**
* closure function as factory returning the router
*
* @param Schema {Object} a MongooseSchema.path value or similar object with attributes representing the valid keys
* @param suppressId {Boolean} if true, the _id is not returned implicitly
* @returns {Router}
*/
const createFilterRouter = (schema, supressID) => {
const router = express.Router();
// the exported router with handler
router.use((req, res, next) => {
const filterString = req.query.filter;
let filterKeys = [];
let err = null;
if (filterString !== undefined) {
filterKeys = filterString.split(',');
filterKeys.forEach((item, index, array) => {
array[index] = item.trim();
});
filterKeys = filterKeys.filter((item) => {
return item.length > 0;
});
if (filterKeys.length === 0) {
err = new Error('given filter does not contain any keys');
err.status = 400;
} else {
const result = limitFilterToSchema(filterKeys, schema);
if (result instanceof Error) {
err = result;
err.status = 400;
} else {
res.locals.filter = result.join(' '); // create a string with space as seperator
if (supressID) {
res.locals.filter = '-_id ' + res.locals.filter;
}
}
}
}
if (err) {
logger(err);
next(err)
} else {
if (res.locals.filter) {
logger('Successfully set filter to ' + res.locals.filter);
}
next()
}
});
return router;
};
module.exports = createFilterRouter;
/** This module defines a express.Router() instance
* - supporting filter=key1,key2
* - it sets res.locals.filter to a string "key1 key2"
* - calls next with error if a filter=key is given, but key does not exist (not raised on empty item arrays!)
*
* Note: it expects to be called before any data is fetched from DB
* Note: it sets an Error-Object to next with error.status set to HTTP status code 400
*
* @author Johannes Konert
* @licence CC BY-SA 4.0
*
* @module restapi/filter-middleware-mongo
* @type {Factory function returning an Router}
* @param Schema {Object} a MongooseSchema.path value or similar object with attributes representing the valid keys
* @param suppressId {Boolean} if true, the _id is not returned implicitly
*/
// remember: in modules you have 3 variables given by CommonJS
// 1.) require() function
// 2.) module.exports
// 3.) exports (which is module.exports)
'use strict';
const express = require('express');
const logger = require('debug')('middleware:filterware');
/**
* private helper function to filter Objects by given keys
* @param keys {Array} the keys from GET parameter filter
* @param schema [Object} containing the keys as attributes that are allowed
* @returns {Object or Error} either the filtered items or an Error object
*/
const limitFilterToSchema = (keys, schema) => {
if (!keys || !schema) { // empty arrays evaluate to false
return undefined; // means no filter at all
}
let error = null;
const result = [];
// now for each given filter=key1,key2in the array check that the schema allows this key and store it in result
keys.forEach((key) => {
if (schema.hasOwnProperty(key)) {
result.push(key);
} else {
error = new Error('given key for filter does not exist in ressource: ' + key);
}
});
return error ? error : result;
};
/**
* closure function as factory returning the router
*
* @param Schema {Object} a MongooseSchema.path value or similar object with attributes representing the valid keys
* @param suppressId {Boolean} if true, the _id is not returned implicitly
* @returns {Router}
*/
const createFilterRouter = (schema, supressID) => {
const router = express.Router();
// the exported router with handler
router.use((req, res, next) => {
const filterString = req.query.filter;
let filterKeys = [];
let err = null;
if (filterString !== undefined) {
filterKeys = filterString.split(',');
filterKeys.forEach((item, index, array) => {
array[index] = item.trim();
});
filterKeys = filterKeys.filter((item) => {
return item.length > 0;
});
if (filterKeys.length === 0) {
err = new Error('given filter does not contain any keys');
err.status = 400;
} else {
const result = limitFilterToSchema(filterKeys, schema);
if (result instanceof Error) {
err = result;
err.status = 400;
} else {
res.locals.filter = result.join(' '); // create a string with space as seperator
if (supressID) {
res.locals.filter = '-_id ' + res.locals.filter;
}
}
}
}
if (err) {
logger(err);
next(err);
} else {
if (res.locals.filter) {
logger('Successfully set filter to ' + res.locals.filter);
}
next();
}
});
return router;
};
module.exports = createFilterRouter;

View File

@ -17,7 +17,7 @@
// 1.) require() function
// 2.) module.exports
// 3.) exports (which is module.exports)
"use strict";
'use strict';
const router = require('express').Router();
const logger = require('debug')('middleware:offsetlimit');
@ -36,10 +36,9 @@ router.use((req, res, next) => {
if (!isNaN(offsetString)) {
offset = parseInt(offsetString);
if (offset < 0) {
err = new Error('offset is negative')
err = new Error('offset is negative');
}
}
else {
} else {
err = new Error('given offset is not a valid number ' + offsetString);
}
}
@ -47,22 +46,21 @@ router.use((req, res, next) => {
if (!isNaN(limitString)) {
limit = parseInt(limitString);
if (limit < 1) {
err = new Error('limit is zero or negative')
err = new Error('limit is zero or negative');
}
}
else {
} else {
err = new Error('given limit is not a valid number ' + limitString);
}
}
if (err) {
logger('problem occurred with limit/offset values');
err.status = 400;
next(err)
next(err);
} else {
res.locals.limitskip = {}; // mongoDB uses parameter object for skip/limit
if (limit) res.locals.limitskip.limit = limit;
if (offset) res.locals.limitskip.skip = offset;
next()
next();
}
});

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
let check = (requiredPermission, actualPermission, res, next) => {
@ -7,21 +7,21 @@ let check = (requiredPermission, actualPermission, res, next) => {
}
return res.status(403).send({
success: false,
message: 'permission denied'
message: 'permission denied',
});
};
module.exports = {
checkSql: (req, res, next) => {
check(1, req.user.permission, res, next)
check(1, req.user.permission, res, next);
},
checkHl: (req, res, next) => {
check(2, req.user.permission, res, next)
check(2, req.user.permission, res, next);
},
checkMT: (req, res, next) => {
check(3, req.user.permission, res, next)
check(3, req.user.permission, res, next);
},
checkAdmin: (req, res, next) => {
check(4, req.user.permission, res, next)
}
check(4, req.user.permission, res, next);
},
};

View File

@ -1,67 +1,66 @@
/** This module defines a express.Router() instance
* - checking Accept-Version header to be 1.0
* - body-data to be JSON on POST/PUT/PATCH
* - body to be not empty on POST/PUT/PATCH
* - Request accepts JSOn as reply content-type
*
* @author Johannes Konert
* @licence CC BY-SA 4.0
*
* @module restapi/request-checks
* @type {Router}
*/
// remember: in modules you have 3 variables given by CommonJS
// 1.) require() function
// 2.) module.exports
// 3.) exports (which is module.exports)
"use strict";
const router = require('express').Router();
// API-Version control. We use HTTP Header field Accept-Version instead of URL-part /v1/
router.use((req, res, next) => {
// expect the Accept-Version header to be NOT set or being 1.0
const versionWanted = req.get('Accept-Version');
if (versionWanted !== undefined && versionWanted !== '1.0') {
// 406 Accept-* header cannot be fulfilled.
res.status(406).send('Accept-Version cannot be fulfilled').end();
} else {
next(); // all OK, call next handler
}
});
// request type application/json check
router.use((req, res, next) => {
if (['POST', 'PUT', 'PATCH'].indexOf(req.method) > -1 &&
(!(/multipart\/form-data/.test(req.get('Content-Type'))) &&
!(/application\/json/.test(req.get('Content-Type'))))) {
// send error code 415: unsupported media type
res.status(415).send('wrong Content-Type'); // user has SEND the wrong type
} else if (!req.accepts('json')) {
// send 406 that response will be application/json and request does not support it by now as answer
// user has REQUESTED the wrong type
res.status(406).send('response of application/json only supported, please accept this');
}
else {
next(); // let this request pass through as it is OK
}
});
// request POST, PUT check that any content was send
router.use((req, res, next) => {
let err = undefined;
if (['POST', 'PUT', 'PATCH'].indexOf(req.method) > -1 && parseInt(req.get('Content-Length')) === 0) {
err = new Error("content in body is missing");
err.status = 400;
next(err);
} else if ('PUT' === req.method && !(req.body.id || req.body._id)) {
err = new Error("content in body is missing field id");
err.status = 400;
next(err);
}
next();
});
module.exports = router;
/** This module defines a express.Router() instance
* - checking Accept-Version header to be 1.0
* - body-data to be JSON on POST/PUT/PATCH
* - body to be not empty on POST/PUT/PATCH
* - Request accepts JSOn as reply content-type
*
* @author Johannes Konert
* @licence CC BY-SA 4.0
*
* @module restapi/request-checks
* @type {Router}
*/
// remember: in modules you have 3 variables given by CommonJS
// 1.) require() function
// 2.) module.exports
// 3.) exports (which is module.exports)
'use strict';
const router = require('express').Router();
// API-Version control. We use HTTP Header field Accept-Version instead of URL-part /v1/
router.use((req, res, next) => {
// expect the Accept-Version header to be NOT set or being 1.0
const versionWanted = req.get('Accept-Version');
if (versionWanted !== undefined && versionWanted !== '1.0') {
// 406 Accept-* header cannot be fulfilled.
res.status(406).send('Accept-Version cannot be fulfilled').end();
} else {
next(); // all OK, call next handler
}
});
// request type application/json check
router.use((req, res, next) => {
if (['POST', 'PUT', 'PATCH'].indexOf(req.method) > -1 &&
(!(/multipart\/form-data/.test(req.get('Content-Type'))) &&
!(/application\/json/.test(req.get('Content-Type'))))) {
// send error code 415: unsupported media type
res.status(415).send('wrong Content-Type'); // user has SEND the wrong type
} else if (!req.accepts('json')) {
// send 406 that response will be application/json and request does not support it by now as answer
// user has REQUESTED the wrong type
res.status(406).send('response of application/json only supported, please accept this');
} else {
next(); // let this request pass through as it is OK
}
});
// request POST, PUT check that any content was send
router.use((req, res, next) => {
let err = undefined;
if (['POST', 'PUT', 'PATCH'].indexOf(req.method) > -1 && parseInt(req.get('Content-Length')) === 0) {
err = new Error('content in body is missing');
err.status = 400;
next(err);
} else if ('PUT' === req.method && !(req.body.id || req.body._id)) {
err = new Error('content in body is missing field id');
err.status = 400;
next(err);
}
next();
});
module.exports = router;

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
// HTTP status codes by name
const codes = require('../routes/http-codes');

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
// HTTP status codes by name
const codes = require('../routes/http-codes');
@ -10,7 +10,7 @@ const idValidator = (req, res, next) => {
const reqId = req.params.id;
if (!reqId.match(/^[0-9a-fA-F]{24}$/)) {
const err = new Error("Invalid request id format");
const err = new Error('Invalid request id format');
err.status = codes.notfound;
return next(err);
}

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
const mongoose = require('mongoose');
const Schema = mongoose.Schema;
@ -7,36 +7,36 @@ const AppUserSchema = new Schema({
username: {
type: String,
required: true,
unique: true
unique: true,
},
password: {
type: String,
required: true
required: true,
},
squad: {
type: mongoose.Schema.Types.ObjectId,
ref: 'Squad',
default: null
default: null,
},
permission: {
type: Number,
get: v => Math.round(v),
set: v => Math.round(v),
get: (v) => Math.round(v),
set: (v) => Math.round(v),
min: 0,
max: 4,
default: 0
default: 0,
},
secret: {
type: String,
required: true
required: true,
},
activated: {
type: Boolean,
default: false
}
default: false,
},
}, {
collection: 'app_user',
timestamps: {createdAt: 'timestamp'}
timestamps: {createdAt: 'timestamp'},
});
// optional more indices
AppUserSchema.index({timestamp: 1});

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
const mongoose = require('mongoose');
const Schema = mongoose.Schema;
@ -6,39 +6,39 @@ const Schema = mongoose.Schema;
const AwardingSchema = new Schema({
userId: {
type: mongoose.Schema.Types.ObjectId,
ref: 'User'
ref: 'User',
},
decorationId: {
type: mongoose.Schema.Types.ObjectId,
ref: 'Decoration'
ref: 'Decoration',
},
reason: {
type: String,
required: true
required: true,
},
proposer: {
type: mongoose.Schema.Types.ObjectId,
ref: 'AppUser',
required: true
required: true,
},
confirmed: {
type: Number,
get: v => Math.round(v),
set: v => Math.round(v),
get: (v) => Math.round(v),
set: (v) => Math.round(v),
min: 0,
max: 2,
default: 0
default: 0,
},
rejectReason: {
type: String
type: String,
},
date: {
type: Date,
default: Date.now()
}
default: Date.now(),
},
}, {
collection: 'awarding',
timestamps: {createdAt: 'timestamp'}
timestamps: {createdAt: 'timestamp'},
});
// optional more indices
AwardingSchema.index({timestamp: 1});

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
const mongoose = require('mongoose');
const Schema = mongoose.Schema;
@ -6,11 +6,11 @@ const Schema = mongoose.Schema;
const CampaignSchema = new Schema({
title: {
type: String,
required: true
}
required: true,
},
}, {
collection: 'campaign',
timestamps: {createdAt: 'timestamp'}
timestamps: {createdAt: 'timestamp'},
});
// optional more indices
CampaignSchema.index({timestamp: 1});

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
const mongoose = require('mongoose');
const Schema = mongoose.Schema;
@ -6,27 +6,27 @@ const Schema = mongoose.Schema;
const DecorationSchema = new Schema({
name: {
type: String,
required: true
required: true,
},
fraction: {
type: String,
enum: ['BLUFOR', 'OPFOR', 'GLOBAL'],
required: true
required: true,
},
description: {
type: String,
required: true
required: true,
},
sortingNumber: {
type: Number,
get: v => Math.round(v),
set: v => Math.round(v),
default: 0
get: (v) => Math.round(v),
set: (v) => Math.round(v),
default: 0,
},
isMedal: {type: Boolean, required: true}
isMedal: {type: Boolean, required: true},
}, {
collection: 'decoration',
timestamps: {createdAt: 'timestamp'}
timestamps: {createdAt: 'timestamp'},
});
// optional more indices
DecorationSchema.index({timestamp: 1});

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
const mongoose = require('mongoose');
const Schema = mongoose.Schema;
@ -7,31 +7,31 @@ const LogBudgetSchema = new Schema({
war: {
type: mongoose.Schema.Types.ObjectId,
ref: 'War',
required: true
required: true,
},
time: {
type: Date,
required: true
required: true,
},
fraction: {
type: String,
enum: ['BLUFOR', 'OPFOR'],
required: true
required: true,
},
oldBudget: {
type: Number,
get: v => Math.round(v),
set: v => Math.round(v),
required: true
get: (v) => Math.round(v),
set: (v) => Math.round(v),
required: true,
},
newBudget: {
type: Number,
get: v => Math.round(v),
set: v => Math.round(v),
required: true
}
get: (v) => Math.round(v),
set: (v) => Math.round(v),
required: true,
},
}, {
collection: 'logBudget'
collection: 'logBudget',
});
// optional more indices
LogBudgetSchema.index({war: 1});

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
const mongoose = require('mongoose');
const Schema = mongoose.Schema;
@ -7,27 +7,27 @@ const LogFlagSchema = new Schema({
war: {
type: mongoose.Schema.Types.ObjectId,
ref: 'War',
required: true
required: true,
},
time: {
type: Date,
required: true
required: true,
},
player: {
type: String,
required: true
required: true,
},
flagFraction: {
type: String,
enum: ['BLUFOR', 'OPFOR'],
required: true
required: true,
},
capture: {
type: Boolean,
required: true
}
required: true,
},
}, {
collection: 'logFlag'
collection: 'logFlag',
});
// optional more indices
LogFlagSchema.index({war: 1, player: 1});

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
const mongoose = require('mongoose');
const Schema = mongoose.Schema;
@ -7,30 +7,30 @@ const LogKillSchema = new Schema({
war: {
type: mongoose.Schema.Types.ObjectId,
ref: 'War',
required: true
required: true,
},
time: {
type: Date,
required: true
required: true,
},
shooter: {
type: String
type: String,
},
target: {
type: String,
required: true
required: true,
},
friendlyFire: {
type: Boolean,
required: true
required: true,
},
fraction: {
type: String,
enum: ['BLUFOR', 'OPFOR', 'NONE'],
required: true
}
required: true,
},
}, {
collection: 'logKill'
collection: 'logKill',
});
// optional more indices
LogKillSchema.index({war: 1, shooter: 1, target: 1});

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
const mongoose = require('mongoose');
const Schema = mongoose.Schema;
@ -7,31 +7,31 @@ const LogKillSchema = new Schema({
war: {
type: mongoose.Schema.Types.ObjectId,
ref: 'War',
required: true
required: true,
},
time: {
type: Date,
required: true
required: true,
},
ptBlufor: {
type: Number,
get: v => Math.round(v),
set: v => Math.round(v),
required: true
get: (v) => Math.round(v),
set: (v) => Math.round(v),
required: true,
},
ptOpfor: {
type: Number,
get: v => Math.round(v),
set: v => Math.round(v),
required: true
get: (v) => Math.round(v),
set: (v) => Math.round(v),
required: true,
},
fraction: {
type: String,
enum: ['BLUFOR', 'OPFOR', 'NONE'],
required: true
}
required: true,
},
}, {
collection: 'logPoints'
collection: 'logPoints',
});
// optional more indices
LogKillSchema.index({war: 1, shooter: 1, target: 1});

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
const mongoose = require('mongoose');
const Schema = mongoose.Schema;
@ -7,18 +7,18 @@ const LogRespawnSchema = new Schema({
war: {
type: mongoose.Schema.Types.ObjectId,
ref: 'War',
required: true
required: true,
},
time: {
type: Date,
required: true
required: true,
},
player: {
type: String,
required: true
}
required: true,
},
}, {
collection: 'logRespawn'
collection: 'logRespawn',
});
// optional more indices
LogRespawnSchema.index({war: 1, player: 1});

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
const mongoose = require('mongoose');
const Schema = mongoose.Schema;
@ -7,31 +7,31 @@ const LogReviveSchema = new Schema({
war: {
type: mongoose.Schema.Types.ObjectId,
ref: 'War',
required: true
required: true,
},
time: {
type: Date,
required: true
required: true,
},
medic: {
type: String,
required: true
required: true,
},
patient: {
type: String,
required: true
required: true,
},
stabilized: {
type: Boolean,
required: true
required: true,
},
fraction: {
type: String,
enum: ['BLUFOR', 'OPFOR'],
required: true
}
required: true,
},
}, {
collection: 'logRevive'
collection: 'logRevive',
});
// optional more indices
LogReviveSchema.index({war: 1, medic: 1});

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
const mongoose = require('mongoose');
const Schema = mongoose.Schema;
@ -7,33 +7,33 @@ const LogTransportSchema = new Schema({
war: {
type: mongoose.Schema.Types.ObjectId,
ref: 'War',
required: true
required: true,
},
time: {
type: Date,
required: true
required: true,
},
driver: {
type: String,
required: true
required: true,
},
passenger: {
type: String,
required: true
required: true,
},
distance: {
type: Number,
get: v => Math.round(v),
set: v => Math.round(v),
required: true
get: (v) => Math.round(v),
set: (v) => Math.round(v),
required: true,
},
fraction: {
type: String,
enum: ['BLUFOR', 'OPFOR'],
required: true
}
required: true,
},
}, {
collection: 'logTransport'
collection: 'logTransport',
});
// optional more indices
LogTransportSchema.index({war: 1, driver: 1});

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
const mongoose = require('mongoose');
const Schema = mongoose.Schema;
@ -7,26 +7,26 @@ const LogVehicleKillSchema = new Schema({
war: {
type: mongoose.Schema.Types.ObjectId,
ref: 'War',
required: true
required: true,
},
time: {
type: Date,
required: true
required: true,
},
shooter: {
type: String
type: String,
},
target: {
type: String,
required: true
required: true,
},
fraction: {
type: String,
enum: ['BLUFOR', 'OPFOR', 'NONE'],
required: true
}
required: true,
},
}, {
collection: 'logVehicle'
collection: 'logVehicle',
});
// optional more indices
LogVehicleKillSchema.index({war: 1, shooter: 1, target: 1});

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
const mongoose = require('mongoose');
const Schema = mongoose.Schema;
@ -6,73 +6,73 @@ const Schema = mongoose.Schema;
const PlayerSchema = new Schema({
name: {
type: String,
required: true
required: true,
},
fraction: {
type: String,
enum: ['BLUFOR', 'OPFOR'],
required: true
required: true,
},
warId: {
type: mongoose.Schema.Types.ObjectId,
ref: 'War',
required: true
required: true,
},
kill: {
type: Number,
get: v => Math.round(v),
set: v => Math.round(v),
required: true
get: (v) => Math.round(v),
set: (v) => Math.round(v),
required: true,
},
vehicle: {
type: Number,
get: v => Math.round(v),
set: v => Math.round(v),
required: true
get: (v) => Math.round(v),
set: (v) => Math.round(v),
required: true,
},
death: {
type: Number,
get: v => Math.round(v),
set: v => Math.round(v),
required: true
get: (v) => Math.round(v),
set: (v) => Math.round(v),
required: true,
},
friendlyFire: {
type: Number,
get: v => Math.round(v),
set: v => Math.round(v),
required: true
get: (v) => Math.round(v),
set: (v) => Math.round(v),
required: true,
},
revive: {
type: Number,
get: v => Math.round(v),
set: v => Math.round(v),
required: true
get: (v) => Math.round(v),
set: (v) => Math.round(v),
required: true,
},
respawn: {
type: Number,
get: v => Math.round(v),
set: v => Math.round(v),
required: true
get: (v) => Math.round(v),
set: (v) => Math.round(v),
required: true,
},
flagTouch: {
type: Number,
get: v => Math.round(v),
set: v => Math.round(v),
required: true
get: (v) => Math.round(v),
set: (v) => Math.round(v),
required: true,
},
sort: {
type: Number,
get: v => Math.round(v),
set: v => Math.round(v)
get: (v) => Math.round(v),
set: (v) => Math.round(v),
},
steamUUID: {
type: Number,
get: v => Math.round(v),
set: v => Math.round(v)
}
get: (v) => Math.round(v),
set: (v) => Math.round(v),
},
}, {
collection: 'player',
timestamps: {createdAt: 'timestamp'}
timestamps: {createdAt: 'timestamp'},
});
// optional more indices
PlayerSchema.index({warId: 1});

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
const mongoose = require('mongoose');
const Schema = mongoose.Schema;
@ -6,39 +6,39 @@ const Schema = mongoose.Schema;
const PromotionSchema = new Schema({
userId: {
type: mongoose.Schema.Types.ObjectId,
ref: 'User'
ref: 'User',
},
proposer: {
type: mongoose.Schema.Types.ObjectId,
ref: 'AppUser',
required: true
required: true,
},
oldRankLvl: {
type: Number,
get: v => Math.round(v),
set: v => Math.round(v),
required: true
get: (v) => Math.round(v),
set: (v) => Math.round(v),
required: true,
},
newRankLvl: {
type: Number,
get: v => Math.round(v),
set: v => Math.round(v),
required: true
get: (v) => Math.round(v),
set: (v) => Math.round(v),
required: true,
},
confirmed: {
type: Number,
get: v => Math.round(v),
set: v => Math.round(v),
get: (v) => Math.round(v),
set: (v) => Math.round(v),
min: 0,
max: 2,
required: true
required: true,
},
rejectReason: {
type: String
}
type: String,
},
}, {
collection: 'promotion',
timestamps: {createdAt: 'timestamp'}
timestamps: {createdAt: 'timestamp'},
});
// optional more indices
PromotionSchema.index({timestamp: 1});

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
const mongoose = require('mongoose');
const Schema = mongoose.Schema;
@ -6,22 +6,22 @@ const Schema = mongoose.Schema;
const RankSchema = new Schema({
name: {
type: String,
required: true
required: true,
},
fraction: {
type: String,
enum: ['BLUFOR', 'OPFOR'],
required: true
required: true,
},
level: {
type: Number,
get: v => Math.round(v),
set: v => Math.round(v),
required: true
}
get: (v) => Math.round(v),
set: (v) => Math.round(v),
required: true,
},
}, {
collection: 'rank',
timestamps: {createdAt: 'timestamp'}
timestamps: {createdAt: 'timestamp'},
});
// optional more indices
RankSchema.index({timestamp: 1});

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
const mongoose = require('mongoose');
const Schema = mongoose.Schema;
@ -6,22 +6,22 @@ const Schema = mongoose.Schema;
const SquadSchema = new Schema({
name: {
type: String,
required: true
required: true,
},
fraction: {
type: String,
enum: ['BLUFOR', 'OPFOR'],
required: true
required: true,
},
sortingNumber: {
type: Number,
get: v => Math.round(v),
set: v => Math.round(v),
default: 0
}
get: (v) => Math.round(v),
set: (v) => Math.round(v),
default: 0,
},
}, {
collection: 'squad',
timestamps: {createdAt: 'timestamp'}
timestamps: {createdAt: 'timestamp'},
});
// optional more indices
SquadSchema.index({timestamp: 1});

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
const mongoose = require('mongoose');
const Schema = mongoose.Schema;
@ -7,22 +7,22 @@ const UserSchema = new Schema({
username: {
type: String,
required: true,
unique: true
unique: true,
},
rankLvl: {
type: Number,
get: v => Math.round(v),
set: v => Math.round(v),
default: 0
get: (v) => Math.round(v),
set: (v) => Math.round(v),
default: 0,
},
squadId: {
type: mongoose.Schema.Types.ObjectId,
ref: 'Squad',
default: null
}
default: null,
},
}, {
collection: 'user',
timestamps: {createdAt: 'timestamp'}
timestamps: {createdAt: 'timestamp'},
});
// optional more indices
UserSchema.index({timestamp: 1});

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
const mongoose = require('mongoose');
const Schema = mongoose.Schema;
@ -6,7 +6,7 @@ const Schema = mongoose.Schema;
const WarSchema = new Schema({
title: {
type: String,
required: true
required: true,
},
date: {
type: Date,
@ -16,58 +16,58 @@ const WarSchema = new Schema({
},
ptBlufor: {
type: Number,
get: v => Math.round(v),
set: v => Math.round(v),
get: (v) => Math.round(v),
set: (v) => Math.round(v),
},
ptOpfor: {
type: Number,
get: v => Math.round(v),
set: v => Math.round(v),
get: (v) => Math.round(v),
set: (v) => Math.round(v),
},
playersBlufor: {
type: Number,
get: v => Math.round(v),
set: v => Math.round(v),
default: 0
get: (v) => Math.round(v),
set: (v) => Math.round(v),
default: 0,
},
playersOpfor: {
type: Number,
get: v => Math.round(v),
set: v => Math.round(v),
default: 0
get: (v) => Math.round(v),
set: (v) => Math.round(v),
default: 0,
},
campaign: {
type: mongoose.Schema.Types.ObjectId,
ref: 'Campaign',
required: true
required: true,
},
budgetBlufor: {
type: Number,
get: v => Math.round(v),
set: v => Math.round(v),
default: 0
get: (v) => Math.round(v),
set: (v) => Math.round(v),
default: 0,
},
budgetOpfor: {
type: Number,
get: v => Math.round(v),
set: v => Math.round(v),
default: 0
get: (v) => Math.round(v),
set: (v) => Math.round(v),
default: 0,
},
endBudgetBlufor: {
type: Number,
get: v => Math.round(v),
set: v => Math.round(v),
default: 0
get: (v) => Math.round(v),
set: (v) => Math.round(v),
default: 0,
},
endBudgetOpfor: {
type: Number,
get: v => Math.round(v),
set: v => Math.round(v),
default: 0
}
get: (v) => Math.round(v),
set: (v) => Math.round(v),
default: 0,
},
}, {
collection: 'war',
timestamps: {createdAt: 'timestamp'}
timestamps: {createdAt: 'timestamp'},
});
// optional more indices
WarSchema.index({timestamp: 1});

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
// modules
const express = require('express');
@ -24,7 +24,7 @@ account.route('/')
res.locals.items = items;
res.locals.processed = true;
next();
})
});
})
.all(
routerHandling.httpMethodNotAllowed
@ -35,7 +35,7 @@ account.route('/:id')
.patch((req, res, next) => {
if (!req.body || (req.body._id && req.body._id !== req.params.id)) {
// little bit different as in PUT. :id does not need to be in data, but if the _id and url id must match
const err = new Error('id of PATCH resource and send JSON body are not equal ' + req.params.id + " " + req.body._id);
const err = new Error('id of PATCH resource and send JSON body are not equal ' + req.params.id + ' ' + req.body._id);
err.status = codes.notfound;
next(err);
return; // prevent node to process this function further after next() has finished.
@ -50,25 +50,22 @@ account.route('/:id')
AppUserModel.findByIdAndUpdate(req.params.id, req.body, {new: true}).populate('squad').exec((err, item) => {
if (err) {
err.status = codes.wrongrequest;
}
else if (!item) {
err = new Error("appUser not found");
} else if (!item) {
err = new Error('appUser not found');
err.status = codes.notfound;
}
else {
} else {
res.locals.items = item;
}
next(err);
})
});
})
.delete((req, res, next) => {
AppUserModel.findByIdAndRemove(req.params.id, (err, item) => {
if (err) {
err.status = codes.wrongrequest;
}
else if (!item) {
err = new Error("item not found");
} else if (!item) {
err = new Error('item not found');
err.status = codes.notfound;
}
// we don't set res.locals.items and thus it will send a 204 (no content) at the end. see last handler

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
// modules
const express = require('express');
@ -62,7 +62,7 @@ let authCheck = (username, password, res) => {
permission: user.permission,
squad: user.squad,
token: jwt.sign({sub: user._id}, secret, {expiresIn: diff * 60}),
tokenExpireDate: new Date(Date.now().valueOf() + diff * 60000 - 1000)
tokenExpireDate: new Date(Date.now().valueOf() + diff * 60000 - 1000),
});
} else {
// authentication failed
@ -101,7 +101,7 @@ let create = (userParam) => {
if (user) {
// username already exists
deferred.reject(new Error("Username already exists"));
deferred.reject(new Error('Username already exists'));
} else {
createUser();
}

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
// modules
const express = require('express');
@ -23,7 +23,7 @@ const resultSet = {
'password': 0,
'permission': 0,
'secret': 0,
'activated': 0
'activated': 0,
};
const awarding = express.Router();
@ -67,11 +67,10 @@ awarding.route('/')
if (req.query.fractFilter) {
for (let item of items) {
if (item.decorationId.fraction === req.query.fractFilter) {
results.push(item)
results.push(item);
}
}
res.locals.items = results;
} else {
res.locals.items = items;
}
@ -108,7 +107,7 @@ awarding.route('/:id')
.patch(apiAuthenticationMiddleware, checkHl, (req, res, next) => {
if (!req.body || (req.body._id && req.body._id !== req.params.id)) {
// little bit different as in PUT. :id does not need to be in data, but if the _id and url id must match
const err = new Error('id of PATCH resource and send JSON body are not equal ' + req.params.id + " " + req.body._id);
const err = new Error('id of PATCH resource and send JSON body are not equal ' + req.params.id + ' ' + req.body._id);
err.status = codes.notfound;
next(err);
return; // prevent node to process this function further after next() has finished.
@ -122,25 +121,22 @@ awarding.route('/:id')
AwardingModel.findByIdAndUpdate(req.params.id, req.body, {new: true}, (err, item) => {
if (err) {
err.status = codes.wrongrequest;
}
else if (!item) {
err = new Error("item not found");
} else if (!item) {
err = new Error('item not found');
err.status = codes.notfound;
}
else {
} else {
res.locals.items = item;
}
next(err);
})
});
})
.delete(apiAuthenticationMiddleware, checkHl, (req, res, next) => {
AwardingModel.findByIdAndRemove(req.params.id, (err, item) => {
if (err) {
err.status = codes.wrongrequest;
}
else if (!item) {
err = new Error("item not found");
} else if (!item) {
err = new Error('item not found');
err.status = codes.notfound;
}
// we don't set res.locals.items and thus it will send a 204 (no content) at the end. see last handler

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
// modules
const express = require('express');
@ -48,9 +48,8 @@ campaigns.route('/:id')
if (err) {
err.status = codes.servererror;
return next(err);
}
else if (!item) {
err = new Error("item not found");
} else if (!item) {
err = new Error('item not found');
err.status = codes.notfound;
return next(err);
}
@ -64,9 +63,8 @@ campaigns.route('/:id')
if (err) {
err.status = codes.wrongrequest;
return next(err);
}
else if (!item) {
err = new Error("item not found");
} else if (!item) {
err = new Error('item not found');
err.status = codes.notfound;
return next(err);
}
@ -74,7 +72,7 @@ campaigns.route('/:id')
res.locals.processed = true;
next();
})
});
})
.all(

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
// modules
const express = require('express');

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
// modules
const fs = require('fs');
@ -29,18 +29,18 @@ decoration.route('/')
.get((req, res, next) => {
const filter = {};
if (req.query.fractFilter) {
filter.fraction = req.query.fractFilter.toUpperCase()
filter.fraction = req.query.fractFilter.toUpperCase();
}
if (req.query.q) {
filter.name = {$regex: req.query.q, $options: 'i'}
filter.name = {$regex: req.query.q, $options: 'i'};
}
DecorationModel.find(filter, {}, {
sort: {
fraction: 'asc',
isMedal: 'asc',
sortingNumber: 'asc',
name: 'asc'
}
name: 'asc',
},
}, (err, items) => {
if (err) {
err.status = codes.servererror;
@ -72,7 +72,7 @@ decoration.route('/')
if (err) next(err);
});
next();
})
});
})
.all(
@ -85,9 +85,8 @@ decoration.route('/:id')
if (err) {
err.status = codes.servererror;
return next(err);
}
else if (!item) {
err = new Error("item not found");
} else if (!item) {
err = new Error('item not found');
err.status = codes.notfound;
return next(err);
}
@ -99,7 +98,7 @@ decoration.route('/:id')
.patch(apiAuthenticationMiddleware, checkHl, upload.single('image'), (req, res, next) => {
if (!req.body || (req.body._id && req.body._id !== req.params.id)) {
// little bit different as in PUT. :id does not need to be in data, but if the _id and url id must match
const err = new Error('id of PATCH resource and send JSON body are not equal ' + req.params.id + " " + req.body._id);
const err = new Error('id of PATCH resource and send JSON body are not equal ' + req.params.id + ' ' + req.body._id);
err.status = codes.notfound;
next(err);
return; // prevent node to process this function further after next() has finished.
@ -124,25 +123,22 @@ decoration.route('/:id')
DecorationModel.findByIdAndUpdate(req.params.id, req.body, {new: true}, (err, item) => {
if (err) {
err.status = codes.wrongrequest;
}
else if (!item) {
err = new Error("item not found");
} else if (!item) {
err = new Error('item not found');
err.status = codes.notfound;
}
else {
} else {
res.locals.items = item;
}
next(err);
})
});
})
.delete(apiAuthenticationMiddleware, checkHl, (req, res, next) => {
DecorationModel.findByIdAndRemove(req.params.id, (err, item) => {
if (err) {
err.status = codes.wrongrequest;
}
else if (!item) {
err = new Error("item not found");
} else if (!item) {
err = new Error('item not found');
err.status = codes.notfound;
}

View File

@ -1,21 +1,21 @@
/**
* mini-module providing the HTTP Status codes
* #
* @author Johannes Konert
* @module http-codes
*/
"use strict";
module.exports = {
success: 200,
created: 201,
nocontent: 204,
wrongrequest: 400,
unauthorized: 401,
forbidden: 403,
notfound: 404,
wrongmethod: 405,
conflict: 409,
wrongdatatyperequest: 406,
wrongmediasend: 415,
servererror: 500
};
/**
* mini-module providing the HTTP Status codes
* #
* @author Johannes Konert
* @module http-codes
*/
'use strict';
module.exports = {
success: 200,
created: 201,
nocontent: 204,
wrongrequest: 400,
unauthorized: 401,
forbidden: 403,
notfound: 404,
wrongmethod: 405,
conflict: 409,
wrongdatatyperequest: 406,
wrongmediasend: 415,
servererror: 500,
};

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
// modules
const express = require('express');
@ -26,11 +26,11 @@ function processLogRequest(model, filter, res, next) {
if (!log || log.length === 0) {
const err = new Error('No logs found');
err.status = require('./http-codes').notfound;
return next(err)
return next(err);
}
res.locals.items = log;
next();
})
});
}
// routes **********************
@ -55,10 +55,10 @@ logsRouter.route('/:warId')
kill: killObjects.exec.bind(killObjects),
vehicle: killObjects.exec.bind(vehicleObjects),
transport: transportObjects.exec.bind(transportObjects),
flag: flagObjects.exec.bind(flagObjects)
flag: flagObjects.exec.bind(flagObjects),
};
async.parallel(resources, function (error, results) {
async.parallel(resources, function(error, results) {
if (error) {
res.status(500).send(error);
return;

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
// modules
const async = require('async');
@ -23,18 +23,18 @@ overview.route('/')
let countBlufor = 0;
const armyOverview = {
BLUFOR: {
squads: []
squads: [],
},
OPFOR: {
squads: []
}
squads: [],
},
};
SquadModel.find({}, {'sortingNumber': 0, 'updatedAt': 0, 'timestamp': 0, '__v': 0}, {
sort: {
sortingNumber: 'asc',
name: 'asc'
}
name: 'asc',
},
}, (err, squads) => {
if (err) {
return next(err);
@ -44,7 +44,7 @@ overview.route('/')
'squadId': 0,
'updatedAt': 0,
'timestamp': 0,
'__v': 0
'__v': 0,
}, {sort: {rankLvl: 'desc', name: 'asc'}}, (err, users) => {
const squadMembers = [];
async.eachSeries(users, (user, callback) => {
@ -59,7 +59,7 @@ overview.route('/')
usr.rank = rank.name;
}
delete usr.rankLvl;
squadMembers.push(usr)
squadMembers.push(usr);
callback();
});
@ -88,7 +88,6 @@ overview.route('/')
callback();
});
});
}, (err) => {
if (err) {
return next(err);

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
// modules
const express = require('express');
@ -27,12 +27,12 @@ campaignPlayer.route('/ranking/:campaignId')
const warIds = wars.map((obj) => {
return obj._id;
});
PlayerModel.find({warId: {"$in": warIds}}, (err, items) => {
PlayerModel.find({warId: {'$in': warIds}}, (err, items) => {
if (err) return next(err);
if (!items || items.length === 0) {
const err = new Error('No players for given campaignId');
err.status = codes.notfound;
return next(err)
return next(err);
}
const rankingItems = [];
@ -40,9 +40,9 @@ campaignPlayer.route('/ranking/:campaignId')
// check only first player to have valid steamUUID - then decide if tracked by name or by ID
const usesUUID = isSteamUUID(items[0].steamUUID);
new Set(items.map(usesUUID ? x => x.steamUUID : x => x.name))
.forEach(player => {
const playerInstances = items.filter(usesUUID ? p => p.steamUUID === player : p => p.name === player);
new Set(items.map(usesUUID ? (x) => x.steamUUID : (x) => x.name))
.forEach((player) => {
const playerInstances = items.filter(usesUUID ? (p) => p.steamUUID === player : (p) => p.name === player);
const resItem = {
name: usesUUID ? playerInstances[playerInstances.length - 1].name : player,
kill: 0,
@ -51,7 +51,7 @@ campaignPlayer.route('/ranking/:campaignId')
friendlyFire: 0,
revive: 0,
respawn: 0,
flagTouch: 0
flagTouch: 0,
};
for (let i = 0; i < playerInstances.length; i++) {
resItem.kill += playerInstances[i].kill;
@ -68,7 +68,7 @@ campaignPlayer.route('/ranking/:campaignId')
function getSortedField(fieldName) {
let num = 1;
rankingItems.sort((a, b) => b[fieldName] - a[fieldName])
rankingItems.sort((a, b) => b[fieldName] - a[fieldName]);
const res = JSON.parse(JSON.stringify(rankingItems));
for (const entity of res) {
entity.num = num++;
@ -83,11 +83,11 @@ campaignPlayer.route('/ranking/:campaignId')
vehicle: getSortedField('vehicle'),
revive: getSortedField('revive'),
respawn: getSortedField('respawn'),
flagTouch: getSortedField('flagTouch')
flagTouch: getSortedField('flagTouch'),
};
next();
})
})
});
});
})
.all(
@ -108,7 +108,7 @@ campaignPlayer.route('/single/:campaignId/:playerId')
const playerId = req.params.playerId;
const filter = {};
filter[isSteamUUID(playerId) ? 'steamUUID' : 'name'] = playerId;
filter['warId'] = {"$in": warIds};
filter['warId'] = {'$in': warIds};
PlayerModel.find(filter)
.populate('warId')
@ -117,17 +117,17 @@ campaignPlayer.route('/single/:campaignId/:playerId')
if (!items || items.length === 0) {
const err = new Error('Unknown player id');
err.status = codes.notfound;
return next(err)
return next(err);
}
res.locals.items = {
name: items[items.length - 1].name,
campaign: campaign,
players: items
players: items,
};
next();
})
})
})
});
});
});
})
.all(

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
// modules
const fs = require('fs');
@ -27,10 +27,10 @@ ranks.route('/')
.get((req, res, next) => {
const filter = {};
if (req.query.fractFilter) {
filter.fraction = req.query.fractFilter.toUpperCase()
filter.fraction = req.query.fractFilter.toUpperCase();
}
if (req.query.q) {
filter.name = {$regex: req.query.q, $options: 'i'}
filter.name = {$regex: req.query.q, $options: 'i'};
}
RankModel.find(filter, {}, {sort: {fraction: 'asc', level: 'asc'}}, (err, items) => {
@ -78,9 +78,8 @@ ranks.route('/:id')
if (err) {
err.status = codes.servererror;
return next(err);
}
else if (!item) {
err = new Error("item not found");
} else if (!item) {
err = new Error('item not found');
err.status = codes.notfound;
return next(err);
}
@ -90,10 +89,9 @@ ranks.route('/:id')
})
.patch(apiAuthenticationMiddleware, checkHl, upload.single('image'), (req, res, next) => {
if (!req.body || (req.body._id && req.body._id !== req.params.id)) {
// little bit different as in PUT. :id does not need to be in data, but if the _id and url id must match
const err = new Error('id of PATCH resource and send JSON body are not equal ' + req.params.id + " " + req.body._id);
const err = new Error('id of PATCH resource and send JSON body are not equal ' + req.params.id + ' ' + req.body._id);
err.status = codes.notfound;
next(err);
return; // prevent node to process this function further after next() has finished.
@ -119,32 +117,29 @@ ranks.route('/:id')
RankModel.findByIdAndUpdate(req.params.id, req.body, {new: true}, (err, item) => {
if (err) {
err.status = codes.wrongrequest;
}
else if (!item) {
err = new Error("item not found");
} else if (!item) {
err = new Error('item not found');
err.status = codes.notfound;
}
else {
} else {
res.locals.items = item;
}
next(err);
})
});
})
.delete(apiAuthenticationMiddleware, checkHl, (req, res, next) => {
RankModel.findByIdAndRemove(req.params.id, (err, item) => {
if (err) {
err.status = codes.wrongrequest;
}
else if (!item) {
err = new Error("item not found");
} else if (!item) {
err = new Error('item not found');
err.status = codes.notfound;
}
// we don't set res.locals.items and thus it will send a 204 (no content) at the end. see last handler
// user.use(..)
res.locals.processed = true;
next(err); // this works because err is in normal case undefined and that is the same as no parameter
})
});
})
.all(

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
// modules
const express = require('express');
@ -26,7 +26,7 @@ const resultSet = {
'password': 0,
'permission': 0,
'secret': 0,
'activated': 0
'activated': 0,
};
const request = express.Router();
@ -81,7 +81,7 @@ request.route('/promotion')
}
let promotionFilter = {
userId: {"$in": userIds}
userId: {'$in': userIds},
};
if (progressFilter) {
promotionFilter.confirmed = 0;
@ -101,9 +101,8 @@ request.route('/promotion')
}
res.locals.processed = true;
next();
})
});
});
})
.post(apiAuthenticationMiddleware, checkSql, (req, res, next) => {
@ -132,7 +131,7 @@ request.route('/promotion/:id')
.patch(apiAuthenticationMiddleware, checkHl, (req, res, next) => {
if (!req.body || (req.body._id && req.body._id !== req.params.id)) {
// little bit different as in PUT. :id does not need to be in data, but if the _id and url id must match
const err = new Error('id of PATCH resource and send JSON body are not equal ' + req.params.id + " " + req.body._id);
const err = new Error('id of PATCH resource and send JSON body are not equal ' + req.params.id + ' ' + req.body._id);
err.status = codes.notfound;
next(err);
return; // prevent node to process this function further after next() has finished.
@ -146,23 +145,20 @@ request.route('/promotion/:id')
PromotionModel.findByIdAndUpdate(req.params.id, req.body, {new: true}, (err, item) => {
if (err) {
err.status = codes.wrongrequest;
}
else if (!item) {
err = new Error("item not found");
} else if (!item) {
err = new Error('item not found');
err.status = codes.notfound;
}
else {
} else {
if (item.confirmed === 1) {
let updateUser = {
_id: item.userId,
rankLvl: item.newRankLvl
rankLvl: item.newRankLvl,
};
UserModel.findByIdAndUpdate(updateUser._id, updateUser, {new: true}, (err, item) => {
if (err) {
err.status = codes.wrongrequest;
}
else if (!item) {
err = new Error("user not found");
} else if (!item) {
err = new Error('user not found');
err.status = codes.notfound;
}
});
@ -170,7 +166,7 @@ request.route('/promotion/:id')
res.locals.items = item;
}
next(err);
})
});
})
.all(
routerHandling.httpMethodNotAllowed

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
// modules
const fs = require('fs');
@ -21,7 +21,6 @@ signatures.route('/:id')
// decode UTF8-escape sequences (special characters)
const uri = decodeURIComponent(req.params.id);
UserModel.findOne({username: uri}, (err, user) => {
const emptyFile = 'resource/signature/0.png';
if (user === null) {
res.sendFile(emptyFile, {root: __dirname + '/../'});
@ -34,15 +33,13 @@ signatures.route('/:id')
} else if (err.code === 'ENOENT') {
res.sendFile(emptyFile, {root: __dirname + '/../'});
} else {
err = new Error("Internal server error");
err = new Error('Internal server error');
err.status = codes.servererror;
return next(err);
}
});
}
})
});
})
.all(

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
// modules
const fs = require('fs');
@ -27,10 +27,10 @@ squads.route('/')
.get((req, res, next) => {
const filter = {};
if (req.query.fractFilter) {
filter.fraction = req.query.fractFilter.toUpperCase()
filter.fraction = req.query.fractFilter.toUpperCase();
}
if (req.query.q) {
filter.name = {$regex: req.query.q, $options: 'i'}
filter.name = {$regex: req.query.q, $options: 'i'};
}
SquadModel.find(filter, {}, {sort: {fraction: 'asc', sortingNumber: 'asc'}}, (err, items) => {
if (err) {
@ -63,7 +63,7 @@ squads.route('/')
if (err) next(err);
});
next();
})
});
} else {
const err = new Error('no image file provided');
err.status = codes.wrongmediasend;
@ -81,9 +81,8 @@ squads.route('/:id')
if (err) {
err.status = codes.servererror;
return next(err);
}
else if (!item) {
err = new Error("item not found");
} else if (!item) {
err = new Error('item not found');
err.status = codes.notfound;
return next(err);
}
@ -93,10 +92,9 @@ squads.route('/:id')
})
.patch(apiAuthenticationMiddleware, checkHl, upload.single('image'), (req, res, next) => {
if (!req.body || (req.body._id && req.body._id !== req.params.id)) {
// little bit different as in PUT. :id does not need to be in data, but if the _id and url id must match
const err = new Error('id of PATCH resource and send JSON body are not equal ' + req.params.id + " " + req.body._id);
const err = new Error('id of PATCH resource and send JSON body are not equal ' + req.params.id + ' ' + req.body._id);
err.status = codes.notfound;
next(err);
return; // prevent node to process this function further after next() has finished.
@ -121,25 +119,22 @@ squads.route('/:id')
SquadModel.findByIdAndUpdate(req.params.id, req.body, {new: true}, (err, item) => {
if (err) {
err.status = codes.wrongrequest;
}
else if (!item) {
err = new Error("item not found");
} else if (!item) {
err = new Error('item not found');
err.status = codes.notfound;
}
else {
} else {
res.locals.items = item;
}
next(err);
})
});
})
.delete(apiAuthenticationMiddleware, checkHl, (req, res, next) => {
SquadModel.findByIdAndRemove(req.params.id, (err, item) => {
if (err) {
err.status = codes.wrongrequest;
}
else if (!item) {
err = new Error("item not found");
} else if (!item) {
err = new Error('item not found');
err.status = codes.notfound;
}

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
// modules
const express = require('express');
@ -32,7 +32,7 @@ users.route('/')
const userQuery = () => {
UserModel.find(dbFilter, res.locals.filter, res.locals.limitskip)
.populate('squadId')
.collation({locale: "en", strength: 2}) // case insensitive order
.collation({locale: 'en', strength: 2}) // case insensitive order
.sort('username').exec((err, users) => {
if (err) return next(err);
if (users.length === 0) {
@ -45,19 +45,19 @@ users.route('/')
res.locals.items = users;
res.locals.processed = true;
return next();
})
})
});
});
};
if (!req.query.q) req.query.q = '';
const dbFilter = {username: {"$regex": req.query.q, "$options": "i"}};
if (req.query.squadId) dbFilter["squadId"] = {"$eq": req.query.squadId};
const dbFilter = {username: {'$regex': req.query.q, '$options': 'i'}};
if (req.query.squadId) dbFilter['squadId'] = {'$eq': req.query.squadId};
// squad / fraction filter setup
if (req.query.fractFilter && req.query.fractFilter !== 'UNASSIGNED' && !req.query.squadId) {
SquadModel.find({'fraction': req.query.fractFilter}, {_id: 1}, (err, squads) => {
dbFilter['squadId'] = {$in: squads.map(squad => squad.id)};
dbFilter['squadId'] = {$in: squads.map((squad) => squad.id)};
userQuery();
})
});
} else {
if (req.query.fractFilter === 'UNASSIGNED') {
dbFilter['squadId'] = {$eq: null};
@ -80,7 +80,7 @@ users.route('/')
res.locals.items = extUser;
res.locals.processed = true;
return next();
})
});
});
})
@ -93,9 +93,8 @@ users.route('/:id')
if (err) {
err.status = codes.servererror;
return next(err);
}
else if (!user) {
err = new Error("item not found");
} else if (!user) {
err = new Error('item not found');
err.status = codes.notfound;
return next(err);
}
@ -108,7 +107,7 @@ users.route('/:id')
.patch(apiAuthenticationMiddleware, checkHl, (req, res, next) => {
if (!req.body || (req.body._id && req.body._id !== req.params.id)) {
// little bit different as in PUT. :id does not need to be in data, but if the _id and url id must match
const err = new Error('id of PATCH resource and send JSON body are not equal ' + req.params.id + " " + req.body._id);
const err = new Error('id of PATCH resource and send JSON body are not equal ' + req.params.id + ' ' + req.body._id);
err.status = codes.notfound;
next(err);
return; // prevent node to process this function further after next() has finished.
@ -123,9 +122,8 @@ users.route('/:id')
UserModel.findByIdAndUpdate(req.params.id, req.body, {new: true}, (err, item) => {
if (err) {
err.status = codes.wrongrequest;
}
else if (!item) {
err = new Error("item not found");
} else if (!item) {
err = new Error('item not found');
err.status = codes.notfound;
}
UserModel.populate(item, {path: 'squadId'}, (err, extUser) => {
@ -141,41 +139,40 @@ users.route('/:id')
res.locals.items = extUser;
res.locals.processed = true;
return next();
})
})
});
});
})
.put(apiAuthenticationMiddleware, checkHl, (req, res, next) => {
// first check that the given element id is the same as the URL id
if (!req.body || req.body._id !== req.params.id) {
// the URL does not fit the given element
var err = new Error('id of PATCH resource and send JSON body are not equal ' + req.params.id + " " + req.body._id);
let err = new Error('id of PATCH resource and send JSON body are not equal ' + req.params.id + ' ' + req.body._id);
err.status = codes.notfound;
next(err);
return; // prevent node to process this function further after next() has finished.
}
// main difference of PUT and PATCH is that PUT expects all data in request: checked by using the schema
const user = new UserModel(req.body);
UserModel.findById(req.params.id, req.body, {new: true}, function (err, item) {
UserModel.findById(req.params.id, req.body, {new: true}, function(err, item) {
// with parameter {new: true} the TweetNModel will return the new and changed object from the DB and not the
// old one.
if (err) {
err.status = codes.wrongrequest;
return next(err);
}
else if (!item) {
err = new Error("item not found");
} else if (!item) {
err = new Error('item not found');
err.status = codes.notfound;
return next(err);
}
// check that version is still accurate
else if (user.__v !== item.__v) {
err = new Error("version outdated. Meanwhile update on item happened. Please GET resource again")
err = new Error('version outdated. Meanwhile update on item happened. Please GET resource again');
err.status = codes.conflict;
return next(err);
}
// now update all fields in DB item with body data in variable video
for (var field in UserModel.schema.paths) {
for (let field in UserModel.schema.paths) {
if ((field !== '_id') && (field !== '__v')) {
// this includes undefined. is important to reset attributes that are missing in req.body
item.set(field, user[field]);
@ -185,7 +182,7 @@ users.route('/:id')
// update updatedAt and increase version
item.updatedAt = new Date();
item.increment(); // this sets __v++
item.save(function (err) {
item.save(function(err) {
if (!err) {
res.locals.items = item;
} else {
@ -197,18 +194,17 @@ users.route('/:id')
res.locals.items = extUser;
res.locals.processed = true;
return next();
})
});
});
})
});
})
.delete(apiAuthenticationMiddleware, checkHl, (req, res, next) => {
UserModel.findByIdAndRemove(req.params.id, (err, item) => {
if (err) {
err.status = codes.wrongrequest;
}
else if (!item) {
err = new Error("item not found");
} else if (!item) {
err = new Error('item not found');
err.status = codes.notfound;
}

View File

@ -1,8 +1,8 @@
"use strict";
'use strict';
// modules
const fs = require('fs');
const mkdirp = require("mkdirp");
const mkdirp = require('mkdirp');
const express = require('express');
const multer = require('multer');
const storage = multer.memoryStorage();
@ -53,7 +53,7 @@ wars.route('/')
return next(err);
}
if (wars) {
campaigns.forEach(campaign => {
campaigns.forEach((campaign) => {
let entry = {_id: campaign._id, title: campaign.title, wars: []};
wars.forEach((war) => {
if (String(campaign._id) === String(war.campaign)) {
@ -70,7 +70,7 @@ wars.route('/')
)
;
}
})
});
})
.post(apiAuthenticationMiddleware, checkMT, upload.single('log'), (req, res, next) => {
@ -82,59 +82,57 @@ wars.route('/')
if (err) {
return next(err);
}
const lineArray = file.toString().split("\n");
const lineArray = file.toString().split('\n');
const statsResult = parseWarLog(lineArray, warBody);
statsResult.war.save((err, war) => {
if (err) {
return next(err);
}
PlayerModel.create(statsResult.players, function (err) {
PlayerModel.create(statsResult.players, function(err) {
if (err) {
return next(err);
}
LogKillModel.create(statsResult.kills, function () {
LogVehicleKillModel.create(statsResult.vehicles, function () {
LogRespawnModel.create(statsResult.respawn, function () {
LogReviveModel.create(statsResult.revive, function () {
LogFlagModel.create(statsResult.flag, function () {
LogBudgetModel.create(statsResult.budget, function () {
LogTransportModel.create(statsResult.transport, function () {
LogPointsModel.create(statsResult.points, function () {
LogKillModel.create(statsResult.kills, function() {
LogVehicleKillModel.create(statsResult.vehicles, function() {
LogRespawnModel.create(statsResult.respawn, function() {
LogReviveModel.create(statsResult.revive, function() {
LogFlagModel.create(statsResult.flag, function() {
LogBudgetModel.create(statsResult.budget, function() {
LogTransportModel.create(statsResult.transport, function() {
LogPointsModel.create(statsResult.points, function() {
const folderName = __dirname + '/../resource/logs/' + war._id;
mkdirp(folderName, function (err) {
mkdirp(folderName, function(err) {
if (err) return next(err);
// save clean log file
const cleanFile = fs.createWriteStream(folderName + '/clean.log');
statsResult.clean.forEach(cleanLine => {
cleanFile.write(cleanLine + '\n\n')
statsResult.clean.forEach((cleanLine) => {
cleanFile.write(cleanLine + '\n\n');
});
cleanFile.end();
// save raw log file
const rawFile = fs.createWriteStream(folderName + '/war.log');
lineArray.forEach(rawLine => {
rawFile.write(rawLine + '\n')
lineArray.forEach((rawLine) => {
rawFile.write(rawLine + '\n');
});
rawFile.end();
res.status(codes.created);
res.locals.items = war;
next();
})
})
})
})
})
})
})
})
})
})
})
});
});
});
});
});
});
});
});
});
});
});
});
} else {
const err = new Error('no Logfile provided');
err.status = codes.wrongmediasend;
@ -152,9 +150,8 @@ wars.route('/:id')
if (err) {
err.status = codes.servererror;
return next(err);
}
else if (!item) {
err = new Error("item not found");
} else if (!item) {
err = new Error('item not found');
err.status = codes.notfound;
return next(err);
}
@ -168,7 +165,6 @@ wars.route('/:id')
res.locals.items = responseObj;
return next();
});
});
})
@ -177,9 +173,8 @@ wars.route('/:id')
if (err) {
err.status = codes.wrongrequest;
return next(err);
}
else if (!item) {
err = new Error("item not found");
} else if (!item) {
err = new Error('item not found');
err.status = codes.notfound;
return next(err);
}
@ -215,8 +210,7 @@ wars.route('/:id')
// user.use(..)
res.locals.processed = true;
next();
})
});
})
.all(

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
const express = require('express');
const path = require('path');
@ -11,7 +11,7 @@ const error = debug('cc:server:err');
const logger = debug('cc:server');
logger.log = console.log.bind(console);
const cors = require('cors')
const cors = require('cors');
const mongoose = require('mongoose');
// own modules
@ -54,7 +54,7 @@ const app = express();
// setup CORS-middleware
const corsOptions = {
methods: ['GET'],
optionsSuccessStatus: 200
optionsSuccessStatus: 200,
};
app.use(cors(corsOptions));
@ -94,8 +94,8 @@ app.use(urls.command, apiAuthenticationMiddleware, checkAdmin, commandRouter);
app.use(urls.account, apiAuthenticationMiddleware, checkAdmin, accountRouter);
// send index.html on all different paths
app.use(function (req, res) {
res.sendFile("public/index.html", {root: __dirname + '/..'});
app.use(function(req, res) {
res.sendFile('public/index.html', {root: __dirname + '/..'});
});
// register error handlers
@ -108,20 +108,19 @@ if (process.env.NODE_ENV !== config.test.env) {
app.listen(config.port, (err) => {
if (err !== undefined) {
error('Error on startup, ', err);
}
else {
} else {
logger('Listening on port ' + config.port);
signatureCronJob.start();
backupCronJob.start();
}
});
})
});
} else {
const mongoosePromise = mongoose.connect(config.database.uri + config.test.db);
mongoosePromise.then((db) => {
app.listen(config.test.port);
logger('Listening on port ' + config.test.port);
})
});
}
module.exports = app;

View File

@ -1,19 +1,19 @@
let mongoose = require("mongoose");
let mongoose = require('mongoose');
let AwardingModel = require('../models/awarding');
let urls = require('../config/api-url');
let codes = require('../routes/http-codes');
//Require the dev-dependencies
// Require the dev-dependencies
let chai = require('chai');
let chaiHttp = require('chai-http');
let server = require('../server');
let should = chai.should();
chai.use(chaiHttp);
//Our parent block
// Our parent block
describe('Awardings', () => {
beforeEach((done) => { //Before each test we empty the database
beforeEach((done) => { // Before each test we empty the database
AwardingModel.remove({}, (err) => {
done();
});
@ -38,7 +38,6 @@ describe('Awardings', () => {
* Test the /POST awardings
*/
describe('/POST awardings', () => {
it('it should not POST an awarding without auth-token provided', (done) => {
chai.request(server)
.post(urls.awards)
@ -57,7 +56,6 @@ describe('Awardings', () => {
* Test the /PATCH awardings
*/
describe('/PATCH awardings', () => {
it('it should not PATCH an awarding without auth-token provided', (done) => {
chai.request(server)
.patch(urls.awards + '/someId')
@ -70,7 +68,6 @@ describe('Awardings', () => {
done();
});
});
});
@ -78,7 +75,6 @@ describe('Awardings', () => {
* Test the /DELETE awardings
*/
describe('/DELETE awardings', () => {
it('it should not accept DELETE method without id in url', (done) => {
chai.request(server)
.delete(urls.awards)
@ -104,7 +100,5 @@ describe('Awardings', () => {
done();
});
});
});
});

View File

@ -1,19 +1,19 @@
let mongoose = require("mongoose");
let mongoose = require('mongoose');
let AwardingModel = require('../models/awarding');
let urls = require('../config/api-url');
let codes = require('../routes/http-codes');
//Require the dev-dependencies
// Require the dev-dependencies
let chai = require('chai');
let chaiHttp = require('chai-http');
let server = require('../server');
let should = chai.should();
chai.use(chaiHttp);
//Our parent block
// Our parent block
describe('Command', () => {
beforeEach((done) => { //Before each test we empty the database
beforeEach((done) => { // Before each test we empty the database
AwardingModel.remove({}, (err) => {
done();
});
@ -24,7 +24,7 @@ describe('Command', () => {
describe('/POST command to create signature', () => {
it('it should not succeed without auth-token provided', (done) => {
chai.request(server)
.post(urls.cmdCreateSig + "/someId")
.post(urls.cmdCreateSig + '/someId')
.send({})
.end((err, res) => {
res.should.have.status(codes.forbidden);
@ -35,5 +35,4 @@ describe('Command', () => {
});
});
});
});

View File

@ -20,10 +20,11 @@ mongoose.connection.on('connected', () => {
});
const createString = (possible, length) => {
let text = "";
let text = '';
for (let i = 0; i < length; i++)
text += possible.charAt(Math.floor(Math.random() * possible.length));
for (let i = 0; i < length; i++) {
text += possible.charAt(Math.floor(Math.random() * possible.length));
}
return text;
};
@ -34,21 +35,19 @@ for (let i = 0; i < quantity; i++) {
UserModel.create({
username: createString('abcdefghijklmnopqrstuvwxyz0123456789', 10),
squadId: squadId,
rankLvl: Math.floor(Math.random() * 22)
}, function (err, user) {
rankLvl: Math.floor(Math.random() * 22),
}, function(err, user) {
if (err) {
console.log(err);
} else {
console.log('User created: ' + user);
}
})
});
}
// If the Node process ends, close the Mongoose connection
process.on('SIGINT', () => {
mongoose.connection.close(function () {
mongoose.connection.close(function() {
console.log('Mongoose default connection disconnected through app termination');
process.exit(0);
});

View File

@ -1,19 +1,19 @@
let mongoose = require("mongoose");
let mongoose = require('mongoose');
let DecorationModel = require('../models/decoration');
let urls = require('../config/api-url');
let codes = require('../routes/http-codes');
//Require the dev-dependencies
// Require the dev-dependencies
let chai = require('chai');
let chaiHttp = require('chai-http');
let server = require('../server');
let should = chai.should();
chai.use(chaiHttp);
//Our parent block
// Our parent block
describe('Decorations', () => {
beforeEach((done) => { //Before each test we empty the database
beforeEach((done) => { // Before each test we empty the database
DecorationModel.remove({}, (err) => {
done();
});
@ -38,7 +38,6 @@ describe('Decorations', () => {
* Test the /POST decorations
*/
describe('/POST decorations', () => {
it('it should not POST a decoration without auth-token provided', (done) => {
chai.request(server)
.post(urls.decorations)
@ -57,7 +56,6 @@ describe('Decorations', () => {
* Test the /PATCH decoration
*/
describe('/PATCH decorations', () => {
it('it should not PATCH a decoration without auth-token provided', (done) => {
chai.request(server)
.patch(urls.decorations + '/someId')
@ -70,7 +68,6 @@ describe('Decorations', () => {
done();
});
});
});
@ -103,7 +100,5 @@ describe('Decorations', () => {
done();
});
});
});
});

View File

@ -1,19 +1,19 @@
let mongoose = require("mongoose");
let mongoose = require('mongoose');
let RankModel = require('../models/rank');
let urls = require('../config/api-url');
let codes = require('../routes/http-codes');
//Require the dev-dependencies
// Require the dev-dependencies
let chai = require('chai');
let chaiHttp = require('chai-http');
let server = require('../server');
let should = chai.should();
chai.use(chaiHttp);
//Our parent block
// Our parent block
describe('Ranks', () => {
beforeEach((done) => { //Before each test we empty the database
beforeEach((done) => { // Before each test we empty the database
RankModel.remove({}, (err) => {
done();
});
@ -38,7 +38,6 @@ describe('Ranks', () => {
* Test the /POST ranks
*/
describe('/POST ranks', () => {
it('it should not POST a rank without auth-token provided', (done) => {
chai.request(server)
.post(urls.ranks)
@ -51,13 +50,12 @@ describe('Ranks', () => {
done();
});
});
})
});
/*
* Test the /PATCH rank
*/
describe('/PATCH ranks', () => {
it('it should not PATCH a rank without auth-token provided', (done) => {
chai.request(server)
.patch(urls.ranks + '/someId')
@ -70,7 +68,6 @@ describe('Ranks', () => {
done();
});
});
});
@ -104,7 +101,5 @@ describe('Ranks', () => {
done();
});
});
});
});

View File

@ -1,19 +1,19 @@
let mongoose = require("mongoose");
let mongoose = require('mongoose');
let SquadModel = require('../models/squad');
let urls = require('../config/api-url');
let codes = require('../routes/http-codes');
//Require the dev-dependencies
// Require the dev-dependencies
let chai = require('chai');
let chaiHttp = require('chai-http');
let server = require('../server');
let should = chai.should();
chai.use(chaiHttp);
//Our parent block
// Our parent block
describe('Squads', () => {
beforeEach((done) => { //Before each test we empty the database
beforeEach((done) => { // Before each test we empty the database
SquadModel.remove({}, (err) => {
done();
});
@ -38,7 +38,6 @@ describe('Squads', () => {
* Test the /POST squad
*/
describe('/POST squads', () => {
it('it should not POST a squad without auth-token provided', (done) => {
chai.request(server)
.post(urls.squads)
@ -57,7 +56,6 @@ describe('Squads', () => {
* Test the /PATCH squad
*/
describe('/PATCH squads', () => {
it('it should not PATCH a squad without auth-token provided', (done) => {
chai.request(server)
.patch(urls.squads + '/someId')
@ -70,7 +68,6 @@ describe('Squads', () => {
done();
});
});
});
@ -103,7 +100,5 @@ describe('Squads', () => {
done();
});
});
});
});

View File

@ -1,20 +1,20 @@
let mongoose = require("mongoose");
let mongoose = require('mongoose');
let UserModel = require('../models/user');
let AppUserModel = require('../models/app-user');
let urls = require('../config/api-url');
let codes = require('../routes/http-codes');
//Require the dev-dependencies
// Require the dev-dependencies
let chai = require('chai');
let chaiHttp = require('chai-http');
let server = require('../server');
let should = chai.should();
chai.use(chaiHttp);
//Our parent block
// Our parent block
describe('Users', () => {
beforeEach((done) => { //Before each test we empty the database
beforeEach((done) => { // Before each test we empty the database
UserModel.remove({}, (err) => {
done();
});
@ -39,7 +39,6 @@ describe('Users', () => {
* Test the /POST route
*/
describe('/POST users', () => {
// let token;
//
// before(function (done) {
@ -106,7 +105,6 @@ describe('Users', () => {
* Test the /PATCH route
*/
describe('/PATCH users', () => {
it('it should not PATCH a user without auth-token provided', (done) => {
chai.request(server)
.patch(urls.users + '/someId')
@ -119,7 +117,6 @@ describe('Users', () => {
done();
});
});
});
@ -152,7 +149,5 @@ describe('Users', () => {
done();
});
});
});
});

View File

@ -1,19 +1,18 @@
let mongoose = require("mongoose");
let mongoose = require('mongoose');
let AwardingModel = require('../models/awarding');
let urls = require('../config/api-url');
let codes = require('../routes/http-codes');
//Require the dev-dependencies
// Require the dev-dependencies
let chai = require('chai');
let chaiHttp = require('chai-http');
let server = require('../server');
let should = chai.should();
chai.use(chaiHttp);
//Our parent block
// Our parent block
describe('Wars', () => {
/*
* Test the /GET awardings
*/
@ -34,7 +33,6 @@ describe('Wars', () => {
* Test the /POST awardings
*/
describe('/POST wars', () => {
it('it should not POST a war without auth-token provided', (done) => {
chai.request(server)
.post(urls.wars)
@ -53,7 +51,6 @@ describe('Wars', () => {
* Test the /DELETE awardings
*/
describe('/DELETE wars', () => {
it('it should not accept DELETE method without id in url', (done) => {
chai.request(server)
.delete(urls.wars)
@ -79,7 +76,5 @@ describe('Wars', () => {
done();
});
});
});
});

View File

@ -5,7 +5,6 @@ const playerArrayContains = require('./util').playerArrayContains;
const WHITESPACE = ' ';
const parseWarLog = (lineArray, war) => {
const NAME_TOO_LONG_ERROR = 'Error: ENAMETOOLONG: name too long, open \'';
const stats = {
@ -19,7 +18,7 @@ const parseWarLog = (lineArray, war) => {
revive: [],
flag: [],
transport: [],
players: []
players: [],
};
const vehicleBlacklist = [
@ -29,7 +28,7 @@ const parseWarLog = (lineArray, war) => {
'Qilin (Unbewaffnet)', 'Qilin (Bewaffnet)', 'Ifrit',
'Tempest-Transporter', 'Tempest-Transporter (abgedeckt)', 'Tempest SanitÀtsfahrzeug',
'Remote Designator [CSAT]', 'UBF Saif',
'Quad Bike', 'HuntIR'
'Quad Bike', 'HuntIR',
];
const addPlayerIfNotExists = (inputPlayer, steamUUID) => {
@ -41,7 +40,7 @@ const parseWarLog = (lineArray, war) => {
}
};
lineArray.some(line => {
lineArray.some((line) => {
/**
* sanitize nameTooLongError coming up in first line
*/
@ -67,8 +66,8 @@ const parseWarLog = (lineArray, war) => {
time: getFullTimeDate(war.date, line.split(WHITESPACE)[5]),
shooter: shooter ? shooter.name : null,
target: target ? target.name : null,
fraction: shooter ? shooter.fraction : 'NONE'
})
fraction: shooter ? shooter.fraction : 'NONE',
});
}
} else {
const targetString = line.substring(line.lastIndexOf(' --- ') + 5, line.lastIndexOf(' von:'));
@ -79,7 +78,7 @@ const parseWarLog = (lineArray, war) => {
shooter: shooter ? shooter.name : null,
target: target ? target.name : null,
friendlyFire: shooter ? target.fraction === shooter.fraction : false,
fraction: shooter ? shooter.fraction : 'NONE'
fraction: shooter ? shooter.fraction : 'NONE',
});
}
}
@ -95,9 +94,8 @@ const parseWarLog = (lineArray, war) => {
stats.war['budgetOpfor'] = transformMoneyString(budg[12].slice(0, -1));
// this date needs to be assigned in first place !important
const dateString = budg[0].slice(0, -1).split('/').map(s => parseInt(s));
const dateString = budg[0].slice(0, -1).split('/').map((s) => parseInt(s));
stats.war.date = new Date(dateString[0], dateString[1] - 1, dateString[2]);
} else if (line.includes('Endbudget')) {
stats.war['endBudgetBlufor'] = transformMoneyString(budg[9].substr(1));
stats.war['endBudgetOpfor'] = transformMoneyString(budg[12].slice(0, -1));
@ -121,7 +119,7 @@ const parseWarLog = (lineArray, war) => {
time: getFullTimeDate(war.date, line.split(WHITESPACE)[5]),
player: playerName,
flagFraction: flagFraction,
capture: capture
capture: capture,
});
}
@ -138,7 +136,7 @@ const parseWarLog = (lineArray, war) => {
// EXIT LOOP
return true;
} else {
stats.points.push(getPointsEntry(pt, line, war._id, war.date))
stats.points.push(getPointsEntry(pt, line, war._id, war.date));
}
}
@ -169,7 +167,7 @@ const parseWarLog = (lineArray, war) => {
stabilized: stabilized,
medic: medic.name,
patient: patient.name,
fraction: medic.fraction
fraction: medic.fraction,
});
}
@ -190,7 +188,7 @@ const parseWarLog = (lineArray, war) => {
driver: driver ? driver.name : null,
passenger: passenger ? passenger.name : null,
fraction: driver ? driver.fraction : 'NONE',
distance: distance
distance: distance,
});
}
@ -200,25 +198,25 @@ const parseWarLog = (lineArray, war) => {
else if (line.includes('(Fraktionsuebersicht)')) {
const playerString = line.substring(line.lastIndexOf('--- ') + 4, line.lastIndexOf(', PUID'));
const playerUUID = line.substring(line.lastIndexOf('PUID ') + 5, line.lastIndexOf('"'));
addPlayerIfNotExists(playerString, playerUUID)
addPlayerIfNotExists(playerString, playerUUID);
}
});
for (let i = 0; i < stats.players.length; i++) {
const playerName = stats.players[i].name;
stats.players[i]['respawn'] = stats.respawn.filter(res => res.player === playerName).length;
stats.players[i]['kill'] = stats.kills.filter(kill => kill.shooter === playerName && !kill.friendlyFire).length;
stats.players[i]['vehicle'] = stats.vehicles.filter(vehicle => vehicle.shooter === playerName && vehicleBlacklist.indexOf(vehicle.target) < 0).length;
stats.players[i]['friendlyFire'] = stats.kills.filter(kill => kill.shooter === playerName && kill.friendlyFire).length;
stats.players[i]['death'] = stats.kills.filter(kill => kill.target === playerName).length;
stats.players[i]['revive'] = stats.revive.filter(rev => rev.medic === playerName && !rev.stabilized).length;
stats.players[i]['flagTouch'] = stats.flag.filter(flag => flag.player === playerName).length;
stats.players[i]['respawn'] = stats.respawn.filter((res) => res.player === playerName).length;
stats.players[i]['kill'] = stats.kills.filter((kill) => kill.shooter === playerName && !kill.friendlyFire).length;
stats.players[i]['vehicle'] = stats.vehicles.filter((vehicle) => vehicle.shooter === playerName && vehicleBlacklist.indexOf(vehicle.target) < 0).length;
stats.players[i]['friendlyFire'] = stats.kills.filter((kill) => kill.shooter === playerName && kill.friendlyFire).length;
stats.players[i]['death'] = stats.kills.filter((kill) => kill.target === playerName).length;
stats.players[i]['revive'] = stats.revive.filter((rev) => rev.medic === playerName && !rev.stabilized).length;
stats.players[i]['flagTouch'] = stats.flag.filter((flag) => flag.player === playerName).length;
stats.players[i]['sort'] = stats.players[i]['kill'] + stats.players[i]['revive'] + stats.players[i]['flagTouch']
- stats.players[i]['friendlyFire'] - stats.players[i]['death'] - stats.players[i]['respawn']
- stats.players[i]['friendlyFire'] - stats.players[i]['death'] - stats.players[i]['respawn'];
}
stats.war.playersBlufor = stats.players.filter(player => player.fraction === 'BLUFOR').length;
stats.war.playersOpfor = stats.players.filter(player => player.fraction === 'OPFOR').length;
stats.war.playersBlufor = stats.players.filter((player) => player.fraction === 'BLUFOR').length;
stats.war.playersOpfor = stats.players.filter((player) => player.fraction === 'OPFOR').length;
return stats;
};
@ -227,8 +225,8 @@ const getRespawnEntry = (respawn, playerName, warId, warDate) => {
return {
war: warId,
time: getFullTimeDate(warDate, respawn[5]),
player: playerName
}
player: playerName,
};
};
const getPointsEntry = (pt, line, warId, warDate) => {
@ -237,8 +235,8 @@ const getPointsEntry = (pt, line, warId, warDate) => {
time: getFullTimeDate(warDate, pt[5]),
ptBlufor: parseInt(pt[10]),
ptOpfor: parseInt(pt[13].slice(0, -3)),
fraction: line.includes('Kein Dominator') ? 'NONE' : line.includes('NATO +1') ? 'BLUFOR' : 'OPFOR'
}
fraction: line.includes('Kein Dominator') ? 'NONE' : line.includes('NATO +1') ? 'BLUFOR' : 'OPFOR',
};
};
const getBudgetEntry = (budg, warId, warDate) => {
@ -247,8 +245,8 @@ const getBudgetEntry = (budg, warId, warDate) => {
time: getFullTimeDate(warDate, budg[5]),
fraction: budg[7] === 'NATO' ? 'BLUFOR' : 'OPFOR',
oldBudget: transformMoneyString(budg[9]),
newBudget: transformMoneyString(budg[12])
}
newBudget: transformMoneyString(budg[12]),
};
};
const getPlayerAndFractionFromString = (nameAndFractionString) => {

View File

@ -1,4 +1,4 @@
"use strict";
'use strict';
// modules used for graphic manipulation
const jimp = require('jimp');
@ -21,7 +21,6 @@ const resourceDir = __dirname + '/../resource/';
let createSignature = (userId, res, next) => {
let loadedImage;
let user;
@ -46,7 +45,7 @@ let createSignature = (userId, res, next) => {
if (!platePath) {
throw new Error('Fraction not defined for user with id ' + userId);
}
return jimp.read(platePath)
return jimp.read(platePath);
})
.then((image) => {
loadedImage = image;
@ -54,7 +53,7 @@ let createSignature = (userId, res, next) => {
return jimp.loadFont(__dirname + '/font/DEVAJU_SANS_19.fnt');
})
.then((font) => {
loadedImage.print(font, 128, 8, user.username)
loadedImage.print(font, 128, 8, user.username);
})
.then(() => {
return jimp.loadFont(__dirname + '/font/DEJAVU_SANS_13.fnt');
@ -68,7 +67,7 @@ let createSignature = (userId, res, next) => {
RankModel.findOne({'level': user.rankLvl, 'fraction': user.squadId.fraction}, (err, result) => {
if (err) {
return next(err)
return next(err);
}
if (result) {
@ -89,21 +88,21 @@ let createSignature = (userId, res, next) => {
rankImage.resize(rankW, rankH);
loadedImage
.print(font, 128, 55, result.name)
.composite(rankImage, rankX, rankY)
.composite(rankImage, rankX, rankY);
})
.then(() => {
addDecorationsAndSave(userId, loadedImage, res, next);
})
});
} else {
// user has not any assignable rank in his fraction at this point,
// e.g. assigned rank has been deleted or switched fraction so rankLvl is not defined
addDecorationsAndSave(userId, loadedImage, res, next);
}
})
});
})
.catch((err) => {
next(err);
})
});
};
@ -128,15 +127,14 @@ let addDecorationsAndSave = (userId, loadedImage, res, next) => {
AwardingModel.find({
'userId': userId,
'confirmed': 1
'confirmed': 1,
}, ['decorationId', 'date']).populate('decorationId', ['isMedal', 'fraction'])
.exec((err, awardings) => {
if (err) {
return next(err);
}
if (awardings.length > 0) {
//TODO: simplify this sorting hell
// TODO: simplify this sorting hell
awardings.sort((a1, a2) => {
if (!a1.decorationId.isMedal && !a2.decorationId.isMedal) {
if (a1.decorationId.fraction === a2.decorationId.fraction) {
@ -203,7 +201,7 @@ let addDecorationsAndSave = (userId, loadedImage, res, next) => {
}
}
callback();
})
});
}, (err) => {
if (err) {
throw err;
@ -214,18 +212,17 @@ let addDecorationsAndSave = (userId, loadedImage, res, next) => {
compareImagesAndSave(loadedImage, userId, res, next);
}
}
)
);
};
let compareImagesAndSave = (generatedImage, userId, res, next) => {
return jimp.read(resourceDir + 'signature/big/' + userId + fileExt)
.then((oldImage) => {
// compare hashes of image map to recognize difference
const sig1 = SHA1(generatedImage.bitmap.data);
const sig2 = SHA1(oldImage.bitmap.data);
if (sig1 !== sig2) {
saveJimpImageAndCompress(generatedImage, userId, res, next)
saveJimpImageAndCompress(generatedImage, userId, res, next);
} else {
res.locals.items = {status: 'nothing to do'};
next();
@ -233,8 +230,7 @@ let compareImagesAndSave = (generatedImage, userId, res, next) => {
})
.catch((err) => {
saveJimpImageAndCompress(generatedImage, userId, res, next);
})
});
};
/**
@ -252,14 +248,14 @@ let saveJimpImageAndCompress = (image, userId, res, next) => {
setTimeout(() => {
imagemin([resourceDir + 'signature/big/' + userId + fileExt], resourceDir + 'signature/', {
plugins: [
imageminpngquant({quality: '65-80'})
]
imageminpngquant({quality: '65-80'}),
],
}).then((files) => {
res.locals.items = {status: 'success'};
return next();
}).catch((error) => {
console.log(error)
})
console.log(error);
});
}, 3000);
};

View File

@ -1,8 +1,8 @@
"use strict";
'use strict';
const isSteamUUID = (input) => {
const steamUIDPattern = new RegExp("[0-9]{17}");
return steamUIDPattern.test(input)
const steamUIDPattern = new RegExp('[0-9]{17}');
return steamUIDPattern.test(input);
};
const sortCollectionBy = (collection, key) => {
@ -17,7 +17,9 @@ const sortCollectionBy = (collection, key) => {
};
const playerArrayContains = (arr, item) => {
let i = 0, count = arr.length, matchFound = false;
let i = 0;
let count = arr.length;
let matchFound = false;
for (; i < count; i++) {
if (arr[i].name === item.name && arr[i].fraction === item.fraction) {
@ -39,9 +41,9 @@ const timeStringToDecimal = (timeString) => {
const decimalToTimeString = (decimal) => {
const hours = parseInt(decimal.toString().split(".")[0]);
const hours = parseInt(decimal.toString().split('.')[0]);
const minutesFloat = ((decimal % 1) * 3600) / 60;
const minutes = parseInt(minutesFloat.toString().split(".")[0]);
const minutes = parseInt(minutesFloat.toString().split('.')[0]);
const seconds = Math.round((minutesFloat - parseInt(minutes)) * 60);
return (hours < 10 ? '0' + hours : hours) + ':' +