# 画面設計書 139-スクリプト取得

## 概要

本ドキュメントは、OpenSearchのストアドスクリプト取得API（`GET /_scripts/{id}`）の画面設計書である。クラスタ状態に保存されたスクリプトの定義情報を取得するためのREST APIエンドポイントの仕様を定義する。

### 本画面の処理概要

本APIは、OpenSearchクラスタに保存されたストアドスクリプトの定義情報をJSON形式で返却するエンドポイントである。ストアドスクリプトはPainless、Mustache、Expressionなどの言語で記述され、検索クエリ、アップデート操作、インジェストパイプラインなどで再利用可能なスクリプトとして保管される。

**業務上の目的・背景**：ストアドスクリプトは、複雑な計算ロジックやデータ変換処理を一元管理するために使用される。スコアリングカスタマイズ、条件付きフィールド更新、検索テンプレートなどの用途で活用される。運用者がスクリプトの内容を確認し、更新の要否を判断する際に本APIが使用される。

**画面へのアクセス方法**：HTTPクライアントから `GET /_scripts/{id}` へリクエストを送信する。

**主要な操作・処理内容**：
1. クライアントがスクリプトIDを指定してGETリクエストを送信する
2. RestGetStoredScriptActionがリクエストを受け取り、GetStoredScriptRequestを構築する
3. クラスタマネージャノードでクラスタ状態からスクリプト定義を取得する
4. スクリプト定義をJSON形式でレスポンスとして返却する

**画面遷移**：本APIで取得したスクリプト定義を基に、スクリプト作成・更新API（140）で更新、スクリプト削除API（141）で削除を行う流れが一般的である。取得したスクリプトは検索API（21）やドキュメント更新API（10）で使用される。

**権限による表示制御**：クラスタのメタデータ読み取り権限が必要。権限不足の場合は403エラーが返却される。

## 関連機能

| 機能No | 機能名 | 関連種別 | 関連する操作・処理 |
|--------|--------|----------|------------------|
| 82 | ストアドスクリプト | 主機能 | 保存済みスクリプトを返す処理 |

## 画面種別

詳細（REST API GETエンドポイント）

## URL/ルーティング

| メソッド | パス | 説明 |
|---------|------|------|
| GET | `/_scripts/{id}` | 指定IDのストアドスクリプトを返す |

## 入出力項目

### パスパラメータ

| パラメータ名 | 型 | 必須 | 説明 |
|-------------|-----|------|------|
| id | string | はい | スクリプトID |

### クエリパラメータ

| パラメータ名 | 型 | 必須 | デフォルト | 説明 |
|-------------|-----|------|-----------|------|
| cluster_manager_timeout | time | いいえ | 30s | クラスタマネージャノードへの接続タイムアウト |
| master_timeout | time | いいえ | 30s | （非推奨）cluster_manager_timeoutを使用すること |

## 表示項目

### レスポンスボディ

| 項目名 | 型 | 説明 |
|--------|-----|------|
| _id | string | スクリプトID |
| found | boolean | スクリプトが見つかったか |
| script | object | スクリプト定義 |
| script.lang | string | スクリプト言語（painless、mustache等） |
| script.source | string | スクリプトのソースコード |

## イベント仕様

### 1-スクリプト取得リクエスト

クライアントからGETリクエストを受信すると、RestGetStoredScriptActionの`prepareRequest`メソッドが呼び出される。パスパラメータからスクリプトIDを取得し、GetStoredScriptRequestオブジェクトを生成する。クラスタマネージャタイムアウトを設定した後、`client.admin().cluster().getStoredScript()`を呼び出す。TransportGetStoredScriptActionのclusterManagerOperationメソッドで、ScriptServiceの`getStoredScript()`を使用してクラスタ状態からスクリプト定義を取得し、GetStoredScriptResponseを生成して返却する。

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

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

| 操作（イベント） | 対象テーブル | 操作種別 | 概要 |
|----------------|-------------|---------|------|
| スクリプト取得 | ClusterState（ScriptMetadata） | SELECT | クラスタ状態からスクリプト定義を読み取り |

### テーブル別更新項目詳細

#### ClusterState - ScriptMetadata

| 操作 | 項目（カラム名） | 更新値・取得条件 | 備考 |
|-----|-----------------|-----------------|------|
| SELECT | scripts[{id}] | 指定IDのスクリプト定義を取得 | StoredScriptSource形式で保存 |

## メッセージ仕様

| メッセージID | メッセージ内容 | 種別 | 発生条件 |
|-------------|--------------|------|---------|
| 200 | スクリプト定義のJSONレスポンス（found=true） | 成功 | スクリプトが存在する場合 |
| 404 | スクリプトが見つからない（found=false） | エラー | 指定IDのスクリプトが存在しない場合 |
| 403 | 権限不足 | エラー | 必要な権限がない場合 |

## 例外処理

- **スクリプトが存在しない場合**: 指定IDのスクリプトが見つからない場合、found=falseのレスポンスがHTTPステータス404で返却される
- **クラスタマネージャノード接続タイムアウト**: 指定時間内に応答がない場合、タイムアウトエラーが返却される
- **クラスタブロック**: クラスタ全体にメタデータ読み取りブロックが設定されている場合、ClusterBlockExceptionが返却される

## 備考

- `master_timeout` パラメータはバージョン2.0.0で非推奨となり、`cluster_manager_timeout` の使用が推奨される
- TransportGetStoredScriptActionはTransportClusterManagerNodeReadActionを継承しており、クラスタマネージャノードで処理される読み取りアクション
- スクリプト定義はStoredScriptSource形式で管理され、lang（言語）とsource（ソースコード）を含む

---

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

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

### 推奨読解順序

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

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 1-1 | GetStoredScriptRequest.java | `server/src/main/java/org/opensearch/action/admin/cluster/storedscripts/GetStoredScriptRequest.java` | 取得リクエストの構造。idフィールド |
| 1-2 | GetStoredScriptResponse.java | `server/src/main/java/org/opensearch/action/admin/cluster/storedscripts/GetStoredScriptResponse.java` | レスポンスのXContent変換ロジック。id、found、scriptフィールド |
| 1-3 | StoredScriptSource.java | `server/src/main/java/org/opensearch/script/StoredScriptSource.java` | ストアドスクリプトのソース定義構造。lang、sourceフィールド |

**読解のコツ**: GetStoredScriptRequestはClusterManagerNodeReadRequestを継承しており、読み取り専用のクラスタマネージャ操作である。

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

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 2-1 | RestGetStoredScriptAction.java | `server/src/main/java/org/opensearch/rest/action/admin/cluster/RestGetStoredScriptAction.java` | RESTリクエストの受付処理 |

**主要処理フロー**:
1. **行58**: ルート定義 - `GET /_scripts/{id}` を登録
2. **行68**: パスパラメータ`id`を取得
3. **行69**: GetStoredScriptRequest(id)を生成
4. **行70-71**: クラスタマネージャタイムアウトの設定（非推奨パラメータの互換処理含む）
5. **行72**: `client.admin().cluster().getStoredScript()` を呼び出し

#### Step 3: トランスポート層を理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 3-1 | TransportGetStoredScriptAction.java | `server/src/main/java/org/opensearch/action/admin/cluster/storedscripts/TransportGetStoredScriptAction.java` | クラスタマネージャノードでの処理 |

**主要処理フロー**:
- **行84**: executor()はThreadPool.Names.SAMEを返す（同一スレッドで実行）
- **行93-98**: clusterManagerOperationでScriptService.getStoredScript()を呼び出し、GetStoredScriptResponseを生成
- **行102-104**: メタデータ読み取りレベルのクラスタブロックチェック

#### Step 4: サービス層を理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 4-1 | ScriptService.java | `server/src/main/java/org/opensearch/script/ScriptService.java` | getStoredScript()メソッドによるクラスタ状態からのスクリプト取得 |

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

```
RestGetStoredScriptAction.prepareRequest()
    |
    +-- GetStoredScriptRequest(id)
    |
    +-- client.admin().cluster().getStoredScript()
            |
            +-- TransportGetStoredScriptAction.clusterManagerOperation()
                    |
                    +-- ScriptService.getStoredScript(state, request)
                    |       |
                    |       +-- ClusterState.metadata().custom(ScriptMetadata.TYPE)
                    |       +-- ScriptMetadata.getStoredScript(id)
                    |
                    +-- GetStoredScriptResponse(id, source)
                            |
                            +-- RestStatusToXContentListener -> JSONレスポンス
```

### データフロー図

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

GET /_scripts/{id}
    |
    +-- id (パスパラメータ) --> RestGetStoredScriptAction           --> GetStoredScriptRequest
    +-- cluster_manager_timeout  |                                       |
                                 v                                       v
                          TransportGetStoredScriptAction         ClusterState読み取り
                                 |                                       |
                                 v                                       v
                          ScriptService.getStoredScript()        GetStoredScriptResponse
                                                                        |
                                                                        v
                                                             {_id, found, script}
```

### 関連ファイル一覧

| ファイル | パス | 種別 | 役割 |
|---------|------|------|------|
| RestGetStoredScriptAction.java | `server/src/main/java/org/opensearch/rest/action/admin/cluster/RestGetStoredScriptAction.java` | ソース | RESTエントリーポイント |
| GetStoredScriptRequest.java | `server/src/main/java/org/opensearch/action/admin/cluster/storedscripts/GetStoredScriptRequest.java` | ソース | リクエストデータ構造 |
| GetStoredScriptResponse.java | `server/src/main/java/org/opensearch/action/admin/cluster/storedscripts/GetStoredScriptResponse.java` | ソース | レスポンスデータ構造 |
| TransportGetStoredScriptAction.java | `server/src/main/java/org/opensearch/action/admin/cluster/storedscripts/TransportGetStoredScriptAction.java` | ソース | トランスポートアクション |
| GetStoredScriptAction.java | `server/src/main/java/org/opensearch/action/admin/cluster/storedscripts/GetStoredScriptAction.java` | ソース | アクション定義 |
| ScriptService.java | `server/src/main/java/org/opensearch/script/ScriptService.java` | ソース | スクリプト管理サービス |
| StoredScriptSource.java | `server/src/main/java/org/opensearch/script/StoredScriptSource.java` | ソース | スクリプトソース定義 |
| ScriptMetadata.java | `server/src/main/java/org/opensearch/script/ScriptMetadata.java` | ソース | スクリプトメタデータ |
| get_script.json | `rest-api-spec/src/main/resources/rest-api-spec/api/get_script.json` | API仕様 | REST API仕様定義 |
