# 通知設計書 117-Read intent除外

## 概要

本ドキュメントは、sp_BlitzWho、sp_BlitzFirst、sp_BlitzCacheストアドプロシージャにおいて、Always On可用性グループのRead Intent（読み取り意図）データベースを処理対象から除外する処理の開始を通知するメッセージの設計を定義します。

### 本通知の処理概要

各種診断ストアドプロシージャ実行時に、Always On可用性グループ環境でセカンダリレプリカ上の読み取り専用データベースを検出し、処理対象から除外する処理の開始を通知します。

**業務上の目的・背景**：Always On可用性グループでは、セカンダリレプリカを読み取り専用ワークロードに使用できます。しかし、これらのデータベースは特殊なアクセス制限があり、一部のDMV（動的管理ビュー）クエリが正常に動作しない場合があります。この通知は、そのような読み取り意図データベースの検出処理が開始されたことをDBAに伝え、特定のデータベースが処理対象外となる理由を理解する助けとなります。

**通知の送信タイミング**：sp_BlitzWho、sp_BlitzFirst、sp_BlitzCache実行の初期化フェーズで、sys.dm_hadr_database_replica_states DMVが存在する場合に送信されます。これはAlways On可用性グループ機能が使用可能であることを示します。

**通知の受信者**：各ストアドプロシージャを実行しているデータベース管理者がSSMS（SQL Server Management Studio）のメッセージタブで受信します。

**通知内容の概要**：「Checking for Read intent databases to exclude」というメッセージで、読み取り意図データベースの検出処理が開始されたことを伝えます。

**期待されるアクション**：通常は特別なアクションは不要です。特定のデータベースが診断結果に含まれない場合、この通知を手がかりにAlways On設定を確認できます。

## 通知種別

コンソール出力（RAISERROR WITH NOWAIT）

## 送信仕様

### 基本情報

| 項目 | 内容 |
|-----|------|
| 送信方式 | 同期（RAISERROR WITH NOWAIT） |
| 優先度 | 低（情報通知） |
| リトライ | なし |

### 送信先決定ロジック

各ストアドプロシージャを実行しているクライアントセッションに対して、RAISERRORによるメッセージ出力として送信されます。

## 通知テンプレート

### コンソール出力の場合

| 項目 | 内容 |
|-----|------|
| メッセージ形式 | RAISERROR |
| 重大度 | 0（情報メッセージ） |
| 状態 | 0 |

### 本文テンプレート

```
Checking for Read intent databases to exclude
```

### 添付ファイル

なし

## テンプレート変数

なし（固定メッセージ）

## 送信トリガー・条件

### トリガー一覧

| トリガー種別 | トリガーイベント | 送信条件 | 説明 |
|------------|----------------|---------|------|
| ストアドプロシージャ実行 | Read Intent DB検出開始 | sys.dm_hadr_database_replica_statesが存在 | Always On AG環境 |

### 送信抑止条件

| 条件 | 説明 |
|-----|------|
| sys.dm_hadr_database_replica_states不存在 | Always On AGが構成されていない環境 |
| sp_BlitzCache: @IgnoreReadableReplicaDBs = 0 | 読み取りレプリカDBを除外しない設定 |

## 処理フロー

### 送信フロー

```mermaid
flowchart TD
    A[ストアドプロシージャ実行] --> B{dm_hadr_database_replica_states存在?}
    B -->|No| C[Read Intent DB除外処理スキップ]
    B -->|Yes| D[RAISERROR Checking for Read intent...]
    D --> E[#ReadableDBs / #WhoReadableDBsに除外DB挿入]
    E --> F[セカンダリレプリカDBを検出]
    F --> G[READ_ONLYアクセスのDBをリストに追加]
    G --> H[後続処理でこれらのDBを除外]
```

## データベース参照・更新仕様

### 参照テーブル一覧

| テーブル名 | 用途 | 備考 |
|-----------|------|------|
| sys.databases | データベース情報取得 | replica_id参照 |
| sys.availability_replicas | レプリカ情報取得 | secondary_role_allow_connections_desc参照 |
| sys.dm_hadr_availability_group_states | プライマリレプリカ判定 | primary_replica参照 |

### テーブル別参照項目詳細

#### sys.databases

| 参照項目（カラム名） | 用途 | 取得条件 |
|-------------------|------|---------|
| database_id | DB識別 | - |
| replica_id | レプリカ参照 | INNER JOIN sys.availability_replicas |

#### sys.availability_replicas

| 参照項目（カラム名） | 用途 | 取得条件 |
|-------------------|------|---------|
| replica_id | JOIN条件 | - |
| replica_server_name | サーバー判定 | @@SERVERNAME |
| secondary_role_allow_connections_desc | アクセス種別 | = 'READ_ONLY' |

#### sys.dm_hadr_availability_group_states

| 参照項目（カラム名） | 用途 | 取得条件 |
|-------------------|------|---------|
| primary_replica | プライマリ判定 | NOT INで除外 |

### 更新テーブル一覧

| テーブル名 | 操作 | 概要 |
|-----------|------|------|
| #ReadableDBs / #WhoReadableDBs | INSERT | 除外対象データベースIDの格納 |

#### #ReadableDBs / #WhoReadableDBs

| 操作 | 項目（カラム名） | 更新値 | 備考 |
|-----|-----------------|-------|------|
| INSERT | database_id | セカンダリレプリカDB | READ_ONLYアクセスのDB |
| INSERT | database_id | 32767 | 内部リソースDB（sp_BlitzCache） |

## エラー処理

### エラーケース一覧

| エラー種別 | 発生条件 | 対処方法 |
|----------|---------|---------|
| 該当なし | 存在チェック後に実行のためエラー発生しにくい | - |

### リトライ仕様

| 項目 | 内容 |
|-----|------|
| リトライ回数 | 0（リトライなし） |
| リトライ間隔 | - |
| リトライ対象エラー | - |

## 配信設定

### レート制限

なし

### 配信時間帯

制限なし

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

- メッセージには機密情報は含まれていません
- Always On AG構成の存在を示唆しますが、セキュリティリスクは低いです

## 備考

- この機能は、READMEの「Known Issues」セクションでも言及されています
- 読み取り意図データベースを有効にするには、コードの該当部分を修正する必要があります
- sp_BlitzCacheでは、内部リソースデータベース（database_id = 32767）も除外対象に追加されます

---

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

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

### 推奨読解順序

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

除外対象DBを格納する一時テーブルの構造を理解することが重要です。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 1-1 | sp_BlitzWho.sql | `sp_BlitzWho.sql` | #WhoReadableDBs一時テーブルの定義 |
| 1-2 | sp_BlitzFirst.sql | `sp_BlitzFirst.sql` | #ReadableDBs一時テーブルの定義 |
| 1-3 | sp_BlitzCache.sql | `sp_BlitzCache.sql` | #ReadableDBs一時テーブルの定義 |

**読解のコツ**: CREATE TABLE #ReadableDBs / #WhoReadableDBsを検索し、database_idカラムの定義を確認します。

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

Read Intent DB検出処理の開始部分を確認します。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 2-1 | sp_BlitzWho.sql | `sp_BlitzWho.sql` | dm_hadr_database_replica_states存在チェック |
| 2-2 | sp_BlitzFirst.sql | `sp_BlitzFirst.sql` | dm_hadr_database_replica_states存在チェック |
| 2-3 | sp_BlitzCache.sql | `sp_BlitzCache.sql` | dm_hadr_database_replica_states存在チェックと@IgnoreReadableReplicaDBs条件 |

**主要処理フロー**:
1. **sp_BlitzWho.sql 行583-588**: dm_hadr_database_replica_states存在チェック、RAISERROR、EXEC INSERT
2. **sp_BlitzFirst.sql 行1113-1118**: dm_hadr_database_replica_states存在チェック、RAISERROR、動的SQL実行
3. **sp_BlitzCache.sql 行1599-1604**: @IgnoreReadableReplicaDBs条件付きチェック、RAISERROR、EXEC INSERT

#### Step 3: 除外DB検出クエリを理解する

Read Intent DBを検出するクエリの構造を確認します。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 3-1 | sp_BlitzWho.sql | `sp_BlitzWho.sql` | INSERT文のSELECT句 |

**主要処理フロー**:
- sys.databases INNER JOIN sys.availability_replicas
- replica_server_name NOT IN (プライマリレプリカ)
- secondary_role_allow_connections_desc = 'READ_ONLY'
- replica_server_name = @@SERVERNAME

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

```
sp_BlitzWho / sp_BlitzFirst / sp_BlitzCache
    |
    +-- (条件) EXISTS dm_hadr_database_replica_states
            |
            +-- RAISERROR('Checking for Read intent databases to exclude')
            |
            +-- INSERT #ReadableDBs / #WhoReadableDBs
                    |
                    +-- SELECT database_id FROM sys.databases
                    |       INNER JOIN sys.availability_replicas
                    |       WHERE replica_server_name NOT IN (primary_replica)
                    |       AND secondary_role_allow_connections_desc = 'READ_ONLY'
                    |       AND replica_server_name = @@SERVERNAME
                    |
                    +-- (sp_BlitzCacheのみ) INSERT 32767 (内部リソースDB)
```

### データフロー図

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

sys.databases             -->
sys.availability_replicas --> 除外DB検出クエリ
sys.dm_hadr_availability_group_states -->            --> #ReadableDBs / #WhoReadableDBs
                                                            |
                                                            +-> database_id
                                                            +-> (32767: 内部リソースDB)

#ReadableDBs              --> 後続クエリのWHERE句で除外
```

### 関連ファイル一覧

| ファイル | パス | 種別 | 役割 |
|---------|------|------|------|
| sp_BlitzWho.sql | `sp_BlitzWho.sql` | ソース | 本通知を発行するストアドプロシージャ |
| sp_BlitzFirst.sql | `sp_BlitzFirst.sql` | ソース | 本通知を発行するストアドプロシージャ |
| sp_BlitzCache.sql | `sp_BlitzCache.sql` | ソース | 本通知を発行するストアドプロシージャ |
| README.md | `README.md` | ドキュメント | Known Issuesに関連記述あり |
| Install-All-Scripts.sql | `Install-All-Scripts.sql` | ソース | 各ストアドプロシージャを含むインストールスクリプト |
| Install-Azure.sql | `Install-Azure.sql` | ソース | Azure向けインストールスクリプト |
