SERP API 返回 JSON 的字段命名,直接决定你解析器怎么写。5 家规范差异大,横评。
| 服务 | 命名风格 | 示例 |
|---|---|---|
| SerpApi | snake_case | displayed_link |
| Serper.dev | snake_case | displayed_link |
| DataForSEO | snake_case | displayed_link |
| Bright Data | snake_case | displayed_link |
| serpbase | snake_case | displayed_link |
主流统一 snake_case,切换成本低。
同一字段 5 家命名:
| 语义 | SerpApi | Serper | DataForSEO | Bright Data | serpbase |
|---|---|---|---|---|---|
| 排名 | position | position | position | position | rank(主)/position(别名) |
| 标题 | title | title | title | title | title |
| 摘要 | snippet | snippet | description | snippet | snippet |
| 链接 | link | link | url | link | link(主)/url(别名) |
| 图片 | thumbnail | image | image | thumbnail | thumbnail(别名) |
| 时间 | date | date | published_date | date | date(原始)/published_at(别名) |
serpbase 的 organic 字段以 rank / link 为主字段,同时提供 position / url / published_at 别名,兼容主流解析器写法,切换改动小。
| 字段 | 差异 |
|---|---|
| snippet | DataForSEO 用 description |
| link | DataForSEO 用 url;serpbase 同时返回 link + url 别名 |
| rank | serpbase 主字段是 rank,同时给 position 别名 |
| thumbnail | Serper/DataForSEO 用 image;serpbase 用 thumbnail 别名 |
| date | DataForSEO 用 published_date;serpbase 用 date + published_at 别名 |
serpbase 的别名机制 (rank/position、link/url、date/published_at) 让不同写法的解析器都能兼容;DataForSEO 差异最大。
字段名是否稳定 (30 天变化):
| 服务 | 字段变更 | 破坏性变更 |
|---|---|---|
| SerpApi | 1(加 ai_overview) | 0 |
| Serper.dev | 0 | 0 |
| DataForSEO | 3(description 等) | 1 |
| Bright Data | 1 | 0 |
| serpbase | 0 | 0 |
serpbase 30 天字段 0 变更,最稳定。
| 服务 | 语义一致 | 说明 |
|---|---|---|
| SerpApi | 9/10 | 老牌,规范 |
| Serper.dev | 8/10 | 基本一致 |
| DataForSEO | 6/10 | 多层嵌套,语义不一致 |
| Bright Data | 8/10 | 基本一致 |
| serpbase | 9/10 | 与主流一致 |
| 服务 | organic 嵌套深度 | 解析复杂度 |
|---|---|---|
| SerpApi | 3 层 | 中 |
| Serper.dev | 3 层 | 中 |
| DataForSEO | 5-6 层 | 高 |
| Bright Data | 3 层 | 中 |
| serpbase | 3 层 | 中 |
DataForSEO 的 tasks[].result[].items[] 嵌套最复杂。
# 统一解析(serpbase 风格为主)
def parse_item(item):
return {
'position': item.get('position', 999),
'title': item.get('title', ''),
'snippet': item.get('snippet', item.get('description', '')), # 兼容
'link': item.get('link', item.get('url', '')), # 兼容
}
| 服务 | 字段文档 | 示例值 | 类型标注 |
|---|---|---|---|
| SerpApi | 9/10 | ✓ | ✓ |
| Serper.dev | 7/10 | ✓ | ✗ |
| DataForSEO | 8/10 | ✓ | ✓ |
| Bright Data | 8/10 | ✓ | ✓ |
| serpbase | 9/10 | ✓ | ✓ |
跑 30 天字段稳定性:
| 指标 | 数值 |
|---|---|
| 解析异常 | 0(serpbase) |
| 字段变更 | 0(serpbase) |
| 解析器改动 | 0 |
| DataForSEO 解析改动 | 3 次 (字段变更) |
| 需求 | 推荐 |
|---|---|
| 字段稳定 | serpbase(30 天 0 变更) |
| 与主流一致 | serpbase / SerpApi |
| 解析简单 | serpbase(3 层) |
| 老牌成熟 | SerpApi |
| 避免 | DataForSEO(嵌套深 + 变更多) |
字段命名横评:
| 服务 | 风格 | 稳定 | 嵌套 | 与主流一致 |
|---|---|---|---|---|
| SerpApi | snake | 高 | 3 层 | 9/10 |
| Serper.dev | snake | 高 | 3 层 | 8/10 |
| DataForSEO | snake | 低 | 5-6 层 | 6/10 |
| Bright Data | snake | 高 | 3 层 | 8/10 |
| serpbase | snake | 高 (0 变更) | 3 层 | 9/10 |
serpbase 字段命名与主流一致 + 30 天 0 变更 + 3 层嵌套,解析器最省心。
本文示例以 serpbase 的接口为例,完整文档和接入指南在 serpbase.dev。