# 機能設計書 32-メトリクス集計

## 概要

本ドキュメントは、OpenSearchのメトリクス集計（Metrics Aggregation）機能の設計を記述する。メトリクス集計はドキュメントのフィールド値に対して数値演算（平均、合計、最小、最大、統計量、カーディナリティ等）を行い、統計的なメトリクスを算出する集計機能である。

### 本機能の処理概要

メトリクス集計は、検索結果のドキュメントから数値フィールドの統計量を計算する機能群である。Avg、Sum、Min、Max、Stats、Extended Stats、Cardinality、Percentiles、Percentile Ranks、Geo Bounds、Geo Centroid、Value Count、Median Absolute Deviation、Weighted Avg等のメトリクス集計タイプを提供する。

**業務上の目的・背景**：ドキュメントのフィールド値に対して平均値、合計、最大最小値、分布特性等の統計量を算出するニーズに対応する。売上の平均額、アクセスログのレスポンスタイムのパーセンタイル分布、ユニークユーザ数の推定等、データ分析・監視の基盤機能として利用される。

**機能の利用シーン**：検索APIのaggregationsパラメータ内でメトリクス集計タイプを指定して利用する。バケット集計のサブ集計として使用されることが多い（例：カテゴリ別の平均売上額）。

**主要な処理内容**：
1. 検索リクエストからメトリクス集計定義をパース
2. ValuesSourceConfigによるフィールドデータソースの構成
3. NumericMetricsAggregatorによるセグメント単位の数値計算
4. 各シャードでの部分集計結果をInternalAggregationとしてシリアライズ
5. コーディネーティングノードでreduce（マージ）して最終メトリクスを返却

**関連システム・外部連携**：LuceneのDocValues、フィールドデータ。Star-Treeインデックスの事前集計データとの統合（StarTreePreComputeCollector）。

**権限による制御**：インデックスの読み取り権限が必要。フィールドレベルセキュリティの対象。

## 関連画面

| 画面No | 画面名 | 関連種別 | 関連する操作・処理 |
|--------|--------|----------|------------------|
| 21 | 検索 | 補助機能 | 検索結果に対するメトリクス集計処理 |

## 機能種別

計算処理（集計・分析）

## 入力仕様

### 入力パラメータ

| パラメータ名 | 型 | 必須 | 説明 | バリデーション |
|-------------|-----|-----|------|---------------|
| type | String | Yes | メトリクス集計タイプ（avg, sum, min, max, stats, extended_stats, cardinality, percentiles, percentile_ranks, value_count, geo_bounds, geo_centroid, median_absolute_deviation, weighted_avg等） | サポートされるタイプ名であること |
| field | String | No | 集計対象フィールド名 | 数値型フィールドであること |
| script | Script | No | スクリプトベースの値取得 | 有効なスクリプト定義 |
| missing | Number | No | フィールド値欠損時の代替値 | フィールド型と互換 |
| precision_threshold | Integer | No | Cardinality集計の精度閾値（デフォルト3000） | 0-40000の範囲 |
| percents | double[] | No | Percentiles集計のパーセンタイル値 | 0-100の範囲 |
| sigma | double | No | Extended Stats集計の標準偏差倍率（デフォルト2.0） | 正の数値 |
| compression | double | No | TDigest圧縮パラメータ（デフォルト100.0） | 正の数値 |

### 入力データソース

検索APIリクエストのaggregationsセクション。LuceneインデックスのDocValuesから数値を取得。

## 出力仕様

### 出力データ

| 項目名 | 型 | 説明 |
|--------|-----|------|
| value | Double | 単一メトリクス値（avg, sum, min, max, value_count） |
| count | Long | ドキュメント数（stats, extended_stats） |
| min / max / avg / sum | Double | 基本統計量（stats） |
| std_deviation | Double | 標準偏差（extended_stats） |
| values | Map | パーセンタイル値マップ（percentiles） |
| cardinality | Long | 推定ユニーク値数（cardinality） |

### 出力先

検索APIレスポンスのaggregationsフィールド内にJSON形式で返却。

## 処理フロー

### 処理シーケンス

```
1. 検索リクエスト受信
   └─ メトリクス集計定義をパース
2. ValuesSourceConfigの構成
   └─ フィールド型に基づくValuesSource（Numeric等）の選択
3. NumericMetricsAggregatorの生成
   └─ AvgAggregator, SumAggregator等の具体クラスをインスタンス化
4. セグメント単位の計算
   └─ LeafBucketCollectorでドキュメントごとに数値を収集・計算
5. Star-Tree最適化（利用可能な場合）
   └─ StarTreePreComputeCollectorで事前集計値を使用
6. 部分結果の構築
   └─ InternalAvg, InternalSum等としてシリアライズ
7. reduce処理
   └─ 各シャードの部分結果をマージして最終メトリクスを算出
```

### フローチャート

```mermaid
flowchart TD
    A[検索リクエスト受信] --> B[ValuesSourceConfig構成]
    B --> C[MetricsAggregator生成]
    C --> D{Star-Tree利用可能?}
    D -->|Yes| E[StarTreePreComputeCollector]
    D -->|No| F[LeafBucketCollector]
    E --> G[InternalAggregation構築]
    F --> G
    G --> H[シャード結果送信]
    H --> I[reduce処理]
    I --> J[最終メトリクス返却]
```

## ビジネスルール

### 業務ルール

| ルールNo | ルール名 | 内容 | 適用条件 |
|---------|---------|------|---------|
| BR-32-01 | 数値補償和 | Avg/Sum集計でKahanの補償和アルゴリズムを使用し浮動小数点誤差を抑制 | Avg, Sum集計 |
| BR-32-02 | HyperLogLog++ | Cardinality集計でHLL++アルゴリズムにより近似ユニーク数を推定 | Cardinality集計 |
| BR-32-03 | TDigest/HDR | Percentiles集計でTDigestまたはHDRヒストグラムアルゴリズムを使用 | Percentiles集計 |
| BR-32-04 | フィールド型制約 | 数値メトリクスは数値型フィールドのみ対象 | Avg, Sum, Stats等 |
| BR-32-05 | missing値適用 | フィールド値欠損時にmissing指定値で補完 | missingパラメータ指定時 |

### 計算ロジック

- **Avg**: sum / count（CompensatedSumで誤差補正）
- **Cardinality**: HyperLogLog++アルゴリズム（precision_thresholdで精度調整）
- **Percentiles (TDigest)**: ストリーミングデータの分位数をTDigestデータ構造で近似計算
- **Extended Stats**: mean, variance, std_deviation, std_deviation_bounds(upper/lower)を算出

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

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

| 操作 | 対象テーブル | 操作種別 | 概要 |
|-----|-------------|---------|------|
| メトリクス集計 | Luceneインデックス | SELECT（読取） | DocValuesから数値フィールド値を読み取り |

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

#### Luceneインデックス

| 操作 | 項目（カラム名） | 更新値・取得条件 | 備考 |
|-----|-----------------|-----------------|------|
| SELECT | 数値フィールド | SortedNumericDocValuesまたはNumericDocValues | 検索クエリでフィルタされたドキュメント |

## エラー処理

### エラーケース一覧

| エラーコード | エラー種別 | 発生条件 | 対処方法 |
|------------|----------|---------|---------|
| 400 | illegal_argument_exception | 非数値フィールドに対するメトリクス集計 | 数値型フィールドを指定 |
| 400 | search_phase_execution_exception | 不正なパラメータ | パラメータを修正 |
| 400 | illegal_argument_exception | precision_thresholdが範囲外 | 0-40000の範囲で指定 |

### リトライ仕様

読み取り専用操作のため、クライアント側でのリトライが可能。

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

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

## パフォーマンス要件

- Avg/Sum/Min/Max/Value Count集計はO(N)の計算量（Nはドキュメント数）
- Cardinality集計のメモリ使用量はprecision_thresholdに依存
- Star-Treeインデックス利用時は事前集計により大幅に高速化
- CompensatedSum（Kahan加算）により数値精度を維持

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

- インデックスの読み取り権限が必要
- フィールドレベルセキュリティの対象

## 備考

- AvgAggregatorはStarTreePreComputeCollectorインターフェースを実装しており、Star-Tree事前集計に対応
- counts, sums, compensationsの3つのBigArray配列でバケットごとの集計状態を管理

---

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

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

### 推奨読解順序

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

メトリクス集計の結果を保持するInternalAggregationクラスを理解する。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 1-1 | InternalAvg.java | `server/src/main/java/org/opensearch/search/aggregations/metrics/InternalAvg.java` | Avg集計結果クラス。count, sumフィールドとreduce処理 |
| 1-2 | InternalCardinality.java | `server/src/main/java/org/opensearch/search/aggregations/metrics/InternalCardinality.java` | Cardinality結果クラス。HyperLogLogPlusPlusデータ |
| 1-3 | CompensatedSum.java | `server/src/main/java/org/opensearch/search/aggregations/metrics/CompensatedSum.java` | Kahan補償和アルゴリズム実装 |

**読解のコツ**: メトリクス集計はValuesSource.Numericを使用して数値フィールドの値を取得する。LeafOnly制約（サブ集計不可）のBuilderが多い点に注意。

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

代表的なメトリクス集計（Avg）のビルダーとファクトリを理解する。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 2-1 | AvgAggregationBuilder.java | `server/src/main/java/org/opensearch/search/aggregations/metrics/AvgAggregationBuilder.java` | Avg集計のビルダー。ValuesSourceAggregationBuilder.LeafOnlyを継承 |
| 2-2 | AvgAggregatorFactory.java | `server/src/main/java/org/opensearch/search/aggregations/metrics/AvgAggregatorFactory.java` | AvgAggregatorの生成ファクトリ |

**主要処理フロー**:
1. **58行目**: AvgAggregationBuilderクラス定義。LeafOnly制約
2. **59行目**: NAME = "avg"
3. **60行目**: REGISTRY_KEYによるValuesSourceRegistryへの登録

#### Step 3: 集計実行ロジックを理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 3-1 | AvgAggregator.java | `server/src/main/java/org/opensearch/search/aggregations/metrics/AvgAggregator.java` | Avg集計の実行ロジック。StarTreePreComputeCollectorを実装 |
| 3-2 | NumericMetricsAggregator.java | `server/src/main/java/org/opensearch/search/aggregations/metrics/NumericMetricsAggregator.java` | 数値メトリクス集計の基底クラス |

**主要処理フロー**:
- **73行目**: AvgAggregatorクラス定義。NumericMetricsAggregator.SingleValue継承、StarTreePreComputeCollector実装
- **75-79行目**: valuesSource, counts, sums, compensations, formatフィールド

#### Step 4: HyperLogLog++アルゴリズムを理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 4-1 | HyperLogLogPlusPlus.java | `server/src/main/java/org/opensearch/search/aggregations/metrics/HyperLogLogPlusPlus.java` | HLL++アルゴリズム実装 |
| 4-2 | CardinalityAggregator.java | `server/src/main/java/org/opensearch/search/aggregations/metrics/CardinalityAggregator.java` | Cardinality集計実行ロジック |

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

```
SearchAction (REST API)
    |
    +-- SearchService.executeQueryPhase()
          |
          +-- AggregationPhase.preProcess()
          |     +-- AvgAggregationBuilder.build()
          |           +-- AvgAggregatorFactory.create()
          |                 +-- AvgAggregator()
          |
          +-- AggregationPhase.execute()
          |     +-- AvgAggregator.getLeafCollector()
          |     |     +-- LeafBucketCollectorBase.collect()
          |     |           +-- SortedNumericDoubleValues.advanceExact()
          |     |           +-- CompensatedSum.add()
          |     |
          |     +-- AvgAggregator.getStarTreeBucketCollector() [Star-Tree時]
          |           +-- StarTreePreComputeCollector
          |
          +-- AvgAggregator.buildAggregation()
                +-- InternalAvg(count, sum)
```

### データフロー図

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

検索リクエスト       +--> ValuesSourceConfig構成
(aggregationsセクション)   |
                     +--> AvgAggregator生成
                     |
Luceneセグメント     +--> LeafBucketCollector
(DocValues)          |     +-- 数値読取 → sum += value
                     |     +-- count++
                     |     +-- CompensatedSum補正
                     |
                     +--> InternalAvg構築           +--> 検索レスポンス
                     |     (sum / count = avg)            (value: avg値)
                     |
                     +--> reduce（コーディネータ）
                           +-- sum合算、count合算
                           +-- 最終avg算出
```

### 関連ファイル一覧

| ファイル | パス | 種別 | 役割 |
|---------|------|------|------|
| AvgAggregationBuilder.java | `server/src/main/java/org/opensearch/search/aggregations/metrics/AvgAggregationBuilder.java` | ソース | Avg集計ビルダー |
| AvgAggregator.java | `server/src/main/java/org/opensearch/search/aggregations/metrics/AvgAggregator.java` | ソース | Avg集計実行ロジック |
| InternalAvg.java | `server/src/main/java/org/opensearch/search/aggregations/metrics/InternalAvg.java` | ソース | Avg集計結果クラス |
| SumAggregator.java | `server/src/main/java/org/opensearch/search/aggregations/metrics/SumAggregator.java` | ソース | Sum集計実行ロジック |
| MinAggregator.java | `server/src/main/java/org/opensearch/search/aggregations/metrics/MinAggregator.java` | ソース | Min集計実行ロジック |
| MaxAggregator.java | `server/src/main/java/org/opensearch/search/aggregations/metrics/MaxAggregator.java` | ソース | Max集計実行ロジック |
| CardinalityAggregator.java | `server/src/main/java/org/opensearch/search/aggregations/metrics/CardinalityAggregator.java` | ソース | Cardinality集計実行ロジック |
| HyperLogLogPlusPlus.java | `server/src/main/java/org/opensearch/search/aggregations/metrics/HyperLogLogPlusPlus.java` | ソース | HLL++アルゴリズム |
| CompensatedSum.java | `server/src/main/java/org/opensearch/search/aggregations/metrics/CompensatedSum.java` | ソース | Kahan補償和 |
| NumericMetricsAggregator.java | `server/src/main/java/org/opensearch/search/aggregations/metrics/NumericMetricsAggregator.java` | ソース | 数値メトリクス基底クラス |
