PlugDiff to show pending updates as well

Related: #348
This commit is contained in:
Junegunn Choi 2015-12-22 23:12:02 +09:00
parent 6843e5aeec
commit e6f40479ee
4 changed files with 129 additions and 39 deletions

View File

@ -104,7 +104,7 @@ Reload .vimrc and `:PlugInstall` to install plugins.
| `PlugClean[!]` | Remove unused directories (bang version will clean without prompt) |
| `PlugUpgrade` | Upgrade vim-plug itself |
| `PlugStatus` | Check the status of plugins |
| `PlugDiff` | See the updated changes from the previous PlugUpdate |
| `PlugDiff` | Examine changes from the previous update and the pending changes |
| `PlugSnapshot[!] [output path]` | Generate script for restoring the current snapshot of the plugins |
### `Plug` options

View File

@ -531,16 +531,20 @@ function! s:syntax()
syn match plugStar /^*/
syn match plugMessage /\(^- \)\@<=.*/
syn match plugName /\(^- \)\@<=[^ ]*:/
syn match plugSha /\%(: \)\@<=[0-9a-z]\{4,}$/
syn match plugTag /(tag: [^)]\+)/
syn match plugInstall /\(^+ \)\@<=[^:]*/
syn match plugUpdate /\(^* \)\@<=[^:]*/
syn match plugCommit /^ [0-9a-z]\{7} .*/ contains=plugRelDate,plugSha
syn match plugCommit /^ [0-9a-z]\{7} .*/ contains=plugRelDate,plugSha,plugTag
syn match plugSha /\(^ \)\@<=[0-9a-z]\{7}/ contained
syn match plugRelDate /([^)]*)$/ contained
syn match plugNotLoaded /(not loaded)$/
syn match plugError /^x.*/
syn match plugH2 /^.*:\n-\+$/
syn keyword Function PlugInstall PlugStatus PlugUpdate PlugClean
hi def link plug1 Title
hi def link plug2 Repeat
hi def link plugH2 Type
hi def link plugX Exception
hi def link plugBracket Structure
hi def link plugNumber Number
@ -557,6 +561,7 @@ function! s:syntax()
hi def link plugError Error
hi def link plugRelDate Comment
hi def link plugSha Identifier
hi def link plugTag Constant
hi def link plugNotLoaded Comment
endfunction
@ -1993,41 +1998,63 @@ function! s:section(flags)
call search('\(^[x-] \)\@<=[^:]\+:', a:flags)
endfunction
function! s:format_git_log(line)
let [sha, refs, subject, date] = split(a:line, nr2char(1))
let tag = matchstr(refs, 'tag: [^,)]\+')
let tag = empty(tag) ? ' ' : ' ('.tag.') '
return printf(' %s%s%s (%s)', sha, tag, subject, date)
endfunction
function! s:append_ul(lnum, text)
call append(a:lnum, ['', a:text, repeat('-', len(a:text))])
endfunction
function! s:diff()
call s:prepare()
call append(0, 'Collecting updated changes ...')
normal! gg
redraw
let cnt = 0
for [k, v] in filter(items(g:plugs), '!has_key(v:val[1], "commit")')
if !isdirectory(v.dir) || !s:is_managed(k)
continue
endif
let diff = s:system_chomp('git log --left-only --pretty=format:"%h %s (%cr)" "HEAD...HEAD@{1}"', v.dir)
call append(0, ['Collecting changes ...', ''])
let cnts = [0, 0]
let bar = ''
let total = filter(copy(g:plugs), 's:is_managed(v:key) && isdirectory(v:val.dir)')
call s:progress_bar(2, bar, len(total))
for origin in [1, 0]
call s:append_ul(2, origin ? 'Pending updates:' : 'Last update:')
for [k, v] in reverse(sort(items(filter(copy(total), (origin ? '' : '!').'(has_key(v:val, "commit") || has_key(v:val, "tag"))'))))
let range = origin ? '..origin/'.v.branch : 'HEAD@{1}..'
let diff = s:system_chomp('git log --pretty=format:"%h%x01%d%x01%s%x01%cr" '.s:shellesc(range), v.dir)
if !empty(diff)
call append(1, '')
call append(2, '- '.k.':')
call append(3, map(s:lines(diff), '" ". v:val'))
let cnt += 1
normal! gg
let ref = has_key(v, 'tag') ? (' (tag: '.v.tag.')') : has_key(v, 'commit') ? (' '.v.commit) : ''
call append(5, extend(['', '- '.k.':'.ref], map(s:lines(diff), 's:format_git_log(v:val)')))
let cnts[origin] += 1
endif
let bar .= '='
call s:progress_bar(2, bar, len(total))
normal! 2G
redraw
endfor
if !cnts[origin]
call append(5, ['', 'N/A'])
endif
endfor
call setline(1, printf('%d plugin(s) updated.', cnts[0])
\ . (cnts[1] ? printf(' %d plugin(s) have pending updates.', cnts[1]) : ''))
call setline(1, cnt == 0 ? 'No updates.' : 'Last update:')
if cnts[0] || cnts[1]
nnoremap <silent> <buffer> <cr> :silent! call <SID>preview_commit()<cr>
nnoremap <silent> <buffer> o :silent! call <SID>preview_commit()<cr>
endif
if cnts[0]
nnoremap <silent> <buffer> X :call <SID>revert()<cr>
normal! gg
setlocal nomodifiable
if cnt > 0
echo "Press 'X' on each block to revert the update"
endif
normal! gg
setlocal nomodifiable
endfunction
function! s:revert()
if search('^Pending updates', 'bnW')
return
endif
let name = s:find_name(line('.'))
if empty(name) || !has_key(g:plugs, name) ||
\ input(printf('Revert the update of %s? (y/N) ', name)) !~? '^y'

View File

@ -18,7 +18,7 @@ clone() {
fi
}
clone_repos() {
clone_repos() (
cd /tmp
mkdir -p junegunn vim-scripts jg
for repo in vader.vim goyo.vim rust.vim seoul256.vim vim-easy-align vim-fnr \
@ -31,11 +31,9 @@ clone_repos() {
clone junegunn/vim-emoji jg/vim-emoji
cd junegunn/seoul256.vim && git checkout no-t_co && git checkout master
)
cd "$BASE"
}
make_dirs() {
make_dirs() (
rm -rf "$PLUG_FIXTURES/$1"
mkdir -p "$PLUG_FIXTURES/$1"
cd "$PLUG_FIXTURES/$1"
@ -51,9 +49,13 @@ make_dirs() {
call add(g:total_order, s:name)
EOF
done
)
cd "$BASE"
}
gitinit() (
cd "$PLUG_FIXTURES/$1"
git init
git commit -m 'commit' --allow-empty
)
prepare() {
make_dirs xxx/ xxx
@ -62,9 +64,11 @@ prepare() {
cat > "$PLUG_FIXTURES/xxx/doc/xxx.txt" << DOC
hello *xxx*
DOC
gitinit xxx
make_dirs yyy/ yyy
make_dirs yyy/after yyy
gitinit yyy
make_dirs z1/ z1
make_dirs z2/ z2

View File

@ -262,12 +262,16 @@ Execute (PlugUpdate only to find out plugins are up-to-date, D key to check):
PlugUpdate
AssertExpect 'Already up-to-date', 2
normal D
AssertEqual 'No updates.', getline(1)
AssertEqual '0 plugin(s) updated.', getline(1)
q
Execute (PlugDiff - 'No updates.'):
PlugDiff
AssertEqual 'No updates.', getline(1)
Log getline(1, '$')
AssertEqual '0 plugin(s) updated.', getline(1)
Assert empty(mapcheck('o'))
Assert empty(mapcheck('X'))
Assert empty(mapcheck("\<cr>"))
q
Execute (New commits on remote, PlugUpdate, then PlugDiff):
@ -281,7 +285,7 @@ Execute (New commits on remote, PlugUpdate, then PlugDiff):
" Now we have updates
normal D
AssertEqual 'Last update:', getline(1)
AssertEqual '2 plugin(s) updated.', getline(1)
" Preview commit
silent! wincmd P
@ -367,7 +371,58 @@ Execute (contd. PlugDiff should not show inverted history):
" PlugDiff should not report the changes i.e. git log --left-only
PlugDiff
Log getline(1, '$')
AssertEqual 'No updates.', getline(1)
AssertEqual '0 plugin(s) updated.', getline(1)
q
**********************************************************************
~ PlugDiff to see the pending changes
**********************************************************************
Execute (PlugDiff):
call plug#begin()
call plug#end()
PlugClean!
call plug#begin()
Plug 'file://'.expand('$PLUG_FIXTURES').'/xxx'
Plug 'file://'.expand('$PLUG_FIXTURES').'/yyy'
call plug#end()
PlugInstall
Log getline(1, '$')
call system('cd "$PLUG_FIXTURES/xxx" && git commit --allow-empty -m update-xxx && git tag -f xxx')
call system('cd "$PLUG_FIXTURES/yyy" && git tag -f yyy && git commit --allow-empty -m update-yyy && git tag -f zzz')
let g:plugs.yyy.tag = 'yyy'
PlugUpdate
Log getline(1, '$')
PlugDiff
" 1 plugin(s) updated. 1 plugin(s) have pending updates.
" [==]
"
" Last update:
" ------------
"
" - xxx:
" 166cfff (tag: xxx) update-xxx (1 second ago)
"
" Pending updates:
" ----------------
"
" - yyy: (tag: yyy)
" c0a064b (tag: zzz) update-yyy (1 second ago)
"
Log getline(1, '$')
AssertEqual 15, line('$')
AssertEqual '1 plugin(s) updated. 1 plugin(s) have pending updates.', getline(1)
AssertEqual '[==]', getline(2)
AssertEqual '- yyy: (tag: yyy)', getline(13)
Assert getline(8) =~ '(tag: xxx)'
Assert getline(14) =~ '(tag: zzz)'
Assert !empty(mapcheck('o'))
Assert !empty(mapcheck('X'))
Assert !empty(mapcheck("\<cr>"))
q
**********************************************************************
@ -1258,9 +1313,13 @@ Execute (Commit hash support):
AssertEqual [' PlugUpdate required.',
\'- vim-emoji: OK'], getline(6, '$')
" Plugins with commit option should not appear in PlugDiff output
" PlugDiff should show pending updates for vim-emoji
PlugDiff
AssertEqual 'No updates.', getline(1)
Log getline(1, '$')
AssertEqual '0 plugin(s) updated. 1 plugin(s) have pending updates.', getline(1)
Assert !empty(mapcheck('o'))
Assert empty(mapcheck('X'))
Assert !empty(mapcheck("\<cr>"))
" Nor in PlugSnapshot output
PlugSnapshot