在Angular 2中解析Hal+JSON对象的信息

5

我有一个使用spring-data-rest创建的仓库,它会生成一个hal+json对象,我希望我的Angular 2前端可以接收并显示它。

Hal+Json对象:

{
  "_embedded" : {
    "users" : [ {
      "name" : "Bob",
      "_links" : {
        "self" : {
          "href" : "http://localhost:4200/api/users/1"
        },
        "user" : {
          "href" : "http://localhost:4200/api/users/1"
        }
      }
    }, {
      "name" : "Joe",
      "_links" : {
        "self" : {
          "href" : "http://localhost:4200/api/users/2"
        },
        "user" : {
          "href" : "http://localhost:4200/api/users/2"
        }
      }
    } ]
  },
  "_links" : {
    "self" : {
      "href" : "http://localhost:4200/api/users"
    },
    "profile" : {
      "href" : "http://localhost:4200/api/profile/users"
    },
    "search" : {
      "href" : "http://localhost:4200/api/users/search"
    }
  },
  "page" : {
    "size" : 20,
    "totalElements" : 2,
    "totalPages" : 1,
    "number" : 0
  }
}

我有一个服务,它向此API发送get请求。

user.service.ts:

import { Injectable } from '@angular/core';
import { Http, Response } from '@angular/http';
import { User } from './user.model';
import { Observable } from 'rxjs';
import 'rxjs/add/operator/map'

@Injectable()
export class UserService {

  constructor(private http: Http) {
  }

  findAllUsers(): Observable<Array<User>> {
    return this.http.get('/api/users')
      .map((response: Response) => response.json())
      .map((data: Array<User>) => {
        return data;
      });
  }
}

然后我的users.component从服务中调用findAllUsers方法。

users.component.ts

import { Component, OnInit } from '@angular/core';
import { User } from './user.model';
import { UserService } from './user.service';

@Component({
  selector: 'app-users',
  providers: [UserService],
  templateUrl: './users.component.html',
  styleUrls: ['./users.component.css']
})
export class UsersComponent implements OnInit {
  users: User[];

  constructor(private userService: UserService) {
  }

  ngOnInit(): void {
   this.userService.findAllUsers().subscribe((data: Array<User>) => {
     this.users = data;
   });
  }

}

最后,users.component.html 文件内容如下:
<h4>Users:</h4>

<div *ngFor="let user of users">
  {{user}}
</div>

在我的视图中,我遇到了一个错误,提示: Cannot find a differ supporting object '[object Object]' of type 'object'. NgFor only supports binding to Iterables such as Arrays. 我不确定该如何解决。
如果我在服务中返回data之前尝试使用调试器,则可以看到我的hal+json对象= data,并且我可以从data._embedded_users中获取所需的正确信息。但是这不能映射到User[],因为_embedded不是我的用户模型的属性。我需要先对Hal+Json对象进行某些处理吗?
1个回答

8

我需要先对Hal+Json对象做些什么吗?

这不显而易见吗?只需在服务中提取数据即可。

findAllUsers(): Observable<Array<User>> {
  return this.http.get('/api/users')
    .map((response: Response) => response.json())
    .map((data: any) => {
      return data._embedded.users as User[];
    });
}

你之前拥有的东西

.map((data: Array<User>) => {
  return data;
});

这是错误的做法,因为你假设第二个 map 中传递的数据是用户数组,但实际上它是整个 HAL 对象。将其更改为 any 可以使你从中提取用户。


您难道不需要从每个用户中删除“_links”吗? - Lamberto Basti
@LambertoBasti 你只需要将响应数据打印到控制台上。你可以看到整个结构。 - Paul Samsotha
我实际上需要将数据绑定到一个类,所以在 .map() 操作符中删除了 _links 字段。 - Lamberto Basti

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接