Version control¶
To work collaboratively on the same software code requires version control. It must be clear who is working on which part of the code, when (and why) someone conducted code changes, and which code sections of one developer are compatible with code sections of another developer (or not). Also, one might need to fall back on an older code version when some current changes turned out to be a dead end.
For HydPy, we choose Git for these tasks. Git is a distributed version control software, allowing for handling multiple repositories of the same project at different places by different people. Each repository contains all projects files including their change histories. We host the main hydpy repository on GitHub. So you first should sing up for a free GitHub account. After that, you can contribute to HydPy online without installing any software or downloading the repository. If you are only aiming to improve the documentation, this could be reasonable. However, for more substantial contributions you need to handle a separate HydPy repository on your local computer with a local installation of Git. Git itself works via command lines, but in the majority of cases using graphical user interface as Sourcetree is much more comfortable.
Contributing to HydPy essentially requires three or four steps, no matter if working on GitHub directly or with your local Git software. For simplicity and generality, we explain these steps using the example of a single file change via GitHub:
Go to the main hydpy repository and click on “Fork”, creating a new HydPy repository under your own GitHub account, allowing to add, change, or delete any files without intervening in the development the original hydpy repository.
Click on “Branch: master”, type a name reflecting your goal (e.g. “improve_gitignore” and click on “Create branch: improve_gitignore from master”. Now that you have created a new branch, you can experiment without affecting the master branch of your forked repository. (This step is not required, but creating branches for different tasks helps to structure your work, to cooperate with others, and to keep the “official” history free from unsuccessful experiments.)
- Change the content of a file. For example:
Click on gitignore.
Click on the pen symbol (“Edit this file”).
change the order of two lines (e.g. “c.” and “.h”)
Write something under “Commit changes” to explain your purpose (e.g. “change the order of two lines in .gitignore to practise it”).
Click on the green “Commit changes” button.
Now you have changed the gitignore file of your specialised branch. Typically, you would commit multiple small changes to one branch. Keeping the single commits small allows for inspecting and reversing different changes.
At last, you can suggest incorporating your changes in the original hydpy repository. Click on “Compare & pull request” to visualise the relevant differences and add some explanations. Click on “Create pull request” to ask others to discuss your changes and to ask the maintainer of the original hydpy repository to pull and merge them into the main development line.
You are responsible for your forked repository only and do not have to be afraid to break the original hydpy repository accidentally. However, you should give your best to focus your pull requests on single issues and explain them clearly. Otherwise, the package maintainer might refuse your contributions in the sake of safeguarding HydPy’s code integrity.
Of course, things are not always as easy as in the example above. Not only your code changes, but the main line of development evolves as well. Then you first have to merge the latest changes of the master branch of the original hydpy repository into your current working branch, to resolve some conflicts if necessary, and to “rebase” everything to provide a granular and understandable pull request. See the much more thorough explanations How to Rebase a Pull Request and Pro Git to improve your Git skills.
Besides working in separate forks, it is a standard Git approach to structure code development in multiple branches. For HydPy, we decided on the following branching model.
First and most importantly, there is the “master” branch, tracking the “stable” changes of the code base, serving as the foundation of collaborative development. Second, there are the “feature” and “fix” branches related to specific issues. Third, there are the “release” branches, one for each official HydPy release.
The master branch is never removed or rebased. Hence, its commits cannot be changed or undone (except by later commits, of course). To avoid confusion and a messy commit historiy, do not commit to the master branch directly. Instead, create new “feature” or “fix” branches based on the head of the master branch and develop the new feature or fix the addressed problem within this branch. Afterwards, you might need to merge recent changes of the master branch into your branch or to clean up your commit history through rebasing. Finally, when everything seems right, your branch can be merged into the master branch with little risk to break something or affect the work of others.
Feature and fix branches should contain both the affected subpackage and module name, as well as a short description of the topic. If reasonable, follow the following pattern: “fix/core/hydpytools/typos”.
We use the tag name patterns “v4.0.0” and “v4.0a0” for stable and preliminary releases, respectively. For stable releases, we tag commits to the master branch, only. We create a separate branch for each minor version number (e.g. release/v4.0 and release/v4.1) to be able to apply fixes later. Fixes are indicated by tags only, increasing the bugfix number (e.g. from v4.0.0 to v4.0.1).