Git: Difference between revisions

From Wiki
No edit summary
mNo edit summary
 
(89 intermediate revisions by the same user not shown)
Line 1: Line 1:
* Create repository (on server)
{| class="wikitable" style="float:right; margin-left: 10px;" width="400px"
| Quick Cheat Sheet
|-
|
<pre class="bash">
git config credential.helper store
 
git config user.email "email@example.com"
git config user.name "username"
 
git log --graph --oneline
</pre>
|}
 
= Command Overview =
<pre class="bash">
git init                          # standard
git init --bare                    # bare (server) repo without working directory
 
git clone https://gerrit.wikimedia.org/r/p/mediawiki/core.git
git clone ssh://user@server/srv/git/git-repo.git
 
git pull                          # (= git fetch && git merge)
git fetch                          # get updates from remote, safe operation
git fetch --all                    #
git fetch upstream
git merge                          # merges those updates into working dir
 
git status                        # show changed files (working dir & staging area)
git diff                          # show changes in working dir
git diff --cached                  # show changes in staging area
git log
 
git add .
git add -A                        # all
 
git commit -m "Commit message"
git commit -a                      # includes add (modified and deleted files, but not new files)
git commit -am "msg"
git commit --amend -m "Fixed"      # only do, if not pushed. Amend commit over last wrong commit
 
git reset --soft
git reset (--mixed)
git reset --hard
git reset --hard origin/master
git clean -df
 
git push
git push origin master           
git push origin --delete <branch>  # delete branch from origin
git push -f origin                # force push
git push -u origin <branch>        # push new local branch to origin
 
git checkout master
git checkout file.txt
 
git log
git log --all --decorate --oneline --graph
 
git branch                        # list branches
git branch -a                      # list local & remote branches
git branch --merged                # list branches that have been merged
git branch <branch>                # create new branch
git branch -d <branch>            # delete
 
git merge <branch>                # to be executed on the branch that stays (usually master)
git merge <branch> --no-ff        # no fast forward, always keep branch in history
git merge upstream/master          # merge upstream master into own fork
git merge --abort
 
git rebase master                  # to be executed on the branch that is to be rebased (e.g. feature)
git rebase --continue
git rebase --abort
git rebase -i                      # interactive
git rebase -i HEAD~3              # interactive mode for 3 most recent commits
 
git revert <hash>                  # revert commit (changes from <hash> will be removed)
 
git config --list                  # show current git config
git remote -v                      # show remote urls
git remote set-url origin https..  # set origin url
git remote add upstream https://.. # add upstream remote url
</pre>
 
<pre class="bash">
# Merge
  A---B---C topic   A---B---C topic
/                   /        \
    D---E---F---G master    D---E---F---G---H master
 
# Rebase
          A---B---C topic                  A'--B'--C' topic
        /                                /
    D---E---F---G master    D---E---F---G master
</pre>
 
= Basics =
<blockquote>
== Create repository ==
<pre class="bash">
git init            # standard
git init --bare      # bare (server) repo without working directory
</pre>
 
== Initial checkout of remote repository ==
<pre class="bash">
git clone https://gerrit.wikimedia.org/r/p/mediawiki/core.git
git clone ssh://user@server/srv/git/git-repo.git
</pre>
 
== Get latest updates from server ==
<pre class="bash">
git pull            # (= git fetch && git merge)
 
git fetch            # get updates from remote, safe operation
git merge            # merges those updates into working dir
</pre>
 
== Change files and commit ==
* show changed files
<pre class="bash">
git status                    # show changed files (working dir & staging area)
git diff                      # show changes in working dir
git diff --cached              # show changes in staging area
git diff --cached --name-only
git diff --name-status
</pre>
 
* add files
<pre class="bash">
git add .
git add -A    # all
</pre>
 
* commit changes
<pre class="bash">
git commit -m "Commit message"
git commit -a                      # includes add
git commit -am.
</pre>
 
* send changes to server
<pre class="bash">
git push
</pre>
 
== .gitignore files ==
<pre class="bash">
*.log
filename.txt
subfolder/*
</pre>
</blockquote>
 
= Staging =
<pre>      <------------------------ checkout ---------------------
Working Directory  -stage->  Staging Area  -commit->  Repository</pre>
<pre class="bash">
git add .      # add all files to staging area
git status    # show staged & unstaged(untracked) files
git reset      # unstage all files
</pre>
 
= Branches =
<pre class="bash">
git branch                    # list local branches
git branch -a                  # list local & remote branches
git branch --merged            # list branches that have been merged
 
git branch <new-branch-name>  # create new branch (from the current commit)
</pre>
 
=== hard reset to specific branch ===
<pre class="bash">
git fetch --all
git reset --hard origin/branchname
</pre>
 
=== switch to branch ===
<pre class="bash">
git switch <new-branch-name>
git commit ... some-stuff
git switch master
</pre>
 
=== merge feature branch into master ===
<pre class="bash">
git checkout master
git merge <new-branch-name> (--no-ff)  # no fast forward: create merge commit
git diff
git commit -a
</pre>
 
=== rebase branch onto latest master ===
<pre class="bash">
git checkout master                        # go to master
git pull                                  # check if new updates in origin
                                          # ...master has proceeded...
git checkout <branch>                      # go to <branch>
git rebase master                          # Rebase pulls the "old" branch up to the latest master position
                                          # now proceed with merge or rebase to get the code onto master
</pre>
 
=== delete branch ===
<pre class="bash">
git branch -d <branch-name>            # local
git push origin --delete <branch-name> # remote
</pre>
 
https://stackoverflow.com/questions/9069061/what-is-the-difference-between-git-merge-and-git-merge-no-ff
 
= Repositories =
=== move repo to new server ===
<pre class="bash">
git remote -v                                            # show remote location
git remote set-url origin <URL to my NEW repo location>  # change remote url
git push -f origin                                      # push to remote url
git remote -v
</pre>
 
=== sparse clone (only specific folder) ===
<pre class="bash">
mkdir <repo>
cd <repo>
git init
git remote add -f origin <url>
git config core.sparseCheckout true
echo "some/dir/" >> .git/info/sparse-checkout
git pull origin master
</pre>
 
= Forks =
=== Syncing fork ===
<pre class="bash">
git clone https://your-fork.git
git remote -v                        # should show your fork
git remote add upstream https        # adding upstream repo
git remote -v                        # should show your fork as origin and upstream
git fetch upstream                    # get changes from upstream
git checkout master (or fork-branch)
git merge upstream/master
git add .
git commit -m "sync with upstream"
git push origin master
</pre>
 
= Undo mistakes =
=== replace file with commited version ===
<pre class="bash">
git checkout file.txt    # file gets replaced by repo version
</pre>
 
=== fix commit message or files ===
<pre class="bash">
git commit -m "Wrong message"
git commit --amend -m "Fixed message"    # only do this if you never pushed the wrong commit
</pre>
 
=== move commit from master to branch ===
<pre class="bash">
git log                              # get hash from commit you want to cherry pick
git checkout <branch>               
git cherry-pick <hash-of-commit>      # add commit to branch
 
git checkout master                  # if not pushed to remote,
git log                              # get hash of previous commit
git reset --soft <hash>              # resets commit to previous hash, but will keep changes in staging area
git reset (--mixed) <hash>            # resets commit to previous hash, will keep changes only in working dir
git reset --hard <hash>              # resets commit to previous hash, will delete changes (untracked files will stay)
git clean -df                        # deletes untracked files from working dir
</pre>
 
=== undo commit after push ===
<pre class="bash">
git log                              # get hash of bad commit
git revert <hash>                    # adds a revert-commit
</pre>
 
= Configuration =
 
=== Show config ===
<pre class="bash">git config --list</pre>
 
=== Store credentials ===
<pre class="bash">git config credential.helper store</pre>
 
=== Set username and email ===
<pre class="bash">
git config --global user.email "you@example.com"
git config --global user.name "Your Name"
</pre>
 
=== Windows - remove old credentials ===
<pre class="bash">rundll32.exe keymgr.dll,KRShowKeyMgr</pre>
 
=== post-receive hook ===
* execute script on main git server, after receiving push: hooks/post-receive
<blockquote>
<blockquote>
<pre>
<pre>
git init
#!/bin/bash
# unset GIT_INDEX_FILE # not needed for post-receive?
git --work-tree=/srv/targetfolder --git-dir=/home/demo/proj/.git checkout -f
</pre>
</pre>
</blockquote>
</blockquote>
 
::or
* add files
<blockquote>
<blockquote>
<pre>
<pre>
git add *
#!/bin/bash
while read oldrev newrev ref
do
    if [[ $ref =~ .*/master$ ]];
    then
        echo "Master ref received.  Deploying master branch to production..."
        git --work-tree=/var/www/html --git-dir=/home/demo/proj checkout -f
    else
        echo "Ref $ref successfully received.  Doing nothing: only the master branch may be deployed on this server."
    fi
done
</pre>
</pre>
</blockquote>
</blockquote>


* commit changes
:* make executable
<blockquote>
<blockquote>
<pre>
<pre>
git commit -m "Commit-Nachricht"
chmod +x post-receive
</pre>
</pre>
</blockquote>
</blockquote>


* send changes to server
= Speed-up =
<pre class="bash">
# alias 'acp' = add+commit+push
git config --global alias.acp '!f() { git add . && git commit -m "$@" && git push; }; f'       
git acp "this is my commit comment"
</pre>
 
= Links =
* https://ohmygit.org/
* https://nvie.com/posts/a-successful-git-branching-model/
* https://www.digitalocean.com/community/tutorials/how-to-set-up-automatic-deployment-with-git-with-a-vps
* https://gist.github.com/noelboss/3fe13927025b89757f8fb12e9066f2fa
* https://gist.github.com/thomasfr/9691385
 
= Other =
== Special features ==
* auto-commit when file changes
<blockquote>
<blockquote>
<pre>
<pre>
git push
inotifywait -q -m -e CLOSE_WRITE --format="git commit -a -m 'autocommit on change' %w" file.txt | sh
</pre>
</pre>
</blockquote>
</blockquote>
 
::or
* get latest changes from server
<blockquote>
<blockquote>
<pre>
<pre>
git pull
while true; do
  inotifywait -qq -e CLOSE_WRITE ~/.calendar/calendar
  cd ~/.calendar; git commit -a -m 'autocommit on change'
done
# inotify "-r"  for recursive
</pre>
</pre>
</blockquote>
</blockquote>
::or
:* etckeeper or [https://github.com/gitwatch/gitwatch gitwatch]


[[Category:Linux/Services]]
[[Category:Programming]]

Latest revision as of 15:13, 28 September 2024

Quick Cheat Sheet
git config credential.helper store

git config user.email "email@example.com"
git config user.name "username"

git log --graph --oneline

Command Overview

git init                           # standard 
git init --bare                    # bare (server) repo without working directory

git clone https://gerrit.wikimedia.org/r/p/mediawiki/core.git
git clone ssh://user@server/srv/git/git-repo.git

git pull                           # (= git fetch && git merge)
git fetch                          # get updates from remote, safe operation
git fetch --all                    # 
git fetch upstream
git merge                          # merges those updates into working dir

git status                         # show changed files (working dir & staging area)
git diff                           # show changes in working dir
git diff --cached                  # show changes in staging area
git log

git add .
git add -A                         # all

git commit -m "Commit message"
git commit -a                      # includes add (modified and deleted files, but not new files)
git commit -am "msg"
git commit --amend -m "Fixed"      # only do, if not pushed. Amend commit over last wrong commit

git reset --soft
git reset (--mixed)
git reset --hard
git reset --hard origin/master
git clean -df

git push
git push origin master             
git push origin --delete <branch>  # delete branch from origin
git push -f origin                 # force push
git push -u origin <branch>        # push new local branch to origin

git checkout master
git checkout file.txt

git log
git log --all --decorate --oneline --graph

git branch                         # list branches
git branch -a                      # list local & remote branches
git branch --merged                # list branches that have been merged
git branch <branch>                # create new branch
git branch -d <branch>             # delete

git merge <branch>                 # to be executed on the branch that stays (usually master)
git merge <branch> --no-ff         # no fast forward, always keep branch in history
git merge upstream/master          # merge upstream master into own fork
git merge --abort

git rebase master                  # to be executed on the branch that is to be rebased (e.g. feature)
git rebase --continue
git rebase --abort
git rebase -i                      # interactive
git rebase -i HEAD~3               # interactive mode for 3 most recent commits

git revert <hash>                  # revert commit (changes from <hash> will be removed)

git config --list                  # show current git config
git remote -v                      # show remote urls
git remote set-url origin https..  # set origin url
git remote add upstream https://.. # add upstream remote url
# Merge
	  A---B---C topic	   A---B---C topic
	 /	                  /         \
    D---E---F---G master     D---E---F---G---H master

# Rebase
          A---B---C topic                  A'--B'--C' topic
         /                                /
    D---E---F---G master     D---E---F---G master

Basics

Create repository

git init             # standard 
git init --bare      # bare (server) repo without working directory

Initial checkout of remote repository

git clone https://gerrit.wikimedia.org/r/p/mediawiki/core.git
git clone ssh://user@server/srv/git/git-repo.git

Get latest updates from server

git pull             # (= git fetch && git merge)

git fetch            # get updates from remote, safe operation
git merge            # merges those updates into working dir

Change files and commit

  • show changed files
git status                     # show changed files (working dir & staging area)
git diff                       # show changes in working dir
git diff --cached              # show changes in staging area
git diff --cached --name-only
git diff --name-status
  • add files
git add .
git add -A    # all
  • commit changes
git commit -m "Commit message"
git commit -a                      # includes add
git commit -am.
  • send changes to server
git push

.gitignore files

*.log
filename.txt
subfolder/*

Staging

       <------------------------ checkout ---------------------
Working Directory   -stage->   Staging Area   -commit->   Repository
git add .      # add all files to staging area
git status     # show staged & unstaged(untracked) files
git reset      # unstage all files

Branches

git branch                     # list local branches
git branch -a                  # list local & remote branches
git branch --merged            # list branches that have been merged

git branch <new-branch-name>   # create new branch (from the current commit)

hard reset to specific branch

git fetch --all
git reset --hard origin/branchname

switch to branch

git switch <new-branch-name>
git commit ... some-stuff
git switch master

merge feature branch into master

git checkout master
git merge <new-branch-name> (--no-ff)   # no fast forward: create merge commit
git diff
git commit -a

rebase branch onto latest master

git checkout master                        # go to master
git pull                                   # check if new updates in origin
                                           # ...master has proceeded...
git checkout <branch>                      # go to <branch>
git rebase master                          # Rebase pulls the "old" branch up to the latest master position
                                           # now proceed with merge or rebase to get the code onto master

delete branch

git branch -d <branch-name>            # local
git push origin --delete <branch-name> # remote

https://stackoverflow.com/questions/9069061/what-is-the-difference-between-git-merge-and-git-merge-no-ff

Repositories

move repo to new server

git remote -v                                            # show remote location
git remote set-url origin <URL to my NEW repo location>  # change remote url
git push -f origin                                       # push to remote url
git remote -v

sparse clone (only specific folder)

mkdir <repo>
cd <repo>
git init
git remote add -f origin <url>
git config core.sparseCheckout true
echo "some/dir/" >> .git/info/sparse-checkout
git pull origin master

Forks

Syncing fork

git clone https://your-fork.git
git remote -v                         # should show your fork 
git remote add upstream https         # adding upstream repo
git remote -v                         # should show your fork as origin and upstream
git fetch upstream                    # get changes from upstream
git checkout master (or fork-branch)
git merge upstream/master
git add .
git commit -m "sync with upstream"
git push origin master

Undo mistakes

replace file with commited version

git checkout file.txt     # file gets replaced by repo version

fix commit message or files

git commit -m "Wrong message"
git commit --amend -m "Fixed message"    # only do this if you never pushed the wrong commit

move commit from master to branch

git log                               # get hash from commit you want to cherry pick
git checkout <branch>                
git cherry-pick <hash-of-commit>      # add commit to branch

git checkout master                   # if not pushed to remote, 
git log                               # get hash of previous commit
git reset --soft <hash>               # resets commit to previous hash, but will keep changes in staging area
git reset (--mixed) <hash>            # resets commit to previous hash, will keep changes only in working dir
git reset --hard <hash>               # resets commit to previous hash, will delete changes (untracked files will stay)
git clean -df                         # deletes untracked files from working dir 

undo commit after push

git log                               # get hash of bad commit
git revert <hash>                     # adds a revert-commit 

Configuration

Show config

git config --list

Store credentials

git config credential.helper store

Set username and email

git config --global user.email "you@example.com"
git config --global user.name "Your Name"

Windows - remove old credentials

rundll32.exe keymgr.dll,KRShowKeyMgr

post-receive hook

  • execute script on main git server, after receiving push: hooks/post-receive
#!/bin/bash
# unset GIT_INDEX_FILE # not needed for post-receive?
git --work-tree=/srv/targetfolder --git-dir=/home/demo/proj/.git checkout -f
or
#!/bin/bash
while read oldrev newrev ref
do
    if [[ $ref =~ .*/master$ ]];
    then
        echo "Master ref received.  Deploying master branch to production..."
        git --work-tree=/var/www/html --git-dir=/home/demo/proj checkout -f
    else
        echo "Ref $ref successfully received.  Doing nothing: only the master branch may be deployed on this server."
    fi
done
  • make executable
chmod +x post-receive

Speed-up

# alias 'acp' = add+commit+push
git config --global alias.acp '!f() { git add . && git commit -m "$@" && git push; }; f'         
git acp "this is my commit comment"

Links

Other

Special features

  • auto-commit when file changes
inotifywait -q -m -e CLOSE_WRITE --format="git commit -a -m 'autocommit on change' %w" file.txt | sh
or
while true; do
  inotifywait -qq -e CLOSE_WRITE ~/.calendar/calendar
  cd ~/.calendar; git commit -a -m 'autocommit on change'
done
# inotify "-r"  for recursive
or