This commit is contained in:
lenheart
2025-03-27 20:24:19 +08:00
parent 21f64fbd9e
commit f2992c2a86
214 changed files with 18814 additions and 316 deletions

View File

@@ -11,42 +11,149 @@
#include <asio/basic_socket_streambuf.hpp>
#include <iostream>
extern HSQUIRRELVM v;
extern std::recursive_mutex SqMtx;
static SQInteger CreateHttp(HSQUIRRELVM v)
{
const SQChar *Host;
sq_getstring(v, 2, &Host);
const SQChar *Sevice;
sq_getstring(v, 3, &Sevice);
const SQChar *Service;
sq_getstring(v, 3, &Service);
const SQChar *Content;
sq_getstring(v, 4, &Content);
asio::io_context ioContext;
asio::ip::tcp::resolver resolver(ioContext);
asio::ip::tcp::resolver::results_type endpoints = resolver.resolve(Host, Sevice);
asio::ip::tcp::socket socket(ioContext);
asio::connect(socket, endpoints);
std::string request = std::string(Content);
asio::write(socket, asio::buffer(request));
asio::streambuf response;
asio::error_code error;
asio::read(socket, response, error);
if (error != asio::error::eof)
try
{
throw asio::system_error(error);
sq_pushnull(v);
}
asio::io_context ioContext;
asio::ip::tcp::resolver resolver(ioContext);
auto endpoints = resolver.resolve(Host, Service);
asio::ip::tcp::socket socket(ioContext);
asio::connect(socket, endpoints);
// 发送HTTP请求假设Content包含完整请求
std::string request = Content;
asio::write(socket, asio::buffer(request));
// 读取响应改进建议解析Content-Length或分块传输
asio::streambuf response;
asio::error_code error;
while (asio::read(socket, response, asio::transfer_at_least(1), error))
{
}
std::istream responseStream(&response);
std::ostringstream oss;
oss << responseStream.rdbuf();
sq_pushstring(v, oss.str().c_str(), -1);
if (error && error != asio::error::eof)
{
throw asio::system_error(error);
}
// 将响应内容返回
std::istream responseStream(&response);
std::ostringstream oss;
oss << responseStream.rdbuf();
sq_pushstring(v, oss.str().c_str(), -1);
return 1;
}
catch (const std::exception &e)
{
return sq_throwerror(v, e.what()); // 返回错误信息
}
catch (...)
{
return sq_throwerror(v, _SC("Unknown error occurred"));
}
}
void handle_client(tcp::socket *socket, HSQOBJECT HttpServerObject)
{
try
{
// 读取请求
asio::streambuf request_buf;
asio::read_until(*socket, request_buf, "\r\n\r\n");
// 提取请求内容
std::string request_data = asio::buffer_cast<const char *>(request_buf.data());
// 调用回调函数(需处理 Squirrel VM 上下文)
std::cout << request_data << std::endl;
std::lock_guard<std::recursive_mutex> lock(SqMtx);
// 执行虚拟机Main函数
SQInteger top = sq_gettop(v); // saves the stack size before the call
sq_pushobject(v, HttpServerObject);
sq_pushstring(v, _SC("Event"), -1);
if (SQ_SUCCEEDED(sq_get(v, -2)))
{
sq_pushobject(v, HttpServerObject);
sq_pushuserpointer(v, socket);
sq_pushstring(v, request_data.c_str(), -1);
sq_call(v, 3, SQFalse, SQTrue); // calls the function
}
sq_settop(v, top); // restores the original stack size
}
catch (std::exception &e)
{
std::cerr << "Error: " << e.what() << std::endl;
}
}
// 启动 HTTP 服务
void start_server(const std::string &host, const std::string &port, HSQOBJECT HttpServerObject)
{
asio::io_context io_context;
tcp::acceptor acceptor(io_context, tcp::endpoint(asio::ip::make_address(host), std::stoi(port)));
std::cout << "Server listening on " << host << ":" << port << std::endl;
while (true)
{
tcp::socket *socket = new tcp::socket(io_context);
acceptor.accept(*socket);
std::cout << "收到信息" << std::endl;
// 传递 HttpServerObject 到 handle_client
std::thread(handle_client, std::move(socket), HttpServerObject).detach();
}
}
static SQInteger CreateHttpServer(HSQUIRRELVM v)
{
const SQChar *host, *port;
sq_getstring(v, 2, &host);
sq_getstring(v, 3, &port);
HSQOBJECT HttpServerObject;
sq_getstackobj(v, 4, &HttpServerObject);
// 必须增加一次引用一会记得删除 不然这个函数会被释放
sq_addref(v, &HttpServerObject);
try
{
std::thread server_thread(start_server, host, port, HttpServerObject);
server_thread.detach();
sq_pushbool(v, true);
}
catch (...)
{
sq_pushbool(v, false);
}
return 1;
}
static SQInteger HttpServerResponse_Write(HSQUIRRELVM v)
{
SQUserPointer P;
sq_getuserpointer(v, 2, &P);
tcp::socket *socket = (tcp::socket *)P;
const SQChar *Content;
sq_getstring(v, 3, &Content);
try
{
std::string response = Content;
asio::write(*socket, asio::buffer(response));
socket->close();
delete socket;
return 0;
}
catch (...)
{
socket->close();
delete socket;
return sq_throwerror(v, _SC("Unknown error occurred"));
}
}
static SQInteger register_Dio_func(HSQUIRRELVM v, SQFUNCTION f, const char *fname)
{
sq_pushroottable(v);
@@ -60,4 +167,8 @@ static void RegisterDio(HSQUIRRELVM v)
{
// 创建Http
register_Dio_func(v, CreateHttp, _SC("Sq_CreateHttp"));
// 创建HttpServer
register_Dio_func(v, CreateHttpServer, _SC("Sq_CreateHttpServer"));
// 回应HttpServer响应体
register_Dio_func(v, HttpServerResponse_Write, _SC("Sq_HttpServerResponse_Write"));
}