Last weekend, Humanitarian Toolbox held a very successful coding event at That Conference. We got quite a bit done on both the crisis checkin and the All Ready applications. Thanks to the organizers of ThatConference, and everyone that attended during the weekend. I’m always impressed by how many developers join us there, and by how much they contribute.
OK, enough of the public service announcement. I wrote this post to help with a common issue: Pull Requests vs. Commit Privileges.
All the Humanitarian Toolbox projects use the Fork & Pull model for development. It enables us to keep the core contributor teams small, and yet enables anyone that wants to contribute to make changes and submit them. I, sadly, didn’t announce that clearly enough to all the volunteers when we started our event. Many of the volunteers thought we were using the Shared Repository Model.
That meant that later in the event, I had a number of developers come to me with issues because they could not commit to the main repository. That’s because they didn’t have the rights.
Announcement: Don’t fix this by just giving commit privileges. It’s not necessary.
Announcement II: Don’t fix this by trying to copy your changes and merging by hand. It’s not necessary either.
Thankfully, this is really easy to fix, once you understand how git works. It does also require using the git command line. The git command line isn’t that hard, and it’s important to learn as you do more with git. If you ever run into this issue, follow the instructions below to fix it.
Before I explain the steps to fix the problem, let me describe what happened, and why it’s a problem. Look at the image below. It’s a portion of the main window in my Github for Windows application. You can see that I have two copies of Crisis Checkin on my local machine. The top one is the clone of a fork that I made in my account. The bottom one is the clone of the master HTBox repository. These two copies have different remote repositories.
If I run ‘git remote –v’ in both directories, you can see the difference. Here’s the output from my fork:
C:\Users\billw\Documents\GitHub\TheBillWagner\crisischeckin [master]> git remote -v
origin https://github.com/BillWagner/crisischeckin.git (fetch)
origin https://github.com/BillWagner/crisischeckin.git (push)
Note the difference when I run the same command in the main repository:
When you execute a ‘git push’, you’ll send your changes to the git repository identified by origin (by default). If you cloned the main repository, git will try to push to that main repository. If you forked, and then cloned your fork, git will try to push to that forked repository.
The goal is to push the changes you made in your desktop to a fork of the repository where you have commit rights. The drawing below shows the relationship between the repositories, and the commands used to create each one.
To save your work, and create a pull request, you’ll need to create a fork, and push the work you’ve already done to that fork. The specific commands are as follows:
I usually create a fork from the github.com website. (Just press the “fork” button in the upper right corner). That creates a copy of the main repository in your account. This copy is also located on the github servers, not on your drive.
This fork is where you want to push your changes.
Now, you need to configure your fork as a remote repository for your working directory. Looking at the image above, you want to push from your desktop (where you have made changes) to the fork (the upper right repository).
You add a remote by typing:
‘git remote add fork https://github.com/BillWagner/crisischeckin.git’
Replace ‘fork’ and the URL with a name you want to use and the URL of your fork. I use ‘fork’ as the name, because it’s easy for me to remember.
You can add new remotes as long as the additional remotes are related to the origin remote. (Unless you start forcing git to do things. That means you can’t accidentally push your changes to crisis checkin to a fork of the Roslyn project (for example).
Now, your local copy is configured with two remotes: The source for the application (owned by HTBox) and your fork (owned by you). These two remotes are named ‘origin’ and ‘fork’.
Now, you need to push your changes from your working area to your fork. That’s just a git push, and specify the fork as the remote:
‘git push fork’.
By adding the extra parameter to the push command, you specify the remote repository where you changes should go.
It’s that easy.
Unless it isn’t. If it has been a while since you cloned the original repository, you may need to sync your working directory with upstream changes. That’s documented here. It’s variation of what I just described, but you should be able to follow it.
After you’ve pushed your changes to your fork, you can open a pull request to discuss your changes and get them merged into the main repository.
After I’ve finished this work, I will often make a new clone of my fork for a given repository. That way, the default remote (referred to by ‘origin’) points to my fork, rather than the main project.
I hope that helps.
All of these projects are Open Source (using the Creative Commons license for content, and the MIT license for code). If you would like to contribute, visit our GitHub Repository. Or, if you have questions, comments, or ideas for improvement, please create an issue for us.