mirror of
https://github.com/telemt/telemt.git
synced 2026-11-03 22:31:59 +03:00
WEB: Base Path: security + reload coverage fixes&tests
This commit is contained in:
@@ -0,0 +1,88 @@
|
||||
use super::*;
|
||||
|
||||
fn web_config() -> &'static str {
|
||||
r#"
|
||||
[access.users]
|
||||
alice = "000102030405060708090a0b0c0d0e0f"
|
||||
|
||||
[[server.listeners]]
|
||||
ip = "127.0.0.1"
|
||||
port = 18080
|
||||
transport = "web"
|
||||
proxy_protocol = false
|
||||
web_client_ip_source = "x_forwarded_for"
|
||||
web_trusted_proxy_cidrs = ["127.0.0.1/32"]
|
||||
|
||||
[web]
|
||||
enabled = true
|
||||
|
||||
[[web.vhosts]]
|
||||
host = "proxy.example.com"
|
||||
public_addr = "203.0.113.10:443"
|
||||
|
||||
[web.vhosts.decoy]
|
||||
mode = "http_upstream"
|
||||
upstream = "http://127.0.0.1:18081"
|
||||
|
||||
[[web.vhosts.profiles]]
|
||||
user = "alice"
|
||||
secret_mode = "plain"
|
||||
"#
|
||||
}
|
||||
|
||||
fn vhosts_patch(base_path: &str) -> Json {
|
||||
serde_json::json!({
|
||||
"web": {
|
||||
"vhosts": [{
|
||||
"host": "proxy.example.com",
|
||||
"base_path": base_path,
|
||||
"public_addr": "203.0.113.10:443",
|
||||
"decoy": {
|
||||
"mode": "http_upstream",
|
||||
"upstream": "http://127.0.0.1:18081"
|
||||
},
|
||||
"profiles": [{
|
||||
"user": "alice",
|
||||
"secret_mode": "plain"
|
||||
}]
|
||||
}]
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
#[tokio::test]
|
||||
async fn config_api_applies_valid_base_path_and_preserves_source_on_invalid_patch() {
|
||||
let directory = tempfile::tempdir().unwrap();
|
||||
let path = directory.path().join("config.toml");
|
||||
std::fs::write(&path, web_config()).unwrap();
|
||||
let active = ProxyConfig::load(&path).unwrap();
|
||||
|
||||
let mut response = apply_patch_to_path(&path, &vhosts_patch("MixedCase/path"), None)
|
||||
.await
|
||||
.unwrap();
|
||||
let desired = ProxyConfig::load(&path).unwrap();
|
||||
let resolved = reconcile_runtime_effect(&mut response, &active, &desired).unwrap();
|
||||
assert!(!response.restart_required);
|
||||
assert!(response.runtime_reload_required);
|
||||
assert!(!response.process_restart_required);
|
||||
assert!(response.deferred_process_fields.is_empty());
|
||||
assert!(resolved.runtime_changed);
|
||||
assert_eq!(desired.web.vhosts[0].base_path, "MixedCase/path");
|
||||
assert_eq!(
|
||||
resolved.effective.web.runtime.as_ref().unwrap().vhosts["proxy.example.com"].base,
|
||||
"/MixedCase/path/"
|
||||
);
|
||||
|
||||
let (managed, _revision) = read_managed_config(&path).await.unwrap();
|
||||
let vhosts = managed["web"]["vhosts"].as_array().unwrap();
|
||||
assert_eq!(vhosts[0]["base_path"].as_str(), Some("MixedCase/path"));
|
||||
assert!(managed["web"].get("runtime").is_none());
|
||||
assert!(!managed.as_table().unwrap().contains_key("access"));
|
||||
|
||||
let before_invalid = std::fs::read(&path).unwrap();
|
||||
let error = apply_patch_to_path(&path, &vhosts_patch("/invalid"), None)
|
||||
.await
|
||||
.unwrap_err();
|
||||
assert_eq!(error.status, hyper::StatusCode::BAD_REQUEST);
|
||||
assert_eq!(std::fs::read(&path).unwrap(), before_invalid);
|
||||
}
|
||||
Reference in New Issue
Block a user