Skip to content

Commit d536ca9

Browse files
dsyeradriancole
authored andcommitted
Add support for expansion of @param lists (OpenFeign#403)
* Add support for expansion of @param lists The existing support for expanders in method parameters is limited to converting a single value. The change applies the expander individually to each item in a collection or array, thus making it useful for multi-valued query parameters, for instance. The old behaviour is preserved because no existing expanders would have been converting collections to strings (probably). * Change Collection to Iterable and add tests * Add test for null conversion to empty string as well * Remove array handling and null handling
1 parent 1c47154 commit d536ca9

File tree

2 files changed

+48
-1
lines changed

2 files changed

+48
-1
lines changed

core/src/main/java/feign/ReflectiveFeign.java

Lines changed: 18 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -202,7 +202,7 @@ public RequestTemplate create(Object[] argv) {
202202
Object value = argv[entry.getKey()];
203203
if (value != null) { // Null values are skipped.
204204
if (indexToExpander.containsKey(i)) {
205-
value = indexToExpander.get(i).expand(value);
205+
value = expandElements(indexToExpander.get(i), value);
206206
}
207207
for (String name : entry.getValue()) {
208208
varBuilder.put(name, value);
@@ -224,6 +224,23 @@ public RequestTemplate create(Object[] argv) {
224224
return template;
225225
}
226226

227+
private Object expandElements(Expander expander, Object value) {
228+
if (value instanceof Iterable) {
229+
return expandIterable(expander, (Iterable) value);
230+
}
231+
return expander.expand(value);
232+
}
233+
234+
private List<String> expandIterable(Expander expander, Iterable value) {
235+
List<String> values = new ArrayList<String>();
236+
for (Object element : (Iterable) value) {
237+
if (element!=null) {
238+
values.add(expander.expand(element));
239+
}
240+
}
241+
return values;
242+
}
243+
227244
@SuppressWarnings("unchecked")
228245
private RequestTemplate addHeaderMapHeaders(Object[] argv, RequestTemplate mutable) {
229246
Map<Object, Object> headerMap = (Map<Object, Object>) argv[metadata.headerMapIndex()];

core/src/test/java/feign/FeignTest.java

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -217,6 +217,30 @@ public void customExpander() throws Exception {
217217
.hasPath("/?date=1234");
218218
}
219219

220+
@Test
221+
public void customExpanderListParam() throws Exception {
222+
server.enqueue(new MockResponse());
223+
224+
TestInterface api = new TestInterfaceBuilder().target("http://localhost:" + server.getPort());
225+
226+
api.expandList(Arrays.asList(new Date(1234l), new Date(12345l)));
227+
228+
assertThat(server.takeRequest())
229+
.hasPath("/?date=1234&date=12345");
230+
}
231+
232+
@Test
233+
public void customExpanderNullParam() throws Exception {
234+
server.enqueue(new MockResponse());
235+
236+
TestInterface api = new TestInterfaceBuilder().target("http://localhost:" + server.getPort());
237+
238+
api.expandList(Arrays.asList(new Date(1234l), null));
239+
240+
assertThat(server.takeRequest())
241+
.hasPath("/?date=1234");
242+
}
243+
220244
@Test
221245
public void headerMap() throws Exception {
222246
server.enqueue(new MockResponse());
@@ -656,6 +680,12 @@ void form(
656680
@RequestLine("POST /?date={date}")
657681
void expand(@Param(value = "date", expander = DateToMillis.class) Date date);
658682

683+
@RequestLine("GET /?date={date}")
684+
void expandList(@Param(value = "date", expander = DateToMillis.class) List<Date> dates);
685+
686+
@RequestLine("GET /?date={date}")
687+
void expandArray(@Param(value = "date", expander = DateToMillis.class) Date[] dates);
688+
659689
@RequestLine("GET /")
660690
void headerMap(@HeaderMap Map<String, Object> headerMap);
661691

0 commit comments

Comments
 (0)