Rolf B: Wie rufe ich mit URL-Parametern dynamisch Inhalte auf?

Beitrag lesen

problematische Seite

Hallo Samuel,

ein paar Hinweise noch dazu. Beim Nachlesen stelle ich fest, dass das Posting etwas wirr scheint - tatsächlich diskutiere ich diverse Optionen, die man wählen kann und aus denen man auswählen muss.

Es gibt übrigens tatsächlich ein "PHP in Browser" Projekt: https://github.com/oraoto/pib, um <script type="text/php"> ausführen zu können. Was genau er da treibt, scheint intransparent, er erzählt was von Docker und verwendet emscripten, den C/C++ to WASM Compiler. Für Anna Normalprogramiererin ist das aber sicherlich der Overkill, und es auch noch Version 0.04, a.k.a. als experimentell zu sehen.

Wenn ich URL Parameter mit PHP verarbeite, geschieht das am Server. Man müsste also nach Erkennen des Parameters am Server dies tun

<div id="append">
<?php
   include "$module.php";
?>
</div>

oder, schlechter:

<?php
   echo '<div id="append">';
   include "$module.php";
   echo '</div>';
?>
</div>

Um das nutzen zu können, muss jeder Tab-Wechsel über den Server laufen, das ist dann kein Ajax mehr. Es ist aber für den initialen Seitenaufruf interessant, wenn jemand die URL für ein bestimmtes TAB in einem Bookmark hat.

Wenn man mit URL-Parametern arbeiten will, hätte man in der Adresszeile URLs wie

http://.../pages/games/demons-souls/
http://.../pages/games/demons-souls/?game
http://.../pages/games/demons-souls/?savegame

Die vorhandene .htaccess Einstellung führt dazu, dass alle diese Abrufe auf der index.php landen. URLs 2 und 3 mit einem entsprechenden Query String, den PHP dann einliest.

Der Standardfall ist, dass die /games/demons-souls Seite abgerufen wird. Die index.php kann loslaufen und per Default das game.php inkludieren. Wenn der User auf der Seite nun ein anderes Tab klickt, z.B. dieses:

<a href="?savegame">Savegame</a>

steht der Link auf /games/demons-souls/?savegame im Raum. Den kann man mit einem Click-Handler im Javascript abfangen und einen Ajax-Request auf savegame.php machen. Und mittels History-API in die Adresszeile pushen:

window.history.pushState(state, "", new URL(href));

state ist ein beliebiges Objekt, das man zum Hinterlegen von Daten nutzen kann (oder halt ein Leerstring). Der 2. Parameter ist ein Dummy, den gab's mal in der Spec und nun kriegt man ihn nicht mehr weg. Der dritte Parameter ist die URL, die in die Browser-Historie soll und dann auch in der Adresszeile steht, nämlich:

http://.../pages/games/demons-souls/?savegame

Wird die gebookmarked und später aufgerufen, bekommt index.php diesen Parameter als Query-String.

Serverseitig ist index.php?savegame aber nicht so leicht zu erkennen. Denn PHPs $_GET Array geht von URL Parametern in der Form name=value aus. Einen "name only" Parameter findet man zwar in $_GET, aber mit einem NULL Wert. Man kann ihn nur mit isset($_GET["savegame"]) entdecken - und das ist lästig, wenn es eine größere Zahl von Tabs gibt. Aber am sichersten, weil gefakte Parameter kein Unheil anrichten können.

Man könnte auch in $_SERVER['QUERY_STRING'] schauen. Dort würde man "?savegame" finden, könnte das ? entfernen, ein ".php" anhängen und das inkludieren. Whoa - STOP - das ist ein Hackerfest. Vorher ist zu prüfen, ob der so übergebene Modulname auch erlaubt ist, denn man könnte dort auch Namen von php Sourcen einsteuern, gerne auch mit .. und \ angereichert, die niemals nicht ein Tab-Modul sind.

Auf diese Weise hätte man die aktuelle Seite als serverseitigen URL-Parameter "versorgt". Dies ist auch die sicherste Implementierung, denn wenn JavaScript nicht läuft, wird einfach über den Server das richtige Tab aktiviert. Progressive Enhancement at work.

Aber ist das schick, dem Anwender eine URL wie /games/demons-souls/?savegame anzuzeigen? Und wo ich gerade dabei bin - /games/demons-souls/#savegame ist auch nicht wirklich schick. Es hat nur den Vorteil, clientseitig mittels hashchange Event die Navigation steuern zu können.

Die Variante /games/demons-souls/savegame ist eigentlich viel schicker, nur führt die dazu, dass direkt savegame.php abgerufen wird; und das liefert ja nur das Tab aus.

Das kann man unterschiedlich lösen. Der typische Apache-Ansatz ist ein Eingriff in die .htaccess, um mit mod_rewrite aus /games/game/page den Abruf von /games/game/index.php?page zu machen - wobei man sich in dem Fall auch das Leben erleichtern und den Parameter als ?tab=page generieren kann. Dann muss man im PHP nur $_GET['tab'] abfragen.

Also - best practice wäre:

  • die URLs in den Tabs ohne Fragezeichen und ohne # notieren. Also genau so, wie sie jetzt sind.
  • am Server in der .htaccess per mod_rewrite dafür sorgen, dass Tab-Namen als ?tab=... an index.php angehängt werden. Falls irgendein Heini direkt die index.php abruft, kommt halt index.php?tab=index.php an. Ja und? Ist ein ungültiger Tab-Name, und:
  • in index.php den tab-Parameter verarbeiten und auf gültige Tab-Namen validieren. Für ungültige oder fehlende Tabnamen das Default-Tab includen
  • als progressive enhancement einen click-Handler auf die Tabs legen, der die Page per Ajax holt und per pushState so tut, als wär's über den Server gelaufen.

Rolf

--
sumpsi - posui - obstruxi
0 75

Wie rufe ich mit URL-Parametern dynamisch Inhalte auf?

borisbaer
  • url
  1. 0
    TS
    • ajax
    • client-server
    • url
    1. 0
      borisbaer
  2. 0
    dedlfix
    1. 0
      borisbaer
      1. 0
        Samuel fiedler
        • javascript
        • php
        • url
        1. 0
          Der Martin
          • php
          • url
        2. 0
          Rolf B
          1. 0
            borisbaer
            1. 0
              Rolf B
              1. 0
                borisbaer
                1. 0
                  Rolf B
                  1. 0
                    borisbaer
                    1. 0
                      Rolf B
                      1. 0
                        borisbaer
                        1. 0
                          tk
                          • php
                          • url
                          1. 0
                            borisbaer
                        2. 0
                          Rolf B
                          1. 0
                            borisbaer
                            1. 0
                              Rolf B
                      2. 1
                        tk
                        • php
                        • url
                        1. 0
                          Rolf B
                          1. 0
                            borisbaer
                            1. 0
                              Der Martin
                              1. 0
                                Rolf B
                                1. 0
                                  borisbaer
                                  1. 0
                                    Rolf B
                                    1. 0
                                      borisbaer
                                      1. 0
                                        Rolf B
                                        1. 0
                                          borisbaer
                                          1. 0
                                            Rolf B
                                            1. 0
                                              borisbaer
                                            2. 0
                                              borisbaer
                                              1. 0
                                                Rolf B
                                                1. 0
                                                  borisbaer
                                                  1. 0
                                                    Rolf B
                                                    1. 0
                                                      borisbaer
                                                      1. 0
                                                        Rolf B
                                                        1. 0
                                                          borisbaer
                                                          1. 0
                                                            borisbaer
                                                            1. 0
                                                              Rolf B
                                                              1. 0
                                                                borisbaer
                                                                1. 0
                                                                  Rolf B
                                                                  1. 0
                                                                    borisbaer
                                                            2. 0
                                                              Rolf B
                                                              1. 0
                                                                borisbaer
                                                                1. 0
                                                                  Rolf B
                                                                  1. 0
                                                                    borisbaer
                                                                    1. 0
                                                                      Rolf B
                                                                      1. 0
                                                                        borisbaer
                                                                        1. 0
                                                                          Rolf B
                                                                          1. 0
                                                                            klawischnigg
                                                                            1. 0
                                                                              Rolf B
                                                                              1. 0
                                                                                klawischnigg
                                                                                1. 0
                                                                                  Rolf B
                                                                          2. 1
                                                                            borisbaer
                                2. 0
                                  Der Martin
                                  1. 0
                                    Rolf B
                                    1. 0
                                      Der Martin
                                      1. 0
                                        Rolf B
                                        1. 0
                                          Der Martin
                                          1. 0
                                            Rolf B
                            2. 0
                              Tabellenkalk
                              1. 0
                                borisbaer
        3. 0
          borisbaer
  3. 0
    Rolf B
    1. 0
      borisbaer
      1. 0
        Rolf B
        1. 0
          borisbaer
          1. 0
            Rolf B
            1. 0
              borisbaer
              1. 1
                Rolf B
                1. 0
                  borisbaer
                  1. 0
                    Rolf B
                    1. 0
                      borisbaer