ResourceAssembler在响应_links中未返回正确的路径(创建的资源路径)

时间:2019-05-15 19:37:40

标签: spring-boot spring-data spring-data-rest spring-hateoas

我有一个控制器来管理用户的POST个工作。成功创建后,响应应包含创建的资源的链接。为此,我写了下面的ResourceAssembler

public class UserJobResourceAssembler implements ResourceAssembler<UserJob, Resource<UserJob>>  {

    private EntityLinks entityLinks;

    public UserJobResourceAssembler(EntityLinks entityLinks) {
        this.entityLinks = entityLinks;
    }

    @Override
    public Resource<UserJob> toResource(UserJob entity) {
        Resource<UserJob> resource = new Resource<>(entity);
        resource.add(
                entityLinks.linkToSingleResource(UserJob.class, entity.getId()).withSelfRel()
                );
        return resource;
    }

}

这是控制器

@RequestMapping(value = "/profiles" )
@ExposesResourceFor(UserJob.class)
public class UserJobController {

    private UserJobService userJobService;

    public UserJobController(UserJobService userJobService) {
        this.userJobService = userJobService;
    }

    @PostMapping(value = "/{uniqueId}/jobs")
    public Resource<UserJob> createJob(@Valid @RequestBody UserJob userJob, final Principal principal, @PathVariable String uniqueId) {

        return userJobService.save(userJob, principal.getName(), uniqueId);

    }

    @GetMapping(value = "/{uniqueId}" + JOBS + "/{jobId}")
    @ResponseStatus(value = HttpStatus.CREATED)
    public Resource<UserJob> getSingleJob(@PathVariable String uniqueId, @PathVariable String jobId) {
        System.out.println("get single job for job id: " + jobId);

        return new Resource<UserJob>(new UserJob());
    }

}

uniqueId是为其创建作业的用户的ID。 尽管ResourceAssembler创建了链接,但链接错误。

"_links": {
        "self": {
            "href": "http://localhost:8085/api/v1/profiles/12"
        }
  }

我期望它是http://localhost:8085/api/v1/profiles/theCoder/jobs/12

我知道这不是ResourceAssembler的问题,而是EntityLinks的问题。这可以通过使用linkTo而不是EntityLinks

来解决
resource.add(linkTo(methodOn(UserJobController.class).getSingleJob(entity.getUser().getUniqueId(), entity.getUserJobId().toString())).withSelfRel());

但是我想以DRY原理实现这一点,使用控制器类会使我将其设为DRY。

有哪些替代方案/解决方案?

1 个答案:

答案 0 :(得分:2)

在资源处理器中,您正在将自身链接设置为UserJob(在控制器中设置的/ profiles)的URL,并连接id,因此它变为“ / profiles / id”。

如果您需要设置指向方法URL的链接,ControllerLinkBuilder是避免对URL进行硬编码的最佳选择(如果使用EntityLink,则需要这样做):

@PostMapping(value = "/{uniqueId}/jobs")
public Resource<UserJob> createJob(@Valid @RequestBody UserJob userJob, final Principal principal, @PathVariable String uniqueId) {

    UserJob userJob = userJobService.save(userJob, principal.getName(), uniqueId);
    return toResource(userJob);

}

private Resource<UserJob> toResource(UserJob userJob) {
    Link selfLink = linkTo(methodOn(UserJobController.class)
        .getSingleJob(/* values */))
        .withSelfRel();

    return new Resource<>(userJob, selfLink);
}