函数异步问题中的Javascript esriRequest(dojo)

时间:2015-09-04 12:07:25

标签: javascript asynchronous dojo gis esri

我面临以下同步问题。如果它有一个简单的解决方案/解决方法,我不会感到惊讶。 BuildMenu()函数从另一个代码块调用,它调用CreateMenuData(),它向返回一些数据的服务发出请求。问题是,因为它是在使用数据变量时对服务的异步调用,所以它是未定义的。我提供了js日志,也显示了我的观点。

        BuildMenu: function () {
            console.log("before call");
            var data=this.CreateMenuData();
            console.log("after call");
            //Doing more stuff with data that fail.
        }


CreateMenuData: function () {
        console.log("func starts");
        data = [];
        dojo.forEach(config.layerlist, function (collection, colindex) {

            var layersRequest = esriRequest({
                url: collection.url,
                handleAs: "json",
            });

            layersRequest.then(
                function (response) {
                    dojo.forEach(response.records, function (value, key) {
                        console.log(key);
                        data.push(key);


                    });

                }, function (error) {

                });

        });
        console.log("func ends");
        return data;
    }

   Console log writes:
   before call
   func starts
   func ends
   after call
   0
   1
   2
   3
   4

1 个答案:

答案 0 :(得分:0)

仅供参考:使用任何东西"道场。"已弃用。确保在#34;要求"中拉出所需的所有模块。

Ken指出了正确的方向,浏览链接并熟悉异步请求。

但是,我想指出你不是只处理一个异步请求,但可能会有更多的异步请求你正在尝试填充数据"用。为了确保只在所有请求完成后才处理结果,您应该使用" dojo / promise / all"。

CreateMenuData: function (callback) {
        console.log("func starts");
        requests = [];
        data = [];
        var scope = this;

        require(["dojo/_base/lang", "dojo/base/array", "dojo/promise/all"], function(lang, array, all){
            array.forEach(config.layerlist, function (collection, colindex) {
                var promise = esriRequest({
                    url: collection.url,
                    handleAs: "json",
                });
                requests.push(promise);
            });

            // Now use the dojo/promise/all object
            all(requests).then(function(responses){
                // Check for all the responses and add whatever you need to the data object.
                ...
                // once it's all done, apply the callback. watch the scope! 
                if (typeof callback == "function")
                    callback.apply(scope, data);

            });
        });        
    }

所以现在你准备好了这个方法,把它叫做

BuildMenu: function () {
    console.log("before call");

    var dataCallback = function(data){
        // do whatever you need to do with the data or call other function that handles them.       
    }

    this.CreateMenuData(dataCallback);  
}