diff --git a/packages/node/binding.node b/packages/node/binding.node index 3498353..c443471 100755 Binary files a/packages/node/binding.node and b/packages/node/binding.node differ diff --git a/packages/node/modules/picoev b/packages/node/modules/picoev index e1c5348..f700fc7 160000 --- a/packages/node/modules/picoev +++ b/packages/node/modules/picoev @@ -1 +1 @@ -Subproject commit e1c534812824886b71b017dab0be5972764dc280 +Subproject commit f700fc70ab8b8c111ad9cd37b9e971638fcc6edc diff --git a/packages/node/modules/picohttpparser b/packages/node/modules/picohttpparser index 798ecad..7ef5440 160000 --- a/packages/node/modules/picohttpparser +++ b/packages/node/modules/picohttpparser @@ -1 +1 @@ -Subproject commit 798ecadd5bdd4acc28fbaed805d91f1aab7682f8 +Subproject commit 7ef54404050f1cdbac73d4dcc6d1c1c4a3aa7743 diff --git a/packages/node/modules/server/server.v b/packages/node/modules/server/server.v index c9c0904..9fc578a 100644 --- a/packages/node/modules/server/server.v +++ b/packages/node/modules/server/server.v @@ -10,33 +10,55 @@ fn callback(data voidptr, req picohttpparser.Request, mut res picohttpparser.Res eprintln('Method not allowed: ${req.method}') res.status(405) res.header('Content-Type', 'application/json') - res.header('Connection', 'close') + res.header('Connection', if req.client_wants_keep_alive() { 'keep-alive' } else { 'close' }) res.body('{"error":"Only POST method is allowed"}') + if res.end() < 0 { + eprintln('Failed to send error response') + } return } - // With the new streaming API, the body is already accumulated in req.body - // by the time this callback is called - if req.body.len == 0 { + // Get the body reader if available + mut body := '' + if mut br := req.get_body_reader() { + body_bytes := br.read_all() or { + eprintln('Failed to read body: ${err}') + res.status(400) + res.header('Content-Type', 'application/json') + res.header('Connection', 'close') + res.body('{"error":"Failed to read request body"}') + if res.end() < 0 { + eprintln('Failed to send error response') + } + return + } + body = body_bytes.bytestr() + } + + if body.len == 0 { eprintln('No body provided') res.status(400) res.header('Content-Type', 'application/json') - res.header('Connection', 'close') + res.header('Connection', if req.client_wants_keep_alive() { 'keep-alive' } else { 'close' }) res.body('{"error":"No body provided"}') + if res.end() < 0 { + eprintln('Failed to send error response') + } return } - eprintln('Received complete body: ${req.body} ${req.body.len}') + eprintln('Received complete body: ${body} ${body.len}') res.status(200) res.header('Content-Type', 'text/plain') - res.header('Connection', 'close') - res.body(req.body) - eprintln('Response prepared') + res.header('Connection', if req.client_wants_keep_alive() { 'keep-alive' } else { 'close' }) + res.body(body) + if res.end() < 0 { + eprintln('Failed to send response') + } } // start creates and starts a new HTTP server on the specified port pub fn start(port int) ! { - eprintln('Starting server on port ${port}') mut s := picoev.new( port: port, cb: callback, @@ -45,6 +67,5 @@ pub fn start(port int) ! { max_write: 8192 )! - eprintln('Server initialized, starting event loop') s.serve() } diff --git a/packages/node/modules/socket/socket.v b/packages/node/modules/socket/socket.v new file mode 100644 index 0000000..31b619e --- /dev/null +++ b/packages/node/modules/socket/socket.v @@ -0,0 +1,33 @@ +module socket + +$if !windows { + #include +} + +// read_socket reads from a socket into a buffer +@[inline] +pub fn read_socket(fd int, buffer &u8, max_len int, offset int) int { + // use `recv` instead of `read` for windows compatibility + return unsafe { C.recv(fd, buffer + offset, max_len - offset, 0) } +} + +// is_fatal_error returns true if the socket error is fatal +@[inline] +pub fn is_fatal_error(fd int) bool { + if C.errno == C.EAGAIN { + // try again later + return false + } + $if windows { + if C.errno == C.WSAEWOULDBLOCK { + // try again later + return false + } + } $else { + if C.errno == C.EWOULDBLOCK { + // try again later + return false + } + } + return true +} \ No newline at end of file