Como você configura o alias sudo = 'nocorrect sudo' corretamente?

5

Até recentemente, eu tinha alias sudo='sudo ' no meu arquivo .zshrc . Hoje me deparei com esse erro ao tentar fazer sudo mv :

➜  ~  sudo mv nginx.conf.orig nginx.conf.orig2
sudo: nocorrect: command not found

Agora pesquisando, descobri que isso parece ter a ver com alguns comandos que são prefixados com nocorrect e que eu poderia corrigir isso com alias sudo='nocorrect sudo' .

No entanto, o problema surge quando tento definir meu alias como alias sudo='nocorrect sudo ' para permitir usar aliases adicionais. Eu também assegurei que meu su estava usando o zsh como mencionado aqui .

➜  ~  alias sudo='nocorrect sudo '            
➜  ~  sudo mv nginx.conf.orig nginx.conf.orig2
sudo: nocorrect: command not found
➜  ~  alias sudo='nocorrect sudo'                           
➜  ~  sudo mv nginx.conf.orig nginx.conf.orig2
➜  ~  su
Password: 
michaelarch# ps -p $$
  PID TTY          TIME CMD
25831 pts/1    00:00:00 zsh

Alguém tem alguma sugestão sobre como resolver isso?

EDIT: alias sudo='sudo ' permite que você use aliases com seus comandos sudo, por exemplo, veja abaixo.

➜  ~  alias cat='echo hello'     
➜  ~  echo goodbye > example.txt
➜  ~  cat example.txt           
hello example.txt
➜  ~  sudo cat example.txt 
goodbye
➜  ~  alias sudo='sudo '
➜  ~  sudo cat example.txt
hello example.txt

Para mais informações sobre o meu shell:

➜  ~  sudo chsh                               
Changing shell for root.
New shell [/usr/bin/zsh]:    
➜  ~  unalias sudo; alias sudo='nocorrect sudo '
➜  ~  echo $SHELL; which sudo                   
/usr/bin/zsh
sudo: aliased to nocorrect sudo 
➜  ~  sudo mv nginx.conf.orig2 nginx.conf.orig  
sudo: nocorrect: command not found
➜  ~  which mv
mv: aliased to nocorrect mv
    
por Mike H-R 03.05.2014 / 15:50

2 respostas

6

O comportamento é reproduzível com:

alias sudo='nocorrect sudo '
alias mv='nocorrect mv '

Então, ao executar sudo mv foo bar , isso é expandido para

nocorrect sudo nocorrect mv foo bar

e gera um erro, pois nocorrect é uma palavra reservada no shell e não pode ser manipulada pelo sudo.

O motivo pelo qual o mv alias é expandido é que você define alias sudo='nocorrect sudo ' com um espaço em branco à direita, que ativa a expansão de alias posteriormente. Sem esse espaço em branco, este exemplo funciona, mas você perde a capacidade de usar alias após o sudo completamente.

Uma solução alternativa para ter uma expansão de alias geralmente após o sudo, mas para evitar que o erro com sudo mv escape do comando mv ao usá-lo com o sudo:

sudo \mv foo bar

Isso impede a expansão de alias de mv.

    
por 03.05.2014 / 16:41
5

Ok, eu tenho cavado isso por um tempo e encontrei algumas coisas na lista de discussão zsh. Não parece haver uma solução "bala de prata", mas um monte de soluções diferentes que fazem coisas diferentes. Vou postar o que fiz (o que é um pouco fora), mas também explorar as outras abordagens e seus problemas. Eu pessoalmente vou com:

➜  ~  alias sudo='sudo '
➜  ~  alias nsudo='nocorrect sudo'

EDITAR:

Agora irei com

sudo \mv foo bar

para os casos em que preciso disso, conforme descrito por @mpy na resposta alternativa.

/ EDIT

porque me permitirá usar aliases na maior parte do tempo e quando eles reclamarem porque estão com alias para nocorrect, eu posso usar nsudo para que eu não acidentalmente estrague meus arquivos.

Melhores abordagens são das listas de discussão zsh. Parece haver dois tópicos que eu encontrei sobre isso. Um de 1999 aqui (essa é a questão, veja os acompanhamentos, especialmente esta que resolve o problema noglob Eu não tenho certeza se ele resolve nocorrect também (o noglob implica nocorrect? caso contrário, acho que não, por favor, comente)

alias sudo='my_sudo '

function my_sudo {
    while [[ $# > 0 ]]; do
        case "$1" in
        command) shift ; break ;;
        nocorrect|noglob) shift ;;
        *) break ;;
        esac
    done
    if [[ $# = 0 ]]; then
        command sudo zsh
    else
        noglob command sudo $@
    fi
}

O que satisfaz os meus requisitos da minha pergunta:

➜  ~  alias cat='echo hello'     
➜  ~  echo goodbye > example.txt
➜  ~  sudo cat
hello
➜  ~  sudo mv example.txt2 example.txt

Parece também que isso surgiu novamente em 2008 na lista de discussão com uma solução assim:

alias sudo='noglob do_sudo '
function do_sudo
{
    integer glob=1
    local -a run
    run=( command sudo )
    if [[ $# -gt 1 && $1 = -u ]]; then
        run+=($1 $2)
        shift ; shift
    fi
    (($# == 0)) && 1=/bin/zsh
    while (($#)); do
        case "$1" in
        command|exec|-) shift; break ;;
        nocorrect) shift ;;
        noglob) glob=0; shift ;;
        *) break ;;
        esac
    done
    if ((glob)); then
        PATH="/sbin:/usr/sbin:/usr/local/sbin:$PATH" $run $~==*
    else
        PATH="/sbin:/usr/sbin:/usr/local/sbin:$PATH" $run $==*
    fi
}

O que parece estar fazendo muita coisa que eu não entendo totalmente. Isso parece ignorar a autocorreção (conforme declarado pelo autor).

    
por 03.05.2014 / 16:51

Tags