![]() |
verstehe neue Vorgehensweise nicht wirklich :-(
Moin,
arbeite mich gerade in "neuere Techniken" ein - komme aber mit folgendem Beispiel nicht klar. (Daten per "neuem" JSONObjectBuilder-Objekt aufbereiten)
Delphi-Quellcode:
Wenn ich jetzt aber die Daten aus einer DB aufbereiten will: Wie kann ich dann einen "BeginObject" und "EndObject" PRO DB-Zeile machen?
var
StringWriter: TStringWriter; Writer: TJsonTextWriter; Builder: TJSONObjectBuilder; begin ... // entspr. objekte erstellen.. StringWriter := TStringWriter.Create(); Writer := TJsonTextWriter.Create(StringWriter); Builder := TJSONObjectBuilder.Create(Writer); Builder .BeginObject .BeginArray('wowarer') .BeginObject .Add('symbol', 'ACME') .Add('price', 75.5) .EndObject .BeginObject .Add('symbol', 'COOL') .Add('price', 21.7) .EndObject .EndArray .EndObject; Wäre super.. Tks |
AW: verstehe neue Vorgehensweise nicht wirklich :-(
Kurz ausgedrückt: Du rutscht über ein
Delphi-Quellcode:
drüber und willst für jede Zeile ein neues Json-Objekt in ein Json-Array stecken. Richtig?
TDataSet
Ich würde erst einmal dein
Delphi-Quellcode:
erstellen. Dann "pro Zeile" ein TJsonObject erstellen (über deinen
System.Json.TJsonArray
Delphi-Quellcode:
oder wie auch immer) und das mittels
TJSONObjectBuilder
Delphi-Quellcode:
hinzufügen.
myJsonArray.AddElement(meinFrischErstelltesObjekt)
|
AW: verstehe neue Vorgehensweise nicht wirklich :-(
so hatte ich es auch immer gemacht - dachte nur das ginge auch irgendwie mit dieser "Punktnotationsarie".
Danke..
Delphi-Quellcode:
// json-array für die rückgabe der daten erstellen..
a := TJSONArray.Create; try // DARF EIGTL NUR EINEN DS FINDEN - source aber für später so belassen // auf ersten satz pos.. dm.qryWoIsser.First; // saetze scannen.. while (NOT dm.qryWoIsser.Eof) do begin // fuer jeden ds ein json-objekt erstellen.. o := TJSONObject.Create; // fuer jedes gewuenschte qry-feld einen eintrag im json-objekt erstellen.. o.AddPair('id',dm.qryWoIsser.FieldByName('id').AsString); o.AddPair('location',dm.qryWoIsser.FieldByName('location').AsString); // objekt dem json-array hinzufügen.. a.AddElement(o); // nächster ds.. dm.qryWoIsser.Next; |
AW: verstehe neue Vorgehensweise nicht wirklich :-(
Klar, gehen müsste das auch: Es zwingt dich ja niemand in einem einzigen Statement, ohne abzusetzen, das Array auch wieder direkt abzuschließen.
Du könntest doch:
Stelle ich mir nur mit vernünftiger Exception-Behandlung (Array und Objekt auf jeden Fall ordentlich abschließen) etwas schwieriger vor. PS: Genannt wird die "neuere Technik" übrigens "Fluent Interface". ![]() |
AW: verstehe neue Vorgehensweise nicht wirklich :-(
Na, da wünsche ich viel Spaß beim Debuggen. Allein um mit F7 endlich in den richtigen Teil reinzukommen. Wie kommt eigentlich die Code-Formatierung mit dieser Geschichte klar? Wird das so wie hier zu sehen formatiert, oder klatscht der wieder alles zusammen in eine Zeile?
Sherlock |
AW: verstehe neue Vorgehensweise nicht wirklich :-(
ich habe da immer ne "unsichtbare" Protokollierung mitlaufen - debugger bin ich kein Fan von. Ich weiß... - aber das kann ich mir live bei Kunden ansehen, mailen lassen, etc.
Bin eigentlich auch kein großer Fan der ganzen neuen Gimmicks - aber man sollte sie halt kennen und manche sind auch echt cool. Trete halt seit rund 10 Jahren auf meinem "Wissen" rum und erlebe Delphi/FMX gerade "neu", weil ich grad Zeit hab. Bin an der Sache noch dran und, sollte ich es hinbekommen, dann post ich mal was zum "verbessern" :oops: |
AW: verstehe neue Vorgehensweise nicht wirklich :-(
Zitat:
|
AW: verstehe neue Vorgehensweise nicht wirklich :-(
übrigens betreffend:
Zitat:
sobald ich "scannen" bzw das 2. Mal auf Builder zugreifen will, bekomme ich "dieser Vorgang ist nicht zulässig, nachdem Paare oder Elemente hinzugefügt wurden."
Delphi-Quellcode:
ne Idee? Aber vielleicht ist meine Denke auch völlig falsch. Ich stelle mir das, wie ein Stream vor (also "Fluent Interface") - die jeweils letzte Anweisung liefert das Objekt für die Parent-Anweisung, richtig?
Builder
.BeginObject .BeginArray('wowarer'); for var i : integer := 0 to 2 do begin Builder .BeginObject .Add('symbol', i.ToString) .Add('price', i) .EndObject; end; Builder.BeginObject.EndObject; Builder.BeginObject.BeginArray('wowarer').EndArray; Tks.. |
AW: verstehe neue Vorgehensweise nicht wirklich :-(
@jaenicke: Hast ja recht - ich werde mich bessern. Steht jetzt auch auf der Liste..
|
AW: verstehe neue Vorgehensweise nicht wirklich :-(
Die letzten beide Zeilen müssen so sein:
Delphi-Quellcode:
Builder.EndArray;
Builder.EndObject; // oder Builder.EndArray.EndObject; |
AW: verstehe neue Vorgehensweise nicht wirklich :-(
Hallo,
damit kenne ich mich wirklich aus, aber
Delphi-Quellcode:
Das läßt sich doch sicher über lokale Variablen vereinfachen.
Builder
.BeginObject .Add('symbol', i.ToString) .Add('price', i) .EndObject;
Delphi-Quellcode:
Oder ist das jetzt wirklich was ganz neues?
BuilderObject:= Builder.BeginObject;
BuilderObject.Add() BuilderObject.Add() BuilderObject.EndObject; |
AW: verstehe neue Vorgehensweise nicht wirklich :-(
Klar geht das, aber was ist daran jetzt besser oder einfacher?
|
AW: verstehe neue Vorgehensweise nicht wirklich :-(
Zitat:
[dcc32 Fehler] Unit1.pas(144): E2361 Auf private-Symbol TJSONCollectionBuilder.EndArray kann nicht zugegriffen werden Aber, wie gesagt, kommt er soweit ja garnicht. In der for-Schleife schmiert er ja schon ab ("dieser Vorgang ist nicht zulässig, nachdem Paare oder Elemente hinzugefügt wurden."). |
AW: verstehe neue Vorgehensweise nicht wirklich :-(
Ja, man müsste sich das begonnene Array merken:
Delphi-Quellcode:
(
procedure buildObject(const builder: TJSONObjectBuilder);
const values: TArray<Single> = [3.14, -99, 0, 12, 17]; var jsonObject: TJSONObjectBuilderPairs; jsonArray: TJSONArrayBuilderElements; value: Single; begin jsonObject := builder.BeginObject(); jsonArray := jsonObject .Add('text', 'Hello World') .Add('someNumber', 42) .BeginArray('values'); for value in values do jsonArray.Add(value); jsonArray.EndArray(); jsonObject .Add('some final text', 'this was added after the array') .EndObject(); end; ![]() Und ja, das ist nicht wirklich übersichtlicher als es "klassisch" zu machen, so wie du es momentan schon hast. Trotzdem, bei einfachen Dingen, das in einem Rutsch so durchzuziehen - Da kann man doch nichts gegen haben. Hat doch sicher jeder schon mal mit einem
Delphi-Quellcode:
auch so gemacht...
TStringBuilder
|
AW: verstehe neue Vorgehensweise nicht wirklich :-(
Danke und klar, aber ich hasse es einfach, wenn ich etwas nicht hinbekomme. Aber folgendes könnte doch ein Ansatz sein. Ich bekomme aber immer nur 1 Objekt hin :-(
Ergebnis: sende: { "wowarer": [ { "id": "0", "location": "ort: 0" } ] } Hmm..
Delphi-Quellcode:
procedure TForm1.Button2Click(Sender: TObject);
function GetPairs : String; var o: TJSONObject; begin // je datensatz ein objekt.. for var i : integer := 0 to 2 do begin o := TJSONObject.Create; o.AddPair('id',i.ToString); o.AddPair('location','ort: ' + i.ToString); result := result + o.ToJSON; o.free; end; end; var StringWriter: TStringWriter; Writer: TJsonTextWriter; Builder: TJSONObjectBuilder; begin // entspr. objekte erstellen.. StringWriter := TStringWriter.Create(); Writer := TJsonTextWriter.Create(StringWriter); Builder := TJSONObjectBuilder.Create(Writer); // json-antwort aufbereiten.. try // json-objekte ins json-format formatieren?? (none = std) Writer.Formatting := TJsonFormatting.Indented; Builder .BeginObject .BeginArray('wowarer') .BeginObject .AddPairs(GetPairs) .EndObject .EndArray .EndObject; memo1.Lines.Add('sende:' + sLineBreak + StringWriter.ToString); finally Builder.Free; Writer.Free; StringWriter.Free; end; end; |
AW: verstehe neue Vorgehensweise nicht wirklich :-(
Ich verstehe nicht ganz was du erwartet hättest. Dein
Delphi-Quellcode:
geht hin und macht einmal ein Array "wowarer" und steckt dort ein Objekt rein.
Button2Click
Du willst jetzt mehrere Objekte in diesem Array? Merke dir das Array und rufe auf ihm so oft du willst
Delphi-Quellcode:
auf. Das habe ich einen Beitrag darüber gezeigt.
AddValue(..)
|
AW: verstehe neue Vorgehensweise nicht wirklich :-(
haha, jetzt war ich so im "flow". Ich brauche ja auch nur 1 Objekt. Aber du hast mich da auf eine Idee gebracht - wird wohl spät werden heute. Ich poste mal was, wenn ich's hinbekommen habe. Tks und schönen Abend erstmal..
|
AW: verstehe neue Vorgehensweise nicht wirklich :-(
Du brauchst ein Array mit mehreren Objekten wenn du eine Datenmenge mit mehreren Zeilen (Records) hast.
Deswegen bezweifel ich deine Aussage "Ich brauche ja auch nur 1 Objekt" sehr stark :gruebel: |
AW: verstehe neue Vorgehensweise nicht wirklich :-(
Vielleicht meine er "nur eine Referenz auf das Array". Oder etwas ganz ausgefuchstes. Bald werden wir es erfahren 😎
|
AW: verstehe neue Vorgehensweise nicht wirklich :-(
Da bin ich auch grad drauf gekommen, als ich wieder in meinem Projekt war, Mist - bin schon völlig kirre! Ich brauche für jeden Datensatz 1 Objekt.
Ich habe mir jetzt nochmal das Ergebnis angesehen und eigentlich fehlt im Result zwischen den Objekten ja nur ein Komma. Der Builder schmeisst die dann logischerweise raus. Hmm.. |
AW: verstehe neue Vorgehensweise nicht wirklich :-(
Im Prinzip stand alles was du wissen musst in der ersten Antwort:
Zitat:
|
AW: verstehe neue Vorgehensweise nicht wirklich :-(
Liste der Anhänge anzeigen (Anzahl: 1)
Moin @ALL,
also, habs jetzt so (s.u.) gemacht und klappt auch super (s. Anhang). Bitte nicht über die ausführlichen Kommentare wundern - dient als Lehrstoff. Und falls noch jemand etwas anzumerken hätte - alls her damit. Tks nochmal..
Delphi-Quellcode:
// json-antwort aufbereiten..
// entspr. objekte erstellen.. StringWriter := TStringWriter.Create(); Writer := TJsonTextWriter.Create(StringWriter); try // json-antwort formatiert aufbereiten?? if uglobal.JSON_FORMATIEREN then Writer.Formatting := TJsonFormatting.Indented; // beginn json-objekt für tabelle.. Writer.WriteStartObject; Writer.WritePropertyName('wowarer'); // beginn json-array für tabelle.. Writer.WriteStartArray; // datensaetze scannen.. dm.qryWoWarer.First; // vorsichtshalber auf ersten ds // info: diese form des scannens, weil man desöfteren im scanvorgang einen index (i) gebrauchen kann // alternativ: while NOT dm.qryWoWarer.Eof do begin - dann entfällt "nächster datensaetz" for var i: integer := 0 to dm.qryWoWarer.RecordCount - 1 do begin // für jeden ds ein json-objekt erstellen.. // beginn json-objekt.. Writer.WriteStartObject; // entspr. tabellen-felder mit deren werten in json-objekt.. Writer.WritePropertyName('id'); Writer.WriteValue(dm.qryWoWarer.FieldByName('id').AsInteger); Writer.WritePropertyName('location'); Writer.WriteValue(dm.qryWoWarer.FieldByName('location').AsString); // ende json-objekt.. Writer.WriteEndObject; // nächster datensaetz.. dm.qryWoWarer.Next; end; // ende json-array für tabelle.. Writer.WriteEndArray; // ende json-objekt für tabelle.. Writer.WriteEndObject; // prot.. if uglobal.OGProtokoll.Protokollieren then begin uglobal.AddToProtokoll('Anforderung gesendet'); if uglobal.OGProtokoll.ProtokollierenJSONString then begin // JSON-String formatiert ausgeben.. uglobal.AddToProtokoll('sende:' + sLineBreak + StringWriter.ToString,false,true); end; end; // senden.. // ContentType setzen, damit der client weiss welche art daten.. Response.ContentType := 'text/plain; charset="UTF-8"'; // und, weil webbies... - alles als string liefern.. Response.Content := StringWriter.ToString; finally Writer.Free; StringWriter.Free; end; |
AW: verstehe neue Vorgehensweise nicht wirklich :-(
Wow, nett.
Delphi-Quellcode:
und Konsorten kannte ich noch nicht. Das ist natürlich besser 👍
WriteStartObject()
Mir würde nur das fehlende try..finally zwischen
Delphi-Quellcode:
und
WriteStartObject()
Delphi-Quellcode:
(analog das Array) stören. Und den inneren Teil mit der Schleife in eine eigene Methode rausziehen, das ist ja schon etwas lang.
WriteEndObject()
Die WriteStartXX-Dinge sind mir echt neu. Wieder was gelernt 😊 |
AW: verstehe neue Vorgehensweise nicht wirklich :-(
ich weiß, aber optimiert wird immer erst später ;-) Baue gerade ein DatenModul rein..
|
Alle Zeitangaben in WEZ +1. Es ist jetzt 05:48 Uhr. |
Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024-2025 by Thomas Breitkreuz