Updated HTTP.lua, added headers argument to websocket

This commit is contained in:
Alessandro Proto 2023-01-17 19:22:44 +01:00
parent b06ab003e0
commit 1443c8a49d
3 changed files with 92 additions and 8 deletions

View file

@ -2,6 +2,24 @@ local http = require("http")
local event = require("event") local event = require("event")
local expect = require("expect").expect local expect = require("expect").expect
local WebSocketHandle = {}
function WebSocketHandle:close()
self:closeAsync()
local _, id
repeat
_, id = event.pull("websocket_close")
until id == self.requestId
end
function WebSocketHandle:receive()
local _, id, par
repeat
_, id, par = event.pull("websocket_message")
until id == self.requestId
return par
end
function http.request(url, body, headers, options) function http.request(url, body, headers, options)
expect(1, url, "string") expect(1, url, "string")
expect(2, body, "string", "nil") expect(2, body, "string", "nil")
@ -37,7 +55,38 @@ function http.post(url, body, headers, options)
expect(1, url, "string") expect(1, url, "string")
expect(2, body, "string", "nil") expect(2, body, "string", "nil")
expect(3, headers, "table", "nil") expect(3, headers, "table", "nil")
expect(4, options, "table", "nil") expect(4, options, "table", "nil")
return http.request(url, body, headers, options) return http.request(url, body, headers, options)
end end
local function buildWebsocketHandle(requestId, handle)
handle.requestId = requestId
local metatable = getmetatable(handle) or {}
metatable.__index = WebSocketHandle
setmetatable(handle, metatable)
return handle
end
function http.websocket(url, headers)
expect(1, url, "string")
expect(2, headers, "table", "nil")
if not http.checkURL(url) then
return nil, "Invalid URL"
end
local requestId = http.websocketAsync(url, headers)
local ev, id, par
repeat
ev, id, par = event.pull("websocket_connect", "websocket_failure")
until id == requestId
if ev == "http_failure" then
return nil, par
end
return buildWebsocketHandle(requestId, par)
end

View file

@ -56,14 +56,14 @@ class WebSocketHandle : IHandle
{ {
var L = Lua.FromIntPtr(state); var L = Lua.FromIntPtr(state);
var data = L.CheckString(2); var data = L.CheckBuffer(2);
var h = GetHandle(L, false); var h = GetHandle(L, false);
if (h is null || h._client.State == WebSocketState.Closed) if (h is null || h._client.State == WebSocketState.Closed)
L.Error("connection is closed"); L.Error("connection is closed");
h._client.SendAsync(Encoding.ASCII.GetBytes(data), WebSocketMessageType.Text, true, CancellationToken.None); h._client.SendAsync(data, WebSocketMessageType.Text, true, CancellationToken.None);
return 0; return 0;
} }

View file

@ -10,8 +10,6 @@ using System.Net.Http;
using System.Net.WebSockets; using System.Net.WebSockets;
using System.Text; using System.Text;
using System.Threading; using System.Threading;
using System.Threading.Tasks;
using static System.Runtime.InteropServices.JavaScript.JSType;
namespace Capy64.LuaRuntime.Libraries; namespace Capy64.LuaRuntime.Libraries;
#nullable enable #nullable enable
@ -21,6 +19,8 @@ public class HTTP : IPlugin
private static HttpClient _httpClient; private static HttpClient _httpClient;
private static long _requestId; private static long _requestId;
public static readonly string UserAgent = $"Capy64/{Capy64.Version}";
private readonly IConfiguration _configuration; private readonly IConfiguration _configuration;
private readonly LuaRegister[] HttpLib = new LuaRegister[] private readonly LuaRegister[] HttpLib = new LuaRegister[]
{ {
@ -46,7 +46,7 @@ public class HTTP : IPlugin
_game = game; _game = game;
_requestId = 0; _requestId = 0;
_httpClient = new(); _httpClient = new();
_httpClient.DefaultRequestHeaders.Add("User-Agent", $"Capy64/{Capy64.Version}"); _httpClient.DefaultRequestHeaders.Add("User-Agent", UserAgent);
_configuration = configuration; _configuration = configuration;
} }
@ -261,6 +261,41 @@ public class HTTP : IPlugin
var requestId = _requestId++; var requestId = _requestId++;
var wsClient = new ClientWebSocket(); var wsClient = new ClientWebSocket();
wsClient.Options.SetRequestHeader("User-Agent", UserAgent);
if (L.IsTable(2)) // headers
{
L.PushCopy(2);
L.PushNil();
while (L.Next(-2))
{
L.PushCopy(-2);
var k = L.CheckString(-1);
if (L.IsStringOrNumber(-2))
{
var v = L.ToString(-2);
wsClient.Options.SetRequestHeader(k, v);
}
else if (L.IsNil(-2))
{
wsClient.Options.SetRequestHeader(k, null);
}
else
{
L.ArgumentError(3, "string, number or nil expected, got " + L.TypeName(L.Type(-2)) + " in field " + k);
}
L.Pop(2);
}
L.Pop(1);
}
var connectTask = wsClient.ConnectAsync(uri, CancellationToken.None); var connectTask = wsClient.ConnectAsync(uri, CancellationToken.None);
connectTask.ContinueWith(async task => connectTask.ContinueWith(async task =>
{ {
@ -301,7 +336,7 @@ public class HTTP : IPlugin
builder.Append(data); builder.Append(data);
} }
if(result.EndOfMessage) if (result.EndOfMessage)
{ {
_game.LuaRuntime.PushEvent("websocket_message", requestId, builder.ToString()); _game.LuaRuntime.PushEvent("websocket_message", requestId, builder.ToString());
builder.Clear(); builder.Clear();