使用 Boost JSON 解析器时出现 JSON 格式设置错误
JSON formatting error using Boost JSON parser
我正在尝试使用 Boost 从我的 Firefox 配置文件夹中读取一个名为 sessionstore.js 的 JSON 文件,其中保存了当前/最后一个 Firefox 会话的信息以供恢复。我已经基于Boost网站上的基于XML的教程编写了一个程序,只需将XML部分换成JSON部分,
如下所示#include <boost/property_tree/ptree.hpp>
#include <boost/property_tree/json_parser.hpp>
#include <boost/foreach.hpp>
#include <string>
#include <set>
#include <exception>
using boost::property_tree::ptree;
using namespace std;
const string FILENAME = "sessionstore.js";
const string WINDOW_TAG = "windows";
struct session_settings
{
void load (const string &FILENAME);
};
void session_settings::load (const string &FILENAME)
{
ptree pt;
read_json (FILENAME, pt);
}
int main()
{
try
{
session_settings Settings;
Settings.load(FILENAME);
}
catch (exception &e)
{
cout << "Error: " << e.what() << endl;
}
return 0;
}
我尝试读取的 JSON 文件的内容是
{"windows":[{"tabs":[{"entries":[{"url":"about:home","title":"Mozilla Firefox Start Page","ID":5,"docshellID":11,"owner_b64":"NhAra3tiRRqhyKDUVsktxQAAAAAAAAAAwAAAAAAAAEYAAQAAAAAAAS8nfAAOr03buTZBMmukiq4HoizADOUR05MxABBLoP1AAAAAAAVhYm91dAAAAARob21l4NodcC97EdOM0ABgsPwUoweiLMAM5RHTkzEAEEug/UAAAAAADm1vei1zYWZlLWFib3V0AAAABGhvbWUAAAA=","docIdentifier":5},{"url":"http://www.google.co.uk/","title":"Google","ID":6,"docshellID":11,"docIdentifier":6,"children":[{"url":"about:blank","ID":7,"docshellID":12,"owner_b64":"NhAra3tiRRqhyKDUVsktxQAAAAAAAAAAwAAAAAAAAEYAAQAAAAAAAd6UctCANBHTk5kAEEug/UAHoizADOUR05MxABBLoP1AAAAAAv////8AAABQAQAAABhodHRwOi8vd3d3Lmdvb2dsZS5jby51ay8AAAAAAAAABAAAAAcAAAAQAAAAB/////8AAAAH/////wAAAAcAAAAQAAAAFwAAAAEAAAAXAAAAAQAAABcAAAABAAAAGAAAAAAAAAAY/////wAAABf/////AAAAF/////8AAAAX/////wEAAAAAAAAAAAABAAA=","docIdentifier":7,"scroll":"0,0"}],"formdata":{"#csi":"1","#hcache":"{"BInSTfL-EtSt8QOl24nrCg":[[69,{}],[14,{}],[60,{}],[81,{"persisted":true}],[42,{}],[43,{}],[83,{}],[95,{"kfe":{"kfeHost":"clients1.google.co.uk","kfeUrlPrefix":"/webpagethumbnail?r=2&f=2&s=300:585&query=&hl=en&gl=uk","maxPrefetchConnections":2,"prefetch":90,"slowConnection":false},"logging":{"csiFraction":0.05,"gen204Fraction":0.05},"msgs":{"loading":"Still loading...","mute":"Mute","noPreview":"Preview not available","sound":"Sound:","soundOff":"off","soundOn":"on","unmute":"Unmute"},"pb":{"desiredHeight":585,"desiredWidth":300,"minHeight":200,"minWidth":300},"time":{"hoverClose":300,"hoverModeTimeout":60,"hoverOpen":125,"loading":100,"longHoverOpen":725,"prefetchOnLoad":3000,"timeout":2500}}],[78,{}],[25,{"m":{"bks":true,"blg":true,"dsc":true,"evn":true,"frm":true,"isch":true,"klg":true,"mbl":true,"nws":true,"plcs":true,"ppl":true,"prc":true,"pts":true,"rcp":true,"shop":true,"vid":true},"t":null}],[64,{}],[105,{}],[22,{"m_errors":{"32":"Sorry, no more results to show.","default":"<font color=red>Error:</font> The server could not complete your request. Try again in 30 seconds."},"m_tip":"Click for more information"}],[77,{}],[84,{}],[99,{}],[29,{"mcr":5}],[92,{"avgTtfc":2000,"fd":1000,"fl":true,"focus":true,"hpt":250,"kn":true,"mds":"clir,clue,dfn,evn,frim,klg,prc,rl,show,sp,sts,ww,mbl_he,mbl_hs,mbl_re,mbl_rs,mbl_sv,isch","msg":{"dym":"Did you mean:","gs":"Google Search","kntt":"Use the up and down arrow keys to select each result. Press Enter to go to the selection.","sif":"Search instead for","srf":"Showing results for"},"odef":true,"ophe":true,"pq":true,"rpt":41,"tct":" ?","tdur":50}],[24,{}],[38,{}]]}"},"scroll":"0,0"}],"index":2,"hidden":false,"attributes":{"image":"http://www.google.co.uk/favicon.ico"},"storage":{"http://www.google.co.uk":{"web-v":"12_c9c918f0"}}}],"selected":1,"_closedTabs":[],"width":994,"height":688,"screenX":1650,"screenY":24,"sizemode":"normal","title":"Google"}],"selectedWindow":0,"_closedWindows":[{"tabs":[{"entries":[{"url":"about:home","title":"Mozilla Firefox Start Page","ID":0,"docshellID":5,"owner_b64":"NhAra3tiRRqhyKDUVsktxQAAAAAAAAAAwAAAAAAAAEYAAQAAAAAAAS8nfAAOr03buTZBMmukiq4HoizADOUR05MxABBLoP1AAAAAAAVhYm91dAAAAARob21l4NodcC97EdOM0ABgsPwUoweiLMAM5RHTkzEAEEug/UAAAAAADm1vei1zYWZlLWFib3V0AAAABGhvbWUAAAA="},{"url":"http://www.facebook.com/","title":"Welcome to Facebook - Log In, Sign Up or Learn More","ID":1,"docshellID":5,"docIdentifier":1,"formdata":{"//xhtml:div[@id='reg_form_box']/xhtml:table/xhtml:tbody/xhtml:tr[6]/xhtml:td[2]/xhtml:div/xhtml:div/xhtml:select":0,"//xhtml:div[@id='reg_form_box']/xhtml:table/xhtml:tbody/xhtml:tr[6]/xhtml:td[2]/xhtml:div/xhtml:div/xhtml:select[2]":0,"#sex":0,"#birthday_month":0,"#birthday_day":0,"#birthday_year":0},"scroll":"0,0"}],"index":2,"hidden":false,"attributes":{"image":"http://www.facebook.com/favicon.ico"}},{"entries":[{"url":"http://twitter.com/","title":"Twitter","ID":3,"docshellID":6,"docIdentifier":3,"children":[{"url":"http://api.twitter.com/receiver.html","ID":4,"docshellID":7,"referrer":"http://twitter.com/","docIdentifier":4,"scroll":"0,0"}],"formdata":{},"scroll":"0,0"}],"index":1,"hidden":false,"attributes":{"image":"http://twitter.com/phoenix/favicon.ico"}}],"selected":2,"_closedTabs":[],"width":994,"height":688,"screenX":1366,"screenY":307,"sizemode":"normal","cookies":[{"host":".facebook.com","value":"J4-69","path":"/","name":"lsd"},{"host":".facebook.com","value":"http%3A%2F%2Fwww.facebook.com%2F","path":"/","name":"reg_fb_gate"},{"host":".facebook.com","value":"http%3A%2F%2Fwww.facebook.com%2F","path":"/","name":"reg_fb_ref"},{"host":".facebook.com","value":"994x624","path":"/","name":"wd"},{"host":".twitter.com","value":"43838368","path":"/","name":"__utmc"},{"host":"twitter.com","value":"4bfz%2B%2BmebEkRkMWFCXm%2FCUOsvDoVeFTl","path":"/","name":"original_referer"},{"host":"scribe.twitter.com","value":"4bfz%2B%2BmebEkRkMWFCXm%2FCUOsvDoVeFTl","path":"/","name":"original_referer"},{"host":".twitter.com","value":"BAh7CToPY3JlYXRlZF9hdGwrCDoVZ%252F4vAToMY3NyZl9pZCIlODE2MGI1ZjJh%250AYmViNDMwODMxNDlkN2U5ZDg5Yjk4ZmU6B2lkIiU2N2I4YjdmNGExNWFkNzlk%250AODI0MDVjMGM1NmMzYjVhYSIKZmxhc2hJQzonQWN0aW9uQ29udHJvbGxlcjo6%250ARmxhc2g6OkZsYXNoSGFzaHsABjoKQHVzZWR7AA%253D%253D--8b0d751e9774c5cfaa61fdec567cb782aa8757dd","path":"/","name":"_twitter_sess","httponly":true},{"host":".twitter.com","value":"43838368","path":"/","name":"__utmc"},{"host":"twitter.com","value":"4bfz%2B%2BmebEkRkMWFCXm%2FCUOsvDoVeFTl","path":"/","name":"original_referer"},{"host":"scribe.twitter.com","value":"4bfz%2B%2BmebEkRkMWFCXm%2FCUOsvDoVeFTl","path":"/","name":"original_referer"},{"host":".twitter.com","value":"BAh7CToPY3JlYXRlZF9hdGwrCDoVZ%252F4vAToMY3NyZl9pZCIlODE2MGI1ZjJh%250AYmViNDMwODMxNDlkN2U5ZDg5Yjk4ZmU6B2lkIiU2N2I4YjdmNGExNWFkNzlk%250AODI0MDVjMGM1NmMzYjVhYSIKZmxhc2hJQzonQWN0aW9uQ29udHJvbGxlcjo6%250ARmxhc2g6OkZsYXNoSGFzaHsABjoKQHVzZWR7AA%253D%253D--8b0d751e9774c5cfaa61fdec567cb782aa8757dd","path":"/","name":"_twitter_sess","httponly":true}],"title":"Twitter"}],"session":{"state":"stopped","lastUpdate":1305658398727}}
当我尝试用我的程序加载它时,我得到了错误
Error: sessionstore.js(1): expected value
由于文件全部格式化在一行上,这意味着错误可能在文件中的任何位置,所以我通过Javascript美化器运行它,保留默认选项,并将结果粘贴回原始文件并执行程序。
格式化的 JSON 是
{
"windows": [{
"tabs": [{
"entries": [{
"url": "about:home",
"title": "Mozilla Firefox Start Page",
"ID": 5,
"docshellID": 11,
"owner_b64": "NhAra3tiRRqhyKDUVsktxQAAAAAAAAAAwAAAAAAAAEYAAQAAAAAAAS8nfAAOr03buTZBMmukiq4HoizADOUR05MxABBLoP1AAAAAAAVhYm91dAAAAARob21l4NodcC97EdOM0ABgsPwUoweiLMAM5RHTkzEAEEug/UAAAAAADm1vei1zYWZlLWFib3V0AAAABGhvbWUAAAA=",
"docIdentifier": 5
}, {
"url": "http://www.google.co.uk/",
"title": "Google",
"ID": 6,
"docshellID": 11,
"docIdentifier": 6,
"children": [{
"url": "about:blank",
"ID": 7,
"docshellID": 12,
"owner_b64": "NhAra3tiRRqhyKDUVsktxQAAAAAAAAAAwAAAAAAAAEYAAQAAAAAAAd6UctCANBHTk5kAEEug/UAHoizADOUR05MxABBLoP1AAAAAAv////8AAABQAQAAABhodHRwOi8vd3d3Lmdvb2dsZS5jby51ay8AAAAAAAAABAAAAAcAAAAQAAAAB/////8AAAAH/////wAAAAcAAAAQAAAAFwAAAAEAAAAXAAAAAQAAABcAAAABAAAAGAAAAAAAAAAY/////wAAABf/////AAAAF/////8AAAAX/////wEAAAAAAAAAAAABAAA=",
"docIdentifier": 7,
"scroll": "0,0"
}],
"formdata": {
"#csi": "1",
"#hcache": "{"BInSTfL-EtSt8QOl24nrCg":[[69,{}],[14,{}],[60,{}],[81,{"persisted":true}],[42,{}],[43,{}],[83,{}],[95,{"kfe":{"kfeHost":"clients1.google.co.uk","kfeUrlPrefix":"/webpagethumbnail?r=2&f=2&s=300:585&query=&hl=en&gl=uk","maxPrefetchConnections":2,"prefetch":90,"slowConnection":false},"logging":{"csiFraction":0.05,"gen204Fraction":0.05},"msgs":{"loading":"Still loading...","mute":"Mute","noPreview":"Preview not available","sound":"Sound:","soundOff":"off","soundOn":"on","unmute":"Unmute"},"pb":{"desiredHeight":585,"desiredWidth":300,"minHeight":200,"minWidth":300},"time":{"hoverClose":300,"hoverModeTimeout":60,"hoverOpen":125,"loading":100,"longHoverOpen":725,"prefetchOnLoad":3000,"timeout":2500}}],[78,{}],[25,{"m":{"bks":true,"blg":true,"dsc":true,"evn":true,"frm":true,"isch":true,"klg":true,"mbl":true,"nws":true,"plcs":true,"ppl":true,"prc":true,"pts":true,"rcp":true,"shop":true,"vid":true},"t":null}],[64,{}],[105,{}],[22,{"m_errors":{"32":"Sorry, no more results to show.","default":"<font color=red>Error:</font> The server could not complete your request. Try again in 30 seconds."},"m_tip":"Click for more information"}],[77,{}],[84,{}],[99,{}],[29,{"mcr":5}],[92,{"avgTtfc":2000,"fd":1000,"fl":true,"focus":true,"hpt":250,"kn":true,"mds":"clir,clue,dfn,evn,frim,klg,prc,rl,show,sp,sts,ww,mbl_he,mbl_hs,mbl_re,mbl_rs,mbl_sv,isch","msg":{"dym":"Did you mean:","gs":"Google Search","kntt":"Use the up and down arrow keys to select each result. Press Enter to go to the selection.","sif":"Search instead for","srf":"Showing results for"},"odef":true,"ophe":true,"pq":true,"rpt":41,"tct":" ?","tdur":50}],[24,{}],[38,{}]]}"
},
"scroll": "0,0"
}],
"index": 2,
"hidden": false,
"attributes": {
"image": "http://www.google.co.uk/favicon.ico"
},
"storage": {
"http://www.google.co.uk": {
"web-v": "12_c9c918f0"
}
}
}],
"selected": 1,
"_closedTabs": [],
"width": 994,
"height": 688,
"screenX": 1650,
"screenY": 24,
"sizemode": "normal",
"title": "Google"
}],
"selectedWindow": 0,
"_closedWindows": [{
"tabs": [{
"entries": [{
"url": "about:home",
"title": "Mozilla Firefox Start Page",
"ID": 0,
"docshellID": 5,
"owner_b64": "NhAra3tiRRqhyKDUVsktxQAAAAAAAAAAwAAAAAAAAEYAAQAAAAAAAS8nfAAOr03buTZBMmukiq4HoizADOUR05MxABBLoP1AAAAAAAVhYm91dAAAAARob21l4NodcC97EdOM0ABgsPwUoweiLMAM5RHTkzEAEEug/UAAAAAADm1vei1zYWZlLWFib3V0AAAABGhvbWUAAAA="
}, {
"url": "http://www.facebook.com/",
"title": "Welcome to Facebook - Log In, Sign Up or Learn More",
"ID": 1,
"docshellID": 5,
"docIdentifier": 1,
"formdata": {
"//xhtml:div[@id='reg_form_box']/xhtml:table/xhtml:tbody/xhtml:tr[6]/xhtml:td[2]/xhtml:div/xhtml:div/xhtml:select": 0,
"//xhtml:div[@id='reg_form_box']/xhtml:table/xhtml:tbody/xhtml:tr[6]/xhtml:td[2]/xhtml:div/xhtml:div/xhtml:select[2]": 0,
"#sex": 0,
"#birthday_month": 0,
"#birthday_day": 0,
"#birthday_year": 0
},
"scroll": "0,0"
}],
"index": 2,
"hidden": false,
"attributes": {
"image": "http://www.facebook.com/favicon.ico"
}
}, {
"entries": [{
"url": "http://twitter.com/",
"title": "Twitter",
"ID": 3,
"docshellID": 6,
"docIdentifier": 3,
"children": [{
"url": "http://api.twitter.com/receiver.html",
"ID": 4,
"docshellID": 7,
"referrer": "http://twitter.com/",
"docIdentifier": 4,
"scroll": "0,0"
}],
"formdata": {},
"scroll": "0,0"
}],
"index": 1,
"hidden": false,
"attributes": {
"image": "http://twitter.com/phoenix/favicon.ico"
}
}],
"selected": 2,
"_closedTabs": [],
"width": 994,
"height": 688,
"screenX": 1366,
"screenY": 307,
"sizemode": "normal",
"cookies": [{
"host": ".facebook.com",
"value": "J4-69",
"path": "/",
"name": "lsd"
}, {
"host": ".facebook.com",
"value": "http%3A%2F%2Fwww.facebook.com%2F",
"path": "/",
"name": "reg_fb_gate"
}, {
"host": ".facebook.com",
"value": "http%3A%2F%2Fwww.facebook.com%2F",
"path": "/",
"name": "reg_fb_ref"
}, {
"host": ".facebook.com",
"value": "994x624",
"path": "/",
"name": "wd"
}, {
"host": ".twitter.com",
"value": "43838368",
"path": "/",
"name": "__utmc"
}, {
"host": "twitter.com",
"value": "4bfz%2B%2BmebEkRkMWFCXm%2FCUOsvDoVeFTl",
"path": "/",
"name": "original_referer"
}, {
"host": "scribe.twitter.com",
"value": "4bfz%2B%2BmebEkRkMWFCXm%2FCUOsvDoVeFTl",
"path": "/",
"name": "original_referer"
}, {
"host": ".twitter.com",
"value": "BAh7CToPY3JlYXRlZF9hdGwrCDoVZ%252F4vAToMY3NyZl9pZCIlODE2MGI1ZjJh%250AYmViNDMwODMxNDlkN2U5ZDg5Yjk4ZmU6B2lkIiU2N2I4YjdmNGExNWFkNzlk%250AODI0MDVjMGM1NmMzYjVhYSIKZmxhc2hJQzonQWN0aW9uQ29udHJvbGxlcjo6%250ARmxhc2g6OkZsYXNoSGFzaHsABjoKQHVzZWR7AA%253D%253D--8b0d751e9774c5cfaa61fdec567cb782aa8757dd",
"path": "/",
"name": "_twitter_sess",
"httponly": true
}, {
"host": ".twitter.com",
"value": "43838368",
"path": "/",
"name": "__utmc"
}, {
"host": "twitter.com",
"value": "4bfz%2B%2BmebEkRkMWFCXm%2FCUOsvDoVeFTl",
"path": "/",
"name": "original_referer"
}, {
"host": "scribe.twitter.com",
"value": "4bfz%2B%2BmebEkRkMWFCXm%2FCUOsvDoVeFTl",
"path": "/",
"name": "original_referer"
}, {
"host": ".twitter.com",
"value": "BAh7CToPY3JlYXRlZF9hdGwrCDoVZ%252F4vAToMY3NyZl9pZCIlODE2MGI1ZjJh%250AYmViNDMwODMxNDlkN2U5ZDg5Yjk4ZmU6B2lkIiU2N2I4YjdmNGExNWFkNzlk%250AODI0MDVjMGM1NmMzYjVhYSIKZmxhc2hJQzonQWN0aW9uQ29udHJvbGxlcjo6%250ARmxhc2g6OkZsYXNoSGFzaHsABjoKQHVzZWR7AA%253D%253D--8b0d751e9774c5cfaa61fdec567cb782aa8757dd",
"path": "/",
"name": "_twitter_sess",
"httponly": true
}],
"title": "Twitter"
}],
"session": {
"state": "stopped",
"lastUpdate": 1305658398727
}
}
错误
Error: sessionstore.js(179): expected value
现在将故障标识为在倒数第三行,即读取"lastUpdate": 1305658398727
的那行。从我读到的有关 JSON 格式的内容来看,这听起来像是这一行中缺少逗号或括号,但这是一个文件,已经生成了我的 Mozilla 以与 Firefox 一起使用,我不相信他们会犯这样的错误,所以我被引导相信 Boost 中的 JSON 解析器存在问题。任何人都可以确认是这种情况,还是我做错了什么?
我认为问题是这个值大于int
或double
。我不知道什么数据类型使用 BOOST JSON 来读取数字。要对此进行测试,只需将数字更改为字符串并再次解析即可。在标准中,数字不受限制,但您必须选择一种数据类型来表示它们,也许他们选择了double
,显然不足以满足这个数字。我将看一下您是否可以配置用于数字的类型。
编辑:
再看一下实现,"数字"规则是使用 Spirit 实现的,如下所示:
number
= strict_real_p
| int_p
;
查看 Spirit strict_real_p
使用 double
作为底层类型,int_p
实际上使用 int
。
坏消息是,对于我在代码中看到的内容,这是不可配置的,因此您必须更改要解释的 JSON。
在收到迭戈·塞维利亚和c-smile的答案后,我做了一些谷歌搜索,以弄清楚如何将他们的建议合并到Boost中,因为不幸的是,更改JSON文件在我的情况下不是一个选项,我在Boost错误跟踪器上遇到了这张票,它描述了我的确切问题。此后,它已修复并与Boost 1.45一起发布。但是,我使用的是 Ubuntu 存储库中的 1.42 版,因此需要手动安装较新版本。
迭戈所说,这是因为1305658398727既不适合strict_real_p
也不适合int_p
生产。
我怀疑您将需要其他JSON解析器或自己修改Spirit定义。
要么像这样:
number
= strict_real_p
| int_p
| int64_p
;
或者只是:
number
= real_p;
理想情况下,JSON 中的日期/时间应由 ISO 格式的字符串表示。在这种情况下,您将不会遇到此类问题。我怀疑自 1970-01-01 以来的数据只有毫秒数(JavaScript Date.valueOf()
)
- 在c++中使用nlohmann从类到json的转换
- 如何在openssl-ecc中获取十六进制格式的私钥
- 将"打开的CV图像"中的"颜色"转换为整数格式
- TDateTime格式在C++Builder中不会更改
- 将json代码格式化为std::string
- <int> 通过 json 格式的串行发送矢量
- 我想将字符串转换为 Json 格式并返回字符串向量作为答案
- 如何以json格式保存弹性搜索的数据
- CPPRestSDK(casablanca)从传入的WebSocket消息中提取JSON(格式错误的令牌)
- 如何使用 C++ 中的 rapidjson 库从 json 格式字符串中获取值
- 如何将标准::字符串格式的 JSON 解码为 Boost 属性树
- 是否有适用于 sigma.js兼容 json 文件的专用格式
- Boost Library函数将JSON格式的属性树转换为点分隔的字符串
- 当在数据库上保存json格式的字符串时,我是否也应该保存值的类型以便稍后转换回来
- Mongo DB C++格式错误十进制,将".0"添加到末尾,在转换器到 JSON
- PHP格式错误的JSON字符串需要纠正
- 使用c++在Mysql查询中插入JSON格式
- 如何读取json格式文本的字符流
- 如何使用c++ boost解析这种特定的JSON格式
- 使用 Boost JSON 解析器时出现 JSON 格式设置错误