我有两个应用程序,一个名为 bar ,它为我提供了HAL格式的资源。另一个是 bcm 来使用该服务。
回复示例 bar 如下所示:
[
{
"name":"Brenner/in",
"_links":{
"self":{
"href":"..host/bbsng-app-rest/betrieb/15"
}
}
},
{
"name":"Dienstleistungshelfer/in HW",
"_links":{
"self":{
"href":"..host/bbsng-app-rest/betrieb/4"
}
}
},
{
...
现在我尝试使用Spring RestTemplate从 bcm 中消费它。我的解决方案有效,但我不满意这个解决方案,我想有一个更干净的方式。
我的客户端代码消耗RestService看起来像:
@Autowired private RestTemplate template;
@Override
@SuppressWarnings("unchecked")
public BerufListe findeAlleBerufe() {
final BerufListe berufListe = new BerufListe();
final ResponseEntity<List> entity = template.getForEntity(LinkUtils.findBeruf(), List.class);
if (OK.equals(entity.getStatusCode())) {
final List<LinkedHashMap> body = entity.getBody();
for (final LinkedHashMap map : body) {
final LinkedHashMap idMap = (LinkedHashMap) map.get("_links");
String id = remove(String.valueOf(idMap.get("self")), "href=");
id = remove(id, "{");
id = remove(id, "}");
final String name = String.valueOf(map.get("name"));
final Beruf beruf = new Beruf(id, name);
berufListe.add(beruf);
}
}
return berufListe;
}
你看到的代码很难看。其中之一是,我的收藏品没有任何泛型。另一点,我得到的Resource_ID非常复杂,我多次使用StringUtils.remove来提取自己的URL。
我确信必须有一种更方便的方法来消耗Spring的HAL-Response。
谢谢你。
答案 0 :(得分:3)
看一下spring-hateaos的Resource课程。
它提供了从响应中提取链接的方法。 但是,由于RestTemplate要求您将类作为变量提供,除了创建所需实体的子类并将其用于RestTemplate之外,我没有找到不同的方法。
您的代码可能如下所示:
public class BerufResource extends Resource<Beruf> { }
BerufResource resource = template.getForEntity("http://example.at/berufe/1", BerufResource.class);
Beruf beruf = resource.getContent();
// do something with the entity
如果要请求完整列表,则需要将实体的数组版本传递给RestTemplate:
BerufResource[] resources = template.getForEntity("http://example.at/berufe", BerufResource[].class);
List<BerufResource> berufResources = Arrays.asList(resources);
for(BerufResource resource : berufResources) {
Beruf beruf = resource.getContent();
}
不幸的是,我们不能编写Resource<Beruf>.class
来破坏泛型类的整个目的,因为我们需要再次为每个实体创建一个子类。其背后的原因称为类型擦除。我曾在某处读到他们计划为RestTemplate引入通用支持,但我不知道任何细节。
解决从网址中提取id的问题:
我建议在客户端使用不同的模型,并用字符串替换id字段的类型,并将整个url存储在其中。这样,您可以随时轻松地重新获取整个实体,而不需要自己构建URL。如果您计划向API提交POST请求,则无论如何您都需要URL,因为spring-hateaos要求您发送链接而不是ID。 典型的POST请求可能如下所示:
{
"firstname": "Thomas",
"nachname": "Maier",
"profession": "http://example.at/professions/1"
}