[[ 또는 [를 사용하면 "if pgrep"이 더 이상 작동하지 않습니다.

[[ 또는 [를 사용하면 "if pgrep"이 더 이상 작동하지 않습니다.

goland.shprocess()가 실행 중인지 감지하려고 합니다 . 나는 이것을 사용했습니다 :

#!/bin/bash

if pgrep "goland.sh" >/dev/null 2>&1 ; then
    echo "running"
    exit 1
fi

echo "not running"

이것은 작동하지만 두 가지를 이해하지 못합니다.

  1. 사용하면 작동하지 않는 이유는 무엇입니까? if [[ pgrep "goland.sh" >/dev/null 2>&1 ]] ; then(프로세스가 실행 중이 아니더라도 항상 "실행 중"을 인쇄합니다.)
  2. 사용하면 작동하지 않는 이유는 무엇입니까? if [ pgrep "goland.sh" >/dev/null 2>&1 ] ; then(프로세스가 실행 중이 아니더라도 항상 "실행 중"을 인쇄합니다.)

나는 1이 구문 분석 방법과 관련이 있다고 생각 >하지만 2에 대해서는 완전히 단서가 없습니다.

답변1

쉘의 테스트 구성 [ ... ](또는 [[ ... ]]Bash의 경우)이 어떻게 작동하는지에 대한 오해가 있는 것 같습니다.

  • if문은 뒤에 오는 명령이 0"오류 없음"을 의미하고 "true"로 해석되는 종료 상태를 반환하는지 확인합니다. 그렇다면 실행은 then스크립트의 분기로 전환됩니다(참조:배쉬 매뉴얼예를 들어).
  • 패턴과 일치하는 프로세스를 찾으면 pgrep명령은 "true"를 반환합니다 . 그렇기 때문에 인스턴스가 활성화된 경우에만 이를 얻을 수 있습니다 0.runninggoland.sh
  • 이것은 [파일, 문자열 및 숫자에 대한 테스트를 수행할 수 있는 특수 명령(일반적으로 쉘 내장)이며 여는 괄호와 닫는 대괄호 사이의 조건이 true인 경우 "true"를 반환합니다. 그러나 특정 구문에 따라 하나 이상의 피연산자에 대한 연산이 참인지 확인하도록 설계되었습니다. 예를 들어 한 숫자(연산자 1)가 다른 숫자(연산자 2)보다 큰지 여부(연산자)입니다. 예를 들어, 쉘 변수 n의 값이 이라고 가정하면 5테스트는
    [ "$n" -gt 5 ]
    
    true를 반환하고 명령문에 대한 테스트 명령으로 사용되면 실행이 분기 if로 전환됩니다 .then
  • 예를 들어 문자열이 비어 있는지, 파일이 존재하는지 및/또는 실행 가능한지 등을 확인할 수 있도록 여러 테스트 구조가 정의되어 있습니다. 그러나 모든 경우에 [ ... ]예상된 결과를 얻으려면 중간에 있는 코드의 올바른 구문을 이해해야 합니다 .

이제 테스트 구성 괄호 안에 "원시" 셸 명령이 포함되어 있습니다. 그러면 상황에 따라 상황이 다소 달라지지만, 유효한 연산자 없이 대괄호 사이에 여러 개의 (상수) 문자열 토큰이 있기 때문에 구문 오류가 발생합니다.

  • 사용하면 [[ ... ]]Bash 구문 요소이고 Bash가 잘못된 구문을 인식하기 때문에 즉시 구문 오류가 발생합니다.
  • 그러나 이런 일이 발생하면 [ ... ]명령이 자동 [으로 실패합니다.주문하다(일반적으로 내장되어 있지만) 인수가 미리 정의된 연산자에 대해 의미가 있을 것으로 예상하고 마지막 인수가 끝 인수가 될 것으로 예상합니다 ]. 그러나 오류 출력을 로 리디렉션했기 때문에 /dev/null오류 메시지가 손실됩니다. .
  • running두 경우 모두 항상 잘못된 구문으로 나타나는 출력을 재현할 수 없습니다.

요약하자면, 테스트에 사용하는 프로그램은 실행 중인 프로세스가 발견되면 이미 "true"를 반환하므로 [ ... ](또는 ) 구문을 사용할 필요가 없습니다 . [[ ... ]]테스트를 기반으로 하고 싶다면산출, pgrep"명령 대체"를 사용해야 합니다 $(pgrep ...)(물론 출력 리디렉션도 제거 /dev/null).

쉘 스크립트를 확인하는 것이 좋습니다shellcheck는 구문(및 일부 논리) 오류를 방지하기 위해 많은 Linux 배포판에서 독립 실행형 프로그램으로도 사용할 수 있습니다.

관련 정보