커맨드 팔레트 47부: VS Code Task 단축키를 물리 키 위치로 고정하기
레이아웃이 바뀌어도 같은 물리 키 위치로 Target Task만 종료되도록 단축키를 고정합니다.
이번 편의 핵심
keybindings.json의 key만 ctrl+[KeyK] ctrl+alt+[KeyT]로 바꾸고 command·args·when은 유지합니다.
완료하면 현재 레이아웃에서 Target만 종료되고 Guard는 계속 실행되며, 실습 규칙과 레이아웃을 원상 복구합니다.
1. 시작하기 전에
예상 시간은 20~30분입니다. 독자는 Workspace Task 실행과 User keybindings.json 편집, Terminal 포커스·텍스트 선택·Find 상태를 이미 확인할 수 있어야 합니다.
준비할 것
- 직접 만든 빈 연습 폴더 — 기존 tasks.json과 업무 파일이 없어야 합니다.
- 현재 User 단축키 전체 백업 — 첫 쓰기 전에 원본과 비교합니다.
- Windows 11 · VS Code Stable 1.137.0 · Windows PowerShell — 이 Run의 로컬 commit은 645f29cc3176500b4b5762ba887cf2a7f0ffdf2c입니다.
- 선택 사항: 이미 설치된 두 번째 Windows 키보드 레이아웃 — 없으면 설치하지 않고 교차 레이아웃 결과를 UNCONFIRMED로 둡니다.
2. 알아둘 핵심 개념
FACT — 문자 키와 물리 위치는 같은 개념이 아닙니다
일반 표기 k와 t는 현재 레이아웃이 해석한 virtual key를 따릅니다. [KeyK]와 [KeyT]는 키보드의 물리 위치를 나타내는 scan code 표기입니다. Microsoft 문서는 scan code 단축키가 레이아웃 변경에도 바뀌지 않는다고 설명합니다. 이 글은 텍스트 입력 동작이 아니라 단축키 선택에만 적용됩니다. [SRC-01] [SRC-04]
FACT — 대괄호와 대소문자도 문법입니다
key 속성은 String입니다. 이 실습의 두 stroke는 ctrl+[KeyK]와 ctrl+alt+[KeyT]이며 한 칸 공백으로 chord를 구분합니다. [KeyK]·[KeyT]는 공식 허용 범위 [KeyA]-[KeyZ]에 들어갑니다. 괄호를 빼거나 [K]처럼 줄이지 않습니다. [SRC-01] [SRC-02] [SRC-03]
FACT — command·args·when은 그대로 유지합니다
바꾸는 필드는 key 하나뿐입니다. command는 workbench.action.tasks.terminate, args는 정확한 실행 중 label인 JCOS Scan Lab Target, when은 45부까지 만든 다섯 조건을 유지합니다. 물리 위치 고정은 Target 선택이나 활성 조건을 넓히지 않습니다. [SRC-01] [SRC-05] [SRC-06]
RECOMMENDATION — 레이아웃 전환은 검증 단계에서만 합니다
Windows 입력 언어 전환은 다른 앱의 입력에도 영향을 줄 수 있습니다. 먼저 현재 레이아웃 이름을 기록하고, 두 번째 레이아웃이 이미 설치된 경우에만 전환 시험을 합니다. 새 언어 팩 설치는 이 글의 범위 밖입니다. [SRC-01] [SRC-04]
3. 순서대로 진행하기
각 단계의 정상 결과를 확인한 뒤 다음 단계로 이동합니다.
1. 빈 연습 폴더를 준비합니다
목적 기존 프로젝트의 Task 설정을 보호합니다.
- 직접 만든 빈 JCOS-VSC47-Scan-Lab 폴더를 File > Open Folder...로 엽니다.
입력 위치 VS Code 메뉴와 Explorer; Workspace Folder 범위
폴더 이름: JCOS-VSC47-Scan-Lab
정상 결과 Explorer 최상위에 연습 폴더만 보입니다.
확인 기존 .vscode/tasks.json과 업무 파일이 0개인지 확인합니다.
실패 신호 다른 프로젝트 파일이나 기존 Task 정의가 보입니다.
복구와 재합류 아무 파일도 쓰지 말고 폴더를 닫은 뒤 새 빈 폴더에서 STEP-01로 재합류합니다.
근거 [SRC-05]
2. 현재 환경과 레이아웃을 기록합니다
목적 시험 전 기준 상태를 남깁니다.
- 별도 PowerShell에서 code --version을 실행하고 Windows 작업 표시줄의 현재 입력 언어 표시를 메모합니다.
입력 위치 Shell: Windows PowerShell; 실행 위치: 임의
code --version
현재 입력 언어: <화면에 보이는 실제 이름>
정상 결과 VS Code 버전·commit과 레이아웃 이름을 기록했습니다.
확인 이 Run 기준 1.137.0과 로컬 commit을 대조합니다. Placeholder는 실제 화면 이름으로 치환합니다.
실패 신호 code를 찾지 못하거나 현재 레이아웃을 식별할 수 없습니다.
복구와 재합류 Help > About으로 버전을 확인합니다. 레이아웃 이름이 불명확하면 교차 레이아웃 시험을 생략하고 STEP-03으로 이동합니다.
3. User 단축키를 백업합니다
목적 전역 설정 변경을 되돌릴 기준을 만듭니다.
- Preferences: Open Keyboard Shortcuts (JSON)을 열고 전체 내용을 연습 폴더의 keybindings-before.jsonc로 복사합니다.
입력 위치 Command Palette와 현재 Profile의 User keybindings.json
keybindings-before.jsonc
정상 결과 백업과 원본의 첫 줄·마지막 줄·객체 수가 같습니다.
확인 원본과 백업을 나란히 비교합니다.
실패 신호 백업이 비었거나 기존 항목이 누락됐습니다.
복구와 재합류 User 파일을 수정하지 말고 백업을 다시 만든 뒤 STEP-03으로 재합류합니다.
근거 [SRC-01]
4. 두 연습 Task를 저장합니다
목적 종료 Target과 보존 Guard를 구별합니다.
- .vscode/tasks.json 전체를 아래 JSON으로 저장합니다.
입력 위치 연습 Workspace의 .vscode/tasks.json
{
"version": "2.0.0",
"tasks": [
{
"label": "JCOS Scan Lab Target",
"type": "process",
"command": "powershell.exe",
"args": [
"-NoLogo",
"-NoProfile",
"-Command",
"$id=[guid]::NewGuid().ToString('N').Substring(0,8); Write-Output ('SCAN_TARGET RUN_ID='+$id); 0..120 | ForEach-Object { Write-Output ('SCAN_TARGET HEARTBEAT='+$_); Start-Sleep -Seconds 1 }"
],
"problemMatcher": [],
"presentation": {
"reveal": "always",
"panel": "dedicated",
"clear": true
}
},
{
"label": "JCOS Scan Lab Guard",
"type": "process",
"command": "powershell.exe",
"args": [
"-NoLogo",
"-NoProfile",
"-Command",
"$id=[guid]::NewGuid().ToString('N').Substring(0,8); Write-Output ('SCAN_GUARD RUN_ID='+$id); 0..120 | ForEach-Object { Write-Output ('SCAN_GUARD HEARTBEAT='+$_); Start-Sleep -Seconds 1 }"
],
"problemMatcher": [],
"presentation": {
"reveal": "always",
"panel": "dedicated",
"clear": true
}
}
]
}
정상 결과 Target과 Guard 두 label이 JSON 오류 없이 저장됩니다.
확인 command가 powershell.exe이고 출력·대기 외 삭제·다운로드·외부 전송이 없는지 읽습니다.
실패 신호 빨간 JSON 오류, 기존 파일 덮어쓰기, 예제 밖 명령이 보입니다.
복구와 재합류 실행하지 말고 오류 원문을 보존합니다. 새 폴더·쉼표·따옴표를 고친 뒤 STEP-04로 재합류합니다.
근거 [SRC-05]
5. 논리 키 규칙을 기준으로 확인합니다
목적 바꾸기 전 key 필드를 분리해서 봅니다.
- 아래 logical_rule을 읽고 key 외 command·args·when 값을 기록합니다. 아직 User 파일에 추가하지 않습니다.
입력 위치 읽기 전용 메모
{
"key": "ctrl+k ctrl+alt+t",
"command": "workbench.action.tasks.terminate",
"args": "JCOS Scan Lab Target",
"when": "taskRunning && terminalFocus && taskTerminalActive && !terminalTextSelected && !terminalFindVisible"
}
정상 결과 기준 key는 ctrl+k ctrl+alt+t이며 네 필드가 분리됩니다.
확인 다음 단계 규칙과 비교할 기준을 한 줄씩 기록합니다.
실패 신호 args label이나 when이 앞선 편과 다릅니다.
복구와 재합류 예제 원문으로 되돌리고 STEP-05에서 다시 비교합니다.
6. scan-code 규칙으로 key만 바꿉니다
목적 같은 명령을 물리 위치 기반 chord에 연결합니다.
- User keybindings.json 배열 끝에 아래 객체 하나를 추가합니다. 기존 항목이 있으면 바깥 대괄호를 복사하지 않습니다.
입력 위치 현재 Profile의 User keybindings.json
{
"key": "ctrl+[KeyK] ctrl+alt+[KeyT]",
"command": "workbench.action.tasks.terminate",
"args": "JCOS Scan Lab Target",
"when": "taskRunning && terminalFocus && taskTerminalActive && !terminalTextSelected && !terminalFindVisible"
}
정상 결과 [KeyK]와 [KeyT]가 대괄호를 포함해 저장되고 JSON 오류가 없습니다.
확인 STEP-05와 비교해 key만 다르고 command·args·when은 동일한지 확인합니다.
실패 신호 [K], KeyK, 따옴표 누락, 중첩 배열 또는 기존 객체 삭제가 보입니다.
복구와 재합류 추가한 객체만 취소하고 백업과 기존 항목을 대조한 뒤 STEP-06으로 재합류합니다.
7. 같은 chord 충돌을 확인합니다
목적 기존 명령을 덮지 않게 합니다.
- Keyboard Shortcuts에서 Record Keys를 켜고 실제 물리 K 자리와 T 자리로 chord를 입력한 뒤 Show Same Keybindings를 확인합니다.
입력 위치 Preferences: Open Keyboard Shortcuts
검색 대상: ctrl+[KeyK] ctrl+alt+[KeyT]
정상 결과 실습 규칙 외 보호할 동일 chord가 없습니다.
확인 Keybinding·When·Source 열을 모두 봅니다.
실패 신호 기본·확장·업무 User 규칙이 같은 chord에서 활성화됩니다.
복구와 재합류 기존 규칙을 삭제하지 말고 미사용 물리 chord를 선택해 두 scan code와 문서의 실제 입력을 함께 바꾼 뒤 STEP-07로 재합류합니다.
근거 [SRC-01]
8. Guard와 Target을 차례로 실행합니다
목적 선택 종료 전 비교 대상을 만듭니다.
- Tasks: Run Task로 Guard를 먼저, Target을 다음에 한 번씩 실행합니다.
입력 위치 Command Palette와 각 전용 Task Terminal
SCAN_GUARD RUN_ID=<실제 값>
SCAN_TARGET RUN_ID=<실제 값>
정상 결과 두 Terminal에서 서로 다른 RUN_ID와 증가하는 HEARTBEAT가 보입니다.
확인 두 label·RUN_ID·현재 heartbeat를 메모합니다.
실패 신호 하나만 실행되거나 marker가 다르거나 예상 밖 명령이 실행됩니다.
복구와 재합류 정확한 연습 Task만 종료하고 STEP-04 정의를 재검토한 뒤 STEP-08로 재합류합니다.
근거 [SRC-05]
9. 현재 레이아웃에서 물리 chord를 누릅니다
목적 scan-code 규칙이 Target에 연결되는지 확인합니다.
- Terminal Find를 닫고 선택 텍스트를 해제한 Target Terminal에 포커스를 둔 뒤 물리 K 자리와 T 자리로 chord를 누릅니다.
입력 위치 Target Task Terminal
입력: Ctrl+[KeyK], 이어서 Ctrl+Alt+[KeyT]
정상 결과 Target heartbeat가 멈추고 Guard heartbeat는 계속 증가합니다.
확인 Tasks: Show Running Tasks와 두 Terminal 출력으로 Target 없음·Guard 실행 중을 교차 확인합니다.
실패 신호 Quick Pick이 뜨거나 Guard가 끝나거나 아무 반응이 없습니다.
복구와 재합류 오류 원문과 두 출력 상태를 보존합니다. 잘못된 label·when·chord를 확인한 뒤 필요하면 STEP-06 또는 STEP-08로 재합류합니다.
10. 다른 기존 레이아웃에서 같은 자리를 시험합니다
목적 표시 문자가 달라도 물리 위치가 유지되는지 관찰합니다.
- 두 번째 Windows 키보드 레이아웃이 이미 설치된 경우에만 입력 언어를 전환하고 Target을 다시 실행한 뒤 같은 물리 K·T 자리를 누릅니다.
입력 위치 Windows 입력 언어 전환과 VS Code Target Terminal
레이아웃 B: <이미 설치된 실제 이름>
같은 물리 위치: [KeyK] → [KeyT]
정상 결과 레이아웃 B에서도 Target만 종료되고 Guard는 계속 실행됩니다.
확인 전환 전후 레이아웃 이름, Target RUN_ID와 Guard heartbeat 증가를 기록합니다.
실패 신호 레이아웃을 전환할 수 없거나 입력 위치를 확신할 수 없습니다.
복구와 재합류 UNCONFIRMED로 기록하고 억지로 설치하지 않습니다. 기본 완료 조건은 현재 레이아웃 시험과 JSON 비교로 유지하며 STEP-11로 이동합니다.
11. Guard를 종료하고 규칙을 제거합니다
목적 실습 프로세스와 User 변경을 정리합니다.
- Tasks: Terminate Task에서 JCOS Scan Lab Guard만 종료한 뒤 User keybindings.json에서 실습 객체 하나만 삭제합니다.
입력 위치 Command Palette와 User keybindings.json
삭제 대상 command: workbench.action.tasks.terminate
args: JCOS Scan Lab Target
key: ctrl+[KeyK] ctrl+alt+[KeyT]
정상 결과 실행 중인 Scan Lab Task가 없고 실습 객체가 사라집니다.
확인 Tasks: Show Running Tasks와 keybindings-before.jsonc를 대조합니다.
실패 신호 다른 User 규칙이 함께 삭제됐거나 Guard가 계속 출력합니다.
복구와 재합류 편집을 중단하고 Undo로 실습 객체 삭제 직전으로 돌아갑니다. 다른 변경이 없을 때만 백업 전체를 복원하고 STEP-11을 재검증합니다.
12. 원래 레이아웃과 완료 조건을 재확인합니다
목적 환경과 설정이 실습 전 상태로 돌아왔는지 확인합니다.
- Windows 입력 언어를 STEP-02의 이름으로 되돌리고, User 파일과 실행 중 Task를 다시 확인합니다.
입력 위치 Windows 작업 표시줄, Keyboard Shortcuts, Tasks: Show Running Tasks
현재 레이아웃=<STEP-02 실제 이름>
Scan Lab Task=0
실습 User 규칙=0
정상 결과 Target만 선택 종료됐던 기록, Guard 지속 기록, 최종 0개 상태가 모두 있습니다.
확인 레이아웃 이름, keybindings-before.jsonc, Tasks: Show Running Tasks를 서로 대조합니다.
실패 신호 레이아웃 이름·User 규칙·실행 Task 중 하나가 실습 전과 다릅니다.
복구와 재합류 원인을 UNKNOWN으로 두고 현재 상태와 오류 원문을 보존합니다. 새 변경을 하지 말고 해당 차이를 복원한 뒤 STEP-12로 재합류합니다.
4. 완료 확인하기
- FILE — User 규칙의 key가 정확히 ctrl+[KeyK] ctrl+alt+[KeyT]이고 command·args·when이 기준 규칙과 같습니다.
- BEHAVIOR — 현재 레이아웃에서 같은 물리 K·T 자리로 Target만 종료됩니다.
- REGRESSION — Guard의 RUN_ID는 유지되고 heartbeat가 계속 증가합니다.
- VARIANT — 두 번째 레이아웃이 이미 있으면 같은 물리 위치에서 반복 확인합니다. 없으면 UNCONFIRMED를 유지합니다.
- ROLLBACK — Scan Lab Task 0개, 실습 User 규칙 0개, 원래 입력 언어로 복귀했습니다.
완료 기준 key 한 필드만 scan-code chord로 바뀌었고, Target 선택 종료·Guard 보존·최종 Rollback을 서로 독립된 화면에서 확인했습니다.
5. 문제가 생겼다면
대괄호 표기에 빨간 오류가 납니다
먼저 확인 [KeyK]·[KeyT]의 대소문자, 대괄호, 두 stroke 사이 공백을 원문과 비교합니다.
복구 key를 ctrl+[KeyK] ctrl+alt+[KeyT]로 되돌립니다.
재합류 STEP-06
아무 반응이 없거나 Quick Pick이 열립니다
먼저 확인 오류 원문을 보존하고 Target label, 실행 상태, Terminal 포커스, 선택·Find 상태를 확인합니다. 원인은 확인 전 UNKNOWN입니다.
복구 하나씩 정상화하고 같은 물리 위치로 다시 시험합니다.
재합류 STEP-08 또는 STEP-09
다른 Task가 종료됐습니다
먼저 확인 두 Terminal의 label·RUN_ID와 User rule args 원문을 보존합니다.
복구 실습을 중단하고 User 규칙을 제거합니다. args가 Target label과 정확히 같은지 확인 전 재실행하지 않습니다.
재합류 STEP-06
레이아웃 B에서 같은 위치인지 확신할 수 없습니다
먼저 확인 작업 표시줄의 레이아웃 이름과 실제 물리 키 위치를 기록합니다.
복구 결과를 UNCONFIRMED로 두고 새 레이아웃을 설치하지 않습니다.
재합류 STEP-11
6. 핵심 정리와 공식 자료
- 일반 문자 표기와 [KeyK] 같은 scan code 표기는 단축키가 따라가는 기준이 다릅니다.
- 이 실습에서는 key만 바꾸고 Target 선택 args와 다섯 when 조건은 유지합니다.
- 두 번째 레이아웃이 없으면 설치하지 않고 Variant를 UNCONFIRMED로 남기는 것이 올바른 완료입니다.
- 마지막에는 Guard 종료, User 규칙 제거, 원래 입력 언어 복귀를 모두 확인합니다.
공식 자료
아래 자료는 2026-09-15 KST에 접근했습니다. Stable 1.137.0과 Windows 11 범위이며, 키보드 하드웨어·IME·조직 정책·확장 규칙 차이는 독자 환경에서 확인해야 합니다.
- Keyboard shortcuts for Visual Studio Code · Microsoft — 키보드 레이아웃, keybindings.json, Define Keybinding, 레이아웃 독립 scan code와 허용 목록
- keybindings.md · Microsoft vscode-docs — 공식 문서 원문에서 [KeyA]-[KeyZ] scan code 허용 범위 교차 확인
- keyCodes.ts · Microsoft vscode — Stable 1.137.0의 KeyK·KeyT ScanCode 문자열과 Windows VK 매핑
- Keybinding Issues · Microsoft vscode — Windows scan code·virtual key·생성 문자 관계와 물리 위치 기반 사용자 정의
- Integrate with External Tools via Tasks · Microsoft — Workspace tasks.json, process Task, label, PowerShell 실행과 Terminal 동작
- Variables reference · Microsoft — workbench.action.tasks.terminate와 args terminateAll 공식 예제; String Target label 사용은 Stable 구현과 이전 편에서 확인
- Visual Studio Code 1.137 · Microsoft — 2026-09-09 공개 Stable 1.137 기준 시점
- VS Code Stable releases API · Microsoft — 접근 시 최신 Stable 목록 첫 항목 1.137.0
'개발 > Visual Studio Code' 카테고리의 다른 글
| 커맨드 팔레트 49부: VS Code 키 매핑 표의 WYSIWYG NO 행 읽기 (0) | 2026.09.17 |
|---|---|
| 커맨드 팔레트 48부: VS Code 현재 키보드 레이아웃의 키 매핑 원문 확인하기 (0) | 2026.09.16 |
| 커맨드 팔레트 46부: VS Code Task 종료 단축키의 매칭 로그로 충돌 진단하기 (0) | 2026.09.16 |
| 커맨드 팔레트 45부: VS Code Terminal Find가 열려 있을 때 Task 종료 단축키 잠그기 (0) | 2026.09.13 |
| 커맨드 팔레트 44부: VS Code Terminal 텍스트 선택 중 Task 종료 단축키 잠그기 (0) | 2026.09.13 |