ssh를 통한 sh 시작 파일


10

sh 쉘이 시작되기 전에 실행해야 할 중요한 명령이 있습니다. 이것은 SSH 명령 ( ssh host somecommand) 및 명령을 실행하는 다른 프로그램 에서 SSH 명령을 전달하는 데 필요 합니다.

내 안에 .profile나는 이것을 가지고있다 :

ihammerhands@wreckcreations:~> cat .profile
#specific environment and startup programs
export PS1="\u@wreckcreations:\w> "
export PYTHONPATH=~/python/lib/python2.4/site-packages
export PATH=$PATH:~/bin:~/python/bin

그러나 이것은 실패합니다.

W:\programming\wreckcreations-site\test-hg>ssh name@host echo $PATH
Enter passphrase for key '/home/Owner/.ssh/id_rsa':
/usr/local/bin:/bin:/usr/bin

누락 된 PATH 옵션을 확인하십시오.

sh 프로파일의 올바른 이름은 무엇입니까? 참고 : 나는 루트 액세스 권한이 없으며 다른 사용자에게 적용하고 싶지 않습니다. 다른 방법이 있습니까?


편집 :에 대한 /bin/sh링크 가 나타납니다 bash. 놀랍게도 내 프로필이 여전히 무시된다는 것입니다. 어떤 제안?


1
매뉴얼 페이지에있는 내용을 반복하고 싶지 않다면 bash 매뉴얼 페이지에서 'INVOCATION'섹션을보십시오. 상단 근처에 있으며 알아야 할 모든 것을 설명합니다.
camh

을 사용해보십시오 ssh name@host -t echo $PATH.
Gert

@Gert 출력은 동일합니다
TheLQ

@camh 매뉴얼 페이지를 아직 확인하지 않았다면이 질문을한다고 생각하십니까? 내가 무대 SSH 명령 및 기타 프로그램의 명령을 실행하는 확실하지 않다 때문에 나는이 특정 문제에 대한 답을 찾을 수있는 그 많은 시간 + 다른 글을 읽을 수 없지만 적이
TheLQ

1
@ TheLQ : 나는 당신을 모른다. 그래서 당신이 맨 페이지를 확인할 것인지 모른다. 내가 아는 것은 대답이 바로 거기에 있다는 것입니다. 그래서 단어마다 단어를 반복하는 대신, 나는 당신에게 그것을 지적했습니다. 좀 더 구체적인 포인터는 비 대화식 쉘을 찾는 것입니다 .ssh 시나리오가 그런 것이기 때문입니다. 매뉴얼 페이지의 내용이 명확하지 않은 경우보다 구체적인 질문을 할 수 있습니다.
camh

답변:


8

질문에 언급 한 명령에 주목할 가치가 있습니다.

ssh name@host echo $PATH

거의 유용하지 않습니다. $ PATH에 대한 변수 대체는 로컬 셸에서 수행되며 원격 시스템에서 echo를 실행하여 로컬 시스템에서 확장 된 경로 변수의 내용을 인쇄하는 ssh로 전달됩니다. 다음은 내 Mac과 네트워크의 Linux 컴퓨터에서 비슷한 작업을 수행하는 예입니다.

LibMBP:~ will$ echo $PATH
/opt/local/bin:/opt/local/sbin:/Users/will/bin:/usr/bin:/bin:/usr/sbin:/sbin:/usr/local/bin:/usr/texbin:/usr/X11/bin
LibMBP:~ will$ ssh warren echo $PATH
will@warren's password: 
/opt/local/bin:/opt/local/sbin:/Users/will/bin:/usr/bin:/bin:/usr/sbin:/sbin:/usr/local/bin:/usr/texbin:/usr/X11/bin
LibMBP:~ will$ ssh warren 'echo $PATH'
will@warren's password: 
/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games
LibMBP:~ will$ 

로컬 쉘이 변수를 확장하지 못하도록 따옴표를 사용하는 방법에 주목하십시오.


Windows Cygwin 랜드에서 작은 따옴표는 Cygwin 또는 명령 프롬프트에서 아무 것도 수행하지 않습니다. 이상하게도 큰 따옴표는 PATH를 Cygwin의 로컬 컴퓨터로 완전히 확장합니다. 그래서 ssh가 나에게 준 것은 내 길이 아니었다. 그것은 서버였다
TheLQ

@TheLQ 작은 따옴표는 Unix 프롬프트 (Cygwin 포함)에 필요하지만 cmd 프롬프트에는 따옴표가 필요하지 않습니다.
Gilles 'SO- 악마 중지'12

12

~/.profile로그인 쉘에 의해서만 실행됩니다. 쉘을 호출하는 프로그램은 쉘이 로그인 쉘이 될지 여부를 결정합니다 ( -쉘 호출에서 0 번째 인수의 첫 번째 문자로). 특정 명령을 실행하기 위해 로그인 할 때는 일반적으로 실행되지 않습니다.

특히 OpenSSH는 명령을 지정하지 않은 경우에만 로그인 쉘을 호출합니다. 따라서 명령을 지정하면 ~/.profile읽을 수 없습니다.

OpenSSH를 사용하면 서버 측에서 환경 변수를 설정할 수 있습니다. 지시문 과 함께 서버 구성 에서 활성화해야합니다 PermitUserEnvironment. 변수는 파일에서 설정할 수 있습니다 ~/.ssh/environment. 공개 키 인증을 사용한다고 가정하면 관련 행의 시작 부분 에 ~/.ssh/authorized_keys: 키를 추가 할 수 있습니다 environment="FOO=bar".

Ssh는 환경 변수 전송도 지원합니다. OpenSSH에서의 SendEnv지시문을 사용하십시오 ~/.ssh/config. 그러나 특정 환경 변수는 AcceptEnv서버 구성에서 지시문 으로 활성화해야 하므로 제대로 작동하지 않을 수 있습니다.

공개 키 인증을 사용하는 한 항상 (이상하게도) 효과가 있다고 생각 되는 것은 파일 command=옵션을 사용하는 것입니다authorized_keys . command옵션이 있는 키 는 지정된 명령을 실행할 때만 적합합니다. 그러나 authorized_keys파일 의 명령 은 환경 변수 SSH_ORIGINAL_COMMAND가 사용자가 지정한 명령으로 설정되어 실행됩니다. 사용자가 명령을 지정하지 않아 대화식 쉘이 필요한 경우이 변수는 비어 있습니다. 따라서 다음과 같은 것을 사용할 수 있습니다 ~/.ssh/authorized_keys(물론 인증 에이 키를 사용하지 않으면 적용되지 않습니다).

command=". ~/.profile; if [ -n \"$SSH_ORIGINAL_COMMAND\" ]; then eval \"$SSH_ORIGINAL_COMMAND\"; else exec \"$SHELL\"; fi" ssh-rsa 

다른 가능성은 서버에서 랩퍼 스크립트를 작성하는 것입니다. 다음과 같은 것 ~/bin/ssh-wrapper:

#!/bin/sh
. ~/.profile
exec "${0##*/}" "$@"

그런 다음 호출이 스크립트에 심볼릭 링크를 만들어 rsync, unison등 패스 --rsync-path='bin/rsync'상의 rsync명령 행 등 다른 프로그램에. 또는 일부 명령을 사용하면 원격으로 실행할 전체 셸 스 니펫을 지정할 수 있으므로 명령을 독립적으로 만들 수 있습니다 --rsync-path='. ~/.profile; rsync'. 예를 들어 rsync를 사용하면을 사용할 수 있습니다 .

로그인 쉘이 bash 또는 zsh인지에 따라 다른 방법이 있습니다. Bash ~/.bashrc는 rshd 또는 sshd에 의해 호출 될 때 항상 대화식이 아니더라도 (로 호출되지는 않더라도) 읽습니다 sh. Zsh는 항상 읽습니다 ~/.zshenv.

## ~/.bashrc
if [[ $- != *i* ]]; then
  # Either .bashrc was sourced explicitly, or this is an rsh/ssh session.
  . ~/.profile
fi

## ~/.zshenv
if [[ $(ps -p $PPID -o comm=) = [rs]shd && $- != *l* ]]; then
  # Not a login shell, but this is an rsh/ssh session
  . ~/.profile
fi

다른 명령이 실행하는 명령은 어떻습니까? 이 경우 Mercurial Hooks가됩니다. 훅이 일을 생각하기 위해서는 머큐리얼이 길에 있어야합니다
TheLQ

비 대화식 ssh 명령으로 프로파일을 실행하도록 지시 한 기술을 사용하십시오. 그들 (중 하나 command=에이 authorized_keys) 투명하게 작동합니다. 다른 서버는 ssh 서버 구성에서 특정 쉘 또는 옵션이 필요합니다. Mercurial에 해당하는 --rsync-path것은 --remotecmd입니다.
Gilles 'SO- 악마 그만

일부 사용자command=
에게는

1

일반적으로 로그인시 bash는 다음에서 명령을 읽습니다.

~ / .bash_profile
~ / .bashrc

bash 맨 페이지에서 :

~ / .bash_profile
로그인 쉘을 위해 실행되는 개인 초기화 파일

~ / .bashrc
개별 대화식 셸 시작 파일


0

나는 이것을 테스트 할 시간이 없지만, 내가 찾은 매뉴얼 페이지를 보았습니다.

man bash : bash가 비 대화식으로 시작될 때 쉘 스크립트를 실행하기 위해, 예를 들어, 환경에서 변수 BASH_ENV를 찾은 후 해당 값이 있으면 확장하고 값을 파일 이름으로 사용합니다. 읽고 실행하십시오. Bash는 다음 명령이 실행 된 것처럼 동작합니다. if [-n "$ BASH_ENV"]; 그때. "$ BASH_ENV"; fi이지만 PATH 변수의 값은 파일 이름을 검색하는 데 사용되지 않습니다.

man ssh : ~ / .ssh / environment 환경 변수에 대한 추가 정의가 들어 있습니다. 위의 환경을 참조하십시오.

이 조합은 ssh가 .profile을 실행하는 방법을 제안합니다.

불행히도 내 서버에는 기본값 인 no로 PermitUserEnvironment가 설정되어있어 작동하지 않습니다 (더 이상 게임 할 시간이 없다고 말했듯이).


환경에 일부 환경 변수를 명시 적으로 명시하여 SSH가 작동하도록해도 다른 프로그램이 명령을 호출 할 때 프로파일이 실행되도록 수정하는 데 도움이되지 않습니다.
TheLQ

귀하의 예에서 환경 변수를 설정하기 만하면됩니다. 다른 작업을 원하십니까?
kasterma

0

(삭제 ... 새로운 사용자로 하나의 하이퍼 링크 만 가질 수 있습니다 ~)

최신 정보

죄송합니다. 위의 링크가 적용되지 않는 비 대화식 세션에 관한 것이 아닙니다.

Bash가 SH 호환 모드에서 시작되면 POSIX® 표준도 준수하면서 sh의 이전 버전의 시작 동작을 최대한 가깝게 모방하려고합니다. 읽은 프로필 파일은 로그인 쉘인 경우 / etc / profile 및 ~ / .profile입니다.

로그인 쉘이 아닌 경우 환경 변수 ENV가 평가되고 결과 파일 이름이 시작 파일의 이름으로 사용됩니다.

시작 파일을 읽은 후 Bash는 POSIX (r) 호환 모드 (시작이 아닌 실행을 위해)에 들어갑니다.

다음과 같은 경우 Bash가 호환 모드에서 시작됩니다.

  • argv [0]의 기본 파일 이름은 sh (:! :주의를 기울인 Linux 사용자에게주의하십시오. :! :)

따라서 문제는 쉘이 이렇게 시작되었지만 왜 실행하지 않는 것입니다.

출처


나는 보았지만 camh에게 어떤 스테이지 ssh 명령과 다른 프로그램 명령이 실행되는지 알 수 없습니다. 매뉴얼 페이지와 기타 안내서를 이미 여러 번 읽었습니다.
TheLQ
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.