Skip to content

Instantly share code, notes, and snippets.

@marioa
Last active February 16, 2020 15:44
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 1 You must be signed in to fork a gist
  • Save marioa/21bd3194fb1e0c7869df169fe32a7463 to your computer and use it in GitHub Desktop.
Save marioa/21bd3194fb1e0c7869df169fe32a7463 to your computer and use it in GitHub Desktop.
EPCC git overview.

Introducing git

My instructor script for steps 1-9 of the software carpentry git lesson with some additions.

Contents

Pre-checks

Make sure that:

  • Your ~/.gitconfig file has been temporarily moved.
  • People can be paired up for the collaborative working.

Motivational Scenarios

Can motivate the use of a revision control system:

  • Development encompassing multiple systems.
  • Collaborative development.
  • Keeping provenance (if you have a student working/researching for you)
    • Good skill for them to learn.
    • Keeps provenance (if they do good comments)

Check that we have git in the shell

Just to check that git is installed in the local machine.

$ git --version 

Getting help

You can get help from git by just typing it at the command line.

$ git 

by itself returns most common commands. Same as:

$ git help 

You get an extended list of commands by doing:

$ git help --all

Want to know more about a command you can do:

$ git help add

which is the same as:

 $ git add --help

Registering with git

Git will complain if you do not set:

$ git config --global user.name "Mario Antonioletti"
$ git config --global user.email "mario@epcc.ed.ac.uk"

Can also set:

$ git config --global color.ui "auto"
$ git config --global core.editor "nano -w"

You can see what configuration parameters you have set by doing:

$ git config -l

Putting entries into:

$ ls ~/.gitconfig

Setting up a proxy

You may have to create a proxy if your organisation does not allow you to directly go into the internet:

 $ git config --global http.proxy proxy-url
 $ git config --global https.proxy proxy-url

to unset:

 $ git config --global --unset http.proxy
 $ git config --global --unset https.proxy

Creating a repository

Let's create a repository:

 $ mkdir paper
 $ cd paper

Check what is there:

 $ ls -A

Initialise the repository:

 $ git init

Check to see what has changed:

 $ ls -A

Check the status of the repository.

 $ git status

First commit

Edit a file (use an editor you are familiar with):

 $ nano README.md

Could add:

# My Paper

Check the state:

 $ ls

Check the file contents:

 $ cat README.md

and what is the repository status?

 $ git status

Workflow

working directory --> staging area --> git repository
       ^                                     |
       |                                     |
       +-------------------------------------+

Add the file to the staging area:

$ git add README.md

Let's check the status:

 $ git status

Suppose you made a mistake and you want to unstage:

 $ git rm --cached README.md

Check:

 $ git status

More commits

 $ git commit -m"Starting my paper."

 [master (root-commit) 18e86a7] Starting my paper.
  1 file changed, 2 insertions(+)
  create mode 100644 README.md

Check the status again:

 $ git status

If you do not specify the "-m" flag it will fire an editor for you.

 $ git log

Can have a shortened version of the commit log

 $ git log --oneline

Modify the text file:

## Section 1

This discusses the ...

Check the contents:

 $ cat README.md

and the status:

$ git status

Suppose you can't remember what you changed, you can do:

$ git diff

If we add the file to the staging area:

$ git add README.md

If you do:

$ git diff

You can not see the difference because the file has been staged. However, you can do:

$ git diff --staged

Make more changes to show that there is a difference between what is committed comes from the staging area and not the working copy.

Directories

Cannot add directories by themselves:

mkdir imgs
git status
git add imgs
git status

you need to add a file - you can create a temporary file:

cd imgs
touch .gitkeep
ls
ls -a
git add .
git commit -m"Added directory for images."

Can get rid of the temporary files later.

Changing a commit message

If you commit with a typo you can change:

$ git commit --amend -m "New message."

Exploring history

Can do a diff with earlier versions:

git log --oneline

pick as specific revision and do:

git diff RevNum README.md

Can short hand this by:

git diff HEAD~N README.md

where the N signifies how many revisions back you want to go and HEAD points to the current version of the repository.

If you want the specific contents of a file at given revision you can do:

git show RevNum README.md

You make modifications to a file that you no longer want to keep:

$ git checkout -- README.md

Or you can even checkout earlier versions of the code:

$ git checkout RevNum -- README.md

If you want to recover the state of the repository you can go back to HEAD by doing:

$ git reset --hard HEAD

Ignoring files

You have seen that git status is a really useful command to show you what has been changed. However if you have files that you do not want to put in the repository such as emacs back up files, binary files, etc you can tell git to ignore these by creating a .gitignore file. You can create this file and add content that will apply recursively:

 *~
 .\#*
 \~*
 bin/

add and commit this file and you will reduce the clutter you get.

$ git add .gitignore
$ git commit -m".gitignore: files to ignore."

git will not let you commit files that are contained in the .gitignore file.

Tagging

Can put a human readable version. Lightweight tag:

$ git tag v0.1
$ git tag             # Lists available tags
$ git show v0.1       # gives you information about the commit

We can do some more edits and do an annotated tag:

$ git tag -a v1.0 -m"First release."
$ git show v1.0

Use lightweight tags for your own use and annotated tags for the benefit of others.

Collaborating

You should have set up a bit bucket account - we use bit bucket because it provides private repositories by default but there are several others you can use:

We shall:

  1. Go to http://github.com.
  2. Login (if you have not created an account you will have to sign up).
  3. Click on the + and choose New repository.
  4. Choose a name for your repository paper.
  5. Use …or push an existing repository from the command line.
  6. Follow the instructions there.
  7. Click on Overview on the left hand menu and you should see your file together with the commits.
  8. click on source and you should be able to browse your sources.

Now we going to do something drastic:

rm -fr paper

We shall take a copy of the remote repository:

git clone https://github.com/marioa/paper.git Person1

If you go into the repository you should see that all your history is there:

cd paper
git log --oneline

Now want you to pair up.

  1. One of you will open up your repository to the other.
  2. Person 1 click on the Settings->Collaborators button.
  3. Type in their collaborators GitHub username.
  4. Person 2 should get an email and see Person 1's repository on their dashboard.
  5. Person 2 should clone the repository.

Note you can clone giving the repository a name:

git clone https://github.com/marioa/paper.git Person2

Now person 2 will change the README.md file and then add and commit:

$ git add README.md
$ git commit -m"README.md: updated the contents."

But this change has only registered in the local repository. We need to push it to the remote repository:

$ git push

Now person 1, in order to see these changes will have to pull the changes, in order to register these in their repository:

$ git pull

and the changes should be merged. Now person 1 and 2 add a line to the mars file.

## Conclusions

Try to make sure that the fruit is different and you are in the same location. Then:

$ git add README.md
$ git commit -m"README.md: added conclusions section."

Person 1:

$ git push 

Person 2:

$ git push

This will fail because person 1 has pushed their data before you did. You have to do a git pull before you can push:

$ git pull

But now you find you have a conflict - you have both tried to edit the same line and git does not know how to resolve the problem. You will have to edit the file, resolve the conflict (talk to the other person!!):

$ git add
$ git commit -m"README.md: resolved the conflict."
$ git push

Person 1 should be able to pull the file and together you can enter into a happy collaboration.

Branching

Branching allows a very powerful way of forking your code. Suppose you want to instrument it for performance analysis or you are collaborating and you do not want to be modifying the same code at the same time. Unlike CVS and SVN branches are really cheap and uncomplicated.

Can use to:

  • Explore/deveop a new feature
  • Stop developers clashing on development
  • Create a particular branch, a version of a release

Let's write a bit of Python code to demonstrate hello.py:

print("Hello World!")

Run the code python hello.py. Now suppose you want to instrument the code (put in timing calls). You do not want to do this in your master branch:

$ git branch # list the branches available, only master $ git branch profile # Creates the new branch $ git checkout profile # Change to the new branch

Now change the code:

import time

start = time.time()

print("Hello World!)

end = time.time()

print("Code took ",(end - start)," seconds)

Execute the code. Add, commit. Go back to the master branch. Change the original code.

print("Hello World!")
print("I am a real programer now!")

Execute, add, commit.

$ git checkout profile
$ cat `hello.py`    # Execute
$ git log --oneline # Check local changes
$ git log --oneline master # Check changes on the master branch
$ git merge master  # Incorporate changes from the maser branch

Make a change on the Hello World line. Execute, add, commit. Change back to the master branch. Change the same line, execute, add and commit. Go back to the profile branch and try to do a merge which should result in a conflict. Show how to resolve the conflict.

To push the branch to the remote repository:

git push origin profile

Finishing off

We want to clone the Edinburgh bootcamp content. This is on GitHub. We did not start using GitHub because they do not offer free private accounts by default. GitHub have a slightly different approach to doing things - you fork code which is a clone at the server end.

  1. Go to https://github.com/hpcarcher/2014-12-03-edinburgh
  2. You have a choice:
    1. Fork the repository and then clone.
    2. Clone the repository as is (but you will have no write access).

Miscellaneous items

Entering a password less often

Ideal way of doing this it to create (or use if you already have one) an ssh public/private key and register your public key with the remote repository.

Can also do

git config credential.helper store

which will store the credentials in plain text at ~/.git-credentials (not very secure).

On a mac you can do:

git config --global credential.helper osxkeychain

and on Linux you can do:

git config credential.helper cache 

which stores the password in memory.

Sometimes the GIT_ASKPASS gets a password to be asked via a fancy window prompt that does not appear (e.g. terminal may not support X).


Creative Commons Licence
This work is licensed under a Creative Commons Attribution 4.0 International License.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment