JSONパスファインダー:完全ガイド
JSONPath構文、クエリ、ツール。複雑なJSON構造からデータを抽出する方法を学びます。
Big JSON Team
• Technical WriterExpert in JSON data manipulation, API development, and web technologies. Passionate about creating tools that make developers' lives easier.
# JSONパスファインダー:完全ガイド
JSONPath を使用して、複雑なJSON構造から特定のデータを抽出する方法を学びます。
JSONPathとは
JSONPathは、JSONドキュメント内の要素をクエリするための構文です(XPathのJSON版)。
基本例
{
"store": {
"book": [
{
"title": "吾輩は猫である",
"author": "夏目漱石",
"price": 800
},
{
"title": "坊っちゃん",
"author": "夏目漱石",
"price": 600
}
]
}
}
JSONPath:
$.store.book[0].title
// 結果: "吾輩は猫である"
基本構文
ルート ($)
$ // ルートオブジェクト
ドット記法 (.)
$.store.name // オブジェクトのプロパティ
$.user.address.city
ブラケット記法 ([])
$['store']['name'] // プロパティ
$['user name'] // スペースを含むキー
配列インデックス
$.books[0] // 最初の要素
$.books[1] // 2番目の要素
$.books[-1] // 最後の要素(一部の実装)
ワイルドカード ()
$.store. // storeのすべての子
$.books[].title // すべての本のタイトル
再帰的検索 (..)
$..title // すべてのtitle
$..book[].author // すべての著者
配列操作
スライス
$.books[0:2] // 最初の2冊
$.books[1:4] // インデックス1-3
$.books[::2] // 1つおき
$.books[::-1] // 逆順
複数インデックス
$.books[0,2,4] // 特定のインデックス
フィルタ式
基本フィルタ
// 価格が1000未満の本
$.books[?(@.price < 1000)]
// 著者が夏目漱石の本
$.books[?(@.author == "夏目漱石")]
// 在庫がある本
$.books[?(@.inStock == true)]
複数条件
// AND条件
$.books[?(@.price < 1000 && @.inStock == true)]
// OR条件
$.books[?(@.author == "夏目漱石" || @.author == "芥川龍之介")]
存在チェック
// ISBNフィールドがある本
$.books[?(@.isbn)]
// セール中の本
$.books[?(@.discount)]
実用例
例1:ユーザーデータ
{
"users": [
{
"id": 1,
"name": "田中太郎",
"age": 30,
"city": "東京"
},
{
"id": 2,
"name": "佐藤花子",
"age": 25,
"city": "大阪"
},
{
"id": 3,
"name": "鈴木一郎",
"age": 35,
"city": "東京"
}
]
}
クエリ例:
// すべてのユーザー名
$.users[].name
// ["田中太郎", "佐藤花子", "鈴木一郎"]
// 東京在住のユーザー
$.users[?(@.city == "東京")]
// 30歳以上のユーザー
$.users[?(@.age >= 30)]
// 最初のユーザーのID
$.users[0].id
// 1
例2:ネストされたデータ
{
"company": {
"name": "Tech Corp",
"departments": [
{
"name": "開発",
"employees": [
{"name": "田中", "role": "エンジニア"},
{"name": "佐藤", "role": "デザイナー"}
]
},
{
"name": "営業",
"employees": [
{"name": "鈴木", "role": "マネージャー"}
]
}
]
}
}
クエリ例:
// すべての部署名
$.company.departments[].name
// ["開発", "営業"]
// すべての従業員名
$..employees[].name
// ["田中", "佐藤", "鈴木"]
// エンジニアを探す
$..employees[?(@.role == "エンジニア")]
JavaScriptでの使用
jsonpath ライブラリ
インストール
npm install jsonpath
基本的な使い方
const jsonpath = require('jsonpath');
const data = {
store: {
book: [
{ title: "吾輩は猫である", price: 800 },
{ title: "坊っちゃん", price: 600 }
]
}
};
// クエリ実行
const titles = jsonpath.query(data, '$.store.book[].title');
console.log(titles);
// ["吾輩は猫である", "坊っちゃん"]
// フィルタ
const cheapBooks = jsonpath.query(
data,
'$.store.book[?(@.price < 700)]'
);
console.log(cheapBooks);
パスの取得
// パスを取得
const paths = jsonpath.paths(data, '$.store.book[].title');
console.log(paths);
// [['$', 'store', 'book', 0, 'title'],
// ['$', 'store', 'book', 1, 'title']]
// パス文字列
const pathStrings = jsonpath.stringify(paths);
ノードの取得
// パスと値の両方
const nodes = jsonpath.nodes(data, '$.store.book[].title');
console.log(nodes);
// [{path: ['$', 'store', 'book', 0, 'title'], value: '吾輩は猫である'},
// {path: ['$', 'store', 'book', 1, 'title'], value: '坊っちゃん'}]
Pythonでの使用
jsonpath-ng ライブラリ
インストール
pip install jsonpath-ng
使用方法
from jsonpath_ng import parse
data = {
"store": {
"book": [
{"title": "吾輩は猫である", "price": 800},
{"title": "坊っちゃん", "price": 600}
]
}
}
# JSONPathをパース
jsonpath_expr = parse('$.store.book[].title')
# クエリ実行
matches = jsonpath_expr.find(data)
# 結果を取得
for match in matches:
print(match.value)
# 吾輩は猫である
# 坊っちゃん
フィルタ使用
from jsonpath_ng.ext import parse
# 拡張パーサー(フィルタサポート)
jsonpath_expr = parse('$.store.book[?(@.price < 700)]')
matches = jsonpath_expr.find(data)
for match in matches:
print(match.value)
オンラインツール
1. BigJSON.online
特徴:- JSONパス検索
- リアルタイムプレビュー
- パスのコピー
- 大きなファイル対応
2. JSONPath Online Evaluator
URL: jsonpath.com 特徴:- クエリテスト
- 結果プレビュー
- 構文ヘルプ
3. JSONPath Finder
特徴:- インタラクティブ
- クリックでパス取得
- 例のライブラリ
コマンドラインツール
jq(代替手段)
jqは独自の構文を使用:
# すべてのタイトル
jq '.store.book[].title' data.json
# フィルタ
jq '.store.book[] | select(.price < 700)' data.json
# マップ
jq '.users | map(.name)' data.json
# 特定のフィールド
jq '.users[].address.city' data.json
高度なパターン
条件付き選択
// 複雑な条件
$.products[?(@.price > 1000 && @.inStock == true && @.category == "electronics")]
// 正規表現(一部の実装)
$.users[?(@.email =~ /.@example\.com/)]
// 配列の長さチェック
$.users[?(@.hobbies.length > 2)]
集約関数(一部実装)
// 最小値
$.books[?(@.price == min($.books[].price))]
// 最大値
$.books[?(@.price == max($.books[].price))]
// 合計
sum($.orders[].total)
// 平均
avg($.products[].price)
ユニオン
// 複数パス
$[store.book, store.music]
// 複数フィールド
$.users[][name,email]
実用的なユースケース
API レスポンスの解析
const response = await fetch('https://api.example.com/data');
const data = await response.json();
// 特定のデータを抽出
const userEmails = jsonpath.query(data, '$.users[].email');
const activeUsers = jsonpath.query(
data,
'$.users[?(@.status == "active")]'
);
設定ファイルの読み取り
const config = require('./config.json');
// 特定の設定を取得
const dbHost = jsonpath.value(config, '$.database.host');
const apiKeys = jsonpath.query(config, '$.services[].apiKey');
データ変換
const sourceData = {...};
// 必要なフィールドのみ抽出
const transformed = jsonpath.query(sourceData, '$.items[]')
.map(item => ({
id: item.id,
name: item.name,
price: item.pricing.amount
}));
ベストプラクティス
1. シンプルに保つ
// 良い
$.users[0].name
// 悪い(過度に複雑)
$..users[?(@.id == 1)][0].name
2. パフォーマンスを考慮
// 遅い(すべてを検索)
$..name
// 速い(特定のパス)
$.users[].name
3. エラーハンドリング
try {
const result = jsonpath.query(data, '$.invalid.path');
if (result.length === 0) {
console.log('結果が見つかりません');
}
} catch (error) {
console.error('無効なJSONPath:', error);
}
4. ドキュメント化
// クエリの意図をコメント
// すべてのアクティブユーザーのメールアドレスを取得
const emails = jsonpath.query(
data,
'$.users[?(@.active == true)].email'
);
JSONPath vs 他の方法
直接アクセス
// JSONPath
jsonpath.query(data, '$.users[0].name');
// 直接アクセス
data.users[0].name;
JSONPathを使用すべき場合:
- 動的パス
- 複雑なクエリ
- フィルタリングが必要
- 複数の結果
jq
# JSONPath風
jq '.store.book[] | select(.price < 700)'
# 独自構文の利点
jq '.users | map(select(.age > 30)) | .[].name'
トラブルシューティング
問題1: 結果が空
原因: パスが間違っている 解決:// ステップバイステップでテスト
console.log(jsonpath.query(data, '$'));
console.log(jsonpath.query(data, '$.users'));
console.log(jsonpath.query(data, '$.users[0]'));
問題2: フィルタが動作しない
確認:- ライブラリがフィルタをサポートしているか
- 構文が正しいか
- データ型が一致しているか
問題3: パフォーマンス問題
最適化:- 再帰検索 (..) を避ける
- 具体的なパスを使用
- 結果をキャッシュ
まとめ
クイックリファレンス
$ // ルート
$.store.book // ドット記法
$['store']['book'] // ブラケット記法
$.books[0] // 配列インデックス
$.books[] // すべての要素
$..author // 再帰検索
$.books[0:2] // スライス
$.books[?(@.price<10)] // フィルタ
JavaScript使用例
const jsonpath = require('jsonpath');
const result = jsonpath.query(data, '$.users[*].name');
const filtered = jsonpath.query(
data,
'$.users[?(@.age > 25)]'
);
JSONPathで、複雑なJSON構造を簡単にナビゲートしましょう!