
목록에서 단어가 포함된 줄을 삭제하기 위해 루프에서 sed를 사용하는 스크립트가 있습니다.
for i in $list; do
sed -i "/$i/d" file
done
$list
SQL 쿼리에서 생성됩니다.
list=$(psql -d dbname -t -c "SELECT foo from table ORDER BY column DESC")
문제는 우리 회사가 최근 all fchown
또는 fchmod
syscall을 포함하는 더 엄격한 auditd 규칙을 구현했다는 것입니다. 을 사용하면 모든 항목에 1 과 syscall이 포함되어 있는 strace
것을 볼 수 있습니다 .sed -i
fchown
fchmod
큰 목록 변수를 사용하면 iowait
auditd가 로그에 엄청나게 많은 행을 기록하기 때문에 급등하고 시스템이 실제로 정체됩니다.
목록 변수를 한 줄로 sed에 전달하여 파일이 한 번만 열리고 닫힐 수 있는 방법이 있는지 알아내려고 노력 중입니다.
이미 질문했는데 auditd 규칙에 대한 변경 사항은 시작이 아닙니다.
감사해요.
답변1
수많은 인라인 명령을 하나씩 호출하는 대신 한 번만 실행하고 sed
단일 스크립트를 사용 하면 됩니다.sed
sedscript=$(mktemp)
for i in $list; do
echo "/$i/d" >> "$sedscript"
done
sed -f "$sedscript" -i /path/to/file
rm -f "$sedscript"
답변2
의 단어를 주의 깊게 할당할 수 있다면 list
bash 매개변수 확장을 사용하여 모든 공백을 정규식 alternator로 바꾼 다음 작업을 |
요청할 수 있습니다.grep
list='auditd the to'
cp file temp &&
grep -Ev "${list// /|}" temp > file &&
rm temp
답변3
쉘이 배열을 지원하는 경우 다음과 같은 작업을 수행할 수 있습니다.
mapfile -t arr < <(psql -d dbname -t -c "SELECT foo from table ORDER BY column DESC")
명령의 출력을 쉘 배열에 넣으려면
printf '/%s/d\n' "${arr[@]}" | sed -i.bak -f - somefile
삭제 순서를 에 적용합니다 somefile
. psql
명령에서 반환된 필드에 에 특별한 문자가 포함될 수 있는 경우 일반적인 주의 사항이 적용됩니다 sed
.
이는 임시 스크립트 파일을 피하고 필요한 경우 테이블 필드의 공백을 처리해야 한다는 점을 제외하면 @DopeGhoti의 솔루션과 유사합니다.
답변4
이것이 psql -d dbname -t -c "SELECT foo from table ORDER BY column DESC"
공백으로 구분된 단어 목록을 제공하는 경우 다음을 시도하십시오.
$ psql -d dbname -t -c "SELECT foo from table ORDER BY column DESC" \
| awk -v FS=" " -v OFS="|" '{$1=$1; print "("$0")"}' \
| xargs -I {} sed -i -E '/{}/d' file