Skip to content

Commit

Permalink
Merge pull request #630 from justinsb/strip_crd_status
Browse files Browse the repository at this point in the history
🐛 CRD generation: remove status before writing
  • Loading branch information
k8s-ci-robot committed Feb 25, 2022
2 parents 99e7fbc + 4e829c2 commit 8cb5ce8
Show file tree
Hide file tree
Showing 9 changed files with 61 additions and 36 deletions.
9 changes: 8 additions & 1 deletion pkg/crd/gen.go
Original file line number Diff line number Diff line change
Expand Up @@ -85,6 +85,13 @@ func (Generator) CheckFilter() loader.NodeFilter {
func (Generator) RegisterMarkers(into *markers.Registry) error {
return crdmarkers.Register(into)
}

// transformRemoveCRDStatus ensures we do not write the CRD status field.
func transformRemoveCRDStatus(obj map[string]interface{}) error {
delete(obj, "status")
return nil
}

func (g Generator) Generate(ctx *genall.GenerationContext) error {
parser := &Parser{
Collector: ctx.Collector,
Expand Down Expand Up @@ -145,7 +152,7 @@ func (g Generator) Generate(ctx *genall.GenerationContext) error {
} else {
fileName = fmt.Sprintf("%s_%s.%s.yaml", crdRaw.Spec.Group, crdRaw.Spec.Names.Plural, crdVersions[i])
}
if err := ctx.WriteYAML(fileName, crd); err != nil {
if err := ctx.WriteYAML(fileName, []interface{}{crd}, genall.WithTransform(transformRemoveCRDStatus)); err != nil {
return err
}
}
Expand Down
6 changes: 0 additions & 6 deletions pkg/crd/spec.go
Original file line number Diff line number Diff line change
Expand Up @@ -164,11 +164,5 @@ func (p *Parser) NeedCRDFor(groupKind schema.GroupKind, maxDescLen *int) {
packages[0].AddError(fmt.Errorf("CRD for %s with version(s) %v does not serve any version", groupKind, crd.Spec.Versions))
}

// NB(directxman12): CRD's status doesn't have omitempty markers, which means things
// get serialized as null, which causes the validator to freak out. Manually set
// these to empty till we get a better solution.
crd.Status.Conditions = []apiext.CustomResourceDefinitionCondition{}
crd.Status.StoredVersions = []string{}

p.CustomResourceDefinitions[groupKind] = crd
}
6 changes: 0 additions & 6 deletions pkg/crd/testdata/gen/bar.example.com_foos.v1beta1.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -48,9 +48,3 @@ spec:
- name: foo
served: true
storage: true
status:
acceptedNames:
kind: ""
plural: ""
conditions: []
storedVersions: []
6 changes: 0 additions & 6 deletions pkg/crd/testdata/gen/bar.example.com_foos.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -48,9 +48,3 @@ spec:
type: object
served: true
storage: true
status:
acceptedNames:
kind: ""
plural: ""
conditions: []
storedVersions: []
6 changes: 0 additions & 6 deletions pkg/crd/testdata/plural/plural.example.com_testquotas.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -37,9 +37,3 @@ spec:
type: object
served: true
storage: true
status:
acceptedNames:
kind: ""
plural: ""
conditions: []
storedVersions: []
6 changes: 0 additions & 6 deletions pkg/crd/testdata/testdata.kubebuilder.io_cronjobs.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -7498,9 +7498,3 @@ spec:
storage: false
subresources:
status: {}
status:
acceptedNames:
kind: ""
plural: ""
conditions: []
storedVersions: []
54 changes: 51 additions & 3 deletions pkg/genall/genall.go
Original file line number Diff line number Diff line change
Expand Up @@ -17,13 +17,14 @@ limitations under the License.
package genall

import (
"encoding/json"
"fmt"
"io"
"io/ioutil"
"os"

"golang.org/x/tools/go/packages"
"sigs.k8s.io/yaml"
rawyaml "gopkg.in/yaml.v2"

"sigs.k8s.io/controller-tools/pkg/loader"
"sigs.k8s.io/controller-tools/pkg/markers"
Expand Down Expand Up @@ -120,18 +121,30 @@ type GenerationContext struct {
InputRule
}

// WriteYAMLOptions implements the Options Pattern for WriteYAML.
type WriteYAMLOptions struct {
transform func(obj map[string]interface{}) error
}

// WithTransform applies a transformation to objects just before writing them.
func WithTransform(transform func(obj map[string]interface{}) error) *WriteYAMLOptions {
return &WriteYAMLOptions{
transform: transform,
}
}

// WriteYAML writes the given objects out, serialized as YAML, using the
// context's OutputRule. Objects are written as separate documents, separated
// from each other by `---` (as per the YAML spec).
func (g GenerationContext) WriteYAML(itemPath string, objs ...interface{}) error {
func (g GenerationContext) WriteYAML(itemPath string, objs []interface{}, options ...*WriteYAMLOptions) error {
out, err := g.Open(nil, itemPath)
if err != nil {
return err
}
defer out.Close()

for _, obj := range objs {
yamlContent, err := yaml.Marshal(obj)
yamlContent, err := yamlMarshal(obj, options...)
if err != nil {
return err
}
Expand All @@ -147,6 +160,41 @@ func (g GenerationContext) WriteYAML(itemPath string, objs ...interface{}) error
return nil
}

// yamlMarshal is based on sigs.k8s.io/yaml.Marshal, but allows for transforming the final data before writing.
func yamlMarshal(o interface{}, options ...*WriteYAMLOptions) ([]byte, error) {
j, err := json.Marshal(o)
if err != nil {
return nil, fmt.Errorf("error marshaling into JSON: %v", err)
}

return yamlJSONToYAMLWithFilter(j, options...)
}

// yamlJSONToYAMLWithFilter is based on sigs.k8s.io/yaml.JSONToYAML, but allows for transforming the final data before writing.
func yamlJSONToYAMLWithFilter(j []byte, options ...*WriteYAMLOptions) ([]byte, error) {
// Convert the JSON to an object.
var jsonObj map[string]interface{}
// We are using yaml.Unmarshal here (instead of json.Unmarshal) because the
// Go JSON library doesn't try to pick the right number type (int, float,
// etc.) when unmarshalling to interface{}, it just picks float64
// universally. go-yaml does go through the effort of picking the right
// number type, so we can preserve number type throughout this process.
if err := rawyaml.Unmarshal(j, &jsonObj); err != nil {
return nil, err
}

for _, option := range options {
if option.transform != nil {
if err := option.transform(jsonObj); err != nil {
return nil, err
}
}
}

// Marshal this object into YAML.
return rawyaml.Marshal(jsonObj)
}

// ReadFile reads the given boilerplate artifact using the context's InputRule.
func (g GenerationContext) ReadFile(path string) ([]byte, error) {
file, err := g.OpenForRead(path)
Expand Down
2 changes: 1 addition & 1 deletion pkg/rbac/parser.go
Original file line number Diff line number Diff line change
Expand Up @@ -263,5 +263,5 @@ func (g Generator) Generate(ctx *genall.GenerationContext) error {
return nil
}

return ctx.WriteYAML("role.yaml", objs...)
return ctx.WriteYAML("role.yaml", objs)
}
2 changes: 1 addition & 1 deletion pkg/webhook/parser.go
Original file line number Diff line number Diff line change
Expand Up @@ -389,7 +389,7 @@ func (Generator) Generate(ctx *genall.GenerationContext) error {
} else {
fileName = fmt.Sprintf("manifests.%s.yaml", k)
}
if err := ctx.WriteYAML(fileName, v...); err != nil {
if err := ctx.WriteYAML(fileName, v); err != nil {
return err
}
}
Expand Down

0 comments on commit 8cb5ce8

Please sign in to comment.