funktionalität in Konstruktoren ähnlicher Klassen besser machen???
bearbeitet von 1unitedpower> Kann man generalisierende _"Hilfsmethode"_ bereit stellen die den Code etwas organisieter machen? Ich komme da einfach nicht weiter, wie ich den Code besser organisieren kann 😕. Kann man überhaupt noch etwas dran drehen oder ist das Ende, so ziehmlich erreicht?
Ein paar Ideen:
- Verlagere die Erzeugung des SQL-Strings vom Konstruktor in eine eigene Methode `toSql`.
- Verändere bei der String-Erzeugung nicht den iternen Zustand des Objekts. Setze den String lokal zusammen und lass ihn von der Methode zurückgeben.
- Entferne den `$negation`-Parameter und schreibe dir eine eigene Klasse `Not` für die Negierung
- Schreibe ein Interface `BooleanValue`. Die Klassen `Between` und `Not` sollten dieses Interface implementieren. `Not` bekommt im Konstruktor ebenfalls ein Objekt vom `BooleanValue` übergeben.
- Entferne den `$safe`-Operator. Ich würde stattdessen ein Interface `NumercialValue` schreiben und dan zwei Klassen `NumberLiteral` und `NumberPlaceholder`, die beide das Interface implementieren. `NumberLiteral` konvertiert eine PHP Wert vom Typ `number` in einen SQL-String. `NumberPlaceholder` erzeugt einfach ein Fragezeichen.
- Entferne die Klasse `ColumnInterface` und schreibe dir eine Klasse `NumberColumn`, die ebenfalls `NumericalInterface` implementiert.
Du kannst den Code von `Between` dann auf das folgende reduzieren:
~~~php
final class Between implements BooleanValue {
private NumericalValue $value;
private NumericalValue $min;
private NumericalValue $max;
public function __construct(NumericalValue $value, NumericalValue $min, NumericalValue $max)
{
$this->value = $value;
$this->min = $min;
$this->max = $max;
}
public function toSql() : string
{
$value = $this->value->toSql();
$min = $this->min->toSql();
$max = $this->max->toSql();
return " $value BETWEEN $min AND $max ";
}
}
~~~
Also nochmal Zusammengefasst, Interfaces:
- NumericalValue
- BooleanValue
Und Klassen:
- NumberLiteral implements NumericalValue
- NumberPlaceholder implements NumericalValue
- NumberColumn implements NumericalValue
- BoolLiteral implements BooleanValue
- BoolPlaceholder implements BooleanValue
- BoolBetween implements BooleanValue
- BoolNot implements BooleanValue
Wenn du das für andere MySQL-Datentypen so fortsetzt, erhälst du eine eine Sammmlung vieler sehr primitiver Klassen, die alle mehr oder weniger den Aufbau wie `Between` oben haben. Ein Konstruktor, der nur die Felder initialisiert und eine Methode `toSql`, die den dazu passenden SQL-String erzeugt. Solche Klassen lassen sich sehr einfach testen, weil sie keinen internen veränderlichen Zustand haben. Außerdem erleichtert eine so fein-granulare Architektur die Verwendung der Library, weil die Typen eine präzise Anleitung dafür liefern, was wie wo verwendet werden darf. Typfehler können auch schon zur Entwicklungszeit angezeigt werden, das erleichtert das Debugging.
Der Nachteil ist natürlich, dass das sehr viel Schreibarbeit ist.