TalkPHP
 
 
Account Login
Latest Articles
» The basic usage of PHPTAL, a XML/XHTML template library for PHP
» Vulnerable methods and the areas they are commonly trusted in.
» Simple way to protect a form from bot
» The Basics On: How Session Stealing Works
» How to keep your forms from double posting data
IRC Channel
IRC Speech Bubble Join the friendly bunch on IRC...
(#TalkPHP on Freenode)

...Also available via a web interface.

See this thread for information on the TalkPHP Free Hugs Initiative™. Subject to availability.
Associates
Associates
CSS Tutorials
Reply
 
LinkBack Thread Tools Search this Thread Display Modes
Old 11-28-2007, 10:53 PM   #1 (permalink)
The Addict
 
Join Date: Nov 2007
Posts: 264
Thanks: 2
TlcAndres is on a distinguished road
Default First Generic Class

Well I've been wanting to get a generic class done for a while and I think I've finally finished one that covers the basics, and I'd like some input on which functions to optimize and the such...all help is appreciated

PHP Code:
<?



class core
{

    
//contains the main mysql abstraction layer
    
var $db;
     
//tags to be searched for
    
var $tags = array();
    
    
//all the replacement for the tags
    
var $reps = array();
    
    
//the neccesary site info
    
var $siteinfo = array();
    
    
//make a holding variable for out content
    
var $rcontent;
    
    
//the general content holder..
    
var $content;    
    
    
//holds the session and cookie names
    
var $secinfo = array('cookie'=>'TlcFinalCMS','session'=>'TlcFinalCMSession');
    
    
//holds member data
    
var $member;
    
    
//holds language
    
var $language;
    

/*====================================================+
| The General Purpose functions
|=====================================================*/


        //the constructor function
        
function core()
        {
            
$this->db NewTlcDB(DB_HOST,DB_USER,DB_PASS,DB_TABLE);
            
            
//determine the site info crap..
            
$this->siteinfo $this->db->Execute("SELECT `url`,`title`,`skin`,`lan`,`defaultmod` FROM `site_config`");
            
$this->siteinfo $this->siteinfo->fields;
            
            
//load the language file.
            
$this->LoadLanguage($this->siteinfo['lan']);
            
            
//build the tags array..
            
$this->tags = array(
                            
'<[siteurl]>',
                            
'<[skinurl]>',
                            
'<[title]>',
                            
'<[gentime]>',
                            
'<[content]>',
                            
'<[cmp(',
                            
')]>'
                        
);
                        
            
//build all there replacements.
            
$this->reps = array(
                            
$this->siteinfo['url'],
                            
$this->siteinfo['url'] . 'template/' $this->siteinfo['skin'],
                            
'<?=$this->siteinfo[\'title\']; ?>',
                            
'<?=$this->siteinfo[\'gentime\']; ?>',
                            
'<? $this->PageCreate(); ?>',
                            
'<? $this->ComponentPlace(',
                            
'); ?>'
                            
);
                            
            
//check all the member atributes
            
if($this->CheckCreds() || !$this->SessionExists())
            {
                
$this->SetUpMember();
            }
            
        }
        
        
//creates random values
        
function GenVal($len=40)
        {
            
//set all variables
            
$val '';
            
$count 0;
            
            
//start the count
            
while($count $len)
            {
                
//use this method..
                
$val .= chr(0x3 rand(0,80));
                
                
//increase the count
                
$count++;
            }
            return 
$val;
        }
                
        
        
//the open function, just opens file and returns there content
        
function open($file)
        {
            
//check if the file exists
            
if(file_exists($file))
            {
                
//it does, so open it in read mode
                
$f fopen($file,'r');
                
                
//start the loop to get contents
                
while(!feof($f))
                {
                    
$buff .= fgets($f,4096);
                }
                
                
//return the material
                
return $buff;
            }
        }
        
        
//it doesnt APPEND to files, it writes them anew
        
function write($file,$cont)
        {
                
//set it up then
                
$f fopen($file,'w');
                
                
//append to the file
                
fwrite($f,$cont);
                return 
true;
        }
        
        
//compares two strings..um, don't really know what I can use it for but w/e
        
function Compare($str1,$str2)
        {    
            
//take the string lengths of both
            
$len strlen($str1);
            
$len2 strlen($str2);
    
            
//if they aren't equal
            
if($len !== $len2)
            {
                
//set it to the biggest
                
$len = (strlen($len) > strlen($len2)) ? $len $len2;
            }
    
            
//grab the 1% value and set the total and count variables
            
$percent 100 $len;
            
$total 0;
            
$count 0;
    
            
//start the loop
            
while($len !== $count)
            {
                
//check if they're equal
                
if(substr($str1,$count,1) == substr($str2,$count,1))
                {
                    
//add the total
                    
$total +=  $percent;
                }
                    
//increase the count
                    
$count++;
            }
                    
//return a rounded down result
                    
return floor($total);
        
        }
        
        
//this is where we fetch the componenets
        
function ComponentPlace($value='')
        {
            
//
        
}
            
        
//ok here is the page create..
        
function PageCreate()
        {    
            
//hell we include it..
            
$this->Mictime();
            
            
//ok now get the data
            
$mod = !empty($_GET['mod']) ? $_GET['mod'] : $this->siteinfo['defaultmod'];
            
$mod $this->MySQLSecure($mod);
            
$mod $this->db->Execute(sprintf("SELECT `folder`,`active` FROM `modules` WHERE `name`='%s'",$mod));

            
$do = !empty($_GET['do']) ? $_GET['do'] : 'main';
            
            
//check if it's empty
            
if(empty($mod->fields['folder']))
            {
                
$this->Mictime();
                echo(
$this->language['nomod']);
                return 
false;
            }            
            
            
//check if it's in a non-active state and thus have to be an admin
            
if($mod->fields['active'] == 0)
            {
                
//they're not an admin
                
if(!$this->Access(3))
                {
                    
//display a no mod error
                    
$this->Mictime();
                    echo(
$this->language['nomod'].'e');
                }
                else
                {
                    
//the are so include the ifle
                    
$this->Mictime();
                    include(
ROOT '/modules/' $mod->fields['folder'] . '/' $do '.php');
                }
            }
            else
            {
                
//guess it is active so include the file either way
                
$this->Mictime();
                include(
ROOT '/modules/' $mod->fields['folder'] . '/' $do '.php');
            }        
        }
        
        
//an ease of use function for mysql_real_string_escape
        
function MySQLSecure($text)
        {
            return 
mysql_real_escape_string($text,$this->db->connectionID);
        }
            
        
//generate forms..it only works within the site,It's EXTREMELY basic..
        
function FormGenerate($to,$values=array(),$echo=false)
        {
            
//set up the form and create the action
            
$data '<form method="post" action="'.$this->siteinfo['url'] . $to.'">
                        <table>'
;
            
            
//start the loop, this method is supposed to be more efficient
            
while(list(, $v) = each($values))
            {
                
//create the table and such
                
$data .= '
                    <tr>
                <td><label for="'
.$v.'">'.$v.'</label><td>
                            <td><input name="'
.$v.'" id="'.$v.'" value="" size="30" maxlength="255" type="text"></td>
                    </tr>'
;
            }
            
            
//finish it all off
            
$data .= '<tr><td><input value="submit" type="submit"></td></tr></table>'
            
            
//return it all
            
if($echo) { echo($data); }else{ return $data; }
        }
        
        function 
Void()
        {
            
//do nothing
        
}
        
        
//load stuff from language file
        
function LoadLanguage($file)
        {
            if(
file_exists(ROOT '/language/' $file '.php'))
            {
                include(
ROOT '/language/' $file '.php');
                
$this->language[] .= $lan;
                unset(
$lan);
            }
        }
        
        
//Generationg time function
        
function Mictime()
        {
            
//$this->siteinfo['gentime'] = empty($this->siteinfo['gentime']) ? microtime() : microtime() - $this->siteinfo['gentime'];
            //check if the variable was alrady filled
            
if(empty($this->siteinfo['gentime']))
            {
                
//it wasnt so fille it
                
$this->siteinfo['gentime'] = microtime();
            }
            else
            {
                
//minute the bigger microtime agaist the smaller to get out time
                
$this->siteinfo['gentime'] = microtime() - $this->siteinfo['gentime'];
            }
        }
        
        
//activate the tinymce editor
        
function tinyeditor($to)
        {
            
$to $this->siteinfo['url'] . $to;
            include(
ROOT '/kernal/resources/tinyMCE.php');
        }
            
                                    

/*====================================================+
| Template portion of the API
|=====================================================*/
            
            
          
function construct($file,$cache=true,$name='',$case=true)
          {
             
$start microtime();
             
//ok does the file exists?
            
if(file_exists($file))
            {
                
//ok now that we know it does exists..call it up
                
$ofile $this->open($file);
                
                
//prepare the tags and replacements
                
$t reset($this->tags);
                
$r reset($this->reps);
                
                
//look at the case
                
$strf $case 'str_replace' 'str_ireplace';
                
                
//now set the loop
                
while($t !== false or $r !== false)
                {
                    
$ofile $strf($t,$r,$ofile);
                    
$t next($this->tags);
                    
$r next($this->reps);
                }
                
                
                
//now thats it done, does he want it cached?
                
if($cache)
                {
                    
$end microtime();
                    
$total $end $start;
                    
//he does so lets give it a name..
                    
$this->write(SYSTEM_CACHE '/' $name '.php',$ofile '<!--' date('Y:m:d'). ' ' $total '--->');
                    return 
true;
                }
                else
                {
                    
//he didn't want it cached..add it to the place holder
                    
$this->rcontent $ofile;
                }
                    
//empty out the ofile
                    
unset($ofile);
             }
          }
          
          
//function to add values to the rep and tag array
          
function addTags($tag,$rep)
          {
              
//check for any empty values
            
if(!empty($tag) || !empty($rep))
            {
                  
$this->tags[] .= $tag;
                
$this->reps[] .= $rep;
              }
          }
          
          
//it fetches the skin
          
function TempSetUp()
          {
            
//does the skin actually exists?
              
if(file_exists('cache/skincache.php'))
            {
                
//it does so include it
            
}
            else
            {
                
//it doesn't so have it construction
                
$this->construct(ROOT '/template/' $this->siteinfo['skin'] . '/index.php',true,'skincache');
            }
                include(
'cache/skincache.php');
          }

/*====================================================+
| Member portion of the API
|=====================================================*/

            //premilinrary credential checks...see if the user is logged in..nothing more
            
function CheckCreds()
            {
                
//check if the session exists and it's an array
                
if($this->SessionExists())
                {
                    return 
true;
                }
                
                
//check if a cookie exists and it's not empty
                
if(isset($_COOKIE[$this->secinfo['cookie']]) && strlen($_SESSION[$this->secinfo['cookie']]) > 0)
                {
                    return 
true;
                }
            }
            
            
//check if a session exists
            
function SessionExists()
            {
                if(isset(
$_SESSION[$this->secinfo['session']]) && is_array($_SESSION[$this->secinfo['session']]))
                {
                    return 
true;
                }
                    return 
false;
            }
            
            
//assuming they've proper session info or cookie info..lets make em up
            
function SetUpMember($user='')
            {
                
//user is empty..
                
if(empty($user))
                {
                    
//does the session even exists?
                    
if(!$this->SessionExists())
                    {
                        
//take the cookie's data
                        
$data $_COOKIE[$this->secinfo['cookie']];
                        
                        
//now preform the SQL statement
                        
$sql $this->db->Execute("SELECT `username`,`email`,`rank` FROM `users` WHERE `hash`='".$data."'");
                        
                        
//set it as a session
                        
$_SESSION[$this->secinfo['session']] = $sql->fields;
                        
$s $this->db->GetOne(sprintf("SELECT `numeric` WHERE `name`='%s'",$sql->fields['rank']));
                        
$_SESSION[$this->secinfo['session']]['rank'] = $s;
                        
                    }
                    
                }
                else
                {
                
                    
//sanitize user incase it's an input
                    
$user $this->MySQLSecure($user);
                    
                    
//I guess they want it for a specific ember
                    
$sql $this->db->Execute(sprintf("SELECT `username`,`email`,`rank` FROM `users` WHERE `username`='%s'",$user));                     
                    
//now set the session..
                    
$_SESSION[$this->secinfo['session']] = $sql->fields;
                    
$s $this->db->GetOne(sprintf("SELECT `numeric` FROM `user_rank` WHERE `name`='%s'",$sql->fields['rank']));
                    
$_SESSION[$this->secinfo['session']]['rank'] = $s;
                    
                    
//well the cookie doesn't exists obviously..so lets create it
                    
$val $this->GenVal(255);
                    
setcookie($this->secinfo['cookie'],$valtime() * 360000);
                    
$this->db->Execute(sprintf("UPDATE `users` WHERE `usersname`='%s' SET `hash`='%s'",$user,$val)); 
                }
                    
$this->member $_SESSION[$this->secinfo['session']];    
            }
            
            
//Regisers users
            
function Register($user,$pass,$email)
            {
                
//sanitize the variables into a clean array
                
$info = array(
                        
'user'=>$this->MySQLSecure($user),
                        
'pass'=>$this->MySQLSecure($pass),
                        
'email'=>$this->MySQLSecure($email)
                        );
                
//ok now make the checks
                
$c $this->db->GetOne(sprintf("SELECT `email` FROM `users` WHERE `username`='%s'",$info['user']));
                if(!empty(
$c))
                {
                    
$var = ($c == $info['emai']) ? 01 00;
                    return 
$var;
                }
                
                
$c $this->db->GetOne(sprintf("SELECT `username` FROM `users` WHERE `email`='%s'",$info['email']));
                if(!empty(
$c))
                {
                    return 
01;
                }
                
                
//ok now create the statement
                
$hash $this->MySQLSecure($this->GenVal(126));
                
$this->db->Execute(
                
sprintf("INSERT INTO `users`(`id`,`username`,`password`,`passhash`,`email`) VALUES('','%s',MD5(CONCAT('%s','%s')),'%s','%s')",
                        
$info['user'],$info['pass'],$hash,$hash,$info['email'])
                );
                
                return 
true;
                
            }
            
            
//Logs in the people
            
function Login($user,$pass)
            {
                
//sanitize variables
                
$info = array('user'=>$this->MySQLSecure($user),'pass'=>$this->MySQLSecure($pass));
                
                
$hash $this->db->GetOne(sprintf("SELECT `passhash` FROM `users` WHERE `username`='%s'",$info['user']));
                
$h $this->db->GetOne(sprintf("SELECT `username` FROM `users` WHERE `password`='%s'",md5($pass.$hash)));
                
                
//check if it's write
                
if($h == $info['user'])
                {
                    
$this->SetUpMember($info['user']);
                    return 
true;
                }
                else
                {
                    return 
false;
                }
            }
            
            
//destroys the sessions and empties the cookie
            
function Logout($user)
            {
                
//obvious...it gets rid of the current session
                
session_destroy();
                
                
//empties cookie and se hash equal to zero
                
setcookie($this->secinfo['cookie'],'',time() * 360000);
                
$this->db->Execute(sprintf("UPDATE `users` WHERE `username`='%s' SET `hash`='0'",$user));
            }
            
            
//are they even logged in?
            
function no_guest($boink=false)
            {
                
//check if the sesison exists
                
if(!$this->SessionExists())
                {
                    
//it doesnt so check if the is empty..
                    
if(strlen($_COOKIE[$this->secinfo['cookie']]) == 0)
                    {
                        if(
$boink)
                        {
                            
header('Location: http://google.com');
                        }
                    
                        
//it is return a false..
                        
return false;
                    }
                }
                        
//everything checked out so send it out as true.
                        
return true;
            }
            
            
//check if they have permission to view the site
            
function Access($lvl=0)
            {
                
//check if they are logged in first of all
                
if(!$this->no_guest())
                {
                    
//they are..so set it up
                    
$this->SetUpMember();
                                        
                    
//check if the sesion still doesn't exists
                    
if(!$this->SessionExists())
                    {
                        return 
false;
                    }
                }
                
                
//now check to 
                
if(is_numeric($this->member['rank']))
                {
                    
$ret = ($this->member['rank'] <= $lvl) ? true false;
                    return 
$ret;
                }
                    return 
false;
            }
            
            function 
KickAccess($lvl=0)
            {
                if(!
$this->Access($lvl))
                {
                    
header('Location: ' $this->siteinfo['url']);
                }
            }


}
This is my accompanying MySQL class

PHP Code:
<?

function NewTlcDB($host,$user,$pass,$db)
{
  return new 
TlcDB($host,$user,$pass,$db);
}

class 
TlcDB
{
    private 
$querycount;
    private 
$queryID;
    public static 
$connectionID;
    private 
$numrows;
    private 
$numfields;
    var 
$fetchMode MYSQL_ASSOC;
    var 
$db;
     
    function 
TlcDB($uHost$uUser$uPass$uDb$Sec=true)
    {
        if (
mysql_connect($uHost$uUser$uPass))
        {   
            
$this->connectionID mysql_connect($uHost$uUser$uPass);
        }else{ return 
false; }
        if (
mysql_select_db($uDb$this->connectionID))
        {   
            
$this->db $uDb;
        }
        
mysql_close();
        if(
$Sec)
        {
            
$this->escape $Sec;
        }
    }
    
    function 
SetDB($db)
    {
        
$this->db $db;
    }
     
    function 
_query($sql)
    {
        
$this->queryID mysql_query($sql,$this->connectionID);
        
$this->querycount++;
        return 
$this->queryID;
    }

    function 
init()
    {    
        
$this->numrows = @mysql_num_rows($this->queryID);
        
$this->numfields = @mysql_num_fields($this->queryID);
    }
 
    function 
Execute($sql)
    {   
        
$this->_query($sql);
        
$this->init();
        
$d = new RecordSet($this->queryID);
        return 
$d;
    }
    
    function 
GetOne($sql)
    {
        
$s $this->_query($sql);
        
$s = @mysql_fetch_array($s,MYSQL_ASSOC);
        if(empty(
$s))
        {
             return 
false;
        }
        return 
reset($s);
    }
    
    function 
GetRow($sql)
    {
        
$s $this->Execute($sql);
        
$e = array();
        
$i 0;
        while(!
$s->EOF)
        {
            
$e[$i] = reset($s->fields);
            
$s->MoveNext();
            
$i++;
        }
        return 
$e;
    }
    
    function 
affectedRow()
    {
        return 
mysql_affected_rows($this->connectionID);
    }
    

    function 
Databases()
    {
        
$d mysql_list_dbs($this->connectionID);
        
$a = array();
        
$i 0;
        
$m mysql_num_rows($d);
        while (
$i $m)
        {   
            
$b mysql_tablename($d$i);
            if (
$b != 'mysql')
            {
                
$a[] = $b;
            }
            
$i++;
        }
        return 
$a;
    }

    function 
ErrNo()
    {    
        if (empty(
$this->connectionID))
        {   
            return @
mysql_errno();
        }
        return @
mysql_errno($this->connectionID);

    }

    function 
ErrMsg()
    {
        if (empty(
$this->connectionID))
        {
            return @
mysql_error();
        }
        return @
mysql_error($this->connectionID);
    }

    function 
Description()
    {   
        return 
$this->GetOne("SELECT version()");
    }
    
    function 
AlphabatizeColumn($sql$col$upper false)
    {    
        
$p $upper 'toupper' 'tolower';
        
$p 'str'.$p;
        
$d $this->Execute($sql);
        
$mast = array();
        
$i = array();
        while (!
$d->EOF)
        {
            
$str $p(substr($d->fields[$col], 01));
            
$mast[$str][$i[$str]] = $d->fields[$col];
            
$i[$str]++;
            
$d->MoveNext();
        }
        return 
$mast;
    }

 
   function 
AffectedRows()
   {
     return 
mysql_affected_rows($this->connectionID);
   }

}

class 
RecordSet extends TlcDB
{
    var 
$fields = array();
    var 
$fieldCount;
    var 
$EOF;
    var 
$queryID;

    function 
RecordSet($query)
    {
        
$this->fields = @mysql_fetch_array($query$this->fetchMode);
        
$this->queryID $query;
        
$this->fieldCount++;
    }
    
    function 
basicquery($sql)
    {
       return 
$this->_query($sql);
    }

    function 
MoveNext($stop=false)
    {
        if (@
$this->fields mysql_fetch_array($this->queryID$this->fetchMode))
        {  
            
$this->fieldCount++;
             if(
$stop 0)
             {
                if(
$stop >= $this->fieldCount)
                {
                    
$this->EOF true;
                    return 
false;
                }
             }
            return 
true;
        }
        if (!
$this->EOF)
        {
            
$this->fieldCount++;
            
$this->EOF true;
        }
        return 
false;
    }
}
?>
TlcAndres is offline  
Reply With Quote
Old 11-29-2007, 03:58 AM   #2 (permalink)
La Vida es Sueño
Advanced Programmer Top Contributor 
 
Wildhoney's Avatar
 
Join Date: Sep 2007
Location: Oldham
Posts: 2,280
Thanks: 90
Wildhoney is on a distinguished road
Default

One problem that immediately springs up is the fact that you haven't used any scopes on your functions. For instance, you've prefixed some functions, such as _query, with the underscore, which tends to be indicative of a private function by Zend Framework standards. However, no scope has been set.

The scopes consist of the following:
  • Private: Only members in the same class has access.
  • Protected: Only members of the same class and those extended have access.
  • Public: Everybody has access (default)

I'll have myself a good read through tomorrow though and see what I can pick out. It does look like a good attempt nonetheless.
__________________
The man who comes back through the Door in the Wall will never be quite the same as the man who went out.
Send a message via AIM to Wildhoney Send a message via MSN to Wildhoney Send a message via Yahoo to Wildhoney
Wildhoney is offline  
Reply With Quote
Old 11-29-2007, 11:04 AM   #3 (permalink)
The Addict
 
Join Date: Nov 2007
Posts: 264
Thanks: 2
TlcAndres is on a distinguished road
Default

Thanks, wild. I never bothered learning any standards, I should look into that.
TlcAndres is offline  
Reply With Quote
Old 11-29-2007, 02:17 PM   #4 (permalink)
The Reckoner
Advanced Programmer Top Contributor 
 
Karl's Avatar
 
Join Date: Sep 2007
Posts: 437
Thanks: 22
Karl is on a distinguished road
Default

Nice start TlcAndres, you seem to have grasped the basic concepts of classes just fine. Now for the problems - I'm analyising the design and structure of your classes here, not the code it contains (I'll let someone else comment on that)

The first problem would be the cohesiveness of the "core" class - that class has so many different tasks it's near impossible to see what the object is responsible for. Good object orientated design suggests that your classes should be loosely coupled and cohesive. A good rule of thumb is "one class, one task". I'm not saying you should stick to these strictly, just being aware of them will improve your code which will in turn make the code easier for other people to understand.

I only flicked through, but I noticed you have separated different parts of the core class into "groups" - indicated by the comments. I would suggest splitting these groups into separate classes, for example, you have some methods specific to members, I would refactor the code and take these methods out of the core class, placing them into their own class.

It just makes things easier and more logical. I also find it helps to think of things in terms of responsibilities, for example, what is the core class responsible for? Each class should have a clear cut responsibility, if you can't figure out what that is (or if the class has many responsibilities) then you should reconsider your object design.

So, my first suggestion for improvement would be to refactor the class, that is, pull out all the "method groups" and place them in their own class.
__________________
Any fool can write code that a computer can understand. Good programmers write code that humans can understand.
Karl is offline  
Reply With Quote
Old 11-29-2007, 05:19 PM   #5 (permalink)
The Prestige
Advanced Programmer Top Contributor Good Samaritan 
 
sketchMedia's Avatar
 
Join Date: Oct 2007
Location: Manchester, UK
Posts: 854
Thanks: 32
sketchMedia is on a distinguished road
Default

The only thing i can see is the 'var' keyword, which in php5 was deprecated in favor of visibility scope identifiers (as pointed out by wildhoney) but left in php5 for backward compatibility.

Also as Karl says your core does seem a little confused about its purpose, i.e. having the
HTML Code:
MySQLSecure($text)
function inside the core, whereas it could be in the mysql class and also templating functions within the core too, but a good start I'd say
__________________
mysql> SELECT * FROM `users` WHERE `users`.`clue` > 0;
Empty set (0.00 sec)
sketchMedia is offline  
Reply With Quote
Old 11-29-2007, 05:28 PM   #6 (permalink)
The Wanderer
 
bmicallef's Avatar
 
Join Date: Nov 2007
Posts: 18
Thanks: 3
bmicallef is on a distinguished road
Default

I agree with Karl ... You need to step back and look at the individual roles/responsibilities you are trying to accomplish.

I typically follow the following breakdown when it comes to data drive web site classes:

1. configuration - a place to store constant data (db connection info, etc)
2. Generic database access class (something I can pass queries to and will return results, errors, etc)
3. Data access objects (these are classes that typically represent tables in the database: tags, page_content, users,etc)
the DAOs have a common interface that allows for:
- Make() returns an empty dao object ( not a datarow yet)
- Save( $obj ) inserts or updates the dao object
- Load( $id ) returns a dao object that does represent a datarow based on the primary key (Id) passed
- Delete( $id ) deletes the data row
4. Finally I create a business object to pull things together
you may have methods such as: GetTags( $pageId ) or LoadPageContent( $pageId )
this business object utilizes the multiple daos and provides more automated methods for the webpage to use instead of dealing with daïs and all the logic in the actual web page.

This approach is good practice and is generically, although not strictly, described by MVC: Model, View, Control be describes the separation of application logic into separate layers.

I hope this helps you continue on your quest for the Generic Class!

Brad

Last edited by bmicallef : 11-29-2007 at 05:31 PM. Reason: typing on an iPhone is not perfect!
Send a message via AIM to bmicallef
bmicallef is offline  
Reply With Quote
Old 11-29-2007, 05:46 PM   #7 (permalink)
bdm
The Acquainted
Good Samaritan 
 
Join Date: Nov 2007
Posts: 127
Thanks: 14
bdm is on a distinguished road
Default

bmicallef: Could you tell me more about your database class?

To the OP: Try sticking to a consistent coding style. I see a bunch of different variables, function names and code logic with different conventions. :)
bdm is offline  
Reply With Quote
Old 11-30-2007, 11:49 AM   #8 (permalink)
The Wanderer
 
bmicallef's Avatar
 
Join Date: Nov 2007
Posts: 18
Thanks: 3
bmicallef is on a distinguished road
Default

gcbdm,

I'd be happy to share what I am doing!

I create a CLASS that will act as a generic database interface

public class myDB()
{}

NOTE: I'm pretty sure DB() is defined in the Zend framework and should be considered reserved ...

The class contains a number of private attributes:

private $_connection = null;
private $_rows_affected = 0;
private $_last_inserted_id = 0;
private $_results = null;
private $_error_message = null;
private $_error_number = null;

I use the __construct() method to set the connection string (I pull login and server variables from a separate configuration class e.g. myConfig::dbUsername, etc.) and I open the connection.

The __construct() method contains error handling that will SET the $_error_number and $_error_message attributes in the event of a failure.

I then have a public method called Query( $sql ) that allows me to pass SQL statements directly.

The Query() CLASS returns a bool (True or False) if the query was successful, but sets the above mentioned private attributes.

NOTE: Like __construct(), this method also contains error handling logic.

Finally, I have a series of Accessors that allow me to GET the values from my private attributes:

public function GetResults()
{
results $this->_results;
}

... etc.

So to use this you do something like this:

$sql = "SELECT * FROM mytable WHERE somevalue = 1";

$db = new myDB();

if ( $db->Query( $sql ) )
{
doSomething( $db->GetResults() );
}

I hope this helps!

Brad
Send a message via AIM to bmicallef
bmicallef is offline  
Reply With Quote
Reply



Currently Active Users Viewing This Thread: 1 (0 members and 1 guests)
 
Thread Tools Search this Thread
Search this Thread:

Advanced Search
Display Modes

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

vB code is On
Smilies are On
[IMG] code is On
HTML code is Off
Trackbacks are On
Pingbacks are On
Refbacks are On


All times are GMT. The time now is 12:42 PM.

 
     

Powered by vBulletin® Version 3.6.8
Copyright ©2000 - 2013, Jelsoft Enterprises Ltd.
Search Engine Optimization by vBSEO 3.1.0
Inactive Reminders By Icora Web Design