A Programmer’s Complete Guide To Git & Github

Shaun Smerling
14 min readJul 21, 2022

Along your developer journey, you’ll come across the process of deploying your code to Git quite often.

The commands, process, and workflow for this can often be extremely tedious and troublesome.

As a new programmer, its absolutely critical that you understand what Git is and how to use it in tangent with Github to make sure you are deploying your code, pulling updated code, branching different code, and using all the right commands to do so!

I’d urge you to save this guide as a bookmark and refer to it whenever you are stuck or need to remind yourself of the right commands needed whenever your deploy your code or pull new edits.

You will 100% have to master Git as a developer, especially when you collaborate with others in a job setting — so learning about it now as a new developer will greatly enhance your skills along your journey!

What Is Git?

Git is a distributed Version Control System. What it will allow you to do is save code in a server computer or elsewhere like Github. This makes it easy for you to collaborate with others on the same codebase, save your own code repetitively, and push new updates to a remote server.

Computers can work on different versions of a codebase, share them, make edits, and publish them all to the same server. Its perfect for collaboration!

Git is used for:

  • Tracking code changes
  • Tracking who made changes
  • Coding collaboration

What does Git do?

  • Manage projects with Repositories
  • Clone a project to work on a local copy
  • Control and track changes with Staging and Committing
  • Branch and Merge to allow for work on different parts and versions of a project
  • Pull the latest version of the project to a local copy
  • Push the local updates to the main project

What does Git workflow look like?

  1. Initialize Git on a folder, making a Repository
  2. Git now creates a hidden folder to keep track of changes in that folder
  3. When a file is changed, added or deleted, it is considered modified
  4. You select the modified files you want to Stage
  5. The Staged files are Committed, which prompts Git to store a permanent snapshot of the files
  6. Git allows you to see the full history of every commit and revert back to previous commits
  7. If you want to push it to Github, you’ll then push that committed file to Github

Check if Git is Installed:

git --version ## if git is installed, then it should say git version X.Y
## if you are on a Mac and don't have it installed, it will ask you to
## if you are on a Windows, go to the official Git website to install on your computer

Configure Git:

git config --global user.name "shaunsmerling"
git config --global user.email "shaunsmerling@gmail.com"
## use the same details you would on GitHub

Creating Git Folders & Initializing:

mkdir myproject # makes a new working directory
cd myproject # goes into that current working directory
git init
#once in your folder, this will initialize it. Git now knows
# to watch this folder

So after this, we begin working! Imagine we’ve just done some work on a file in that folder, but we haven’t yet pushed it to Git. We can check this by looking at Git Status

Git Status:

git status
On branch master
No commits yetUntracked files:
(use "git add ..." to include in what will be committed)
index.html
nothing added to commit but untracked files present (use "git add" to track)

Now Git is aware of the file, but has not added it to our repository. Files in your Git repository can only be in one of 2 states:

  • Tracked: files that Git knows about are added to the repository
  • Untracked: files that are in your working directory, but not added to the repository

When you first add files to an empty repository, they are all untracked. To get Git to track them, you need to stage them, or add them to the staging environment.

Git Staging Environment:

One of the core functions of Git is the concepts of the Staging Environment, and the Commit.

When you work, you may be adding/editing/removing files. But whenever you hit a milestone/finish a part of the work, you should add files to a Staging Environment

  • Staged files are files that are ready to be committed to the repository

Stage a File:

git add index.html #we've just added index.html to the staging environment#to check, use git statusgit status
On branch master
No commits yetChanges to be committed:
(use "git rm --cached ..." to unstage)
new file: index.html

Here we’ve added index.html to be staged on the local repo.

Let’s say you’ve made multiple changes to different files, instead of add them all one by one, you can just use this:

git add -A

#using --all or -A instead of individual file names will stage all changes made

Git Commit:

We’ve finished our work, and are now ready to move from the Staging phase to the Committing phase

You can think of each commit as a “save point”. Its a point in the project you can go back to if you find a bug, or want to make a change.

Each commit should include a message

git commit -m "First release of Hello World!"
[master (root-commit) 221ec6e] First release of Hello World!
3 files changed, 26 insertions(+)
create mode 100644 README.md
create mode 100644 bluestyle.css
create mode 100644 index.html
#using the git log command will also show you the history of commits for
# a repository

in the case that you need help and want to see all commands, you can use git help — all to see all possible commands

Git Push:

  • Time to push your local repo to the remote origin. Send it to either master or main, depending on which branch you’d like to push it to! Main is default.
git push --set-upstream origin main

Working with Git Branches:

In Git, a branch is a new/separate version of the main repository. If you have a project and want to update a certain design of it, its better to create a separate branch then use the main code being worked on. With a new branch called new-design, edit the code directly without impacting the man branch

Branches are great when you want to fix errors, confirm, and then add it to the main branch

Branches allow you to work on different parts of the project without impacting the main branch

When the work is complete, a branch can be merged with the main project

New Git Branch:

  • We are working in our local repo, and we don’t want to disturb or wreck the main project so we create a new branch:
git branch hello-world-images

# Now we've created a new branch called "hello world images"
# Use the command git branch to see which branch you are in

git branch
hello-world-images
* master

#We can see the new branch named "hello world images", but the * beside
# the master specifices that we are currently on the master branch

Checkout is the command used to check out a branch. It’ll move us from the current branch, to the one specified at the end of the command:

  • Example: Git checkout hello-world-images

Merge Branches:

  • So we’ve made the necessary fixes on a separate branch, let’s now merge the master and the emergency fix branch.
#firstly, lets check into the master branch
git checkout master

#next, use the name of your separate branch + merge to merge into master
git merge hello-world-images

#once you've merged, don't forge to add -all for staging, and then commit
git add --all
git commit -m "added new image"
[hello-world-images 1f1584e] added new image
2 files changed, 1 insertion(+)
create mode 100644 img_hello_git.jpg

Using Git & Github:

  • Create a Github account, sign in, and create a new Repo
  • Fill in the Repo name, Public or Private, then click “Create Repo”
  • Since we already have a local Git repo setup, we are going to push that to Github
  • Copy the HTTPS
git remote add origin <https://github.com/w3schools-test/hello-world.git>

#git remote add origin URL specifies that you are adding a remote repo,
# with the specified URL, as an origin to your local Git Rep

Now we are going to push our master branch to the origin URL, and set it as the default remote branch

git push --set-upstream origin master

Editing in Github:

  • Github allows you to edit code directly! Just remember to commit changes after, and we’ll want to commit directly to the master branch. Remember to add a description to the commit

Pulling to Keep Up To Date with Changes:

When working as a team on a project, its important that everyone stays up to date.

Any time you start working on a project, you should get the most recent changes.

You can do this with a pull request

  • There is two different types of pull commands: fetch & merge

Git Fetch:

  • Fetch gets all the change history of a tracked branch/repo
git fetch origin
remote: Enumerating objects: 5, done.
remote: Counting objects: 100% (5/5), done.
remote: Compressing objects: 100% (3/3), done.
remote: Total 3 (delta 2), reused 0 (delta 0), pack-reused 0
Unpacking objects: 100% (3/3), 733 bytes | 3.00 KiB/s, done.
From <https://github.com/w3schools-test/hello-world>
e0b6038..d29d69f master -> origin/master

Fetch updates to see what has changed on Github. Once fetched, you can use status to see where we are at.

git status
On branch master
Your branch is behind 'origin/master' by 1 commit, and can be fast-forwarded.
(use "git pull" to update your local branch)

nothing to commit, working tree clean

We are behind the origin/master by 1 commit. That should be the updated README.md change we made on the Github, we can double check by viewing the log

  • Example: git log origin/master
git log origin/master
commit d29d69ffe2ee9e6df6fa0d313bb0592b50f3b853 (origin/master)
Author: w3schools-test <77673807+w3schools-test@users.noreply.github.com>
Date: Fri Mar 26 14:59:14 2021 +0100

Updated README.md with a line about GitHub

commit e0b6038b1345e50aca8885d8fd322fc0e5765c3b (HEAD -> master)
Merge: dfa79db 1f1584e
Author: w3schools-test
Date: Fri Mar 26 12:42:56 2021 +0100

merged with hello-world-images after fixing conflicts

...
...

Git Merge:

Merge combines the current branch with a specified branch. After we’ve confirmed that the updates are as expected, we can merge our current branch (master) with origin/master

git merge origin/master
Updating e0b6038..d29d69f
Fast-forward
README.md | 4 +++-
1 file changed, 3 insertions(+), 1 deletion(-)

Git Pull:

A quicker way to go about this is using pull. Pull is a combination of fetch and marge. It is used to pull all changes from a remote repository into the branch you are working on.

  • Use pull to update our local Git.
git pull origin
remote: Enumerating objects: 5, done.
remote: Counting objects: 100% (5/5), done.
remote: Compressing objects: 100% (3/3), done.
remote: Total 3 (delta 1), reused 0 (delta 0), pack-reused 0
Unpacking objects: 100% (3/3), 794 bytes | 1024 bytes/s, done.
From <https://github.com/w3schools-test/hello-world>
a7cdd4b..ab6b4ed master -> origin/master
Updating a7cdd4b..ab6b4ed
Fast-forward
README.md | 2 ++
1 file changed, 2 insertions(+)

Great, your local repo is up to date!

Git Push:

Typical workflow…..

  1. Make changes to your local repo
  2. Stage & Commit the changes
git commit -a -m "Updated index.html. Resized image"
[master e7de78f] Updated index.html. Resized image
1 file changed, 1 insertion(+), 1 deletion(-)

3. Check the status

git status
On branch master
Your branch is ahead of 'origin/master' by 1 commit.
(use "git push" to publish your local commits)

nothing to commit, working tree clean

4. Now push our changes to our remote origin

git push origin
Enumerating objects: 9, done.
Counting objects: 100% (8/8), done.
Delta compression using up to 16 threads
Compressing objects: 100% (5/5), done.
Writing objects: 100% (5/5), 578 bytes | 578.00 KiB/s, done.
Total 5 (delta 3), reused 0 (delta 0), pack-reused 0
remote: Resolving deltas: 100% (3/3), completed with 3 local objects.
To <https://github.com/w3schools-test/hello-world.git>
5a04b6f..facaeae master -> master

5. Now you can go to GitHub and confirm that the repository has a new commit

Creating a New Branch on Github:

  • On Github, access your repo and click the “master” branch buton. There, you can create a new Branch. Type in a description name, and click Create branch:
  • You can start working on this existing file in the branch. Make edits as you like.
  • After you have finished editing, you can click the previous changes tab to see the changes you made that are highlighted
  • If you are happy with the change, add a comment that explains what you did, and click Commit changes!

Pulling a New Branch on Github:

  • Now continue working on our new branch in our local git. We have to pull from our Github repository again so that our code is up-to-date:
git pull
remote: Enumerating objects: 5, done.
remote: Counting objects: 100% (5/5), done.
remote: Compressing objects: 100% (3/3), done.
remote: Total 3 (delta 2), reused 0 (delta 0), pack-reused 0
Unpacking objects: 100% (3/3), 851 bytes | 9.00 KiB/s, done.
From <https://github.com/w3schools-test/hello-world>
* [new branch] html-skeleton -> origin/html-skeleton
Already up to date.

## we can see our main branch is up to date, and we can see that
## there is a new branch.

git status
On branch master
Your branch is up to date with 'origin/master'.

nothing to commit, working tree clean

git branch
* master

## so we don't have that new branch we made on Github on our local Git
## we can use -a after branch to see all local and remote branches:

git branch -a
* master
remotes/origin/html-skeleton
remotes/origin/master

# we can see that branch html-skeleton is available remotely, but not locally.
# lets check it out

git checkout html-skeleton
Switched to a new branch 'html-skeleton'
Branch 'html-skeleton' set up to track remote branch 'html-skeleton' from 'origin'.

git pull
Already up to date.

# What branches do we have now? And where are we working from?

git branch
* html-skeleton
master

Now open up your editor and confirm that the changes from the Github branch carried over. That is how you pull a Github branch to your local Git.

Git Push Brand to Github:

  • Let’s try to create a new local branch and push it to Github
git checkout -b update-readme
Switched to a new branch 'update-readme'

#Start by creating a branch, like we did earlier
# We make some changes to the README.md file.

git status
On branch update-readme
Changes not staged for commit:
(use "git add ..." to update what will be committed)
(use "git restore ..." to discard changes in working directory)
modified: README.md

no changes added to commit (use "git add" and/or "git commit -a")

#We see that README.md is modified but not added to the Staging Environment

git add README.md

#staged

git commit -m "Updated README"

#committed to the branch
#Now push the branch frm our local Git repo, to Github, where everyone
#can see the changes

git push origin update-readme
Enumerating objects: 5, done.
Counting objects: 100% (5/5), done.
Delta compression using up to 16 threads
Compressing objects: 100% (3/3), done.
Writing objects: 100% (3/3), 366 bytes | 366.00 KiB/s, done.
Total 3 (delta 2), reused 0 (delta 0), pack-reused 0
remote: Resolving deltas: 100% (2/2), completed with 2 local objects.
remote:
remote: Create a pull request for 'update-readme' on GitHub by visiting:
remote: <https://github.com/w3schools-test/hello-world/pull/new/update-readme>
remote:
To <https://github.com/w3schools-test/hello-world.git>
* [new branch] update-readme -> update-readme

Lastly, we should go to Github and confirm that the repository has a new branch. We can see the changes and merge them into the master branch if we approve

  • If you click “Compare & pull request”, you can go through the changes made and new files added
  • Commit Pull and Merge Pull.

Github Workflow:

The workflow focuses on branching and makes it possible for teams to experiment freely, and make deployments regularly

  • Create a new Branch → Key concept in Git. Works around the rule that the MASTER branch is ALWAYS deployable. That means you can always experiment and try something new! Branching gives you an environment where you can make changes without affecting the main branch
  • Make changes and add Commits → After the branch is created you can make changes by adding, editing, and deleting. When you reach small milestones, add the changes to your branch by commit. Adding commits keep tracks of your work. Each commit needs a message explaining on what has changed and why.
  • Open a Pull Request → A pull request notifies people you have changes ready for them to consider/review. You can ask others to review your changes or pull your contribution and merge it into their branch
  • Review → When a pull request is made, it can be reviewed by whoever has the proper access to the branch. This is where good discussions and review of the changes happen
  • Deploy → When the pull request has been reviewed and everything looks good, it is time for the final testing. Github allows you to deploy frm a branch for final testing, before merging with the master
  • Merge → You can finally merge the code into the master branch!

Get Github Pages:

Github allows you to host a webpage from your repository.

  • Start by creating a new repo in the pages
  • The repo needs a special name to function as a GH page.
  • It needs to be GitHub username + .github.io
  • Add the new page on local, give it a name e..g “gh-page”
  • Add it as new remote:
  • git remote add gh-page https://github.com/w3schools-test/w3schools-test.github.io.git
  • Push to the master branch git push gh-page master
  • Click the settings to navigate to the page

Github Forking:

  • At the heart of Git is collaboration. However, you can’t add to someone else’s code without access rights

A fork is a copy of a repo. Fork is not a command in Git, but something offered in Github and other repo hosts.

  • You can fork someone else's code, and it will clone it on your GH.
  • Now we have our own fork, but only on Github. We also want a clone on our local Git.
  • Move back to the original repo, and click the green “code”button to get the URL to the clone.
  • Open your git bash and clone the repo.
git clone <https://github.com/w3schools-test/w3schools-test.github.io.git>
Cloning into 'w3schools-test.github.io'...
remote: Enumerating objects: 33, done.
remote: Counting objects: 100% (33/33), done.
remote: Compressing objects: 100% (15/15), done.
remote: Total 33 (delta 18), reused 33 (delta 18), pack-reused 0
Receiving objects: 100% (33/33), 94.79 KiB | 3.16 MiB/s, done.
Resolving deltas: 100% (18/18), done.
  • We have a full copy of a repo, whose origin we are not allowed to make changes to.
  • Let’s see how the remotes of this Git is set up:
git remote -v
origin <https://github.com/w3schools-test/w3schools-test.github.io.git> (fetch)
origin <https://github.com/w3schools-test/w3schools-test.github.io.git> (push)
  • We see that origin is set up to the original “w3schools-test” repo, we also want to add our own fork.
  • Firstly, rename the original origin remote:
git remote rename origin upstream
git remote -v
upstream <https://github.com/w3schools-test/w3schools-test.github.io.git> (fetch)
upstream <https://github.com/w3schools-test/w3schools-test.github.io.git> (push)

then fetch the URL of our own fork, and add that as origin

git remote add origin <https://github.com/kaijim/w3schools-test.github.io.git>
git remote -v
origin <https://github.com/kaijim/w3schools-test.github.io.git> (fetch)
origin <https://github.com/kaijim/w3schools-test.github.io.git> (push)
upstream <https://github.com/w3schools-test/w3schools-test.github.io.git> (fetch)
upstream <https://github.com/w3schools-test/w3schools-test.github.io.git> (push) <https://github.com/w3schools-test/w3schools-test.github.io.git> (push)
  • Now we have 2 remotes:
  • Origin — our own fork, write & read access
  • Upstream — the original, only read access

THANK YOU! Please consider following and sharing. Hope this helps!

--

--