# 画面設計書 163-外部プロセス

## 概要

本ドキュメントは、dbatools PowerShellモジュールにおける外部プロセス管理機能（Get-DbaExternalProcess/Stop-DbaExternalProcess）の画面設計書です。SQL Serverが生成したオペレーティングシステムレベルの子プロセス（xp_cmdshell、BCP、SSIS等で生成されたプロセス）を特定・管理する機能を提供します。

### 本画面の処理概要

**業務上の目的・背景**：SQL Serverセッションが外部待機タイプ（WAITFOR_RESULTS、EXTERNAL_SCRIPT_NETWORK_IO等）でハングしている場合、その原因は多くの場合、SQL Serverが起動した外部プロセスにあります。本機能は、SQL Server（sqlservr.exe）を親プロセスとする子プロセスを特定し、問題のあるプロセスを終了させることで、セッションのハング問題を解決します。これは、セッション自体をKILLするよりもターゲットを絞ったアプローチであり、根本原因に対処できます。

**画面へのアクセス方法**：PowerShellコマンドラインから `Get-DbaExternalProcess` または `Stop-DbaExternalProcess` コマンドレットを実行してアクセスします。Get-DbaExternalProcessの出力をStop-DbaExternalProcessにパイプで渡すワークフローを推奨します。

**主要な操作・処理内容**：
1. 対象コンピュータにWMI接続し、win32_processクラスを照会
2. sqlservr.exeプロセスのProcessIdを取得
3. ParentProcessIdがSQL ServerのProcessIdと一致するプロセスを特定
4. 各外部プロセスのリソース使用状況（メモリ、ハンドル等）を取得
5. 必要に応じてStop-Processで外部プロセスを終了

**画面遷移**：Get-DbaExternalProcessの出力はStop-DbaExternalProcessにパイプで渡すことができます。

**権限による表示制御**：WMI（Windows Management Instrumentation）へのアクセス権限が必要です。リモートコンピュータの場合、対象マシンのローカル管理者権限またはWMIアクセス権限が必要です。

## 関連機能

| 機能No | 機能名 | 関連種別 | 関連する操作・処理 |
|--------|--------|----------|------------------|
| 124 | Get-DbaExternalProcess | 主機能 | 外部プロセスの取得 |
| 235 | Stop-DbaExternalProcess | 主機能 | 外部プロセスの停止 |
| 94 | Get-DbaCmObject | 内部呼出 | WMI オブジェクトの取得 |

## 画面種別

CLI（コマンドラインインターフェース）- 診断・管理

## URL/ルーティング

PowerShellコマンド: `Get-DbaExternalProcess`, `Stop-DbaExternalProcess`

## 入出力項目

### Get-DbaExternalProcess 入力パラメータ

| パラメータ名 | 型 | 必須 | 説明 |
|-------------|-----|------|------|
| ComputerName | DbaInstanceParameter[] | Yes | 対象コンピュータ名 |
| Credential | PSCredential | No | WMIアクセス用の資格情報 |
| EnableException | switch | No | 例外を有効化 |

### Stop-DbaExternalProcess 入力パラメータ

| パラメータ名 | 型 | 必須 | 説明 |
|-------------|-----|------|------|
| ComputerName | DbaInstanceParameter | Yes | 対象コンピュータ名 |
| Credential | PSCredential | No | WMIアクセス用の資格情報 |
| ProcessId | int | Yes | 終了するプロセスID |
| EnableException | switch | No | 例外を有効化 |

### 出力項目（Get-DbaExternalProcess）

| 項目名 | 型 | 説明 |
|--------|-----|------|
| ComputerName | string | コンピュータ名 |
| ProcessId | uint | プロセスID |
| Name | string | プロセス名（実行ファイル名） |
| HandleCount | uint | オープンハンドル数 |
| WorkingSetSize | ulong | 使用中メモリ（バイト） |
| VirtualSize | ulong | 仮想アドレス空間（バイト） |
| CimObject | CimInstance | WMI プロセスオブジェクト |

### 出力項目（Stop-DbaExternalProcess）

| 項目名 | 型 | 説明 |
|--------|-----|------|
| ComputerName | string | コンピュータ名 |
| ProcessId | int | 終了したプロセスID |
| Name | string | プロセス名 |
| Status | string | 常に"Stopped" |

## 表示項目

Get-DbaExternalProcessはSelect-DefaultViewにより主要プロパティのみがデフォルト表示されます。CimObjectプロパティから詳細なWin32_Processプロパティにアクセス可能です。

## イベント仕様

### 1-Get-DbaExternalProcess実行

1. **SQL Server PID取得**（行70）: Get-DbaCmObjectでwin32_processからsqlservr.exeのProcessIdを取得
2. **子プロセス検索**（行71）: ParentProcessIdがSQL ServerのPIDと一致するプロセスを検索
3. **結果出力**（行73-84）: 各外部プロセスの情報をPSCustomObjectとして出力

### 2-Stop-DbaExternalProcess実行

1. **プロセス名取得**（行82-83）: 終了対象プロセスの名前を事前取得
2. **Stop-Process実行**（行86-88）: Invoke-Command2でリモート実行
3. **結果出力**（行90-95）: 終了確認情報を出力

## データベース更新仕様

### 操作別データベース影響一覧

本機能はSQL Serverデータベースに直接アクセスしません。WMI経由でOSレベルのプロセス情報を操作します。

| 操作（イベント） | 対象 | 操作種別 | 概要 |
|----------------|------|---------|------|
| プロセス取得 | Win32_Process | WMI Query | プロセス情報の参照 |
| プロセス終了 | OS Process | Stop-Process | プロセスの強制終了 |

## メッセージ仕様

| メッセージタイプ | 条件 | メッセージ内容 |
|-----------------|------|---------------|
| Error | WMI接続失敗 | "Failure for {computer}" |
| Error | プロセス終了失敗 | "Error killing {ProcessId} on {ComputerName}" |

## 例外処理

| 例外条件 | 処理内容 |
|---------|---------|
| WMIアクセス失敗 | Stop-Functionでエラーを記録し、次のコンピュータの処理を継続 |
| プロセス終了失敗 | Stop-Functionでエラーを記録して継続 |
| sqlservr.exeが見つからない | 結果なし（外部プロセスも見つからない） |

## 備考

- 本機能はOSレベルでSQL Serverの子プロセスを特定するため、SQL Server接続は不要
- 外部待機タイプのトラブルシューティングに特化した機能
- 参考URL: https://web.archive.org/web/20201027122300/http://vickyharp.com/2013/12/killing-sessions-with-external-wait-types/
- SQL Serverクラスター環境では、現在アクティブなノードのコンピュータ名を指定する必要あり

---

## コードリーディングガイド

本画面を理解するために参照すべきファイルと、推奨する読み解き順序を以下に示す。

### 推奨読解順序

#### Step 1: データ構造を理解する

WMI Win32_Processクラスから取得する情報と出力形式を理解します。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 1-1 | Get-DbaExternalProcess.ps1 | `public/Get-DbaExternalProcess.ps1` | 行40-52の.OUTPUTSセクション |

**読解のコツ**: CimObjectプロパティには完全なWin32_Processオブジェクトが含まれ、追加のプロパティにアクセス可能。

#### Step 2: エントリーポイントを理解する

Get-DbaExternalProcessの主要処理フローを理解します。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 2-1 | Get-DbaExternalProcess.ps1 | `public/Get-DbaExternalProcess.ps1` | 行60-66のパラメータ定義 |
| 2-2 | Get-DbaExternalProcess.ps1 | `public/Get-DbaExternalProcess.ps1` | 行70-71のSQL Server PID取得と子プロセス検索 |

**主要処理フロー**:
1. **行70**: Get-DbaCmObjectでsqlservr.exeのProcessIdを取得
2. **行71**: ParentProcessIdでフィルタリングして子プロセスを取得
3. **行73-84**: 各プロセスの情報を出力

#### Step 3: Stop-DbaExternalProcess処理を理解する

プロセス終了処理の実装を理解します。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 3-1 | Stop-DbaExternalProcess.ps1 | `public/Stop-DbaExternalProcess.ps1` | 行79-100のプロセス終了処理 |

**主要処理フロー**:
- **行82-83**: プロセス名を事前取得（終了後は取得できないため）
- **行85-88**: Invoke-Command2でリモートStop-Process実行
- **行90-95**: 終了確認出力

### プログラム呼び出し階層図

```
Get-DbaExternalProcess
    |
    +-- Get-DbaCmObject (行70)
    |       └── WMI win32_process クエリ（sqlservr.exe検索）
    |
    +-- Get-DbaCmObject (行71)
    |       └── WMI win32_process クエリ（子プロセス検索）
    |
    └-- PSCustomObject 出力 (行74-84)
            └── プロセス情報の整形

Stop-DbaExternalProcess
    |
    +-- Get-DbaCmObject (行82)
    |       └── プロセス名取得
    |
    +-- Invoke-Command2 (行86-88)
    |       └── Stop-Process リモート実行
    |
    └-- PSCustomObject 出力 (行90-95)
            └── 終了確認情報
```

### データフロー図

```
[入力]                      [処理]                           [出力]

ComputerName ─────────┐
                      │
Credential ───────────┼──> Get-DbaCmObject (sqlservr.exe)
                      │           │
                      │           v
                      │    SQL Server PID
                      │           │
                      │           v
                      └──> Get-DbaCmObject (子プロセス)
                                  │
                                  v
                           プロセスリスト
                                  │
                                  v
                           PSCustomObject ──────> [Stop-DbaExternalProcess]
                                                         │
                                                         v
                                                   Invoke-Command2
                                                         │
                                                         v
                                                   Stop-Process
                                                         │
                                                         v
                                                   終了確認出力
```

### 関連ファイル一覧

| ファイル | パス | 種別 | 役割 |
|---------|------|------|------|
| Get-DbaExternalProcess.ps1 | `public/Get-DbaExternalProcess.ps1` | ソース | 外部プロセス取得の実装 |
| Stop-DbaExternalProcess.ps1 | `public/Stop-DbaExternalProcess.ps1` | ソース | 外部プロセス終了の実装 |
| Get-DbaCmObject.ps1 | `public/Get-DbaCmObject.ps1` | ソース | WMIオブジェクト取得 |
| Invoke-Command2.ps1 | `internal/functions/Invoke-Command2.ps1` | ソース | リモートコマンド実行ヘルパー |
