diff options
Diffstat (limited to 'src/server.zig')
| -rw-r--r-- | src/server.zig | 71 |
1 files changed, 71 insertions, 0 deletions
diff --git a/src/server.zig b/src/server.zig new file mode 100644 index 0000000..184af92 --- /dev/null +++ b/src/server.zig @@ -0,0 +1,71 @@ +const std = @import("std"); +const log = std.log.scoped(.server); + +const routes = @import("routes/root.zig"); +const Storage = @import("storage/root.zig"); +const config = @import("config"); + +const Self = @This(); + +storage: Storage = undefined, +net_server: std.net.Server = undefined, +pool: std.Thread.Pool = undefined, + +pub fn init( + self: *Self, + address: std.net.Address, + allocator: std.mem.Allocator, +) !void { + self.storage = try .init(allocator); + self.net_server = try address.listen(.{ .reuse_address = true }); + try self.pool.init(.{ .allocator = allocator }); + log.info("listing on {f}", .{address}); + + if (comptime config.disable_auth) { + log.warn("authentication is disabled", .{}); + } +} + +pub fn run(self: *Self, allocator: std.mem.Allocator) void { + while (true) { + const connection = self.net_server.accept() catch |err| { + log.err("error: {}", .{err}); + continue; + }; + + self.pool.spawn(handle_connection, .{self, allocator, connection}) catch |err| { + std.log.err("failed to spawn thread: {}", .{err}); + }; + } +} + +fn handle_connection( + self: *Self, + allocator: std.mem.Allocator, + connection: std.net.Server.Connection, +) void { + defer connection.stream.close(); + + var read_buf: [1024 * 8]u8 = undefined; + var write_buf: [1024 * 8]u8 = undefined; + var reader = connection.stream.reader(&read_buf); + var writer = connection.stream.writer(&write_buf); + var http_server = std.http.Server.init(reader.interface(), &writer.interface); + + var request = http_server.receiveHead() catch return; + log.info("{s} {s}", .{ + std.enums.tagName(std.http.Method, request.head.method) orelse "<unknown>", + request.head.target, + }); + + const handler_info = routes.get(request.head.target); + handler_info.handle(&request, &self.storage, allocator) catch |err| { + std.log.err("{}", .{err}); + }; +} + +pub fn deinit(self: *Self) void { + log.info("shutdown", .{}); + self.net_server.deinit(); + self.storage.deinit(); +} |