dedlfix: PDO Klasse erweitern

Beitrag lesen

Tach!

Ich möchte eine Art Ersatzfunktion für bindParam erstellen die die Sache etwasübersichtlicher machen soll. Dazu habe ich die PDO Klasse erweitert:

Alternativer Vorschlag: Man kann die Parameter auch als Array dem execute() übergeben und spart sich so das Gebinde. Dass die dann alle als String übergeben werden, stört nicht weiter.

class ePDO extends PDO
{
	/**
	 * Secure PDO Prepare
	 *
	 * @param string $Query
	 */
	public function SQL($Query)
	{
		if(strpos($Query, 'WHERE') === false && strpos($Query, 'INSERT') === false)
		{
			die('ERROR: No WHERE clause defined.');
		}
		return $this->prepare($Query);
	}

	/**
	 * Binding numbers to same Postname
	 */
	public function Number($Name)
	{
		return ? bindParam(':'. $Name, $_POST[$Name], PDO::PARAM_INT);
	}
}

Nur ich weiß nicht, wie ich das mit dem bindParam machen soll. Der Einfachheit halber, habe ich das erstmal auf public gesetzt.

Das nützt nur nichts, weil das prepare() ein Objekt der Klasse PDOStatement zurückgibt, dein Bind-Ersatz jedoch in ePDO steht. Der müsste in PDOStatement angesiedelt werden. Dummerweise kann man aber die bestehende Klasse nicht erweitern. Eine neue erstellen, die von PDOStatement erbt und dein Bindung enthält, ist zwar möglich, aber das prepare() stört sich daran nicht und gibt weiterhin PDOStatement zurück. Nun könnte man aufwendig mit dem Decorator-Pattern das PDOStatement in eine neue Klasse einbetten und am Ende von ePDO::SQL() das PDOStatement dekorieren und zurückgeben. Aber das kann man sich sparen, wenn man im PHP-Handbuch das PDO-Attribut PDO::ATTR_STATEMENT_CLASS entdeckt hat. Damit kannst du also eine abgeleitete Klasse von PDOStatement mit deinen Bind-Methoden erweitern und dem PDO verklickern, dass es diese nehmen soll.

Um nun ein Fluent Interface oder Method Chaining zu erreichen, muss dein Bind-Ersatz nicht das Ergebnis von bindParam() zurückgeben, denn das ist nur ein Boolean. Stattdessen sollte das innerhalb der Ersatzmethode ausgewertet werden und im Fehlerfall eine Exception werfen. Im Gutfall muss $this zurückgegeben werden, also ein Verweis auf sich selbst, so dass man da weitere Methoden der Klasse hintendrangehängt aufrufen kann.

Und auch execute() darf nicht das Ende der Fahnenstange sein, weil du die Instanz auch noch brauchst, um die Ergebnismenge abzurufen. Mindestens das execute() muss also so überschrieben werden, dass es ebenfalls $this zurückgibt (oder eine Exception wirft).

dedlfix.