How to develop a client web application that execute Rest Ws Spring - java

In my application server Wildfly I have a war which contains code of a RESTful Web Service done with Apache CXF and Spring Framework, this war call an external ws.
With Postman I call API inside my war with success :-) , I ask what technology is better to develope my new client web application to emulate Postman.
Thanks in advance

I always use the Apache HTTP client to call external web services, regardless if it is SOAP or REST using JSON or XML or whatever other data format.
The reason is: In real live, more than 50% of all web services do not follow the standards. Working around the standards is often hard work when you use frameworks. But with the Apache HTTP client it is easy to implement workarounds for whatever might happen, for example:
Fix wrong XML Namespaces or content by search/replace before parsing it.
Process HTTP result codes in non-standard way
Send and receive custom HTTP headers
Use requests that combine GET (Url-) parameters with POST body
non-standard encryption
non-standard authentication (not everything that they call OAuth2 is really OAuth2)
Work with certificates - even self-made certifictes that do not match any root certificate
All that might sound ridiculous to you but it happens very very often in the projects where I was involved in. The Apache HTTP client gives you full access to the HTTP protocol and is easy to understand.
You can still marshal and unmarshal the objects to XML/JSON using your framework. But it is better to keep control over the many small details of the HTTP communication.

I prefer Spring RestTemplate. You can inject the RestTemplate in your beans and send GET and POST easily:
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.client.RestTemplate;
import org.springframework.http.ResponseEntity;
public class Test {
#Autowired
RestTemplate restTemplate;
public ResponseEntity<Response> test(String url, Request request){
return restTemplate.postForEntity(url, request, Response.class);
}
}

Related

Caching based on Cache-Control Headers with Feign Client

We are moving away from HttpClient to now use RestTemplate, even better FeignClient. But looking at the https://github.com/OpenFeign/feign it seems Response Caching is in road map of feign 11.
I was looking at possibility of writing a custom mechanism to support Caching based on Cache Control headers. I will try to explain this with sample example
Service A exposes an API /greet/{name}. This API sends max-age
response header so that client can cache the response.
Service B calls this API using FeignClient
Below is sample Feign Interface.
#FeignClient(name="app/app", contextId="AppService", configuration=AppConfig.class)
public interface AppFeignService {
#GET
#Path(value = "/api/greet/{name}")
public String greet(#PathParam("name") String name);
}
One way to support caching is, add an intermediate layer above feign client and cache the response based on needs. But this takes the caching logic to client side and I want to make sure the decision of how much to cache (max-age header) should be left to server and client shouldn't drive it.
Question here is - do we know when we can expect caching support in Feign? Is there any interim solution we can go with to still have caching support? Feign is really good considering its abstraction and we do not really want to write code to call it using RestTemplate.
Your recommendations are highly appreciated.
I am actually building my own hobby app and was thinking about exactly same thing and then I hit upon your question. What I have decided so far is to use a okhttpClient as proxy (this one has a very good caching support) to my micro-service. I am using spring boot. I am looking for a way to do it.
So every request from the Fiegn client will first hit my okhttp client with caching support and then it will do all the magic, to forward the request to eureka server micro service or not.
My micro service uses a very specific http client to do the request and I don;t want to touch that part.

Microserivce Using Spring Boot to Consume SOAP

I need to create a REST service that first consumes SOAP. What would the best way to go about this?
I would like to use Spring Boot to create a microservice, but I have a few questions for those with experience:
What other architectures or technologies should I look into using
(with spring boot)?
Is there a standard technology stack for this?
Are there pitfalls I should be aware of?
What other architectures or technologies should I look into using (with spring boot)?
My answer is if you just want to simply provide RESTful service
without Spring Cloud, then I think you can refer to following 2
tutorials on Spring official website to achieve this:
Building a RESTful Web Service
Consuming a SOAP web service
Is there a standard technology stack for this?
Currently, I will suggest you to use Spring Boot as your first choice. Because these are rich resources on the web and it does reduces much effort in development.
Are there pitfalls I should be aware of?
If you finally choose Spring Boot, please be familiar to its components, you can start from Guides to realize how it works. Or you may mix up Spring Boot with tradition Spring framework.
There are similar cases in our project and we did it with spring components. As far as i understood, you want to open a REST endpoint which most probably accepts json object and you want to make a soap web service request within that request then you want to return a response containing information from the soap response. To make a soap request, you can use spring web services - WebServiceTemplate. It will marshall your object to xml and make soap request for you. Of course you can use some other web service frameworks like apache cxf which may best fit for some special cases, but i would first try to use a framework which is from spring family while using Spring. You should set timeout values on webservicetemplate object to not wait too long if the external system is not working well or you have some problems with the network. Because it directly affects your systems performance. Also here, i suggest you to implement circuit breaker pattern to make your system more robust. You should always isolate your systems performance from other systems that you integrate and in this scenario you can do this by doing the things explained above.
As per my knowledge , you should use Spring boot application with Maven build.
In order to send a REST call to SOAP web service and get back a JSON Response ,you need to follow all of this steps in order :
Business Logic : Mapping the JSON fields such as headers, query-param , body variables to XML Request mandatory fields (either using pojo classes or object-mapper) Reason : Since the SOAP end point will only accept XML Request.
Service Broker Logic : Import "org.springframework.web.client.RestTemplate" and use
**ResponseEntity<String> responseEntity=RestTemplate.exchange(endPointURL, HttpMethod.GET/POST/PUT/DELETE, HttpEntity/headers, uriVariables)**
**endpointURL** -- SOAP End point URL ,that the REST service has to consume.
**HTTPMethod** -- Method Type such as GET ,PUT ,POST ,DELETE etc.
**HTTPEntity** -- Soap requires for mandatory sender/headers/{a}.Make sure that you set your header name and value as key-Valye pair in HTTP headers.
**uriVariables** -- (Object... urivariables) such as String.class ,Integer.class
You should also put the **connectTimeout** ,**isSSLDisabled**,**responseCached** elements while generating request to restTemplate.
responseEntity.getBody() is the XML response after un-marshalling.It can be extracted by using mapper.
XML_BaseResponse response=mapper.readValue(responseEntity.getBody(), XML_BaseResponse.class);
Business Logic : Extract necessary field from XML_BaseResponse and using setter's or getter's functions,set the mandatory fields in the response.
baseResponse.setName(xml_baseResponse.getPersonsName());
baseResponse.setAddress(xml_baseResponse.getAddress());
baseResponse.setCity(xml_baseResponse.getcityName());

Cloud Endpoints custom domain workaround

We have an AppEngine app with that we would like to use with Google Endpoints. We need to support a web client as well as mobile clients which is what makes Endpoints attractive to us since we can easily generate Android and iOS client APIs.
The problem is that cloud endpoints currently don't support custom domains, so our web client cannot directly communicate with the endpoints (the mobile clients do not have this issue).
Here is what we've tried already:
CORS requests from the client to the appspot.com domain. The problem with this is since our request do not meet the requirements for simple CORS (custom headers, cookies, etc.), a preflight request must be sent with every request, which slows everything down
Client makes request to our custom domain which in turn makes a request to the appspot endpoint. Again, the extra request is not good for performance
We've also tried setting up a duplicate Jersey REST API just for the web client. We double annotate all our methods (once for Cloud Endpoints and once for Jersey) and the web client accesses the Jersey API and the mobile clients access the Endpoints API. This works pretty well except that Jersey and Endpoints use different exceptions. So if we want to throw a 404 Endpoints exception that will mess up the Jersey response and vice versa.
Are there any other options? We want to use the power of Endpoints for generating mobile clients but also get around the custom domain limitation for the web client.
We ended up ditching Cloud Endpoints entirely and went with a pure Jersey REST API instead.
To deal with our need to generate mobile clients for the API, we annotated our API with Swagger. As an added bonus, Swagger seems to support more client generation than Cloud Endpoints and also makes it relatively easy to setup your own client generation from a template if your target language isn't directly supported.
Jersey + Swagger was not as easy to setup as Cloud Endpoints, but it is more customizable and allowed us to get around the custom domain restriction imposed by Cloud Endpoints.
Google Cloud Endpoints 2.0 now supports custom domains. If you are using Google Cloud Endpoints 1.0 you can migrate by doing the following:
Update your dependency to use the new artifact. In Maven, this looks
something like below:
com.google.endpoints endpoints-framework 2.0.0-beta.8
Remove the legacy dependency, which is the appengine-endpoints artifact.
Update the API entry point in your project web.xml file:
Rename all occurrences of SystemServiceServlet to EndpointsServlet.
Replace all occurences of the path /_ah/spi/* to the new required path /_ah/api/*
See:
https://cloud.google.com/appengine/docs/java/endpoints/migrating
https://code.google.com/p/googleappengine/issues/detail?id=9384
Easiest solution is to use reverse proxy.
For example if your application is http://myapp.appspot.com, create simple html page on http://myapp.com and redirect to http://myapp.appspot.com using javascript.
Index.html on http://myapp.com.
<html>
<head>
<script>
windows.location = http://myapp.appspot.com;
</script>
</head>
<body></body>
</html>
It has one more advantage: if you put your proxy page on another hosting (not appspot.com) your application ( http://myapp.appspot.com ) will be accessible from China.

Using the REST API of Twilio

Not being familiar with REST and after reading some doc about it I am a little bit confused about the way it works.
I actually want to use Twilio SMS Gateway that provides a REST API to interact with and send text messages from an existing web-application.
From what I understand, REST is a way to structure a web service and in the end, instead of using SOAP for example, we just access 'resources' with URLs, relying on HTTP to GET, PUT or DELETE data.
The SMS Gateway I am talking about is providing a Java API that I could integrate to my web-app. The classes in this API uses httpcore, httpclient and commons-codec jars. Is this because REST rely on HTTP?
So basically, their API is relying on the Apache and HTTP libs to construct HTTP requests in Java and setting the basics, so I just have to provide with the data I want to submit and/or specific information?
REST API's are HTTP API's. The word REST is supposed to indicate something about how your API works. Basically that you use POST requests to update data and GET requests to retrieve it, and you have different HTTP endpoints for all of the different resources in your API, like Calls or Recordings.
The Twilio helper libraries (including the Java library) are basically wrappers around HTTP calls to the Twilio API. The idea was to make it easier for you to make API calls to Twilio by abstracting away the HTTP authentication and request stuff behind some more language-specific code. We also parse the HTTP response into an object for you.

Implementing an HTTP proxy to overcome cross-site AJAX requests restrictions (?)

I have a Spring-MVC webapp (3.0.5-RELEASE) which needs to access JSON webservices from another webapp on a different sub-domain (from the client/browser via AJAX).
I've solved this in the past by either:
writing a simple controller that proxies the requests, using Apache Commons HttpClient to handle the requests. Thus overcoming the cross-site/cross-origin request security limitations of most browsers
implementing a JSONP service on the server side (when calling our own JSON services) - not always possible
In the case where JSONP is not possible, is there a better way of doing (1.)?
and/or
Is there a library that will handle this for me? So I don't have to write all the HttpClient code myself - its not a lot of code, but I wonder if I'm (badly) re-inventing the wheel.
I have often had to consume third party web services (API), and as you mentioned, JSONP is not always an option. This is how I go about designing:
If the API is user centric, it has to provide a jsonp interface and that's what I will use. User centric means that you cannot perceive any reason to call the API, do some computations with the response, may be call one of your ajax services and then combine the response and show the user.
If my use case includes calling the API, and then acting on the response, like calling additional services from my application, combining the data and then showing it to the user, I would prefer not doing this in the browser. I would instead use RestTemplate and make backend api calls to the service. In which case there are no cross domain restrictions.
The only case where using a Server Proxy to bypass jsonp is when you are creating a Product that allows people to build custom plugins, plugins which are hosted on your page, but need to make Ajax calls to the app developers servers. This is a very involved case! (As as example look at how Apigee creates Public Facing REST API around your existing urls, or how Zendesk allows you to develop apps)
Hope this helps.

Categories