깨끗한 환경에서 스크립트를 시작하는 방법은 무엇입니까?

깨끗한 환경에서 스크립트를 시작하는 방법은 무엇입니까?

다음을 시도했지만 작동하지 않는 것 같습니다.

$ cat script.sh
#!/bin/env -i /bin/sh

/bin/env
$ script.sh
/bin/env: invalid option -- ' '
Try `/bin/env --help' for more information.

답변1

-i /bin/sh이것이 작동하지 않는 이유는 단일 매개변수 로 처리되기 때문입니다 env. 일반적으로 이는 2개의 매개변수가 되며 -i이는 /bin/shshebang의 제한 사항일 뿐입니다. 주변에는 방법이 없습니다.


그러나 다른 방식으로 이 작업을 수행할 수도 있습니다.

유사한 작업을 수행할 필요 없이 스크립트 자체에서 이 작업을 수행하려면 env -i script.sh스크립트가 자체적으로 다시 실행되도록 할 수 있습니다.

#!/bin/sh
[ -z "$CLEANED" ] && exec /bin/env -i CLEANED=1 /bin/sh "$0" "$@"

CLEANED환경 변수가 설정되지 않으면 스크립트가 자동으로 다시 실행됩니다. 그런 다음 재실행 시 루프에 빠지지 않도록 변수를 설정합니다.

답변2

다음 명령을 사용하여 스크립트를 실행하십시오 env -i.

env -i script.sh

평소와 동일한 스크립트:

#!/bin/sh
# ... your code here

런타임에 이를 명시적으로 명시하지 않고 깨끗한 환경에서 실행하려는 경우. Eduardo Ivanec이 몇 가지 아이디어를 제시합니다.이 답변exec, 환경이 깨끗하지 않은 경우(예: $HOME 정의) 스크립트를 재귀적으로 호출할 수 있습니다.

[ "$HOME" != "" ] && exec -c $0

답변3

Bash를 사용하면 다음과 같은 작업을 수행할 수 있습니다.

#!/usr/bin/bash

set -e
set -u

[ -v HOME ] && exec -c "$0" "$@"

# continue with the rest of the script
# e.g. print the cleaned environment:
export

set -e및 명령이 set -u 꼭 필요한 것은 아니지만 이 접근 방식이 설정되지 않은 변수(예: [ "$HOME" != "" ])에 액세스하는 데 의존하지 않고 설정과 호환된다는 점을 보여주기 위해 포함했습니다 set -e.

HOMEbash는 비대화형 모드에서 스크립트를 실행하므로 테스트 변수는 안전해야 합니다. 즉 ~/.bashrc, (환경 변수를 설정할 수 있는) 등의 구성 파일은 시작 중에 선택되지 않습니다.

출력 예:

declare -x OLDPWD
declare -x PWD="/home/juser"
declare -x SHLVL="1"

답변4

대부분의 답변은 Linux 2 매개변수 shebang 제한(인터프리터 + 단일 매개변수)을 가리키지만 그렇게 할 수 없다고 말하는 것은 잘못된 것입니다. 단일 매개변수로 유용한 작업을 수행할 수 있는 인터프리터로 변경하면 됩니다.

#!/usr/bin/perl -we%ENV=();exec "/bin/sh " . join " ", map "'$_'", @ARGV;
# your sh script here

그것이 하는 일은 (저렴하게 ) 정리 하고 인수를 올바르게 인용하여 호출하는 perl한 줄 스크립트( )를 사용 하여 호출하는 것입니다. 필요한 경우 더 많은 논리를 추가할 수 있습니다 (Linux에서는 문자 수가 제한되어 있기 때문에 많지는 않지만 아마도 128개일 수 있습니다). 변형이 있습니다. 사용-e%ENVenv -iexec /bin/shperlBINPRM_BUF_SIZEawk 이 답변에서이 문제에 대한Shebang의 여러 매개변수

불행히도 이것은 Linux에만 해당되며 여러 shebang 매개변수를 허용하는 시스템에서는 작동하지 않습니다.

perl이 문자열을 단일 인수로 처리하므로인용되지 않음위의 내용은 명령줄에서 일반적으로 수행하는 작업과 같습니다 perl -e ...(따옴표를 추가하면 해당 내용은 보존되고 Perl은 쓸모 없는 상수에 대해 불평하는 경고와 함께 리터럴 문자열만 표시됩니다).

또한 이 방법을 사용하면 동작이 약간 변경된다는 점에 유의하세요. @ARGV일반적으로 매개변수만 포함되고 $0스크립트 이름도 포함되지만, 이 shebang을 사용하면 매개변수를 더 쉽게 $ARGV[0]생성할 수 있는 스크립트 이름이 포함 됩니다 .exec()$0-e

-c또한 AT&T가 ksh93했던 것처럼 (추가 매개변수 없이) 명령줄을 "재처리"하는 인터프리터를 사용하여 이 문제를 해결할 수도 있습니다 .

#!/bin/ksh /usr/bin/env -i /bin/sh

ksh지금은 덜 일반적일 수도 있지만 ;-)

( bash유사한 기능으로 --wordexp,하지만작동하는 버전에서는 "문서화되지 않았으며" 문서화된 버전에서는 컴파일 타임에 활성화되지 않습니다. :-/ 두 개의 인수가 필요하기 때문에 이 목적으로도 사용할 수 없습니다...)

또한 실제로 @Patrick 및 @maxschlepzig의 답변이 변형되었습니다.

#!/bin/bash
[ "$_" != bash ] && exec -c -a "bash" /bin/bash "$0" "$@"
# your script here

새 변수 가 아닌 특수한 " _" 변수를 사용하며 완전히 "bash"로 설정되지 않은 경우 스크립트를 execusing 으로 대체하여 "bash"만 -a만들고 using을 사용하여 환경을 지웁니다.ARGV[0]$_-c

또는 스크립트 시작 부분에서 환경을 정리할 수 있는 경우(bash에만 해당):

#!/bin/sh
unset $(compgen -e)
# your script here

(완성 도우미)를 사용하여 compgen내보낸 모든 환경 변수의 이름을 나열하고 unset한 번에 모두 저장합니다.

당신은 또한 볼 수 있습니다Shebang의 여러 매개변수Shebang 동작과 관련된 일반적인 문제에 대한 자세한 내용입니다.

관련 정보