Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP
Browse files

Update vim bundles

  • Loading branch information...
commit aaf96a4e9f7965329a14e3c300850c200780808f 1 parent 0af3050
@gabebw authored
View
2  vim/bundle/ctrlp.vim/autoload/ctrlp.vim
@@ -2,7 +2,7 @@
" File: autoload/ctrlp.vim
" Description: Fuzzy file, buffer, mru, tag, etc finder.
" Author: Kien Nguyen <github.com/kien>
-" Version: 1.78
+" Version: 1.79
" =============================================================================
" ** Static variables {{{1
View
9 vim/bundle/jellybeans.vim/colors/jellybeans.vim
@@ -357,7 +357,7 @@ call s:X("Function","fad07a","","","Yellow","")
call s:X("Statement","8197bf","","","DarkBlue","")
call s:X("PreProc","8fbfdc","","","LightBlue","")
-hi! link Operator Normal
+hi! link Operator Structure
call s:X("Type","ffb964","","","Yellow","")
call s:X("NonText","606060",g:jellybeans_background_color,"",s:termBlack,"")
@@ -402,6 +402,9 @@ hi! link phpQuoteDouble StringDelimiter
hi! link phpBoolean Constant
hi! link phpNull Constant
hi! link phpArrayPair Operator
+hi! link phpOperator Normal
+hi! link phpRelation Normal
+hi! link phpVarSelector Identifier
" Python
@@ -470,9 +473,9 @@ hi! link objcMethodName Identifier
hi! link objcMethodArg Normal
hi! link objcMessageName Identifier
-" Haskell
+" Vimscript
-hi! link hsOperator Structure
+hi! link vimOper Normal
" Debugger.vim
View
20 vim/bundle/supertab/plugin/supertab.vim
@@ -13,7 +13,7 @@
" }}}
"
" License: {{{
-" Copyright (c) 2002 - 2012
+" Copyright (c) 2002 - 2013
" All rights reserved.
"
" Redistribution and use of this software in source and binary forms, with
@@ -48,7 +48,7 @@
" }}}
"
" Testing Info: {{{
-" Running vim + supertab with the absolute bar minimum settings:
+" Running vim + supertab with the absolute bare minimum settings:
" $ vim -u NONE -U NONE -c "set nocp | runtime plugin/supertab.vim"
" }}}
@@ -353,7 +353,7 @@ function! s:SetDefaultCompletionType() " {{{
endif
endfunction " }}}
-function! s:SuperTab(command) " {{{
+function! SuperTab(command) " {{{
" Used to perform proper cycle navigation as the user requests the next or
" previous entry in a completion list, and determines whether or not to simply
" retain the normal usage of <tab> based on the cursor position.
@@ -770,8 +770,8 @@ endfunction " }}}
imap <c-x> <c-r>=<SID>ManualCompletionEnter()<cr>
- imap <script> <Plug>SuperTabForward <c-r>=<SID>SuperTab('n')<cr>
- imap <script> <Plug>SuperTabBackward <c-r>=<SID>SuperTab('p')<cr>
+ imap <script> <Plug>SuperTabForward <c-r>=SuperTab('n')<cr>
+ imap <script> <Plug>SuperTabBackward <c-r>=SuperTab('p')<cr>
exec 'imap ' . g:SuperTabMappingForward . ' <Plug>SuperTabForward'
exec 'imap ' . g:SuperTabMappingBackward . ' <Plug>SuperTabBackward'
@@ -797,17 +797,17 @@ endfunction " }}}
endif
function! s:ForwardBack(command, map)
exec "let map = \"" . escape(a:map, '<') . "\""
- return pumvisible() ? s:SuperTab(a:command) : map
+ return pumvisible() ? SuperTab(a:command) : map
endfunction
if g:SuperTabCrMapping
let expr_map = 0
- try
+ if v:version > 703 || (v:version == 703 && has('patch32'))
let map_dict = maparg('<cr>', 'i', 0, 1)
- let expr_map = map_dict.expr
- catch
+ let expr_map = has_key(map_dict, 'expr') && map_dict.expr
+ else
let expr_map = maparg('<cr>', 'i') =~? '\<cr>'
- endtry
+ endif
if expr_map
" Not compatible w/ expr mappings. This is most likely a user mapping,
View
29 vim/bundle/tabular/README.md
@@ -0,0 +1,29 @@
+Tabular
+==============
+Sometimes, it's useful to line up text. Naturally, it's nicer to have the
+computer do this for you, since aligning things by hand quickly becomes
+unpleasant. While there are other plugins for aligning text, the ones I've
+tried are either impossibly difficult to understand and use, or too simplistic
+to handle complicated tasks. This plugin aims to make the easy things easy
+and the hard things possible, without providing an unnecessarily obtuse
+interface. It's still a work in progress, and criticisms are welcome.
+
+See [Aligning Text with Tabular.vim](http://vimcasts.org/episodes/aligning-text-with-tabular-vim/)
+for a screencast that shows how Tabular.vim works.
+
+See [doc/Tabular.txt](http://raw.github.com/godlygeek/tabular/master/doc/Tabular.txt)
+for detailed documentation.
+
+Installation
+==============
+If you don't have a preferred installation method, I recommend installing
+[pathogen.vim](https://github.com/tpope/vim-pathogen), and then simply
+copy and paste:
+
+ mkdir -p ~/.vim/bundle
+ cd ~/.vim/bundle
+ git clone git://github.com/godlygeek/tabular.git
+
+Once help tags have been generated (either using Pathogen's `:Helptags`
+command, or by pointing vim's `:helptags` command at the directory where you
+installed Tabular), you can view the manual with `:help tabular`.
View
51 vim/bundle/tslime.vim/plugin/tslime.vim
@@ -11,7 +11,7 @@ let g:loaded_tslime = 1
" Main function.
" Use it in your script if you want to send text to a tmux session.
function! Send_to_Tmux(text)
- if !exists("g:tmux_sessionname") || !exists("g:tmux_windowname") || !exists("g:tmux_panenumber")
+ if !exists("g:tslime")
call <SID>Tmux_Vars()
end
@@ -22,7 +22,7 @@ function! Send_to_Tmux(text)
endfunction
function! s:tmux_target()
- return '"' . g:tmux_sessionname . '":' . g:tmux_windowname . "." . g:tmux_panenumber
+ return '"' . g:tslime['session'] . '":' . g:tslime['window'] . "." . g:tslime['pane']
endfunction
function! s:set_tmux_buffer(text)
@@ -40,12 +40,12 @@ endfunction
" Window completion
function! Tmux_Window_Names(A,L,P)
- return system('tmux list-windows -t "' . g:tmux_sessionname . '" | grep -e "^\w:" | sed -e "s/ \[[0-9x]*\]$//"')
+ return <SID>TmuxWindows()
endfunction
" Pane completion
function! Tmux_Pane_Numbers(A,L,P)
- return system('tmux list-panes -t "' . g:tmux_sessionname . '":' . g:tmux_windowname . " | sed -e 's/:.*$//'")
+ return <SID>TmuxPanes()
endfunction
function! s:TmuxSessions()
@@ -53,31 +53,50 @@ function! s:TmuxSessions()
return sessions
endfunction
+function! s:TmuxWindows()
+ return system('tmux list-windows -t "' . g:tslime['session'] . '" | grep -e "^\w:" | sed -e "s/\s*([0-9].*//g"')
+endfunction
+
+function! s:TmuxPanes()
+ return system('tmux list-panes -t "' . g:tslime['session'] . '":' . g:tslime['window'] . " | sed -e 's/:.*$//'")
+endfunction
+
" set tslime.vim variables
function! s:Tmux_Vars()
let names = split(s:TmuxSessions(), "\n")
+ let g:tslime = {}
if len(names) == 1
- let g:tmux_sessionname = names[0]
+ let g:tslime['session'] = names[0]
else
- let g:tmux_sessionname = ''
+ let g:tslime['session'] = ''
endif
- while g:tmux_sessionname == ''
- let g:tmux_sessionname = input("session name: ", "", "custom,Tmux_Session_Names")
+ while g:tslime['session'] == ''
+ let g:tslime['session'] = input("session name: ", "", "custom,Tmux_Session_Names")
endwhile
- let g:tmux_windowname = substitute(input("window name: ", "", "custom,Tmux_Window_Names"), ":.*$" , '', 'g')
- let g:tmux_panenumber = input("pane number: ", "", "custom,Tmux_Pane_Numbers")
- if g:tmux_windowname == ''
- let g:tmux_windowname = '0'
+ let windows = split(s:TmuxWindows(), "\n")
+ if len(windows) == 1
+ let window = windows[0]
+ else
+ let window = input("window name: ", "", "custom,Tmux_Window_Names")
+ if window == ''
+ let window = windows[0]
+ endif
endif
- if g:tmux_panenumber == ''
- let g:tmux_panenumber = '0'
+ let g:tslime['window'] = substitute(window, ":.*$" , '', 'g')
+
+ let panes = split(s:TmuxPanes(), "\n")
+ if len(panes) == 1
+ let g:tslime['pane'] = panes[0]
+ else
+ let g:tslime['pane'] = input("pane number: ", "", "custom,Tmux_Pane_Numbers")
+ if g:tslime['pane'] == ''
+ let g:tslime['pane'] = panes[0]
+ endif
endif
endfunction
-""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""
-
vmap <unique> <Plug>SendSelectionToTmux "ry :call Send_to_Tmux(@r)<CR>
nmap <unique> <Plug>NormalModeSendToTmux vip <Plug>SendSelectionToTmux
View
73 vim/bundle/vim-fugitive/plugin/fugitive.vim
@@ -1,6 +1,6 @@
" fugitive.vim - A Git wrapper so awesome, it should be illegal
" Maintainer: Tim Pope <http://tpo.pe/>
-" Version: 1.2
+" Version: 2.0
" GetLatestVimScripts: 2975 1 :AutoInstall: fugitive.vim
if exists('g:loaded_fugitive') || &cp
@@ -646,8 +646,8 @@ call s:command("-bar Gstatus :execute s:Status()")
function! s:Status() abort
try
Gpedit :
- set foldmethod=syntax foldlevel=1
wincmd P
+ set foldmethod=syntax foldlevel=1
nnoremap <buffer> <silent> q :<C-U>bdelete<CR>
catch /^fugitive:/
return 'echoerr v:errmsg'
@@ -683,7 +683,11 @@ endfunction
function! s:stage_info(lnum) abort
let filename = matchstr(getline(a:lnum),'^#\t\zs.\{-\}\ze\%( ([^()[:digit:]]\+)\)\=$')
let lnum = a:lnum
- let colon = '\%(:\|\%uff1a\)'
+ if has('multi_byte_encoding')
+ let colon = '\%(:\|\%uff1a\)'
+ else
+ let colon = ':'
+ endif
while lnum && getline(lnum) !~# colon.'$'
let lnum -= 1
endwhile
@@ -1092,7 +1096,7 @@ function! s:Edit(cmd,bang,...) abort
endif
if a:bang
- let args = s:gsub(a:0 ? a:1 : '', '\\@<!%(\\\\)*\zs[%#]', '\=s:buffer().expand(submatch(0))')
+ let args = s:gsub(join(a:000, ' '), '\\@<!%(\\\\)*\zs[%#]', '\=s:buffer().expand(submatch(0))')
if a:cmd =~# 'read'
let git = buffer.repo().git_command()
let last = line('$')
@@ -1127,7 +1131,7 @@ function! s:Edit(cmd,bang,...) abort
if a:0 && a:1 == ''
return ''
elseif a:0
- let file = buffer.expand(a:1)
+ let file = buffer.expand(join(a:000, ' '))
elseif expand('%') ==# ''
let file = ':'
elseif buffer.commit() ==# '' && buffer.path('/') !~# '^/.git\>'
@@ -1148,7 +1152,7 @@ function! s:Edit(cmd,bang,...) abort
endfunction
function! s:EditComplete(A,L,P) abort
- return s:repo().superglob(a:A)
+ return map(s:repo().superglob(a:A), 'fnameescape(v:val)')
endfunction
function! s:EditRunComplete(A,L,P) abort
@@ -1159,20 +1163,20 @@ function! s:EditRunComplete(A,L,P) abort
endif
endfunction
-call s:command("-bar -bang -nargs=? -complete=customlist,s:EditComplete Ge :execute s:Edit('edit<bang>',0,<f-args>)")
-call s:command("-bar -bang -nargs=? -complete=customlist,s:EditComplete Gedit :execute s:Edit('edit<bang>',0,<f-args>)")
-call s:command("-bar -bang -nargs=? -complete=customlist,s:EditRunComplete Gpedit :execute s:Edit('pedit',<bang>0,<f-args>)")
-call s:command("-bar -bang -nargs=? -complete=customlist,s:EditRunComplete Gsplit :execute s:Edit('split',<bang>0,<f-args>)")
-call s:command("-bar -bang -nargs=? -complete=customlist,s:EditRunComplete Gvsplit :execute s:Edit('vsplit',<bang>0,<f-args>)")
-call s:command("-bar -bang -nargs=? -complete=customlist,s:EditRunComplete Gtabedit :execute s:Edit('tabedit',<bang>0,<f-args>)")
-call s:command("-bar -bang -nargs=? -count -complete=customlist,s:EditRunComplete Gread :execute s:Edit((!<count> && <line1> ? '' : <count>).'read',<bang>0,<f-args>)")
+call s:command("-bar -bang -nargs=* -complete=customlist,s:EditComplete Ge :execute s:Edit('edit<bang>',0,<f-args>)")
+call s:command("-bar -bang -nargs=* -complete=customlist,s:EditComplete Gedit :execute s:Edit('edit<bang>',0,<f-args>)")
+call s:command("-bar -bang -nargs=* -complete=customlist,s:EditRunComplete Gpedit :execute s:Edit('pedit',<bang>0,<f-args>)")
+call s:command("-bar -bang -nargs=* -complete=customlist,s:EditRunComplete Gsplit :execute s:Edit('split',<bang>0,<f-args>)")
+call s:command("-bar -bang -nargs=* -complete=customlist,s:EditRunComplete Gvsplit :execute s:Edit('vsplit',<bang>0,<f-args>)")
+call s:command("-bar -bang -nargs=* -complete=customlist,s:EditRunComplete Gtabedit :execute s:Edit('tabedit',<bang>0,<f-args>)")
+call s:command("-bar -bang -nargs=* -count -complete=customlist,s:EditRunComplete Gread :execute s:Edit((!<count> && <line1> ? '' : <count>).'read',<bang>0,<f-args>)")
" }}}1
" Gwrite, Gwq {{{1
-call s:command("-bar -bang -nargs=? -complete=customlist,s:EditComplete Gwrite :execute s:Write(<bang>0,<f-args>)")
-call s:command("-bar -bang -nargs=? -complete=customlist,s:EditComplete Gw :execute s:Write(<bang>0,<f-args>)")
-call s:command("-bar -bang -nargs=? -complete=customlist,s:EditComplete Gwq :execute s:Wq(<bang>0,<f-args>)")
+call s:command("-bar -bang -nargs=* -complete=customlist,s:EditComplete Gwrite :execute s:Write(<bang>0,<f-args>)")
+call s:command("-bar -bang -nargs=* -complete=customlist,s:EditComplete Gw :execute s:Write(<bang>0,<f-args>)")
+call s:command("-bar -bang -nargs=* -complete=customlist,s:EditComplete Gwq :execute s:Wq(<bang>0,<f-args>)")
function! s:Write(force,...) abort
if exists('b:fugitive_commit_arguments')
@@ -1202,7 +1206,7 @@ function! s:Write(force,...) abort
endif
let mytab = tabpagenr()
let mybufnr = bufnr('')
- let path = a:0 ? a:1 : s:buffer().path()
+ let path = a:0 ? join(a:000, ' ') : s:buffer().path()
if path =~# '^:\d\>'
return 'write'.(a:force ? '! ' : ' ').s:fnameescape(s:repo().translate(s:buffer().expand(path)))
endif
@@ -1327,9 +1331,9 @@ endfunction
" }}}1
" Gdiff {{{1
-call s:command("-bang -bar -nargs=? -complete=customlist,s:EditComplete Gdiff :execute s:Diff(<bang>0,<f-args>)")
-call s:command("-bar -nargs=? -complete=customlist,s:EditComplete Gvdiff :execute s:Diff(0,<f-args>)")
-call s:command("-bar -nargs=? -complete=customlist,s:EditComplete Gsdiff :execute s:Diff(1,<f-args>)")
+call s:command("-bang -bar -nargs=* -complete=customlist,s:EditComplete Gdiff :execute s:Diff(<bang>0,<f-args>)")
+call s:command("-bar -nargs=* -complete=customlist,s:EditComplete Gvdiff :execute s:Diff(0,<f-args>)")
+call s:command("-bar -nargs=* -complete=customlist,s:EditComplete Gsdiff :execute s:Diff(1,<f-args>)")
augroup fugitive_diff
autocmd!
@@ -1421,20 +1425,21 @@ function! s:Diff(bang,...)
call s:diffthis()
return ''
elseif a:0
- if a:1 ==# ''
+ let arg = join(a:000, ' ')
+ if arg ==# ''
return ''
- elseif a:1 ==# '/'
+ elseif arg ==# '/'
let file = s:buffer().path('/')
- elseif a:1 ==# ':'
+ elseif arg ==# ':'
let file = s:buffer().path(':0:')
- elseif a:1 =~# '^:/.'
+ elseif arg =~# '^:/.'
try
- let file = s:repo().rev_parse(a:1).s:buffer().path(':')
+ let file = s:repo().rev_parse(arg).s:buffer().path(':')
catch /^fugitive:/
return 'echoerr v:errmsg'
endtry
else
- let file = s:buffer().expand(a:1)
+ let file = s:buffer().expand(arg)
endif
if file !~# ':' && file !~# '^/' && s:repo().git_chomp('cat-file','-t',file) =~# '^\%(tag\|commit\)$'
let file = file.s:buffer().path(':')
@@ -1631,7 +1636,7 @@ function! s:Blame(bang,line1,line2,count,args) abort
execute "vertical resize ".(s:linechars('.\{-\}\ze\s\+\d\+)')+1)
nnoremap <buffer> <silent> q :exe substitute(bufwinnr(b:fugitive_blamed_bufnr).' wincmd w<Bar>'.bufnr('').'bdelete','^-1','','')<CR>
nnoremap <buffer> <silent> gq :exe substitute(bufwinnr(b:fugitive_blamed_bufnr).' wincmd w<Bar>'.bufnr('').'bdelete<Bar>if expand("%:p") =~# "^fugitive:[\\/][\\/]"<Bar>Gedit<Bar>endif','^-1','','')<CR>
- nnoremap <buffer> <silent> <CR> :<C-U>exe <SID>BlameJump('')<CR>
+ nnoremap <buffer> <silent> <CR> :<C-U>exe <SID>BlameCommit("exe 'norm q'<Bar>edit")<CR>
nnoremap <buffer> <silent> - :<C-U>exe <SID>BlameJump('')<CR>
nnoremap <buffer> <silent> P :<C-U>exe <SID>BlameJump('^'.v:count1)<CR>
nnoremap <buffer> <silent> ~ :<C-U>exe <SID>BlameJump('~'.v:count1)<CR>
@@ -1761,11 +1766,11 @@ endfunction
" }}}1
" Gbrowse {{{1
-call s:command("-bar -bang -range -nargs=? -complete=customlist,s:EditComplete Gbrowse :execute s:Browse(<bang>0,<line1>,<count>,<f-args>)")
+call s:command("-bar -bang -range -nargs=* -complete=customlist,s:EditComplete Gbrowse :execute s:Browse(<bang>0,<line1>,<count>,<f-args>)")
function! s:Browse(bang,line1,count,...) abort
try
- let rev = a:0 ? substitute(a:1,'@[[:alnum:]_-]*\%(://.\{-\}\)\=$','','') : ''
+ let rev = a:0 ? substitute(join(a:000, ' '),'@[[:alnum:]_-]*\%(://.\{-\}\)\=$','','') : ''
if rev ==# ''
let expanded = s:buffer().rev()
elseif rev ==# ':'
@@ -1808,8 +1813,8 @@ function! s:Browse(bang,line1,count,...) abort
endif
endif
- if a:0 && a:1 =~# '@[[:alnum:]_-]*\%(://.\{-\}\)\=$'
- let remote = matchstr(a:1,'@\zs[[:alnum:]_-]\+\%(://.\{-\}\)\=$')
+ if a:0 && join(a:000, ' ') =~# '@[[:alnum:]_-]*\%(://.\{-\}\)\=$'
+ let remote = matchstr(join(a:000, ' '),'@\zs[[:alnum:]_-]\+\%(://.\{-\}\)\=$')
elseif path =~# '^\.git/refs/remotes/.'
let remote = matchstr(path,'^\.git/refs/remotes/\zs[^/]\+')
else
@@ -2242,10 +2247,10 @@ endif
augroup fugitive_temp
autocmd!
autocmd BufNewFile,BufReadPost *
- \ if has_key(s:temp_files,expand('<amatch>:p')) |
- \ let b:git_dir = s:temp_files[expand('<amatch>:p')] |
+ \ if has_key(s:temp_files,expand('<afile>:p')) |
+ \ let b:git_dir = s:temp_files[expand('<afile>:p')] |
\ let b:git_type = 'temp' |
- \ call s:Detect(expand('<amatch>:p')) |
+ \ call s:Detect(expand('<afile>:p')) |
\ setlocal bufhidden=delete |
\ nnoremap <buffer> <silent> q :<C-U>bdelete<CR>|
\ endif
View
16 vim/bundle/vim-rails/CONTRIBUTING.markdown
@@ -0,0 +1,16 @@
+If your [commit message sucks][suck], I'm not going to accept your pull
+request. I've explained very politely dozens of times that [my general
+guidelines][guidelines] are absolute rules on my own repositories, so I may
+lack the energy to explain it to you yet another time. And please, if I ask
+you to change something, `git commit --amend` and `git push -f`.
+
+If a feature idea is nontrivial, you should probably open an issue to [discuss
+it][] before attempting a pull request. One of the biggest challenges in
+maintaining rails.vim has been beating back the bloat, so do not assume that
+your idea will make the cut. And if I like your idea, I'm generally amenable
+to just knocking it out myself, rather than making you familiarize yourself
+with a 4 thousand line code base.
+
+[suck]: http://stopwritingramblingcommitmessages.com/
+[guidelines]: http://tbaggery.com/2008/04/19/a-note-about-git-commit-messages.html
+[discuss it]: http://www.igvita.com/2011/12/19/dont-push-your-pull-requests/
View
86 vim/bundle/vim-rails/README.markdown
@@ -1,5 +1,4 @@
-rails.vim
-=========
+# rails.vim
Remember when everybody and their mother was using TextMate for Ruby on
Rails development? Well if it wasn't for rails.vim, we'd still be in
@@ -9,10 +8,10 @@ features:
* Easy navigation of the Rails directory structure. `gf` considers
context and knows about partials, fixtures, and much more. There are
two commands, `:A` (alternate) and `:R` (related) for easy jumping
- between files, including favorites like model to migration, template
- to helper, and controller to functional test. For more advanced
- usage, `:Rmodel`, `:Rview`, `:Rcontroller`, and several other commands
- are provided. `:help rails-navigation`
+ between files, including favorites like model to schema, template to
+ helper, and controller to functional test. For more advanced usage,
+ `:Rmodel`, `:Rview`, `:Rcontroller`, and several other commands are
+ provided. `:help rails-navigation`
* Enhanced syntax highlighting. From `has_and_belongs_to_many` to
`distance_of_time_in_words`, it's here. For easy completion of these
@@ -25,18 +24,18 @@ features:
arbitrary migrations, load individual fixtures, and more.
`:help rails-rake`
-* Interface to `script/*`. Generally, use `:Rscript about` to call
- `script/about` or `script/rails about`. Most commands have wrappers
+* Interface to the `rails` command. Generally, use `:Rails console` to
+ call `rails console` or `script/console`. Most commands have wrappers
with additional features: `:Rgenerate controller Blog` generates a
blog controller and edits `app/controllers/blog_controller.rb`.
`:help rails-scripts`
-* Partial extraction and migration inversion. `:Rextract {file}`
- replaces the desired range (ideally selected in visual line mode) with
- `render :partial => '{file}'`, which is automatically created with
- your content. The `@{file}` instance variable is replaced with the
- `{file}` local variable. `:Rinvert` takes a `self.up` migration and
- writes a `self.down`. `:help rails-refactoring`
+* Partial and concern extraction. In a view, `:Rextract {file}`
+ replaces the desired range (typically selected in visual line mode)
+ with `render '{file}'`, which is automatically created with your
+ content. In a model or controller, a concern is created, with the
+ appropriate `include` declaration left behind.
+ `:help rails-:Rextract`
* Integration with other plugins. `:Rtree` spawns
[NERDTree.vim](https://github.com/scrooloose/nerdtree). If
@@ -45,11 +44,10 @@ features:
`database.yml`. Users of
[abolish.vim](https://github.com/tpope/vim-abolish) get pluralize and
tableize coercions, and users of
- [bundler.vim](https://github.com/tpope/vim-bundler) get `bundle exec
- rake`. `:help rails-integration`
+ [bundler.vim](https://github.com/tpope/vim-bundler) get a smattering of
+ features. `:help rails-integration`
-Installation
-------------
+## Installation
If you don't have a preferred installation method, I recommend
installing [pathogen.vim](https://github.com/tpope/vim-pathogen), and
@@ -57,20 +55,25 @@ then simply copy and paste:
cd ~/.vim/bundle
git clone git://github.com/tpope/vim-rails.git
+ git clone git://github.com/tpope/vim-bundler.git
+
+
+You don't strictly need [bundler.vim][], but it helps.
Once help tags have been generated, you can view the manual with
`:help rails`.
-FAQ
----
+[bundler.vim]: https://github.com/tpope/vim-bundler
+
+## FAQ
-> I installed the plugin and started Vim. Why does only the :Rails
+> I installed the plugin and started Vim. Why does only the `:Rails`
> command exist?
This plugin cares about the current file, not the current working
directory. Edit a file from a Rails application.
-> I opened a new tab. Why does only the :Rails command exist?
+> I opened a new tab. Why does only the `:Rails` command exist?
This plugin cares about the current file, not the current working
directory. Edit a file from a Rails application. You can use the `:RT`
@@ -87,19 +90,10 @@ I wrote [rake.vim](https://github.com/tpope/vim-rake) for exactly that
purpose. It activates for any project with a `Rakefile` that's not a
Rails application.
-> Is Rails 3 supported yet?
-
-Of course.
-
-> Is Rails 2 still supported?
+> What Rails versions are supported?
-Baby, you can go all the way back to Rails 1 if you like (give or take
-some syntax highlighting).
-
-> Can I use rails.vim with engines?
-
-Not officially, but if you create `config/environment.rb` in the root of
-the engine, it will mostly work.
+All of them. A few features like syntax highlighting tend to reflect the
+latest version only.
> Rake is slow. How about making `:Rake` run
> `testrb`/`rspec`/`cucumber` directly instead of `rake`?
@@ -120,26 +114,7 @@ meantime, here's how you can set up `:make` to run the current test:
autocmd User Bundler
\ if &makeprg !~# 'bundle' | setl makeprg^=bundle\ exec\ | endif
-Contributing
-------------
-
-If your [commit message sucks](http://stopwritingramblingcommitmessages.com/),
-I'm not going to accept your pull request. I've explained very politely
-dozens of times that
-[my general guidelines](http://tbaggery.com/2008/04/19/a-note-about-git-commit-messages.html)
-are absolute rules on my own repositories, so I may lack the energy to
-explain it to you yet another time. And please, if I ask you to change
-something, `git commit --amend`.
-
-Beyond that, don't be shy about asking before patching. What takes you
-hours might take me minutes simply because I have both domain knowledge
-and a perverse knowledge of VimScript so vast that many would consider
-it a symptom of mental illness. On the flip side, some ideas I'll
-reject no matter how good the implementation is. "Send a patch" is an
-edge case answer in my book.
-
-Self-Promotion
---------------
+## Self-Promotion
Like rails.vim? Follow the repository on
[GitHub](https://github.com/tpope/vim-rails) and vote for it on
@@ -148,8 +123,7 @@ you're feeling especially charitable, follow [tpope](http://tpo.pe/) on
[Twitter](http://twitter.com/tpope) and
[GitHub](https://github.com/tpope).
-License
--------
+## License
Copyright (c) Tim Pope. Distributed under the same terms as Vim itself.
See `:help license`.
View
1,439 vim/bundle/vim-rails/autoload/rails.vim
@@ -37,12 +37,15 @@ function! s:startswith(string,prefix)
return strpart(a:string, 0, strlen(a:prefix)) ==# a:prefix
endfunction
-function! s:uniq(list)
- let seen = {}
+function! s:uniq(list) abort
let i = 0
+ let seen = {}
while i < len(a:list)
- if has_key(seen,a:list[i])
- call remove(a:list, i)
+ if (a:list[i] ==# '' && exists('empty')) || has_key(seen,a:list[i])
+ call remove(a:list,i)
+ elseif a:list[i] ==# ''
+ let i += 1
+ let empty = 1
else
let seen[a:list[i]] = 1
let i += 1
@@ -64,13 +67,20 @@ function! s:esccmd(p)
endfunction
function! s:rquote(str)
- " Imperfect but adequate for Ruby arguments
if a:str =~ '^[A-Za-z0-9_/.:-]\+$'
return a:str
elseif &shell =~? 'cmd'
- return '"'.s:gsub(s:gsub(a:str,'\','\\'),'"','\\"').'"'
+ return '"'.s:gsub(s:gsub(a:str, '"', '""'), '\%', '"%"').'"'
else
- return "'".s:gsub(s:gsub(a:str,'\','\\'),"'","'\\\\''")."'"
+ return shellescape(a:str)
+ endif
+endfunction
+
+function! s:fnameescape(file) abort
+ if exists('*fnameescape')
+ return fnameescape(a:file)
+ else
+ return escape(a:file," \t\n*?[{`$\\%#'\"|!<")
endif
endfunction
@@ -303,15 +313,13 @@ function! s:controller(...)
return rails#buffer().controller_name(a:0 ? a:1 : 0)
endfunction
-function! s:find_classification(classifications, filename) abort
+function! s:find_projection(projections, filename) abort
let f = a:filename
- for c in a:classifications
- for prefix in s:split(get(c, 'prefix', []))
- for suffix in s:split(get(c, 'suffix', '.rb'))
- if s:startswith(f, prefix) && f[-strlen(suffix) : - 1] ==# suffix
- return [f[strlen(prefix) : -strlen(suffix)-1], c]
- endif
- endfor
+ for c in a:projections
+ for [prefix, suffix] in s:projection_pairs(c)
+ if s:startswith(f, prefix) && f[-strlen(suffix) : - 1] ==# suffix
+ return [f[strlen(prefix) : -strlen(suffix)-1], c]
+ endif
endfor
endfor
return ['', {}]
@@ -322,7 +330,7 @@ function! s:readable_controller_name(...) dict abort
if has_key(self,'getvar') && self.getvar('rails_controller') != ''
return self.getvar('rails_controller')
endif
- let [root, _] = s:find_classification(filter(values(self.app().config('classifications')), 'get(v:val, "affinity", "") ==# "controller"'), f)
+ let [root, _] = s:find_projection(filter(values(self.app().projections()), 'get(v:val, "affinity", "") ==# "controller"'), f)
if root !=# ''
return root
endif
@@ -369,15 +377,19 @@ function! s:readable_model_name(...) dict abort
if has_key(self,'getvar') && self.getvar('rails_model') != ''
return self.getvar('rails_model')
endif
- let [root, _] = s:find_classification(filter(values(self.app().config('classifications')), 'get(v:val, "affinity", "") ==# "model"'), f)
+ let [root, _] = s:find_projection(filter(values(self.app().projections()), 'get(v:val, "affinity", "") ==# "model"'), f)
if root !=# ''
return root
endif
+ let [root, _] = s:find_projection(filter(values(self.app().projections()), 'get(v:val, "affinity", "") ==# "collection"'), f)
+ if root !=# ''
+ return rails#singularize(root)
+ endif
if f =~ '\<app/models/.*_observer.rb$'
return s:sub(f,'.*<app/models/(.*)_observer\.rb$','\1')
elseif f =~ '\<app/models/.*\.rb$'
return s:sub(f,'.*<app/models/(.*)\.rb$','\1')
- elseif f =~ '\<test/unit/.*_observer_test\.rb$'
+ elseif f =~ '\<test/\%(unit\|models\)/.*_observer_test\.rb$'
return s:sub(f,'.*<test/unit/(.*)_observer_test\.rb$','\1')
elseif f =~ '\<test/\%(unit\|models\)/.*_test\.rb$'
return s:sub(f,'.*<test/%(unit|models)/(.*)_test\.rb$','\1')
@@ -681,8 +693,6 @@ function! s:readable_calculate_file_type() dict abort
let r = "spec"
elseif f =~ '_helper\.rb$'
let r = "helper"
- elseif f =~ '\<app/metal/.*\.rb$'
- let r = "metal"
elseif f =~ '\<app/mailers/.*\.rb'
let r = "mailer"
elseif f =~ '\<app/models/'
@@ -749,7 +759,7 @@ function! s:readable_calculate_file_type() dict abort
let r = "db-migration"
elseif f=~ '\<db/schema\.rb$'
let r = "db-schema"
- elseif f =~ '\<vendor/plugins/.*/recipes/.*\.rb$' || f =~ '\.rake$' || f =~ '\<\%(Rake\|Cap\)file$' || f =~ '\<config/deploy\.rb$'
+ elseif f =~ '\.rake$' || f =~ '\<\%(Rake\|Cap\)file$' || f =~ '\<config/deploy\.rb$'
let r = "task"
elseif f =~ '\<log/.*\.log$'
let r = "log"
@@ -799,8 +809,11 @@ endfunction
function! s:app_default_locale() dict abort
if self.cache.needs('default_locale')
- let candidates = map(filter(s:readfile(self.path('config/environment.rb')),'v:val =~ "^ *config.i18n.default_locale = :[\"'']\\=[A-Za-z-]\\+[\"'']\\= *$"'),'matchstr(v:val,"[A-Za-z-]\\+[\"'']\\= *$")')
- call self.cache.set('default_locale',get(candidates,0,'en'))
+ let candidates = map(filter(
+ \ s:readfile(self.path('config/application.rb')) + s:readfile(self.path('config/environment.rb')),
+ \ 'v:val =~ "^ *config.i18n.default_locale = :[\"'']\\=[A-Za-z-]\\+[\"'']\\= *$"'
+ \ ), 'matchstr(v:val,"[A-Za-z-]\\+[\"'']\\= *$")')
+ call self.cache.set('default_locale', get(candidates, 0, 'en'))
endif
return self.cache.get('default_locale')
endfunction
@@ -809,6 +822,7 @@ function! s:app_has(feature) dict
let map = {
\'test': 'test/',
\'spec': 'spec/',
+ \'bundler': 'Gemfile',
\'cucumber': 'features/',
\'turnip': 'spec/acceptance/',
\'sass': 'public/stylesheets/sass/',
@@ -820,7 +834,11 @@ function! s:app_has(feature) dict
let features = self.cache.get('features')
if !has_key(features,a:feature)
let path = get(map,a:feature,a:feature.'/')
- let features[a:feature] = isdirectory(rails#app().path(path))
+ if path =~# '/$'
+ let features[a:feature] = isdirectory(rails#app().path(path))
+ else
+ let features[a:feature] = filereadable(rails#app().path(path))
+ endif
endif
return features[a:feature]
endfunction
@@ -839,47 +857,53 @@ call s:add_methods('readable',['app','relative','absolute','spec','calculate_fil
" Ruby Execution {{{1
function! s:app_ruby_shell_command(cmd) dict abort
- if self.path() =~ '://'
- return "ruby ".a:cmd
- else
- return "ruby -C ".s:rquote(self.path())." ".a:cmd
- endif
+ return 'ruby '.a:cmd
endfunction
function! s:app_script_shell_command(cmd) dict abort
- if self.has_file('script/rails') && a:cmd !~# '^rails\>'
+ if !empty(glob(rails#app().path('.zeus.sock'))) && a:cmd =~# '^\%(console\|dbconsole\|destroy\|generate\|server\|runner\)\>'
+ return 'zeus '.a:cmd
+ elseif self.has_file('script/rails')
let cmd = 'script/rails '.a:cmd
- else
+ elseif self.has_file('script/' . matchstr(a:cmd, '\w\+'))
let cmd = 'script/'.a:cmd
+ elseif self.has_file('bin/rails')
+ let cmd = 'bin/rails '.a:cmd
+ elseif self.has('bundler')
+ return 'bundle exec rails ' . a:cmd
+ else
+ return 'rails '.a:cmd
endif
return self.ruby_shell_command(cmd)
endfunction
function! s:app_background_script_command(cmd) dict abort
let cmd = s:esccmd(self.script_shell_command(a:cmd))
- if has_key(self,'options') && has_key(self.options,'gnu_screen')
- let screen = self.options.gnu_screen
- else
- let screen = g:rails_gnu_screen
- endif
- if has("gui_win32")
- if &shellcmdflag == "-c" && ($PATH . &shell) =~? 'cygwin'
- silent exe "!cygstart -d ".s:rquote(self.path())." ruby ".a:cmd
- else
+ let title = s:sub(a:cmd, '\s.*', '')
+ call s:push_chdir(1)
+ try
+ if has("gui_win32")
exe "!start ".cmd
+ elseif exists("$STY") && !has("gui_running") && executable("screen")
+ silent exe "!screen -ln -fn -t ".title.' '.cmd
+ elseif exists("$TMUX") && !has("gui_running") && executable("tmux")
+ silent exe '!tmux new-window -n "'.title.'" "'.cmd.'"'
+ else
+ exe "!".cmd
endif
- elseif exists("$STY") && !has("gui_running") && screen && executable("screen")
- silent exe "!screen -ln -fn -t ".s:sub(s:sub(a:cmd,'\s.*',''),'^%(script|-rcommand)/','rails-').' '.cmd
- elseif exists("$TMUX") && !has("gui_running") && screen && executable("tmux")
- silent exe '!tmux new-window -n "'.s:sub(s:sub(a:cmd,'\s.*',''),'^%(script|-rcommand)/','rails-').'" "'.cmd.'"'
- else
- exe "!".cmd
- endif
+ finally
+ call s:pop_command()
+ endtry
return ''
endfunction
function! s:app_execute_script_command(cmd) dict abort
- exe '!'.s:esccmd(self.script_shell_command(a:cmd))
+ call s:push_chdir(1)
+ try
+ exe '!'.s:esccmd(self.script_shell_command(a:cmd))
+ finally
+ call s:pop_command()
+ endtry
return ''
endfunction
@@ -888,9 +912,8 @@ function! s:app_lightweight_ruby_eval(ruby,...) dict abort
if !executable("ruby")
return def
endif
- let args = '-e '.s:rquote('begin; require %{rubygems}; rescue LoadError; end; begin; require %{active_support}; rescue LoadError; end; '.a:ruby)
+ let args = '-e '.s:rquote(a:ruby)
let cmd = self.ruby_shell_command(args)
- " If the shell is messed up, this command could cause an error message
silent! let results = system(cmd)
return v:shell_error == 0 ? results : def
endfunction
@@ -902,8 +925,12 @@ function! s:app_eval(ruby,...) dict abort
endif
let args = "-r./config/boot -r ".s:rquote(self.path("config/environment"))." -e ".s:rquote(a:ruby)
let cmd = self.ruby_shell_command(args)
- " If the shell is messed up, this command could cause an error message
- silent! let results = system(cmd)
+ call s:push_chdir(1)
+ try
+ silent! let results = system(cmd)
+ finally
+ call s:pop_command()
+ endtry
return v:shell_error == 0 ? results : def
endfunction
@@ -912,44 +939,17 @@ call s:add_methods('app', ['ruby_shell_command','script_shell_command','execute_
" }}}1
" Commands {{{1
-function! s:prephelp()
- let fn = fnamemodify(s:file,':h:h').'/doc/'
- if filereadable(fn.'rails.txt')
- if !filereadable(fn.'tags') || getftime(fn.'tags') <= getftime(fn.'rails.txt')
- silent! helptags `=fn`
- endif
- endif
-endfunction
-
-function! RailsHelpCommand(...)
- call s:prephelp()
- let topic = a:0 ? a:1 : ""
- if topic == "" || topic == "-"
- return "help rails"
- elseif topic =~ '^g:'
- return "help ".topic
- elseif topic =~ '^-'
- return "help rails".topic
- else
- return "help rails-".topic
- endif
-endfunction
-
function! s:BufCommands()
- call s:BufFinderCommands()
call s:BufNavCommands()
call s:BufScriptWrappers()
+ command! -buffer -bar -nargs=+ Rnavcommand :call s:Navcommand(<bang>0,<f-args>)
+ command! -buffer -bar -nargs=* -bang Rabbrev :call s:Abbrev(<bang>0,<f-args>)
command! -buffer -bar -nargs=? -bang -count -complete=customlist,s:Complete_rake Rake :call s:Rake(<bang>0,!<count> && <line1> ? -1 : <count>,<q-args>)
command! -buffer -bar -nargs=? -bang -range -complete=customlist,s:Complete_preview Rpreview :call s:Preview(<bang>0,<line1>,<q-args>)
command! -buffer -bar -nargs=? -bang -complete=customlist,s:Complete_environments Rlog :call s:Log(<bang>0,<q-args>)
command! -buffer -bar -nargs=* -bang -complete=customlist,s:Complete_set Rset :call s:Set(<bang>0,<f-args>)
command! -buffer -bar -nargs=0 Rtags :execute rails#app().tags_command()
- " Embedding all this logic directly into the command makes the error
- " messages more concise.
- command! -buffer -bar -nargs=? -bang Rdoc :
- \ if <bang>0 || <q-args> =~ "^\\([:'-]\\|g:\\)" |
- \ exe RailsHelpCommand(<q-args>) |
- \ else | call s:Doc(<bang>0,<q-args>) | endif
+ command! -buffer -bar -nargs=0 Ctags :execute rails#app().tags_command()
command! -buffer -bar -nargs=0 -bang Rrefresh :if <bang>0|unlet! g:autoloaded_rails|source `=s:file`|endif|call s:Refresh(<bang>0)
if exists(":NERDTree")
command! -buffer -bar -nargs=? -complete=customlist,s:Complete_cd Rtree :NERDTree `=rails#app().path(<f-args>)`
@@ -961,35 +961,16 @@ function! s:BufCommands()
if RailsFilePath() =~ '\<app/views/'
" TODO: complete controller names with trailing slashes here
command! -buffer -bar -bang -nargs=? -range -complete=customlist,s:controllerList Rextract :<line1>,<line2>call s:Extract(<bang>0,<f-args>)
+ elseif rails#buffer().name() =~# '^app/helpers/.*.rb$'
+ command! -buffer -bar -bang -nargs=1 -range Rextract :<line1>,<line2>call s:RubyExtract(<bang>0, 'app/helpers', [], s:sub(<f-args>, '_helper$|Helper$|$', '_helper'))
+ elseif rails#buffer().name() =~# '^app/\w\+/.*\.rb$'
+ command! -buffer -bar -bang -nargs=1 -range Rextract :<line1>,<line2>call s:RubyExtract(<bang>0, matchstr(rails#buffer().name(), '^app/\w\+/').'concerns', [' extend ActiveSupport::Concern', ''], <f-args>)
endif
if RailsFilePath() =~ '\<db/migrate/.*\.rb$'
command! -buffer -bar Rinvert :call s:Invert(<bang>0)
endif
endfunction
-function! s:Doc(bang, string)
- if a:string != ""
- if exists("g:rails_search_url")
- let query = substitute(a:string,'[^A-Za-z0-9_.~-]','\="%".printf("%02X",char2nr(submatch(0)))','g')
- let url = printf(g:rails_search_url, query)
- else
- return s:error("specify a g:rails_search_url with %s for a query placeholder")
- endif
- elseif isdirectory(rails#app().path("doc/api/classes"))
- let url = rails#app().path("/doc/api/index.html")
- elseif s:getpidfor("0.0.0.0","8808") > 0
- let url = "http://localhost:8808"
- else
- let url = "http://api.rubyonrails.org"
- endif
- call s:initOpenURL()
- if exists(":OpenURL")
- exe "OpenURL ".s:escarg(url)
- else
- return s:error("No :OpenURL command found")
- endif
-endfunction
-
function! s:Log(bang,arg)
if a:arg == ""
let lf = "log/".s:environment().".log"
@@ -1012,31 +993,52 @@ function! s:Log(bang,arg)
endif
endfunction
-function! rails#new_app_command(bang,...)
- if a:0 == 0
- let msg = "rails.vim ".g:autoloaded_rails
- if a:bang && exists('b:rails_root') && rails#buffer().type_name() == ''
- echo msg." (Rails)"
- elseif a:bang && exists('b:rails_root')
- echo msg." (Rails-".rails#buffer().type_name().")"
- elseif a:bang
- echo msg
- else
- !rails
- endif
- return
+function! rails#new_app_command(bang,...) abort
+ if !a:0 && a:bang
+ echo "rails.vim ".g:autoloaded_rails
+ elseif !a:0 || a:1 !=# 'new'
+ return 'echoerr '.string('Usage: rails new <path>')
endif
- let args = map(copy(a:000),'expand(v:val)')
+
+ let args = copy(a:000)
if a:bang
- let args = ['--force'] + args
+ let args += ['--force']
endif
- exe '!rails '.join(map(copy(args),'s:rquote(v:val)'),' ')
- for dir in args
- if dir !~# '^-' && filereadable(dir.'/'.g:rails_default_file)
- edit `=dir.'/'.g:rails_default_file`
- return
+
+ if &shellpipe !~# 'tee' && index(args, '--skip') < 0 && index(args, '--force') < 0
+ let args += ['--skip']
+ endif
+
+ let temp = tempname()
+ try
+ exe '!rails' join(map(copy(args),'s:rquote(v:val)'),' ') &shellpipe temp
+ catch /^Vim:Interrupt/
+ endtry
+
+ if filereadable(expand(args[1]))
+ let lines = readfile(temp)
+ if get(lines, 0, '') =~# ' $'
+ let pos = '2cc'
+ let lines[0] .= '.'
+ call writefile(lines, temp)
+ else
+ let pos = 'cfirst'
endif
- endfor
+
+ let old_errorformat = &l:errorformat
+ let chdir = exists("*haslocaldir") && haslocaldir() ? 'lchdir' : 'chdir'
+ let cwd = getcwd()
+ try
+ exe chdir s:fnameescape(expand(args[1]))
+ let &l:errorformat = s:efm_generate
+ exe 'cgetfile' temp
+ exe pos
+ finally
+ let &l:errorformat = old_errorformat
+ exe chdir s:fnameescape(cwd)
+ endtry
+ endif
+ return ''
endfunction
function! s:app_tags_command() dict
@@ -1112,7 +1114,8 @@ function! s:app_rake_tasks() dict
if self.cache.needs('rake_tasks')
call s:push_chdir()
try
- let lines = split(system("rake -T"),"\n")
+ let output = system(self.has_file('bin/rake') ? self.ruby_shell_command('bin/rake -T') : 'rake -T')
+ let lines = split(output, "\n")
finally
call s:pop_command()
endtry
@@ -1141,6 +1144,7 @@ let s:efm_backtrace='%D(in\ %f),'
function! s:makewithruby(arg,bang,...)
let old_make = &makeprg
+ call s:push_chdir(1)
try
let &l:makeprg = rails#app().ruby_shell_command(a:arg)
exe 'make'.(a:bang ? '!' : '')
@@ -1148,6 +1152,7 @@ function! s:makewithruby(arg,bang,...)
cwindow
endif
finally
+ call s:pop_command()
let &l:makeprg = old_make
endtry
endfunction
@@ -1158,14 +1163,19 @@ function! s:Rake(bang,lnum,arg)
let old_makeprg = &l:makeprg
let old_errorformat = &l:errorformat
try
- if exists('b:bundler_root') && b:bundler_root ==# rails#app().path()
+ call s:push_chdir(1)
+ if !empty(glob(rails#app().path('.zeus.sock'))) && executable('zeus')
+ let &l:makeprg = 'zeus rake'
+ elseif rails#app().has_file('bin/rake')
+ let &l:makeprg = rails#app().ruby_shell_command('bin/rake')
+ elseif exists('b:bundler_root') && b:bundler_root ==# rails#app().path()
let &l:makeprg = 'bundle exec rake'
else
let &l:makeprg = 'rake'
endif
let &l:errorformat = s:efm_backtrace
let arg = a:arg
- if &filetype =~# '^ruby\>' && arg == '' && g:rails_modelines
+ if &filetype =~# '^ruby\>' && arg == ''
let mnum = s:lastmethodline(lnum)
let str = getline(mnum)."\n".getline(mnum+1)."\n".getline(mnum+2)."\n"
let pat = '\s\+\zs.\{-\}\ze\%(\n\|\s\s\|#{\@!\|$\)'
@@ -1176,12 +1186,7 @@ function! s:Rake(bang,lnum,arg)
endif
endif
if arg == ''
- let opt = s:getopt('task','bl')
- if opt != ''
- let arg = opt
- else
- let arg = rails#buffer().default_rake_task(lnum)
- endif
+ let arg = rails#buffer().default_rake_task(lnum)
endif
if !has_key(self,'options') | let self.options = {} | endif
if arg == '-'
@@ -1191,10 +1196,7 @@ function! s:Rake(bang,lnum,arg)
let withrubyargs = '-r ./config/boot -r '.s:rquote(self.path('config/environment')).' -e "puts \%((in \#{Dir.getwd}))" '
if arg =~# '^notes\>'
let &l:errorformat = '%-P%f:,\ \ *\ [%*[\ ]%l]\ [%t%*[^]]] %m,\ \ *\ [%*[\ ]%l] %m,%-Q'
- " %D to chdir is apparently incompatible with %P multiline messages
- call s:push_chdir(1)
exe 'make! '.arg
- call s:pop_command()
if !a:bang
cwindow
endif
@@ -1238,6 +1240,7 @@ function! s:Rake(bang,lnum,arg)
finally
let &l:errorformat = old_errorformat
let &l:makeprg = old_makeprg
+ call s:pop_command()
endtry
endfunction
@@ -1478,9 +1481,10 @@ endfunction
" Script Wrappers {{{1
function! s:BufScriptWrappers()
- command! -buffer -bar -nargs=* -complete=customlist,s:Complete_script Rscript :execute rails#app().script_command(<bang>0,<f-args>)
- command! -buffer -bar -nargs=* -complete=customlist,s:Complete_generate Rgenerate :execute rails#app().generate_command(<bang>0,<f-args>)
- command! -buffer -bar -nargs=* -complete=customlist,s:Complete_destroy Rdestroy :execute rails#app().destroy_command(<bang>0,<f-args>)
+ command! -buffer -bang -bar -nargs=* -complete=customlist,s:Complete_script Rscript :execute rails#app().script_command(<bang>0,<f-args>)
+ command! -buffer -bang -bar -nargs=* -complete=customlist,s:Complete_script Rails :execute rails#app().script_command(<bang>0,<f-args>)
+ command! -buffer -bang -bar -nargs=* -complete=customlist,s:Complete_generate Rgenerate :execute rails#app().generator_command(<bang>0,'generate',<f-args>)
+ command! -buffer -bar -nargs=* -complete=customlist,s:Complete_destroy Rdestroy :execute rails#app().generator_command(1,'destroy',<f-args>)
command! -buffer -bar -nargs=? -bang -complete=customlist,s:Complete_server Rserver :execute rails#app().server_command(<bang>0,<q-args>)
command! -buffer -bang -nargs=1 -range=0 -complete=customlist,s:Complete_ruby Rrunner :execute rails#app().runner_command(<bang>0 ? -2 : (<count>==<line2>?<count>:-1),<f-args>)
command! -buffer -nargs=1 -range=0 -complete=customlist,s:Complete_ruby Rp :execute rails#app().runner_command(<count>==<line2>?<count>:-1,'p begin '.<f-args>.' end')
@@ -1488,20 +1492,45 @@ function! s:BufScriptWrappers()
command! -buffer -nargs=1 -range=0 -complete=customlist,s:Complete_ruby Ry :execute rails#app().runner_command(<count>==<line2>?<count>:-1,'y begin '.<f-args>.' end')
endfunction
-function! s:app_generators() dict
+function! s:app_gems() dict abort
+ if self.has('bundler') && exists('*bundler#project')
+ return bundler#project(self.path()).gems()
+ else
+ return {}
+ endif
+endfunction
+
+function! s:app_generators() dict abort
if self.cache.needs('generators')
- let generators = self.relglob("vendor/plugins/","*/generators/*")
- let generators += self.relglob("","lib/generators/*")
- call filter(generators,'v:val =~ "/$"')
- let generators += split(glob(expand("~/.rails/generators")."/*"),"\n")
- call map(generators,'s:sub(v:val,"^.*[\\\\/]generators[\\\\/]\\ze.","")')
- call map(generators,'s:sub(v:val,"[\\\\/]$","")')
- call self.cache.set('generators',generators)
+ let paths = [self.path('vendor/plugins/*'), self.path('lib'), expand("~/.rails")]
+ if !empty(self.gems())
+ let gems = values(self.gems())
+ let paths += map(values(self.gems()), 'v:val . "/lib/rails"')
+ let paths += map(values(self.gems()), 'v:val . "/lib"')
+ let builtin = []
+ else
+ let builtin = ['assets', 'controller', 'generator', 'helper', 'integration_test', 'jbuilder', 'jbuilder_scaffold_controller', 'mailer', 'migration', 'model', 'resource', 'scaffold', 'scaffold_controller', 'task']
+ endif
+ let generators = s:split(globpath(s:pathjoin(paths), 'generators/**/*_generator.rb'))
+ call map(generators, 's:sub(v:val,"^.*[\\\\/]generators[\\\\/]\\ze.","")')
+ call map(generators, 's:sub(v:val,"[\\\\/][^\\\\/]*_generator\.rb$","")')
+ call map(generators, 'tr(v:val, "/", ":")')
+ let builtin += map(filter(copy(generators), 'v:val =~# "^rails:"'), 'v:val[6:-1]')
+ call filter(generators,'v:val !~# "^rails:"')
+ call self.cache.set('generators',s:uniq(builtin + generators))
endif
- return sort(split(g:rails_generators,"\n") + self.cache.get('generators'))
+ return self.cache.get('generators')
endfunction
function! s:app_script_command(bang,...) dict
+ let msg = "rails.vim ".g:autoloaded_rails
+ if a:0 == 0 && a:bang && rails#buffer().type_name() == ''
+ echo msg." (Rails)"
+ return
+ elseif a:0 == 0 && a:bang
+ echo msg." (Rails-".rails#buffer().type_name().")"
+ return
+ endif
let str = ""
let cmd = a:0 ? a:1 : "console"
let c = 2
@@ -1509,9 +1538,6 @@ function! s:app_script_command(bang,...) dict
let str .= " " . s:rquote(a:{c})
let c += 1
endwhile
- if cmd ==# "plugin"
- call self.cache.clear('generators')
- endif
if a:bang || cmd =~# 'console'
return self.background_script_command(cmd.str)
else
@@ -1523,8 +1549,13 @@ function! s:app_runner_command(count,args) dict
if a:count == -2
return self.script_command(a:bang,"runner",a:args)
else
- let str = self.ruby_shell_command('-r./config/boot -e "require '."'commands/runner'".'" '.s:rquote(a:args))
- let res = s:sub(system(str),'\n$','')
+ let str = self.script_shell_command('runner '.s:rquote(a:args))
+ call s:push_chdir(1)
+ try
+ let res = s:sub(system(str),'\n$','')
+ finally
+ call s:pop_command()
+ endtry
if a:count < 0
echo res
else
@@ -1549,11 +1580,13 @@ endfunction
function! s:app_server_command(bang,arg) dict
let port = matchstr(a:arg,'\%(-p\|--port=\=\)\s*\zs\d\+')
- if port == ''
+ if empty(port)
let port = "3000"
endif
- " TODO: Extract bind argument
- let bind = "0.0.0.0"
+ let bind = matchstr(a:arg,'\%(-b\|--binding=\=\)\s*\zs\S\+')
+ if empty(bind)
+ let bind = "0.0.0.0"
+ endif
if a:bang && executable("ruby")
let pid = s:getpidfor(bind,port)
if pid =~ '^\d\+$'
@@ -1569,12 +1602,7 @@ function! s:app_server_command(bang,arg) dict
return
endif
endif
- if has_key(self,'options') && has_key(self.options,'gnu_screen')
- let screen = self.options.gnu_screen
- else
- let screen = g:rails_gnu_screen
- endif
- if has("win32") || has("win64") || (exists("$STY") && !has("gui_running") && screen && executable("screen")) || (exists("$TMUX") && !has("gui_running") && screen && executable("tmux"))
+ if has("win32") || has("win64") || (exists("$STY") && !has("gui_running") && executable("screen")) || (exists("$TMUX") && !has("gui_running") && executable("tmux"))
call self.background_script_command('server '.a:arg)
else
" --daemon would be more descriptive but lighttpd does not support it
@@ -1584,54 +1612,43 @@ function! s:app_server_command(bang,arg) dict
return ''
endfunction
-function! s:app_destroy_command(bang,...) dict
- if a:0 == 0
- return self.execute_script_command('destroy')
- elseif a:0 == 1
- return self.execute_script_command('destroy '.s:rquote(a:1))
- endif
- let str = ""
- let c = 1
- while c <= a:0
- let str .= " " . s:rquote(a:{c})
- let c += 1
- endwhile
- call self.execute_script_command('destroy'.str)
- call self.cache.clear('user_classes')
- return ''
+function! s:color_efm(pre, before, after)
+ return a:pre . '%\S%# %#' . a:before . "\e[0m %#" . a:after . ',' .
+ \ a:pre . ' %#'.a:before.' %#'.a:after . ','
endfunction
-function! s:app_generate_command(bang,...) dict
- if a:0 == 0
- return self.execute_script_command('generate')
- elseif a:0 == 1
- return self.execute_script_command('generate '.s:rquote(a:1))
- endif
+let s:efm_generate =
+ \ s:color_efm('%-G', 'invoke', '%f') .
+ \ s:color_efm('%-G', 'conflict', '%f') .
+ \ s:color_efm('%-G', 'run', '%f') .
+ \ s:color_efm('Overwrite%.%#', '%m', '%f') .
+ \ s:color_efm('', '%m', '%f') .
+ \ '%-G%.%#'
+
+function! s:app_generator_command(bang,...) dict
+ call self.cache.clear('user_classes')
+ call self.cache.clear('features')
let cmd = join(map(copy(a:000),'s:rquote(v:val)'),' ')
- if cmd !~ '-p\>' && cmd !~ '--pretend\>'
- let execstr = self.script_shell_command('generate '.cmd.' -p -f')
- let res = system(execstr)
- let g:res = res
- let junk = '\%(\e\[[0-9;]*m\)\='
- let file = matchstr(res,junk.'\s\+\%(create\|force\)'.junk.'\s\+\zs\f\+\.rb\ze\n')
- if file == ""
- let file = matchstr(res,junk.'\s\+\%(identical\)'.junk.'\s\+\zs\f\+\.rb\ze\n')
- endif
- else
- let file = ""
- endif
- if !self.execute_script_command('generate '.cmd) && file != ''
- call self.cache.clear('user_classes')
- call self.cache.clear('features')
- if file =~ '^db/migrate/\d\d\d\d'
- let file = get(self.relglob('',s:sub(file,'\d+','[0-9]*[0-9]')),-1,file)
+ let old_makeprg = &l:makeprg
+ let old_errorformat = &l:errorformat
+ try
+ let &l:makeprg = self.script_shell_command(cmd)
+ let &l:errorformat = s:efm_generate
+ call s:push_chdir(1)
+ if a:bang
+ make!
+ else
+ make
endif
- edit `=self.path(file)`
- endif
+ finally
+ call s:pop_command()
+ let &l:errorformat = old_errorformat
+ let &l:makeprg = old_makeprg
+ endtry
return ''
endfunction
-call s:add_methods('app', ['generators','script_command','runner_command','server_command','destroy_command','generate_command'])
+call s:add_methods('app', ['gems','generators','script_command','runner_command','server_command','generator_command'])
function! s:Complete_script(ArgLead,CmdLine,P)
let cmd = s:sub(a:CmdLine,'^\u\w*\s+','')
@@ -1639,10 +1656,6 @@ function! s:Complete_script(ArgLead,CmdLine,P)
return []
elseif cmd =~# '^\w*$'
return s:completion_filter(rails#app().relglob("script/","**/*"),a:ArgLead)
- elseif cmd =~# '^\%(plugin\)\s\+'.a:ArgLead.'$'
- return s:completion_filter(["discover","list","install","update","remove","source","unsource","sources"],a:ArgLead)
- elseif cmd =~# '\%(plugin\)\s\+\%(install\|remove\)\s\+'.a:ArgLead.'$' || cmd =~ '\%(generate\|destroy\)\s\+plugin\s\+'.a:ArgLead.'$'
- return s:pluginList(a:ArgLead,a:CmdLine,a:P)
elseif cmd =~# '^\%(generate\|destroy\)\s\+'.a:ArgLead.'$'
return s:completion_filter(rails#app().generators(),a:ArgLead)
elseif cmd =~# '^\%(generate\|destroy\)\s\+\w\+\s\+'.a:ArgLead.'$'
@@ -1654,21 +1667,17 @@ function! s:Complete_script(ArgLead,CmdLine,P)
elseif target ==# 'helper'
return s:autocamelize(rails#app().relglob('app/helpers/','**/*','_helper.rb'),a:ArgLead)
elseif target ==# 'integration_test' || target ==# 'integration_spec' || target ==# 'feature'
- return s:integrationtestList(a:ArgLead,"","")
- elseif target ==# 'metal'
- return s:autocamelize(rails#app().relglob('app/metal/','**/*','.rb'),a:ArgLead)
+ return s:autocamelize(
+ \ rails#app().relglob('test/integration/','**/*','_test.rb') +
+ \ rails#app().relglob('spec/features/', '**/*', '_spec.rb') +
+ \ rails#app().relglob('spec/requests/', '**/*', '_spec.rb') +
+ \ rails#app().relglob('features/', '**/*', '.feature'), a:ArgLead)
elseif target ==# 'migration' || target ==# 'session_migration'
return s:migrationList(a:ArgLead,"","")
+ elseif target ==# 'mailer'
+ return s:mailerList(a:ArgLead,"","")
elseif target =~# '^\w*\%(model\|resource\)$' || target =~# '\w*scaffold\%(_controller\)\=$' || target ==# 'mailer'
- return s:modelList(a:ArgLead,"","")
- elseif target ==# 'observer'
- let observers = rails#app().relglob("app/models/","**/*","_observer.rb")
- let models = s:modelList("","","")
- if cmd =~# '^destroy\>'
- let models = []
- endif
- call filter(models,'index(observers,v:val) < 0')
- return s:completion_filter(observers + models,a:ArgLead)
+ return s:completion_filter(rails#app().relglob('app/models/','**/*','.rb'), a:ArgLead)
else
return []
endif
@@ -1719,28 +1728,21 @@ endfunction
" Navigation {{{1
function! s:BufNavCommands()
+ command! -buffer -bar -nargs=? -complete=customlist,s:Complete_cd Cd :cd `=rails#app().path(<q-args>)`
+ command! -buffer -bar -nargs=? -complete=customlist,s:Complete_cd Lcd :lcd `=rails#app().path(<q-args>)`
command! -buffer -bar -nargs=? -complete=customlist,s:Complete_cd Rcd :cd `=rails#app().path(<q-args>)`
command! -buffer -bar -nargs=? -complete=customlist,s:Complete_cd Rlcd :lcd `=rails#app().path(<q-args>)`
- command! -buffer -bar -nargs=* -count=1 -complete=customlist,s:Complete_find Rfind :call s:warn( 'Rfind has been deprecated in favor of :1R or :find' )|call s:Find(<count>,'<bang>' ,<f-args>)
- command! -buffer -bar -nargs=* -count=1 -complete=customlist,s:Complete_find REfind :call s:warn('REfind has been deprecated in favor of :1RE or :find')|call s:Find(<count>,'E<bang>',<f-args>)
- command! -buffer -bar -nargs=* -count=1 -complete=customlist,s:Complete_find RSfind :call s:warn('RSfind has been deprecated in favor of :1RS or :find')|call s:Find(<count>,'S<bang>',<f-args>)
- command! -buffer -bar -nargs=* -count=1 -complete=customlist,s:Complete_find RVfind :call s:warn('RVfind has been deprecated in favor of :1RV or :find')|call s:Find(<count>,'V<bang>',<f-args>)
- command! -buffer -bar -nargs=* -count=1 -complete=customlist,s:Complete_find RTfind :call s:warn('RTfind has been deprecated in favor of :1RT or :find')|call s:Find(<count>,'T<bang>',<f-args>)
- command! -buffer -bar -nargs=* -count=1 -complete=customlist,s:Complete_find Rsfind :call s:warn('Rsfind has been deprecated in favor of :1RS or :sfind')|<count>RSfind<bang> <args>
- command! -buffer -bar -nargs=* -count=1 -complete=customlist,s:Complete_find Rtabfind :call s:warn('Rtabfind has been deprecated in favor of :1RT or :tabfind')|<count>RTfind<bang> <args>
- command! -buffer -bar -nargs=* -bang -complete=customlist,s:Complete_edit Redit :call s:warn( 'Redit has been deprecated in favor of :R')|call s:Edit(<count>,'<bang>' ,<f-args>)
- command! -buffer -bar -nargs=* -bang -complete=customlist,s:Complete_edit REedit :call s:warn('REedit has been deprecated in favor of :RE')|call s:Edit(<count>,'E<bang>',<f-args>)
- command! -buffer -bar -nargs=* -bang -complete=customlist,s:Complete_edit RSedit :call s:warn('RSedit has been deprecated in favor of :RS')|call s:Edit(<count>,'S<bang>',<f-args>)
- command! -buffer -bar -nargs=* -bang -complete=customlist,s:Complete_edit RVedit :call s:warn('RVedit has been deprecated in favor of :RV')|call s:Edit(<count>,'V<bang>',<f-args>)
- command! -buffer -bar -nargs=* -bang -complete=customlist,s:Complete_edit RTedit :call s:warn('RTedit has been deprecated in favor of :RT')|call s:Edit(<count>,'T<bang>',<f-args>)
- command! -buffer -bar -nargs=* -range=0 -complete=customlist,s:Complete_edit RDedit :call s:warn('RDedit has been deprecated in favor of :RD')|call s:Edit(<count>,'<line1>D<bang>',<f-args>)
command! -buffer -bar -nargs=* -range=0 -complete=customlist,s:Complete_related A :call s:Alternate('<bang>', <line1>,<line2>,<count>,<f-args>)
command! -buffer -bar -nargs=* -range=0 -complete=customlist,s:Complete_related AE :call s:Alternate('E<bang>',<line1>,<line2>,<count>,<f-args>)
command! -buffer -bar -nargs=* -range=0 -complete=customlist,s:Complete_related AS :call s:Alternate('S<bang>',<line1>,<line2>,<count>,<f-args>)
command! -buffer -bar -nargs=* -range=0 -complete=customlist,s:Complete_related AV :call s:Alternate('V<bang>',<line1>,<line2>,<count>,<f-args>)
command! -buffer -bar -nargs=* -range=0 -complete=customlist,s:Complete_related AT :call s:Alternate('T<bang>',<line1>,<line2>,<count>,<f-args>)
command! -buffer -bar -nargs=* -range=0 -complete=customlist,s:Complete_related AD :call s:Alternate('D<bang>',<line1>,<line2>,<count>,<f-args>)
- command! -buffer -bar -nargs=* -range=0 -complete=customlist,s:Complete_related AN :call s:Related('<bang>' ,<line1>,<line2>,<count>,<f-args>)
+ command! -buffer -bar -nargs=* -range=0 -complete=customlist,s:Complete_related E :call s:Related('E<bang>',<line1>,<line2>,<count>,<f-args>)
+ command! -buffer -bar -nargs=* -range=0 -complete=customlist,s:Complete_related S :call s:Related('S<bang>',<line1>,<line2>,<count>,<f-args>)
+ command! -buffer -bar -nargs=* -range=0 -complete=customlist,s:Complete_related V :call s:Related('V<bang>',<line1>,<line2>,<count>,<f-args>)
+ command! -buffer -bar -nargs=* -range=0 -complete=customlist,s:Complete_related T :call s:Related('T<bang>',<line1>,<line2>,<count>,<f-args>)
+ command! -buffer -bar -nargs=* -range=0 -complete=customlist,s:Complete_related D :call s:Related('D<bang>',<line1>,<line2>,<count>,<f-args>)
command! -buffer -bar -nargs=* -range=0 -complete=customlist,s:Complete_related R :call s:Related('<bang>' ,<line1>,<line2>,<count>,<f-args>)
command! -buffer -bar -nargs=* -range=0 -complete=customlist,s:Complete_related RE :call s:Related('E<bang>',<line1>,<line2>,<count>,<f-args>)
command! -buffer -bar -nargs=* -range=0 -complete=customlist,s:Complete_related RS :call s:Related('S<bang>',<line1>,<line2>,<count>,<f-args>)
@@ -1917,13 +1919,13 @@ function! s:RailsFind()
let res = s:findamethod('require','\1')
if res != ""|return res.(fnamemodify(res,':e') == '' ? '.rb' : '')|endif
- let res = s:findamethod('belongs_to\|has_one\|composed_of\|validates_associated\|scaffold','app/models/\1.rb')
+ let res = s:findamethod('belongs_to\|has_one\|embedded_in\|embeds_one\|composed_of\|validates_associated\|scaffold','app/models/\1.rb')
if res != ""|return res|endif
- let res = rails#singularize(s:findamethod('has_many\|has_and_belongs_to_many','app/models/\1'))
+ let res = rails#singularize(s:findamethod('has_many\|has_and_belongs_to_many\|embeds_many','app/models/\1'))
if res != ""|return res.".rb"|endif
- let res = rails#singularize(s:findamethod('create_table\|change_table\|drop_table\|add_column\|rename_column\|remove_column\|add_index','app/models/\1'))
+ let res = rails#singularize(s:findamethod('create_table\|change_table\|drop_table\|rename_table\|\%(add\|remove\)_\%(column\|index\|timestamps\|reference\|belongs_to\)\|rename_column\|remove_columns\|rename_index','app/models/\1'))
if res != ""|return res.".rb"|endif
let res = rails#singularize(s:findasymbol('through','app/models/\1'))
@@ -2155,27 +2157,89 @@ function! s:RailsIncludefind(str,...)
endfunction
" }}}1
-" File Finders {{{1
+" Projection Commands {{{1
function! s:addfilecmds(type)
let l = s:sub(a:type,'^.','\l&')
- let cmds = 'ESVTD '
- let cmd = ''
- while cmds != ''
+ for prefix in ['E', 'S', 'V', 'T', 'D', 'R', 'RE', 'RS', 'RV', 'RT', 'RD']
let cplt = " -complete=customlist,".s:sid.l."List"
- exe "command! -buffer -bar ".(cmd == 'D' ? '-range=0 ' : '')."-nargs=*".cplt." R".cmd.l." :execute s:".l.'Edit("'.(cmd == 'D' ? '<line1>' : '').cmd.'<bang>",<f-args>)'
- let cmd = strpart(cmds,0,1)
- let cmds = strpart(cmds,1)
- endwhile
+ exe "command! -buffer -bar ".(prefix =~# 'D' ? '-range=0 ' : '')."-nargs=*".cplt." ".prefix.l." :execute s:".l.'Edit("'.(prefix =~# 'D' ? '<line1>' : '').s:sub(prefix, '^R', '').'<bang>",<f-args>)'
+ endfor
endfunction
-function! s:BufFinderCommands()
- command! -buffer -bar -nargs=+ Rnavcommand :call s:Navcommand(<bang>0,<f-args>)
- call s:define_navcommand('helper', {'prefix': 'app/helpers/', 'suffix': '_helper.rb', 'default': 'controller'})
- call s:define_navcommand('initializer', {'prefix': 'config/initializers/', 'default': '../routes'})
- call s:define_navcommand('metal', {'prefix': 'app/metal/', 'default': '../boot'})
- call s:define_navcommand('observer', {'prefix': 'app/observers/', 'suffix': '_observer.rb', 'default': 'model'})
- call s:addfilecmds("model")
+function! s:BufProjectionCommands()
+ call s:define_navcommand('environment', {
+ \ 'prefix': 'config/environments/',
+ \ 'default': ['config/application.rb', 'config/environment.rb']})
+ call s:define_navcommand('helper', {
+ \ 'prefix': 'app/helpers/',
+ \ 'suffix': '_helper.rb',
+ \ 'template': "module %SHelper\nend",
+ \ 'affinity': 'controller'})
+ call s:define_navcommand('initializer', {
+ \ 'prefix': 'config/initializers/',
+ \ 'default': ['config/routes.rb']})
+ call s:define_navcommand('lib', {
+ \ 'format': 'lib/%s.rb',
+ \ 'default': ['Gemfile']})
+ call s:define_navcommand('model', {
+ \ 'prefix': 'app/models/',
+ \ 'suffix': '.rb',
+ \ 'template': "class %S\nend",
+ \ 'affinity': 'model'})
+ call s:define_navcommand('task', {
+ \ 'format': 'lib/tasks/%s.rake',
+ \ 'default': ['Rakefile']})
+ let tests = filter([
+ \ ['test', 'test/unit/%s_test.rb', 'test/functional/%s_test.rb'],
+ \ ['test', 'test/models/%s_test.rb', 'test/controllers/%s_test.rb'],
+ \ ['test', 'test/helpers/%s_test.rb', 'test/mailers/%s_test.rb'],
+ \ ['spec', 'spec/models/%s_spec.rb', 'spec/controllers/%s_spec.rb'],
+ \ ['spec', 'spec/helpers/%s_spec.rb', 'spec/mailers/%s_spec.rb']],
+ \ 'rails#app().has(v:val[0])')
+ if !empty(tests)
+ call s:define_navcommand('unit test', {
+ \ 'format': map(copy(tests), 'v:val[1]'),
+ \ 'template': {
+ \ 'test/unit/': "require 'test_helper'\n\nclass %STest < ActiveSupport::TestCase\nend",
+ \ 'test/models/': "require 'test_helper'\n\nclass %STest < ActiveSupport::TestCase\nend",
+ \ 'test/helpers/': "require 'test_helper'\n\nclass %STest < ActionView::TestCase\nend",
+ \ 'spec/models/': "require 'spec_helper'\n\ndescribe %S do\nend",
+ \ 'spec/helpers/': "require 'spec_helper'\n\ndescribe %S do\nend"},
+ \ 'affinity': 'model'})
+ call s:define_navcommand('functional test', {
+ \ 'format': map(copy(tests), 'v:val[2]'),
+ \ 'template': {
+ \ 'test/functional/': "require 'test_helper'\n\nclass %STest < ActionController::TestCase\nend",
+ \ 'test/controllers/': "require 'test_helper'\n\nclass %STest < ActionController::TestCase\nend",
+ \ 'test/mailers/': "require 'test_helper'\n\nclass %STest < ActionMailer::TestCase\nend",
+ \ 'spec/models/': "require 'spec_helper'\n\ndescribe %S do\nend",
+ \ 'spec/helpers/': "require 'spec_helper'\n\ndescribe %S do\nend"},
+ \ 'affinity': 'controller'})
+ endif
+ let integration_tests = map(filter([
+ \ ['test', 'test/integration/%s_test.rb'],
+ \ ['spec', 'spec/features/%s_spec.rb'],
+ \ ['spec', 'spec/requests/%s_spec.rb'],
+ \ ['spec', 'spec/integration/%s_spec.rb'],
+ \ ['cucumber', 'features/%s.feature'],
+ \ ['turnip', 'spec/acceptance/%s.feature']],
+ \ 'rails#app().has(v:val[0])'), 'v:val[1]')
+ if !empty(integration_tests)
+ call s:define_navcommand('integration test', {
+ \ 'format': integration_tests,
+ \ 'template': {
+ \ 'test/integration/': "require 'test_helper'\n\nclass %STest < ActionDispatch::IntegrationTest\nend",
+ \ 'spec/requests/': "require 'spec_helper'\n\ndescribe \"%h\" do\nend",
+ \ 'spec/features/': "require 'spec_helper'\n\ndescribe \"%h\" do\nend",
+ \ 'spec/integration/': "require 'spec_helper'\n\ndescribe \"%h\" do\nend",
+ \ 'features/': "Feature: %h",
+ \ 'spec/acceptance/': "Feature: %h"},
+ \ 'default': [
+ \ 'test/test_helper.rb',
+ \ 'features/support/env.rb',
+ \ 'spec/spec_helper.rb']})
+ endif
call s:addfilecmds("view")
call s:addfilecmds("controller")
call s:addfilecmds("mailer")
@@ -2184,30 +2248,15 @@ function! s:BufFinderCommands()
call s:addfilecmds("layout")
call s:addfilecmds("fixtures")
call s:addfilecmds("locale")
- if rails#app().has('test') || rails#app().has('spec')
- call s:addfilecmds("unittest")
- call s:addfilecmds("functionaltest")
- endif
- if rails#app().has('test') || rails#app().has('spec') || rails#app().has('cucumber')
- call s:addfilecmds("integrationtest")
- endif
if rails#app().has('spec')
call s:addfilecmds("spec")
endif
call s:addfilecmds("stylesheet")
call s:addfilecmds("javascript")
call s:addfilecmds("plugin")
- call s:addfilecmds("task")
- call s:addfilecmds("lib")
- call s:addfilecmds("environment")
- for [name, command] in items(rails#app().config('classifications'))
+ for [name, command] in items(rails#app().projections())
call s:define_navcommand(name, command)
endfor
- if exists('b:rails_file_types')
- for [name, command] in items(b:rails_file_types)
- call s:define_navcommand(name, command)
- endfor
- endif
endfunction
function! s:completion_filter(results,A)
@@ -2215,6 +2264,9 @@ function! s:completion_filter(results,A)
call filter(results,'v:val !~# "\\~$"')
let filtered = filter(copy(results),'s:startswith(v:val,a:A)')
if !empty(filtered) | return filtered | endif
+ let prefix = s:sub(a:A,'(.*[/]|^)','&_')
+ let filtered = filter(copy(results),"s:startswith(v:val,prefix)")
+ if !empty(filtered) | return filtered | endif
let regex = s:gsub(a:A,'[^/]','[&].*')
let filtered = filter(copy(results),'v:val =~# "^".regex')
if !empty(filtered) | return filtered | endif
@@ -2304,12 +2356,6 @@ function! s:javascriptList(A,L,P)
return s:completion_filter(list,a:A)
endfunction
-function! s:modelList(A,L,P)
- let models = rails#app().relglob("app/models/","**/*",".rb")
- call filter(models,'v:val !~# "_observer$"')
- return s:autocamelize(models,a:A)
-endfunction
-
function! s:fixturesList(A,L,P)
return s:completion_filter(
\ rails#app().relglob('test/fixtures/', '**/*') +
@@ -2342,50 +2388,6 @@ function! s:schemaList(A,L,P)
return s:autocamelize(tables, a:A)
endfunction
-function! s:unittestList(A,L,P)
- let found = []
- if rails#app().has('test')
- let found += rails#app().relglob("test/unit/","**/*","_test.rb")
- endif
- if rails#app().has('spec')
- let found += rails#app().relglob("spec/models/","**/*","_spec.rb")
- endif
- return s:autocamelize(found,a:A)
-endfunction
-
-function! s:functionaltestList(A,L,P)
- let found = []
- if rails#app().has('test')
- let found += rails#app().relglob("test/functional/","**/*","_test.rb")
- endif
- if rails#app().has('spec')
- let found += rails#app().relglob("spec/controllers/","**/*","_spec.rb")
- let found += rails#app().relglob("spec/mailers/","**/*","_spec.rb")
- endif
- return s:autocamelize(found,a:A)
-endfunction
-
-function! s:integrationtestList(A,L,P)
- if a:A =~# '^\u'
- return s:autocamelize(rails#app().relglob("test/integration/","**/*","_test.rb"),a:A)
- endif
- let found = []
- if rails#app().has('test')
- let found += rails#app().relglob("test/integration/","**/*","_test.rb")
- endif
- if rails#app().has('spec')
- let found += rails#app().relglob("spec/requests/","**/*","_spec.rb")
- let found += rails#app().relglob("spec/integration/","**/*","_spec.rb")
- endif
- if rails#app().has('cucumber')
- let found += rails#app().relglob("features/","**/*",".feature")
- endif
- if rails#app().has('turnip')
- let found += rails#app().relglob("spec/acceptance/","**/*",".feature")
- endif
- return s:completion_filter(found,a:A)
-endfunction
-
function! s:specList(A,L,P)
return s:completion_filter(rails#app().relglob("spec/","**/*","_spec.rb"),a:A)
endfunction
@@ -2398,29 +2400,6 @@ function! s:pluginList(A,L,P)
endif
endfunction
-" Task files, not actual rake tasks
-function! s:taskList(A,L,P)
- let all = rails#app().relglob("lib/tasks/","**/*",".rake")
- if RailsFilePath() =~ '\<vendor/plugins/.'
- let path = s:sub(RailsFilePath(),'<vendor/plugins/[^/]*/\zs.*','')
- let all = rails#app().relglob(path."tasks/","**/*",".rake")+rails#app().relglob(path."lib/tasks/","**/*",".rake")+all
- endif
- return s:autocamelize(all,a:A)
-endfunction
-
-function! s:libList(A,L,P)
- let all = rails#app().relglob('lib/',"**/*",".rb")
- if RailsFilePath() =~ '\<vendor/plugins/.'
- let path = s:sub(RailsFilePath(),'<vendor/plugins/[^/]*/\zs.*','lib/')
- let all = rails#app().relglob(path,"**/*",".rb") + all
- endif
- return s:autocamelize(all,a:A)
-endfunction
-
-function! s:environmentList(A,L,P)
- return s:completion_filter(rails#app().relglob("config/environments/","**/*",".rb"),a:A)
-endfunction
-
function! s:Navcommand(bang,...)
let command = {'prefix': []}
let i = 0
@@ -2448,22 +2427,36 @@ function! s:Navcommand(bang,...)
return s:define_navcommand(name, command)
endfunction
-function! s:define_navcommand(name, command) abort
- let command = extend({'default': '', 'glob': '**/*'}, a:command)
- let command.prefix = s:split(get(command, 'prefix', []))
- let command.suffix = s:split(get(command, 'suffix', ['.rb']))
- if has_key(command, 'affinity') && command.default ==# ''
- let command.default = command.affinity . '()'
+function! s:define_navcommand(name, projection) abort
+ let projection = extend({'default': '', 'glob': '**/*'}, a:projection)
+ if !has_key(projection, 'format')
+ let projection.prefix = s:split(get(projection, 'prefix', []))
+ let projection.suffix = s:split(get(projection, 'suffix', ['.rb']))
+ if empty(projection.prefix)
+ return
+ endif
endif
- if a:name !~# '^[a-z]\+$'
- return s:error("E182: Invalid command name")
+ if has_key(projection, 'affinity') && empty(projection.default)
+ let projection.default = projection.affinity . '()'
+ endif
+ if get(projection, 'command', 1) =~# '^0\=$'
+ return
+ endif
+ if type(get(projection, 'command', 1)) ==# type('')
+ let name = projection.command
+ else
+ let name = s:gsub(a:name, '[[:space:][:punct:]]', '')
+ endif
+ if name !~# '^[a-z]\+$'
+ return s:error("E182: Invalid command name ".name)
endif
- for type in ['E', 'S', 'V', 'T', 'D', '']
- exe 'command! -buffer -bar -bang -nargs=* '
+ for prefix in ['E', 'S', 'V', 'T', 'D', 'R', 'RE', 'RS', 'RV', 'RT', 'RD']
+ exe 'command! -buffer -bar -bang -nargs=* ' .
+ \ (prefix =~# 'D' ? '-range=0 ' : '') .
\ '-complete=customlist,'.s:sid.'CommandList ' .
- \ 'R' . type . a:name . ' :execute s:CommandEdit(' .
- \ string(type . "<bang>") . ',' .
- \ string(a:name) . ',' . string(command) . ',<f-args>)'
+ \ prefix . name . ' :execute s:CommandEdit(' .
+ \ string((prefix =~# 'D' ? '<line1>' : '') . s:sub(prefix, '^R', '') . "<bang>") . ',' .
+ \ string(a:name) . ',' . string(projection) . ',<f-args>)'
endfor
endfunction
@@ -2472,16 +2465,15 @@ function! s:CommandList(A,L,P)
exe cmd." &"
let command = s:last_options
let matches = []
- for prefix in command.prefix
- for suffix in command.suffix
- let matches += rails#app().relglob(prefix, command.glob, suffix)
- endfor
+ for [prefix, suffix] in s:projection_pairs(command)
+ let results = rails#app().relglob(prefix, command.glob, suffix)
+ if suffix =~# '\.rb$' && a:A =~# '^\u'
+ let matches += map(results, 'rails#camelize(v:val)')
+ else
+ let matches += results
+ endif
endfor
- if command.suffix == ['.rb']
- return s:autocamelize(matches, a:A)
- else
- return s:completion_filter(matches, a:A)
- endif
+ return s:completion_filter(matches, a:A)
endfunction
function! s:CommandEdit(cmd, name, options, ...)
@@ -2558,6 +2550,19 @@ call s:add_methods('app', ['migration'])
function! s:migrationEdit(cmd,...)
let cmd = s:findcmdfor(a:cmd)
let arg = a:0 ? a:1 : ''
+ if arg =~# '!'
+ " This will totally miss the mark if we cross into or out of DST.
+ let ts = localtime()
+ let local = strftime('%H', ts) * 3600 + strftime('%M', ts) * 60 + strftime('%S')
+ let offset = local - ts % 86400
+ if offset <= -12 * 60 * 60
+ let offset += 86400
+ endif
+ return rails#buffer().open_command(a:cmd, strftime('%Y%m%d%H%M%S', ts - offset).'_'.arg, 'migration', {
+ \ 'template': 'class ' . rails#camelize(matchstr(arg, '[^!]*')) . " < ActiveRecord::Migration\nend",
+ \ 'prefix': 'db/migrate/',
+ \ 'suffix': '.rb'})
+ endif
let migr = arg == "." ? "db/migrate" : rails#app().migration(arg)
if migr != ''
return s:findedit(cmd,migr)
@@ -2601,17 +2606,11 @@ function! s:localeEdit(cmd,...)
if c =~# '\.'
return s:edit(a:cmd,rails#app().find_file(c,'config/locales',[],'config/locales/'.c))
else
- return s:findedit(a:cmd,rails#app().find_file(c,'config/locales',['.yml','.rb'],'config/locales/'.c))
+ return rails#buffer().open_command(a:cmd, c, 'locale', {
+ \ 'format': ['config/locales/%s.yml', 'config/locales/%s.rb']})
endif
endfunction
-function! s:modelEdit(cmd,...)
- return rails#buffer().open_command(a:cmd, a:0 ? a:1 : '', 'model', {
- \ 'prefix': 'app/models/',
- \ 'suffix': '.rb',
- \ 'affinity': 'model'})
-endfunction
-
function! s:dotcmp(i1, i2)
return strlen(s:gsub(a:i1,'[^.]', '')) - strlen(s:gsub(a:i2,'[^.]', ''))
endfunc
@@ -2710,18 +2709,24 @@ endfunction
function! s:controllerEdit(cmd,...)
let suffix = '.rb'
+ let template = "class %S < ApplicationController\nend"
if a:0 == 0
let controller = s:controller(1)
if rails#buffer().type_name() =~# '^view\%(-layout\|-partial\)\@!'
- let suffix .= '#'.expand('%:t:r')
+ let jump = '#'.expand('%:t:r')
+ else
+ let jump = ''
endif
else
- let controller = a:1
+ let controller = matchstr(a:1, '[^#!]*')
+ let jump = matchstr(a:1, '[#!].*')
endif
if rails#app().has_file("app/controllers/".controller."_controller.rb") || !rails#app().has_file("app/controllers/".controller.".rb")
+ let template = "class %SController < ApplicationController\nend"
let suffix = "_controller".suffix
endif
- return rails#buffer().open_command(a:cmd, controller, 'controller', {
+ return rails#buffer().open_command(a:cmd, controller . jump, 'controller', {
+ \ 'template': template,
\ 'prefix': 'app/controllers/',
\ 'suffix': suffix})
endfunction
@@ -2730,6 +2735,7 @@ function! s:mailerEdit(cmd,...)
return rails#buffer().open_command(a:cmd, a:0 ? a:1 : '', 'mailer', {
\ 'prefix': ['app/mailers/', 'app/models/'],
\ 'suffix': '.rb',
+ \ 'template': "class %S < ActionMailer::Base\nend",
\ 'affinity': 'controller'})
endfunction
@@ -2767,93 +2773,13 @@ function! s:javascriptEdit(cmd,...)
endif
endfunction
-function! s:unittestEdit(cmd,...)
- let f = rails#underscore(a:0 ? matchstr(a:1,'[^!#:]*') : s:model(1))
- let jump = a:0 ? matchstr(a:1,'[!#:].*') : ''
- if jump =~ '!'
- let cmd = s:editcmdfor(a:cmd)
- else
- let cmd = s:findcmdfor(a:cmd)
- endif
- let mapping = {'test': ['test/unit/','_test.rb'], 'spec': ['spec/models/','_spec.rb']}
- let tests = map(filter(rails#app().test_suites(),'has_key(mapping,v:val)'),'get(mapping,v:val)')
- if empty(tests)
- let tests = [mapping['test']]
- endif
- for [prefix, suffix] in tests
- if !a:0 && rails#buffer().type_name('model-aro') && f != '' && f !~# '_observer$'
- if rails#app().has_file(prefix.f.'_observer'.suffix)
- return s:findedit(cmd,prefix.f.'_observer'.suffix.jump)
- endif
- endif
- endfor
- for [prefix, suffix] in tests
- if rails#app().has_file(prefix.f.suffix)
- return s:findedit(cmd,prefix.f.suffix.jump)
- endif
- endfor
- return s:EditSimpleRb(a:cmd,"unittest",f.jump,tests[0][0],tests[0][1],1)
-endfunction
-
-function! s:functionaltestEdit(cmd,...)
- let f = rails#underscore(a:0 ? matchstr(a:1,'[^!#:]*') : s:controller(1))
- let jump = a:0 ? matchstr(a:1,'[!#:].*') : ''
- if jump =~ '!'
- let cmd = s:editcmdfor(a:cmd)
- else
- let cmd = s:findcmdfor(a:cmd)
- endif
- let mapping = {'test': [['test/functional/'],['_test.rb','_controller_test.rb']], 'spec': [['spec/controllers/','spec/mailers/'],['_spec.rb','_controller_spec.rb']]}
- let tests = map(filter(rails#app().test_suites(),'has_key(mapping,v:val)'),'get(mapping,v:val)')
- if empty(tests)
- let tests = [mapping[tests]]
- endif
- for [prefixes, suffixes] in tests
- for prefix in prefixes
- for suffix in suffixes
- if rails#app().has_file(prefix.f.suffix)
- return s:findedit(cmd,prefix.f.suffix.jump)
- endif
- endfor
- endfor
- endfor
- return s:EditSimpleRb(a:cmd,"functionaltest",f.jump,tests[0][0][0],tests[0][1][0],1)
-endfunction
-
-function! s:integrationtestEdit(cmd,...)
- if !a:0
- return s:EditSimpleRb(a:cmd,"integrationtest","test/test_helper\nfeatures/support/env\nspec/spec_helper","",".rb")
- endif
- let f = rails#underscore(matchstr(a:1,'[^!#:]*'))
- let jump = matchstr(a:1,'[!#:].*')
- if jump =~ '!'
- let cmd = s:editcmdfor(a:cmd)
- else
- let cmd = s:findcmdfor(a:cmd)
- endif
- let tests = [['test/integration/','_test.rb'], ['spec/requests/','_spec.rb'], ['spec/integration/','_spec.rb'], ['features/','.feature'], ['spec/acceptance/','.feature']]
- call filter(tests, 'isdirectory(rails#app().path(v:val[0]))')
- if empty(tests)
- let tests = [['test/integration/','_test.rb']]
- endif
- for [prefix, suffix] in tests
- if rails#app().has_file(prefix.f.suffix)
- return s:findedit(cmd,prefix.f.suffix.jump)
- elseif rails#app().has_file(prefix.rails#underscore(f).suffix)
- return s:findedit(cmd,prefix.rails#underscore(f).suffix.jump)
- endif
- endfor
- return s:EditSimpleRb(a:cmd,"integrationtest",f.jump,tests[0][0],tests[0][1],1)
-endfunction
-
-function! s:specEdit(cmd,...)
- if a:0
- return rails#buffer().open_command(a:cmd, a:1, 'spec', {
- \ 'prefix': 'spec/',
- \ 'suffix': '_spec.rb'})
- else
- return s:EditSimpleRb(a:cmd,"spec","spec_helper","spec/",".rb")
- endif
+function! s:specEdit(cmd,...) abort
+ let describe = s:sub(s:sub(rails#camelize(a:0 ? a:1 : ''), '^[^:]*::', ''), '!.*', '')
+ return rails#buffer().open_command(a:cmd, a:0 ? a:1 : '', 'spec', {
+ \ 'prefix': 'spec/',
+ \ 'suffix': '_spec.rb',
+ \ 'template': "require 'spec_helper'\n\ndescribe ".describe." do\nend",
+ \ 'default': ['spec/spec_helper.rb']})
endfunction
function! s:pluginEdit(cmd,...)
@@ -2877,48 +2803,9 @@ function! s:pluginEdit(cmd,...)
return s:findedit(cmd,"vendor/plugins/".a:1."\nvendor/plugins/".plugin."/".a:1)
endif
else
- return s:findedit(a:cmd,"Gemfile")
- endif
-endfunction
-
-function! s:taskEdit(cmd,...)
- let plugin = ""
- let extra = []
- if RailsFilePath() =~ '\<vendor/plugins/.'
- let plugin = matchstr(RailsFilePath(),'\<vendor/plugins/[^/]*')
- let extra = [plugin."/tasks/", plugin."/lib/tasks/"]
- endif
- if a:0
- return rails#buffer().open_command(a:cmd, a:1, 'task', {
- \ 'prefix': extra + ['lib/tasks/'],
- \ 'suffix': '.rake'})
- else
- return s:findedit(a:cmd,(plugin != "" ? plugin."/Rakefile\n" : "")."Rakefile")
- endif
-endfunction
-
-function! s:libEdit(cmd,...)
- let extra = []
- if RailsFilePath() =~ '\<vendor/plugins/.'
- let extra = [s:sub(RailsFilePath(),'<vendor/plugins/[^/]*/\zs.*','lib/')]
- endif
- if a:0
- return rails#buffer().open_command(a:cmd, a:1, 'lib', {
- \ 'prefix': extra + ['lib/'],
- \ 'suffix': '.rb'})
- else
- return s:findedit(a:cmd,"Gemfile")
- endif
-endfunction
-
-function! s:environmentEdit(cmd,...)
- if a:0 || rails#app().has_file('config/application.rb')
- return rails#buffer().open_command(a:cmd, a:1, 'environment', {
- \ 'prefix': 'config/environments/',
- \ 'suffix': '.rb',
- \ 'default': '../application'})
- else
- return s:EditSimpleRb(a:cmd,"environment","environment","config/",".rb")
+ call s:findedit(a:cmd,"Gemfile")
+ call s:warn(':Rplugin is deprecated. Use :Rlib to open the Gemfile.')
+ return ''
endif
endfunction
@@ -2976,7 +2863,25 @@ function! s:try(cmd) abort
return 1
endfunction
-function! s:readable_open_command(cmd, argument, name, options) abort
+function! s:projection_pairs(options)
+ let pairs = []
+ if has_key(a:options, 'format')
+ for format in s:split(a:options.format)
+ if format =~# '%s'
+ let pairs += [s:split(format, '%s')]
+ endif
+ endfor
+ else
+ for prefix in s:split(get(a:options, 'prefix', []))
+ for suffix in s:split(get(a:options, 'suffix', []))
+ let pairs += [[prefix, suffix]]
+ endfor
+ endfor
+ endif
+ return pairs
+endfunction
+
+function! s:readable_open_command(cmd, argument, name, options) dict abort
let cmd = s:editcmdfor(a:cmd)
let djump = ''
let default = get(a:options, 'default', get(a:options, 'affinity', '').'()')
@@ -2997,39 +2902,49 @@ function! s:readable_open_command(cmd, argument, name, options) abort
endif
elseif a:argument ==# '' && type(default) == type([])
for file in default
- if rails#app().has_file(file)
- return cmd . ' ' . fnameescape(file)
+ if self.app().has_file(file)
+ return cmd . ' ' . s:fnameescape(self.app().path(file))
endif
endfor
- return cmd . ' ' . fnameescape(a:default[0])
+ return cmd . ' ' . s:fnameescape(self.app().path(a:default[0]))
else
let root = a:argument
endif
if root ==# ''
return 'echoerr "E471: Argument required"'
endif
- let pairs = []
- for prefix in s:split(get(a:options, 'prefix', []))
- for suffix in s:split(get(a:options, 'suffix', []))
- let pairs += [[prefix, suffix]]
- endfor
- endfor
+ let pairs = s:projection_pairs(a:options)
for [prefix, suffix] in pairs
- let file = rails#app().path(prefix . root . suffix)
+ let file = self.app().path(prefix . (suffix =~# '\.rb$' ? rails#underscore(root) : root) . suffix)
if filereadable(file)
- return cmd . ' ' . fnameescape(simplify(file)) . '|exe ' . s:sid . 'djump('.string(djump) . ')'
+ return cmd . ' ' . s:fnameescape(simplify(file)) . '|exe ' . s:sid . 'djump('.string(djump) . ')'
endif
endfor
if djump !~# '^!'
- return 'echoerr '.string('No such '.a:name.' '.a:argument)
+ return 'echoerr '.string('No such '.tr(a:name, '_', ' ').' '.a:argument)
endif
for [prefix, suffix] in pairs
- if isdirectory(rails#app().path(prefix))
- let file = rails#app().path(prefix . root . suffix)
+ if isdirectory(self.app().path(prefix))
+ let file = self.app().path(prefix . (suffix =~# '\.rb$' ? rails#underscore(root) : root) . suffix)
if !isdirectory(fnamemodify(file, ':h'))
call mkdir(fnamemodify(file, ':h'), 'p')
endif
- return cmd . ' ' . fnameescape(simplify(prefix . root . suffix))
+ if type(get(a:options, 'template', '')) == type({})
+ let template = s:split(get(a:options.template, prefix, ''))
+ else
+ let template = s:split(get(a:options, 'template', ''))
+ endif
+ let placeholders = {
+ \ '%s': rails#underscore(root),
+ \ '%S': rails#camelize(root),
+ \ '%h': toupper(root[0]) . tr(rails#underscore(root), '_', ' ')[1:-1],
+ \ '%%': '%'}
+ if suffix =~# '\.js\>'
+ let placeholders['%S'] = s:gsub(placeholders['%S'], '::', '.')
+ endif
+ call map(template, 'substitute(v:val, "%.", "\\=get(placeholders, submatch(0), submatch(0))", "g")')
+ call map(template, 's:gsub(v:val, "\t", " ")')
+ return cmd . ' ' . s:fnameescape(simplify(file)) . '|call setline(1, '.string(template).')' . '|set nomod'
endif
endfor
return 'echoerr '.string("Couldn't find destination directory for ".a:name.' '.a:argument)
@@ -3094,11 +3009,11 @@ function! s:Alternate(cmd,line1,line2,count,...)
return call('s:Edit',[1,a:cmd]+a:000)
endif
else
- let file = s:getopt(a:count ? 'related' : 'alternate', 'bl')
- if file == ''
- let file = rails#buffer().related(a:count)
+ let file = [s:getopt(a:count ? 'related' : 'alternate', 'bl')]
+ if empty(file[0])
+ let file = rails#buffer().alternate(a:count)
endif
- if file != ''
+ if !empty(file)
call s:findedit(a:cmd,file)
else
call s:warn("No alternate file is defined")