Rachus: MySQL Loginsystem

Beitrag lesen

Hallo,

mein Kopf qualmt schon wieder!

Nein, nicht Verbindung_en_, nur eine.

Damit verdeutlichst du mir implizit, dass meine Klasse so ähnlich sein sollte wie MySQLi, nur dass sie mehrere Verbindungen verwaltet. Da ich aber aufgrund deines restlichen Textes das nicht glauben kann, denke ich, dass ich da etwa zu weit hineininterpretiert habe.

Jein. Sieh die Einfachheit meiner Klasse. Der Mehrwert liegt darin, dass kein Connect mit Test, kein Kodierungsaushandeln, nicht zwangsläufig ein Quoten und Zusammenbauen eines Statements stattfinden muss. Einfach nur (ein einmaliges Initialisieren am Scriptanfang und) ein query()-Aufruf in einem try-catch-Block. Der Verwender kann sich ganz auf seine Geschäftslogik konzentrieren.

Hieße das nicht eher, dass die Initiation bereits in einem try-catch-Block sein muss, damit man die Exception, die bei Fehlschlag des Verbindungsaufbaus geworfen wird, abfängt? Wozu benötige ich denn den try-catch-Block um query() bzw. wann wird da eine Ausnahme ausgelöst?

Ja, es ist sinnvoll, mehrere Verbindungen haben zu können, aber wann braucht man das schon? Selten. Deswegen kann ich hier auch den Aufwand aus Verwendersicht so gering wie möglich halten. Selbst das Instantiieren und Rumschleppen eines DB-Objekts spar ich mir durch den statischen Aufruf.

Sollte ich mal das Factory-Pattern außer Acht lassen, sagst du mir somit, dass ich das ganze statisch umsetzen soll. Ich sehe jetzt auch die Vorteile, die das bringen würde. Aber wie läuft es da wieder mit der Fehlerbehandlung? Bei einem erzeugten Objekt, weiß ich, dass es initialisiert wurde, bei der statischen Umsetzung kann es passieren, dass ein "Query()" vor der Initialisierung aufgerufen wird. Da würde ich dann eine zusätzliche if-Abfrage benötigen. Zwar gebe ich zu, dass das kein Problem ist, aber trotzdem meine ich, dass das irgendwie "schlampig" zu sein oder gar der OOP widerspricht. (Eine Klasse zu haben, von der man keine [sinnvollen] Objekte instanzieren kann.)
Dennoch könnte ich mich zu so einem Konstrukt durchringen.

Die Quote()-Methode braucht es auch nur selten, denn, erwähnt hatte ich es noch nicht, aber die Query()-Methode nimmt das Statement mit Platzhaltern entgegen sowie ein Array mit den Werten und baut sich selbst ein ordentliches, sicheres Statement selbst zurecht. Ob es dazu Prepared Statements oder sprintf() nimmt, steht auf einem anderen Blatt.

Also sähe dann ein Aufruf etwa so aus:
DB::query('SELECT x.foo, y.bar FROM x, y WHERE x.name=%s AND y.name=%s', array($_POST['name'], $_POST['name']));
(da interessiert mich auch, ob das SQL so richtig wäre)
Das ist eigentlich ein ganz gute Idee. Das Quotieren würde allerdings dann immernoch für die Identifier nötig werden. Außerdem könnte ich dann nicht wissen, ob ein %s ein Identifier oder ein String/eine Zahl/etc. ist.
Sonst könnte ich dafür ja sprintf() verwenden.

Das ist dann wirklich nur mehr oder weniger ein Wrapper. Wenn du das so machst, musst du immer ein DB-Objekt herumtragen. Oder du nimmst das Factory-Pattern, um dir bei tatsächlichem Bedarf eine Instanz zu holen. Die kannst du nach getaner Arbeit fallen lassen, weil sie sich der Nächste auch wieder über die Factory holt. [...]

Das würde doch eigentlich auch nur bei mehreren Verbindungen Sinn machen. Weil für jeweils eine Verbindung müsste ich dann nicht extra eine Factory schreiben. Außerdem sehe ich gerade wieder keinen Unterschied zwischen:

DB::InitConnection('foo', Parameter_der_ersten_Verbindung);  
$db=DB::GetConnection('foo');

und
$db=new DB(Parameter_der_ersten_Verbindung);
Vom Sinn her ist das für mich fast das gleiche.

Der Mehrwert für den Verwender muss mindestens den Aufwand der Erstellung übersteigen, sonst wird das Ganze ineffizient.

Dann war das mehr als ineffizient!

In Java kann man, wenn ich mich recht erinnere, keine klassenlosen Funktionen erstellen. Also hast du mindestens eine Klasse, der du eine (private) statische Eigenschaft als Ablage verpassen kannst. Das selbe bei C#. C++ entzieht sich meiner Kenntnis.

Allerdings, ich erinnere mich, dass man in Java eine Klasse braucht. C# kenne ich nicht weiter, aber ich wage mich zu erinnern, dass es (zumindest in C) eine Möglichkeit gab, statische Funktionsvariablen zu erzeugen. Das sind so Features, die ich nie genutzt habe und daher vergaß.

Einen schönen Abend

Rachus