operator-framework / operator-sdk

SDK for building Kubernetes applications. Provides high level APIs, useful abstractions, and project scaffolding.
https://sdk.operatorframework.io
Apache License 2.0
7.21k stars 1.74k forks source link

Some fields get lost in cr #5416

Closed Cosrider closed 2 years ago

Cosrider commented 2 years ago

Bug Report

What did you do?

  1. Use operator-sdk to generate crds and run operator. crd struct
    type RabbitmqClusterSpec struct {   
    Version string `json:"version"`
    // VolumeClaimTemplate allows a user to specify how volumes inside a Rabbitmq cluster
    // +optional
    VolumeClaimTemplate *corev1.PersistentVolumeClaim `json:"volumeClaimTemplate,omitempty"`

k8s.io\api\core\v1\types.go

// PersistentVolumeClaim is a user's request for and claim to a persistent volume
type PersistentVolumeClaim struct {
    metav1.TypeMeta `json:",inline"`
    // Standard object's metadata.
    // More info: https://git.k8s.io/community/contributors/devel/api-conventions.md#metadata
    // +optional
    metav1.ObjectMeta `json:"metadata,omitempty" protobuf:"bytes,1,opt,name=metadata"`

    // Spec defines the desired characteristics of a volume requested by a pod author.
    // More info: https://kubernetes.io/docs/concepts/storage/persistent-volumes#persistentvolumeclaims
    // +optional
    Spec PersistentVolumeClaimSpec `json:"spec,omitempty" protobuf:"bytes,2,opt,name=spec"`

    // Status represents the current information/status of a persistent volume claim.
    // Read-only.
    // More info: https://kubernetes.io/docs/concepts/storage/persistent-volumes#persistentvolumeclaims
    // +optional
    Status PersistentVolumeClaimStatus `json:"status,omitempty" protobuf:"bytes,3,opt,name=status"`
}

contents of crds generated by operator-sdk

             version:
                description: Version defines the Rabbitmq Docker image version.
                type: string
              volumeClaimTemplate:
                description: VolumeClaimTemplate allows a user to specify how volumes
                  inside a Rabbitmq cluster
                properties:
                  apiVersion:
                    description: 'APIVersion defines the versioned schema of this
                      representation of an object. Servers should convert recognized
                      schemas to the latest internal value, and may reject unrecognized
                      values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources'
                    type: string
                  kind:
                    description: 'Kind is a string value representing the REST resource
                      this object represents. Servers may infer this from the endpoint
                      the client submits requests to. Cannot be updated. In CamelCase.
                      More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds'
                    type: string
                  metadata:
                    description: 'Standard object''s metadata. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#metadata'
                    type: object
                  spec:
                    description: 'Spec defines the desired characteristics of a volume
                      requested by a pod author. More info: https://kubernetes.io/docs/concepts/storage/persistent-volumes#persistentvolumeclaims'
                    properties:
                      accessModes:
                        description: 'AccessModes contains the desired access modes
                          the volume should have. More info: https://kubernetes.io/docs/concepts/storage/persistent-volumes#access-modes-1'
                        items:
                          type: string
                        type: array
                      dataSource:
                        description: 'This field can be used to specify either: *
                          An existing VolumeSnapshot object (snapshot.storage.k8s.io/VolumeSnapshot)
                          * An existing PVC (PersistentVolumeClaim) If the provisioner
                          or an external controller can support the specified data
                          source, it will create a new volume based on the contents
                          of the specified data source. If the AnyVolumeDataSource
                          feature gate is enabled, this field will always have the
                          same contents as the DataSourceRef field.'
                        properties:
                          apiGroup:
                            description: APIGroup is the group for the resource being
                              referenced. If APIGroup is not specified, the specified
                              Kind must be in the core API group. For any other third-party
                              types, APIGroup is required.
                            type: string
                          kind:
                            description: Kind is the type of resource being referenced
                            type: string
                          name:
                            description: Name is the name of resource being referenced
                            type: string
                        required:
                        - kind
                        - name
                        type: object

in the generated crd, volumeClaimTemplate's metadata type is ojbect and lost properties

  1. edit cr yaml and apply it , after applied some fields are lost in cr. eg: name is lost part of cr content
    volumeClaimTemplate:
    metadata:
      name: data
    spec:
      accessModes:
      - ReadWriteOnce
      resources:
        requests:
          storage: 1Gi
      storageClassName: openebs-hostpath2
    status: {}

    What did you expect to see?

    when get crd crName -oyaml ; expect to see :

    volumeClaimTemplate:
    metadata:
      name: data
    spec:
      accessModes:
      - ReadWriteOnce
      resources:
        requests:
          storage: 1Gi
      storageClassName: openebs-hostpath2
    status: {}

    What did you see instead? Under which circumstances?

    metadata' field name is lost, Actually {}

    volumeClaimTemplate:
    metadata:{}      
    spec:
      accessModes:
      - ReadWriteOnce
      resources:
        requests:
          storage: 1Gi
      storageClassName: openebs-hostpath2
    status: {}

    Environment

    operator-sdk version: "v1.15.0", commit: "f6326e832a8a5e5453d0ad25e86714a0de2c0fc8", kubernetes version: "1.21", go version: "go1.16.10", GOOS: "linux", GOARCH: "amd64"

    Possible Solution

    i have to edit crd Manually and add some needed fields

    
    volumeClaimTemplate:
                description: VolumeClaimTemplate allows a user to specify how volumes
                  inside a Rabbitmq cluster
                properties:
                  apiVersion:
                    description: 'APIVersion defines the versioned schema of this
                      representation of an object. Servers should convert recognized
                      schemas to the latest internal value, and may reject unrecognized
                      values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources'
                    type: string
                  kind:
                    description: 'Kind is a string value representing the REST resource
                      this object represents. Servers may infer this from the endpoint
                      the client submits requests to. Cannot be updated. In CamelCase.
                      More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds'
                    type: string
                  metadata:
                    description: 'Standard object''s metadata. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#metadata'
                    properties:                                     <---------------added 
                      name:                                          <---------------added
                        type: string                                <---------------added
                    required:                                        
                    -  name
                    type: object
                  spec:
                    description: 'Spec defines the desired characteristics of a volume
                      requested by a pod author. More info: https://kubernetes.io/docs/concepts/storage/persistent-volumes#persistentvolumeclaims'
                    properties:


#### Additional context
   any better idea?
jberkhahn commented 2 years ago

Inserting the entire corev1.PersistentVolumeClaim golang struct into your struct probably isn't a good idea; at the very least there will be a bunch of stuff in there like the Status that you don't need. It would probably be a better idea to only specify the specific fields you care about (name, size, maybe other things), and manually add those fields to the spec of your custom type.

I need some additional information to specifically help you, though. What exactly are you using the PVC for? Is this intended to create a dependent PVC or point to an existing one or something else?

Cosrider commented 2 years ago

to create a dependent PVC. my operator will generate a statefulset, the cr's VolumeClaimTemplate information is used for statefulset's volumeClaimTemplates. as the VolumeClaimTemplate's name lost, pvc can’t be created.

jberkhahn commented 2 years ago

Ok, then you should only manually add the fields to your object spec that are strictly necessary to instantiate the PVC, and have the controller create it, like how the Deployments are created in the memcached example controller. We don't insert the entire deployment object into our CRD, we only collect the information we want the user to specify (the number of nodes).

Cosrider commented 2 years ago

ok, thanks.