blob: 6c24ffbc045123c7cf0443dc98c875d6d3b6c501 (
plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
|
exception Missing_field of string
type t = {
app_name: string;
data_dir: string;
program_dir: string;
config_dir: string;
primary_config: string;
fallback_config: string;
socket: string;
pid_file: string;
log_file: string option;
log_template: string;
log_level: string;
} [@@deriving show]
(* XXX: there should be a better way than to fully initialize it
with garbage just to update it later *)
let empty_config = {
app_name = "";
data_dir = "";
program_dir = "";
config_dir = "";
primary_config = "";
fallback_config = "";
socket = "";
pid_file = "";
log_file = None;
log_template = "";
log_level = "";
}
(* XXX: We assume that nesting in TOML config files never goes beyond two levels *)
let get_field conf tbl_name field_name =
(* NB: TomlLenses module uses "table" and "field" names for function names,
hence tbl_name and field_name
*)
TomlLenses.(get conf (key tbl_name |-- table |-- key field_name |-- string))
let mandatory_field conf table field =
let value = get_field conf table field in
match value with
| Some value -> value
| None -> raise @@ Missing_field (Printf.sprintf "Invalid config: Missing mandatory field \"%s\" in section [%s]" field table)
let optional_field default conf table field =
let value = get_field conf table field in
Util.substitute_default value default
let load filename =
try
let open Defaults in
let conf_toml = Toml.Parser.from_filename filename |> Toml.Parser.unsafe in
let conf = empty_config in
(* Mandatory fields *)
let conf = {conf with app_name = mandatory_field conf_toml "appliance" "name"} in
let conf = {conf with data_dir = mandatory_field conf_toml "appliance" "data_dir"} in
let conf = {conf with config_dir = mandatory_field conf_toml "appliance" "config_dir"} in
let conf = {conf with program_dir = mandatory_field conf_toml "appliance" "program_dir"} in
let conf = {conf with primary_config = mandatory_field conf_toml "appliance" "primary_config"} in
let conf = {conf with fallback_config = mandatory_field conf_toml "appliance" "fallback_config"} in
(* Optional fields *)
let conf = {conf with pid_file = optional_field defaults.pid_file conf_toml "vyconf" "pid_file"} in
let conf = {conf with socket = optional_field defaults.socket conf_toml "vyconf" "socket"} in
let conf = {conf with log_template = optional_field defaults.log_template conf_toml "vyconf" "log_template"} in
let conf = {conf with log_level = optional_field defaults.log_level conf_toml "vyconf" "log_level"} in
(* log_file is already string option, so we don't need to unwrap *)
let conf = {conf with log_file = get_field conf_toml "vyconf" "log_file"} in
Result.Ok conf
with
| Sys_error msg -> Error msg
| Toml.Parser.Error (msg, _) -> Error msg
| Missing_field msg -> Error msg
let dump = show
|