Skip to content

Commit

Permalink
Fix typo in headline "Namespace"
Browse files Browse the repository at this point in the history
  • Loading branch information
mogsie authored and camilamacedo86 committed Jan 16, 2023
1 parent 196f2e3 commit 7f49590
Show file tree
Hide file tree
Showing 2 changed files with 95 additions and 131 deletions.
56 changes: 23 additions & 33 deletions docs/book/src/quick-start.md
Original file line number Diff line number Diff line change
Expand Up @@ -9,13 +9,7 @@ This Quick Start guide will cover:

## Prerequisites

<<<<<<< HEAD
- [go](https://golang.org/dl/) version v1.19.0+
=======
- [go](https://golang.org/dl/) version v1.15+ (kubebuilder v3.0 < v3.1).
- [go](https://golang.org/dl/) version v1.16+ (kubebuilder v3.1 < v3.3).
- [go](https://golang.org/dl/) version v1.17+ (kubebuilder v3.3+).
>>>>>>> 1b016c51 (Update go prerequisites for the 3.3 release)
- [docker](https://docs.docker.com/install/) version 17.03+.
- [kubectl](https://kubernetes.io/docs/tasks/tools/install-kubectl/) version v1.11.3+.
- Access to a Kubernetes v1.11.3+ cluster.
Expand Down Expand Up @@ -111,11 +105,7 @@ and the `controllers/guestbook_controller.go` where the reconciliation business
logic. For more info see [Designing an API](/cronjob-tutorial/api-design.md) and [What's in
a Controller](cronjob-tutorial/controller-overview.md).

<<<<<<< HEAD
If you are editing the API definitions, generate the manifests such as Custom Resources (CRs) or Custom Resource Defintions (CRDs) using
=======
If you are editing the API definitions, generate the manifests such as CRs or CRDs using
>>>>>>> 1b016c51 (Update go prerequisites for the 3.3 release)
```bash
make manifests
```
Expand All @@ -126,33 +116,33 @@ make manifests
```go
// GuestbookSpec defines the desired state of Guestbook
type GuestbookSpec struct {
// INSERT ADDITIONAL SPEC FIELDS - desired state of cluster
// Important: Run "make" to regenerate code after modifying this file
// INSERT ADDITIONAL SPEC FIELDS - desired state of cluster
// Important: Run "make" to regenerate code after modifying this file

// Quantity of instances
// +kubebuilder:validation:Minimum=1
// +kubebuilder:validation:Maximum=10
Size int32 `json:"size"`
// Quantity of instances
// +kubebuilder:validation:Minimum=1
// +kubebuilder:validation:Maximum=10
Size int32 `json:"size"`

// Name of the ConfigMap for GuestbookSpec's configuration
// +kubebuilder:validation:MaxLength=15
// +kubebuilder:validation:MinLength=1
ConfigMapName string `json:"configMapName"`
// Name of the ConfigMap for GuestbookSpec's configuration
// +kubebuilder:validation:MaxLength=15
// +kubebuilder:validation:MinLength=1
ConfigMapName string `json:"configMapName"`

// +kubebuilder:validation:Enum=Phone;Address;Name
Type string `json:"alias,omitempty"`
// +kubebuilder:validation:Enum=Phone;Address;Name
Type string `json:"alias,omitempty"`
}

// GuestbookStatus defines the observed state of Guestbook
type GuestbookStatus struct {
// INSERT ADDITIONAL STATUS FIELD - define observed state of cluster
// Important: Run "make" to regenerate code after modifying this file
// INSERT ADDITIONAL STATUS FIELD - define observed state of cluster
// Important: Run "make" to regenerate code after modifying this file

// PodName of the active Guestbook node.
Active string `json:"active"`
// PodName of the active Guestbook node.
Active string `json:"active"`

// PodNames of the standby Guestbook nodes.
Standby []string `json:"standby"`
// PodNames of the standby Guestbook nodes.
Standby []string `json:"standby"`
}

// +kubebuilder:object:root=true
Expand All @@ -161,11 +151,11 @@ type GuestbookStatus struct {

// Guestbook is the Schema for the guestbooks API
type Guestbook struct {
metav1.TypeMeta `json:",inline"`
metav1.ObjectMeta `json:"metadata,omitempty"`
metav1.TypeMeta `json:",inline"`
metav1.ObjectMeta `json:"metadata,omitempty"`

Spec GuestbookSpec `json:"spec,omitempty"`
Status GuestbookStatus `json:"status,omitempty"`
Spec GuestbookSpec `json:"spec,omitempty"`
Status GuestbookStatus `json:"status,omitempty"`
}
```

Expand Down Expand Up @@ -253,7 +243,7 @@ make undeploy
## Next Step

Now, see the [architecture concept diagram][architecture-concept-diagram] for a better overview and follow up the
[CronJob tutorial][cronjob-tutorial] to better understand how it works by developing a
[CronJob tutorial][cronjob-tutorial] to better understand how it works by developing a
demo example project.

<aside class="note">
Expand Down
170 changes: 72 additions & 98 deletions docs/book/src/reference/envtest.md
Original file line number Diff line number Diff line change
@@ -1,36 +1,36 @@
# Configuring envtest for integration tests

The [`controller-runtime/pkg/envtest`][envtest] Go library helps write integration tests for your controllers by setting up and starting an instance of etcd and the
The [`controller-runtime/pkg/envtest`][envtest] Go library helps write integration tests for your controllers by setting up and starting an instance of etcd and the
Kubernetes API server, without kubelet, controller-manager or other components.

## Installation

Installing the binaries is as a simple as running `make envtest`. `envtest` will download the Kubernetes API server binaries to the `bin/` folder in your project
by default. `make test` is the one-stop shop for downloading the binaries, setting up the test environment, and running the tests.
by default. `make test` is the one-stop shop for downloading the binaries, setting up the test environment, and running the tests.

The make targets require `bash` to run.
The make targets require `bash` to run.

## Installation in Air Gapped/disconnected environments
If you would like to download the tarball containing the binaries, to use in a disconnected environment you can use
[`setup-envtest`][setup-envtest] to download the required binaries locally. There are a lot of ways to configure `setup-envtest` to avoid talking to
the internet you can read about them [here](https://github.com/kubernetes-sigs/controller-runtime/tree/master/tools/setup-envtest#what-if-i-dont-want-to-talk-to-the-internet).
The examples below will show how to install the Kubernetes API binaries using mostly defaults set by `setup-envtest`.
If you would like to download the tarball containing the binaries, to use in a disconnected environment you can use
[`setup-envtest`][setup-envtest] to download the required binaries locally. There are a lot of ways to configure `setup-envtest` to avoid talking to
the internet you can read about them [here](https://github.com/kubernetes-sigs/controller-runtime/tree/master/tools/setup-envtest#what-if-i-dont-want-to-talk-to-the-internet).
The examples below will show how to install the Kubernetes API binaries using mostly defaults set by `setup-envtest`.

### Download the binaries
`make envtest` will download the `setup-envtest` binary to `./bin/`.
`make envtest` will download the `setup-envtest` binary to `./bin/`.
```shell
make envtest
```

Installing the binaries using `setup-envtest` stores the binary in OS specific locations, you can read more about them
Installing the binaries using `setup-envtest` stores the binary in OS specific locations, you can read more about them
[here](https://github.com/kubernetes-sigs/controller-runtime/tree/master/tools/setup-envtest#where-does-it-put-all-those-binaries)
```sh
./bin/setup-envtest use 1.21.2
```

### Update the test make target
Once these binaries are installed, change the `test` make target to include a `-i` like below. `-i` will only check for locally installed
binaries and not reach out to remote resources. You could also set the `ENVTEST_INSTALLED_ONLY` env variable.
binaries and not reach out to remote resources. You could also set the `ENVTEST_INSTALLED_ONLY` env variable.

```makefile
test: manifests generate fmt vet
Expand Down Expand Up @@ -184,16 +184,9 @@ expectedOwnerReference := v1.OwnerReference{
Expect(deployment.ObjectMeta.OwnerReferences).To(ContainElement(expectedOwnerReference))
```

<<<<<<< HEAD
<aside class="warning">

<h2>Namespace usage limitation</h2>
=======

<aside class="warning">

<h2>Namesapce usage limitation</h2>
>>>>>>> 33c275b6 (Adds section on envtest limitations)

EnvTest does not support namespace deletion. Deleting a namespace will seem to succeed, but the namespace will just be put in a Terminating state, and never actually be reclaimed. Trying to recreate the namespace will fail. This will cause your reconciler to continue reconciling any objects left behind, unless they are deleted.

Expand All @@ -205,21 +198,13 @@ type MyCoolReconciler struct {
...
Namespace string // restrict namespaces to reconcile
}
<<<<<<< HEAD
func (r *MyCoolReconciler) Reconcile(ctx context.Context, req ctrl.Request) (ctrl.Result, error) {
_ = r.Log.WithValues("myreconciler", req.NamespacedName)
=======
func (r *MyCoolReconciler) Reconcile(ctx context.Context, req ctrl.Request) (ctrl.Result, error) {
_ = r.Log.WithValues("myreconciler", req.NamespacedName)
>>>>>>> 33c275b6 (Adds section on envtest limitations)
// Ignore requests for other namespaces, if specified
if r.Namespace != "" && req.Namespace != r.Namespace {
return ctrl.Result{}, nil
}
```
<<<<<<< HEAD
Whenever your tests create a new namespace, it can modify the value of reconciler.Namespace. The reconciler will effectively ignore the previous namespace.
For further information see the issue raised in the controller-runtime [controller-runtime/issues/880](https://github.com/kubernetes-sigs/controller-runtime/issues/880) to add this support.
</aside>
Expand All @@ -228,108 +213,108 @@ For further information see the issue raised in the controller-runtime [controll
Projects scaffolded with Kubebuilder can enable the [`metrics`][metrics] and the [`cert-manager`][cert-manager] options. Note that when we are using the ENV TEST we are looking to test the controllers and their reconciliation. It is considered an integrated test because the ENV TEST API will do the test against a cluster and because of this the binaries are downloaded and used to configure its pre-requirements, however, its purpose is mainly to `unit` test the controllers.
Therefore, to test a reconciliation in common cases you do not need to care about these options. However, if you would like to do tests with the Prometheus and the Cert-manager installed you can add the required steps to install them before running the tests.
Therefore, to test a reconciliation in common cases you do not need to care about these options. However, if you would like to do tests with the Prometheus and the Cert-manager installed you can add the required steps to install them before running the tests.
Following an example.
```go
// Add the operations to install the Prometheus operator and the cert-manager
// before the tests.
BeforeEach(func() {
By("installing prometheus operator")
Expect(utils.InstallPrometheusOperator()).To(Succeed())
By("installing the cert-manager")
Expect(utils.InstallCertManager()).To(Succeed())
}
// You can also remove them after the tests::
AfterEach(func() {
By("uninstalling the Prometheus manager bundle")
utils.UninstallPrometheusOperManager()
By("uninstalling the cert-manager bundle")
utils.UninstallCertManager()
})
// before the tests.
BeforeEach(func() {
By("installing prometheus operator")
Expect(utils.InstallPrometheusOperator()).To(Succeed())
By("installing the cert-manager")
Expect(utils.InstallCertManager()).To(Succeed())
}
// You can also remove them after the tests::
AfterEach(func() {
By("uninstalling the Prometheus manager bundle")
utils.UninstallPrometheusOperManager()
By("uninstalling the cert-manager bundle")
utils.UninstallCertManager()
})
```
Check the following example of how you can implement the above operations:
```go
const (
prometheusOperatorVersion = "0.51"
prometheusOperatorURL = "https://raw.githubusercontent.com/prometheus-operator/" + "prometheus-operator/release-%s/bundle.yaml"
certmanagerVersion = "v1.5.3"
certmanagerURLTmpl = "https://github.com/jetstack/cert-manager/releases/download/%s/cert-manager.yaml"
prometheusOperatorVersion = "0.51"
prometheusOperatorURL = "https://raw.githubusercontent.com/prometheus-operator/" + "prometheus-operator/release-%s/bundle.yaml"
certmanagerVersion = "v1.5.3"
certmanagerURLTmpl = "https://github.com/jetstack/cert-manager/releases/download/%s/cert-manager.yaml"
)
func warnError(err error) {
fmt.Fprintf(GinkgoWriter, "warning: %v\n", err)
fmt.Fprintf(GinkgoWriter, "warning: %v\n", err)
}
// InstallPrometheusOperator installs the prometheus Operator to be used to export the enabled metrics.
func InstallPrometheusOperator() error {
url := fmt.Sprintf(prometheusOperatorURL, prometheusOperatorVersion)
cmd := exec.Command("kubectl", "apply", "-f", url)
_, err := Run(cmd)
return err
url := fmt.Sprintf(prometheusOperatorURL, prometheusOperatorVersion)
cmd := exec.Command("kubectl", "apply", "-f", url)
_, err := Run(cmd)
return err
}
// UninstallPrometheusOperator uninstalls the prometheus
func UninstallPrometheusOperator() {
url := fmt.Sprintf(prometheusOperatorURL, prometheusOperatorVersion)
cmd := exec.Command("kubectl", "delete", "-f", url)
if _, err := Run(cmd); err != nil {
warnError(err)
}
url := fmt.Sprintf(prometheusOperatorURL, prometheusOperatorVersion)
cmd := exec.Command("kubectl", "delete", "-f", url)
if _, err := Run(cmd); err != nil {
warnError(err)
}
}
// UninstallCertManager uninstalls the cert manager
func UninstallCertManager() {
url := fmt.Sprintf(certmanagerURLTmpl, certmanagerVersion)
cmd := exec.Command("kubectl", "delete", "-f", url)
if _, err := Run(cmd); err != nil {
warnError(err)
}
url := fmt.Sprintf(certmanagerURLTmpl, certmanagerVersion)
cmd := exec.Command("kubectl", "delete", "-f", url)
if _, err := Run(cmd); err != nil {
warnError(err)
}
}
// InstallCertManager installs the cert manager bundle.
func InstallCertManager() error {
url := fmt.Sprintf(certmanagerURLTmpl, certmanagerVersion)
cmd := exec.Command("kubectl", "apply", "-f", url)
if _, err := Run(cmd); err != nil {
return err
}
// Wait for cert-manager-webhook to be ready, which can take time if cert-manager
//was re-installed after uninstalling on a cluster.
cmd = exec.Command("kubectl", "wait", "deployment.apps/cert-manager-webhook",
"--for", "condition=Available",
"--namespace", "cert-manager",
"--timeout", "5m",
)
_, err := Run(cmd)
return err
url := fmt.Sprintf(certmanagerURLTmpl, certmanagerVersion)
cmd := exec.Command("kubectl", "apply", "-f", url)
if _, err := Run(cmd); err != nil {
return err
}
// Wait for cert-manager-webhook to be ready, which can take time if cert-manager
//was re-installed after uninstalling on a cluster.
cmd = exec.Command("kubectl", "wait", "deployment.apps/cert-manager-webhook",
"--for", "condition=Available",
"--namespace", "cert-manager",
"--timeout", "5m",
)
_, err := Run(cmd)
return err
}
// LoadImageToKindCluster loads a local docker image to the kind cluster
func LoadImageToKindClusterWithName(name string) error {
cluster := "kind"
if v, ok := os.LookupEnv("KIND_CLUSTER"); ok {
cluster = v
}
kindOptions := []string{"load", "docker-image", name, "--name", cluster}
cmd := exec.Command("kind", kindOptions...)
_, err := Run(cmd)
return err
cluster := "kind"
if v, ok := os.LookupEnv("KIND_CLUSTER"); ok {
cluster = v
}
kindOptions := []string{"load", "docker-image", name, "--name", cluster}
cmd := exec.Command("kind", kindOptions...)
_, err := Run(cmd)
return err
}
```
However, see that tests for the metrics and cert-manager might fit better well as e2e tests and not under the tests done using ENV TEST for the controllers. You might want to give a look at the [sample example][sdk-e2e-sample-example] implemented into [Operator-SDK][sdk] repository to know how you can write your e2e tests to ensure the basic workflows of your project.
Also, see that you can run the tests against a cluster where you have some configurations in place they can use the option to test using an existing cluster:
```go
testEnv = &envtest.Environment{
UseExistingCluster: true,
UseExistingCluster: true,
}
```
Expand All @@ -339,14 +324,3 @@ testEnv = &envtest.Environment{
[cert-manager]: https://book.kubebuilder.io/cronjob-tutorial/cert-manager.html
[sdk-e2e-sample-example]: https://github.com/operator-framework/operator-sdk/tree/master/testdata/go/v3/memcached-operator/test/e2e
[sdk]: https://github.com/operator-framework/operator-sdk
=======
Whenever your tests create a new namespace, it can modify the value of reconciler.Namespace. The reconciler will effectively ignore the previous namespace.
For further information see the issue raised in the controller-runtime [controller-runtime/issues/880](https://github.com/kubernetes-sigs/controller-runtime/issues/880) to add this support.
</aside>
[envtest]:https://pkg.go.dev/sigs.k8s.io/controller-runtime/pkg/envtest
[setup-envtest]:https://pkg.go.dev/sigs.k8s.io/controller-runtime/tools/setup-envtest
>>>>>>> 33c275b6 (Adds section on envtest limitations)

0 comments on commit 7f49590

Please sign in to comment.