 |
13.03.2006, 18:01
| Nach oben
#1 | | Martin Breuer
Registriert seit: 17.08.2005 Ort: Berlin
Beiträge: 1.642
| [PHP] Fremde Webseiten auslesen Fremde Webseiten mit PHP auslesen und analysieren Vorwort: Die Anwendung dieser Art der Datenbeschaffung sollte _immer_ mit dem Betreiber der fremden Seite abgesprochen werden oder nur im Rahmen einer Lizenz, falls vorhanden, durchgeführt werden. Ihr solltet euch gegebenenfalls eine rechtliche Beratung zu diesem Thema einholen.
Dieses Tutorial befasst sich mit dem Auslesen von Inhalten fremder Webseiten. Ziel ist es, die Wissensgrundlagen zu schaffen um von Partnerseiten bestimmte Informationen zu erhalten. Das Beispiel in diesem Tutorial wird den Tutorialbereich des Forums durchsuchen und eine Linkliste der Tutorien sowie ein paar weitere kleiner Informationen zusammenstellen.
Für das Kapitel 3 sollten euch Klassen und Methoden nicht fremd sein. Ist dem nicht so, dann bitte erst hier darüber informieren. Kapitel:- Auslesen einer fremden Webseite
- Filtern des gewünschten Bereichs
- Erstellen einer Parserklasse für vBulletin-Foren
Geändert von Jann Hendrik (28.05.2008 um 19:53 Uhr).
Grund: link aktualisiert
|
| |
14.03.2006, 14:03
| Nach oben
#2 | | Martin Breuer
Registriert seit: 17.08.2005 Ort: Berlin
Beiträge: 1.642
| 1. Auslesen einer fremden Webseite
Das Auslesen einer fremden Webseite ist genauso leicht wie das Öffnen einer Datei. Wir benötigen dafür die Funktionen fopen() und fclose(). PHP-Code: <?php $filestream = fopen("http://forum.developers-guide.net", "r"); while(!feof($filestream)) { $buffer = fgets($filestream, 4096); echo $buffer; } fclose($filestream); ?> Wer dieses Beispiel testet wird feststellen, dass nun das Forum von Developers-Guide.net fast komplett übertragen wurde. Einzige Mängel sind fehlende Bilder, was allerdings daran liegt, dass die Pfadangaben für die Bilder meistens relativ sind und daher nun ins Leere verweisen.
Geändert von WarrenFaith (14.03.2006 um 19:42 Uhr).
|
| |
14.03.2006, 14:04
| Nach oben
#3 | | Martin Breuer
Registriert seit: 17.08.2005 Ort: Berlin
Beiträge: 1.642
| 2. Filtern des gewünschten Bereichs
Noch einfacher dagegen ist das Arbeiten mit der Funktion file_get_contents() welche den Inhalt der Webseite in einem String zurückgibt. Damit ist der Inhalt der Seite leicht zu durchsuchen.
Unsere erste Aufgabe wird es sein, alle Links aus dem Unterforum "Tutorials" herauszufiltern. PHP-Code: <?php $host = "http://forum.developers-guide.net/forumdisplay.php?f=9"; $filestring = file_get_contents($host); $startpos = 0; while($pos = strpos($filestring, "<a href", $startpos)) { $string = substr($filestring, $pos, strpos($filestring, "</a>", $pos + 1) - $pos); echo $string."</br>"; $startpos = $pos + 1; } ?> Wie wir nun sehen, können wir mit dem Ergebnis nicht zufrieden sein, denn wir haben nicht nur die Threads, sondern auch jeglichen Navigationslink mit dabei.
Um nur die Thread-Links herauszufiltern nutzen wir den HTML-Code des Forums und können feststellen, dass alle Thread-Links eine eindeutige ID haben: Code: id="thread_title_xxxx"
Daher erweitern wir den Filter um die Überprüfung, ob der String "thread_title_" im Linktag vorkommt. PHP-Code: <?php $host = "http://forum.developers-guide.net/forumdisplay.php?f=9"; $filestring = file_get_contents($host); $startpos = 0; while($pos = strpos($filestring, "<a href", $startpos)) { $string = substr($filestring, $pos, strpos($filestring, "</a>", $pos + 1) - $pos); // Wenn 'id="thread_title_' in $string ist, gib den Link aus if(stristr($string, 'id="thread_title_')) { echo $string."</br>"; } $startpos = $pos + 1; } ?>
Geändert von WarrenFaith (14.03.2006 um 23:14 Uhr).
|
| |
14.03.2006, 15:59
| Nach oben
#4 | | Martin Breuer
Registriert seit: 17.08.2005 Ort: Berlin
Beiträge: 1.642
| 3. Erstellen einer Parserklasse für vBulletin-Foren
Im Idealfall einigt man sich mit dem Webmaster der fremden Seite, dass dieser ein paar Tags in HTML-Kommentaren versteckt oder die erwünschten Informationen direkt in einem Kommentarblock am Anfang einer Seite anbietet. Damit sind aufwendige Parser unnötig und man muss den Parser nicht umschreiben, sobald sich die Struktur der Webseite deutlich ändert.
Die vBulletin-Foren haben glücklicherweise eindeutige CSS-Klassen oder ID-Bezeichnungen für bestimmte Elemente, an dene man sich im Quellcode "durchhangeln" kann. So ist z.B. die Seitenanzahl in einem Layer, welches eine im Quellcode einmalige CSS-Klassen und Style-Attributkombination besitzt.
Das nachfolgende Beispiel ist eine Parserklasse, welche die externe Durchsuchung von vBulletin-Foren ermöglicht. Die Klasse dient als Aussicht auf Möglichkeiten des durchsuchens fremder Seiten. Ich empfehle daher diese nur als Ideenstütze zu nutzen und die eigenen Fähigkeiten selbst umzusetzen oder die Klasse an die eigenen Bedürfnisse anzupassen.
parser.class.php: PHP-Code: <?php class Parser { /** * String mit dem Inhalt der Webseite */ private $filestring = '';
/** * URL des Hosts */ private $host = '';
/** * Verfeinerung des Hosts * z.B 'forumdisplay.php?f=9' */ private $subdetails = '';
/** * Seitenanzahl des Forumteils */ private $seitenanzahl = 1;
/** * Seitennummer, auf der der Parser sich * gerade befindet */ private $aktuelle_seite = 1;
/** * Die Linkliste besitzt alle vorgekommenen * Threadtitel */ private $linkliste = array();
/** * Liste zum speichern aller Threads und * deren Authoren */ private $link = array("Link" => array(), "Author" => array());
/** * Soll die Suche über alle vorhandenen * Seiten ausgedehnt werden */ private $pages = true;
/** * Konstruktor der Klasse * Die fremde Webseite wird beim inistanzieren der Klasse * geparst, aber noch nicht ausgegeben * * Hier werden die benoetigten Klassenvariablen belegt * und einige Methoden aufgerufen * * @param - $host - String - URL des Hosts * @param - $subdetails - String - Direkte URL-Anweisungen * @param - $start_tag - String - Starttag für Seitenanzahl * @param - $suchstring - String - Suchstring für Seitenanzahl * @param - $end_tag - String - Endtag für Seitenanzahl * @param - $link_ident - String - Identifikation der wichtigen Links * @param - $start_tag_author - String - Starttag zur Authoridentifikation * @param - (boolean) Ob alle Seiten durchsucht werden sollen (optional) */ public function __construct($host, $subdetails, $start_tag, $suchstring, $end_tag, $link_ident, $start_tag_author, $pages = false) { $this->host = $host; $this->subdetails = $subdetails; $this->pages = $pages; $this->start_tag_author = $start_tag_author; $this->loadWebsite(); $this->getSeitenanzahl($start_tag, $suchstring, $end_tag); $this->parse($link_ident); }
/** * Die fremde Webseite wird geladen und als String der * Klassenvariable $filestring zugewiesen */ private function loadWebsite() { if($this->pages) { $str_page = '&:page='.$this->aktuelle_seite; } else { $str_page = ''; } $this->filestring = file_get_contents($this->host.$this->subdetails.$str_page); }
/** * Die Seitenzahl wird anhand eines frei definierbaren Start- und Endtags * sowie eines Suchstrings, der vor der Seitenzahl enden muss, rausgefiltert */ private function getSeitenanzahl($start_tag, $suchstring, $end_tag) { $pos = strpos($this->filestring, $start_tag, 1); $string = substr($this->filestring, $pos, 1028); $seitenende = strpos($string, $end_tag, 0); $startpos = strpos($string, $suchstring, 0) + strlen($suchstring); $endpos = $seitenende - $startpos; $this->seitenanzahl = substr($string, $startpos, $endpos); }
/** * Hier wird der übergebene String zu einem Link zusammengesetzt. * Durch das hinzufügen des Hosts wird aus jedem relativen Pfad, * ein absoluter und die Links führen sofort zum richtigen Ziel */ private function setLink($string) { $link = substr($string, 0, 9); $link .= $this->host; $link .= substr($string, 9, strlen($string)); $link .= "</a>"; return $link; }
/** * Die gefundenen Links werden auf das vorhandensein einer * $link_ident überprüft und beim vorfinden in die Linklisten * aufgenommen */ private function getLinkdetails($string, $link_ident, $pos) { if(stristr($string, $link_ident)) { $gefunden = true; $linktext = substr($string, strpos($string, '">') + 2, strlen($string) - (strpos($string, '">') - 2)); foreach($this->linkliste as $value) { if($value == $linktext) { $gefunden = false; } } if($gefunden) { $this->linkliste[] = $linktext; $this->link["Link"][] = $this->setLink($string); $this->link["Author"][] = $this->getAuthor($pos); } } }
/** * Die eigentliche Funktion, welche den Filestring nach Links durchsucht * und bei Treffern dann getLinkdetails() aufruft. * Die komplette Webseite samt Unterseiten wird durchsucht */ private function parse($link_ident) { while($this->aktuelle_seite <= $this->seitenanzahl) { $this->loadWebsite($this->pages); $startpos = 0; while($pos = strpos($this->filestring, "<a href", $startpos)) { $string = substr($this->filestring, $pos, strpos($this->filestring, "</a>", $pos + 1) - $pos); $this->getLinkdetails($string, $link_ident, $pos); $startpos = $pos + 1; } $this->aktuelle_seite++; } }
/** * Dient der veranschaulichten Darstellung der gesammelten Links und der Authoren */ public function showLinks() { $html = ''; for($i = 0; $i < sizeof($this->link['Link']); $i++) { $html .= $this->link['Link'][$i]." | Author: ".$this->link['Author'][$i]."<br/>\n"; } return $html; }
/** * Die Authoren der ermittelten Links werden gesucht */ private function getAuthor($pos) { $pos_member = strpos($this->filestring, $this->start_tag_author, $pos); // Benutzernamen rausfiltern $laenge = strpos($this->filestring, "</span>", $pos_member) - strpos($this->filestring, '>', $pos_member) - 1; $startpos = (strpos($this->filestring, '>', $pos_member)+1); return substr($this->filestring, $startpos, $laenge); } } ?> Die index.php könnte dann so aussehen: PHP-Code: <?php error_reporting(E_ALL ^ E_STRICT); // Includieren der Klassendatei require_once "parser.class.php";
/** * Instanziieren der Parserklasse * * @param - URL des Hosts * @param - Direkte URL-Anweisungen * @param - Starttag für Seitenanzahl * @param - Suchstring für Seitenanzahl * @param - Endtag für Seitenanzahl * @param - Identifikation der wichtigen Links * @param - Starttag zur Authoridentifikation * @param - (boolean) Ob alle Seiten durchsucht werden sollen (optional) */ $Parser = new Parser('http://forum.developers-guide.net/', 'forumdisplay.php?f=9', 'class="vbmenu_control" style="font-weight:normal"', ' von ', '</td>', 'id="thread_title_', 'style="cursor:pointer" onclick="window.open(\'member.php', true);
// Ausgabe der Linksammlung echo $Parser->showLinks(); ?>
Geändert von WarrenFaith (08.02.2007 um 09:47 Uhr).
|
| | |
Aktive Benutzer in diesem Thema: 1 (Registrierte Benutzer: 0, Gäste: 1) | | | | Themen-Optionen | Thema durchsuchen | | | |
Forumregeln
| Es ist dir nicht erlaubt, neue Themen zu verfassen. Es ist dir nicht erlaubt, auf Beiträge zu antworten. Es ist dir nicht erlaubt, Anhänge hochzuladen. Es ist dir nicht erlaubt, deine Beiträge zu bearbeiten. HTML-Code ist aus. | | | Alle Zeitangaben in WEZ +2. Es ist jetzt 00:35 Uhr.
|