Certified Operator Build Guide
  • Introduction
  • What is an Operator?
  • Pre-Requisites
  • Helm Operators
    • Building a Helm Operator
      • Using a Single Image Variable (Red Hat Marketplace)
      • Dockerfile Requirements
      • Update the Controller Manager
      • Building and Pushing Image
  • Ansible Operators
    • Building an Ansible Operator
      • Using a Single Image Variable (Red Hat Marketplace)
      • Dockerfile Requirements
      • Update the Controller Manager
      • Building and Pushing Image
  • Golang Operator Gotcha's
    • Writing to the Status Subresource
  • OpenShift Deployment
    • Operator Metadata
      • Update CRDs from v1beta1
      • Creating the Metadata Bundle
      • Adjusting the ClusterServiceVersion
      • Reviewing your Metadata Bundle
      • Metadata Bundle Image
        • Managing OpenShift Versions
    • Installing an OpenShift Environment
    • Deploying onto OpenShift
  • Troubleshooting and Resources
    • Creating an Ansible Role From a Helm Chart
    • Security Context Constraints
    • Connect Metadata Test Results
    • Red Hat Marketplace Requirements
  • Appendix
    • What if I've already published a Community Operator?
      • Consuming Applications from RHCC
      • Applying Security Context Constraints
      • Choosing a Unique Package Name
      • Assembling the Metadata Bundle
    • Community Operators
    • AWS OpenShift 4 Cluster Quick Start Guide
    • Using Third Party Network Operators with OpenShift
      • Appendix A - CNI Operator Manifests
      • Appendix B - Cluster Network Status
      • Appendix C - Operator Group Manifest
      • Appendix D - Subscription Manifest
    • Bundle Maintenance After Migration
    • Frequently Asked Questions (FAQ)
    • Multi-Arch Operator Certification
      • Glossary of Terms
      • Requirements and Limitations
      • Building a Multi-Arch Operator Image
      • Scanning and Publishing
      • Updating the Bundle Image
Powered by GitBook
On this page
  • Helm Operators
  • Update your Helm chart
  • Override the image variable
  • Ansible Operators
  • Update your Ansible role
  • Golang Operators
  • All Operators (Helm, Ansible or Golang)
  • Define the environment variables
  • Entitled Registry
  • Other things to watch for
  1. Troubleshooting and Resources

Red Hat Marketplace Requirements

A walk through of the changes required to enable your operator to work in an offline environment. This is also a technical requirement for Red Hat Marketplace.

PreviousConnect Metadata Test ResultsNextWhat if I've already published a Community Operator?

Last updated 3 years ago

Helm Operators

You can find an .

Update your Helm chart

Make sure your Helm chart only references the values file for images. Each image should be a single value (it can't be split into repository and tag, for example).

values.yaml
  containers:
  - name: {{ template "etcd.fullname" . }}
    image: "{{ .Values.image.image }}"
    imagePullPolicy: "{{ .Values.image.pullPolicy }}"

A great way to find all the parts of your helm chart that will need to be updated is to recursively search your project's template folder for "image:"

$ grep -r 'image:' ./helm-charts/etcd/templates/*
  ./helm-charts/etcd/templates/statefulset.yaml:        image: "{{ .Values.image.repository }}:{{ .Values.image.tag }}"

Here we see that the image is split into two values - repository and tag. This won't work because we need to have a single variable to override. Replace this line with a new, single variable:

$ grep -r 'image:' ./helm-charts/etcd/templates/*
  ./helm-charts/etcd/templates/statefulset.yaml:        image: "{{ .Values.image.image }}"

Don't forget to add this new value to your Values.yaml file!

Override the image variable

In the watches.yaml file, add a field for overrideValues. It should contain each variable from the values.yaml file that corresponds to an image, and should be set to the environment variable you want to use.

watches.yaml
overrideValues:
  image.image: $RELATED_IMAGE_STATEFULSET

NOTE: the variable name MUST follow the pattern RELATED_IMAGE_. There is code looking for that string in your operator.

Ansible Operators

Update your Ansible role

Make sure your role is using environment variables for images instead of hard-coded or regular variables. If it's not, update it:

tasks/main.yaml
containers:
- name: mongodb
  image: "{{ 'dbImage' | quote }}"

Above you can see a reference to a image that's defined in the role's defaults/main.yaml file with an option to override it in values/main.yaml. Instead, use Ansible's lookup module to reference an environment variable and remove the variable from defaults/main.yaml to avoid confusion:

tasks/main.yaml
        containers:
        - name: mongodb
          image: "{{ lookup('env','RELATED_IMAGE_DB') | quote }}"

NOTE: Your environment variables need to follow the RELATED_IMAGE_ format, as there is code looking for this pattern.

Golang Operators

Make sure your code is using environment variables for any images your operator uses (any image except the operator itself).

func newPodsForCR(cr *noopv1alpha1.UBINoOp) []*corev1.Pod {
	ubiImg := os.Getenv("RELATED_IMAGE_UBI_MINIMAL")
	}

All Operators (Helm, Ansible or Golang)

Define the environment variables

In the CSV and operator.yaml files, declare the variable and set to a default value.

clusterserviceversion.yaml
            spec:
              containers:
              - env:
                - name: WATCH_NAMESPACE
                  valueFrom:
                    fieldRef:
                      fieldPath: metadata.annotations['olm.targetNamespaces']
                - name: POD_NAME
                  valueFrom:
                    fieldRef:
                      fieldPath: metadata.name          
                - name: OPERATOR_NAME
                  value: ectd-helm
                  
              #This is the new environment variable
                - name: RELATED_IMAGE_STATEFULSET
                  value: k8s.gcr.io/etcd-amd64:3.2.26
              #The operator image itself doesn't change    
                image: quay.io/dhoover103/etcd-helm-operator:v0.0.1

You may now use external image registries if desired. You are not required to host all images in the Red Hat Connect internal image registry as was the previous practice for Red Hat Marketplace integration.

Entitled Registry

Other things to watch for

If you're in the habit of using the "latest" tag for your images, make sure you specify it. Because of how the automation is written that picks up these images, we need a tag to be present.

Make sure you aren't overwriting the image in your CR (and by extension in the alm-examples field of the CSV). The best way to handle this is removing the field from the CR/alm-examples.

Using operator-sdk version 0.14.0 or later, build the updated operator image, and skip down to the

You can find an .

Build your updated operator image, and skip down to the

You can find an .

Build your updated operator image, and skip down to the

If you want to use the entitled registry for Red Hat Marketplace, your images must be hosted in .

You will need to scan your operator with the docker images using , replacing all your image references to use this docker registry.

From there, apply an ImageContentSourcePolicy to point to . This will allow the marketplace operator to use the entitled registry and properly replace the image strings.

example Helm Operator here
example Ansible operator here
example Go operator here
registry.connect.redhat.com
registry.marketplace.redhat.com/rhm
registry.marketplace.redhat.com/rhm
registry.connect.redhat.com
last section
last section
last section