select() has a problem with a configured context.input
If something was piped to the process, a new readline context is required.
Setting the new input stream, only allows to type letters, so input() with the context works, but select does not.
Specifically: next to default's shown select name, letters appear when pressing any, but up and down does not work.
Example node code:
// test.js
import { open as fsOpen } from 'node:fs/promises';
import { select } from '@inquirer/prompts';
let TTY_INTERFACE = undefined;
if (!stdin.isTTY) {
//* handle reading text from stream here.
// ... some code. For testing, doesn't even have to be used, piping itself will already occupy the stdin.
//* get a new stream for input to be able to use readLine again.
const fd = process.platform === 'win32' ? '\\\\.\\CON' : '/dev/tty';
let stdinNew = (await fsOpen(fd, 'r')).createReadStream();
TTY_INTERFACE = {
input: stdinNew,
output: process.stdout
};
}
await select(
{
message: 'Select your API:',
choices: [{name: '-', value: ''}, {name: '#1', value: '1'}, {name: '#2', value: '2'}],
default: '-'
},
TTY_INTERFACE
);
test:
ls | node test.js
Did you try with other mode than r. I wonder if readonly mode doesn't listen for arrow keypresses as that would be a write option?
I am trying to figure out what's wrong with this for the last few hours ... But it seems
process.stdin.setRawMode(true);
// process.stdin.setEncoding('utf-8');
makes the difference for being able to pick up arrow keys and other special keys (wasn't there something about a those keys being 2 bytes or something..).
well, stdinNew : ReadStream !== Node.ReadStream (process.stdin is a Node.ReadStream) ... and setRawMode is not available
Ahhh yes, setRawMode(true) is set by default under certains circumstances (I think if we set events listeners as soon as the module load; otherwise it must be called manually.)
I added a warning on the documentation hopefully help the next people running into this issue. Cheers!