Bash 스크립트에서 복잡한 명령 실행

Bash 스크립트에서 복잡한 명령 실행

Bash 스크립트 내에서 다음 명령을 실행하려고 합니다.

rm -rf `ls -t ${FOLDER}/other_folder | awk 'NR>5'`

그리고 나는 다음과 같은 것을 시도하고 있습니다.

RM_CMD="$(rm -rf 'ls -t ${FOLDER}/other_folder | awk NR>5')"

나중에 명령이 실제로 실행되기를 원하는 함수에서 사용됩니다.

여러 변형을 시도했지만 항상 실패합니다. 여기서 올바른 접근 방식은 무엇입니까?

-편집하다-

추가 정보

내가 다음과 같은 것을 시도하면

RM_CMD="rm -rf `ls -t ${FOLDER}/other_folder | awk 'NR>5'`"

명령을 즉시 실행하려고 시도하는 것 같습니다. 이는 제가 의도한 바가 아니지만(나중에 실행하기 위해 올바른 명령을 저장하고 싶습니다) 모든 올바른 값을 가져옵니다. 즉, 아무것도 비어 있지 않습니다.

-편집 2-

다음과 같이 명령을 최대한 분할해 보았습니다.

LS_CMD="ls -t ${FOLDER}/other_folder"    
AWK_CMD="awk 'NR>5' ${LS_CMD}"    
RM_CMD="rm -rf '${AWK_CMD}'"

하지만 이런 문제가 발생합니다.

+ ssh -t user@server 'rm -rf '\''awk '\''NR>5'\'' ls -t /full/path/to/folder/other_folder'\'''
bash: 5 ls -t /full/path/to/folder/other_folder: No such file or directory

답변1

일반적으로 이와 같은 질문에 대한 대답은 다음을 읽어 보는 것입니다.BashFAQ #50: "변수에 명령을 넣으려고 하는데 복잡한 경우가 항상 실패합니다!". 간략한 요약: 변수는 실행 가능한 코드가 아닌 데이터용이며, 변수에 코드를 넣으려고 하면 온갖 문제가 발생합니다.

하지만 이 경우에는 또 다른 중요한 요소가 있습니다. 를 통해 명령을 실행한다는 것입니다 ssh. 이는 해당 명령이 원격 시스템으로 전달된다는 의미입니다.데이터로, 원격 컴퓨터의 셸에서 명령으로 구문 분석됩니다. 이는 스크립트(로컬 컴퓨터)의 변수에 명령(데이터)을 저장하는 것이 합리적이라는 것을 의미합니다.

당신이 겪고있는 가장 큰 문제는 역 따옴표를 사용하거나 $( )작은 따옴표로 묶이지 않은 경우 내부 명령이 즉시 (로컬 컴퓨터에서) 실행되고 그 출력이 다음 위치에 저장된다는 것입니다. 변수. 이를 방지하려면 변수를 정의할 때 관련 문자를 이스케이프 처리하면 됩니다.

RM_CMD="rm -rf \$(ls -t '${FOLDER}/other_folder' | awk 'NR>5')"

$( )일반적으로 선호되는 역따옴표 대신 역따옴표를 사용했습니다 . 제가 보기엔 당신이 어떤 점에서 작은따옴표와 역따옴표를 혼동한 것 같습니다. 비슷해 보이지만 완전히 다른 효과를 가지고 있습니다. $( )본질적으로 동일한 작업을 수행하지만 시각적으로 모호하지는 않습니다.

또한 는 로컬 컴퓨터의 변수라고 가정하므로 ${FOLDER}즉시 확장해야 합니다(그리고 공백이나 다른 셸 메타 문자가 포함된 경우에는 작은따옴표를 추가했습니다). 원격 셸로 확장하려면 \"\${FOLDER|/other_folder\"대신 사용하세요. 실제로 ${FOLDER}작은따옴표 자체가 포함되어 있으면 작은따옴표를 넣는 것은 작동하지 않습니다. 이 문제를 해결할 방법이 있지만 여기서는 신경 쓰지 않았습니다.

변수 할당에 작은 따옴표를 사용할 수도 있지만 명령에서 작은 따옴표로 인해 문제가 발생할 수 있습니다 awk(작은 따옴표로 묶인 문자열에 작은 따옴표를 중첩하는 명확한 방법은 없습니다). ${FOLDER}로컬 컴퓨터에서 확장합니다 . 이는 혼합 인용으로 해결할 수 있지만 지저분합니다.

마지막으로 변수를 사용할 때는 큰따옴표로 묶어야 합니다.

ssh -t user@server "$RM_CMD"

... 이 특별한 경우에는 문제가 되지 않지만 큰따옴표가 아닌 변수 참조에는 문제가 발생할 수 있는 모든 종류의 것들이 있으므로 일반적으로 큰따옴표를 사용하는 것이 좋습니다.

답변2

다음을 사용하여 bash 스크립트의 일반적인 오류를 확인할 수 있습니다.쉘체크, 온라인으로 작동하지만오프라인 프로그램. 다양한 쉘(shebang으로 식별됨)을 지원하고 스타일 경고도 제공합니다(귀하의 경우 $(...)백틱 대신 사용할 수 있음). 붙여넣은 코드를 실시간으로 편집하고 등급이 어떻게 지정되는지 확인할 수도 있습니다(코딩 스타일에 대한 일반 튜토리얼과 함께 사용하면 도움이 됨) ).

관련 정보