`source` 명령의 반대


9

source변수 값을 읽거나 인쇄하기 위해 bash 스크립트에서 명령을 사용 합니다.

more linuxmachines_mount_point.txt

export linuxmachine01="sdb sdc sdf sdd sde sdg"
export linuxmachine02="sde sdd sdb sdf sdc"
export linuxmachine03="sdb sdd sdc sde sdf"
export linuxmachine06="sdb sde sdf sdd"

source  linuxmachines_mount_point.txt

echo $linuxmachine01
sdb sdc sdf sdd sde sdg

source변수를 설정 해제하기 위해 반대는 무엇입니까 ?

예상 결과

echo $linuxmachine01

< no output >

14
그것은 source환경에서 변수를 설정하는 것이 아니라 export파일 의 명령문을 설정하는 것 source입니다. 따라서 같은 변수 를 가진 다른 파일 인 경우 반대가 source될 수 있습니다 . sourcesourceunset
user4556274

2
yael, 내보내기를 사용하지 말고 name = "val"만 사용하십시오. 내보내기는 스크립트-바이너리 변수 (환경)입니다.
ctrl-d


2
이것은 불가능 해. 찾고있는 개념을 가역 컴퓨팅 이라고 합니다. 프로그래밍 언어는 뒤집을 수 있도록 몇 가지 심각한 제한 사항 으로 특별히 설계 해야합니다 . Bash는 그러한 프로그래밍 언어 중 하나가 아닙니다.
Jörg W Mittag

1
@yael, 그것은 사실이 아닙니다 (그리고 당신은 ctrl-d에게 지시하는 테스트를 결코 결코 실행하지 않았습니다); 당신은 절대적으로 필요하지 않습니다 export. 모든 exportIS 환경에 값을 복사하지 않습니다 -하지만 쉘 변수로 그들이있는 거 현재 그들은뿐만 아니라 환경 변수로 정의하고 있는지 여부. 또한 불필요한 환경 변수를 정의하면 프로세스 당 동일한 (제한된!) 공간에 저장되므로 최대 명령 줄 길이가 줄어 듭니다.
Charles Duffy

답변:


21

서브 쉘 사용 (권장)

서브 쉘에서 소스 명령을 실행하십시오.

(
source linuxmachines_mount_point.txt
cmd1 $linuxmachine02
other_commands_using_variables
etc
)
echo $linuxmachine01  # Will return nothing

서브 쉘은 parens에 의해 정의됩니다 (...). 서브 쉘이 종료되면 서브 쉘 내에 설정된 모든 쉘 변수가 잊혀집니다.

설정되지 않은 사용

다음으로 내 보낸 변수를 설정 해제합니다 linuxmachines_mount_point.txt.

unset $(awk -F'[ =]+' '/^export/{print $2}' linuxmachines_mount_point.txt)
  • -F'[ =]+' awk에게 공백과 등호의 조합을 필드 구분 기호로 사용하도록 지시합니다.

  • /^export/{print $2}

    이것은 awk에게 시작하는 줄을 선택한 export다음 두 번째 필드를 인쇄하도록 지시 합니다.

  • unset $(...)

    이 명령은 inside 명령을 실행 $(...)하고 stdout을 캡처 한 후 출력에 의해 명명 된 변수를 설정 해제합니다.


`awk '{print $ 2}'파일에서 i를 사용하지 않는 이유 | awk -F "=" '{print $ 1}'`; 설정을 해제 $ i; 완료? (unset에 대한 더 간단한)
yael

2
@yael 필요없는 추가 프로세스와 루프를 사용합니다. 의견은 다를 수 있지만 더 간단하지는 않습니다. 또한 잠재적으로 위험하기 때문에 모든 줄 file은 내보내기 문 이라고 가정합니다 .
John1024

8
@yael 또한 변수를 설정 해제하고 다른 코드 부작용을 실행 취소하는 것이 서브 쉘의 목적입니다. 그들은 간단하고 확실하게 그것을합니다. 특별한 이유가 없다면, 서브 쉘을 사용해야합니다.
John1024

4

source스크립트를 해제 할 수 없습니다 .

할 수있는 일은 내 보낸 모든 변수를 임시 파일에 저장하고 스크립트를 소싱 한 후 변수와 비교 한 다음 다음과 같이 오버플로를 제거하는 것입니다 unset.

export > temp_file
source myscript

#... do some stuff

unset "$(comm -3 <(sort temp_file) <(export | sort) | awk -F'[ =]' '{print $3}' | tr '\n' ' ')"

`awk '{print $ 2}'파일에서 i를 사용하지 않는 이유 | awk -F "=" '{print $ 1}'`; 설정을 해제 $ i; 완료? (unset에 대한 더 간단한)
yael

@yael 스크립트에 exports 만 포함 된 경우에만 작동합니다 .
jimmij

"export s"라는 의미, 내 파일은 linuxmachine01 = "sdb sdc sdf sdd sde sdg"등을 포함하며 awk 루프를 사용하면 문제없이 변수 설정이 해제됩니다
yael

@yael 파일이 어떻게 생겼는지 모르겠습니다. 예를 들어 스크립트에 맨 위에 "# 마운트 지점으로 내보낼 변수가 있습니다."라는 주석이 포함되어있는 경우와 같은 일반적인 대답이 있습니다.
jimmij

2

unset명령을 사용 하여 변수를 "잊어 버릴"수 있습니다.


파일은 diff machines과 함께있을 수 있으므로 파일의 두 번째 변수를 설정 해제하는 방법은 무엇입니까?
yael

unset variablename은 그것을 잊어 버릴 것입니다 (bash / sh / ksh / zsh 매뉴얼 페이지에서 설명 할 수 있습니다) 데모 : pastebin.com/MGQyTZEA
francois P

예. 그러나 변수가 diff 일 수 있으므로 bash 스크립트는 파일에서 변수를 읽고 설정을 해제하여 변수를 수행해야합니다. 변수를 알 수 없기 때문에 정적
yael

그런 다음 설정을 해제 할 파일의 변수를 나열하기 위해 내보내기 행을 잘라냅니다 (export) linuxmachine06 = "sdb sde sdf sdd"그런 다음 unset 명령 의 이름으로 linuxmachine06을 가져옵니다. pastebin.com/M9eCtLc7 변수 이름을 모르는 경우에만 끝
francois P

좋아, 나는`awk '{print $ 2}'파일에서 i를 설정 해제하기 위해이 문법을 사용할 것이다. | awk -F "=" '{print $ 1}'`; 설정을 해제 $ i; 완료
yael

2

원하는 결과를 얻는 가장 간단한 해결책은 변수를 비어있는 것으로 다시 선언하는 것입니다.

$ export linuxmachine01="sdb sdc sdf sdd sde sdg"
$ echo "$linuxmachine01"
sdb sdc sdf sdd sde sdg

$ linuxmachine01=""
$ echo "$linuxmachine01"
$

물론 변수는 여전히 정의되어 있고 내보내지고 비어 있지만 정의됩니다.

$ declare -p linuxmachine01
declare -x linuxmachine01=""

환경과 실행중인 쉘에서 변수를 올바르게 제거하려면 unset (권장 방법)을 사용해야합니다.

$ unset linuxmachine01
$ declare -p linuxmachine01
bash: declare: linuxmachine01: not found
$ echo "$linuxmachine01"
$

1

가장 간단한 방법은 스크립트를 수정하여 스크립트의 효과를 취소하는 명령을 정의하는 것입니다.

export linuxmachine01="sdb sdc sdf sdd sde sdg"
export linuxmachine02="sde sdd sdb sdf sdc"
export linuxmachine03="sdb sdd sdc sde sdf"
export linuxmachine06="sdb sde sdf sdd"
alias linuxmachines_mount_point='for v in linuxmachine01 linuxmachine02 linuxmachine03 linuxmachine04; do unset $v; done; unalias linuxmachines_mount_point'

왜 함수가 아닌 별칭입니까? 별칭은 비 대화식 쉘에서 기본적으로 비활성화되어 있으므로 기본적으로 스크립트에서 작동하지 않습니다.
Charles Duffy

우리가 정의 된 경우 ... 실제로, 이것은 더 쉽게 될 하나 개의 변수를, 따라서 하나의 해제했다 : declare -A linuxmachines=( [01]="sdb sdc sdf" [02]="sde sdd sdb" [03]="whatever" ), 그것은 단지 unset linuxmachines되돌릴.
Charles Duffy

@CharlesDuffy : 별명과 기능 모두이 목적에 적합합니다. 모든 것을 하나의 변수에 넣지 않는 이유는 실행 취소 명령을 정의하는 것이 훨씬 일반적이기 때문입니다. 변수뿐만 아니라 기능, 별명, 시스템 설정, 터미널 설정 등도 정의 할 수 없습니다. undo 명령의 정확한 내용에 신경 쓸 필요가 없으므로 더 나은 추상화를 제공합니다.
Lie Ryan

위의 요점은 "목적"에 비 대화식 사용 (예 : 스크립트 호출)이 포함되어 있으면 별칭 목적에 적합 하지 않다는 것입니다.
찰스 더피

0

linuxmachines_mount_point.txt를 다음과 같이 작성할 수 있습니다

test "$linuxmachine01" && unset -v linuxmachine01 || linuxmachine01="sdb sdc sdf sdd sde sdg"

변수가 필요할 때

source linuxmachines_mount_point.txt

변수를 제거하고 싶을 때

source linuxmachines_mount_point.txt

0

source명령을 사용하여 를 활성화하는 경우 명령을 VirtualEnvironment사용하여 종료 할 수 있습니다 deactivate.

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.