Heredoc을 사용하여 명령 목록 반복

Heredoc을 사용하여 명령 목록 반복

이것은 잘 작동합니다:

$ eval 'echo "1" > ~/Desktop/in/foo'

하지만 이건 아니다:

$ while IFS= read _cmd; do eval "$_cmd"; done < <(cat << EOF
'echo "1" > ~/Desktop/in/foo'
'echo "2" > ~/Desktop/in/bar'
EOF
)
bash: echo "1" > ~/Desktop/in/foo: No such file or directory
bash: echo "2" > ~/Desktop/in/bar: No such file or directory

어떻게 고치나요?


고쳐 쓰다

제안된 대로 작은따옴표를 제거하면 작동하지만 이 변형에서는 작동하지 않습니다(작은따옴표로만 묶인 파일 이름에도 마찬가지입니다).

$ while IFS= read _cmd; do eval "$_cmd"; done < <(cat << EOF 
echo "1" > ~/Desktop/in/foo (bis)
echo "2" > ~/Desktop/in/bar
EOF
)

제공된 솔루션과 함께:

"$SHELL" << EOF
echo "1" > ~/Desktop/in/'foo (bis)'
echo "2" > ~/Desktop/in/bar
EOF

답변1

를 실행하면 eval 'echo "1" > ~/Desktop/in/foo'셸은 작은따옴표를 제거한 다음 를 eval평가합니다 echo "1" > ~/Desktop/in/foo.

eval "$_cmd"업데이트 전 코드에서 실행하면 셸이 $_cmd큰따옴표를 확장하고 제거한 다음 작은따옴표를 eval평가합니다 'echo "1" > ~/Desktop/in/foo'. 해당 항목을 보고 싶지 않으시면 eval여기 문서에서 삭제해 주세요.

업데이트된 코드에서 를 eval평가할 수 있으므로 echo "1" > ~/Desktop/in/'foo (bis)'여기 문서의 이 줄을 사용하세요.


글쎄, "정확하다"는 일반적으로 올바른 단어가 아닙니다. 일반적으로 << EOF(예를 들어 반대 << 'EOF') 여기 문서의 변수와 몇 가지 다른 사항을 확장합니다(귀하의 예에서는 아니지만 일반적으로 작동 방식입니다). 그럼 IFS= read _cmd안돼IFS= read -r _cmd. 마지막으로 eval문자열을 얻습니다. 반드시 그럴 필요는 없습니다.정밀한사용하는 문자열입니다.

한 줄씩 평가하면 여러 줄 명령을 평가할 수 없습니다.

제공한 문자열을 실제로 사용하여 이를 사용하여 작업을 수행하려는 경우가 아니면 << EOF( IFS= read무엇을 하고 있는지 알고 있는 경우) 스크립트에 직접 코드를 작성하면 됩니다. 결국, 계산을 수행하기 위해 쉘이 스크립트를 해석하기를 원합니다 echo "1" > ~/Desktop/in/foo. 심지어 다른 쉘 프로세스도 필요하지 않습니다. 여기서는 문서가 필요하지 않습니다.

다른 쉘 프로세스에 대한 코드 전처리가 의미가 있을 수도 있지만(어떤 경우에는 조심할 때) eg bash << EOF, not 을 사용해야 합니다 read.


또 다른 점: 코드 조각을 done < <(cat << EOF단순화할 수 있습니다 done << EOF(이 변경 사항은 )코드 끝에서 제거되어야 합니다).

관련 정보