Skip to content
New issue

Have a question about this project? # for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “#”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? # to your account

Scaffold a requirements.yml file for collection dependencies #2652

Merged
merged 4 commits into from
Mar 17, 2020
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 4 additions & 2 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -18,8 +18,10 @@
- Add Prometheus metrics support to Helm-based operators. ([#2603](https://github.com/operator-framework/operator-sdk/pull/2603))

### Changed
- Ansible scaffolding has been rewritten to be simpler and make use of newer features of Ansible and Molecule.
- The Kubernetes modules have migrated to the [Kubernetes Ansible collection](https://github.com/ansible-collections/kubernetes). All scaffolded code now references modules from this collection instead of Ansible Core. No immediate action is required for existing users of the modules from core, though it is recommended they switch to using the collection to continue to get non-critical bugfixes and features. The collection is now installed by default in the base image. ([#2646](https://github.com/operator-framework/operator-sdk/pull/2646))
- The base image now includes version 0.10.3 of the OpenShift Python client. This should fix hanging in Python3
- The Kubernetes modules have migrated to the [Kubernetes Ansible collection](https://github.com/ansible-collections/kubernetes). All scaffolded code now references modules from this collection instead of Ansible Core. No immediate action is required for existing users of the modules from core, though it is recommended they switch to using the collection to continue to get non-critical bugfixes and features. To install the collection, users will need to add the install step to their `build/Dockerfile`. New projects will have a `requirements.yml` scaffolded that includes the `community.kubernetes` collection, as well as the corresponding install step in the `build/Dockerfile`. ([#2646](https://github.com/operator-framework/operator-sdk/pull/2646))
- **Breaking change** `The operator_sdk.util` collection is no longer installed by default in the base image. Existing projects will need to install it in the `build/Dockerfile`. New projects will have a `requirements.yml` scaffolded that includes the `operator_sdk.util` collection, as well as the corresponding install step in the `build/Dockerfile`. ([#2652](https://github.com/operator-framework/operator-sdk/pull/2652))
- Ansible scaffolding has been rewritten to be simpler and make use of newer features of Ansible and Molecule. ([#2425](https://github.com/operator-framework/operator-sdk/pull/2425))
- No longer generates the build/test-framework directory or molecule/test-cluster scenario
- Adds new `cluster` scenario that can be used to test against an existing cluster
- There is no longer any Ansible templating done in the `deploy/` directory, any templates used for testing will be located in `molecule/templates/` instead.
Expand Down
5 changes: 3 additions & 2 deletions cmd/operator-sdk/migrate/cmd.go
Original file line number Diff line number Diff line change
Expand Up @@ -95,8 +95,9 @@ func migrateAnsible() error {
}

dockerfile := ansible.DockerfileHybrid{
Watches: true,
Roles: true,
Watches: true,
Roles: true,
Requirements: true,
}
_, err := os.Stat(ansible.PlaybookYamlFile)
switch {
Expand Down
1 change: 1 addition & 0 deletions cmd/operator-sdk/new/cmd.go
Original file line number Diff line number Diff line change
Expand Up @@ -268,6 +268,7 @@ func doAnsibleScaffold() error {
},
&ansible.DeployOperator{},
&ansible.Travis{},
&ansible.RequirementsYml{},
&ansible.MoleculeTestLocalMolecule{},
&ansible.MoleculeTestLocalPrepare{},
&ansible.MoleculeTestLocalVerify{},
Expand Down
26 changes: 12 additions & 14 deletions doc/ansible/dev/developer_guide.md
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,16 @@ Finally, a user must install the Ansible Kubernetes collection from ansible-gala
$ ansible-galaxy collection install community.kubernetes
```

Alternatively, if you've already initialized your operator, you will have a `requirements.yml`
file at the top level of your project. This file specifies Ansible dependencies that
need to be installed for your operator to function. By default it will install the
`community.kubernetes` collection, which are used to interact with the Kubernetes API, as well
as the `operator_sdk.util` collection, which provides modules and plugins for operator-specific
operations. To install the Ansible modules from this file, run
```bash
$ ansible-galaxy collection install -r requirements.yml
```

### Testing the k8s Ansible modules locally

Sometimes it is beneficial for a developer to run the Ansible code from their
Expand All @@ -50,6 +60,7 @@ Create foo-operator/tmp/build/go-test.sh
Rendering Ansible Galaxy role [foo-operator/roles/Foo]...
Cleaning up foo-operator/tmp/init
Create foo-operator/watches.yaml
Create foo-operator/requirements.yml
Create foo-operator/deploy/rbac.yaml
Create foo-operator/deploy/crd.yaml
Create foo-operator/deploy/cr.yaml
Expand All @@ -59,8 +70,8 @@ Initialized empty Git repository in /home/dymurray/go/src/github.com/dymurray/op
Run git init done

$ cd foo-operator
$ ansible-galaxy collection install -r requirements.yml
```

Modify `roles/Foo/tasks/main.yml` with desired Ansible logic. For this example
we will create and delete a namespace with the switch of a variable:
```yaml
Expand Down Expand Up @@ -442,19 +453,6 @@ Please look over the following sections for help debugging an Ansible Operator:
* [Additional Ansible debug](../user-guide.md#additional-ansible-debug)
* [Testing Ansible Operators with Molecule](testing_guide.md#testing-ansible-operators-with-molecule)

### Using k8s_status Ansible module with `run --local`
This section covers the required steps to using the `k8s_status` Ansible module
with `operator-sdk run --local`. If you are unfamiliar with managing status from
the Ansible Operator, see the [proposal for user-driven status
management][manage_status_proposal].

If your operator takes advantage of the `k8s_status` Ansible module and you are
interested in testing the operator with `operator-sdk run --local`, then
you will need to install the collection locally.

```sh
$ ansible-galaxy collection install operator_sdk.util
```
## Extra vars sent to Ansible
The extra vars that are sent to Ansible are managed by the operator. The `spec`
section will pass along the key-value pairs as extra vars. This is equivalent
Expand Down
10 changes: 6 additions & 4 deletions doc/ansible/dev/testing_guide.md
Original file line number Diff line number Diff line change
Expand Up @@ -15,13 +15,15 @@ To begin, you sould have:
without modification. Your top-level project structure should look like this:
```
.
├── build
├── deploy
├── molecule
├── roles
├── build/
├── deploy/
├── molecule/
├── roles/
├── playbook.yml (optional)
├── requirements.yml
└── watches.yaml
```
- The Ansible content specified in `requirements.yml` will also need to be installed. You can install them with `ansible-galaxy collection install -r requirements.yml`

### Molecule scenarios
If you look into the `molecule` directory, you will see four directories (`default`, `test-local`, `cluster`, `templates`).
Expand Down
1 change: 1 addition & 0 deletions doc/ansible/project_layout.md
Original file line number Diff line number Diff line change
Expand Up @@ -10,4 +10,5 @@ After creating a new operator project using
| roles/\<kind> | Contains an Ansible Role initialized using [Ansible Galaxy](https://docs.ansible.com/ansible/latest/galaxy/user_guide.html) |
| build/ | Contains scripts that the `operator-sdk` uses for build and initialization. |
| watches.yaml | Contains Group, Version, Kind, and the Ansible invocation method. |
| requirements.yml | contains the Ansible collections and role dependencies to install during build. |
| molecule/ | Contains [Molecule](https://molecule.readthedocs.io/) scenarios for end-to-end testing of your role and operator |
20 changes: 20 additions & 0 deletions doc/migration/version-upgrade-guide.md
Original file line number Diff line number Diff line change
Expand Up @@ -973,6 +973,25 @@ With:
- name: {{your operator name which is the value of metadata.name in this file}}
```

#### Migration to Ansible collections

The core Ansible Kubernetes modules have been moved to the [`community.kubernetes` Ansible collection][kubernetes-ansible-collection]. Future development of the modules will occur there, with only critical bugfixes going into the modules in core. Additionally, the `operator_sdk.util` collection is no longer installed by default in the base image. Instead, users should add a `requirements.yml` to their project root, with the following content:

```yaml
collections:
- community.kubernetes
- operator_sdk.util
```

Users should then add the following stages to their `build/Dockerfile`:

```
COPY requirements.yml ${HOME}/requirements.yml
RUN ansible-galaxy collection install -r ${HOME}/requirements.yml \
&& chmod -R ug+rwx ${HOME}/.ansible
```


[legacy-kubebuilder-doc-crd]: https://book-v1.book.kubebuilder.io/beyond_basics/generating_crd.html
[v0.8.2-go-mod]: https://github.com/operator-framework/operator-sdk/blob/28bd2b0d4fd25aa68e15d928ae09d3c18c3b51da/internal/pkg/scaffold/go_mod.go#L40-L94
[activating-modules]: https://github.com/golang/go/wiki/Modules#how-to-install-and-activate-module-support
Expand All @@ -988,3 +1007,4 @@ With:
[api-rules]: https://github.com/kubernetes/kubernetes/tree/36981002246682ed7dc4de54ccc2a96c1a0cbbdb/api/api-rules
[generating-crd]: https://book.kubebuilder.io/reference/generating-crd.html
[markers]: https://book.kubebuilder.io/reference/markers.html
[kubernetes-ansible-collection]: https://github.com/ansible-collections/kubernetes
4 changes: 4 additions & 0 deletions internal/scaffold/ansible/build_dockerfile.go
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,10 @@ func (b *BuildDockerfile) GetInput() (input.Input, error) {

const buildDockerfileAnsibleTmpl = `FROM quay.io/operator-framework/ansible-operator:[[.ImageTag]]

COPY requirements.yml ${HOME}/requirements.yml
RUN ansible-galaxy collection install -r ${HOME}/requirements.yml \
&& chmod -R ug+rwx ${HOME}/.ansible

COPY watches.yaml ${HOME}/watches.yaml

COPY [[.RolesDir]]/ ${HOME}/[[.RolesDir]]/
Expand Down
12 changes: 9 additions & 3 deletions internal/scaffold/ansible/dockerfilehybrid.go
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,9 @@ type DockerfileHybrid struct {

// Watches - if true, include a COPY statement for watches.yaml
Watches bool

// Requirements - if true, include a COPY and RUN to install Ansible requirements
Requirements bool
}

// GetInput - gets the input
Expand Down Expand Up @@ -73,13 +76,12 @@ RUN yum clean all && rm -rf /var/cache/yum/* \
&& pip3 install --no-cache-dir --ignore-installed ipaddress \
ansible-runner==1.3.4 \
ansible-runner-http==1.0.0 \
openshift==0.9.2 \
openshift~=0.10.0 \
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Add entry in the changelog over the upgrade of openshift version.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

👍 done

ansible~=2.9 \
jmespath \
&& yum remove -y gcc libffi-devel openssl-devel python36-devel \
&& yum clean all \
&& rm -rf /var/cache/yum \
&& ansible-galaxy collection install operator_sdk.util community.kubernetes
&& rm -rf /var/cache/yum

COPY build/_output/bin/[[.ProjectName]] ${OPERATOR}
COPY bin /usr/local/bin
Expand All @@ -95,6 +97,10 @@ RUN TINIARCH=$(case $(arch) in x86_64) echo -n amd64 ;; ppc64le) echo -n ppc64el
&& curl -L -o /tini https://github.com/krallin/tini/releases/latest/download/tini-$TINIARCH \
&& chmod +x /tini

[[- if .Requirements ]]
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Add entry in the changelog over requirements. Is not it a breaking change?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This part is not a breaking change, but existing users will indeed need to add a requirements file to their existing projects to pull in the operator_sdk.util collection and community.kubernetes collection. Added to changelog and migration guide

COPY requirements.yml ${HOME}/requirements.yml
RUN ansible-galaxy collection install -r ${HOME}/requirements.yml \
&& chmod -R ug+rwx ${HOME}/.ansible[[ end ]]
[[- if .Watches ]]
COPY watches.yaml ${HOME}/watches.yaml[[ end ]]
[[- if .Roles ]]
Expand Down
40 changes: 40 additions & 0 deletions internal/scaffold/ansible/requirements.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
// Copyright 2020 The Operator-SDK Authors
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

package ansible

import (
"github.com/operator-framework/operator-sdk/internal/scaffold/input"
)

// RequirementsYml - A requirements file for Ansible collection dependencies
type RequirementsYml struct {
StaticInput
}

// GetInput - gets the input
func (r *RequirementsYml) GetInput() (input.Input, error) {
if r.Path == "" {
r.Path = "requirements.yml"
}
r.TemplateBody = requirementsYmlTmpl
return r.Input, nil
}

const requirementsYmlTmpl = `---
collections:
- name: community.kubernetes
version: "<1.0.0"
- operator_sdk.util
`
3 changes: 3 additions & 0 deletions test/ansible/build/Dockerfile
Original file line number Diff line number Diff line change
@@ -1,5 +1,8 @@
FROM quay.io/operator-framework/ansible-operator:dev

COPY requirements.yml ${HOME}/requirements.yml
RUN ansible-galaxy collection install -r ${HOME}/requirements.yml \
&& chmod -R ug+rwx ${HOME}/.ansible
COPY ansible.cfg /etc/ansible/ansible.cfg
COPY watches.yaml ${HOME}/watches.yaml

Expand Down
3 changes: 3 additions & 0 deletions test/ansible/requirements.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
collections:
- community.kubernetes
- operator_sdk.util