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
// Copyright Materialize, Inc. and contributors. All rights reserved.
//
// Use of this software is governed by the Business Source License
// included in the LICENSE file.
//
// As of the Change Date specified in that file, in accordance with
// the Business Source License, use of this software will be governed
// by the Apache License, Version 2.0.

use std::path::PathBuf;
use std::sync::Arc;

use clap::ArgEnum;

use mz_orchestrator_kubernetes::secrets::KubernetesSecretsReader;
use mz_orchestrator_process::secrets::ProcessSecretsReader;
use mz_secrets::SecretsReader;

#[derive(clap::Parser)]
pub struct SecretsReaderCliArgs {
    /// The secrets reader implementation to use.
    #[structopt(long, arg_enum, env = "SECRETS_READER")]
    secrets_reader: SecretsReaderKind,
    /// When using the process secrets reader, the directory on the filesystem
    /// where secrets are stored.
    #[structopt(
        long,
        required_if_eq("secrets-reader", "process"),
        env = "SECRETS_READER_PROCESS_DIR"
    )]
    secrets_reader_process_dir: Option<PathBuf>,
    /// When using the Kubernetes secrets reader, the Kubernetes context to
    /// load.
    #[structopt(
        long,
        required_if_eq("secrets-reader", "kubernetes"),
        env = "SECRETS_READER_KUBERNETES_CONTEXT"
    )]
    secrets_reader_kubernetes_context: Option<String>,
}

#[derive(ArgEnum, Debug, Clone)]
enum SecretsReaderKind {
    Process,
    Kubernetes,
}

impl SecretsReaderCliArgs {
    /// Loads the secrets reader specified by the command-line arguments.
    pub async fn load(self) -> Result<Arc<dyn SecretsReader>, anyhow::Error> {
        match self.secrets_reader {
            SecretsReaderKind::Process => {
                let dir = self.secrets_reader_process_dir.expect("clap enforced");
                Ok(Arc::new(ProcessSecretsReader::new(dir)))
            }
            SecretsReaderKind::Kubernetes => {
                let context = self
                    .secrets_reader_kubernetes_context
                    .expect("clap enforced");
                Ok(Arc::new(KubernetesSecretsReader::new(context).await?))
            }
        }
    }
}