Post-update hook (do option)

This commit is contained in:
Junegunn Choi 2014-07-26 22:49:18 +09:00
parent 5b2c03d3a8
commit f98c8456fa
3 changed files with 152 additions and 17 deletions

View File

@ -76,6 +76,7 @@ Reload .vimrc and `:PlugInstall` to install plugins.
| -------------- | -------------------------------------------------------------------- | | -------------- | -------------------------------------------------------------------- |
| `branch`/`tag` | Branch or tag of the repository to use | | `branch`/`tag` | Branch or tag of the repository to use |
| `rtp` | Subdirectory that contains Vim plugin | | `rtp` | Subdirectory that contains Vim plugin |
| `do` | Post-update hook (string of funcref) |
| `on` | On-demand loading: Commands or <Plug>-mappings | | `on` | On-demand loading: Commands or <Plug>-mappings |
| `for` | On-demand loading: File types | | `for` | On-demand loading: File types |
| `frozen` | Do not install/update plugin unless explicitly given as the argument | | `frozen` | Do not install/update plugin unless explicitly given as the argument |

View File

@ -9,14 +9,24 @@
" "
" Edit your .vimrc " Edit your .vimrc
" "
" call plug#begin() " call plug#begin('~/.vim/plugged')
" "
" " Make sure you use single quotes
" Plug 'junegunn/seoul256.vim' " Plug 'junegunn/seoul256.vim'
" Plug 'junegunn/vim-easy-align' " Plug 'junegunn/vim-easy-align'
" Plug 'junegunn/goyo.vim', { 'on': 'Goyo' } "
" " Plug 'user/repo1', 'branch_or_tag' " " On-demand loading
" " Plug 'user/repo2', { 'rtp': 'vim/plugin/dir', 'branch': 'branch_or_tag' } " Plug 'scrooloose/nerdtree', { 'on': 'NERDTreeToggle' }
" " ... " Plug 'tpope/vim-fireplace', { 'for': 'clojure' }
"
" " Using git URL
" Plug 'https://github.com/junegunn/vim-github-dashboard.git'
"
" " Plugin options
" Plug 'nsf/gocode', { 'tag': 'go.weekly.2012-03-13', 'rtp': 'vim' }
"
" " Locally-managed plugin
" Plug '~/.fzf'
" "
" call plug#end() " call plug#end()
" "
@ -354,7 +364,8 @@ function! s:syntax()
syn match plugDash /^-/ syn match plugDash /^-/
syn match plugPlus /^+/ syn match plugPlus /^+/
syn match plugStar /^*/ syn match plugStar /^*/
syn match plugName /\(^- \)\@<=[^:]*/ syn match plugMessage /\(^- \)\@<=.*/
syn match plugName /\(^- \)\@<=[^ ]*:/
syn match plugInstall /\(^+ \)\@<=[^:]*/ syn match plugInstall /\(^+ \)\@<=[^:]*/
syn match plugUpdate /\(^* \)\@<=[^:]*/ syn match plugUpdate /\(^* \)\@<=[^:]*/
syn match plugCommit /^ [0-9a-z]\{7} .*/ contains=plugRelDate,plugSha syn match plugCommit /^ [0-9a-z]\{7} .*/ contains=plugRelDate,plugSha
@ -372,6 +383,7 @@ function! s:syntax()
hi def link plugPlus Constant hi def link plugPlus Constant
hi def link plugStar Boolean hi def link plugStar Boolean
hi def link plugMessage Function
hi def link plugName Label hi def link plugName Label
hi def link plugInstall Function hi def link plugInstall Function
hi def link plugUpdate Type hi def link plugUpdate Type
@ -430,6 +442,32 @@ function! s:assign_name()
silent! execute "f ".fnameescape(name) silent! execute "f ".fnameescape(name)
endfunction endfunction
function! s:do(pull, todo)
for [name, spec] in items(a:todo)
execute 'cd '.s:esc(spec.dir)
if has_key(s:prev_update.new, name) || (a:pull &&
\ !empty(s:system_chomp('git log --pretty=format:"%h" "HEAD...HEAD@{1}"')))
call append(3, '- Post-update hook for '. name .' ... ')
let type = type(spec.do)
if type == 1 " String
call system(spec.do)
let result = v:shell_error ? ('Exit status: '.v:shell_error) : 'Done!'
elseif type == 2 " Funcref
try
call spec.do()
let result = 'Done!'
catch
let result = 'Error: ' . v:exception
endtry
else
let result = 'Error: Invalid type!'
endif
call setline(4, getline(4) . result)
endif
cd -
endfor
endfunction
function! s:finish(pull) function! s:finish(pull)
call append(3, '- Finishing ... ') call append(3, '- Finishing ... ')
redraw redraw
@ -486,8 +524,11 @@ function! s:update_impl(pull, args) abort
normal! 2G normal! 2G
redraw redraw
if !isdirectory(g:plug_home)
call mkdir(g:plug_home, 'p')
endif
let len = len(g:plugs) let len = len(g:plugs)
let s:prev_update = { 'errors': [], 'pull': a:pull, 'threads': threads } let s:prev_update = { 'errors': [], 'pull': a:pull, 'new': {}, 'threads': threads }
if has('ruby') && threads > 1 if has('ruby') && threads > 1
try try
let imd = &imd let imd = &imd
@ -517,6 +558,7 @@ function! s:update_impl(pull, args) abort
else else
call s:update_serial(a:pull, todo) call s:update_serial(a:pull, todo)
endif endif
call s:do(a:pull, filter(copy(todo), 'has_key(v:val, "do")'))
if len(g:plugs) > len if len(g:plugs) > len
call plug#end() call plug#end()
endif endif
@ -562,20 +604,21 @@ function! s:update_serial(pull, todo)
execute 'cd '.s:esc(spec.dir) execute 'cd '.s:esc(spec.dir)
let [valid, msg] = s:git_valid(spec, 0, 0) let [valid, msg] = s:git_valid(spec, 0, 0)
if valid if valid
let result = a:pull ? if a:pull
let result =
\ s:system( \ s:system(
\ printf('git checkout -q %s 2>&1 && git pull origin %s 2>&1 && git submodule update --init --recursive 2>&1', \ printf('git checkout -q %s 2>&1 && git pull origin %s 2>&1 && git submodule update --init --recursive 2>&1',
\ s:shellesc(spec.branch), s:shellesc(spec.branch))) : 'Already installed' \ s:shellesc(spec.branch), s:shellesc(spec.branch)))
let error = a:pull ? v:shell_error != 0 : 0 let [result, error] = [result, v:shell_error != 0]
else
let [result, error] = ['Already installed', 0]
endif
else else
let result = msg let result = msg
let error = 1 let error = 1
endif endif
cd - cd -
else else
if !isdirectory(base)
call mkdir(base, 'p')
endif
let result = s:system( let result = s:system(
\ printf('git clone --recursive %s -b %s %s 2>&1 && cd %s && git submodule update --init --recursive 2>&1', \ printf('git clone --recursive %s -b %s %s 2>&1 && cd %s && git submodule update --init --recursive 2>&1',
\ s:shellesc(spec.uri), \ s:shellesc(spec.uri),
@ -583,6 +626,7 @@ function! s:update_serial(pull, todo)
\ s:shellesc(substitute(spec.dir, '[\/]\+$', '', '')), \ s:shellesc(substitute(spec.dir, '[\/]\+$', '', '')),
\ s:shellesc(spec.dir))) \ s:shellesc(spec.dir)))
let error = v:shell_error != 0 let error = v:shell_error != 0
if !error | let s:prev_update.new[name] = 1 | endif
endif endif
let bar .= error ? 'x' : '=' let bar .= error ? 'x' : '='
if error if error
@ -773,8 +817,9 @@ function! s:update_parallel(pull, todo, threads)
dir, uri, branch = pair.last.values_at *%w[dir uri branch] dir, uri, branch = pair.last.values_at *%w[dir uri branch]
branch = esc branch branch = esc branch
subm = "git submodule update --init --recursive 2>&1" subm = "git submodule update --init --recursive 2>&1"
exists = File.directory? dir
ok, result = ok, result =
if File.directory? dir if exists
dir = esc dir dir = esc dir
ret, data = bt.call "#{cd} #{dir} && git rev-parse --abbrev-ref HEAD 2>&1 && git config remote.origin.url", nil, nil ret, data = bt.call "#{cd} #{dir} && git rev-parse --abbrev-ref HEAD 2>&1 && git config remote.origin.url", nil, nil
current_uri = data.lines.to_a.last current_uri = data.lines.to_a.last
@ -797,11 +842,11 @@ function! s:update_parallel(pull, todo, threads)
end end
end end
else else
FileUtils.mkdir_p(base)
d = esc dir.sub(%r{[\\/]+$}, '') d = esc dir.sub(%r{[\\/]+$}, '')
log.call name, 'Installing ...', :install log.call name, 'Installing ...', :install
bt.call "(git clone #{progress} --recursive #{uri} -b #{branch} #{d} 2>&1 && cd #{esc dir} && #{subm})", name, :install bt.call "(git clone #{progress} --recursive #{uri} -b #{branch} #{d} 2>&1 && cd #{esc dir} && #{subm})", name, :install
end end
mtx.synchronize { VIM::command("let s:prev_update.new['#{name}'] = 1") } if !exists && ok
log.call name, result, ok log.call name, result, ok
end end
} if running } if running
@ -1082,7 +1127,7 @@ function! s:diff()
endif endif
execute 'cd '.s:esc(v.dir) execute 'cd '.s:esc(v.dir)
let diff = system('git log --pretty=format:"%h %s (%cr)" "HEAD@{0}...HEAD@{1}"') let diff = system('git log --pretty=format:"%h %s (%cr)" "HEAD...HEAD@{1}"')
if !v:shell_error && !empty(diff) if !v:shell_error && !empty(diff)
call append(1, '') call append(1, '')
call append(2, '- '.k.':') call append(2, '- '.k.':')

View File

@ -396,7 +396,7 @@ Expect (Aligned code):
a = 1 a = 1
aa = 2 aa = 2
Given (nothing): Given:
Execute (Partial PlugUpdate): Execute (Partial PlugUpdate):
PlugUpdate vim-redis PlugUpdate vim-redis
q q
@ -576,6 +576,94 @@ Execute (Retry failed tasks):
AssertExpect! '[xxx]', 1 AssertExpect! '[xxx]', 1
q q
**********************************************************************
~ Post-update hook (`do` option)
**********************************************************************
Execute (Cleanup):
call plug#begin()
call plug#end()
PlugClean!
Execute (On install):
call plug#begin()
Plug 'junegunn/vim-easy-align', { 'do': 'touch installed' }
Plug 'junegunn/vim-pseudocl'
call plug#end()
PlugInstall
q
Assert filereadable(g:plugs['vim-easy-align'].dir.'/installed'),
\ 'vim-easy-align/installed should exist'
Assert !filereadable(g:plugs['vim-pseudocl'].dir.'/installed'),
\ 'vim-pseudocl/installed should not exist'
Execute (On update):
call plug#begin()
Plug 'junegunn/vim-easy-align', { 'do': 'touch updated' }
Plug 'junegunn/vim-pseudocl', { 'do': 'touch updated' }
call plug#end()
" Reset for updates
call system('cd '.g:plugs['vim-pseudocl'].dir.' && git reset --hard HEAD^')
PlugUpdate
Log getline(1, '$')
q
Assert !filereadable(g:plugs['vim-easy-align'].dir.'/updated'),
\ 'vim-easy-align/updated should not exist'
Assert filereadable(g:plugs['vim-pseudocl'].dir.'/updated'),
\ 'vim-pseudocl/updated should exist'
Execute (When already installed):
call plug#begin()
Plug 'junegunn/vim-easy-align', { 'do': 'touch installed2' }
Plug 'junegunn/vim-pseudocl', { 'do': 'touch installed2' }
call plug#end()
PlugInstall
q
Assert !filereadable(g:plugs['vim-easy-align'].dir.'/installed2'),
\ 'vim-easy-align/installed2 should not exist'
Assert !filereadable(g:plugs['vim-pseudocl'].dir.'/installed2'),
\ 'vim-pseudocl/installed2 should exist'
Execute (When already updated):
call plug#begin()
Plug 'junegunn/vim-easy-align', { 'do': 'touch updated2' }
Plug 'junegunn/vim-pseudocl', { 'do': 'touch updated2' }
call plug#end()
PlugUpdate
q
Assert !filereadable(g:plugs['vim-easy-align'].dir.'/updated2'),
\ 'vim-easy-align/updated2 should not exist'
Assert !filereadable(g:plugs['vim-pseudocl'].dir.'/updated2'),
\ 'vim-pseudocl/updated2 should exist'
Execute (Using Funcref):
function! PlugUpdated()
call system('touch me')
endfunction
call plug#begin()
Plug 'junegunn/vim-easy-align', { 'do': function('PlugUpdated') }
Plug 'junegunn/vim-pseudocl', { 'do': function('PlugUpdated') }
call plug#end()
call system('cd '.g:plugs['vim-easy-align'].dir.' && git reset --hard HEAD^')
call system('rm -rf '.g:plugs['vim-pseudocl'].dir)
PlugUpdate
Log getline(1, '$')
q
Assert filereadable(g:plugs['vim-easy-align'].dir.'/me'),
\ 'vim-easy-align/me should exist'
Assert filereadable(g:plugs['vim-pseudocl'].dir.'/me'),
\ 'vim-pseudocl/me should exist'
Execute (Cleanup): Execute (Cleanup):
call system('rm -rf '.temp_plugged) call system('rm -rf '.temp_plugged)
call rename('fzf', 'fzf-staged') call rename('fzf', 'fzf-staged')
@ -586,6 +674,7 @@ Execute (Cleanup):
unlet temp_plugged vader plug basertp save_rtp repo lnum fzf unlet temp_plugged vader plug basertp save_rtp repo lnum fzf
delf PlugStatusSorted delf PlugStatusSorted
delf AssertExpect delf AssertExpect
delf PlugUpdated
delc AssertExpect delc AssertExpect
Restore Restore