Как выполнить группу команд от имени другого пользователя в Bash?
Здесь уже заданы некоторые вопросы о запуске команд от имени другого пользователя. Однако вопрос и ответы сосредоточены на одной команде, а не на длинной группе команд.
Например, рассмотрим следующий скрипт:
#!/bin/bash
set -e
root_command -p param1 # run as root
# these commands must be run as another user
command1 -p 'parameter with "quotes" inline'
command2 -p 'parameter with "quotes" inline'
command3 -p 'parameter with "quotes" inline'
Здесь следует отметить пару важных моментов:
Последние три команды должны быть запущены как другой пользователь, используя
su
или жеsudo
, В примере было три команды, но предположим, что их было намного больше...Сами команды используют одинарные и двойные кавычки.
Второй пункт выше запрещает использование следующего синтаксиса:
su somebody -c "command"
... поскольку сами команды содержат кавычки.
Как правильно "группировать" команды и запускать их под другой учетной записью пользователя?
3 ответа
Попробуй это:
su somebody <<'EOF'
command1 -p 'parameter with "quotes" inline'
command2 -p 'parameter with "quotes" inline'
command3 -p 'parameter with "quotes" inline'
EOF
<<
представляет здесь док. Следующий токен является разделителем, и все, вплоть до строки, начинающейся с разделителя, подается в качестве стандартного ввода в команду. Помещение разделителя в одинарные кавычки предотвращает подстановку переменных в here-doc.
Я не очень хорош в bash-foo, так что есть способ быть более элегантным, но в прошлом я подходил к этой проблеме, используя несколько скриптов и "драйвер"
Например
Водитель
#!/bin/bash
set -e
su root script1
su somebody script2
script1
#!/bin/bash
set -e
root_command -p param1 # run as root
Скрипт2
#!/bin/bash
set -e
# these commands must be run as another user
command1 -p 'parameter with "quotes" inline'
command2 -p 'parameter with "quotes" inline'
command3 -p 'parameter with "quotes" inline'
Этот скрипт проверяет, является ли текущий пользователь, выполняющий скрипт, нужным пользователем. Если нет, то сценарий повторно выполняется с нужным пользователем.
#!/usr/bin/env bash
TOKEN_USER_X=TOKEN_USER_X
USER_X=peter # other user!
SCRIPT_PATH=$(readlink -f "$BASH_SOURCE")
if [[ "$@" != "$TOKEN_USER_X" ]]; then
###### RUN THIS PART AS the user who started the script
echo "This script is $SCRIPT_PATH"
echo -n "Current user: "
echo $USER
read -p "insert: "
echo "got $REPLY"
su - $USER_X -c "$SCRIPT_PATH $TOKEN_USER_X" # execute code below after else (marked #TOKEN_USER_X)
else
#TOKEN_USER_X -- come here only if script received one parameter TOKEN_USER_X
###### RUN THIS PART AS USER peter
echo
echo "Now this script is $SCRIPT_PATH"
echo -n "Current user: "
echo $USER
read -p "insert: "
echo "got $REPLY"
exit 0
fi
echo
echo "Back to initial user..."
echo -n "Current user: "
echo $USER