Можно ли получить вывод пути grep в переменной? - PullRequest
0 голосов
/ 11 июня 2018

У меня проблемы с сценарием, и я хочу знать, возможно ли сохранить путь соответствующего результата поиска grep?

Я нахожусь на RHEL 7, скрипт проверяет файл rsyslog.conf, который завершает или добавляет правильное значение параметра (тест CIS rhel7, часть 4.2.1.3).

Полный сценарий на данный момент:

#!/bin/bash

if grep "^\$FileCreateMode" /etc/rsyslog.conf /etc/rsyslog.d/*.conf
then
    read -p "Is $FileCreateMode superior or equal to 0640 ? [y/n]" rep
    if [ $rep == "y" ]
    then
        echo "No action needed"
    else
        read -p "Enter the new $FileCreateMode value (0640 recommanded)" rep2
        sed -i "/^\$FileCreateMode/ $rep2" 
        echo "$FileCreateMode new value is now $rep2"
    fi
else
    echo "$FileCreateMode doesn't exist in rsyslog conf files"
    read -p "What's the path of the file to modify ?(Press [ENTER] for default /etc/rsyslog.conf)" path
    if [ $path -z ] 
    then
        echo "$FileCreateMode 0640" >> /etc/rsyslog.conf
    else
        echo "$FileCreateMode 0640" >> $path
    fi
fi

Итак, моя проблема в седьмой строке на 11-й строке.Могу ли я получить правильный путь, если мой grep в 3-й строке совпал с переменной, чтобы повторно использовать его 11-го числа.

И я борюсь с тем же sed, потому что я хочу, чтобы он заменил значение после $FileCreateMode, но он продолжает изменять строку $ FileCreateMode.

Я тоже пробовал этот синтаксис, но все еще не получил результат, который я хочу

sed -i -e "s,^\($FileCreateMode[ ]*\).*,\1 0640 ,g" /etc/rsyslog.conf

Заранее спасибо за любую помощь, которую выможет принести, и хорошего дня:)

Редактировать:

По просьбе я упрощаю здесь.

Я хочу grep $ FileCreateMode в / etc / rsyslog.conf и /etc/rsyslog.d/*.conf, и я пытаюсь получить файл назначения (может быть rsyslog.conf, но это может быть testpotato.conf в rsyslog.d) в переменную (например, $ var), чтобы бытьвозможность использовать путь в моем седе в 11-й строке как

sed -i "/^\$FileCreateMode/ 0640" $var

И для проблемы с седом, когда я выполняю эту команду, я хотел бы иметь что-то вроде

old : $FileCreateMode 0777
sed -i "/^\$FileCreateMode/ 0640" $var
new : $FileCreateMode 0640

Но вместо этогоя получаю

old : $FileCreateMode 0777
sed -i "/^\$FileCreateMode/ 0640" $var
new : 0640 ($FileCreateMode is deleted)

надеюсь, что я более нестабилен, еще раз спасибо и чувствуюможете запросить более подробную информацию

Ответы [ 2 ]

0 голосов
/ 12 июня 2018

Если ваш grep поддерживает -H, вы можете просто сделать:

while grep -H "^\$FileCreateMode" /etc/rsyslog.conf /etc/rsyslog.d/*.conf \
        | IFS=: read path line; do

        # Here, $path is the path to the file that matches
        # and $line is the line that matched.
done

Если вы предпочитаете, вы можете использовать if ...; then вместо while ...; do Имейте в виду, что переменные потеряют своизначение после завершения подоболочки.

0 голосов
/ 12 июня 2018

Используйте $(), чтобы присвоить результаты grep переменной, а затем используйте цикл for для обработки файлов один за другим:

# Assign grep results to FILES
FILES=$(grep -l '^$FileCreateMode' /etc/rsyslog.conf /etc/rsyslog.d/*.conf)

# Check if FILES variable is not empty
if [[ -n ${FILES} ]]; then
    # Loop through all the files
    for file in ${FILES}; do
        # ...
        sed -iE "s/^(\\\$FileCreateMode\s+)[[:digit:]]+/\1${rep2}/" ${file}
        # ...
    done
else
    # OP's logic for when $FileCreateMode doesn't exist in any of the files

sed fix:

Обратите внимание, что я также обновил ваше выражение sed (см. Выше).Вы были очень близки, но вам пришлось дважды избегать знака доллара: один раз, чтобы использовать его внутри "", и один раз, чтобы он не интерпретировался как END_OF_LINE в регулярном выражении.

...