This is the first in a series of posts about Git.
Let’s start at the beginning as Humpty Dumpty so wisely advised Alice. What is Git? — Git is a version control system.
A version control system is a program that helps you, essentially, keep copies of your work so that if something goes wrong (you screw up your code so badly you can’t fix it, for example) you can go back to the last working version.
Git also facilitates sharing code with teammates. If you work alone a version control system brings value in saving versions of your code and, if you use a service like GitHub, it keeps a copy of every version of your code off site, which is good in case your computer gets dropped into a pond.
There is much more you can do with it, but those are its essential functions.
Git is probably the world’s most popular version control system, even though it has a reputation (false) that it is very difficult to learn. We will demonstrate that it isn’t all that difficult after all.
GUI vs. Command Line
I was a big believer in learning Git by using a GUI application for years. There are many excellent ones available from Git Desktop which is dead simple to use, to Fork which is more difficult and more powerful. Visual Studio itself is a great Git GUI application.
I’ve come to believe, however, that the best way to learn Git is from the command line, and to use GUIs where they make life considerably easier after you understand what they are doing. In short, I tend to spend about 75% of my Git time on the command line, and 25% in one or another GUI.
You can get Git here. Install on Windows and/or Mac and/or Linux.
The next step is to set up an account on GitHub or Azure or another server so that you can share with your co-workers and so that you can have off-site copies. I’ll be using GitHub for this series of posts. Getting started is as easy as navigating to Github.com. (Note: we use Azure DevOps where I work and I like it even better than Github, but Github is free and I’m not certain about Azure Devo0p) In any case, all that follows applies wherever your remote repository (see below) is.
We will look at what you can do on Github once we’ve discussed the moving pieces.
The Moving Pieces
Before we go much further, let’s talk about the principal “pieces” of Git. Then dealing with GitHub will make much more sense.
There are 5 areas we’ll be concerned with:
The three in red we’ll be using all the time, Staging less so, and we won’t do much with Stash except explain what it is.
The Work Area
The work area is where your code is. That’s all, but it is surprisingly difficult to get your head around this because the contents of your work area will be changed by your use of Git.
There is exactly one work area. At any given time you are looking at a single set of code. All the other versions of your code are handled by Git in a (not so) hidden folder .git which we’ll see in just a moment.
It is very hard to lose your work with Git, but messing with the .git folder is a very good way to do it. We’ll come back to this.
The Local Repository
The local repository is where all your versions are stored, along with some meta-data. It is called “local” because it is on your machine (in that little .git folder I mentioned above). After you create a local repository look at the top folder and (if you are showing hidden folders) you will see .git. Look, but don’t touch.
The Remote Repository
The remote repository resides on a server somewhere (in our case, it will be on GitHub). It usually is an exact replica of your local repository, except when you make local changes but have not yet sent those changes to the remote repo.
It is typical to start off with the local and remote repositories being the same, and then doing some work in the work area, “checking it in” to the local repo and then “pushing” it up to the remote repo.
The Staging Area
The staging area holds files that are ready to be committed. When you say
you move the files in the staging area into the local repo. We’ll see how to do that, and we’ll see how to skip the staging area and go right to the repository.
Sometimes you have files that you are not yet ready to stage or commit but you want to hold on to while you go do other work. In order to not lose these files you can put them in the stash, and get them out later.
Assuming you have an account on GitHub look for a button that says New Clicking this will start the process of creating a remote repository. You will be brought to a form and prompted for the name of your new repository. You will then need to decide if your repo is public or private (I recommend private for now).
Next, check Add A Readme, always a good idea.
Check the box to Add gitignore. A gitignore file says not to checkin files that meet certain criteria (like being bin or obj files). Assuming you are using Visual Studio to work in C# scroll all the way down and pick Visual Studio.
The third checkbox has to do with what kind of license you want to assign to your work. Pick whichever one is comfortable for you (I use the MIT license).
Click the green Create Repository button. You did it! You created your remote repository. Now you want to create a local repository that reflects the remote one.
There are many ways to do this. The easiest by far is to install Github Desktop, and let it do the work for you. Once that is installed, return to Github and click on the green Code button. You’ll be presented with a menu of choices. Pick Open With Github Desktop. A dialog box will pop up offering you to pick the folder you want to put your repository in. Remember, though, that folder must be empty at this point.
Click the blue Clone button, Github Desktop will “clone” (make a copy) your remote repository into the folder you chose. You now have a local and a remote repository for your project.
Your working area will be empty because you haven’t yet created a project. Do that now: open Visual Studio and create a C# Console application with the same name as your repository (You are not required to use the same name, but it reduces confusion).
Moving Things Around
You move files into the repository from the work area, by using the commit command. You move files from the repository into the work area by using checkout.
You move files from the local repository to the remote, using push, and you get files from the remote into the local repo using pull.
It is very hard to understand what is going on with git unless you grok two concepts: commits and branches.
A commit takes one or more files that you have created or changed and moves them into the local repository. Essentially, it takes a snapshot of your entire working area as you have modified it since the last checkout.
As you will see, each commit is uniquely identified, and also carries with it the name of the person who made the commit, and other meta-data.
A branch is a set of commits. You could just add one commit after another, but if something goes wrong you might want to abandon the work you’ve done recently and go back to your main branch of development. Think of branches as looking like this.
This diagram shows you development through time. Each child commit points to its parent. We start with the root parent (Main at the bottom of the drawing). We then create two children: the first branch above our root Main, and Feature1 First Branch Commit
Feature 1 continues its development, with each child building on its parent.
This is critical: each child begins with all the code of its parent. It then changes that code or adds new files (etc.) and is checked in as the next commit (one oval higher in the diagram).
Notice that Feature2 branches off Main from a different commit. That is not required but it is permissible.
If I’m working on Feature1 and I complete it, I can “merge” it back into Main, adding all its changes to the Main Branch. If I decide that Feature2 is not working out I can abandon it.
If on Feature1 I decide that the third commit was a mistake, I can “roll back” to the previous commit, and it will be as if I never created the third commit.
Typically you will begin by checking out a branch. That switches you to the branch you’ve chosen. You would then Pull the latest version of that code (the most recent commit) to your local repository and your working area.
You can then work on that branch, and when you hit a reasonable stopping point, you commit your work (put a copy into your local repository).
Periodically you will push your work to the server, which takes a copy of the latest commit(s) and puts it into the server repository.
There is a good bit more to know about Git (it is a very powerful system) but you now know the fundamentals. In fact, you know enough to start working with Git.
It is very hard to lose code with Git — you have to work at it. But it is not hard to appear to lose code, or to get lost in the commits and branches. Make sure there is someone experienced with Git around to help if things go kerflooey. If you don’t have a Git guru at your beck and call, make sure, for now, that you are working on code you don’t care much about.
This is only the first in a series on Git. In the next post we’ll look at merging, pull requests, and more.