Red Green Repeat Adventures of a Spec Driven Junkie

Working with git forks

I am documenting an important process I use in my team: managing their git repository using forks.

I go through the benefits of using forks, even in a branched repository environment, and show specific steps in how I work.

My goal is for you to come away with an understanding of how to incorporate working with forks in your git workflow.

This article will take you six minutes to read.

Babylonian - Necklace pendants and beads source & more information

Introduction

I want to talk about working with software, specifically how to work when managing code with git.

If you don’t know, git is a distributed version control system for developing software. The official documentation is here. Github is a hosted service that works with git’s protocol.

Repository Styles: Fork & Branch

In git, there’s two ways to work with a repository:

  • forked repository, where everyone on the team would have their own copy of the repository.
    • Key difference with branched repository: each team member only has their branches. Teammate’s branches are not in part of others’ repository.
    • There’s no “true” repository, each team member’s repository is a valid copy of the repository. One repository can make pull requests to another. It’s decentralized! (insane, right?!)
  • branched repository, where everyone on the team works from the same repository.
    • Key difference with forked repository: each team member who has the repository always has all branches of each team member is working on, even updated ones.
    • There’s a single “true” repository.

Fork or nothing

I always fork the main software repository the team is using. Even if the team is using the branched model.

The benefits I experienced using my own fork of the repository:

  • MY branches only
    • never deal with others’ branches (i.e. clean up, stale, branch name collisions, etc.)
    • my version of develop, master, etc.
  • work like the pros, the linux kernel uses this model and open source projects expect you to fork the repository before making a contribution.

Areas where branched repository is easier than using forked repository:

  • I need to maintain copy of main develop, master, etc.
    • adding colleagues branches takes another step.
  • Integrations on main repository might not always work on your copy of the repository.
    • Continuous integration services deploy from repositories that are not configured for the main repository.

Even if the team is using a “branched style”, a forked repository easily co-exists with a branched repository. There are areas where a forked repository will take extra work over a branched repository and I will share how to solve those situations.

Step 1: On github.com

One thing to do when you get access to the main repository: click the “fork” button and create a fork of the repository on your account.

Save the URL of this, which will be in the form:

  • git@github.com:<your github ID>/<repository name>.git

If you’re using HTTP it would be: https://github.com/<your github ID>/<repository name>.git

Step 2: Local Computer Setup

One thing that helps me maintain my sanity when working with forks: having two remotes: origin and upstream to differentiate the repositories:

  • origin refers to my copy of the repository, the one just made when clicking fork on github.
    • url would be: git@github.com:<your github ID>/<repository name>.git
  • upstream refers to the main repository of the team, the one you just go access to.
    • url would be: git@github.com:<organization github ID>/<repository name>.git

To add the remote repository to track origin and upstream:

  • git remote add origin git@github.com:<your github ID>/<repository name>.git
  • git remote add upstream git@github.com:<organization github ID>/<repository name>.git

When I need to get changes from the authoratative source, I use upstream. When I need to sync my work, I use my copy of the repository, which is origin.

Step 2.1: Getting Teammates’ Branches

This is to overcome the objections of not having access to teammates’ branches: add them as another remote!

To add your coworkers’ repositories, you would need their github ID and add it as:

git remote add <coworker name> git@github.com:<coworker's github ID>/<repository name>.git

Step 3: Getting Current Changes

As the main working repository has the current code, get the updated code, always pull from upstream, (git fetch upstream) to ensure your changes are on the current version the team is working from.

In the examples, I will use master in the examples as the main working branch.

git fetch upstream

This gets all the branches and code changes from the main repository and mirrored on your version of upstream.

Sync your version of master with the upstream version of master:

  • 3.1. git fetch upstream
  • 3.2. git checkout master
  • 3.3. git pull upstream master
  • 3.4. git push master

  • Step 3.1: gets all changes on the main repository
  • Step 3.2: sets my current branch to master
  • Step 3.3: pulls in the changes of the master branch onto my version of master.
  • Step 3.4: pushes the changes to my copy of the repository on github

(or oneline it with: git fetch upstream; git checkout master; git pull upstream master; git push origin)

Step 4: starting work

Create a new branch from the main working branch after getting the current version.

  • Step 4.1 git checkout -b <feature/fix>/<unique change name>

Step 5: Do Work

When doing your work, perform work exclusively on the branch you created. Never pull in changes (i.e. git pull) from the main working branch until you are ready to make a pull request for your team to review.

Step 6: Preparing for a Pull Request

When you want to make a pull request for other team members to review:

  • 6.1 git fetch upstream; git checkout master; git pull upstream master; git push origin
  • 6.2 git checkout <feature/fix>/<unique change name>
  • 6.3 git rebase master
  • 6.4 run tests!
  • 6.5 git push -u

  • Step 6.1 get current version from step 3.
  • Step 6.2 change back to the branch your work is on (one shortcut: git checkout -).
  • Step 6.3 put your changes on top of the current version of the working branch by rebase.
  • Step 6.4 run your tests to make sure there’s no surprises!
  • Step 6.5 put your changes on github.

Step 7: Making a Pull Request

On github, create a pull request

Don’t forget to click: Compare across forks as your work exists only on your repository.

Additional Tips

When making a pull request, always present your best work. That means:

Conclusion

This is how I prefer and my team members to work with git repository: fork mode. I find it easier as:

  • I never deal with others’ branches.
  • I have the right habits to work with other open source projects, like the Linux Kernel.
  • I can shoot myself in the foot. :-)

When learning git, I definitely shot myself in the foot and if I did this on a branched repository model, my stress level would have been even higher.