JSONReaderStreamUsage topic
Using JSON readers with streams and files
Declaration
JSONReaderStreamUsageDescription
Both TJSONEventReader and TJSONConsumerReader can read JSON data from various sources including streams, files, and strings.
This flexibility allows you to process JSON data from files, network streams, or any other stream-based source without loading the entire content into memory first.
Here's an example that reads JSON from a file stream:
program JSONStreamDemo;
{$mode objfpc}{$H+}
uses
Classes, SysUtils, jsonreader;
type
TJSONCounter = class
private
FObjectCount: Integer;
FArrayCount: Integer;
FStringCount: Integer;
FNumberCount: Integer;
public
procedure OnStartObject(Sender: TObject);
procedure OnStartArray(Sender: TObject);
procedure OnStringValue(Sender: TObject; const AValue: UTF8String);
procedure OnIntegerValue(Sender: TObject; const AValue: Integer);
procedure OnFloatValue(Sender: TObject; const AValue: Double);
property ObjectCount: Integer read FObjectCount;
property ArrayCount: Integer read FArrayCount;
property StringCount: Integer read FStringCount;
property NumberCount: Integer read FNumberCount;
end;
procedure TJSONCounter.OnStartObject(Sender: TObject);
begin
Inc(FObjectCount);
end;
procedure TJSONCounter.OnStartArray(Sender: TObject);
begin
Inc(FArrayCount);
end;
procedure TJSONCounter.OnStringValue(Sender: TObject; const AValue: UTF8String);
begin
Inc(FStringCount);
end;
procedure TJSONCounter.OnIntegerValue(Sender: TObject; const AValue: Integer);
begin
Inc(FNumberCount);
end;
procedure TJSONCounter.OnFloatValue(Sender: TObject; const AValue: Double);
begin
Inc(FNumberCount);
end;
var
FileStream: TFileStream;
Reader: TJSONEventReader;
Counter: TJSONCounter;
JSONData: string;
TempFile: TextFile;
begin
// Create a sample JSON file
JSONData := '{"users": [{"name": "John", "age": 25}, {"name": "Jane", "age": 30}], "total": 2}';
AssignFile(TempFile, '/tmp/claude/sample.json');
Rewrite(TempFile);
try
Write(TempFile, JSONData);
finally
CloseFile(TempFile);
end;
Counter := TJSONCounter.Create;
FileStream := TFileStream.Create('/tmp/claude/sample.json', fmOpenRead);
Reader := TJSONEventReader.Create(FileStream, []);
try
// Assign counting event handlers
Reader.OnStartObject := @Counter.OnStartObject;
Reader.OnStartArray := @Counter.OnStartArray;
Reader.OnStringValue := @Counter.OnStringValue;
Reader.OnIntegerValue := @Counter.OnIntegerValue;
Reader.OnFloatValue := @Counter.OnFloatValue;
// Parse the JSON file
Reader.Execute;
// Display statistics
Writeln('JSON Statistics:');
Writeln(' Objects: ', Counter.ObjectCount);
Writeln(' Arrays: ', Counter.ArrayCount);
Writeln(' Strings: ', Counter.StringCount);
Writeln(' Numbers: ', Counter.NumberCount);
finally
Reader.Free;
FileStream.Free;
Counter.Free;
// Clean up temp file
DeleteFile('/tmp/claude/sample.json');
end;
end.
You can also use the readers with string sources when the JSON data is already in memory:
// String source Reader := TJSONEventReader.Create(JSONString, []); // Unicode string source Reader := TJSONEventReader.Create(UnicodeJSONString, []); // Stream source with options Reader := TJSONEventReader.Create(MyStream, [joUTF8, joStrict]);
The parsing options (TJSONOptions) allow you to control:
-
joUTF8: Handle UTF-8 encoding properly -
joStrict: Use strict JSON parsing rules -
joIgnoreTrailingComma: Allow trailing commas in objects and arrays -
joComments: Allow JavaScript-style comments in JSON
An experiment, built from development snapshots. Not the official Free Pascal or Lazarus documentation.
