Meine etwas überarbeitete MySQLi Klasse
Aber viele Erweiterungen sind noch experimentell und kaum getestet. Auch bezüglich Geschwindigkeit habe ich noch gar keine Tests gemacht.
Kritik gerne
<?php
// Klasse instantiieren und mit DB verbinden
$db = new mysqli_class('localhost', 'benutzer', 'passwort', 'tabelle';
// Klasse definieren
class mysqli_class
{
// =========================================================================
// ATTRIBUTE DEKLARIEREN
// =========================================================================
private $link = NULL; // von mysqli_connect
private $result = NULL; // von mysqli_query
//private $query = NULL;
// =========================================================================
// KONSTRUKTOR
// =========================================================================
public function __construct($host, $benutzer, $pw, $db)
{
// MySQLi Report für lokale Anwendungen
if ($_SERVER['HTTP_HOST'] == 'localhost' {
mysqli_report(MYSQLI_REPORT_ERROR);
// nicht MYSQLI_REPORT_ALL, sonst: No index used in query/prepared statement
// mysqli_report(MYSQLI_REPORT_ALL);
}
// Mit Datenbank verbinden
$this->connect($host, $benutzer, $pw, $db);
return TRUE;
}
// =========================================================================
// MYSQLI VERBINDUNG HERSTELLEN
// =========================================================================
public function connect($host, $benutzer, $pw, $db)
{
$this->link = mysqli_connect($host, $benutzer, $pw, $db) or $this->fehler();
return TRUE;
}
// =========================================================================
// DESTRUKTOR: MYSQL VERBINDUNG SCHLIESSEN
// =========================================================================
// public! Sonst kann sie bei unset() nicht aufgerufen werden
public function __destruct()
{
if (is_object($this->link)) {
mysqli_close($this->link);
}
if (is_object($this->result)) {
$this->free_result($this->result);
}
// Immer ausschalten, wird ansonsten für ALLE MySQLi Anwendungen verwendet!
// http://ch2.php.net/manual/de/function.mysqli-report.php#58489
mysqli_report(MYSQLI_REPORT_OFF);
return TRUE;
}
// =========================================================================
// MYSQL ABFRAGE DURCHFUEHREN
// =========================================================================
public function query($query, $a_parameter = FALSE)
{
if (is_object($this->link)) {
// mysqli_real_escape_string() fuer alle zusaetzlichen Parameter
if (is_array($a_parameter)) {
$query = vsprintf($query, array_map(array($this, 'escape_string', $a_parameter));
}
//echo '<p>' . $query . '</p>'; // nur zu Testzwecken
$this->result = mysqli_query($this->link, $query) or $this->fehler();
return $this->result;
}
return FALSE;
}
// =========================================================================
// WERTE AUS DATENBANK AUSLESEN
// =========================================================================
public function fetch($result = FALSE)
{
return mysqli_fetch_assoc($this->get_result($result));
}
public function fetch_extract($result = FALSE, $prefix = 'row_'
{
$row = $this->fetch($result);
if (!$row or !is_array($row)) {
return FALSE;
}
foreach ($row as $key => $var) {
$GLOBALS[$prefix . $key] = $var;
}
return TRUE;
}
// -------------------------------------------------------------------------
// Gibt die erste (oder einzige) Zeile als assoziatives Array zurueck
// -------------------------------------------------------------------------
public function fetch_single_row($result = FALSE)
{
$result = $this->get_result($result);
// MUSS NOCH GETESTET WERDEN!!
if ($this->num_rows($result) > 1) {
mysqli_data_seek($result, 0);
}
return mysqli_fetch_array($result);
}
public function num_rows($result = FALSE)
{
return mysqli_num_rows($this->get_result($result));
}
// -------------------------------------------------------------------------
// Gibt einen einzelnen Wert zurueck
// -------------------------------------------------------------------------
public function fetch_value($result = FALSE)
{
$result = $this->get_result($result);
return false;
}
// =========================================================================
// GIBT EIGENES ODER VORHANDENES RESULT ZURÜCK
// =========================================================================
private function get_result($result = FALSE)
{
if (!$result or !is_object($result)) {
return $this->result;
}
if (is_string($result)) {
// Kann auch als query benutzt werden, z.B.
// echo $db->num_rows('SELECT ... FROM ...';
$this->query($result);
return $this->result;
}
return $result;
}
// =========================================================================
// KLEINE METHODEN
// =========================================================================
// =========================================================================
// ANDERE DATENBANK AUSWAEHLEN
// =========================================================================
public function select_db($db)
{
return mysqli_select_db($this->link, $db) or $this->fehler();
}
// =========================================================================
// ABFRAGE PARAMETER ESCAPEN
// =========================================================================
private function escape_string($var)
{
return mysqli_real_escape_string($this->link, $var);
}
// =========================================================================
// FEHLERMELDUNGEN ANZEIGEN LASSEN
// =========================================================================
private function fehler()
{
$meldung = '<p>--<br /><strong>Es ist ein Datenbank Fehler aufgetreten!</strong>';
if ($_SERVER['HTTP_HOST'] == 'localhost' {
$meldung .= '<br />' . mysqli_error($this->link);
}
$meldung .= '<br />--</p>';
die($meldung);
}
// =========================================================================
// SPEICHER FREIGEBEN
// =========================================================================
public function free_result($obj)
{
mysqli_free_result($obj);
return true;
}
}
/*
================================================================================
VERBESSERUNGSVORSCHLÄGE
================================================================================
2) In der Fehler Methode lieber nur einen String zurückgeben. Das Programm sollte entscheiden, was mit dem Fehler passiert (also die(..) oder eine andere Fehlerbehandlung). Hier sollte auch kein HTML Code sondern nur die Meldung zurückgegeben werden.
## FERTIG ##
1) Ich würde einen Konstruktor definiere, der dann intern connect aufruft.
3) Der destructor sollte free_result benutzen
5) Die Query Method nimmt beliebig viele Parameter entgegen, das ist unübersichtlich. Besser wäre es die zusätzlichen Parameter als Array zu übergeben, der ansonsten leer bleibt. Es ist dann viel leichter zu verstehen
4) Die Query Methode liefert ein Objekt zurück, dass von dem Programm wieder an die Klasse übergeben werden muss, beispielsweise bei fetch_assoc. Schöner wäre es wenn der User diesen Rückgabewert nicht selbst verwalten müsste. Entweder könntest du ihn in einem Klassenattribut speichern (dann kann die Klasse natürlich immer nur ein Query) oder du kapselst den Rückgabewert wieder in einem Objekt, das dann die dazugehörigen Zugriffsfunktionen hat (fetch_assoc usw)
================================================================================
VERAENDERUNG
================================================================================
* $query = vsprintf($query, array_map(array(__CLASS__, 'escape_string', $a_parameter));
in
$query = vsprintf($query, array_map(array($this, 'escape_string', $a_parameter));
geaendert, ansonsten Strict Error (PHP 5.1.2).
*/
?>
Wie man sieht das ist das ganze noch etwas Gettho
Vieles ist noch nicht (so) eingebaut, wie ich das gerne hätte und wie gesagt, vieles ist noch
experimentell.
Vorschläge?