• [PHP] Weiterlesen-Link

    Jeder kennt es, keiner weiß wie es geht. Zumindest die Anfänger von MySql und PHP versuchen den schwierigsten und kompliziertesten Weg einen "Weiterlesen..." Link zu realisieren.
    Hier möchte ich euch nun eine rudimentäre, einfache Art veranschaulichen.

    Als Erstes wird eine config.php erstellt, die die benötigte SQL-Tabelle erstellt.
    Das kann man, wenn vorhanden, natürlich auch mit PHPmyAdmin machen.

    Zuerst die Zugriffsdaten einbinden und die Verbindung herstellen:
    PHP-Code:
    <?php
        
    require('mysql.inc.php');
        
    $dz mysql_connect($host$user$pass);
        
    mysql_select_db($database$dz);
    ?>
    Mit require wird eine weitere PHP-Datei eingebunden, die Benutzername, Kennwort etc.enthält. Wird später noch genauer erklärt. Die Datei sollte die Endung php haben, damit man sie nicht im Browser anschauen kann (Sicherheitsrisiko).

    Dann erstellen wir mal die Tabelle:
    PHP-Code:
    mysql_query
    ("
        CREATE TABLE substring_test
        (
            id int(255) auto_increment,
            header varchar(255),
            text text,
            PRIMARY KEY (id)
        )
        ENGINE = MyIsam;
    "
    ) or DIE(mysql_error()); //Gibt eine Fehlermeldung aus, wenn die Tabelle bereits besteht 
    Hier der vollständige Code der config.php:
    PHP-Code:
    <?php
        
    require('mysql.inc.php');
        
    $dz mysql_connect($host$user$pass);
        
    mysql_select_db($database$dz);
        
    mysql_query
        
    ("
            CREATE TABLE substring_test(
                id int(255) auto_increment,
                header varchar(255),
                text text,
                PRIMARY KEY (id)
                )
            ENGINE = MyIsam;
        "
    ) or DIE(mysql_error());
    ?>
    Und jetzt noch die mysql.inc.php:
    PHP-Code:
    <?php
        $host 
    "localhost";
        
    $user "root";
        
    $pass "";
        
    $database "test";
    ?>
    Die Angaben müssen für eure Datenbank angepasst werden.

    Soweit, sogut! Die Tabelle sollte erstellt sein. Nun fügt ihr Daten in die Tabelle ein (Überschrift/Inhalt), entweder via PHPmyAdmin oder Formular. Zu diesem Thema möchte ich hier nichts weiter anfügen, da es euch vermutlich klar ist, wie das funktioniert.


    Beginnen wir mit dem Script zur Abfrage der Daten!

    Am Anfang die Fehlerunterdrückung/Fehleranzeige:
    Während der Entwicklung sollte die am Besten so ausschauen:
    PHP-Code:
    error_reportingE_ALL E_STRICT );
    ini_set'display_errors'1); 
    Wenn das Skript dann fertig ist, auf das umändern,
    um dem Benutzer eventuelle Warnungen zu ersparen:
    PHP-Code:
    error_reporting(0); 
    Als nächstes kommen wieder die Zugriffsdaten.
    PHP-Code:
    require('mysql.inc.php'); 
    Indem sie in die mysql.inc.php ausgelagert sind, muss man sie bei Bedarf nur an einer Stelle ändern, statt in jeder PHP-Datei.

    Nun brauchen wir Übergabeparameter, damit das Script weiß, welcher Eintrag in der Datenbank gemeint ist. Das machen wir mit einer einfachen $_GET Variable.
    PHP-Code:
    $id $_GET['id']; 
    Das das nun eine nicht unbedingt sichere Art ist Daten zu übergeben, werden wir die übergebenen Variablen überprüfen.
    Dazu verwenden wir eine if Anweisung:
    PHP-Code:
    if (isset($_GET['id']) && (!is_numeric($_GET['id'])))
    //Wenn die id, falls übergeben, keine Nummer ist...
        
    echo "Kein Eintrag!<br>";
        exit; 
    //...wird das Script an der Stelle abgebrochen

    Okay, so sollte euer Script bisher aussehen:
    PHP-Code:
    <?php
        error_reporting
    E_ALL E_STRICT );
        
    ini_set'display_errors'1);
        require(
    'mysql.inc.php');
        if (isset(
    $_GET['id']) && (!is_numeric($_GET['id'])))
        {
            echo 
    "Kein Eintrag!<br>";
            exit;
        }
    ?>
    Bevor es nun weitergeht, hier ein wenig HTML Code welcher nach unseren bisherigen Programmzeilen hinkommt:
    HTML-Code:
    <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
    <html xmlns="http://www.w3.org/1999/xhtml">
      <head>
        <title>Untitled Document</title>
      </head>
      <body>
    Für mich perönlich ist das auch immer eine gute Orientierungshilfe,
    wo der HTML-formatierte Teil beginnt

    Ab jetzt muss unterschieden werden, ob eine id übergeben wurde.
    Wenn nicht, werden alle Überschriften mit dem ersten Textteil ausgegeben,
    hier die jeweils ersten 50 Zeichen. Dazu kommt immer der Mehr-Link,
    der auf die selbe PHP-Datei leitet, allerdings dann mit id.
    PHP-Code:
    if(!isset($_GET['id']))
    {
        
    $query "SELECT * FROM substring_test";
        
    $sql mysql_query($query);
        while(
    $ds mysql_fetch_object($sql))
        {
        echo 
    "<h3>" $ds->header "</h3>" substr($ds->text,0,50) .
                
    "<a href='" $_SERVER['PHP_SELF'] . "?id=" $ds->id "'>[MEHR...]</a><br>";
        }

    Eine grundlegende Funktion des Scripts is "substr()".
    Diese Funktion kürzt einen Eintrag nach belieben.
    PHP-Code:
    substr('DEINTEXT'start_beiende_bei)
    //start_bei: z.B. 0 - ab Beginn des Eintrags
    //ende_bei: z.B. 50 - 50 Zeichen nehmen 
    Ok. Das wars, oder? Nein, natürlich fehlt noch ein wenig Code für die punktuelle Abfrage.

    Ihr erinnert euch an den "MEHR..." Link?
    PHP-Code:
    "<a href='" $_SERVER['PHP_SELF'] . "?id=" $ds->id "'>[MEHR...]</a><br>" 
    Hier übergeben wir die "id" aus der Datenbank an den $_GET Parameter ganz oben im Script.
    Jetzt also der Fall, wenn eine id übergeben wurde:
    PHP-Code:
    else //if !isset...
    {
        
    $query "SELECT * FROM substring_test WHERE id = " trim($_GET['id']);
        
    $sql mysql_query($query);
        while(
    $ds mysql_fetch_object($sql))
        {
        echo 
    "<h3>" $ds->header "</h3>" $ds->text;
        echo 
    "<br><a href='javascript:history.back()'>Zur&uuml;ck</a>";
        exit;
        }

    Hier nochmal der gesamte Code:
    PHP-Code:
    <?php
        error_reporting
    E_ALL E_STRICT );
        
    ini_set'display_errors'1);
        require(
    'mysql.inc.php');
        if (isset(
    $_GET['id']) && (!is_numeric($_GET['id'])))
        {
            echo 
    "Kein Eintrag!<br>";
            exit;
        }
    ?>

    <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
    <html xmlns="http://www.w3.org/1999/xhtml">
      <head>
        <title>Untitled Document</title>
      </head>
      <body>

    <?php
        
    if(!isset($_GET['id']))
        {
            
    $query "SELECT * FROM substring_test";
            
    $sql mysql_query($query);
            while(
    $ds mysql_fetch_object($sql))
            {
            echo 
    "<h3>" $ds->header "</h3>" substr($ds->text,0,50) .
                    
    "<a href='" $_SERVER['PHP_SELF'] . "?id=" $ds->id "'>[MEHR...]</a><br>";
            }
        }
        else
        {
            
    $query "SELECT * FROM substring_test WHERE id = " trim($_GET['id']);
            
    $sql mysql_query($query);
            while(
    $ds mysql_fetch_object($sql))
            {
            echo 
    "<h3>" $ds->header "</h3>" $ds->text;
            echo 
    "<br><a href='javascript:history.back()'>Zur&uuml;ck</a>";
            exit;
            }
        }
    ?>

      </body>
    </html>
    Zum Schluss bleibt mir nur ein großes DANKESCHÖN an das alle von Tutorials.de zu auszusprechen. Ich habe so einiges gelernt und gebe dies nun weiter!

    Bis bald

    Euer Newcomer1!
     


     
    Kommentare 7 Kommentare
    1. Avatar von Bratkartoffel
      Bratkartoffel -
      Hi,

      grundstzlich ein schönes How-To, nur hast du da ne SQL-Injection Lücke drin.

      PHP-Code:
      $query "SELECT * FROM substring_test WHERE id = " trim($_GET['id']); 
      Bitte erscape die id, zum Beispiel so:
      PHP-Code:
      $query "SELECT * FROM substring_test WHERE id = " intval($_GET['id']); 
      Gruß
      BK
    1. Avatar von sheel
      sheel -
      Bratkartoffel,
      PHP-Code:
          if (isset($_GET['id']) && (!is_numeric($_GET['id'])))
          {
              echo 
      "Kein Eintrag!<br>";
              exit;
          } 
      An unerlaubten Zeichen sollte es nicht scheitern.
    1. Avatar von Bratkartoffel
      Bratkartoffel -
      Autsch, das hab ich überlesen :/
      Frage mich nur wie ich da drüber gescrollt habe, im Text steht sogar ein Satz zur Erklärung dabei.
    1. Avatar von Yaslaw
      Yaslaw -
      Ich bin etwas erstaunt. Ich dachte es geht um das Thema 'Php Weiterlesen-Link'. Doch dieses Thema nimmt etwa 2 Zeilen des ganzen Tutorials ein. Der Rest ist DB-Grundwissen und HTML-Grundwissen. Nicht das dies schlecht wäre, es ist sogar gut beschreiben. Doch gehe ich davon aus, dass jemand der Weiterlesen-Link umsetzen will bereits eine DB mit seinen Texten drin hat und auch bereits ein HTML-Layout besitzt.

      Mehr hätte mich interessiert, wie ich verhindern kann, dass nach 50 Zeichen einfach Wörter zerhackt werden...
      Deine Code substr($ds->text,0,50) hackt einfach nach 50 Zeichen ab. Egal was dort steht
      Aus dem Text:
      'Bei der Explosion einer Bombe in Teheran ist iranischen Medienberichten zufolge Mostafa Ahmadi Roshan – ein im Atombereich tätiger Universitätsprofessor – getötet worden. Zwei weitere Mitfahrer wurden bei dem Anschlag verletzt.'
      wird einfach:
      'Bei der Explosion einer Bombe in Teheran ist irani'
      Dies ist nicht gerade sehr hübsch, dass mitten im Wort geschnitten wird.

      Es gibt einfache Möglichkeiten einen wordCut zu realisieren, so dass mindestens die Wörter fertig sind.

      PHP-Code:
      //Testdaten. Werden normalerweise aus einer DB geladen
      $id 15;
      $text 'Bei der Explosion einer Bombe in Teheran ist iranischen Medienberichten zufolge Mostafa Ahmadi Roshan – ein im Atombereich tätiger Universitätsprofessor – getötet worden. Zwei weitere Mitfahrer wurden bei dem Anschlag verletzt. ';

      //Pattern für den Weiterführenlink
      $linkPattern "<a href='{$_SERVER['SCRIPT_NAME']}?id=%d'><i>[MEHR...]</i></a>";

      //Gekürtzten Text mit Weiterführenlink
      echo wordCut($text,  50sprintf($linkPattern$id));

      /**
       * wordCut()
       * Schneidet einen Text nach Anzahl Zeichen ab und erweitert mit einem anderen String
       * @url = http://wiki.yaslaw.info/wikka/PhpWordCut
       * @param String            $text
       * @param Number            $maxlen
       * @param optional String   $suffix
       * @return String
       */
      function wordCut($text$maxlen 30$suffix ''){
          
      define('C_DELIMITER''#wordCut#');
          
      // Falls der Text selber schon genug kurz ist, diesen unverändert zurückgeben
          
      if(strlen($text)<$maxlen) return $text;
          
      // Mittels wordwrap den String unterteilen und danach den ersten Teil davon extrahieren
          
      $trunc array_shift(explode(C_DELIMITERwordwrap($text$maxlenC_DELIMITERtrue)));
          return 
      trim("{$trunc} {$suffix}");    

      Gibt aus.
      HTML-Code:
      Bei der Explosion einer Bombe in Teheran ist <a href='/test/test2.php?id=15'><i>[MEHR...]</i></a>
    1. Avatar von Napofis
      Napofis -
      Was passiert wenn die ID -3 ist oder einfach nicht mehr existiert? (Suchmaschinen und gelöschte Beiträge)

      Code sql:
      1
      
      SELECT * FROM substring_test WHERE id = " . trim($_GET['id']
      Eine Stringfunktion auf Integer? Wieso trim() überhaupt? Aber das schlimmste SELECT * ein typischer Anfängerfehler.
      Code sql:
      1
      
      SELECT * FROM substring_test
      Der Text kann nach dem verwendeten Datentyp bis zu 65.535 Zeichen lang werden, in deinem Beispiel werden aber nur 50 gebraucht. Bis zu 65.485 Zeichen (pro Datensatz) werden unnötig mitgeschickt.

      PHP-Code:
      echo "Kein Eintrag!<br>";
      exit; 
      Die Ausgabe Erfolgt vor dem HTML-Markup, das Skript wird anschließend einfach abgewürgt.


      @Yaslaw: \b
    1. Avatar von byf-ferdy
      byf-ferdy -
      Du solltest auf PHP_SELF verzichten, da es hier zu einer Cross-Site-Scripting-Sicherheitslücke kommt
      (Quelle: http://blog.oncode.info/2008/05/07/p...scripting-xss/)

      mfg
      FRED
    1. Avatar von Yaslaw
      Yaslaw -
      Thx Byf_ferdy
      Habs in meinem Beispiel angepasst