Highway to Shell, with NodeJS

Highway to Shell, with NodeJS

If we execute node without arguments from the command line, we obtain a REPL (Read-Eval-Print-Loop) environment. Inside this

If we execute node without arguments from the command line, we obtain a REPL (Read-Eval-Print-Loop) environment. Inside this ‘shell’ we can write a javascript code that will be executed immediately; this is very useful to experiment with NodeJS, to debug and to learn javascript.

Your own REPL

The REPL interface in NodeJS is a module that we can use to create our own REPL environments inside our applications. This enables us to communicate with our application while it is being executed.

In order to add REPL functionality to our application, we should use repl.start from the repl module:

var repl = require('repl');
repl.start('my prompt >');

Then, by executing the application we have a REPL environment with our personalized prompt:

$ node app.js
my prompt >var a = 1
undefined
my prompt >a
1
my prompt >

In addition to indicating the prompt, we can pass an object to the function repl.start, with the following fields (among others):

  • prompt– The prompt, as we have seen.
  • input– Input Stream. It is process.stdin, by default.
  • output– Output Stream. It is process.stdout, by default.
  • eval– A function that will be used to assess each input stream. It is an eval() wrapper by default. At the end I will show how to make a personalized assessment.

REPL Context

The repl runs on its own context. Therefore, if we want to have access to data outside this context we can assign new properties to the context object of the REPLServer in the following way:

var repl = require('repl');
var replServer = repl.start('my prompt >');
var obj = {
        a: 1,
        b: 2
};
function printObj() {
        console.log(obj);
}
replServer.context.obj = obj
replServer.context.printObj = printObj;

In this case, we are adding the object obj and the function printObj to the repl context. Then, executing the application:

$ node app.js
my prompt >obj
{ a: 1, b: 2 }
my prompt >printObj
[Function: printObj]
my prompt >printObj();
{ a: 1, b: 2 }
undefined
my prompt >obj.a = 5
5
my prompt >obj
{ a: 5, b: 2 }
my prompt >printObj();
{ a: 5, b: 2 }
undefined
my prompt >

We can see that, from the repl, we have access to the object and the function. Moreover, if we modify the properties of the object from the repl, they are modified in the context of the application as well.

Connection through TCP socket

Using the net module of nodejs we can set a repl interface in a TCP socket, and then get connected to the socket remotely by means of a client (for example, netcat). We can do that in the following way:

var net = require("net"),
    repl = require("repl");

net.createServer(function (socket) {
  repl.start({
    prompt: "My prompt via TCP Socket> ",
    input: socket,
    output: socket
  }).on('exit', function() {
    socket.end();
  });
}).listen(9000);

Then, we can get connected with netcat:

$ nc localhost 9000
My prompt via TCP Socket>

Personalized assessment function

As we have seen, we can use our own assessment function, which should have the following form:

function eval(cmd, context, filename, callback) {
  callback(null, result);
}

For example, an assessment function that shows the input using only capital letters:

var repl = require('repl');
var replServer = repl.start({eval: myEval});

function myEval(cmd, context, filename, callback) {
        result = cmd.replace(/n/, '').toUpperCase();
        callback(null, result);
}

Please note that we replace the end of the line since the cmd includes it. Then, we execute the application and we obtain the expected result:

> test
'TEST'

For more information

READ THE HAT’S BLOG

Comments?  Contact us for more information. We’ll quickly get back to you with the information you need.

SUBSCRIBE TO OUR NEWSLETTER

See All Posts