First of all, I'm not trying to start a flame-war here. I know Jersey sufficiently well, but have hardly used httpclient.
What are the key differences between jersey-client and Apache's httpclient? In what areas is one better than the other? Is there a good comparison chart somewhere? Which one performs better with larger files (say 2048 MB)?
Many thanks for your comments!
These two things probably should not be compared directly. Jersey is a REST-client, featuring full JAX-RS implementation, neat fluent API and a powerfull filter stack. Apache Http Client is a HTTP-client, perfect in managing low-level details like timeouts, complex proxy routes and connection polling. They act on a different levels of your protocol stack.
When you're using Jersey there is always some kind of HTTP client backend involved. Given no backend explicitly, Jersey will use HttpUrlConnection as a default backend.
Jersey with HttpUrlConnection backend example:
Client client = Client.create();
WebResource webResource = client.resource("http://localhost:8080/path");
ClientResponse response = webResource.accept("application/json")
.get(ClientResponse.class);
Jersey with Apache Http Client backend example:
HttpClient apacheClient = HttpClientBuilder.create().build();
Client client = new Client(new ApacheHttpClient4Handler(apacheClient,
new BasicCookieStore(),
true));
WebResource webResource = client.resource("http://localhost:8080/path");
ClientResponse response = webResource.accept("application/json")
.get(ClientResponse.class);
Please note usage of Handler in the last example. This is a key integration abstraction for Jersey to incorporate and utilize various backends. First example uses URLConnectionClientHandler deep under the hood.
Speaking about performance and features it makes little sense to compare Apache Http Client with Jersey. One may want to compare different Jersey backends here, as Jersey itself is merely a wrapping API. I'd like to highlight some key differencies between HttpUrlConnection and Apache Http Client based on my own experience:
HttpUrlConnection
No external dependencies are necessary. This may be quite valuable on embedded or mobile platforms.
Extremely well documented everywhere
Has poorly designed API. HttpUrlConnection-based implementation is difficult to maintain and extend.
Many features are configured through JVM properties, some of which may be non-reconfigurable during runtime.
In some cases hopeless at handling timeouts. You may end up setting 10 different JVM properties for different timeouts and still get your connections hanging forever in some circumstances.
Since Gingerbread is a recommended http client API for Android.
Apache Http Client
For 3.X versions it's performance was somewhat similar to HttpUrlConnection. Version 4.1 contains lots of performance enchancements and performs way better than it's counterpart
Quite good at managing connection and data read timeouts
It's design follows Open/Closed Principle, so you can customize almost any part of HTTP processing with your own implementation. Examples: redirect strategies, retry strategies, custom cookie storages, interceptors for requests/responses, etc.
Provides rich proxy support with customizable route builders for complex multy-proxy paths
Has out of the box per-route connection pool. This may give a good performance benefit if SSL/TLS is used, especialy having hardware PKCS#11 tokens involved. HttpUrlConnection also has an internal pooling, but you have no tools to customize what or when to pool, no monitoring facilities to check the pool state.
Features detailed logging
Keep in mind, that it also possible to use other backends (e.g. for non-blocking clients) with Jersey if you have an appropriate com.sun.jersey.api.client.ClientHandler implementation.
Related
We have service which mostly use gRPC. So we just use netty+io.grpc and need no extra frameworks here.
But we also need to support some HTTP requests for our infrastructure team.
And I think it will be better to reuse Netty (EventLoopGroup, ChannelFactory, etc) which we already configured.
So basically I need small HTTP routing library for already configured Netty.
But most of HTTP over Netty frameworks like Vert.x, Jooby, Ratpack or Armeria, manage Netty by their-self and just too complex for my case.
It will be simpler to me just use HttpServer from JDK and doesn't care about a bit of context switches because of over creating event loops.
But I really want to get clean solution.
I'm open to any suggestions.
I was reading many articles to find the best Rest Client for java application, I found finally using Jersey with Apache HTTP client 4.5 is great but in a lot of articles I found that now Retrofit is the best (I didn't mention
Volley because in my case I don't need that the API supports caching.
Does Retrofit is better for a java client application. or is it just better for android? and why I didn't find this comparison before .. they cannot be compared?
Can I have a comparison between their performance, connection pooling, on which layer do they work, compression of the requests and responses, Timeout, de-serialization?
HTTP3 does not support connection pooling, is that why retrofit is used usually for android ?? so It will not be practical for a normal java application where it will cause connection leak.
My target is to find the best Rest API client with a high performance, and support high number of connections.
Thank you in advance
You're mixing different things together. To clear things up up-front:
Retrofit is a client library to interact with REST APIs. As such it offers the same abstraction level as Jersey, RESTeasy or Spring's RestTemplate. They all allow to interact with REST APIs using a type-safe API without having to deal with low level aspects like serialization, request building and response handling.
Each of those libraries uses a HTTP client underneath to actually talk to an HTTP server. Examples are Apache HTTP client that you mentioned, OkHttp or the plain-old HttpUrlConnection shipping with the JDK.
You can usually mix and match the different REST client libraries and HTTP clients except for Retrofit because Retrofit has a hard dependency on OkHttp since version 2 (with Retrofit 1.x you can use Apache HTTP Client, HttpUrlConnection or OkHttp).
Back to the actual question: What to pick when.
Android: It's easy here because JAX-RS, the API/technology behind Jersey and RESTeasy isn't supported on Android. Hence Retrofit is more or less your only option except maybe Volley if you don't want to talk HTTP directly. Spring isn't available either and Spring Android is abandoned.
JRE/JDK: Here you have the full choice of options.
Retrofit might be nice if you want a quick and easy solution to implement a third-party API for which no SDK is available or JAX-RS interfaces.
Spring's RestTemplate is a good choice if you're using Spring and there are no JAX-RS interfaces or you don't want to buy into JAX-RS, i.e. also using it on the server-side.
JAX-RS (Jersey, RESTeasy, …) is a good choice if you want to share interface definitions between client and servers or if you're all-in on JavaEE anyway.
Regarding performance: The main drivers here is the time spent on doing HTTP and (de)serialization. Because (de)serialization is performed by specialized libraries like Jackson or protobuf and all use the same (or you could at least make them to) there shouldn't be any meaningful difference.
It took a while to find, however I have found the perfect REST client library that makes our development declarative and easy. We can use this as the standard when developing new REST implementations or APIs.
It is called Feign, developed by the Netflix team and made to work with Spring Cloud Netflix. More details here on the project’s site.
Some features include:
- Integration with Jackson, Gson and other Encoders/Decoders
- Using OkHttp for network communication, a proven HTTP library
- Binding with SLF4J for logging features
- Interface-based implementation, minimal development. Below is a sample client:
#FeignClient("stores")
public interface StoreClient
{
#RequestMapping(method = RequestMethod.GET, value = "/stores")
List<Store> getStores();
#RequestMapping(method = RequestMethod.POST, value = "/stores/{storeId}", consumes = "application/json")
Store update(#PathVariable("storeId") Long storeId, Store store);
}
And after #aha 's answer as quoted below:
JRE/JDK: Here you have the full choice of options.
Retrofit might be nice if you want a quick and easy solution to
implement a third-party API for which no SDK is available or JAX-RS
interfaces.
Spring's RestTemplate is a good choice if you're using
Spring and there are no JAX-RS interfaces or you don't want to buy
into JAX-RS, i.e. also using it on the server-side.
JAX-RS (Jersey,
RESTeasy, …) is a good choice if you want to share interface
definitions between client and servers or if you're all-in on JavaEE
anyway.
Feign works like retrofit and JAX-RS together: easy solution and can share interface definitions between client and servers and can use JAX-RS interfaces
After some benchmarking I've found that AsyncHttpClient (https://github.com/AsyncHttpClient/async-http-client) seems to be the most stable and scalable async http client out there as it's based on NIO and seems to scale very well during load. I compared it against OkHttp and Apache Async and it seems to perform really well when simulating a backend with latency.
Unfortunately I have not yet found any way to expose it as a Spring AsyncRestTemplate, making a migration in our existing codebase a pain.
Does anyone know of any good bridge to RestTemplate's using the library, or if otherwise, how to create an issue in the Spring project to include it among the other Async http client factories?
You can't use RestTemplate for async requests, that's what the AsyncRestTemplate is for. You'll need to implement your own AsyncClientHttpRequestFactory. I briefly looked into the link you provided in your post, and it looked like you could wrap a AsyncRestClient and return BoundRequestBuilder from AsyncClientHttpRequestFactory.createAsyncRequest. Then onwards, you basically need to delegate the calls from Spring-specific interfaces to AsyncRestClient-specific classes. It shouldn't be too hard.
That said, Spring 5 Web comes with a WebClient that does async and more. I suggest seriously considering it before building your own async library, albeit on top of another one.
Here is an official java doc of spring RestTemplate.
Note: by default the RestTemplate relies on standard JDK facilities to
establish HTTP connections. You can switch to use a different HTTP
library such as Apache HttpComponents, Netty, and OkHttp through the
HttpAccessor.setRequestFactory(org.springframework.http.client.ClientHttpRequestFactory)
property.
EDIT:
OK here you go with spoon feeded answer:
AsyncRestTemplate template = new AsyncRestTemplate(
new HttpComponentsAsyncClientHttpRequestFactory());
HttpComponentsAsyncClientHttpRequestFactory is part of spring since 4.0
Jetty 9 supports both it's own Jetty Websocket API as well as the standard JSR 356 API, for what I assume are historical reasons (Jetty's API precedes the final JSR 356).
I've looked over the basic documentation of both APIs, as well as some examples. Both APIs seem fairly complete and rather similar. However, I need to choose one over the other for a new project I'm writing, and I'd like to avoid using an API that might be deprecated in the future or might turn out to be less feature-rich.
So are there any important differences between the two except for the obvious fact that one is standardized?
Implementor of both on Jetty here :)
The Jetty WebSocket API came first, and the JSR-356 API is built on top of it.
The JSR-356 API does a few things that the Jetty WebSocket API does not, such as
Decoder's for automatic Bin/Text to Object conversion
Encoder's for automatic Object to Bin/Text conversion
Path Param handling (aka automatic URI Template to method param mapping)
However, the Jetty WebSocket API can do things the JSR-356 API cannot.
WebSocketCreator logic for arbitrary creation of the WebSocket endpoint, with access to the HttpServletRequest
Better control of timeouts
Finer buffer / memory configurations
You can manage WebSocket Extensions
Supports Reg-ex based Path mappings for endpoints
Access to raw Frame events
WebSocket client supports HTTP proxies (JSR-356 standalone client has no configuration options for proxies)
WebSocket client supports better connect logic with timeouts
WebSocket client supports SSL/TLS (JSR-356 standalone client has no configuration options for SSL/TLS)
Access to the both InetAddress endpoint information from the active WebSocket Session object
Access to UpgradeRequest from active WebSocket Session object
Better support for stateless endpoints
Read events support suspend/resume logic to allow application some basic tcp backpressure / flow control
Filter based or Servlet based configuration (the JSR-356 approach requires upgrade to occur before all other servlet and filter processing)
Hope this helps, if you want more details, please use the jetty-users mailing list, as this sort of question is really inappropriate for stackoverflow.
I have been seeing SOAP is "Heavy Weight" and REST is "Light Weight". On what parameters, we are telling REST is lightweight than SOAP?
We were using IFW model web services in our company earlier. But our management told us to develop all the new APIs going forward in REST. We are backend service providers in my company.
How REST is best useful for us?
What does "lightweight" means in context?
This question seems like repetition but don't understand the terms used.
REST gives you a session less window into a system. It does not track you, it does not care about you. All you have done is send a request which contains..hopefully some id to verify that you can make it. It may return a HTTP status code, it may return some body but ultimately, once the request is complete you are forgotten.
SOAP is heavy in a sense that it describes a "contract" between the remote system and your client. In order for your client to communicate effectively it MUST implement its schema...this is the SOAP skeleton. It describes the calls you can make and the objects you can expect back.
The reason why SOAP is heavy is because of serialization. Upon each SOAP request you typically serialize a java object, send it over HTTP and get a serialized response which is deserialized into an object via reflection...this is heavy. It also means that if the endpoint changes how they work, you must change your contract. You don't have to do this with REST.
With SOAP you run into multi threaded issues.
To answer quickly..
they might mean that a REST service is "lightweight" because you do not need to release changes to clients. You simply make changes to your logic, retaining URLS and the response should remain the same.
With SOAP...if you added a new field to an object, you would have to get the client to implement the new schema. SOAP is pretty old had.
REST is lightweight in that it and relies upon the HTTP standard to do its work. It is great to get a useful web service up and running quickly. If you don't need a strict API definition, this is the way to go. Most web services fall into this category. You can version your API so that updates to the API do not break it for people using old versions(as long as they specify a version). REST essentially requires HTTP and is format-agnostic, so you can use XML, JSON, HTML etc).
But the SOAP will wrap the structure into a SOAP envelope (follows an XML standard). The complexity of the SOAP envelope is based on the used message version and additional Web Service protocols. SOAP is generally transport-agnostic, meaning you don't necessarily need to use HTTP.
It can be pointed out that SOAP was designed for a distributed computing environment whereas REST was designed for a point-to-point environment.
I wonder if it is OK to say that while SOAP gives more security, REST-based API s will be easier on the resources and more scalable? As an example, Twitter, Facebook, Google Drive, Blogger, etc all have REST-based APIs that clients can consume.
Generally REST reduces the size and scope of request payloads by mapping request semantics to the underlying HTTP protocol. For example, SOAP will usually add an envelope (of varying complexity) which utilizes a WSDL (a contract) for both request and response types and service mappings. REST will just use POST, GET, etc to a URL with some HTTP encoded parameters and thus lacks an enforced contract.
There are several aspects of lightweight. SOAP is XML only, while REST allows you to send any payload, such as JSON which is less verbose and simpler than XML. Generally speaking, it takes less memory and less bandwidth to deal with JSON than XML.
On another level, using SOAP you typically describe everything as services. So, you need to define a message schema/structure for each verb and noun i.e. "CreateOrder". In REST, you use the predefined HTTP methods such as POST and put the noun/"resource" in the URI which uses already existing constructs on the HTTP level - not reinventing them in XML.
Then there is the effort it takes to adapt to change. A small change in SOAP requires you to redefine the schema, redefine the wsdl and handle versions. In rest, in the best of worlds, there is a degree of dynamic coded into the API (links to referenced resources, among other things), so that some changes can be implemented and takes effect directly.
All the heavy weight strictness of SOAP of course has a valid reason for existence. It's less likely two implementations have different interpretations of the API, than in a loosely defined REST API. SOAP also allows you to implement skeleton code in various languages based on a WSDL. In some complex scenarios, this is actually almost the only productive way to work with SOAP. Marshalling and unmarshalling between objects and serialized XML is rather heavy and adds to the heavyness of SOAP.