Comment enregistrer un fichier pour lequel je n'ai aucune autorisation d'écriture?

26

Parfois, il arrive que j'ouvre un fichier et que j'apporte quelques modifications en tant que mon propre utilisateur, sans remarquer ou "oublier" de remarquer l' [read-only]avertissement dans la ligne d'état (c'est-à-dire un /etcfichier de configuration aléatoire comme /etc/resolv.conf).

:w!échoue évidemment dans ce cas parce que mon utilisateur n'a de toute façon aucune autorisation d'écriture. Je dois donc :w /home/filename, sortir et sudo mv ..., très mal à l'aise.

Existe-t-il un moyen pour que j'escalade temporairement vers root pour pouvoir enregistrer le fichier actuellement ouvert? (étant donné que je suis en sudoersou / et que je peux sudirectement)?

guido
la source

Réponses:

24

L'astuce consiste à utiliser un appel externe pour sudo:

:w !sudo tee %

Comment cela fonctionne:

  • :w !<command>s'exécute <command>avec le contenu du tampon en tant que stdin.
  • teeduplique stdin dans un fichier & stdout; %se développe au nom de fichier actuel ..
  • Vous préfixez cela avec sudopour les autorisations root.

Vous n'enregistrez pas vraiment le fichier avec Vim, vous appelez plutôt un programme externe pour écraser le contenu du fichier que vous modifiez. C'est pourquoi vous recevrez un avertissement de Vim:

W12: Warning: File "xxx" has changed and the buffer was changed in Vim as well
See ":help W12" for more info.
[O]K, (L)oad File: 

Vous pouvez transformer cela en une fonction:

fun! SuperWrite()
        write !sudo tee %
        " Or with :silent (but that doesn't seem to work for everyone)
        "silent write !sudo tee %
        edit!
endfun

Et raccourci clavier:

nnoremap <Leader>w! :call SuperWrite()<CR>

Avec su, seul l'utilisateur root peut utiliser -cpour exécuter immédiatement une commande. Je ne pense pas que vous puissiez vous en servir su, mais il y a peut-être une astuce que je ne connais pas ...

Martin Tournoij
la source
SuperWritefonctionne, mais il vous renvoie le fichier. En l' :silentexécutant, vous entrez votre mot de passe de manière invisible.
TankorSmash
@TankorSmash Merci; réponse mise à jour. Vous ne savez pas ce que vous voulez dire par "entrez votre mot de passe de manière invisible", cependant? L'ajout silentsemble bien fonctionner?
Martin Tournoij
Je ne lance pas vim avec sudo, donc cela peut être en jeu ici, mais quand je vais sur sudo té le fichier, il me demande le mot de passe sudo. Si c'est silencieux, je ne vois pas l'invite, mais je dois quand même saisir un mot de passe.
TankorSmash
1
Ce que vous voyez est la fonctionnalité standard de tee d'écho sur stdout ainsi que le fichier donné. Une solution consiste à rediriger stdout vers / dev / null, a la: w ! tee % > /dev/null Cela fera toujours écho au résultat de la commande (une seule ligne), mais pas à tout le contenu du tampon.
Jon Carter
Plutôt que d'utiliser teepuis de jeter sa sortie, ne fonctionnerait pas cataussi si vous ne voulez pas que le fichier soit imprimé?
Lie Ryan
12

J'utilise le mappage suivant dans mon .vimrc, que je trouve utile:

cnoremap w!! w !sudo tee %

Il est facile de s'en souvenir, car w«écrire» w!est «écrire de force» et «écrire de force w!!super-duper». : P

Poignée de porte
la source
1
Je l'ai depuis longtemps mappé W, mais il w!!est beaucoup plus logique de mettre à jour mon .vimrc. Merci
jalanb