별칭 확장을 통해 입력을 zsh로 파이프하는 방법은 무엇입니까?

별칭 확장을 통해 입력을 zsh로 파이프하는 방법은 무엇입니까?

zsh에 기록의 한 줄을 입력하여 이를 실행하려고 합니다.

cat ~/.zsh_history | cut -d ';' -f 2 | sk --tac | zsh

대화식으로 행을 선택하면 예를 sk들어 .PATHman zsh

ck그러나 확장 프로그램을 실행하는 대신 와 같은 별칭이 있는 경우 cd .. && ls"명령을 찾을 수 없음" 오류가 발생합니다.


편집: 또한 다음을 입력하면:

echo "cd .. && ls" | zsh

상위 디렉터리에서 실행한 결과를 인쇄 ls하지만 명령이 종료되면 하위 디렉터리의 원래 프롬프트로 돌아갑니다. 마치 프롬프트에 수동으로 입력하고 Enter 키를 누른 것처럼 zsh에서 파이프로 연결된 내용을 처리하도록 하는 방법이 있습니까?

답변1

코드를 파이프하여 zsh별도의 프로세스에서 코드를 실행합니다. 이 프로세스에는 별칭 및 함수(읽지 않음 .zshrc)와 같은 대화형 설정이 없으며 셸 변수 및 현재 셸의 기타 상태도 없습니다. 다른 프로세스가 종료되면 해당 프로세스의 상태(예: 현재 디렉터리)가 손실됩니다.

eval현재 셸 프로세스에서 코드를 실행하려면 해당 코드를 내장 함수 에 인수(입력이 아님)로 전달하세요 .

eval "$(<~/.zsh_history cut -d ';' -f 2 | sk --tac)"

그러나 기록 항목을 선택하는 특정 사용 사례의 경우 다른 접근 방식이 있습니다. 이것fc내장. 다음 명령은 fcedit_sk임시 파일의 이름인 하나의 인수를 사용하여 함수를 실행합니다. 이 함수가 호출되면 파일에는 모든 기록 항목( 최신 항목을 나타내는 ${${(kn)history}[1]}가장 오래된 항목의 인덱스 -1)이 포함됩니다. 함수가 반환되면 zsh는 프롬프트에 입력한 대로 파일에 포함된 모든 것을 실행합니다.

fc -e fcedit_sk ${${(kn)history}[1]} -1

파일의 내용을 호출하고 그 출력을 다시 파일에 쓰는 함수를 만듭니다 fcedit_sk. sk그래서 sk이보다 더 쉬운 방법이 있는지 모르겠습니다.

fcedit_sk () {
  local output
  output=$(sk --tac <$1)
  if (($?)); then
    echo >|$1 # Cancelled
  else
    print -lr -- $output >|$1
  fi
}

관련 정보