env module now properly supports config file

cron
Jef Roosens 2022-04-06 17:51:06 +02:00
parent 21ef262ede
commit e9d7858380
Signed by untrusted user: Jef Roosens
GPG Key ID: B75D4F293C7052DB
4 changed files with 51 additions and 33 deletions

View File

@ -8,7 +8,8 @@ pub fn cmd() cli.Command {
name: 'build' name: 'build'
description: 'Run the build process.' description: 'Run the build process.'
execute: fn (cmd cli.Command) ? { execute: fn (cmd cli.Command) ? {
conf := env.load<env.BuildConfig>() ? config_file := cmd.flags.get_string('config-file') ?
conf := env.load<env.BuildConfig>(config_file) ?
build(conf) ? build(conf) ?
} }

View File

@ -1,6 +1,7 @@
module env module env
import os import os
import toml
// The prefix that every environment variable should have // The prefix that every environment variable should have
const prefix = 'VIETER_' const prefix = 'VIETER_'
@ -32,9 +33,9 @@ fn get_env_var(field_name string) ?string {
env_var := os.getenv(env_var_name) env_var := os.getenv(env_var_name)
env_file := os.getenv(env_file_name) env_file := os.getenv(env_file_name)
// If both aren't set, we report them missing // If both are missing, we return an empty string
if env_var == '' && env_file == '' { if env_var == '' && env_file == '' {
return error('Either $env_var_name or $env_file_name is required.') return ''
} }
// If they're both set, we report a conflict // If they're both set, we report a conflict
@ -56,37 +57,47 @@ fn get_env_var(field_name string) ?string {
} }
} }
fn load_in_place<T>(mut o T) ? {
$for field in T.fields {
o.$(field.name) = get_env_var(field.name) or {
// We use the default instead, if it's present
mut default := ''
for attr in field.attrs {
if attr.starts_with('default: ') {
default = attr[9..]
break
}
}
if default == '' {
return err
}
default
}
}
}
// load<T> attempts to create the given type from environment variables. For // load<T> attempts to create the given type from environment variables. For
// each field, the corresponding env var is its name in uppercase prepended // each field, the corresponding env var is its name in uppercase prepended
// with the hardcoded prefix. If this one isn't present, it looks for the env // with the hardcoded prefix. If this one isn't present, it looks for the env
// var with the file_suffix suffix. // var with the file_suffix suffix.
pub fn load<T>() ?T { pub fn load<T>(path string) ?T {
mut res := T{} mut res := T{}
load_in_place<T>(mut res) ? if os.exists(path) {
res = toml.parse_file(path) ?.reflect<T>()
}
$for field in T.fields {
$if field.typ is string {
env_value := get_env_var(field.name) ?
// The value of the env var will always be chosen over the config
// file
if env_value != '' {
res.$(field.name) = env_value
}
// If there's no value from the toml file either, we try to find a
// default value
else if res.$(field.name) == '' {
// We use the default instead, if it's present
mut default := ''
for attr in field.attrs {
if attr.starts_with('default: ') {
default = attr[9..]
break
}
}
if default == '' {
return error("Missing config variable '$field.name' with no provided default. Either add it to the config file or provide it using an environment variable.")
}
res.$(field.name) = default
}
}
}
return res return res
} }

View File

@ -18,7 +18,8 @@ pub fn cmd() cli.Command {
name: 'list' name: 'list'
description: 'List the current repos.' description: 'List the current repos.'
execute: fn (cmd cli.Command) ? { execute: fn (cmd cli.Command) ? {
conf := env.load<Config>() ? config_file := cmd.flags.get_string('config-file') ?
conf := env.load<Config>(config_file) ?
list(conf) ? list(conf) ?
} }
@ -29,7 +30,8 @@ pub fn cmd() cli.Command {
usage: 'url branch' usage: 'url branch'
description: 'Add a new repository.' description: 'Add a new repository.'
execute: fn (cmd cli.Command) ? { execute: fn (cmd cli.Command) ? {
conf := env.load<Config>() ? config_file := cmd.flags.get_string('config-file') ?
conf := env.load<Config>(config_file) ?
add(conf, cmd.args[0], cmd.args[1]) ? add(conf, cmd.args[0], cmd.args[1]) ?
} }
@ -40,7 +42,8 @@ pub fn cmd() cli.Command {
usage: 'url branch' usage: 'url branch'
description: 'Remove a repository.' description: 'Remove a repository.'
execute: fn (cmd cli.Command) ? { execute: fn (cmd cli.Command) ? {
conf := env.load<Config>() ? config_file := cmd.flags.get_string('config-file') ?
conf := env.load<Config>(config_file) ?
remove(conf, cmd.args[0], cmd.args[1]) ? remove(conf, cmd.args[0], cmd.args[1]) ?
} }
@ -59,7 +62,8 @@ fn list(conf Config) ? {
} }
fn add(conf Config, url string, branch string) ? { fn add(conf Config, url string, branch string) ? {
mut req := http.new_request(http.Method.post, '$conf.address/api/repos?url=$url&branch=$branch', '') ? mut req := http.new_request(http.Method.post, '$conf.address/api/repos?url=$url&branch=$branch',
'') ?
req.add_custom_header('X-API-Key', conf.api_key) ? req.add_custom_header('X-API-Key', conf.api_key) ?
res := req.do() ? res := req.do() ?
@ -68,7 +72,8 @@ fn add(conf Config, url string, branch string) ? {
} }
fn remove(conf Config, url string, branch string) ? { fn remove(conf Config, url string, branch string) ? {
mut req := http.new_request(http.Method.delete, '$conf.address/api/repos?url=$url&branch=$branch', '') ? mut req := http.new_request(http.Method.delete, '$conf.address/api/repos?url=$url&branch=$branch',
'') ?
req.add_custom_header('X-API-Key', conf.api_key) ? req.add_custom_header('X-API-Key', conf.api_key) ?
res := req.do() ? res := req.do() ?

View File

@ -8,7 +8,8 @@ pub fn cmd() cli.Command {
name: 'server' name: 'server'
description: 'Start the Vieter server' description: 'Start the Vieter server'
execute: fn (cmd cli.Command) ? { execute: fn (cmd cli.Command) ? {
conf := env.load<env.ServerConfig>() ? config_file := cmd.flags.get_string('config-file') ?
conf := env.load<env.ServerConfig>(config_file) ?
server(conf) ? server(conf) ?
} }