Назад | Перейти на главную страницу

Почему sudo -E на самом деле не сохраняет мою среду?

Я пытаюсь выполнить sudo некоторые двоичные файлы, которые находятся в настраиваемом пути. Этот пользовательский путь удаляется, когда я запускаю sudo хотя, но sudo -E должен сохранить мой путь. Почему не работает?

$ env | egrep ^PATH
PATH=/home/codemonkey/.nvm/v0.6.1/bin:/usr/local/bin:/usr/bin:/bin:/usr/local/gam
es:/usr/games

$ sudo env | egrep ^PATH
PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/X11R6/bin

$ sudo -E env | egrep ^PATH
PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/X11R6/bin

Я знаю, как это обойти, я просто хочу знать, почему sudo -E не работает

Вы можете установить exempt_group возможность указать sudo сохранить PATH для пользователей в этой группе.

Например, предположим, что ваш пользователь входит в группу «sys». Добавьте следующее в свой файл sudoers

Defaults exempt_group="sys"

Теперь у вашего пользователя не будет PATH сбросить для команд sudo (-E не требуется, чтобы это работало).
Видеть страница руководства Больше подробностей.

РЕДАКТИРОВАТЬ: Придется отметить это как плохой ответ. Это правда, что это работает, но у него есть побочный эффект, который я не заметил, играя с ним. Это также освобождает пользователей в этой группе от необходимости вводить свой пароль. Кажется, вы не можете получить сохранение PATH, не допустив этого. Я думаю, немного глупо ...

Из sudoers(5):

 setenv            Allow the user to disable the env_reset option from the 
                   command line via the -E option.  Additionally, environment
                   variables set via the command line are not subject to the
                   restrictions imposed by env_check, env_delete, or env_keep.  
                   As such, only trusted users should be allowed to set  
                   variables in this manner.  This flag is off by default.

Предлагаю другое решение в дополнение к уже введенному. Это работает только для bash (но может быть изменено для других оболочек).

Ниже приводится обертка вокруг sudo который будет искать команду, которую вы ему передаете. Найдя команду, он изменяет ее на полный путь.
Так что по сути sudo echo hello становится sudo /bin/echo hello.

Поместите следующее в свой ~/.bashrc

function sudo() {
   local ARGS
   declare -a ARGS=()
   while (( $# )); do
      if [[ "${1:0:1}" == "-" ]]; then
         # the argument is a dash-arg; '-s' for example
         ARGS[${#ARGS[@]}]="$1"
         if [[ "$1" =~ ^-[pugD]$ ]]; then
            # these are the arguments that take a parameter, so skip the next
            ARGS[${#ARGS[@]}]="$2"
            shift
         fi
         shift
      elif [[ "$1" == *"="* ]]; then
         # the argument is a env var to set, not a command
         ARGS[${#ARGS[@]}]="$1"
         shift
      else
         # finally, a command
         CMD="$(which --skip-alias --skip-functions "$1")"
         [[ -z "$CMD" ]] && ARGS[${#ARGS[@]}]="$1" || ARGS[${#ARGS[@]}]="$CMD"
         shift
         break
      fi
   done
   command sudo "${ARGS[@]}" "$@"
}

Обратите внимание: он не справится с этим должным образом, если у вас есть команда с = в его имени. Это крайне маловероятно, поэтому я принял это предостережение, чтобы не усложнять задачу.

Я бы посмотрел на параметры в файле sudoers, поскольку они управляют некоторым поведением sudo.

И, конечно, я бы посоветовался со страницей руководства для файла sudoers.