From 256e8932393d52c005a6f79be60b6dad2aa44bbe Mon Sep 17 00:00:00 2001 From: Florian Festi Date: Thu, 20 Dec 2007 14:20:31 +0100 Subject: apply ffesti's changes Nevertheless is putting the slides into a git repo and maintaining them further a great idea. Feel free to include my changes and ask for help if ideas for extending the slides pop up. Florian Signed-off-by: Florian Festi Signed-off-by: Karel Zak --- git.tex | 490 ++++++++++++++++++++++++++++++++++++++++++++-------------------- 1 file changed, 342 insertions(+), 148 deletions(-) diff --git a/git.tex b/git.tex index a02fcee..696c8c7 100644 --- a/git.tex +++ b/git.tex @@ -24,33 +24,41 @@ \usepackage{colortbl} \usepackage[absolute,overlay]{textpos} +% Automatically create section page +\newcommand{\sectionpage}{\usebeamertemplate*{section page}} +\AtBeginSection[]% +{ + \begin{rhbg} + \frame{\sectionpage} + \end{rhbg} +} + \defverb\verbemail|Random Hacker | \defverb\kzakemail|| % presentation title/author/etc. \title{Git} \subtitle{(Why not CVS? ... because Git.)} -\author{Karel Zak\\ -\kzakemail} -\date{} - -% fancy section/part pages? -%\fancySectionOpens -%\fancyPartOpens +\author{Karel Zak \and\\ +Florian Festi \and\\ +Bart Trojanowski} \begin{document} \begin{rhbg} -\begin{frame} - \titlepage -\end{frame} + \begin{frame} + \titlepage + \end{frame} \end{rhbg} \begin{frame}[plain] -\vspace*{30ex} -Copyright \copyright{}\ \ \the\year\ \ Karel Zak.\\ -\vspace*{1ex} +\vspace*{15ex} +Copyright \copyright{}\ \ \the\year\ \ Karel Zak\\ +Copyright \copyright{}\ \ \the\year\ \ Tomas Janousek (beamer template)\\ +Copyright \copyright{}\ \ \the\year\ \ Florian Festi\\ +Copyright \copyright{}\ \ \the\year\ \ Bart Trojanowski\\ +\vspace*{5ex} Permission is granted to copy, distribute and/or modify this document under the terms of the GNU Free Documentation License, Version 1.2 or any later version published by the Free Software Foundation; @@ -90,7 +98,7 @@ Texts. \item ready for large projects (very good performance) \item repositories can be easily published (git://, ssh://, http://, rsync://, ...) \item cryptographic authentication of history (GPG-signed tags) - \item internally objects are addressed by content (SHA-1) -- no filenames + \item internally objects are addressed by content (SHA-1) -- not filenames \item local branches are local only (off-line work) \end{itemize} \end{frame} @@ -104,6 +112,8 @@ Texts. \item extra policy for write access \item SCM is not development tool, but source code archive only \item every change has impact to all developers + \item no privat branches + \item needs connection to server for most operations \end{itemize} \end{frame} @@ -124,10 +134,10 @@ Texts. branching and merging is cheap \begin{itemize} - \item you can prototyping + \item you can prototype \item you can collaborate with others developers on incomplete and unstable stuff \item you can easily (e.g. every day) rebase your changes to new upstream code - \item often merging (rebase) minimize conflicts between your patches and upstream + \item merge (rebase) often minimizes conflicts between your patches and upstream \end{itemize} \item @@ -136,12 +146,87 @@ Texts. \begin{itemize} \item reviewers hate huge patches \item well separated feature or change is easy to revert + \item per item commit messages \end{itemize} + \item much less dependent on your patches going in upstream + \item manage patches - not just store them \end{itemize} \end{frame} -\section{Implementation} +\begin{frame}[containsverbatim] + \frametitle{Workflow} + Changes go through several stages before ending up in their final destination + \begin{description}[master branch] + \item[working dir] current checkout - editing happens here + \item[index] aka ``cache'' aka ``staging area'' - changes that are selected to be commited + \item[commit] now packaged up with a commit message and part of the history + \item[master branch] move the commits over when the feature is finished + \item[origin] get the changes upstream + \end{description} +\end{frame} +\subsection{Commands} + +\begin{frame}[containsverbatim] + \frametitle{Syntax} + \begin{itemize} + \item \texttt{git [options]} + \item \texttt{git- [options]} + \item \texttt{man git-} + \item \texttt{git help } + \end{itemize} + + \begin{exampleblock}{High level commands: Porcelain} + \begin{verbatim} $ git commit -a -s -m "cool change" \end{verbatim} + \end{exampleblock} + \begin{exampleblock}{Low level commands: Plumbing} + \begin{verbatim} $ git rev-list --pretty=oneline v2.13.. \end{verbatim} + \end{exampleblock} +\end{frame} + +\begin{frame} + \frametitle{Basic commands (local)} + \begin{description}[git commit] + \item[git init] creates en empty repository at \texttt{./.git} + \item[git add] adds file contents to the next commit + \item[git rm] removes a file + \item[git mv] move a file + \item[git status] shows the working tree status + \item[git commit] records changes to the repository + \item[git log] shows commit log + \item[git show] shows commit (or another object) + \end{description} +\end{frame} + +\begin{frame} + \frametitle{Basic commands (remote)} + \begin{description}[git format-patch] + \item[git fetch] get new changes from external repository + \item[git pull] fetch + merge + \item[git push] write new changes to external repository + \item[git format-patch] exports a change + \item[git send-email] sends patch(s) + \item[git am] applies a series of patches from a mailbox + \end{description} +\end{frame} + +\begin{frame} + \frametitle{Advanced Commands (local)} + \begin{description}[git cherry-pick] + \item[git branch] create/modify/delete branches + \item[git checkout] switch work dir to another branch/commit + \item[git merge] merge two or more branches + \item[git rebase] changes starting point of a branch + \item[git cherry-pick] copy patch from another branch + \item[git reset] set back a branch HEAD + \item[git bisect] find the breaking patch + \item[git stash] save/restore current work dir changes + \item[git gc] compactify repository and do clean ups + \end{description} +\end{frame} + +\section{Implementation} +\subsection{Internal objects} \begin{frame} \frametitle{Internal objects} @@ -150,10 +235,9 @@ Texts. \end{block} \begin{description}[references] - \item[commit] refers to ``tree'' and ``parent`` (connection into the project history) + \item[commit] refers to ``tree'' and ``parent'' (connection into the project history) and contains the commit message \item[tree] represents the state of a single directory (list of ``blob'' objects and subtrees) \item[blob] contains file data without any other structure - \item[references] are human readable names for commits; for example tags, see files under .git/refs/heads/. \end{description} \end{frame} @@ -167,13 +251,37 @@ Texts. \end{description} \end{frame} +\begin{frame} + \frametitle{References} + \begin{itemize} + \item Tag + \begin{itemize} + \item contains SHA-1 sum of a commit + \item may contain an explaining message + \item can be PGP-signed + \item stays fix + \item .git/refs/tags + \end{itemize} + \item Branch + \begin{itemize} + \item SHA-1 sum of a commit + \item ``leaf'' of the history ``tree'' + \item follows the commits to that branch + \item .git/refs/heads + \end{itemize} + \item tracked branches - .git/refs/remotes/ origin + \item HEAD - the current branch + \item ORIG\_HEAD - HEAD before the last reset + \end{itemize} +\end{frame} \begin{frame}[containsverbatim] \frametitle{Trust} \begin{itemize} \item everything is content-addressed and based on SHA-1 \item two trees are same when HEAD SHA-1 are same - \item tags could be GPG-signed + \item SHA-1 summ are checked to asure data integrity + \item content, history and commit messages can be signed by only GPG-signing one tag \end{itemize} \begin{exampleblock}{} @@ -241,7 +349,42 @@ Texts. \end{itemize} \end{frame} -\section{Repositories} +\section{Getting started} +\subsection{Configuration} + +\begin{frame}[containsverbatim] + \frametitle{Configuration} + global configuration is in $\sim$/.gitconfig + \begin{exampleblock}{} + \begin{verbatim} $ git config --global --list + user.name=Florian Festi + user.email=ffesti@redhat.com + diff.color=auto\end{verbatim} + \end{exampleblock} + repository configuration is in repo/.git/config + \begin{exampleblock}{} + \begin{verbatim} $ git config --list\end{verbatim} + \end{exampleblock} + changing settings + \begin{exampleblock}{} + \begin{verbatim} $ git config --global user.name "Florian Festi" + $ git config --global user.email ffesti@redhat.com \end{verbatim} + \end{exampleblock} +\end{frame} + +\begin{frame}[containsverbatim] + \frametitle{.gitconfig} +simple sample config + \begin{exampleblock}{} + \begin{verbatim}[user] + name= Florian Festi + email = ffesti@redhat.com +[diff] + color = auto +\end{verbatim} +\end{exampleblock} +see \texttt{man git-config} for all config options +\end{frame} \begin{frame}[containsverbatim] \frametitle{Create a repository} @@ -271,11 +414,86 @@ Texts. \end{itemize} \end{frame} +\begin{frame}[containsverbatim] + \frametitle{Repository config file} + \begin{exampleblock}{} + \begin{verbatim} +[core] + repositoryformatversion = 0 + filemode = true + bare = false + logallrefupdates = true +[remote "origin"] + url = ssh://login.linux.duke.edu/.../yum.git + fetch = +refs/heads/*:refs/remotes/origin/* +[branch "master"] + remote = origin + merge = refs/heads/master +\end{verbatim} +\end{exampleblock} +\end{frame} + + +\subsection{Visualisation} + \begin{frame} \frametitle{Visualisation} + \begin{itemize} + \item visualization helps when working with branches + \item http://git.or.cz/gitwiki/InterfacesFrontendsAndTools + \end{itemize} +History viewer: + \begin{description} + \item[gitk] Tcl/Tk History Viewer + \item[qgit] Qt History Viewer, patch import/export + \item[gitweb] Web front end (CGI, mod\_perl) + \end{description} +Commit tools + \begin{description} + \item[git gui] Tcl/Tk, builtin + \end{description} +\end{frame} + +\begin{frame} + \frametitle{Visualisation: gitk} \includegraphics[width=0.9\textwidth]{gitk.png} \end{frame} +\begin{frame} + \frametitle{Visualisation: qgit} + \includegraphics[width=0.9\textwidth]{qgit.png} +\end{frame} + +\begin{frame} + \frametitle{Visualisation: Gitweb} + \includegraphics[width=0.9\textwidth]{gitweb.png} +\end{frame} + +\begin{frame}[containsverbatim] + \frametitle{Browsing changes} + \begin{description}[git whatchanged] + \item[git log] shows commit logs + \item[git show] shows one or more objects (blobs, trees, tags and commits) + \item[git blame] shows what revision and author last modified each line of a file + \item[git whatchanged] shows logs with difference each commit introduces + \end{description} + \begin{exampleblock}{} + \begin{scriptsize} + \begin{verbatim} +$ git log v2.5.. # commits since v2.5 +$ git log test..master # commits reachable from master + # but not test +$ git log --since="2 weeks ago" # commits from the last 2 weeks +$ git log Makefile # commits which modify Makefile +$ git log --pretty=format:"%h [%an]" # commit log in format + # "sha-1 [Author Name]" +$ git blame -L 10,15 foo.c # who modified code between lines + 10 and 15 +$ git show c1a47c171b # shows selected object (commit) \end{verbatim} + \end{scriptsize} + \end{exampleblock} +\end{frame} + \section{Branches} \begin{frame}[containsverbatim] @@ -293,8 +511,10 @@ Texts. \item[branch] is line of development \item[branch head] is a reference to the most recent commit on a branch \end{description} - \vspace*{1ex} - Branches, remote-tracking branches, and tags are all references to commits. + \begin{itemize} + \item branches become remote branches when cloning a repository + \item use \texttt{git branch -a} (all) or \texttt{-r} (remote) to see the remote branches + \end{itemize} \end{frame} @@ -310,6 +530,27 @@ Texts. \end{itemize} \end{frame} +\begin{frame}[containsverbatim] + \frametitle{Merge branch} + \begin{exampleblock}{Before} + \begin{verbatim} + A---B---C topic + / + D---E---F---G master \end{verbatim} + \end{exampleblock} + + \begin{exampleblock}{Command} + \begin{verbatim} $ git merge topic \end{verbatim} + \end{exampleblock} + + \begin{exampleblock}{After} + \begin{verbatim} + A---B---C topic + / \ + D---E---F---G---H master \end{verbatim} + \end{exampleblock} +\end{frame} + \begin{frame}[containsverbatim] \frametitle{Rebase branch} \begin{exampleblock}{Before} @@ -329,133 +570,112 @@ Texts. / D---E---F---G master \end{verbatim} \end{exampleblock} + \begin{exampleblock}{Alternative} + \begin{verbatim} $ git rebase -i topic \end{verbatim} + \end{exampleblock} \end{frame} -\begin{frame}[containsverbatim] - \frametitle{Edit 2nd commit from the top} - \begin{enumerate} - \item create a temporary branch (rewind to the commit in question): - \begin{exampleblock}{} - \begin{verbatim} $ git checkout -f -b tmp HEAD~2 \end{verbatim} - \end{exampleblock} +\begin{frame} + \frametitle{Merge vs Rebase} + \begin{itemize} + \item Merge + \begin{itemize} + \item does an 3-way merge (for simple cases) + \item leads to non linear history + \item merging several branches with each other looks messy + \item keeps separate branches visible + \item Use in public repositories! + \end{itemize} + \item Rebase + \begin{itemize} + \item reapplies the patches on top + \item alters history - new patches with new SHA-1 sums + \item breaks work based on that branch + \item therefore not suited for published work + \item allows creating ``the perfect patch'' against upstream + \item Use for private work! + \end{itemize} + \item Read the man pages for details! + \end{itemize} +\end{frame} - \item reset old changes and redo the commit - \begin{exampleblock}{} - \begin{verbatim} - $ git reset HEAD^ - $ vim foo.c - $ git commit -a -c ORIG_HEAD \end{verbatim} - \end{exampleblock} +\begin{frame} + \frametitle{Resolve Conflicts} + \begin{itemize} + \item Read the messages! + \item resolved stuff gets added to the index + \item conflicts are applied to the work dir only + \item resolve and add to index + \item merge: \texttt{commit} + \item rebase: \texttt{--continue}, \texttt{--abort} or \texttt{--skip} + \end{itemize} +\end{frame} - \item replay the later changes to the master: - \begin{exampleblock}{} - \begin{verbatim} $ git rebase --onto tmp master~2 master \end{verbatim} - \end{exampleblock} +\section{Real life with Git} +\subsection{Changing History} - \item clean up (delete) the temporary branch - \begin{exampleblock}{} - \begin{verbatim} $ git branch -D tmp \end{verbatim} - \end{exampleblock} +\begin{frame}[containsverbatim] + \frametitle{Edit 3rd commit from the top} + \begin{enumerate} + \item Working on branch master + \begin{exampleblock}{} + \begin{verbatim} + A--B--C--D--E(master)\end{verbatim} + \end{exampleblock} + \item realized you made a mistake in commit 'B' + \begin{exampleblock}{} + \begin{verbatim} $ git checkout HEAD~3 + $ git commit --amend + .B'(HEAD) + / + A--B--C--D--E(master)\end{verbatim} + \end{exampleblock} + \item bring back the other commits + \begin{exampleblock}{} + \begin{verbatim} $ git rebase HEAD master + A--B'--C--D--E(master)\end{verbatim} + \end{exampleblock} \end{enumerate} \end{frame} -\section{Real life with Git} - \begin{frame} \frametitle{Changes in project history} \begin{itemize} - \item the latest patches -- (\texttt{git reset}) reset current HEAD - + \item the very last patch -- \texttt{"git commit --amend"} to add changes to last commit + \item the latest patches -- \texttt{"git reset"} to remove the last commits from the history + \item organize your own branch + \begin{itemize} + \item \texttt{"git cherry-pick"} patch per patch into a new branch + \item \texttt{"git rebase -i"} to freely reorder patches + \end{itemize} \item deep in project history \begin{itemize} - \item rebease - \begin{itemize} - \item impact to all rebased commits (new SHA-1) - \item impact to all tags - - \item useless for publicly pushed changes - \end{itemize} - \item patch revert (\texttt{git revert}) - \begin{itemize} - \item zero impact to project history - \end{itemize} + \item \texttt{"git rebase"} to move around large part of the history + \item \texttt{"git revert"} to add a reversed patch on top \end{itemize} \end{itemize} \end{frame} +\subsection{Handling Patches} + \begin{frame} \frametitle{Send a patch} Basic rules: \begin{itemize} - \item one patch per e-mail + \item \structure{one patch per e-mail} \item don't use stupid e-mail clients (e.g. Outlook) - \item (don't use attachments) + \item \structure{don't use attachments} \item export patches by \texttt{git format-patch} \item send patches by \texttt{git send-email} \item well formatted patch is possible to apply by \texttt{git am} - \item don't forget to keep correct authorship (e.g when you are not author of the patch) + \item don't forget to \structure{keep correct authorship} (e.g when you are not author of the patch) - \item use commit messages -- a patch without comment is incomplete crap + \item \structure{use commit messages} -- a patch without comment is incomplete crap \end{itemize} \end{frame} -\section{Commands} - -\begin{frame}[containsverbatim] - \frametitle{Syntax} - \begin{itemize} - \item \texttt{git [options]} - \item \texttt{git- [options]} - \end{itemize} - - \begin{exampleblock}{High level} - \begin{verbatim} $ git commit -a -s -m "cool change" \end{verbatim} - \end{exampleblock} - \begin{exampleblock}{Low level} - \begin{verbatim} $ git rev-list --pretty=oneline v2.13.. \end{verbatim} - \end{exampleblock} -\end{frame} - -\begin{frame} - \frametitle{Basic commands} - \begin{description}[git format-path] - \item[git init] creates en empty repository at \texttt{./.git} - \item[git add] adds file contents to the next commit - \item[git reset] resets current HEAD - \item[git status] shows the working tree status - \item[git commit] records changes to the repository - \item[git log] shows commit log - \item[git show] shows commit (or another object) - \item[git format-path] exports a change - \item[git send-email] sends patch(s) - \item[git am] applies a series of patches from a mailbox - \end{description} -\end{frame} - -\subsection{Commits and patches} - -\begin{frame}[containsverbatim] - \frametitle{Commit changes} - \begin{block}{} - \begin{verbatim} git commit [options] [] \end{verbatim} - \end{block} - \begin{itemize} - \item \structure{-a} commits all modified or deleted files - \item \structure{-s} adds Signed-off-by line at the end of the commit message - - \item \structure{-c ORIG\_HEAD} reuses a commit message (e.g. from previously reseted commit) - \item \structure{--author "\verbemail"} overrides the author name - - \item starts \structure{\$EDITOR} for commit message (or \texttt{-m ""}) - \end{itemize} - - \begin{exampleblock}{} - \begin{verbatim} $ git commit -a -s\end{verbatim} - \end{exampleblock} -\end{frame} - \begin{frame}[containsverbatim] \frametitle{Export patches to files} \begin{block}{} @@ -501,37 +721,9 @@ $ git send-email --to "God " \ \end{exampleblock} \end{frame} -\begin{frame}[containsverbatim] - \frametitle{Browsing changes} - \begin{description}[git whatchanged] - \item[git log] shows commit logs - \item[git show] shows one or more objects (blobs, trees, tags and commits) - \item[git blame] shows what revision and author last modified each line of a file - \item[git whatchanged] shows logs with difference each commit introduces - \end{description} - \begin{exampleblock}{} - \begin{scriptsize} - \begin{verbatim} -$ git log v2.5.. # commits since v2.5 -$ git log test..master # commits reachable from master - # but not test -$ git log --since="2 weeks ago" # commits from the last 2 weeks -$ git log Makefile # commits which modify Makefile -$ git log --pretty=format:"%h [%an]" # commit log in format - # "sha-1 [Author Name]" -$ git blame -L 10,15 foo.c # who modified code between lines - 10 and 15 -$ git show c1a47c171b # shows selecte object (commit) \end{verbatim} - \end{scriptsize} - \end{exampleblock} -\end{frame} \section{Misc} -\begin{frame} - \frametitle{Gitweb} - \includegraphics[width=0.9\textwidth]{gitweb.png} -\end{frame} \begin{frame} \frametitle{References} @@ -554,8 +746,10 @@ $ git show c1a47c171b # shows selecte object (commit) \end{verbat {\Huge The end.} \par\vspace*{0.5cm} Thanks for listening. - \end{center} \hfill + \par\vspace*{5cm} + \url{http://kzak.fedorapeople.org/git-presentation.pdf} + \end{center} \end{frame} \end{document} -- cgit