mirror of
https://github.com/NLnetLabs/krill.git
synced 2026-09-11 03:57:41 +02:00
176 lines
5.7 KiB
Rust
176 lines
5.7 KiB
Rust
#[cfg(feature = "multi-user")]
|
|
mod openid_connect_mock;
|
|
|
|
use tokio::task;
|
|
use OpenIDConnectMockMode::NotStarted;
|
|
|
|
use std::process::Command;
|
|
use std::{env, process::ExitStatus};
|
|
|
|
use krill::daemon::config::Config;
|
|
use krill::test::*;
|
|
|
|
#[allow(dead_code)]
|
|
#[derive(Copy, Clone)]
|
|
pub enum OpenIDConnectMockMode {
|
|
NotStarted,
|
|
WithRPInitiatedLogout,
|
|
WithOAuth2Revocation,
|
|
WithNoLogoutEndpoints,
|
|
}
|
|
|
|
pub struct OpenIDConnectMockConfig {
|
|
mode: OpenIDConnectMockMode,
|
|
enabled_on_startup: bool,
|
|
}
|
|
|
|
#[allow(dead_code)]
|
|
impl OpenIDConnectMockConfig {
|
|
/// Don't start the OpenID Connect mock.
|
|
pub fn do_not_start() -> OpenIDConnectMockConfig {
|
|
Self {
|
|
mode: NotStarted,
|
|
enabled_on_startup: false,
|
|
}
|
|
}
|
|
|
|
/// Start the OpenID Mock and enable it ready for use.
|
|
pub fn enabled(mode: OpenIDConnectMockMode) -> OpenIDConnectMockConfig {
|
|
Self {
|
|
mode,
|
|
enabled_on_startup: true,
|
|
}
|
|
}
|
|
|
|
/// Start the OpenID Mock initially disabled. This can be useful to prevent initial OpenID Connect Discovery
|
|
/// succeeding before the first test runs.
|
|
pub fn disabled(mode: OpenIDConnectMockMode) -> OpenIDConnectMockConfig {
|
|
Self {
|
|
mode,
|
|
enabled_on_startup: false,
|
|
}
|
|
}
|
|
|
|
pub fn mode(&self) -> OpenIDConnectMockMode {
|
|
self.mode
|
|
}
|
|
|
|
pub fn enabled_on_startup(&self) -> bool {
|
|
self.enabled_on_startup
|
|
}
|
|
}
|
|
|
|
#[cfg(not(feature = "multi-user"))]
|
|
pub async fn run_krill_ui_test(test_name: &str, _: OpenIDConnectMockConfig) {
|
|
assert!(do_run_krill_ui_test(test_name).await);
|
|
}
|
|
|
|
#[cfg(feature = "multi-user")]
|
|
pub async fn run_krill_ui_test(test_name: &str, openid_connect_mock_config: OpenIDConnectMockConfig) {
|
|
let op_handle = match openid_connect_mock_config.mode() {
|
|
NotStarted => None,
|
|
_ => Some(openid_connect_mock::start(openid_connect_mock_config, 1).await),
|
|
};
|
|
|
|
let test_result = do_run_krill_ui_test(test_name).await;
|
|
|
|
if let Some(handle) = op_handle {
|
|
openid_connect_mock::stop(handle).await;
|
|
}
|
|
|
|
assert!(test_result);
|
|
}
|
|
|
|
struct CypressRunner {
|
|
status: ExitStatus,
|
|
}
|
|
impl CypressRunner {
|
|
pub async fn run(test_name: &str) -> Self {
|
|
let test_name = test_name.to_string();
|
|
|
|
ctrlc::set_handler(move || {
|
|
// If `cargo test` is stopped with CTRL-C the background Cypress Docker container continues to run. This
|
|
// prevents the next run of `cargo test` from working as the container unexpectedly already exists. Tell
|
|
// Docker to kill it to avoid leaving it lying around.
|
|
Command::new("docker")
|
|
.arg("kill")
|
|
.arg("cypress")
|
|
.spawn()
|
|
.expect("Failed to kill Cypress Docker container");
|
|
})
|
|
.expect("Error setting Ctrl-C handler");
|
|
|
|
let task = task::spawn_blocking(move || {
|
|
// NOTE: the directory mentioned here must be the same as the directory
|
|
// mentioned in the tests/ui/cypress/plugins/index.js file in the
|
|
// "integrationFolder" property otherwise Cypress mysteriously complains
|
|
// that it cannot find the spec file.
|
|
let cypress_spec_path = format!("tests/ui/cypress/specs/{}.js", test_name);
|
|
|
|
let mut cmd = Command::new("docker");
|
|
|
|
cmd.arg("run")
|
|
.arg("--name")
|
|
.arg("cypress")
|
|
.arg("--rm")
|
|
.arg("--net=host")
|
|
.arg("--ipc=host")
|
|
.arg("-v")
|
|
.arg(format!("{}:/e2e", env::current_dir().unwrap().display()))
|
|
.arg("-w")
|
|
.arg("/e2e");
|
|
|
|
if let Ok(debug_level) = std::env::var("CYPRESS_DEBUG") {
|
|
// Example values:
|
|
// - To get LOTS of Cypress logging: CYPRESS_DEBUG=cypress:*
|
|
// - To get logging relating to HTTP requests: CYPRESS_DEBUG=cypress:proxy:http:*
|
|
cmd.arg("-e").arg(format!("DEBUG={}", debug_level));
|
|
}
|
|
|
|
if std::env::var("CYPRESS_INTERACTIVE").is_ok() {
|
|
// After running `cargo test` a Chrome browser should open from the Cypress Docker container on your local
|
|
// X server. For this to work you might need to run this command in your shell prior to `cargo test`:
|
|
// xhost +
|
|
cmd.arg("-v")
|
|
.arg("/tmp/.X11-unix:/tmp/.X11-unix")
|
|
.arg("-e")
|
|
.arg("DISPLAY")
|
|
.arg("--entrypoint")
|
|
.arg("cypress");
|
|
}
|
|
|
|
cmd.arg("cypress/included:8.1.0");
|
|
|
|
if std::env::var("CYPRESS_INTERACTIVE").is_ok() {
|
|
cmd.arg("open").arg("--project").arg(".");
|
|
} else {
|
|
cmd.arg("--spec").arg(cypress_spec_path);
|
|
}
|
|
|
|
cmd.arg("--browser")
|
|
.arg("chrome")
|
|
.status()
|
|
.expect("Failed to run Cypress Docker UI test suite")
|
|
})
|
|
.await;
|
|
|
|
Self { status: task.unwrap() }
|
|
}
|
|
|
|
pub fn success(self) -> bool {
|
|
self.status.success()
|
|
}
|
|
}
|
|
|
|
async fn do_run_krill_ui_test(test_name: &str) -> bool {
|
|
krill::constants::enable_test_mode();
|
|
let config_path = &format!("test-resources/ui/{}.conf", test_name);
|
|
let config = Config::read_config(config_path).unwrap();
|
|
|
|
// Start Krill as a Tokio task in the background and wait just until we can tell that it has started.
|
|
start_krill_with_custom_config(config).await;
|
|
|
|
// Run the specified Cypress UI test suite and wait for it to finish
|
|
CypressRunner::run(test_name).await.success()
|
|
}
|