Segédletek.hu

Segédletek weblap szerkesztéshez!
ingyen letöltés

| Mind | PHP | HTML | CSS | Java |
|Legújabbak |Legtöbbször olvasottak|

Készítsünk adatbázis burkolót:

Adatbázis eléréséhez PHP-ban rengeteg függvény segítségünkre van. Jó ötletnek tünhet ezek elrejtése egy adatbázi burkolóval.
Legfőbb előnye abban mutatkozik meg, hogy segítségével ( és egy Gyár-függvénnyel) hihetetlen egszerüen tudunk váltani adatbázis kiszólgálók és adatbázis- tipusok között. Példaként gondoljunk bele hány fájlt, hány sort kéne megváltoztatnunk ha mySQL helyett mondjuk SQLite-ra kell átálnunk.

Ennek elkerülésére vezessünk be egy absztrakt felületet amit majd megvalósíthatnak az SQL meghajtó osztályaink.
<?php
abstract class DB{ 
  protected $dbname//Adatbázis neve
  protected $dbh; //Adatbázis azonosító
  abstract public function connect(); //Kapcsolódás az adatbázishoz
  abstract public function execute($query); //Lekérdezés végrehajtása
  abstract public function insert_id(); //Utoljára beszúrt sor id-ja
}
?>
Most már birtokában vagyunk egy lekéréshez szükséges felületnek, de még egységesítenünk kell az eredményt is:
<?php
abstract class DB_Statement{

  public $result; //Eredménytábla azonosítója
  protected $query//Összeállított lekérdezés
  protected $dbh//Adatbázis azonosító
  abstract public function __construct($dbh, $query);
  abstract public function num_rows()//Eredménytábla sorainak száma
  abstract public function fetch_row()//Eredménytábla első sora tömbelemenként
  abstract public function fetch_assoc()//Eredméytábla első sora asszociatív tömbként
  abstract public function fetchall_assoc()//Teljes eredménytábla kétdimmenziós tömbként
   
}
?>
Az alábbi példában nézzük meg hogyan valósíthajuk meg adatbáziskezelő osztályainkat mySQL adatbázisokhoz.
<?php
class DB_Mysql extends DB{
  protected $user;     //Felhasználónév
  protected $pass;     //Jelszó
  protected $dbhost;   //Adatbázis szerver
 
  public function __construct($user, $pass, $dbhost, $dbname){
    //Beállítjuk a csatlakozáshoz szükséges adatokat
    $this->user   = $user;
    $this->pass   = $pass;
    $this->dbhost = $dbhost;
    $this->dbname = $dbname;
  }
 
  function connect(){
    //Csatlakozás az adatbázishoz pconnect függvénnyel
    $this->dbh = mysql_pconnect($this->dbhost,
                                $this->user,
                                $this->pass);
    //Hiba esetén kivételeket dobunk a vezérlőnek
    if (!is_resource($this->dbh)) {
      throw new Exception();
    }
    if (!mysql_select_db($this->dbname)) {
      throw new Exception();
    }

  }
     
  public function execute($query){
    //Ha még nem tettük, csatlakozunk az adatbázishoz
    if (!$this->dbh){
      $this->connect();
    }
    //Végrehajtjuk a lekérdezést ha nem sikerül kivételt dobunk
    $ret = mysql_query($query, $this->dbh);
    if (!$ret){
      throw new Exception($query ."" .mysql_error() );
    }
    else if ( !is_resource($ret)){
      //Ha olyan parancsot futtatunk, ami nem ad vissza eredményt, igazzal térünk vissza
      return true
    } else {
      //Különben pedig visszatérünk az eredménytleíró osztályunkkal
      $stmt = new DB_MysqlStatement($this->dbh);
      $stmt->result = $ret;
      return $stmt;
    }
  }
   
  public function insert_id(){
    //Utoljára beszúrt elem id-jét adja vissza
    return mysql_insert_id();
  }
}
?>
Mindjárt ott tartunk, hogy ki tudjuk próbálni a gyakorlatban is, de még hátra van az eredményt leíró objektumunk megvalósítása
<?php
class DB_MysqlStatement extends DB_Statement {
 
  public function __construct($dbh){
    //Megkapjuk az adatbáziskapcsolatot és ellenőrizzük
    $this->dbh = $dbh;
    if (!is_resource($dbh)){
      throw new Exception("Not valid database connection");
    } 
  }
 
  public function num_rows() {
    //Sorok száma
    return mysql_num_rows($this->result);
  }
  //Műveletek megvalósítása
  public function fetch_row() {
    if (!$this->result) {
      throw new Exception("Query not executed");
    }
    return mysql_fetch_row($this->result)
  }
 
  public function fetch_assoc() {
    return mysql_fetch_assoc($this->result);
  }
 
  public function fetchall_assoc() {
    $retval = array();
    while ($row = $this->fetch_assoc()){
      $retval[] = $row;
    }
    return $retval;
  }
}
?>
Most már minden megvan, itt az ideje kipróbálni gyakorlatban is
<?php
   //Hozzunk létre egy adatbázis osztályt
   $db = new DB_Mysql("root","root", "localhost","burkolo");
   $db->connect()//nem muszáj használni mert az első lekérdezéskor automatikusan meghívódik
   
   //Hozzunk létre egy táblát
   $query"CREATE TABLE pelda (
                id INT NOT NULL AUTO_INCREMENT PRIMARY KEY ,
                title VARCHAR( 30 ) NOT NULL ,
                text TEXT NOT NULL
              )"
;
   $db->execute($query);
   //Szúrjunk be pár elemet
   $query_array = array (
         "INSERT INTO pelda VALUES('','első cikk','Első cikkem az adatbázis burkolórol szól') ",
         "INSERT INTO pelda VALUES('','második cikk','Második cikkem valószinüleg az ACL technika bemutatása lesz') "
         //...
         //... 
   );
   foreach( $query_array as $query){
     $db->execute($query);
   }
   
   //Végül kérdezzük le és irassuk ki
   $query = "SELECT * FROM pelda";
   $stmt = $db->execute($query);
   print "<pre>";
   print_r($stmt->fetchall_assoc());
   print "</pre>";
   
   //használhatjuk rövidebben is:   
   print_r( $db->execute($query)->fetchall_assoc() );
?>

Írta: Firith - 2007-03-06 18:09:35

* Nem vagy bejelentkezve!
* Nem töltheted le a segédlet forrását egyben!
* Nem szavazhatsz a segédletre!
* Nem írhatsz a segédlethez tartozó fórum témába!


Firith 2007-03-09 00:24:04
Láttam én is de ha rákattintok szemembe vigyorog egy "Go away!" felirat
requiem 2007-03-08 15:54:34
Hmmm, ki mondta, hogy nem lehet módosítani a segédletet? :)
még mielőtt vélegesíted, ott van a kis jegyzettömb ikon :)
Firith 2007-03-08 09:52:02
Az osztályokhoz tartozó kivételekre tényleg érdemes létrehozni egy új kivétel-osztályt, ez most kimaradt :) de kiindulásnak szerintem így is megteszi.
Az osztály amit bemutattam a PHP fejlesztés felsőfokon című könyvben szerepel, de szerintem sokan nem ismerik ezt a könyvet, pedig ez a megoldás nagyon hasznos. Tudom hiba volt nem feltüntetni, de tudnod kell, hogy nagyon sokat szenvedtem azzal, hogy megjelenjen a cikk, mert az oldal nem tudta fogadni a ' karaktert, a módosítás funkció meg nem elérhető, mindig újra be kellett másolnom az egész cikket. A végére majdnem elment a kedvem az egésztől.
Ami a következő cikkemben benne lesz, az már (szerintem) nincs benne a könyvben, szeretném megmutatni egy egyszerű gyár-függvénnyel, milyen egyszerű a váltás.

"Nem látom be mien előnye van megmutatni a felhasználónak..." ezt sajna nem értettem mire írod, de jó lenne ha kifejtenéd.
Gaia 2007-03-07 15:49:37
Ja és még annyi hogy fölösleges a fetch-nél a fetch_assoc-ot kiírni, mer nem látom be hogy mien alapon használ vki mysql_fetch_row() -t ~ _assoc helyett...
Gaia 2007-03-07 15:45:24
Én is vmi iesmire gondoltam...
1-2 megjegyzés: abstract class helyett sztem inkább az interface -t kellene használni, mert az összességében rövidebb nem kell mindenhova beírni az abstract tulajdonságot.
A kivételekkel kapcsolatban meg én nem bízok meg a php alap kivételosztályában szal vagy írj 1 saját class MysqlException extends Exception -t, vagy csinálj még 1 error() funkciót az osztályba hogy akkor már a hibakezelést is letudd. Nem látom be mien előnye van megmutatni a felhasználónak ráadásul akkor még figyelni kell arra is hogy
try
{
$sql = new DB_Mysql('...');
}
catch(Exception $e)
{
...

Ja meg még annyi hogy ez majdnem 100%-osan vmi PHP-s könyvből van... nem jut eszembe a címe. Nem rosszmájuságként, csakhogy tisztába legyenek vele az olvasók.
Firith 2007-03-06 20:52:12
Remélem meg lehet érteni, nem túl sok dolgot írtam hozzá :)
Azért szeretem használni, mert elrejti a MySQL-t, így bármikor megírhatom más adatbázisra, csak az absztrakt felületből kell származtatnom
requiem 2007-03-06 18:16:25
hmmm... fincsi :)
Ultra-zoom fényképezőgép
Széles látószögű, 15x optikai zoom-os Samsung fényképezőgépek!
www.samsung.com

Önnek is jár évi 72 000 forint
állami támogatás lakás-előtakarékosság esetén. Válassza a Fundamentát!
www.fundamenta.hu

Miért fizetne többet?
Akciós élelmiszer, műszaki cikk, gyümölcs, bútor. Nézzen be, megéri!
www.tesco.hu

Ford Focus ajánlat
Ford Focus most akár 1.160.000 Ft kedvezménnyel az Öné lehet!
Focus.Ford.hu

Lakástakarék
Éljen a lehetőséggel! Állami támogatás. Kedvező fix törlesztő és futamidő.
lakastakarek.com

Hirdessen itt