31 Commits
v2.1 ... v2.2

Author SHA1 Message Date
Tim Pope
34719016ec fugitive.vim 2.2
* Provide :Gpush, :Gfetch, :Gmerge, and Gpull.
* Use -L to handle :Glog range.
* :Gcommit -v opens message in new tab.
* API for custom :Gbrowse handlers.
* Invoke :Browse if available to open URL.
* Colorize hashes in :Gblame buffer.
* Set cursorbind and nobuflisted in :Gblame buffers.
* :Gblame in blame buffer toggles buffer.
2015-01-20 01:37:22 -05:00
Daniel Hahler
2c8461db08 Use <nomodeline> with Fugitive autocmds, and un-silent them
Closes #580.
2014-11-21 03:25:20 -05:00
John Whitley
d3b98d9886 Make configured_tree a caching global function
This implements the changes suggested in tpope/fugitive#415.
s:repo_configured_tree is now a global, s:configured_tree() that caches
the bidirectional relation between the worktree and the git_dir.
extract_git_dir() now uses that relation to check whether the
directories it scans are valid worktrees known by the repo at $GIT_DIR.
2014-11-06 13:49:30 -05:00
Tim Pope
5699f4613c Fix instaweb support
Closes #571.
2014-11-06 13:47:26 -05:00
Tim Pope
0374322ba5 Fix :Glog
Closes #545.
2014-09-02 12:05:34 -04:00
Tim Pope
90ee6fb5d2 Pass line1 and line2 as 0 for :Gbrowse without range
Closes #530.
2014-07-27 12:14:42 -04:00
Tim Pope
04fe4bfcd9 Set nobuflisted in blame buffers 2014-07-23 17:55:15 -04:00
Tom McDonald
7423d72b51 Ensure clipboard support before using * register
Closes #526.
2014-07-23 17:46:47 -04:00
Tim Pope
24d4098ceb Change arity of browse API
It's debatable whether the repo object should be passed at all, so let's
not commit to a positional parameter for it.

References #445.
2014-07-22 20:48:40 -04:00
Tim Pope
5aaa65736d Browse handler API
Taking experimental out of the name, but small tweaks may occur before
then next release.

For future compatibility, any third party handlers should bail and
return an empty string if any of the following are true:

* More than 2 arguments are given.
* The second argument isn't a dictionary.
* The dictionary doesn't contain a "remote" key.

Closes #445.
2014-07-22 00:18:24 -04:00
Tim Pope
5d1c219ee5 Fix load order issue 2014-07-17 21:05:03 -04:00
Tim Pope
a739112bfc Experimentally expose browse API
References #445.
2014-07-17 20:16:28 -04:00
Tim Pope
d376506177 Try including helptags instructions in README 2014-07-17 19:57:09 -04:00
Tim Pope
9af975c82c Don't run pre-commit hook on merge 2014-07-07 21:23:22 -04:00
Tim Pope
11f89ba749 Only change 'tags' if tags file exists
Closes #402.  References #426.
2014-07-06 00:20:19 -04:00
Tim Pope
45e5317200 Try harder to avoid -esp on :Gcommit follow-up
Closes #516.
2014-07-05 19:01:00 -04:00
Tim Pope
ee2b0ecdb8 Provide :Gpush and :Gfetch
Closes #450.
2014-06-30 14:30:44 -04:00
Tim Pope
94a5d6fe2f Fix :Gcommit when closing message lands in different project 2014-06-30 14:02:53 -04:00
Tim Pope
0cd33c6170 :Gcommit -v opens message in new tab
Closes #513.  References #480.
2014-06-29 14:52:43 -04:00
Tim Pope
6239f5ed8e Ignore ^[[K lines from progress output 2014-06-29 14:46:16 -04:00
Tim Pope
188692556a Fix subcommand complete when cursor mid-line 2014-06-29 11:02:47 -04:00
Tim Pope
716f3d2d4e Expose list of global git subcommands 2014-06-29 10:54:57 -04:00
Tim Pope
8576741d61 Don't quote url argument to :Browse 2014-06-26 17:08:59 -04:00
Tim Pope
32957cb552 Invoke :Browse if available to open URL
Example that invokes open(1) on OS X:

    command! -bar -nargs=1 Browse silent! !open <args>

Closes #509.
2014-06-26 17:07:07 -04:00
Tim Pope
fdc8569c18 :Gblame in blame buffer deletes buffer
Closes #511.
2014-06-26 14:40:09 -04:00
Tim Pope
7fb703534a :Gmerge and :Gpull 2014-06-25 13:05:14 -04:00
Tim Pope
41cdbdcd62 Force :Gstatus U to root of tree
References #97.
2014-06-25 10:29:17 -04:00
Tim Pope
91900baad1 Set cursorbind in :Gblame 2014-06-24 23:10:57 -04:00
Tim Pope
fb5661211d Colorize hashes in blame
References #369.
2014-06-24 21:54:25 -04:00
Tim Pope
276f89837f Use -L to handle :Glog range
Closes #507.  References #286.
2014-06-24 19:36:47 -04:00
Tim Pope
4581cd4217 Support -L in :Glog errorformat
References #507.
2014-06-24 19:36:47 -04:00
3 changed files with 376 additions and 93 deletions

View File

@@ -55,15 +55,13 @@ and `Git!` to open the output of a command in a temp file.
## Installation ## Installation
If you don't have a preferred installation method, I recommend If you don't have a preferred installation method, one option is to install
installing [pathogen.vim](https://github.com/tpope/vim-pathogen), and [pathogen.vim](https://github.com/tpope/vim-pathogen), and then copy
then simply copy and paste: and paste:
cd ~/.vim/bundle cd ~/.vim/bundle
git clone git://github.com/tpope/vim-fugitive.git git clone git://github.com/tpope/vim-fugitive.git
vim -u NONE -c "helptags vim-fugitive/doc" -c q
Once help tags have been generated, you can view the manual with
`:help fugitive`.
If your Vim version is below 7.2, I recommend also installing If your Vim version is below 7.2, I recommend also installing
[vim-git](https://github.com/tpope/vim-git) for syntax highlighting and [vim-git](https://github.com/tpope/vim-git) for syntax highlighting and

View File

@@ -63,12 +63,32 @@ that are part of Git repositories).
to commit, |:Gstatus| is called instead. Unless the to commit, |:Gstatus| is called instead. Unless the
arguments given would skip the invocation of an editor arguments given would skip the invocation of an editor
(e.g., -m), a split window will be used to obtain a (e.g., -m), a split window will be used to obtain a
commit message. Write and close that window (:wq or commit message, or a new tab if -v is given. Write
|:Gwrite|) to finish the commit. Unlike when running and close that window (:wq or |:Gwrite|) to finish the
the actual git-commit command, it is possible (but commit. Unlike when running the actual git-commit
unadvisable) to muck with the index with commands like command, it is possible (but unadvisable) to alter the
git-add and git-reset while a commit message is index with commands like git-add and git-reset while a
pending. commit message is pending.
*fugitive-:Gmerge*
:Gmerge [args] Calls git-merge and loads errors and conflicted files
into the quickfix list. Opens a |:Gcommit| style
split window for the commit message if the merge
succeeds. If called during a merge conflict, the
conflicted files from the current index are loaded
into the quickfix list.
*fugitive-:Gpull*
:Gpull [args] Like |:Gmerge|, but for git-pull.
*fugitive-:Gpush*
:Gpush [args] Invoke git-push, load the results into the quickfix
list, and invoke |:cwindow| to reveal any errors.
|:Dispatch| is used if available for asynchronous
invocation.
*fugitive-:Gfetch*
:Gfetch [args] Like |:Gpush|, but for git-fetch.
*fugitive-:Ggrep* *fugitive-:Ggrep*
:Ggrep [args] |:grep| with git-grep as 'grepprg'. :Ggrep [args] |:grep| with git-grep as 'grepprg'.
@@ -84,6 +104,11 @@ that are part of Git repositories).
previous commits rather than previous file revisions previous commits rather than previous file revisions
are loaded. are loaded.
:{range}Glog [args] Use git-log -L to load previous revisions of the given
range of the current file into the quickfix list. The
cursor is positioned on the first line of the first
diff hunk for each commit.
*fugitive-:Gllog* *fugitive-:Gllog*
:Gllog [args] Like |:Glog|, but use the location list instead of the :Gllog [args] Like |:Glog|, but use the location list instead of the
quickfix list. quickfix list.

View File

@@ -1,6 +1,6 @@
" fugitive.vim - A Git wrapper so awesome, it should be illegal " fugitive.vim - A Git wrapper so awesome, it should be illegal
" Maintainer: Tim Pope <http://tpo.pe/> " Maintainer: Tim Pope <http://tpo.pe/>
" Version: 2.1 " Version: 2.2
" GetLatestVimScripts: 2975 1 :AutoInstall: fugitive.vim " GetLatestVimScripts: 2975 1 :AutoInstall: fugitive.vim
if exists('g:loaded_fugitive') || &cp if exists('g:loaded_fugitive') || &cp
@@ -145,6 +145,13 @@ function! fugitive#extract_git_dir(path) abort
if root ==# $GIT_WORK_TREE && fugitive#is_git_dir($GIT_DIR) if root ==# $GIT_WORK_TREE && fugitive#is_git_dir($GIT_DIR)
return $GIT_DIR return $GIT_DIR
endif endif
if fugitive#is_git_dir($GIT_DIR)
" Ensure that we've cached the worktree
call s:configured_tree($GIT_DIR)
if has_key(s:dir_for_worktree, root)
return s:dir_for_worktree[root]
endif
endif
let dir = s:sub(root, '[\/]$', '') . '/.git' let dir = s:sub(root, '[\/]$', '') . '/.git'
let type = getftype(dir) let type = getftype(dir)
if type ==# 'dir' && fugitive#is_git_dir(dir) if type ==# 'dir' && fugitive#is_git_dir(dir)
@@ -178,20 +185,34 @@ function! fugitive#detect(path) abort
endif endif
endif endif
if exists('b:git_dir') if exists('b:git_dir')
silent doautocmd User FugitiveBoot if exists('#User#FugitiveBoot')
try
let [save_mls, &modelines] = [&mls, 0]
doautocmd User FugitiveBoot
finally
let &mls = save_mls
endtry
endif
cnoremap <buffer> <expr> <C-R><C-G> fnameescape(<SID>recall()) cnoremap <buffer> <expr> <C-R><C-G> fnameescape(<SID>recall())
nnoremap <buffer> <silent> y<C-G> :call setreg(v:register, <SID>recall())<CR> nnoremap <buffer> <silent> y<C-G> :call setreg(v:register, <SID>recall())<CR>
let buffer = fugitive#buffer() let buffer = fugitive#buffer()
if expand('%:p') =~# '//' if expand('%:p') =~# '//'
call buffer.setvar('&path', s:sub(buffer.getvar('&path'), '^\.%(,|$)', '')) call buffer.setvar('&path', s:sub(buffer.getvar('&path'), '^\.%(,|$)', ''))
endif endif
if stridx(buffer.getvar('&tags'), escape(b:git_dir.'/tags', ', ')) == -1 if stridx(buffer.getvar('&tags'), escape(b:git_dir, ', ')) == -1
if filereadable(b:git_dir.'/tags')
call buffer.setvar('&tags', escape(b:git_dir.'/tags', ', ').','.buffer.getvar('&tags')) call buffer.setvar('&tags', escape(b:git_dir.'/tags', ', ').','.buffer.getvar('&tags'))
if &filetype !=# '' endif
if &filetype !=# '' && filereadable(b:git_dir.'/'.&filetype.'.tags')
call buffer.setvar('&tags', escape(b:git_dir.'/'.&filetype.'.tags', ', ').','.buffer.getvar('&tags')) call buffer.setvar('&tags', escape(b:git_dir.'/'.&filetype.'.tags', ', ').','.buffer.getvar('&tags'))
endif endif
endif endif
silent doautocmd User Fugitive try
let [save_mls, &modelines] = [&mls, 0]
doautocmd User Fugitive
finally
let &mls = save_mls
endtry
endif endif
endfunction endfunction
@@ -209,6 +230,8 @@ augroup END
let s:repo_prototype = {} let s:repo_prototype = {}
let s:repos = {} let s:repos = {}
let s:worktree_for_dir = {}
let s:dir_for_worktree = {}
function! s:repo(...) abort function! s:repo(...) abort
let dir = a:0 ? a:1 : (exists('b:git_dir') && b:git_dir !=# '' ? b:git_dir : fugitive#extract_git_dir(expand('%:p'))) let dir = a:0 ? a:1 : (exists('b:git_dir') && b:git_dir !=# '' ? b:git_dir : fugitive#extract_git_dir(expand('%:p')))
@@ -232,21 +255,23 @@ function! s:repo_dir(...) dict abort
return join([self.git_dir]+a:000,'/') return join([self.git_dir]+a:000,'/')
endfunction endfunction
function! s:repo_configured_tree() dict abort function! s:configured_tree(git_dir) abort
if !has_key(self,'_tree') if !has_key(s:worktree_for_dir, a:git_dir)
let self._tree = '' let s:worktree_for_dir[a:git_dir] = ''
if filereadable(self.dir('config')) let config_file = a:git_dir . '/config'
let config = readfile(self.dir('config'),'',10) if filereadable(config_file)
let config = readfile(config_file,'',10)
call filter(config,'v:val =~# "^\\s*worktree *="') call filter(config,'v:val =~# "^\\s*worktree *="')
if len(config) == 1 if len(config) == 1
let self._tree = matchstr(config[0], '= *\zs.*') let s:worktree_for_dir[a:git_dir] = matchstr(config[0], '= *\zs.*')
let s:dir_for_worktree[s:worktree_for_dir[a:git_dir]] = a:git_dir
endif endif
endif endif
endif endif
if self._tree =~# '^\.' if s:worktree_for_dir[a:git_dir] =~# '^\.'
return simplify(self.dir(self._tree)) return simplify(a:git_dir . '/' . s:worktree_for_dir[a:git_dir])
else else
return self._tree return s:worktree_for_dir[a:git_dir]
endif endif
endfunction endfunction
@@ -254,7 +279,7 @@ function! s:repo_tree(...) dict abort
if self.dir() =~# '/\.git$' if self.dir() =~# '/\.git$'
let dir = self.dir()[0:-6] let dir = self.dir()[0:-6]
else else
let dir = self.configured_tree() let dir = s:configured_tree(self.git_dir)
endif endif
if dir ==# '' if dir ==# ''
call s:throw('no work tree') call s:throw('no work tree')
@@ -267,7 +292,7 @@ function! s:repo_bare() dict abort
if self.dir() =~# '/\.git$' if self.dir() =~# '/\.git$'
return 0 return 0
else else
return self.configured_tree() ==# '' return s:configured_tree(self.git_dir) ==# ''
endif endif
endfunction endfunction
@@ -332,7 +357,7 @@ function! s:repo_head(...) dict abort
return branch return branch
endfunction endfunction
call s:add_methods('repo',['dir','configured_tree','tree','bare','translate','head']) call s:add_methods('repo',['dir','tree','bare','translate','head'])
function! s:repo_git_command(...) dict abort function! s:repo_git_command(...) dict abort
let git = g:fugitive_git_executable . ' --git-dir='.s:shellesc(self.git_dir) let git = g:fugitive_git_executable . ' --git-dir='.s:shellesc(self.git_dir)
@@ -648,15 +673,19 @@ function! s:Git(bang, args) abort
return matchstr(a:args, '\v\C\\@<!%(\\\\)*\|\zs.*') return matchstr(a:args, '\v\C\\@<!%(\\\\)*\|\zs.*')
endfunction endfunction
function! s:GitComplete(A,L,P) abort function! fugitive#git_commands() abort
if !exists('s:exec_path') if !exists('s:exec_path')
let s:exec_path = s:sub(system(g:fugitive_git_executable.' --exec-path'),'\n$','') let s:exec_path = s:sub(system(g:fugitive_git_executable.' --exec-path'),'\n$','')
endif endif
let cmds = map(split(glob(s:exec_path.'/git-*'),"\n"),'s:sub(v:val[strlen(s:exec_path)+5 : -1],"\\.exe$","")') return map(split(glob(s:exec_path.'/git-*'),"\n"),'s:sub(v:val[strlen(s:exec_path)+5 : -1],"\\.exe$","")')
if a:L =~ ' [[:alnum:]-]\+ ' endfunction
return s:repo().superglob(a:A)
else function! s:GitComplete(A, L, P) abort
if strpart(a:L, 0, a:P) !~# ' [[:alnum:]-]\+ '
let cmds = fugitive#git_commands()
return filter(sort(cmds+keys(s:repo().aliases())), 'strpart(v:val, 0, strlen(a:A)) ==# a:A') return filter(sort(cmds+keys(s:repo().aliases())), 'strpart(v:val, 0, strlen(a:A)) ==# a:A')
else
return s:repo().superglob(a:A)
endif endif
endfunction endfunction
@@ -792,9 +821,9 @@ function! s:StageUndo() abort
if section ==# 'untracked' if section ==# 'untracked'
call delete(s:repo().tree(filename)) call delete(s:repo().tree(filename))
elseif section ==# 'unstaged' elseif section ==# 'unstaged'
call repo.git_chomp('checkout', '--', filename) call repo.git_chomp_in_tree('checkout', '--', filename)
else else
call repo.git_chomp('checkout', 'HEAD', '--', filename) call repo.git_chomp_in_tree('checkout', 'HEAD', '--', filename)
endif endif
call s:StageReloadSeek(filename, line('.'), line('.')) call s:StageReloadSeek(filename, line('.'), line('.'))
let @" = hash let @" = hash
@@ -960,15 +989,16 @@ endfunction
call s:command("-nargs=? -complete=customlist,s:CommitComplete Gcommit :execute s:Commit(<q-args>)") call s:command("-nargs=? -complete=customlist,s:CommitComplete Gcommit :execute s:Commit(<q-args>)")
function! s:Commit(args) abort function! s:Commit(args, ...) abort
let repo = a:0 ? a:1 : s:repo()
let cd = exists('*haslocaldir') && haslocaldir() ? 'lcd ' : 'cd ' let cd = exists('*haslocaldir') && haslocaldir() ? 'lcd ' : 'cd '
let dir = getcwd() let dir = getcwd()
let msgfile = s:repo().dir('COMMIT_EDITMSG') let msgfile = repo.dir('COMMIT_EDITMSG')
let outfile = tempname() let outfile = tempname()
let errorfile = tempname() let errorfile = tempname()
try try
try try
execute cd.s:fnameescape(s:repo().tree()) execute cd.s:fnameescape(repo.tree())
if s:winshell() if s:winshell()
let command = '' let command = ''
let old_editor = $GIT_EDITOR let old_editor = $GIT_EDITOR
@@ -976,7 +1006,7 @@ function! s:Commit(args) abort
else else
let command = 'env GIT_EDITOR=false ' let command = 'env GIT_EDITOR=false '
endif endif
let command .= s:repo().git_command('commit').' '.a:args let command .= repo.git_command('commit').' '.a:args
if &shell =~# 'csh' if &shell =~# 'csh'
noautocmd silent execute '!('.command.' > '.outfile.') >& '.errorfile noautocmd silent execute '!('.command.' > '.outfile.') >& '.errorfile
elseif a:args =~# '\%(^\| \)-\%(-interactive\|p\|-patch\)\>' elseif a:args =~# '\%(^\| \)-\%(-interactive\|p\|-patch\)\>'
@@ -1002,15 +1032,18 @@ function! s:Commit(args) abort
let error = get(errors,-2,get(errors,-1,'!')) let error = get(errors,-2,get(errors,-1,'!'))
if error =~# 'false''\=\.$' if error =~# 'false''\=\.$'
let args = a:args let args = a:args
let args = s:gsub(args,'%(%(^| )-- )@<!%(^| )@<=%(-[esp]|--edit|--interactive|patch|--signoff)%($| )','') let args = s:gsub(args,'%(%(^| )-- )@<!%(^| )@<=%(-[esp]|--edit|--interactive|--patch|--signoff)%($| )','')
let args = s:gsub(args,'%(%(^| )-- )@<!%(^| )@<=%(-c|--reedit-message|--reuse-message|-F|--file|-m|--message)%(\s+|\=)%(''[^'']*''|"%(\\.|[^"])*"|\\.|\S)*','') let args = s:gsub(args,'%(%(^| )-- )@<!%(^| )@<=%(-c|--reedit-message|--reuse-message|-F|--file|-m|--message)%(\s+|\=)%(''[^'']*''|"%(\\.|[^"])*"|\\.|\S)*','')
let args = s:gsub(args,'%(^| )@<=[%#]%(:\w)*','\=expand(submatch(0))') let args = s:gsub(args,'%(^| )@<=[%#]%(:\w)*','\=expand(submatch(0))')
let args = s:sub(args, '\ze -- |$', ' --no-edit --no-interactive --no-signoff')
let args = '-F '.s:shellesc(msgfile).' '.args let args = '-F '.s:shellesc(msgfile).' '.args
if args !~# '\%(^\| \)--cleanup\>' if args !~# '\%(^\| \)--cleanup\>'
let args = '--cleanup=strip '.args let args = '--cleanup=strip '.args
endif endif
if bufname('%') == '' && line('$') == 1 && getline(1) == '' && !&mod if bufname('%') == '' && line('$') == 1 && getline(1) == '' && !&mod
execute 'keepalt edit '.s:fnameescape(msgfile) execute 'keepalt edit '.s:fnameescape(msgfile)
elseif a:args =~# '\%(^\| \)-\%(-verbose\|\w*v\)\>'
execute 'keepalt tabedit '.s:fnameescape(msgfile)
elseif s:buffer().type() ==# 'index' elseif s:buffer().type() ==# 'index'
execute 'keepalt edit '.s:fnameescape(msgfile) execute 'keepalt edit '.s:fnameescape(msgfile)
execute (search('^#','n')+1).'wincmd+' execute (search('^#','n')+1).'wincmd+'
@@ -1052,11 +1085,130 @@ function! s:FinishCommit() abort
let args = getbufvar(+expand('<abuf>'),'fugitive_commit_arguments') let args = getbufvar(+expand('<abuf>'),'fugitive_commit_arguments')
if !empty(args) if !empty(args)
call setbufvar(+expand('<abuf>'),'fugitive_commit_arguments','') call setbufvar(+expand('<abuf>'),'fugitive_commit_arguments','')
return s:Commit(args) return s:Commit(args, s:repo(getbufvar(+expand('<abuf>'),'git_dir')))
endif endif
return '' return ''
endfunction endfunction
" Section: Gmerge, Gpull
call s:command("-nargs=? -bang -complete=custom,s:RevisionComplete Gmerge " .
\ "execute s:Merge('merge', <bang>0, <q-args>)")
call s:command("-nargs=? -bang -complete=custom,s:RemoteComplete Gpull " .
\ "execute s:Merge('pull --progress', <bang>0, <q-args>)")
function! s:RevisionComplete(A, L, P) abort
return s:repo().git_chomp('rev-parse', '--symbolic', '--branches', '--tags', '--remotes')
\ . "\nHEAD\nFETCH_HEAD\nORIG_HEAD"
endfunction
function! s:RemoteComplete(A, L, P) abort
let remote = matchstr(a:L, ' \zs\S\+\ze ')
if !empty(remote)
let matches = split(s:repo().git_chomp('ls-remote', remote), "\n")
call filter(matches, 'v:val =~# "\t" && v:val !~# "{"')
call map(matches, 's:sub(v:val, "^.*\t%(refs/%(heads/|tags/)=)=", "")')
else
let matches = split(s:repo().git_chomp('remote'), "\n")
endif
return join(matches, "\n")
endfunction
function! fugitive#cwindow() abort
if &buftype == 'quickfix'
cwindow
else
botright cwindow
if &buftype == 'quickfix'
wincmd p
endif
endif
endfunction
let s:common_efm = ''
\ . '%+Egit:%.%#,'
\ . '%+Eusage:%.%#,'
\ . '%+Eerror:%.%#,'
\ . '%+Efatal:%.%#,'
\ . '%-G%.%#%\e[K%.%#,'
\ . '%-G%.%#%\r%.%\+'
function! s:Merge(cmd, bang, args) abort
let cd = exists('*haslocaldir') && haslocaldir() ? 'lcd' : 'cd'
let cwd = getcwd()
let [mp, efm] = [&l:mp, &l:efm]
let had_merge_msg = filereadable(s:repo().dir('MERGE_MSG'))
try
let &l:errorformat = ''
\ . '%-Gerror:%.%#false''.,'
\ . '%-G%.%# ''git commit'' %.%#,'
\ . '%+Emerge:%.%#,'
\ . s:common_efm . ','
\ . '%+ECannot %.%#: You have unstaged changes.,'
\ . '%+ECannot %.%#: Your index contains uncommitted changes.,'
\ . '%+EThere is no tracking information for the current branch.,'
\ . '%+EYou are not currently on a branch. Please specify which,'
\ . 'CONFLICT (%m): %f deleted in %.%#,'
\ . 'CONFLICT (%m): Merge conflict in %f,'
\ . 'CONFLICT (%m): Rename \"%f\"->%.%#,'
\ . 'CONFLICT (%m): Rename %.%#->%f %.%#,'
\ . 'CONFLICT (%m): There is a directory with name %f in %.%#,'
\ . '%+ECONFLICT %.%#,'
\ . '%+EKONFLIKT %.%#,'
\ . '%+ECONFLIT %.%#,'
\ . "%+EXUNG \u0110\u1ed8T %.%#,"
\ . "%+E\u51b2\u7a81 %.%#,"
\ . 'U%\t%f'
if a:cmd =~# '^merge' && empty(a:args) &&
\ (had_merge_msg || isdirectory(s:repo().dir('rebase-apply')) ||
\ !empty(s:repo().git_chomp('diff-files', '--diff-filter=U')))
let &l:makeprg = g:fugitive_git_executable.' diff-files --name-status --diff-filter=U'
else
let &l:makeprg = s:sub(g:fugitive_git_executable.' -c core.editor=false '.
\ a:cmd . (a:args =~# ' \%(--no-edit\|--abort\|-m\)\>' ? '' : ' --edit') . ' ' . a:args,
\ ' *$', '')
endif
if !empty($GIT_EDITOR)
let old_editor = $GIT_EDITOR
let $GIT_EDITOR = 'false'
endif
execute cd fnameescape(s:repo().tree())
silent noautocmd make!
catch /^Vim\%((\a\+)\)\=:E211/
let err = v:exception
finally
redraw!
let [&l:mp, &l:efm] = [mp, efm]
if exists('old_editor')
let $GIT_EDITOR = old_editor
endif
execute cd fnameescape(cwd)
endtry
call fugitive#reload_status()
if empty(filter(getqflist(),'v:val.valid'))
if !had_merge_msg && filereadable(s:repo().dir('MERGE_MSG'))
cclose
return 'Gcommit --no-status -n -t '.s:shellesc(s:repo().dir('MERGE_MSG'))
endif
endif
let qflist = getqflist()
let found = 0
for e in qflist
if !empty(e.bufnr)
let found = 1
let e.pattern = '^<<<<<<<'
endif
endfor
call fugitive#cwindow()
if found
call setqflist(qflist, 'r')
if !a:bang
return 'cfirst'
endif
endif
return exists('err') ? 'echoerr '.string(err) : ''
endfunction
" Section: Ggrep, Glog " Section: Ggrep, Glog
if !exists('g:fugitive_summary_format') if !exists('g:fugitive_summary_format')
@@ -1065,8 +1217,8 @@ endif
call s:command("-bang -nargs=? -complete=customlist,s:EditComplete Ggrep :execute s:Grep('grep',<bang>0,<q-args>)") call s:command("-bang -nargs=? -complete=customlist,s:EditComplete Ggrep :execute s:Grep('grep',<bang>0,<q-args>)")
call s:command("-bang -nargs=? -complete=customlist,s:EditComplete Glgrep :execute s:Grep('lgrep',<bang>0,<q-args>)") call s:command("-bang -nargs=? -complete=customlist,s:EditComplete Glgrep :execute s:Grep('lgrep',<bang>0,<q-args>)")
call s:command("-bar -bang -nargs=* -range=0 -complete=customlist,s:EditComplete Glog :call s:Log('grep<bang>',<count>,<f-args>)") call s:command("-bar -bang -nargs=* -range=0 -complete=customlist,s:EditComplete Glog :call s:Log('grep<bang>',<line1>,<count>,<f-args>)")
call s:command("-bar -bang -nargs=* -complete=customlist,s:EditComplete Gllog :call s:Log('lgrep<bang>',<count>,<f-args>)") call s:command("-bar -bang -nargs=* -range=0 -complete=customlist,s:EditComplete Gllog :call s:Log('lgrep<bang>',<line1>,<count>,<f-args>)")
function! s:Grep(cmd,bang,arg) abort function! s:Grep(cmd,bang,arg) abort
let grepprg = &grepprg let grepprg = &grepprg
@@ -1107,13 +1259,13 @@ function! s:Grep(cmd,bang,arg) abort
endtry endtry
endfunction endfunction
function! s:Log(cmd, count, ...) abort function! s:Log(cmd, line1, line2, ...) abort
let path = s:buffer().path('/') let path = s:buffer().path('/')
if path =~# '^/\.git\%(/\|$\)' || index(a:000,'--') != -1 if path =~# '^/\.git\%(/\|$\)' || index(a:000,'--') != -1
let path = '' let path = ''
endif endif
let cmd = ['--no-pager', 'log', '--no-color'] let cmd = ['--no-pager', 'log', '--no-color']
let cmd += ['--pretty=format:fugitive://'.s:repo().dir().'//%H'.path.':'.(a:count ? a:count : '').'::'.g:fugitive_summary_format] let cmd += ['--pretty=format:fugitive://'.s:repo().dir().'//%H'.path.'::'.g:fugitive_summary_format]
if empty(filter(a:000[0 : index(a:000,'--')],'v:val !~# "^-"')) if empty(filter(a:000[0 : index(a:000,'--')],'v:val !~# "^-"'))
if s:buffer().commit() =~# '\x\{40\}' if s:buffer().commit() =~# '\x\{40\}'
let cmd += [s:buffer().commit()] let cmd += [s:buffer().commit()]
@@ -1123,7 +1275,11 @@ function! s:Log(cmd, count, ...) abort
end end
let cmd += map(copy(a:000),'s:sub(v:val,"^\\%(%(:\\w)*)","\\=fnamemodify(s:buffer().path(),submatch(1))")') let cmd += map(copy(a:000),'s:sub(v:val,"^\\%(%(:\\w)*)","\\=fnamemodify(s:buffer().path(),submatch(1))")')
if path =~# '/.' if path =~# '/.'
let cmd += ['--',path[1:-1]] if a:line2
let cmd += ['-L', a:line1 . ',' . a:line2 . ':' . path[1:-1]]
else
let cmd += ['--', path[1:-1]]
endif
endif endif
let grepformat = &grepformat let grepformat = &grepformat
let grepprg = &grepprg let grepprg = &grepprg
@@ -1132,7 +1288,7 @@ function! s:Log(cmd, count, ...) abort
try try
execute cd.'`=s:repo().tree()`' execute cd.'`=s:repo().tree()`'
let &grepprg = escape(call(s:repo().git_command,cmd,s:repo()),'%#') let &grepprg = escape(call(s:repo().git_command,cmd,s:repo()),'%#')
let &grepformat = '%f:%l::%m,%f:::%m' let &grepformat = '%Cdiff %.%#,%C--- %.%#,%C+++ %.%#,%Z@@ -%\d%\+\,%\d%\+ +%l\,%\d%\+ @@,%-G-%.%#,%-G+%.%#,%-G %.%#,%A%f::%m,%-G%.%#'
exe a:cmd exe a:cmd
finally finally
let &grepformat = grepformat let &grepformat = grepformat
@@ -1401,6 +1557,35 @@ augroup fugitive_commit
autocmd VimLeavePre,BufDelete COMMIT_EDITMSG execute s:sub(s:FinishCommit(), '^echoerr (.*)', 'echohl ErrorMsg|echo \1|echohl NONE') autocmd VimLeavePre,BufDelete COMMIT_EDITMSG execute s:sub(s:FinishCommit(), '^echoerr (.*)', 'echohl ErrorMsg|echo \1|echohl NONE')
augroup END augroup END
" Section: Gpush, Gfetch
call s:command("-nargs=? -bang -complete=custom,s:RemoteComplete Gpush execute s:Dispatch('<bang>', 'push '.<q-args>)")
call s:command("-nargs=? -bang -complete=custom,s:RemoteComplete Gfetch execute s:Dispatch('<bang>', 'fetch '.<q-args>)")
function! s:Dispatch(bang, args)
let cd = exists('*haslocaldir') && haslocaldir() ? 'lcd' : 'cd'
let cwd = getcwd()
let [mp, efm, cc] = [&l:mp, &l:efm, get(b:, 'current_compiler', '')]
try
let b:current_compiler = 'git'
let &l:errorformat = s:common_efm
let &l:makeprg = g:fugitive_git_executable . ' ' . a:args
execute cd fnameescape(s:repo().tree())
if exists(':Make') == 2
noautocmd Make
else
silent noautocmd make!
redraw!
return 'call fugitive#cwindow()'
endif
return ''
finally
let [&l:mp, &l:efm, b:current_compiler] = [mp, efm, cc]
if empty(cc) | unlet! b:current_compiler | endif
execute cd fnameescape(cwd)
endtry
endfunction
" Section: Gdiff " Section: Gdiff
call s:command("-bang -bar -nargs=* -complete=customlist,s:EditComplete Gdiff :execute s:Diff('',<f-args>)") call s:command("-bang -bar -nargs=* -complete=customlist,s:EditComplete Gdiff :execute s:Diff('',<f-args>)")
@@ -1666,6 +1851,7 @@ augroup fugitive_blame
autocmd FileType fugitiveblame setlocal nomodeline | if exists('b:git_dir') | let &l:keywordprg = s:repo().keywordprg() | endif autocmd FileType fugitiveblame setlocal nomodeline | if exists('b:git_dir') | let &l:keywordprg = s:repo().keywordprg() | endif
autocmd Syntax fugitiveblame call s:BlameSyntax() autocmd Syntax fugitiveblame call s:BlameSyntax()
autocmd User Fugitive if s:buffer().type('file', 'blob') | exe "command! -buffer -bar -bang -range=0 -nargs=* Gblame :execute s:Blame(<bang>0,<line1>,<line2>,<count>,[<f-args>])" | endif autocmd User Fugitive if s:buffer().type('file', 'blob') | exe "command! -buffer -bar -bang -range=0 -nargs=* Gblame :execute s:Blame(<bang>0,<line1>,<line2>,<count>,[<f-args>])" | endif
autocmd ColorScheme,GUIEnter * call s:RehighlightBlame()
augroup END augroup END
function! s:linechars(pattern) abort function! s:linechars(pattern) abort
@@ -1679,6 +1865,9 @@ function! s:linechars(pattern) abort
endfunction endfunction
function! s:Blame(bang,line1,line2,count,args) abort function! s:Blame(bang,line1,line2,count,args) abort
if exists('b:fugitive_blamed_bufnr')
return 'bdelete'
endif
try try
if s:buffer().path() == '' if s:buffer().path() == ''
call s:throw('file or blob required') call s:throw('file or blob required')
@@ -1720,12 +1909,18 @@ function! s:Blame(bang,line1,line2,count,args) abort
endif endif
for winnr in range(winnr('$'),1,-1) for winnr in range(winnr('$'),1,-1)
call setwinvar(winnr, '&scrollbind', 0) call setwinvar(winnr, '&scrollbind', 0)
if exists('+cursorbind')
call setwinvar(winnr, '&cursorbind', 0)
endif
if getbufvar(winbufnr(winnr), 'fugitive_blamed_bufnr') if getbufvar(winbufnr(winnr), 'fugitive_blamed_bufnr')
execute winbufnr(winnr).'bdelete' execute winbufnr(winnr).'bdelete'
endif endif
endfor endfor
let bufnr = bufnr('') let bufnr = bufnr('')
let restore = 'call setwinvar(bufwinnr('.bufnr.'),"&scrollbind",0)' let restore = 'call setwinvar(bufwinnr('.bufnr.'),"&scrollbind",0)'
if exists('+cursorbind')
let restore .= '|call setwinvar(bufwinnr('.bufnr.'),"&cursorbind",0)'
endif
if &l:wrap if &l:wrap
let restore .= '|call setwinvar(bufwinnr('.bufnr.'),"&wrap",1)' let restore .= '|call setwinvar(bufwinnr('.bufnr.'),"&wrap",1)'
endif endif
@@ -1733,6 +1928,9 @@ function! s:Blame(bang,line1,line2,count,args) abort
let restore .= '|call setwinvar(bufwinnr('.bufnr.'),"&foldenable",1)' let restore .= '|call setwinvar(bufwinnr('.bufnr.'),"&foldenable",1)'
endif endif
setlocal scrollbind nowrap nofoldenable setlocal scrollbind nowrap nofoldenable
if exists('+cursorbind')
setlocal cursorbind
endif
let top = line('w0') + &scrolloff let top = line('w0') + &scrolloff
let current = line('.') let current = line('.')
let s:temp_files[tolower(temp)] = { 'dir': s:repo().dir(), 'args': cmd } let s:temp_files[tolower(temp)] = { 'dir': s:repo().dir(), 'args': cmd }
@@ -1743,6 +1941,9 @@ function! s:Blame(bang,line1,line2,count,args) abort
execute top execute top
normal! zt normal! zt
execute current execute current
if exists('+cursorbind')
setlocal cursorbind
endif
setlocal nomodified nomodifiable nonumber scrollbind nowrap foldcolumn=0 nofoldenable winfixwidth filetype=fugitiveblame setlocal nomodified nomodifiable nonumber scrollbind nowrap foldcolumn=0 nofoldenable winfixwidth filetype=fugitiveblame
if exists('+concealcursor') if exists('+concealcursor')
setlocal concealcursor=nc conceallevel=2 setlocal concealcursor=nc conceallevel=2
@@ -1854,6 +2055,8 @@ function! s:BlameJump(suffix) abort
return '' return ''
endfunction endfunction
let s:hash_colors = {}
function! s:BlameSyntax() abort function! s:BlameSyntax() abort
let b:current_syntax = 'fugitiveblame' let b:current_syntax = 'fugitiveblame'
let conceal = has('conceal') ? ' conceal' : '' let conceal = has('conceal') ? ' conceal' : ''
@@ -1872,7 +2075,7 @@ function! s:BlameSyntax() abort
syn match FugitiveblameNotCommittedYet "(\@<=Not Committed Yet\>" contained containedin=FugitiveblameAnnotation syn match FugitiveblameNotCommittedYet "(\@<=Not Committed Yet\>" contained containedin=FugitiveblameAnnotation
hi def link FugitiveblameBoundary Keyword hi def link FugitiveblameBoundary Keyword
hi def link FugitiveblameHash Identifier hi def link FugitiveblameHash Identifier
hi def link FugitiveblameUncommitted Function hi def link FugitiveblameUncommitted Ignore
hi def link FugitiveblameTime PreProc hi def link FugitiveblameTime PreProc
hi def link FugitiveblameLineNumber Number hi def link FugitiveblameLineNumber Number
hi def link FugitiveblameOriginalFile String hi def link FugitiveblameOriginalFile String
@@ -1880,6 +2083,37 @@ function! s:BlameSyntax() abort
hi def link FugitiveblameShort FugitiveblameDelimiter hi def link FugitiveblameShort FugitiveblameDelimiter
hi def link FugitiveblameDelimiter Delimiter hi def link FugitiveblameDelimiter Delimiter
hi def link FugitiveblameNotCommittedYet Comment hi def link FugitiveblameNotCommittedYet Comment
let seen = {}
for lnum in range(1, line('$'))
let hash = matchstr(getline(lnum), '^\^\=\zs\x\{6\}')
if hash ==# '' || hash ==# '000000' || has_key(seen, hash)
continue
endif
let seen[hash] = 1
if &t_Co > 16 && exists('g:CSApprox_loaded')
\ && empty(get(s:hash_colors, hash))
let [s, r, g, b; __] = map(matchlist(hash, '\(\x\x\)\(\x\x\)\(\x\x\)'), 'str2nr(v:val,16)')
let color = csapprox#per_component#Approximate(r, g, b)
if color == 16 && &background ==# 'dark'
let color = 8
endif
let s:hash_colors[hash] = ' ctermfg='.color
else
let s:hash_colors[hash] = ''
endif
exe 'syn match FugitiveblameHash'.hash.' "\%(^\^\=\)\@<='.hash.'\x\{1,34\}\>" nextgroup=FugitiveblameAnnotation,FugitiveblameOriginalLineNumber,fugitiveblameOriginalFile skipwhite'
endfor
call s:RehighlightBlame()
endfunction
function! s:RehighlightBlame() abort
for [hash, cterm] in items(s:hash_colors)
if !empty(cterm) || has('gui_running')
exe 'hi FugitiveblameHash'.hash.' guifg=#'.hash.get(s:hash_colors, hash, '')
else
exe 'hi link FugitiveblameHash'.hash.' Identifier'
endif
endfor
endfunction endfunction
" Section: Gbrowse " Section: Gbrowse
@@ -1964,18 +2198,32 @@ function! s:Browse(bang,line1,count,...) abort
let raw = remote let raw = remote
endif endif
let url = s:github_url(s:repo(),raw,rev,commit,path,type,a:line1,a:count) for Handler in g:fugitive_browse_handlers
if url == '' let url = call(Handler, [{
let url = s:instaweb_url(s:repo(),rev,commit,path,type,a:count > 0 ? a:line1 : 0) \ 'repo': s:repo(),
\ 'remote': raw,
\ 'revision': rev,
\ 'commit': commit,
\ 'path': path,
\ 'type': type,
\ 'line1': a:count > 0 ? a:line1 : 0,
\ 'line2': a:count > 0 ? a:count : 0}])
if !empty(url)
break
endif endif
endfor
if url == '' if empty(url)
call s:throw("Instaweb failed to start and '".remote."' is not a GitHub remote") call s:throw("Instaweb failed to start and '".remote."' is not a supported remote")
endif endif
if a:bang if a:bang
if has('clipboard')
let @* = url let @* = url
endif
return 'echomsg '.string(url) return 'echomsg '.string(url)
elseif exists(':Browse') == 2
return 'echomsg '.string(url).'|Browse '.url
else else
return 'echomsg '.string(url).'|call netrw#NetrwBrowseX('.string(url).', 0)' return 'echomsg '.string(url).'|call netrw#NetrwBrowseX('.string(url).', 0)'
endif endif
@@ -1984,24 +2232,27 @@ function! s:Browse(bang,line1,count,...) abort
endtry endtry
endfunction endfunction
function! s:github_url(repo,url,rev,commit,path,type,line1,line2) abort function! s:github_url(opts, ...) abort
let path = a:path if a:0 || type(a:opts) != type({})
return ''
endif
let domain_pattern = 'github\.com' let domain_pattern = 'github\.com'
let domains = exists('g:fugitive_github_domains') ? g:fugitive_github_domains : [] let domains = exists('g:fugitive_github_domains') ? g:fugitive_github_domains : []
for domain in domains for domain in domains
let domain_pattern .= '\|' . escape(split(domain, '://')[-1], '.') let domain_pattern .= '\|' . escape(split(domain, '://')[-1], '.')
endfor endfor
let repo = matchstr(a:url,'^\%(https\=://\|git://\|git@\)\=\zs\('.domain_pattern.'\)[/:].\{-\}\ze\%(\.git\)\=$') let repo = matchstr(get(a:opts, 'remote'), '^\%(https\=://\|git://\|git@\)\=\zs\('.domain_pattern.'\)[/:].\{-\}\ze\%(\.git\)\=$')
if repo ==# '' if repo ==# ''
return '' return ''
endif endif
let path = a:opts.path
if index(domains, 'http://' . matchstr(repo, '^[^:/]*')) >= 0 if index(domains, 'http://' . matchstr(repo, '^[^:/]*')) >= 0
let root = 'http://' . s:sub(repo,':','/') let root = 'http://' . s:sub(repo,':','/')
else else
let root = 'https://' . s:sub(repo,':','/') let root = 'https://' . s:sub(repo,':','/')
endif endif
if path =~# '^\.git/refs/heads/' if path =~# '^\.git/refs/heads/'
let branch = a:repo.git_chomp('config','branch.'.path[16:-1].'.merge')[11:-1] let branch = a:opts.repo.git_chomp('config','branch.'.path[16:-1].'.merge')[11:-1]
if branch ==# '' if branch ==# ''
return root . '/commits/' . path[16:-1] return root . '/commits/' . path[16:-1]
else else
@@ -2014,27 +2265,27 @@ function! s:github_url(repo,url,rev,commit,path,type,line1,line2) abort
elseif path =~# '^\.git\>' elseif path =~# '^\.git\>'
return root return root
endif endif
if a:rev =~# '^[[:alnum:]._-]\+:' if a:opts.revision =~# '^[[:alnum:]._-]\+:'
let commit = matchstr(a:rev,'^[^:]*') let commit = matchstr(a:opts.revision,'^[^:]*')
elseif a:commit =~# '^\d\=$' elseif a:opts.commit =~# '^\d\=$'
let local = matchstr(a:repo.head_ref(),'\<refs/heads/\zs.*') let local = matchstr(a:opts.repo.head_ref(),'\<refs/heads/\zs.*')
let commit = a:repo.git_chomp('config','branch.'.local.'.merge')[11:-1] let commit = a:opts.repo.git_chomp('config','branch.'.local.'.merge')[11:-1]
if commit ==# '' if commit ==# ''
let commit = local let commit = local
endif endif
else else
let commit = a:commit let commit = a:opts.commit
endif endif
if a:type == 'tree' if a:opts.type == 'tree'
let url = s:sub(root . '/tree/' . commit . '/' . path,'/$','') let url = s:sub(root . '/tree/' . commit . '/' . path,'/$','')
elseif a:type == 'blob' elseif a:opts.type == 'blob'
let url = root . '/blob/' . commit . '/' . path let url = root . '/blob/' . commit . '/' . path
if a:line2 > 0 && a:line1 == a:line2 if get(a:opts, 'line2') && a:opts.line1 == a:opts.line2
let url .= '#L' . a:line1 let url .= '#L' . a:opts.line1
elseif a:line2 > 0 elseif get(a:opts, 'line2')
let url .= '#L' . a:line1 . '-' . a:line2 let url .= '#L' . a:opts.line1 . '-' . a:opts.line2
endif endif
elseif a:type == 'tag' elseif a:opts.type == 'tag'
let commit = matchstr(getline(3),'^tag \zs.*') let commit = matchstr(getline(3),'^tag \zs.*')
let url = root . '/tree/' . commit let url = root . '/tree/' . commit
else else
@@ -2043,47 +2294,54 @@ function! s:github_url(repo,url,rev,commit,path,type,line1,line2) abort
return url return url
endfunction endfunction
function! s:instaweb_url(repo,rev,commit,path,type,...) abort function! s:instaweb_url(opts) abort
let output = a:repo.git_chomp('instaweb','-b','unknown') let output = a:opts.repo.git_chomp('instaweb','-b','unknown')
if output =~# 'http://' if output =~# 'http://'
let root = matchstr(output,'http://.*').'/?p='.fnamemodify(a:repo.dir(),':t') let root = matchstr(output,'http://.*').'/?p='.fnamemodify(a:opts.repo.dir(),':t')
else else
return '' return ''
endif endif
if a:path =~# '^\.git/refs/.' if a:opts.path =~# '^\.git/refs/.'
return root . ';a=shortlog;h=' . matchstr(a:path,'^\.git/\zs.*') return root . ';a=shortlog;h=' . matchstr(a:opts.path,'^\.git/\zs.*')
elseif a:path =~# '^\.git\>' elseif a:opts.path =~# '^\.git\>'
return root return root
endif endif
let url = root let url = root
if a:commit =~# '^\x\{40\}$' if a:opts.commit =~# '^\x\{40\}$'
if a:type ==# 'commit' if a:opts.type ==# 'commit'
let url .= ';a=commit' let url .= ';a=commit'
endif endif
let url .= ';h=' . a:repo.rev_parse(a:commit . (a:path == '' ? '' : ':' . a:path)) let url .= ';h=' . a:opts.repo.rev_parse(a:opts.commit . (a:opts.path == '' ? '' : ':' . a:opts.path))
else else
if a:type ==# 'blob' if a:opts.type ==# 'blob'
let tmp = tempname() let tmp = tempname()
silent execute 'write !'.a:repo.git_command('hash-object','-w','--stdin').' > '.tmp silent execute 'write !'.a:opts.repo.git_command('hash-object','-w','--stdin').' > '.tmp
let url .= ';h=' . readfile(tmp)[0] let url .= ';h=' . readfile(tmp)[0]
else else
try try
let url .= ';h=' . a:repo.rev_parse((a:commit == '' ? 'HEAD' : ':' . a:commit) . ':' . a:path) let url .= ';h=' . a:opts.repo.rev_parse((a:opts.commit == '' ? 'HEAD' : ':' . a:opts.commit) . ':' . a:opts.path)
catch /^fugitive:/ catch /^fugitive:/
call s:throw('fugitive: cannot browse uncommitted file') call s:throw('fugitive: cannot browse uncommitted file')
endtry endtry
endif endif
let root .= ';hb=' . matchstr(a:repo.head_ref(),'[^ ]\+$') let root .= ';hb=' . matchstr(a:opts.repo.head_ref(),'[^ ]\+$')
endif endif
if a:path !=# '' if a:opts.path !=# ''
let url .= ';f=' . a:path let url .= ';f=' . a:opts.path
endif endif
if a:0 && a:1 if get(a:opts, 'line1')
let url .= '#l' . a:1 let url .= '#l' . a:opts.line1
endif endif
return url return url
endfunction endfunction
if !exists('g:fugitive_browse_handlers')
let g:fugitive_browse_handlers = []
endif
call extend(g:fugitive_browse_handlers,
\ [s:function('s:github_url'), s:function('s:instaweb_url')])
" Section: File access " Section: File access
function! s:ReplaceCmd(cmd,...) abort function! s:ReplaceCmd(cmd,...) abort
@@ -2260,7 +2518,9 @@ function! s:BufWriteIndexFile() abort
endif endif
if v:shell_error == 0 if v:shell_error == 0
setlocal nomodified setlocal nomodified
silent execute 'doautocmd BufWritePost '.s:fnameescape(expand('%:p')) if exists('#BufWritePost')
execute 'doautocmd BufWritePost '.s:fnameescape(expand('%:p'))
endif
call fugitive#reload_status() call fugitive#reload_status()
return '' return ''
else else
@@ -2387,7 +2647,7 @@ augroup fugitive_temp
\ let b:git_type = 'temp' | \ let b:git_type = 'temp' |
\ let b:git_args = s:temp_files[tolower(expand('<afile>:p'))].args | \ let b:git_args = s:temp_files[tolower(expand('<afile>:p'))].args |
\ call fugitive#detect(expand('<afile>:p')) | \ call fugitive#detect(expand('<afile>:p')) |
\ setlocal bufhidden=delete | \ setlocal bufhidden=delete nobuflisted |
\ nnoremap <buffer> <silent> q :<C-U>bdelete<CR>| \ nnoremap <buffer> <silent> q :<C-U>bdelete<CR>|
\ endif \ endif
augroup END augroup END