| 

.NET C# Java Javascript Exception

0
Heute geht es darum, wie man auf möglichst einfache Weise eine Klasse in PHP realisiert, welche den Datensatz einer MySQL-Datenbanktabelle repräsentiert. Dazu soll ausschließlich auf die Verwendung von Standard-PHP-Mitteln zurückgegriffen werden, ohne dass irgendwelche Frameworks oder PlugIns benötigt werden. Zunächst … Weiterlesen

Heute geht es darum, wie man auf möglichst einfache Weise eine Klasse in PHP realisiert, welche den Datensatz einer MySQL-Datenbanktabelle repräsentiert. Dazu soll ausschließlich auf die Verwendung von Standard-PHP-Mitteln zurückgegriffen werden, ohne dass irgendwelche Frameworks oder PlugIns benötigt werden. Zunächst sollte man sich überlegen, welche Operationen notwendig sind, um sinnvoll mit einem konkreten Objekt arbeiten zu können – prinzipiell sollen Daten gelesen und geschreiben werden.

Zunächst benötigt man einen Datenbank-Handler, welche für die Kommunikation mit der Datenbank verwendet wird. Anschließend kann man sich auch schon der Klasse widmen, die den Datensatz einer Tabelle repräsentieren soll. Da wir den Datenbankhandler innerhalb der Klasse verwenden wollen ist es sinnvoll diesen auch dort als Variable zu deklarieren. Weiterhin benötigen wir den Namen der Tabelle, auf die zugegriffen werden soll, den Namen des ID-Feldes, sowie ein Array, welches die Informationen aus der Datenbank hält. Außerdem soll die Klasse mit Auto_increment (die ID wird automatisch bei einem Insert erzeugt) und ohne Auto_increment arbeiten können. Natürlich soll auf die Tabellenspalten auf die übliche Weise ($obj->spaltenname) zugegriffen werden können, sodass die __get und die __set-Methoden überschrieben werden müssen. Bei der Speicherung eines Datensatz muss nun zwischen Insert und Update unterschieden werden, je nachdem, ob der Datensatz bereits in der Datenbank existiert oder nicht. Hierzu wird sowohl eine save()-Methode realisiert, welche die Unterscheidung automatisch vornimmt, also auch eine insert() und eine update()-Methode. Dadurch wird erreicht, dass Datensätze später sehr einfach kopiert werden können.

Eine Implementierung, welche all diese Anforderungen erfüllt könnte wie folgt aussehen:

$dbHandler = mysql_connect("server", "user", "pass");
mysql_select_db("datenbankname", $dbHandler);
class Data {
 protected $dbHandler;
 protected $tableName;
 protected $idField;
 protected $autoIncrement;
 protected $data;
 /**
 * Konstruktor
 *
 * Setzt die Tabellenparameter, laedt die Feldnamen und prueft,
 * ob die Tabelle mit Auto-Increment arbeitet
 *
 * @param string $tableName Name der Tabelle
 * @param string $idField Name des ID-Feldes
 */
 public function __construct($tableName, $idField = null) {
 global $dbHandler;
 $this->dbHandler = $dbHandler;
 $this->tableName = $tableName;
 $this->idField = $idField;
 $this->loadFieldsNames();
 $this->setAutoIncrementValue();
 }
 /**
 * Laedt die Spaltenname der Tabelle und erstellt die
 * entsprechenden Felder im $data-Array
 */
 private function loadFieldsNames() {
 $query = "SHOW COLUMNS FROM ".$this->tableName;
 $res = mysql_query($query, $this->dbHandler) or die(mysql_error());
 while ($row = mysql_fetch_assoc($res)) {
 	$this->data[$row["Field"]] = null;
 }
 }
 /**
 * Prueft, ob die Tabelle mit Auto-Increment arbeitet oder nicht.
 */
 private function setAutoIncrementValue() {
 $query = "SHOW TABLE STATUS LIKE '".$this->tableName."'";
 $res = mysql_query($query) or die(mysql_error());
 $row = mysql_fetch_assoc($res);
 if ( is_null($row['Auto_increment']) ) {
 	$this->autoIncrement = false;
 } else {
 	$this->autoIncrement = true;
 }
 }
 /**
 * Laedt den Datensatz mit dem angegebenen Identifier aus der Datenbank
 *
 * @param mixed $id Identifier der Tabelle
 *
 * @return bool
 */
 public function load($id) {
 $this->$idField = $id;
 $query = "SELECT * FROM ".$this->tableName."
 WHERE ".$this->idField." = '".$id."'";
 $res = mysql_query($query, $this->dbHandler) or die(mysql_error());
 if ( mysql_num_rows($res) > 0 ) {
 	$this->data = mysql_fetch_assoc($res);
 	return true;
 } else {
 	return false;
 }
 }
 /**
 * Ueberschreibt die __get-Methode und ermittelt den Wert des Datensatzes
 *
 * @param string $fieldName Name des Feldes
 *
 * @return mixed
 */
 public function __get($fieldName) {
 return $this->data[$fieldName];
 }
 /**
 * Ueberschreibt die __set-Methode und setzt den Wert im $data-Array
 *
 * @param string $fieldName Name des Feldes
 * @param mixed $value		Wert des Feldes
 */
 public function __set($fieldName, $value) {
 if ( array_key_exists($fieldName, $this->data) ) {
 	$this->data[$fieldName] = $value;
 }
 }
 /**
 * Speichert den Datensatz in der Datenbank. Ist der Datensatz bereits
 * vorhanden wird ein Update durchgefuehrt, andernfalls ein Insert.
 *
 * @return bool
 */
 public function save() {
 if ( is_null($this->data[$this->idField]) ) {
 	return $this->insert();
 } else {
 	return $this->update();
 }
 }
 /**
 * Fuegt den Datensatz in die Datenbank ein.
 *
 * @return bool
 */
 public function insert() {
 if ( $this->autoIncrement ) {
 	$values = array_diff_key($this->data, array($this->idField => null));
 	$query = "INSERT INTO ".$this->tableName."
 (".implode(",", array_keys($values)).")
 VALUES ('".implode("','", $values)."')";
 } else {
 	$this->data[$this->idField] = $this->getNextId();
 	$query = "INSERT INTO ".$this->tableName."
 (".implode(",", array_keys($this->data)).")
 VALUES ('".implode("','", $this->data)."')";
 }
 if ( mysql_query($query, $this->dbHandler) ) {
 	if ( $this->autoIncrement ) {
 		$this->data[$this->idField] = mysql_insert_id();
 	}
 	return true;
 } else {
 	if ( !$this->autoIncrement ) {
 		$this->data[$this->idField] = null;
 	}
 	return false;
 }
 }
 /**
 * Fuehrt ein Update auf den Datensatz durch.
 *
 * @return bool
 */
 public function update() {
 $values = array_diff_key($this->data, array($this->idField => null));
 foreach ($values as $key => $value) {
 	$values[$key] = $key."='".$value."'";
 }
 $query = "UPDATE ".$this->tableName. " SET ".implode(" AND ", $values)."
 WHERE ".$this->idField." = ".$this->data[$this->idField];
 if ( mysql_query($query, $this->dbHandler) ) {
 	return true;
 } else {
 	return false;
 }
 }
 /**
 * Ermittelt die naechste ID fuer ein Insert. Wird nur dann verwendet,
 * wenn die Tabelle ohne Auto_increment arbeitet.
 *
 * @return int
 */
 private function getNextID() {
 $query = "SELECT MAX(".$this->idField.") as max FROM ".$this->tableName;
 $res = mysql_query($query, $this->dbHandler);
 $row = mysql_fetch_assoc($res);
 return $row['max']+1;
 }
}

Nun hat man mehrere Möglichkeiten mit dieser Klasse zu arbeiten. Man könnte die Klasse direkt benutzen und Objekte von ihr erzeugen. Die wesentlich elegantere Variante ist allerdings, dass man für jede Tabelle in der Datenbank eine eigene Klasse erstellt, welche dann von der vorgestellten Klasse Data ableitet. Dadurch ergiben sich mehrere Vorteile.

  1. Man kann problemlos Methoden überschreiben, falls diese nicht auf das zu lösende Problem passen. Andere Klassen bleiben dadurch unberührt.
  2. Sinnvolle Kapselung – Die Grundfunktionalitäten bleiben in der Data-Klasse, während spezielle Methoden in der abgeleiteten Klasse implementiert werden.
  3. Bessere Übersicht und intuitives Handling, da jede Datenbanktabelle auch als Klasse in der Anwendung existiert.

Angenommen in der Datenbank existiert eine Tabelle namens “testTabelle” und den Spalten “id” (ID-Feld) und “name”, dann könnte eine solche Klasse wie folgt aussehen:

class BeispielKlasse extends Data {
 function __construct($id = null) {
 parent::__construct("testtabelle", "id");
	if (!is_null($this->id)) {
	 $this->load($id);
	}
 }
}
mysql datenbank vererbung (web-)entwicklung set get klasse php-objekt auto-increment datenbankzugriff datensatz
Schreibe einen Kommentar:
Themen:
datensatz datenbankzugriff auto-increment php-objekt klasse get set (web-)entwicklung vererbung datenbank mysql
Entweder einloggen... ...oder ohne Wartezeit registrieren
Benutzername
Passwort
Passwort wiederholen
E-Mail