tags:

views:

320

answers:

4

Hi, I have a validation class which I would like to use to check all values in my application are within allowed constraints.

I am passing an object to a static function within the validation class, from another class (in this case User)

function validate() {
    $errors = Validation::validate($this);
}

In the validation class, I create a new object and then proceed through the properties of the passed parameter object (or at least that is what I would like to do).

function validate($object) {
            $validation = new Validation();
            print_r($object);
            print_r('<br />');
            foreach($object as $key => $val) {
                print_r($val);
                isset($val->maxlength) ? $validation->validateLengthNoMoreThan($val->value, $val->maxlength) : null;
                isset($val->minlength) ? $validation->validateLengthAtLeast($val->value, $val->minlength) : null;
                isset($val->required) && ($val->required == true) ? $validation->validateNotBlank($val->value) : null;
            }
            return $validation->errors;
        }

I am printing out values within the function purely for test purposes. What I don't understand is why the object prints out fine outside of the foreach loop, but if I try to access the values within the loop, nothing is displayed.

This is what is displayed OUTSIDE of the foreach loop:

User Object ( 
[username:protected] => Property Object ( [value] => aaa [maxlength] => 12 [minlength] => 3 [required] => 1 ) 
[firstname:protected] =Property Object ( [value] => aaa [maxlength] => 12 [minlength] => 3 [required] => 1 )
[lastname:protected] =Property Object ( [value] => aaa [maxlength] => 12 [minlength] => 3 [required] => 1 ) 
) 

The validation class does NOT extend the User class, so I understand why the values would not be available, just not why they are available outside of the loop but not inside of it.

Also, what would be the best way to carry out validation on protected/private properties?

Any advice/tips would be greatly appreciated.

Thanks.

+8  A: 

From the docs ( http://us3.php.net/manual/en/language.oop5.visibility.php ):

Members declared protected can be accessed only within the class itself and by inherited and parent classes.

and from http://us3.php.net/manual/en/function.print-r.php :

print_r(), var_dump() and var_export() will also show protected and private properties of objects with PHP 5. Static class members will not be shown.

Just because print_r() can print something, doesn't mean it can be accessed by your code. consider print_r(), var_dump() and var_export() to be 'special' functions.

Scott Saunders
+1  A: 

You can get around this issue by foreach'ing the properties inside the actual object. So each object must have a validate() function, which you could enforce with an interface. E.g.:

class MyClass implements Validator {
  $var1;
  $var2;

  public function validate(){ //required by Validator interface
     $validation = new Validation();
     foreach($this as $k=>$v) {
        //run validations
     }
     return $validation->errors;     
  }
}
dnagirl
Yes indeed. This is the Visitor pattern.
Scott Saunders
drat! I so wanted to be original. ;)
dnagirl
Thanks,The only thing is I was trying not to repeat myself and having to declare the same functions in multiple classes seems a bit redundant. This isn't such an issue for my application luckily as I use a lot of inheritance so can just stick the functions in the parent class. ( I think! lol)
Dan
indeed. if User is a model, make a function on Model called validate. you'll be able to access all protected properties from there. just not User private properties.
seanmonstar
A: 

You can to use get_object_vars() function:

    $vars = get_object_vars($obj);

    foreach ($vars as $field=>$value){
         ...
    }

It works well with protected fields.

Max
I don't think that's a PHP function.
Scott Saunders
Yep, i'd it was may own wrapper function. Thx. The post is edited.
Max
according to the manual: Gets the accessible non-static properties of the given object according to scope. http://ca.php.net/manual/en/function.get-object-vars.phpSo I don't think it will solve the problem.
dnagirl
A: 

If the properties of the User object are protected or private, then the foreach won't traverse them. That may explain why you cannot access them within the foreach statement.

If this is the case, it is easily solvable by using SPL ArrayIterator interface : http://www.php.net/manual/en/class.arrayiterator.php

Petrunov