0
\$\begingroup\$

I tried my hand at a contact-us PHP script. I came up with the following. First the markup, then a little client-side validation and then the email script. I just need to know if this is usable code.

I actually got to the point where I can make some cash developing websites. I just need to know if this is valid

HTML

function validateContactForm() {
  var valid = true;

  $(".info").html("");
  $(".input-field").css('border', '#e0dfdf 1px solid');
  var userName = $("#userName").val();
  var userEmail = $("#userEmail").val();
  var subject = $("#subject").val();
  var content = $("#content").val();

  if (userName == "") {
    $("#userName-info").html("Required.");
    $("#userName").css('border', '#e66262 1px solid');
    valid = false;
  }
  if (userEmail == "") {
    $("#userEmail-info").html("Required.");
    $("#userEmail").css('border', '#e66262 1px solid');
    valid = false;
  }
  if (!userEmail.match(/^([\w-\.]+@([\w-]+\.)+[\w-]{2,4})?$/)) {
    $("#userEmail-info").html("Invalid Email Address.");
    $("#userEmail").css('border', '#e66262 1px solid');
    valid = false;
  }

  if (subject == "") {
    $("#subject-info").html("Required.");
    $("#subject").css('border', '#e66262 1px solid');
    valid = false;
  }
  if (content == "") {
    $("#userMessage-info").html("Required.");
    $("#content").css('border', '#e66262 1px solid');
    valid = false;
  }
  return valid;
}
<form name="frmContact" id="frmContact" method="post" action="" enctype="multipart/form-data" onsubmit="return validateContactForm()">

  <div class="input-row">
    <label style="padding-top: 20px;">Name</label> <span id="userName-info" class="info"></span><br />
    <input type="text" class="input-field" name="userName" id="userName" />
  </div>
  <div class="input-row">
    <label>Email</label> <span id="userEmail-info" class="info"></span><br /> <input type="text" class="input-field" name="userEmail" id="userEmail" />
  </div>
  <div class="input-row">
    <label>Subject</label> <span id="subject-info" class="info"></span><br /> <input type="text" class="input-field" name="subject" id="subject" />
  </div>
  <div class="input-row">
    <label>Message</label> <span id="userMessage-info" class="info"></span><br />
    <textarea name="content" id="content" class="input-field" cols="60" rows="6"></textarea>
  </div>
  <div>
    <input type="submit" name="send" class="btn-submit" value="Send" />

    <div id="statusMessage">
      <?php if (!empty($message)) { ?>
      <p class='<?php echo $type; ?>Message'>
        <?php echo $message; ?>
      </p>
      <?php } ?>
    </div>
  </div>
</form>

PHP

<?php if (!empty($_POST['send'])) {
    $name = $_POST['userName'];
    $email = $_POST['userEmail'];
    $subject = $_POST['subject'];
    $content = $_POST['content'];

    $toEmail = '[email protected]';
    $mailHeaders = 'From: ' . $name . '<' . $email . ">\r\n";
    if (mail($toEmail, $subject, $content, $mailHeaders)) {
        $message = 'Your contact information is received successfully.';
        $type = 'success';
    }
}
require_once "contact-view.php";
?>
\$\endgroup\$
3
  • \$\begingroup\$ If somebody could help me format that code to look more pretty I would appreciate it. \$\endgroup\$
    – Neil Meyer
    Commented Mar 12, 2021 at 9:17
  • 3
    \$\begingroup\$ you must validate $name and $email or this script will become a spam gate that will make possible to send any email to any address due to Mail injection. Better yet, do not add the custom From: header at all \$\endgroup\$ Commented Mar 12, 2021 at 9:22
  • \$\begingroup\$ Your title doesn't need to ask for "reviews". Your title should endeavor to uniquely describe what your script does. \$\endgroup\$ Commented Mar 13, 2021 at 13:50

1 Answer 1

3
\$\begingroup\$

The script is extremely basic but it seems to me that it is also not secure. I have seen similar code that vulnerable to header injection, so it was possible for spammers to add a BCC header, and instead spam other people through your server (and your IP address will get blacklisted as a result).

Even a seasoned class like phpmailer has suffered nasty security bugs. Another article that touches on the issue: Why mail() is dangerous in PHP

Since $mailHeaders is injectable, I can provide an E-mail address like:

[email protected]@\r\nBcc: [email protected]

and I should be able to send spam to [email protected], with your unwitting assistance.

Validation of form fields in Javascript is not sufficient, it has to be performed server-side as well. Javascript is useful for instant, client-side validation to avoid back and forth exchanges with the server but cannot be considered a security feature since you don't control the client and can't trust it.

It is only a matter of time until your form is indexed by spambots, that will start pounding your server. The bots don't care about Javascript. Your script will not stop them. So basically everything you wrote in JS has to be implemented server-side in PHP. JS validation is nice to have but optional.

Since it appears that you are using Bootstrap, you could perhaps take advantage of the validation options available. Then you can also get rid of the inline CSS styling eg: $("#userEmail").css('border', '#e66262 1px solid');.

You can also use the required attribute in your mandatory HTML controls. Then the browser will prompt the user if some fields are empty, and will not submit the form. It is a small extra and costs nothing.

To sum up, I suggest that you read up a bit on header injection and don't reinvent the wheel. There is mature, open-source third-party code available for this kind of task. It will be more secure that your homemade attempt.

I seem to remember that there is also the possibility of nullbyte injection but can't remember the details right now.

\$\endgroup\$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.