LangChain + Gemini 2.5 Flash 処理コマンド(画像アップロード可能)(ソースコードと実行結果)

Python開発環境,ライブラリ類

ここでは、最低限の事前準備について説明する。機械学習や深層学習を行う場合は、NVIDIA CUDA、Visual Studio、Cursorなどを追加でインストールすると便利である。これらについては別ページ https://www.kkaneko.jp/cc/dev/aiassist.htmlで詳しく解説しているので、必要に応じて参照してください。

Python 3.12 のインストール(Windows 上) [クリックして展開]

以下のいずれかの方法で Python 3.12 をインストールする。Python がインストール済みの場合、この手順は不要である。

方法1:winget によるインストール

管理者権限コマンドプロンプトで以下を実行する。管理者権限のコマンドプロンプトを起動するには、Windows キーまたはスタートメニューから「cmd」と入力し、表示された「コマンドプロンプト」を右クリックして「管理者として実行」を選択する。

winget install --scope machine --id Python.Python.3.12 -e --silent --disable-interactivity --force --accept-source-agreements --accept-package-agreements --override "/quiet InstallAllUsers=1 PrependPath=1 Include_pip=1 Include_test=0 Include_launcher=1 InstallLauncherAllUsers=1"

--scope machine を指定することで、システム全体(全ユーザー向け)にインストールされる。このオプションの実行には管理者権限が必要である。インストール完了後、コマンドプロンプトを再起動すると PATH が自動的に設定される。

方法2:インストーラーによるインストール

  1. Python 公式サイト(https://www.python.org/downloads/)にアクセスし、「Download Python 3.x.x」ボタンから Windows 用インストーラーをダウンロードする。
  2. ダウンロードしたインストーラーを実行する。
  3. 初期画面の下部に表示される「Add python.exe to PATH」に必ずチェックを入れてから「Customize installation」を選択する。このチェックを入れ忘れると、コマンドプロンプトから python コマンドを実行できない。
  4. 「Install Python 3.xx for all users」にチェックを入れ、「Install」をクリックする。

インストールの確認

コマンドプロンプトで以下を実行する。

python --version

バージョン番号(例:Python 3.12.x)が表示されればインストール成功である。「'python' は、内部コマンドまたは外部コマンドとして認識されていません。」と表示される場合は、インストールが正常に完了していない。

AIエディタ Windsurf のインストール(Windows 上) [クリックして展開]

Pythonプログラムの編集・実行には、AIエディタの利用を推奨する。ここでは、Windsurfのインストールを説明する。Windsurf がインストール済みの場合、この手順は不要である。

管理者権限コマンドプロンプトで以下を実行する。管理者権限のコマンドプロンプトを起動するには、Windows キーまたはスタートメニューから「cmd」と入力し、表示された「コマンドプロンプト」を右クリックして「管理者として実行」を選択する。

winget install --scope machine --id Codeium.Windsurf -e --silent --disable-interactivity --force --accept-source-agreements --accept-package-agreements --custom "/SP- /SUPPRESSMSGBOXES /NORESTART /CLOSEAPPLICATIONS /DIR=""C:\Program Files\Windsurf"" /MERGETASKS=!runcode,addtopath,associatewithfiles,!desktopicon"
powershell -Command "$env:Path=[System.Environment]::GetEnvironmentVariable('Path','Machine')+';'+[System.Environment]::GetEnvironmentVariable('Path','User'); windsurf --install-extension MS-CEINTL.vscode-language-pack-ja --force; windsurf --install-extension ms-python.python --force; windsurf --install-extension Codeium.windsurfPyright --force"

--scope machine を指定することで、システム全体(全ユーザー向け)にインストールされる。このオプションの実行には管理者権限が必要である。インストール完了後、コマンドプロンプトを再起動すると PATH が自動的に設定される。

関連する外部ページ

Windsurf の公式ページ: https://windsurf.com/

必要なライブラリをシステム領域にインストール

管理者権限コマンドプロンプトで以下を実行する。管理者権限のコマンドプロンプトを起動するには、Windows キーまたはスタートメニューから「cmd」と入力し、表示された「コマンドプロンプト」を右クリックして「管理者として実行」を選択する。

pip install langchain-google-genai pillow langchain-core

LangChain + Gemini 2.5 Flash 処理コマンド(画像アップロード可能)

概要

本プログラムは、LangChainフレームワークとGemini 2.5 Flash APIを組み合わせたバッチ処理型AIアプリケーションである。テキストファイルと画像ファイル(オプション)を入力として受け付け、指定されたインストラクションに基づいて処理を行うマルチモーダル機能を持つ。コマンドライン引数による一回完結の処理方式を採用し、Gemini 2.5 Flash の思考機能による高度な推論処理と問題解決を実現している。

主要技術

Gemini 2.5 Flash API

Gemini Teamが2025年に開発した思考機能付き言語モデルAPI [1]。推論プロセスを経た内部思考により、複雑な問題解決を可能とする。

LangChain

Harrison Chaseが2022年に開発した大規模言語モデル統合フレームワーク [2][3]。LLMを活用したアプリケーション開発を支援する。

Python argparse

Python標準ライブラリのコマンドライン引数解析モジュール。位置引数とオプション引数の処理、ヘルプメッセージの自動生成を提供する。

技術的特徴

本実装では、複数の技術的工夫が施されている。マルチモーダルメッセージ構築にはLangChainのHumanMessageクラスを使用し、インストラクションテキストと処理対象テキストファイル、オプションの画像データを統合処理する。画像データはBase64エンコーディングによってテキスト形式に変換され、APIリクエストに組み込まれる。APIキー管理については、環境変数(GEMINI_API_KEY、GOOGLE_API_KEY)と.envファイルの双方からの自動取得機能を実装している。

実装の特色

バッチ処理型設計により、コマンドライン引数で処理内容を指定し、一回の実行で完結する効率的な処理を実現している。出力形式は標準出力またはファイル出力(-oオプション)を選択可能で、自動化処理やパイプライン処理に適している。設定値の定数化(TEMPERATURE、MODEL_NAME)により、保守性と可読性を向上させている。包括的なエラーハンドリングにより、ファイル存在確認、APIキー検証、例外処理を適切に実装している。

参考文献

[1] Gemini Team, Google. (2025). Gemini 2.5: Our newest Gemini model with thinking. Google DeepMind. https://blog.google/technology/google-deepmind/gemini-model-thinking-updates-march-2025/

[2] Chase, H. (2022). LangChain: Building applications with LLMs through composability. GitHub. https://github.com/langchain-ai/langchain

[3] LangChain Development Team. (2025). LangChain Documentation. LangChain Inc. https://python.langchain.com/docs/introduction/

ソースコード

#!/usr/bin/env python3
# LangChain + Gemini 2.5 Flash 処理コマンド
# 特徴技術名: Gemini 2.5 Flash API
# 出典: Gemini Team, Google. (2025). Gemini 2.5: Our newest Gemini model with thinking. Google DeepMind. https://blog.google/technology/google-deepmind/gemini-model-thinking-updates-march-2025/
# 特徴機能: 思考機能による文脈理解推論(推論プロセスを経た思考により、単純な応答生成ではなく複雑な問題解決と文脈理解を実現)
# 学習済みモデル: 使用なし(Gemini 2.5 Flash APIによる直接呼び出し)
# 方式設計:
#   関連利用技術: LangChain(LLMフレームワーク)、argparse(コマンドライン引数解析)、base64(画像エンコーディング)、pathlib(ファイル操作)
#   入力と出力: 入力: インストラクション(コマンドライン引数)、テキストファイル、画像ファイル(オプション)、出力: AI応答テキスト(標準出力またはファイル)
#   処理手順: APIキー取得→コマンドライン引数解析→ファイル読み込み→LangChain初期化→API呼び出し→結果出力
#   前処理、後処理: 前処理: テキストファイル読み込み、画像Base64エンコーディング、マルチモーダルメッセージ構築、後処理: 結果の標準出力またはファイル保存
#   調整を必要とする設定値: GEMINI_API_KEY(Gemini APIアクセスキー)、TEMPERATURE(応答の一貫性制御)、MODEL_NAME(使用モデル)
# 前準備: pip install langchain-google-genai langchain-core

import os
import re
import sys
import base64
import argparse
from pathlib import Path
from datetime import datetime
from langchain_google_genai import ChatGoogleGenerativeAI
from langchain_core.messages import HumanMessage

# 設定定数
TEMPERATURE = 0.1
MODEL_NAME = "gemini-2.5-flash"

def load_api_key():
    # 環境変数から取得
    for var_name in ['GEMINI_API_KEY', 'GOOGLE_API_KEY']:
        if api_key := os.getenv(var_name):
            return api_key

    # .envファイルから取得
    for env_file in ['.env', '.env.development']:
        if Path(env_file).exists():
            try:
                content = Path(env_file).read_text()
                for var_name in ['GEMINI_API_KEY', 'GOOGLE_API_KEY']:
                    if match := re.search(rf'^\s*{var_name}\s*=(.+)$', content, re.M):
                        return match.group(1).strip().strip('"\'')
            except Exception:
                continue
    return None

def encode_image(image_path):
    try:
        with open(image_path, "rb") as f:
            return base64.b64encode(f.read()).decode()
    except Exception as e:
        print(f"画像読み込みエラー: {e}", file=sys.stderr)
        return None

def generate_filename(extension="txt"):
    timestamp = datetime.now().strftime("%Y%m%d_%H%M%S")
    return f"gemini_2.5_flash_output_{timestamp}.{extension}"

def main():
    # プログラム開始時の明確なタイトル表示
    print("=== LangChain + Gemini 2.5 Flash 処理コマンド ===")

    parser = argparse.ArgumentParser()
    parser.add_argument("instruction", help="処理インストラクション")
    parser.add_argument("text_file", help="処理対象テキストファイル")
    parser.add_argument("image_file", nargs="?", help="画像ファイル(オプション)")
    parser.add_argument("-o", "--output", help="出力ファイル")
    args = parser.parse_args()

    api_key = load_api_key()
    if not api_key:
        # APIキー取得手順を表示
        print("=" * 60)
        print("Gemini APIキーが見つかりません")
        print("=" * 60)
        print()
        print("このプログラムを使用するには、Gemini APIキーが必要です。")
        print()
        print("APIキー取得手順:")
        print("1. または手動でAPIキーを取得:")
        print("   - https://aistudio.google.com/app/apikey にアクセス")
        print("   - Googleアカウントでログイン")
        print("   - 'Get API key' → 'Create API key' をクリック")
        print("   - 'Create API key in new project' を選択")
        print("   - 生成されたAPIキーをコピー")
        print()
        print("参考: 「Gemini APIキー取得支援ツール」を用意しています")
        print("   https://www.kkaneko.jp/ai/labo/geminiapikey.html")
        print()
        print("2. 設定")
        print("   **1. 環境変数での設定**")
        print("   - `GEMINI_API_KEY` または `GOOGLE_API_KEY` を環境変数に設定")
        print("   **2. .envファイルでの設定**")
        print("   - プログラムと同じフォルダに `.env` ファイルを作成し、以下のように記述:")
        print("   GEMINI_API_KEY=your_api_key_here")
        print("   または")
        print("   GOOGLE_API_KEY=your_api_key_here")
        print()
        print("3. 設定後、このプログラムを再実行してください")
        print("=" * 60)

    if not Path(args.text_file).exists():
        print(f"テキストファイルが見つかりません: {args.text_file}", file=sys.stderr)
        return 1

    try:
        text_content = Path(args.text_file).read_text(encoding='utf-8')
    except Exception as e:
        print(f"テキストファイル読み込みエラー: {e}", file=sys.stderr)
        return 1

    image_data = None
    if args.image_file:
        if not Path(args.image_file).exists():
            print(f"画像ファイルが見つかりません: {args.image_file}", file=sys.stderr)
            return 1
        image_data = encode_image(args.image_file)
        if not image_data:
            return 1

    try:
        # 初期化完了メッセージ
        print("LangChain初期化中...")
        llm = ChatGoogleGenerativeAI(
            model=MODEL_NAME,
            google_api_key=api_key,
            temperature=TEMPERATURE
        )
        print("初期化完了!処理を開始します")

        # 操作ガイドの表示
        print(f"使用モデル: {MODEL_NAME}")
        print(f"処理対象ファイル: {args.text_file}")
        if args.image_file:
            print(f"画像ファイル: {args.image_file}")
        print(f"インストラクション: {args.instruction}")

        prompt = f"{args.instruction}\n\n{text_content}"

        if image_data:
            message = HumanMessage(
                content=[
                    {"type": "text", "text": prompt},
                    {"type": "image_url", "image_url": f"data:image/jpeg;base64,{image_data}"}
                ]
            )
            response = llm.invoke([message])
        else:
            response = llm.invoke(prompt)

        result = response.content

        if args.output:
            Path(args.output).write_text(result, encoding='utf-8')
            print(f"結果をファイルに保存しました: {args.output}")
        else:
            # タイムスタンプ付きファイル名の自動生成と保存
            output_filename = generate_filename()
            Path(output_filename).write_text(result, encoding='utf-8')
            print(f"結果をファイルに保存しました: {output_filename}")
            print("\n=== 処理結果 ===")
            print(result)

    except KeyboardInterrupt:
        print("\n\nプログラムを終了します", file=sys.stderr)
        return 1
    except Exception as e:
        print(f"エラー: {e}", file=sys.stderr)
        return 1

    return 0

if __name__ == "__main__":
    sys.exit(main())