From 26d4f9b5d9bf2dd1726f55f10aa670eec01ae692 Mon Sep 17 00:00:00 2001 From: Lukasz Piatkowski Date: Fri, 17 May 2019 14:18:01 +0200 Subject: [PATCH 1/3] fix missing -exist option to ipset add --- pkg/nettools/ipset.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pkg/nettools/ipset.go b/pkg/nettools/ipset.go index be943ec..6b217fb 100644 --- a/pkg/nettools/ipset.go +++ b/pkg/nettools/ipset.go @@ -258,7 +258,7 @@ func (h *execIPSetHelper) getIPSetEntries(name string) ([]string, error) { } func (h *execIPSetHelper) addElementToSet(setName, elementTypeName string, element fmt.Stringer) error { - res := h.exec.RunCommand("ipset", "add", setName, element.String()) + res := h.exec.RunCommand("ipset", "add", setName, element.String(), "-exist") if res.Err != nil || res.ExitCode != 0 { log.Errorf("Error adding %s %s to ipset %s: %v, stdErr: %s", elementTypeName, element.String(), setName, res.Err, res.StdErr) From 6247a272d0c776b3fcce409a457ae8ff23bbf835 Mon Sep 17 00:00:00 2001 From: Lukasz Piatkowski Date: Mon, 27 May 2019 16:20:51 +0200 Subject: [PATCH 2/3] new tests --- pkg/nettools/iptables.go | 9 ++- pkg/nettools/iptables_inputs_test.go | 110 +++++++++++++++++++++++++++ 2 files changed, 116 insertions(+), 3 deletions(-) create mode 100644 pkg/nettools/iptables_inputs_test.go diff --git a/pkg/nettools/iptables.go b/pkg/nettools/iptables.go index f2acf8c..c7ef5c7 100644 --- a/pkg/nettools/iptables.go +++ b/pkg/nettools/iptables.go @@ -34,8 +34,10 @@ var ( const ( iptablesRetries = 3 iptablesRetriesDelayMSec = 100 - // this uses awk to list the content of a single chain in a table using iptables-save command - awkIptablesSaveMagicFilter = "iptables-save | awk -v table=%s -v chain=%s " + + iptablesSaveBin = "iptables-save" + // AwkIptablesSaveMagicFilter defines awk program that filters the content of a + // single chain in a table from iptables-save command output + AwkIptablesSaveMagicFilter = "awk -v table=%s -v chain=%s " + `'$0 ~ "^*"table"$" {in_table=1};$1 ~ "^COMMIT$" {in_table=0};in_table == 1 && $2 ~ "^"chain"$" {print $0}'` ) @@ -298,7 +300,8 @@ func (h *execIPTablesHelper) runExistsRule(tableName, chainName, selector, comme } func (h *execIPTablesHelper) listRules(tableName, chainName, regexpFilter string) ([]string, error) { - shCommand := fmt.Sprintf(awkIptablesSaveMagicFilter, tableName, chainName) + shCommand := fmt.Sprintf("%s | %s", iptablesSaveBin, + fmt.Sprintf(AwkIptablesSaveMagicFilter, tableName, chainName)) res := h.exec.RunCommandWithRetriesAndDelay(iptablesRetries, iptablesRetriesDelayMSec, []int{0}, "sh", "-c", shCommand) if res.Err != nil || res.StdErr != "" { diff --git a/pkg/nettools/iptables_inputs_test.go b/pkg/nettools/iptables_inputs_test.go new file mode 100644 index 0000000..b90a13e --- /dev/null +++ b/pkg/nettools/iptables_inputs_test.go @@ -0,0 +1,110 @@ +/* Copyright 2019 DevFactory FZ LLC + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + +http://www.apache.org/licenses/LICENSE-2.0 +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. */ + +package nettools_test + +import ( + "fmt" + "testing" + + "github.com/DevFactory/go-tools/pkg/linux/command" + "github.com/DevFactory/go-tools/pkg/nettools" + "github.com/stretchr/testify/assert" +) + +const iptables_save_output = `# Generated by iptables-save v1.6.0 on Thu May 16 12:08:08 2019 +*mangle +:PREROUTING ACCEPT [3857:1791517] +:INPUT ACCEPT [3857:1791517] +:FORWARD ACCEPT [0:0] +:OUTPUT ACCEPT [3499:273893] +:POSTROUTING ACCEPT [3499:273893] +:SNM-PREROUTING - [0:0] +-A PREROUTING -m comment --comment "\"for SNM\"" -j SNM-PREROUTING +COMMIT +# Completed on Thu May 16 12:08:08 2019 +# Generated by iptables-save v1.6.0 on Thu May 16 12:08:08 2019 +*filter +:INPUT ACCEPT [7228:2692747] +:FORWARD ACCEPT [0:0] +:OUTPUT ACCEPT [5979:577631] +:KUBE-FORWARD - [0:0] +-A FORWARD -m comment --comment "kubernetes forwarding rules" -j KUBE-FORWARD +COMMIT +# Completed on Thu May 16 12:08:08 2019 +# Generated by iptables-save v1.6.0 on Thu May 16 12:08:08 2019 +*nat +:PREROUTING ACCEPT [21:964] +:INPUT ACCEPT [21:964] +:OUTPUT ACCEPT [36:2320] +:POSTROUTING ACCEPT [36:2320] +:KUBE-FIREWALL - [0:0] +:KUBE-LOAD-BALANCER - [0:0] +:KUBE-MARK-MASQ - [0:0] +:KUBE-NODE-PORT - [0:0] +:KUBE-POSTROUTING - [0:0] +:KUBE-SERVICES - [0:0] +:SNM-POSTROUTING-MASQ - [0:0] +:SNM-PREROUTING - [0:0] +-A PREROUTING -m comment --comment "kubernetes service portals" -j KUBE-SERVICES +-A PREROUTING -m comment --comment "\"for SNM\"" -j SNM-PREROUTING +-A OUTPUT -m comment --comment "kubernetes service portals" -j KUBE-SERVICES +-A POSTROUTING -m comment --comment "kubernetes postrouting rules" -j KUBE-POSTROUTING +-A POSTROUTING -j KUBE-POSTROUTING +-A POSTROUTING -m comment --comment "\"for SNM\"" -j SNM-POSTROUTING-MASQ +-A SNM-POSTROUTING-MASQ -m mark --mark 0x100000/0x100000 -m comment --comment "\"masquerade traffic marked in PREROUTING rules as destined for services\"" -j MASQUERADE +COMMIT +# Completed on Thu May 16 12:08:08 2019` + +func Test_execIPTablesHelper_RunAWK(t *testing.T) { + tests := []struct { + name string + input string + chain string + expected command.ExecResult + }{ + { + name: "match empty", + input: iptables_save_output, + chain: "SNM-PREROUTING", + expected: command.ExecResult{ + ExitCode: 0, + StdOut: "", + StdErr: "", + }, + }, + { + name: "match 1 rule", + input: iptables_save_output, + chain: "PREROUTING", + expected: command.ExecResult{ + ExitCode: 0, + StdOut: `-A PREROUTING -m comment --comment "\"for SNM\"" -j SNM-PREROUTING` + "\n", + StdErr: "", + }, + }, + } + exec := command.NewExecutor() + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + cmd := fmt.Sprintf("echo '%s' | %s", iptables_save_output, + fmt.Sprintf(nettools.AwkIptablesSaveMagicFilter, "mangle", tt.chain)) + res := exec.RunCommand("sh", "-c", cmd) + assert.Equal(t, tt.expected.Err, res.Err) + assert.Equal(t, tt.expected.ExitCode, res.ExitCode) + assert.Equal(t, tt.expected.StdOut, res.StdOut) + assert.Equal(t, tt.expected.StdErr, res.StdErr) + assert.True(t, res.Duration > 0) + }) + } +} From c3c1c137e0ace1c0cbdfccd1ffd48e6624d3743f Mon Sep 17 00:00:00 2001 From: Lukasz Piatkowski Date: Mon, 27 May 2019 16:31:26 +0200 Subject: [PATCH 3/3] tests fixed --- pkg/nettools/ipset_test.go | 12 ++++++------ pkg/nettools/iptables_test.go | 2 +- 2 files changed, 7 insertions(+), 7 deletions(-) diff --git a/pkg/nettools/ipset_test.go b/pkg/nettools/ipset_test.go index 8adf30e..270c97f 100644 --- a/pkg/nettools/ipset_test.go +++ b/pkg/nettools/ipset_test.go @@ -190,11 +190,11 @@ func Test_execIPSetHelper_EnsureSetHasOnly(t *testing.T) { Returned: netth.ExecResultOKNoOutput(), }, { - Expected: "ipset add 12341234abc 127.0.0.1", + Expected: "ipset add 12341234abc 127.0.0.1 -exist", Returned: netth.ExecResultOKNoOutput(), }, { - Expected: "ipset add 12341234abc 127.0.0.2", + Expected: "ipset add 12341234abc 127.0.0.2 -exist", Returned: netth.ExecResultOKNoOutput(), }, }, @@ -230,7 +230,7 @@ func Test_execIPSetHelper_EnsureSetHasOnly(t *testing.T) { Returned: execResultIpsetIPs(), }, { - Expected: "ipset add 12341234abc 127.0.0.3", + Expected: "ipset add 12341234abc 127.0.0.3 -exist", Returned: netth.ExecResultOKNoOutput(), }, { @@ -344,11 +344,11 @@ func Test_execIPSetHelper_EnsureSetHasOnlyNetPort(t *testing.T) { Returned: netth.ExecResultOKNoOutput(), }, { - Expected: fmt.Sprintf("ipset add 12341234abc %s", np1), + Expected: fmt.Sprintf("ipset add 12341234abc %s -exist", np1), Returned: netth.ExecResultOKNoOutput(), }, { - Expected: fmt.Sprintf("ipset add 12341234abc %s", np2), + Expected: fmt.Sprintf("ipset add 12341234abc %s -exist", np2), Returned: netth.ExecResultOKNoOutput(), }, }, @@ -384,7 +384,7 @@ func Test_execIPSetHelper_EnsureSetHasOnlyNetPort(t *testing.T) { Returned: execResultIpsetNetPorts(), }, { - Expected: fmt.Sprintf("ipset add 12341234abc %s", np3), + Expected: fmt.Sprintf("ipset add 12341234abc %s -exist", np3), Returned: netth.ExecResultOKNoOutput(), }, { diff --git a/pkg/nettools/iptables_test.go b/pkg/nettools/iptables_test.go index 2cf85ea..9339018 100644 --- a/pkg/nettools/iptables_test.go +++ b/pkg/nettools/iptables_test.go @@ -29,7 +29,7 @@ import ( const ( awkIPTablesForNatTest = "sh -c iptables-save | awk -v table=nat -v chain=test " + - `'$0 ~ "^\*"table"$" {in_table=1};$1 ~ "^COMMIT$" {in_table=0};in_table == 1 && $2 ~ "^"chain"$" {print $0}'` + `'$0 ~ "^*"table"$" {in_table=1};$1 ~ "^COMMIT$" {in_table=0};in_table == 1 && $2 ~ "^"chain"$" {print $0}'` ) func Test_execIPTablesHelper_EnsureChainExists(t *testing.T) {