You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

121 lines
2.6 KiB
JavaScript

/* JSON parser based on the grammar described at http://json.org/. */
/* ===== Syntactical Elements ===== */
start
= _ object { return $2; }
object
= "{" _ "}" _ { return {}; }
/ "{" _ members "}" _ { return $3; }
members
= pair ("," _ pair)* {
var result = {};
result[$1[0]] = $1[1];
for (var i = 0; i < $2.length; i++) {
result[$2[i][2][0]] = $2[i][2][1];
}
return result;
}
pair
= string ":" _ value { return [$1, $4]; }
array
= "[" _ "]" _ { return []; }
/ "[" _ elements "]" _ { return $3; }
elements
= value ("," _ value)* {
var result = [$1];
for (var i = 0; i < $2.length; i++) {
result.push($2[i][2]);
}
return result;
}
value
= string
/ number
/ object
/ array
/ "true" _ { return true; }
/ "false" _ { return false; }
// FIXME: We can't return null here because that would mean parse failure.
/ "null" _ { return "null"; }
/* ===== Lexical Elements ===== */
string "string"
= '"' '"' _ { return ""; }
/ '"' chars '"' _ { return $2; }
chars
= char+ { return $1.join(""); }
char
// In the original JSON grammar: "any-Unicode-character-except-"-or-\-or-control-character"
= [^"\\\0-\x1F\x7f]
/ '\\"' { return '"'; }
/ "\\\\" { return "\\"; }
/ "\\/" { return "/"; }
/ "\\b" { return "\b"; }
/ "\\f" { return "\f"; }
/ "\\n" { return "\n"; }
/ "\\r" { return "\r"; }
/ "\\t" { return "\t"; }
/ "\\u" hexDigit hexDigit hexDigit hexDigit {
return String.fromCharCode(parseInt("0x" + $2 + $3 + $4 + $5));
}
number "number"
= int frac exp _ { return parseFloat($1 + $2 + $3); }
/ int frac _ { return parseFloat($1 + $2); }
/ int exp _ { return parseFloat($1 + $2); }
/ int _ { return parseFloat($1); }
int
= digit19 digits { return $1 + $2; }
/ digit
/ "-" digit19 digits { return $1 + $2 + $3; }
/ "-" digit { return $1 + $2; }
frac
= "." digits { return $1 + $2; }
exp
= e digits { return $1 + $2; }
digits
= digit+ { return $1.join(""); }
e
= [eE] [+-]? { return $1 + $2; }
/*
* The following rules are not present in the original JSON gramar, but they are
* assumed to exist implicitly.
*
* FIXME: Define them according to ECMA-262, 5th ed.
*/
digit
= [0-9]
digit19
= [1-9]
hexDigit
= [0-9a-fA-F]
/* ===== Whitespace ===== */
_ "whitespace"
= whitespace*
// Whitespace is undefined in the original JSON grammar, so I assume a simple
// conventional definition consistent with ECMA-262, 5th ed.
whitespace
= [ \t\n\r]