/ / Delphi / REST / JSON - JSON、残り、デルファイ

Delphi / REST / JSON - json、rest、delphi

Delphi Tokyo 10.2 Update 1と、RESTRequest、RESTResponse、およびRESTClientの各コンポーネントを使用してRESTサーバーと通信しています。これが私の最初のREST / JSONの試みです。

ログインリクエスト(POST)を送信しましたそして期待された応答(GUID)を受け取りました。その後、GUIDを使用して他のさまざまな要求(GET)を実行します。行われた要求のうちの2つは、空のファイルと文書のJSONテンプレートを送り返し、それを次に入力します。 JSONオブジェクトのプロパティ値を更新する最善の方法がわかりません。

これが空のJSONファイルテンプレートです。

{
"boxId": 0,
"changedBy": 0,
"customSort": "",
"dateChanged": "1990-01-01T00:00:00",
"dateStarted": "1990-01-01T00:00:00",
"destruction": "1990-01-01T00:00:00",
"documentCount": 0,
"documents": {
"TotalCount": 0,
"Collection": [

]
},
"extraData": {
"TotalCount": 0,
"Collection": [

]
},
"fieldDefs": {
"TotalCount": 0,
"Collection": null
},
"field": [
"",
"",
"",
"",
"",
"",
"",
"",
"",
"",
"",
"",
"",
"",
"",
"",
"",
"",
"",
"",
""
],
"fileId": 0,
"filePtr": 0,
"id": 0,
"isIndexed": false,
"keyValue": "",
"keyVisualValue": "",
"labelPrinted": "1990-01-01T00:00:00",
"lineItems": {
"TotalCount": 0,
"Collection": [

]
},
"notes": "",
"objectType": 5,
"projectId": 0,
"routeInfo": null,
"routingDoc": null,
"remoteId": 0,
"saveNotesOnly": false,
"saveStyle": -999,
"status": 1,
"syncFlag": 0,
"totalDocumentCount": 0,
"viewerContext": 0
}

Pythonでは、フィールドプロパティ配列に最初の2つの値を入力するために、私は単にするでしょう:

inc_filetemplate = json.loads(requests.get(NEWFILE_string).text)
inc_doctemplate = json.loads(requests.get(NEWDOC_string).text)
filetemplate = inc_filetemplate
doctemplate = inc_doctemplate
filetemplate["field"][1] = dcn
filetemplate["field"][2] = batchname

簡単です!!!! ;)

Delphiでこれを行うための最良の方法は何ですか?

"field"配列から値を取得することができます(この例では最初の2つの項目は偶然空になっています)。これらの項目に値を設定する最善の方法がわからないだけです。

これが私が始めたものです。

procedure PopulateFileTemplate(const AFileTemplate: String);
var
JO: TJSONObject;
JOPair: TJSONPair;
JOArray: TJSONArray;
FieldDCN: String;
FieldBatchName: String;

begin
JO := TJSONObject.ParseJSONValue(AFileTemplate) as TJSONObject;

try
if JO = nil then
begin
MessageDlg("Unable to parse JSON file template.", mtError, [mbOK], 0);

Exit;
end;

JOArray := JO.Get("field").JsonValue as TJSONArray;
FieldDCN := JOArray.Items[0].Value;
FieldBatchName := JOArray.Items[1].Value;

Memo1.Lines.Add("The old value of DCN is: " + FieldDCN);
Memo1.Lines.Add("The old value of BatchName is: " + FieldBatchName);

// Best way to set Values here???????

Memo1.Lines.Add("The new value of DCN is: " + FieldDCN);
Memo1.Lines.Add("The new value of BatchName is: " + FieldBatchName);
finally
JO.Free;
end;
end;

回答:

回答№1は0

TJSONArray.Items[] プロパティはaを返します TJSONValueこれはあなたの例では TJSONString 以来のオブジェクト fields 文字列の配列

TJSONArray 実際には変更できるようには設計されていません 既存の 配列内のオブジェクト 配列の末尾に新しいオブジェクトを追加したり、配列から任意のオブジェクトを削除したりできますが、任意のインデックスに新しいオブジェクトを挿入したり、既存のオブジェクトを新しいオブジェクトに置き換えることはできません。

この種の機能に最も近いのは、 TList<TJSONValue> その中に必要なオブジェクトを入れて、それを TJSONArray.SetElements()。理想的ではありません。

そして TJSONString 編集用のメソッドやプロパティはありません。 string 値(を除く TJSONString.AddChar())。

あなたは保護されたものにアクセスするためにアクセサ/ヘルパークラスを使ってみることができます TJSONString.FStrBuffer メンバーになってから、必要に応じてその内容を編集します。

type
TJSONStringAccess = class(TJSONString)
end;

procedure SetJSONStringValue(JSONValue: TJSONString; const S: string);
begin
with TJSONStringAccess(JSONValue) do
begin
FStrBuffer.Clear;
FStrBuffer.Append(S);
end;
end;

procedure PopulateFileTemplate(const AFileTemplate: String);
var
JO: TJSONObject;
JOPair: TJSONPair;
JOArray: TJSONArray;
FieldDCN: TJSONString;
FieldBatchName: TJSONString;
begin
JO := TJSONObject.ParseJSONValue(AFileTemplate) as TJSONObject;
if JO = nil then
begin
MessageDlg("Unable to parse JSON file template.", mtError, [mbOK], 0);
Exit;
end;
try
JOArray := JO.Get("field").JsonValue as TJSONArray;
FieldDCN := JOArray.Items[0] as TJSONString;
FieldBatchName := JOArray.Items[1] as TJSONString;

Memo1.Lines.Add("The old value of DCN is: " + FieldDCN.Value);
Memo1.Lines.Add("The old value of BatchName is: " + FieldBatchName.Value);

SetJSONStringValue(FieldDCN, "...");
SetJSONStringValue(FieldBatchName, "...");

Memo1.Lines.Add("The new value of DCN is: " + FieldDCN.Value);
Memo1.Lines.Add("The new value of BatchName is: " + FieldBatchName.Value);
finally
JO.Free;
end;
end;

type
TJSONStringHelper = helper class for TJSONString
procedure SetValue(const S: string);
end;

procedure TJSONStringHelper.SetValue(const S: string);
begin
Self.FStrBuffer.Clear;
Self.FStrBuffer.Append(S);
end;

procedure PopulateFileTemplate(const AFileTemplate: String);
var
JO: TJSONObject;
JOPair: TJSONPair;
JOArray: TJSONArray;
FieldDCN: TJSONString;
FieldBatchName: TJSONString;
begin
JO := TJSONObject.ParseJSONValue(AFileTemplate) as TJSONObject;
if JO = nil then
begin
MessageDlg("Unable to parse JSON file template.", mtError, [mbOK], 0);
Exit;
end;
try
JOArray := JO.Get("field").JsonValue as TJSONArray;
FieldDCN := JOArray.Items[0] as TJSONString;
FieldBatchName := JOArray.Items[1] as TJSONString;

Memo1.Lines.Add("The old value of DCN is: " + FieldDCN.Value);
Memo1.Lines.Add("The old value of BatchName is: " + FieldBatchName.Value);

FieldDCN.SetValue("...");
FieldBatchName.SetValue("...");

Memo1.Lines.Add("The new value of DCN is: " + FieldDCN.Value);
Memo1.Lines.Add("The new value of BatchName is: " + FieldBatchName.Value);
finally
JO.Free;
end;
end;

それ以外の場合は、値の編集をネイティブでサポートしているサードパーティのJSONライブラリへの切り替えを検討してください。といった スーパーオブジェクト.