How to send Multipart data and json object from ajax to spring - angularjs

I have done a poc to upload(drag&drop) file from angular js by sending multi part request to controller(Sprig), but i need to send some more parameters along with file(Multi part content) can any one suggest me to post file(Multi part content) and json object to controller.

You can't do both just in one method. If it's a big object I suggest to create another method and call it after or before file upload. Otherwise for e.g. if you have HTML form you can do something like this:
var form = new FormData(document.getElementById('file-upload-form'));
$.ajax({
url: /file/upload,
data: form,
dataType: 'text',
processData: false,
contentType: false,
type: 'POST',
success: function () {
//Do something
},
error: function (jqXHR) {
//Do something
}
});
Then in your Spring controller:
#RequestMapping(value = "/file/upload", method = RequestMethod.POST)
#ResponseBody
public ResponseEntity uploadFile(MultipartHttpServletRequest request) {
Iterator<String> itr = request.getFileNames();
MultipartFile file;
try {
file = request.getFile(itr.next()); //Get the file.
} catch (NoSuchElementException e) {
}
String param = request.getParamterer("paramName"); //Get your parameters
//Do something else.
}
You have to declare MultipartHttpServletRequest which will contain the file and all form data of your request.
Hope this helps.

Related

POST request not getting mapped to Spring MVC Controller

I am sending a POST request from Angularjs $http service . It is working fine when my promise is like below and is getting properly mapped to Spring Controller ,
service.js
reassignKsaPendingLeads : function(data,username)
{
var promise = $http({
url : "reassignPendingLeads.htm",
method : "POST",
data : mydata
})
.success(function(data, status, header, config, statusText)
{
}
}
Spring Controller
#RequestMapping({ "reassignPendingLeads.htm" })
public #ResponseBody String updateAccessStatus(#RequestBody List<KsaLead> ksaLeads)
{
log.info("Inside updateAccessStatus");
return "true";
}
The json object i pass from service.js is getting mapped properly to #RequestBody List ksaLeads.
Since the json object contains same keys as bean properties of KsaLead.
But Now i want to pass another parameter username apart from json body (data).
Then i get Request method 'POST' not supported in Spring Controller .
new service.js
reassignKsaPendingLeads : function(data,username)
{
var mydata = JSON.stringify(data) + '&username=' + username;
var promise = $http({
url : "reassignPendingLeads.htm",
method : "POST",
data : mydata
})
.success(function(data, status, header, config, statusText)
{
}
new Spring Controller
#RequestMapping({ "reassignPendingLeads.htm" })
public #ResponseBody String updateAccessStatus(#RequestBody List<KsaLead> ksaLeads,#RequestParam String username)
{
log.info("Inside updateAccessStatus");
return "true";
}
Can anyone guide me as to how should i pass data from angularJs so that it gets mapped correctly to Spring Controller
I would assume that you want to pass the username as a request parameter. In order to do this, the $http can have a params input field:
function(data,username) {
var promise = $http({
url: "reassignPendingLeads.html",
method: "POST",
data: data,
params: { username: username }
})
// continue with your promise here
}
If you want to pass it inside the request body we have to do the following steps:
We have to add the username to the mydata object.
// we assume that data is not a primitive type
function(data,username) {
var mydata;
// check if data is defined
if (data) {
// make a deep copy first, since we don't want to modify the input
mydata = angular.copy(data);
} else {
// if the data is undefined, create e new object
mydata = {};
}
// add the username to mydata
mydata.username = username;
var promise = $http({
url: "reassignPendingLeads.html",
method: "POST",
data: mydata
})
// continue with your promise here
}
On the back-end we have to make sure that we can accept this kind of data. For this it is advised to create a data class which holds the username and any other fields which may appear on your data object from the front-end.
Probably something like this:
public class MyDataClass {
private String username;
// other fields
// no args constructor
public MyDataClass() {}
// all args constructor
public MyDataClass(String username) {
this.username = username;
}
// getter and setters
}
Now we modify the controller to accept it:
#RequestMapping(value = "reassignPendingLeads.htm", method = RequestMethod.POST)
public #ResponseBody String updateAccessStatus(#RequestBody MyDataClass data)
{
log.info(data.getUsername());
return "true";
}

Get Json object passed in $http.put request

I am a newbie to angularjs. I am trying to send a json object in $http.put request as follows:
function LoginCtrl($http){
this.login = function(){
var self = this;
self.user = {
username: this.username,
password: this.password
}
$http.put('http://localhost:8086/app/login',self.user).then(function
successCallback(response) {
}, function errorCallback(response) {
})
}
}
I just want to get this json object in Rest api, the code of which is as follows:
#Path("/app")
public class LoginResource {
public LoginResource() {
}
#PUT
#Path("/login")
#Consumes(MediaType.APPLICATION_JSON)
public Response getUserByName() {
return Response.status(Response.Status.ACCEPTED).build();
}
What parameters i need to pass to this getUserByName api?. I am using dropwizard
Also if somebody could tell how to set the index.html page as the starting page in jetty server config.
First, in your Dropwizard(Jersey) backend define your input
public Response getUserByName(User user) { ...
Then you can map your JSON to an entity like this:
public class User {
#JsonProperty("name")
private String name; }
In angularJS pass the Json object as a request payload in $http.PUT(uri,<JsonObject>)
http.put(url, JSON.stringify(self.user), function (err, response)
{
// do something here
}

Web API creating new actions always results in 404 errors

I have been trying to expand on my Account Controller for my web api however I cannot seem to get new actions to work. I just want an action that intakes a string. So I wrote my action like this:
Update: This action works if I remove the parameter (String val) now = ()
[AllowAnonymous]
[Route("Stuff")]
public IHttpActionResult Stuff(String val)
{
return Ok();
}
Then in my AngularJS I wrote a function to call into my action
function storeConnID (event, data){
return $http({
url: State.Endpoint + "/api/account/stuff",
method: "POST",
headers: {
'Authorization' : 'Bearer '+ State.User.Access_Token
},
data: {
val: data
}
}).then(function (res) { }, function (err) {
console.log(err);
});
};
The url after it is all formatted is as such:
https://localhost:44375/api/account/stuff
Every other action in my controller works however I cannot create new ones?
Continued research:
Javascript isn't simply sending in a string, it is sending a json object with a key/value pair. The web api action doesn't understand this object when I am looking for a string.
My proposed solution:
[AllowAnonymous]
[Route("Stuff")]
public IHttpActionResult Stuff(Dynamic Data)
{
return Ok();
}
By changing the input to a dynamic type the data can come as any form of object.

How to send multiple parameters in AngularJS $http.post to Web API controller action method

How to send multiple parameters in an angularjs $http.post to web api controller action method.
Below is my code.
AngularJS code
var complexObj = { prop1: "value", prop2: "value" };
var id = 100;
var data = { id: id, complexObj: complexObj };
$http({
method: 'POST',
url: 'http://localhost/api/WebApiController/MethodName',
data: data
}).success(function (data, status) {
//do something...
});
$http.post('http://localhost/api/WebApiController/MethodName', data)
.success(function (data, status) {
//do something...
});
Web API controller
[RoutePrefix("api/WebApiController")]
public class WebApiController: ApiController
{
[Route("MethodName")]
public ReturnValue WebApiAction(string id,ComplexObj complexObj)
{
// process request and return data...
}
}
I am getting below response message in fiddler.
{ "message": "No HTTP resource was found that matches the request
URI 'http://localhost/api/WebApiController/MethodName'.",
"messageDetail": "No action was found on the controller
'WebApiController' that matches the request." }
When I send the complexObj alone, its hitting the web api,but all properties are null or set to default values.
What am I doing wrong? How can I send two or more parameters(both complex objects and string/int) in $http.post? Any help is much appreciated.
Web API doesn't support multiple post parameters in this way.
Your best bet is to roll up Id into ComplexObj and post it as a single parameter.
complexObj.id = id;
var data = complexObj;
Update your signature to take just a single object.
[Route("MethodName")]
public ReturnValue WebApiAction(ComplexObj complexObj)
{
// process request and return data...
}
If you absolutely want to be able to post data like this, consider Rick Strahl's post on creating a custom parameter binder.

Ajax Post containing list of objects to Spring MVC Controller

How do i post a list of objects from javascript to Spring MVC Controller? I can post arrays, objects, but not a combination of the 2. This is my code below.
Javascript:
var utilData = getTableData();
// Sending data over to server
console.log(utilData);
$.ajax({
url: "saveUtilData2.html",
type: "POST",
contentType: "application/json",
dataType: "json",
data: {utilArray: utilData},
success: function(data){
alert("save was sucessful");
},
error: function(){
alert("Save wasn't successful");
}
});
Spring Controller (tried changing utilData to String[] and object[] ... both didnt work:
#RequestMapping(value="/saveUtilData2.html", method=RequestMethod.POST)
public ModelAndView saveUtilData2(#RequestParam("utilArray") String[] utilData, HttpServletRequest request)
{
System.out.println("Util Save Data method 2");
ModelAndView mv = new ModelAndView("util");
return mv;
}
Use #Requestbody instead of Requestparam

Resources