Выполнение команды без наследования родительской среды

14

Есть ли способ выполнить команду «как будто» в новой сессии входа в систему?

Я уже попробовал env -i. Однако я не хочу иметь дело с различными переменными ENV, которые я должен установить или сбросить.

Я тоже пробовал bash -c "some command"и bash -l -c "some commmand", но они все копируют текущую среду.

Самое близкое, что я пришел, - это решение гетто: ssh me@localhost "some command"

dgo.a
источник
Используйте, /bin/bash --loginчтобы получить такое поведение. Я использую это, например, чтобы получить надлежащее $PATH.
Даниэль Бек
Это эквивалент /bin/bash --l, который я уже пробовал. Копирует оригинальную среду. Попробуйте: export SOME_VAL=something. Потом /bin/bash --login. Потом env | grep SOME_VAL. Значение будет там.
dgo.a

Ответы:

12

Вот ответ, который не требует привилегий sudo или пароля пользователя, но все же обеспечивает среду, подобную той, которую вы получите при новом входе в систему.

env -i HOME="$HOME" bash -l -c 'your_command'

Пример:

$ export ABC=123
$ env -i HOME="$HOME" bash -l -c 'env' | grep ABC
$ env HOME="$HOME" bash -l -c 'env' | grep ABC
ABC=123

Разбить это для объяснения:

  1. env -i HOME="$HOME": Очищает окружающую среду. В -iустанавливает пустую среду с каким - либо переменными бы то ни было . Это проблематично, потому что это означает, что если вы попытаетесь наивно запустить, bash -lон не будет загружать ваши .bash_profileи т. Д., Потому что HOMEне установлен. Чтобы смягчить это, мы явно передаем HOME="$HOME", создавая среду, где HOME(и только HOME) установлен.

  2. bash -l -c ...: Запускает нужную команду в оболочке входа в систему. Для этого вам понадобится оболочка входа в систему, потому что мы начинаем с чистой среды и должны перезагрузить все.

В частности:

  • Это не требует привилегий sudo ( sudoверсия делает).
  • Это не требует ввода пароля пользователя ( suверсия делает).
  • Это не требует запуска сервера SSH и наличия ключа без пароля, который можно использовать для входа в систему на компьютере ( sshверсия этого требует).
Эллиот Слотер
источник
Спасибо, Эллиотт. Это выглядит так просто и очевидно ... теперь, когда на меня это указали.
dgo.a
12
su -l $USER

sudo -u $USER -i

Для чего-то еще более агрессивного env -i bash, но это отменяет все, включая $ HOME и $ TERM.

user1686
источник
2
Благодарность! Вторая команда дает мне именно то, что я хочу. Я искал более 2 часов и не нашел ничего похожего на ваш ответ. Основываясь на вашем ответе, я вернулся man sudoи обнаружил: «если целевой пользователь совпадает с вызывающим пользователем, пароль не требуется». ( suКажется, пароль всегда запрашивается.) Я такой дурак, что пропустил что-то такое простое в первом абзаце manстраницы :( Во-первых, я избегал sudo, потому что предполагал, что он всегда спрашивает пароль. Спасибо снова!
dgo.a
1
просто подсказка для других ... если вы вошли в систему как $USERвам нужно будет войти как root, а затем sudo -u ...как ваш пользователь. Если вы просто делаете sudo -uкак пользователь, вы будете наследовать.
Адам Гент
это не работает, очевидно, если у вас нет sudoдоступа. Есть ли альтернативный метод, который не требует sudo?
user5359531
@ user5359531: Да - su -l $USER.
user1686
1
который запрашивает пароль; Я вошел через аутентификацию по ssh-ключу, поэтому даже не знаю, какой пароль. И приглашение пароля собирается убить возможность сценария. Пока что его ssh $USER@localhost <command>
внешний