I'm having a issue submitting my form. I'm trying to a make a multi-step form with Flask and bit of JS. The basic HTML structure of the form is:
<form id="regForm" action="{{ url_for("index")}}" method="post" enctype="multipart/form-data">
<div class="tab"> <!--Some fields--> </div>
<div class="tab"> <!--Some fields--> </div>
<div class="tab"> <!--Some fields--> </div>
<div class="tab"> <!--Some fields--> </div>
<!--Buttons to change tabs-->
<button type="button" id="prevBtn" onclick="nextPrev(-1)">Previous</button>
<button type="button" id="nextBtn" onclick="nextPrev(1)">Next</button>
The nextPrev() functions are in a file called scripts.js. This is directly from a W3 schools example. It is as follows:
var currentTab = 0;
showTab(currentTab);
function showTab(n) {
var x = document.getElementsByClassName("tab");
x[n].style.display = "block";
if (n == 0) {
document.getElementById("prevBtn").style.display = "none";
} else {
document.getElementById("prevBtn").style.display = "inline";
}
if (n == (x.length - 1)) {
document.getElementById("nextBtn").innerHTML = "Submit";
} else {
document.getElementById("nextBtn").innerHTML = "Next";
}
fixStepIndicator(n)
}
function nextPrev(n) {
var x = document.getElementsByClassName("tab");
if (n == 1 && !validateForm()) return false;
x[currentTab].style.display = "none";
currentTab = currentTab + n;
if (currentTab >= x.length) {
document.getElementById("regForm").submit();
return false;
}
showTab(currentTab);
}
The document.getElementById("regForm").submit(); line should be submitting the form, since I see the button text changing to 'Submit' on the last slide. This isn't submitting it to my app though. The app looks for a POST request to / .
from flask import Flask, request, render_template, redirect, url_for
import os
def create_app():
app = Flask(__name__)
assets._named_bundles = {}
register_extensions(app)
#app.route("/", methods =["GET", "POST"])
def index():
if request.method == "POST":
# Do a bunch of stuff
return render_template("index.html")
Why is this not sending a request to my Python script?
The above code is minimal, I've uploaded a gist with the full code for Flask, JS, HTML.
I've created a codesandbox with my code here, you can also view the form itself here.
Have you added csrf_protection in your app?
If you did, Then do csrf.protection.exempt()
Related
i am trying to make a multi-step questionnaire where there are 3 steps. This questionnaire allows users to input their desired answers and will return company names that are in the selected category, features and integration needed. This data is stored in the MySQL database, i will attach a diagram of the schema.
Diagram
Step 1 is category, uses radio button as only one can be selected.
Step 2 is Features, uses checkbox as multiple items can be selected
Step 3 is integration, uses radio button as only one can be selected.
The way i have tried to implement this is to include the user input value into the SQL select query and then use the results as the next step values. The issue i have is, as it is multi-step the second query does not run until the full questionnaire is submitted. Also i get the feeling this not the right way to do it as questions will not load if the database does not respond quickly.
Can i implement Javascript to do the multi-step logic and then run one query at the end? i am kind of lost on how to go about this.
Any help with be greatly appreciated.
App.py
#app.route('/home', methods = ['GET', 'POST'])
def home():
firstInput = ''
myresult2 = ''
sqlFirst = 'SELECT DISTINCT * FROM categories;'
if request.method == 'POST':
firstInput = request.form.get('cat_in')
my_data = (firstInput,)
fetchFetch = 'SELECT distinct features.features, categories.categories, mytable.cat_FK_KEY, categories.categoryID, mytable.Categories FROM mytable, features, nameFeatures, categories WHERE mytable.id = `nameFeatures`.`name_FK_ID` and features.featureID = nameFeatures.feature_FK_ID and mytable.cat_FK_KEY = categories.categoryID and categories.categoryID = %s;'
cursor.execute(fetchFetch, my_data)
myresult2 = cursor.fetchall()
cursor.execute(sqlFirst)
myresult = cursor.fetchall()
return render_template('index.html', firstInput=firstInput, myresult=myresult, myresult2=myresult2)
index.html
<form id="regForm" action="" method="post">
<div class="tab">Please pick a Category:
{% for row in myresult %}
<input type="radio" id="{{row[0]}}" oninput="this.className = ''" name="cat_in" value="{{row[0]}}">
<label for="{{row[0]}}">{{row[1]}}</label><br>
{% endfor %}
</div>
<div class="tab">Select the features:
<p>{{firstInput}}</p>
{% for row in myresult2 %}
<input type="checkbox" id="{{row[0]}}" oninput="this.className = ''" name="feature_in" value="{{row[0]}}">
<label for="{{row[0]}}">{{row[0]}}</label><br>
{% endfor %}
</div>
<div class="tab">Which intergration:
</div>
<div style="overflow:auto;">
<div style="float:right;">
<button type="button" id="prevBtn" onclick="nextPrev(-1)">Previous</button>
<button type="button" id="nextBtn" onclick="nextPrev(1)">Next</button>
</div>
</div>
<!-- Circles which indicates the steps of the form: -->
<div style="text-align:center;margin-top:40px;">
<span class="step"></span>
<span class="step"></span>
<span class="step"></span>
<span class="step"></span>
</div>
</form>
<script>
var currentTab = 0; // Current tab is set to be the first tab (0)
showTab(currentTab); // Display the current tab
function showTab(n) {
// This function will display the specified tab of the form...
var x = document.getElementsByClassName("tab");
x[n].style.display = "block";
//... and fix the Previous/Next buttons:
if (n == 0) {
document.getElementById("prevBtn").style.display = "none";
} else {
document.getElementById("prevBtn").style.display = "inline";
}
if (n == (x.length - 1)) {
//document.getElementById("nextBtn").innerHTML = "Submit";
document.getElementById("nextBtn").submit();
} else {
document.getElementById("nextBtn").innerHTML = "Next";
}
//... and run a function that will display the correct step indicator:
fixStepIndicator(n)
}
function nextPrev(n) {
// This function will figure out which tab to display
var x = document.getElementsByClassName("tab");
// Exit the function if any field in the current tab is invalid:
if (n == 1 && !validateForm()) return false;
// Hide the current tab:
x[currentTab].style.display = "none";
// Increase or decrease the current tab by 1:
currentTab = currentTab + n;
// if you have reached the end of the form...
if (currentTab >= x.length) {
// ... the form gets submitted:
document.getElementById("regForm").submit();
return false;
}
// Otherwise, display the correct tab:
showTab(currentTab);
console.log(currentTab);
}
function validateForm() {
// This function deals with validation of the form fields
var x, y, i, valid = true;
x = document.getElementsByClassName("tab");
y = x[currentTab].getElementsByTagName("input");
// A loop that checks every input field in the current tab:
for (i = 0; i < y.length; i++) {
// If a field is empty...
if (y[i].value == "") {
// add an "invalid" class to the field:
y[i].className += " invalid";
// and set the current valid status to false
valid = false;
}
}
// If the valid status is true, mark the step as finished and valid:
if (valid) {
document.getElementsByClassName("step")[currentTab].className += " finish";
}
console.log(valid);
return valid; // return the valid status
}
function fixStepIndicator(n) {
// This function removes the "active" class of all steps...
var i, x = document.getElementsByClassName("step");
for (i = 0; i < x.length; i++) {
x[i].className = x[i].className.replace(" active", "");
}
//... and adds the "active" class on the current step:
x[n].className += " active";
}
</script>
i have input form to upload you file and submitting that file(method = post) i need to cheack if user upload the image or not. if not should display error message and return false. but in my case return false don't working
my code
const jobs = document.getElementById("jobImage");
const error = document.getElementById("Error");
my function
function func(){
if(jobs.value < 1){
console.log("1")
error.style.display = "block";
error.textContent = "Pleas upload your image";
setTimeout(function(){ window.location.reload(); },5000);
return false
}
}
when i use my function its return true not false
<div class="form-group">
<div class="col-md-offset-2 col-md-10">
<button type="submit" value="Save" class="btn btn-default" id="save" onclick="func()">Go now</button>
</div>
</div>
</div>
best regards
you must change if to :
if( jobs.files.length == 0 ){
...
}
Python Code
from flask import Flask, render_template
app = Flask(__name__)
#app.route("/")
def button():
return render_template("buttons.html")
if __name__ == "__main__":
app.run(debug=True)
HTML Code
<!DOCTYPE html>
<html>
<head>
<title>Creating new channel</title>
<script src="{{url_for('static', filename = 'js/button.js')}}"></script>
</head>
<body>
<ul class="unordered"></ul>
<form>
<input type="text" class="name" placeholder="Create Channel" autocomplete="off" />
<button class="submit">Create Channel</button>
</form>
</body>
</html>
Javascript code
document.addEventListener('DOMContentLoaded', () => {
document.querySelector('.submit').disabled = true;
document.querySelector('.name').onkeyup = () => {
// checking whether the input bar is empty or not
if (document.querySelector('.name').value.length > 0)
document.querySelector('.submit').disabled = false;
else
document.querySelector('.submit').disabled = true;
};
document.querySelector('.form').onsubmit = () => {
//Crearting a list item
const li = document.createElement('li');
li.innerHTML = document.querySelector('.name').value;
//Appending it to the unordered list
document.querySelector('.unordered').append(li);
//Clear input feild
document.querySelector('.name').value = '';
document.querySelector('.submit').disabled = true;
//Stop form from submitting
return false;
};
});
When i run this code seperately, meaning when i only run the HTML file in the webpage than the program runs perfectly (when you press the button then whatever is in the input feild, shows up as an unordered list). But when i am using the html file in a python file, it doesn't work(when i press the button the page refreshes and nothing happens)
I am trying to use a simple jquery/php newsletter script. The script works fine. As I enter name and email and hit the submit button, it saves data into a .txt file, and display a success message along with the form. Now, I would like to modify the script. I do not want the form to be seen as I hit the submit, instead it should show the success message only "Thank you." Being very novice to javascript, I have so far figured out that I need to "fadeOut" the form after clicking the submit button.
I think the code might be look like
$("#submit").on("click", function(e) {
e.stopImmediatePropagation();
$("#signup").fadeOut(280, function() {
// callback method to display new text
// setup other codes here to store the e-mail address
$(this).after('<p id="success">Thank you</p>');
});
});
I have tried to integrate this code, but due to my limited JS experience I cannot do it successfully.
Here is my original jquery script
var error_1 = "Please enter your valid email address";
var error_2 = "Please enter your name";
var thankyou = "Thank you";
function trim(str) {
str = str.replace(/^\s*$/, '');
return str;
}
function $Npro(field) {
var element = document.getElementById(field);
return element;
return false;
}
function emailvalidation(field, errorMessage) {
var goodEmail = field.value.match(/[a-zA-Z0-9!#$%&'*+/=?^_`{|}~-]+(?:\.[a-zA-Z0-9!#$%&'*+/=?^_`{|}~-]+)*#(?:[a-zA-Z0-9](?:[a-zA-Z0-9-]*[a-zA-Z0-9])?\.)+[a-zA-Z0-9](?:[a-zA-Z0-9-]*[a-zA-Z0-9])?/);
apos = field.value.indexOf("#");
dotpos = field.value.lastIndexOf(".");
lastpos = field.value.length - 1;
tldLen = lastpos - dotpos;
dmLen = dotpos - apos - 1;
var badEmail = (tldLen < 2 || dmLen < 2 || apos < 1);
if (!goodEmail || badEmail) {
$Npro("Error").innerHTML = errorMessage;
$Npro("Error").style.display = "inline";
field.focus();
field.select();
return false;
} else {
return true;
}
}
function emptyvalidation(entered, errorMessage) {
$Npro("Error").innerHTML = "";
with(entered) {
if (trim(value) == null || trim(value) == "") { /*alert(errorMessage);*/
$Npro("Error").innerHTML = errorMessage;
$Npro("Error").style.display = "inline";
return false;
} else {
return true;
}
} //with
} //emptyvalidation
function signup(thisform) {
with(thisform) {
if (emailvalidation(email, error_1) == false) {
email.focus();
return false;
};
if (emptyvalidation(name, error_2) == false) {
name.focus();
return false;
};
}
$("#submit, #myResponse").hide(); // Hide the buttom and the message
$("#loading").show(); // show the loading image.
params = $("#subform").serialize();
$.post("optIn.php", params, function(response) {
//alert(response); //may need to activate this line for debugging.
$("#loading").hide();
$("#myResponse").html(thankyou); //Writes the "Thank you" message that comes from optIn.php and styles it.
$('#myResponse').css({
display: 'inline',
color: 'green'
})
$("#submit").show();
})
return false;
}
Here is the html markup
<form onSubmit="return signup(this);return false;" method="post" name="subform" id="subform" action="
<?php echo optIn.php ?>">
<div>
<span style="FONT-FAMILY: Arial; FONT-SIZE: 12pt; font-weight:bold;">Subscribe to our newsletter</span>
</div>
<div style="margin-top:20px">
<div>
<label style="display: inline-block;width:135px">Email:</label>
<input type="text" id="email" name="email" value="">
</div>
<div>
<label style="display: inline-block;width:135px">Name:</label>
<input type="text" name="name" id="name" value="">
</div>
<div>
<div style="display:inline-block;width:135px;"> </div>
<input type="submit" id="submit" name="submit" value="Sign up">
</div>
<div style="width:100%">
<span id="Error" style="color:red;display:none;"></span>
</div>
<div id="myResponse" style="DISPLAY:none;"></div>
<div id="loading" style="display:none;">
<img src="wait.gif" alt="">
</div>
</div>
</form>
Here is my php code:
<?php
//ini_set('display_errors', 0);
header ("Expires: Mon, 26 Jul 1997 05:00:00 GMT");
header("Cache-Control: no-store, no-cache, must-revalidate");
header("Pragma: no-cache");
$email = trim(htmlspecialchars($_REQUEST["email"]));
$name = trim(htmlspecialchars($_REQUEST["name"]));
$pfileName = "mails.txt";
$MyFile = fopen($pfileName, "a");
$nline="\"".$email."\"" ."," ."\"".$name."\"" ."\r\n";
fwrite($MyFile, $nline);
fclose($MyFile);
die;
?>
Try providing a .delay() so that the fadeOut() function has finished before attempting to display the success message:
$("#submit").on("click", function(e) {
e.stopImmediatePropagation();
$("#signup").delay(500).fadeOut(280, function() {
$(this).after('<p id="success">Thank you</p>');
});
});
If I understand you correctly you want the user to submit the information via your html form. Then you want the form to go away after you hit the submit button.
From reading the JQuery method you have tried I found one mistake that is preventing your form from fading out. You were using the wrong id for your form in your JQuery code(it should be subform according to your html). Note that I removed your PHP code so that I could create an example in jsfiddle for you. My sample posts to google.com to prevent your from getting an error page displayed in the results sections.
jsfiddle: fade out form on submission
$("#submit").on("click", function(e) {
//changed from e.stopImmediatePropogation()
e.preventDefault();
//#subform is the actual id of your form, you were using signup
$("#subform").fadeOut(280, function() {
// callback method to display new text
// setup other codes here to store the e-mail address
$(this).after('<p id="success">Thank you</p>');
});
});
I am new one to Asp.Net Mvc4 with Entity Framework. Now i am doing Captcha verification for Forgot Password. As my code, I it is passing the Email id value to Controller when i am clicking submit button even the Captcha code is Invalid. I want to pass the Email id value to controller if the Captcha code is correct otherwise it should show the validation error and New captcha should get reloaded. Please help me to fix it. Thanks in advance.
This is my Java Script code for generation and validating the captcha:
var captchastring = '';
function getCaptcha() {
var chars = "0Aa1Bb2Cc3Dd4Ee5Ff6Gg7Hh8Ii9Jj0Kk1Ll2Mm3Nn4Oo5Pp6Qq7Rr8Ss9Tt0Uu1Vv2Ww3Xx4Yy5Zz";
var string_length = 7;
captchastring = '';
for (var i = 0; i < string_length; i++) {
var rnum = Math.floor(Math.random() * chars.length);
captchastring += chars.substring(rnum, rnum + 1);
}
document.getElementById("randomfield").innerHTML = captchastring;
}
function validation() {
var text2 = document.getElementById("txtcode").value;
if (text2 == captchastring) {
var email = document.getElementById("UserEmail").value;
x = document.getElementById("demo");
// Find the element
x.innerHTML = "valid";
x.style.color = "#ff0000";
}
else {
x = document.getElementById("demo"); // Find the element
x.innerHTML = "Invalid Captcha. Try again";
x.style.color = "#ff0000";
}
}
</script>
This is my body of my cshtml code:
<div class="col-md-5">
#using (Html.BeginForm())
{
#Html.ValidationSummary(true)
<h5 class="nomargin">Forgot Password</h5>
#Html.TextBoxFor(u => u.UserEmail, new { #class = "form-control", placeholder = "Email" })
<br />
<div id="captcha">
<div id="captcha_gen">
<label id="randomfield">
</label>
</div>
<button type="button" onclick="getCaptcha();" style="border: 0; background: transparent;float:right; position:relative";>
<img src="../../Content/FSLBootstrapUI/images/playback_reload.png" width="25" height="25" alt="submit" />
</button>
</div>
<input type="text" id="txtcode" class="form-control" placeholder="Enter code here" />
<button class="btn btn-success btn-block" value="submit" onclick="validation()">Reset</button> <p id="demo"> </p>
}
</div>
What is happening currently? I mean, how is the application behaving?
EDIT:
You can try server side validation for example if you have a field to validate you can add a validation tag there.For example:
<input type="text" name="SampleTextBox" id="SampleTextBoxId"/>
#Html.ValidationMessage("SampleTextBox", "*")
Then you go to the controller and add this kind of code:
if (!string.IsNullOrEmpty(SampleTextBox))
{
//Your Code.
}
else
{
ViewData.ModelState.AddModelError("SampleTextBoxId", "Text should not be empty.");
}
Use Model.IsValid as your condition to write your main code.
Model.IsValid becomes False if ViewData.ModelState.AddModelError("SampleTextBoxId", "Text should not be empty."); is executed.
This is a way to add validations. You can check for your valid/invalid captcha in your controller itself and throw error.
For Example:
if (IsValidCaptcha(enteredCaptcha))
{
//Code
}
else
{
ViewData.ModelState.AddModelError("captchaId", "Enter valid captcha");
}
Lastly, add a validation summary to your page
#Html.ValidationSummary("Error Messages")