docs: improve config file documentation
Add a header and show default values.
This commit is contained in:
parent
2609ce4fbc
commit
52ec22a18c
1 changed files with 63 additions and 25 deletions
88
src/main.zig
88
src/main.zig
|
|
@ -667,16 +667,12 @@ fn read_nested_include_files(T: type, allocator: std.mem.Allocator, conf: *T, bu
|
|||
|
||||
pub const ConfigWriteError = error{ CreateConfigFileFailed, WriteConfigFileFailed, WriteFailed };
|
||||
|
||||
pub fn write_config(conf: anytype, allocator: std.mem.Allocator) (ConfigDirError || ConfigWriteError)!void {
|
||||
pub fn write_config(data: anytype, allocator: std.mem.Allocator) (ConfigDirError || ConfigWriteError)!void {
|
||||
const T = @TypeOf(data);
|
||||
config_mutex.lock();
|
||||
defer config_mutex.unlock();
|
||||
_ = allocator;
|
||||
const file_name = try get_app_config_file_name(application_name, @typeName(@TypeOf(conf)));
|
||||
return write_text_config_file(@TypeOf(conf), conf, file_name[0 .. file_name.len - 5]);
|
||||
// return write_json_file(@TypeOf(conf), conf, allocator, try get_app_config_file_name(application_name, @typeName(@TypeOf(conf))));
|
||||
}
|
||||
|
||||
fn write_text_config_file(comptime T: type, data: T, file_name: []const u8) ConfigWriteError!void {
|
||||
const file_name = try get_app_config_file_name(application_name, @typeName(T));
|
||||
var file = std.fs.createFileAbsolute(file_name, .{ .truncate = true }) catch |e| {
|
||||
std.log.err("createFileAbsolute failed with {any} for: {s}", .{ e, file_name });
|
||||
return error.CreateConfigFileFailed;
|
||||
|
|
@ -684,7 +680,20 @@ fn write_text_config_file(comptime T: type, data: T, file_name: []const u8) Conf
|
|||
defer file.close();
|
||||
var buf: [4096]u8 = undefined;
|
||||
var writer = file.writer(&buf);
|
||||
write_config_to_writer(T, data, &writer.interface) catch |e| {
|
||||
|
||||
try writer.interface.print(
|
||||
\\# This file is written by flow when settings are changed interactively. You may
|
||||
\\# edit values by hand, but not comments. Comments will be overwritten. Values
|
||||
\\# configured to the default value will be automatically commented and possibly
|
||||
\\# updated if the default value changes. To store values that cannot be changed
|
||||
\\# by flow, put them in a new file and reference it in the include_files
|
||||
\\# configuration option at the end of this file. include_files are never
|
||||
\\# modified by flow.
|
||||
\\
|
||||
\\
|
||||
, .{});
|
||||
|
||||
write_config_to_writer_internal(T, data, &writer.interface) catch |e| {
|
||||
std.log.err("write file failed with {any} for: {s}", .{ e, file_name });
|
||||
return error.WriteConfigFileFailed;
|
||||
};
|
||||
|
|
@ -692,8 +701,24 @@ fn write_text_config_file(comptime T: type, data: T, file_name: []const u8) Conf
|
|||
}
|
||||
|
||||
pub fn write_config_to_writer(comptime T: type, data: T, writer: *std.Io.Writer) std.Io.Writer.Error!void {
|
||||
try writer.print(
|
||||
\\# This file is generated by flow and updated when opened by an interactive
|
||||
\\# command. You may edit values by hand, but not comments. Comments will be
|
||||
\\# overwritten. Values configured to the default value will be automatically
|
||||
\\# commented and possibly updated if the default value changes. To store
|
||||
\\# values that cannot be changed by flow, put them in a new file and reference
|
||||
\\# it in the include_files configuration option at the end of this file.
|
||||
\\# include_files are never modified by flow.
|
||||
\\
|
||||
\\
|
||||
, .{});
|
||||
return write_config_to_writer_internal(T, data, writer);
|
||||
}
|
||||
|
||||
fn write_config_to_writer_internal(comptime T: type, data: T, writer: *std.Io.Writer) std.Io.Writer.Error!void {
|
||||
const default: T = .{};
|
||||
inline for (@typeInfo(T).@"struct".fields) |field_info| {
|
||||
var is_default = false;
|
||||
if (config_eql(
|
||||
T,
|
||||
field_info.type,
|
||||
|
|
@ -701,29 +726,39 @@ pub fn write_config_to_writer(comptime T: type, data: T, writer: *std.Io.Writer)
|
|||
@field(default, field_info.name),
|
||||
)) {
|
||||
try writer.print("# {s} ", .{field_info.name});
|
||||
is_default = true;
|
||||
} else {
|
||||
try writer.print("{s} ", .{field_info.name});
|
||||
}
|
||||
switch (field_info.type) {
|
||||
u24 => try write_color_value(@field(data, field_info.name), writer),
|
||||
?u24 => if (@field(data, field_info.name)) |value|
|
||||
try write_color_value(value, writer)
|
||||
else
|
||||
try writer.writeAll("null"),
|
||||
else => {
|
||||
var s: std.json.Stringify = .{ .writer = writer, .options = .{ .whitespace = .minified } };
|
||||
try s.write(@field(data, field_info.name));
|
||||
},
|
||||
}
|
||||
try write_config_value(field_info.type, @field(data, field_info.name), writer);
|
||||
try writer.print("\n", .{});
|
||||
if (!is_default) {
|
||||
try writer.print("# default value: ", .{});
|
||||
try write_config_value(field_info.type, @field(default, field_info.name), writer);
|
||||
try writer.print("\n", .{});
|
||||
}
|
||||
try writer.print("# value type: ", .{});
|
||||
try write_config_value_description(T, field_info.type, writer);
|
||||
try write_config_value_description(T, field_info.type, field_info.name, writer);
|
||||
try writer.print("\n", .{});
|
||||
try writer.print("\n", .{});
|
||||
}
|
||||
}
|
||||
|
||||
fn write_config_value_description(T: type, field_type: type, writer: *std.Io.Writer) !void {
|
||||
fn write_config_value(T: type, value: T, writer: *std.Io.Writer) !void {
|
||||
switch (T) {
|
||||
u24 => try write_color_value(value, writer),
|
||||
?u24 => if (value) |v|
|
||||
try write_color_value(v, writer)
|
||||
else
|
||||
try writer.writeAll("null"),
|
||||
else => {
|
||||
var s: std.json.Stringify = .{ .writer = writer, .options = .{ .whitespace = .minified } };
|
||||
try s.write(value);
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
fn write_config_value_description(T: type, field_type: type, comptime field_name: []const u8, writer: *std.Io.Writer) !void {
|
||||
switch (@typeInfo(field_type)) {
|
||||
.int => switch (field_type) {
|
||||
u24 => try writer.print("24 bit hex color value in quotes", .{}),
|
||||
|
|
@ -743,14 +778,17 @@ fn write_config_value_description(T: type, field_type: type, writer: *std.Io.Wri
|
|||
},
|
||||
.optional => |info| switch (@typeInfo(info.child)) {
|
||||
else => {
|
||||
try write_config_value_description(T, info.child, writer);
|
||||
try write_config_value_description(T, info.child, field_name, writer);
|
||||
try writer.print(" or null", .{});
|
||||
},
|
||||
},
|
||||
.pointer => |info| switch (info.size) {
|
||||
.slice => if (info.child == u8)
|
||||
try writer.print("quoted string", .{})
|
||||
else if (info.child == u16)
|
||||
.slice => if (info.child == u8) {
|
||||
if (std.mem.eql(u8, field_name, "include_files"))
|
||||
try writer.print("quoted string of {c} separated paths", .{std.fs.path.delimiter})
|
||||
else
|
||||
try writer.print("quoted string", .{});
|
||||
} else if (info.child == u16)
|
||||
try writer.print("quoted string (u16)", .{})
|
||||
else if (info.child == []const u8)
|
||||
try writer.print("list of quoted strings", .{})
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue