Come posso ottenere i comandi sudo per usare le impostazioni in /root/.bashrc


9

Ho personalizzato .bashrccon un certo numero di alias, in particolare lleexport LS_OPTIONS='--color=auto'

Purtroppo questo non funziona se usato con sudo, quindi ho anche modificato /root/.bashrc, ma questo sembra non aver fatto alcuna differenza.

sudo envspettacoli HOME=/rooteSHELL=/bin/bash

Come posso ottenere i sudocomandi per utilizzare le impostazioni /root/.bashrc?

Comprendo che ciò accade solo quando bashviene eseguito in modo interattivo, quindi sono aperto a qualsiasi altro suggerimento su come personalizzare.


@ daniel-gelling - Ho sempre pensato che questo Q fosse un problema XY - meta.stackexchange.com/questions/66377/what-is-the-xy-problem . Il titolo implica che vogliono qualcosa da fuori /root/.bashrcma in realtà ciò che la Q sta cercando sono gli alias da questo file - questo non è possibile per questo - unix.stackexchange.com/questions/1496/… .
slm

@slm quello che sto cercando è l'aggiunta di un metodo per bashrc - come ho fatto nel mio file .bashrc personale così come il file .bashrc per root "disable" l' -ropzione crontab: crontab () { [[ $@ =~ -[iel]*r ]] && echo '"r" not allowed' || command crontab "$@" ;}. Funziona quando si accede come uno degli utenti, tuttavia quando lo eseguo sudo crontab -rviene comunque eseguito.
Daniel Gelling,

@DanielGelling - vedi se la mia risposta funziona per te scenario.
slm

Risposte:


6

sudoesegue un eseguibile, non un comando shell. Quindi non conosce gli alias. Se corri sudo ls, è così sudo /bin/ls, non usa alcun lsalias che potresti avere.

Puoi causare sudo lsl'espansione dell'alias inserendo quanto segue nel tuo .bashrc:

alias sudo='sudo '

Nota lo spazio finale - che dice alla shell di continuare l'espansione dell'alias con la parola che viene dopo sudo. Attenzione che espandere gli alias dopo sudo potrebbe non essere sempre una buona idea, dipende dal tipo di alias che hai.

Inoltre sudo rimuove la maggior parte delle variabili dall'ambiente. Ciò non influirà su un alias come alias ls='ls $LS_OPTIONS', poiché si tratta di una variabile di shell utilizzata dalla shell mentre sta espandendo il comando (ed esportandolo da .bashrcnon serve a nulla). Ma influirebbe sulle variabili utilizzate dal comando, ad esempio LS_COLORS. Puoi configurare sudo per mantenere determinate variabili d'ambiente modificando la sua configurazione: esegui visudoe aggiungi la linea

Defaults env_keep += "LS_COLORS"

Con queste impostazioni, sudo llotterrai i colori a cui sei abituato.

In alternativa, puoi eseguire una shell di root con sudo -s. Questa shell caricherà il suo file di configurazione ( ~/.bashrcper bash). A seconda di come è configurato sudo, questo può essere HOMEimpostato sulla tua home directory o cambiarlo in /root. Puoi forzare la home directory per essere impostata su root con sudo -Hs; viceversa, per mantenere la home directory originale, eseguire sudo env HOME="$HOME" bash.


3

Grazie a coloro che hanno risposto, che mi hanno spinto a leggere man sudopiù attentamente.

sudo -s Se non viene specificato alcun comando, viene eseguita una shell interattiva.

Questa shell interattiva utilizza /root/.bashrce quindi include le mie personalizzazioni.

Richiede che il comando sia inserito separatamente, ma questo è OK.


2

sfondo

Ho sempre pensato che questa domanda fosse un problema XY . Il titolo implica che vogliono qualcosa da fuori /root/.bashrcma in realtà ciò che la domanda è dopo è gli alias di questo file - questo è ampiamente ritenuto impossibile per questo - Perché il mio script Bash non riconosce gli alias? .

È fondamentalmente in base alla progettazione che i tuoi alias non verranno raccolti in sudoe in altri luoghi perché non sono portatili, e questa è anche la mia opinione su di loro.

Tutto ciò che si trova nell'ambiente dell'utente non deve essere assunto da script e software che possono essere eseguiti su una determinata casella. Ma mi rendo conto che ci sono scenari in cui potrebbero esserci alcuni alias in un determinato account utente $HOME/.bashrcche altri potrebbero voler sfruttare in scenari interattivi.

A tal fine puoi semplicemente dire all'interprete Bash di espandere tutti gli alias che trova durante il processo di accesso al di fuori dei normali comportamenti della shell in cui ti imbatti durante l'utilizzo sudo.

Esempio

Impostare

Per le cose set up che ho aggiunto i seguenti alias, variabili d'ambiente, e le funzioni per il mio utente root /root/.bashrce /root/.bash_profilefile.

$ grep smurf ~/.bashrc
alias brc_smurf='echo "ran alias from /root/.bashrc"'
export brc_smurf_env='var from /root/.bashrc'
bpf_smurf_func() { echo 'ran func from /root/.bash_profile'; }

$ grep smurf ~/.bash_profile
alias bpf_smurf='echo "ran alias from /root/.bash_profile"'
export bpf_smurf_env='var from /root/.bash_profile'
brc_smurf_func() { echo 'ran func from /root/.bashrc'; }

Senza fare nulla di nessuno di questi lavori (nessuna sorpresa):

$ sudo brc_smurf
sudo: brc_smurf: command not found

$ sudo bpf_smurf
sudo: bpf_smurf: command not found

Vediamo che il aliascomando non mostra alias quando eseguito in sudo:

$ sudo alias
$

Questo comportamento suggerisce che non dovresti aspettarti che gli alias siano accessibili. Ma continuiamo ...

Passaggio n. 1: alias visibili

Se corriamo bash -cipossiamo indurre Bash a leggere almeno il nostro $HOME/.bashrc:

$ sudo bash -ci 'alias' | grep smurf
alias brc_smurf='echo "ran alias from /root/.bashrc"'

Bene, quindi forse possiamo farcela?

$ sudo bash -ci 'alias; brc_smurf'
bash: alias; brc_smurf: No such file or directory

Passo 2 - shopt -s expand_aliases

No. Ancora una volta questo è di progettazione, stiamo facendo qualcosa che non dovremmo fare, quindi c'è una serie di "sicurezze" che dobbiamo disabilitare. l'altra "sicurezza" è Bash.

$ sudo bash -ci 'shopt -s expand_aliases; alias; brc_smurf'
alias brc_smurf='echo "ran alias from /root/.bashrc"'
alias cp='cp -i'
alias egrep='egrep --color=auto'
alias fgrep='fgrep --color=auto'
alias grep='grep --color=auto'
alias l.='ls -d .* --color=auto'
alias ll='ls -l --color=auto'
alias ls='ls --color=auto'
alias mv='mv -i'
alias rm='rm -i'
alias which='alias | /usr/bin/which --tty-only --read-alias --show-dot --show-tilde'
ran alias from /root/.bashrc

Qui possiamo vedere il nostro messaggio /root/.bashrc, abbiamo eseguito correttamente l'alias dell'utente root brc_smurf.

Step # 3 - che dire di env vars?

Se stai usando il metodo mostrato sopra, ora dovrebbero funzionare anche questi.

$ sudo bash -ci 'shopt -s expand_aliases; brc_smurf; echo $brc_smurf_env'
ran alias from /root/.bashrc
var from /root/.bashrc

Step # 4 - che dire delle funzioni?

Funziona anche come previsto:

$ sudo bash -ci 'shopt -s expand_aliases; brc_smurf; echo $brc_smurf_env;brc_smurf_func'
ran alias from /root/.bashrc
var from /root/.bashrc
ran func from /root/.bashrc

TLDR;

Puoi farlo per ottenere l'accesso alle variabili di ambiente + alias da /root/.bashrc:

$ sudo bash -ci 'shopt -s expand_aliases; <cmds>'

Asporto

Questo metodo abilita il contenuto di /root/.bashrc, non raccoglie il contenuto di /root/.bash_profile.

Riferimenti


Sì, anche se ci sono alcune differenze minori tra loro, non entriamo nei dettagli qui ;-). Ad ogni modo, potresti aiutarmi con la situazione che ho indicato nei commenti della domanda: usare le funzioni .bashrccon sudo; rimuovendo specificamente l' -ropzione da crontab?
Daniel Gelling,

Va bene, ma questo significherebbe che dovrei correre: sudo bash -ci 'alias; shopt -s expand_aliases; echo $brc_smurf_env'invece di un semplice sudo echo $brc_smurf_env?
Daniel Gelling,

Puoi rimuovere il alias, che era semplicemente per mostrarli, che avresti dovuto faresudo bash -ci 'shopt -s expand_aliases; <cmds>'
slm

Sarebbe un sacco di digitare solo per modificare il mio crontab per root. Permettetemi di creare un alias per questo :-P
Daniel Gelling,

@DanielGelling - sì, benvenuto a tutto il divertimento nelle viscere delle conchiglie.
slm

0

Ci sono un sacco di impostazioni nel file / etc / sudoers in particolare o l'impostazione di un ambiente per l'esecuzione dei comandi sudo (ad es. Accertarsi che il PERCORSO abbia solo posizioni attendibili) ma a seconda di ciò che si spera di uscire da questo potresti non essere in grado di fare ciò che cerchi se comporta l'esecuzione di comandi effettivi in ​​una shell per configurare l'ambiente. Il Sudoing specifico non ti dà una shell di login di root in modo che non crei un profilo regolare per te.


0

Diciamo che modifichiamo /root/.bashrc per essere:

$ sudo su -
Password: ******
# cat ~/.bashrc

echo "root bashrc file was read"
PATH=~/bin:$PATH
echo "$PATH"
export USERVAR=set
echo "$USERVAR"

umask 022
alias ll='ls $LS_OPTIONS -l'
alias l='ls $LS_OPTIONS -lA'

Consente di disconnettersi e riconnettersi per fare in modo che bash legga il file:

# exit
$ sudo su -
root bashrc file was read
/root/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin
set
root@here:~# alias l
alias l='ls $LS_OPTIONS -lA'
root@here:~# 

Come puoi vedere, il file è stato letto, il PERCORSO è stato modificato e gli alias sono stati impostati. Tutto è funzionale come da lei richiesto.

Tuttavia, sudo continuerà a non funzionare come previsto.

root@here:~# exit
$ sudo env | grep USERVAR              # no output 
$ sudo env | grep PATH
PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin

PERCORSO non è cambiato. Potrebbero esserci modi per cambiare il percorso nei sudoer, ma ti consiglio vivamente di evitare di farlo. E, comunque, gli alias, le funzioni e alcune altre modifiche non verranno ancora applicati cambiando solo il PERCORSO. Un file deve essere di provenienza. Farlo per ogni script o comando chiederà al computer di eseguire più lavoro senza alcun vantaggio reale. Gli script non usano alias (non vi è alcun uso pratico per loro all'interno degli script).

Quindi, basta accedere, il .bashrcfile verrà caricato automaticamente e funzionerà.

Puoi iniziare bash come questo:

$ sudo bash
root bashrc file was read
/root/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin
set
root@mail:/home/isaac/me/temp/clocks-master#

Ma come vedi sopra, la pwd (la directory di lavoro) non è cambiata e, se si controlla un po 'di più, anche alcune altre impostazioni non sono cambiate. Ecco perché il comando corretto è usare:

$ sudo su -

Se quel comando è troppo lungo per essere digitato, crea un alias o una funzione nell'utente (non root) dove verrà usato quel comando, qualcosa come:

$ alias mysu='sudo su -'
$ mysu
# 

0

TL; DR: è possibile utilizzare sudo -iper eseguire una funzione definita /root/.bashrc(ma non un alias) e inoltre avere accesso alle variabili esportate da quel file:

argomenti del comando sudo -i 

Tuttavia, gli alias non funzionano lì, ma puoi facilmente convertirli in funzioni se desideri renderli disponibili sudo -i.

Continua a leggere per un'analisi completa e maggiori dettagli.


Ci sono alcuni problemi qui, alcuni su come funziona sudo e altri su come funziona bash stesso ...

Per impostazione predefinita, sudocercherà solo per i comandi e consentirà di bypassare il guscio, così semplicemente in esecuzione sudo llsarà solo lavoro se c'è un lleseguibile in una delle directory in $PATH. Quindi, per usare gli alias (o le funzioni) è necessario assicurarsi che una shell sia invocata come parte del processo.

Un modo sarebbe quello di eseguire qualcosa di simile sudo sho sudo bash, sebbene moderno sudo(lo sto testando su sudo 1.8.19p1) ha opzioni -se -iper quello scopo.

Quindi un tentativo sarebbe qualcosa di simile sudo -s ll(che equivale a sudo bash -c 'll', supponendo che tu $SHELLsia Bash, che sembra essere il caso in base a quello che rcfilehai citato.) Ma neanche questo funziona, poiché avvia la shell in modo non interattivo, modalità non di accesso, che non legge nessuno dei suoi file di avvio. È essenzialmente lo stesso di scrivere uno script di shell e utilizzarlo #!/bin/bashper eseguirlo. Gli alias (e le funzioni) che hai nel tuo ~/.bashrcnon saranno accessibili da quello script ...

Quindi la prossima -iopzione è che crea una shell di login. Questo è il più promettente, dal momento che sarà leggere i file di avvio! Eppure, sudo -i ll(equivalente a sudo bash -l -c 'll') non funzionerà ancora. Quindi come è possibile, dato che ha letto la definizione lldell'alias?

Bene, la prossima spiegazione qui è che, per impostazione predefinita, bash non espanderà gli alias, tranne quando la shell è interattiva ... Questa shell avviata da sudo -i(o bash -l) è una shell di login , ma non è ancora interattiva.

Quindi il prossimo passo è ottenere una shell interattiva , che quindi funzioni :

sudo bash -i -c 'll'

(Avere sia login che interattivo va bene, ovviamente, bash -l -i -c ...funzionerà.)

Un'altra alternativa è continuare a utilizzare una shell di accesso (non interattiva) ma chiederle esplicitamente di espandere gli alias, quindi funzionerà anche:

sudo bash -l -O expand_aliases -c 'll'

(Il caso in cui bash era interattivo non aveva bisogno di una shell di accesso , poiché questo è sufficiente per leggere i file di inizializzazione, ma questo deve -lleggerli.)

Queste sono righe di comando abbastanza lunghe ... E richiedono anche che tu citiate l'intero comando shell, quindi se stai chiamando un alias con argomenti, dovrai trasformare tutto ciò in una stringa ... Quindi è un po ' goffo da usare ...

Nota che prima stavo parlando di alias e funzioni ... Era apposta, dal momento che le funzioni in realtà sono molto più convenienti qui. Non hai bisogno di nulla di speciale (come avere una shell interattiva o impostare un'opzione specifica) per eseguire funzioni su una shell, purché tu stia approvando la loro definizione.

Quindi, se definissi lluna funzione anziché un alias, saresti in grado di usarla direttamente con il -icollegamento di sudo :

sudo -i ll

E se hai una riga di comando più lunga, con argomenti, puoi passarli direttamente anche qui:

sudo -i ll -C -R /etc

(Confronta con sudo bash -i -c 'll -C -R /etc'.)

Le funzioni sono anche molto più flessibili e in genere più facili da mantenere ... Di solito è facile convertire un alias in una funzione, l'unico avvertimento è quello di utilizzare sempre "$@"dove ti aspetteresti di prendere argomenti extra (in genere alla fine del alias.)

Ad esempio, questo alias:

alias ll='ls $LS_OPTIONS -l'

Potrebbe essere trasformato in questa funzione:

ll () {
    ls $LS_OPTIONS -l "$@"
}

Sono, per la maggior parte degli scopi, equivalenti. E, come accennato in precedenza, la funzione dovrebbe essere accessibile direttamente da sudo -i, quindi questo è un ulteriore vantaggio.

Spero che questa risposta e spiegazione siano utili!


DV - Non penso che questo stia migliorando la situazione più di quanto non sia già qui.
slm

1
@slm Penso che la mia risposta stia aggiungendo qualcosa, dal momento che nessuna risposta precedente ha menzionato il modulo sudo -i command argumentsper poter eseguire funzioni da /root/.bashrce avere variabili esportate disponibili. Ma vedo come la mia risposta sia stata forse troppo lunga e quell'informazione fosse in qualche modo sepolta lì dentro ... Quindi ho aggiunto un TL; DR per riassumerlo (mantenendo ancora i dettagli tecnici dell'indagine in giro.) Per favore dai un'altra occhiata.
filbranden,
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.