PHP Von einem Objekt auf das erzeugende zugreifen?

gaunt

Lt. Commander
Registriert
Aug. 2007
Beiträge
2.016
Hi
ich muss mal wieder eine doofe Frage stellen.
Ich habe ein Objekt, welches wiederrum dynamisch weitere Objekte erzeugt. Wird ein bestimmtes erzeugt, soll dieses ein Attribut im Elternobjekt ansprechen. Geht das irgendwie?

Ich kann natürlich Workarounds bauen. Z.B. die abgeprüfte Bedingung in die Elternklasse schreiben, oder eben eine Refferenz auf das übergeordnete Objekt an den Konstruktor übergeben. Will ich aber nicht.
Denn das untergeordnete Objekt prüft auf eine Bedingung die nur seeehr selten erfüllt ist. Und da ich auf performance achten muss soll die Prüfung auch nur dann stattfinden wenn sie benötigt wird. Und eben nicht immer.

Worum gehts?
Ein simples Admin Login. Aber das wird im Alltag nur extrem selten benötigt. Deswegen soll der Controller des Admin Objekts im Konstruktor prüfen ob eine Admin Session besteht. Kein Ding. Danach wird aber die Action aufgerufen welche aus der URL generiert wird. Besteht keine Admin Session, muss die Action im FrontController vom AdminController von einer beliebigen Admin Seite auf das Login umgebogen werden.
Ich könnte natürlich die Action in eine globale Variable statt in ein Attribut schreiben, würde ich aber ungern machen.

Vielleicht stehe ich ja einfach auf dem Schlauch.
Hat einer nen Tipp?
 
Eine kleine if-Abfrage kostet quasi keine Zeit... if(!isset($_SESSION['isAdmin'])) { //redirect zum Login}

Optimiere niemals an der Performance herum, bevor du ein Performance-Problem hast. Die Arbeitzeit, die du in nutzlose Optimierungen steckst, kostet am Ende mehr als ein kleines Hardware-Upgrade, das die Optimierung für lange Zeit obsolet werden lässt.
 
Ich versteh überhaupt nicht wovon du redest.

Ich habe ein Objekt, welches wiederrum dynamisch weitere Objekte erzeugt. Wird ein bestimmtes erzeugt, soll dieses ein Attribut im Elternobjekt ansprechen. Geht das irgendwie?

Code:
class A{
protected $var;
}

class B extends A{
function __construct() {
       print self::$var; //oder parent::
   }}

Meinst du sowas?
 
Code:
class Parent {
    protected $attribute;
}

class Child extends Parent{
     public function generateData($params) {
         if($params == $condition) {
             parent::$attribute = "something";
         }
     }
}

Meinst du sowas?
Normalerweise kommst du über Parent bzw $this auf das entsprechende Attribut, falls du erbst.
 
Naja, bei uns haben schon des öfteren nicht optimierte Anwendungen zu großen Problemen geführt. Von daher muss ich da schon en bissel drauf achten. Das ist auch der Grund weshalb ich erstmal kein fertiges Framework genommen hab sondern mir nur das nötigste für ein eigenes kleines MVC gebaut habe.

Ein if auf eine Admin Session geht natürlich. Aber ich müsste ja nochmehr prüfen. Mindestens ob überhaupt eine Seite aufgerufen wird welche ein Login erfordert. Denn der normale Endkundenbereich kennt keine User.
Könnte ich das alles im Konstruktor vom Admin Controller lassen dann hätte ich in der restlichen Anwendung keinerlei Benutzersteuerung und bräuchte nichtmal Sessions. Gleichzitig wäre sicher gestellt das definitiv nie eine Admin Seite ohne Login aufgerufen wird.

Ich hab die Action jetzt erstmal in eine globale Variable geschrieben, bzw. nutze einfach die globale aus der die Info kommt. Geht erstmal, gefällt mir aber nicht.

@Blackstorm
PHP. Siehe Titel;-)
Ist aber egal. Ist in PHP und Java gleich. Egal ob das Attribut Private, Protected oder Public ist. Ohne Refferenz auf das Obekt ists wurst wie das Attribut geschützt ist.

EDIT:
Sorry das ich von Eltern uns so geredet hab.
!!!ES GEHT NICHT UM VERERBUNG!!!
Nur darum eine Refferenz auf das Objekt zu bekommen, welches ein anderes erzeugte.
 
Mir fällt es gerade erstmal schwer schlau aus dem zu werden, was du schreibst. Ein kleines, konkretes Codebeispiel könnte ein bisschen Licht ins Dunkel bringen.

Wird ein bestimmtes erzeugt, soll dieses ein Attribut im Elternobjekt ansprechen. Geht das irgendwie?
Meine beiden Ideen: Referenz mitgeben und per Getter/Setter auf das Attribut des erzeugenden Objekts zugreifen. Oder aber, wie schon ein Beispiel zeigt, die Klasse des zu erzeugenden Objekts von der Klasse des erzeugenden Objekts erben lassen. Wahrscheinlich muss das ominöse Attribut dann aber ein Klassenattribut sein (also statisch), genaueres geht aus deinem Text nicht hervor.
 
@Fortatus
Dank dir! Genau darum gehts!
Geht also nicht:-( Habs schon vermutet...

1. Aggregate the parent object via Injection
Mag ich nicht. Denn dann müsste ich das Parent an alle möglichen Objekte geben die das garnicht brauchen.

2. Use Composition
Erzeugt eine neue Instanz. Geht also nicht.

3. Use Inheritance
Vererbung macht hier keinen Sinn. Hier gibts nix zu vererben. Würde technisch gehen, ist aber Sinnlos.

4. Use global keyword
Das ist dann wohl der saure Apfel. Ich hasse globale Variablen. Spätestens wenn Projekte etwas größer werden verliert man den überblick wo überall die scheiß globals modifiziert werden!!!
So hab ichs aber im Moment auch gemacht. Naja, wenn snicht anders geht:-(
 
Kennst du das MVC Pattern?
Du schreibst einen Front Controller der abhängig von weitern Umständen den passenden Controller erzeugt. Und Controller gibt es viele.
Wenn ich den FC möglichst schank halten will (weil der bei jedem Request aufgerufen wird!) kann ich hier nicht tausend prüfungen vornehmen. Ich müsste die Refferenz also jedem Controller übergeben.
Das Login braucht aber nur der Admin Controller.
 
Das klingt für mich eher nach MVC + Factory Pattern für Daten bzw. Objekte
 
@SymA
Factory passt auch nicht wirklich. Evtl. (weiß aber nicht ob das mit PHP überhaupt geht) könnte man ein Observer Pattern verwenden. Wäre aber auch wieder mit Overhead verbunden.
 
Wenn du keinen Overhead willst, dann müßtest du aber auch auf OO verzichten... und wahrscheinlich auch gleich auf PHP und stattdessen C einsetzen :P

Kennst du schon https://github.com/facebook/hhvm? Vielleicht ist das ja eine Option in Hinsicht auf Performance.
 
Facebook ist einer der wenigen Punkte, wo die Leistung von PHP mit aktivem OpCode-Cache nicht ausreichend schnell ist... Wenn man nicht gerade mod_suphp oder CGI verwendet oder allgemein keinen OpCode-Cache laufen hat, sind 90% der Performance-Sorgen eh gekoppelt an die Datenbank-Verbindung, nicht an den PHP-Code.

Wie ich schon sagte: Bevor du ewig dran rum bastelst, wirf lieber mehr Hardware auf das Problem. Angenommen, du bringst jetzt 6 Stunden mit dem Problem zu... dafür hätte dein Boss schon wieder einen kompletten kleinen Server für 1 Jahr aus der Hetzner Serverbörse besorgen können, der das Problem durch meeeeehr Power löst.
 
Naja, ich arbeite im Moment für eines der größten Portale in D. Die Elemente die da genutzt werden werden schon arg gefoltert.
Hinter den Scripten stecken schon ein paar Server (15-20 Frontends und keine Ahnung wieviele DB's). Aber an der Architektur schrauben die Jungs nur ungern rumm. Und ein neuer Server? LOL bis der da ist bin ich in Rente;-) Aber ohne scheiß. Auf die LB/PHP/Frontend/DB Konfig hab ich leider keinen Einfluss. Ich muss mit dem leben was da ist.

Naja, auf OO verzichten will ich auch nicht;-)
Ich will nur ein bisschen drauf achten nix überflüssiges verwenden. Ist ja auch grundsätzlich nicht verkehrt, und die Lösung mit der Globalen ist nicht schön, funktioniert aber. Hab an der Stelle wo sie verwendet wird einfach dazukommentiert, dass sie an ggf. unerwarteter Stelle modifiziert wird. Für den Fall das ich vergesse was ich gemacht hab oder mal jemand anderes drann mus. Denke das ist OK.

sind 90% der Performance-Sorgen eh gekoppelt an die Datenbank-Verbindung, nicht an den PHP-Code.
Damit dürftest du recht haben.

HHVM läuft nicht mit Apache und selbst wenn. Auf den Wunsch neue Plugins (oder überhaupt irgendetwas neues) einzusetzen steht hier die standrechtliche Steinigung mit ausgedienten Blades;-)
 
Dann wende dich doch einfach zumindest vom MVC-Pattern ab. MVC wird ganz schnell zu einem aufgeblähtem Monstrum. Ja, MVC erzeugt erweiterbaren und wartbaren Code, aber das kann man anderweitig auch.

Hast du mal daran gedacht, den Kram gar nicht selbst zu schreiben, sondern einfach ein schnelles CMS auf das Problem zu werfen? Contao ist z.B. seit Version 3.0 wirklich pervers schnell geworden, und da hast du direkt auch ne sehr stabile Lösung für deinen Admin-Login.
 
Naja, ich hab ja kein fertiges Framework genommen sondern die notwendigen Komponenten schnell selbst geschrieben. Ist ja nicht so viel. Und was da ist brauche ich auch. Z.B. für sprechende URLs wegen Seo. Ansonsten halt drei Klassen pro Funktionsblock. Halb so wild. Außerdem kann ich so den Frontendlern einfach erklären was sie machen können.

Contao werde ich mir mal ansehen. Für das Thema gerade ist ein CMS aber übertrieben. Außerdem muss ich dann immer wieder Updates einspielen da es zu Standardsoftware immer wieder Exploits gibts die irgendwelche Scripter halt auch testen wollen. Und spätestens wenn größere Versionssprünge kommen hat man fast immer Stress. Zudem ist das aktuelle Tool schon weitestgehend fertig. Werde Contao aber mal im Hinterkopf behalten.
 
Ich verwende Contao jetzt schon seit 2.5 oder 2.6, damals hieß es noch TypoLight... und die bisher aufgetauchten Frontend-Sicherheitslücken konnte man an einer Hand abzählen, nachdem man 50 Jahre im Sägewerk gearbeitet hat. Im Backend tauchten so grob alle 1-2 Jahre mal kleine Lücken auf, durch die jemand unter teilweise arg konstruierten Situationen seine Rechte ausweiten konnte.
Der aktuelle Zweig, 3.2, ist als LTS deklariert. Das gibt dann zwar keinen so endlosen Support wie z.B. Typo3 LTS oder gar Betriebssystem-LTS, aber 18 Monate sind mehr als realistisch.

Wie gesagt, wenns um schlankes selbst-schreiben geht, würde ich gar kein MVC-Pattern verwenden. Da verzettelt man sich irgendwann in den Controllern, so wie du gerade.
Aber insgesamt kann ich mir echt nicht vorstellen, dass ein paar gut gewählte If-Abfragen tatsächlich einen Einfluss auf die Leistung haben sollten, egal wie viele Besucher ihr habt. In dem Moment, wo die erste geprüfte Variable ist, ob die Seite überhaupt einen Login erfordert, endet jede weitere Prüfung so oder so. Sinngemäß
PHP:
if($this->Page->authRequired() && (!$this->User->isAdmin() && !$this->User->hasPermission($this->Page->pageId)))
{
// Zugang verweigert!
}
Das kostet im Idealfall (freie Seite) einen Vergleich, wenn er Admin ist 2 und wenn er zwar kein Admin aber ein authorisierter User ist 3. Da dauert der Verbindungsaufbau zur Datenbank länger...
 
Zurück
Oben