milestone 8: web server, rest api, sse, auth, metrics and static assets

This commit is contained in:
2026-08-02 00:54:13 +02:00
parent a8092bb1b9
commit 5253c47303
59 changed files with 19640 additions and 150 deletions
+16 -13
View File
@@ -31,6 +31,7 @@ const dns_cache = @import("../cache/dns_cache.zig");
const forward_zones = @import("../local/forward_zones.zig");
const handler = @import("handler.zig");
const header = @import("../dns/header.zig");
const local_tables = @import("local_tables.zig");
const logger_mod = @import("../storage/logger.zig");
const manager = @import("../filter/manager.zig");
const matcher = @import("../filter/matcher.zig");
@@ -39,6 +40,7 @@ const model = @import("../config/model.zig");
const name = @import("../dns/name.zig");
const packet = @import("../dns/packet.zig");
const pause = @import("pause.zig");
const query_sink = @import("query_sink.zig");
const question = @import("../dns/question.zig");
const rate_limiter = @import("rate_limiter.zig");
const record = @import("../dns/record.zig");
@@ -59,9 +61,6 @@ const testing = std.testing;
/// enough that a broken server fails the run instead of hanging it.
const budget: std.Io.Timeout = .{ .duration = .{ .raw = .fromSeconds(5), .clock = .awake } };
const empty_records: records.Records = .empty;
const empty_zones: forward_zones.Zones = .empty;
/// A five-second TTL makes the blocking answer's TTL unmistakable next to the
/// upstream's 300.
const blocking: response.Options = .{ .mode = .zero, .ttl = 5 };
@@ -84,8 +83,6 @@ fn baseHandler(client: transport.Client) handler.Handler {
.upstream = client,
.blocking = blocking,
.forward_read_timeout = forward_timeout,
.records = &empty_records,
.zones = &empty_zones,
};
}
@@ -316,11 +313,12 @@ test "S7 case 1: a blocked domain is answered with the zero address and logged"
var queue_buf: [log_queue_len]logger_mod.Entry = undefined;
var lg: logger_mod.Logger = .init(.{}, &queue_buf);
var sink: query_sink.QuerySink = .init(&lg, null);
var fake: FakeUpstream = .{ .reply = .a };
var h = baseHandler(fake.client());
h.manager = &mgr;
h.logger = ≶
h.sink = &sink;
var loop = try Loop.bind(gpa, io, &h);
defer loop.stop(gpa, io);
@@ -409,7 +407,8 @@ test "S7 case 3: a local record answers authoritatively without an upstream" {
var fake: FakeUpstream = .{ .reply = .a };
var h = baseHandler(fake.client());
h.records = &table;
var tables: local_tables.LocalTables = .{ .records = table };
h.local_tables = &tables;
var loop = try Loop.bind(gpa, io, &h);
defer loop.stop(gpa, io);
@@ -477,7 +476,8 @@ test "S7 case 4: a forward zone reaches its resolver, bypasses the blocklist and
var fake: FakeUpstream = .{ .reply = .a };
var h = baseHandler(fake.client());
h.manager = &mgr;
h.zones = &zones;
var tables: local_tables.LocalTables = .{ .zones = zones };
h.local_tables = &tables;
h.cache = &cache;
h.negative_ttl_max = 3600;
@@ -528,12 +528,13 @@ test "S7 case 5: a cached answer comes back with a fresh id, an aged ttl and a l
var queue_buf: [log_queue_len]logger_mod.Entry = undefined;
var lg: logger_mod.Logger = .init(.{}, &queue_buf);
var sink: query_sink.QuerySink = .init(&lg, null);
var fake: FakeUpstream = .{ .reply = .a };
var h = baseHandler(fake.client());
h.cache = &cache;
h.negative_ttl_max = 3600;
h.logger = ≶
h.sink = &sink;
var loop = try Loop.bind(gpa, io, &h);
defer loop.stop(gpa, io);
@@ -616,11 +617,12 @@ test "S7 case 6: a cname into a blocked target blocks the original question" {
var queue_buf: [log_queue_len]logger_mod.Entry = undefined;
var lg: logger_mod.Logger = .init(.{}, &queue_buf);
var sink: query_sink.QuerySink = .init(&lg, null);
var fake: FakeUpstream = .{ .reply = .{ .cname = "tracker.example.org" } };
var h = baseHandler(fake.client());
h.manager = &mgr;
h.logger = ≶
h.sink = &sink;
var loop = try Loop.bind(gpa, io, &h);
defer loop.stop(gpa, io);
@@ -724,11 +726,12 @@ test "S7 case 8: the third query inside the window is refused" {
var queue_buf: [log_queue_len]logger_mod.Entry = undefined;
var lg: logger_mod.Logger = .init(.{}, &queue_buf);
var sink: query_sink.QuerySink = .init(&lg, null);
var fake: FakeUpstream = .{ .reply = .a };
var h = baseHandler(fake.client());
h.limiter = &limiter;
h.logger = ≶
h.sink = &sink;
var loop = try Loop.bind(gpa, io, &h);
defer loop.stop(gpa, io);
@@ -961,10 +964,10 @@ test "S7 case 11: the app boots, serves a query and exits zero on shutdown" {
shutdown.reset();
defer shutdown.reset();
var future = try test_io.concurrent(app.run, .{ runner, cli.Paths{
var future = try test_io.concurrent(app.run, .{ runner, cli.RunArgs{ .paths = .{
.data_dir = root,
.config = config_path,
} });
} } });
const client_address: net.IpAddress = try .parse("127.0.0.1", 0);
const client = try client_address.bind(test_io, .{ .mode = .dgram });