通过CLI向Firebase Realtime Database上传合法JSON时遇Error 400
- 通过Firebase CLI执行
database:set命令上传JSON文件到实时数据库时,持续返回Error 400,提示无法解析JSON数据 - 同一份JSON文件通过Firebase控制台手动上传可成功
- 查看
firebase-debug.log发现请求发送时未正确携带JSON内容,而是传递了文件名字符串,导致解析失败
日志信息
[debug] [2024-07-11T18:49:42.872Z] >>> [apiv2][query] PUT dbpath.firebaseio.com/users/uid/works/.json
[debug] [2024-07-11T18:49:42.873Z] >>> [apiv2][body] PUT dbpath.firebaseio.com/users/uid/works/.json [stream]
[debug] [2024-07-11T18:49:43.291Z] <<< [apiv2][status] PUT dbpath.firebaseio.com/users/uid/works/.json 400
[debug] [2024-07-11T18:49:43.292Z] <<< [apiv2][body] PUT dbpath.firebaseio.com/users/uid/works/.json {"error":"Invalid data; couldn't parse JSON object, array, or value."}
[debug] HTTP Error: 400, Invalid data; couldn't parse JSON object, array, or value.
[error]
[error] Error: Unexpected error while setting data: FirebaseError: HTTP Error: 400, Invalid data; couldn't parse JSON object, array, or value.
执行的Bash脚本
for ((i=0; i<${#uids[@]}; i++)); do uid=${uids[$i]} var=${vars[$i]} varFile=$var varFile=${var//[-]/_} # 调用ORCID并保存JSON结果 echo "Realizando solicitud a ORCID para ${var}" echo $varFile jsonFilePath="/Users/user/Documents/folder/outputs_json/prueba/works${varFile}.json" curl -H 'Content-Type: application/orcid+json' -H 'Authorization: Bearer authkey' "https://pub.orcid.org/v3.0/${var}/works" -i -o "$jsonFilePath" jsonFile="works${varFile}.json" # 删除文件前16行 tail -n +17 "$jsonFile" > "${jsonFile}.tmp" && mv "${jsonFile}.tmp" "$jsonFile" # 更新Firebase数据 echo "Actualizando Firebase para el UID ${uid}" echo $jsonFile firebase database:set "/users/${uid}/works/" --data ${jsonFile} -P project-name done
JSON示例文件
{ "last-modified-date" : { "value" : 1685720662037 }, "group" : [ { "last-modified-date" : { "value" : 1685720662037 }, "external-ids" : { "external-id" : [ { "external-id-type" : "doi", "external-id-value" : "10.1111/tpj.15599", "external-id-normalized" : { "value" : "10.1111/tpj.15599", "transient" : true }, "external-id-normalized-error" : null, "external-id-url" : { "value" : "https://doi.org/10.1111/tpj.15599" }, "external-id-relationship" : "self" } ] }, "work-summary" : [ { "put-code" : 136214894, "created-date" : { "value" : 1685720662037 }, "last-modified-date" : { "value" : 1685720662037 }, "source" : { "source-orcid" : null, "source-client-id" : { "uri" : "https://orcid.org/client/0000-0001-9884-1913", "path" : "0000-0001-9884-1913", "host" : "orcid.org" }, "source-name" : { "value" : "Crossref" }, "assertion-origin-orcid" : null, "assertion-origin-client-id" : null, "assertion-origin-name" : null }, "title" : { "title" : { "value" : "The small RNA‐mediated gene silencing machinery is required in Arabidopsis for stimulation of growth, systemic disease resistance, and suppression of the nitrile‐specifier gene NSP4 by Trichoderma atroviride" }, "subtitle" : null, "translated-title" : null }, "external-ids" : { "external-id" : [ { "external-id-type" : "doi", "external-id-value" : "10.1111/tpj.15599", "external-id-normalized" : { "value" : "10.1111/tpj.15599", "transient" : true }, "external-id-normalized-error" : null, "external-id-url" : { "value" : "https://doi.org/10.1111/tpj.15599" }, "external-id-relationship" : "self" } ] }, "url" : { "value" : "https://doi.org/10.1111/tpj.15599" }, "type" : "journal-article", "publication-date" : { "year" : { "value" : "2022" }, "month" : { "value" : "02" }, "day" : null }, "journal-title" : { "value" : "The Plant Journal" }, "visibility" : "public", "path" : "/0000-0001-7872-3135/work/136214894", "display-index" : "0" } ] }, ], "path" : "/0000-0001-7872-3135/works" }
核心问题
Firebase CLI的database:set命令中,--data参数如果要指定本地JSON文件,必须在文件名前加@符号;直接传递文件名会被当作字符串上传,导致JSON解析失败,这是报错的根本原因。
修复步骤
修正Firebase命令的
--data参数
将脚本中的Firebase命令行修改为:firebase database:set "/users/${uid}/works/" --data "@${jsonFile}" -P project-name(如果文件名包含空格或特殊字符,
@${jsonFile}需要用引号包裹,确保参数传递正确)优化curl请求(可选但推荐)
当前curl命令使用-i参数会把HTTP响应头写入文件,导致文件开头不是纯JSON;虽然用tail删除了前17行,但响应头行数可能因请求结果变化而不稳定。建议去掉-i参数,直接保存纯JSON响应:curl -H 'Content-Type: application/orcid+json' -H 'Authorization: Bearer authkey' "https://pub.orcid.org/v3.0/${var}/works" -o "$jsonFilePath"此修改后可省略后续
tail处理文件的步骤,避免因响应头行数变化导致JSON损坏。确保文件路径正确
脚本中jsonFilePath是绝对路径,但jsonFile是相对文件名;如果执行脚本时的工作目录不是JSON文件所在目录,tail和firebase命令会找不到文件。可以改为直接使用绝对路径:jsonFile="${jsonFilePath}"或者在处理文件前切换到目标目录:
cd "/Users/user/Documents/folder/outputs_json/prueba/"
验证修正后的脚本片段
# 更新Firebase数据 echo "Actualizando Firebase para el UID ${uid}" echo $jsonFilePath firebase database:set "/users/${uid}/works/" --data "@${jsonFilePath}" -P project-name
内容的提问来源于stack exchange,提问作者moco

