milestone 33: contract closure — samples, file-authority enumeration, dead code, bundle ceiling
This commit is contained in:
@@ -91,7 +91,7 @@ fn confirmLogin(
|
||||
|
||||
/// Ends the session the cookie names. An unknown cookie is not an error: the
|
||||
/// point of logging out is to end up logged out, which is where it already is.
|
||||
pub fn applyLogout(state: *server.WebState, io: std.Io, cookie_header: []const u8) bool {
|
||||
fn applyLogout(state: *server.WebState, io: std.Io, cookie_header: []const u8) bool {
|
||||
const sessions = state.sessions orelse return false;
|
||||
const value = http_util.cookieValue(cookie_header, auth.cookie_name) orelse return false;
|
||||
return sessions.logout(io, value);
|
||||
|
||||
@@ -85,7 +85,7 @@ pub const StatusView = struct {
|
||||
// decisions
|
||||
// ---------------------------------------------------------------------------
|
||||
|
||||
pub fn applyCreate(
|
||||
fn applyCreate(
|
||||
state: *server.WebState,
|
||||
io: std.Io,
|
||||
arena: Allocator,
|
||||
@@ -103,7 +103,7 @@ pub fn applyCreate(
|
||||
return .{ .id = id };
|
||||
}
|
||||
|
||||
pub fn applyUpdate(
|
||||
fn applyUpdate(
|
||||
state: *server.WebState,
|
||||
io: std.Io,
|
||||
arena: Allocator,
|
||||
@@ -121,7 +121,7 @@ pub fn applyUpdate(
|
||||
return mutations.reload(state, io);
|
||||
}
|
||||
|
||||
pub fn applyDelete(state: *server.WebState, io: std.Io, id: i64) ?Failure {
|
||||
fn applyDelete(state: *server.WebState, io: std.Io, id: i64) ?Failure {
|
||||
const database = mutations.requireConfigDb(state) catch return mutations.no_config_db;
|
||||
|
||||
state.config_lock.lockUncancelable(io);
|
||||
@@ -158,7 +158,7 @@ fn pruneFiles(state: *server.WebState, io: std.Io) void {
|
||||
/// `refreshAll` already ends in the manager's own reload; the seam is called
|
||||
/// too, because it is how the composition root learns that a change landed and
|
||||
/// the only reload a test can observe.
|
||||
pub fn applyRefresh(state: *server.WebState, io: std.Io, out: []manager_mod.SourceStatus) union(enum) {
|
||||
fn applyRefresh(state: *server.WebState, io: std.Io, out: []manager_mod.SourceStatus) union(enum) {
|
||||
statuses: usize,
|
||||
fail: Failure,
|
||||
} {
|
||||
|
||||
@@ -56,7 +56,7 @@ const PrefixesBody = struct {
|
||||
// decisions
|
||||
// ---------------------------------------------------------------------------
|
||||
|
||||
pub fn applyUpdate(
|
||||
fn applyUpdate(
|
||||
state: *server.WebState,
|
||||
io: std.Io,
|
||||
id: i64,
|
||||
@@ -72,7 +72,7 @@ pub fn applyUpdate(
|
||||
return mutations.reload(state, io);
|
||||
}
|
||||
|
||||
pub fn applyDelete(state: *server.WebState, io: std.Io, id: i64) ?Failure {
|
||||
fn applyDelete(state: *server.WebState, io: std.Io, id: i64) ?Failure {
|
||||
const database = mutations.requireConfigDb(state) catch return mutations.no_config_db;
|
||||
|
||||
state.config_lock.lockUncancelable(io);
|
||||
@@ -83,7 +83,7 @@ pub fn applyDelete(state: *server.WebState, io: std.Io, id: i64) ?Failure {
|
||||
return mutations.reload(state, io);
|
||||
}
|
||||
|
||||
pub fn applyReplacePrefixes(
|
||||
fn applyReplacePrefixes(
|
||||
state: *server.WebState,
|
||||
io: std.Io,
|
||||
arena: Allocator,
|
||||
|
||||
@@ -48,7 +48,7 @@ const Created = union(enum) { id: i64, fail: Failure };
|
||||
// decisions
|
||||
// ---------------------------------------------------------------------------
|
||||
|
||||
pub fn applyCreate(
|
||||
fn applyCreate(
|
||||
state: *server.WebState,
|
||||
io: std.Io,
|
||||
arena: Allocator,
|
||||
@@ -68,7 +68,7 @@ pub fn applyCreate(
|
||||
return .{ .id = id };
|
||||
}
|
||||
|
||||
pub fn applyUpdate(
|
||||
fn applyUpdate(
|
||||
state: *server.WebState,
|
||||
io: std.Io,
|
||||
arena: Allocator,
|
||||
@@ -105,7 +105,7 @@ fn updateLocked(database: *db.Db, arena: Allocator, id: i64, item: model.Group)
|
||||
return null;
|
||||
}
|
||||
|
||||
pub fn applyDelete(state: *server.WebState, io: std.Io, arena: Allocator, id: i64) ?Failure {
|
||||
fn applyDelete(state: *server.WebState, io: std.Io, arena: Allocator, id: i64) ?Failure {
|
||||
const database = mutations.requireConfigDb(state) catch return mutations.no_config_db;
|
||||
|
||||
state.config_lock.lockUncancelable(io);
|
||||
@@ -133,7 +133,7 @@ fn deleteLocked(database: *db.Db, arena: Allocator, id: i64) ?Failure {
|
||||
return null;
|
||||
}
|
||||
|
||||
pub fn applySetSources(
|
||||
fn applySetSources(
|
||||
state: *server.WebState,
|
||||
io: std.Io,
|
||||
id: i64,
|
||||
|
||||
@@ -150,7 +150,7 @@ pub fn protection(input: Input) Protection {
|
||||
};
|
||||
}
|
||||
|
||||
pub fn queryHistoryState(input: Input) []const u8 {
|
||||
fn queryHistoryState(input: Input) []const u8 {
|
||||
if (input.writer_failed) return query_history_failed;
|
||||
if (input.gate_episode == .losing) return query_history_losing;
|
||||
return query_history_recording;
|
||||
@@ -159,13 +159,13 @@ pub fn queryHistoryState(input: Input) []const u8 {
|
||||
/// The operational log is not recording — either the store never opened or its
|
||||
/// writes are failing. Both mean the same thing to an operator: the record of
|
||||
/// what went wrong is not being kept.
|
||||
pub fn diagnosticsUnavailable(input: Input) bool {
|
||||
fn diagnosticsUnavailable(input: Input) bool {
|
||||
return !input.diagnostics_present or input.diagnostics_write_failed;
|
||||
}
|
||||
|
||||
/// `warn` reads as a log level rather than as a quantity of disk. The monitor
|
||||
/// keeps its own name; the wire says what an operator sees on the page.
|
||||
pub fn diskState(state: disk_monitor.State) []const u8 {
|
||||
fn diskState(state: disk_monitor.State) []const u8 {
|
||||
return switch (state) {
|
||||
.ok => disk_ok,
|
||||
.warn => disk_low,
|
||||
|
||||
@@ -47,7 +47,7 @@ pub fn view(entry: *const sse.Entry) EventView {
|
||||
|
||||
/// One `event: query` frame. JSON never contains a raw newline, so the whole
|
||||
/// payload is a single `data:` line.
|
||||
pub fn writeEvent(w: *std.Io.Writer, entry: *const sse.Entry) std.Io.Writer.Error!void {
|
||||
fn writeEvent(w: *std.Io.Writer, entry: *const sse.Entry) std.Io.Writer.Error!void {
|
||||
try w.writeAll("event: query\ndata: ");
|
||||
var stringify: std.json.Stringify = .{ .writer = w };
|
||||
try stringify.write(view(entry));
|
||||
|
||||
@@ -88,7 +88,7 @@ fn publish(state: *server.WebState, io: std.Io, arena: Allocator, database: *@im
|
||||
return mutations.reload(state, io);
|
||||
}
|
||||
|
||||
pub fn applyCreateRecord(
|
||||
fn applyCreateRecord(
|
||||
state: *server.WebState,
|
||||
io: std.Io,
|
||||
arena: Allocator,
|
||||
@@ -106,7 +106,7 @@ pub fn applyCreateRecord(
|
||||
return .{ .id = id };
|
||||
}
|
||||
|
||||
pub fn applyUpdateRecord(
|
||||
fn applyUpdateRecord(
|
||||
state: *server.WebState,
|
||||
io: std.Io,
|
||||
arena: Allocator,
|
||||
@@ -124,7 +124,7 @@ pub fn applyUpdateRecord(
|
||||
return publish(state, io, arena, database);
|
||||
}
|
||||
|
||||
pub fn applyDeleteRecord(state: *server.WebState, io: std.Io, arena: Allocator, id: i64) ?Failure {
|
||||
fn applyDeleteRecord(state: *server.WebState, io: std.Io, arena: Allocator, id: i64) ?Failure {
|
||||
const database = mutations.requireConfigDb(state) catch return mutations.no_config_db;
|
||||
|
||||
state.config_lock.lockUncancelable(io);
|
||||
@@ -139,7 +139,7 @@ pub fn applyDeleteRecord(state: *server.WebState, io: std.Io, arena: Allocator,
|
||||
// forward zones: decisions
|
||||
// ---------------------------------------------------------------------------
|
||||
|
||||
pub fn applyCreateZone(
|
||||
fn applyCreateZone(
|
||||
state: *server.WebState,
|
||||
io: std.Io,
|
||||
arena: Allocator,
|
||||
@@ -157,7 +157,7 @@ pub fn applyCreateZone(
|
||||
return .{ .id = id };
|
||||
}
|
||||
|
||||
pub fn applyUpdateZone(
|
||||
fn applyUpdateZone(
|
||||
state: *server.WebState,
|
||||
io: std.Io,
|
||||
arena: Allocator,
|
||||
@@ -175,7 +175,7 @@ pub fn applyUpdateZone(
|
||||
return publish(state, io, arena, database);
|
||||
}
|
||||
|
||||
pub fn applyDeleteZone(state: *server.WebState, io: std.Io, arena: Allocator, id: i64) ?Failure {
|
||||
fn applyDeleteZone(state: *server.WebState, io: std.Io, arena: Allocator, id: i64) ?Failure {
|
||||
const database = mutations.requireConfigDb(state) catch return mutations.no_config_db;
|
||||
|
||||
state.config_lock.lockUncancelable(io);
|
||||
|
||||
@@ -390,12 +390,6 @@ pub fn checkSource(arena: Allocator, source: model.BlocklistSource) error{OutOfM
|
||||
return firstProblem(arena, cfg);
|
||||
}
|
||||
|
||||
pub fn checkClientIp(arena: Allocator, ip: []const u8) error{OutOfMemory}!?[]const u8 {
|
||||
var cfg = skeleton(&default_groups);
|
||||
cfg.clients = &.{.{ .ip = ip, .group = skeleton_group }};
|
||||
return firstProblem(arena, cfg);
|
||||
}
|
||||
|
||||
pub fn checkClientPrefix(arena: Allocator, prefix: []const u8, priority: i32) error{OutOfMemory}!?[]const u8 {
|
||||
var cfg = skeleton(&default_groups);
|
||||
cfg.client_prefixes = &.{.{ .prefix = prefix, .group = skeleton_group, .priority = priority }};
|
||||
@@ -625,7 +619,6 @@ test "a valid candidate row reports no problem" {
|
||||
try checkForwardZone(arena, .{ .zone = "lan", .resolver = "udp://10.0.0.1:53" }),
|
||||
);
|
||||
try testing.expectEqual(@as(?[]const u8, null), try checkRule(arena, "*.ads.example", .wildcard));
|
||||
try testing.expectEqual(@as(?[]const u8, null), try checkClientIp(arena, "192.168.1.10"));
|
||||
try testing.expectEqual(@as(?[]const u8, null), try checkClientPrefix(arena, "192.168.1.0/24", 100));
|
||||
try testing.expectEqual(@as(?[]const u8, null), try checkGroupName(arena, "kids"));
|
||||
try testing.expectEqual(@as(?[]const u8, null), try checkGroupName(arena, "default"));
|
||||
|
||||
@@ -43,7 +43,7 @@ pub fn view(pause: *const pause_mod.Pause, now_s: i64) View {
|
||||
return .{ .paused = true, .until = until };
|
||||
}
|
||||
|
||||
pub fn apply(
|
||||
fn apply(
|
||||
state: *server.WebState,
|
||||
io: std.Io,
|
||||
body: Body,
|
||||
|
||||
@@ -54,7 +54,7 @@ fn toInput(body: Body) union(enum) { input: rules_repo.RuleInput, fail: Failure
|
||||
// decisions
|
||||
// ---------------------------------------------------------------------------
|
||||
|
||||
pub fn applyCreate(
|
||||
fn applyCreate(
|
||||
state: *server.WebState,
|
||||
io: std.Io,
|
||||
arena: Allocator,
|
||||
@@ -74,7 +74,7 @@ pub fn applyCreate(
|
||||
return .{ .id = id };
|
||||
}
|
||||
|
||||
pub fn applyUpdate(
|
||||
fn applyUpdate(
|
||||
state: *server.WebState,
|
||||
io: std.Io,
|
||||
arena: Allocator,
|
||||
@@ -94,7 +94,7 @@ pub fn applyUpdate(
|
||||
return mutations.reload(state, io);
|
||||
}
|
||||
|
||||
pub fn applyDelete(state: *server.WebState, io: std.Io, id: i64) ?Failure {
|
||||
fn applyDelete(state: *server.WebState, io: std.Io, id: i64) ?Failure {
|
||||
const database = mutations.requireConfigDb(state) catch return mutations.no_config_db;
|
||||
|
||||
state.config_lock.lockUncancelable(io);
|
||||
|
||||
@@ -309,7 +309,7 @@ pub fn view(cfg: model.Config) View {
|
||||
|
||||
/// Reads, merges, validates, writes, and — when the password changed — ends
|
||||
/// every session. Returns the configuration as it now stands.
|
||||
pub fn applyPut(
|
||||
fn applyPut(
|
||||
state: *server.WebState,
|
||||
io: std.Io,
|
||||
arena: Allocator,
|
||||
|
||||
@@ -385,7 +385,7 @@ pub const PeriodError = error{BadPeriod};
|
||||
|
||||
/// An absent `period` is the default; anything else it cannot read is a 400,
|
||||
/// never a silent fallback — a typo must not return a window nobody asked for.
|
||||
pub fn periodParam(query: []const u8) PeriodError!Period {
|
||||
fn periodParam(query: []const u8) PeriodError!Period {
|
||||
var buf: [8]u8 = undefined;
|
||||
const found = http_util.queryValue(query, "period", &buf) catch return error.BadPeriod;
|
||||
const text = found orelse return default_period;
|
||||
|
||||
@@ -38,7 +38,7 @@ const Created = union(enum) { id: i64, fail: Failure };
|
||||
// decisions
|
||||
// ---------------------------------------------------------------------------
|
||||
|
||||
pub fn applyCreate(
|
||||
fn applyCreate(
|
||||
state: *server.WebState,
|
||||
io: std.Io,
|
||||
arena: Allocator,
|
||||
@@ -59,7 +59,7 @@ pub fn applyCreate(
|
||||
return .{ .id = id };
|
||||
}
|
||||
|
||||
pub fn applyUpdate(
|
||||
fn applyUpdate(
|
||||
state: *server.WebState,
|
||||
io: std.Io,
|
||||
arena: Allocator,
|
||||
@@ -94,7 +94,7 @@ pub fn applyUpdate(
|
||||
/// The last enabled upstream cannot go: a resolver with nowhere to forward to
|
||||
/// answers nothing, and `validate.validate` refuses that configuration at
|
||||
/// startup — so allowing it here would only produce a box that will not boot.
|
||||
pub fn applyDelete(state: *server.WebState, io: std.Io, arena: Allocator, id: i64) ?Failure {
|
||||
fn applyDelete(state: *server.WebState, io: std.Io, arena: Allocator, id: i64) ?Failure {
|
||||
const database = mutations.requireConfigDb(state) catch return mutations.no_config_db;
|
||||
|
||||
state.config_lock.lockUncancelable(io);
|
||||
|
||||
Reference in New Issue
Block a user