(JSON) Object parser Browser vs. Client
Ich verzweifle an etwas, das ich als Bug bezeichnen würde.
Ich habe eine Funktion (global), die im Browser problemlos geht, aber in der App fehlschlägt und das gesamte globale Skript zerschießt.
Das Problem besteht darin, ein JSON-Objekt in einer Liste zu speichern, hier um ein gültiges GeoJSON zu erzeigen mit.
features: [{...}]
Wenn ich diese Liste nicht erzwinge (damit aber kein gültiges GeoJSON), ist es kein Problem.
Der Fehler deutet darauf hin, dass in ein Objekt geschrieben wird, das nicht existiert.
Hier zwei Versuche, beide nicht erfolgreich:
Version 1
function make_GeoJSON(ref : Places,JJ : text) do
let fJ := [{}];
let gJ := {};
let pJ := {
PLACE_ID: number(ref),
PLACE_NAME: ref.Name,
PLACE_TYPE: ref.Type.Name,
PLACE_TYPE_ID: ref.Type.number(Id),
distance: 0
};
if JJ = "" then JJ := ref.GeoJSON end;
let J := parseJSON(JJ);
if cnt(J.features) > 0 then
fJ := [J.first(features)];
if ref.'Primary Location' and longitude(ref.'Primary Location') != 0 and
latitude(ref.'Primary Location') != 0 and
longitude(ref.'Primary Location') and
latitude(ref.'Primary Location') and
first(fJ).geometry.type = "Point" then
setItem(first(fJ).geometry, "coordinates", [longitude(ref.'Primary Location'), latitude(ref.'Primary Location')])
end;
if not first(fJ).properties then
setItem(first(fJ), "properties", pJ)
end;
if not first(fJ).properties.distance then
setItem(first(fJ).properties, "distance", 0)
end;
setItem(first(fJ), "id", number(ref));
setItem(first(fJ).properties, "PLACE_ID", number(ref));
setItem(first(fJ).properties, "PLACE_NAME", ref.Name);
setItem(first(fJ).properties, "PLACE_TYPE", ref.Type.Name);
setItem(first(fJ).properties, "PLACE_TYPE_ID", ref.Type.number(Id));
setItem(J, "features", fJ)
else
void
end;
formatJSON(J)
end;
Hier ist das Problem in:
let fJ := [{}];
Version 2
function make_GeoJSON(ref : Places,JJ : text) do
let fJ := {};
let gJ := {};
let pJ := {
PLACE_ID: number(ref),
PLACE_NAME: ref.Name,
PLACE_TYPE: ref.Type.Name,
PLACE_TYPE_ID: ref.Type.number(Id),
distance: 0
};
if JJ = "" then JJ := ref.GeoJSON end;
let J := parseJSON(JJ);
if cnt(J.features) > 0 then
fJ := J.first(features);
if ref.'Primary Location' and longitude(ref.'Primary Location') != 0 and
latitude(ref.'Primary Location') != 0 and
longitude(ref.'Primary Location') and
latitude(ref.'Primary Location') and
fJ.geometry.type = "Point" then
setItem(fJ.geometry, "coordinates", [longitude(ref.'Primary Location'), latitude(ref.'Primary Location')])
end;
if not fJ.properties.distance then
setItem(fJ.properties, "distance", 0)
end;
setItem(fJ, "id", number(ref));
setItem(fJ.properties, "PLACE_ID", number(ref));
setItem(fJ.properties, "PLACE_NAME", ref.Name);
setItem(fJ.properties, "PLACE_TYPE", ref.Type.Name);
setItem(fJ.properties, "PLACE_TYPE_ID", ref.Type.number(Id));
setItem(J, "features", [fJ])
else
void
end;
formatJSON(J)
end;
Hier ist das Problem in
setItem(J, "features", [fJ])
19 Antworten
-
Zum leichteren Verständnis, hier ein korrektes GeoJSON:
{"type":"FeatureCollection","features":[{"geometry":{"coordinates":[-1.4440324,40.405312],"type":"Point"},"id":28,"properties":{"PLACE_ID":28,"PLACE_NAME":"Albarracín","PLACE_TYPE":"locality","PLACE_TYPE_ID":55,"distance":1180.7024668824363},"type":"Feature"}]}
-
Und das void in else ist nicht im Original, hier nur zur Verkürzung. Tatsächlich wird dort dann ein ganzes GeoJSON konstruiert statt aktualisiert.
-
Hi Christoph. Der Datentyp "Places" ist mir nicht bekannt. Wenn du hier mit dem Parameter "ref" ein Objekt übergibst, dann müßte dort "any" stehen und dann wechseln sofort alle Fehlermeldungen in die Tiefe, weil z.B. ref.'Primary Location' vom Typ "any" ist und nicht "location", demzufolge nicht an longitude() übergeben werden kann. Falls ich hier falsch liege, dann schreibe doch noch, welches Format der Parameter "ref" hat. Mirko
-
Moin,
ich habe eine Vermutung.
Wenn ich das richtig sehe, möchtest du mit der Zeile hier ein Array auf den Key "features" schreiben.setItem(J, "features", [fJ])
Das Problem scheint nun zu sein, dass das object nicht korrekt definiert ist.
Versuche bitte mal folgendes.
Erstelle das leere Array so:let fJ := [{}][< (< {})];
Dann in der if-Abfrage das Array so beschreiben:
fJ := array(fJ, [J.first(features)]);
Dann sollte das in dem setItem so aussehen:
setItem(J, "features", first(fJ))
Das ist gerade ziemlich experimentell und ohne die Datenbank ist das schwer nachzuvollziehen. Falles es nicht klappt, kannst du mal eine Testdatenbank hier hochladen?
Grüße Philipp -
Tests haben ergeben, dass der Fehler bei der Mac-App-Version unter v3.10.x auftritt.
Ein Update auf eine aktuelle Version sollte es beheben.
Ist die Nutzung einer Version unter 3.10.x zwingend notwendig, sollte folgendes Script funktionieren.let ref := this;
let fJ := [{}][< (< {})];
let gJ := {};
let pJ := {
PLACE_ID: number(ref),
PLACE_NAME: ref.Name,
distance: 0
};
let JJ := ref.GeoJSON;
let J := parseJSON(JJ);
if cnt(J.features) > 0 then
fJ := array(fJ, [J.first(features)]);
if not first(fJ).properties then
setItem(first(fJ), "properties", pJ)
end;
if not first(fJ).properties.distance then
setItem(first(fJ).properties, "distance", 0)
end;
setItem(first(fJ), "id", number(ref));
setItem(first(fJ).properties, "PLACE_ID", number(ref));
setItem(first(fJ).properties, "PLACE_NAME", "UweG");
setItem(J, "features", [first(fJ)])
end;
if cnt(J.features) < 1 then
gJ := {
type: "Point",
coordinates: [0, 0]
};
J := {
type: "FeatureCollection",
features: [{
type: "Feature",
id: number(ref),
geometry: gJ,
properties: pJ
}]
}
end;
J -
Das selbe bekommt man auch wie folgt hin:
let arrObj := [{}];
arrObj := null
let arrTxt := [""];
arrTxt := null
etc.
Man definiert den Type eines Arrays und hat anschließend ein leeres Array mit dem man arbeiten kann.
Ist halt eine Zeile mehr Script
Content aside
- Status Answered
- vor 2 MonatenZuletzt aktiv
- 19Antworten
- 115Ansichten
-
5
Folge bereits