diff --git a/pkg/output/junit.go b/pkg/output/junit.go
index d19a817..19177d3 100644
--- a/pkg/output/junit.go
+++ b/pkg/output/junit.go
@@ -10,9 +10,10 @@ import (
"bufio"
"encoding/xml"
"fmt"
- "github.com/yannh/kubeconform/pkg/validator"
"io"
"time"
+
+ "github.com/yannh/kubeconform/pkg/validator"
)
type TestSuiteCollection struct {
@@ -105,8 +106,6 @@ func (o *junito) Write(result validator.Result) error {
o.suites[result.Resource.Path] = suite
}
- suite.Tests++
-
sig, _ := result.Resource.Signature()
var objectName string
if len(sig.Namespace) > 0 {
@@ -121,21 +120,20 @@ func (o *junito) Write(result validator.Result) error {
case validator.Valid:
o.nValid++
case validator.Invalid:
- suite.Failures++
o.nInvalid++
failure := TestCaseError{Message: result.Err.Error()}
testCase.Failure = append(testCase.Failure, failure)
case validator.Error:
- suite.Errors++
o.nErrors++
testCase.Error = &TestCaseError{Message: result.Err.Error()}
case validator.Skipped:
- suite.Skipped++
testCase.Skipped = &TestCaseSkipped{}
o.nSkipped++
case validator.Empty:
+ return nil
}
+ suite.Tests++
suite.Cases = append(suite.Cases, testCase)
return nil
diff --git a/pkg/output/junit_test.go b/pkg/output/junit_test.go
index 044e631..c8e6ee6 100644
--- a/pkg/output/junit_test.go
+++ b/pkg/output/junit_test.go
@@ -2,73 +2,36 @@ package output
import (
"bytes"
- "github.com/yannh/kubeconform/pkg/resource"
"regexp"
"testing"
- "github.com/yannh/kubeconform/pkg/validator"
+ "github.com/yannh/kubeconform/pkg/resource"
- "github.com/beevik/etree"
+ "github.com/yannh/kubeconform/pkg/validator"
)
-func isNumeric(s string) bool {
- matched, _ := regexp.MatchString("^\\d+(\\.\\d+)?$", s)
- return matched
-}
-
-func TestJUnitWrite(t *testing.T) {
+func TestJunitWrite(t *testing.T) {
for _, testCase := range []struct {
name string
withSummary bool
isStdin bool
verbose bool
results []validator.Result
- evaluate func(d *etree.Document)
+ expect string
}{
{
- "empty document",
- false,
+ "an empty result",
+ true,
false,
false,
[]validator.Result{},
- func(d *etree.Document) {
- root := d.FindElement("/testsuites")
- if root == nil {
- t.Errorf("Can't find root testsuite element")
- return
- }
- for _, attr := range root.Attr {
- switch attr.Key {
- case "time":
- case "tests":
- case "failures":
- case "disabled":
- case "errors":
- if !isNumeric(attr.Value) {
- t.Errorf("Expected a number for /testsuites/@%s", attr.Key)
- }
- continue
- case "name":
- if attr.Value != "kubeconform" {
- t.Errorf("Expected 'kubeconform' for /testsuites/@name")
- }
- continue
- default:
- t.Errorf("Unknown attribute /testsuites/@%s", attr.Key)
- continue
- }
- }
- suites := root.SelectElements("testsuite")
- if len(suites) != 0 {
- t.Errorf("No testsuite elements should be generated when there are no resources")
- }
- },
+ "\n",
},
{
- "a single deployment, verbose, with summary",
+ "a single deployment, summary, no verbose",
true,
false,
- true,
+ false,
[]validator.Result{
{
Resource: resource.Resource{
@@ -77,84 +40,52 @@ func TestJUnitWrite(t *testing.T) {
kind: Deployment
metadata:
name: "my-app"
- namespace: "my-namespace"
`),
},
Status: validator.Valid,
Err: nil,
},
},
- func(d *etree.Document) {
- suites := d.FindElements("//testsuites/testsuite")
- if len(suites) != 1 {
- t.Errorf("Expected exactly 1 testsuite element, got %d", len(suites))
- return
- }
- suite := suites[0]
- for _, attr := range suite.Attr {
- switch attr.Key {
- case "name":
- if attr.Value != "deployment.yml" {
- t.Errorf("Test suite name should be the resource path")
- }
- continue
- case "id":
- if attr.Value != "1" {
- t.Errorf("testsuite/@id should be 1")
- }
- continue
- case "tests":
- if attr.Value != "1" {
- t.Errorf("testsuite/@tests should be 1")
- }
- continue
- case "failures":
- if attr.Value != "0" {
- t.Errorf("testsuite/@failures should be 0")
- }
- continue
- case "errors":
- if attr.Value != "0" {
- t.Errorf("testsuite/@errors should be 0")
- }
- continue
- case "disabled":
- if attr.Value != "0" {
- t.Errorf("testsuite/@disabled should be 0")
- }
- continue
- case "skipped":
- if attr.Value != "0" {
- t.Errorf("testsuite/@skipped should be 0")
- }
- continue
- default:
- t.Errorf("Unknown testsuite attribute %s", attr.Key)
- continue
- }
- }
- testcases := suite.SelectElements("testcase")
- if len(testcases) != 1 {
- t.Errorf("Expected exactly 1 testcase, got %d", len(testcases))
- return
- }
- testcase := testcases[0]
- if testcase.SelectAttrValue("name", "") != "my-namespace/my-app" {
- t.Errorf("Test case name should be namespace / name")
- }
- if testcase.SelectAttrValue("classname", "") != "Deployment@apps/v1" {
- t.Errorf("Test case class name should be resource kind @ api version")
- }
- if testcase.SelectElement("skipped") != nil {
- t.Errorf("skipped element should not be generated if the kind was not skipped")
- }
- if testcase.SelectElement("error") != nil {
- t.Errorf("error element should not be generated if there was no error")
- }
- if len(testcase.SelectElements("failure")) != 0 {
- t.Errorf("failure elements should not be generated if there were no failures")
- }
+ "\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ "\n",
+ },
+ {
+ "a deployment, an empty resource, summary, no verbose",
+ true,
+ false,
+ false,
+ []validator.Result{
+ {
+ Resource: resource.Resource{
+ Path: "deployment.yml",
+ Bytes: []byte(`apiVersion: apps/v1
+kind: Deployment
+metadata:
+ name: "my-app"
+`),
+ },
+ Status: validator.Valid,
+ Err: nil,
+ },
+ {
+ Resource: resource.Resource{
+ Path: "deployment.yml",
+ Bytes: []byte(`#A single comment`),
+ },
+ Status: validator.Empty,
+ Err: nil,
+ },
},
+ "\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ "\n",
},
} {
w := new(bytes.Buffer)
@@ -165,9 +96,13 @@ metadata:
}
o.Flush()
- doc := etree.NewDocument()
- doc.ReadFromString(w.String())
+ // We remove the time, which will be different every time, before the comparison
+ output := w.String()
+ r := regexp.MustCompile(`time="[^"]*"`)
+ output = r.ReplaceAllString(output, "time=\"\"")
- testCase.evaluate(doc)
+ if output != testCase.expect {
+ t.Errorf("%s - expected:, got:\n%s\n%s", testCase.name, testCase.expect, output)
+ }
}
}
diff --git a/pkg/output/tap_test.go b/pkg/output/tap_test.go
index 3cce4a2..8fce042 100644
--- a/pkg/output/tap_test.go
+++ b/pkg/output/tap_test.go
@@ -8,7 +8,7 @@ import (
"github.com/yannh/kubeconform/pkg/validator"
)
-func TestTextWrite(t *testing.T) {
+func TestTapWrite(t *testing.T) {
for _, testCase := range []struct {
name string
withSummary bool
diff --git a/pkg/output/text_test.go b/pkg/output/text_test.go
index a3ca187..39df12a 100644
--- a/pkg/output/text_test.go
+++ b/pkg/output/text_test.go
@@ -8,7 +8,7 @@ import (
"github.com/yannh/kubeconform/pkg/validator"
)
-func TestTapWrite(t *testing.T) {
+func TestTextWrite(t *testing.T) {
for _, testCase := range []struct {
name string
withSummary bool
diff --git a/pkg/validator/validator_test.go b/pkg/validator/validator_test.go
index cd8b2e4..d8e7751 100644
--- a/pkg/validator/validator_test.go
+++ b/pkg/validator/validator_test.go
@@ -1,13 +1,12 @@
package validator
import (
- "github.com/yannh/kubeconform/pkg/registry"
- "testing"
+ "github.com/yannh/kubeconform/pkg/registry"
+ "testing"
- "github.com/yannh/kubeconform/pkg/resource"
+ "github.com/yannh/kubeconform/pkg/resource"
)
-
type mockRegistry struct {
SchemaDownloader func() ([]byte, error)
}
@@ -22,14 +21,13 @@ func (m mockRegistry) DownloadSchema(resourceKind, resourceAPIVersion, k8sVersio
return m.SchemaDownloader()
}
-
func TestValidate(t *testing.T) {
for i, testCase := range []struct {
- name string
- rawResource, schemaRegistry1 []byte
- schemaRegistry2 []byte
- ignoreMissingSchema bool
- expect Status
+ name string
+ rawResource, schemaRegistry1 []byte
+ schemaRegistry2 []byte
+ ignoreMissingSchema bool
+ expect Status
}{
{
"valid resource",
@@ -292,11 +290,11 @@ lastName: bar
} {
val := v{
opts: Opts{
- SkipKinds: map[string]struct{}{},
- RejectKinds: map[string]struct{}{},
+ SkipKinds: map[string]struct{}{},
+ RejectKinds: map[string]struct{}{},
IgnoreMissingSchemas: testCase.ignoreMissingSchema,
},
- schemaCache: nil,
+ schemaCache: nil,
schemaDownload: downloadSchema,
regs: []registry.Registry{
newMockRegistry(func() ([]byte, error) {