【问题标题】:Getting [object Object] while mapping http response in Angular 2在Angular 2中映射http响应时获取[object Object]
【发布时间】:2017-07-14 15:51:18
【问题描述】:

在角度 2 中使用 Observable 地图时,我得到了一个 [object Object]。

这是来自 API 服务的响应对象。

{
  "isSuccess": true,
  "message": "Connection Successfull",
  "data": [
    {
      "marketId": 1,
      "city": "san",
      "cityF": "san",
      "name": null,
      "nameF": "hello",
      "sortOrder": 1,
      "isActive": true
    },
    {
      "marketId": 2,
      "city": "san",
      "cityF": "san",
      "name": null,
      "nameF": "hello",
      "sortOrder": 1,
      "isActive": true
    },
    {
      "marketId": 3,
      "city": "san",
      "cityF": "san",
      "name": null,
      "nameF": "hello",
      "sortOrder": 1,
      "isActive": true
    },
    {
      "marketId": 4,
      "city": "san",
      "cityF": "san",
      "name": null,
      "nameF": "hello",
      "sortOrder": 1,
      "isActive": true
    }
  ],
  "exceptionErrorMessage": null,
  "errorCode": 0,
  "successMessage": null
}

这是我创建的用于映射响应的模型。

export class MarketViewModel 
{
public isSuccess: boolean;
public message : string;
public successMessage : string;
public exceptionErrorMessage : string;
public errorCode: number;
public data: MarketListObject[];

}
export class MarketListObject 
{
    public marketId : number;
    public city: string;
    public cityF : string;
    public name : string;
    public nameF : string;
    public sortOrder : number;
    public isActive : boolean; 
}

调用 http 并映射响应的服务类。

import { Headers, RequestOptions } from '@angular/http';
import { Router, ActivatedRoute, Params } from '@angular/router';
import { MarketViewModel} from "../ViewModel/Market.ViewModel";
import { Injectable }     from '@angular/core';
import { Http, Response } from '@angular/http';
import {Observable} from 'rxjs/Rx';
import 'rxjs/add/operator/map';
import 'rxjs/add/operator/catch';

@Injectable()
export class DashBoardService {
    private MarketUrl = "DashBoard/GetMarketList";
    private ResponseData: any;
    constructor(private http: Http, private router: Router, private  marketModel : MarketViewModel) {}

    public GetMarketListCall() :Observable<MarketViewModel> {
         return this.http.get(this.MarketUrl).map(this.extractData)
                    .catch(this.handleError);
    } 
private extractData(res: Response) {
    let body = res.json();
        console.log("Body Data = "+body.data);
    return body.data || { };
  }

这是调用 Service.ts 的 Component.ts

import { Component } from '@angular/core';
import { MarketViewModel} from "../ViewModel/Market.ViewModel";
import { DashBoardService} from "../Service/DashBoard.Service";
import { Observable } from 'rxjs/Observable';

 @Component({
     selector: 'Market-app',
    templateUrl: 'DashBoard/MarketListView',
    providers: [DashBoardService, MarketViewModel]
 })

export class MarketComponent {
  constructor(private DashBoardservice: DashBoardService, private  marketModel : MarketViewModel) {
   }

ngOnInit() {
        this.DashBoardservice.GetMarketListCall().subscribe(
                               data => {this.marketModel = data;
                                    console.log("this"+this.marketModel); }, 
                                err => {console.log(err);});
}
}

当我看到控制台时,我得到 [object Object] 响应。我想不通的错误在哪里

【问题讨论】:

  • 您在此处将对象附加到字符串 - console.log("Body Data = "+body.data); ... 试试这个 - console.log("Body Data = ", body.data);"this"+this.marketModel) 也是一样

标签: angular typescript asp.net-core angular-services


【解决方案1】:

您的extractData 有问题,您希望响应保持原样,以匹配您的MarketViewModel,因此您需要从该方法中删除data,如果有,还需要返回一个空对象没有回应:

private extractData(res: Response) {
  let body = res.json();
  return body || {};
}

一些提示:

  • 在您的 Service 和 MarketComponent 中,您不需要注入 MarketViewModel 在您的构造函数中。
  • 你需要在你的组件中声明一个变量marketModel, 可以使用this.marketModel
  • 在组件中你声明了方法ngOnInit,但没有在你的组件中实现它

在测试您的应用时,它工作正常:

getMarketListCall(): Observable<MarketViewModel>{
    return this.http.get('theUrl')
        .map(res => res.json()) // or use the 'extractData'
        // .catch(this.handleError);
}

你的组件:

marketmodel: MarketViewModel

ngOnInit() {
    this.DashBoarservice.GetMarketListCall()
       .subscribe(data => {
          this.marketModel = data;
        },
        err => { console.log(err); 
    });
}

您的观点,您应该将 html 包装在 if 语句中,因为您的数据是异步检索的:

例如:

<div *ngIf="marketModel"> <!-- Here! -->
  <h2>MarketModel Message: {{marketModel.message}}</h2>
  <div *ngFor="let data of marketModel.data">Id: {{data.marketId}} </div>
</div><br>

我们需要记住,尽管这段代码运行良好,但我们实际上并没有将响应转换为您的类的实例。如果您想这样做,我建议使用以下链接并提供一些很好的答案:) How do I cast a JSON object to a typescript class

【讨论】:

  • 我收到一个错误...无法解析 MarketViewModel 的所有参数:(?, ?, ?, ?, ?, ?)。
  • 嗯,奇怪,非常适合我。您在什么时候收到错误消息?
  • 不要使用类来定义这些类型。使用接口。
【解决方案2】:

您必须更改您的DashBoardService 如下,因为您必须将MarketListObject 数组作为可观察的而不是MarketViewModel 返回:

@Injectable()
export class DashBoardService {
  private MarketUrl = "DashBoard/GetMarketList";
  private ResponseData: any;

  constructor(private http: Http, private router: Router, private  marketModel : MarketViewModel) {}

  public GetMarketListCall() :Observable<MarketListObject[]> {
     return this.http.get(this.MarketUrl).map(this.extractData)
                .catch(this.handleError);
  } 

  private extractData(res: Response) {
    let body = res.json();
    console.log("Body Data = "+body.data);
    return body.data || [];
  }
}

此外,也无需将MarketViewModel 作为MarketComponent 中的提供者传递,因此请从MarketComponent 提供者列表中删除MarketViewModel 并更改您的组件,如下所示。

import { Component } from '@angular/core';
import { DashBoardService} from "../Service/DashBoard.Service";
import { Observable } from 'rxjs/Observable';

@Component({
  selector: 'Market-app',
  templateUrl: 'DashBoard/MarketListView',
  providers: [DashBoardService]
})
export class MarketComponent {

  public marketList: any[];

  constructor(private dashBoardservice: DashBoardService) {
  }

  ngOnInit() {
    this.dashBoardservice.GetMarketListCall().subscribe((data) => { 
      this.marketList = data;
      console.log("this" + this.marketList);
    },(err) => {
      console.log(err);
    });
  }
}

【讨论】:

  • 它对我不起作用..我得到 [object Object],[object Object],[object Object],[object Object]
  • extractData 函数内部还是在MarketComponentngOnInit 内部?还可以通过从 GetMarketListCall 函数返回类型中删除 :Observable&lt;MarketListObject[]&gt; 来检查。
  • 如果我在服务中使用订阅,那么一切正常。当我使用地图时,我得到了一个对象。是的,我检查了 ngOnInit。我仍然得到对象
  • 我在我的回答中更新了组件。组件内部marketList 变量应该是MarketListObject 的数组,例如public marketList: MarketListObject[],因此如果需要,请导入它并更改它,否则any[] 也可以工作。
  • 您能否让我知道如何将类映射为来自 web api 类的响应。我不想要直接数组。我想用对象映射
猜你喜欢
  • 2020-11-17
  • 2020-02-05
  • 2018-05-16
  • 2017-08-09
  • 1970-01-01
  • 1970-01-01
  • 2018-10-19
  • 2019-06-05
  • 2016-06-05
相关资源
最近更新 更多