110 lines
4.2 KiB
Go
110 lines
4.2 KiB
Go
package db
|
|||
|
|
|
||
|
|
import (
|
||
|
|
"errors"
|
||
|
|
"reflect"
|
||
|
|
"testing"
|
||
|
|
)
|
||
|
|
|
||
|
|
// RegistryBreakdown and RegistryBreakdownList over the slice of the registry
|
||
|
|
// filter. Run 1 holds three addresses (cycle 1), run 2 a re-check of .1 (cycle 2).
|
||
|
|
func TestRegistryBreakdown(t *testing.T) {
|
||
|
|
d, ctx := newTestDB(t)
|
||
|
|
const a1, a2, a3 = "10.0.0.1", "10.0.0.2", "10.0.1.1"
|
||
|
|
submit(t, d, RunManual, a1, a2, a3)
|
||
|
|
s1, s2 := InboundSource(1), InboundSource(2)
|
||
|
|
for _, c := range []struct {
|
||
|
|
addr, source, typ, target string
|
||
|
|
ok bool
|
||
|
|
}{
|
||
|
|
{a1, SourceEgress, "https", "T1", true}, {a1, SourceEgress, "https", "T2", false},
|
||
|
|
{a1, s1, "tcp-22", a1, true}, {a1, s1, "tcp-443", a1, false}, {a1, s2, "tcp-443", a1, true},
|
||
|
|
{a2, SourceEgress, "https", "T1", false}, {a2, SourceEgress, "https", "T2", false}, {a2, s1, "tcp-443", a2, true},
|
||
|
|
{a3, SourceEgress, "https", "T1", true}, {a3, SourceEgress, "https", "T3", true},
|
||
|
|
} {
|
||
|
|
addCheck(t, d, c.addr, c.source, c.typ, c.target, c.ok)
|
||
|
|
}
|
||
|
|
finish(t, d, a1, ResultPartial, -1)
|
||
|
|
finish(t, d, a2, ResultFail, -1)
|
||
|
|
finish(t, d, a3, ResultPass, -1)
|
||
|
|
run1 := runs(t, d)[0].ID
|
||
|
|
|
||
|
|
submit(t, d, RunManual, a1)
|
||
|
|
addCheck(t, d, a1, SourceEgress, "https", "T1", false)
|
||
|
|
addCheck(t, d, a1, SourceEgress, "https", "T2", true)
|
||
|
|
finish(t, d, a1, ResultPartial, -1)
|
||
|
|
|
||
|
|
eg := RegistryFilter{Level: LevelEgress, Family: "https"}
|
||
|
|
in := RegistryFilter{Level: LevelIngress, Family: "tcp"}
|
||
|
|
for _, tc := range []struct {
|
||
|
|
name string
|
||
|
|
f RegistryFilter
|
||
|
|
group string
|
||
|
|
addrs int
|
||
|
|
want []BreakdownRow
|
||
|
|
}{
|
||
|
|
{"egress, run 1: most successful first", withRun(eg, run1), BreakdownTarget, 3,
|
||
|
|
[]BreakdownRow{{"T1", 3, 2}, {"T3", 1, 1}, {"T2", 2, 0}}},
|
||
|
|
{"egress, newest cycle; equal counts by key", eg, BreakdownTarget, 3,
|
||
|
|
[]BreakdownRow{{"T1", 3, 1}, {"T2", 2, 1}, {"T3", 1, 1}}},
|
||
|
|
{"egress, subnet", RegistryFilter{RunID: run1, Level: LevelEgress, Family: "https", Subnet: "10.0.0.0/24"}, BreakdownTarget, 2,
|
||
|
|
[]BreakdownRow{{"T1", 2, 1}, {"T2", 2, 0}}},
|
||
|
|
{"egress, status in scope", RegistryFilter{RunID: run1, Level: LevelEgress, Family: "https", LastResult: ResultFail}, BreakdownTarget, 1,
|
||
|
|
[]BreakdownRow{{"T1", 1, 0}, {"T2", 1, 0}}},
|
||
|
|
{"ingress by site, checks not addresses", withRun(in, run1), BreakdownSite, 2,
|
||
|
|
[]BreakdownRow{{s1, 3, 2}, {s2, 1, 1}}},
|
||
|
|
{"egress tls does not exist", RegistryFilter{Level: LevelEgress, Family: "tls"}, BreakdownTarget, 0, nil},
|
||
|
|
} {
|
||
|
|
b, err := d.RegistryBreakdown(ctx, tc.f)
|
||
|
|
if err != nil {
|
||
|
|
t.Fatalf("%s: %v", tc.name, err)
|
||
|
|
}
|
||
|
|
if b.Group != tc.group || b.Addresses != tc.addrs || !reflect.DeepEqual(b.Rows, tc.want) {
|
||
|
|
t.Errorf("%s: group=%s addresses=%d rows=%v, want %s %d %v", tc.name, b.Group, b.Addresses, b.Rows, tc.group, tc.addrs, tc.want)
|
||
|
|
}
|
||
|
|
// The chart covers the addresses of the list.
|
||
|
|
if _, total, err := d.ListRegistryPage(ctx, tc.f, 10, 0); err != nil || total != b.Addresses {
|
||
|
|
t.Errorf("%s: list total=%d err=%v, chart addresses=%d", tc.name, total, err, b.Addresses)
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
// The list: failures first, then registry order; the key picks the group.
|
||
|
|
for _, tc := range []struct {
|
||
|
|
name string
|
||
|
|
f RegistryFilter
|
||
|
|
key string
|
||
|
|
want [][3]string // address, type, success
|
||
|
|
}{
|
||
|
|
{"egress T1", withRun(eg, run1), "T1", [][3]string{{a2, "https", "0"}, {a1, "https", "1"}, {a3, "https", "1"}}},
|
||
|
|
{"ingress site 1", withRun(in, run1), s1, [][3]string{{a1, "tcp-443", "0"}, {a1, "tcp-22", "1"}, {a2, "tcp-443", "1"}}},
|
||
|
|
} {
|
||
|
|
got, err := d.RegistryBreakdownList(ctx, tc.f, tc.key)
|
||
|
|
if err != nil {
|
||
|
|
t.Fatalf("%s: %v", tc.name, err)
|
||
|
|
}
|
||
|
|
var rows [][3]string
|
||
|
|
for _, c := range got {
|
||
|
|
ok := "0"
|
||
|
|
if c.Success {
|
||
|
|
ok = "1"
|
||
|
|
}
|
||
|
|
rows = append(rows, [3]string{c.IPAddress, c.CheckType, ok})
|
||
|
|
}
|
||
|
|
if !reflect.DeepEqual(rows, tc.want) {
|
||
|
|
t.Errorf("%s: %v, want %v", tc.name, rows, tc.want)
|
||
|
|
}
|
||
|
|
}
|
||
|
|
if _, err := d.RegistryBreakdownList(ctx, withRun(eg, run1), "nope"); !errors.Is(err, ErrNotFound) {
|
||
|
|
t.Errorf("unknown key: %v", err)
|
||
|
|
}
|
||
|
|
for _, f := range []RegistryFilter{{}, {Level: LevelEgress}, {Family: "https"}, {Level: "sideways", Family: "https"}} {
|
||
|
|
if _, err := d.RegistryBreakdown(ctx, f); !errors.Is(err, ErrValidation) {
|
||
|
|
t.Errorf("%+v: %v", f, err)
|
||
|
|
}
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
func withRun(f RegistryFilter, run int64) RegistryFilter {
|
||
|
|
f.RunID = run
|
||
|
|
return f
|
||
|
|
}
|