Skip to content
Cheeseness edited this page Feb 24, 2014 · 15 revisions

Git is a distributed source control system, which keeps track of all changes made to files within a "repository", and provides tools for navigating these histories and merging with changes from others.

If you haven't used Git before, please take the time to learn how to use it. This page is not a full tutorial, but it will point you to the right direction. If you do have past experience with git, it's still a good idea to check out our best practices. These are pretty standard stuff, but try make sure you are aligned with it.

Contents:

  • Getting Started
  • Forking
  • Cloning
  • Setting up Remotes
  • Committing
  • Branches
  • Creating a New Branch
  • Multiple Branches
  • Merging Branches To Master
  • Merging Master to Branches
  • Working With Remotes
  • Push
  • Keeping Your Repository Up To Date
  • Pull Requests
  • Mistakes and Pitfalls
  • Adding Unwanted Files
  • Bad Golf: Community Edition Specific Notes
  • 23rd of February history changes
  • Open Issues

Getting started

There are much better guides on how to work with Git than this one. Probably one of the best ones to get started with is this guide in Stack Overflow.

Quick tip: don't feel overwhelmed!* It takes a bit of practice to get the hang of it. A lot of the examples are command line interface, but most commands are fairly simple. You may find some useful GUI frontends (such as Git Tortoise or the GitHub app for Windows and Mac), but it's better if you know your basic command lines. Regardless to the way you run Git, you must learn the basic concepts and best practices. When you feel lost or insecure, just ask!

See this github help page for some details of what's being discussed in this part.

Forking

Since you want to contribute to this project, you don't create your own repository. Instead you should fork the current repository. Forking a repository means you have your own copy. Unlike your file system in which you copy a file and it's completely separate, forking means you can still get updates from the main repository and still contribute changes you make in your forked repository back to the main repository.

In github it's rather simple to fork, just click on the button and a forked repository will appear for your github user. github forking

Cloning

We are pretty much done with the github web interface for now, so get comfortable. The next step is to clone your forked repository to your local machine. Cloning is actually just like forking, but in this case you will be using git. Go to the parent directory where you'd like to clone your repository.

$ git clone https://github.com/<username>/bad-golf-community-edition.git

Where is your github user name. This command will create a subdirectory called bad-golf-community-edition and copy all the files in the repository.

Setting up Remotes

So now you have 2 of your cloned repositories. The first is the github fork and the second is your local clone. When you cloned the repository git automatically added a remote called 'origin'. Whenever you commit your changes to git it saves them only locally. If you would like to update your changes to your forked repository you will have to push your changes (more on that later). Before we do that, we should add a second remote repository, which is the main repository. This is normally called upstream (you should use the same naming convention so you can easily follow other instructions later)

$ cd bad-golf-community-edition
$ git remote add upstream https://github.com/Double-Fine-Game-Club/bad-golf-community-edition.git

Committing

To save your changes to your current repository (remember, you are working on a local repository) it's not enough to just make the file changes, you must commit your changes. To see the pending changes just type

$ git status

Each file shown has had changes made to it and must be 'staged' for commit with the command

git add <filename>

To stage all changed files, it is faster to just use

git add -A

but this runs the risk of adding unwanted files. To revert a changed file use

git checkout <filename>

which will give you a fresh copy of the unmodified file. To save your changes you should use the commit command. It's very important to add a meaningful message on what you have done. This is good practice so others understand your commits. So for example:

$ git commit -m "Issue #33: Fixed cart catching fire when space is pressed"

We will not going into further details here on these basic commands, you can find a lot more right here

Branches

So you are ready to go, right? Well, not yet. There's a very important aspect for you to learn which is branches.

The main branch is called 'master'. This is where the latest code is always available. By default, when you cloned your repository you are set to work on this main branch. However, changing your code in master is bad practice. It is much better to start using branches. Even if the change seems small, it is still highly not recommended to do these on master. There are several reasons for that. The first is that branches allow you to create granular changes. It will be easier for others to understand what you've done. The second reason is that it will be much easier for you to work on other things while your changes have not been integrated yet. It may seem like an annoyance at first, but do trust us this is in fact easier to work this way, mainly because you are not developing here alone.

Recommended reading: here

Creating a new branch

Suppose you want to create a new cart model. Then let's create a branch for that

$ git checkout -b my_cart_model

Note that the '-b' switch creates the branch, and the checkout command switches to that branch. if you don't like using that switch and prefer using 2 commands then do the following:

$ git branch my_cart_model
$ git checkout my_cart_model

This is equivalent.

Multiple branches

You can have as many branches as you'd like. Suppose you are still in the middle of creating your cart and would like to add a new tree type. This has nothing to do with the cart, so we should branch off from the master again. First go back to the master branch

$ git checkout master

Now, simply create your second branch

$ git checkout -b great_tree

Merging branches to master

At some point you'll want to merge changes of your branch back to master. This is rather simple, just switch to master and merge:

$ git checkout master
$ git merge my_cart_model

Merging master to branch

You will most likely update your master branch from time to time to be up to date with the latest main repository changes (details next section). If you'd like your branch to also be up to date you can simply merge the master to your branch. The procedure is exactly the same, while you are in your branch do

$ git merge master

In fact, remember this part, it will be useful later.

Working with remotes

push

Remember that your changes are all local even after you commit your changes. To apply your changes to your forked remote repository simply can simply push your changes to the origin. To push the master branch back to origin do:

$ git push origin master

You cannot push directly to the 'upstream' remote we created. That requires a pull request which we'll explain in a moment.

Keeping Your Repository Up To Date

Obviously you are not alone. Other continue to work on the game while you make your own changes. The simplest way to be up to date is to use the pull command (reminder: upstream is this repository)

$ git pull upstream

This will take the changes, and merge them to your own branch. Notice that the merge is done to your current branch, so if you'd like to pull into master only and not your branch, ensure you checkout master first.

It's probably best you first pull changes from upstream to your own repository master before merging changes from a branch. This way you can address conflicts while doing the merge, and if they are difficult to solve you can go back and still have an up to date master branch.

Pull requests

Finally we arrive at the point where you can submit your code. You can make pull requests to ask the people maintaining the main repository to merge your changes. Of course you should do that when you're done. Github allows an easy interface to do that.

It's best practice to create pull requests for your branches. If you properly followed the recommendations here you should have a branch per specific topic. This will allow you to make multiple contributions without having to worry when the pull request has been approved (it's not uncommon for pull requests to be handled only after a few days). This means you can continue working uninterrupted on any other task.

Before making the pull request you should make sure you pulled the latest from upstream and merged those changes into your branch. This will ensure you have resolved all possible merge conflicts and it will mean much quicker and easier response to your pull request.

Open issues

Issues are created, or can be created, whenever a change is requested for the project. This includes all of implementing a feature, fixing a bug, creating a model, and writing documents for this Wiki. An issue consists of a subject for the issue and a description where full details can be provided about what the issue wants resolved as well as attachments. Issues also provide a place for contributors to discuss possible solutions for the requested changes. Each issue is automatically given an issue number by GitHub e.g. #24.

Should we require squash merge to have a single commit before merge? (probably requires creating a branch just for merge, a bit more complex but cleaner)

Mistakes and pitfalls

Adding unwanted files

Refrain from adding files that are auto-generated by Unity. Doing so would not only unnecessarily increase the repository size, but it will also make tracking changes an impossible task. If you added those inadvertently do not just delete the files and make another commit. Git will remember those actions which again will be difficult for everyone else later.

It's best you contact the community here if that happens, do not create a pull request with such changes.

Bad Golf Community Edition Specific Notes

23rd of February history changes

If you have forked after the 23rd of February, specifically after 4bd119a714441c46483768fd59a88bd246163b25, you can safely ignore this.

Similarly if you haven't pulled since before 82af6a751edcba4235e154bb38daef7ed97a28a4, you can ignore it too.

Due to accidental commits of large files which belonged in the asset sources repository, we've made things a bit awkward for everybody with downstream forks. Though the files were removed (even before they were pushed to the repository), they still exist in the git history, increasing its size unnecessarily. Through this process, we were able to nearly half the repository size.

Unfortunately, this is going to break pull requests and require you to re-make any commits which haven't made it upstream (or use git cherry-pick and create patches to manually apply if you're up to doing that). Anybody with knowledge of a simpler workflow for navigating this sort of thing is welcome to chime in!

The following assumes you have an "remote" called upstream as described at the first section of this page.

git stash (if you have any uncommitted changes)

git rebase <branchname> --onto 82af6a751edcba4235e154bb38daef7ed97a28a4 (If working from a local branch replace with the branch's name, otherwise remove it)

git pull upstream master

git push

git stash pop (if you stashed uncommitted changes before)

From there, continue working as normal! Grumbliness about this situation can be thrown in Cheeseness' direction <3