Thank you for your time and effort to help us improve Rook! Here are a few steps to get started. If you have any questions, don't hesitate to reach out to us on our Slack dev channel.
Navigate to http://github.com/rook/rook and click the "Fork" button.
In a console window:
# Create the rook repo path
mkdir -p $GOPATH/src/github.com/rook
# Navigate to the local repo path
cd $GOPATH/src/github.com/rook
# Clone your fork, where <user> is your GitHub account name
git clone https://github.com/<user>/rook.git
Add the upstream remote to your local git:
# Add 'upstream' to the list of remotes
cd rook
git remote add upstream https://github.com/rook/rook.git
# Verify the remote was added
git remote -v
Two remotes should be available: origin
and upstream
.
Before building the project, fetch the remotes to synchronize tags.
# Fetch all remotes
git fetch -a
make build
!!! tip
If in a Linux environment and `make build` command throws an error like `unknown revision` for some imports, add `export GOPROXY=https://proxy.golang.org,direct` to `~/.bashrc`. Reload your environment and confirm with `go env` that `GOPROXY` is set.
!!! hint
Make will automatically pick up `podman` if `docker` packages are not available on your machine.
For consistent whitespace and other formatting in .go
and other source files, apply
the following settings in your IDE:
goreturns
tool!!! tip
VS Code will prompt you automatically with some recommended extensions to install, such as
Markdown, Go, YAML validator, and ShellCheck.
VS Code will automatically use the recommended settings in the .vscode/settings.json
file.
To self-assign an issue that is not yet assigned to anyone else, add a comment in the issue with /assign
in the body.
The overall source code layout is summarized:
rook
├── build # build makefiles and logic to build, publish and release all Rook artifacts
├── cluster
│ ├── charts # Helm charts
│ │ └── rook-ceph
│ │ └── rook-ceph-cluster
│ └── examples # Sample manifestes to configure the cluster
│
├── cmd
│ ├── rook # Main command entry points for operators and daemons
│
├── design # Design documents
├── Documentation # Documentation that is published to rook.io
├── images # Rook docker image sources
│
├── pkg
│ ├── apis
│ │ ├── ceph.rook.io # ceph specs used in the CRDs
│ │ │ ├── v1
│ ├── client # auto-generated strongly typed client code to access Rook APIs
│ ├── clusterd
│ ├── daemon # daemons for configuring ceph
│ │ ├── ceph
│ │ └── discover
│ ├── operator # all reconcile logic and custom controllers
│ │ ├── ceph
│ │ ├── discover
│ │ ├── k8sutil
│ ├── util
│ └── version
└── tests
├── framework # integration test framework
│ ├── clients
│ ├── installer
│ └── utils
├── integration # integration test cases that will be invoked during golang testing
└── scripts # scripts for setting up integration and manual testing environments
To submit a change, create a branch in your fork and then submit a pull request (PR) from the branch.
For new features of significant scope and complexity, a design document is recommended before work begins on the implementation. Create a design document if:
For smaller, straightforward features and bug fixes, there is no need for a design document. Authoring a design document has many advantages:
!!! note
Writing code to prototype the feature while working on the design may be very useful to help flesh out the approach.
A design document should be written as a markdown file in the design folder. Follow the process outlined in the design template. There are many examples of previous design documents in that folder. Submit a pull request for the design to be discussed and approved by the community, just like any other change to the repository.
From a console, create a new branch based on your fork where changes will be developed:
# Update the remotes
git fetch --all
# Create a new branch that is based off upstream master. Give it a simple, but descriptive name.
# Generally it will be two to three words separated by dashes and without numbers.
git checkout -b feature-name upstream/master
During the development lifecycle, keep your branch(es) updated with the latest upstream master. As others on the team push changes, rebase your commits on top of the latest. This avoids unnecessary merge commits and keeps the commit history clean.
Whenever an update is needed to the local repository, never perform a merge, always rebase. This will avoid merge commits in the git history. If there are any modified files, first stash them with git stash
.
git fetch --all
git rebase upstream/master
Rebasing is a very powerful feature of Git. You need to understand how it works to avoid risking losing your work. Read about it in the Git documentation. Briefly, rebasing does the following:
After a feature or bug fix is completed in your branch, open a Pull Request (PR) to the upstream Rook repository.
Before opening the PR:
All pull requests must pass all continuous integration (CI) tests before they can be merged. These tests automatically run against every pull request. The results of these tests along with code review feedback determine whether your request will be merged.
From the root of your local Rook repo execute the following to run all of the unit tests:
make test
Unit tests for individual packages can be run with the standard go test
command.
To see code coverage on the packages that you changed, view the coverage.html
in a browser to inspect your new code.
go test -coverprofile=coverage.out
go tool cover -html=coverage.out -o coverage.html
Good unit tests start with easily testable code. Small chunks ("units") of code can be easily tested for every possible input. Higher-level code units that are built from smaller, already-tested units can more easily verify that the units are combined together correctly.
Common cases that may need tests:
Rook's upstream continuous integration (CI) tests will run integration tests against your changes automatically.
Integration tests will be run in Github actions. If an integration test fails, enable a tmate session to troubleshoot the issue by one of the following steps:
debug-ci
to the PR and push your changes again.See the action details for an ssh connection to the Github runner.
Rook maintainers value clear, lengthy and explanatory commit messages.
Requirements for commits:
Signed-off-by
tag is at the end of the commit message, achieved by committing with git commit -s
An example acceptable commit message:
component: commit title
This is the commit message. Here I'm explaining what the bug was along with its root cause.
Then I'm explaining how I fixed it.
Signed-off-by: FirstName LastName <email address>
To prepare your branch to open a PR, the minimal number of logical commits is preferred to maintain a clean commit history. Most commonly a PR will include a single commit where all changes are squashed, although sometimes there will be multiple logical commits.
# Inspect your commit history to determine if you need to squash commits
git log
To squash multiple commits or make other changes to the commit history, use git rebase
:
#
# In this example, the last 5 commits will be opened in the git rebase tool.
git rebase -i HEAD~5
Once your commit history is clean, ensure the branch is rebased on the latest upstream before opening the PR.
Go to the Rook github to open the PR. If you have pushed recently to a branch, you will see an obvious link to open the PR. If you have not pushed recently, go to the Pull Request tab and select your fork and branch for the PR.
After the PR is open, make changes simply by pushing new commits. The PR will track the changes in your fork and rerun the CI automatically.
Always open a pull request against master. Never open a pull request against a released branch (e.g. release-1.2) unless working directly with a maintainer.
The flow for getting a fix into a release branch is:
mergify
bot will automatically open a PR with the commits backported to the release branchThe Ceph manager modules are written in Python and can be individually and dynamically loaded from the manager. We can take advantage of this feature in order to test changes and to debug issues in the modules. This is just a hack to debug any modification in the manager modules.
The dashboard
and the rook
orchestrator modules are the two modules most commonly have modifications that need to be tested.
Make modifications directly in the manager module and reload:
Update the cluster so only a single mgr pod is running. Set the mgr.count: 1
in the CephCluster CR if it is not already.
Shell into the manager container:
kubectl exec -n rook-ceph --stdin --tty $(kubectl get pod -n rook-ceph -l ceph_daemon_type=mgr,instance=a -o jsonpath='{.items[0].metadata.name}') -c mgr -- /bin/bash
Make the modifications needed in the required manager module. The manager module source code is found in /usr/share/ceph/mgr/
.
!!! Note
If the manager pod is restarted, all modifications made in the mgr container will be lost
Example for restarting the rook manager module with the kubectl plugin:
kubectl rook-ceph ceph mgr module disable rook
kubectl rook-ceph ceph mgr module enable rook
Once the module is restarted the modifications will be running in the active manager. View the manager pod log or other changed behavior to validate the changes.