-
Notifications
You must be signed in to change notification settings - Fork 16
Overriding, Detaching and Skipping Components
Components such as serializers, deserializers and interceptors attached at the root of the endpoint are common to all requests. If a new request defined on the endpoint requires and an alternate component, you should be able to override the root definition. In contrast, if the new request wishes to skip the component, you should be able to detach the entire root definition or skip individual components. Without any special provision for overriding, detaching and skipping, component definitions would have to be repeated for every request to which it's attached.
####1. Overriding and Detaching Serializers and Deserializers
Serializers and deserializers are attached with the @Serialize
and @Deserialize
annotations. Obviously, a single request can only use a single serializer or deserializer. When either of these components are attached to the endpoint, it applies to all requests. If a single request needs to override the root definition, simply reattach the required serializer or deserializer to the request.
@Deserialize(JSON)
@Endpoint("https://api.github.com")
public interface GitHubEndpoint {
@GET("/users/{user}")
User getUser(@PathParam("user") String user);
@GET("/users/{user}/gists")
@Deserialize(type = GistDeserializer.class)
List<Gist> getGists(@PathParam("user") String user);
}
JSON deserializer is overridden by
GistDeserializer
.
To detach the root definition all-together, use the @Detach
annotation with the Class
of the annotation used for attaching the component.
@Deserialize(JSON)
@Endpoint("https://api.github.com")
public interface GitHubEndpoint {
@GET("/users/{user}")
User getUser(@PathParam("user") String user);
@Detach(Deserialize.class) //detach all components; directive: Deserialize
@GET("/users/{user}/gists")
HttpEntity getGists(@PathParam("user") String user);
}
JSON deserializer is detached;
getGists()
will not be using any deserializer.
####2. Detaching and Skipping Interceptors
Interceptors work a tad differently than serializers and deserializers. There is no concept of interceptor overriding. The interceptor(s) attached to the endpoint will be applied together with any interceptor(s) attached to the request. However, all interceptors, defined on the endpoint or request can be detached by using @Detach
. Individual interceptors defined on the endpoint can be skipped by using @Skip
on a request.
@Deserialize(JSON)
@Endpoint("https://api.github.com")
@Intercept({HeaderInterceptor.class, AuthInterceptor.class})
public interface GitHubEndpoint {
@GET("/user/repos")
@Intercept(RepoInterceptor.class)
List<Repo> getRepos();
@GET("/users/{user}")
@Skip(AuthInterceptor.class)
@Intercept(UserInterceptor.class)
User getUser(@PathParam("user") String user);
@GET("/emojis")
@Detach(Intercept.class) //detach all components; directive: Intercept
String getEmojis();
}
getRepos()
will be usingHeaderInterceptor
,AuthInterceptor
andRepoInterceptor
.
getUser()
will be usingHeaderInterceptor
andUserInterceptor
, but notAuthInterceptor
.
getEmojis()
will not be using any interceptor.
####3. Detaching an Async Directive
An @Async
annotation placed on an endpoint will cause all requests to be executed asynchronously. If a request should be exempted from this rule, the @Async
directive can be detached with @Detach
.
@Async
@Deserialize(JSON)
@Endpoint("https://api.github.com")
public interface GitHubEndpoint {
@GET("/users/{user}/repos")
List<Repo> getRepos(@PathParam("user") String user, AsyncHandler<List<Repo>> asyncHandler);
@GET("/meta")
@Detach(Async.class)
Meta getMetaInfo();
}
Although none of the above examples demonstrate multiple component-type detachment and skipping, keep in mind that this is possible.
@Detach({Async.class, Intercept.class, Serialize.class, Deserialize.class})
@Skip({HeaderInterceptor.class, AuthInterceptor.class})