phpmailer how to check if field is empty sintax - php

Unfortunately I could not find the answer in other questions even though some of them seems to be similar. I am new to phpmailer but I managed to succesfully send email succesfully through smtp by using below code. However, I wish to stop sending emails with empty fields but I can't find proper sintax to do it and I would appreciate advise as how to stop email being sent if fields are empty or how to make fields required . (I know how to make client side validation but server side is a problem). Please see below:
<?php
if(isset($_POST['submit'])) {
$message=
'Name: '.$_POST['name'].'<br />
Subject: '.$_POST['subject'].'<br />
Email: '.$_POST['email'].'<br />
Message: '.$_POST['message'].'';
require "PHPMailer-master/class.phpmailer.php";
$mail = new PHPMailer();
require "smtp.php";
$mail->SetFrom($_POST['email'], $_POST['name']);
$mail->AddReplyTo($_POST['email'], $_POST['name']);
$mail->Subject = "Message from www";
$mail->MsgHTML($message);
$mail->AddAddress("address1#domain.com", " First receipient");
$mail->AddCC("address2#domain.com", "Second receipient");
$result = $mail->Send();
$message = $result ? '<div class="alert alert-success" role="alert"> Message has been sent ! </div>': '<div class="alert alert-danger" role="alert"><strong>Error!</strong> !</div>';
unset($mail);
}
?>

You just need to tack on some checks into your if statement. empty() is great for checking for empty, null, or 0 fields
if(isset($_POST['submit'])
&& !empty($_POST['name'])
&& !empty($_POST['subject'])
&& !empty($_POST['email'])
&& !empty($_POST['message'])) {
You can do some validation before your if statement to make sure the fields are filled and valid, and throw an error if they aren't.

Follow what #anyber has suggested, I just wanted to follow up and let you know that based on your code, this looks like a contact us form.
You don't want to set the from to the email that's entered on the form, you should change that to your email address. Setting the from with someone else's email can lead to a lot of problems, if that user has DMARC or other authentication methods enabled, take a look at this resource: Common Contact US Problems

Related

PHP Contact Form Submitting Randomly

I hope I'm missing something pretty basic here but: An empty form is getting submitted randomly, sometimes 3-8 times a day, then none for a few days and so on.
The empty submits always email with the subject as "[Website Contact Form]." Even though there is no validation in my php, in the html code the subject is chosen from a drop-down menu with the default as "General Enquiry." Notice in the php code below, there is no way for a human to submit an empty form with the above subject line, that is, it would always be "[Website Contact Form]General Enquiry" if I press submit without entering anything.
I have contact.html call this contact.php file:
<?
$email = 'info#mail.com';
$mailadd = $_POST['email'];
$headers = 'From: ' . $_POST['email'] . "\r\n";
$name = $_POST['name'];
$subject = '[Website Contact Form] ' . $_POST['subject'];
$message = 'Message sent from: ' . $name . '. Email: ' . $mailadd . '. Organization: ' . $_POST['company'] . '. Phone: ' . $_POST['phone'] . '. ';
$message .= 'Message: ';
$message .= $_POST['message'];
if (mail($email,$subject,$message, $headers)) {
echo "<p>Thank You! We'll get back to you shortly.</p>";
}
else {
echo "<p>Error...</p>";
}
?>
I use this code for many websites, but have never encountered this issue. Is there something so obviously wrong with this code that I'm missing? Any help would be greatly appreciated!
I suspect that you may not be checking that these variables are set before you send the email. Someone requesting contact.php directly (without any form data) may produce the results you have described. If this is the case, the following code should work like a charm:
<?php
if (isset($_POST['submit']) {
// form code
}
else {
// The form was not submitted, do nothing
}
?>
Even if that's not that case, such a simple check is always good practice.
Furthermore, you should always validate any user input just as a good habit. You don't want your server flooding your inbox with emails. I suggest using regexs to validate the input provided and possibly use a captcha service (such as ReCaptcha).
If you've been using this code and it's been working fine then I'd check what variables you changed with this case for example your submit form.
Try out your form with all common possibilities and see if it works. And empty Subject will give your form the subject "[Website Contact Form]". Check that your script actually get's the post variables and your form submits the right variables. Your dropdown might have an option with value of "" and the innerHTML "General Enquiry". The value is what will get submitted.
It's good to check inputs server-side as well
<?php
if(isset($_POST['subject'],$_POST['email'])){
}
?>

Is this form safe?

I have this form by which a user sends me an email. I don't know if it is secured, or if issues with security appear only if sql is involved...
html:
<form id="form4" action="send_mic.php" name="form4" method="post" >
<textarea name="message4" cols="4" rows="4" id="message4" ></textarea><br />
<input type="text" id="name4" name="name4" value="" /><br />
<input type="text" id="email4" name="email4" value="" /><br />
<input type="submit" value="" id="submit" />
</form>
jquery:
<script type="text/javascript">
$(document).ready(function () {
$('#form4').ajaxForm({
beforeSubmit: validate
});
function validate(formData, jqForm, options) {
var name = $('input[name=name4]').fieldValue();
var email = $('input[name=email4]').fieldValue();
var message = $('textarea[name=message4]').fieldValue();
if (!name[0]) {
alert('Please enter a value for name');
return false;
}
if (!email[0]) {
alert('Please enter a value for email');
return false;
}
if (!message[0]) {
alert('Please enter a value for message');
return false;
}
else {
$("#content").fadeOut(1000, function () {
$(this).html("<img src='images/postauto3.png'/>").fadeIn(2000);
});
var message = $('textarea[name=message4]').val('');
var name = $('input[name=name4]').val('');
var email = $('input[name=email4]').val('');
}
}
});
</script>
php:
<?php
if($_POST){
$email = $_POST['email4'];
$name = $_POST ['name4'];
$message = $_POST ['message4'];
// response hash
$ajaxresponse = array('type'=>'', 'message4'=>'');
try {
// do some sort of data validations, very simple example below
$all_fields = array('name4', 'email4', 'message4');
foreach($all_fields as $field){
if(empty($_POST[$field])){
throw new Exception('Required field "'.ucfirst($field).'" missing input.');
}
}
// ok, if field validations are ok
// now Send Email, ect.
// let's assume everything is ok, setup successful response
$subject = "New Contact";
//get todays date
$todayis = date("l, F j, Y, g:i a") ;
$message = " $todayis \n
Attention: \n\n
Please see the message below: \n\n
Email Address: $email \n\n
Message: $message \n\n
";
$from = "From: $email\r\n";
//put your email address here
mail("contact#....ro", $subject, $message, $from);
//prep json response
$ajaxresponse['type'] = 'success';
$ajaxresponse['message'] = 'Thank You! Will be in touch soon';
} catch(Exception $e){
$ajaxresponse['type'] = 'error';
$ajaxresponse['message'] = $e->getMessage();
}
// now we are ready to turn this hash into JSON
print json_encode($ajaxresponse);
exit;
}
?>
So, are there any security problems when using forms to send emails? Is this ok?
Thanks!
In general, rule of the thumb should always be: NEVER trust user provided data. And no, your code is not bullet proof. Since you do not verify nor sanitize user input and you use mail() at the same time you are vulnerable. User can easily feed you with crafted value for email4 filed. Since you use form data directly, then email4 can be used to inject additional mail headers to your outgoing mail. It these headers would be BCC: or CC: or even TO: then then you would be simply acting as spam relay. For example if I post this
some#address.com
CC: spamvictim1#foo.com, spamvictim2#foo.com, spamvictim3#foo.com,
X-Spam-Owned: Whoa
as your email4 then your header would end looking like this:
To: some#address.com
CC: spamvictim1#foo.com, spamvictim2#foo.com, spamvictim3#foo.com,
X-Spam-Owned: Whoa
to post multiline data you simply glue texts with CRLFs.
To avoid security holes like this you should consider dropping mail() and use something more clever that would take care of something like this too (not that mail() is bad, but you need to know what you are doing as it is rather low than high level function). I suggest using PHPMailer or similar package. You should always verify user provided data (especially ensure that single-line fields, like subject are really single line - stripping CRLFs suffice). Add captcha as you are open to automated form submission.
You could add a captcha to prevent spam.
You could protect against email injections by using:
filter_var($email, FILTER_VALIDATE_EMAIL)
I think this form is safe, mean that no one can really h#ck your website throught this form.
But you need to add somethings for better result:
1. You should also check the post variable in php server side, mean that you should check if email / name / message is valid of not
2. You should add some captcha to prevent spam
You can additionally wrap your server side code with
if(!empty($_SERVER['HTTP_X_REQUESTED_WITH']) && strtolower($_SERVER['HTTP_X_REQUESTED_WITH']) == 'xmlhttprequest') {
/* special ajax here */
die($content);
}
This will ensure the ajax request is coming on the server.
And please mind your ID that you are using in one of your jQuery selector in your question.
Even if you are not working with database, there could be security problems in email sending. Of course you can't be hacked by this form, but the problems will occure when the user will input something like this in EMail field:
email-address1#example.com // there is a new line here
CC:email-address2#example.com,email-addresses3#example.com,.............................email-addressesn#example.com
so the best you can do is sanitizing all the input fields for mail function, to prevent such spam delivery. And as #WebnetMobile.com has already sad, never trust user inputs
I don't see a security issue in there, since you are not modifying anything on your server side. Might be an issue with spam though. Add some captcha to it. The rest looks ok.
You should add captcha , client side and server side validation in form

PHP: Email validation and accepting email address from a certain domain

I am currently working with AJAX/JS to have form without a button click or page refresh. The inquiry I have is in regards of email validation. Right now the PHP code checks if an email address is valid or not. I would like to only have it accept emails from a certain domain. How can I achieve through php to accept only email address from gmail? Example
PHP for validation of email:
if($_POST) {
$email = $_POST['email'];
if (preg_match('|^[A-Z0-9._%+-]+#[A-Z0-9.-]+\.[A-Z]{2,4}$|i', $email)) {
echo ('<div id="email_input"><span id="resultval">'.$email.'</span></div>');
}
else {
echo ('<div id="email_input"><span id="resultval">Include a valid email address.</span></div>');
}
}
Php has an easy function to help you with checking if an email address is valid:
$isValid = filter_var($email, FILTER_VALIDATE_EMAIL);
To check if the email adress is a gmail address, the following would do the trick:
list ($user, $domain) = explode('#', $email);
$isGmail = ($domain == 'gmail.com');
Be careful with your regex, it won't validate all actual email addresses.
You have a built-in PHP function to check if an email is valid :
$email = filter_var($_POST['email'], FILTER_VALIDATE_EMAIL);
If this returns true, then you just have to check if the string ends with #gmail.com. Note that there may be some strange issues with this function, because email validation standards can be surprising.
If you really want a regex which validates all email addresses, here it is :
(?:[a-z0-9!#$%&'*+/=?^_{|}~-]+(?:\.[a-z0-9!#$%&'*+/=?^_{|}~-]+)*|"(?:[\x01-\x08\x0b\x0c\x0e-\x1f\x21\x23-\x5b\x5d-\x7f]|\\[\x01-\x09\x0b\x0c\x0e-\x7f])*")#(?:(?:[a-z0-9](?:[a-z0-9-]*[a-z0-9])?\.)+[a-z0-9](?:[a-z0-9-]*[a-z0-9])?|\[(?:(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.){3}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?|[a-z0-9-]*[a-z0-9]:(?:[\x01-\x08\x0b\x0c\x0e-\x1f\x21-\x5a\x53-\x7f]|\\[\x01-\x09\x0b\x0c\x0e-\x7f])+)\])
You should change you're regular expression to this
'|^[A-Z0-9._%+-]+#gmail\.com$|i'

How is this contact us script vulnerable / being manipulated?

A client recently got a spam warning from their host.
I think I have pin pointed the issue to an old contact us form. Simple html on the front end and a simple PHP script on the back end.
if ($_POST['submit'] == "Send"){
//START SEND MAIL SCRIPT
$mail = $_POST['email'];
$to = "me#gmail.com";
$subject = "Message from Website Contact Us Form";
$headers = "From: Contact us Form <webmaster#website.co.uk>";
$message = "Message from Contact Us Form\n\n";
$message .= "\nName: " . $_POST['contactname'];
$message .= "\nEmail: " . $_POST['contactemail'];
$message .= "\nTelephone: " . $_POST['contactphone'];
$message .= "\n\n\nMessage:\n" . $_POST['contactmessage'];
if(mail($to,$subject,$message,$headers)) {
header('Location: http://www.website.co.uk/contact-us/?action=success');
}else{
header('Location: http://www.webisite.co.uk/contact-us/?action=fail');
}//END IF MAIL
}//END SCRIPT
I know the remedies to fix it such as sanitizing post vars properly, using captchas, using a hidden 'honeypot' blank field, js tricks etc etc (I also like the look of this script too http://www.alt-php-faq.com/local/115/)
But to help me understand what was going on I want to know how this script is being manipulated. A foreign script posting vars to it but how do they send email to anyone apart from
'me#gmail.com' or if they are forcing cc / bcc fields somehow why do I not get all spam as well??
Thanks
Line like this $message .= "\nName: " . $_POST['contactname']; can be dangerous.
If $_POST['contactname']='MegaSteve4 \r\nCc: email1#mail.com, email2#mail.com'; are set, 2 uses will get spam mail.
See carefully. Its appending more headers. In this case Cc. I am not sure if Cc is a raw email header. But I hope you get the idea.
You're not doing any escaping of the post data. That means that this form is vulnerable to injection attacks.
I couldn't tell you how they did it, but that's probably what happened.

How to sanitze user input in PHP before mailing?

I have a simple PHP mailer script that takes values from a form submitted via POST and mails them to me:
<?php
$to = "me#example.com";
$name = $_POST['name'];
$message = $_POST['message'];
$email = $_POST['email'];
$body = "Person $name submitted a message: $message";
$subject = "A message has been submitted";
$headers = 'From: ' . $email;
mail($to, $subject, $body, $headers);
header("Location: http://example.com/thanks");
?>
How can I sanitize the input?
Sanitize the post variable with filter_var().
Example here. Like:
echo filter_var($_POST['email'], FILTER_SANITIZE_EMAIL);
Since you're not building an SQL query or anything here, the only relevant validation that I can see for those inputs is an email validation for $_POST["email"], and maybe an alphanumeric filter on the other fields if you really want to limit the scope of what the message can contain.
To filter the email address, simply use filter_var:
$email = filter_var($email, FILTER_SANITIZE_EMAIL);
As per Frank Farmer's suggestion, you can also filter out newlines in the email subject:
$subject = str_replace(array("\r","\n"),array(" "," "),$subject);
As others have noted, filter_var is great. If it's not available, add this to your toolchest.
The $headers variable is particularly bad security-wise. It can be appended to and cause spoofed headers to be added. This post called Email Injection discusses it pretty well.
filter_var is great, but another way to assure that something is an email address and not something bad is to use an isMail() function. Here's one:
function isEmail($email) {
return preg_match('|^[_a-z0-9-]+(\.[_a-z0-9-]+)*#[a-z0-9-]+(\.[a-z0-9-]{2,})+$|i', $email);
};
So to use this, you could do:
if (isset($_POST['email']) && isEmail($_POST['email'])) {
$email = $_POST['email'] ;
} else {
// you could halt execution here, set $email to a default email address
// display an error, redirect, or some combination here,
}
In terms of manual validation, limiting the length using substr(), running strip_tags() and otherwise limiting what can be put in.
You need to remove any newlines from input provided by users in $headers, which gets passed to mail() ($email in your case)! See Email injection.
PHP should take care of sanitizing $to and $subject, but there are versions of PHP with bugs (Affected are PHP 4 <= 4.4.6 and PHP 5 <= 5.2.1, see MOPB-34-2007).
You can use the code from artlung's answer above to validate email..
I use this kind of code to prevent header injection ..
// define some mail() header's parts and commonly used spam code to filter using preg_match
$match = "/(from\:|to\:|bcc\:|cc\:|content\-type\:|mime\-version\:|subject\:|x\-mailer\:|reply\-to\:|\%0a|\%0b)/i";
// check if any field's value containing the one or more of the code above
if (preg_match($match, $name) || preg_match( $match, $message) || preg_match( $match, $email)) {
// I use ajax, so I call the string below and send it to js file to check whether the email is failed to send or not
echo "failed";
// If you are not using ajax, then you can redirect it with php header function i.e: header("Location: http://example.com/anypage/");
// stop the script before it reach or executing the mail function
die();
}
The mail()'s header filtering above is too strict, since some users may be using the filtered strings in their message without any intention to hijack your email form, so redirect it to a page that is explaining what kind of strings that is not allowed in the form or explain it on your form page.

Categories