2016-05-13 3 views
0

В весна-Web RestController мы используем PagedResources для создания ResponseEntities. У нас есть RequestMethod, который инициирует поиск фона для Elements в радиусе 5 км, если результат не достигнет 10 км, 20 км, пока мы не найдем какой-либо элемент.Как продлить PagedResourceAssembler

Поскольку мы теперь изменяем заданные параметры от Клиента (ресурс вызывается с заданным расстоянием), мы хотим вернуть измененное SearchDistance обратно клиенту. Фактический ответ, то будет что-то вроде этого:

{ 
    "_links": { 
    "self": { 
     "href": "http://... 
     "templated": true 
    } 
    }, 
    "_embedded": { 
    "parcelShopResourceList": [ 
     { 
     "_id": "2760183530" 
     ... 
     }, 
     { 
     "_id": "2760128505" 
     ... 
     }, 
     { 
     "_id": "2760162267" 
     ... 
     }, 
     { 
     "_id": "2760196914" 
     ... 
     }, 
     { 
     "_id": "2760147255" 
     ... 
     } 
    ] 
    }, 
    "page": { 
    "size": 200, 
    "totalElements": 5, 
    "totalPages": 1, 
    "number": 0 
    "searchDistance": 10 
    } 
} 

Теперь вопрос:

  • Как я могу продлить PagedResourcesAssembler, поэтому он будет возвращать дополнительную информацию страницу?

Я думал, что это было бы достаточно, чтобы создать расширенный Page, поэтому PagedResourcesAssembler добавит дополнительную информацию на странице информации, но это было не так.

ResponseEntity.ok(pagedResourcesAssembler.toResource(page, resourceAssembler));

Затем я попытался, чтобы переопределить PagedResourcesAssembler себя, но так как он использует много частных методов Переопределить из PagedResourcesAssembler.createResource не очень полезно.

Я думаю, что я чего-то не хватает. Может ли кто-нибудь объяснить мне, как я могу добавить дополнительную информацию в свой ответ? Я уверен, что для этого есть намного более простой способ.

Поскольку я хочу добавить информацию, касающуюся всего списка, я не хочу вставлять эту информацию в один ресурс только для удобства.

ответ

0

Действительно, способ создать собственный ресурс страницы и настроить свой объект по своему желанию. Сюда относятся контент для рендеринга и метаданные, такие как расстояние поиска, размер и т. Д.

Вот Exemple:

/** 
* 
* Pagination for a resource content 
* 
* @param <T> content to render 
*/ 
public class PagedResource<T> { 
    private List<T> content; 
    private final Map metadata; 
    public PagedResource(Page<T> page, String pageParam, String sizeParam, String sortParam, String sortField) { 
    super(); 
    this.setContent(page.getContent()); 
    this.metadata = new HashMap(); 
    List<Link> links = new ArrayList<Link>(); 
    if (page.hasPrevious()) { 
     String path = createBuilder().queryParam(pageParam, page.getNumber() - 1).queryParam(sizeParam, page.getSize()).queryParam(sortParam, sortField).build().toUriString(); 
     Link previousPageLink = new Link(path, Link.REL_PREVIOUS); 
     links.add(previousPageLink); 
    } 
    if (page.hasNext()) { 
     String path = createBuilder().queryParam(pageParam, page.getNumber() + 1).queryParam(sizeParam, page.getSize()).queryParam(sortParam, sortField).build().toUriString(); 
     Link nextPageLink = new Link(path, Link.REL_NEXT); 
     links.add(nextPageLink); 
    } 
    if (!page.isFirst()) { 
     Link firstPageLink = buildPageLink(pageParam, 0, sizeParam, page.getSize(), sortParam, sortField, Link.REL_FIRST); 
     links.add(firstPageLink); 
    } 
    if (!page.isLast()) { 
     int lastPage = page.getTotalPages() - 1; 
     Link lastPageLink = buildPageLink(pageParam, lastPage, sizeParam, page.getSize(), sortParam, sortField, Link.REL_LAST); 
     links.add(lastPageLink); 
    } 
    Link currentPagelink = buildPageLink(pageParam, page.getNumber(), sizeParam, page.getSize(), sortParam, sortField, Link.REL_SELF); 
    links.add(currentPagelink); 
    populateMetadata(page, links); 
    } 
    private void populateMetadata(Page<T> page, List<Link> links) { 
    int per_page = page.getSize(); 
    int totalPages = page.getTotalPages(); 
    int numberOfPageElements = page.getNumberOfElements(); 
    metadata.put("numberOfPageElements", numberOfPageElements); 
    metadata.put("perPage", per_page); 
    metadata.put("totalPages", totalPages); 
    metadata.put("links", links); 
    } 
    private Link buildPageLink(String pageParam, int page, String sizeParam, int size, String sortParam, String sortAttribute, String rel) { 
    String path = createBuilder().queryParam(pageParam, page).queryParam(sizeParam, size).queryParam(sortParam, sortAttribute).toUriString(); 
    Link link = new Link(path, rel); 
    return link; 
    } 
    private ServletUriComponentsBuilder createBuilder() { 
    return ServletUriComponentsBuilder.fromCurrentRequestUri(); 
    } 
    public List<T> getContent() { 
    return content; 
    } 
    public void setContent(List<T> content) { 
    this.content = content; 
    } 
    public Map getMetadata() { 
    return metadata; 
    } 
} 

Вы можете найти ниже полный example о том, как использовать пользовательские страничный ресурсы.

0

Спасибо за пример Хассама, но я был более или менее связан с существующей структурой ответа, предоставляемой ненавистью!

Фактически я решил проблему, создав оболочку в RestController, которая создает новый ответ и добавляет необходимую информацию вокруг ответа, созданного PagedResourcesAssembler.