knobby2k Posted July 13, 2011 Share Posted July 13, 2011 hey people, i am trying to do a preg_match to validate name being entered into an input field using the following code: if ( !preg_match("/^([a-z\-\' ])+$/i", $this->input[$field]) ) The only characters that i want to allow through are... a-z - ' however, it still will not allow me to enter a ' into the field. any ideas why? Thanks Quote Link to comment https://forums.phpfreaks.com/topic/241919-preg_match/ Share on other sites More sharing options...
AyKay47 Posted July 13, 2011 Share Posted July 13, 2011 the - doesn't need to be escaped, but other than that, it should allow apostrophes preg_match("/^([a-z-\' ])+$/i", $this->input[$field]) Also, you do realize that this regex will allow names like "J- o- h-- n" right? Quote Link to comment https://forums.phpfreaks.com/topic/241919-preg_match/#findComment-1242368 Share on other sites More sharing options...
knobby2k Posted July 13, 2011 Author Share Posted July 13, 2011 the - doesn't need to be escaped, but other than that, it should allow apostrophes preg_match("/^([a-z-\' ])+$/i", $this->input[$field]) Also, you do realize that this regex will allow names like "J- o- h-- n" right? no i didnt realise that. I need to allow for the following (in two seperate fields)... 1 - [dash] for things like double baralled names such as 'anne-louise smith' or 'John smith-thompson' 1 [space] for names like 'lee james smith' (although i might keep it to only the firstname and surname) 1 ' [apostrophes] mainly for foreign names like Al'habsi can you recommend how to make those improvement's? It still won't allow me to enter an apostrophe for some reason Thanks Quote Link to comment https://forums.phpfreaks.com/topic/241919-preg_match/#findComment-1242376 Share on other sites More sharing options...
knobby2k Posted July 13, 2011 Author Share Posted July 13, 2011 think i know why... when i go to view source on the page it displays this: <p>*First Name: <input type="text" name="firstname" value="John&#039;" maxlength="80" /> It's cleansing the data earlier on in the script here: $data[$key] = trim(htmlspecialchars(strip_tags(stripslashes($value)), ENT_QUOTES, 'UTF-8')); so converting the apostrophe to '&#039;'. Obviously with me then doing a preg_match it is refusing the '&#;'. Now my question is... A) do i allow for '&#;' in the preg_match OR B) remove the htmlspecialchars any suggestions? cheers Quote Link to comment https://forums.phpfreaks.com/topic/241919-preg_match/#findComment-1242384 Share on other sites More sharing options...
requinix Posted July 13, 2011 Share Posted July 13, 2011 1. Do you have magic_quotes enabled? 2. Depending on what the code does with $data you should/should not be using htmlspecialchars(). Quote Link to comment https://forums.phpfreaks.com/topic/241919-preg_match/#findComment-1242386 Share on other sites More sharing options...
knobby2k Posted July 13, 2011 Author Share Posted July 13, 2011 I'm not sure if magic_quotes are enabled or not. basically i'm using someone's excellent validation script with a few additional modifications. Here is the script... <?php /************************************************************ Validation Class Author: Jason Ashdown Updated: 12:12 24/07/2008 Version 0.2j -------------------------------------------------------- Change Log:- v0.2j - Added 'decode' function to form helpers. To help pass UTF-8 characters back to a form from the DB. v0.2h - Removed 'spaces' from the regexp strings v0.2g - Email address function is now in compliant with RFC 2822 v0.2f - Added $masks for allErrors to be more user-friendly, updated loop_clean to use htmlspecialchars and supports UTF-8 v0.2e - Fixed allErrors() to include wrappers v0.2d - Changed "required" to check for empty strings properly v0.2c - Added "not_equal" and "selected" functions v0.2b - Tidied comments; fixed email mx check v0.2a - Added loop_clean (multi-array sanitiser) V0.2 - Added new helper functions (label, check) - - - v0.1 - Initial Release *************************************************************/ class validateForm { var $input = array(); var $error = array(); var $error_wrapper; var $pass; // You can call the validated inputs directly from this class // when you come to inserting them into the db, e.g. // $form = new validateForm($_POST); // $form->input['fullname']; etc... function validateForm($input=array()) // Yes, post the the whole $_POST/$_GET array into the function { $this->input = $input; // Clone form inputs array into here $this->pass = true; // Flag changes if theres an error // Config $this->error_wrapper['start'] = "<br /><span class=\"error\">"; $this->error_wrapper['end'] = "</span>"; // Sanitise our arrays $this->loop_clean($this->input); } // // We can even perform some security checks here if we wish // function loop_clean(&amp;amp;$data) { foreach ($data as $key => $value) { if ( !is_array($value) ) { // Well formatted string; PHP4 requires "stripslashes" on all input fields $data[$key] = trim(htmlspecialchars(strip_tags(stripslashes($value)), ENT_QUOTES, 'UTF-8')); } else { $this->loop_clean($value); $data[$key] = $value; } } } /************************************/ /* Error Functions */ /************************************/ // Set error function error($item, $desc) { $this->pass = false; $this->error[$item] .= $desc." "; // Append multiple error messages } // Return the error function showError($item) { return $this->error_wrapper['start'].trim($this->error[$item]).$this->error_wrapper['end']; } function allErrors($masks=array()) { foreach ( $this->error as $key => $value ) { // Mask field names with more appropriate User friendly names $key = $masks[$key] != '' ? $masks[$key] : $key; echo $this->error_wrapper['start']."<b>".ucfirst($key)."</b>: ".trim($value).$this->error_wrapper['end']; } } /************************************/ /* Debugging */ /************************************/ function showInputs() { print_r($this->input); } /************************************/ /* Validation Functions */ /************************************/ function not_equal($string, $field) { if ( is_string($string) ) { if ($string == $this->input[$field]) { $msg = "You must select a different option other than \"$string\""; $this->error($field, $msg); return false; } return true; } return false; } function min_length($min=0, $field) { if( strlen($this->input[$field]) < (int) $min ) { $msg = "This field cannot be shorter than $min characters."; $this->error($field, $msg); return false; } return true; } function max_length($max=0, $field) { if ( strlen($this->input[$field]) > (int) $max ) { $msg = "This field cannot be longer than $max characters."; $this->error($field, $msg); return false; } return true; } function alpha($field) { if ( !preg_match("/^([a-z])+$/i", $this->input[$field]) ) { $msg = "This field can only contain letters (A-Z). No foreign characters allowed."; $this->error($field, $msg); return false; } return true; } // Double-barrel names and marital status will require this function alpha_dotdash($field) { if ( !preg_match("/^([a-z\-\.])+$/i", $this->input[$field]) ) { $msg = "This field can only contain characters (A-Z-.). No foreign characters allowed."; $this->error($field, $msg); return false; } return true; } // Useful for Addresses or fields that may contain unusual but still valid chars function alpha_special($field) { if ( !preg_match("/^([a-z0-9\-+\.,_='\"@#])+$/i", $this->input[$field]) ) { $msg = "This field has illegal characters. You can use letters, numbers and (._-+='\"@#)."; $this->error($field, $msg); return false; } return true; } function numeric($field) { if ( !preg_match("/^[\-+]?[0-9]*\.?[0-9]+$/", $this->input[$field]) ) { $msg = "This field must contain only numbers."; $this->error($field, $msg); return false; } return true; } function alpha_numeric($field) { if( !preg_match("/^([a-z0-9])+$/i", $this->input[$field]) ) { $msg = "This field can only contain letters and numbers."; $this->error($field, $msg); return false; } return true; } function required($field) { if ( !isset($this->input[$field]) OR $this->input[$field] == '' ) { $this->error($field, 'This field is required.'); return false; } elseif ( is_array($this->input[$field]) ) { $this->error($field, 'This is an array and won\'t be passed.'); return false; } return true; } /************************************/ /* Alias Functions */ /************************************/ function fullname($field, $req=true) { if ( $req == true AND !$this->required($field) ) return false; return $this->alpha_dotdash($field); } function address($field, $req=true) { if ( $req == true AND !$this->required($field) ) return false; return $this->alpha_special($field); } function telephone($field, $req=true) { if ( $req == true AND !$this->required($field) ) return false; if ( $this->numeric($field) AND $this->min_length(11, $field) AND $this->max_length(14, $field) ) { return true; } return false; } function mobile($field, $req=true) { if ( $req == true AND !$this->required($field) ) return false; return $this->telephone($field); } function postcode($field, $req=true) { if ( $req == true AND !$this->required($field) ) return false; if ( !preg_match("/^[a-zA-Z]{1,3}[0-9]{1,3} [0-9]{1}[a-zA-Z]{2}$/i", $this->input[$field]) ) { $msg = "Postcode must follow the format of \"XX1 1XX\"."; $this->error($field, $msg); return false; } return true; } function email($field, $req=true, $mx_records=false) { if ( $req == true AND !$this->required($field) ) return false; // Function from: http://www.ilovejackdaniels.com/php/email-address-validation/ // Complies with the email address specification guidelines: RFC 2822 // First, we check that there's one @ symbol, and that the lengths are right if (!ereg("^[^@]{1,64}@[^@]{1,255}$", $this->input[$field])) { // Email invalid because wrong number of characters in one section, or wrong number of @ symbols. $msg = "Your email address is the wrong length."; $this->error($field, $msg); return false; } // Split it into sections to make life easier $email_array = explode("@", $this->input[$field]); $local_array = explode(".", $email_array[0]); for ($i = 0; $i < sizeof($local_array); $i++) { if (!ereg("^(([A-Za-z0-9!#$%&amp;amp;'*+/=?^_`{|}~-][A-Za-z0-9!#$%&amp;amp;'*+/=?^_`{|}~\.-]{0,63})|(\"[^(\\|\")]{0,62}\"))$", $local_array[$i])) { $msg = "The first part of your email is malformed."; $this->error($field, $msg); return false; } } if (!ereg("^\[?[0-9\.]+\]?$", $email_array[1])) // Check if domain is IP. If not, it should be valid domain name { $domain_array = explode(".", $email_array[1]); if (sizeof($domain_array) < 2) { $msg = "Your email doesn't have a valid domain."; $this->error($field, $msg); return false; // Not enough parts to domain } for ($i = 0; $i < sizeof($domain_array); $i++) { if (!ereg("^(([A-Za-z0-9][A-Za-z0-9-]{0,61}[A-Za-z0-9])|([A-Za-z0-9]+))$", $domain_array[$i])) { $msg = "Your email doesn't have a valid domain."; $this->error($field, $msg); return false; } } } // Check online to see if this is a real email host! if ( $mx_records != false ) { $host = $email_array[1]; //The whooole domain getmxrr($host, $mxhosts); if ( count($mxhosts) < 1 ) { $msg = "There is no email host associated with your email. This probably means its fake."; $this->error($field, $msg); return false; } } return true; } /************************************/ /* Helper Functions */ /************************************/ function decode($field) { return html_entity_decode($this->input[$field]); } function label($text, $id) { return "<label for=\"$id\">$text</label>"; } function check($field, $value, $default=false) { if ( $default == true AND empty($this->input[$field]) ) return 'checked="checked"'; return $this->input[$field] == $value ? 'checked="checked"' : ''; } function selected($field, $value, $default=false) { if ( $default == true AND empty($this->input[$field]) ) return 'selected="selected"'; return $this->input[$field] == $value ? 'selected="selected"' : ''; } } /* Example: You can just edit $this->error_wrapper['start'] AND $this->error_wrapper['end'] to make the errors display how you want. */ if ( $_SERVER['REQUEST_METHOD'] == 'POST' ) { $form = new validateForm($_POST); $form->required('firstname'); $form->required('lastname'); $form->mobile('mobile'); $form->email('email', true); // Validate email AND make it required $form->required('t-and-c'); // Terms &amp;amp; Conditions if ( $form->pass == true ) { // Insert data into DB ... echo "Success"; } } else { $form = new validateForm(); } ?> <div class="error"> <?php // Masks are used if you have an unfriendly named field that may cause the user confusion. // You just specify the names and the fields in the array with the text you want to replace it with. $masks = array( 't-and-c' => 'Terms &amp;amp; Conditions'); $form->allErrors($masks); ?> </div> <form method="post"> <p>*First Name: <input type="text" name="firstname" value="<?php echo $form->input['firstname'];?>" maxlength="80" /> <?php // Show inidividual errors echo $form->showError('firstname'); ?> </p> <p>*Last Name: <input type="text" name="lastname" value="<?php echo $form->input['lastname'];?>" maxlength="80" /></p> <?php // OR Specify your own error message if ( $form->showError('lastname') ) { echo 'You must fill in the "Last Name" field.'; } ?> <p>Mobile: <input type="text" name="mobile" value="<?php echo $form->input['mobile'];?>" /></p> <p>*Email: <input type="text" name="email" value="<?php echo $form->input['email'];?>" /></p> <p>Comment: <textarea name="comment"> < ?php // If you ever send data that has UTF-8 in it, you can use the decode helper if retrieving it from a DB echo $form->decode('comment'); ?></textarea></p> <p><input type="checkbox" name="t-and-c" id="t-and-c" value="true" <?php echo $form->check('t-and-c', true);?>/> <?php echo $form->label('Terms and Conditions*' ,'t-and-c');?></p> <p><strong>* Required</strong></p> <p><input type="submit" value="Send" /></p> </form> Quote Link to comment https://forums.phpfreaks.com/topic/241919-preg_match/#findComment-1242389 Share on other sites More sharing options...
knobby2k Posted July 13, 2011 Author Share Posted July 13, 2011 1. Do you have magic_quotes enabled? 2. Depending on what the code does with $data you should/should not be using htmlspecialchars(). yes it looks like magic_quotes are enabled... is this a good thing or a bad thing?? cheers Quote Link to comment https://forums.phpfreaks.com/topic/241919-preg_match/#findComment-1242392 Share on other sites More sharing options...
AyKay47 Posted July 13, 2011 Share Posted July 13, 2011 think i know why... when i go to view source on the page it displays this: <p>*First Name: <input type="text" name="firstname" value="John&#039;" maxlength="80" /> It's cleansing the data earlier on in the script here: $data[$key] = trim(htmlspecialchars(strip_tags(stripslashes($value)), ENT_QUOTES, 'UTF-8')); so converting the apostrophe to '&#039;'. Obviously with me then doing a preg_match it is refusing the '&#;'. Now my question is... A) do i allow for '&#;' in the preg_match OR B) remove the htmlspecialchars any suggestions? cheers it wouldn't make much sense to sanitize your value before passing it through preg_match Quote Link to comment https://forums.phpfreaks.com/topic/241919-preg_match/#findComment-1242393 Share on other sites More sharing options...
AyKay47 Posted July 13, 2011 Share Posted July 13, 2011 magic_quotes is deprecated and should be turned off Quote Link to comment https://forums.phpfreaks.com/topic/241919-preg_match/#findComment-1242394 Share on other sites More sharing options...
knobby2k Posted July 13, 2011 Author Share Posted July 13, 2011 magic_quotes is deprecated and should be turned off Hey thanks for the reply, is there any harm in leaving it on? Quote Link to comment https://forums.phpfreaks.com/topic/241919-preg_match/#findComment-1242395 Share on other sites More sharing options...
knobby2k Posted July 13, 2011 Author Share Posted July 13, 2011 think i know why... when i go to view source on the page it displays this: <p>*First Name: <input type="text" name="firstname" value="John&#039;" maxlength="80" /> It's cleansing the data earlier on in the script here: $data[$key] = trim(htmlspecialchars(strip_tags(stripslashes($value)), ENT_QUOTES, 'UTF-8')); so converting the apostrophe to '&#039;'. Obviously with me then doing a preg_match it is refusing the '&#;'. Now my question is... A) do i allow for '&#;' in the preg_match OR B) remove the htmlspecialchars any suggestions? cheers it wouldn't make much sense to sanitize your value before passing it through preg_match So should i sanitize it once i've passed it through preg_match... just in case? or just completely really on preg_match? thanks Quote Link to comment https://forums.phpfreaks.com/topic/241919-preg_match/#findComment-1242398 Share on other sites More sharing options...
AyKay47 Posted July 13, 2011 Share Posted July 13, 2011 well preg_match won't actually sanitize the string, depending on what you are doing with the input you will want to sanitize it.. Quote Link to comment https://forums.phpfreaks.com/topic/241919-preg_match/#findComment-1242406 Share on other sites More sharing options...
Recommended Posts
Join the conversation
You can post now and register later. If you have an account, sign in now to post with your account.