java.lang.IllegalArgumentException: URL query string must not have replace block [duplicate] - path

This question already has an answer here:
Retrofit with an old school service
(1 answer)
Closed 3 years ago.
I am using Retrofit and GET Request:
#GET("Master/GetConsignerPartyList?prefix={claimId}")
Observable<ConsignerPartyResponse> consignerPartyReq(#HeaderMap Map<String, String> headers, #Path("claimId") String search);
and getting this error:
java.lang.IllegalArgumentException: URL query string "prefix={claimId}" must not have replace block. For dynamic query parameters use #Query.
What's going wrong?

Remove ?prefix={claimId} from your url because query name should not be static in url.
#GET("Master/GetConsignerPartyList")
Observable<ConsignerPartyResponse> consignerPartyReq(
#HeaderMap Map<String, String> headers,
#Query("prefix") String search);
It's will work :-)

claimId is part of the query as you've set it in the URL - ?prefix={claimId}"
#Path replaces placeholders in the path, i.e., #GET("Master/{claimId}/").
To replace in the query just use #Query("claimId"):
#GET("Master/GetConsignerPartyList?prefix={claimId}")
Observable<ConsignerPartyResponse> consignerPartyReq(
#HeaderMap Map<String, String> headers,
#Query("claimId") String search);

Related

FeignClient GET converted into POST

We have a quite simple FeignClient
#GetMapping("/{id:.+}")
ResponseEntity<Resource> get(
final HttpServletRequest request,
#PathVariable(name = "id") final String id);
We are using thex Hoxton SR 4 spring cloud dependencies and
it uses the spring-cloud-openfeign 2.2.2.RELEASE.
For some reason this GET request is getting converted into a POST
request and we have no idea why.
Changing {id:.+} to {id} fixes the issue.

Dynamically add query parameters without value to Retrofit request

I have request that set list of services that are turned on for user.
Request has following format:
https://myserver.com/setservices?param1=val1&param2=val2&service[10]&service[1000]&service[10000]
List of service parameters ("service[10]&service[1000]&service[10000]") is created dynamically and each parameter doesn't have value. Is it possible to achive this using Retrofit?
From the retrofit documentation:
For complex query parameter combinations a Map can be used.
#GET("/group/{id}/users")
List<User> groupList(#Path("id") int groupId, #QueryMap Map<String, String> options);
I guess this will make what you want to achieve.
I found workaround how to do this.
#GET("/setservices{services_query}")
ServicesSetResponse setServices(#EncodedPath("services_query") String servicesQuery);
And then:
getService().setServices("?param1=val1&param2=val2" + "&services[10]&services[100000]&services[1000000]")
We can pass using the #QueryMap as below:
GET("/movies")
Call<List<Movies>> getMovies(
#QueryMap Map<String, String> options
);
To build the parameters:
Map<String, String> data = new HashMap<>();
data.put("director", "Haresh");
data.put("page", String.valueOf(2));
It will generate the Url like:
http://your.api.url/movies?page=2&director=Haresh

ServiceStack PostFIleWithRequest "has" hard coded content-disposition name field

I have an issue with the PostFileWithRequest<> method in ServiceStack in that the name of the file field is hard coded to the word "upload">
Part of the data stream
Content-Disposition: form-data;name="upload";filename="Julie.mp3"
And this is from line 407 in the file ServiceClientBase.cs
stream.Write("Content-Disposition: form-data;name=\"{0}\";filename=\"{1}\"{2}{3}".FormatWith(new object[] { "upload", fileName, text, text }));
This is contained in a virtual method but I do not know how I can change that in a derived class as there are other methods that are not accessible to my new class.
public virtual TResponse PostFileWithRequest<TResponse>(string relativeOrAbsoluteUrl, Stream fileToUpload, string fileName, object request)
Any ideas?
This look like a bug to me as the name of the form-data;name should be configurable and not hard coded.
In my case I need the file to be in a name called "File" in order to use a specific API.
Chris
I submitted a pull request to ServiceStack (albeit v4) which has been accepted and will be included in the next version 4.0.14.
This adds an optional parameter of fieldName to the PostFileWithRequest<TResponse> method which allows you to specify the field name instead of being stuck with upload.
So the new signature of the method:
public virtual TResponse PostFileWithRequest<TResponse>(string relativeOrAbsoluteUrl, Stream fileToUpload, string fileName, object request, string fieldName = "upload")

Pass dynamic parameters in the keyvalue (message key) to package.properties

I have tried to pass dynamic parameters to keyvalue(message to display) which I will get from package.properties to the Action class through the getText() method. To get the message, we can use getText(String keyvalue) method. What should I do to pass some parameters and retrieve the parameters with the message through the getText() method?
I saw some API's to pass dynamic parameters. But I don't know how to use, these are the following API's, click here to see the Struts 2 API Documentation.
getText(String aTextName, List<Object> args)
getText(String key, String[] args)
getText(String key, String defaultValue, String[] args)
Thanks in advance..
I suppose that you have following properties in your package.properties
username.required=user name is required
password.required=password is required
you can use getText() as
getText("username.required")
getText("password.required")
Now if we want to use getText(String key, String[] args) we have to pass following parameters
aTextName - the resource bundle key that is to be searched for
args - a list args to be used in a MessageFormat message
That means the message format pattern and other static strings will, of course, be obtained from resource bundles. Other parameters will be dynamically determined at runtime.
example
we have following entry in resource file
disk.data=The disk \"{0}\" artist name is {1}.
in this {1} and {0} are the dynamic parameters and will be determined at run time so args will contain the value of these parameters.
String artistName= demo;
String diskName = "Artist";
String[] testArgs = {artistName, diskName};
So final call will be getText(disk.data, testArgs);
and it will show
The disk demo artist name is Artist.
Please go through MessageFormat to know how this work

Get body content using HttpServletRequest in Jersey

I am using Jersey 1.7 and I am trying to access the request body in my method very similar to this question:
How do I read POST parameters for a RESTful service using Jersey?
Body value comes in fine as email=xx#ws.com&password=test1
I tried using #Context HttpServletRequest request and tried to access the email with request.getParameter("email") but get nothing. There is nothing inside request.getparameterMap() either.
My API looks like this:
#POST
#Produces(...)
public Response getData(#FormParam("email") String email, #FormParam("password") String password, String body, #Context HttpServletRequest request) { ....
I tried changing the position of String body and request but to no avail.
The String body gets the value perfectly fine(it is coming from an iPhone device and not through a Form Submit and so shows up in the String body). Right now, I am trying to parse the body content(email=xx#ws.com&password=test1) and get each variable like email out but that is painful.
Is there some way to get the values using request.getParameter("email") ?
Or is there any quick utility to convert the body content into String email and String password ?
TIA,
Vijay
I never used form parameters myself, but the docs say it should work since forever:
#POST
#Consumes("application/x-www-form-urlencoded")
public void post(MultivaluedMap<String, String> formParams) {
// Store the message
}
http://wikis.sun.com/display/Jersey/Overview+of+JAX-RS+1.0+Features

Resources