はじめに
JSON(JavaScript Object
Notation)は、データを構造化して表現するための軽量なテキストフォーマットである。比較的人間が読みやすく、プログラムでも簡単に解析できるため、Web
APIや設定ファイルなどで広く利用されている。
名前の通りJavaScriptのオブジェクト表記だが、他の言語でも使われる。
JSONの基本
JSONは、キーと値のペアで構成されるオブジェクトが基本である。オブジェクトは{}で囲まれる。キーと値のペアは"key": valueで表され、カンマ,で区切られる。
{
"name": "Alice",
"age": 30,
"isStudent": false
}
これだけといえばこれだけである。コメントも書けない。コメントを入れたければ、次のように入れるしかない。
{
"description": "JSONオブジェクトの例",
"name": "Alice",
"age": 30,
"isStudent": false
}
ファイルにする場合の拡張子は.jsonである。
データ型
文字列
文字列はダブルクォーテーション"で囲む。
数値
"age": 30,
"height": 175.5
整数や浮動小数点数を直接記述する。
ブール値
trueまたはfalseを使用する。
null値
値が存在しないことをnullで表します
データ構造
配列
順序付きの配列を[]で表せる。
"hobbies": ["reading", "swimming", "coding"]
オブジェクト
オブジェクトは入れ子にできる。
{
"person": {
"name": "Bob",
"age": 25,
"address": {
"city": "Osaka",
"zip": "530-0001"
}
}
}
オブジェクトを配列の要素にすることもできる。
"employees": [
{
"name": "Charlie",
"department": "Engineering"
},
{
"name": "Diana",
"department": "Marketing"
}
]
まぜこぜすることもできる。
{
"company": "Tech Corp",
"locations": ["Tokyo", "New York", "London"],
"founded": 2001,
"ceo": {
"name": "Eve",
"age": 45
}
}
実践的な使用
JSONの検証
書式のチェックだけであれば、Pythonを使って以下のようにすればよい。
$ python -c "import json; json.load(open('config.json')); print('OK')"
JSONスキーマによる検証は、check-jsonschemaでできる。
schema.json
{
"$schema": "http://json-schema.org/draft-07/schema#",
"type": "object",
"properties": {
"name": {
"type": "string"
},
"age": {
"type": "integer",
"minimum": 0
},
"email": {
"type": "string",
"format": "email"
}
},
"required": ["name", "age"]
}
data.json
{
"name": "Alice",
"age": 30,
"email": "alice@example.com"
}
インストール
$ pip install check-jsonschema
実行
$ check-jsonschema --schemafile schema.json data.json
ok -- validation done
JSONスキーマは、データの構造や制約(例:
必須フィールド、データ型、値の範囲など)を定義するルールセットであり、これにより、データの整合性を検証したりできる。たとえば、上の例でいうと、ageの設定が抜けていたりすると、次のような結果となる。
$ check-jsonschema --schemafile schema.json data.json
Schema validation errors were encountered.
data.json::$: 'age' is a required property
Pythonプログラムで検証する場合は、jsonschemaを用いる。
# validation.py
import json
from jsonschema import validate, ValidationError
# スキーマの定義
schema = {
"$schema": "http://json-schema.org/draft-07/schema#",
"type": "object",
"properties": {
"name": {"type": "string"},
"age": {"type": "integer", "minimum": 0},
"email": {"type": "string", "format": "email"}
},
"required": ["name", "age"]
}
# JSONデータの読み込み
data = {
"name": "Alice",
"age": 30,
"email": "alice@example.com"
}
# スキーマに基づく検証
try:
validate(instance=data, schema=schema)
print("JSON is valid according to the schema.")
except ValidationError as e:
print("Invalid JSON:", e.message)
Pythonの時点ではすでにJSONではないので(ただの辞書なので)、JSON以外の検証にも使える。
設定ファイルとしての利用
JSONを設定ファイルとして利用した場合の例を以下に示す。
{
"app": {
"name": "My Application",
"version": "1.0.0",
"debug": true,
"log_level": "INFO"
},
"database": {
"host": "localhost",
"port": 5432,
"name": "mydb",
"user": "admin",
"password": "secret",
"max_connections": 10
},
"server": {
"host": "0.0.0.0",
"port": 8000,
"timeout": 30,
"allowed_origins": [
"http://localhost:3000",
"https://example.com"
]
},
"special": {
"features": {
"feature1": true,
"feature2": true
},
"thresholds": {
"cpu": 90,
"memory": 80
}
}
}
Pythonでの利用例
# read_json.py
import json
import logging
from typing import Dict, Any
def load_config(config_path: str) -> Dict[str, Any]:
"""JSON設定ファイルを読み込む"""
with open(config_path, 'r') as file:
config = json.load(file)
return config
def setup_logging(config: Dict[str, Any]) -> None:
"""ログ設定を適用"""
log_level = config['app']['log_level']
logging.basicConfig(
level=log_level,
format='%(asctime)s - %(name)s - %(levelname)s - %(message)s'
)
def main():
# 設定ファイルを読み込む
config = load_config('config.json')
# ログ設定を適用
setup_logging(config)
# 設定を使用してアプリケーションを構成
app_name = config['app']['name']
db_config = config['database']
server_config = config['server']
logging.info(f"Starting {app_name} version {config['app']['version']}")
# データベース接続(例)
#db = connect_to_database(db_config)
# サーバー起動(例)
#start_server(server_config)
# 特別な設定を使用
if 'feature1' in config['special']['features']:
logging.info("Feature1 is enabled")
if config['special']['thresholds']['cpu'] > 80:
logging.warning("High CPU threshold configured")
if __name__ == "__main__":
main()
|