# 機能設計書 552-Get-DbaDbOrphanUser

## 概要

本ドキュメントは、SQL Server データベース内の孤立ユーザー（Orphan User）を検出する機能について、その処理内容、入出力仕様、および実装詳細を記述した機能設計書である。

### 本機能の処理概要

Get-DbaDbOrphanUserは、SQL Serverデータベース内で対応するサーバーログインが存在しない「孤立ユーザー」を検出するPowerShellコマンドレットである。孤立ユーザーとは、Loginプロパティが空であるか、サーバーのログインコレクションに対応するログインが存在しないデータベースユーザーを指す。

**業務上の目的・背景**：データベースの移行、復元、ログインの削除などの操作後に、データベースユーザーとサーバーログインの対応関係が失われることがある。これらの孤立ユーザーはセキュリティリスクとなる可能性があり、また不要なオブジェクトとしてデータベースを汚染する。本機能は、これらの孤立ユーザーを特定し、Repair-DbaDbOrphanUserやRemove-DbaDbOrphanUserと連携して問題を解決するために使用される。

**機能の利用シーン**：
- データベース移行後の整合性チェック
- 定期的なセキュリティ監査
- ログイン削除後のクリーンアップ作業
- バックアップからのリストア後の検証

**主要な処理内容**：
1. 指定されたSQL Serverインスタンスへの接続
2. アクセス可能なデータベースのフィルタリング（Database/ExcludeDatabase）
3. 各データベース内のユーザーに対して孤立状態をチェック
4. SQLログイン/証明書ベースユーザーでLoginプロパティが空のものを検出
5. Windowsユーザー/グループでサーバーログインに存在しないものを検出
6. 検出された孤立ユーザー情報の出力

**関連システム・外部連携**：
- SMO（SQL Server Management Objects）を使用
- Repair-DbaDbOrphanUser（孤立ユーザーの修復）
- Remove-DbaDbOrphanUser（孤立ユーザーの削除）

**権限による制御**：データベースユーザー情報の参照には、各データベースへのアクセス権限が必要。

## 関連画面

| 画面No | 画面名 | 関連種別 | 関連する操作・処理 |
|--------|--------|----------|------------------|
| 38 | データベースユーザー管理 | 補助画面 | 孤立ユーザーの検出 |

## 機能種別

データ取得（SELECT） / 検証処理

## 入力仕様

### 入力パラメータ

| パラメータ名 | 型 | 必須 | 説明 | バリデーション |
|-------------|-----|-----|------|---------------|
| SqlInstance | DbaInstanceParameter[] | Yes | 対象のSQL Serverインスタンス。パイプライン入力対応 | 有効なSQL Serverインスタンス名 |
| SqlCredential | PSCredential | No | 接続に使用する代替資格情報 | Get-Credentialで取得した資格情報 |
| Database | object[] | No | 検査対象のデータベース名 | - |
| ExcludeDatabase | object[] | No | 除外するデータベース名 | - |
| EnableException | switch | No | 例外処理の有効化 | - |

### 入力データソース

- SQL Serverインスタンス（$server.Databases）
- 各データベースのUsersコレクション（$db.Users）

## 出力仕様

### 出力データ

| 項目名 | 型 | 説明 |
|--------|-----|------|
| ComputerName | string | SQL Serverが稼働するコンピュータ名 |
| InstanceName | string | SQL Serverインスタンス名 |
| SqlInstance | string | 完全なSQL Serverインスタンス名 |
| DatabaseName | string | 孤立ユーザーが存在するデータベース名 |
| User | string | 孤立ユーザー名 |
| SmoUser | Microsoft.SqlServer.Management.Smo.User | SMOユーザーオブジェクト |

### 出力先

- PowerShellパイプライン（PSCustomObject型）

## 処理フロー

### 処理シーケンス

```
1. パラメータバインディング
   └─ SqlInstance、フィルタ条件の受け取り

2. foreach ($instance in $SqlInstance) ループ開始
   └─ 各インスタンスに対して処理実行

3. SQL Serverへの接続
   └─ Connect-DbaInstanceによる接続確立

4. データベースコレクションの取得
   └─ IsAccessibleがtrueのデータベースのみ対象
   └─ Databaseパラメータによる絞り込み
   └─ ExcludeDatabaseによる除外

5. 各データベースでの孤立ユーザー検出
   ├─ SQLログイン/証明書: Loginプロパティが空、ID > 4、SID長が16
   └─ Windows認証: Loginがサーバーログインに存在しない、ID > 4、SID長 > 16

6. 結果の出力
   └─ PSCustomObjectとして出力
   └─ Select-DefaultViewで既定プロパティを選択
```

### フローチャート

```mermaid
flowchart TD
    A[開始] --> B[パラメータ受け取り]
    B --> C{各インスタンスをループ}
    C --> D[Connect-DbaInstance]
    D --> E{接続成功?}
    E -->|No| F[Stop-Function / Continue]
    F --> C
    E -->|Yes| G[IsAccessibleなDBを取得]
    G --> H{Database指定?}
    H -->|Yes| I[DB絞り込み]
    H -->|No| J{ExcludeDatabase?}
    I --> J
    J -->|Yes| K[DB除外]
    J -->|No| L{DBコレクション > 0?}
    K --> L
    L -->|No| M[Verbose: 分析対象DBなし]
    L -->|Yes| N{各DBをループ}
    N --> O[SQLログイン孤立ユーザー検出]
    O --> P[Windows認証孤立ユーザー検出]
    P --> Q{孤立ユーザーあり?}
    Q -->|No| R[Verbose: 孤立ユーザーなし]
    Q -->|Yes| S[PSCustomObject出力]
    R --> N
    S --> N
    M --> C
    N -->|完了| C
    C -->|完了| T[終了]
```

## ビジネスルール

### 業務ルール

| ルールNo | ルール名 | 内容 | 適用条件 |
|---------|---------|------|---------|
| BR-001 | SQLログイン孤立判定 | Login=""、ID>4、SID長=16、LoginType=SqlLoginまたはCertificate | 常時 |
| BR-002 | Windows認証孤立判定 | Loginがサーバーログインに存在しない、ID>4、SID長>16、LoginType=WindowsUserまたはWindowsGroup | 常時 |
| BR-003 | システムユーザー除外 | ID <= 4のユーザーは対象外（dbo, guest, INFORMATION_SCHEMA, sys） | 常時 |
| BR-004 | アクセス可能DBのみ | IsAccessibleがtrueのデータベースのみ処理対象 | 常時 |

### 計算ロジック

孤立ユーザー判定ロジック:
- SQLログイン/証明書: `($_.Login -eq "") -and ($_.ID -gt 4) -and ($_.Sid.Length -eq 16) -and ($_.LoginType -in 'SqlLogin', 'Certificate')`
- Windows認証: `($_.Login -notin $server.Logins.Name) -and ($_.ID -gt 4) -and ($_.Sid.Length -gt 16 -and $_.LoginType -in 'WindowsUser', 'WindowsGroup')`

## データベース操作仕様

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

| 操作 | 対象テーブル | 操作種別 | 概要 |
|-----|-------------|---------|------|
| ユーザー取得 | sys.database_principals | SELECT | SMO経由でDBユーザーを取得 |
| ログイン取得 | sys.server_principals | SELECT | SMO経由でサーバーログインを取得 |

### テーブル別操作詳細

#### sys.database_principals（SMO経由アクセス）

| 操作 | 項目（カラム名） | 更新値・取得条件 | 備考 |
|-----|-----------------|-----------------|------|
| SELECT | name, principal_id, sid, type等 | 全ユーザー | SMOのUsersコレクション経由 |

## エラー処理

### エラーケース一覧

| エラーコード | エラー種別 | 発生条件 | 対処方法 |
|------------|----------|---------|---------|
| ConnectionError | 接続エラー | SQL Serverへの接続失敗 | Stop-Functionで警告、次のインスタンスへ継続 |
| - | 処理エラー | DB処理中のエラー | Stop-Functionで継続 |

### リトライ仕様

リトライは実装されていない。

## トランザクション仕様

読み取り専用操作のため、トランザクション制御は不要。

## パフォーマンス要件

- 各データベースのUsersコレクションを完全に走査
- 大量のデータベース/ユーザーがある場合は処理時間に注意

## セキュリティ考慮事項

- 各データベースへのアクセス権限が必要
- 孤立ユーザーの検出はセキュリティ監査の一環として使用

## 備考

- Repair-DbaDbOrphanUser、Remove-DbaDbOrphanUserと組み合わせて使用
- WhatIf、Confirmパラメータが定義されているが、この関数は読み取り専用

---

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

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

### 推奨読解順序

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

孤立ユーザーの判定に使用されるプロパティを理解する。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 1-1 | Get-DbaDbOrphanUser.ps1 | `public/Get-DbaDbOrphanUser.ps1` | 出力PSCustomObjectの構造（115-122行目） |

**読解のコツ**: SMO Userオブジェクトの Login、ID、Sid、LoginType プロパティが孤立判定の鍵。

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

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 2-1 | Get-DbaDbOrphanUser.ps1 | `public/Get-DbaDbOrphanUser.ps1` | function宣言とparamブロック（80-88行目） |

**主要処理フロー**:
1. **80-88行目**: パラメータ定義
2. **89行目**: processブロック開始
3. **90行目**: foreachループでインスタンス処理開始

#### Step 3: 孤立ユーザー検出ロジックを理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 3-1 | Get-DbaDbOrphanUser.ps1 | `public/Get-DbaDbOrphanUser.ps1` | 孤立判定ロジック（109-111行目） |

**主要処理フロー**:
- **109-110行目**: 孤立ユーザーの定義
  - SQLログイン/証明書: Login空、ID>4、SID長=16
  - Windows認証: Loginがサーバーログインに存在しない、ID>4、SID長>16
- **111行目**: 検出条件のOR結合

#### Step 4: 出力処理を理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 4-1 | Get-DbaDbOrphanUser.ps1 | `public/Get-DbaDbOrphanUser.ps1` | PSCustomObject生成（114-123行目） |

**主要処理フロー**:
- **115-122行目**: PSCustomObjectで出力オブジェクト生成
- **122行目**: Select-DefaultViewで既定プロパティを選択

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

```
Get-DbaDbOrphanUser
    │
    ├─ Connect-DbaInstance
    │      └─ SQL Server SMO接続
    │
    ├─ $server.Databases（フィルタリング）
    │      └─ IsAccessible, Database, ExcludeDatabase
    │
    ├─ $db.Users（各DBのユーザー）
    │      └─ 孤立判定ロジック適用
    │
    └─ Select-DefaultView（出力整形）
```

### データフロー図

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

SqlInstance ───▶ Connect-DbaInstance ───▶ SMO Server
                        │
                        ▼
              $server.Databases ───▶ IsAccessible フィルタ
                        │
                        ▼
              各 $db.Users ───▶ 孤立判定
                        │
           ┌────────────┴────────────┐
           ▼                         ▼
    SQLログイン孤立          Windows認証孤立
    (Login空、SID=16)       (Loginなし、SID>16)
           │                         │
           └────────────┬────────────┘
                        ▼
              PSCustomObject ───▶ パイプライン出力
```

### 関連ファイル一覧

| ファイル | パス | 種別 | 役割 |
|---------|------|------|------|
| Get-DbaDbOrphanUser.ps1 | `public/Get-DbaDbOrphanUser.ps1` | ソース | メイン実装 |
| Connect-DbaInstance.ps1 | `public/Connect-DbaInstance.ps1` | ソース | SQL Server接続機能 |
| Repair-DbaDbOrphanUser.ps1 | `public/Repair-DbaDbOrphanUser.ps1` | ソース | 孤立ユーザー修復（関連機能） |
| Remove-DbaDbOrphanUser.ps1 | `public/Remove-DbaDbOrphanUser.ps1` | ソース | 孤立ユーザー削除（関連機能） |
