文章目录
- [JSON 格式学习笔记](#JSON 格式学习笔记)
-
- [1. 什么是 JSON](#1. 什么是 JSON)
-
- [为什么用 JSON](#为什么用 JSON)
- [2. JSON 基本数据类型](#2. JSON 基本数据类型)
- [3. JSON 对象](#3. JSON 对象)
- [4. JSON 数组](#4. JSON 数组)
- [5. JSON 与 MQTT 配合](#5. JSON 与 MQTT 配合)
-
- [为什么 MQTT 用 JSON](#为什么 MQTT 用 JSON)
- 消息示例
- [如何设计良好的 JSON 消息](#如何设计良好的 JSON 消息)
- [6. JSON Schema](#6. JSON Schema)
- [7. JSON 常见问题](#7. JSON 常见问题)
-
- [7.1 数字 vs 字符串](#7.1 数字 vs 字符串)
- [7.2 布尔值 vs 0/1](#7.2 布尔值 vs 0/1)
- [7.3 时间戳格式](#7.3 时间戳格式)
- [7.4 空值处理](#7.4 空值处理)
- [8. JSON 验证工具](#8. JSON 验证工具)
JSON 格式学习笔记
1. 什么是 JSON
JSON(JavaScript Object Notation)是一种轻量级的数据交换格式,基于 JavaScript 语法子集,但语言无关。
为什么用 JSON
- 可读性好:纯文本,直观
- 跨语言:几乎所有编程语言都有 JSON 解析库
- 轻量:比 XML 更简洁
- 自描述:字段名即含义
2. JSON 基本数据类型
| 类型 | 示例 | 说明 |
|---|---|---|
| 字符串 | "hello" |
双引号包裹 |
| 数字 | 42、3.14 |
整数或浮点数 |
| 布尔值 | true、false |
小写 |
| 空值 | null |
表示空 |
| 数组 | [1, 2, 3] |
有序列表 |
| 对象 | {"key": "value"} |
键值对集合 |
注意事项
json
// ❌ 错误写法
{
name: "张三", // 键名必须用双引号
"age": 30, // 正确
"is_student": false, // 正确
"scores": [90, 85], // 正确
"description": 'hello' // 字符串必须用双引号,不能用单引号
}
3. JSON 对象
对象是键值对的无序集合,用 {} 包裹:
json
{
"name": "装载机001",
"type": "loader",
"speed": 12.5,
"connected": true
}
嵌套对象
对象的值可以是另一个对象,形成嵌套结构:
json
{
"vehicle": {
"speed": 12.5,
"gear": 1
},
"body": {
"device_power": 78.5,
"fault_level": 0
}
}
嵌套结构的好处是按功能域分组,前端按需消费,不需要关心不相关的字段。
4. JSON 数组
数组是有序列表,用 [] 包裹:
json
// 数字数组
[1, 2, 3, 4, 5]
// 字符串数组
["front", "back", "left", "right"]
// 对象数组
[
{"code": 1, "label": "急停触发"},
{"code": 4, "label": "通讯中断"}
]
数组常用于列表、批量数据、告警集合等场景。
5. JSON 与 MQTT 配合
为什么 MQTT 用 JSON
- 解耦:发布者和订阅者通过 JSON 格式约定通信,不依赖具体语言
- 可扩展:增加字段不影响已有客户端
- 自描述:每个字段有名称,比二进制协议更容易调试
消息示例
json
// 车辆状态消息(MQTT payload)
{
"timestamp": 1723345678123,
"vehicle": {
"speed": 12.5,
"gear": 1
},
"body": {
"device_power": 78.5
}
}
如何设计良好的 JSON 消息
- 字段名一致:全程用 snake_case 或 camelCase,本项目用 snake_case
- 嵌套分组:按功能域分组,避免扁平化
- 必填最小化:只标记本身没有意义就无法消费的字段
- 类型明确:数字用 number,开关用 boolean,枚举用 string
6. JSON Schema
JSON Schema 是描述 JSON 数据结构的标准,用于验证消息格式是否正确。
基本结构
json
{
"$schema": "http://json-schema.org/draft-07/schema#",
"type": "object",
"properties": {
"name": {
"type": "string",
"description": "名称"
},
"age": {
"type": "integer",
"minimum": 0,
"maximum": 150
}
},
"required": ["name"]
}
常用关键字
| 关键字 | 作用 | 示例 |
|---|---|---|
type |
指定类型 | "type": "string" |
properties |
定义对象属性 | "properties": {...} |
required |
必填字段列表 | "required": ["name"] |
minimum / maximum |
数值范围 | "minimum": 0 |
enum |
枚举值 | "enum": ["a", "b"] |
description |
字段说明 | "description": "车速" |
$ref |
引用外部定义 | "$ref": "common.json#/definitions/timestamp" |
示例:验证车速
json
// Schema
{
"type": "object",
"properties": {
"speed": {
"type": "number",
"minimum": 0,
"maximum": 80,
"description": "车速 (km/h)"
}
},
"required": ["speed"]
}
json
// 合法消息
{"speed": 12.5} // 通过
// 非法消息
{"speed": -1} // 不通过,小于 minimum
{"speed": "12.5"} // 不通过,类型应为 number
{} // 不通过,缺少必填字段
7. JSON 常见问题
7.1 数字 vs 字符串
json
// ❌ 混淆
{"speed": "12.5"} // 字符串,不是数字
{"speed": 12.5} // 正确,数字
// 前端处理时 typeof 不同
typeof "12.5" → "string"
typeof 12.5 → "number"
7.2 布尔值 vs 0/1
json
// ✅ 推荐:使用布尔值
{"charging": true}
// ❌ 不推荐:使用 0/1
{"charging": 1}
7.3 时间戳格式
json
// Unix 毫秒整数(性能好,适合高频数据)
{"timestamp": 1723345678123}
// ISO 8601 字符串(可读性好,适合调试)
{"timestamp": "2026-08-11T10:30:00.123Z"}
7.4 空值处理
json
// 字段不存在
{"speed": 12.5} // 没有 power 字段
// 字段为 null
{"speed": 12.5, "power": null} // power 明确为空
// 推荐:数据不存在时不发该字段,而不是发 null
8. JSON 验证工具
| 工具 | 用途 | 链接 |
|---|---|---|
| JSONLint | JSON 语法验证 | jsonlint.com |
| ajv | JSON Schema 验证(Node.js) | npm install ajv |
| Python json | 内置 json 模块 | import json |
命令行验证
bash
# Python 验证 JSON 语法
python -c "import json; json.load(open('file.json'))"
# 使用 ajv 验证 Schema
ajv validate -s schema.json -d data.json