Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Adds a persistent Sandbox for evaluating code #2

Open
wants to merge 4 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
80 changes: 63 additions & 17 deletions dist/logger.js
Original file line number Diff line number Diff line change
@@ -1,10 +1,54 @@
/* Logger class to take care of the logging and conneting to the server.*/
/* jshint eqnull:true */
function debug(message, method) {
Ti.API.debug("[Logger" + (method != null ? "." + method : "") + "] " + message);
}

var Sandbox = function(logger) {
// Normally saving a reference to logger whould no be a problem. However we
// use "this" as the context to execute the eval. So we want to hide logger
// and only expose the log function. Because of this we use a closure to
// hide the logger object but still offer a log function.
this.log = function() { return logger.log.apply(logger, arguments); };
this.reset = function() { return logger.reset.apply(logger, arguments); };
};

Sandbox.exec = function(code, sandbox) {
/* jshint evil:true, boss:true */
var result;
if (result = code.match(/^\s*\/([A-za-z]+)(?:\s+(.+))?$/)) {
return Sandbox.command(sandbox, result[1].toLowerCase(), result[2]);
}
else {
return eval("(function(exports){" + code + "}).call(sandbox,sandbox)");
}
};

Sandbox.command = function(/* sandbox, command, options... */) {
var
sandbox = arguments[0],
command = arguments[1],
options = 3 <= arguments.length ? [].slice.call(arguments, 2) : [];
switch (command) {
case "reset":
sandbox.reset();
break;
default:
throw "Unknown command: " + command;
}
};

var Logger = function(host,port) {
this.host = host;
this.port = port;
this.socket = null;
this.connected = false;
this._msgs = []; // just to queued up the messages
this.reset();
};

Logger.prototype.reset = function() {
this.sandbox = new Sandbox(this);
};

Logger.prototype.connect = function() {
Expand All @@ -16,26 +60,27 @@ Logger.prototype.connect = function() {
});
this.socket.addEventListener('read', function(msg) {
try {
eval('(function(){' + msg.data + '})()' );
self.log(Sandbox.exec(msg.data,self.sandbox));
} catch(ex) {
Ti.API.debug(ex);
};
self.log(ex);
debug(ex, "connect");
}
});
this.socket.addEventListener('readError', function(){
Ti.API.debug('Error Reading from Logging Server');
debug('Error Reading from Logging Server', "connect");
self.connected = false;
// self.ensureConnection();
});
this.socket.addEventListener('writeError', function() {
Ti.API.debug('Error Writing to Logging Server');
debug('Error Writing to Logging Server', "connect");
self.connected = false;
// self.ensureConnection();
});
this.ensureConnection();
};

Logger.prototype.ensureConnection = function() {
if(this.socket.isValid) {return; };
if (this.socket.isValid) { return; }
this.connected = false;
var self = this;
var attempts = 0;
Expand All @@ -44,37 +89,38 @@ Logger.prototype.ensureConnection = function() {
attempts++;
if(attempts > 3) {
clearInterval(checkSocketConnected);
Ti.API.debug('Giving up trying to connect to Logging server');
};
debug('Giving up trying to connect to Logging server', "ensureConnection");
}
if(self.connected) {
clearInterval(checkSocketConnected);
self.log('===========================================');
self.log('Device ' + Titanium.Platform.macaddress + ' connected (' + String.formatDate( new Date(), 'medium') + ')');
for(var i = 0, len = self._msgs.length; i < len; i++ ) {
self.log(self._msgs[i]);
};
}
self._msgs = [];
} else {
self.socket.connect(); // attempt to connect
};
}
}, 10000);
};
/*
Log a message to the remote logging server
If the socket is not ready, queue up the messages to an array that will be sent when there's a good connection
*/
Logger.prototype.log = function(msg) {
if(msg === null) { msg = ''; }; // make sure it doesn't bomb out on null objects
if (msg == null) { return; } // make sure it doesn't bomb out on null objects
try {
// this.ensureConnection();
if(this.connected) {
this.socket.write(JSON.stringify(msg));
} else {
this._msgs.push(msg); // queue up the msg
};
}
} catch (ex) {
Ti.API.debug(ex);
};
debug(ex, "log");
}
debug(msg, "log"); // Redundent data is ok.
};


Expand All @@ -87,7 +133,7 @@ exports.logger = function(host, post) {
logger.connect();
} catch (ex) {
alert( 'Connection Error' );
Ti.API.debug(ex);
};
debug(ex);
}
return logger;
};
};
80 changes: 63 additions & 17 deletions src/logger.js
Original file line number Diff line number Diff line change
@@ -1,10 +1,54 @@
/* Logger class to take care of the logging and conneting to the server.*/
/* jshint eqnull:true */
function debug(message, method) {
Ti.API.debug("[Logger" + (method != null ? "." + method : "") + "] " + message);
}

var Sandbox = function(logger) {
// Normally saving a reference to logger whould no be a problem. However we
// use "this" as the context to execute the eval. So we want to hide logger
// and only expose the log function. Because of this we use a closure to
// hide the logger object but still offer a log function.
this.log = function() { return logger.log.apply(logger, arguments); };
this.reset = function() { return logger.reset.apply(logger, arguments); };
};

Sandbox.exec = function(code, sandbox) {
/* jshint evil:true, boss:true */
var result;
if (result = code.match(/^\s*\/([A-za-z]+)(?:\s+(.+))?$/)) {
return Sandbox.command(sandbox, result[1].toLowerCase(), result[2]);
}
else {
return eval("(function(exports){" + code + "}).call(sandbox,sandbox)");
}
};

Sandbox.command = function(/* sandbox, command, options... */) {
var
sandbox = arguments[0],
command = arguments[1],
options = 3 <= arguments.length ? [].slice.call(arguments, 2) : [];
switch (command) {
case "reset":
sandbox.reset();
break;
default:
throw "Unknown command: " + command;
}
};

var Logger = function(host,port) {
this.host = host;
this.port = port;
this.socket = null;
this.connected = false;
this._msgs = []; // just to queued up the messages
this.reset();
};

Logger.prototype.reset = function() {
this.sandbox = new Sandbox(this);
};

Logger.prototype.connect = function() {
Expand All @@ -16,26 +60,27 @@ Logger.prototype.connect = function() {
});
this.socket.addEventListener('read', function(msg) {
try {
eval('(function(){' + msg.data + '})()' );
self.log(Sandbox.exec(msg.data,self.sandbox));
} catch(ex) {
Ti.API.debug(ex);
};
self.log(ex);
debug(ex, "connect");
}
});
this.socket.addEventListener('readError', function(){
Ti.API.debug('Error Reading from Logging Server');
debug('Error Reading from Logging Server', "connect");
self.connected = false;
// self.ensureConnection();
});
this.socket.addEventListener('writeError', function() {
Ti.API.debug('Error Writing to Logging Server');
debug('Error Writing to Logging Server', "connect");
self.connected = false;
// self.ensureConnection();
});
this.ensureConnection();
};

Logger.prototype.ensureConnection = function() {
if(this.socket.isValid) {return; };
if (this.socket.isValid) { return; }
this.connected = false;
var self = this;
var attempts = 0;
Expand All @@ -44,37 +89,38 @@ Logger.prototype.ensureConnection = function() {
attempts++;
if(attempts > 3) {
clearInterval(checkSocketConnected);
Ti.API.debug('Giving up trying to connect to Logging server');
};
debug('Giving up trying to connect to Logging server', "ensureConnection");
}
if(self.connected) {
clearInterval(checkSocketConnected);
self.log('===========================================');
self.log('Device ' + Titanium.Platform.macaddress + ' connected (' + String.formatDate( new Date(), 'medium') + ')');
for(var i = 0, len = self._msgs.length; i < len; i++ ) {
self.log(self._msgs[i]);
};
}
self._msgs = [];
} else {
self.socket.connect(); // attempt to connect
};
}
}, 10000);
};
/*
Log a message to the remote logging server
If the socket is not ready, queue up the messages to an array that will be sent when there's a good connection
*/
Logger.prototype.log = function(msg) {
if(msg === null) { msg = ''; }; // make sure it doesn't bomb out on null objects
if (msg == null) { return; } // make sure it doesn't bomb out on null objects
try {
// this.ensureConnection();
if(this.connected) {
this.socket.write(JSON.stringify(msg));
} else {
this._msgs.push(msg); // queue up the msg
};
}
} catch (ex) {
Ti.API.debug(ex);
};
debug(ex, "log");
}
debug(msg, "log"); // Redundent data is ok.
};


Expand All @@ -87,7 +133,7 @@ exports.logger = function(host, post) {
logger.connect();
} catch (ex) {
alert( 'Connection Error' );
Ti.API.debug(ex);
};
debug(ex);
}
return logger;
};
};