spring-projects / spring-projects/spring-hateoas
Handling composite template variables in links and UriTemplate expansion
Nobody has claimed this yet.
- Dominant language
- Java
- Stars
- 1.1k
- Forks
- 476
- PR merge metrics
- No merged PRs in 30d
Description
I'm having some issues with building a link to a method where I think the template variable should be a composite parameter (i.e. {paramName*}).
I have a controller with a "search-like" method, which can take arbitrary key=[value] parameters, with the declaration:
@PostMapping("/{entityId}/populateFromSearch")
@Transactional
public ResponseEntity populateFromSearch(@PathVariable UUID entitytId, @RequestParam MultiValueMap<String, String> searchParameters)
I'm adding a link to this on my EntityModels, using the normal form: linkTo(methodOn(MyController.class).populateFromSearch(null, null).withRel("populateFromSearch")
This produces a URI template ending /populateFromSearch?searchParameters={searchParameters}. But this can't be expanded as a composite parameter by the UriTemplate class. Even if the parameterised part were correct ({searchParameters*}) the expansion leaves the original query parameter in place, i.e. ?searchParameters=&foo=qux&baz=buz.
My other approach is to manually set up the Link from a UriTemplate and manually add a TemplateVariable:
resource.add(Link.of(
UriTemplate.of(linkTo(DataBasketRepositoryExtension.class).slash(entityId).slash("populateFromSearch")
.toUriComponentsBuilder().build().toUriString(),
new TemplateVariables(TemplateVariable.compositeParameter("searchParameters"))),
"populateFromSearch"
));
This produces a 'working' URI (ending with /inputSearch{*searchParameters}) but this brings me to the second issue: there's an incompatibility between TemplateVariable.compositeParameter("foo") and uriTemplate.expand.
The TemplateVariable is rendered {*paramName} (ref), while the expansion expects the composite marker to be at the end of the parameter (i.e. {paramName*} (ref).
This is a bit frustrating, but can be worked around using the manual link approach - I can just append the {searchParameters*} string manually when building the UriTemplate.
Contributor guide
No contributing guide indexed for this repository
First steps
- Read the whole issue, then the project's contributing guide.
- Comment on the issue to say you are picking it up — it saves two people doing the same work.
- Fork the repository and make your change on a branch.
- Open a pull request that references the issue number.
Research direction
Start with TemplateVariable.java around compositeParameter and UriTemplate.java around the expansion logic referenced in the issue. Reproduce the link-generation and expansion examples for searchParameters, then inspect how composite query variables are rendered and parsed. Done means the two paths agree on composite-variable syntax and the resulting URI expands without retaining an incorrect placeholder.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- java, spring
- Domain
- api
- Issue type
- Bug
- Difficulty
- 3/5
- Estimated time
- 1-2 days
- Activity status
- Stale
- Clarity
- Mostly clear
- Newbie friendliness
- 45/100