9

我有一个$resource其 API 将始终返回一些需要在进入表示层之前清理的数据。具体来说,它是 .NET 以可爱的'/Date(...)/'格式返回 Date 对象。

我不想每次打电话.query().get(). 是否有某种方法可以通过在更新实例属性的 REST 方法上调用的回调来扩展资源,或者通过添加某种$watch在日期属性更改时触发的回调?基本上每个 this 实例都会发生一些事情$resource

angular.module('myAppServices', ['ngResource'])
    .factory('Participant', ['$resource', function ($resource) {
        var res = $resource('api/url/participants/:id', { id: '@id' });

        // This obviously doesn't work, but something kinda like this?
        res.prototype.$watch(this.FieldName, function(newVal, oldVal) {
            if (needsCleaning(newVal.fieldName) {
                this.FieldName = cleanupField(newVal);
            }
        };
    });
4

3 回答 3

12

啊哈,我找到了解决方法,并将其留在这里。在 1.1.2 版本中,他们添加了对将所有$http.config选项传递给$resource. 当然,我使用的 CDN 没有足够新的 angular-resource.js 版本,但切换 CDN 解决了​​这个问题。

我只是使用该transformResponse选项在数据返回时对其进行修改。

angular.module('myAppServices', ['ngResource'])
    .factory('Participant', ['$resource', '$http', function ($resource, $http) {
        var res = $resource('api/url/participants/:id', { id: '@id' }, {
        save: {
            method: 'POST',
            transformResponse: $http.defaults.transformResponse.concat([
                function (data, headersGetter) {
                    data.FieldName = yourDateParsingFunction(data.FieldName);

                    return data;
                }
            ])
        }
    });

我只是将我$httpProvider的转换器添加到 transformResponse 中,它将完成所有的反序列化等。

于 2013-04-05T20:08:03.367 回答
8

一种简单的方法是用自己的方法覆盖$resource您想要进行后处理的现有方法。有关示例,请参见下面的代码和注释。

angular.module('myAppServices', ['ngResource'])
    .factory('Participant', ['$resource', function ($resource) {
        var res = $resource('api/url/participants/:id', { id: '@id' }, {
            // create aliases for query and get to be used later
            _query: { method: 'GET', isArray: true },
            _get:   { method: 'GET' }
        });

        // redefine the query method
        res.query = function() {
            // call the original query method via the _query alias, chaining $then to facilitate
            // processing the data
            res._query.apply(null, arguments).$then(function(res) {
                var data = res.data;
                // do any processing you need to do with data here
                return data;
            });
        };

        // redefine the  method
        res.get = function() {
            // call the original get method via the _get alias, chaining $then to facilitate
            // processing the data
            res._get.apply(null, arguments).$then(function(res) {
                var data = res.data;
                // do any processing you need to do with data here
                return data;
            });
        };

        return res;
    });

您可以像当前Participant在代码中使用它一样使用它,通过Participant.query()Participant.get()。您在链接的 $then 处理程序中返回的数据将用于解决$resource.

于 2013-04-05T20:00:12.013 回答
0

我这样做的方法是向模块添加服务:

angular.module('keeniolab', ['ngResource']).
factory('KeenIO',function ($resource) {
    // factory implementation
}).service('KeenModel', function (KeenIO) {
    var KeenSession = function () {
        this.data = {};
    };

    KeenSession.prototype.fetch = function (query) {
        var self = this;

        KeenIO.get(query, function (result) {
            self.data = result;
        });
    };

    return new KeenSession();
});

现在您可以简单地监视集合:

$scope.$watchCollection(function () {
    return KeenModel.data;
},
function (value) {
    // code here
});

具有服务模型的 Keen.IO 资源工厂

于 2013-06-06T12:47:59.267 回答