switching socket.io-client for ReconnectingWebSocket library

This commit is contained in:
Jared Tabor 2016-08-28 13:01:59 -07:00
parent 6d4a2a8f8e
commit e9b54dcd3c
8 changed files with 94 additions and 195 deletions

View File

@ -713,80 +713,53 @@ var tower = angular.module('Tower', [
$rootScope.removeOpenSocket();
}
$rootScope.removeOpenSocket = $rootScope.$on('OpenSocket', function() {
// Listen for job changes and issue callbacks to initiate
// DOM updates
function openSocket() {
var schedule_socket, control_socket;
sock = Socket({ scope: $rootScope, endpoint: "jobs" });
sock.init();
sock.on("status_changed", function(data) {
$log.debug('Job ' + data.unified_job_id +
' status changed to ' + data.status +
' send to ' + $location.$$url);
// this acts as a router...it emits the proper
// value based on what URL the user is currently
// accessing.
if ($state.is('jobs')) {
$rootScope.$emit('JobStatusChange-jobs', data);
} else if ($state.includes('jobDetail') ||
$state.is('adHocJobStdout') ||
$state.is('inventorySyncStdout') ||
$state.is('managementJobStdout') ||
$state.is('scmUpdateStdout')) {
$log.debug("sending status to standard out");
$rootScope.$emit('JobStatusChange-jobStdout', data);
}
if ($state.includes('jobDetail')) {
$rootScope.$emit('JobStatusChange-jobDetails', data);
} else if ($state.is('dashboard')) {
$rootScope.$emit('JobStatusChange-home', data);
} else if ($state.is('portalMode')) {
$rootScope.$emit('JobStatusChange-portal', data);
} else if ($state.is('projects')) {
$rootScope.$emit('JobStatusChange-projects', data);
} else if ($state.is('inventoryManage')) {
$rootScope.$emit('JobStatusChange-inventory', data);
}
});
sock.on("summary_complete", function(data) {
$log.debug('Job summary_complete ' + data.unified_job_id);
$rootScope.$emit('JobSummaryComplete', data);
});
schedule_socket = Socket({
scope: $rootScope,
endpoint: "schedules"
});
schedule_socket.init();
schedule_socket.on("schedule_changed", function(data) {
$log.debug('Schedule ' + data.unified_job_id + ' status changed to ' + data.status);
$rootScope.$emit('ScheduleStatusChange', data);
});
control_socket = Socket({
scope: $rootScope,
endpoint: "control"
});
control_socket.init();
control_socket.on("limit_reached", function(data) {
$log.debug(data.reason);
$rootScope.sessionTimer.expireSession('session_limit');
$state.go('signOut');
});
$rootScope.socket = Socket({ scope: $rootScope});
$rootScope.socket.init();
}
openSocket();
setTimeout(function() {
$rootScope.$apply(function() {
sock.checkStatus();
$rootScope.socket.checkStatus();
$log.debug('socket status: ' + $rootScope.socketStatus);
});
}, 2000);
});
// {'groups':
// {'jobs': ['status_changed', 'summary'],
// 'schedules': ['changed'],
// 'ad_hoc_command_events': [ids,],
// 'job_events': [ids,],
// 'control': ['limit_reached'],
// }
// }
$rootScope.$on('$stateChangeStart', function(event, toState, toParams, fromState) {
if(toState.name === 'dashboard'){
$rootScope.socket.emit('{"groups":{"jobs": ["status_changed"]}}');
}
else if(toState.name === 'jobDetail'){
$rootScope.socket.emit(`{"groups":{"jobs": ["status_changed", "summary"]},{"job_events":[${toParams.id}]}}`);
}
else if(toState.name === 'jobStdout'){
$rootScope.socket.emit('{"groups":{"jobs": ["status_changed"]}}');
}
else if(toState.name === 'jobs'){
$rootScope.socket.emit('{"groups":{"jobs": ["status_changed"]}, {"schedules": ["changed"]}}');
}
else if(toState.name === 'portalMode'){
$rootScope.socket.emit('{"groups":{"jobs": ["status_changed"]}}');
}
else if(toState.name === 'projects'){
$rootScope.socket.emit('{"groups":{"jobs": ["status_changed"]}}');
}
else if(toState.name === 'inventory'){
$rootScope.socket.emit('{"groups":{"jobs": ["status_changed"]}}');
}
else if(toState.name === 'adHocJobStdout'){
$rootScope.socket.emit(`{"groups":{"ad_hoc_command_events": [${toParams.id}]}}`);
}
});
$rootScope.$on('$stateChangeSuccess', function(event, toState, toParams, fromState) {

View File

@ -28,7 +28,7 @@
// custom_login_info: "example notice" // have a notice displayed in the login modal for users. note that, as a security measure, custom html is not supported and will be escaped.
tooltip_delay: { show: 500, hide: 100 }, // Default number of milliseconds to delay displaying/hiding tooltips
debug_mode: false, // Enable console logging messages
debug_mode: true, // Enable console logging messages
password_length: 8, // Minimum user password length. Set to 0 to not set a limit
password_hasLowercase: true, // require a lowercase letter in the password

View File

@ -198,7 +198,7 @@ export default
"<p><i class=\"fa fa-circle unreachable-hosts-color\"></i> Unreachable</p>\n" +
"<p><i class=\"fa fa-circle failed-hosts-color\"></i> Failed</p>\n";
function openSocket() {
$rootScope.event_socket.on("job_events-" + job_id, function(data) {
$rootScope.socket.on("job_events-" + job_id, function(data) {
// update elapsed time on each event received
scope.job_status.elapsed = GetElapsed({
start: scope.job.created,
@ -213,9 +213,9 @@ export default
});
// Unbind $rootScope socket event binding(s) so that they don't get triggered
// in another instance of this controller
scope.$on('$destroy', function() {
$rootScope.event_socket.removeAllListeners("job_events-" + job_id);
});
// scope.$on('$destroy', function() {
// $rootScope.socket.removeAllListeners("job_events-" + job_id);
// });
}
openSocket();

View File

@ -13,22 +13,22 @@ export default {
parent: 'jobs',
label: "{{ job.id }} - {{ job.name }}"
},
resolve: {
jobEventsSocket: ['Socket', '$rootScope', function(Socket, $rootScope) {
if (!$rootScope.event_socket) {
$rootScope.event_socket = Socket({
scope: $rootScope,
endpoint: "job_events"
});
$rootScope.event_socket.init();
// returns should really be providing $rootScope.event_socket
// otherwise, we have to inject the entire $rootScope into the controller
return true;
} else {
return true;
}
}]
},
// resolve: {
// jobEventsSocket: ['Socket', '$rootScope', function(Socket, $rootScope) {
// if (!$rootScope.event_socket) {
// $rootScope.event_socket = Socket({
// scope: $rootScope,
// endpoint: "job_events"
// });
// $rootScope.event_socket.init();
// // returns should really be providing $rootScope.event_socket
// // otherwise, we have to inject the entire $rootScope into the controller
// return true;
// } else {
// return true;
// }
// }]
// },
templateUrl: templateUrl('job-detail/job-detail'),
controller: 'JobDetailController'
};

View File

@ -22,16 +22,16 @@
* @methodOf shared.function:Socket
* @description
*/
import ReconnectingWebSocket from 'reconnectingwebsocket'
export default
angular.module('SocketIO', ['Utilities'])
.factory('Socket', ['$rootScope', '$location', '$log', 'Authorization', 'Store', function ($rootScope, $location, $log, Authorization, Store) {
return function(params) {
var scope = params.scope,
host = $location.host(),
host = window.location.host,
endpoint = params.endpoint,
protocol = $location.protocol(),
io = require('socket.io-client'),
config, socketPort,
url;
@ -45,7 +45,9 @@ angular.module('SocketIO', ['Utilities'])
config = Store('AnsibleConfig');
socketPort = config.websocket_port;
}
url = protocol + '://' + host + ':' + socketPort + '/socket.io/' + endpoint;
url = "ws://" + host + "/websocket/";
// url = protocol + '://' + host + ':' + socketPort + '/socket.io/' + endpoint;
$log.debug('opening socket connection to: ' + url);
function getSocketTip(status) {
@ -75,86 +77,10 @@ angular.module('SocketIO', ['Utilities'])
// We have a valid session token, so attempt socket connection
$log.debug('Socket connecting to: ' + url);
self.scope.socket_url = url;
self.socket = io.connect(url, {
query: "Token="+token,
headers:
{
'Authorization': 'Token ' + token, // i don't think these are actually inserted into the header--jt
'X-Auth-Token': 'Token ' + token
},
'connect timeout': 3000,
'try multiple transports': false,
'max reconnection attempts': 10,
'reconnection limit': 2000,
'force new connection': true
});
self.socket.on('connection', function() {
$log.debug('Socket connecting...');
self.scope.$apply(function () {
self.scope.socketStatus = 'connecting';
self.scope.socketTip = getSocketTip(self.scope.socketStatus);
});
});
self.socket.on('connect', function() {
$log.debug('Socket connection established');
self.scope.$apply(function () {
self.scope.socketStatus = 'ok';
self.scope.socketTip = getSocketTip(self.scope.socketStatus);
});
});
self.socket.on('connect_failed', function(reason) {
var r = reason || 'connection refused by host',
token_actual = Authorization.getToken();
$log.debug('Socket connection failed: ' + r);
if (token_actual === token) {
self.socket.socket.disconnect();
}
self.scope.$apply(function () {
self.scope.socketStatus = 'error';
self.scope.socketTip = getSocketTip(self.scope.socketStatus);
});
});
self.socket.on('diconnect', function() {
$log.debug('Socket disconnected');
self.scope.$apply(function() {
self.scope.socketStatus = 'error';
self.scope.socketTip = getSocketTip(self.scope.socketStatus);
});
});
self.socket.on('error', function(reason) {
var r = reason || 'connection refused by host';
$log.debug('Socket error: ' + r);
$log.error('Socket error: ' + r);
self.scope.$apply(function() {
self.scope.socketStatus = 'error';
self.scope.socketTip = getSocketTip(self.scope.socketStatus);
});
});
self.socket.on('reconnecting', function() {
$log.debug('Socket attempting reconnect...');
self.scope.$apply(function() {
self.scope.socketStatus = 'connecting';
self.scope.socketTip = getSocketTip(self.scope.socketStatus);
});
});
self.socket.on('reconnect', function() {
$log.debug('Socket reconnected');
self.scope.$apply(function() {
self.scope.socketStatus = 'ok';
self.scope.socketTip = getSocketTip(self.scope.socketStatus);
});
});
self.socket.on('reconnect_failed', function(reason) {
$log.error('Socket reconnect failed: ' + reason);
self.scope.$apply(function() {
self.scope.socketStatus = 'error';
self.scope.socketTip = getSocketTip(self.scope.socketStatus);
});
self.socket = new ReconnectingWebSocket(url, null, {
debug: true,
timeoutInterval: 3000,
maxReconnectAttempts: 10
});
}
else {
@ -167,21 +93,19 @@ angular.module('SocketIO', ['Utilities'])
// Check connection status
var self = this;
if(self){
if(self.socket){
if(self.socket.socket){
if (self.socket.socket.connected) {
self.scope.socketStatus = 'ok';
}
else if (self.socket.socket.connecting || self.socket.reconnecting) {
self.scope.socketStatus = 'connecting';
}
else {
self.scope.socketStatus = 'error';
}
self.scope.socketTip = getSocketTip(self.scope.socketStatus);
return self.scope.socketStatus;
if(self.socket){
if (self.socket.readyState === 0 ) {
self.scope.socketStatus = 'connecting';
}
else if (self.socket.readyState === 1){
self.scope.socketStatus = 'ok';
}
else if (self.socket.readyState === 2 || self.socket.readyState === 3 ){
self.scope.socketStatus = 'error';
}
self.scope.socketTip = getSocketTip(self.scope.socketStatus);
return self.scope.socketStatus;
}
}
}
},
@ -189,7 +113,8 @@ angular.module('SocketIO', ['Utilities'])
var self = this;
if(self){
if(self.socket){
self.socket.on(eventName, function () {
self.socket.onmessage(eventName, function (e) {
console.log('Received From Server: ' + e.data);
var args = arguments;
self.scope.$apply(function () {
callback.apply(self.socket, args);
@ -201,7 +126,7 @@ angular.module('SocketIO', ['Utilities'])
},
emit: function (eventName, data, callback) {
var self = this;
self.socket.emit(eventName, data, function () {
self.socket.send(eventName, data, function () {
var args = arguments;
self.scope.$apply(function () {
if (callback) {
@ -217,7 +142,7 @@ angular.module('SocketIO', ['Utilities'])
var self = this;
if(self){
if(self.socket){
self.socket.removeAllListeners(eventName);
self.socket.removeEventListener(eventName);
}
}
},

View File

@ -22,7 +22,7 @@ export default ['$log', '$rootScope', '$scope', '$state', '$stateParams', 'Proce
function openSockets() {
if ($state.current.name === 'jobDetail') {
$log.debug("socket watching on job_events-" + job_id);
$rootScope.event_socket.on("job_events-" + job_id, function() {
$rootScope.socket.on("job_events-" + job_id, function() {
$log.debug("socket fired on job_events-" + job_id);
if (api_complete) {
event_queue++;
@ -30,9 +30,9 @@ export default ['$log', '$rootScope', '$scope', '$state', '$stateParams', 'Proce
});
// Unbind $rootScope socket event binding(s) so that they don't get triggered
// in another instance of this controller
$scope.$on('$destroy', function() {
$rootScope.event_socket.removeAllListeners("job_events-" + job_id);
});
// $scope.$on('$destroy', function() {
// $rootScope.socket.removeAllListeners("job_events-" + job_id);
// });
}
if ($state.current.name === 'adHocJobStdout') {
$log.debug("socket watching on ad_hoc_command_events-" + job_id);
@ -44,9 +44,9 @@ export default ['$log', '$rootScope', '$scope', '$state', '$stateParams', 'Proce
});
// Unbind $rootScope socket event binding(s) so that they don't get triggered
// in another instance of this controller
$scope.$on('$destroy', function() {
$rootScope.adhoc_event_socket.removeAllListeners("ad_hoc_command_events-" + job_id);
});
// $scope.$on('$destroy', function() {
// $rootScope.adhoc_event_socket.removeAllListeners("ad_hoc_command_events-" + job_id);
// });
}
}

View File

@ -99,7 +99,8 @@
"moment": "^2.10.2",
"ng-toast": "leigh-johnson/ngToast#2.0.1",
"nvd3": "leigh-johnson/nvd3#1.7.1",
"select2": "^4.0.2",
"socket.io-client": "^0.9.17"
"reconnectingwebsocket": "^1.0.0",
"rrule": "jkbrzt/rrule#4ff63b2f8524fd6d5ba6e80db770953b5cd08a0c",
"select2": "^4.0.2"
}
}

View File

@ -27,7 +27,7 @@ var vendorPkgs = [
'ng-toast',
'nvd3',
'select2',
'socket.io-client',
'reconnectingwebsocket'
];
var dev = {