Summary
TJsonObject.GetPath supports object navigation (a.b.c) and single-level array indexing (items[3]), but rejects nested array indexing such as matrix[1][2] or rows[0][3].name. Even when the underlying data exists and the path is unambiguous, the call raises EJsonCastException from PathError.
For JSON documents containing 2-D arrays (grids, matrices, tabular data, paginated rows-of-rows), this means callers can't use GetPath at all for that branch of the tree — they have to break navigation into multiple calls and lose the path API's convenience.
Where it fails
In TJsonObject.GetPath, after the closing ] is consumed, the code only handles two next-character cases:
if P^ = '.' then
begin
Inc(P);
Obj := Item.ObjectValue;
Item := nil;
end
else if P^ = #0 then
begin
// return array element
Result.FData.FIntern := Item;
Break;
end;
If P^ is [, neither branch is taken; the outer loop iterates with F = P pointing at [, the fast-forward immediately breaks (Ch in [#0, '[', '.']), so F = EndF, and PathError is raised.
Reproduction
var
O: TJsonObject;
begin
O := TJsonBaseObject.Parse('{ "matrix": [ [1, 2], [3, 4] ] }') as TJsonObject;
try
// works:
Writeln(O.A['matrix'].A[1].I[0].ToString); // "3"
// fails — raises EJsonCastException:
Writeln(O.Path['matrix[1][0]'].IntValue.ToString);
finally
O.Free;
end;
end;
Suggested approach
After resolving Item from the inner ], if the next character is [, treat that element as the array to index into for the next iteration. Conceptually a "carry" variable holding the just-resolved array. The F = EndF guard (used to detect an empty name segment) needs to be relaxed when the current character is [, since the segment between ] and the next [ is legitimately empty.
If it'd help, I have a local implementation that does this; happy to send a PR.
Summary
TJsonObject.GetPathsupports object navigation (a.b.c) and single-level array indexing (items[3]), but rejects nested array indexing such asmatrix[1][2]orrows[0][3].name. Even when the underlying data exists and the path is unambiguous, the call raisesEJsonCastExceptionfromPathError.For JSON documents containing 2-D arrays (grids, matrices, tabular data, paginated rows-of-rows), this means callers can't use
GetPathat all for that branch of the tree — they have to break navigation into multiple calls and lose the path API's convenience.Where it fails
In
TJsonObject.GetPath, after the closing]is consumed, the code only handles two next-character cases:If
P^is[, neither branch is taken; the outer loop iterates withF = Ppointing at[, the fast-forward immediately breaks (Ch in [#0, '[', '.']), soF = EndF, andPathErroris raised.Reproduction
Suggested approach
After resolving
Itemfrom the inner], if the next character is[, treat that element as the array to index into for the next iteration. Conceptually a "carry" variable holding the just-resolved array. TheF = EndFguard (used to detect an empty name segment) needs to be relaxed when the current character is[, since the segment between]and the next[is legitimately empty.If it'd help, I have a local implementation that does this; happy to send a PR.