PHP Classes

File: Filtreatment_class.php

Recommend this page to a friend!
  Classes of Cristian Navalici   Filtreatment   Filtreatment_class.php   Download  
File: Filtreatment_class.php
Role: Class source
Content type: text/plain
Description: Class main file
Class: Filtreatment
Validate and filter text values based on rules
Author: By
Last change: Small fix for bug in date validation (spotted by Klevis Miho)
Date: 14 years ago
Size: 14,755 bytes
 

Contents

Class file image Download
<?php /** * FILTREATMENT CLASS FILE * * * @author Cristian N&#259;v&#259;lici {@link http://www.lemonsoftware.eu} lemonsoftware [at] gmail [.] com * @version 1.32 06 January 2010 * @license http://opensource.org/licenses/gpl-license.php GNU Public License * @package Filtreatment * */ //error_reporting(E_ALL); /** * constant used in float comparisions */ define('EPSILON', 1.0e-8); /** * CLASS DEFINITION * * This class can be used to sanitize user inputs and prevent * most of known vulnerabilities * it requires at least PHP 5.0 * * @package Filtreatment */ class Filtreatment { public $minval = 0; public $maxval = 0; public $error = ''; /** * CONSTRUCTOR * * do some settings at init * * @param none * @return void */ function __construct() { if ( get_magic_quotes_gpc() ) { if ( !defined('MAGICQUOTES') ) define ('MAGICQUOTES', TRUE); } else { if ( !defined('MAGICQUOTES') ) define ('MAGICQUOTES', FALSE); } } //----------------------------------------------------------------------------- /** * CHECKS FOR AN INTEGER * * if the $minval and|or $maxval are set, a comparison will be performed * * NOTE: because the function can return 0 also as a valid result, check with === the return value * @param int $input - what to check/transform * @return int|bool */ public function ft_integer($input) { $input_c = (int)$input; $mnval = (int)$this->minval; $mxval = (int)$this->maxval; if ( !$mnval && !$mxval ) { return $input_c; } else if ( $mnval && $mxval ) { // check if they are in order (min < max) if ( $mnval > $mxval ) { $temp = $mnval; $mnval = $mxval; $mxval = $temp; } // and then check if the value is between these values return (($input >= $mnval) && ($input <= $mxval)) ? $input_c : FALSE; } else { // only one value set if ( $mnval ) return (($input >= $mnval) ? $input_c : FALSE ); if ( $mxval ) return (($input <= $mxval) ? $input_c : FALSE ); } } //----------------------------------------------------------------------------- /** * CHECKS FOR A FLOAT * * if the $minval and|or $maxval are set, a comparison will be performed * * @param int $input - what to check/transform * @return int|bool */ public function ft_float($input) { $input_c = (float)$input; $mnval = (float)$this->minval; $mxval = (float)$this->maxval; if ( !$mnval && !$mxval ) { return $input_c; } else if ( $mnval && $mxval ) { // check if they are in order (min < max) if ( $this->ft_realcmp($mnval, $mxval) > 0 ) { $temp = $mnval; $mnval = $mxval; $mxval = $temp; } // and then check if the value is between these values $lt = $this->ft_realcmp($input, $mxval); //-1 or 0 for true if ( $lt === -1 || $lt === 0 ) $lt = $input_c; else $lt = FALSE; $gt = $this->ft_realcmp($input, $mnval); //1 or 0 for true if ( $gt === 1 || $gt === 0 ) $gt = TRUE; else $gt = FALSE; return (( $lt && $gt ) ? $input_c : FALSE); } else { // only one value set if ( $mnval ) { $gt = $this->ft_realcmp($input, $mnval); //1 or 0 for true return ( $gt === 1 || $gt === 0 ) ? $input_c : FALSE; } if ( $mxval ) { $lt = $this->ft_realcmp($input, $mxval); //-1 or 0 for true return ( $lt === -1 || $lt === 0 ) ? $input_c : FALSE; } } } //----------------------------------------------------------------------------- /** * VALIDATES A DATE * * must be in YYYY-MM-DD format * * @param string $str - date in requested format * @return string|bool - the string itselfs only for valid date */ public function ft_validdate($str) { if ( preg_match("/^([0-9]{4})-([0-9]{1,2})-([0-9]{1,2})$/", $str) ) { $arr = split("-",$str); // splitting the array $yy = $arr[0]; // first element of the array is year $mm = $arr[1]; // second element is month $dd = $arr[2]; // third element is days return ( checkdate($mm, $dd, $yy) ? $str : FALSE ); } else { return FALSE; } } //----------------------------------------------------------------------------- /** * VALIDATES AN EMAIL * * implies RFC 2822 * * @param string $str - email to validate * @return string|bool - the string itselfs only for valid email */ public function ft_email($email) { if (MAGICQUOTES) { $value = stripslashes($email); } // check for @ symbol and maximum allowed lengths if (!ereg("^[^@]{1,64}@[^@]{1,255}$", $email)) { return FALSE; } // split for sections $email_array = explode("@", $email); $local_array = explode(".", $email_array[0]); for ($i = 0; $i < sizeof($local_array); $i++) { if ( !ereg("^(([A-Za-z0-9!#$%&'*+/=?^_`{|}~-][A-Za-z0-9!#$%&'*+/=?^_`{|}~\.-]{0,63})|(\"[^(\\|\")]{0,62}\"))$", $local_array[$i]) ) { return FALSE; } } if (!ereg("^\[?[0-9\.]+\]?$", $email_array[1])) { // verify if domain is IP. If not, it must be a valid domain name $domain_array = explode(".", $email_array[1]); if (sizeof($domain_array) < 2) { return FALSE; } 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])) { return false; } } } // if return $email; } //----------------------------------------------------------------------------- /** * PREPARES THE INPUT FOR DATABASE * * works with mysql/postgresql * NOTE: mysql_real_escape_string() requires that a valid mysql connection (mysql_connect()) exists to work * * @param string $value - email to validate * @param string $db_type - allow two constants MYSQL | PGSQL * @return string|bool $value sanitized value */ public function ft_dbsql($value, $db_type = 'MYSQL') { if (MAGICQUOTES) { $value = stripslashes($value); } // Quote if not a number or a numeric string if (!is_numeric($value)) { switch ($db_type) { case 'MYSQL': $value = "'" . mysql_real_escape_string($value) . "'"; break; case 'PGSQL': $value = "'" . pg_escape_string($value) . "'"; break; } } return $value; } //----------------------------------------------------------------------------- /** * WORKS ON A STRING WITH REGEX EXPRESSION * * checks a string for specified characters * * @param string $value - variable to sanitize * @param string $regex - is in a special form detailed below: * it contains ONLY allowed characters, ANY other characters making invalid string * it must NOT contain begin/end delimitators /[... ]/ * eg: 0-9, 0-9A-Za-z, AERS * @param int $cv - 1 or 2 * @return string|bool return string if check succeed ($cv = 1) or string with replaced chars */ public function ft_strregex($value, $regex, $cv = 1) { $s = TRUE; //var control $regexfull = "/[^" . $regex . "]/"; // function of $cv might be a clean up operation, or just verifying switch ($cv) { // verify the string case '1': $s = ( preg_match($regexfull, $value) ? FALSE : TRUE ); break; // cleanup the string case '2': $value = preg_replace($regexfull,'',$value); break; // if $cv is not specified or it's wrong default: if ( preg_match($regexfull, $value) ) $s = FALSE; } return ( $s ? $value : FALSE ); } //----------------------------------------------------------------------------- /** * CLEANS AGAINST XSS * * NOTE all credits goes to codeigniter.com * @param string $str - string to check * @param string $charset - character set (default ISO-8859-1) * @return string|bool $value sanitized string */ public function ft_xss($str, $charset = 'ISO-8859-1') { /* * Remove Null Characters * * This prevents sandwiching null characters * between ascii characters, like Java\0script. * */ $str = preg_replace('/\0+/', '', $str); $str = preg_replace('/(\\\\0)+/', '', $str); /* * Validate standard character entities * * Add a semicolon if missing. We do this to enable * the conversion of entities to ASCII later. * */ $str = preg_replace('#(&\#*\w+)[\x00-\x20]+;#u',"\\1;",$str); /* * Validate UTF16 two byte encoding (x00) * * Just as above, adds a semicolon if missing. * */ $str = preg_replace('#(&\#x*)([0-9A-F]+);*#iu',"\\1\\2;",$str); /* * URL Decode * * Just in case stuff like this is submitted: * * <a href="http://%77%77%77%2E%67%6F%6F%67%6C%65%2E%63%6F%6D">Google</a> * * Note: Normally urldecode() would be easier but it removes plus signs * */ $str = preg_replace("/%u0([a-z0-9]{3})/i", "&#x\\1;", $str); $str = preg_replace("/%([a-z0-9]{2})/i", "&#x\\1;", $str); /* * Convert character entities to ASCII * * This permits our tests below to work reliably. * We only convert entities that are within tags since * these are the ones that will pose security problems. * */ if (preg_match_all("/<(.+?)>/si", $str, $matches)) { for ($i = 0; $i < count($matches['0']); $i++) { $str = str_replace($matches['1'][$i], html_entity_decode($matches['1'][$i], ENT_COMPAT, $charset), $str); } } /* * Convert all tabs to spaces * * This prevents strings like this: ja vascript * Note: we deal with spaces between characters later. * */ $str = preg_replace("#\t+#", " ", $str); /* * Makes PHP tags safe * * Note: XML tags are inadvertently replaced too: * * <?xml * * But it doesn't seem to pose a problem. * */ $str = str_replace(array('<?php', '<?PHP', '<?', '?>'), array('&lt;?php', '&lt;?PHP', '&lt;?', '?&gt;'), $str); /* * Compact any exploded words * * This corrects words like: j a v a s c r i p t * These words are compacted back to their correct state. * */ $words = array('javascript', 'vbscript', 'script', 'applet', 'alert', 'document', 'write', 'cookie', 'window'); foreach ($words as $word) { $temp = ''; for ($i = 0; $i < strlen($word); $i++) { $temp .= substr($word, $i, 1)."\s*"; } $temp = substr($temp, 0, -3); $str = preg_replace('#'.$temp.'#s', $word, $str); $str = preg_replace('#'.ucfirst($temp).'#s', ucfirst($word), $str); } /* * Remove disallowed Javascript in links or img tags */ $str = preg_replace("#<a.+?href=.*?(alert\(|alert&\#40;|javascript\:|window\.|document\.|\.cookie|<script|<xss).*?\>.*?</a>#si", "", $str); $str = preg_replace("#<img.+?src=.*?(alert\(|alert&\#40;|javascript\:|window\.|document\.|\.cookie|<script|<xss).*?\>#si","", $str); $str = preg_replace("#<(script|xss).*?\>#si", "", $str); /* * Remove JavaScript Event Handlers * * Note: This code is a little blunt. It removes * the event handler and anything up to the closing >, * but it's unlikely to be a problem. * */ $str = preg_replace('#(<[^>]+.*?)(onblur|onchange|onclick|onfocus|onload|onmouseover|onmouseup|onmousedown|onselect|onsubmit|onunload|onkeypress|onkeydown|onkeyup|onresize)[^>]*>#iU',"\\1>",$str); /* * Sanitize naughty HTML elements * * If a tag containing any of the words in the list * below is found, the tag gets converted to entities. * * So this: <blink> * Becomes: &lt;blink&gt; * */ $str = preg_replace('#<(/*\s*)(alert|applet|basefont|base|behavior|bgsound|blink|body|embed|expression|form|frameset|frame|head|html|ilayer|iframe|input|layer|link|meta|object|plaintext|style|script|textarea|title|xml|xss)([^>]*)>#is', "&lt;\\1\\2\\3&gt;", $str); /* * Sanitize naughty scripting elements * * Similar to above, only instead of looking for * tags it looks for PHP and JavaScript commands * that are disallowed. Rather than removing the * code, it simply converts the parenthesis to entities * rendering the code un-executable. * * For example: eval('some code') * Becomes: eval&#40;'some code'&#41; * */ $str = preg_replace('#(alert|cmd|passthru|eval|exec|system|fopen|fsockopen|file|file_get_contents|readfile|unlink)(\s*)\((.*?)\)#si', "\\1\\2&#40;\\3&#41;", $str); /* * Final clean up * * This adds a bit of extra precaution in case * something got through the above filters * */ $bad = array( 'document.cookie' => '', 'document.write' => '', 'window.location' => '', "javascript\s*:" => '', "Redirect\s+302" => '', '<!--' => '&lt;!--', '-->' => '--&gt;' ); foreach ($bad as $key => $val) { $str = preg_replace("#".$key."#i", $val, $str); } return $str; } //----------------------------------------------------------------------------- /** * DISPLAY ERRORS * * @param int $mode - if 1 then echo the string; if 2 then echo the string * @return void */ public function display_error($mode = 1) { $errstr = ( $this->error ) ? $this->error : ''; if ( $mode == 1 ) { echo '<br />' .$this->ft_xss($errstr) . '<br />'; } else { return $this->ft_xss($errstr); } } //----------------------------------------------------------------------------- /** * REAL COMPARASION BETWEEN FLOATS * * 0 - for ==, 1 for r1 > r2, -1 for r1 '<' r2 * * @param float $r1 * @param float $r2 * @return int */ private function ft_realcmp($r1, $r2) { $diff = $r1 - $r2; if ( abs($diff) < EPSILON ) return 0; else return $diff < 0 ? -1 : 1; } //----------------------------------------------------------------------------- } // class ?>