身份验证:“在填充metadataStore之前无法执行_executeQueryCore”

时间:2015-06-10 16:14:04

标签: angularjs breeze ionic

我正在尝试为使用Angular和Breeze构建的移动应用添加身份验证。

在我的app.js中:

app.config(function ($httpProvider) {
    $httpProvider.interceptors.push(intercept)
});

//intercept runs on every http request and response
//When there is a 401 error it uses broadcast to send an event to 
//the application scope
function intercept($rootScope) {
    return {
        request: function (config) {
            $rootScope.$broadcast('loading:show');
            return config;
        },
        response: function (response) {
            $rootScope.$broadcast('loading:hide');
            return response;
        },
        responseError: function (error) {
            if (error.status === 401) {
                $rootScope.$broadcast('error:401');
            }
            return error;
        }
    }
}

app.run(function ($rootScope, $ionicLoading, $state) {
    $rootScope.$on('loading:show', function () {
        $ionicLoading.show({ template: 'Loading...' });
    });

    $rootScope.$on('loading:hide', function () {
        $ionicLoading.hide();
    });

    //401 errors mean the user is not authenticated
    //display a login dialog
    $rootScope.$on('error:401', function () {
        $ionicModal
            .fromTemplateUrl("app/user/login.html", { focusFirstInput: true })
            .then(function (modal) {
                modal.show();
            });
    });
});

在我的dataContext.js中:

var properties = [];

function getProperties(refresh) {

    if (!refresh && properties.length > 0) {
        return common.$q.when(properties);
    }

    var query = EntityQuery
                .from('Properties')
                .select('ID, NameNumber, StreetName, ...etc')
                .orderBy('StreetName, NameNumber')
                .toType("Property")
                .using(manager)
                .execute()
                .then(querySucceeded, queryFailed);

    return query;

    function querySucceeded(data) {
        //set the properties held in memory
        properties = map(data.results);
        return properties;
    }

    function queryFailed(error) {
        console.log("Error while making http call: " + error.message);
        //return the properties held in memory
        return properties;
    }
}

逻辑是这样的:

  1. getProperties()名为

  2. EntityQuery触发了对http://.../breeze/breeze/Metadata

  3. 的请求
  4. 响应为401(用户未经过身份验证) - 正如预期的那样

  5. '错误:401'事件被广播和处理,并显示登录屏幕

  6. 这一切都运作得很好。

    现在,如果我取消登录对话框,然后刷新,再次触发getProperties,但这次我在queryFailed函数中报告了此错误:

      

    在填充metadataStore

    之前无法执行_executeQueryCore

    所以我猜Breeze知道以前打过电话,因此希望它在那里,即使它失败了401.我该怎么办才能解决这个问题?

1 个答案:

答案 0 :(得分:1)

在尝试了很多其他事情之后,我终于意识到我需要拒绝解决responseError。否则(我猜)Breeze认为MetaData调用成功,然后尝试访问它,然后在不成功时生成错误:

responseError: function (error) {
    if (error.status === 401) {
        $rootScope.$broadcast('error:401');
    }

    //return error; wrong!

    return $q.reject(error);
}