koide 4ed1849c3a
All checks were successful
Deploy Docusaurus Site / deploy (push) Successful in 30s
Add: DGX Spark GUI操作動画解析システム記事
2026-02-24 10:07:20 +00:00

8.6 KiB
Raw Blame History

sidebar_position, title, description, hide_table_of_contents, displayed_sidebar
sidebar_position title description hide_table_of_contents displayed_sidebar
2 DGX SparkでGUI操作動画解析システムを作る NVIDIA DGX SparkでQwen3-VLとLanceDBを使ったGUI操作動画解析システムの構築方法 false null

DGX Sparkで作るGUI操作動画解析システム

Qwen3-VL + LanceDBでサーバー設定作業を自動ドキュメント化

はじめに

サーバーの設定作業をGUIで行う場面、意外と多いですよね。WebUIでの管理画面操作、設定ウィザードの実行...。後から「あの時どう設定したっけ?」と振り返りたいことがあります。

この記事では、NVIDIA DGX Sparkを使って、GUI操作の録画動画から設定内容を自動抽出し、検索・マニュアル生成ができるシステムを構築します。

作るもの

  • 入力: GUI操作を録画したMP4動画
  • 処理: フレーム抽出 → VLMで画面解析 → ベクトルDB格納
  • 出力: 設定値の検索、操作手順のマニュアル生成

使用技術

コンポーネント 技術
ハードウェア NVIDIA DGX Spark (128GB統合メモリ)
VLM Qwen3-VL 8B (Ollama)
フレーム抽出 OpenCV + SSIM
ベクトルDB LanceDB
WebUI Gradio

DGX Sparkとは

NVIDIA DGX Sparkは、デスクトップサイズの「AIスーパーコンピュータ」です。

スペック

項目 仕様
CPU ARM64 20コア (Cortex-X925 x10 + Cortex-A725 x10)
GPU NVIDIA GB10 (Blackwell) - 6144 CUDA Cores
メモリ 128GB 統合メモリ (CPU/GPU共有)
OS Ubuntu 24.04 LTS

開発上のポイント

  1. 統合メモリアーキテクチャ (UMA): CPUとGPUがメモリを共有。大規模モデルが載りやすい
  2. ARM64: x86のwheelは使えない。ARM64ビルドを使用
  3. Ollama対応: すぐ動く。公式サポート済み

システム構成

GUI操作動画(MP4)
      │
      ▼
① フレーム抽出 (OpenCV + SSIM)
      │ 画面変化を検出し重要フレームのみ抽出
      ▼
② Qwen3-VL 8B (Ollama)
      │ 各フレームの画面内容を解析
      │ 設定項目・値・操作内容を抽出
      ▼
③ LanceDB
      │ 解析結果をベクトルインデックス化
      ▼
④ Gradio WebUI
      └─ 検索・マニュアル生成

環境構築

前提条件

  • DGX Sparkにssh接続可能
  • Ollamaインストール済み

セットアップ

# プロジェクトディレクトリ作成
mkdir -p ~/projects/video-config-analyzer
cd ~/projects/video-config-analyzer

# 仮想環境作成
python3 -m venv venv
source venv/bin/activate

# 依存パッケージインストール
pip install opencv-python-headless gradio lancedb sentence-transformers \
    pillow pyyaml requests numpy tqdm scikit-image pyarrow

# Qwen3-VLモデル取得未取得の場合
ollama pull qwen3-vl:8b-instruct

実装解説

1. フレーム抽出 (frame_extractor.py)

動画から「画面が変化した」フレームのみを抽出します。

from skimage.metrics import structural_similarity as ssim
import cv2

def extract_keyframes(video_path, threshold=0.95):
    """SSIMで画面変化を検出し、変化があったフレームのみ抽出"""
    cap = cv2.VideoCapture(video_path)
    prev_frame = None
    keyframes = []
    
    while True:
        ret, frame = cap.read()
        if not ret:
            break
        
        gray = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)
        
        if prev_frame is None:
            keyframes.append(frame)
            prev_frame = gray
            continue
        
        # SSIM計算
        score = ssim(prev_frame, gray)
        if score < threshold:  # 変化検出
            keyframes.append(frame)
            prev_frame = gray
    
    return keyframes

:::tip ポイント SSIM (Structural Similarity Index) を使うことで、わずかなノイズに反応せず、実際の画面遷移のみを検出できます。 :::

2. VLM解析 (vlm_analyzer.py)

Ollama経由でQwen3-VLを呼び出し、画面内容を解析します。

import base64
import requests

def analyze_frame(image_path, ollama_url="http://localhost:11434"):
    """フレームをVLMで解析し、設定情報を抽出"""
    with open(image_path, "rb") as f:
        image_b64 = base64.b64encode(f.read()).decode()
    
    prompt = """この画像はサーバー設定画面です。以下をJSON形式で抽出:
    {
      "screen_title": "画面タイトル",
      "visible_settings": [{"name": "設定名", "value": "値", "type": "タイプ"}],
      "buttons_visible": ["ボタン名リスト"],
      "current_action": "操作の説明"
    }"""
    
    response = requests.post(f"{ollama_url}/api/generate", json={
        "model": "qwen3-vl:8b-instruct",
        "prompt": prompt,
        "images": [image_b64],
        "stream": False
    })
    
    return response.json()["response"]

3. インデックス化 (indexer.py)

LanceDBで解析結果をベクトル化して保存。後から自然言語で検索可能に。

import lancedb
from sentence_transformers import SentenceTransformer

class VideoIndexer:
    def __init__(self, db_path="./data/lancedb"):
        self.db = lancedb.connect(db_path)
        self.embedder = SentenceTransformer("all-MiniLM-L6-v2")
    
    def index(self, analysis_results, video_id):
        """解析結果をベクトルインデックスに追加"""
        entries = []
        for result in analysis_results:
            text = f"{result['screen_title']} {result['current_action']}"
            vector = self.embedder.encode(text).tolist()
            entries.append({
                "video_id": video_id,
                "text": text,
                "vector": vector,
                **result
            })
        
        table = self.db.create_table("video_analysis", entries, mode="overwrite")
        return len(entries)

4. WebUI (web_ui.py)

Gradioで直感的なインターフェースを提供。

import gradio as gr

def create_ui(pipeline):
    with gr.Blocks(title="Video Config Analyzer") as app:
        gr.Markdown("# GUI操作動画解析システム")
        
        with gr.Tab("動画解析"):
            video_input = gr.File(label="動画ファイル (MP4)")
            analyze_btn = gr.Button("解析開始")
            status = gr.Textbox(label="ステータス")
        
        with gr.Tab("検索"):
            query = gr.Textbox(label="検索クエリ")
            search_btn = gr.Button("検索")
            results = gr.Dataframe()
        
        with gr.Tab("マニュアル生成"):
            video_select = gr.Dropdown(label="動画選択")
            generate_btn = gr.Button("生成")
            manual_output = gr.Markdown()
    
    return app

WebUIの起動

cd ~/projects/video-config-analyzer
source venv/bin/activate
python app/web_ui.py

WebUIは http://localhost:7860 でアクセスできます。

トラブルシューティング

Q: Ollamaが応答しない

# Ollamaサービス確認
systemctl status ollama

# モデル確認
ollama list | grep qwen3-vl

Q: メモリ不足エラー

DGX Sparkの統合メモリを活用するため、他のプロセスを停止して試してください。

# GPU使用状況確認
nvidia-smi

# 不要なプロセス停止
pkill -f "python.*some_heavy_process"

Q: ARM64用パッケージが見つからない

一部のPyPIパッケージはARM64用wheelがない場合があります。その場合はソースからビルド:

pip install --no-binary :all: パッケージ名

まとめ

DGX Sparkの統合メモリアーキテクチャは、VLMを使った画像解析タスクに最適です。128GBの大容量メモリにより、8Bパラメータのモデルも余裕で動作します。

このシステムを使えば、GUI操作の録画を後から検索可能なドキュメントに変換できます。

今後の改善案

  • OmniParser V2の統合: GUI要素の検出精度向上
  • バッチ処理: 複数動画の一括処理
  • 差分検出の高度化: 動的なコンテンツの除外

参考リンク


この記事は2026年2月時点の情報です。