Skip to content

Commit aa08d22

Browse files
committed
refactor: merge and move webserver config & envars to controller/build
1 parent 2032835 commit aa08d22

8 files changed

Lines changed: 85 additions & 99 deletions

File tree

rust/operator-binary/src/config/webserver_config.rs

Lines changed: 0 additions & 73 deletions
This file was deleted.

rust/operator-binary/src/controller/build/config_map.rs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -15,11 +15,11 @@ use stackable_operator::{
1515
};
1616

1717
use crate::{
18-
config::webserver_config,
1918
controller::{
2019
ValidatedCluster, ValidatedLogging,
21-
build::properties::product_logging::{
22-
LOG_CONFIG_FILE, create_airflow_config, vector_config_file_content,
20+
build::properties::{
21+
product_logging::{LOG_CONFIG_FILE, create_airflow_config, vector_config_file_content},
22+
webserver_config,
2323
},
2424
},
2525
crd::{AIRFLOW_CONFIG_FILENAME, AirflowConfigOverrides, Container, STACKABLE_LOG_DIR},

rust/operator-binary/src/env_vars.rs renamed to rust/operator-binary/src/controller/build/properties/env_vars.rs

File renamed without changes.
Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,6 @@
1-
//! Renders the config files (logging, …) assembled into the rolegroup `ConfigMap`.
1+
//! Renders the config files (`webserver_config.py`, env vars, logging, …) assembled into the
2+
//! rolegroup `ConfigMap`.
23
4+
pub mod env_vars;
35
pub mod product_logging;
6+
pub mod webserver_config;

rust/operator-binary/src/config/mod.rs renamed to rust/operator-binary/src/controller/build/properties/webserver_config.rs

Lines changed: 76 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -1,30 +1,40 @@
1-
pub mod webserver_config;
1+
//! Builds the `webserver_config.py` Flask configuration file from the resolved
2+
//! authentication/authorization config plus user-provided config overrides.
23
3-
use std::collections::BTreeMap;
4+
use std::{collections::BTreeMap, io::Write};
45

56
use indoc::formatdoc;
67
use snafu::{ResultExt, Snafu};
78
use stackable_operator::{
89
commons::tls_verification::TlsVerification,
910
crd::authentication::{ldap, oidc},
11+
v2::flask_config_writer,
1012
};
1113

12-
use crate::crd::{
13-
AirflowConfigOptions,
14-
authentication::{
15-
AirflowAuthenticationClassResolved, AirflowClientAuthenticationDetailsResolved,
16-
DEFAULT_OIDC_PROVIDER, FlaskRolesSyncMoment,
14+
use crate::{
15+
controller::ValidatedCluster,
16+
crd::{
17+
AirflowConfigOptions,
18+
authentication::{
19+
AirflowAuthenticationClassResolved, AirflowClientAuthenticationDetailsResolved,
20+
DEFAULT_OIDC_PROVIDER, FlaskRolesSyncMoment,
21+
},
22+
authorization::AirflowAuthorizationResolved,
1723
},
18-
authorization::AirflowAuthorizationResolved,
1924
};
2025

21-
pub const PYTHON_IMPORTS: &[&str] = &[
26+
const PYTHON_IMPORTS: &[&str] = &[
2227
"import os",
2328
"from flask_appbuilder.const import (AUTH_DB, AUTH_LDAP, AUTH_OAUTH, AUTH_REMOTE_USER)",
2429
"basedir = os.path.abspath(os.path.dirname(__file__))",
2530
"WTF_CSRF_ENABLED = True",
2631
];
2732

33+
/// Marks arbitrary Python code to prepend verbatim to the generated file.
34+
const CONFIG_OVERRIDE_FILE_HEADER_KEY: &str = "FILE_HEADER";
35+
/// Marks arbitrary Python code to append verbatim to the generated file.
36+
const CONFIG_OVERRIDE_FILE_FOOTER_KEY: &str = "FILE_FOOTER";
37+
2838
type Result<T, E = Error> = std::result::Result<T, E>;
2939

3040
#[derive(Snafu, Debug)]
@@ -37,6 +47,57 @@ pub enum Error {
3747

3848
#[snafu(display("invalid well-known OIDC configuration URL"))]
3949
InvalidWellKnownConfigUrl { source: oidc::v1alpha1::Error },
50+
51+
#[snafu(display("failed to write the webserver config file"))]
52+
WriteConfigFile {
53+
source: flask_config_writer::FlaskAppConfigWriterError,
54+
},
55+
56+
#[snafu(display("failed to write the header/footer to the webserver config file"))]
57+
WriteHeaderFooter { source: std::io::Error },
58+
}
59+
60+
/// Renders the `webserver_config.py` contents: operator defaults (derived from the
61+
/// resolved authentication/authorization config) with the user's `config_overrides`
62+
/// applied last, wrapped by the optional `FILE_HEADER`/`FILE_FOOTER` Python blocks.
63+
pub fn build(
64+
validated_cluster: &ValidatedCluster,
65+
config_file_overrides: &BTreeMap<String, String>,
66+
) -> Result<String, Error> {
67+
// this will call default values from AirflowClientAuthenticationDetails
68+
let mut config = build_airflow_config(
69+
&validated_cluster.cluster_config.authentication_config,
70+
&validated_cluster.cluster_config.authorization_config,
71+
&validated_cluster.image.product_version,
72+
)?;
73+
74+
let mut file_config = config_file_overrides.clone();
75+
76+
// now add any overrides, replacing any defaults
77+
config.append(&mut file_config);
78+
79+
let mut config_file = Vec::new();
80+
81+
// By removing the keys from `config`, we avoid pasting the Python code into a Python variable as well
82+
// (which would be bad)
83+
if let Some(header) = config.remove(CONFIG_OVERRIDE_FILE_HEADER_KEY) {
84+
writeln!(config_file, "{}", header).context(WriteHeaderFooterSnafu)?;
85+
}
86+
87+
let temp_file_footer: Option<String> = config.remove(CONFIG_OVERRIDE_FILE_FOOTER_KEY);
88+
89+
flask_config_writer::write::<AirflowConfigOptions, _, _>(
90+
&mut config_file,
91+
config.iter(),
92+
PYTHON_IMPORTS,
93+
)
94+
.context(WriteConfigFileSnafu)?;
95+
96+
if let Some(footer) = temp_file_footer {
97+
writeln!(config_file, "{}", footer).context(WriteHeaderFooterSnafu)?;
98+
}
99+
100+
Ok(String::from_utf8(config_file).expect("the Flask config writer only emits valid UTF-8"))
40101
}
41102

42103
/// Builds the operator-default `webserver_config.py` entries derived from the resolved
@@ -322,15 +383,13 @@ mod tests {
322383
shared::time::Duration,
323384
};
324385

325-
use crate::{
326-
config::build_airflow_config,
327-
crd::{
328-
authentication::{
329-
AirflowAuthenticationClassResolved, AirflowClientAuthenticationDetailsResolved,
330-
FlaskRolesSyncMoment, default_user_registration,
331-
},
332-
authorization::{AirflowAuthorizationResolved, OpaConfigResolved},
386+
use super::build_airflow_config;
387+
use crate::crd::{
388+
authentication::{
389+
AirflowAuthenticationClassResolved, AirflowClientAuthenticationDetailsResolved,
390+
FlaskRolesSyncMoment, default_user_registration,
333391
},
392+
authorization::{AirflowAuthorizationResolved, OpaConfigResolved},
334393
};
335394

336395
const TEST_AIRFLOW_VERSION: &str = "3.0.6";

rust/operator-binary/src/controller/build/resource/executor.rs

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@ use crate::{
2727
ValidatedCluster, ValidatedLogging,
2828
build::{
2929
graceful_shutdown::add_graceful_shutdown_config,
30+
properties::env_vars::build_airflow_template_envs,
3031
resource::pod::{
3132
add_authentication_volumes_and_volume_mounts, add_git_sync_resources,
3233
build_logging_container,
@@ -37,11 +38,9 @@ use crate::{
3738
crd::{
3839
CONFIG_PATH, Container, ExecutorConfig, LOG_CONFIG_DIR, STACKABLE_LOG_DIR, TEMPLATE_NAME,
3940
},
40-
env_vars::build_airflow_template_envs,
4141
};
4242

4343
#[derive(Snafu, Debug)]
44-
#[snafu(visibility(pub(crate)))]
4544
pub enum Error {
4645
#[snafu(display("invalid container name"))]
4746
InvalidContainerName {

rust/operator-binary/src/controller/build/resource/statefulset.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,7 @@ use crate::{
3333
AirflowRoleGroupConfig, ValidatedCluster, ValidatedLogging,
3434
build::{
3535
graceful_shutdown::add_graceful_shutdown_config,
36+
properties::env_vars,
3637
resource::{
3738
pod::{
3839
add_authentication_volumes_and_volume_mounts, add_git_sync_resources,
@@ -48,7 +49,6 @@ use crate::{
4849
LISTENER_VOLUME_NAME, LOG_CONFIG_DIR, METRICS_PORT, METRICS_PORT_NAME, STACKABLE_LOG_DIR,
4950
TEMPLATE_LOCATION, TEMPLATE_VOLUME_NAME,
5051
},
51-
env_vars,
5252
};
5353

5454
#[derive(Snafu, Debug)]

rust/operator-binary/src/main.rs

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -39,11 +39,9 @@ use crate::{
3939
};
4040

4141
mod airflow_controller;
42-
mod config;
4342
mod controller;
4443
mod controller_commons;
4544
mod crd;
46-
mod env_vars;
4745
mod util;
4846
mod webhooks;
4947

0 commit comments

Comments
 (0)