【问题标题】:Nodejs and express routing, how to handle client side promisesNodejs 和 express 路由,如何处理客户端的 Promise
【发布时间】:2016-09-10 14:26:14
【问题描述】:

我正在尝试对 mongodb 来回执行单个路由,但似乎在客户端我无法从从 $resource 收到的承诺中检索数据。 在 HTML 页面上,有一个 ng-click 到以下功能的按钮:

$scope.getToken = function() {
    console.log('$scope.getToken()');
    authenticationService.getToken($scope.data.email).then(function(result) {
        $scope.data.token = result;
    });
}

收到的结果是:

对象“m”,具有字段 - 0:“j”,1:“6”,2:“o”,3:“p”,4:“E”,5:“7”,6:“ X", 7: "t", $promise: d, $resolved: true, proto: Object

如您所见,我收到生成的令牌,数据库似乎工作正常,函数调用也正常。

接收应答的客户端服务有一个功能:

    function getToken(userEmail) {
    var deferred = $q.defer();
    $resource(baseUrl + '/getToken').save({
        email : userEmail
    }, function(result, error) {
        if(result) {
            deferred.resolve(result);
        }
        else {
            deferred.reject(error);
        }
    });
    return deferred.promise;
}

发送此消息的服务器端函数:

var router = require('express').Router();
var authenticator = require('../utils/authUtils');
router.post('/getToken', function(request, response) {
authenticator.getToken(
    function(error, result) {
        if(error) {
            //handle error
        }
        else if(result) {
            response.json(result);
        }
    }
);

在 authUtils.js 中:

var mongoUtils = require('./mongoUtils');
getToken : function(callback) {
    var genToken = randToken.generate(8);
    mongoUtils.query(COLLECTIONS.TOKENS, {'token': { $eq: genToken } },
        function(error, result) {
            if((result && result.length) || error) {
                //handle error or duplicates
            }
            else if(result) {
                callback(null, genToken);
            }
        }
    );
}

在 mongoUtils 中:

query : function(collectionName, query, callback) {
    _db.collection(collectionName).find(query).toArray(function (error, result) {
        console.log('Utils.query');
        if(error) {
            //handle error
        }
        else {
            callback(error, result);
        }
    });
}

为什么服务器端会在一个对象中连同 promise 一起发送答案,我应该如何处理?

【问题讨论】:

    标签: javascript angularjs node.js mongodb express


    【解决方案1】:

    它作为索引对象返回的原因是 toArray 在:

     _db.collection(collectionName).find(query).toArray(function... 
    

    一种可能的解决方案是不在字符串上使用toArray,或者在发回结果之前调用slice

    response.status(200).json({token: Array.prototype.slice.call(result)})
    

    我可能无法完全理解您的问题的另一种可能性是尝试:

    authenticationService.getToken($scope.data.email).$promise.then(...)
    

    如果它是一个 ngResource,我已经通过 $promise 访问了 then,只是一个想法。

    【讨论】:

    • 非常感谢!将对象从服务器端发送回客户端会导致收到响应的字段!
    【解决方案2】:

    所以你的问题有 3 个部分,为什么是一个对象,为什么要承诺以及如何处理它。

    1:为什么在对象内部?

    根据Angular官方$resource页面$resource当你使用$resource返回的资源总是object,同样在你的API(服务器端)你将响应作为json object 所以你显然会得到对象。

    else if(result)
    {
        response.json(result);
    }
    

    2:为什么要承诺?

    $resource$http 都返回一个承诺,REST 是 HTTP 的一个子集。这意味着可以通过 REST 完成的所有事情都可以通过 HTTP 完成,但并非所有可以通过 HTTP 完成的事情都可以通过 REST 完成。这就是 $resource 在内部使用 $http 的原因。 $resource 建立在 $http 之上。所以$promise 是肯定的。供参考Why Promise

    3:如何处理

    我不确定“如何处理它”是什么意思,因为您已经有了对象,我假设您打算分离实际生成的令牌数据对象并保留其他所有内容,如果是这样的话可以简单地将结果对象中的数据分配给您的$scope

    你正在做的是将整个对象分配给$scope,它包含所有其他对象

     $scope.data.token = result;
    

    您只需将生成的令牌分配给$scope.data.token 例如:

    $scope.data.token = result.genToken;
    

    希望这能回答这个问题。

    【讨论】:

      猜你喜欢
      • 2018-02-25
      • 1970-01-01
      • 2021-02-19
      • 1970-01-01
      • 2021-02-23
      • 2018-06-18
      • 1970-01-01
      • 2016-10-06
      • 1970-01-01
      相关资源
      最近更新 更多