Updated tinycore to support bare minimum diagnostic

Bryan Roe committed Jan 24, 2021 at 16:17 UTC 6fcdbe3d4c1d4a76ce921284dc9de9bf4b66ef52
1 file changed +145 -36
agents/tinycore.js
+145 -36
@@ -14,54 +14,163 @@ See the License for the specific language governing permissions and
14 limitations under the License.
15 */
16
17 -function createMeshCore(agent) {
18 - var obj = {};
19 -
20 - // MeshAgent JavaScript Core Module. This code is sent to and running on the mesh agent.
21 - obj.meshCoreInfo = "TinyCore v1";
22 -
23 - if (agent == null) {
24 - // If we are running in Duktape, agent will be null
25 - var mesh = require('MeshAgent');
26 - } else {
27 - // Running in nodejs
28 - var mesh = agent.getMeshApi();
29 - }
17 +var obj = { meshCoreInfo: 'TinyCore v1' };
18 +var mesh = null;
19 +
20 +// Replace a string with a number if the string is an exact number
21 +function toNumberIfNumber(x) { if ((typeof x == 'string') && (+parseInt(x) === x)) { x = parseInt(x); } return x; }
22
31 - // Handle a mesh agent command
32 - function handleServerCommand(data) {
33 - if ((typeof data == 'object') && (data.action == 'msg') && (data.type == 'console') && data.value && data.sessionid) {
34 - mesh.SendCommand({ "action": "msg", "type": "console", "value": "Tiny core: " + data.value, "sessionid": data.sessionid });
23 +// Split a string taking into account the quoats. Used for command line parsing
24 +function splitArgs(str)
25 +{
26 + var myArray = [], myRegexp = /[^\s"]+|"([^"]*)"/gi;
27 + do { var match = myRegexp.exec(str); if (match != null) { myArray.push(match[1] ? match[1] : match[0]); } } while (match != null);
28 + return myArray;
29 +}
30 +// Parse arguments string array into an object
31 +function parseArgs(argv)
32 +{
33 + var results = { '_': [] }, current = null;
34 + for (var i = 1, len = argv.length; i < len; i++)
35 + {
36 + var x = argv[i];
37 + if (x.length > 2 && x[0] == '-' && x[1] == '-')
38 + {
39 + if (current != null) { results[current] = true; }
40 + current = x.substring(2);
41 + } else
42 + {
43 + if (current != null) { results[current] = toNumberIfNumber(x); current = null; } else { results['_'].push(toNumberIfNumber(x)); }
44 }
45 }
37 -
38 - // Called when the server connection state changes
39 - function handleServerConnection(state) {
40 - if (state == 1) { mesh.SendCommand({ "action": "coreinfo", "value": obj.meshCoreInfo }); } // Server connected, send mesh core information
46 + if (current != null) { results[current] = true; }
47 + return results;
48 +}
49 +function sendConsoleText(msg, sessionid)
50 +{
51 + try
52 + {
53 + if (sessionid != null)
54 + {
55 + require('MeshAgent').SendCommand({ action: 'msg', type: 'console', value: msg, sessionid: sessionid });
56 + }
57 + else
58 + {
59 + require('MeshAgent').SendCommand({ action: 'msg', type: 'console', value: msg });
60 + }
61 }
42 -
43 - obj.start = function() {
44 - // Hook up mesh agent events
45 - mesh.AddCommandHandler(handleServerCommand);
46 - mesh.AddConnectHandler(handleServerConnection);
47 - mesh.SendCommand({ "action": "coreinfo", "value": obj.meshCoreInfo }); // TODO: Check if connected before sending
62 + catch(e)
63 + {
64 }
49 -
50 - obj.stop = function() {
51 - mesh.AddCommandHandler(null);
52 - mesh.AddConnectHandler(null);
65 +}
66 +
67 +function processConsoleCommand(cmd, args, rights, sessionid)
68 +{
69 + try
70 + {
71 + var response = null;
72 + switch (cmd)
73 + {
74 + case 'help':
75 + response = "Available commands are: eval, osinfo, setdebug, versions.";
76 + break;
77 + case 'versions':
78 + response = JSON.stringify(process.versions, null, ' ');
79 + break;
80 + case 'eval':
81 + { // Eval JavaScript
82 + if (args['_'].length < 1)
83 + {
84 + response = 'Proper usage: eval "JavaScript code"'; // Display correct command usage
85 + } else
86 + {
87 + response = JSON.stringify(require('MeshAgent').eval(args['_'][0])); // This can only be run by trusted administrator.
88 + }
89 + break;
90 + }
91 + case 'setdebug':
92 + {
93 + if (args['_'].length < 1) { response = 'Proper usage: setdebug (target), 0 = Disabled, 1 = StdOut, 2 = This Console, * = All Consoles, 4 = WebLog, 8 = Logfile'; } // Display usage
94 + else { if (args['_'][0] == '*') { console.setDestination(2); } else { console.setDestination(parseInt(args['_'][0]), sessionid); } }
95 + break;
96 + }
97 + case 'osinfo': { // Return the operating system information
98 + var i = 1;
99 + if (args['_'].length > 0) { i = parseInt(args['_'][0]); if (i > 8) { i = 8; } response = 'Calling ' + i + ' times.'; }
100 + for (var j = 0; j < i; j++)
101 + {
102 + var pr = require('os').name();
103 + pr.sessionid = sessionid;
104 + pr.then(function (v)
105 + {
106 + sendConsoleText("OS: " + v, this.sessionid);
107 + });
108 + }
109 + break;
110 + }
111 + default: { // This is an unknown command, return an error message
112 + response = 'Unknown command \"' + cmd + '\", type \"help\" for list of available commands.';
113 + break;
114 + }
115 + }
116 + } catch (e) { response = "Command returned an exception error: " + e; console.log(e); }
117 + if (response != null) { sendConsoleText(response, sessionid); }
118 +}
119 +
120 +
121 +// Handle a mesh agent command
122 +function handleServerCommand(data)
123 +{
124 + if ((typeof data == 'object') && (data.action == 'msg') && (data.type == 'console') && data.value && data.sessionid)
125 + {
126 + if (data.value && data.sessionid)
127 + {
128 + try
129 + {
130 + var args = splitArgs(data.value);
131 + processConsoleCommand(args[0].toLowerCase(), parseArgs(args), data.rights, data.sessionid);
132 + }
133 + catch(e)
134 + {
135 + sendConsoleText(e);
136 + }
137 + }
138 }
139 +}
140 +
141 +// Called when the server connection state changes
142 +function handleServerConnection(state)
143 +{
144 + if (state == 1) { mesh.SendCommand({ "action": "coreinfo", "value": obj.meshCoreInfo }); } // Server connected, send mesh core information
145 +}
146 +
147 +obj.start = function ()
148 +{
149 + // Hook up mesh agent events
150 + mesh.AddCommandHandler(handleServerCommand);
151 + mesh.AddConnectHandler(handleServerConnection);
152 + mesh.SendCommand({ action: 'coreinfo', value: "TinyCore", caps: 0 });
153 +}
154
55 - return obj;
155 +obj.stop = function ()
156 +{
157 + mesh.AddCommandHandler(null);
158 + mesh.AddConnectHandler(null);
159 }
160
161 +
162 var xexports = null;
163 try { xexports = module.exports; } catch (e) { }
164
61 -if (xexports != null) {
165 +if (xexports != null)
166 +{
167 // If we are running within NodeJS, export the core
63 - module.exports.createMeshCore = createMeshCore;
64 -} else {
168 + module.exports.createMeshCore = function (agent) { mesh = agent.getMeshApi(); return (obj); };
169 +}
170 +else
171 +{
172 // If we are not running in NodeJS, launch the core
66 - createMeshCore().start(null);
173 + sendConsoleText('TinyCore Started...');
174 + mesh = require('MeshAgent');
175 + obj.start();
176 }