Передача пароля (cat )в sed для замены значения конфигурации

Основываясь на вашем примере test.csv, ваш файл на самом деле разделен не запятыми, а пробелами. Попробуйте изменить цикл чтения во время чтения на:

while read -r ELMS_SIZE ELMS_NAME ELMS_ENV ELMS_DB
do
  if [ "$ELMS_DB" = "NOMATCH" ]; then
   echo "done"
  fi
done < <(tac "${CSM_DATA_DIR}/test.csv")

exit
0
19.03.2021, 10:39
4 ответа

Попробуйте использовать другой разделитель для sed... Существует риск сбоя в зависимости от вашего фактического пароля (, например. если он включал | или и или \1).

sed -i "s|DB_PASSWORD=|DB_PASSWORD=$mysqlpwd|".env
1
28.04.2021, 22:58

Пароли по самой своей природе должны содержать любые символы, которые могут быть надежно воспроизведены с помощью клавиатуры . Это означает, что пароли могут легко содержать действительный код sedили строки, которые при введении в сценарий редактирования sedломают этот сценарий, записываются в произвольные файлы в системе или, с помощью GNU sed, выполняют произвольные команды. (особенно интересно, когда вы работаете как пользователь root, которым вы выглядите ).

Не используйте sed, когда вам нужно использовать предоставленные пользователем -данные, если вы точно не знаете, как их очистить. Я бы лично избегал sedдля всего, что потребовало бы от меня двойных кавычек выражения sed(вместо одинарных -кавычек ), чтобы позволить оболочке расширить переменную, над которой я мало контролировал.

Вместо этого используйтеawk:

awk -F '=' '
    BEGIN { OFS = FS }
    NR == FNR { password = $0; next }
    $1 == "DB_PASSWORD" { sub("=.*",""); $2 = password }; 1' /root/.mysql/db00.yml.db.env >.env.new &&
mv.env.new.env

Сначала считывается пароль из первой строки первого файла (. Предполагается, что он содержит только одну строку с дословным паролем ).

Затем он обрабатывает ваш .envфайл как файл с=-полями с разделителями.

Когда первым полем в строке является DB_PASSWORD, он очищает все после первого =в строке (на тот случай, если старый пароль содержит =), и вставляет пароль как второе поле.

Все строки, измененные или нет, выводятся в .env.new,и этот файл затем заменяет старый .envна mv.

Важно отметить, что я никогда не использую данные, считанные из любого из двух файлов, как код в моей awkпрограмме, и я никогда не позволяю awkрассматривать какую-либо часть пароля как особую. Обратите внимание, что использование пароля в качестве строки замены при вызове sub()будет проблематичным, так как это будет рассматривать любое &в строке как особое.

2
28.04.2021, 22:58

Вы не должны указывать пароли в аргументах командной строки; они могут быть прочитаны любым пользователем системы через psили topили многими другими способами. Я понимаю, что это может быть маловероятным в некоторых сценариях автоматизации (, потому что никто, вероятно, не войдет в систему ), но это все же плохая идея, и всегда есть вероятность того, что какое-то средство мониторинга или какой-либо скрипт кем-то другим в какой-то момент времени произойдет регистрация процессов, запущенных в системе, — таким образом, ваш пароль будет записан неизвестно куда.

Хороший ответ уже был дан с использованием awk; Я также написал простое решение, используя ex, которым я поделюсь. Это будет работать для любого пароля с любыми специальными символами, за исключением того, что не может заканчиваться обратной косой чертой.

Если файл .envсодержит:

somevar1=someval
somevar2=some other val
DB_PASSWORD=
somevar3=another val
somevar4=val

И myscriptсодержит:

/^DB_PASSWORD=$/a
!@#$#% some complicated password "^$%^&@#,.,cmxz\k'dvok][
.
0//j!
x

Просто запустите ex.env < myscript, чтобы получить результаты, как показано:

$ ex.env < myscript
$ cat.env
somevar1=someval
somevar2=some other val
DB_PASSWORD=!@#$#% some complicated password "^$%^&@#,.,cmxz\k'dvok][
somevar3=another val
somevar4=val
$ 
0
28.04.2021, 22:58
sed -i -e "
  /^DB_PASSWORD=/c\\
DB_PASSWORD=$(sed -e 's:[\\]:&&:g' /root/.mysql/db00.yml.db)
" ./.env
  • Мы интегрируем в код sed очистку пароля для возможности подключения в команду измененияc\
0
28.04.2021, 22:58

Теги

Похожие вопросы