Vim Fugitive in action - dzx.fr
Vim Fugitive by Tim Pope is a Git<br>wrapper for Vim. Its purpose is to integrate Git inside Vim, providing easier<br>access to the most common features, and some additional ones that would be<br>harder to replicate from the command-line interface (CLI).
Beginners might find Fugitive difficult because it provides a new interface and<br>requires both a good knowledge of Git (concepts and commands from the first 3<br>chapters of the Git Book) and Vim (Ex<br>commands, buffers, windows, diffs).
The reference documentation for Fugitive is accessible with :help fugitive.<br>It contains the list of commands, keybindings, and object specifiers. The<br>purpose of this article is to bridge the gap between a working knowledge of Git<br>and the use of Fugitive through concrete examples.
Table of Contents
Introduction
1.1<br>FizzBuzz
1.2<br>Git
1.3<br>Fugitive
Record changes
2.1<br>Summary view
2.2<br>Track files
2.3<br>Stage files
2.4<br>Commit
Advanced staging
3.1<br>Create a new branch
3.2<br>Inline diffs
3.3<br>Split changes
Review the commit history
4.1<br>Push to a remote
4.2<br>Unpushed commits
4.3<br>Commit log
4.4<br>Going further
Merge conflicts
5.1<br>Unmerged files
5.2<br>2-way diff
5.3<br>3-way diff
Rebase
6.1<br>Stash
6.2<br>Rebase conflict
6.3<br>Keybindings
Advanced merge
7.1<br>Preparation
7.2<br>With the CLI
7.3<br>With Fugitive
Conclusion
Introduction
This article iterates on a FizzBuzz implementation in Python to demonstrate the<br>use of Fugitive for common Git operations.
1.1<br>FizzBuzz
The algorithm is simple: for iii from 111 to 202020:
If 333 and 555 both divide iii, print “FizzBuzz”.
Else if 333 divides iii, print “Fizz”.
Else if 555 divides iii, print “Buzz”.
Else, print iii.
1.2<br>Git
Initialize a new Git repository at ~/fizzbuzz:
$ git init ~/fizzbuzz<br>Initialized empty Git repository in ~/fizzbuzz/.git/
Change directory to this repository:
$ cd ~/fizzbuzz
Then, start vim (or nvim).
1.3<br>Fugitive
To install Fugitive, follow the instructions for your Vim plugin manager on<br>VimAwesome. To check that it is<br>properly installed, try to open the documentation with :help fugitive.
The plugin defines the Ex command :Git [args] (abbreviated as :G [args])<br>that works almost like git in a shell. The only difference is that commands<br>such as :Git diff or :Git log are augmented: their output is redirected to<br>a Fugitive buffer inside Vim that serves as a pager.
In these buffers, Fugitive identifies objects: file names, commit hashes, or<br>diffs. It provides keybindings to act upon them and perform Git operations:<br>staging, diffing, committing, etc. It also provides syntax highlighting for<br>selected output formats.
On the Ex command line, Fugitive extends the revision specifiers defined by Git<br>in git-rev-parse(1). You can use<br>them with the command :Git, but also with extra commands such as :Gedit [object] to edit the specified object in a new buffer.
Record changes
The summary buffer constitutes Fugitive’s main interface, from which you can<br>stage, diff, and commit files to record changes to a Git repository.
2.1<br>Summary view
Run the command :G without arguments to access the main summary buffer<br>(interactive equivalent of git status):
1 Head: master<br>2 Push: origin/master<br>3 Help: g?<br>~/fizzbuzz/.git/index [-][RO] 1,1 All<br>:G | only
Note that Fugitive doesn’t perform any window management, so you will often end<br>up with a new split, or it will replace the focused buffer. Such commands in<br>Fugitive have variations to split vertically, horizontally, or open a new tab.<br>For the status, you can use Vim’s built-in window management commands, like<br>:only to hide windows other than the focused one (same as ). You<br>can chain it after a Git command as :G | only.
Inside the buffers it manages, Fugitive defines a number of keybindings for<br>common Git operations. Press g? to quickly open the documentation at the key<br>mappings section.
2.2<br>Track files
Edit a new file with :e main.py and append the following content:
main.py
for i in range(1, 21):<br>print(i)
Save the file with :w. The summary buffer shows its name under the<br>“Untracked” section, which means it doesn’t belong to the repository yet:
1 Head: master<br>2 Push: origin/master<br>3 Help: g?<br>5 Untracked (1)<br>6 ? main.py<br>~/fizzbuzz/.git/index [-][RO] 1,1 All<br>"main.py" [New] 2L, 33C written
Vim may create an additional main.py.swp file for recovery purposes. You can<br>create a gitignore file to hide these<br>swap files from Git’s untracked files, or configure Vim to save them elsewhere<br>(see: :h directory).
Files listed in the summary buffer are an example of Fugitive objects that you<br>can act upon. Git offers the ability to add untracked files without staging<br>them. To track the file with Fugitive, position the cursor on main.py and<br>press I (this is equivalent to git add --intent-to-add main.py):
1 Head: master<br>2 Push: origin/master<br>3 Help: g?<br>5 Unstaged (1)<br>6 A main.py<br>~/fizzbuzz/.git/index [-][RO] 1,1 All
In the unstaged state, the file belongs to the worktree. The attribute A<br>indicates a new...