0

I am using getJSON to grab data from a database, which I am then displaying to a map using Leaflet.

I want to use multiple getJSON calls that I then display as different layers on the same map. My problem is how to get the callback working with multiple geoJSON calls in the getData function. Or alternatively (I'm unsure which is the better approach) - having multiple versions of the getData function and then being able to access all of them to form the layers.

For a single getJSON the following works:

function getData(callback) {
   $.getJSON("getData.php", callback );
}

getData(function(data) {
   let markerlist = [];

   for (let i = 0; i< data.length; i++) {
      let location = new L.LatLng(data[i].siteLat, data[i].siteLon);
      let marker = new L.Marker(location, {
         icon: myIcon,
         title: 'thetitle' });

         markerlist.push(marker);
      }

      let myLayerGroup = L.layerGroup(markerlist) // create the layer
      map.addLayer(myLayerGroup); // add the layer to the map

      var overlays = {"layername":myLayerGroup};
      L.control.layers(baseLayers,overlays).addTo(map);

   });

I have tried to follow Need callback returns multiple values in nodejs , which looks similar, but with no success.

I tried:

function getData(callback) {
   let callbackString = {};
   $.getJSON("getData.php", callbackString.set1);
   $.getJSON("getOtherData.php", callbackString.set2);
   callback(null,callbackString);
}

getData(function(data) {
   let data1 = data.set1;
   let data2 = data.set2;
   let markerlist = [];

   for (let i = 0; i< data1.length; i++) {
      let location = new L.LatLng(data1[i].siteLat, data1[i].siteLon);
      let marker = new L.Marker(location, {
         icon: myIcon,
         title: 'thetitle' });

         markerlist.push(marker);
      }

      let myLayerGroup = L.layerGroup(markerlist) // create the layer
      map.addLayer(myLayerGroup); // add the layer to the map

      var overlays = {"layername":myLayerGroup};
      L.control.layers(baseLayers,overlays).addTo(map);

   });

which gave the error TypeError: null is not an object (evaluating 'data.set1')

I do not know where to start to have multiple versions of the getData and then access all the info in the data function.

1
  • $.getJSON("getData.php", callbackString.set1); ... set1 will be undefined, because you just created callbackString as an empty object! I think you've misunderstood the purpose of the second argument to getJSON ... that's data that is sent in the request Commented Sep 27, 2018 at 2:11

1 Answer 1

1

This code

let callbackString = {};
$.getJSON("getData.php", callbackString.set1);
$.getJSON("getOtherData.php", callbackString.set2);
callback(null,callbackString);

.set1 and .set2 will be undefined, because you just created callbackString as an empty object! I think you've misunderstood the purpose of the second argument to getJSON ... that's data that is sent in the request

You're also calling callback with the first argument as null - yet you're trying to use getData like

getData(function(data) { ...

therefore, data will always be null

Also, $.getJSON is asynchronous and your code does not wait for the request to complete - therefore you'd have no chance of accessing the results

Perhaps this will help

function getData(callback) {
   $.when($.getJSON("getData.php"), $.getJSON("getOtherData.php")).then(function(set1, set2) {
        callback({set1:set1, set2:set2});
   });
}

however, if you want proper error handling, then you may do something like

function getData(callback) {
   $.when($.getJSON("getData.php"), $.getJSON("getOtherData.php"))
   .then(function(set1, set2) {
        callback(null, {set1:set1, set2:set2});
   })
   .catch(function(err) {
       callback(err);
   });
}


getData(function(err, data) {
    if (err) {
        //handle error
    } else {
        let data1 = data.set1;
        let data2 = data.set2;
        let markerlist = [];
        ...
        ...
    }
});

Personally, because $.getJSON returns a Promise (well, jQuery's version of a promise), I'd be more likely to write the code like:

const getData = () => Promise.all([$.getJSON("getData.php"), $.getJSON("getOtherData.php")]);

getData()
.then(([data1, data2]) => { // note that data1, data2 are now the arguments to the function
    let markerlist = [];
    for (let i = 0; i< data1.length; i++) {
    ...
    ...
    }
})
.catch(err => {
    // handle errors here
});
Sign up to request clarification or add additional context in comments.

1 Comment

Thank you - I went with the Promise version at the bottom and it's worked for me. You are definitely right that I've misunderstood the second argument of getJSON -> I was following an example and since it worked I used it.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.