rename -regitry to -schema-location, make its syntax more compatible to kubeval

This commit is contained in:
Yann Hamon 2020-10-18 14:28:19 +02:00
parent 472100550c
commit 0949b76f51
3 changed files with 33 additions and 31 deletions

View file

@ -42,8 +42,8 @@ Usage of ./bin/kubeconform:
number of routines to run in parallel (default 4) number of routines to run in parallel (default 4)
-output string -output string
output format - text, json (default "text") output format - text, json (default "text")
-registry value -schema-location value
override schemas registry path (can be specified multiple times) override schemas location search path (can be specified multiple times)
-skip string -skip string
comma-separated list of kinds to ignore comma-separated list of kinds to ignore
-strict -strict
@ -90,24 +90,24 @@ $ echo $?
* Validating a folder, increasing the number of parallel workers * Validating a folder, increasing the number of parallel workers
``` ```
$ ./bin/kubeconform -summary -n 16 fixtures $ ./bin/kubeconform -summary -n 16 fixtures
fixtures/multi_invalid.yaml - Service is invalid: Invalid type. Expected: integer, given: string fixtures/crd_schema.yaml - CustomResourceDefinition trainingjobs.sagemaker.aws.amazon.com failed validation: could not find schema for CustomResourceDefinition
fixtures/invalid.yaml - ReplicationController is invalid: Invalid type. Expected: [integer,null], given: string fixtures/invalid.yaml - ReplicationController bob is invalid: Invalid type. Expected: [integer,null], given: string
[...] [...]
Summary: 48 resources found in 25 files - Valid: 39, Invalid: 2, Errors: 7 Skipped: 0 Summary: 65 resources found in 34 files - Valid: 55, Invalid: 2, Errors: 8 Skipped: 0
``` ```
### Overriding schemas registries lookup order - CRD support ### Overriding schemas location - CRD support
When the `-registry` file is not used, kubeconform will default to downloading schemas from When the `-schema-location` file is not used, kubeconform will default to downloading schemas from
`kubernetesjsonschema.dev`. Kubeconform however supports the use of one, or multiple, custom schemas `https://kubernetesjsonschema.dev`. Kubeconform however supports the use of one, or multiple, custom schemas
registries - with access over HTTP or local filesystem. Kubeconform will lookup for schema definitions registries - with access over HTTP or local filesystem. Kubeconform will lookup for schema definitions
in each of them, in order, stopping as soon as a matching file is found. in each of them, in order, stopping as soon as a matching file is found.
All 3 following command lines are equivalent: All 3 following command lines are equivalent:
``` ```
$ ./bin/kubeconform fixtures/valid.yaml $ ./bin/kubeconform fixtures/valid.yaml
$ ./bin/kubeconform -registry kubernetesjsonschema.dev fixtures/valid.yaml $ ./bin/kubeconform -schema-location https://kubernetesjsonschema.dev fixtures/valid.yaml
$ ./bin/kubeconform -registry 'https://kubernetesjsonschema.dev/{{ .NormalizedVersion }}-standalone{{ .StrictSuffix }}/{{ .ResourceKind }}{{ .KindSuffix }}.json' fixtures/valid.yaml $ ./bin/kubeconform -schema-location 'https://kubernetesjsonschema.dev/{{ .NormalizedVersion }}-standalone{{ .StrictSuffix }}/{{ .ResourceKind }}{{ .KindSuffix }}.json' fixtures/valid.yaml
``` ```
To support validating CRDs, we need to convert OpenAPI files to JSON schema, storing the JSON schemas To support validating CRDs, we need to convert OpenAPI files to JSON schema, storing the JSON schemas
@ -115,7 +115,7 @@ in a local folder - for example schemas. Then we specify this folder as an addit
``` ```
# If the resource Kind is not found in kubernetesjsonschema.dev, also lookup in the schemas/ folder for a matching file # If the resource Kind is not found in kubernetesjsonschema.dev, also lookup in the schemas/ folder for a matching file
$ ./bin/kubeconform -registry kubernetesjsonschema.dev -registry 'schemas/{{ .ResourceKind }}{{ .KindSuffix }}.json' fixtures/custom-resource.yaml $ ./bin/kubeconform -registry kubernetesjsonschema.dev -schema-location 'schemas/{{ .ResourceKind }}{{ .KindSuffix }}.json' fixtures/custom-resource.yaml
``` ```
### Generating a JSON schema from an OpenAPI file ### Generating a JSON schema from an OpenAPI file

View file

@ -86,7 +86,7 @@
} }
@test "Pass when parsing a Custom Resource and using a local schema registry with appropriate CRD" { @test "Pass when parsing a Custom Resource and using a local schema registry with appropriate CRD" {
run bin/kubeconform -registry './fixtures/registry/{{ .ResourceKind }}{{ .KindSuffix }}.json' fixtures/test_crd.yaml run bin/kubeconform -schema-location './fixtures/registry/{{ .ResourceKind }}{{ .KindSuffix }}.json' fixtures/test_crd.yaml
[ "$status" -eq 0 ] [ "$status" -eq 0 ]
} }
@ -96,22 +96,22 @@
[ "$output" = "Summary: 1 resource found in 1 file - Valid: 1, Invalid: 0, Errors: 0 Skipped: 0" ] [ "$output" = "Summary: 1 resource found in 1 file - Valid: 1, Invalid: 0, Errors: 0 Skipped: 0" ]
} }
@test "Pass when using a valid, preset --registry" { @test "Pass when using a valid, preset -schema-location" {
run bin/kubeconform --registry kubernetesjsonschema.dev fixtures/valid.yaml run bin/kubeconform -schema-location https://kubernetesjsonschema.dev fixtures/valid.yaml
[ "$status" -eq 0 ] [ "$status" -eq 0 ]
} }
@test "Pass when using a valid HTTP --registry" { @test "Pass when using a valid HTTP -schema-location" {
run bin/kubeconform --registry 'https://kubernetesjsonschema.dev/{{ .NormalizedVersion }}-standalone{{ .StrictSuffix }}/{{ .ResourceKind }}{{ .KindSuffix }}.json' fixtures/valid.yaml run bin/kubeconform -schema-location 'https://kubernetesjsonschema.dev/{{ .NormalizedVersion }}-standalone{{ .StrictSuffix }}/{{ .ResourceKind }}{{ .KindSuffix }}.json' fixtures/valid.yaml
[ "$status" -eq 0 ] [ "$status" -eq 0 ]
} }
@test "Fail when using an invalid HTTP --registry" { @test "Fail when using an invalid HTTP -schema-location" {
run bin/kubeconform --registry 'http://foo' fixtures/valid.yaml run bin/kubeconform -schema-location 'http://foo' fixtures/valid.yaml
[ "$status" -eq 1 ] [ "$status" -eq 1 ]
} }
@test "Fail when using an invalid non-HTTP --registry" { @test "Fail when using an invalid non-HTTP -schema-location" {
run bin/kubeconform --registry 'foo' fixtures/valid.yaml run bin/kubeconform -schema-location 'foo' fixtures/valid.yaml
[ "$status" -eq 1 ] [ "$status" -eq 1 ]
} }

View file

@ -215,7 +215,7 @@ func getFiles(files []string, fileBatches chan []string, validationResults chan
} }
func realMain() int { func realMain() int {
var regs arrayParam var schemaLocationsParam arrayParam
var skipKindsCSV, k8sVersion, outputFormat string var skipKindsCSV, k8sVersion, outputFormat string
var summary, strict, verbose, ignoreMissingSchemas bool var summary, strict, verbose, ignoreMissingSchemas bool
var nWorkers int var nWorkers int
@ -223,7 +223,7 @@ func realMain() int {
var files []string var files []string
flag.StringVar(&k8sVersion, "k8sversion", "1.18.0", "version of Kubernetes to test against") flag.StringVar(&k8sVersion, "k8sversion", "1.18.0", "version of Kubernetes to test against")
flag.Var(&regs, "registry", "override schemas registry path (can be specified multiple times)") flag.Var(&schemaLocationsParam, "schema-location", "override schemas location search path (can be specified multiple times)")
flag.BoolVar(&ignoreMissingSchemas, "ignore-missing-schemas", false, "skip files with missing schemas instead of failing") flag.BoolVar(&ignoreMissingSchemas, "ignore-missing-schemas", false, "skip files with missing schemas instead of failing")
flag.BoolVar(&summary, "summary", false, "print a summary at the end") flag.BoolVar(&summary, "summary", false, "print a summary at the end")
flag.IntVar(&nWorkers, "n", 4, "number of routines to run in parallel") flag.IntVar(&nWorkers, "n", 4, "number of routines to run in parallel")
@ -244,18 +244,20 @@ func realMain() int {
return ok && isSkipKind return ok && isSkipKind
} }
registries := []registry.Registry{} if len(schemaLocationsParam) == 0 {
if len(regs) == 0 { schemaLocationsParam = append(schemaLocationsParam, "https://kubernetesjsonschema.dev") // if not specified, default behaviour is to use kubernetesjson-schema.dev as registry
regs = append(regs, "kubernetesjsonschema.dev") // if not specified, default behaviour is to use kubernetesjson-schema.dev as registry
} }
for _, reg := range regs { registries := []registry.Registry{}
if reg == "kubernetesjsonschema.dev" { for _, schemaLocation := range schemaLocationsParam {
registries = append(registries, registry.NewHTTPRegistry("https://kubernetesjsonschema.dev/{{ .NormalizedVersion }}-standalone{{ .StrictSuffix }}/{{ .ResourceKind }}{{ .KindSuffix }}.json", strict)) if strings.HasSuffix(schemaLocation, "json") { // If we dont specify a full templated path, we assume the paths of kubernetesjsonschema.dev
} else if strings.HasPrefix(reg, "http") { schemaLocation += "/{{ .NormalizedVersion }}-standalone{{ .StrictSuffix }}/{{ .ResourceKind }}{{ .KindSuffix }}.json"
registries = append(registries, registry.NewHTTPRegistry(reg, strict)) }
if strings.HasPrefix(schemaLocation, "http") {
registries = append(registries, registry.NewHTTPRegistry(schemaLocation, strict))
} else { } else {
registries = append(registries, registry.NewLocalRegistry(reg, strict)) registries = append(registries, registry.NewLocalRegistry(schemaLocation, strict))
} }
} }