I having a problem in sending json data from front end bootstrap to express servlet. Here is what i have tried. I use ajax to send data from my form to servlet class with json. please give my hand to solve this problem .here is my form to register student:
<html>
<head>
<link rel="stylesheet" type="text/css" href="resources/css/bootstrap.min.css">
<script type="text/javascript" src="resources/js/jquery.min.js"></script>
<script type="text/javascript" src="resources/js/bootstrap.min.js"> </script>
<script type="text/javascript">
function registerStudent() {
var firstName = $("#firstName").val();
var lastname = $("#lastname").val();
var phone = $("#phone").val();
var email = $("#email").val();
var studentCode = $("#studentCode").val();
$.ajax({
type : "POST",
url : "/RegisterStudent",
data :{data: "firstName=" + firstName + "lastname=" + lastname + " phone=" + phone + "email=" + email+"studentCode"+studentCode},
success : function(data) {
var ht = data.msg;
$("#resp").html(ht);
},
error : function(data) {
alert("Some error occured.");
}
});
}
</script>
</head>
<body>
<div class="container">
<div class="card " style="width:750px;margin:0px auto">
<div class="card-header">Student Register</div>
<div class="card-body">
<form data-toggle="validator" role="form" method="post" >
<div class="form-group">
<label class="control-label" for="firstName">Name</label>
<input class="form-control" data-error="Please enter name field." id="firstName" placeholder="Name" type="text" required />
<div class="help-block with-errors"></div>
</div>
<div class="form-group">
<label for="lastname" class="control-label">lastname</label>
<input type="text" class="form-control" id="lastname" placeholder="lastname" required>
<div class="help-block with-errors"></div>
</div>
<div class="form-group">
<label for="phone" class="control-label">phone</label>
<div class="form-group">
<input type="text" data-minlength="5" class="form-control" id="phone" data-error="fill your phone" placeholder="phone" required>
<div class="help-block with-errors"></div>
</div>
</div>
<div class="form-group">
<label class="control-label" for="email">email</label>
<textarea class="form-control" data-error="Please enter email field." id="email" placeholder="email" required=""></textarea>
<div class="help-block with-errors"></div>
</div>
<div class="form-group">
<label for="studentCode" class="control-label">studentCode</label>
<div class="form-group">
<input type="text" class="form-control" id="studentCode" data-error="fill your studentCode" placeholder="studentCode" required>
<div class="help-block with-errors"></div>
</div>
</div>
</form>
</div>
<button onclick="registerStudent();" type="button" class="btn btn-success btn-block">Register</button>
<div class="text-center" id="resp" style="margin-top: 14px;"></div>
</div>
</div>
and this is my servletclass for send data to database .
#WebServlet(urlPatterns = "/RegisterStudent")
public class RegisterStudentController extends HttpServlet {
StudentServiceInter service = new StudentServiceImpl();
ObjectMapper mapper = new ObjectMapper();
String json = "";
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
Student student = new Student();
req.getSession().setAttribute("student", student);
resp.sendRedirect("/addStudent.jsp");
}
#Override
protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
String jsonData = req.getParameter("data");
resp.setContentType("application/json");
PrintWriter out = resp.getWriter();
out.println(jsonData);
out.close();
}
}
Try this...
$.ajax({
type: 'GET',
url: '<?php echo base_url(); ?>"/RegisterStudent"', // your syntax
data: {
'firstName ': firstName ,
'lastName' :lastname,
'phone': phone,
'email' : email,
'studentCode' : studentCode,
},
success : function(data) {
var ht = data.msg;
$("#resp").html(ht);
},
error : function(data) {
alert("Some error occured.");
}
});
One problem is that, client-side, you are not creating json, and server side you try to parse a json. Json format doesn't have equal (=) sign.
A valid object is:
data = {
data: {
firstName: 'Name',
lastName: 'Surname',
phone: '123-4456',
email: 'a#b.c',
studentCode: 12345
}
};
and before sending it you should do JSON.stringify(data).
Related
I'm trying to upload multiple files to springboot server from angular but I don't know why I'm getting error.But in postman the code is working fine and I'm able to upload files and output format.
I'm getting this error in browser
HttpErrorResponse {headers: HttpHeaders, status: 400, statusText: "OK", url: 'http://localhost:8080/file/Upload', ok: false, …}
Error in backend terminal:
DefaultHandlerExceptionResolver : Resolved [org.springframework.web.multipart.support.MissingServletRequestPartException: Required request part 'fileN' is not present]
springboot restapi:
#postMapping(value="/Upload")
public ResponseEntity<List<String>> uploadFiles(#RequestParam ("fileN")List<MultipartFile> multipartFiles,#RequestParam("fileFormat")String id) throws IOException, FOPException, TransformerException{
List<String> filenames = new ArrayList<>();
try{
for(MultipartFile file : multipartFiles){
String filename = StringUtils.cleanPath(file.getOriginalFilename());
Path fileStorage = get(DIRECTORY, filename).toAbsolutePath().normalize();
copy(file.getInputStream(), fileStorage, REPLACE_EXISTING);
filenames.add(filename);
}
fileConversion.Convert(id);
}
catch (Exception e){
e.printStackTrace();
}
return ResponseEntity.ok().body(filenames);
user service:
constructor(private http: HttpClient){}
uploadFile(formData: FormData): Observable<any>{
const headerDist = {
'Access-Control-Allow-Origin': '*';
'Access-Control-Allow-Headers': 'Origin, X-Requested-With, Content-Type, Accept',
'access-control-allow-credentials':'true'
'Content-Type': 'multipart/form data; boundary=Inflow'
}
const requestOptions = {
headers: new HttpHeaders(headerDist),
};
return this.http.post('http://localhost:8080/file/Upload',formData,requestOptions);
}
appcomponent:
onSubmit(){
const formData = new formData();
formData.append('fileN', this.angForm.get('file1').value);
formData.append('fileN', this.angForm.get('file2').value);
formData.append('fileN', this.angForm.get('file3').value);
formData.append('fileN', this.angForm.get('fileFormat').value);
this.userService.uploadFile(formData).subscribe (
(res) => console.log(res),
(err) => console.log(err)
)};
html:
<h2 id="zone" xmlns="http://www.w3.org/1999/html">File Conversions</h2>
<form [formGroup]="angForm" enctype="multipart/form-data" (ngSubmit)="onSubmit()" >
<div class="main">
<div class="classOne">
<div class="form-two">
<input type="file" class="file-input" formControlName="file1" id="ixml" value="" accept="xml/*" required (change)='uploadF($any($event.target).files)' #open>
<div class="file-upload">
<p class="para-tag">Input XML :</p>
<button mat-raised-button color="primary" class="upload-btn" (click)="open.click()">Choose File</button>
</div>
</div>
</div>
<div *ngIf="angForm.controls['file1'].invalid" class ="alert alert-danger">
<div *ngIf="angForm.controls['file1'].errors.required"></div>
</div>
<div class="classTwo">
<div class="form-two">
<input type="file" class="file-input" formControlName="file2" id="udtd" value="" accept="dtd/*" required (change)="uploadFile($event.target.files)"#ele>
<div class="file-upload">
<p class="para-tag">Upload DTD : </p>
<button mat-raised-button color="primary" class="upload-btn" (click)="ele.click()">Choose File</button>
</div>
</div>
</div>
<div *ngIf="angForm.controls['file2'].invalid" class ="alert alert-danger">
<div *ngIf="angForm.controls['file2'].errors.required"></div>
</div>
<div class="classThree">
<div class="form-two">
<input type="file" class="file-input" formControlName="file3" id="uxsl" value="" accept="xsl/*" required (change)="uploading($event.target.files);"#choose>
<div class="file-upload">
<p class="para-tag">Upload XSL : </p>
<button mat-raised-button color="primary" class="upload-btn" (click)="choose.click()">Choose File</button>
</div>
</div>
</div>
<div *ngIf="angForm.controls['file3'].invalid" class ="alert alert-danger">
<div *ngIf="angForm.controls['file3'].errors.required"></div>
</div>
<div class="classFour">
<p class="para-tag-two">Choose Your Output Format :</p>
<div>
<input type="radio" id="pdf" value="pdf" name="fileFormat" formControlName="fileFormat">
<label for="pdf">PDF</label><br>
<input type="radio" id="ps" value="ps" name="fileFormat" formControlName="fileFormat">
<label for="ps">PostScript</label><br>
<input type="radio" id="png" value="png" name="fileFormat" formControlName="fileFormat">
<label for="png">PNG</label><br>
<input type="radio" id="txt" value="txt" name="fileFormat" formControlName="fileFormat">
<label for="txt">Text</label><br>
<input type="radio" id="print" value="print" name="fileFormat" formControlName="fileFormat">
<label for="print">Print</label><br><br>
</div>
</div>
<div *ngIf="angForm.controls['fileFormat'].invalid" class ="alert alert-danger">
<div *ngIf="angForm.controls['fileFormat'].errors.required"></div>
</div>
<div class="submit">
<button style="width:100px;" type="submit" [disabled]="angForm.invalid" mat-raised-button color="warn"disabled="true" >Submit</button>
</div>
</div>
</form>
I have a side bar for my user profile page which has two items for 1) Updating the information and 2) showing the reviews that the user has already written.
The first item works perfectly (as it includes a form and has a submit button). But for the second one, I have no idea. The goal is that when I click on My Reviews, a method from the controller class is called, the reviews of the user are extracted from the database and the results are shown on the right side of the page.
As I don't have a submit button or a form for the second item, I don't know how I can implement it.
Here is my code:
<div class="module-inner">
<div class="side-bar">
<nav class="side-menu">
<div class="col-xs-3">
<ul class="nav nav-pills nav-stacked">
<li class="active"><a data-toggle="pill" href="#profile">Profile</li>
<li class="active"><a data-toggle="pill" href="#review">My
Reviews</a></li>
</ul>
</div>
</nav>
</div>
<div class="content-panel">
<div class="col-xs-9">
<div class="tab-content">
<div id="profile" class="tab-pane fade">
<form class="form-horizontal" th:action="#{/edit_profile}"> <fieldset class="fieldset">
<h3 class="fieldset-title">Personal Info</h3>
<div class="form-group">
<label class="col-md-2 col-sm-3 col-xs-12 control-label">User
Name</label>
<div class="col-md-10 col-sm-9 col-xs-12">
<input type="text" class="form-control"
th:disabled="${currentUser.email}"
th:value="${currentUser.email}">
</div>
</div>
<div class="form-group">
<label class="col-md-2 col-sm-3 col-xs-12 control-label">First
Name</label>
<div class="col-md-10 col-sm-9 col-xs-12">
<input name="firstname" type="text" class="form-control"
th:value="${currentUser.firstname}">
</div>
</div>
<div class="form-group">
<label class="col-md-2 col-sm-3 col-xs-12 control-label">Last
Name</label>
<div class="col-md-10 col-sm-9 col-xs-12">
<input name="lastname" type="text" class="form-control"
th:value="${currentUser.lastname}">
</div>
</div>
</fieldset>
<hr>
<div class="form-group">
<div
class="col-md-10 col-sm-9 col-xs-12 col-md-push-2 col-sm-push-3 col-xs-push-0">
<input class="btn btn-primary" type="submit"
value="Update Profile">
</div>
</div>
</form>
</div>
<div id="review" class="tab-pane fade">
<h3>Menu 2</h3>
<p>You have no reviews yet.</p>
</div>
</div>
</div>
</div>
</div>
Here is my controller:
#RequestMapping(value = "/findUserReviews", method = RequestMethod.GET)
public ModelAndView findUserReviews() {
ModelAndView modelAndView = new ModelAndView();
Authentication auth = SecurityContextHolder.getContext().getAuthentication();
User user = userService.findUserByEmail(auth.getName());
..
modelAndView.addObject("reviews", reviewRepository.findUserRevies());
modelAndView.setViewName("profile");
return modelAndView;
}
I use the following technologies: Spring boot, Hibernate and Thymeleaf.
Any help would be appreciated.
Final update: The provided code in the accepted answer works, provided that I don't return a ModelAndView but a List<Review>.
With Ajax calls you can call the controller endpoints using javascript. One ajax call looks like this :
function getReviews() {
$.ajax({
type: "GET",
url: "/users/findUserReviews", //example
dataType: "JSON",
success: function (data) {
//do something with this JSON
fillReviews(data);
}
});
}
Now you can use this function as an on-click event for your button. And the fillReviews() is a function that gets the element with id="review" from the jsp page and create the list tree with the fetched data.
function fillReviews(data) {
var reviewDiv= document.getElementById('review');
var reviewList = document.createElement('ul');
for ( var i=0 ; i < data.length; i++)
{
var reviewListItem = createListItem(data[i]);
reviewList.appendChild(reviewListItem);
}
reviewDiv.appendChild(reviewList);
}
And createListItem(data[i]) could look like this:
function createListItem(data)
{
var listItem = document.createElement('li');
listItem.innerHTML = data["reviewName"]; // for example ..
return listItem;
}
And now all you have to do is to call getReviews() here :
<button onclick="getReviews()"/>
EDIT : The "data" from the ajax call is a JSON. So the "/users/findUserReviews" should return a List<Review> for example. And there is no need to change your original "/findUserReviews" endpoint. This was only an example, you can create a new endpoint in your controller which returns a list.
On my view, I generate input "username", select with attribute multiple=multiple, which has name "rolesss".
My issue is, that if I send such form via post, my controller should convert roles to list, but i get only list containing single element.
For example:
I send post, with values:
username:MyUser
_csrf:aef50238-92cf-48df-86a4-cb6e2b8f62c9
rolesss:USER
rolesss:ADMIN
In debug mode in my controller I see values:
roless: "USER"
username: "MyUser"
"ADMIN" did just disappear.
My controller looks like:
#Controller
#RequestMapping("/user-management")
public class UserManagementController {
#RequestMapping("")
public ModelAndView home() {
ModelAndView modelAndView = new ModelAndView();
modelAndView.setViewName("pages/user-management");
return modelAndView;
}
#RequestMapping(value = "", method = RequestMethod.POST)
public ModelAndView changeRoles(#ModelAttribute("username") String username,#ModelAttribute("rolesss") List<String> rolesss) {
return null;
}
}
My view I merged 2 thymeleaf fragments into 1, in my code #user-roles-form is in separate fragment, but I think that it should not change anything:
<th:block layout:fragment="main-content">
<section>
<h2 class="section-title no-margin-top">Role Management</h2>
<div class="form-group">
<div class="panel panel-primary">
<div class="panel-heading">Změna rolí uživatele</div>
<div class="panel-body">
<form class="form-horizontal" role="form" action="/user-management" method="post">
<div class="form-group">
<label for="user-name" class="col-sm-2 control-label">Uživatel</label>
<div class="col-sm-10">
<input id="user-name" class="autocomplete form-control" type="text"
placeholder="Jméno uživatele" name="username"/>
</div>
<input type="hidden"
th:name="${_csrf.parameterName}"
th:value="${_csrf.token}"/>
</div>
<div id="user-roles-form" th:fragment="roles(roles)" xmlns:th="http://www.thymeleaf.org">
<div class="form-group">
<label for="user-roles" class="col-sm-2 control-label">Uživatelovy role</label>
<div class="col-sm-10">
<select multiple="multiple" class="form-control" id="user-roles" name="rolesss">
<th:block th:each="role : ${roles}">
<option th:value="${role.userRole.role}" th:text="${role.userRole.role}" th:selected="${role.selected}"></option>
</th:block>
</select>
</div>
</div>
<div class="form-group">
<div class="col-sm-offset-2 col-sm-10">
<button type="submit" class="btn btn-ar btn-primary">Uložit</button>
</div>
</div>
</div>
</form>
</div>
</div>
</div>
</section>
</th:block>
try using like below in your controller
in your HTML or JSP
<form modelAttribute="your_model_name"></form>
if you are using model attribute then use #ModelAttribute
otherwise, use #RequestParam("username")
In your case
#RequestMapping(value = "", method = RequestMethod.POST)
public ModelAndView changeRoles(#RequestParam("username") String username,#RequestParam("rolesss") List<String> rolesss) {
..........
.........
return null;
}
Spring-controller is getting the MultipartFile, but its still throwing
"DefaultHandlerExceptionResolver:186 - Handler execution resulted in exception: Required MultipartFile parameter 'txnFile' is not present"
This is causing AngularJS client call to fail with 400.
JAVA-Spring-Controller:
#RequestMapping(value = "/uploadMultipleFile", method = RequestMethod.POST)
public #ResponseBody Response uploadMultipleFileHandler(
#RequestParam("fileType") String fileType,
#RequestParam("fileEtx") String fileEtx,
#RequestParam("country") String country,
#RequestParam("network") String network,
#RequestParam("version") String version,
#RequestParam("txnDate") String txnDateStr,
#RequestParam("txnFile") MultipartFile txnFile,
#RequestParam("exceptionFile") MultipartFile exceptionFile){
Response response= null;
try {
Here, txnFile and exceptionFile is not null. Code runs file as well. But it still throws "DefaultHandlerExceptionResolver:186 - Handler execution resulted in exception: Required MultipartFile parameter 'txnFile' is not present"
Java-Spring-Config:
<bean id="multipartResolver" class="org.springframework.web.multipart.commons.CommonsMultipartResolver">
<property name="maxUploadSize" value="1000000" />
</bean>
HTML-AngularJS-Form:
<form method="POST" action="http://localhost:8080/recon-validation-tool/ctrl/core/uploadMultipleFile" enctype="multipart/form-data">
<fieldset>
<legend>Select Txn file:</legend>
<div class="form-group">
<label for="">Txn-file:</label>
<input type="file" file-model="txnFile"/>
</div>
</fieldset>
<fieldset>
<legend>Select Exec file:</legend>
<div class="form-group">
<label for="">Exec file:</label>
<input type="file" file-model="exceptionFile"/>
</div>
</fieldset>
<fieldset>
<legend>Please enter carrier details:</legend>
<div class="form-group">
<label for="txnDate">Date:</label>
<input type="date" name="txnDate" ng-model="formData.txnDate" value="2017-05-30">
</div>
<div class="form-group">
<label for="fileType">Type:</label>
<input type="text" name="fileType" ng-model="formData.fileType">
</div>
<div class="form-group">
<label for="fileEtx">Ext:</label>
<input type="text" name="fileEtx" ng-model="formData.fileEtx">
</div>
<div class="form-group">
<label for="country">country:</label>
<input type="text" name="country" ng-model="formData.country">
</div>
<div class="form-group">
<label for="country">network:</label>
<input type="text" name="network" ng-model="formData.network">
</div>
<div class="form-group">
<label for="version">version:</label>
<input type="text" name="version" ng-model="formData.version">
</div>
</fieldset>
<br>
<button ng-click="uploadFile()">Validate</button>
</form>
AngularJS-Controller:
controllerM.controller('HomeController', function($scope, $http, $location, $rootScope){
$scope.formData= {};
$scope.formData.fileEtx= "";
$scope.formData.fileType= "";
$scope.formData.country= "";
$scope.formData.network= "";
$scope.formData.version= "";
$scope.formData.txnDate= "";
$scope.uploadFile = function(){
var data = new FormData();
data.append('fileEtx', $scope.formData.fileEtx);
data.append('fileType', $scope.formData.fileType);
data.append('country', $scope.formData.country);
data.append('network', $scope.formData.network);
data.append('version', $scope.formData.version);
data.append('txnDate', $scope.formData.txnDate);
data.append('txnFile', $scope.txnFile);
data.append('exceptionFile', $scope.exceptionFile);
var uploadUrl = "http://localhost:8080/recon-validation-tool/ctrl/core/uploadMultipleFile";
$http.post(uploadUrl, data, {
headers: {'Content-Type': undefined},
transformRequest: angular.identity
})
.success(function(resp){
console.log(resp);
})
.error(function(resp){
console.log(resp);
});
};
});
well i have got this Themeforest Template and played around with it until the website looks in a way how i imagined it. The only Problem i have is that the .js form somehow doesnt work and i dont have any idea. I dont even know where to tell the form to which Adress it should send the text. Maybe you can help me.
The Domain is: entwicklung.thechillingbull.de
This is the HTML:
<div class="container"> </div>
<div class="container"> </div>
<div class="bg-2 section" id="contact">
<div class="inner" data-topspace="50" data-bottomspace="20" data-image="flavours/coffeecream/images/demo-content/background-6.jpg">
<div class="container">
<h3 class="hdr4">Kontakt und Reservierung</h3>
<div class="easyBox full">
<div class="row nomargin">
<div class="col-md-11">
<h4 class="hdr2 special">Wenn du Uns etwas mitteilen oder Reservieren möchtest hast du hier die Chance!</h4>
<form class="simpleForm" action="form/form.php" method="post">
<fieldset>
<div class="form-group">
<label>Dein Name</label>
<input type="text" class="form-control" name="field_[]" placeholder="Schreibe deinen Namen">
</div>
<div class="form-group">
<label>Deine E-Mail-Adresse</label>
<input type="email" required class="form-control" name="email" placeholder="Schreibe deine E-Mail-Adresse">
</div>
<div class="form-group">
<label>Deine Nachricht</label>
<textarea class="form-control" rows="5" name="field_[]" placeholder="Schreibe deine Nachricht"></textarea>
</div>
<input type="hidden" name="msg_subject" value="Contact Form">
<input type="hidden" name="field_[]" value=" ">
<input class="btn btn-default" type="submit" value="Senden">
</fieldset>
</form>
<div class="successMsg" style="display:none;">Nachricht erfolgreich gesendet! </div>
<div class="errorMsg" style="display:none;"> Ups! Es ist ein Fehler unterlaufen, versuche es später erneut. </div>
</div>
<div class="col-md-2"> </div>
</div>
</div>
</div>
</div>
and this is the .js
/**
* Submitting Form
*/
jQuery(document).ready(function ($) {
var debug = false; //show system errors
var sendingMessage = 'Sending...';
$('.simpleForm').submit(function () {
var $f = $(this);
var $submit = $f.find('input[type="submit"]');
//prevent double click
if ($submit.hasClass('disabled')) {
return false;
}
$submit.attr('data-value', $submit.val()).val(sendingMessage).addClass('disabled');
$.ajax({
url: $f.attr('action'),
method: 'post',
data: $f.serialize(),
dataType: 'json',
success: function (data) {
if (data.errors) {
// error
var $errorMsg = jQuery($f).parent().find(".errorMsg");
jQuery($f).fadeOut(300,function(){
$errorMsg.fadeIn();
});
} else {
// success
var $successMsg = jQuery($f).parent().find(".successMsg");
jQuery($f).fadeOut(300,function(){
$successMsg.fadeIn();
});
}
$submit.val($submit.attr('data-value')).removeClass('disabled');
},
error: function (data) {
if (debug) {
alert(data.responseText);
}
$submit.val($submit.attr('data-value')).removeClass('disabled');
}
});
return false;
});
});
hope you can help me get this to work.
Thank you !
Change:
<form class="simpleForm" action="form/form.php" method="post">
To
<form class="simpleForm" action="/your-code-file" method="post">
where your-code-file will be the location of the file which will handle the form values.