I have some html5 form fields on a website that I manage that push the data inputted by users to a php file that sends an email to a dedicated yahoo email for the site.
Here is the html:
<form role="form" method="post" action="php/contact-us.php" lang="es" id="contactForm">
<div class="row">
<div class="form-group col-lg-4 required">
<label for="name">Name</label>
<input type="text" class="form-control" name="name" required placeholder="Enter Name" />
</div>
<div class="form-group col-lg-4 required">
<label for="email">Email</label>
<input type="email" class="form-control" name="email" required placeholder="Enter valid email" />
</div>
<div class="form-group col-lg-4">
<label for="phone">Phone Number</label>
<input type="tel" class="form-control" name="phone" placeholder="e.g. (000) 000 - 0000">
</div>
<div class="clearfix"></div>
<div class="form-group col-lg-12 required">
<label for="message">Mensaje</label>
<textarea class="form-control" rows="6" name="message" required placeholder="Write your message here"></textarea>
</div>
<div class="form-group col-lg-12">
<input type="hidden" name="save" value="contact">
<button type="submit" class="btn btn-default">Enviar</button>
</div>
</div>
</form>
Before, I did not have any validation on the fields, but I was getting empty emails with no user content so I thought people are just pushing the button without entering anything which I could also test myself. So I added the following validation JS, also eused webshim for unsupported browsers (and the required tags in the form elements above):
<script>
$('#contactForm input[type=text], select, textarea').on('change invalid', function() {
var field = $(this).get(0);
field.setCustomValidity('');
if (!field.validity.valid) {
field.setCustomValidity('Please fill required fields');
}
});
$('#contactForm input[type=email]').on('change invalid', function() {
var field = $(this).get(0);
field.setCustomValidity('');
if (!field.validity.valid) {
field.setCustomValidity('Enter a valid email');
}
});
</script>
Previously I was getting the inputted email form the user and setting it as the senders email but I was having issues with certain email addresses, etc. So I defaulted it to a random email that would always work and just included the users inputted email in the message. Here is my php file (contact-us.php):
<?php
// Set your email below
$to = "<dedicatedemail>#yahoo.com";
// Receive and sanitize input
$name = $_POST['name'];
$email = $_POST['email'];
$phone = $_POST['phone'];
$message = $_POST['message'];
$subject = "Request from website";
$headers = "From: no-reply#gmail.com";
// set up email
$msg = "Sender Information \nName: " . $name . "\nEmail: " . $email . "\nPhone: " . $phone . "\n\n" . $message;
$msg = wordwrap($msg,70);
// mail
mail($to,$subject,$msg,$headers);
header('Location: ../contact-thank-you.html');
?>
So first let me say that everything is working. When I test the functionality here everything works. I am able to send an email from my ios device and my laptop and I have had a couple friends send from their android devices. The validation works for me so it does not let me send an email without at least filling the required fields out. I was getting empty emails before I added validation and setting the sender email to a default one. However I still get empty emails even after all the changes. When I test I cannot test across all platforms and browsers but I cannot force an empty email after I added checks. Is my validation failing somewhere? I feel like people are filling in the fields but somehow the email is coming in empty. When I say empty I mean the stuff that I programmatically add to the message comes through but the actual info that the user is suppose to input does not? How is this happening?
Always perform server side validation and confirm there is a POST incoming. Otherwise even something as simple as a webcrawler will tigger empty emails.
<?php
if (empty($_POST['email']) || empty($_POST['name'])) {
// Respond with a proper error message
...
} else {
// Send email
$to = "<dedicatedemail>#yahoo.com";
$name = $_POST['name'];
$email = $_POST['email'];
...
}
Related
I am trying to build a contact form that uses bootstrap form HTML structure and PHP to control the backend validation and send the form information to my email.
Right now whenever I hit the submit button, I get a 404 Not Found Error which I assume has to do with the HTML not communicating the correct way with my PHP code. My website is 100% live (being hosted through NameCheap), and have been using cPanel's File Manager to upload all HTML, CSS, Image, and PHP files. I followed a Youtube tutorial on what the PHP should look like to validate my form's data and send it to my email.
I hadn't tried the $invalid_class_name aspect of the code yet, as I was trying to get the data to pass successfully first. I have the contact-form.php file in the same location as my HTML file, but I am wondering if I need to save my index.html file as a PHP file to make this work or an extra PHP plug-in on my website.
I have this PHP code included in HTML right above my form code
<?php
if($message_sent);
?>
<h3>Thanks,we'll be in touch</h3>
<?php
else:
?>
HTML
<form name=”contact_form” action=”contact-form.php” method=”POST” class="row g-4">
<div class="col-md-6">
<label for="first-name" class="form-label">First Name</label>
<input type="text" name="first-name" class="form-control" id="first-name" placeholder="John" required>
</div>
<div class="col-md-6">
<label for="last-name" class="form-label">Last Name</label>
<input type="text" name="last-name" class="form-control" id="last-name" placeholder="Smith" required>
</div>
<div class="col-md-6">
<label for="email" class="form-label">Email</label>
<input type="email" name="email" class="form-control" id="email-address" required>
</div>
<div class="col-md-12">
<label for="notes" class="form-label">Notes</label>
<textarea class="form-control" name="notes" id="notes" rows="4" placeholder="Include any additional information"></textarea>
</div>
<div class="col-12">
<button type="submit" class="pcs-cta-button form-submit-button">Submit</button>
</div>
</form>
PHP
<?php
$message_sent = false;
if (isset($_POST['email'])) && $_POST['email'] !='') {
if(filter_var($_POST['email'], FILTER_VALIDATE_EMAIL) ){
//submit the form
$userFirstName = $_POST['first-name'];
$userLastName = $_POST['last-name'];
$userEmail = $_POST['email'];
$message = $_POST['notes'];
$to = "myemail#gmail.com";
$body = "";
$body .= "From: ".$userFirstName." ".$userLastName "\r\n";
$body .= "Email: ".$userFirstName. "\r\n";
$body .= "Notes: ".$message. "\r\n";
mail($to, $messageSubject, $body);
$message_sent = true;
}
else {
$invalid_class_name = "form-invalid";
}
}
?>
This is because you are using ” instead of " in action of the form (and generally form attributes)
Change this:
<form name=”contact_form” action=”contact-form.php” method=”POST” class="row g-4">
to this:
<form name="contact_form" action="contact-form.php" method="POST" class="row g-4">
Now your browser tries to GET "%E2%80%9Dcontact-form.php%E2%80%9D" instead of "contact-form.php". And yes, it tries GET (default method) not POST, as your form method is invalid as well (same reasons - wrong quotation marks).
Closed. This question needs details or clarity. It is not currently accepting answers.
Want to improve this question? Add details and clarify the problem by editing this post.
Closed 1 year ago.
Improve this question
Really struggling with this one, didn't think a simple form would be this complicated. I'm a newbie when it comes to the back-end.
I have 3 fields; name, email, and message. On submit, I just want a simple "thank you" message inside the form box. I do not want to send to another page or refresh to the top of the current page. I want the form to refresh with the 'thank you' message, ideally with the message disappearing after a few seconds.
After trying a few different methods I am almost there with JS, using an event listener to show the "thank you" message after clicking submit.
However, now the contact form doesn't refresh on submit and the data that was inputted still shows on the form along with the thank you message. How do you get the form to refresh on submit?
I have always used WordPress, and contact forms seemed so simple. I have spent hours on this so far.
HTML
<div class="form-box">
<p id="thank-you-message">
Thank you for your message. We will be in touch with you very soon.
</p>
<form method="POST" action="contact-form.php" >
<div class="form-control">
<input class="text-box" id="name" name="name" type="text" placeholder="Your Name*" required>
<input class="text-box" id="email" name="email" type="email" placeholder="Your Email Adress*" required>
</div>
<div>
<textarea id="message" name="message" placeholder="Project Details" required></textarea>
<button class="send" name="submit" type="submit">SEND</button>
</div>
</form>
PHP
<?php
if(isset($_POST['email']) && $_POST['email'] !='') {
$name = $_POST['name'];
$visitor_email = $_POST ['email'];
$message = $_POST ['message'];
$email_from = 'website.com';
$email_subject = "New Form Submission";
$email_body = "User Name: $name.\n".
"User Email: $visitor_email.\n".
"User Message: $message.\n";
$to = "contact#email.com";
$headers = "From: $email_from \r\n";
$headers .= "Reply-To: $visitor_email \r\n";
mail($to,$email_subject,$email_body,$headers);
header("Location: index.html");
}
?>
JS
const form = document.querySelector('form');
const thankYouMessage = document.querySelector('#thank-you-message');
form.addEventListener('submit', (e) => {
e.preventDefault();
thankYouMessage.classList.add('show');
setTimeout(() => form.submit(), 2000);
});
#James Bakker
HTML
<form method="POST" action="contact-form.php" >
<?php echo $successMessage ?>
<div class="form-control">
<input type="hidden" name="valid" value="false">
<input class="text-box" id="name" name="name" type="text" placeholder="Your Name*" required>
<input class="text-box" id="email" name="email" type="email" placeholder="Your Email Adress*" required>
</div>
<div>
<textarea id="message" name="message" placeholder="Project Details" required></textarea>
<button class="send" name="button" type="submit">SEND</button>
</div>
</form>
JS
const form = document.querySelector('form');
form.addEventListener('submit', (e) => {
e.preventDefault();
form.valid.value = 'true';
consultForm.submit();
});
PHP
<?php
$successMessage == '';
if($_POST['valid'] == 'true'){
$name = $_POST['name'];
$visitor_email = $_POST ['email'];
$message = $_POST ['message'];
$email_from = 'website.com';
$email_subject = "New Form Submission";
$email_body = "User Name: $name.\n".
"User Email: $visitor_email.\n".
"User Message: $message.\n";
$to = "contact#email.com";
$headers = "From: $email_from \r\n";
$headers .= "Reply-To: $visitor_email \r\n";
$header("Location: index.html");
$success = mail($to,$email_subject,$email_body,$headers);
if ($success){
$successMessage = 'Your Message was sent!';
} else {
$successMessage = 'There was a problem, message was not sent';
}
}
?>
If you were to use fetch or regular XMLHttpRequest you can use the callback to manipulate the DOM after the data has been sent to the backend PHP script.
The PHP script that handles the request will no longer require the header('Location: index.html'); - instead you could echo/return a message to be used by the ajax callback.
The below is not tested as such
document.addEventListener('DOMContentLoaded',()=>{
let form=document.querySelector('form');
form.querySelector('button[type="submit"]').addEventListener('click',e=>{
e.preventDefault();
fetch( 'contact-form.php' , { method:'post', body:( new FormData( e.target.parentNode.parentNode ) ) } )
.then( r=>r.text() )
.then( data=>{
//show the message
document.querySelector('#thank-you-message').classList.add('show');
//iterate through form elements and set the value to empty string if it is not a button
for( i=0; i<form.elements.length; i++ ){
let el=form.elements[i]
if( el.type!='button' )el.value='';
}
// remove the button
e.target.parentNode.removeChild(e.target);
})
})
});
<div class="form-box">
<p id="thank-you-message">
Thank you for your message. We will be in touch with you very soon.
</p>
<form method="POST" action="contact-form.php" >
<div class="form-control">
<input class="text-box" id="name" name="name" type="text" placeholder="Your Name*" required>
<input class="text-box" id="email" name="email" type="email" placeholder="Your Email Adress*" required>
</div>
<div>
<textarea id="message" name="message" placeholder="Project Details" required></textarea>
<button class="send" name="submit" type="submit">SEND</button>
</div>
</form>
</div>
The short answer is: You need to change the name attribute of your submit button to something other than submit, then you will be able to call form.submit() using your JS.
Currently your page works as such:
User enters info and clicks submit
Your JS captures the event and
prevents default action
You display the thank you message and then
submit() the form.
The problems with this approach are:
The thank you message is displayed before the actual message is sent.
There is no form validation
The message is only displayed for 2 seconds, and only before the actual email is sent.
A better approach is:
User fills out form and clicks submit
JS captures the event, prevents default, validates all of the data, and if everything is valid if submits the form, POSTing the form values to the current page, this will reload the page and clear the form fields.
Your PHP script will take the POSTed variables, send the email, and display your thank you message on the page.
The advantages are:
You don't display a message until the email is actually sent
You are making sure the form has valid entries
Your message is displayed after refresh and wont disappear after 2 seconds
Heres how, (code isn't tested):
Make a hidden input in your form with the name 'valid':
<input type="hidden" name="valid" value="false">
Once the your JS has validated the inputs you would set this to true and submit() the form. This will post the variable to your PHP along with the rest of the form values.
form.valid.value = 'true';
consultForm.submit();
in your php you write an if statement:
$successMessage == '';
create empty variable success message than we will assign a message if a form submission is detected.
if($_POST['valid] == 'true'){ //keep in mind we are passing a string
not an actual boolean
//insert your php email script here
$success = mail($to,$email_subject,$email_body,$headers);
//assigning return value of mail() to variable named success
if($success){
$successMessage = 'Your Message was sent!'
} else {
$successMessage = 'There was a problem, message was not sent'
}
you can then echo $successMessage anywhere in your HTML.
<?php echo $successMessage ?>
when the page is initially loaded, before the form submit, $successMessage will be an empty string, so echo $successMessage will have no affect on the page.
I have this basic PHP form and I'd like to prevent the page from refreshing after pressing the submit button. Or more like, I would like to have a confirmation paragraph created after the form is sent.
I'm very close, but the paragraph is not getting displayed I think because the page is getting refreshed.
if($_POST["submit"]) {
$recipient="contact#d.com";
$subject="Form to email message";
$sender=$_POST["sender"];
$senderEmail=$_POST["senderEmail"];
$message=$_POST["message"];
$mailBody="Name: $sender\nEmail: $senderEmail\n\n$message";
mail($recipient, $subject, $mailBody, "From: $sender <$senderEmail>");
$thankYou="<div class='thanksDiv'><p>Thank you! Your message has been sent. I'll get back to you ASAP. <i class='as fa-smile-beam'></i></p><a style='cursor:pointer' class='thanksExit'><i class='fas fa-times fa-2x'></i></a></div>";
}
<form id="myForm" name="myemailform" method="post" action="index.php">
<div class="inline">
<label>Name</label>
<input id="firstName" required placeholder="e.g: Emma" type="text" size="32" name="sender" value="">
</div>
<div class="inline">
<label>Email</label>
<input autocomplete="off" required id="email" type="email" placeholder="e.g: EmmaSmith#example.com" name="senderEmail">
</div>
<div class="inline">
<label>How can I help?</label>
<textarea id="textarea" required placeholder="Type a message here..." name="message"></textarea>
</div>
<input type="submit" name="submit" value="Submit">
<?=$thankYou ?>
</form>
Note: I've tried the preventDefault function and Ajax and they didn't work.
Thank you!
They are different ways and approaches to resolve that issue.
How I do it:
I have a processing php that will receive the post and send the email then I redirect the user to a thanks page.
header("location: thanks.php);
exit();
You can also use ajax, and disable the button once it is pressed. It depends on the developer, framework and programming preferences.
You will first need to send some data back to your AJAX from PHP.
session_start();
if(isset($_POST["submit"])) {
$recipient="contact#d.com";
$subject="Form to email message";
$sender=$_POST["sender"];
$senderEmail=$_POST["senderEmail"];
$message=$_POST["message"];
$mailBody="Name: $sender\nEmail: $senderEmail\n\n$message";
mail($recipient, $subject, $mailBody, "From: $sender <$senderEmail>");
$thankYou="<div class='thanksDiv'><p>Thank you! Your message has been sent. I'll get back to you ASAP. <i class='as fa-smile-beam'></i></p><a style='cursor:pointer' class='thanksExit'><i class='fas fa-times fa-2x'></i></a></div>";
echo $thankYou;
}
Now your PHP will send the HTML back to the AJAX Call.
$(function() {
$("#myForm").submit(function(e) {
e.preventDefault();
$.post($(this).attr("action"), $(this).serialize(), function(result) {
$(this).append(result);
});
});
});
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<form id="myForm" name="myemailform" method="post" action="index.php">
<div class="inline">
<label>Name</label>
<input id="firstName" required placeholder="e.g: Emma" type="text" size="32" name="sender" value="">
</div>
<div class="inline">
<label>Email</label>
<input autocomplete="off" required id="email" type="email" placeholder="e.g: EmmaSmith#example.com" name="senderEmail">
</div>
<div class="inline">
<label>How can I help?</label>
<textarea id="textarea" required placeholder="Type a message here..." name="message"></textarea>
</div>
<input type="submit" name="submit" value="Submit">
</form>
In this JavaScript, you will notice, I make use of the Event object for the Submit Callback. This allows me to use .preventDefault() properly.
Trying to put the message into your Session is fine, yet it requires loading another page to call up a session. PHP is only executed before the web server sends the HTML to the Web Browser. With AJAX, the Post request is being performed "in the background", so data can be sent back in HTML, Text, JSON, or XML without the need to reload or redirect. The JavaScript can then work with that data on the same page, no "flicker".
In this case, we append the HTML to the Form, so once the message has been sent via PHP mail(), the User will see the Thank You message.
Update
Consider the following PHP alternate code.
<?php
if(isset($_POST["submit"])) {
$recipient = "contact#d.com";
$subject = "Form to email message";
$sender = $_POST["sender"];
$senderEmail = $_POST["senderEmail"];
$message = wordwrap($_POST["message"], 70, "\r\n");
$headers = "From: $sender <$senderEmail>\r\n";
$headers .= "Reply-To: $senderEmail\r\n";
$headers .= "X-Mailer: PHP/" . phpversion() . "\r\n";
$headers .= "X-Originating-IP: " . $_SERVER['REMOTE_ADDR']
$mailBody="Name: $sender\r\nEmail: $senderEmail\r\n\r\n$message";
var $res = mail($recipient, $subject, $mailBody, $headers);
if($res){
echo "<div class='thanksDiv'><p>Thank you! Your message has been sent. I'll get back to you ASAP. <i class='as fa-smile-beam'></i></p><a style='cursor:pointer' class='thanksExit'><i class='fas fa-times fa-2x'></i></a></div>";
} else {
echo "<div class='mailError'><p>Sorry, there was an error sending your message. Please check the details and try submitting it again.</p></div>";
}
}
Some solutions:
If the user does not need to stay on the same page then as Vidal posted, redirect to a success/thank you page.
If the user needs to stay on the same page then you have a few options:
Method A:
Set session with a form identifier (anything) if nothing is posted (i.e. initial page load). e.g. if(!isset($_POST['field'])){ $_SESSION['....
When form is submitted, check that session exists with the form identifier and process then destroy session.
Now if it's refreshed, the session won't exist, you can inform user that it's already submitted
Problem with this is that if session has timed out and the refresh is done, it will go through.
Method B:
Disable refresh: https://stackoverflow.com/a/7997282/1384889
Method C:
Check database for repeat entry
Method D: (I don't like this but it's used plenty)
Reload same page with '&t='.time() appended to URL by php header() or javascript depending on where your script is executed.
I have a form.php file that redirects to a sendformdata.php file when I submit the form. However, I can't get the sendformdata.php file to display an error message within the form when the proper fields aren't filled out.
I am simply redirected to the include file, db_connect.php, which shows up as a blank page. How can I get the page to stay on form.php and display an error message in html? This is my current sendformdata.php file:
<?php
include_once('db_connect.php');
$lokotitle = $description = $category = $showyourname = $yourname = $lat = $lng = "";
if($_SERVER['REQUEST_METHOD'] == 'POST'){
$lokotitle=$_POST['lokotitle'];
$description=$_POST['description'];
$category=$_POST['category'];
$showyourname=$_POST['showyourname'];
$yourname=$_POST['yourname'];
$lat=$_POST['lat'];
$lng=$_POST['lng'];
// Validation will be added here
if(empty($lokotitle)) {
$error_message = "Please input a Loko title.";
?><script>$('#notitle'.text($error_message));</script><?php
exit;
}
if(!isset($error_message)){
//Inserting record in table using INSERT query
$insqDbtb="INSERT INTO `new`.`web_form`
(`lokotitle`, `description`, `category`, `showyourname`, `yourname`, `lat`, `lng`) VALUES ('$lokotitle', '$description', '$category', '$showyourname', '$yourname', '$lat', '$lng')";
mysqli_query($link,$insqDbtb) or die(mysqli_error($link));
?><script>window.location.href = "../index.php"; </script> <?php
exit;
}
}
?>
This is a section of form.php that I am trying to display an error message in:
<form class="form-horizontal" role="form" action="handleform/sendformdata.php" method="POST">
<legend></legend>
<div class="form-group">
<label for="lokotitle" class="col-sm-2">Loko Title</label>
<div class="col-sm-4">
<input type="text" class="form-control" name="lokotitle" id="lokotitle" placeholder="Title">
<span id="notitle"></span>
</div>
Thanks in advance for the help!
I recommend you to use both html5 required attribute which will force the user to enter the data. But remember the user can bypass front end validation (by means of inspect element), hence back end validation is also necessary.
Use required attribute like:
<input type="text" required />
You can try this
if(empty($lokotitle)) {
$error_message = "Please input a Loko title.";
echo "<script>
document.getElementById('#notitle').value='".$error_message."';".
"</script>";
exit;
}
Let me know if this solves your problem
I have read other answers for the same question but I am having problems and would be grateful for some advice.
I have javaScript in my html file, and an Onclick() statement on the submit button to clear the form but now the email confirmation message does not come up and the message is no longer sent. If I put the onClick(); in the body of the form, every field is cleared just by clicking on a form field. I really want to be able to submit a message, then have the form cleared on successful send.
<script type ="text/javascript">
function clearform () {
document.getElementById("name").value="";
document.getElementById("email").value="";
document.getElementById("subject").value="";
document.getElementById("message").value="";
}
</script>
<div class="row">
<div class="col-sm-6">
<h2>Send us a message</h2>
<!-- action="replace it with active link."-->
<form action="contact.php" method="post" name="contact-form" id="contact-form" >
<label for="name">Your Name <span>*</span></label>
<input type="text" name="name" id="name" value="" required />
<label for="email">Your E-Mail <span>*</span></label>
<input type="text" name="email" id="email" value="" required />
<label for="subject">Subject</label>
<input type="text" name="subject" id="subject" value="" />
<label for="message">Your Message</label>
<textarea name="message" id="message"></textarea>
<div class="row">
<div class="col-sm-6">
<input type="submit" name="sendmessage" id="sendmessage" value="Submit" onclick="clearform();" />
</div>
<div class="col-sm-6 dynamic"></div>
</div>
</form>
I then have the following in the PHP file:
private function sendEmail(){
$mail = mail($this->email_admin, $this->subject, $this->message,
"From: ".$this->name." <".$this->email.">\r\n"
."Reply-To: ".$this->email."\r\n"
."X-Mailer: PHP/" . phpversion());
if($mail)
{
$this->response_status = 1;
//$this->response_html = '<p>Thank You!</p>';
}
}
function sendRequest(){
$this->validateFields();
if($this->response_status)
{
$this->sendEmail();
}
$response = array();
$response['status'] = $this->response_status;
$response['html'] = $this->response_html;
echo "<span class=\"alert alert-success\" >Your message has been received. Thanks!</span>";
header("Location: contact.php");// redirect back to your contact form
exit;
}
}
$contact_form = new Contact_Form($_POST, $admin_email, $message_min_length);
$contact_form->sendRequest();
?>
No ajax form post
If you are not using ajax to submit the form (you don't seem to be using it), there is no need for javascript to clear the form, the form will be reloaded on submit and it will be empty.
However, you have a problem with your location redirect: You are outputting html before that so the redirect will probably fail.
You should not output anything before you redirect and you could add a query variable to the url so that you can show your success message when the form loads:
if($this->response_status)
{
$this->sendEmail();
}
header("Location: contact.php");// redirect back to your contact form
exit;
Using ajax to post the form
If you are using ajax (the setting of your response variables seems to indicate that you want to do that), you should put the clearform () call in the success function of your ajax call and remove the header() redirect in php. Instead you probably want to return / output the results:
if($this->response_status)
{
$this->sendEmail();
}
$response = array();
$response['status'] = $this->response_status;
$response['html'] = $this->response_html;
echo json_encode($response);
exit;
You've got to make sure the event continues to propagate and the form is submitted:
function clearform () {
document.getElementById("name").value="";
document.getElementById("email").value="";
document.getElementById("subject").value="";
document.getElementById("message").value="";
return true;
}