Skip to content

Instantly share code, notes, and snippets.

@vlandham
Last active March 21, 2024 12:57
Show Gist options
  • Save vlandham/3b2b79c40bc7353ae95a to your computer and use it in GitHub Desktop.
Save vlandham/3b2b79c40bc7353ae95a to your computer and use it in GitHub Desktop.
Feature Branches and Pull Requests : Walkthrough

Here's a little walkthrough of how Yannick and I are using feature branches and pull requests to develop new features and adding them to the project. Below are the steps I take when working on a new feature. Hopefully this, along with watching the process on Github, will serve as a starting point to having everyone use a similar workflow.

Questions, comments, and suggestions for improvements welcome!

Start with the latest on master

When starting a new feature, I make sure to start with the latest and greatest codebase:

git checkout master
git pull origin master

This reduces complications of dealing with out of date code, and reduces the chances of merge issues.

Create feature branch

Now I develop a local branch to house the changes required for the new feature.

Here we are using the term 'feature' loosely. Its a logical grouping of code and configuration changes to enable a new portion of the code, fix an issue, or improve existing code. The idea is to use your best judgement and try to keep the scope of the changes limited to a single logical issue.

git checkout -b add_linting

This will create a new branch called add_linting and check it out for me.

We could argue about branch naming practices, but so far I haven't found naming to be that big of an issue.

git status

Will show we are on the new branch and ready to work

Modify code

Now we implement the new feature / bug fix. Work as you would normally, making small incremental changes and checking them into the local feature branch.

Use descriptive comments when adding new changes so that the history of changes is easy to follow. They can still be short and succinct - but clear.

Push Feature Branch to Remote

Ok, you are done with the implementation. You've checked and double checked the changes, and are ready to have them integrated into the main code base.

The first step of the review process is to push your feature branch to origin.

git push origin add_linting

This will push your current branch to a new branch on origin with the same name.

Of course you can do this multiple times during the development process - if you want the peace of mind of having your changes distributed, or you want another set of eyes on it even before the pull request.

Create Pull Request

With your feature branch on github, navigate to the project on github. On the main page, you should see a new little toolbar that shows your feature branch listed and asks if you want to create a pull request from it. So let's do it!

screen shot 2015-05-27 at 10 28 45 am

When creating a pull request, you want to summarize the changes being made for this new feature and give it a descriptive title.

You can reference existing issues or other PR's by typing # - and then the issue number. A little pop-up should help with picking the right issue number.

Feel free to add screenshots or other images if there are visual changes associated with your PR.

Once you have written out the description for the new PR - submit it and sit back for a bit while a teammate reviews.

Next up, we will look at the PR review process and how it can be done efficiently on github.

Now that a Pull Request is live, someone has to review it. Let's walk through some of the steps involved in making this process go quickly.

Finding Pull Requests

First we need to get to the PR. From a project's main page, we can see that Pull Requests are a menu option.

screen_shot_2015-05-27_at_8_57_48_am

Click that to see a list of all the open PR's.

For this example, I'm going to focus on my Generated Docs PR .

Reviewing a PR

As a reviewer, its my job to check out the PR for any major issues, as well as comment on smaller issues I find in the code. I think a goal here is to be through but balance your time and the developer's time.

On a PR's main page, I can see the PR's description and any existing comments about the code.

screen shot 2015-05-27 at 9 04 40 am

Start here to understand the scope of the request.

Then, skip to the File Changes tab to start reviewing.

(So far, I haven't found the Commits tab all that useful for reviewing the code - it gets too fragmented when there are multiple changes).

screen_shot_2015-05-27_at_9_08_45_am

Commenting on Issues

So the PR isn't perfect. No biggie - that is expected. The review process makes it easy for a reviewer to spot issues and for the coder to implement changes.

As a reviewer, you can add comments inline to the change preview on github. Simply click on the little + next to the line or lines you have issue with.

screen shot 2015-05-27 at 8 04 44 am

As the PR requester, you can comment on those comments to justify or suggest future actions.

Here is an example where Yannick catches a spot where I left in some old code.

screen shot 2015-05-27 at 8 43 58 am

I follow up, indicating that it will be dealt with on this branch

screen shot 2015-05-27 at 8 44 14 am

Dealing with Issues

Now that there is a problem with the PR, we need to fix it. The PR process makes this pretty easy too.

Locally, on my feature branch, I simply implement the changes to fix the problem and commit the changes.

Then I push those changes up to the remote branch again. In this case, the branch was called docs. So:

git push origin docs

The PR is automatically updated with the latest changes. As Yannicks comments are on code affected by this new commit, they are hidden by default.

screen shot 2015-05-27 at 8 51 39 am

Merging PR

After a few messages, we should arrive at a desired +1 - which means its time to get this merged.

screen shot 2015-05-27 at 9 17 03 am

Additional suggestions can be dealt with in a separate PR - or added as another commit to the existing one - if you feel the scope is small enough. I typically like smaller PRs to bigger ones, so if I can justify splitting out additional suggestions into separate issues, I go that route.

If you are lucky, the PR can be automerged - and you can do it right inside github!

But sometimes (and not often honestly), the magic doesn't quite work, and you need to return to the command line one final time for the merge.

screen shot 2015-05-27 at 9 21 48 am

Luckily, the instructions for getting started are right there, just a click away.

screen shot 2015-05-27 at 9 23 53 am

First make sure you have the latest master in your local repo.

git checkout master
git pull origin master

Then switch back to the feature branch and merge in master

git checkout docs
git merge master

This should fail, and it should tell you which files you need to look at to resolve the conflict.

screen shot 2015-05-27 at 9 29 30 am

Here, I just have one file that needs attention gruntfile.js

Opening it up in my text editor, i look for the <<<< indicating a merge conflict.

screen shot 2015-05-27 at 9 28 46 am

I modify the code until all the conflicts are dealt with. Then add the file to staging.

git add gruntfile.js

The rest of the merge is already in staging - so now I can commit the merge

git commit -m 'merged master'

And switch back to master to push up this change

git checkout master
git merge --no-ff docs
git push origin master

A lot more work then the auto-merge -but hopefully its unusual that auto-merge isn't an option

Delete remote branch

Either way, once the PR is merged into master, we can remove the remote branch - which keeps our github project cleaned up.

screen shot 2015-05-27 at 9 45 03 am

Reviewing PR's Locally

In many cases, a visual check of the changes via the PR page on github is enough to give a +1 to changes. But sometimes, you want to try things out locally to really get a feel for what is going on.

Here is a few tips for doing just that.

Dealing with Local Changes

Optimally, you will be at a good stopping point in your own work, so that you are mentally prepared to review someone else's changes.

Obviously, sometimes this isn't the case. There's a PR that's urgent and needs to get looked at Now! There is a lull in your creative process, and you want to perform some other tasks before trying to tackle your problem again. Someone just asks you to take a look - and you want to get back to them before they go to bed. Plenty of reasons why you might have unfinished business in your local repo.

Option 1: Use Your Feature Branch A suggested option would be to simply check in your current changes into your local feature branch before pulling down someone else's. This is another great benefit to feature branches. They are for your changes only, and are meant to be used for small commits as you work on a particular feature/problem.

A git status will tell you if you might have forgotten to create a feature branch before you started working on a problem. If you did, referring to above, you can just git checkout -b feature_name (assuming you are already on master), and then just check in your changes there.

Option 2: Use git stash

If you really don't want to check in your changes for some reason, git also provides a handy nook to hide things in with git stash. Git Stash is provided - as the headline says - for when "things are in a messy state and you want to switch branches for a bit to work on something else."

Using git stash in its basic form is pretty simple:

git stash

This will stash your local, uncommitted changes making your repo again clean and free of changes, thus allowing you to move on to the PR viewing.

Pull Down PR

Getting the PR down from github and into your local repository can be done in many ways. As github's documentation suggests, you can use the GUI github client to pull down remote branches visually.

Else, you can pull down the PR using something like this:

git fetch origin pull/ID/head:BRANCHNAME

Where ID is the numerical ID assigned to the PR (which you can see in its url or at the top of the PR page), and BRANCHNAME is the local branch name you want to give it.

For example, on the mvlvm project, there is a PR with an ID of 21.

screen shot 2015-06-11 at 8 52 18 am

I'll grab this PR using the following command:

git fetch origin pull/21/head:bool_vis

Which gives me a new read only reference to the PR.

screen shot 2015-06-11 at 8 53 29 am

Now I switch to this branch in my local repo

git checkout bool_vis

A quick third alternative is to pull down the remote branch that the PR is based on. You would do that with something like:

git checkout -b BRANCHNAME origin/BRANCHNAME

So, for the branch for this PR, I would do:

git checkout -b module_experiment origin/module_experiment

In all cases, the PR get into your local repo for experimentation.

Retrieving Local Changes

Once done with the review, it's time to get back to work.

If you used a feature branch approach, and checked in your changes, you can just switch back to your feature branch and go.

If you used stash, you'll want to pop those stashed changes off the stash (which actually works like a stack - allowing you to stash many things). Back in your feature branch, you can run:

git stash pop

And all stashed changes will be back locally, and uncommitted, just the way you left them.

@truetechcode
Copy link

Great brief. Thanks

@Pixelalb
Copy link

@vlandham This is exactly I am doing but have a question on further proceedings. What should I do if I want to start a new branch say beta which requires code from alpha which is under review and not merged with master yet. Should I create a new branch from master and merge changes from alpha? Is this the right approach or there is something I am missing?

... so how did you end up doing this? :) I am facing the same situation now

@gwu1
Copy link

gwu1 commented Dec 3, 2019

This is a very good reference. I've no doubt sharing this gist to new teammates as a reading material.

@jimz-yucolab
Copy link

thank you for sharing your experience, definitely need to keep sticky for our team.

@lgammo
Copy link

lgammo commented Apr 14, 2021

What if the original pull request (called it feature-1) was made against one development branch (call it dev-1.0), then a new development branch was created (dev-2.0) and we need to merge with that. So far that should work trivially (assuming no conflict in the merge). However, we need to add new changes to the feature-1?

All of the examples online assume merging with one 'master' branch. This is not always the case.

Copy link

ghost commented May 6, 2021

Great work and thanks for the write up.

@dannykd
Copy link

dannykd commented Dec 12, 2022

super useful, definitely bookmarking this for future reference. although i'm new to this workflow, isn't it usually recommended to pull in changes from origin/main and then merging the updated main onto the feature branch before pushing into origin/feature? so that you can pull in the most recent development work and check for conflicts prior to the PR?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment