curl转R的httr代码报错:如何正确构造POST请求体?
问题:curl POST转httr代码时请求体未被API识别
原可正常运行的curl命令:
curl -X POST "https://api.purpleair.com/v1/groups/zzz/members" -H "Content-Type: application/json" -H "X-API-Key: xxxxxxxxx" -d '{"sensor_index":"yyyyyy"}'
用户编写的httr代码:
library(httr) url <- "https://api.purpleair.com/v1/groups/zzz/members" body <- list(sensor_index = "yyyyyy") headers <- c("Content-Type" = "application/json", "X-API-Key" = "xxxxxxxxx") response <- POST(url, body = body, add_headers(.headers = headers))
返回错误:
"error" : "MissingIdentifierError", "description" : "Missing sensor_id or sensor_index value."
解决方法
问题根源:httr默认会把list类型的body编码为表单格式(application/x-www-form-urlencoded),而非你指定的JSON格式,导致API无法解析请求体中的sensor_index参数。
有两种修正方式:
方式1:使用encode="json"参数
直接在POST()中指定encode="json",让httr自动将list序列化为JSON:
library(httr) url <- "https://api.purpleair.com/v1/groups/zzz/members" body <- list(sensor_index = "yyyyyy") headers <- c("X-API-Key" = "xxxxxxxxx") # 无需手动指定Content-Type,encode="json"会自动添加 response <- POST(url, body = body, add_headers(.headers = headers), encode = "json")
方式2:手动序列化JSON
用jsonlite::toJSON()将list转成JSON字符串,再传入body:
library(httr) library(jsonlite) url <- "https://api.purpleair.com/v1/groups/zzz/members" body <- toJSON(list(sensor_index = "yyyyyy"), auto_unbox = TRUE) # auto_unbox确保单个值不被包裹为数组 headers <- c("Content-Type" = "application/json", "X-API-Key" = "xxxxxxxxx") response <- POST(url, body = body, add_headers(.headers = headers))
说明
- 方式1更简洁,httr会自动处理Content-Type头和JSON序列化
- 方式2适合需要更精细控制JSON格式的场景,
auto_unbox=TRUE避免API因数组格式的参数报错
内容的提问来源于stack exchange,提问作者JerryN
相关产品推荐
相关产品推荐

