upgrade to codeigniter 1.7.2 for f12
[www-register-wizard.git] / libraries / Validation.php
1 <?php  if ( ! defined('BASEPATH')) exit('No direct script access allowed');
2 /**
3  * CodeIgniter
4  *
5  * An open source application development framework for PHP 4.3.2 or newer
6  *
7  * @package             CodeIgniter
8  * @author              ExpressionEngine Dev Team
9  * @copyright   Copyright (c) 2008 - 2009, EllisLab, Inc.
10  * @license             http://codeigniter.com/user_guide/license.html
11  * @link                http://codeigniter.com
12  * @since               Version 1.0
13  * @filesource
14  */
15
16 // ------------------------------------------------------------------------
17
18 /**
19  * Validation Class
20  *
21  * @package             CodeIgniter
22  * @subpackage  Libraries
23  * @category    Validation
24  * @author              ExpressionEngine Dev Team
25  * @link                http://codeigniter.com/user_guide/libraries/validation.html
26  */
27 class CI_Validation {
28         
29         var $CI;
30         var $error_string               = '';
31         var $_error_array               = array();
32         var $_rules                             = array();
33         var $_fields                    = array();
34         var $_error_messages    = array();
35         var $_current_field     = '';
36         var $_safe_form_data    = FALSE;
37         var $_error_prefix              = '<p>';
38         var $_error_suffix              = '</p>';
39
40         
41
42         /**
43          * Constructor
44          *
45          */     
46         function CI_Validation()
47         {       
48                 $this->CI =& get_instance();
49                 
50                 if (function_exists('mb_internal_encoding'))
51                 {
52                         mb_internal_encoding($this->CI->config->item('charset'));
53                 }
54                 
55                 log_message('debug', "Validation Class Initialized");
56         }
57         
58         // --------------------------------------------------------------------
59         
60         /**
61          * Set Fields
62          *
63          * This function takes an array of field names as input
64          * and generates class variables with the same name, which will
65          * either be blank or contain the $_POST value corresponding to it
66          *
67          * @access      public
68          * @param       string
69          * @param       string
70          * @return      void
71          */
72         function set_fields($data = '', $field = '')
73         {       
74                 if ($data == '')
75                 {
76                         if (count($this->_fields) == 0)
77                         {
78                                 return FALSE;
79                         }
80                 }
81                 else
82                 {
83                         if ( ! is_array($data))
84                         {
85                                 $data = array($data => $field);
86                         }
87                         
88                         if (count($data) > 0)
89                         {
90                                 $this->_fields = $data;
91                         }
92                 }               
93                         
94                 foreach($this->_fields as $key => $val)
95                 {
96                         $this->$key = ( ! isset($_POST[$key])) ? '' : $this->prep_for_form($_POST[$key]);
97                         
98                         $error = $key.'_error';
99                         if ( ! isset($this->$error))
100                         {
101                                 $this->$error = '';
102                         }
103                 }               
104         }
105         
106         // --------------------------------------------------------------------
107         
108         /**
109          * Set Rules
110          *
111          * This function takes an array of field names and validation
112          * rules as input ad simply stores is for use later.
113          *
114          * @access      public
115          * @param       mixed
116          * @param       string
117          * @return      void
118          */
119         function set_rules($data, $rules = '')
120         {
121                 if ( ! is_array($data))
122                 {
123                         if ($rules == '')
124                                 return;
125                                 
126                         $data = array($data => $rules);
127                 }
128         
129                 foreach ($data as $key => $val)
130                 {
131                         $this->_rules[$key] = $val;
132                 }
133         }
134         
135         // --------------------------------------------------------------------
136         
137         /**
138          * Set Error Message
139          *
140          * Lets users set their own error messages on the fly.  Note:  The key
141          * name has to match the  function name that it corresponds to.
142          *
143          * @access      public
144          * @param       string
145          * @param       string
146          * @return      string
147          */
148         function set_message($lang, $val = '')
149         {
150                 if ( ! is_array($lang))
151                 {
152                         $lang = array($lang => $val);
153                 }
154         
155                 $this->_error_messages = array_merge($this->_error_messages, $lang);
156         }
157         
158         // --------------------------------------------------------------------
159         
160         /**
161          * Set The Error Delimiter
162          *
163          * Permits a prefix/suffix to be added to each error message
164          *
165          * @access      public
166          * @param       string
167          * @param       string
168          * @return      void
169          */     
170         function set_error_delimiters($prefix = '<p>', $suffix = '</p>')
171         {
172                 $this->_error_prefix = $prefix;
173                 $this->_error_suffix = $suffix;
174         }
175         
176         // --------------------------------------------------------------------
177         
178         /**
179          * Run the Validator
180          *
181          * This function does all the work.
182          *
183          * @access      public
184          * @return      bool
185          */             
186         function run()
187         {
188                 // Do we even have any data to process?  Mm?
189                 if (count($_POST) == 0 OR count($this->_rules) == 0)
190                 {
191                         return FALSE;
192                 }
193         
194                 // Load the language file containing error messages
195                 $this->CI->lang->load('validation');
196                                                         
197                 // Cycle through the rules and test for errors
198                 foreach ($this->_rules as $field => $rules)
199                 {
200                         //Explode out the rules!
201                         $ex = explode('|', $rules);
202
203                         // Is the field required?  If not, if the field is blank  we'll move on to the next test
204                         if ( ! in_array('required', $ex, TRUE))
205                         {
206                                 if ( ! isset($_POST[$field]) OR $_POST[$field] == '')
207                                 {
208                                         continue;
209                                 }
210                         }
211                         
212                         /*
213                          * Are we dealing with an "isset" rule?
214                          *
215                          * Before going further, we'll see if one of the rules
216                          * is to check whether the item is set (typically this
217                          * applies only to checkboxes).  If so, we'll
218                          * test for it here since there's not reason to go
219                          * further
220                          */
221                         if ( ! isset($_POST[$field]))
222                         {                       
223                                 if (in_array('isset', $ex, TRUE) OR in_array('required', $ex))
224                                 {
225                                         if ( ! isset($this->_error_messages['isset']))
226                                         {
227                                                 if (FALSE === ($line = $this->CI->lang->line('isset')))
228                                                 {
229                                                         $line = 'The field was not set';
230                                                 }                                                       
231                                         }
232                                         else
233                                         {
234                                                 $line = $this->_error_messages['isset'];
235                                         }
236                                         
237                                         // Build the error message
238                                         $mfield = ( ! isset($this->_fields[$field])) ? $field : $this->_fields[$field];
239                                         $message = sprintf($line, $mfield);
240
241                                         // Set the error variable.  Example: $this->username_error
242                                         $error = $field.'_error';
243                                         $this->$error = $this->_error_prefix.$message.$this->_error_suffix;
244                                         $this->_error_array[] = $message;
245                                 }
246                                                 
247                                 continue;
248                         }
249         
250                         /*
251                          * Set the current field
252                          *
253                          * The various prepping functions need to know the
254                          * current field name so they can do this:
255                          *
256                          * $_POST[$this->_current_field] == 'bla bla';
257                          */
258                         $this->_current_field = $field;
259
260                         // Cycle through the rules!
261                         foreach ($ex As $rule)
262                         {
263                                 // Is the rule a callback?                      
264                                 $callback = FALSE;
265                                 if (substr($rule, 0, 9) == 'callback_')
266                                 {
267                                         $rule = substr($rule, 9);
268                                         $callback = TRUE;
269                                 }
270                                 
271                                 // Strip the parameter (if exists) from the rule
272                                 // Rules can contain a parameter: max_length[5]
273                                 $param = FALSE;
274                                 if (preg_match("/(.*?)\[(.*?)\]/", $rule, $match))
275                                 {
276                                         $rule   = $match[1];
277                                         $param  = $match[2];
278                                 }
279                                 
280                                 // Call the function that corresponds to the rule
281                                 if ($callback === TRUE)
282                                 {
283                                         if ( ! method_exists($this->CI, $rule))
284                                         {               
285                                                 continue;
286                                         }
287                                         
288                                         $result = $this->CI->$rule($_POST[$field], $param);     
289                                         
290                                         // If the field isn't required and we just processed a callback we'll move on...
291                                         if ( ! in_array('required', $ex, TRUE) AND $result !== FALSE)
292                                         {
293                                                 continue 2;
294                                         }
295                                         
296                                 }
297                                 else
298                                 {                               
299                                         if ( ! method_exists($this, $rule))
300                                         {
301                                                 /*
302                                                  * Run the native PHP function if called for
303                                                  *
304                                                  * If our own wrapper function doesn't exist we see
305                                                  * if a native PHP function does. Users can use
306                                                  * any native PHP function call that has one param.
307                                                  */
308                                                 if (function_exists($rule))
309                                                 {
310                                                         $_POST[$field] = $rule($_POST[$field]);
311                                                         $this->$field = $_POST[$field];
312                                                 }
313                                                                                         
314                                                 continue;
315                                         }
316                                         
317                                         $result = $this->$rule($_POST[$field], $param);
318                                 }
319                                                                 
320                                 // Did the rule test negatively?  If so, grab the error.
321                                 if ($result === FALSE)
322                                 {
323                                         if ( ! isset($this->_error_messages[$rule]))
324                                         {
325                                                 if (FALSE === ($line = $this->CI->lang->line($rule)))
326                                                 {
327                                                         $line = 'Unable to access an error message corresponding to your field name.';
328                                                 }                                               
329                                         }
330                                         else
331                                         {
332                                                 $line = $this->_error_messages[$rule];
333                                         }                               
334
335                                         // Build the error message
336                                         $mfield = ( ! isset($this->_fields[$field])) ? $field : $this->_fields[$field];
337                                         $mparam = ( ! isset($this->_fields[$param])) ? $param : $this->_fields[$param];
338                                         $message = sprintf($line, $mfield, $mparam);
339                                         
340                                         // Set the error variable.  Example: $this->username_error
341                                         $error = $field.'_error';
342                                         $this->$error = $this->_error_prefix.$message.$this->_error_suffix;
343
344                                         // Add the error to the error array
345                                         $this->_error_array[] = $message;                               
346                                         continue 2;
347                                 }                               
348                         }
349                         
350                 }
351                 
352                 $total_errors = count($this->_error_array);
353
354                 /*
355                  * Recompile the class variables
356                  *
357                  * If any prepping functions were called the $_POST data
358                  * might now be different then the corresponding class
359                  * variables so we'll set them anew.
360                  */     
361                 if ($total_errors > 0)
362                 {
363                         $this->_safe_form_data = TRUE;
364                 }
365                 
366                 $this->set_fields();
367
368                 // Did we end up with any errors?
369                 if ($total_errors == 0)
370                 {
371                         return TRUE;
372                 }
373                 
374                 // Generate the error string
375                 foreach ($this->_error_array as $val)
376                 {
377                         $this->error_string .= $this->_error_prefix.$val.$this->_error_suffix."\n";
378                 }
379
380                 return FALSE;
381         }
382         
383         // --------------------------------------------------------------------
384         
385         /**
386          * Required
387          *
388          * @access      public
389          * @param       string
390          * @return      bool
391          */
392         function required($str)
393         {
394                 if ( ! is_array($str))
395                 {
396                         return (trim($str) == '') ? FALSE : TRUE;
397                 }
398                 else
399                 {
400                         return ( ! empty($str));
401                 }
402         }
403         
404         // --------------------------------------------------------------------
405         
406         /**
407          * Match one field to another
408          *
409          * @access      public
410          * @param       string
411          * @param       field
412          * @return      bool
413          */
414         function matches($str, $field)
415         {
416                 if ( ! isset($_POST[$field]))
417                 {
418                         return FALSE;
419                 }
420                 
421                 return ($str !== $_POST[$field]) ? FALSE : TRUE;
422         }
423         
424         // --------------------------------------------------------------------
425         
426         /**
427          * Minimum Length
428          *
429          * @access      public
430          * @param       string
431          * @param       value
432          * @return      bool
433          */     
434         function min_length($str, $val)
435         {
436                 if (preg_match("/[^0-9]/", $val))
437                 {
438                         return FALSE;
439                 }
440
441                 if (function_exists('mb_strlen'))
442                 {
443                         return (mb_strlen($str) < $val) ? FALSE : TRUE;         
444                 }
445
446                 return (strlen($str) < $val) ? FALSE : TRUE;
447         }
448         
449         // --------------------------------------------------------------------
450         
451         /**
452          * Max Length
453          *
454          * @access      public
455          * @param       string
456          * @param       value
457          * @return      bool
458          */     
459         function max_length($str, $val)
460         {
461                 if (preg_match("/[^0-9]/", $val))
462                 {
463                         return FALSE;
464                 }
465                 
466                 if (function_exists('mb_strlen'))
467                 {
468                         return (mb_strlen($str) > $val) ? FALSE : TRUE;         
469                 }
470
471                 return (strlen($str) > $val) ? FALSE : TRUE;
472         }
473         
474         // --------------------------------------------------------------------
475         
476         /**
477          * Exact Length
478          *
479          * @access      public
480          * @param       string
481          * @param       value
482          * @return      bool
483          */     
484         function exact_length($str, $val)
485         {
486                 if (preg_match("/[^0-9]/", $val))
487                 {
488                         return FALSE;
489                 }
490         
491                 if (function_exists('mb_strlen'))
492                 {
493                         return (mb_strlen($str) != $val) ? FALSE : TRUE;                
494                 }
495
496                 return (strlen($str) != $val) ? FALSE : TRUE;
497         }
498         
499         // --------------------------------------------------------------------
500         
501         /**
502          * Valid Email
503          *
504          * @access      public
505          * @param       string
506          * @return      bool
507          */     
508         function valid_email($str)
509         {
510                 return ( ! preg_match("/^([a-z0-9\+_\-]+)(\.[a-z0-9\+_\-]+)*@([a-z0-9\-]+\.)+[a-z]{2,6}$/ix", $str)) ? FALSE : TRUE;
511         }
512
513         // --------------------------------------------------------------------
514         
515         /**
516          * Valid Emails
517          *
518          * @access      public
519          * @param       string
520          * @return      bool
521          */     
522         function valid_emails($str)
523         {
524                 if (strpos($str, ',') === FALSE)
525                 {
526                         return $this->valid_email(trim($str));
527                 }
528                 
529                 foreach(explode(',', $str) as $email)
530                 {
531                         if (trim($email) != '' && $this->valid_email(trim($email)) === FALSE)
532                         {
533                                 return FALSE;
534                         }
535                 }
536                 
537                 return TRUE;
538         }
539
540         // --------------------------------------------------------------------
541         
542         /**
543          * Validate IP Address
544          *
545          * @access      public
546          * @param       string
547          * @return      string
548          */
549         function valid_ip($ip)
550         {
551                 return $this->CI->input->valid_ip($ip);
552         }
553
554         // --------------------------------------------------------------------
555         
556         /**
557          * Alpha
558          *
559          * @access      public
560          * @param       string
561          * @return      bool
562          */             
563         function alpha($str)
564         {
565                 return ( ! preg_match("/^([a-z])+$/i", $str)) ? FALSE : TRUE;
566         }
567         
568         // --------------------------------------------------------------------
569         
570         /**
571          * Alpha-numeric
572          *
573          * @access      public
574          * @param       string
575          * @return      bool
576          */     
577         function alpha_numeric($str)
578         {
579                 return ( ! preg_match("/^([a-z0-9])+$/i", $str)) ? FALSE : TRUE;
580         }
581         
582         // --------------------------------------------------------------------
583         
584         /**
585          * Alpha-numeric with underscores and dashes
586          *
587          * @access      public
588          * @param       string
589          * @return      bool
590          */     
591         function alpha_dash($str)
592         {
593                 return ( ! preg_match("/^([-a-z0-9_-])+$/i", $str)) ? FALSE : TRUE;
594         }
595         
596         // --------------------------------------------------------------------
597         
598         /**
599          * Numeric
600          *
601          * @access      public
602          * @param       string
603          * @return      bool
604          */     
605         function numeric($str)
606         {
607                 return (bool)preg_match( '/^[\-+]?[0-9]*\.?[0-9]+$/', $str);
608
609         }
610
611         // --------------------------------------------------------------------
612
613         /**
614          * Is Numeric
615          *
616          * @access      public
617          * @param       string
618          * @return      bool
619          */
620         function is_numeric($str)
621         {
622                 return ( ! is_numeric($str)) ? FALSE : TRUE;
623         } 
624
625         // --------------------------------------------------------------------
626         
627         /**
628          * Integer
629          *
630          * @access      public
631          * @param       string
632          * @return      bool
633          */     
634         function integer($str)
635         {
636                 return (bool)preg_match( '/^[\-+]?[0-9]+$/', $str);
637         }
638
639         // --------------------------------------------------------------------
640
641         /**
642          * Is a Natural number  (0,1,2,3, etc.)
643          *
644          * @access      public
645          * @param       string
646          * @return      bool
647          */
648         function is_natural($str)
649         {   
650                 return (bool)preg_match( '/^[0-9]+$/', $str);
651         }
652
653         // --------------------------------------------------------------------
654
655         /**
656          * Is a Natural number, but not a zero  (1,2,3, etc.)
657          *
658          * @access      public
659          * @param       string
660          * @return      bool
661          */
662         function is_natural_no_zero($str)
663         {   
664                 if ( ! preg_match( '/^[0-9]+$/', $str))
665                 {
666                         return FALSE;
667                 }
668         
669                 if ($str == 0)
670                 {
671                         return FALSE;
672                 }
673
674                 return TRUE;
675         }
676
677         // --------------------------------------------------------------------
678         
679         /**
680          * Valid Base64
681          *
682          * Tests a string for characters outside of the Base64 alphabet
683          * as defined by RFC 2045 http://www.faqs.org/rfcs/rfc2045
684          *
685          * @access      public
686          * @param       string
687          * @return      bool
688          */
689         function valid_base64($str)
690         {
691                 return (bool) ! preg_match('/[^a-zA-Z0-9\/\+=]/', $str);
692         }
693
694         // --------------------------------------------------------------------
695         
696         /**
697          * Set Select
698          *
699          * Enables pull-down lists to be set to the value the user
700          * selected in the event of an error
701          *
702          * @access      public
703          * @param       string
704          * @param       string
705          * @return      string
706          */     
707         function set_select($field = '', $value = '')
708         {
709                 if ($field == '' OR $value == '' OR  ! isset($_POST[$field]))
710                 {
711                         return '';
712                 }
713                         
714                 if ($_POST[$field] == $value)
715                 {
716                         return ' selected="selected"';
717                 }
718         }
719         
720         // --------------------------------------------------------------------
721         
722         /**
723          * Set Radio
724          *
725          * Enables radio buttons to be set to the value the user
726          * selected in the event of an error
727          *
728          * @access      public
729          * @param       string
730          * @param       string
731          * @return      string
732          */     
733         function set_radio($field = '', $value = '')
734         {
735                 if ($field == '' OR $value == '' OR  ! isset($_POST[$field]))
736                 {
737                         return '';
738                 }
739                         
740                 if ($_POST[$field] == $value)
741                 {
742                         return ' checked="checked"';
743                 }
744         }
745         
746         // --------------------------------------------------------------------
747         
748         /**
749          * Set Checkbox
750          *
751          * Enables checkboxes to be set to the value the user
752          * selected in the event of an error
753          *
754          * @access      public
755          * @param       string
756          * @param       string
757          * @return      string
758          */     
759         function set_checkbox($field = '', $value = '')
760         {
761                 if ($field == '' OR $value == '' OR  ! isset($_POST[$field]))
762                 {
763                         return '';
764                 }
765                         
766                 if ($_POST[$field] == $value)
767                 {
768                         return ' checked="checked"';
769                 }
770         }
771         
772         // --------------------------------------------------------------------
773         
774         /**
775          * Prep data for form
776          *
777          * This function allows HTML to be safely shown in a form.
778          * Special characters are converted.
779          *
780          * @access      public
781          * @param       string
782          * @return      string
783          */
784         function prep_for_form($data = '')
785         {
786                 if (is_array($data))
787                 {
788                         foreach ($data as $key => $val)
789                         {
790                                 $data[$key] = $this->prep_for_form($val);
791                         }
792                         
793                         return $data;
794                 }
795                 
796                 if ($this->_safe_form_data == FALSE OR $data == '')
797                 {
798                         return $data;
799                 }
800
801                 return str_replace(array("'", '"', '<', '>'), array("&#39;", "&quot;", '&lt;', '&gt;'), stripslashes($data));
802         }
803         
804         // --------------------------------------------------------------------
805         
806         /**
807          * Prep URL
808          *
809          * @access      public
810          * @param       string
811          * @return      string
812          */     
813         function prep_url($str = '')
814         {
815                 if ($str == 'http://' OR $str == '')
816                 {
817                         $_POST[$this->_current_field] = '';
818                         return;
819                 }
820                 
821                 if (substr($str, 0, 7) != 'http://' && substr($str, 0, 8) != 'https://')
822                 {
823                         $str = 'http://'.$str;
824                 }
825                 
826                 $_POST[$this->_current_field] = $str;
827         }
828         
829         // --------------------------------------------------------------------
830         
831         /**
832          * Strip Image Tags
833          *
834          * @access      public
835          * @param       string
836          * @return      string
837          */     
838         function strip_image_tags($str)
839         {
840                 $_POST[$this->_current_field] = $this->CI->input->strip_image_tags($str);
841         }
842         
843         // --------------------------------------------------------------------
844         
845         /**
846          * XSS Clean
847          *
848          * @access      public
849          * @param       string
850          * @return      string
851          */     
852         function xss_clean($str)
853         {
854                 $_POST[$this->_current_field] = $this->CI->input->xss_clean($str);
855         }
856         
857         // --------------------------------------------------------------------
858         
859         /**
860          * Convert PHP tags to entities
861          *
862          * @access      public
863          * @param       string
864          * @return      string
865          */     
866         function encode_php_tags($str)
867         {
868                 $_POST[$this->_current_field] = str_replace(array('<?php', '<?PHP', '<?', '?>'),  array('&lt;?php', '&lt;?PHP', '&lt;?', '?&gt;'), $str);
869         }
870
871 }
872 // END Validation Class
873
874 /* End of file Validation.php */
875 /* Location: ./system/libraries/Validation.php */