# バッチ設計書 31-find-spark-home

## 概要

本ドキュメントは、Sparkの環境変数SPARK_HOMEの検出・設定を行うスクリプト `bin/find-spark-home` のバッチ設計書である。本スクリプトはBashスクリプトとPythonスクリプト（`python/pyspark/find_spark_home.py`）の2つのコンポーネントで構成され、Sparkの各CLIスクリプト（spark-submit、pyspark等）から呼び出される共通基盤スクリプトである。

### 本バッチの処理概要

本スクリプトは、Sparkの各種CLIツールやデーモン起動スクリプトが正しく動作するために必要なSPARK_HOME環境変数を自動的に検出・設定する役割を担う。

**業務上の目的・背景**：Sparkのすべてのコマンドラインツール（spark-submit、spark-shell、pysparkなど）は、SPARK_HOMEを基準にクラスパスや設定ファイルを解決する。ユーザーがSPARK_HOMEを明示的に設定していない場合でも、ソースビルド環境やpipインストール環境など多様なインストール形態に対応してSPARK_HOMEを正確に検出する必要がある。本スクリプトはこの検出ロジックを一元化し、すべてのSparkスクリプトが一貫した基準で動作することを保証する。

**バッチの実行タイミング**：Sparkの各CLIスクリプト（spark-submit、pyspark、spark-shell等）の起動時に毎回sourceコマンドで読み込まれる。ユーザーが直接実行するスクリプトではなく、他スクリプトからの間接呼び出しが主な利用形態である。

**主要な処理内容**：
1. 環境変数SPARK_HOMEが既に設定済みかを確認し、設定済みであれば即座に終了する
2. find_spark_home.pyスクリプトの存在有無により、pipインストール環境かソースビルド環境かを判定する
3. ソースビルド環境の場合、スクリプトの親ディレクトリをSPARK_HOMEとして設定する
4. pipインストール環境の場合、Pythonスクリプト（find_spark_home.py）を使用してSPARK_HOMEを探索する
5. Pythonスクリプトでは、複数の候補パス（モジュールパス、spark-distribution配下等）を順に検査し、bin/spark-submitとjarsディレクトリの存在をもってSPARK_HOMEを確定する

**前後の処理との関連**：本スクリプトはSpark CLIの起動チェーン最初期に呼び出される。spark-submit、spark-shell、pyspark、spark-sql、spark-class等のすべてのbinスクリプトから参照される前提スクリプトである。後続処理としてload-spark-env.shが呼ばれ、SPARK_HOMEを基準にした追加の環境設定が行われる。

**影響範囲**：SPARK_HOME環境変数の設定に影響するため、Sparkのすべてのコマンドラインツール、デーモン起動スクリプト、およびpipインストールされたPySparkに影響する。SPARK_HOMEが正しく設定されない場合、クラスパス解決、設定ファイル読み込み、JARファイル検索などあらゆる後続処理が失敗する。

## バッチ種別

環境設定（SPARK_HOME検出・設定ユーティリティ）

## 実行スケジュール

| 項目 | 内容 |
|-----|------|
| 実行頻度 | 随時（Sparkコマンド起動ごと） |
| 実行時刻 | N/A |
| 実行曜日 | N/A |
| 実行日 | N/A |
| トリガー | 他スクリプトからのsource呼び出し |

## 実行条件

### 前提条件

| 条件 | 説明 |
|-----|------|
| Bashシェル環境 | Bashスクリプト部分は`/usr/bin/env bash`で実行可能であること |
| Python3（pipインストール時） | pipインストール環境では`python3`または`PYSPARK_DRIVER_PYTHON`で指定されたPythonインタープリタが必要 |
| ファイルシステムアクセス | スクリプトのディレクトリ構造にアクセス可能であること |

### 実行可否判定

SPARK_HOMEが既に設定されている場合は即座に終了（exit 0）する。未設定の場合、スクリプトの配置場所に応じた検出ロジックを実行する。

## 入力仕様

### 入力パラメータ

| パラメータ名 | 型 | 必須 | デフォルト値 | 説明 |
|-------------|-----|-----|-------------|------|
| SPARK_HOME（環境変数） | string | No | 未設定 | 既に設定されている場合、検出処理をスキップ |
| PYSPARK_DRIVER_PYTHON（環境変数） | string | No | 未設定 | pipインストール時に使用するPythonインタープリタのパス |
| PYSPARK_PYTHON（環境変数） | string | No | python3 | PYSPARK_DRIVER_PYTHON未設定時のフォールバック用Pythonインタープリタ |

### 入力データソース

| データソース | 形式 | 説明 |
|-------------|------|------|
| find_spark_home.py | Python | pipインストール時のSPARK_HOME検出用Pythonスクリプト（bin/ディレクトリ同階層に存在する場合に使用） |
| bin/spark-submit | スクリプト | SPARK_HOME候補パスの検証に使用（存在確認のみ） |
| jars/ または assembly/ | ディレクトリ | SPARK_HOME候補パスの検証に使用（存在確認のみ） |

## 出力仕様

### 出力データ

| 出力先 | 形式 | 説明 |
|-------|------|------|
| SPARK_HOME（環境変数） | 環境変数（export） | 検出されたSPARK_HOMEのパスをexportする |

### 出力ファイル仕様

ファイル出力なし。環境変数SPARK_HOMEの設定のみを行う。

## 処理フロー

### 処理シーケンス

```
1. SPARK_HOME環境変数チェック
   └─ 既に設定されている場合、exit 0で終了
2. find_spark_home.pyの存在チェック
   └─ スクリプトと同階層にfind_spark_home.pyが存在するかを確認
3a. [find_spark_home.py不在の場合] ソースビルド環境と判定
   └─ スクリプトの親ディレクトリ（bin/の一つ上）をSPARK_HOMEとしてexport
3b. [find_spark_home.py存在の場合] pipインストール環境と判定
   └─ Pythonインタープリタの決定
      └─ PYSPARK_DRIVER_PYTHON → PYSPARK_PYTHON → python3 の優先順で選択
   └─ find_spark_home.pyを実行し、以下の候補パスを順に検査:
      (1) スクリプトの親ディレクトリ（../）
      (2) pysparkモジュールディレクトリ配下のspark-distributionディレクトリ
      (3) pysparkモジュールディレクトリ自体
      (4) pysparkモジュールの2階層上（edit modeインストール時）
   └─ 候補パスの検証: bin/spark-submitファイル存在 かつ jarsまたはassemblyディレクトリ存在
   └─ 最初に検証を通過したパスをSPARK_HOMEとしてexport
```

### フローチャート

```mermaid
flowchart TD
    A[スクリプト開始] --> B{SPARK_HOME設定済み?}
    B -->|はい| C[exit 0]
    B -->|いいえ| D{find_spark_home.py存在?}
    D -->|いいえ| E[親ディレクトリをSPARK_HOMEに設定]
    D -->|はい| F[Pythonインタープリタ決定]
    F --> G[find_spark_home.py実行]
    G --> H[候補パスリスト構築]
    H --> I{候補パスにbin/spark-submit<br/>とjars/assembly存在?}
    I -->|見つかった| J[SPARK_HOMEとしてexport]
    I -->|見つからない| K[エラーメッセージ出力, exit -1]
    E --> L[終了]
    J --> L
    K --> L
    C --> L
```

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

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

データベース操作なし。本スクリプトはファイルシステムの参照と環境変数の設定のみを行う。

## エラー処理

### エラーケース一覧

| エラーコード | エラー種別 | 発生条件 | 対処方法 |
|------------|----------|---------|---------|
| -1 | SPARK_HOME検出失敗 | 候補パスのいずれにもSpark環境が見つからない場合（Pythonスクリプト経由） | SPARK_HOME環境変数を手動設定するか、PySparkを正しくインストールする |
| N/A | Pythonインタープリタ不在 | pipインストール環境でpython3が見つからない場合 | PYSPARK_DRIVER_PYTHONまたはPYSPARK_PYTHON環境変数で有効なPythonパスを指定する |

### リトライ仕様

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

### 障害時対応

SPARK_HOME検出に失敗した場合は、エラーメッセージに検索したパスの一覧が表示される。ユーザーはSPARK_HOME環境変数を手動でexportするか、PySparkのインストール状態を確認する。pipインストール環境では`python -c 'import pyspark'`でPySparkが正しくインポートできるか確認する。

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

| 項目 | 内容 |
|-----|------|
| トランザクション範囲 | N/A（環境変数設定のみ） |
| コミットタイミング | N/A |
| ロールバック条件 | N/A |

## パフォーマンス要件

| 項目 | 内容 |
|-----|------|
| 想定処理件数 | 1回（単一のSPARK_HOME検出） |
| 目標処理時間 | 1秒未満 |
| メモリ使用量上限 | 最小限（シェルプロセスのみ） |

## 排他制御

排他制御なし。環境変数の設定のみであり、並行実行の影響はない。

## ログ出力

| ログ種別 | 出力タイミング | 出力内容 |
|---------|--------------|---------|
| エラーログ | SPARK_HOME検出失敗時 | 検索した候補パスの一覧と、pipインストール環境の場合の対処方法ガイダンス |

## 監視・アラート

| 監視項目 | 閾値 | アラート先 |
|---------|-----|----------|
| N/A | N/A | N/A |

本スクリプトは即時実行・即時終了の性質を持つため、監視・アラートの対象外とする。

## 備考

- 本スクリプトはBashスクリプト（`bin/find-spark-home`）とPythonスクリプト（`python/pyspark/find_spark_home.py`）の2つのファイルで構成される
- pipインストールされたPySpark環境では、`spark-distribution`ディレクトリ配下にダウンロードされたSparkバイナリを検出する機能がある（SPARK-32017対応）
- PYSPARK_DRIVER_PYTHONが未設定の場合、PYSPARK_PYTHONが参照され、それも未設定の場合は`python3`がデフォルトで使用される
- ソースビルド環境（直接クローンしたリポジトリ）では、Pythonスクリプトを経由せず直接親ディレクトリをSPARK_HOMEとして設定する
