#!/bin/bash
params=$(cat /var/tmp/patterns.txt)
remoteLog="/home/remotefile.txt"
nodes=("192.168.1.2" "192.168.1.3")
for node in "${nodes[@]}";do
ssh ${node} << 'EOF'
grep -i "${params}" "$remotelog" >/var/tmp/output.txt
EOF
done
cat /var/tmp/patterns.txt
abc
efg
ijk
원격 서버에 로그인하고 로컬 컴퓨터에 있는 Patterns.txt 파일에 지정된 문자열을 grep하려고 합니다. 스크립트를 실행하면 원격 시스템에 로그인하지만 로컬 시스템에 있는 Patterns.txt 파일에 지정된 패턴을 검색하지 않습니다.
원격 서버에 Patterns.txt 파일을 생성하면 스크립트가 제대로 작동하지만 스크립트를 실행하는 로컬 컴퓨터에 파일이 있는 경우에는 작동하지 않습니다.
답변1
여기 있는 문서는 로 참조됩니다 <<'EOF'
. 첫 번째 구분 기호를 인용했으므로 여기 있는 문서 전체가 인용됩니다. 이는 쉘이 내부에서 확장을 수행하지 않음을 의미합니다. 이는 이 두 변수가 로컬 쉘에 의해 건드려지지 않고 원격 쉘에 의해 확장되어 빈 문자열로 확장될 가능성이 높다는 것을 의미합니다.
또 다른 문제는 그것을 사용하는 $params
방식 입니다 grep
. 한 줄에 별도의 정규식이 아닌 단일 정규식으로 작동합니다(내 생각에는 이것이 귀하의 의도라고 생각합니다).
대신에:
for node in "${nodes[@]}"; do
ssh "$node" "cat -- '$remotelog'" |
grep -f "$params" |
ssh "$node" 'cat >/var/tmp/output.txt'
done
이는 grep
각 호스트에서 얻은 데이터에 대해 로컬 작업을 수행합니다. 이 작업은 grep
옵션을 통해 파일의 정규식을 사용한 다음 결과를 원격 호스트의 파일로 다시 출력합니다.$params
-f
또 다른 접근 방식은 스키마를 각 호스트로 전송하고 원격으로 작업을 수행하는 것입니다.
for node in "${nodes[@]}"; do
scp "$params" "$node:/var/tmp/patterns.txt" &&
ssh "$node" <<EOF
grep -f /var/tmp/patterns.txt '$remotelog' >/var/tmp/output.txt
rm -f /var/tmp/patterns.txt
EOF
done