Сокеты-сопрограммы и неблокирующий TCP
Используйте ngx.socket.tcp для асинхронных подключений к серверной части в content_by_lua.
«Сокеты-сопрограммы и неблокирующий TCP» — бесплатный урок Lua Academy на CoddyKit. Это урок 3 из 4. Ты можешь прочитать весь урок бесплатно ниже — а потом практиковать его прямо в браузере с встроенным редактором кода и ИИ-репетитором 24/7. Это часть пути обучения Lua Academy, и твой прогресс синхронизируется между веб-версией и приложением CoddyKit. Курс Lua Academy содержит 4 уроков всего.
Что такое косокеты
Косокеты OpenResty — это неблокирующие TCP/UDP-сокеты, интегрированные с циклом обработки событий Nginx. Во время ожидания данных они приостанавливают сопрограмму, освобождая рабочий процесс для обработки других запросов.
Создание TCP-косокета
Используйте ngx.socket.tcp(), чтобы создать косокет. Операции подключения, отправки и получения автоматически приостанавливаются, когда ввод-вывод может заблокироваться.
-- content_by_lua_block
local sock = ngx.socket.tcp()
local ok, err = sock:connect("redis.local", 6379)
if not ok then
ngx.log(ngx.ERR, "Connect failed: ", err)
return ngx.exit(500)
endОтправка данных
sock:send(data) отправляет строку. Возвращает число отправленных байтов или nil + ошибку.
local bytes, err = sock:send("PING\r\n")
if not bytes then
ngx.log(ngx.ERR, "Send error: ", err)
endПолучение данных
sock:receive(pattern) считывает данные. Шаблоны: "*l" считывает строку, "*a" считывает всё до закрытия соединения, а число считывает ровно N байтов.
local data, err = sock:receive("*l")
if not data then
ngx.log(ngx.ERR, "Receive error: ", err)
return ngx.exit(500)
end
ngx.say("Response: " .. data)Установка времени ожидания
Задайте время ожидания для подключения, отправки и получения данных, чтобы предотвратить зависание.
sock:settimeout(1000) -- 1 second timeout
-- or separate timeouts:
sock:settimeouts(1000, 5000, 5000) -- connect, send, receive (ms)Пул соединений
sock:setkeepalive(timeout, pool_size) помещает сокет обратно в пул для повторного использования. Это важно для производительности Redis/MySQL.
sock:setkeepalive(60000, 100) -- 60s timeout, pool size 100Отправка HTTP-запроса
Реализуйте простой запрос GET по HTTP/1.0 с использованием косокета.
local function httpGet(host, path)
local sock = ngx.socket.tcp()
sock:connect(host, 80)
sock:send("GET " .. path .. " HTTP/1.0\r\nHost: " .. host .. "\r\n\r\n")
local resp = sock:receive("*a")
sock:close()
return resp
endUDP-косокет
ngx.socket.udp() создаёт UDP-косокет. Он полезен для передачи метрик statsd.
local udp = ngx.socket.udp()
udp:setpeername("statsd.local", 8125)
udp:send("requests:1|c")Шаблон обработки ошибок
Все методы косокетов следуют соглашению Lua: при сбое возвращаются nil и строка ошибки. Всегда проверяйте оба возвращаемых значения.
Ограничения косокетов
Косокеты нельзя использовать в: init_by_lua, set_by_lua, header_filter_by_lua. Используйте их только в фазах содержимого, доступа и переписывания.
Сравнение производительности
Косокеты обеспечивают такую же пропускную способность, как необёрнутый код на C с использованием epoll, поскольку напрямую используют механизм ввода-вывода Nginx. Дополнительные затраты на потоки или процессы отсутствуют.
Вопрос о косокетах
Что происходит, когда косокет ожидает данные от медленного сервера?
Итоги: косокеты и неблокирующий TCP
Косокеты OpenResty обеспечивают неблокирующий TCP/UDP и приостанавливают выполнение во время ввода-вывода, что позволяет поддерживать высокую степень параллелизма. Используйте setkeepalive для организации пула соединений. Устанавливайте время ожидания, чтобы избежать зависания. Косокеты доступны только в фазах содержимого, доступа и переписывания.
Часто задаваемые вопросы
Урок «Сокеты-сопрограммы и неблокирующий TCP» бесплатный?
Да — полный текст урока «Сокеты-сопрограммы и неблокирующий TCP» бесплатно доступен здесь в веб-версии. Чтобы практиковать его интерактивно (встроенный редактор кода и ИИ-репетитор 24/7) и разблокировать остальной курс Lua Academy, подпишись на CoddyKit PRO. Курс Lua Academy содержит 4 уроков всего.
Чему я научусь в уроке «Сокеты-сопрограммы и неблокирующий TCP»?
Используйте ngx.socket.tcp для асинхронных подключений к серверной части в content_by_lua. Ты практикуешь Lua Academy с помощью реального кода, который запускаешь прямо в браузере, и ИИ-репетитор 24/7 отвечает на твои вопросы во время урока.
Нужен ли мне опыт, чтобы начать Lua Academy?
Предыдущий опыт не требуется. Lua Academy на CoddyKit структурирован для всех уровней — от новичков до продвинутых, поэтому ты можешь начать отсюда или с самого начала и учиться в своем темпе. Это урок 3 из 4.
Сколько времени занимает урок «Сокеты-сопрограммы и неблокирующий TCP»?
Большинство уроков CoddyKit занимают около 5–10 минут. Каждый из них компактный и интерактивный, поэтому ты постоянно делаешь прогресс и продолжаешь с того же места в веб-версии и приложении.
Можно ли писать и запускать код в этом уроке Lua Academy?
Да. Каждый урок Lua Academy включает встроенный редактор кода, поэтому ты пишешь и запускаешь реальный код прямо в браузере и получаешь моментальную обратную связь от AI — локальная установка не требуется.
Все уроки этого курса
- Архитектура OpenResty
- Обработка HTTP-запросов в Lua
- Сокеты-сопрограммы и неблокирующий TCP
- Словари общей памяти