TalkPHP

TalkPHP (http://www.talkphp.com/forums.php)
-   Absolute Beginners (http://www.talkphp.com/absolute-beginners/)
-   -   acessing multiple methods.... (http://www.talkphp.com/absolute-beginners/4324-acessing-multiple-methods.html)

allworknoplay 05-17-2009 03:48 PM

acessing multiple methods....
 
Is there any way to access multiple methods so you don't have to type the variable you're checking against over and over?

For example, instead of this:

PHP Code:

$val->checkEmpty($username);
$val->checkLength($username); 

I want to be able to check for both empty and length in one shot.

So I tried this, but it didn't work.

PHP Code:

$val->checkEmpty->checkLength($username); 


Salathe 05-17-2009 03:58 PM

Perhaps write another method which takes the variable and a list of checks.

PHP Code:

$val->check($username'empty''length'); 


allworknoplay 05-17-2009 04:15 PM

Quote:

Originally Posted by Salathe (Post 24209)
Perhaps write another method which takes the variable and a list of checks.

PHP Code:

$val->check($username'empty''length'); 


Thanks, I'll look into doing it that way, and using optional arguments in the methods so they behave differently based on what's passed to them...

PHP Code:

$val->check($email'empty''email');
$val->check($username'empty''length''username');
$val->check($sex'empty''sex'); 

Hopefully what I typed above doesn't break any rules....
And hopefully the class method doesn't get too big and bloated looking...

Wildhoney 05-17-2009 05:01 PM

1 Attachment(s)
Building upon Salathe's idea, I came up with the following which may well work:

php Code:
class TalkPHP_Check
{
    const NOT_EMPTY = '_isNotEmpty';
    const IS_EMAIL = '_isEmail';
   
    public function isValid($szVariable)
    {
        $bValidated = false;
        $aArgs = func_get_args();
        array_shift($aArgs);
       
        foreach ($aArgs as $szFunction)
        {
            if (!method_exists($this, $szFunction))
            {
                throw new Exception(sprintf('Method does not exist: %s', $szFunction));
            }
           
            $bValidated = $this->$szFunction($szVariable);
           
            if (!$bValidated)
            {
                return false;
            }
        }
       
        return true;
    }
   
    private function _isNotEmpty($szVariable)
    {
        if (empty($szVariable))
        {
            return false;
        }
       
        return true;
    }
   
    private function _isEmail($szVariable)
    {
        if (!preg_match('~^.+?@.+?\..+?$~i', $szVariable))
        {
            return false;
        }
       
        return true;
    }
}

Then of course to use that you would simply do:

php Code:
$szEmail = 'adam@example.com';
$pCheck = new TalkPHP_Check();
$bResult = $pCheck->isValid($szEmail, TalkPHP_Check::NOT_EMPTY, TalkPHP_Check::IS_EMAIL);
var_dump($bResult);

If you want me to explain the code, please ask! I don't know if it's understandale or not, as it is.

allworknoplay 05-17-2009 05:27 PM

Quote:

Originally Posted by Wildhoney (Post 24213)
Building upon Salathe's idea, I came up with the following which may well work:

php Code:
class TalkPHP_Check
{
    const NOT_EMPTY = '_isNotEmpty';
    const IS_EMAIL = '_isEmail';
   
    public function isValid($szVariable)
    {
        $bValidated = false;
        $aArgs = func_get_args();
        array_shift($aArgs);
       
        foreach ($aArgs as $szFunction)
        {
            if (!method_exists($this, $szFunction))
            {
                throw new Exception(sprintf('Method does not exist: %s', $szFunction));
            }
           
            $bValidated = $this->$szFunction($szVariable);
           
            if (!$bValidated)
            {
                return false;
            }
        }
       
        return true;
    }
   
    private function _isNotEmpty($szVariable)
    {
        if (empty($szVariable))
        {
            return false;
        }
       
        return true;
    }
   
    private function _isEmail($szVariable)
    {
        if (!preg_match('~^.+?@.+?\..+?$~i', $szVariable))
        {
            return false;
        }
       
        return true;
    }
}

Then of course to use that you would simply do:

php Code:
$szEmail = 'adam@example.com';
$pCheck = new TalkPHP_Check();
$bResult = $pCheck->isValid($szEmail, TalkPHP_Check::NOT_EMPTY, TalkPHP_Check::IS_EMAIL);
var_dump($bResult);

If you want me to explain the code, please ask! I don't know if it's understandale or not, as it is.


I just started re-coding my class based on Sal's suggestion. I'll take a look at yours since it builds off of his suggestion.

Quickly glancing it, I think I do get it...

^^

allworknoplay 05-17-2009 06:32 PM

Ok, I do have some questions.

1)You create constants so you can call them statically from the main script. Then pass them as arguments in the isValid() function. How are you able to pass in extra arguments when it's not defined in the function? Or does PHP loosely allow you to add optional arguments without have to specify them when creating the functions? And if so, does this work for regular functions too or just class methods?


2) $bValidated is set to false. Why do we do this? Is this because we have to declare every property in the class before using it?

3) array_shift($aArgs). Since in your example, you passed 3 arguments to the isValid function and then do a foreach loop on the array $aArgs, are you shifting to the 2nd element so that the foreach starts from there, so basically all we get are the 2 constants: NOT_EMPTY and IS_EMAIL....?

4) After checking if a method exists, I'm a little unclear on what we do here. We set:

$bValidated = $this->$szFunction($szVariable);

I don't see any methods called: $szFunction, so I'm not sure what is going on here.

5) We then do this:

PHP Code:

if(!$bValidated) { return false; } 

But since further up, we already declare $bValidated as false, wouldn't putting a negation operator convert it to true?


6) Since the other methods are set to private. Is the isValid method basically our "getter" method?

allworknoplay 05-17-2009 07:37 PM

Ok, I understand #4 now...

PHP Code:

$bValidated $this->$szFunction($szVariable); 

Of course there's no function called $szFunction, it's taking the name of the passed element from the foreach array!!!
Then passes the actual data, so that the method actually gets called...

DUH!

Salathe 05-17-2009 07:46 PM

Quote:

Originally Posted by allworknoplay (Post 24217)
1)You create constants so you can call them statically from the main script. Then pass them as arguments in the isValid() function. How are you able to pass in extra arguments when it's not defined in the function? Or does PHP loosely allow you to add optional arguments without have to specify them when creating the functions? And if so, does this work for regular functions too or just class methods?

Functions and methods can accept any number of arguments. The function definition just defines some required, or optional with defaults, arguments. See function arguments.

Quote:

Originally Posted by allworknoplay (Post 24217)
2) $bValidated is set to false. Why do we do this? Is this because we have to declare every property in the class before using it?

It would probably (from my understanding of the code) be more useful to name it $bValid. There is no requirement to declare object properties before using them but $bValidated is not a property anyway, just a regular variable.

Quote:

Originally Posted by allworknoplay (Post 24217)
3) array_shift($aArgs). Since in your example, you passed 3 arguments to the isValid function and then do a foreach loop on the array $aArgs, are you shifting to the 2nd element so that the foreach starts from there, so basically all we get are the 2 constants: NOT_EMPTY and IS_EMAIL....?

Yes. array_shift just removes (and returns) the first item from the array (in this case, of arguments).

Quote:

Originally Posted by allworknoplay (Post 24217)
4) After checking if a method exists, I'm a little unclear on what we do here. We set:

$bValidated = $this->$szFunction($szVariable);

I don't see any methods called: $szFunction, so I'm not sure what is going on here.

This is a little obscure concept if you've not seen it before: it uses the concept of variable functions. Say, for example, $szFunction had a value of 'foo' then the line would actually call $this->foo($szVariable);.

Quote:

Originally Posted by allworknoplay (Post 24217)
5) We then do this:

PHP Code:

if(!$bValidated) { return false; } 

But since further up, we already declare $bValidated as false, wouldn't putting a negation operator convert it to true?

The value associated with the variable is not changed, the negation is only for the condition used for the if. It is just asking if $bValidated is false, if so return false.

Quote:

Originally Posted by allworknoplay (Post 24217)
6) Since the other methods are set to private. Is the isValid method basically our "getter" method?

No. Getter methods only provide an interface to accessing private (or protected) class members. This is just a regular, plain method—no special name.

allworknoplay 05-17-2009 09:01 PM

Quote:

Originally Posted by Salathe (Post 24219)
There is no requirement to declare object properties before using them but $bValidated is not a property anyway, just a regular variable.

Got it. So if the variable was created within the class scope, then it would be a class property. As it is, it's just a regular local variable within the method scope...

Quote:

Originally Posted by Salathe (Post 24219)
This is a little obscure concept if you've not seen it before: it uses the concept of variable functions. Say, for example, $szFunction had a value of 'foo' then the line would actually call $this->foo($szVariable);.

I didn't realize this at first. I am familiar with "variable variables", or some call it "indirect variables".

This is the first time I've seen it used for functions.
Very tricky....gotta keep an eye out for this in the future...

Quote:

Originally Posted by Salathe (Post 24219)
The value associated with the variable is not changed, the negation is only for the condition used for the if. It is just asking if $bValidated is false, if so return false.

I'll have to ponder on this a little bit. I understand that we are not changing the value, still confused about why (!) doesn't equate the variable to "true", if it was originally set as "false".

The way I am seeing it, (which is probably wrong) is this:

if(!false) return true;


Quote:

Originally Posted by Salathe (Post 24219)
No. Getter methods only provide an interface to accessing private (or protected) class members. This is just a regular, plain method—no special name.

Ok so getter and setter methods = access to class properties.



Here's what I have working so far. Obviously the layout is a quick hack....but it's functioning!

http://www.gatebattle.com/form.html

What I am going to try to do next is provide the error info next to each input element so you know what the actual error status is talking about, instead of just listing it.

allworknoplay 05-17-2009 09:21 PM

Here's my class. As you can see, it has parts of what WH provided earlier on...

I have some issues with this which I will be working on.

1) There's no way yet to correlate the errors with the data input. So right now all the errors get thrown into an array and then just printed out.

2) The string length check is minimum of 6. Not sure if this is good to be hardcoded.

3) Need to have a characters range method.

4) Sanitizing data input from SQL injects and buffer overflow. Don't know if this belongs in the validation class, or the database class.

5) Checking for existence of username/email already in the system.

PHP Code:

<?php

    
// VALIDATION CLASS
    
    
class Validation {

        private 
$_errorList = array();
        const 
CHECK_EMPTY '_checkEmpty';
        const 
CHECK_EMAIL '_checkEmail';
        const 
CHECK_LENGTH '_checkLength';
        
        private 
$aValidationRules  = array(
        
'name' => '[A-Za-z0-9\.|-|_/i]{2,20}',
        
'company' => '[A-Za-z0-9\.|-|_/i]{3,30}'
        
'address' => '[A-Za-z0-9\.|-|_/i]{3,50}'
        
'email' => '([^\W][a-zA-Z0-9_]+(\.[a-zA-Z0-9_]+)*\@[a-zA-Z0-9_]+(\.[a-zA-Z0-9_]+)*\.[a-zA-Z]{2,4})'
        
'phone' => '(\s*\[?0\d{4}\]?\s*\d{6}\s*)|(\s*\[?0\d{3}\]?\s*\d{3}\s*\d{4}\s*)'
        
);

        
        public function 
__construct() {
            
//RUN THIS METHOD TO CLEAR ERROR LIST AND START FRESH
            
$this->_resetErrorList();
        }
        
        

        public function 
checkValid($szVariable) {
        
            
$bValid false;
            
$aArgs func_get_args();
            
array_shift($aArgs);
            
            foreach (
$aArgs AS $szFunction) {
            
                if(!
method_exists($this$szFunction)) {
                    throw new 
Exception(sprintf('Method does not exist: %s'$szFunction));
                }
            
                
$bValid $this->$szFunction($szVariable);
                
                if(!
$bValid) return false;
            
            }
            
        }
        
        
        private function 
_checkEmpty($szVariable) {

            if(empty(
$szVariable)) {
                
$this->_errorList[] = 'Data is Empty';
                return 
false;
            }else{
                return 
true;
            }
        }
        
        private function 
_checkEmail($szVariable) {

            
$pattern $this->aValidationRules['email'];
            
            if(
preg_match($pattern$szVariable))
            {
                return 
true;
            }else{
                
$this->_errorList[] = 'Not a valid email address';
                return 
false;
            }
        }
        
        private function 
_checkLength($szVariable) {

            if(
strlen($szVariable) < 6) {
                
$this->_errorList[] = 'Too short';
                return 
false;
            }else{
                return 
true;
            }
        }
        
        public function 
countErrors()
        {
            
            
$count count($this->_errorList);
            
            if (
$count 0)
            {
                return 
$count;
            }
            else
            {
                return 
false;
            }
        }
    
        
        public function 
getErrorList()
        {
            return 
$this->_errorList;
        }
        
        
        
// THIS GETS CALLED ON NEW INSTANTIATED OBJECT TO START FRESH
        
private function _resetErrorList()
        {
            
$this->_errorList = array();
        }




}
//END Validation Class
    
?>


allworknoplay 05-17-2009 10:32 PM

BTW, this is what my main script looks like:

PHP Code:

<?

    
function __autoload($class_name) {
        require_once 
'includes/' $class_name '.php';
    }

$val = new validation();

$username $_POST['username'];
$email $_POST['email'];

echo 
"Username is: " $username "<br /><br />";
echo 
"Email is: " $email "<br /><br />";

echo 
$val->checkValid($username,VALIDATION::CHECK_EMPTY,VALIDATION::CHECK_LENGTH)  . "<br /><br />";
echo 
$val->checkValid($email,VALIDATION::CHECK_EMPTY,VALIDATION::CHECK_EMAIL)  . "<br /><br />";

$errors $val->getErrorList();

echo 
"Error status, if any. <Br />";
echo 
"------------------------ <Br />";
if(
$val->countErrors()) {
    echo 
"<ul>";
    foreach (
$errors AS $e) {
        echo 
"<li>" $e;    
    }
    echo 
"</ul>";
}
if(!
$val->countErrors()) echo "ALL IS GOOD! <Br />";
?>


Wildhoney 05-17-2009 11:51 PM

Quote:

Originally Posted by allworknoplay (Post 24221)
I'll have to ponder on this a little bit. I understand that we are not changing the value, still confused about why (!) doesn't equate the variable to "true", if it was originally set as "false".

$bValidated shouldn't remain false. If all is well, it'll be changed to true from either of the two private functions.

php Code:
$bValidated = $this->$szFunction($szVariable);

If it's still false after that then it failed validation.

Tanax 05-18-2009 11:51 AM

Quote:

Originally Posted by allworknoplay (Post 24221)
I'll have to ponder on this a little bit. I understand that we are not changing the value, still confused about why (!) doesn't equate the variable to "true", if it was originally set as "false".

The way I am seeing it, (which is probably wrong) is this:

if(!false) return true;

It's wrong.
Basicly
PHP Code:

if(!$bValidated) return false

is essentially the same as putting
PHP Code:

if($bValidated != true) return false;
// or if($bValidated == false) return false; 



All times are GMT. The time now is 04:49 PM.

Powered by vBulletin® Version 3.6.8
Copyright ©2000 - 2013, Jelsoft Enterprises Ltd.
Search Engine Optimization by vBSEO 3.1.0