Multiple requestparam, rest philosophy and good pratice - rest

I have many crud operation.
User must be able to search by many field of the resource.
Some have around 10.
I could use RequestParam, but method will have a lot of parameter an habitually it's not a good pratice.
/card?id=2&imso=trx&icco=98x&type=23&scm=988&createat=2017-02-01
Is there another good solution?

There are two issues here and depending on what carries what importance to you - you can approach a solution.
Problem # 1 : Long REST URLs at client
Problem # 2 : Controller methods with long & complicated signatures
Solution 1 : You group your #RequestParam into optional & mandatory parameters and then you create a DTO only for optional parameters. Then You can have your controller method signature like controllerMethod(#RequestParam param1 , #RequestParam param2, DTO dto).
Note that, you don't use #RequestBody before DTO.
Values for DTO will be passed in client URL itself like before and Spring MVC automatically converts it into DTO.
This solves complicated controller method signature but not long URL problem while you retain your request type to be GET
It is assumed that usually mandatory parameters are only a few and there is always a long list of optional fields.
Solution 2: You change server side to convert your GET request to a POST and start accepting a #RequestBody DTO. This solves both the problems but your original API changes to POST type.
As far as I know, changing a GET to POST shouldn't be a problem in most cases but vice versa is not true.

Related

Creating two different rest api with optional values

I am just new to rest api and need to create two api. both of them use post.
1) First one takes 2 parameters inside of the body
url is : /myapp/resources
2) Second one is doing the same function as the first one does but it needs 2 optional parameter. I thought using path or request param but as the parameters are optional it will be confusing when there is no paramaters. So there will be conflict with the first api.
/myapp/resources?param1=xx&param2=xx ==> what if there is no parameter
/myapp/resources/param1/{xxx}/param2/{yyy} ==> so still what if there is no param:
So what is the best way to define second api without causing a conflict with the first api when optional parameters are not passed.
I would suggest going with the first approach (query params) so:
/myapp/resources?param1=xx&param2=xx
The reason being - in this case you can define or extend the logic of just one endpoint, the /myapp/resources, that is going to verify if parameters exist and react accordingly.
With the second approach (path params), you would have to most likely define two (or more) separate endpoints (like /myapp/resources/, /myapp/resources/param1/{param1} and /myapp/resources/param1/{param1}/param2/{param2}

Can the Post for a ODataContoller in WebAPI 2 take an IEnumerable of a complex object

I want to know if passing a collection to the post of an ODataController is even possible before I waste my time trying to figure out where my problem is.
I've seen variations of this question over the internet, but nothing that has led me to an answer.
I created the Post method on an ODataContoller where I want to pass in a IEnumerable of a complex object. However, when I debug the controller, the parameter is null.
When I take each individual element of the collection and pass it into a Controller's Post (that takes a single object), the object is accepted. So I know the individual objects are being formatted correctly.
Technically this is possible. If you get null as complexObjects in the following call
[HttpPost]
public IHttpActionResult CreateMany([FromBody] IEnumerable<ComplexObject> complexObjects)
{
// ...
}
it's probably due to a format error in the bodies json object. If you have a working single object you can post, you just need to wrap it in brackets ... an array is an array even if it cotains only one element. This assumes, you check your web api actions via postman, fiddler etc., where you can 'compose' the entire request. Alternatively you can use the output of a 'GET all' action (if you have one) as input.
Regarding another aspect, the REST-fulness of list creation, you may find RESTful way to create multiple items in one request interesting
Hope this helps.

What REST action should I use for Validate?

I have a design question on REST. I need to expose a validate method as a rest resource. Let us say it looks like this
public ValidatedResult validate(ObjectToBeValidated object)
ObjectToBeValidated is a class that contains the actual Object and also some parameters concerning the validation.
When I design this as a Restful resource, which action do I use? From my understanding GET is the action that best suits this case. If that is so, how I can pass my ObjectTobeValidated as an object but not as URL parameters? I shy away from URL parameters because ObjectToBeValidated may contain a lot of properties, ending up with an URL like below which is feel is too long
http://localhost/rest/validate?prop1=somevalu&prop2=somevalue&prop3=something&prop11=somevalu&prop22=somevalue&prop33=something
Any help would be appreciated
Thanks
Kay
The HTTP standard allows you to use the POST method. It does not necessary need to have a side effect.
The action performed by the POST method might not result in a resource
that can be identified by a URI. In this case, either 200 (OK) or 204
(No Content) is the appropriate response status, depending on whether
or not the response includes an entity that describes the result.
HTTP 1.1 / method definitions / POST
In your case you can do something like this if you want to follow the noun-verb approach Tim suggested:
POST /api/my/object/validator
Be aware that by REST the messages must be self-descriptive, so either you need a vendor MIME type or you need to add meta-data e.g. RDF to describe what this link does and what params are allowed. Otherwise we are not talking about REST, just a regular webapp.

Http DELETE with parameters using Jersey

I have code that contains several different DELETE methods, one of which takes a parameter, or at least ideally it would take a parameter. However when I make this request, either through CURL or through a web client, it doesn't work. The other DELETE requests function fine and I've hard-coded in the parameter that I want to pass just to see if the call works and it does. I've tried this with both PathParam and QueryParam and neither works. Here's how I'm using the PathParams, which I'm pretty sure is correct, QueryParams looks very similar so I don't want to post that too.
#DELETE
#Path("/byId/{id}")
public void deleteById(#PathParam("id") String id)
And then essentially the same thing for QueryParams but obviously the path is different
From what I understand a lot of RESTful APIs ignore any kind of request body with a DELETE request, or treat it as a PUT or POST. Is there any way around this? Basically I have a database that contains several objects and I need to delete one based on a unique identifier, to be passed in by the client. If there is no way around this is there some other way that I could do it?
Its possible that I'm missing something obvious here as I've only been using Jersey for a few weeks now and up to this point had never even heard of the concept of RESTful services.
You can send information to a RESTful service as either headers, path param, query param or message body.
If all the values go through as expected there is no problem with jax-rs/jersey. Now you need to debug the code and fix your implementation. jax-rs will only match a DELETE call with the DELETE http method you have implemented.
It is then your responsibility to actually perform a DELETE operation of the resource within the method. jax-rs or jersey is not going to complain if you do not DELETE or if you do some other action within the method.

Rest Service URI Parameter types

I'm having two rest methods as follows
/objects/(int:type)/(id:objectID)/(ver:version)
/objects/(int:type)/(id:objectID)/(str:version)
if i send the request as like the following URI
http://localhost/REST/objects/0/123/latest which of the above method gets called.
whether the 2 methods are same or different.
need to know what are all the parameter types available and what is the actual usage of each type.
And how the URI identifies the exact method
That question is all about the server framework you are using and nothing about REST. REST says nothing about URI structure, and certainly nothing about how URIs are mapped to handlers.