Исправлен drift-check host firewall для established/related, добавлены тесты и trim policy в status

This commit is contained in:
2026-05-11 18:54:15 +05:00
parent 36600c0a5a
commit 640178a592
2 changed files with 78 additions and 5 deletions
+70 -3
View File
@@ -320,9 +320,7 @@ fn host_firewall_drift_reason_from_text(nt: &str, cfg: &Config) -> Option<String
if !nt.contains("iif lo accept") {
return Some("missing loopback allow".into());
}
if !(nt.contains("ct state established,related accept")
|| nt.contains("ct state related,established accept"))
{
if !has_established_related_rule(nt) {
return Some("missing established/related allow".into());
}
if !nt.contains(&ssh) {
@@ -348,6 +346,11 @@ fn host_firewall_drift_reason_from_text(nt: &str, cfg: &Config) -> Option<String
None
}
fn has_established_related_rule(nt: &str) -> bool {
nt.contains("ct state established related accept")
|| nt.contains("ct state related established accept")
}
fn apply_rule(transport: &dyn NsTransport, cidr: &str, max_conn: u32) -> anyhow::Result<()> {
let _ = transport.run(&[
"nft",
@@ -686,6 +689,70 @@ table inet awg2_host_firewall {
assert_eq!(host_firewall_drift_reason_from_text(&nt, &cfg), None);
}
#[test]
fn normalized_established_related_rule_matches() {
let nt = normalize_nft_text("ct state established,related accept");
assert!(nt.contains("ct state established related accept"));
assert!(has_established_related_rule(&nt));
}
#[test]
fn host_firewall_drift_detects_missing_established_related_rule() {
let table = r#"
table inet awg2_host_firewall {
chain input {
type filter hook input priority filter; policy drop;
iif "lo" accept
tcp dport 2323 accept
udp dport 443 accept
ip protocol icmp accept
ip6 nexthdr icmpv6 accept
}
}
"#;
let cfg = Config {
amnezia: crate::config::AmneziaConfig {
container_names: vec!["amnezia-awg2".into()],
interface_candidates: vec!["awg0".into()],
interface_patterns: vec!["awg*".into()],
peer_ipv4_cidr: "10.8.1.0/24".into(),
},
traffic: crate::config::TrafficConfig {
enabled: true,
peer_limit: "70mbit".into(),
root_rate: "1000mbit".into(),
reconcile_interval_secs: 15,
container_ready_timeout_secs: 30,
class_start_id: 10,
ifb_name: "ifb0".into(),
},
host_firewall: crate::config::HostFirewallConfig::default(),
anti_torrent: crate::config::AntiTorrentConfig {
enabled: false,
max_connections_per_peer: 100,
peer_ipv4_cidr: "10.8.1.0/24".into(),
apply_in_amnezia_netns: false,
},
reboot: crate::config::RebootConfig {
enabled: false,
window_start_utc: "01:00".into(),
window_end_utc: "02:00".into(),
},
swap: crate::config::SwapConfig {
enabled: false,
path: "/swapfile".into(),
size_mb: 2048,
priority: 1,
swappiness: 1,
},
};
let nt = normalize_nft_text(table);
assert_eq!(
host_firewall_drift_reason_from_text(&nt, &cfg),
Some("missing established/related allow".into())
);
}
#[test]
fn host_firewall_batch_script_does_not_include_delete_table() {
let cfg = Config {