Как отправить запрос на какой-либо сайт из сервера, работающего на NodeJS?
Обычно NodeJS создают для того чтобы «ПРИНИМАТЬ ЗАПРОСЫ» и «ОТПРАВЛЯТЬ ОТВЕТЫ». И в таком случае NodeJS работает именно как «СЕРВЕР«.
Но в то же время NodeJS может работать и как «КЛИЕНТ«, как обычный пользовательский агент, который сам рассылает запросы вместо того, чтобы на них отвечать.
Получается, что наш NodeJS в одно и тоже время может быть и «КЛИЕНТОМ» и «СЕРВЕРОМ«.
Редактор кода VSC и ОС Windows
Для простого понимания процесса работы NodeJS в роли «КЛИЕНТА» предлагаю в операционной системе Windows установить редактор VSC.
В терминале редактора мы сразу будем вызывать наш код.
NodeJS и ОС Windows
Также нам нужно установить NodeJS с официального сайта проекта в операционную систему Windows.
Это можно делать и на серверных ОС, но нам для наглядности будет удобнее всё делать в графической ОС.
Проверка существования NodeJS
Когда NodeJS будет установлен, тогда в редакторе Visual Studio Code мы можем перейти на вкладку «Terminal» (Терминал)

В выпадающем списке нам нужно нажать на «New Terminal» (Новый терминал)

Окно разделится на две части и увидим классическую командную строку Windows внутри редактора VSC.
Проверяем существование и версию NodeJS командой:
node -v
Если NodeJS существует, то мы увидим что-то подобное:

В нашем случае установлена самая последняя версия для ОС Windows 7. Более свежие версии Windows 7 не поддерживает.
Подключение к NodeJS через терминал
Чтобы подключиться к консоли самого NodeJS нужно написать команду в терминале:
node
После этого мы увидим характерную для NodeJS информацию и прямоугольный указатель белого цвета для ввода.

С этого момента мы имеем активную консоль для ввода JavaScript синтаксиса. Сюда нужно будет вставлять наш код для тестирования.
Решение задачи
В NodeJS встроены стандартные модули, которые помогают отправлять HTTP-запросы на различные сайты:
- Модуль http — https://nodejs.org/api/http.html
- Модуль http2 — https://nodejs.org/api/http2.html
- Модуль https — https://nodejs.org/api/https.html
Мы возьмём за основу модуль «https«. HTTPS — это протокол HTTP поверх TLS/SSL. В NodeJS это реализовано в виде отдельного модуля.
Нас интересуют два производства (два варианта использования метода request):
- https.request(options[, callback])
- https.request(url[, options][, callback])
Оба они принимают некоторый объект настроек — «options«.
Ключи объекта «options» могут быть следующими:
- agent
- auth
- createConnection
- defaultPort
- family
- headers
- hints
- host
- hostname
- insecureHTTPParser
- localAddress
- localPort
- lookup
- maxHeaderSize
- method
- path
- port
- protocol
- setHost
- socketPath
- timeout
- signal
В нашем случае по умолчанию будут заданы следующие ключи и их значения:
- Ключ protocol, значение ‘https:’
- Ключ port, значение 443
- Ключ agent, значение https.globalAgent
С этого момента, если мы хотим просто получить содержимое какой-нибудь страницы сайта, работающего на HTTPS, то мы можем просто указать его адрес.
let req44 = https.request('https://s.efim360.ru')
В таком виде будет создан сам ОБЪЕКТ ЗАПРОСА в среде выполнения кода с NodeJS. Мы попытемся совершить запрос к главной странице сайта ‘https://s.efim360.ru‘. Она заранее подготовлена и отвечает простой строкой ‘Hello World‘.
Но сейчас этот запрос НЕ ВЫЗВАН (НЕ ОТПРАВЛЕН). Мы его ещё формируем.
Метод request() может принимать два параметра. Второй из них — это коллбек. Мы ещё не написали функцию обратного вызова, после того как сервер сайта вернёт нам ОТВЕТ. Что мы будем делать с ОТВЕТОМ? Как мы будем его читать? А что нам нужно прочитать из ответа? Где в ответе сами данные?
Функция обратного вызова ожидает получить ОБЪЕКТ ОТВЕТА. Поэтому мы должны с ним провзаимодействовать.
Давайте начнём её писать:
let res44 = (res) => {}
В теле функции нам нужна переменная, которая будет накапливать строку данных из ОТВЕТА.
Назовём её «resStr«. И тут очень важный момент. Мы не должны объявлять её без типа данных. Если это сделать, то может появиться паразитная строка ‘undefined’ с которой будет начинаться наша строка данных. Поэтому мы явно укажем, что это СТРОКА (хоть и пустая)
let res44 = (res) => {
let resStr = ''
}
Теперь нам нужно написать два обработчика СОБЫТИЙ ОТВЕТА.
Нас интересуют события:
- процесс получения данных — событие «data«
- завершение получения данных — событие «end«
То есть мы будем что-то делать, когда данные будут приниматься, и будем что-то делать, когда весь приём нужных нам данных завершится.
Из стандарта
Во время события ‘response‘ (ответ) можно добавить слушателей к ОБЪЕКТУ ОТВЕТА; особенно для прослушивания события ‘data‘ (данные).
Если обработчик ответа ‘response‘ не добавлен, ответ будет полностью отброшен. Однако, если добавлен обработчик события ‘response‘, то данные из ОБЪЕКТА ОТВЕТА должны быть использованы либо путем вызова response.read() всякий раз, когда есть «читаемое» событие ‘readable‘, либо путем добавления обработчика события «данных» — ‘data‘, или вызвав метод .resume(). Пока данные не будут использованы, событие ‘end‘ (конец) не сработает. Кроме того, пока данные не будут прочитаны, они будут потреблять память, что в конечном итоге может привести к ошибке ‘process out of memory’ (процессу не хватает памяти).
Для обратной совместимости ОБЪЕКТ ОТВЕТА res будет выдавать событие ошибки ‘error‘ только в том случае, если зарегистрирован прослушиватель события ошибки ‘error‘.
Node.js не проверяет, равны ли Content-Length и длина переданного тела.
Допишем наши слушатели событий для ОБЪЕКТА ОТВЕТА:
let res44 = (res) => { let resStr = '' // переменная для хранения данных из ответа res.on('data', (data) => { resStr += data; }); res.on('end', () => { console.log(`Строка ответа: ${resStr}`) // вывести в консоль данные, когда ОТВЕТ будет готов }); res.on('error', (e) => { console.error(`Ошибка ответа: ${e.message}`) }); }
Теперь можно добавить обработку ошибки для нашего ЗАПРОСА
req44.on('error', (e) => { console.error(`Ошибка ЗАПРОСА: ${e.message}`) });
Теперь можно ВЫЗВАТЬ наш ЗАПРОС:
req44.end()
Информация
Добавляет функцию слушателя в конец массива слушателей для события с именем eventName. Никаких проверок, чтобы увидеть, был ли уже добавлен прослушиватель, не делается. Множественные вызовы, передающие одну и ту же комбинацию eventName и прослушивателя, приведут к тому, что прослушиватель будет добавлен и вызван несколько раз.
Весь код
ВНИМАНИЕ!!!
Для терминала NodeJS не должно быть пустых строк между участками кода, потому что они будут восприняты как разрыв и всё сломается!!!
Пишите БЕЗ ПУСТЫХ СТРОК
const https = require(‘node:https’);
let res44 = (res) => {
let resStr = »;
res.on(‘data’, (data) => {
resStr += data;
});
res.on(‘end’, () => {
console.log(`Строка—данные ОТВЕТА: ${resStr}`)
});
res.on(‘error’, (e) => {
console.error(`Ошибка ОТВЕТА: ${e.message}`)
});
};
let req44 = https.request(‘https://s.efim360.ru’, res44);
req44.on(‘error’, (e) => {
console.error(`Ошибка ЗАПРОСА: ${e.message}`)
});
req44.end();
Точки с запятыми проставляются на случай превращения многострочного кода в однострочный.>
Информационные ссылки
Стандарт NodeJS — https://nodejs.org/api/
Стандарт NodeJS — Модуль HTTPS — Метод request() — Синтаксис 1 — https://nodejs.org/api/https.html#httpsrequestoptions-callback
Стандарт NodeJS — Модуль HTTPS — Метод request() — Синтаксис 2 — https://nodejs.org/api/https.html#httpsrequesturl-options-callback
Стандарт NodeJS — Модуль Events (События) — https://nodejs.org/api/events.html
Стандарт NodeJS — Слушатель событий ON — https://nodejs.org/api/events.html#emitteroneventname-listener