You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Copy file name to clipboardExpand all lines: README.md
+1-1Lines changed: 1 addition & 1 deletion
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -89,7 +89,7 @@ All input to `JSON.parse` that is currently rejected will continue to be, all in
89
89
### Modified values
90
90
Reviver functions are intended to modify or remove values in the output, but those changes should have no effect on the source-derived arguments passed to them.
91
91
Because reviver functions are invoked bottom-up, this means that values may not correlate with source text.
92
-
We consider this to be acceptable, but moot (see the following point).
92
+
We consider this to be acceptable, but mostly moot (see the following point). Where _not_ moot (such as when not-yet-visited array indexes or object entries are modified), source text is suppressed.
93
93
94
94
### Non-primitive values
95
95
Per https://github.com/tc39/proposal-json-parse-with-source/issues/10#issuecomment-704441802 , source text exposure is limited to primitive values.
<p>This function parses a JSON text (a JSON-formatted String) and produces an ECMAScript language value. The JSON format represents literals, arrays, and objects with a syntax similar to the syntax for ECMAScript literals, Array Initializers, and Object Initializers. After parsing, JSON objects are realized as ECMAScript objects. JSON arrays are realized as ECMAScript Array instances. JSON strings, numbers, booleans, and null are realized as ECMAScript Strings, Numbers, Booleans, and *null*.</p>
67
-
<p>The optional _reviver_ parameter is a function that <del>takes two parameters, _key_ and _value_. It</del> can filter and transform the results. <del>It is called with each of the _key_/_value_ pairs produced by the parse,</del><ins>For each value produced by the parse, it is called with three arguments (the key, the value, and a context object containing [for primitive values] details of the corresponding Parse Node)</ins> and its return value is used instead of the original value. If it returns what it received, the structure is not modified. If it returns *undefined* then the property is deleted from the result.</p>
67
+
<p>The optional _reviver_ parameter is a function that <del>takes two parameters, _key_ and _value_. It</del> can filter and transform the results. <del>It is called with each of the _key_/_value_ pairs produced by the parse,</del><ins>For each value produced by the parse, it is called with three arguments (the key, the value, and a context object containing [for unmodified primitive values] details of the corresponding Parse Node)</ins> and its return value is used instead of the original value. If it returns what it received, the structure is not modified. If it returns *undefined* then the property is deleted from the result.</p>
68
68
<emu-alg>
69
69
1. Let _jsonString_ be ? ToString(_text_).
70
70
1. [id="step-json-parse-validate"] Parse StringToCodePoints(_jsonString_) as a JSON text as specified in ECMA-404. Throw a *SyntaxError* exception if it is not a valid JSON text as defined in that specification.
<p>However, because <emu-xref href="#sec-runtime-semantics-propertydefinitionevaluation"></emu-xref> behaves differently during `JSON.parse`, the same source text can produce different results when evaluated as a |PrimaryExpression| rather than as JSON. Furthermore, the Early Error for duplicate *"__proto__"* properties in object literals, which likewise does not apply during `JSON.parse`, means that not all texts accepted by `JSON.parse` are valid as a |PrimaryExpression|, despite matching the grammar.</p>
91
92
</emu-note>
92
93
94
+
<ins class="block">
95
+
<emu-clause id="sec-json-parse-record">
96
+
<h1>JSON Parse Record</h1>
97
+
<p>A <dfn variants="JSON Parse Records">JSON Parse Record</dfn> is a Record value used to describe the initial state of a value parsed from JSON text.</p>
98
+
<p>JSON Parse Records have the fields listed in <emu-xref href="#table-json-parse-record"></emu-xref>.</p>
99
+
<emu-table id="table-json-parse-record" caption="JSON Parse Record Fields">
100
+
<table>
101
+
<tr>
102
+
<th>Field Name</th>
103
+
<th>Value</th>
104
+
<th>Meaning</th>
105
+
</tr>
106
+
<tr>
107
+
<td>[[ParseNode]]</td>
108
+
<td>a Parse Node</td>
109
+
<td>The context Parse Node.</td>
110
+
</tr>
111
+
<tr>
112
+
<td>[[Key]]</td>
113
+
<td>a property name</td>
114
+
<td>The property name with which [[Value]] is associated.</td>
115
+
</tr>
116
+
<tr>
117
+
<td>[[Value]]</td>
118
+
<td>an ECMAScript language value</td>
119
+
<td>The value produced by evaluation of [[ParseNode]].</td>
120
+
</tr>
121
+
<tr>
122
+
<td>[[Elements]]</td>
123
+
<td>a List of JSON Parse Records</td>
124
+
<td>JSON Parse Records corresponding with the elements of a [[Value]] that is an Array, in order. If [[Value]] is not an Array, the List will be empty.</td>
125
+
</tr>
126
+
<tr>
127
+
<td>[[Entries]]</td>
128
+
<td>a List of JSON Parse Records</td>
129
+
<td>JSON Parse Records corresponding with the entries of a [[Value]] that is a non-Array Object, in source order. If [[Value]] is not a non-Array Object, the List will be empty.</td>
<dd>It recursively combines a _parseNode_ parsed from JSON text and the _val_ produced by its evaluation.</dd>
146
+
</dl>
147
+
<emu-alg>
148
+
1. Let _typedValNode_ be ShallowestContainedJSONValue of _parseNode_.
149
+
1. Assert: _typedValNode_ is not ~empty~.
150
+
1. Let _elements_ be a new empty List.
151
+
1. Let _entries_ be a new empty List.
152
+
1. If _val_ is an Object, then
153
+
1. Let _isArray_ be ! IsArray(_val_).
154
+
1. If _isArray_ is *true*, then
155
+
1. Assert: _typedValNode_ is an |ArrayLiteral| Parse Node.
156
+
1. Let _contentNodes_ be ArrayLiteralContentNodes of _typedValNode_.
157
+
1. Let _len_ be the number of elements in _contentNodes_.
158
+
1. Let _valLen_ be ! LengthOfArrayLike(_val_).
159
+
1. Assert: _valLen_ = _len_.
160
+
1. Let _I_ be 0.
161
+
1. Repeat, while _I_ < _len_,
162
+
1. Let _propName_ be ! ToString(𝔽(_I_)).
163
+
1. Let _elementParseRecord_ be CreateJSONParseRecord(_contentNodes_[_I_], _propName_, ! Get(_val_, _propName_)).
164
+
1. Append _elementParseRecord_ to _elements_.
165
+
1. Set _I_ to _I_ + 1.
166
+
1. Else,
167
+
1. Assert: _typedValNode_ is an |ObjectLiteral| Parse Node.
168
+
1. Let _propertyNodes_ be PropertyDefinitionList of _typedValNode_.
169
+
1. NOTE: Because _val_ was produced from JSON text and has not been modified, all of its property keys are Strings and will be exhaustively enumerated in source text order.
170
+
1. Let _keys_ be ! EnumerableOwnProperties(_val_, ~key~).
171
+
1. For each String _P_ of _keys_, do
172
+
1. NOTE: In the case of JSON text specifying multiple name/value pairs with the same name for a single object (such as <code>{"a":"lost","a":"kept"}</code>), the value for the corresponding property of the resulting ECMAScript object is specified by the last pair with that name.
173
+
1. Let _propertyDefinition_ be ~empty~.
174
+
1. For each Parse Node _propertyNode_ of _propertyNodes_, do
175
+
1. Let _propName_ be PropName of _propertyNode_.
176
+
1. If SameValue(_propName_, _P_) is *true*, set _propertyDefinition_ to _propertyNode_.
177
+
1. Assert: _propertyDefinition_ is <emu-grammar>PropertyDefinition : PropertyName `:` AssignmentExpression</emu-grammar>.
178
+
1. Let _propertyValueNode_ be the |AssignmentExpression| of _propertyDefinition_.
179
+
1. Let _entryParseRecord_ be CreateJSONParseRecord(_propertyValueNode_, _P_, !Get(_val_, _P_)).
180
+
1. Append _entryParseRecord_ to _entries_.
181
+
1. Else,
182
+
1. Assert: _typedValNode_ is not an |ArrayLiteral| Parse Node and not an |ObjectLiteral| Parse Node.
183
+
1. Return the JSON Parse Record { [[ParseNode]]: _typedValNode_, [[Key]]: _key_, [[Value]]: _val_, [[Elements]]: _elements_, [[Entries]]: _entries_ }.
1. <ins>Assert: _typedValNode_ is an |ObjectLiteral| Parse Node.</ins>
135
-
1. <ins>Let _properties_ be PropertyDefinitionList of _typedValNode_.</ins>
136
233
1. Let _keys_ be ? EnumerableOwnProperties(_val_, ~key~).
137
234
1. For each String _P_ of _keys_, do
138
-
1. <ins>Let _propertyDefinition_ be ~empty~.</ins>
139
-
1. <ins>For each Parse Node _candidate_ of _properties_, do</ins>
140
-
1. <ins>Let _propName_ be PropName of _candidate_.</ins>
141
-
1. <ins>If SameValue(_propName_, _P_) is *true*, set _propertyDefinition_ to _candidate_.</ins>
142
-
1. <ins>Assert: _propertyDefinition_ is not ~empty~.</ins>
143
-
1. <ins>NOTE: In the case of JSON text specifying multiple name/value pairs with the same name for a single object (such as <code>{"a":"lost","a":"kept"}</code>), the value for the corresponding property of the resulting ECMAScript object is specified by the last pair with that name.</ins>
144
-
1.<ins>Assert: _propertyDefinition_ is <emu-grammar>PropertyDefinition : PropertyName `:` AssignmentExpression</emu-grammar>.</ins>
145
-
1.<ins>Let _propertyValueNode_ be the |AssignmentExpression| of _propertyDefinition_.</ins>
146
-
1. Let _newElement_ be ?InternalizeJSONProperty(_val_, _P_, _reviver_<ins>, _propertyValueNode_</ins>).
235
+
1. <ins>Let _entryRecord_ be the element of _entryRecords_ whose [[Key]] field is _P_. If there is no such element, let _entryRecord_ be ~empty~.</ins>
236
+
1. Let _newElement_ be ? InternalizeJSONProperty(_val_, _P_, _reviver_<ins>, _entryRecord_</ins>).
0 commit comments