쉘 스크립트 내의 현재 쉘에서 프로그램 실행

쉘 스크립트 내의 현재 쉘에서 프로그램 실행

.ssh 구성을 구문 분석하고 fzf로 항목을 선택한 다음 해당 호스트에 연결하는 작은 쉘 스크립트를 만들었습니다.

#!/bin/bash

set -o nounset -o errexit -o pipefail

list_remote_hosts()
{
    choice="$(cat $HOME/.ssh/config | awk -v RS= -v FS=\\n -v IGNORECASE=1 '
        {
            ip = ""
            alias = ""
            id_file = ""
            username = ""
            port = ""

            for (j = 1; j <= NF; ++j) {
                split($j, tmp, " ")
                if (tmp[1] == "Host") { alias = tmp[2] }
                if (tmp[1] == "Hostname") { ip = tmp[2] }
                if (tmp[1] == "IdentityFile") { id_file = tmp[2] }
                if (tmp[1] == "User") { username = tmp[2] }
                if (tmp[1] == "Port") { port = tmp[2] }
            }

            if (ip || alias && alias != "*") {
                if (port == "")
                {
                    port = "22"
                }
                print "ssh " username "@" ip " -i " id_file " -p " port
            }
        }
    ' | fzf)"

    "$($choice)"
}

list_remote_hosts

작동하지만 현재 쉘에 소유권을 부여하는 데 문제가 있습니다. 연결되면 스크립트가 정지됩니다(ssh가 제가 생각하는 하위 쉘에서 시작되기 때문입니다). 예를 들어 exit를 입력하고 ssh 명령이 종료되면 출력을 볼 수 있습니다.

스크립트가 실행될 때 현재 셸에 자동으로 소유권을 부여하여 터미널 내에서 ssh 명령을 실행하는 것과 동일한 동작을 얻고 싶습니다.

or 을 추가 && zsh하거나 사용하는 것과 같은 모든 종류의 작업을 시도했지만 이들 중 어느 것도 작동하지 않았습니다. 어떻게 해야 하나요?evalexec

답변1

"$($choice)"간단히(따옴표 없음)로 변경해 보십시오 $choice. 그러면 awk 출력이 단어로 확장되고 현재 프로세스에서 ssh 명령이 생성됩니다.


이건 문제가 될 수도 있을 것 같은데

if (ip || alias && alias != "*") {
    if (port == "") port = "22"
    print "ssh " username "@" ip " -i " id_file " -p " port
}

ip비어 있지만 alias비어 있으면 어떻게 되나요 ? 블록을 입력하지만 별칭 변수는 어디에서나 사용하지 않습니다. 당신은 원할 수도 있습니다

if (!ip) { ip = alias }
if (ip && ip != "*") { ...

이는 함수를 구조화하는 또 다른 방법으로 작동할 수 있습니다. 테스트되지 않음:

remote_host_connect() {
    awk '...' $HOME/.ssh/config \
    | fzf \
    | sh </dev/tty >/dev/tty 2>&1
}

이것은 독립형 스크립트로 작동합니다.

#!/bin/bash
eval "$(
    awk -v RS= -F'[[:space:]]+' '{
        for (i=1; i<NF; i+=2)
            data[$i]=$(i+1)
        ip = (data["HostName"] ? data["HostName"] : data["Host"])
        if (ip && ip != "*")
            printf "ssh %s@%s %s %s\n",
                (data["User"] ? data["User"] : ENVIRON["LOGNAME"]),
                ip,
                (data["IdentityFile"] ? "-i " data["IdentityFile"] : ""),
                "-p " (data["Port"] ? data["Port"] : 22)
    }' ~/.ssh/config \
    | fzf
)"

관련 정보