cron에서 실행하면 이 스크립트가 실패하지만 수동으로 실행하면 작동하는 이유는 무엇입니까?

cron에서 실행하면 이 스크립트가 실패하지만 수동으로 실행하면 작동하는 이유는 무엇입니까?

직접 호출하면 잘 작동하지만 cron으로 실행하면 실패하는 비교적 간단한 bash 스크립트가 있습니다. 이것이 실패하는 이유는 무엇이며 cron을 통해 작동하게 하려면 어떻게 해야 합니까?

#!/bin/bash
apt-get update -y
apt-get upgrade -y
apt-get install boinc-client -y

cron이 이를 실행하려고 시도한 후 수동으로 호출하면 다음 오류가 발생합니다.

dpkg was interrupted, you must manually run 'sudo dpkg --configure -a' to correct the problem.

그러나 처음 수동으로 실행하는 한 정상적으로 작동합니다.

답변1

이러한 유형의 질문에 대한 일반적인 대답은 cron 작업이 비대화형, 비로그인 셸에서 실행되므로 대부분의 셸 시작 파일(시스템 전체 파일 /etc과 홈 디렉터리의 개인 도트 파일 모두)이 소스가 아니라는 것입니다( 읽고 실행됨), 대부분의 쉘 시작 파일은 로그인 쉘(컴퓨터에 로그인할 때 표시되는 첫 번째 쉘) 또는 대화형 쉘(사용자가 로그인하기 때문에 터미널, SSH 세션 또는 터미널 에뮬레이터에 연결되는 쉘)에 적용되기 때문입니다. 해당 터미널을 통해 그들과 상호 작용합니다).

따라서 일반적으로 , , 또는 PATH와 같은 위치에서 발생하는 일부 환경 설정(변경 포함)에 실제로 의존하는 크론 작업에 명령을 입력하면 해당 설정은 크론 작업에 대해 발생하지 않습니다. cron 파일 형식을 사용하면 작업에 대한 환경 변수를 지정할 수 있으므로 소스에 대한 셸 시작 스크립트에서 이를 지정 하거나 가리킬 수 있습니다. 매뉴얼 페이지 의 "호출" 섹션을 참조하십시오 ./etc/profile/etc/bashrc~/.profile~/.bashrcBASH_ENVENVbash(1)

답변2

이것은 답변의 자격이 없지만 논평할 수는 없습니다. 제안:

  1. bash 스크립트 앞에 다음을 추가하십시오. 메일 출력에 기록된 마지막 줄은 실패한 명령이 됩니다.

    set -x
    set -e
    
    • postfixsendmail이 있는지 확인하십시오( 또는 같은 제공 패키지 설치 esmtp).
    • 메일 리더 설치(권장 mutt)
    • 메일이 당신에게 도착했는지 확인하세요
      • postfix를 통해(설치 프로그램에 의해 자동으로 수행될 수 있음): root: my-user-name추가 /etc/aliases또는/etc/postfix/aliases
      • cron을 통해: MAILTO="my-user-name"적절한 crontab파일 에 추가
  2. 스크립트가 다른 환경에서 실행되는지 확인합니다. apt-get에 대한 전체 경로를 지정하고(apt-get이 발견된 것으로 알려졌으므로 범인이 아닐 수도 있음) X 외부의 콘솔(터미널이 아님)에서 실행합니다(일부 dpkg 구성 스크립트에는 X 세션이 필요함).

    • 절대 경로를 사용하도록 스크립트를 수정합니다. 즉, /usr/bin/apt-get update -y(올바른 경로로 교체)
    • 눌러서 콘솔로 전환ctrl-alt-f1
    • 루트 사용자로 전환:sudo -i
    • 환경 없이 비로그인 쉘을 시작하십시오: env -i /bin/bash --noprofile --norc(올바른 경로로 바꾸십시오)
    • 스크립트를 실행하십시오: /my/full/path/to/cronscript. 작동합니까?
  3. 스크립트에 권한이 있습니까? 시스템 crontab을 사용하고 있습니까? (다시 한번 말씀드리지만 범인은 아닐 가능성이 높습니다)

    • 시스템 crontab을 사용한다고 밝혔으므로 이 부분은 건너뜁니다.
  4. apt-get에는 세션 지원(consolekit 또는 systemd)이 필요합니까? 그러나 이것은 단지 어둠 속에서의 촬영일 뿐입니다.

    • 도움이 될 만큼 지식이 부족합니다.

답변3

무슨 일이 일어나고 있는지 거의 이해하지 못한 채 문제를 해결했습니다. 루트 crontab에서 실행 중이더라도 apt-get 명령 앞에는 여전히 sudo가 필요하다는 것이 밝혀졌습니다. 논리적으로 나는 스크립트가 이미 "루트로" 실행 중이므로 필요하지 않을 것이라고 예상했지만 sudo를 추가하면 모든 것이 예상대로 정확하게 작동했습니다.

관련 정보