Ankündigung

Einklappen
Keine Ankündigung bisher.

Architektur einer Verwaltungssoftware

Einklappen

Neue Werbung 2019

Einklappen
X
  • Filter
  • Zeit
  • Anzeigen
Alles löschen
neue Beiträge

  • Architektur einer Verwaltungssoftware

    Hallo,

    zur Zeit überarbeite ich eine Verwaltungssoftware für einen Verein auf PHP und MySQL Basis. Hierbei möchte ich auch eine neue Grundstruktur einführen.

    Alle Module werden weitestgehend objekorientiert aufgebaut und in einem seperaten Ordner mit allen notwendigen zugehörigen Dateien abelegt. Zudem gibt es in der Datenbank eine Tabelle "modul" der installierten Module mit Titel, Beschreibung, Einstellungen, Optionen usw...

    Mit einer speziellen PHP-Klasse "modul" wird nun das entsprechende Modul initialisiert.

    PHP-Code:
      $modul = new modul('address'); 
    In dieser Klasse wird nun eine Datenbankabfrage durchgeführt und die erforderlichen Daten aus der Tabelle "modul" ausgelesen. Schlägt dieses nicht fehl, soll dynamisch das entsprechende Modul nachgeladen werden und normalerweise die Eigenschaften von "modul" erben.

    PHP-Code:
      $irgendeinname = new $modul->name(); 
    Wie kann hier sinnvoll eine Initialisierung der Kindklasse stattfinden? Was haltet ihr von dieser Idee oder habt ihr weitere Vorschläge?
    www.webdeveloperfactory.de - Der Blog und Ratgeber für Webentwickler mit zahlreichen Informationen


  • #2
    Also das was du da machst habe ich so noch nie gesehen, glaube nicht das dies wirklich richtig ist. Weil du bildest mit mit $address eine neue Instanz auf die Methode einer Instanz der Klasse modul, dass ist komisch.

    Jedenfalls hat das da 100% nichts mit Kindklasse und somit nichts mit Vererbung zu tun, dass ist schon mal sicher.

    Hast du den Code so ausprobiert und keine Fehlermeldungen erhalten? Kann ich mir kaum vorstellen.
    Aus dem Dynamo Lande kommen wir. Trinken immer reichlich kühles Bier. Und dann sind wir alle voll, die Stimmung ist so toll. Aus dem Dynamo Lande kommen wir.
    http://www.lit-web.de

    Kommentar


    • #3
      Ich mache das nun mal ausführlicher... Ich brauche eine Idee für die Einbindung sowie die Initialisierung der Kindklasse?

      PHP-Code:

        
      // datei1.php

        
      class modules {

          function 
      __construct($modul_name) {

            if(
      strlen($modul_name) > 1) {
              
      //datenbankabfrage
            
      }

          }

          function 
      funktion_zum_modulladen() {
            ???
          }

        }

        
      // datei2.php aus dem Modulordner

        
      class address extends modules {

          function 
      foo() {
            return 
      $content;
          }

        } 
      www.webdeveloperfactory.de - Der Blog und Ratgeber für Webentwickler mit zahlreichen Informationen

      Kommentar


      • #4
        Das Konzept an sich wird so schon funktionieren. Für mich stellt sich nur die Frage, in welchem Umfeld bzw. auf welcher Ebene sich ein Modul bei dir abspielen soll. Sind wir auf GUI-Ebene oder ist das "Modul" eine Business-Komponente? Diese Faktoren beinflussen die Erzeugung eines Moduls (hier sprechen wir entweder vom Abstract Factory- oder dem Builder-Pattern).

        Im Software-Design-Forum gab es dazu eine ausführliche Diskussion über Modularisierung und den dabei relevanten Problemstellungen. Nutze bitte die Board-Suche nach "Modul", da wirst du sicher einen Beitrag von mir finden.
        Viele Grüße,
        Dr.E.

        ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
        1. Think about software design before you start to write code!
        2. Discuss and review it together with experts!
        3. Choose good tools (-> Adventure PHP Framework (APF))!
        4. Write clean and reusable software only!
        ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

        Kommentar


        • #5
          Ich denke, dass dieses in Richtung Builder-Pattern geht...

          Die Klasse "address" ist ein eigenständiges Modul, ähnlich einer Typo3-Extension und verfügt in der Regel nicht über weitere Kindklassen. Initialisiert werden soll das Modul allerdings nur, wenn dieses über die Elternklasse "modules" erzeugt wird, da hierbei wichtige Informationen die während der gesamten Zeit des Objektes existieren sollen.

          Zur Verständnis: Bei dieser Vorgehensweise kann ich aber nicht innerhalb der Klasse "modules" über eine Methode die erforderliche Datei der Klasse inkludieren und diese in der Methode mit new $this->modul_name; initialiseren oder wie sollte dieses gesehen?

          PHP-Code:

            
          class modules {

              function 
          __construct($modul_name) {

                if(
          strlen($modul_name) > 1) {
                  
          //datenbankabfrage
                
          }

              }

              function 
          funktion_zum_modulladen() {
                
                include(
          'address.php');
                
          $mod = new $this->modul_name();

              }

            } 
          www.webdeveloperfactory.de - Der Blog und Ratgeber für Webentwickler mit zahlreichen Informationen

          Kommentar


          • #6
            Und welchen Mehrwert bringt deine "modules" Klasse jetzt bzw. was erwartest du von ihr? Auf includes/requires solltest du ganz verzichten, dafuer gibt es das Autoloading.
            "Mein Name ist Lohse, ich kaufe hier ein."

            Kommentar


            • #7
              Diese Klasse verhindert, dass ich in für jedes einzelne Modul die Datenbank für Informationen abfragen muss, die Rechte erstellen, Menü laden usw... Dieses möchte ich nur einmal machen und nicht in jedem Modul, da es eigentlich immer das Gleiche ist...

              Geht das überhaupt so? Ein Modul innerhalb eines Modul initialisieren welches per extends von eigentlichen Modul abhängig ist?
              www.webdeveloperfactory.de - Der Blog und Ratgeber für Webentwickler mit zahlreichen Informationen

              Kommentar


              • #8
                Ja das geht, warum auch nicht. Ich wuerde das Modul aber eher ein Interface implementieren lassen (oder alternativ eine abstrakte Modulklasse). Dann kannst du die noetigen Informationen (Datenbankverbindung etc.) "injizieren". Erscheint mir sinniger. Hab aber ehrlich gesagt keine Erfahrung mit Modul/Plugin-Erstellung.
                "Mein Name ist Lohse, ich kaufe hier ein."

                Kommentar


                • #9
                  Hallo Mano,

                  ich kann Chriz in der Tat nur zustimmen. Definiere erst mal WAS GENAU ein Modul für dich ist. Deine Beschreibung ist einfach zu wirr und sagt trotz der Verwendung von "builder pattern" quasi nichts aus.
                  Viele Grüße,
                  Dr.E.

                  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
                  1. Think about software design before you start to write code!
                  2. Discuss and review it together with experts!
                  3. Choose good tools (-> Adventure PHP Framework (APF))!
                  4. Write clean and reusable software only!
                  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

                  Kommentar


                  • #10
                    Ich versuch das mal näher zu erläutern:

                    Das Modul "modules" bei mir folgende Funktionalitäten für das geladene Modul:
                    * Informationen zum Modul
                    * Rechte
                    * Menü
                    * Besonderheiten

                    Beispielsweise umfasst das Modul "address" bei mir folgende Funktionalitäten:
                    * Verarbeitung
                    * Ausgabe
                    * Beinhaltet alle Funktionalitäten (Export, Import, usw...) für die Adressenverwaltung

                    Wie gesagt das Modul welches über die Klasse modules geladen werden soll ist einer Extension für Typo3, Mangento sehr ähnlich...
                    www.webdeveloperfactory.de - Der Blog und Ratgeber für Webentwickler mit zahlreichen Informationen

                    Kommentar


                    • #11
                      Hallo Mano,

                      Wie gesagt das Modul welches über die Klasse modules geladen werden soll ist einer Extension für Typo3, Mangento sehr ähnlich...
                      Und das bedeutet, dass dein Konzept automatisch gut ist? Magento ist hinsichtlich seiner Architektur sicher kein Vorzeige-Projekt, TYPO3 ist an vielen Stellen überfrachtet.

                      Das Modul "modules" bei mir folgende Funktionalitäten für das geladene Modul:
                      * Informationen zum Modul
                      * Rechte
                      * Menü
                      * Besonderheiten
                      Das ist schon mal ein Anfang, aber die Bedeutung ist dir offensichtlich noch nicht klar. "Menü" bedeutet z.B., dass das Modul eine GUI-Ausgabe erzeugt, "Rechte" ist mehr eine Sache im Hintergrund (Business-Schicht) und "Besonderheiten" erschließt sich mir nicht.

                      Ist ein Modul nun eine "Komponente", die eine Ausgabe generiert und mit UI-Komponenten interagiert oder nur eine klassische API innerhalb deiner Applikation, die wiederum Kern-Komponenten deiner Software nutzt? Oder beides? Wenn beides, dann muss es aber innerhalb deiner modules-Klasse die entsprechenden Factory-Methoden zur Erzeugung der Sub-Komponenten deines Moduls geben, die sich für die entsprechenden Bereiche verantwortlich zeichnen.

                      Beispielsweise umfasst das Modul "address" bei mir folgende Funktionalitäten:
                      * Verarbeitung
                      * Ausgabe
                      * Beinhaltet alle Funktionalitäten (Export, Import, usw...) für die Adressenverwaltung
                      Dieser Absatz klingt mir mehr nach Frontend-Funktionalität - abgesehen von der Export/Import-Geschichte. Beschränken wir uns also auf die GUI-Funktionalitäten (denn "alle" Funktionalitäten kann ich nicht zu einem konkreten Bereich zuordnen):

                      Hier ist es für die Komponente, die als Modul eingebettet wird wichtig das unter http://www.php.de/software-design/52...tml#post404611 beschriebene vom Umfeld zu kennen. Anschließend muss ein Mechanismus geschaffen werden, der die Einbettung der Ergebnisse an den relevanten Stellen schafft. Wenn ein Modul auch ein Menü erzeugen soll, kann das auf Basis einer erweiterten GUI-Modularisierung passieren (=das Modul kann unterschiedliche Views belegen; z.B. eines für sein Menü, eines für den Content, ...) oder das Menü wird implizit durch die Datenstruktur in der Datenbank vorgegeben und kann - sobald es adressiert ist - von der Rahmen-Anwendung ausgelesen und dargestellt werden.

                      Das sind meiner Ansicht nach die wichtigen Punkte zu denen mehr Prosa oder UML-Diagramme notwendig sind. Ob die Klasse nun "modules" oder "FooFactory" heißt, ist absolut zweitrangig.

                      Hier noch einige Links zum Thema:
                      Viele Grüße,
                      Dr.E.

                      ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
                      1. Think about software design before you start to write code!
                      2. Discuss and review it together with experts!
                      3. Choose good tools (-> Adventure PHP Framework (APF))!
                      4. Write clean and reusable software only!
                      ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

                      Kommentar


                      • #12
                        Und das bedeutet, dass dein Konzept automatisch gut ist? Magento ist hinsichtlich seiner Architektur sicher kein Vorzeige-Projekt, TYPO3 ist an vielen Stellen überfrachtet.
                        Darüber kann man streiten Ich habe bereits viele Deiner Beiträge gelesen und auch in anderen Foren ähnliche Themen zum grunsätzlichen Softwareaufbau gefunden. Es gibt ja leider keine Musterlösung, da dieses in der Regel durch den jeweiligen Anwendungsfall beeinflusst wird. Und da bekanntlich viele Wege nach Rom führen, schaut man sich natürlich zur Inspiration auf dem Markt um. Aus diesem Grund finde ich es wichtig, über das Forum hier weitere Ideen für mein Vorhaben zu sammeln und natürlich eure Meinungen hierzu einholen.

                        Das ist schon mal ein Anfang, aber die Bedeutung ist dir offensichtlich noch nicht klar. "Menü" bedeutet z.B., dass das Modul eine GUI-Ausgabe erzeugt, "Rechte" ist mehr eine Sache im Hintergrund (Business-Schicht) und "Besonderheiten" erschließt sich mir nicht.
                        Ja, da hast Du recht. Mein Beispielmodul "address" beinhaltet neben der HTML-Ausgabe auch die Verarbeitung über Formulare. Fast jede Aktion erhält hierbei in der Klasse "address" eine eigene Methode. Außerdem muss in jedem Modul so auch im Beispielmodul "address" eine Methode output() für die Rückgabe der HTML-Ausgabe enthalten sein.

                        Ich habe nochmal ein Beispiel hinzugefügt und bin über konstruktive Kritik dankbar, da einiges noch nicht so richtig geht wie ich mir da vorstelle:

                        PHP-Code:

                          
                        //class.modul.php
                          
                          
                        class modules {
                          
                            public 
                        $modul_title;
                            private 
                        $modul_obj;

                            function 
                        __construct($modul_name) {

                              if(
                        strlen($modul_name) > 1) {
                                
                        //datenbankabfrage
                              
                        }

                              
                        // Dieses könnte man auch über __autoload machen ;-)
                              
                        if(!file_exists(OPT_SERVER_PATH "modules/" $this->modul_name "/class.modul_" $this->modul_name ".php")) {
                                return 
                        false;
                              } else {
                                require_once(
                        OPT_SERVER_PATH "modules/" $this->modul_name "/class.modul_" $this->modul_name ".php");
                              }

                              if(!
                        class_exists($this->modul_nametrue)) {
                                return 
                        false;
                              }

                              
                        // ??
                              
                        $modul_obj = new $this->modul_name();
                              
                        $this->modul_obj $modul_obj;

                            }

                            public function 
                        setTitle($title) {
                              if(
                        $title != '') {
                                
                        $this->modul_title trim($title);
                              }
                            }
                            
                            public function 
                        getTitle() {

                              if(
                        $this->modul_title != '') {
                                return 
                        $this->modul_title;
                              }

                            }

                            
                            function 
                        getContent() {
                              return 
                        $this->modul_obj->output();
                            }

                          } 
                        PHP-Code:

                          
                        //class.address.php
                          
                          
                        class address extends modules {

                            function 
                        __construct($foo) {
                            
                              
                        // GEHT NICHT!
                              
                        parent::setTitle('test');
                            
                            }
                          
                            function 
                        foo() {
                              return 
                        $content;
                            }

                          } 
                        PHP-Code:

                        // index.php

                        $modul = new modules('address');

                        // hier wird komischerweise der Standardtitel aus der Datenbank ausgeben
                         
                        $modul->getTitle(); 
                        www.webdeveloperfactory.de - Der Blog und Ratgeber für Webentwickler mit zahlreichen Informationen

                        Kommentar


                        • #13
                          Da hast du aber einige Dellen im Code:
                          • public-Properties
                          • Konstruktoren die boolsche Werte zurückliefern (wollen)
                          • Konstanten die aus dem Nichts verwendet werden
                          • Validierungen die nichts bringen ($modules->setTitle('<ein Haufen Leerzeichen>') <- tricked)
                          • Datenbankabfragen im Konstruktor (wo kommt die DB-Verbindung her?)
                          • Objekterzeugung im Konstruktor
                          • require-Anweisung im Konstruktor
                          • $address->foo() erzeugt PHP-Notice
                          • ...


                          Fang doch erstmal damit an sauber zu programmieren (syntaktisch, logisch, konzeptionell) - danach kannst du dich dann an die Entwurfsmuster wagen.
                          "Mein Name ist Lohse, ich kaufe hier ein."

                          Kommentar


                          • #14
                            Hallo Mano,

                            Ja, da hast Du recht. Mein Beispielmodul "address" beinhaltet neben der HTML-Ausgabe auch die Verarbeitung über Formulare. Fast jede Aktion erhält hierbei in der Klasse "address" eine eigene Methode. Außerdem muss in jedem Modul so auch im Beispielmodul "address" eine Methode output() für die Rückgabe der HTML-Ausgabe enthalten sein.
                            Das geht genau in die konzeptionelle Uncle Bob-Richtung, die ich für einen Fehler halte. Wenn ein Modul in einer generischen GUI mehrere Views füllen können soll (Menü, Content), dann ist es auch notwendig, dass die Modul-Schnittstelle dieses berücksichtigt. Hierzu sind mehrere Dinge notwendig:

                            1. Modul-Definition für GUI-Elemente, die die möglichen Views mit einem entsprechenden Widget oder View-Template definiert.
                            2. Applikations-Rahmen, der ein Element eines Moduls auf Basis einer definierten Semantik einbindet und mit den Rahmenbedingungen ausstattet.
                            3. Saubere API des Software-Kerns, damit dieser von den Modulen zu deren Zweck genutzt werden kann.

                            Sofern das nicht gegeben ist, macht es keinen Sinn, über Module zu sprechen. Ein Modul im OO-Sinne ist IMHO nie eine Klasse die alles macht, sondern ein Interface, das entsprechend implementiert werden muss. Dieses Interface kann nun aus mehreren Bereichen oder Elemente bestehen.

                            Um den Gedanken weiter zu spinnen: wenn ein Modul nun ein Menü und einen Content-Bereich darstellen können soll, gebe ich dem Modul dazu die Möglichkeit, 3 Elemente zu implementieren:
                            • Front-Controller-Action um die (View-)Modell-Informationen für die einzelnenen Views aufzubauen.
                            • View-Template, dass das Menü darstellt.
                            • View-Template, dass den Content-Bereich darstellt.

                            Diese Elemente lassen sich in einer Datenbank-Struktur wie folgt abbilden (ich denke hier ein wenig in APF-Strukturen, da es am konkreten Beispiel einfacher ist):

                            Code:
                            +----+----------+-----------+-----------+---------------+------------------+
                            | id | key      | namespace | fc_action | menu_template | content_template |
                            +----+----------+-----------+-----------+---------------+------------------+
                            |  1 |    users | mods::one | OneAction |      menu_one |      content_one |
                            +----+----------+-----------+-----------+---------------+------------------+
                            |  2 | meetings | mods::two | TwoAction |      menu_two |      content_two |
                            +----+----------+-----------+-----------+---------------+------------------+
                            |  3 |     news | mods::tre | TreAction |    menu_three |    content_three |
                            +----+----------+-----------+-----------+---------------+------------------+
                            Nun könntest du an Hand des "key" erkennen, welches Modul zu laden und auszuführen ist. Konzeptionell könnte der Ablauf so sein:

                            1. Rahmen-Applikation starten.
                            2. FC-Action der Rahmen-Applikation ausführen und dabei URL nach Modul-Schlüssel durchsuchen.
                            3. FC-Action des aktiven Moduls ausführen.
                            4. View der Rahmen-Applikation aufbauen.
                            5. An den relevanten Stellen die View-Templates des Moduls an Hand der in 2. gefundenen Informationen einbinden.

                            Ein "Modul" hätte nun damit die Freiheit, verschiedene Ausgaben nach immer semantisch gleichen Konzepten zu erzeugen, würde aber einem sauberen OO-Design folgen, in dem jeder Bereich durch exakt ein Element repräsentiert wird, das seiner Aufgabe auch gerecht wird. Wichtig dabei ist jedoch, dass du ein Tool nutzt, dass dich hierbei unterstützt (mehrere Front-Controller-Actions, mehrere Views pro Applikation (HMVC?)).

                            Wenn du dich leichter tust, kann ich dir auch mal ein kleines Code-Beispiel schreiben, das das Konzept verdeutlicht. Ich denke auf Basis des APF sollte das nicht mehr wie 100 Zeilen effektiven Code ausmachen.
                            Viele Grüße,
                            Dr.E.

                            ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
                            1. Think about software design before you start to write code!
                            2. Discuss and review it together with experts!
                            3. Choose good tools (-> Adventure PHP Framework (APF))!
                            4. Write clean and reusable software only!
                            ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

                            Kommentar


                            • #15
                              Fang doch erstmal damit an sauber zu programmieren (syntaktisch, logisch, konzeptionell) - danach kannst du dich dann an die Entwurfsmuster wagen.
                              Sorry, aber war vorhin etwas eilig BTW: Wo ist eigentlich der WYSIWYG-Editor in diesem Forum geblieben? Meiner Meinung nach, ging dieses schneller als immer meine Beiträge in BB-Codes zu fassen

                              Das geht genau in die konzeptionelle Uncle Bob-Richtung, die ich für einen Fehler halte. Wenn ein Modul in einer generischen GUI mehrere Views füllen können soll (Menü, Content), dann ist es auch notwendig, dass die Modul-Schnittstelle dieses berücksichtigt.
                              Schonmal vielen Dank für Deine ausführliche Antwort. Das APF habe ich mir auch heruntergeladen und bereits etwas im Code gestöbert. Allerdings wird eine kleinere Lösung für mich angebrachter sein. Aus diesem Grund fasse ich das nochmal kurz für meinen Anwendungsfall zusammen.

                              Rahmen-Applikation starten.
                              1. Inititalisierung der Klasse "modul" beim Seitenaufruf von tralalla.de/irgendwas...
                              2. Durch den entsprechenden Key wird im Konstruktor der Klasse die Datenbank für die Module abgefragt
                              3. Ist das Modul in der Datenbank vorhanden, wird die gewünschte Klasse "address" eingebunden

                              FC-Action der Rahmen-Applikation ausführen und dabei URL nach Modul-Schlüssel durchsuchen.
                              1. Da die Klasse "modul" nicht weiß welche Aktionen die Klasse "address" besetzt wird die Aktion erst in dieser ausgefiltert

                              FC-Action des aktiven Moduls ausführen.
                              1. Ruft die aufgerufene Aktion (Methode) der Klasse "address" auf

                              View der Rahmen-Applikation aufbauen.
                              1. HTML-Template einlesen und Platzhalter definieren

                              An den relevanten Stellen die View-Templates des Moduls an Hand der in 2. gefundenen Informationen einbinden.
                              1. Platzhalter mit Leben aus der Methode von "address" füllen
                              2. Rückgabe der Methode an die Elternklasse "modul"

                              Wenn du dich leichter tust, kann ich dir auch mal ein kleines Code-Beispiel schreiben, das das Konzept verdeutlicht. Ich denke auf Basis des APF sollte das nicht mehr wie 100 Zeilen effektiven Code ausmachen.
                              Natürlich nehme ich gerne Dein Angebot an und freue mich über ein kleines Code-Beispiel. Dieses würde mir auch schemenhaft reichen, sodass ich dieses selbst verstehen und ohne fertiges APFramework umsetzen könnte. Danke schonmal!!
                              www.webdeveloperfactory.de - Der Blog und Ratgeber für Webentwickler mit zahlreichen Informationen

                              Kommentar

                              Lädt...
                              X