简体   繁体   English

当集合服务返回字典而不是数组时,如何使用Restangular?

[英]How to use Restangular when the service for a collection returns a dictionary instead of an array?

I'm in the early phases of the development of a client app to an existing REST service and I'm trying to decide what to use for server communication. 我正处于开发客户端应用程序到现有REST服务的早期阶段,我正在尝试决定使用什么来进行服务器通信。 So far I'm loving Restangular documentation, it seems really solid, but I'm worried it's not going to work with the service because the responses look something like this: 到目前为止,我喜欢Restangular文档,它看起来非常可靠,但我担心它不能与服务一起使用,因为响应看起来像这样:

{
  "0": {
    "name": "John",
    "total": 230,
    "score": 13
  },
  "1": {
    "name": "Sally",
    "total": 190,
    "score": 12
  },
  "2": {
    "name": "Harry",
    "total": 3,
    "score": 0
  },
  "...": "..."
}

I can't find in the docs if something like this is supported or how am I supposed to handle this type of response. 我在文档中找不到支持这样的东西或者我应该如何处理这种类型的响应。 Has anyone tried? 有人试过吗? Any ideas? 有任何想法吗?

I'm the creator of Restangular :). 我是Restangular :)的创造者。

You can use that response with Restangular. 您可以将该响应与Restangular一起使用。 You need to use the responseInterceptor. 您需要使用responseInterceptor。 I guess that your response looks like that when you're getting an array. 我想当你得到一个阵列时,你的回答看起来就像那样。 So you need to do: 所以你需要这样做:

RestangularProvider.setListTypeIsArray(false)
RestangularProvider.setResponseExtractor(function(response, operation) {
  // Only for lists
  if (operation === 'getList') {
    // Gets all the values of the property and created an array from them
    return _.values(response)
  }
  return response;
});

With this, it's going to work :) 有了它,它会工作:)

Please let me know if this worked out fr you 请告诉我你是否能解决这个问题

You could do this if if you attached a "then" statement to the promise that you return. 如果您将“then”语句附加到您返回的承诺上,则可以执行此操作。 That is, instead of this: 也就是说,而不是这个:

return <RectangularPromise>;

you have this: 你有这个:

return <RectangularPromise>.then(function(response){return _.values(response);};

Essentially, it's the same as @mgonto's answer, but doing it this way means that you don't have to modify your whole Rectangular Service if you only need to do this for one endpoint. 本质上,它与@ mgonto的答案相同,但这样做意味着如果您只需要为一个端点执行此操作,则无需修改整个矩形服务。 (Although, another way to avoid this is to create multiple instances of the service as outlined in the readme). (尽管另一种避免这种情况的方法是创建服务的多个实例,如自述文件中所述)。

遗憾的是listTypeIsArray没有在自述文件中描述,所以我没有尝试过这个选项,但我解决了类似的问题,如https://github.com/mgonto/restangular/issues/100#issuecomment-24649851

RestangularProvider.setListTypeIsArray() has been deprecated. RestangularProvider.setListTypeIsArray()已被弃用。

If you are expecting an object then handle it within addResponseInterceptor 如果您期望一个对象,则在addResponseInterceptor中处理它

app.config(function(RestangularProvider) {

// add a response interceptor
RestangularProvider.addResponseInterceptor(function(data, operation, what, url, response, deferred) {
  var extractedData;
  // .. to look for getList operations
  if (operation === "getList") {
    // .. and handle the data and meta data
    extractedData = data.data.data;
    extractedData.meta = data.data.meta;
  } else {
    extractedData = data.data;
  }
  return extractedData;
});     });

If you are expecting string response then convert it to array. 如果您期望字符串响应,则将其转换为数组。

  app.config(function(RestangularProvider) {
RestangularProvider.addResponseInterceptor(function(data, operation, what, url, response, deferred) {
  var newData = data;
  if (angular.isString(data)) {
      newData = [data]; //covert string to array
    }
    return newData;
});  });

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM