added unit testing, and started implementing unit tests...phew

This commit is contained in:
Josh Burman
2019-03-12 22:28:02 -04:00
parent 74aad4a957
commit e8c2539f1b
3489 changed files with 464813 additions and 88 deletions

View File

@ -3,6 +3,8 @@ import ClientBase from './clients/clientBase';
import MHSClient from './clients/sites/mhsClient';
import MHSChannel from './channels/sites/mhsChannel';
var logger = require('./logger');
class ChannelManager {
channels: ChannelBase[]|MHSChannel[] = [];
@ -13,15 +15,19 @@ class ChannelManager {
}
createChannel(data: any) {
var channel: ChannelBase|MHSChannel|null = this.channelExists(data.channel);
var channelExists: ChannelBase|MHSChannel|null = this.channelExists(data.channel);
var channel: ChannelBase|MHSChannel;
if (channel) {
console.log('channel already exists');
if (channelExists) {
channel = channelExists;
logger.accessLog.info(`Channel already exists: ${channel.id}`);
} else {
channel = this.getChannelType(data);
channel ? this.channels.push(channel) : null;
console.log('added channel to channel manager');
channel = this.createByChannelType(data);
this.channels.push(channel);
logger.accessLog.info(`Added channel to channel manager: ${channel.id}`);
}
return channel;
}
channelExists(channel_id: string) {
@ -40,19 +46,21 @@ class ChannelManager {
if (channel) {
channel.addClient(client);
client.connectToChannel(channel);
return {'status': 'success'};
} else {
console.log(`channel with id ${channel_id} does not exist.`)
logger.accessLog.info(`channel with id ${channel_id} does not exist.`);
return {'status': 'notice', 'message': `channel with id ${channel_id} does not exist.`};
}
}
getChannelType(data: any) {
createByChannelType(data: any) {
try {
var Channel = require(`./channels/${data.client_type}s/${data.client}channel`);
console.log(`attempting to create channel of type ${data.client}, channel id: ${data.channel}...`);
logger.accessLog.info(`attempting to create channel of type ${data.client}, channel id: ${data.channel}...`);
return new Channel(data.channel);
} catch (e) {
console.log(e);
console.log(`creating base channel`);
logger.errorLog.info(e);
logger.accessLog.info(`creating base channel: ${data.channel}`);
return new ChannelBase(data.channel);
}
}

View File

@ -1,22 +1,25 @@
import ClientBase from '../clients/clientBase';
import MHSClient from '../clients/sites/mhsClient';
var logger = require('../logger');
class ChannelBase {
id: string;
clients: MHSClient[]|ClientBase[] = [];
constructor(id: string) {
this.id = id;
console.log('channel created');
logger.accessLog.info('Channel Created', {channelId: id});
}
addClient(client: MHSClient|ClientBase) {
console.log(client.data)
if (this.clientExists(client.id)) {
console.log('client already exits in channel');
logger.errorLog.info('Client already exits in channel', {channelId: this.id, clientId: client.id});
return {'status': 'notice', 'message': 'client aleady exists in channel'};
} else {
this.clients.push(client);
console.log('added client to channel');
logger.accessLog.info('Added client to channel', {channelId: this.id, clientId: client.id});
return {'status': 'success', 'message': 'client added'};
}
}
@ -34,12 +37,13 @@ class ChannelBase {
for (let client of this.clients) {
if (client != from) {
client.ws.send(message);
console.log(`sent to ${client.id}: %s`, message);
console.log(message);
logger.accessLog.info(`sent to ${client.id}: `, {message: message});
} else {
console.log('client is same as sender');
logger.accessLog.info(`client is same as sender: ${client.id} - `, {message: message});
}
}
return {'status': 'success', 'message': `message broadcast complete`};
}
};

View File

@ -2,17 +2,20 @@ import ClientBase from '../../clients/clientBase';
import MHSClient from '../../clients/sites/mhsClient';
import ChannelBase from '../channelBase';
var logger = require('../../logger');
class MHSChannel extends ChannelBase {
broadcastMessage(from: ClientBase|MHSClient|null, message: string) {
for (let client of this.clients) {
if (client != from && client.data.user_type == 'teacher') {
client.ws.send(message);
console.log(`sent to ${client.id}: %s`, message);
console.log(message);
logger.accessLog.info(`sent to ${client.id}: `, {message: message});
} else {
console.log('client is same as sender and/or not a teacher.');
logger.accessLog.info(`client is same as sender: ${client.id} - `, {message: message});
}
}
return {'status': 'success', 'message': `message broadcast complete`};
}
};

View File

@ -2,6 +2,8 @@ import * as WebSocket from 'ws';
import ClientBase from './clients/clientBase';
import MHSClient from './clients/sites/mhsClient';
var logger = require('./logger');
class ClientManager {
clients: ClientBase[]|MHSClient[] = [];
@ -13,10 +15,10 @@ class ClientManager {
if (data.client_type && !this.clientExists(data.user_id)) {
var client = this.getClientType(data, ws);
this.clients.push(client);
console.log('client added to client manager');
logger.accessLog.info(`client added to client manager: ${data.user_id}`);
return client;
} else {
console.log('no client type designated or client already exists, socket disconnected.')
logger.accessLog.info(`no client type designated or client already exists, socket disconnected: ${data.user_id}`);
ws.close();
return null;
}
@ -55,7 +57,7 @@ class ClientManager {
if (client.id == id) {
client.ws.close();
this.clients.splice(index, 1);
console.log('client disconnected');
logger.accessLog.info(`client disconnected: ${client.id}`);
return true;
}
@ -66,11 +68,11 @@ class ClientManager {
getClientType(data: any, ws: WebSocket) {
try {
var Client = require(`./clients/${data.client_type}s/${data.client}client`);
console.log(`attempting to create client of type ${data.client}, client id: ${data.user_id}...`);
logger.accessLog.info(`attempting to create client of type ${data.client}, client id: ${data.user_id}...`);
return new Client(data, ws);
} catch (e) {
console.log(e);
console.log(`creating base client`);
logger.errorLog.info(e);
logger.accessLog.info(`creating base client: ${data.user_id}`);
return new ClientBase(data, ws);
}
}

View File

@ -3,6 +3,8 @@ import * as ChannelManager from '../channelManager';
import ChannelBase from '../channels/channelBase';
import MHSChannel from '../channels/sites/mhsChannel';
var logger = require('../logger');
class ClientBase {
ws: WebSocket;
data: any;
@ -28,8 +30,9 @@ class ClientBase {
this.channel = channel;
this.ws.on('message', (message: string) => {
logger.accessLog.info(`starting broadcast on channel ${channel.id}: `, {message: message});
channel.broadcastMessage(this, message);
console.log('broadcasted: %s', message);
logger.accessLog.info(`broadcast complete on channel ${channel.id}: `, {message: message});
});
}

View File

@ -1,10 +1,12 @@
import * as WebSocket from 'ws';
import ClientBase from '../clientBase';
var logger = require('../../logger');
class MHSClient extends ClientBase {
constructor(data: any, ws: WebSocket) {
super(data, ws);
console.log('mhs client created');
logger.accessLog.info('MHS Client Created', {data: data});
}
};

View File

@ -6,6 +6,7 @@ module.exports = {
port: process.env.PORT || 8443,
hostname: process.env.HOSTNAME || 'ysbraid.localhost',
environment: process.env.ENVIRONMENT || 'development',
log_level: process.env.LOG_LEVEL || 'debug',
signOptions : {
issuer: 'Yardstick Software',
subject: 'Braid JWT',

41
src/logger.ts Normal file
View File

@ -0,0 +1,41 @@
var {winston, transports, createLogger, format} = require('winston');
var path = require('path');
// Set this to whatever, by default the path of the script.
var logPath = './logs/';
const tsFormat = () => (new Date().toISOString());
const errorLog = createLogger({
format: format.combine(
format.timestamp(),
format.json()
),
transports: [
new transports.File({
filename: path.join(logPath, 'errors.log'),
timestamp: tsFormat,
level: 'debug'
})
]
});
const accessLog = createLogger({
format: format.combine(
format.timestamp(),
format.json()
),
transports: [
new transports.File({
filename: path.join(logPath, 'access.log'),
timestamp: tsFormat,
level: 'info'
})
]
});
module.exports = {
errorLog: errorLog,
accessLog: accessLog
};

View File

@ -9,6 +9,7 @@ import * as url from 'url';
//internal imports
var routes = require('./routes');
var app = require('./config/app');
var logger = require('./logger');
import ClientManager from './clientManager';
import ChannelManager from './channelManager';
import ClientBase from './clients/clientBase';
@ -29,8 +30,8 @@ let clientManager = new ClientManager();
let channelManager = new ChannelManager();
wss.on('connection', (ws: WebSocket, request: object, args: string) => {
console.log('client connected');
var data = JSON.parse(args).data
logger.accessLog.info(`Client Connected: ${data.user_id}`);
if (!channelManager.channelExists(data.channel)) {
channelManager.createChannel(data);
@ -60,7 +61,7 @@ server.on('upgrade', async function upgrade(request, socket, head) {
args = await verifyConnection()
} catch (e) {
socket.destroy();
console.log('connection terminated.');
logger.accessLog.info('Connection Terminated');
return;
}
@ -90,4 +91,5 @@ server.on('upgrade', async function upgrade(request, socket, head) {
server.listen(app.port, () => {
console.log(`Braid v${app.version} is running!\n`);
logger.accessLog.info(`Braid v${app.version} is running!\n`);
});

View File

@ -0,0 +1,47 @@
import ChannelBase from '../channels/channelBase';
import ClientBase from '../clients/clientBase';
var expect = require('chai').expect;
var sinon = require('sinon');
var WebSocketClient = require('websocket').client;
var app = require('../config/app');
var name: string = 'test channel';
var channel: ChannelBase;
var wsLink: string = `wss://${app.hostname}:${app.port}`;
var wsClient = new WebSocketClient();
var data: any = { 'client': 'test', 'client_type':'site', 'user_id': 125, 'user_type': 'user', 'channel': name }
var client: ClientBase = new ClientBase(data, wsClient);
describe('ChannelBase', function () {
it('should create a class of ChannelBase', function () {
channel = new ChannelBase(name);
expect(channel.id).to.be.equal(name);
});
it('should add a client to channel', function () {
var result: any = channel.addClient(client);
expect(result.status).to.be.equal('success');
});
it('should find a client when trying to add said client to channel', function () {
var result: any = channel.addClient(client);
expect(result.status).to.be.equal('notice');
});
it('should find a client', function () {
var exist = channel.clientExists(client.id);
var result = exist ? true : false;
expect(result).to.be.equal(true);
});
it('should not broadcase a message to self', function () {
// var wstClient = new WebSocketClient(wsLink);
// var teacher_data: any = { 'client': 'test', 'client_type':'site', 'user_id': 126, 'user_type': 'teacher', 'channel': name }
// var teacher: ClientBase = new ClientBase(teacher_data, wstClient);
// channel.addClient(client);
// channel.addClient(teacher);
var result = channel.broadcastMessage(client, 'test message');
expect(result.status).to.be.equal('success');
});
});

View File

@ -0,0 +1,58 @@
import ChannelBase from '../channels/channelBase';
import ClientBase from '../clients/clientBase';
import MHSClient from '../clients/sites/mhsClient';
import MHSChannel from '../channels/sites/mhsChannel';
import ChannelManager from '../channelManager';
var expect = require('chai').expect;
var sinon = require('sinon');
var name: string = 'test channel';
var data: any = { 'client': 'test', 'client_type':'site', 'user_id': 125, 'user_type': 'user', 'channel': name }
var WebSocketClient = require('websocket').client;
var wsClient = new WebSocketClient();
var client: ClientBase = new ClientBase(data, wsClient);
let channelManager = new ChannelManager();
describe('ChannelManager', function () {
var channel: ChannelBase;
it('should create a channel', function () {
channel = channelManager.createChannel(data);
expect(channel.id).to.be.equal(name);
});
it('should return existing channel when attempting to create a channel', function () {
channel = channelManager.createChannel(data);
expect(channel.id).to.be.equal(name);
});
it('should return a channel when searching if channel exists', function () {
var exists = channelManager.channelExists(channel.id);
var result = exists ? true : false;
expect(result).to.be.equal(true);
});
it('should not return a channel when serachingif channel exists', function () {
var exists = channelManager.channelExists('no channel');
var result = exists ? true : false;
expect(result).to.be.equal(false);
});
it('should add a client to channel', function () {
var result = channelManager.addClientToChannel(client, channel.id);
expect(result.status).to.be.equal('success');
});
it('should not add a client to channel', function () {
var result = channelManager.addClientToChannel(client, 'no channel');
expect(result.status).to.be.equal('notice');
});
it('should create a channel of type MHSChannel', function () {
var data2 = { 'channel': 'test channel 2', 'client': 'mhs', 'client_type':'site' };
var result = channelManager.createByChannelType(data2);
expect(result.id).to.be.equal('test channel 2');
});
});

View File

View File

View File

View File