# How to read input from the command line in Node.js

By Atta Ur Rehman Shah (https://attacomsian.com/about). Published Apr 15, 2020, updated Oct 1, 2022. Topics: Node.js.
Canonical URL: https://attacomsian.com/blog/nodejs-read-input-from-cli

> A quick guide to learning how to make a Node.js CLI program interactive by prompting users to enter data from the command line.

Are you developing a little CLI tool in Node.js and want to be able to prompt users to enter input from the command line? Node.js provides the [readline](https://nodejs.org/api/readline.html) module precisely for this purpose. It offers an interface for reading data from a readable stream such as `process.stdin`, one line at a time.

Here is a simple example that prompts the user to input their name and nationality and then print these details on the console:

```javascript
const readline = require('readline')

const rl = readline.createInterface({
  input: process.stdin,
  output: process.stdout
})

// ask the user for the name input
rl.question(`What's your name? `, name => {
  // ask for nationality
  rl.question(`What are you from? `, country => {
    // log user details
    console.log(`${name} is from ${country}`)

    // close the stream
    rl.close()
  })
})
```

In the above example, the `readline.createInterface()` method is used to create an instance of `readline` by defining readable and writable streams.

The `rl.question()` method displays the query (the question) and waits for the user to enter an answer. Once the input data is available, it calls the callback method passing the user's input as the first parameter.

Finally, we call the `rl.close()` method in the final callback to close the `readline` interface. You can also listen to the `close` event invoked when the stream is closed. It can be useful to do some post questions work:

```javascript
// listen for close event
rl.on('close', () => {
  console.log('Goodbye ?')

  // exit the process
  process.exit(0)
})
```

Read the `readline` [documentation](https://nodejs.org/api/readline.html) to learn more about all the available methods and events.

## 3rd-Party Modules

The `readline` module is a low-level Node.js package that you might think is too complicated for complex use cases. If you want a higher-level interface for handling user input, just use the [prompt](https://www.npmjs.com/package/prompt) module from the Node Package Manager (NPM). You can add it to your project by executing the following command:

```bash
$ npm install prompt --save
```

It is relatively easy to use `prompt` than the `readline` module. You don't need to explicitly configure readable and writable streams.

Let us rewrite the above example by using the `prompt` module:

```javascript
const prompt = require('prompt')

// start the prompt
prompt.start()

// ask the user for the input
prompt.get(['name', 'country'], (err, result) => {
  if (err) {
    throw err
  }

  // print user details
  console.log(`${result.name} is from ${result.country}`)
})
```

### Handling Passwords

The `prompt` module makes it easier to securely ask the user to input a password. It will mask the input instead of showing the actual characters of the password:

```javascript
const prompt = require('prompt')

// start the prompt
prompt.start()

// define properties schema
var schema = {
  properties: {
    name: {
      pattern: /^[a-zA-Z\s\-]+$/,
      message: 'Name must be only letters, spaces, or dashes',
      required: true
    },
    password: {
      hidden: true
    }
  }
}

// ask the user for the input
prompt.get(schema, (err, result) => {
  if (err) {
    throw err
  }

  // print user credentials
  console.log(`${result.name} / ${result.password}`)
})
```

Notice the `pattern` attribute in the above example. It ensures that the input, we receive from the user for the `name` property, is validated before moving to the next property input.

### Adding Properties to an Object

The `prompt` module exposes another convenient method called `addProperties()` to extend an existing object by adding properties data from the command line:

```javascript
const prompt = require('prompt')

// start the prompt
prompt.start()

// create an object
const user = {
  name: 'John Doe',
  country: 'USA'
}

// extend `user` object
prompt.addProperties(user, ['email', 'age'], err => {
  if (err) {
    throw err
  }

  // print modified object
  console.dir(user)
})
```

Now, if you run the above program, you should see an output similar to the following:

```bash
$ node index.js
prompt: email:  john.doe@example.com
prompt: age:  23
{ name: 'John Doe',
  country: 'USA',
  email: 'john.doe@example.com',
  age: '23' }
```

As you can see above, `prompt` is highly customizable. Check out the official [documentation](https://www.npmjs.com/package/prompt) for more information. `prompt` can be a good choice if you are planning to build a solid CLI tool in Node.js.
