DuckDB WASMとは?ブラウザでSQL分析を実行する仕組みと実装・採用判断
DuckDB WASMは、列指向の分析データベースDuckDBをWebAssemblyにコンパイルし、ブラウザの中でそのままSQLを実行できるようにした公式パッケージです。サーバーを介さずにParquet・CSV・JSONへクエリを投げられるため、ダッシュボードのフィルタ応答やデータプレビューをクライアント側だけで完結できます。本記事では、Web Workerを使った実行構造、jsDelivr CDNとnpmでの導入手順、registerFile系APIによるファイル読み込み、4GBメモリ上限をはじめとする制約までを公式ドキュメントの記載に沿って解説します。対象はDuckDB本体1.5系、npmパッケージ@duckdb/duckdb-wasm1.33系(いずれも2026年7月時点)です。
目次
まとめ:DuckDB WASMはサーバー不要でブラウザ内SQL分析を成立させる
DuckDB WASMを使うと、集計・結合といった分析SQLをブラウザのタブの中だけで実行できます。導入はjsDelivrのCDNから読み込むか、npmで@duckdb/duckdb-wasmを入れるかの2択で、バックエンドのAPIサーバーを増やす必要はありません。読み込めるのはParquet・CSV・JSON・Apache Arrowの各形式で、リモートファイルはHTTP経由の部分読み込みに対応します。
採用の結論を先に示します。集約済みの数百MB級データを配信し、閲覧者ごとの絞り込みや再集計を即時に返したい分析UIならDuckDB WASMは有力です。逆に、数十GB級の生データ集計や複数ユーザーの同時書き込みは、WebAssemblyの4GBメモリ上限とブラウザごとに独立した実行モデルに阻まれるため、通常のDuckDBやクラウドDWHの領分になります。この線引きの根拠は本文後半の判断章で示します。
DuckDB WASMの仕組み:WebAssemblyでブラウザに載る分析エンジンの構造
実装に入る前に、どこで何が動いているのかを押さえます。ここが分かると後続の手順とエラーの切り分けが素直になります。
インプロセス型DuckDBをWasm化しWeb Workerで非同期実行する構成
DuckDBはアプリケーションのプロセス内で動く列指向のOLAPエンジンで、DuckDB WASMはこれをWebAssemblyへコンパイルしてブラウザのJavaScript実行環境に載せたものです。開発元が2021年10月に公開した紹介記事では、TPC-Hベンチマークでsql.jsやArqueroといった既存のブラウザ内処理系を上回る実測結果が示されています。エンジン本体の設計やSQLite・PostgreSQLとの違いはDuckDBとは?特徴・用途とSQLite・PostgreSQLとの違いを解説で扱っているため、本記事はWASM版固有の構造に絞ります。
実行の中心はWeb Workerです。重い集計をメインスレッドで走らせると画面描画が止まるため、公式クライアントのAsyncDuckDBはエンジンをWorker側に置き、メインスレッドからは非同期APIで指示だけを送る構造を取ります。UI側のコードはPromiseの解決を待つだけで済み、集計中も画面操作が固まりません。
mvp・ehの2バンドルとブラウザ機能判定による自動選択の仕組み
配布されるWebAssemblyバイナリは1種類ではありません。公式ドキュメントは、基本仕様のブラウザでも動くmvpと、WebAssemblyの例外処理機能を前提に速度を上げたehの2系統のバンドルを案内しており、selectBundle()がブラウザの機能判定に基づいて適合するものを自動選択します。実装側でユーザーのブラウザ差を吸収する分岐を書く必要はありません。
並列実行には条件が付きます。マルチスレッド動作はSharedArrayBufferを前提とするため、配信側でCOOP・COEPヘッダを設定したクロスオリジン分離環境が必要になり、既定ではシングルスレッドで動きます。性能の見積もりは、まず単一スレッド前提で行うのが安全です。
Parquet・CSV・JSONを読み込む2段階のファイル登録モデル
データの読み込みは「ファイル登録」と「取り込み・クエリ」の2段階に分かれます。第1段階ではregisterFileURL(リモートURL)、registerFileBuffer(バイナリ)、registerFileText(テキスト)、registerFileHandle(ファイル選択の結果)の各APIで、仮想ファイルシステムに名前を登録する流れです。第2段階では登録名に対してSQLを直接実行するか、insertCSVFromPathやinsertArrowTableでテーブルとして取り込みます。
ここで効くのがHTTPの部分読み込みです。列指向のParquetは必要な列のブロックだけ取得すれば集計できるため、リモートの大きなファイルでも全量をダウンロードせずにクエリが返ります。JSONは行指向・列指向の両形式に対応しており、APIレスポンスをそのまま取り込む用途にも回せます。
DuckDB WASMの実装手順:CDN読み込みから初回クエリ実行までの最小構成
最小構成は「バンドル選択→Worker起動→接続→クエリ」の4手です。フレームワークなしのHTMLからでも動かせます。
jsDelivr CDNからの読み込みとAsyncDuckDB初期化の実装
手早く試すならjsDelivr CDNです。ESモジュールとして@duckdb/duckdb-wasmを読み込み、getJsDelivrBundles()で候補一覧を取得し、selectBundle()で適合バンドルを決めます。返ってきたワーカーURLでnew Worker()を起動し、new AsyncDuckDB(logger, worker)を作ってinstantiate()にWASMモジュールのURLを渡せば初期化完了です。バージョンを固定したい場合はnpmで導入します。公開版は1.33系(2026年7月時点・jsDelivr配信で実測)で、エンジン本体の安定版1.5系とは版番号の体系が別である点に注意してください。
初期化後はconst conn = await db.connect()で接続を取り、以降のクエリはこの接続オブジェクトに投げます。
registerFile系APIによるファイル登録とSQL実行の手順
リモートのParquetを集計する場合、registerFileURL('sales.parquet', url)で登録したうえで、SELECT region, sum(amount) FROM 'sales.parquet' GROUP BY regionのようにファイル名をテーブルとして参照します。結果はApache Arrow形式のテーブルで返り、toArray()でJavaScriptの配列に変換して、そのまま描画ライブラリへ渡せます。
CSVは自動型推論での取り込みに加えて、insertCSVFromPathで区切り文字・ヘッダー有無・列型を明示指定できます。型が曖昧な実務CSVでは、推論に任せず列型を指定したほうが後段の結合で型不一致に悩まされません。閲覧者の手元にあるファイルを扱う場合は、ファイル選択欄で受け取ったハンドルをregisterFileHandleに渡す流れになります。
WebpackやVite構成へ組み込む際のwasmファイル配置の注意点
アプリケーションに組み込む場合は、wasmファイルとワーカースクリプトの配置が論点になります。Webpackではduckdb-mvp.wasmとduckdb-eh.wasmの2ファイルを静的アセットとして扱い、対応するワーカーの明示指定が必要です。Viteでは?url付きインポートでアセットURLを取得する方式が公式ドキュメントに載っており、TypeScriptの型を保ったまま設定できます。CDNへ依存できない社内システムなら、jsDelivrから取得したファイル一式を自社サーバーに置く自己ホスト構成も選択肢です。
いずれの構成でも、WASMバイナリは数MB規模になるためHTTPキャッシュの方針を先に決めておくべきです。初回アクセスの体感を左右するのは、クエリ性能よりむしろこのロード時間です。
クライアントサイド分析の適用場面と制約:効く用途と越えられない上限
仕組みが分かったところで、どの実装で効き、どこで頭打ちになるかを整理します。
ダッシュボードのフィルタ応答やデータプレビューで効く実装場面
効果がはっきり出るのは、サーバー往復をなくしたい対話的UIです。具体的には、ダッシュボードでのフィルタ・並べ替え・集計粒度の切り替えをブラウザ内で完結させる実装、オブジェクトストレージに置いたParquetのスキーマ確認やプレビュー、ブラウザだけで完結するSQL学習環境が代表例になります。操作のたびにAPIを呼ぶ構成と違い、ネットワーク遅延の影響を受けずに応答が返る構造です。Parquetを蓄積する基盤側の設計はデータレイクとは?データウェアハウス・レイクハウスとの違いを実装視点で解説が前提知識になります。
もう1つの適所は、データを端末の外へ出せない場面です。集計がブラウザ内で完結する構造上、機密ファイルをサーバーへアップロードさせずに分析機能を提供できます。
4GBメモリ上限・単一スレッド既定・CORSというブラウザ実行の制約
制約は4つ挙げられます。第一にメモリで、公式ドキュメントはWebAssemblyの制約により上限4GB、ブラウザによってはさらに低くなると明記しています。第二に並列度で、前述の通り既定はシングルスレッド動作です。第三に初回ロードで、数MB規模のWASMバイナリ取得が挟まります。第四にCORSで、S3などのオブジェクトストレージを直接読む場合はバケット側でCORSヘッダを許可しないと取得自体が失敗します。
ここから導かれる設計指針は「ブラウザに渡すのは集約済みデータまで」です。生データの重い前処理はサーバー側の通常のDuckDBやDWHで済ませ、WASM側には表示用の絞り込みと再集計だけを担わせる分担が現実的です。
DuckDB WASM採用の判断基準:通常のDuckDB・サーバー型との線引き
受託開発でデータ基盤と業務システムを設計してきた立場から、採用と見送りの条件を言い切ります。迷ったら次の比較を起点にしてください。
採用する条件:集約済み数百MB級データの配信と対話的な分析UIの要件
まず実行環境ごとの向き不向きを整理します。
| 観点 | DuckDB WASM | 通常のDuckDB | クラウドDWH |
|---|---|---|---|
| 実行場所 | 閲覧者のブラウザ内 | 手元マシンやサーバーのプロセス内 | クラウドの共有基盤 |
| 向くデータ規模 | 集約済み数百MB級まで | 数十GB級まで | TB級以上 |
| 同時利用 | 閲覧者ごとに独立 | 書き込みは1プロセス限定 | 多数ユーザーの同時実行 |
| 主な用途 | 対話的な分析UI・プレビュー | ローカル分析・ETL前処理 | 全社共有の分析基盤 |
採用してよいのは、配信するデータが集約済みで数百MB級までに収まり、閲覧者ごとに独立した絞り込み・再集計を即時に返したい場合です。社外へ出せないデータをアップロードなしで集計したい要件も、WASM側の適所になります。手元マシンでの前処理や検証は通常のDuckDBの担当で、導入コマンドと操作はDuckDBの使い方:インストールからPython・CLI・ファイル読み込みまでの実装手順で解説しています。
見送る場面:数十GB級の生データ集計・共有更新・初期表示が厳しいページ
見送るべき場面は3つです。第一に、数十GB級の生データをその場で集計する要件。4GBのメモリ上限に正面から当たるため、前段のサーバー側集約が必須です。第二に、複数ユーザーで同じデータを更新する業務システムのバックエンド。ブラウザ内のデータベースは閲覧者ごとに独立しており、共有状態の管理には向きません。第三に、初期表示速度が事業指標に直結するページで、WASMロードの数MBを許容できない場合です。
この線を越えるなら、基盤側はBigQueryなどのDWHを軸にした構成が候補になります。5層アーキテクチャでの設計手順はデータ分析基盤の構築とは?5層アーキテクチャとBigQuery実装手順を技術視点で解説に整理しました。ブラウザ内分析を含めて、どこまでをクライアントに寄せるか判断がつかない場合は、当社のデータ分析基盤構築・MLOps構築支援が要件整理から設計・実装までを請け負います。
よくある質問
DuckDB WASMについて、検索で相談の多い5つの質問に回答します。
DuckDB WASMは無料で商用利用できますか?
できます。DuckDB本体と同じくMITライセンスで公開されており、npmパッケージ@duckdb/duckdb-wasmの組み込み・商用配布とも追加費用や利用申請は不要です。商用サポートが必要な場合は、開発元メンバーが関与するDuckDB Labsが窓口になります。ライセンス費用ゼロで検証を始められるため、PoC段階の稟議が通しやすい点も実務上の利点です。
通常のDuckDBとWASM版で使えるSQLに違いはありますか?
同じエンジンをコンパイルしているため、SQLの文法や関数は基本的に共通です。違いが出るのはI/O周りで、ブラウザのサンドボックス内で動く都合上、ローカルファイルのパス直接参照はregisterFile系APIを介した登録に置き換わり、利用できる拡張機能も限られます。既存のDuckDB資産を移す場合、書き換えの中心はSQLではなくファイルの受け渡し部分です。
どのブラウザで動作しますか?
公式はChrome・Firefox・Safariの主要ブラウザに加え、Node.jsでの動作をテスト済みと案内しています。実行時にはselectBundle()がブラウザの機能を判定し、基本仕様のmvpと例外処理対応のehから適合するバンドルを自動で選ぶため、対応表を自前で管理する必要はありません。
S3上のParquetファイルを直接読めますか?
読めます。registerFileURLでオブジェクトのURLを登録するか、SQL内でURLを直接参照する方法が公式ドキュメントに記載されています。列指向のParquetは必要な列だけを部分取得できるため、全量ダウンロードは発生しません。ただしバケット側のCORS設定でブラウザからのアクセスを許可しておくことが前提条件です。
マルチスレッドで動かすには何が必要ですか?
SharedArrayBufferの有効化が前提です。具体的には、配信サーバーでCOOP・COEPヘッダを設定してクロスオリジン分離を成立させる必要があります。この設定がない環境では既定のシングルスレッドで動作します。まず単一スレッドで性能を確認し、足りない場合にヘッダ設定を検討する順番が現実的です。
関連記事
- DuckDBとは?特徴・用途とSQLite・PostgreSQLとの違いを解説:本記事の親にあたる定義・比較編。エンジン本体の特徴を体系的に押さえたい方はこちらから
- DuckDBの使い方:インストールからPython・CLI・ファイル読み込みまでの実装手順:ローカル環境での実装編。CLI・Python連携の手順はこちら
- データ分析基盤の構築とは?5層アーキテクチャとBigQuery実装手順を技術視点で解説:ブラウザ内分析の先にある基盤全体の設計手順
- データレイクとは?データウェアハウス・レイクハウスとの違いを実装視点で解説:ParquetをS3に溜める構成の前提知識。部分読み込み連携の土台