Submitting AJAX form when a field is changed - javascript

I have a GET form that when submitted uses an AJAX request to update a php page.
I want this form to automatically submit any time a field is changed, the form contains mostly text inputs and a few dropdowns.
What I have tried:
onchange="this.form.submit()" - This works, but instead of AJAXing the data to the php page, it actually redirects me to the page, which is a no go.
<input type="submit"> - I would like this to be a last resort, because I want the form to send automatically, but it does work otherwise.
I know that sending a form every input change isn't usually a good idea, so ideally I would like it to send the form 1-2 seconds after inactivity (After inputting something obviously) - if that isn't possible, then every time a field is changed would be acceptable as its a low traffic server.
So my question is, what is the proper way to send a form via ajax automatically?
My current :
<form method="GET" id="submitRequest" action="showTable.php">
<th><input type="text" id="SSeries" name="SSeries" class="form-control"></th>
<th><input type="text" id="SModel" name="SModel" class="form-control"></th>
<th><input type="text" id="SSerial" name="SSerial" class="form-control"></th>
<th><input type="text" id="SColor" name="SColor" class="form-control"></th>
<th><input type="text" id="SStorage" name="SStorage" class="form-control"></th>
<th><input type="text" id="SCarrier" name="SCarrier" class="form-control"></th>
<th><input type="text" id="SType" name="SType" class="form-control"></th>
<th><input type="text" id="SUPC" name="SUPC" class="form-control"></th>
<th><input type="text" id="SStatus" name="SStatus" class="form-control"></th>
<input type="submit" class="btn btn-success">
</form>
My current AJAX:
$(document).ready(function() {
$('#submitRequest').submit( function( event ) {
$.ajax({ // create an AJAX call...
data: $('#submitRequest').serialize(), // serialize the form
type: $('#submitRequest').attr('method'), // GET or POST from the form
url: $('#submitRequest').attr('action'), // the file to call from the form
success: function(response) { // on success..
showTable();
}
});
event.preventDefault();
});
});

try this:
When input value change then form will submit,
jQuery("#submitRequest input").change(function(){
$('#submitRequest').submit();
});

I was able to fix my problem by simply changing my jquery selection and function.
I changed it from
$('#submitRequest').submit( function( event ) {
To
$('.submitForm').on('keyup', function(){
and I added submitForm to each inputs class.

You can make a post in ajax after change, and get a response from server
$("#submitRequest input").change(function(){
var data = {
SSeries : $("#SSeries").val(),
...
}
$.ajax({
url: 'your_url_method',
type: 'POST',
data: data,
success : function(res){
showTable();
console.log("Success, you submit your form" + res);
},
error : function(error){
console.log(error, "Error in submit")
}
});
});

Related

Ajax call for second submit button of a form

I'm using spring boot and thymeleaf.
Managing to call a spring controller method on click of first submit button.
I'm trying for a Ajax call on hit of second submit button , how can I achieve it?
Ajax call for the second submit button
$(document).ready(function() {
$("#download").click(function() {
var checked = [];
$('.checkbox:checked').each(function() {
checked.push($(this).val());
});
console.log(checked);
$.ajax({
type: "POST",
url: "selectedsalesDownload",
data: {
name: checked
},
success: function(msg) {
console.log(mgs);
alert(msg);
}
});
});
});
<form name="salesList" th:action="#{/selectedsales}" th:object="${sales}" method="post">
<div class="container">
<hr>
<table class="table table-striped">
<thead class="thead-dark">
<tr>
<th>SELECT</th>
<th>Mandy Name</th>
<th>GSTIN</th>
</tr>
</thead>
<tbody>
<tr id="salesDataTable" th:each="tempSales:${sales}">
<td>
<input class="checkbox" type="checkbox" th:name="selected" th:value="${tempSales.ID}" />
</td>
<td th:text="${tempSales.mandyName}"></td>
<td th:text="${tempSales.gstin}"></td>
</tr>
</tbody>
</table>
<div>
<input type="submit" value="SELECT" name="submit" class="btn btn-primary btn-sm mb-3" />
<input id="download" type="submit" value="DOWNLOAD" name="download" class="btn btn-primary btn-sm mb-3" />
</div>
</div>
</form>
Controller Method for first submit button
#PostMapping("/selectedsales")
public String selectedSales(
#RequestParam(value = "selected", required = false) List<Integer> selectedList,
Model model
) {
//...
}
Controller Method for second submit button
#RequestMapping(value = "/selectedsalesDownload")
#ResponseBody
public String toDownload(#RequestParam("name") List<Integer> list) {
return "msg";
}
I'm not able to get into "toDownload" method in the controller on click of second submit button instead I'm getting into first submit button controller method "selectedSales".
And also I need to send the checked box value which is stored in the javascript array variable "checked" to spring controller method "toDownload".
Need Solution.
Two things here...
You aren't preventing the second submit button from submitting the form normally. Either use a button type...
<input id="download" type="button" ... />
or make sure you prevent the default event action
$("#download").on("click", function(e) {
e.preventDefault()
// and so on
})
#RequestParam list parameters should be sent with the following format for the greatest compatibility
name=1&name=2&name=3...
Unfortunately, the default for jQuery is
name[]=1&name[]=2&name[]=3...
probably for compatibility with PHP. You can change this though via the traditional option
$.ajax({
method: "POST",
url: "selectedsalesDownload",
data: {
name: checked
},
traditional: true, // 👈 note the value here
success: function(msg) {
console.log(mgs);
alert(msg);
}
});
See https://api.jquery.com/jquery.ajax/ and more specifically https://api.jquery.com/jQuery.param/
Why do you need two submit buttons? Which one actually completes the form?
Adding the following code to your JS would immediately solve the issue, but ultimately you really should change one of those submit inputs to type="button" as well. This will prevent the default functionality of the form element and you can then override it with your own code:
$("form").submit(function(){
event.preventDefault();
// Your other code to execute on form submission
});

AJAX how to serialize and post all form elements from within an element

I'm trying to serialize and post all form elements that may come from either witin a <form> element, or from within any other elements (div, tr, etc.).
In short, my form will come from either:
<form id="frm1">
Name: <input ...>
Gender: <select ...>
<input type="button" value="Submit" onClick="submitFormData('frm1')"/>
</form>
and sometimes, I have html TABLE so cannot have a <form> in them, therefor I use:
<table>
<tr id="frm1">
<td><input type...></td>
<td><select...></td>
<td><input type="button" value="Submit" onClick="submitFormData('frm1')"/></td>
</tr>
<tr id="frm2">
<td><input type...></td>
<td><select...></td>
<td><input type="button" value="Submit" onClick="submitFormData('frm2')"/></td>
</tr>
</table>
I can't seem to figure out how to pull out and serialize all form elements (inputs, selects, etc.) FROM within a given element.
My code so far :
const ERROR_TYPE_FATALERROR = 1;
const ERROR_TYPE_INPUTERROR = 2;
const ERROR_TYPE_GLOBALMESSAGE = 3;
function submitFormData(formid) {
var formNode = document.getElementById(formid);
$.ajax({
type: 'POST',
url: $(location).attr('href'),
// data: jQuery('#' + formid + ' input').serialize(), // this works, but will only get <INPUT...>s
data: formNode.serialize(), // this doesn't work
dataType : "json",
}).done(function(response) {
// If we have response, then it's PHP that returned an error!
if(response) {
// error type
switch (response.type) {
case ERROR_TYPE_GLOBALMESSAGE:
// unhide informational box (i.e. "Data saved!")
$('#globalMessage').addClass('d-block');
$('#globalMessagePH').empty();
$('#globalMessagePH').append(response.message);
break;
case ERROR_TYPE_FATALERROR:
// unhide form fatal error message box showing response.message
$('#fatalError').addClass('d-block');
$('#fatalErrorMessagePH').empty();
$('#fatalErrorMessagePH').append(response.message);
break;
case ERROR_TYPE_INPUTERROR:
// unhide form input error messages based on response.field
break;
default:
// ...
}
}
// Successful post, but not response came back !?
else {
console.error("Post sent, but no response came back!?");
}
}).fail(function(response) {
console.error("Unknown Error!"); // not sure yet how I'd get here... ?
});
}
I had also tried adding a "data2post" class to all form elements in order get all the elements needed for post and serialize them:
var formNode = document.getElementById(formid);
var formData = formNode.getElementsByClassName('data2post');
...
data: formData.serialize()
...
but it doesn't work: formData.serialize is not a function
As you can see from my JS snippet, I know having just
data: jQuery('#' + formid + ' input').serialize()
works, but this will only get the <INPUT...>. I need to be able to get all form elements regardless of type (inputs, select, textarea, etc.)
And even for the sake of it, might I ask at the same time, considering you folks see what I'm using this ajax for, in good practice, should I be getting the response.type, etc more in the .fail() section ? Not sure how I to do this yet in PHP, meaning trigger a failure. All I know is if I die() my script with JSON data, it'll be sent as the response...
Thanks a million for your help.
Cheers, Pat
EDIT: here is an example of my SELECT inputs:
<tr id="row_1">
<!-- STATUS -->
<td class="text-nowrap">
<select name="isActive" id="isActive" class="form-control pl-2" aria-label="Account Status" aria-describedby="isActiveReq" required>
<option value="1" selected>Enabled</option>
<option value="0" >Disabled</option>
</select>
<!-- missing field: add 'is-invalid' to the <input>'s classes to show OR 'was-validated' to the form's classes -->
<div id="isActiveReq" class="pl-1 invalid-feedback">
This field is required!
</div>
</td>
<td><input type="button" name="btnSave" value="Save" onClick="submitFormData('row_1')"></td>
</tr>
try use $('#frm1').serialize();
var data = $('#frm1').serialize();
$.ajax({
type: "POST",
url: url,
data: data,
success: function(response){
console.log(response);
}
});
Its OK if you don't have form element,
Clone specified id element, either its div or anything:
$('#myDiv').clone()
Append into a form element:
$('<form>').append($('#myDiv').clone()).serialize();
Below is working example, almost type of element included:
function getSerialize(id){
let element = $("#"+id);
// if you are using form element
if( element.prop("tagName") === "FORM" ){
var data = element.serialize();
}
// if your are using another elements
else{
var myInputs = element.clone();
// this is the bug getting select box selected value when clone, so we have selected value in clone using this hack.
element.find('select').each(function(i) {
myInputs.find('select').eq(i).val($(this).val())
})
var data = $('<form>').append(myInputs).serialize();
}
// you can return 'data' variable from here.
console.log(data);
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<h1>Div Serialize</h1>
<div id="myDiv">
<input type="text" name="name" placeholder="Name"><br><br>
<select name="age" placeholder="Age">
<option value="">Age</option>
<option value="18+">18+</option>
</select><br><br>
<textarea name="about" placeholder="About"></textarea><br><br>
<button onClick="getSerialize('myDiv')">Get Serialize</button>
</div>
<h1>Form Serialize</h1>
<form id="myDivForm" action="" onSubmit="return false;">
<input type="text" name="name" placeholder="Name"><br><br>
<select name="age" placeholder="Age">
<option value="">Age</option>
<option value="18+">18+</option>
</select><br><br>
<textarea name="about" placeholder="About"></textarea><br><br>
<button onClick="getSerialize('myDivForm')">Get Serialize Form</button>
</form>
Hope this help.

Why is this code showing anomalous behaviour? (form not submitted)

I'm trying to submit a form using PHP and Ajax. But the problem is that sometimes it inserts one value, sometimes 2, sometimes all, and now it is inserting nothing. Why is it happening? How can I correct it?
Here's my code:
Ajax
$(document).ready(function(){
$("button").click(function(){
$.ajax({
url: "submitform.php",
type: "POST",
data: $("form").serialize(),
success: function(data){
alert("well");
},
error: function(){
alert("Error");
}
});
});
});
HTML
<form id="signupform" name="form1" method="post" enctype="multipart/form-data">
<table>
<tr>
<td><input type="text" name="name" placeholder="Enter your name" required /></td>
<td rowspan="3"><div class="propic"><img id="imgid" src="images/dp.png" /></div>
<input id="imgInput" type="file" name="image"/></td>
</tr>
<tr>
<td><input type="text" name="username" placeholder="Enter username" required /></td>
</tr>
<tr>
<td><input id="digits" type="text" name="phone" maxlength="10" placeholder="Enter your phone no." required /></td>
</tr>
<tr>
<td><input type="password" name="password" maxlength="12" placeholder="Enter password" required /></td>
<td><input id="button" type="submit" name="submit" value="Sign Up" /></td>
</tr>
</table>
</form>
PHP
<?php
$conn=mysqli_connect("localhost", "root", "", "winkcage");
//$im=$_SESSION["pathsession"];
$nam=""; $usernam=""; $phon=""; $pass="";
$nam=$_POST["name"];
$usernam=$_POST["username"];
$phon=$_POST["phone"];
$pass=$_POST["password"];
$signquery="INSERT INTO signup(name, username, phone, password) VALUES('$nam', '$usernam', '$phon', '$pass')";
$signqueryrun=mysqli_query($conn, $signquery);
?>
NOTE: I don't want to insert image value right now. I'll insert it later when this problem is fixed.
You may have entered a ' quote and it killed your sql statement. This is called sql injection. To prevent sql injection you can use pdo prepared statements. You will also want to hash passwords to prevent people from stealling them if they get access to your database. Hashing password is a one way encryption that is easy to check.
$pdo = new PDO("mysql:host=$db_host;dbname=$DB_name", $user, $pass);
$sql = "INSERT INTO signup(name, username, phone, password) VALUES(':name', ':username', ':phone', ':pass')";
if ($con = $pdo->prepare($sql)) {
$con->execute([
':name' => $_POST["name"],
':username' => $_POST["username"],
':phone' => $_POST["username"],
':pass' => $_POST["password"]
]);
}
As far as the html and javascript goes. Catch the submitted form with jquerys .submit() function.
$('form').submit(function(e){
e.preventDefault();
$.post('submit.php',$(this).serialize(),function(response){
alert('complete');
}).error(function(){
alert('wrong');
});
});
This makes sure than any submit event triggers the ajax.
Since you are using a form with a submit button, when you click the button it will submit the form. You may be having a conflict between the AJAX action and the form submit. Try preventing the default action on the button click and see if it works as follows:
$(document).ready(function(){
$("#button").click(function(event){
if($("form").get()[0].checkValidity()){
$.ajax({
url: "submitform.php",
type: "POST",
data: $("form").serialize(),
success: function(data){
alert("well");
},
error: function(){
alert("Error");
}
});
});
}
event.preventDefault();
});
You assign your onclick to a button element, but there is no button element on your page, your button is an input element. Change that to a button and it may work. I personally would advise using ids, rather than element types, I think it makes things clearer, and will allow you to have more than one element of the same type without breaking your code.
Change
$("button").click(function(){
to
$("#button").click(function(){
and
data: $("form").serialize(),
to
data: $("#signupform").serialize(),

Submitting form data through ajax not working

sorry for the dumb question but I can't seem to get this going and I figured I best give you more info than not enough -
I have a form that I am running inside a loop in php like this:
<form name="primaryTagForm'.$post->ID.'" id="primaryTagForm'.$post->ID.'" method="POST" enctype="multipart/form-data" >
<fieldset class="tags">
<label for="post_tags'.$post->ID.'">Tags:</label>
<input type="text" value="" tabindex="35" name="postTags'.$post->ID.'" id="postTags'.$post->ID.'" />
</fieldset>
<fieldset>
<input type="hidden" name="submitted" id="submitted" value="true" />
'.wp_nonce_field( 'post_nonce', 'post_nonce_field' ).'
<button class="button" type="submit">Tag</button>
</fieldset>
</form>
I have tried adding my ajax under that form (Still within the loop so I can grab the post_id) and in my console it my tag-ajax.php file is posted just fine. Here is my weak attempt at that based on this: Save data through ajax jQuery post with form submit and other like questions.
<script>
jQuery(document).ready(function($) {
$(".button").click(function(e) {
e.preventDefault();
$.ajax({
type: "POST",
url: "'.get_stylesheet_directory_uri().'/tags-ajax.php",
data: "primaryTagForm'.$post->ID.'",
success: function(data){
//alert("---"+data);
alert("Tags have been updated successfully.");
}
});
});
});
</script>
And lastly here is what is in my tags-ajax.php file -
if(isset($_POST['submitted']) && isset($_POST['post_nonce_field']) && wp_verify_nonce($_POST['post_nonce_field'], 'post_nonce')) {
wp_set_object_terms( $post->ID, explode( ',', $_POST['postTags'.$post->ID] ), 'product_tag', true );
echo'Success!';
}
So when I try running this a couple of things happen by looking in the console, if I hit submit on one of the forms then all them forms on that page post to tags-ajax.php (Im sure it is because I am doing this in a loop but not sure how else to do it and bring in post->ID on tags-ajax.php)
The second, most important thing is that nothing actually saves, I click the "Tag" but (submit) and I get those success alerts (for each post unfortunately) but when I click through those the tags are not actually saved.
My question: How do I get the data to actually save with the ajax/php and how can I have that post refresh without reloading the page so the user sees they actually were added?
Latest Update: After making the serialize edits mentioned below I submit my form and check the console and see the post method is getting a 500 internal server error.. Im thinking if my problem is coming from because I have the form and an inline script with the ajax running in a loop? So there are technically 20 posts/forms/inline scripts on a page and when you submit one, all of them submit which may be causing the 500 internal error?
The data: option in ajax should be
data: $("#primaryTagForm'.$post->ID.'").serialize(),
Use serialize
You have to change
data: "primaryTagForm'.$post->ID.'",
to
data: $("#primaryTagForm'.$post->ID.'").serialize(),
Simplify your markup. You dont have to use id attributes everywhere. Just include a hidenn tag in your form with the value of $post->id. Also echo the ajax url at the form's acton attribute.
So the html should be similar to this:
<form method="POST" action="' . get_stylesheet_directory_uri() .'/tags-ajax.php" >
<input type='hidden" name="id" value="'.$post->ID.'">
<fieldset class="tags">
<label>Tags:</label>
<input type="text" value="" tabindex="35" name="tags" />
</fieldset>
<fieldset>
<input type="hidden" name="submitted" id="submitted" value="true" />
'.wp_nonce_field( 'post_nonce', 'post_nonce_field' ).'
<button class="button" type="submit">Tag</button>
</fieldset>
</form>
Then you can use a script like this:
jQuery(document).ready(function($) {
$(".button").click(function(e) {
e.preventDefault();
var $target = $(e.target),
$form = $target.closest('form');
$.ajax({
type: "POST",
url: $form.prop('action'),
data: $form.serialize(),
success: function(data){
//alert("---"+data);
alert("Tags have been updated successfully.");
}
});
});
});

Make a Post request with request body from HTML form

I am working on a html page which is supposed to submit a post request with request body to my server like below
<html>
<head>Customer app</head>
<body>
<div>
<table>
<tr>
<td>Customer Id :</td>
<td>
<form name="submitform" method="post">
<input type="text" id="customerId" name="customerId"/>
<input type="submit" value="Submit">
</form>
</td>
</tr>
</table>
</div>
</body>
<script>
$(document).ready(function(){
$("#submitform").click(function(e)
{
var MyForm = JSON.stringify($("#customerId").serializeJSON());
console.log(MyForm);
$.ajax({
url : "http://localhost:7777/ola-drive/customer/ride",
type: "POST",
data : MyForm,
});
e.preventDefault(); //STOP default action
});
});
</script>
</html>
It does not work as expected throwing 404 Not Found getting redirected to http://localhost:7777/customerapp.html. But form data corresponding to the request submission seems to be correct.
Can someone help me fix the issue with my html code submit POST request redirection ?
Your issue is in this line:
$("#submitform").click(function(e)
Your form does not have an id but a name, so you can write:
$('[name="submitform"]').click(function(e)
That is the reason because your form is giving you a redirection error.
$('[name="submitform"]').click(function (e) {
e.preventDefault();
$.ajax({
url: "http://localhost:7777/ola-drive/customer/ride",
type: "POST",
data: {"customerId": $("#customerId").val()},
success: function (result) {
//do somthing here
}
});
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div>
<table>
<tr>
<td>Customer Id :</td>
<td>
<form name="submitform" method="post">
<input type="text" id="customerId" name="customerId"/>
<input type="submit" value="Submit">
</form>
</td></tr>
</table>
</div>
You are already created form using html, you can add action attrbiute with value for post url like
<form name="submitform" method="post" action="/ola-drive/customer/ride">
Unless you want to use ajax, you create your data form manually
you have this:
$("#submitform").click(function(e){...}
The first problem is you are selecting an input tag, instead the Form. The second is rather the action desired, in this case should be "submit". And if you already are using JQuery you might be interested in save some space using the method 'serialize()'. Try:
$('form').on('sumbit', function(e){
e.preventDefault();
$.ajax({
url: // your path
type: 'post',
data: $(this).seialize(),
...})
})
And use an id for Form, it's easier to select it.

Categories

Resources