Allow setting openid provider clientSecret with an external file #881
Labels
No Label
dependencies
duplicate
help wanted
invalid
kind/bug
kind/feature
needs reproduction
question
security
wontfix
No Milestone
No Assignees
6 Participants
Notifications
Due Date
No due date set.
Dependencies
No dependencies set.
Reference: vikunja/vikunja#881
Loading…
Reference in New Issue
Block a user
No description provided.
Delete Branch "%!s()"
Deleting a branch is permanent. Although the deleted branch may continue to exist for a short time before it actually gets removed, it CANNOT be undone in most cases. Continue?
I use NixOS for all my systems. It's a declarative OS, where the config file is readable for all users and processes on the host. Therefore secrets are saved normally in environment variables or extra files.
I tried to setup an OpenID Provider with parts of the config (everything except
clientsecret
) in the config file and theclientsecret
as environment variable. For me that did not work. There are two options: Either I did something wrong or it is not supported to set lists in environment variables (I think it's the second option).In my opinion, the easiest way to solve this problem is to introduce a new configuration option
auth.openid.clientsecret_file
, where a path to a file containing only the client secret can be specified. This option would be mutually exclusive withauth.openid.clientsecret
.Maybe I will try in some days to implement this myself, but I'm not really good at Go.
You are correct, setting lists in env variables is currently not supported.
There's also vikunja/api#704 which goes in a bit more detail about setting config variables from files.
I think that providing the config variables from files should work for all config variables (or at least the secrets) not only for openid secrets. Then your problem becomes a two part problem: 1) Getting list config from env and 2) getting config secrets from files.
Until this is sorted out, you should be able to just put the secrets in an external
.nix
file and import that (at least that's what I would do 🙃 ).With nix you might be interested in this module: https://kolaente.dev/vikunja/desktop-nix (I'm also using nix as my main OS, just not (yet) for server stuff)
I don't think that would be a good option beacause also in that case the secret(s) would be public in
/nix/store/...
for every program and user.That would be even better. Then I think getting list config from env isn't really a problem, because I could set the path to the secret file paths in the config file.
Ah, I didn't found that issue. But in the case of openid client secrets that wouldn't work I think, because of the list stuff, so it would be better to allow setting the secret file paths (also) in the config file.
Thank you, currently I packaged the API and Frontend, but it's not published yet. I will have a look at your work, maybe you've done it in a better way than me ;)
But the env value has to be stored somewhere hasn't it? I might be wrong though.
Would using a plain old yaml/toml config file be an option?
Maybe but THB I'm not so sure about that one 🙂 . It's one of my first nix module and based on @jtojnar module.
Yes and no. On my servers the secrets are stored in a gpg encrypted file which is in the nix store. These files are unencrypted on each boot (and every other system activation) into a tmpfs. The decrypted files are only readble for a specific user (e.g.
root
orvikunja
).Another option than having
_file
options for secrets, is to allow using multiple yaml/toml/json config files, in which one in my case would be encryptedI see, that makes sense. Currently Vikunja will look in various places for a config file and use the first one it finds. Using multiple different config files would get a bit difficult for matching/merging I think (things like which config file should take precence if multiple ones specify different values for the same key).
Would it be an option to use one encrypted config file with all config variables?
It would be an option, but not the best I think. With that I couldn't use the full potential of NixOS modules.
For me the best would be to allow reading secrets out of files (as I described already).
Personally, I currently do not bother with hiding secrets as I do not use any security critical ones. Where possible (e.g. vikunja-api), I leave the software to generate keys at start-up and store them in in-memory, since it is less pain for me to re-log in when the service restarts than wrangling the keys. If a software cannot do without a key, I store it in git-crypt and let it end up in the Nix store. But yeah, it is suboptimal.
I am following https://github.com/NixOS/nixpkgs/issues/102397 looking forward to using systemd for secrets once NixOS updates to 248.
Apparently, systemd authors do recommed using files instead of env vars: https://github.com/NixOS/nixpkgs/issues/102397#issuecomment-853472016
Also, here is my attempt at vikunja-api and the NixOS configuration in case you are interested.
For Vikunja's jwt this works great, but with secrets from external sources (like openid) that won't work. I understand why just using the in-memory secret is useful though.
I guess the "good" way would be to have Vikunja read config variables from files and until then just store the whole config file somewhere encrypted?
I think it is useful to be able to separate the secret and public parts of the config as to minimize what is opaque to the version control.
Just having read the systemd manual, I think vikunja also looking in
$CREDENTIALS_DIRECTORY/$config.key
file might be useful. But having anonymous list items for the openid makes it harder.Alternative would be allowing a dictionary as a password key:
which would make vikunja read the contents of
$CREDENTIALS_DIRECTORY/openid_foo_client_secret
.I think that would be a very nice solution.
Was this ever implemented or a solution/workaround found? I'm trying to deploy on NixOS and running into this exact problem with openID secrets
Viper, the library used to parse the configuration also mentions string replacers here. This could probably be used to allow for referencing environment variables in the yaml config, e.g. have a config like this:
Which would replace/insert
$CLIENT_ID
and$CLIENT_SECRET
with provided env files of that nameHaven't tried that in a while now. Of course we could also implement sth with environment variables replacing on the NixOS side.
Disclaimer: I've never used Go let alone viper so I may be way off on some things.
Regarding being able to use env vars in the config file, it looks like decoder hooks would be the way to do that (https://github.com/spf13/viper/issues/418). It seems as though those are only used when using
Unmarshal
.Would exposing an
Unmarshal
function and then using that to parse providers be a viable solution? Could also modifyGetString
andGetStringSlice
to unmarshal so all strings in the config file could use env vars. Something likeconfig.go
providers.go
Any updates on this? I think the environment variable method wouldn't be a bad idea. It's not really an option for me to put my secrets directly in the config file, as I'm also on NixOS.