Jerome
Jerome

Reputation: 1192

How to make 3 calls using Meteor promise

I want to avoid the Callbacks Hell so I founded the promise but I'm a bit stuck.

I need to make getAllDataSource -> createDashboard-> `sendDashboard``

So the code is :

var call = Promise.promisify(Meteor.call, Meteor);

var calls = call(getAllDataSource()).
            then(call.bind(Meteor, createDashboard())).
            then(call.bind(Meteor, sendDashboard()));

calls.then(function(resThree){
    console.log("Got Response!", resThree);
}).catch(function(err){
    console.log("Got Error", err); 
});

But I'm a bit lost with the first var callI think I need to change it but with what ? And then how this will know when getAllDataSourceis done ?

var allDataSources;
getAllDataSources = Meteor.bindEnvironment(function(){
    HTTP.call("GET", 'http://localhost:3000/api/datasources', {
            headers: {
                'Accept': 'application/json',
                'Content-Type': 'application/json',
                'Authorization': 'Bearer eyJrIjoic2RRbU9oM2Rkbmc0bHZUSjVlTjBPckRVNlplSW1DYzEiLCJuIjoibG9jYWxob3N0X2FkbWluX2tleSIsImlkIjoxfQ==',
            },
        },
        function(error, result) {
            if (!error) {
              allDataSources = result.data;
            } else {
                console.error(error);
            }
        });
});

var sendme;
createDashboard = Meteor.bindEnvironment(function(){
  for (var i = 0; i < 5; i++) {
    console.log("I have " + i + " apples in " + allDataSources);
    sendme = "hihihih";
  }
});

sendDashboard = Meteor.bindEnvironment(function(){
  for (var i = 0; i < 7; i++) {
    console.log("I have " + i + " cats with " + sendme);
  }
});

It automatically go to the method 2 when result is created ?

Thank you for the help

[EDIT] This actually give me that on the console:

Got Error { [Error: Method 'undefined' not found [404]]
I20170209-10:39:30.990(1)?   error: 404,
I20170209-10:39:30.991(1)?   reason: 'Method \'undefined\' not found',
I20170209-10:39:30.991(1)?   details: undefined,
I20170209-10:39:30.991(1)?   message: 'Method \'undefined\' not found [404]',
I20170209-10:39:30.991(1)?   errorType: 'Meteor.Error' }

[EDIT2] After followed the answer of @ymz I got this error:

Got Error { [Error: Method '[object Object],[object Object],[object Object],[object Object]' not found [404]]
I20170209-11:23:48.154(1)?   error: 404,
I20170209-11:23:48.154(1)?   reason: 'Method \'[object Object],[object Object],[object Object],[object Object]\' not found',
I20170209-11:23:48.154(1)?   details: undefined,
I20170209-11:23:48.154(1)?   message: 'Method \'[object Object],[object Object],[object Object],[object Object]\' not found [404]',
I20170209-11:23:48.154(1)?   errorType: 'Meteor.Error' }

And I think it comes from var calls = call(data).then .... // proceed from here because getAllDataSource() puts an array inside the data here. I need a bit more help please

Upvotes: 2

Views: 524

Answers (2)

Jerome
Jerome

Reputation: 1192

So after trying and trying I have made this code:

new Promise(function(resolve) {
  console.log("step1")
    // 1. first async task
    HTTP.call("GET", 'http://localhost:3000/api/datasources', {
            headers: {
                'Accept': 'application/json',
                'Content-Type': 'application/json',
                'Authorization': 'Bearer 123',
            },
        },
        function(error, result) {
            if (!error) {
              allDataSources = result.data;
              console.log("step1.5" + allDataSources)
              resolve(allDataSources);
            } else {
                console.error(error);
            }
        });

}).then(function(allDataSources) {
  console.log("step2")
    // 2. second async task
    return new Promise(function(resolve) {
      console.log("step 2.5" + resolve + allDataSources)
      for (var dataSource = 0; dataSource < allDataSources.length; dataSource++) {
         sendme = "sendme";
      }
      resolve(sendme);
    });

}).then(function(sendme) {
    // 3. now we can render the products after two async tasks are done
    console.log('Rending product ' + sendme);
});

I want to give a huge thank you to @ymz who helped me

Upvotes: 2

ymz
ymz

Reputation: 6924

This question is tricky because it failed due to 2 different factors

  1. wrong reference for Promise
  2. wrong approach while using async code

The complete fix:

First - use require to Bluebird Promise lib:

var Promise = require('bluebird');

Second - handle your async code with a callback

function whenDataArrive(data)
{
    if (!data) return;

    var calls = call(data).then .... // proceed from here
}

getAllDataSources = Meteor.bindEnvironment(function(id){
HTTP.call("GET", 'http://localhost:3000/api/datasources', {
        headers: {
            'Accept': 'application/json',
            'Content-Type': 'application/json',
            'Authorization': 'Bearer 123',
        },
    },
    function(error, result) {
        if (!error) {
          whenDataArrive(result.data);
        } else {
            console.error(error);
            whenDataArrive();
        }
    });

});

Upvotes: 0

Related Questions