다음을 통해 공유


셸 통합

터미널 1.15 미리 보기부터 Windows 터미널은 일부 "셸 통합" 기능을 실험적으로 지원하기 시작했습니다. 이러한 기능을 사용하면 명령줄을 더 쉽게 사용할 수 있습니다. 이전 릴리스에서는 셸을 사용하여 터미널에 현재 작업 디렉터리가 무엇인지 알릴 수 있도록 했습니다. 이제 셸이 터미널 출력의 일부를 "프롬프트", "명령" 또는 "출력"으로 의미상 설명할 수 있도록 더 많은 시퀀스에 대한 지원을 추가했습니다. 셸은 명령의 성공 또는 실패 여부를 터미널에 알릴 수도 있습니다.

터미널 v1.18에서 출시한 셸 통합 기능 중 일부에 대한 가이드입니다. 향후 이러한 기능을 기반으로 더 많은 기능을 빌드할 계획이므로 사람들이 이러한 기능을 사용하는 방법에 대한 추가 피드백을 얻고 싶습니다.

참고: 터미널 1.21을 기준으로 표시는 이제 안정적인 기능입니다. 1.21 이전에는 터미널의 미리 보기 빌드에만 표시를 사용할 수 있었습니다. 1.21 이전 버전의 터미널을 사용하는 경우 설정의 showMarksOnScrollbar 이름이 지정 experimental.showMarksOnScrollbar되고 autoMarkPrompts 이름이 지정 experimental.autoMarkPrompts되었습니다.

어떻게 작동하나요?

셸 통합은 셸(또는 명령줄 애플리케이션)이 터미널에 특수한 "이스케이프 시퀀스"를 쓰도록 하여 작동합니다. 이러한 이스케이프 시퀀스는 터미널에 인쇄되지 않습니다. 대신 터미널에서 애플리케이션에서 진행 중인 작업을 자세히 파악하는 데 사용할 수 있는 메타데이터 비트를 제공합니다. 이러한 시퀀스를 셸의 프롬프트에 고정하면 셸에서 셸만 알고 있는 정보를 터미널에 지속적으로 제공할 수 있습니다.

다음 시퀀스의 경우:

  • OSC은(는) 이스케이프 문자 "\x1b]"와 그 뒤에 오는 문자열 ]
  • ST은(는) "문자열 종결자"이며, \x1b\(ESC 문자 뒤에 \이(가) 오는 문자) 또는 \x7(BEL 문자) 중 하나일 수 있음
  • 공백은 단지 예시일 뿐입니다.
  • <>의 문자열은 다른 값으로 대체해야 하는 매개 변수입니다.

터미널 v1.18을 기준으로 지원되는 관련 셸 통합 시퀀스는 다음과 같습니다.

  • OSC 133 ; A ST ("FTCS_PROMPT") - 프롬프트의 시작입니다.
  • OSC 133 ; B ST ("FTCS_COMMAND_START") - 명령줄의 시작(읽기: 프롬프트의 끝)입니다.
  • OSC 133 ; C ST ("FTCS_COMMAND_EXECUTED") - 명령 출력의 시작/명령줄의 끝입니다.
  • OSC 133 ; D ; <ExitCode> ST ("FTCS_COMMAND_FINISHED") - 명령의 끝입니다. ExitCode ExitCode이(가) 제공된 경우 터미널은 0을(를) "성공" 및 기타 모든 것을 오류로 처리합니다. 생략하면 터미널은 표시를 기본 색으로 그대로 둡니다.

셸 통합 표시를 사용하도록 설정하는 방법

이러한 기능을 지원하려면 셸과 터미널 간의 협력이 필요합니다. 터미널에서 이러한 새로운 기능을 사용하도록 설정하고 셸의 프롬프트를 수정해야 합니다.

터미널에서 이러한 기능을 사용하도록 설정하려면 설정에 다음을 추가해야 합니다.

"profiles":
{
    "defaults":
    {
        // Enable marks on the scrollbar
        "showMarksOnScrollbar": true,

        // Needed for both pwsh, CMD and bash shell integration
        "autoMarkPrompts": true,

        // Add support for a right-click context menu
        // You can also just bind the `showContextMenu` action
        "experimental.rightClickContextMenu": true,
    },
}
"actions":
[
    // Scroll between prompts
    { "keys": "ctrl+up",   "command": { "action": "scrollToMark", "direction": "previous" }, },
    { "keys": "ctrl+down", "command": { "action": "scrollToMark", "direction": "next" }, },

    // Add the ability to select a whole command (or its output)
    { "command": { "action": "selectOutput", "direction": "prev" }, },
    { "command": { "action": "selectOutput", "direction": "next" }, },

    { "command": { "action": "selectCommand", "direction": "prev" }, },
    { "command": { "action": "selectCommand", "direction": "next" }, },
]

셸에서 이러한 표시를 사용하도록 설정하는 방법은 셸마다 다릅니다. CMD, PowerShell 및 Zsh에 대한 자습서는 다음과 같습니다.

PowerShell(pwsh.exe)

이전에 PowerShell 프롬프트를 변경한 적이 없는 경우 먼저 about_Prompts를 확인해야 합니다.

CWD에 대해 터미널에 알리고 프롬프트를 적절한 표시로 표시하려면 prompt을(를) 편집해야 합니다. 또한 PowerShell을 사용하면 이전 명령의 오류 코드를 133;D 시퀀스에 포함할 수 있습니다. 그러면 명령이 실패하거나 실패한 경우 터미널에서 자동으로 표시 색을 지정할 수 있습니다.

다음을 PowerShell 프로필에 추가합니다.

$Global:__LastHistoryId = -1

function Global:__Terminal-Get-LastExitCode {
  if ($? -eq $True) {
    return 0
  }
  $LastHistoryEntry = $(Get-History -Count 1)
  $IsPowerShellError = $Error[0].InvocationInfo.HistoryId -eq $LastHistoryEntry.Id
  if ($IsPowerShellError) {
    return -1
  }
  return $LastExitCode
}

function prompt {

  # First, emit a mark for the _end_ of the previous command.

  $gle = $(__Terminal-Get-LastExitCode);
  $LastHistoryEntry = $(Get-History -Count 1)
  # Skip finishing the command if the first command has not yet started
  if ($Global:__LastHistoryId -ne -1) {
    if ($LastHistoryEntry.Id -eq $Global:__LastHistoryId) {
      # Don't provide a command line or exit code if there was no history entry (eg. ctrl+c, enter on no command)
      $out += "`e]133;D`a"
    } else {
      $out += "`e]133;D;$gle`a"
    }
  }


  $loc = $($executionContext.SessionState.Path.CurrentLocation);

  # Prompt started
  $out += "`e]133;A$([char]07)";

  # CWD
  $out += "`e]9;9;`"$loc`"$([char]07)";

  # (your prompt here)
  $out += "PWSH $loc$('>' * ($nestedPromptLevel + 1)) ";

  # Prompt ended, Command started
  $out += "`e]133;B$([char]07)";

  $Global:__LastHistoryId = $LastHistoryEntry.Id

  return $out
}

오 마이 포쉬 설정

오- 마이 포쉬를 사용? 위의 내용을 약간 수정하여 원래 프롬프트를 숨긴 다음 셸 통합 이스케이프 시퀀스의 중간에 다시 추가하려고 합니다.

# initialize oh-my-posh at the top of your profile.ps1
oh-my-posh init pwsh --config "$env:POSH_THEMES_PATH\gruvbox.omp.json" | Invoke-Expression
# then stash away the prompt() that oh-my-posh sets
$Global:__OriginalPrompt = $function:Prompt

function Global:__Terminal-Get-LastExitCode {
  if ($? -eq $True) { return 0 }
  $LastHistoryEntry = $(Get-History -Count 1)
  $IsPowerShellError = $Error[0].InvocationInfo.HistoryId -eq $LastHistoryEntry.Id
  if ($IsPowerShellError) { return -1 }
  return $LastExitCode
}

function prompt {
  $gle = $(__Terminal-Get-LastExitCode);
  $LastHistoryEntry = $(Get-History -Count 1)
  if ($Global:__LastHistoryId -ne -1) {
    if ($LastHistoryEntry.Id -eq $Global:__LastHistoryId) {
      $out += "`e]133;D`a"
    } else {
      $out += "`e]133;D;$gle`a"
    }
  }
  $loc = $($executionContext.SessionState.Path.CurrentLocation);
  $out += "`e]133;A$([char]07)";
  $out += "`e]9;9;`"$loc`"$([char]07)";
  
  $out += $Global:__OriginalPrompt.Invoke(); # <-- This line adds the original prompt back

  $out += "`e]133;B$([char]07)";
  $Global:__LastHistoryId = $LastHistoryEntry.Id
  return $out
}

명령 프롬프트

명령 프롬프트는 PROMPT 환경 변수에서 프롬프트를 표시합니다. CMD.exe 문자로 읽습니다 $e ESC . 안타깝게도 CMD.exe는 프롬프트에서 이전 명령의 반환 코드를 가져올 방법이 없으므로 CMD 프롬프트에서 성공/오류 정보를 제공할 수 없습니다.

다음을 실행하여 현재 CMD.exe 인스턴스에 대한 프롬프트를 변경할 수 있습니다.

PROMPT $e]133;D$e\$e]133;A$e\$e]9;9;$P$e\$P$G$e]133;B$e\

또는 이후의 모든 세션에 대한 명령줄에서 변수를 설정할 수 있습니다.

setx PROMPT $e]133;D$e\$e]133;A$e\$e]9;9;$P$e\$P$G$e]133;B$e\

이러한 예제에서는 현재 사용자의 PROMPT이(가) $P$G(이)라 가정합니다. 대신 다음과 같이 현재 프롬프트를 래핑하도록 선택할 수 있습니다.

PROMPT $e]133;D$e\$e]133;A$e\$e]9;9;$P$e\%PROMPT%$e]133;B$e\

Bash

bash에서 셸 통합을 사용하도록 설정하려면 다음을 끝에 추가할 수 있습니다 ~/.bashrc .

PS1="\[\033]133;D;\007\]\[\033]133;A;\007\]$PS1\[\033]133;B;\007\]"

이렇게 하면 셸 통합을 사용하도록 설정하는 데 필요한 시퀀스로 기존 $PS1 항목을 래핑합니다.

참고: 즐겨찾는 셸이 여기에 표시되지 않나요? 당신이 그것을 알아 내는 경우, 원하는 셸에 대한 솔루션을 기여 주시기 바랍니다!

셸 통합 기능

동일한 작업 디렉터리에서 새 탭 열기

동일한 작업 디렉터리에서 새 탭 열기

스크롤 막대에서 각 명령에 대한 표시 보이기

스크롤 막대에서 각 명령에 대한 표시 보이기

명령 간에 자동으로 이동

위에서 정의한 scrollToMark 대로 작업을 사용합니다.

명령 간에 자동으로 이동

명령의 전체 출력 선택

이 gif에서는 바인딩된 selectOutput ctrl+g 작업을 사용하여 명령의 전체 출력을 선택합니다. 명령의 전체 출력 선택

다음은 이 설정을 사용하여 experimental.rightClickContextMenu 터미널에서 마우스 오른쪽 단추로 클릭하는 상황에 맞는 메뉴를 사용하도록 설정합니다. 해당 및 셸 통합을 사용하도록 설정하면 명령을 마우스 오른쪽 단추로 클릭하여 전체 명령 또는 해당 출력을 선택할 수 있습니다.

마우스 오른쪽 단추로 클릭 상황에 맞는 메뉴를 사용하여 명령을 선택합니다.

최근 명령 제안

셸 통합을 사용하도록 설정하면 최근 명령도 표시하도록 제안 UI를 구성할 수 있습니다.

최근 명령을 보여 주는 제안 UI

다음 작업을 사용하여 이 메뉴를 열 수 있습니다.

{
    "command": { "action": "showSuggestions", "source": "recentCommands", "useCommandline": true },
},

(자세한 내용은 다음을 참조하세요 .제안 설명서)

추가 리소스