Claudius L.: Umsetzung der Trennung von PHP- und HTML-Code / des EVA-Prinzips

Hallo!

Beim mitlesen hier im Forum ist mir neulich dieser Thread aufgefallen, der mir mal wieder vor Augen geführt hat, wie „schön“, sinnvoll und nützlich die Anwendung des EVA-Prinzips und die Trennung von HTML- und Programm-Code sein kann.
Im Moment bastle ich an einem kleinen Projekt, in welchem ich diese Prinzipien gerne anwenden möchte. Allerdings habe ich große Probleme bei der Umsetzung, insbesondere, wenn Datenbankabfragen zu verarbeiten sind. Dabei ist mir nicht klar, wie ich die Verarbeitung des Querys von der Ausgabe des resultierenden HTML-Codes sinnvoll trennen könnte.
Um meine Probleme zu verdeutlichen, hier ein Stück aus meinem Code[1]:

// Auflistung aller Konten  
  
$sql = 'SELECT id, konten.name AS konto_name, konten.besitzerid, besitzer.name AS besitzer_name FROM konten LEFT JOIN besitzer ON konten.besitzerid = besitzer.besitzerid ORDER BY besitzer_name';  
$result = $mysqli->query($sql) or die ('Abfrage der Konten nicht möglich: '.$mysqli->error);  
  
if ($result->num_rows == 0)  
	{  
		echo "<p>Keine Konten</p>";  
	}  
else  
	{  
		echo "<table>";  
		$format = '<tr>  
	<td>%1$s</td>  
	<td>%3$s (%4$s)</td>  
	<td>  
		<form action="index.php?view=manage_accounts" method="post">  
			<input type="hidden" name="delete_account_id" value="%2$s" />  
			<input type="hidden" name="delete_account_name" value="%1$s" />  
			<input type="hidden" name="delete_account_owner_name" value="„%4$s“" />  
			<input type="submit" value="entfernen" />  
		</form>  
	</td>  
</tr>';  
		while ($row = $result->fetch_assoc())  
			{  
				printf($format, htmlspecialchars($row['konto_name']), htmlspecialchars($row['id']), htmlspecialchars($row['besitzerid']), htmlspecialchars($row['besitzer_name']));  
			}  
		echo "</table>";  
	}

Würde ich versuchen, hier Verarbeitung und Ausgabe zu trennen - was käme da dann raus?
Ich müsste doch $result bzw. die einzelnen Zeilen zwischenspeichern, um dann die while-Schleife mit $format und printf in einen Ausgabe-Teil zu verschieben. Wobei ich dann dort $result verarbeiten müsste, was doch ziemlich nach „Verarbeitung“ und nicht nur nach “Ausgabe“ riecht (mein Problem dann also nichtmehr Ausgabe während der Verarbeitung sondern Verarbeitung während der Ausgabe wäre …).
Als Alternative könnte ich auch $format auslagern (in ein Array, Objekt, eine externe Datei), aber wenn ich diese Daten dann verwende, vermische ich doch wieder Verarbeitung und Ausgabe. Der HTML-Code stünde zwar nicht direkt im PHP-Code, aber der Vorgang des Ausgebens würde wieder während der Verarbeitung geschehen.

Ähnlich schwer tue ich mich an dieser Stelle des Codes[2]:

// Abfrage der Bestätigung, falls ein Konto zum Löschen markiert wurde  
  
if (set_not_empty('post', 'delete_account_id') && set_not_empty('post', 'delete_account_name') && set_not_empty('post', 'delete_account_owner_name'))  
	{		  
		$format = '<p>Wirklich das Konto %1$s löschen? (Besitzer: %2$s)</p>  
<form action="index.php?view=manage_accounts" method="post">  
	<fieldset>  
		<input type="hidden" name="account_id" value="%3$s" />  
		<button name="confirm" value="ok" type="submit">Ja</button>  
		<button name="confirm" value="" type="submit">Nein</button>  
	</fieldset>  
</form>';  
		  
		printf($format, htmlspecialchars($_POST['delete_account_name']), htmlspecialchars($_POST['delete_account_owner_name']), htmlspecialchars($_POST['delete_account_id']));  
	}

Da ich hier nicht wie oben mehrere Zeilen auszugeben habe ($row), wäre es hier natürlich noch eher denkbar $format und printf an eine andere Stelle zu verschieben. Allerdings müsste ich dann an dieser Stelle nochmals prüfen, ob die Bedingung aus dem if () erfüllt wäre. Dies stellt in meinen Augen aber eine Art Redundanz dar, da ich die gleiche Bedingung zwei Mal prüfen würde und obiges Codefragment dann eigentlich keinerlei Funktion mehr hätte - oder sehe ich das falsch?

Irgendwie habe ich das Gefühl, völlig auf dem Holzweg zu sein. Daher meine Frage: Wie macht man’s richtig? Wie stelle ich es an, dass ich meinen HTML-Code nicht in den PHP-Code mische, wenn es nicht nur um die bloße Ersetzung von Platzhaltern im HTML durch Textfragmente geht (wie etwa hier diskutiert), sondern ich wie in meinen Beispielen oben HTML-Code tatsächlich generieren muss? Mir scheint es fast widersprüchlich, zu versuchen, HTML- und PHP-Code voneinander zu trennen, wenn mein Ziel doch ist, mit Hilfe von PHP HTML zu generieren.
Ich würde mich über Tipps, wie man es besser machen könnte, sehr freuen!

Danke schon jetzt und einen schönen Abend noch,

Claudius

[1]: Ich weiß, dass die „Fehlerbehandlung“ mit die() nicht optimal ist. Allerdings handelt es sich bei dem Projekt aus dem der Code stammt um nichts, dass jemals auf einem öffentlichen Server laufen wird, sondern es wird nur von mir verwendet werden - und für diesen Fall scheint es mir zweckmäßig.

[2]: Die Funktion set_not_empty() ist eine vorher im Programmablauf definierte Funktion, die im Prinzip nur isset() und $foo != '' zusammenfasst.

  1. hi,

    Im Moment bastle ich an einem kleinen Projekt, in welchem ich diese Prinzipien gerne anwenden möchte. Allerdings habe ich große Probleme bei der Umsetzung, insbesondere, wenn Datenbankabfragen zu verarbeiten sind.

    Da kannst Du am Besten gleich mit der Trennung weitermachen, also SQL auch noch vom Code trennen.

    Hier mal ein Beispiel in Perl (da ich PHP nicht unterstütze):

      
      
    # im Code  
    tie my %log, 'TieLog'; # Variable an Klasse binden  
      
    # in Klasse  
    sub TIEHASH{  
       # Objekt erstellen, calling new()  
       # Verbindung zur DB, DB-Handle in Objekt legen  
    }  
      
    # in Code, Objektverwendung  
    tied(%log)->daily('2011-07-19', \&cb); # Tagesreport anfordern  
       # es wird eine Callbackfunktion übergeben, die HTML ausgibt  
      
    sub cb{  
       my $record = shift; # Array-Referenz auf einen Record von vielen  
       # $record auf Spalten aufteilen und print auf STDOUT  
    }  
      
    # anderer Code, Hash-Verwendung  
    %log = (url => $url, hugo => $hugo, ref => $self->param('ref'), ts => time);  
       # schreibe Log-Table, einen Eintrag machen  
    
    

    Ergo: HTML wird irgendwo schon vom Code erzeugt. Meine Art der Trennung besteht darin, das auf eine Funktion zu beschränken.

    Hotti

    1. Hallo

      "[..]da ich PHP nicht unterstütze"

      weil...? Warum bevorzugst du Perl?

      Guten Abend, der Selektor

      1. Moin,

        "[..]da ich PHP nicht unterstütze"

        weil...? Warum bevorzugst du Perl?

        Hauptsächlich wegen genau diesem hier angesprochenen Thema. In der Tat habe ich schonmal begonnen, ein paar Web-Anwendungen, die ich bereits in Perl hatte, nach PHP umzuschreiben. Unter Beibehaltung meines bisherigen Perl-Styles (z.B. Kontrollstrukturen zur Parameterverarbeitung) habe ich feststellen müssen, dass Perl zielführender/produktiver ist, Perl-Code wird übersichtlicher, teamfreundlicher und ist leichter zu pflegen.

        Von eimem Parser, wie CGI::param (Perl-Modul CGI.pm) ist PHP weit entfernt. Die param()-Method des CGI-Moduls lässt sich in Perl z.B. infolge Delegierung recht einfach an ein eigenes Objekt binden, ohne alle Methoden von CGI.pm erben zu müssen. Weil das Beispiel so schon ist:

          
        package myCMS;  
        use CGI;  
          
        sub new{  
          my $class = shift;  
          my $self = bless{  
            CGI => CGI->new,  
          ), $class;  
          return $self;  
        }  
          
        # Delegation  
        sub param{  
        	my $self = shift;  
        	return $self->{CGI}->param(@_);  
        }  
          
        package main;  
          
        my $u = myCMS->new;  
        @params = $u->params;  
        
        

        Versionskonflikte: Ich programmiere seit 1998 mit Perl und die Scripts sind weitgehend unabhängig von der Perl-Verison, erst neulich habe ich ein 10 jahre altes Perl-Script aus meinem Archiv gefischt, es funktionierte auf Anhieb und plattformunabhängig. Perl unterstützt OOP seit v5.

        Unicode/Inernationalisierung: Viele in PHP gemachte Seiten, die ich so kenne, haben Probleme mit der Zeichenkodierung, was möglicherweise nicht an PHP an sich liegt sondern eher an der Umsetzung und in dieser Sache spricht auch dieses Forum Bände ;)  Die Unicode-Unterstützung in Perl ist vorzüglich.

        DBI: Das I steht für Unabhängigkeit vom RDBMS-Layer. Beruflich habe ich schon zwei Umstellungen von MySQL auf Postgresql und umgekehrt mitgemacht, die erste hat einen halben Tag gedauert, die zweite eine halbe Stunde (einschließlich Kaffepause).

        Abschließend noch ein schönes Stück Code zum Thema Trennung der abstract Layer zur redundanten Datenhaltung:

          
        my %pbin = ();  
        tie(%pbin, 'ORM') || tie(%pbin, 'Objects');  
        
        

        'ORM' hält die Objekte in einer DB, 'Objects' in einer Datei. Ist die DB mal nicht erreichbar, wird %pbin mit den Daten aus der Datei versorgt.

        Zum Thema Datenfernübertragung per HTTP habe ich in eigener Sache ein Modul geschrieben, das wäre in PHP nicht machbar. Dieses Modul serialisiert Objekte oder Sammlungen von Objekten in einen Byte-Stream, der serverseitig wieder in dieselbe Datenstruktur umgewandelt wird, z.B. für den Einbau in eine DB oder eine Datei und natürlich geht die Übertragung auch umgekehrt vom Server zum Client.

        Fürs Erste ;)
        Hotti

        1. Hallo Hottie,

          hab deinen Beitrag mal überflogen und muss dir obwohl ich PHP Nutzer bin bei vielen Dingen beipflichten. Die Unicode Unterstützung ist echt ein Problem, da muss man extra Funktionen benutzen damit das funktioniert (stat substr() mb_substr() etc...). Das müsste PHP intern irgendwie lösen.

          Was die Datenbank angeht muss ich das aber glaub ich ein wenig entschärfen. Wenn man das PDO benutzt und das ganze in Klassen zusätzlich noch Kapselt, dann ist die Umstellung auf andere Systeme auch recht einfach. Naja das bedeutet natürlich mehr Aufwand, da man diese "geordneten Zugriffe" erstmal selber bauen muss.

          Für das leichtere Vererben oder Delegieren wirken die Magic-Functions in PHP manchmal wunder.

          Im großen und ganzen ist PHP für den schnellen Einstieg und für kleine bis mittelgroße Webseiten bestimmt die richtige Wahl.
          Ansonsten ist das Ansichtssache. Was der eine bevorzugt sieht der andere als Pfusch an. Bei Javascript kannst du z.B. dem this in einem Object einfach einen anderen Wert geben. Das ist Pfusch, aber manchmal vermisse ich diese Funktionalität in PHP.

          Gruß
          phpler
          T-Rex

          1. Hi!

            Die Unicode Unterstützung ist echt ein Problem, da muss man extra Funktionen benutzen damit das funktioniert (stat substr() mb_substr() etc...). Das müsste PHP intern irgendwie lösen.

            Ist in Arbeit, kommt mit PHP 6. Da das eine gehörige Umstellung ist, weil man wieder niemand damit gerechnet hat, dass es andere Sprachen als Englisch gibt, als man für PHP 4 die zu Grunde liegende Zend Engine entwarf, dauert das eben schon ein paar Jahre. Vielleicht sind auch nur nicht genügend kompetente Mitarbeiter mit freier Zeit zu finden.

            Was die Datenbank angeht muss ich das aber glaub ich ein wenig entschärfen. Wenn man das PDO benutzt und das ganze in Klassen zusätzlich noch Kapselt, dann ist die Umstellung auf andere Systeme auch recht einfach. Naja das bedeutet natürlich mehr Aufwand, da man diese "geordneten Zugriffe" erstmal selber bauen muss.

            Einfach geht das nur, wenn man keine speziellen Funktionalitäten und Dialekteigenheiten verwendet. Dann stellt sich die Frage, warum man umstellen will. Bleibt man dabei, das neue DBMS neutral zu benutzen, kann eigentlich nur Lizenz, Performance oder Politik ein Wechselgrund sein.

            Ansonsten ist das Ansichtssache. Was der eine bevorzugt sieht der andere als Pfusch an.

            Was der eine in einem System sich jahrelang erarbeitet hat, wird er im anderen System nicht von heut auf morgen beherrschen. Ständig mit dem bisherigen System zu vergleichen statt sich auf die Philosophie des neuen Systems einzulassen - in die man sich auch erst einmal einarbeiten muss -, behindert auch das Anfreunden mit dem Neuen. Zudem kann noch Frust hinzukommen, wenn man sich beim Lernzeitbedarf verschätzt hat.

            Bei Javascript kannst du z.B. dem this in einem Object einfach einen anderen Wert geben. Das ist Pfusch, aber manchmal vermisse ich diese Funktionalität in PHP.

            Da fällt mir lediglich als Anwendungsfall ein, im Konstruktor ein anderes Objekt in $this abzulegen, damit dieser dieses zurückgibt - also eine Factory. Kann man sicher besser lösen. Oder was für einen Fall hast du?

            Lo!

            1. Ja genau diesen!
              Besser ist Ansichtssache ;).

              Gruß
              der beste
              T-Rex

          2. hi,

            Ansonsten ist das Ansichtssache. Was der eine bevorzugt sieht der andere als Pfusch an.

            Pssssst, nicht doch soooo direkt ;) (oder doch(*))

            Nochmal zu Perl: Es macht mir viel Freude, eigene Libs zu entwickeln. Mächtig gewaltig ist tie(); damit lassen sich Module schreiben, die sowohl einen OO-Zugriff als auch Zugriffe auf "Daten" über Datenstrukturen wie Array, Hash oder Scalar(Referenz) ermöglichen.

            tie %bin, 'Objects'; # File Abstract Layer

            In %bin liegt der gesamte Content meiner Website. Aber nicht wirklich, denn das würde ja bedeuten, dass einige MBs im RAM rumliegen. Der 'innere' Hash in %bin enthält daher nur die Namen der Object-IDs, die Namen der Attribute und die Postitionen im FileHandle, wo die Werte zu finden sind. Das Objekt %bin ist, mit wenigen kB, also sehr viel kleiner als der gesamte Datenbestand. Erst, wenn ein Attribut-Wert abgefragt wird, $bin{'/'}{body}, greift innerhalb der Tie-Klasse das Objekt in die Datei und gibt den Wert zurück.

            tie %bin, 'ORM'; ist wieder ein bischen anders, der innere Hash ist leer, das hinter %bin liegende Objekt enthält das DB-Handle und ein paar prepared Statements womit der Datenzugriff performant wird.

            (*) Ich kann mir nicht vorstellen, das in PHP machen zu müssen. PHP-Code, den ich bisher sah, namentlich hier im Forum, sieht oft nach Pfusch aus, oder zumindest nach Bastelei und nicht professionell.

            Viele Grüße,
            Hotti

    2. Hallo hotti,

      auch dir vielen Dank für deine Antwort. Leider habe ich großen Respekt vor allen, die Perl verstehen oder gar schreiben können – und zwar weil ich selbst von beidem meilenweit entfernt bin. ;-)
      Aber ich werde noch ein bisschen darüber meditieren, vielleicht kommt mir ja noch eine Erkenntnis …
      Zumindest die Vermischung auf nur eine Funktion zu beschränken ist ein guter Gedanke, danke!

      Viele Grüße,

      Claudius

  2. Hi!

    Würde ich versuchen, hier Verarbeitung und Ausgabe zu trennen - was käme da dann raus?
    Ich müsste doch $result bzw. die einzelnen Zeilen zwischenspeichern, um dann die while-Schleife mit $format und printf in einen Ausgabe-Teil zu verschieben. Wobei ich dann dort $result verarbeiten müsste, was doch ziemlich nach „Verarbeitung“ und nicht nur nach “Ausgabe“ riecht (mein Problem dann also nichtmehr Ausgabe während der Verarbeitung sondern Verarbeitung während der Ausgabe wäre …).

    "Ausgabe" beschränkt sich nicht nur auf echo und Konsorten, vielmehr ist mit diesem Teil die Ausgabelogik gemeint. Wenn also für die Ausgabe ein Array mit Datensätzen zu durchlaufen ist, und (abgesehen davon, dass man das mit modernem CSS machen kann) jede zweite Zeile eine andere Formatierung bekommen soll, dann ist die foreach-Schleife, das Umschalten des Zweite-Zeile-Flags und das if, um darauf zu testen, nicht Verarbeitungs- sondern Ausgabelogik.

    Ein weiteres Beispiel wäre ein Fehlerfall. Die Information, ob ein Fehler vorliegt (und auch welches Eingabeelement er betrifft, wenn es nicht grad ein allgemeiner Fehler ist) wird in der Verarbeitungslogik ermitteln. Die Ausgabelogik prüft darauf und gibt entweder eine Fehlermeldung aus oder das was im Gutfall auszugeben ist.

    Ähnlich schwer tue ich mich an dieser Stelle des Codes[2]:
    // Abfrage der Bestätigung, falls ein Konto zum Löschen markiert wurde
    if (set_not_empty('post', 'delete_account_id') && set_not_empty('post', 'delete_account_name') && set_not_empty('post', 'delete_account_owner_name'))

    Das ist Verarbeitungslogik. Die erstellt für die Ausgabelogik eine boolesche Variable. Die A. muss das da oben alles nicht wissen. Sie muss nur entscheiden können, ob dies oder jenes auszugeben ist.

    Wie macht man’s richtig?

    Ein absolutes "Richtig" oder "Falsch" gibt es nicht. Die Antwort kann eigentlich nur lauten: So, dass man die Aufgabenstellung leicht im Code nachvollziehen kann, dass Änderungen einfach ohne riesige Auswirkungen auf den Rest des Programms erledigt werden können.

    Wie stelle ich es an, dass ich meinen HTML-Code nicht in den PHP-Code mische, wenn es nicht nur um die bloße Ersetzung von Platzhaltern im HTML durch Textfragmente geht (wie etwa hier diskutiert), sondern ich wie in meinen Beispielen oben HTML-Code tatsächlich generieren muss? Mir scheint es fast widersprüchlich, zu versuchen, HTML- und PHP-Code voneinander zu trennen, wenn mein Ziel doch ist, mit Hilfe von PHP HTML zu generieren.

    Eben. HTML muss nicht von PHP getrennt werden, sondern die Verarbeitungsschritte und -teilschritte sollten klar definiert sein und mit überschaubaren Schnittstellen mit dem Rest des Programms kommunizieren.

    Das Thema ist übrigens grad vor drei Tagen diskutiert worden: Trennung der Anliegen (Logik - Layout).

    [2]: Die Funktion set_not_empty() ist eine vorher im Programmablauf definierte Funktion, die im Prinzip nur isset() und $foo != '' zusammenfasst.

    Dafür gibt es empty().

    Lo!

    1. Hallo dedlfix,

      und vielen Dank für deine Antwort.

      "Ausgabe" beschränkt sich nicht nur auf echo und Konsorten, vielmehr ist mit diesem Teil die Ausgabelogik gemeint. Wenn also für die Ausgabe ein Array mit Datensätzen zu durchlaufen ist, und (abgesehen davon, dass man das mit modernem CSS machen kann) jede zweite Zeile eine andere Formatierung bekommen soll, dann ist die foreach-Schleife, das Umschalten des Zweite-Zeile-Flags und das if, um darauf zu testen, nicht Verarbeitungs- sondern Ausgabelogik.

      Ok, so habe ich es noch nie betrachtet. Nach dieser Definition ist mein obiges Codebeispiel (zumindest das obere) also eigentlich ein Stück reiner Ausgabelogik, richtig?

      Ähnlich schwer tue ich mich an dieser Stelle des Codes[2]:
      // Abfrage der Bestätigung, falls ein Konto zum Löschen markiert wurde
      if (set_not_empty('post', 'delete_account_id') && set_not_empty('post', 'delete_account_name') && set_not_empty('post', 'delete_account_owner_name'))

      Das ist Verarbeitungslogik. Die erstellt für die Ausgabelogik eine boolesche Variable. Die A. muss das da oben alles nicht wissen. Sie muss nur entscheiden können, ob dies oder jenes auszugeben ist.

      Soweit kann ich das im Prinzip nachvollziehen. Das ist im Prinzip die Art „redundater Prüfung“, von der ich nach dem zweiten Codebeispiel gesprochen habe. Und genau das scheint mir in meinem Fall so seltsam, da der oben zitierte Code der letzte meiner Verarbeitungsschritte ist. Folglich ergäbe sich bei Verwendung einer boolschen Kontrollvariablen für die Ausgabe:

      // Abfrage der Bestätigung, falls ein Konto zum Löschen markiert wurde  
        
      $account_selected_to_delete = false;  
        
      if (set_not_empty('post', 'delete_account_id') && set_not_empty('post', 'delete_account_name') && set_not_empty('post', 'delete_account_owner_name'))  
      	{  
      		$account_selected_to_delete = true;  
      	}  
        
      // Beginn der Ausgabe  
        
      if ($account_selected_to_delete)  
      	{  
      		$format = '<p>Wirklich das Konto %1$s löschen? (Besitzer: %2$s)</p>  
      <form action="index.php?view=manage_accounts" method="post">  
      	<fieldset>  
      		<input type="hidden" name="account_id" value="%3$s" />  
      		<button name="confirm" value="ok" type="submit">Ja</button>  
      		<button name="confirm" value="" type="submit">Nein</button>  
      		<!--<input type="submit" name="confirm" value="ok" />  
      		<input type="submit" name="confirm" value="" />-->  
      	</fieldset>  
      </form>';  
      		  
      		printf($format, htmlspecialchars($_POST['delete_account_name']), htmlspecialchars($_POST['delete_account_owner_name']), htmlspecialchars($_POST['delete_account_id']));  
      	}  
      	  
      // Weitere Ausgaben wie Auflistung aller Konten (vgl. Codebeispiel 1)
      

      Aber so meinst du doch im Prinzip, oder?

      Ein absolutes "Richtig" oder "Falsch" gibt es nicht. Die Antwort kann eigentlich nur lauten: So, dass man die Aufgabenstellung leicht im Code nachvollziehen kann, dass Änderungen einfach ohne riesige Auswirkungen auf den Rest des Programms erledigt werden können.

      Ist zwar vermutlich Ansichtssache, aber welches Vorgehen ist deiner Meinung nach empfehlenswerter: das von mir oben gezeigte, oder so, wie es zehbaeh macht?
      In zehbaehs Version ist meiner Meinung nach das HTML besser les- und durchschaubar, meine Version legt das Augenmerk mehr auf die technische Seite. Dafür habe ich aber auch das ganze HTML mit Platzhaltern kompakt in einem String. Gibt es hier ein objektives „Besser“?

      Das Thema ist übrigens grad vor drei Tagen diskutiert worden: Trennung der Anliegen (Logik - Layout).

      Danke für den Hinweis, das habe ich übersehen. ;-)
      Enthält auf jeden Fall einige interessante Denkanstöße.

      [2]: Die Funktion set_not_empty() ist eine vorher im Programmablauf definierte Funktion, die im Prinzip nur isset() und $foo != '' zusammenfasst.

      Dafür gibt es empty().

      Ohje, das ist peinlich. Da hat der Wunsch, eine praktische, zusammenfassende Funktion zu basteln wohl das Denken vernebelt …

      Schönen Abend noch und viele Grüße,

      Claudius

      1. Hi!

        Ok, so habe ich es noch nie betrachtet. Nach dieser Definition ist mein obiges Codebeispiel (zumindest das obere) also eigentlich ein Stück reiner Ausgabelogik, richtig?

        Nein, denn es enthält eine DBMS-Abfrage inklusive einer rudimentären Fehlerbehandlung (die() ist Mist, weil es eine unfertige Seite hinterlässt. Zudem ist der ausgegebene Text für den Anwender nicht nützlich. Die genaue Fehlerursache ist auch nichts, was die Öffentlichkeit angeht.) Im Prinzip sollte auch das Fetchen zur Verarbeitungslogik gehören. Vor allem dann, wenn die Daten vor der Ausgabe noch weiter bearbeitet werden sollen. Wenn sie nur abzulegen wären, um sie 1:1 der Ausgabe zu übergeben, könnte der Pragmatiker sagen: "EVA ist kein bindendes Gesetz, fetch ich die Daten lieber später, als sie einfach nur in ein Zwischenarray zu kopieren". Besser wäre es, ein Lazy-Fetch zu implementieren und den eigentlichen Fetch-Vorgang vor der Ausgabelogik in einer foreach-Schleife zu verstecken, indem man die Interfaces Iterator (und ggf. IteratorAggregate) implementiert. Aber das fängt dann schon langsam an, höhere Kunst zu werden.

        Soweit kann ich das im Prinzip nachvollziehen. Das ist im Prinzip die Art „redundater Prüfung“, von der ich nach dem zweiten Codebeispiel gesprochen habe.

        Redundant im Ganzen gesehen. Aber manchmal muss man solche Zwischenschritte einfügen, damit man eine Trennung und damit eine leichtere Wartung und andere Vorteile nutzen zu können.

        Und genau das scheint mir in meinem Fall so seltsam, da der oben zitierte Code der letzte meiner Verarbeitungsschritte ist. Folglich ergäbe sich bei Verwendung einer boolschen Kontrollvariablen für die Ausgabe:

        // Abfrage der Bestätigung, falls ein Konto zum Löschen markiert wurde

        $account_selected_to_delete = false;

        if (set_not_empty('post', 'delete_account_id') && set_not_empty('post', 'delete_account_name') && set_not_empty('post', 'delete_account_owner_name'))
        {
        $account_selected_to_delete = true;
        }

          
        Kann man zusammenfassen, indem man notiert:  
          
          $account\_selected\_to\_delete = !empty(...) and !empty(...) ...  
          
        
        > // Beginn der Ausgabe  
        >   
        > if ($account\_selected\_to\_delete)  
        > 	{  
        > 		$format = '<p>Wirklich das Konto %1$s löschen? (Besitzer: %2$s)</p>  
        > <form action="index.php?view=manage\_accounts" method="post">  
        > 	<fieldset>  
        > 		<input type="hidden" name="account\_id" value="%3$s" />  
        > 		<button name="confirm" value="ok" type="submit">Ja</button>  
        > 		<button name="confirm" value="" type="submit">Nein</button>  
        > 		<!--<input type="submit" name="confirm" value="ok" />  
        > 		<input type="submit" name="confirm" value="" />-->  
        > 	</fieldset>  
        > </form>';  
        > 		  
        > 		printf($format, htmlspecialchars($\_POST['delete\_account\_name']), htmlspecialchars($\_POST['delete\_account\_owner\_name']), htmlspecialchars($\_POST['delete\_account\_id']));  
        > 	}  
          
        Bei mir beginnt die Ausgabe eines HTML-Dokuments mit dem Doctype und <html> usw. Da ist also noch einiger Abstand zwischen der Erzeugung des Flags $account\_selected\_to\_delete und der Auswertung in der Ausgabe.  
          
        
        > Ist zwar vermutlich Ansichtssache, aber welches Vorgehen ist deiner Meinung nach empfehlenswerter: das von mir oben gezeigte, oder so, wie es [zehbaeh](https://forum.selfhtml.org/?t=205988&m=1398068) macht?  
          
        Ich leg mich da nicht allgemein fest sondern entscheide das von Fall zu Fall, was mir grad einfacher verständlich oder einfacher zu implementieren scheint.  
          
        
        > In zehbaehs Version ist meiner Meinung nach das HTML besser les- und durchschaubar, meine Version legt das Augenmerk mehr auf die technische Seite. Dafür habe ich aber auch das ganze HTML mit Platzhaltern kompakt in einem String. Gibt es hier ein objektives „Besser“?  
          
        PHP ist ja schon ein Template-System, also kann man auch seine Fähigkeiten nutzen, statt sie anderweitig nachzubilden. (Sie trotzdem nachzubilden kann gewichtigere Gründe haben, als so basisnah wie möglich zu sein.) Ich nehme gern reines HTML gespickt mit der [alternativen Syntax von Kontrollstrukturen](http://www.php.net/manual/en/control-structures.alternative-syntax.php) und statt dem länglichen <?php echo htmlspecialchars($foo) ?> nehme ich eine Helper-Funktion: <?php h($foo) ?>. Diese enthält noch etwas mehr Logik, die man manchmal braucht, damit es nicht nur ein Quasi-Alias ist.  
          
          
        Lo!
        
        1. Hallo!

          Ok, so habe ich es noch nie betrachtet. Nach dieser Definition ist mein obiges Codebeispiel (zumindest das obere) also eigentlich ein Stück reiner Ausgabelogik, richtig?

          Nein, denn es enthält eine DBMS-Abfrage inklusive einer rudimentären Fehlerbehandlung […] Im Prinzip sollte auch das Fetchen zur Verarbeitungslogik gehören. Vor allem dann, wenn die Daten vor der Ausgabe noch weiter bearbeitet werden sollen. Wenn sie nur abzulegen wären, um sie 1:1 der Ausgabe zu übergeben, könnte der Pragmatiker sagen: "EVA ist kein bindendes Gesetz, fetch ich die Daten lieber später, als sie einfach nur in ein Zwischenarray zu kopieren". Besser wäre es, ein Lazy-Fetch zu implementieren und den eigentlichen Fetch-Vorgang vor der Ausgabelogik in einer foreach-Schleife zu verstecken, indem man die Interfaces Iterator (und ggf. IteratorAggregate) implementiert. Aber das fängt dann schon langsam an, höhere Kunst zu werden.

          Also zu früh früh gefreut …
          Ich fürchte, darüber muss ich erstmal ein bisschen nachdenken. Mit so etwas habe ich mich bisher leider noch nie beschäftigt. Aber vielen Dank für den Tipp.
          Dass die DBMS-Abfrage und die Verarbeitung des Ergebnisses nicht in die Ausgabe gehören ist mir noch einleuchtend. Für den Rest werde ich mich wohl erstmal über Lazy-Fetch und die Verwendung der von dir verlinkten Interfaces informieren müssen, momentan geht das noch deutlich über meinen Horizont hinaus.

          (die() ist Mist, weil es eine unfertige Seite hinterlässt. Zudem ist der ausgegebene Text für den Anwender nicht nützlich. Die genaue Fehlerursache ist auch nichts, was die Öffentlichkeit angeht.)

          Ja, ich weiß. Wie aber schon im ersten Posting erwähnt ist dieses Projekt für die Nutzung durch mich selbst ausgelegt. Und sollte dann mal was nicht klappen, bin ich eigentlich ganz froh, die genauer Fehlerursache sofort zu Gesicht zu bekommen. Aber sauber ist anders, das gebe ich zu.

          Bei mir beginnt die Ausgabe eines HTML-Dokuments mit dem Doctype und <html> usw. Da ist also noch einiger Abstand zwischen der Erzeugung des Flags $account_selected_to_delete und der Auswertung in der Ausgabe.

          Ja. Jain. Bei mir auch.
          Was ich bisher nicht erwähnt habe, ist dass die hier erzeugten Ausgaben zunächt in einem Ausgabepuffer landen und später an der richtigen Stelle im Dokument eingefügt werden.
          Ich habe also ein Template mit einigen einfachen Platzhaltern, die nur ersetzt werden müssen. Einer dieser Platzhalter befindet sich im Body und wird durch den Output meiner „Ausgabe“ ersetzt. Blöde Idee?

          In zehbaehs Version ist meiner Meinung nach das HTML besser les- und durchschaubar, meine Version legt das Augenmerk mehr auf die technische Seite. Dafür habe ich aber auch das ganze HTML mit Platzhaltern kompakt in einem String. Gibt es hier ein objektives „Besser“?

          PHP ist ja schon ein Template-System, also kann man auch seine Fähigkeiten nutzen, statt sie anderweitig nachzubilden. (Sie trotzdem nachzubilden kann gewichtigere Gründe haben, als so basisnah wie möglich zu sein.) Ich nehme gern reines HTML gespickt mit der alternativen Syntax von Kontrollstrukturen und statt dem länglichen <?php echo htmlspecialchars($foo) ?> nehme ich eine Helper-Funktion: <?php h($foo) ?>. Diese enthält noch etwas mehr Logik, die man manchmal braucht, damit es nicht nur ein Quasi-Alias ist.

          Ich glaube, ich muss jetzt mal noch umfassender verraten, wie ich eigentlich vorgehe:

          * zu beginn des Skripts lege ich ein leeres Arry $out an.
          * ob_start()
          * je nach anzuzeigender Seite inkludiere ich eine Datei, die alles Seitenspezifische enthält. Die ganz oben geposteten Codefragmente sind Auszüge aus einer solchen Datei - innerhalb der ich momentan versuche/versuchen möchte, Verarbeitung und Ausgabe möglichst sauber zu trennen.
          * $out['maincontent'] = ob_get_contents();
          * inkludieren der Template-Datei, die dann z.B. folgendes enthält:

          <!-- […]statisches HTML[…] -->  
          <?php echo $out['maincontent']; ?>  
          <!-- weitere HTML-Fragmente und PHP-Ausgaben aus $out -->
          

          Ist das komplett unsinnig?
          Wenn ich so darüber nachdenke, wäre es vermutlich zumindest ein Ansatz, das Konzept aus der Template-Datei konsequent anzuwenden und die „Datei für’s Seitenspezifische“ möglichst unter der Verwendung der von dir verlinkten alternativen Syntax nach Eingabe und Verarbeitung zu trennen. Klingt das vernünftig?
          Entschuldige bitte, wenn ich so „unmündige“ Fragen nach richtigem und falschem Vorgehen stelle, aber ich habe das Gefühl, noch einige grundlegend falschen Vorstellungen über eine ordentliche Struktur zu haben …
          Vor allem frage ich mich immer wieder Folgendes: Im Moment reden wir nur über die Ausgabe von HTML - ein Kontext, in dem es mich auch überzeugt, dass eben PHP- und HTML-Code nicht völlig zu trennen sind. Aber angenommen (rein hypothetisch, habe ich nicht vor), ich wollte mir genauso die Möglichkeit offen halten, zur Ausgabe beispielsweise ein Bild zu erzeugen. Das würde doch bedeuten, dass das, was mein Verarbeitungs-Part an die Ausgabe weitergibt, völlig frei von jeglicher HTML-Auszeichnung sein müsste. Allerdings ist doch genau das scheinbar weder sinnvoll noch unbedingt notwendig.
          Ich hoffe, ich rede keinen völligen Blödsinn - bin in dieser Hinsicht etwas verwirrt.

          Jedenfalls vielen Dank an dich für deine Unterstützung, du hilfst mir sehr weiter!

          Viele Grüße,

          Claudius

          1. Hi!

            Für den Rest werde ich mich wohl erstmal über Lazy-Fetch und die Verwendung der von dir verlinkten Interfaces informieren müssen, momentan geht das noch deutlich über meinen Horizont hinaus.

            Lazy-Irgendwas bedeutet, dass das Programm "zu faul" ist, dieses Irgendwas sofort zu tun. Stattdessen wartet es damit, bis es wirklich notwendig ist, also wenn eine konkrete Anforderung nach den Daten besteht. Wenn es Glück hat, nimmt der Programmfluss einen anderen Verlauf, bei dem die Daten doch nicht benötigt werden, und es hat sich die Arbeit gespart.

            Bei mir beginnt die Ausgabe eines HTML-Dokuments mit dem Doctype und <html> usw. Da ist also noch einiger Abstand zwischen der Erzeugung des Flags $account_selected_to_delete und der Auswertung in der Ausgabe.
            Ja. Jain. Bei mir auch.
            Was ich bisher nicht erwähnt habe, ist dass die hier erzeugten Ausgaben zunächt in einem Ausgabepuffer landen und später an der richtigen Stelle im Dokument eingefügt werden.

            Dann wäre das Einschalten des Ausgabepuffers die erste Amtshandlung der Ausgabelogik, und das stünde dann zwischem dem Erzeugen des Flags und seiner ersten Anwendung. Gut, das ist jetzt auch kein großer Abstand, aber wir nehmen einfach mal an, dass das Programm später erweitert wird und sich der Abstand dadurch vergrößert. Oder dir fällt auf, dass die Abfrage doch schon weiter oben benötigt wird, oder oder oder. Jedenfalls willst du doch eine klare Trennung, auch um damit Erfahrung zu sammeln, und da kannst du ruhig mal konsequent sein, auch wenn dir das redundant vorkommt. Dieser kleine Zusatzschritt bringt deinen Server nicht um - er wird nicht mal messbar sein.

            Ich habe also ein Template mit einigen einfachen Platzhaltern, die nur ersetzt werden müssen. Einer dieser Platzhalter befindet sich im Body und wird durch den Output meiner „Ausgabe“ ersetzt. Blöde Idee?

            Nicht unbedingt. Solange es nachvollziehbar, übersichtlich und wartbar bleibt, sollte das o.k. sein. Wie bewertet man aber diese Kriterien? Eine Formel gibt es dafür nicht, aber mit zunehmender Erfahrung wirst du ein Bauchgefühl dafür entwickeln.

            Ich glaube, ich muss jetzt mal noch umfassender verraten, wie ich eigentlich vorgehe:

            Zusammenfassend, deine Ausgabe beginnt also damit, gepuffert den Hauptinhalt zu erzeugen, der später an der gewünschten Stelle in den Rest der Seite eingefügt wird.

            Ist das komplett unsinnig?

            Nö. Das könnte im Gegenteil sogar vorteilhaft, weil du damit das Wesentliche zuerst machst und "der unbedeutende Rest" irgendwo hinten steht. Allerdings erhöht sich damit auch die Komplexität wieder ein wenig, einerseits durch die zusätzliche Pufferung und andererseits durch die nicht mehr lineare Reihenfolge beim Erstellen der Ausgabe. Doch das würde ich jetzt nicht überbewerten wollen, weil es mir nicht als ein wirklicher Nachteil erscheint.

            Wenn ich so darüber nachdenke, wäre es vermutlich zumindest ein Ansatz, das Konzept aus der Template-Datei konsequent anzuwenden und die „Datei für’s Seitenspezifische“ möglichst unter der Verwendung der von dir verlinkten alternativen Syntax nach Eingabe und Verarbeitung zu trennen. Klingt das vernünftig?

            Du meinst, statt einen großen, mehrzeiligen String mit Platzhaltern zu erstellen, die in einem zweiten Schritt mit printf() ersetzt werden, lieber gleich HTML erzeugen, in das die Werte eingefügt werden? Hat zumindest den Vorteil, dass ein Editor oder eine IDE das HTML als solches erkennen können, und dafür Syntax-Unterstützung anbieten können. Wie es mit der Übersicht aussieht, muss man sehen. Einerseits kommt der die Ausgabe eines Wertes genau an die Stelle, an der er stehen soll, andererseits ist bei der Platzhaltergeschichte das Drumherum besser lesbar, weil da nur ein kleines %s steht und der HTML-Code nicht durch PHP-Code zerrissen wird. Da muss man fallweise entscheiden, was der bessere Kompromiss ist. Wenn so ein HTML-Tag mit mehreren Attributen drin mehrfach durch PHP-Code unterbrochen wird, bekommt nicht nur die Syntaxunterstützung ein Problem, die Teile auseinanderzuhalten, auch das Auge des Betrachters. Sowas würde ich dann eher einzeln einem printf() zum Zusammenbauen übergeben. Nur-HTML-Blöcke stehen besser für sich zwischen ?> und <?php.

            Entschuldige bitte, wenn ich so „unmündige“ Fragen nach richtigem und falschem Vorgehen stelle, aber ich habe das Gefühl, noch einige grundlegend falschen Vorstellungen über eine ordentliche Struktur zu haben …

            Entwicklungspotential zu haben ist für mich kein Grund, um Entschuldigung zu ersuchen. Das hat doch jeder.

            Vor allem frage ich mich immer wieder Folgendes: Im Moment reden wir nur über die Ausgabe von HTML - ein Kontext, in dem es mich auch überzeugt, dass eben PHP- und HTML-Code nicht völlig zu trennen sind. Aber angenommen (rein hypothetisch, habe ich nicht vor), ich wollte mir genauso die Möglichkeit offen halten, zur Ausgabe beispielsweise ein Bild zu erzeugen. Das würde doch bedeuten, dass das, was mein Verarbeitungs-Part an die Ausgabe weitergibt, völlig frei von jeglicher HTML-Auszeichnung sein müsste. Allerdings ist doch genau das scheinbar weder sinnvoll noch unbedingt notwendig.

            Ein Bild hat keinen HTML-Code. Aber wenn du es erst erzeugen musst, dann doch aus dem Grund, dass es aus mehreren Teilen zusammenzusetzen ist - beispielsweise ein Hintergrund und individuelle Schrift drauf - oder durch Bearbeitung aus einem anderen Bild entstehen soll - wie zum Beispiel bei einer Verkleinerung. Auch hier kann man das EVA-Prinzip anwenden, wenn es sich lohnt. Der größte Teil wird jedoch der Verarbeitung zuzuordnen sein und die Ausgabe beschränkt sich auf ein oder mehrere header()-Aufrufe und ein imagejpeg() und Konsorten. Da würde ich einfach nur die einzelnen Bildverarbeitungsschritte kennzeichnen und wenn es hilfreich erscheint Berechnungen in Funktionen auslagern.

            Ich hoffe, ich rede keinen völligen Blödsinn - bin in dieser Hinsicht etwas verwirrt.

            Nun, dann hoffe ich doch, noch ein paar weitere Klarheiten beseitigt zu haben. (Das hab ich grad mit einem schelmischen und einem ernsten Auge gesagt, denn je weiter man in den Ozean abtaucht, desto mehr erkennt man von seiner unendlich erscheinenden Komplexität und dem eigenen Unvermögen, alles ergründen zu können.)

            Lo!

            1. Hallo!

              Lazy-Irgendwas bedeutet, dass das Programm "zu faul" ist, dieses Irgendwas sofort zu tun. Stattdessen wartet es damit, bis es wirklich notwendig ist, also wenn eine konkrete Anforderung nach den Daten besteht. Wenn es Glück hat, nimmt der Programmfluss einen anderen Verlauf, bei dem die Daten doch nicht benötigt werden, und es hat sich die Arbeit gespart.

              Das klingt nett, aber sehe ich es dann richtig, dass Lazy-Fetch vor allem Performance-Vorteile mit sich bring?

              Dann wäre das Einschalten des Ausgabepuffers die erste Amtshandlung der Ausgabelogik, und das stünde dann zwischem dem Erzeugen des Flags und seiner ersten Anwendung. Gut, das ist jetzt auch kein großer Abstand, aber wir nehmen einfach mal an, dass das Programm später erweitert wird und sich der Abstand dadurch vergrößert. Oder dir fällt auf, dass die Abfrage doch schon weiter oben benötigt wird, oder oder oder. Jedenfalls willst du doch eine klare Trennung, auch um damit Erfahrung zu sammeln, und da kannst du ruhig mal konsequent sein, auch wenn dir das redundant vorkommt. Dieser kleine Zusatzschritt bringt deinen Server nicht um - er wird nicht mal messbar sein.

              Da gebe ich dir absolut Recht. Ich war nur davon ausgegangen, dass das so nicht sein könnte, weil ich nur die Redundanz, nicht aber die Vorteile daraus gesehen habe. Inzwischen bin ich überzeugt. :-)

              Zusammenfassend, deine Ausgabe beginnt also damit, gepuffert den Hauptinhalt zu erzeugen, der später an der gewünschten Stelle in den Rest der Seite eingefügt wird.

              Genau so.

              Ist das komplett unsinnig?

              Nö. Das könnte im Gegenteil sogar vorteilhaft, weil du damit das Wesentliche zuerst machst und "der unbedeutende Rest" irgendwo hinten steht. Allerdings erhöht sich damit auch die Komplexität wieder ein wenig, einerseits durch die zusätzliche Pufferung und andererseits durch die nicht mehr lineare Reihenfolge beim Erstellen der Ausgabe. Doch das würde ich jetzt nicht überbewerten wollen, weil es mir nicht als ein wirklicher Nachteil erscheint.

              Danke für deine Einschätzung. Ich sehe das ähnlich: Der Nutzen, dass der Hauptinhalt separat vom „unbedeutenden Rest“ steht ist mir mehr wert als eine lineare Reihenfolge.

              Wenn ich so darüber nachdenke, wäre es vermutlich zumindest ein Ansatz, das Konzept aus der Template-Datei konsequent anzuwenden und die „Datei für’s Seitenspezifische“ möglichst unter der Verwendung der von dir verlinkten alternativen Syntax nach Eingabe und Verarbeitung zu trennen. Klingt das vernünftig?

              Du meinst, statt einen großen, mehrzeiligen String mit Platzhaltern zu erstellen, die in einem zweiten Schritt mit printf() ersetzt werden, lieber gleich HTML erzeugen, in das die Werte eingefügt werden? Hat zumindest den Vorteil, dass ein Editor oder eine IDE das HTML als solches erkennen können, und dafür Syntax-Unterstützung anbieten können. Wie es mit der Übersicht aussieht, muss man sehen. Einerseits kommt der die Ausgabe eines Wertes genau an die Stelle, an der er stehen soll, andererseits ist bei der Platzhaltergeschichte das Drumherum besser lesbar, weil da nur ein kleines %s steht und der HTML-Code nicht durch PHP-Code zerrissen wird. Da muss man fallweise entscheiden, was der bessere Kompromiss ist. Wenn so ein HTML-Tag mit mehreren Attributen drin mehrfach durch PHP-Code unterbrochen wird, bekommt nicht nur die Syntaxunterstützung ein Problem, die Teile auseinanderzuhalten, auch das Auge des Betrachters. Sowas würde ich dann eher einzeln einem printf() zum Zusammenbauen übergeben. Nur-HTML-Blöcke stehen besser für sich zwischen ?> und <?php.

              Gestern hatte ich eine Idee, welchen Mittelweg ich hier für meine Zwecke momentan für am besten geeignet halte. Besonders gefällt mir, dass die Vorteile von HTML gespickt mit PHP-Ausgaben mit denen von Platzhaltern und printf() kombiniert werden:

                
              /* Verarbeitung: Datenbank lesen und schreiben, Ergebnisse von Abfragen in Arrays kopieren (z.B. $accounts), Kontrollvariablen setzen  
                
              Verarbeitungsschritte … */  
                
              /*************** Ausgabe: ****************/  
                
              // Wurde ein Konto zum Löschen markiert?  
                
              if ($confirm_delete_account): ob_start(); ?>  
                
              <p>Wirklich das Konto %1$s löschen? (Besitzer: %2$s)</p>  
              <form action="index.php?view=manage_accounts" method="post">  
              	<fieldset>  
              		<input type="hidden" name="account_id" value="%3$s" />  
              		<button name="confirm" value="ok" type="submit">Ja</button>  
              		<button name="confirm" value="" type="submit">Nein</button>  
              	</fieldset>  
              </form>  
              <?php o($_POST['delete_account_name'], $_POST['delete_account_owner_name'], $_POST['delete_account_id']);  
              endif;  
                
              // Auflistung aller Konten  
                
              if ($accounts_exist):  
              	echo '<table>';  
              	ob_start();  
              	foreach ($accounts as $account):?>  
              	<tr>  
              		<td>%1$s</td>  
              		<td>%3$s (%4$s)</td>  
              		<td>  
              			<form action="index.php?view=manage_accounts" method="post">  
              				<fieldset><input type="hidden" name="delete_account_id" value="%2$s" />  
              				<input type="hidden" name="delete_account_name" value="%1$s" />  
              				<input type="hidden" name="delete_account_owner_name" value="„%4$s“" />  
              				<input type="submit" value="entfernen" /></fieldset>  
              			</form>  
              		</td>  
              	</tr>  
              <?php o($account['account_name'], $account['account_id'], $account['owner_id'], $account['owner_name']);  
              	endforeach;  
              	echo '</table>';  
              else:  
              	echo '<p>Keine Konten</p>';  
              endif;
              

              Die dazugehörige Funktion o:

              function o ()  
              	{  
              		$format = ob_get_contents();  
              		ob_end_clean();  
                
              		$args = array();  
              		foreach (func_get_args() as $arg)  
              			{  
              				if (is_array($arg) && isset($arg[0]))  
              					{  
              						if (isset($arg[1]) && $arg[1] == false)  
              							{  
              								$args[] = $arg[0];  
              							}  
              						else  
              							{  
              								$args[] = htmlspecialchars($arg[0]);  
              							}  
              					}  
              				elseif(!is_array($arg))  
              					{  
              						$args[] = htmlspecialchars($arg);  
              					}  
              				else  
              					{  
              						$args[] = 'Ungültiger Parameter übergeben!';  
              					}  
              			}  
              			  
              		vprintf($format, $args);  
              	}
              

              Das HTML steht also gespickt mit Platzhaltern und eingebettet in die alternative Kontrollstruktursyntax außerhalb von PHP-Tags. Allerdings landet jeder einzelne HTML-Bereich in einem eigenen Ausgabepuffer. Die Ausgabefunktion o() füttert vprintf() mit dem HTML-Platzhalter-Mix als $format und nimmt als Parameter entgegen, wodurch die Platzhalter ersetzt werden sollen. Werden Arrays übergeben, so kann auch festgelegt werden, ob der Parameter noch für den HTML-Kontext behandelt werden muss.

              Entschuldige bitte, wenn ich so „unmündige“ Fragen nach richtigem und falschem Vorgehen stelle, aber ich habe das Gefühl, noch einige grundlegend falschen Vorstellungen über eine ordentliche Struktur zu haben …

              Entwicklungspotential zu haben ist für mich kein Grund, um Entschuldigung zu ersuchen. Das hat doch jeder.

              Freut mich, dass du das so siehst. :-)

              Vor allem frage ich mich immer wieder Folgendes: Im Moment reden wir nur über die Ausgabe von HTML - ein Kontext, in dem es mich auch überzeugt, dass eben PHP- und HTML-Code nicht völlig zu trennen sind. Aber angenommen (rein hypothetisch, habe ich nicht vor), ich wollte mir genauso die Möglichkeit offen halten, zur Ausgabe beispielsweise ein Bild zu erzeugen. Das würde doch bedeuten, dass das, was mein Verarbeitungs-Part an die Ausgabe weitergibt, völlig frei von jeglicher HTML-Auszeichnung sein müsste. Allerdings ist doch genau das scheinbar weder sinnvoll noch unbedingt notwendig.

              Ein Bild hat keinen HTML-Code. Aber wenn du es erst erzeugen musst, dann doch aus dem Grund, dass es aus mehreren Teilen zusammenzusetzen ist - beispielsweise ein Hintergrund und individuelle Schrift drauf - oder durch Bearbeitung aus einem anderen Bild entstehen soll - wie zum Beispiel bei einer Verkleinerung. Auch hier kann man das EVA-Prinzip anwenden, wenn es sich lohnt. Der größte Teil wird jedoch der Verarbeitung zuzuordnen sein und die Ausgabe beschränkt sich auf ein oder mehrere header()-Aufrufe und ein imagejpeg() und Konsorten. Da würde ich einfach nur die einzelnen Bildverarbeitungsschritte kennzeichnen und wenn es hilfreich erscheint Berechnungen in Funktionen auslagern.

              Was ich meinte ging in eine etwas andere Richtung - ich versuch’s nochmal besser zu erklären:
              Angenommen, ich möchte eine Liste darstellen. Dann sollte meine Verarbeitung doch ein Array mit Listenelementen liefern. Und diese Listenelemente sollten doch frei von irgendwelcher Auszeichnung wie z.B. <li> sein, um zu ermöglichen, dass ich die Listenelemente nicht nur in einem HTML-Dokument ausgeben kann, sondern meine Ausgabe z.B. auch ein Bild erzeugen kann, auf welchem die Liste abgebildet ist oder ein RSS-Feed, welches nur die ersten paar Listenelemente will, diese jedoch auch frei von irgendwelchen HTML-Elementen, da die Listenelemente vielleicht als Aufzählung dargestellt werden sollen etc.
              Solche (für mich momentan hypothetischen) Anwendungsfälle sind es, an die ich denke, wenn ich davon spreche, dass in bestimmten Fällen Verarbeitung und Ausgabe doch völlig und nicht nur „so gut wie möglich“ getrennt sein müssten.

              Ich hoffe, ich rede keinen völligen Blödsinn - bin in dieser Hinsicht etwas verwirrt.

              Nun, dann hoffe ich doch, noch ein paar weitere Klarheiten beseitigt zu haben. (Das hab ich grad mit einem schelmischen und einem ernsten Auge gesagt, denn je weiter man in den Ozean abtaucht, desto mehr erkennt man von seiner unendlich erscheinenden Komplexität und dem eigenen Unvermögen, alles ergründen zu können.)

              Ich denke, du hast erfolgreich einige Klarheiten beseitigt und einige geschaffen. Aber so ist es wahrscheinlich immer, da das Verständnis des Einen immer auch Fragen nach vielen andern mit sich bringt.
              Hübsche Ozean-Metapher - ich mag da auch Sokrates ganz gern: Ich weiß, dass ich nicht weiß.

              Schönen Sonntagabend noch,

              Claudius

              1. Hi!

                Das klingt nett, aber sehe ich es dann richtig, dass Lazy-Fetch vor allem Performance-Vorteile mit sich bring?

                Ja, spart Zwischenspeicher und die Handlung, ihn zu füllen. Allerdings ist das in PHP mit dem Speicherverbrauch nicht ganz so wild. Wenn PHP eine Variable aufgrund einer Zuweisung oder Übergabe als Parameter kopieren müsste, legt es stattdessen eine Quasi-Referenz an. Es gibt also eine alte Verwaltungsstruktur für die alte Variable und eine für die neue, die aber beide auf den selben Inhalt verweisen. Erst wenn der durch eine Änderung an einer der beiden Stellen nicht mehr gleich ist, wird eine echte Kopie erzeugt. (References explained)

                Gestern hatte ich eine Idee, welchen Mittelweg ich hier für meine Zwecke momentan für am besten geeignet halte. Besonders gefällt mir, dass die Vorteile von HTML gespickt mit PHP-Ausgaben mit denen von Platzhaltern und printf() kombiniert werden:

                Gefällt mir nicht wirklich. Auf den ersten Blick muten die Platzhalter seltsam an, die da so scheinbar motivationslos in der Gegend herumlungern. Erst später kommt ein Funktionsaufruf, bei dem man den Inhalt der Funktion kennen muss, um ihn zu verstehen. (Bekommt man aber hin, nach der ersten allgemeinen Verunsicherung.) Nehmen wir mal an, du hast dich in diese Methode verliebt - klar, ist ja ein Kind deiner eigenen Gedanken - und kommst dann an eine Stelle, an der der HTML-Code-Block größer wird und Platzhalter und deren Ersetzung noch mehr auseinanderbringt. Was machst du dann?

                Angenommen, ich möchte eine Liste darstellen. Dann sollte meine Verarbeitung doch ein Array mit Listenelementen liefern. Und diese Listenelemente sollten doch frei von irgendwelcher Auszeichnung wie z.B. <li> sein, um zu ermöglichen, dass ich die Listenelemente nicht nur in einem HTML-Dokument ausgeben kann, sondern meine Ausgabe z.B. auch ein Bild erzeugen kann, auf welchem die Liste abgebildet ist oder ein RSS-Feed, welches nur die ersten paar Listenelemente will, diese jedoch auch frei von irgendwelchen HTML-Elementen, da die Listenelemente vielleicht als Aufzählung dargestellt werden sollen etc.
                Solche (für mich momentan hypothetischen) Anwendungsfälle sind es, an die ich denke, wenn ich davon spreche, dass in bestimmten Fällen Verarbeitung und Ausgabe doch völlig und nicht nur „so gut wie möglich“ getrennt sein müssten.

                Die Verarbeitung ist die Ermittlung der Daten. Alles was du hier aufgezählt hast, wäre Ausgabelogik.

                Es wird etwas komplexer, wenn die Aufgabe ist, ein oder mehrere Bilder vielleicht erst noch in Empfang zu nehmen, sie aber auf alle Fälle im Dateisystem abzulegen und zusätzlich noch Thumbnails zu erstellen. Weiterhin sollen Bilder und Thumbnails Wasserzeichen eingebaut bekommen. Die eigentliche Ausgabe des Scripts ist aber eine HTML-Seite, die über den Erfolg der Aktion berichten soll. Hier kann man erstmal nicht relativ klar die drei EVA-Teile haben. Stattdessen kann man innerhalb der Verarbeitung Unteraufgaben vergeben, die dann jeweils für sich nach EVA gestaltet sind.

                EVA ist übrigens kein Allheilmittel, sondern stößt auch irgendwann an seine Grenzen. Aber es gibt ja auch noch andere Entwurfsmuster, nach denen man sein Programm strukturieren kann.

                Lo!

                1. Moin!

                  Gestern hatte ich eine Idee, welchen Mittelweg ich hier für meine Zwecke momentan für am besten geeignet halte. Besonders gefällt mir, dass die Vorteile von HTML gespickt mit PHP-Ausgaben mit denen von Platzhaltern und printf() kombiniert werden:

                  Gefällt mir nicht wirklich. Auf den ersten Blick muten die Platzhalter seltsam an, die da so scheinbar motivationslos in der Gegend herumlungern. Erst später kommt ein Funktionsaufruf, bei dem man den Inhalt der Funktion kennen muss, um ihn zu verstehen. (Bekommt man aber hin, nach der ersten allgemeinen Verunsicherung.) Nehmen wir mal an, du hast dich in diese Methode verliebt - klar, ist ja ein Kind deiner eigenen Gedanken - und kommst dann an eine Stelle, an der der HTML-Code-Block größer wird und Platzhalter und deren Ersetzung noch mehr auseinanderbringt. Was machst du dann?

                  Gefällt mir schon deshalb nicht, weil das ob_start() außerhalb mitten im Code steht, und das ob_end_clean() innerhalb dieser o()-Funktion.

                  Das bedeutet: Man kann die Funktion nicht einfach so aufrufen, sondern muss vorher einen ob_start()-Bereich eröffnet haben. Das widerspricht vernünftiger Symmetrie und Verschachtelung.

                  - Sven Rautenberg

                  1. Hallo!

                    Das bedeutet: Man kann die Funktion nicht einfach so aufrufen, sondern muss vorher einen ob_start()-Bereich eröffnet haben. Das widerspricht vernünftiger Symmetrie und Verschachtelung.

                    Da hast du leider Recht. Dieses Problem war mir ursprünglich nicht klar - darauf aufmerksam wurde ich erst durch die PHP-Notices, nachdem ich das erste Mal ein ob_start() vergessen hatte.

                    Grüße,

                    Claudius

                2. Hallo!

                  ich danke dir wieder für deinen Rat - ich konnte leider nicht eher Antworten, da mit Semesterende auch ein paar Klausuren anstehen …

                  Gestern hatte ich eine Idee, welchen Mittelweg ich hier für meine Zwecke momentan für am besten geeignet halte. Besonders gefällt mir, dass die Vorteile von HTML gespickt mit PHP-Ausgaben mit denen von Platzhaltern und printf() kombiniert werden:

                  Gefällt mir nicht wirklich. Auf den ersten Blick muten die Platzhalter seltsam an, die da so scheinbar motivationslos in der Gegend herumlungern. Erst später kommt ein Funktionsaufruf, bei dem man den Inhalt der Funktion kennen muss, um ihn zu verstehen. (Bekommt man aber hin, nach der ersten allgemeinen Verunsicherung.) Nehmen wir mal an, du hast dich in diese Methode verliebt - klar, ist ja ein Kind deiner eigenen Gedanken - und kommst dann an eine Stelle, an der der HTML-Code-Block größer wird und Platzhalter und deren Ersetzung noch mehr auseinanderbringt. Was machst du dann?

                  Ich muss zugeben, als ich das zum ersten Mal gelesen hatte, wollte ich widersprechen. Muss wohl daran gelegen haben, dass ich mich tatsächlich in die Methode verliebt hatte. Inzwischen sehe ich leider auch einige Nachteile.
                  Dass die Platzhalter „motivationslos“ im HTML stehen halte ich immer noch für unproblematisch - genau genommen war es sogar meine Absicht, das HTML möglichst übersichtlich und frei von zu viel sonstigem Code zu halten. Auch, dass man den Funktionsinhalt kennen muss, um ihn zu verstehen, ist für mich kein allzu schlimmes Kriterium, schließlich muss man jedes System erstmal kennenlernen, bevor man es verwenden sollte.
                  Den Knackpunkt sehe ich wie du aber vor allem in zu großen - und auch in zu kleinen - HTML-Blöcken. Werden sie zu groß, wird unübersichtlich, was durch was ersetzt wird. Sind sie sehr klein, so hat man unverhältnismäßig viel Overhead durch das ob_start(), PHP-Bereich schließen, öffnen, Funktionsaufruf.
                  Ich werde also noch ein bisschen weiter suchen müssen, bis zur perfekten Methode. Vermutlich wird es aber darauf hinauslaufen, situationsabhängig teils mit printf(), teils mit PHP in HTML zu arbeiten. Wenn ich mich nicht täusche war das sogar einer deiner ersten Hinweise hier im Thread …

                  Die Verarbeitung ist die Ermittlung der Daten. Alles was du hier aufgezählt hast, wäre Ausgabelogik.

                  Ok, dann hatte ich vorher etwas missverstanden. So ist es einleuchtend.

                  EVA ist übrigens kein Allheilmittel, sondern stößt auch irgendwann an seine Grenzen. Aber es gibt ja auch noch andere Entwurfsmuster, nach denen man sein Programm strukturieren kann.

                  Ja, ich glaube das ist auch eine der größten Erkenntnisse, die ich hieraus habe. Dass es eben keine absoluten Prinzipien gibt, sondern eher allgemeine Schemata, nach denen man sich richten kann.

                  Schönen Abend noch,

                  Claudius