Спецификация на это ясна.Раздел 3.3.2.1 сообщает нам, что:
Методы ресурса НЕ ДОЛЖНЫ иметь более одного параметра, который не аннотирован одной из перечисленных выше аннотаций.
перечисленные выше аннотации - это аннотации параметров JAX-RS: @QueryParam
, @MatrixParam
и т. д.
Однако существует определенный способ решения этой проблемы для Джерси.Использование InjectableProvider
.Итак, метод, который определяет два не-JAX-RS параметра:
@POST
public void postIt(@CustomInjectable final Customer customer,
final Transaction transaction) {
// ...
}
Конечно, мы должны закодировать аннотацию:
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.PARAMETER)
public @interface CustomInjectable {
}
Реализация InjectableProvider
, которая знаеткак предоставить Customer
s:
import com.sun.jersey.spi.inject.Injectable;
import com.sun.jersey.spi.inject.InjectableProvider;
import com.sun.jersey.api.model.Parameter;
@Provider
public class CustomerInjectableProvider implements
InjectableProvider<CustomInjectable, Parameter> {
// you can use @Context variables, as in any Provider/Resource
@Context
private Request request;
public ComponentScope getScope() {
// ComponentScope.Singleton, Request or Undefined
}
public Injectable getInjectable(ComponentContext i,
CustomInjectable annotation,
Parameter param) {
Injectable injectable = null;
if (Customer.getClass().isAssignableFrom(param.getParameterClass()) {
injectable = getInjectable();
}
return injectable;
}
private Injectable getInjectable() {
return new Injectable<Customer>() {
public Customer getValue() {
// parse the customer from request... or session... or whatever...
}
};
}
}
Но Джерси учитывает только последнюю аннотацию (см. JERSEY-ISSUE-731 ), поэтому будьте осторожны.
И, более портативный способ (если вы все равно делаете об этом заботитесь):
// simple bean
public class CustomerWithTransaction {
private Customer customer;
private Transaction transaction;
// getters and setters
}
Затем измените метод на:
@POST
public void postIt(CustomerWithTransaction customerWithTransaction) {
// ...
}
Затем создайте свойсобственные MessageBodyReader
для CustomerWithTransaction
, где вы также можете получить доступ к любым контекстным переменным (запрос, заголовки и т. д.).