feat(docker, firewall): Add stateful network connection check and optimize NAT rules
continuous-integration/drone/push Build is passing
continuous-integration/drone/push Build is passing
This adds an IsConnected method to verify if a container is already connected to a network with the expected IP, preventing redundant operations. In reconcileIPs, it skips reconnections if the state is correct. In applyNATRule, MASQUERADE is now applied in the same namespace as DNAT (container or host) for consistent and accurate rule application.
This commit is contained in:
@@ -273,6 +273,16 @@ func (m *Manager) InsertPreroutingRule(sourceIP, proto, sourcePort, targetIP, ta
|
||||
|
||||
// InsertPreroutingRuleOnInterface inserts a DNAT PREROUTING rule on a specific interface
|
||||
func (m *Manager) InsertPreroutingRuleOnInterface(iface, proto, sourcePort, targetIP, targetPort, comment string) error {
|
||||
logger.Info("IPTABLES: checking PREROUTING DNAT rule on interface %s: proto=%s dport=%s -> %s:%s comment=%q",
|
||||
iface, proto, sourcePort, targetIP, targetPort, comment)
|
||||
|
||||
// Check if rule already exists (idempotent: don't re-apply)
|
||||
existing := m.getLineNumbers("PREROUTING", "nat", comment, "DNAT", targetIP)
|
||||
if len(existing) > 0 {
|
||||
logger.Debug("IPTABLES: PREROUTING DNAT rule already exists on %s (lines=%v), skipping", iface, existing)
|
||||
return nil
|
||||
}
|
||||
|
||||
logger.Info("IPTABLES: inserting PREROUTING DNAT rule on interface %s: proto=%s dport=%s -> %s:%s comment=%q",
|
||||
iface, proto, sourcePort, targetIP, targetPort, comment)
|
||||
args := []string{
|
||||
@@ -288,13 +298,18 @@ func (m *Manager) InsertPreroutingRuleOnInterface(iface, proto, sourcePort, targ
|
||||
|
||||
// InsertPostroutingMasquerade inserts a MASQUERADE POSTROUTING rule on the host
|
||||
func (m *Manager) InsertPostroutingMasquerade(sourceCIDR, proto, sourcePort, comment string) error {
|
||||
logger.Info("IPTABLES: inserting POSTROUTING MASQUERADE rule: src=%s proto=%s sport=%s comment=%q",
|
||||
logger.Info("IPTABLES: checking POSTROUTING MASQUERADE rule: src=%s proto=%s sport=%s comment=%q",
|
||||
sourceCIDR, proto, sourcePort, comment)
|
||||
patterns := []string{"MASQUERADE", comment, sourceCIDR, sourcePort}
|
||||
if err := m.deleteMatchingLines("POSTROUTING", "nat", patterns...); err != nil {
|
||||
return fmt.Errorf("failed to delete old POSTROUTING rules: %w", err)
|
||||
|
||||
// Check if rule already exists (idempotent: don't re-apply)
|
||||
existing := m.getLineNumbers("POSTROUTING", "nat", comment, "MASQUERADE", sourceCIDR)
|
||||
if len(existing) > 0 {
|
||||
logger.Debug("IPTABLES: POSTROUTING MASQUERADE rule already exists (lines=%v), skipping", existing)
|
||||
return nil
|
||||
}
|
||||
|
||||
logger.Info("IPTABLES: inserting POSTROUTING MASQUERADE rule: src=%s proto=%s sport=%s comment=%q",
|
||||
sourceCIDR, proto, sourcePort, comment)
|
||||
args := []string{
|
||||
"-w", "-t", "nat", "-I", "POSTROUTING",
|
||||
"-s", sourceCIDR,
|
||||
|
||||
Reference in New Issue
Block a user