Method has too many Body parameters - spring-cloud-netflix

I have the following requestMethod in a RestController class and it´s working fine:
#RequestMapping(path = "/api/v1/rest/websearcher/search/results", method = RequestMethod.POST,
produces = MediaType.APPLICATION_JSON_UTF8_VALUE)
public ResponseEntity<WebResultResponse> getSavedAvailability(#RequestBody final WebResultRequest navigationRequest,
#CookieValue(value = "forceSupplier", defaultValue = "") final String forceSupplier)
I´ve also a feign client working fine as well. I added a new parameter called forceSupplier in both methods, but after adding it, I´m having the issue Method has too many Body parameters but I don´t really understand why I´m receiving this message because the param is the same.
This is the method in Feign:
#RequestMapping(path = "/api/v1/rest/websearcher/search/results", method = RequestMethod.POST,
produces = MediaType.APPLICATION_JSON_VALUE + ";charset=UTF-8")
ResponseEntity<WebResultResponse> getAndSavedAvailability(#RequestBody WebResultRequest webSearcherResultRequest, #CookieValue(value = "forceSupplier", defaultValue = "") String forceSupplier);
What am I doing wrong? Thanks

The annotation #CookieValue is not supported when using Spring Cloud OpenFeign. As a result, Feign sees your #RequestBody and #CookieValue parameters as the request entities, and since you only have one request entity, Feign throws the exception you are seeing.
There is currently no support for Cookies in Feign.

Related

ResponseEntity : HTTP Status 400 – Bad Request

I have a web service that returns JSON. I am trying to print the screen using this web service spring mvc. The code I wrote is getting 400 errors. How can I resolve it?
I use json object:
{"currencyRates":[{"currencyPair":"BGN/IRR","date":1519922870105,"askPrice":4.376,"bidPrice":2.162},{"currencyPair":"ROL/LKR","date":1519922870105,"askPrice":4.056,"bidPrice":2.132},{"currencyPair":"KES/MGF","date":1519922870105,"askPrice":4.067,"bidPrice":3.005}]}
Controller:
#RequestMapping(value = "/list", method = RequestMethod.GET, produces = MediaType.APPLICATION_JSON_VALUE)
public String userList(ModelMap model) {
RestTemplate restTemplate = new RestTemplate();
ResponseEntity<List<CurrencyRate>> rateResponse = restTemplate.exchange(
"http://localhost:8080/denemeDenemeDeneme/rates", HttpMethod.GET, null,
new ParameterizedTypeReference<List<CurrencyRate>>() {
});
List<CurrencyRate> rates = rateResponse.getBody();
model.addAttribute("list", rates);
return "list";
}
Thanks...
The problem is that the target class which cannot be a non-static inner class. It doesn't work embedded in the Controller class which I think is the problem.
The details are in here but it boils down to the way Java added inner classes means they don't have the default constructor that Jackson requires.
or Check if your class CurrencyRates does have constructor without any parameter.

Get json content of request and response on annotated Spring Controller

I want to build a library that will save the Json content of request and response on annotated Spring controller.
So i've build my own annotation #Foo and put it on some controllers:
#Foo
#RequestMapping(method = RequestMethod.POST, value = "/doSomeThing", produces = {
MediaType.APPLICATION_JSON_VALUE, MediaType.TEXT_XML_VALUE,
MediaType.APPLICATION_XML_VALUE})
public ResponseEntity<T> doSomething(/*some parameters*/) {
T t = doSomeJob(T.class);
return new ResponseEntity<T>(t, HttpStatus.OK);
}
I have no guarantee that request and response are in Contrellor's parameters!
And i'm catching the call on any Controller having that annotation within an #AfterReturning AOP pointcut.
#Component
#Aspect
public class XYInterceptor
#AfterReturning(
pointcut = "execution(#my.annotation.Foo)")
public void doSomethingWithJsonContent(JoinPoint joinPoint) throws Throwable {
//How can i get json value of request and response here?
}
How can I get request and response content formatted in json (such as it is send/returned to the client) ?
Thanx for your help!
Well, you need request and response somehow accessible from your controller method, either via an injected class member, method parameter or method return value. It has got to be somewhere. Because you did not explain where you intend to get it from, I can just post a general answer showing how to determine method arguments and return value from an #AfterReturning advice. If you update the question with more detailed information, I can also update the answer accordingly.
My pointcut (the commented-out one also works, choose your favourite one) binds the return value to a parameter and just assumes that both request and response are of String type. Feel free to replace by your favourite. Furthermore, you can bind a parameter from your intercepted method (no matter where it is in the signature) to a typed advice method parameter if you know that the parameter exists and also know its (super) type. This way you can get rid of the slow and ugly loop over getArgs().
//#AfterReturning(pointcut = "execution(#my.annotation.Foo * *(..))", returning = "response")
#AfterReturning(pointcut = "#annotation(my.annotation.Foo)", returning = "response")
public void interceptRequest(String response, JoinPoint thisJoinPoint) {
System.out.println(thisJoinPoint);
for (Object arg : thisJoinPoint.getArgs()) {
if (arg instanceof String)
System.out.println(" request = " + arg);
}
System.out.println(" response = " + response);
}

Spring MVC HTTP Status 405 - Request method 'POST' not supported - Backbone Request

I am new at Spring MVC and I am trying to build a Web Application from scratch using Spring MVC + Hibernate to serve something like a JSON Rest API, having this API consumed through Backbone at the client side. To do that I have started following this tutorial ( http://www.mkyong.com/spring-mvc/spring-3-mvc-and-json-example/ ) .
So I have a model Message which will have the following REST API Interface:
GET /api/messages ( working ok )
GET /api/messages/:id ( working ok )
DELETE /api/messages/:id ( working ok )
PUT /api/messages/:id ( working ok )
POST /api/messages ( error: (DefaultHandlerExceptionResolver.java:194) - Request method 'POST' not supported)
I expected this problem happens for PUT or DELETE requests when doing the request through a form, but not for a POST request. I am not even doing the request through a form. On the client side the request is done through Backbone like this:
new App.Models.Message({ attributeA : 'a', attributeB : 'b' }).save();
I have already tried to add the httpMethodFilter at web.xml as suggested in other Stackoverflow questions:
<filter>
<filter-name>httpMethodFilter</filter-name>
<filter-class>org.springframework.web.filter.HiddenHttpMethodFilter</filter-class>
</filter>
<filter-mapping>
<filter-name>httpMethodFilter</filter-name>
<servlet-name>mvc-dispatcher</servlet-name>
</filter-mapping>
Has anyone had the same problem?
I leave here my MessagesController:
#Controller
#RequestMapping("/api/messages")
public class MessagesController {
#Autowired
private MessageService messageService;
#RequestMapping(method = RequestMethod.GET)
public #ResponseBody List<Message> getMessagesInJSON(#RequestParam( value = "type", required = false ) String type) {
List<Message> messages = messageService.findAll();
return messages;
}
#RequestMapping( value = "/{id}", method = RequestMethod.GET )
public #ResponseBody Message getMessageInJson(#PathVariable Integer id ) {
Message message = messageService.findById(id);
return message;
}
#RequestMapping( value = "/{id}", method = RequestMethod.DELETE )
#ResponseStatus( value = HttpStatus.NO_CONTENT )
public void deleteMessage(#PathVariable Integer id ) throws NotFoundException {
messageService.delete(id);
}
#RequestMapping( value = "/{id}", method = RequestMethod.PUT )
#ResponseStatus( value = HttpStatus.NO_CONTENT )
public void editMessage( #PathVariable Integer id, #RequestBody Message message ) throws NotFoundException {
message.setId(id);
messageService.update(message);
}
#RequestMapping( value = "/", method = RequestMethod.POST )
#ResponseStatus(HttpStatus.CREATED)
public #ResponseBody Message createMessage( #RequestBody Message message ) {
return messageService.create(message);
}
}
Thanks a lot!
You have already mapped /api/messages to the getMessagesInJSON method which only allows a GET request. Your POST request is mapping to a different path.
I suggest to omit the value attribute on your request mapping for createMessage.
#RequestMapping(method = RequestMethod.POST )
I think the problem is that your #RequestMapping is located at the top of your class definition, and conflicts with the strings that you associated with the value argument in the other #RequestMapping annotations in front of each method. By contrast, I would start the class with the following:
#Controller
#SessionAttributes(types = SomeClassName.class)
public class SomeClassNameController {
Then you can use the value parameter in the #RequestMapping annotations that you have in front of each method.
It is also good to keep in mind that this error might happen if you are implementing /error endpoint for exception handling. If your /error endpoint has a method type and it doesn't match the method of the endpoint where the exception was thrown; you might end up getting 405. If that is the case, remove method type from the error endpoint to serve to all.

JSON + Spring 3.1

Hi I am trying to write small app with REST Json. I have some method that returns ArrayList of entity objects. And I am doing that:
#RequestMapping(value="/workers/", method = RequestMethod.GET)
public #ResponseBody ArrayList<Workers> showAllEmployes() throws Exception
{
ArrayList<Workers> workers = new ArrayList<Workers>();
workers = (ArrayList<Workers>) spiroService.getAllWorkers();
return workers;
}
And after this I got:
HTTP Status 500. The server encountered an internal error that prevented it from fulfilling this request.
When I try to return primitive data type then all is ok. I have nothing in server logs. And I have necessary imports. Please some tip.
Seems you have issue in produce json format, try this.
#RequestMapping(value = "/workers/", method = RequestMethod.GET,
produces={MediaType.APPLICATION_JSON_VALUE})

MVC4 Model Binding - Null Values

I know there are a bunch of questions on this already - I'm having a hard time sorting out which ones are related to problems with versions, and which ones are related to jQuery (which I'm not using), etc. I have the MVC4 RC (4.0.20505.0), Visual Studio 2010 Ultimate SP1.
I have a complex type in my model:
public HttpResponseMessage Post([FromUri]Person person)
{
TableStorageHelper personHelper = new TableStorageHelper();
personHelper.Save(personHelper.GetTableNameForType("Person"), person);
var response = Request.CreateResponse<Person>(HttpStatusCode.Created, person);
return response;
}
I am passing in this JSON string - using Fiddler mostly, but also trying from code in another controller (trying to do all testing locally just to verify that I can get values in the object received by the controller):
The JSON:
{"FirstName":"Andy","LastName":"Schultz","PartitionKey":"USW","RowKey":"per-928c8f74-2efd-4fc2-a71c-fb3ea8acc6d7","NickName":null,"FullName":"Andy Schultz","Description":null,"ImageLocation":null,"Region":"USW","CommentsAboutMe":{"Comments":[]},"CommentsByMe":{"Comments":[]}}
All of the properties here do exist in the class.
The code from the other controller:
HttpWebRequest request = HttpWebRequest.Create("http://127.0.0.2:8080/api/persons/") as HttpWebRequest;
request.Method = "POST";
request.ContentType = "text/json";
using (var writer = new StreamWriter(request.GetRequestStream()))
{
Person person = new Person("Andy", "Schultz", "USW");
Formatting formatting = new Formatting();
JsonSerializerSettings settings = new JsonSerializerSettings();
settings.ReferenceLoopHandling = ReferenceLoopHandling.Ignore;
string json = JsonConvert.SerializeObject(person, formatting, settings);
writer.Write(json);
}
Every time, I get an empty Person object in my controller (I'm debugging on the very first line there). Every value is NULL.
You may have noticed the [FromUri] attribute on my controller - I had to do that to get around an error telling me there was no ModelBinder for an undefined type, but I'm not sure that it's correct - I'm not passing any info in the Uri, it's in the body, as you can tell.
Thank you Mike Stall: http://blogs.msdn.com/b/jmstall/archive/2012/04/16/how-webapi-does-parameter-binding.aspx
The [FromUri] attribute did indeed tell my controller to read the uri and not the request body looking for the parameter for my controller method. It wasn't there, so everything was null.
The error that adding that attribute fixed, which said there was no formatter defined for a type of content Undefined, was caused by my improperly declaring the content-type of the request. The correct way was "Content-Type: text/json; charset=utf-8