Чтение больших файлов построчно в Node.js: эффективные методы
Пройдите тест, узнайте какой профессии подходите
Быстрый ответ
const readline = require('readline');
const fs = require('fs');
const lineReader = readline.createInterface({
input: fs.createReadStream('file.txt')
});
lineReader.on('line', (line) => console.log(line));
В примере выше демонстрируется, как за счет возможностей модулей readline
и fs
реализовать потоковую обработку текстового файла на Node.js. Пройдясь по каждой его строке, мы выводим ее на экран. Вместо 'file.txt'
нужно указать актуальный путь к файлу.
Правильная обработка переносов строк и больших файлов
Работа с различными типами переносов строк
При обработке файлов с разнообразными форматами окончания строк либо работы с потоками данных выбор значения crlfDelay
как Infinity
оказывается особенно полезным. Это помогает интерпретировать каждую последовательность символов \r\n
как единый перенос строки.
const lineReader = readline.createInterface({
input: fs.createReadStream('file.txt'),
crlfDelay: Infinity
});
Асинхронное чтение для эффективной обработки больших файлов
Объемные файлы при неправильной обработке могут привести к исчерпанию памяти. Для избежания этого проблему решает асинхронная обработка каждой строки файла с помощью асинхронных возможностей потоков Node.js.
lineReader.on('line', async (line) => {
await processLine(line); // функция processLine должна быть максимально эффективна
});
Обеспечение чтения до последней строки
Для гарантированного прочтения каждой строки из большого файла, включая последнюю, которая может и не завершаться переносом строки, следует использовать событие close
.
lineReader.on('close', () => {
console.log('Весь файл прочитан, от первой до последней строки.');
});
Современный метод итерации в Node.js
В Node.js версии 11.4 и более поздних встроен цикл for await...of
, весьма изящно решающий задачу итерации по строкам файла.
const rl = readline.createInterface({
input: fs.createReadStream('file.txt'),
crlfDelay: Infinity
});
for await (const line of rl) {
console.log(`Получена строка: ${line}`);
}
Визуализация
Представить чтение файла построчно с помощью Node.js можно так:
📜 == Река (Файл)
🚡 == Гондола (Поток)
Каждая строка файла — это проезд гондолы через реку:
const readline = require('readline');
const fs = require('fs');
const rl = readline.createInterface({
input: fs.createReadStream('file.txt')
});
rl.on('line', (line) => {
console.log(`Гондола доставляет: ${line}`);
});
Этот процесс можно схематически изобразить:
🚡 Старт | 📜 Строка 1 | 🚡 Финиш
🚡 Старт | 📜 Строка 2 | 🚡 Финиш
// и так до последней строки
Каждый проезд гондолы — это активация события .on('line', ...)
, считывающего строку файла, что делает процесс крайне эффективным.
Решение распространенных проблем
Важность выбора правильной текстовой кодировки
Указание правильной кодировки, например, 'utf-8'
, избавляет от проблем с неправильным отображением спецсимволов или текста.
const lineReader = readline.createInterface({
input: fs.createReadStream('file.txt', { encoding: 'utf-8' }) // чтобы говорить на одном языке
});
Приоритет нативных модулей
Несмотря на то что readline
предпочтительнее использовать, в специфических случаях могут пригодиться пакеты вроде Lazy
и event-stream
.
Обязательная обработка ошибок
При настройке интерфейса readline
не забывайте об обработке ошибок:
lineReader.on('error', (error) => {
console.error(`Упс! Произошла ошибка: ${error}`);
});
Возможность синхронного чтения
Вопреки эффективности асинхронного чтения, в более простых случаях может быть уместно использовать fs.readFileSync
. Это позволяет разделить текст на строки для последующей обработки:
const allLines = fs.readFileSync('file.txt', { encoding: 'utf-8' }).split(/\r?\n/);
allLines.forEach((line) => {
console.log(line); // строки, как партнеры в танце
});
Полезные материалы
- File system | Документация Node.js v21.6.1 — официальная документация по Node.js по
fs.createReadStream
. - Readline | Документация Node.js v21.6.1 — подробная инструкция из документации Node.js по использованию
readline
для построчного чтения файлов. - Understanding Streams in Node.js – NodeSource — статья о теории и практике работы с потоками в Node.js.
- javascript – Чтение файла по одной строке в node.js? – Stack Overflow — обсуждение на Stackoverflow, где можно найти практические решения и мнения сообщества разработчиков.
- line-reader – npm — страница npm-библиотеки
line-reader
, предназначенной для построчного чтения файлов в Node.js. - event-stream – npm — страница npm с
event-stream
, которая помогает в обработке больших файлов в Node.js без ошибок. - Лучшие практики и советы по Node.js от экспертов | Toptal® — сборник наилучших практик и советов для разработчиков на Node.js.