Spec-Zone.ru › Node.js 10 LTS

Readline

Устойчивость: 2 - Стабильно

Модуль readline предоставляет интерфейс для чтения данных из потока Readable (например, process.stdin) по одной строке за раз. К нему можно обратиться следующим образом:

const readline = require('readline');

Следующий простой пример демонстрирует основное использование модуля readline.

const readline = require('readline');

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

rl.question('What do you think of Node.js? ', (answer) => {
  // TODO: Log the answer in a database
  console.log(`Thank you for your valuable feedback: ${answer}`);

  rl.close();
});

После запуска приложения Node.js не завершит работу до тех пор, пока поток readline.Interface не будет закрыт, поскольку интерфейс ожидает получения данных из потока input.

Класс: Интерфейс

Добавлен в: v0.1.104

Экземпляры класса readline.Interface создаются с помощью метода readline.createInterface(). Каждый экземпляр связан с одним потоком Readable и одним потоком Writable. Поток output используется для вывода подсказок для пользовательского ввода, который поступает и считывается из потока input.

Событие: 'close'

Добавлен в: v0.1.98

Событие 'close' генерируется в следующих случаях:

  • Вызван метод rl.close(), и экземпляр readline.Interface передал управление потоками input и output;
  • Поток input получает событие 'end';
  • Поток input получает <ctrl>-D для сигнализации о конце передачи (EOT);
  • Поток input получает <ctrl>-C для сигнализации о SIGINT, и на экземпляре readline.Interface нет обработчика событий 'SIGINT'.

Функция-обработчик вызывается без аргументов.

Экземпляр readline.Interface завершается после генерации события 'close'.

Событие: 'line'

Добавлен в: v0.1.98

Событие 'line' генерируется всякий раз, когда поток input получает входные данные с новой строки (\n, \r, или \r\n). Это обычно происходит, когда пользователь нажимает клавиши <Enter>, или <Return>.

Функция-обработчик вызывается со строкой, содержащей полученную строку ввода.

rl.on('line', (input) => {
  console.log(`Received: ${input}`);
});

Событие: 'pause'

Добавлен в: v0.7.5

Событие 'pause' генерируется в следующих случаях:

  • Поток input приостановлен.
  • Поток input не приостановлен и получает событие 'SIGCONT'. (См. события 'SIGTSTP' и 'SIGCONT'.)

Функция-обработчик вызывается без аргументов.

rl.on('pause', () => {
  console.log('Readline paused.');
});

Событие: 'resume'

Добавлен в: v0.7.5

Событие 'resume' генерируется всякий раз, когда поток input возобновляется.

Функция-обработчик вызывается без аргументов.

rl.on('resume', () => {
  console.log('Readline resumed.');
});

Событие: 'SIGCONT'

Добавлен в: v0.7.5

Событие 'SIGCONT' генерируется, когда процесс Node.js, ранее переведённый в фоновый режим с помощью <ctrl>-Z (т.е. SIGTSTP ), затем возвращён в фоновый режим с помощью fg(1p).

Если поток input был приостановлен до запроса SIGTSTP, это событие не будет сгенерировано.

Функция-обработчик вызывается без аргументов.

rl.on('SIGCONT', () => {
  // `prompt` will automatically resume the stream
  rl.prompt();
});

Событие 'SIGCONT' не поддерживается на Windows.

Событие: 'SIGINT'

Добавлен в: v0.3.0

Событие 'SIGINT' генерируется всякий раз, когда поток input получает ввод <ctrl>-C, обычно известный как SIGINT. Если обработчики событий 'SIGINT' не зарегистрированы, когда поток input получает SIGINT, событие 'pause' будет сгенерировано.

Функция-обработчик вызывается без аргументов.

rl.on('SIGINT', () => {
  rl.question('Are you sure you want to exit? ', (answer) => {
    if (answer.match(/^y(es)?$/i)) rl.pause();
  });
});

Событие: 'SIGTSTP'

Добавлен в: v0.7.5

Событие 'SIGTSTP' генерируется, когда поток input получает ввод <ctrl>-Z, обычно известный как SIGTSTP. Если обработчики событий 'SIGTSTP' не зарегистрированы, когда поток input получает SIGTSTP, процесс Node.js будет отправлен в фоновый режим.

При возобновлении программы с помощью fg(1p) будут сгенерированы события 'pause' и 'SIGCONT'. Их можно использовать для возобновления потока input.

События 'pause' и 'SIGCONT' не будут сгенерированы, если поток input был приостановлен до отправки процесса в фоновый режим.

Функция-обработчик вызывается без аргументов.

rl.on('SIGTSTP', () => {
  // This will override SIGTSTP and prevent the program from going to the
  // background.
  console.log('Caught SIGTSTP.');
});

Событие 'SIGTSTP' не поддерживается на Windows.

rl.close()

Добавлен в: v0.1.98

Метод rl.close() закрывает экземпляр readline.Interface и передаёт управление потоками input и output. При вызове будет сгенерировано событие 'close'.

Вызов rl.close() немедленно не останавливает генерацию других событий (включая 'line') экземпляром readline.Interface.

rl.pause()

Добавлен в: v0.3.4

Метод rl.pause() приостанавливает поток input, позволяя его возобновить позже при необходимости.

Вызов rl.pause() немедленно не останавливает генерацию других событий (включая 'line') экземпляром readline.Interface.

rl.prompt([preserveCursor])

Добавлен в: v0.1.98
  • preserveCursor <boolean> Если true, предотвращает сброс позиции курсора до 0.

Метод rl.prompt() записывает заданный экземпляром readline.Interface конфигурированный prompt на новую строку в output , чтобы предоставить пользователю новое место для ввода.

При вызове rl.prompt() возобновит поток input , если он был приостановлен.

Если экземпляр readline.Interface был создан с output установленным в null или undefined, подсказка не будет выведена.

rl.question(query, callback)

Добавлен в: v0.3.3
  • query <строка> Текст для вывода в output, добавленный перед подсказкой.
  • callback <Функция> Функция обратного вызова, которая вызывается с пользовательским вводом в ответ на query.

Метод rl.question() отображает query , записывая его в output, ожидает пользовательского ввода в input, а затем вызывает функцию callback, передавая полученный ввод в качестве первого аргумента.

При вызове rl.question() возобновит поток input , если он был приостановлен.

Если экземпляр readline.Interface был создан с output установленным в null или undefined, query не будет выведено.

Пример использования:

rl.question('What is your favorite food? ', (answer) => {
  console.log(`Oh, so your favorite food is ${answer}`);
});

Функция callback, переданная в rl.question(), не следует типичному шаблону, принимающему объект Error или null в качестве первого аргумента. Функция callback вызывается с предоставленным ответом в качестве единственного аргумента.

rl.resume()

Добавлен в: v0.3.4

Метод rl.resume() возобновляет поток input , если он был приостановлен.

rl.setPrompt(prompt)

Добавлен в: v0.1.98
  • prompt <строка>

Метод rl.setPrompt() устанавливает подсказку, которая будет выведена в output всякий раз, когда вызывается rl.prompt().

rl.write(data[, key])

Добавлен в: v0.1.98
  • data <string>
  • key <Object>

    • ctrl <boolean> true для указания ключа <ctrl>.
    • meta <boolean> true для указания ключа <Meta>.
    • shift <boolean> true для указания ключа <Shift>.
    • name <string> Название ключа.

Метод rl.write() запишет либо data, либо последовательность ключей, идентифицированную key, в output. Аргумент key поддерживается только если output является текстовым терминалом TTY.

Если key указано, data игнорируется.

При вызове rl.write() возобновит поток input, если он был приостановлен.

Если readline.Interface был создан с output установленным в null или undefined, data и key не записываются.

rl.write('Delete this!');
// Simulate Ctrl+u to delete the line written previously
rl.write(null, { ctrl: true, name: 'u' });

Метод rl.write() запишет данные в readline Interface в input как если бы они были введены пользователем.

rl[Symbol.asyncIterator]()

История
Версия Изменения
v11.4.0

Добавлена в: v11.4.0

v10.17.0

Поддержка Symbol.asyncIterator больше не экспериментальная.

Уровень стабильности: 2 - Стабильно
  • Возвращает: <AsyncIterator>

Создаёт объект AsyncIterator, который итерируется по каждой строке в потоке ввода как строка. Этот метод позволяет асинхронно итерироваться по объектам readline.Interface через циклы for-await-of.

Ошибки в потоке ввода не передаются.

Если цикл прерывается с помощью break, throw, или return, будет вызван rl.close(). Другими словами, итерация по readline.Interface всегда полностью потребляет поток ввода.

Особенностью использования этой экспериментальной API является то, что производительность в настоящее время не соответствует традиционному API событий 'line', и поэтому не рекомендуется для приложений, чувствительных к производительности. Ожидается, что ситуация улучшится в будущем.

async function processLineByLine() {
  const rl = readline.createInterface({
    // ...
  });

  for await (const line of rl) {
    // Each line in the readline input will be successively available here as
    // `line`.
  }
}

readline.clearLine(stream, dir)[src]

Добавлена в: v0.7.7
  • stream <stream.Writable>
  • dir <number>

    • -1 - влево от курсора
    • 1 - вправо от курсора
    • 0 - вся строка

Метод readline.clearLine() очищает текущую строку указанного потока TTY в заданном направлении, определённом dir.

readline.clearScreenDown(stream)[src]

Добавлена в: v0.7.7
  • stream <stream.Writable>

Метод readline.clearScreenDown() очищает указанный поток TTY от текущей позиции курсора вниз.

readline.createInterface(options)[src]

История
Версия Изменения
v8.3.0, 6.11.4

Удален максимальный лимит опции crlfDelay.

v6.6.0

Опция crlfDelay теперь поддерживается.

v6.3.0

Опция prompt теперь поддерживается.

v6.0.0

Опция historySize теперь может быть 0.

v0.1.98

Добавлена в: v0.1.98

  • options <Object>

    • input <stream.Readable> Поток Readable для прослушивания. Эта опция обязательна.
    • output <stream.Writable> Поток Writable для записи данных readline.
    • completer <Function> Необязательная функция для автодополнения Tab.
    • terminal <boolean> true указывает, следует ли рассматривать потоки input и output как TTY, и записывать ли к ним коды ANSI/VT100. По умолчанию: проверка isTTY в потоке output при создании.
    • historySize <number> Максимальное число строк в истории. Для отключения истории установите это значение в 0. Эта опция имеет смысл только если terminal установлено в true пользователем или внутренним output check. В противном случае механизм кеширования истории не инициализируется. По умолчанию: 30.
    • prompt <string> Строка запроса. По умолчанию: '> '.
    • crlfDelay <number> Если задержка между \r и \n превышает crlfDelay миллисекунд, \r и \n будут рассматриваться как отдельные входные данные. crlfDelay будет приведено к числу не меньше 100. Может быть установлено в Infinity, в этом случае \r и \n всегда будут рассматриваться как один символ новой строки (что может быть уместно для чтения файлов с разделителем строк \r\n). По умолчанию: 100.
    • removeHistoryDuplicates <boolean> Если true, когда новая строка ввода дублирует более старую в списке истории, она удаляет старую строку из списка. По умолчанию: false.
    • escapeCodeTimeout <number> Продолжительность, которую readline будет ожидать символ (при чтении неоднозначной последовательности символов, которая может быть как полной последовательностью символов, так и может принять дополнительные входные данные для завершения более длинной последовательности) в миллисекундах. По умолчанию: 500.

Метод readline.createInterface() создаёт новый экземпляр readline.Interface.

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

После создания экземпляра readline.Interface, наиболее распространённым случаем является прослушивание события 'line'.

rl.on('line', (line) => {
  console.log(`Received: ${line}`);
});

Если terminal установлено в true для этого экземпляра, тогда поток output получит лучшую совместимость, если он определит свойство output.columns и выпустит событие 'resize' на output, если или когда количество столбцов изменится (process.stdout делает это автоматически, когда это TTY).

Использование функции completer

Функция completer принимает текущую введённую пользователем строку в качестве аргумента и возвращает Array с 2 элементами:

  • Массив Array с совпадающими элементами для завершения.
  • Подстрока, которая использовалась для соответствия.

Например: [[substr1, substr2, ...], originalsubstring].

function completer(line) {
  const completions = '.help .error .exit .quit .q'.split(' ');
  const hits = completions.filter((c) => c.startsWith(line));
  // show all completions if none found
  return [hits.length ? hits : completions, line];
}

Функция completer может быть вызвана асинхронно, если она принимает два аргумента:

function completer(linePartial, callback) {
  callback(null, [['123'], linePartial]);
}

readline.cursorTo(stream, x, y)[src]

Добавлена в: v0.7.7
  • stream <stream.Writable>
  • x <число>
  • y <число>

Метод readline.cursorTo() перемещает курсор в указанную позицию в заданном TTY stream.

readline.emitKeypressEvents(stream[, interface])[src]

Добавлен в: v0.7.7
  • stream <stream.Readable>
  • interface <readline.Interface>

Метод readline.emitKeypressEvents() заставляет заданный поток Readable начинать передавать события 'keypress' соответствующие полученному вводу.

Необязательно, interface указывает экземпляр readline.Interface для которого отключение автозаполнения происходит при обнаружении ввода, скопированного-вставленного.

Если stream является TTY, то он должен быть в режиме raw.

Этот метод автоматически вызывается любым экземпляром readline для своего input если input является терминалом. Закрытие экземпляра readline не останавливает input от отправки событий 'keypress'.

readline.emitKeypressEvents(process.stdin);
if (process.stdin.isTTY)
  process.stdin.setRawMode(true);

readline.moveCursor(stream, dx, dy)[src]

Добавлен в: v0.7.7
  • stream <stream.Writable>
  • dx <число>
  • dy <число>

Метод readline.moveCursor() перемещает курсор относительно его текущей позиции в заданном TTY stream.

Пример: Небольшая командная строка

Следующий пример иллюстрирует использование класса readline.Interface для реализации небольшой командной строки:

const readline = require('readline');
const rl = readline.createInterface({
  input: process.stdin,
  output: process.stdout,
  prompt: 'OHAI> '
});

rl.prompt();

rl.on('line', (line) => {
  switch (line.trim()) {
    case 'hello':
      console.log('world!');
      break;
    default:
      console.log(`Say what? I might have heard '${line.trim()}'`);
      break;
  }
  rl.prompt();
}).on('close', () => {
  console.log('Have a great day!');
  process.exit(0);
});

Пример: Чтение файла потока по строкам

Распространённый случай использования readline — это потребление файла ввода построчно. Самый простой способ сделать это — использовать API fs.ReadStream а также цикл for-await-of:

const fs = require('fs');
const readline = require('readline');

async function processLineByLine() {
  const fileStream = fs.createReadStream('input.txt');

  const rl = readline.createInterface({
    input: fileStream,
    crlfDelay: Infinity
  });
  // Note: we use the crlfDelay option to recognize all instances of CR LF
  // ('\r\n') in input.txt as a single line break.

  for await (const line of rl) {
    // Each line in input.txt will be successively available here as `line`.
    console.log(`Line from file: ${line}`);
  }
}

processLineByLine();

В качестве альтернативы можно использовать событие 'line':

const fs = require('fs');
const readline = require('readline');

const rl = readline.createInterface({
  input: fs.createReadStream('sample.txt'),
  crlfDelay: Infinity
});

rl.on('line', (line) => {
  console.log(`Line from file: ${line}`);
});

В настоящее время цикл for-await-of может быть немного медленнее. Если async / await поток и скорость имеют первостепенное значение, можно применить смешанный подход:

const { once } = require('events');
const { createReadStream } = require('fs');
const { createInterface } = require('readline');

(async function processLineByLine() {
  try {
    const rl = createInterface({
      input: createReadStream('big-file.txt'),
      crlfDelay: Infinity
    });

    rl.on('line', (line) => {
      // Process the line.
    });

    await once(rl, 'close');

    console.log('File processed.');
  } catch (err) {
    console.error(err);
  }
})();

© Joyent, Inc. and other Node contributors
Licensed under the MIT License.
Node.js is a trademark of Joyent, Inc. and is used with its permission.
We are not endorsed by or affiliated with Joyent.
https://nodejs.org/dist/latest-v10.x/docs/api/readline.html

Spec-Zone.ru

Настройки Оффлайн Что нового Помощь О нас
Spec-Zone .ru
спецификации, руководства, описания, API