regex pattern mit zwischen Zeichen = egal
lima-city → Forum → Programmiersprachen → PHP, MySQL & .htaccess
array
ausgabe
auslese
beschreibung
buffer
code
gemischte zeichen
header
http
info
klicken
machen
match
speichern
status
text
treffer
type
url
versuch
-
Hallo
ich möchte definierte Werte aus TAGs (HTML) auslesen
Bsispiel:
preg_match_all ("/<meta name=\"description\" content=\"(.*)\"/iUs", $html, $matches); $descritpion = $matches[1][0];
das klappt auch meistens, aber nicht wenn zwischen drin mehrehre Leerzeichen sind,
was vorkommt, wenn jemand seinen Quellcode besonders "schön" formatiert hat
Beispiel:
... <meta name="description" content="Hier steht die Beschreibung zur Homepage als Text"> <meta name="keywords" content="Wote, durch, Komma, getrennt"> <meta name="author" content="Donald Duck"> ...
also hier sind vor
unterschiedlich viele Leerzeichen ...content=
... deshalb greift mein Parrtern nicht mehr ... der erwartet nur 1 Leerzeichen
Wie muss ich den Pattern ändern, damit es egal ist, wieviele (Leer-)Zeichen vor
sind ?content=
noch ein Beispiel:
$html = '<a href="ziel.php" rel="nofollow" target="_self" title="Weiter gehts">hier klicken</a>';
Wenn ich jetzt mit preg_match_all den Wert für href= und den Link-Text auslesen will,
weiß ich ja vorher nicht, was alles zwischen
undhref="..."
steht,>hier klicken</a>
diesesmal sind es nicht nur Leerzeichen, sondern gemischte Zeichen (Text) dazwischen
Wie muss ein Pattern aussehen, der Wert für href= und den Link-Text auslesen kann,
wobei egal sein soll, was noch so an "Text" (gemischte Zeichen) dazwischen steht.
ich hoffe Ihr könnt mir helfen :=)
PS: sorry für den "komischen" Beitrags-Titel ... regex pattern mit zwischen Zeichen = egal
wenn jemand was besseres als Überschrift einfällt, gerne dazu schreiben :)
Beitrag zuletzt geändert: 6.3.2013 15:04:55 von webfav -
Diskutiere mit und stelle Fragen: Jetzt kostenlos anmelden!
lima-city: Gratis werbefreier Webspace für deine eigene Homepage
-
Das funktioniert mit
\s+
Vollständiger Code:<?php $html = <<< ETX <meta name="description" content="Hier steht die Beschreibung zur Homepage als Text"> <meta name="keywords" content="Wote, durch, Komma, getrennt"> <meta name="author" content="Donald Duck"> ETX; $pattern = '/<meta name="(.+)"\\s+content="(.*)"/iU'; preg_match_all($pattern, $html, $matches); header('content-type: text/plain'); print_r($matches);
Ausgabe:Array ( [0] => Array ( [0] => <meta name="description" content="Hier steht die Beschreibung zur Homepage als Text" [1] => <meta name="keywords" content="Wote, durch, Komma, getrennt" [2] => <meta name="author" content="Donald Duck" ) [1] => Array ( [0] => description [1] => keywords [2] => author ) [2] => Array ( [0] => Hier steht die Beschreibung zur Homepage als Text [1] => Wote, durch, Komma, getrennt [2] => Donald Duck ) )
-
hach, da war hackyourlife mal wieder ne minute schneller...
...bedenke noch das manchmal die attribute der meta-tags nicht in " stehen sondern in ' oder gar ganz ohne anführungszeichen...da wäre das pattern dann so denke ich:
<?php $pattern = '/<meta name=["\']?(.+)["\']?\\s+content=["\']?(.*)["\']?/iU'; ?>
(oder kann man quantoren nur nach ausdrücken schrieben und nicht nach zeichenklassen ? versuch macht kluch...) -
Danke, das funktioniert ...
preg_match_all ('/<title>(.*)<\/title>/iU', $html, $matches1); preg_match_all ('/<meta name="description"\\s+content="(.*)"/iU', $html, $matches2); preg_match_all ('/<meta name="keywords"\\s+content="(.*)"/iU', $html, $matches3); ...
aber wenn ich die Variante für double-/single-quote oder ohne nehme,
dann bekomme ich aus den <meta> TAGs kein Ergebnis mehr ??
preg_match_all ('/<title>(.*)<\/title>/iU', $html, $matches1); preg_match_all ('/<meta name=["\']?description["\']?\\s+content=["\']?(.*)["\']?/iU', $html, $matches2); preg_match_all ('/<meta name=["\']?keywords["\']?\\s+content=["\']?(.*)["\']?/iU', $html, $matches3); ...
bei diesem zweiten Code mit
anstatt["\']?
geht leider"
nur der <title> TAG, aber die <meta> TAGs nicht ?!
... sollte doch richtig escaped sein ? ...
PS: ich will bewusst nur bestimmte META-Tags auslesen (title, description, keywords, author)
denn ich denke, wenn jemand viele weitere als diese definiert hat,
dann braucht preg_match_all() auch deutlich mehr Performance ?! ... oder nicht ?
und die PHP-Funktion: get_meta_tags() wäre auch eine Alternative für <meta> TAGs,
aber ich habe gelesen, damit ist es viel langsamer als mit Pattern und preg_match_all ...
Beitrag zuletzt geändert: 6.3.2013 15:49:05 von webfav -
Versuch es mal so:
<?php $html = <<< ETX <meta name="description" content="Hier steht die Beschreibung zur Homepage als Text"> <meta name="keywords" content="Wote, durch, Komma, getrennt"> <meta name="author" content="Donald Duck"> <meta name='author' content="Donald Duck"> <meta name='author' content='Donald Duck'> <meta name=author content='Donald Duck'> <meta name=author content=Donald> ETX; $pattern = '/<meta name=(["\']?)(.+?)\\1\\s+content=(["\']?)(.+?)\\3[ >]/i'; preg_match_all($pattern, $html, $matches); header('content-type: text/plain'); print_r($matches);
-
aehhm ... ok ... interessant ... :)
anstatt nocmal
macht Du einfach(["\']?)
... also erstern Treffer wieder anwenden ??//1
das gleiche mit dem 3. Treffer .... so so ... :) ... was nicht alles geht ^^
also habe ich dann den Wert für name="..." im matches[2] ... und content="..." dann in matches[4]
habe den Pattern am Ende noch um das / Zeiche ergänzt (escaped mit Backslash)
$pattern = '/<meta name=(["\']?)(.+?)\\1\\s+content=(["\']?)(.+?)\\3[ \/>]/i';
wegen XHTML Code ... wo <meta .... .... /> wieder "geschlossen" wird .. wie bei <br />
für den Fall dass kein Leerzeichen vor dem abschließenen /> steht (siehe folgendes in 3. Zeile)
<meta name='description' content="Donald Duck ist nicht der Osterhase"> <meta name="description" content='Donald Duck ist nicht der Osterhase' /> <meta name='description' content=Donald Duck ist nicht der Osterhase/>
damit ich nur die zwei META-TAGS description und keywords bekomme mache ich dann so
$pattern2 = '/<meta name=(["\']?)(description|keywords)\\1\\s+content=(["\']?)(.+?)\\3[ \/>]/i';
dann habe ich "nur" die zwei Meta-TAGs .... :=)
......... hier der bisher gebastelte Code: http://pastebin.com/KAWcbn8A
EDIT: (das Speichern ist noch nicht dabei, nur eine DEBUG-Ausgabe der $_POST Werte)
Datei: GetMeta1.php
<?php // --------------------------------------------------------------- header("Content-Type: text/html; charset=utf-8"); error_reporting(E_ALL); ini_set("display_errors", 1); ## $myscript = 'GetMeta1.php'; $myscript = $_SERVER['PHP_SELF']; // ------------------------------------------------------------ print "<br />\n"; print "<br /> --- <a href=\"".$myscript."\">HOME</a> (RESET) --- \n"; print "<br />\n"; // ---------------------------------------------------- if (!empty($_REQUEST['url'])) { $go_url = trim(chop($_REQUEST['url'])); $go_url = str_replace('http://http://','http://',$go_url); if (strpos($go_url,'http://') === FALSE && strpos($go_url,'https://') === FALSE) { $go_url = 'http://'.$go_url; } // ----- to-do: filters and/or escape url string ----- } else { $go_url = 'http://'; } // ---------------------------------------------------- function pingSite($url) { $fp = curl_init($url); curl_setopt($fp,CURLOPT_TIMEOUT,10); curl_setopt($fp,CURLOPT_FAILONERROR,1); curl_setopt($fp,CURLOPT_RETURNTRANSFER,0); curl_setopt($fp,CURLOPT_NOBODY,1); curl_exec($fp); if (curl_errno($fp) != 0) { $status = false; } else { $status = true; } curl_close($fp); return $status; } // ---------------------------------------------------- $online = pingSite($go_url); if ( !$online && !empty($go_url) && $go_url != 'http://' ) { print "<br />\n"; print "<br /> ........ Die URL <span style=\"margin:8px; padding:4px; background:#DDEEDD;\">".$go_url."</span> ist <strong style=\"color:red;\">nicht</strong> online !!! ... <a href=\"".$myscript."\">zurück</a>\n"; print "<br />\n"; } else { // ------------------------------------------------------------ if ( !empty($_REQUEST['save']) && !empty($go_url) && $go_url != 'http://' ) { print "<br />\n"; print "<br /> To-Do ........ Speichern \n"; print "<br />\n"; print "<br /> ###### DEBUG ###### _POST ###### \n"; print "<br />\n"; print "<br />\n"; print "<pre style=\"margin:4px; padding:4px; background:#DEDEDE; text-align:left;\">\n"; print_r($_POST); print "</pre>\n"; print "<br />\n"; print "<br />\n"; print "<br />\n"; } else { // ------------------------------------------------------------ $formular1 = ' <form name="form1" method="post" action=""> <br /> URL: <input type="text" name="url" size="48" maxlength="180" value="'.$go_url.'" /> <br /> <br /> RUN: <input type="submit" name="meta" value="Get MetaTags" /> INFO: <span id="minfo" style="margin:12px; padding:4px; background:#DDEEDD;">Bitte eine URL eingeben.</span> <br /> <br /> Titel: <input type="text" name="title" size="48" maxlength="90" /> <br /> <br /> Beschreibung: <br /> <textarea name="description" cols="48" rows="4" wrap="VIRTUAL"></textarea> <br /> <br /> Keywords: <br /> <textarea name="keywords" cols="48" rows="4" wrap="VIRTUAL"></textarea> <br /> <br /> OK: <input type="submit" name="save" value="Speichern" /> <br /> </form> '; // ---------------------------------------------------- print "<br />\n"; print "<br />\n"; print $formular1; print "<br />\n"; print "<br />\n"; } // ---------------------------------------------------- function str_utf8_encode($str) { if (mb_detect_encoding($str, 'UTF-8', true) === FALSE) { $str = utf8_encode($str); } return $str; } // ---------------------------------------------------------------- // ---------------------------------------------------------------- function get_meta_description($url) { $html = ''; if($fh = @fopen($url,"r")){ while (!feof($fh)){ $buffer = fgets($fh, 4096); if (strpos($buffer,'/head') !== FALSE) { break; } $html .= $buffer; } fclose($fh); } else { print "<br />ERROR ... fopen\n"; exit; } // -------------------------------------------- $pattern1 = '/<title>(.*)<\/title>/iU'; preg_match_all ($pattern1, $html, $matches_title); ## print "<pre>\n"; ## print_r($matches_title); ## print "</pre>\n"; // -------------------------------------------- $pattern2 = '/<meta name=(["\']?)(description|keywords)\\1\\s+content=(["\']?)(.+?)\\3[ \/>]/i'; preg_match_all ($pattern2, $html, $matches_meta, PREG_SET_ORDER); ## print "<pre>\n"; ## print_r($matches_meta); ## print "</pre>\n"; // -------------------------------------------- $matchdata = array(); $matchdata['title'] = (isset($matches_title[1][0])) ? str_utf8_encode($matches_title[1][0]) : ''; foreach($matches_meta as $matchitem) { $mkey = strtolower($matchitem[2]); $matchdata[$mkey] = (isset($matchitem[4])) ? str_utf8_encode($matchitem[4]) : ''; } // -------------------------------------------- return $matchdata; } // ---------------------------------------------------------------- // ---------------------------------------------------------------- // ---------------------------------------------------- if ( !empty($_REQUEST['meta']) ) { // --------------------------------- if ( !empty($go_url) && $go_url != 'http://' ) { $data = get_meta_description($go_url); print "<p>###### DEBUG ######</p>\n"; print "<br />URL: ".$go_url."\n"; print "<br />\n"; print "<pre style=\"margin:4px; padding:4px; background:#DEDEDE; text-align:left;\">\n"; print_r($data); print "</pre>\n"; print "<br />\n"; print "<br />\n"; $jscode = ''; $jscode .= ' <script type="text/javascript"> '; $jscode .= ' document.form1.title.value = "'.$data['title'].'"; document.form1.description.value = "'.$data['description'].'"; document.form1.keywords.value = "'.$data['keywords'].'"; '; $jscode .= ' document.getElementById("minfo").innerHTML = "OK ... MetaTags wurden gelesen."; '; $jscode .= ' </script> '; print $jscode; } else { // --------------------------------- print ' <script type="text/javascript"> document.getElementById("minfo").innerHTML = "Kannst Du nicht Lesen? ... zuerst eine URL eintragen !!!"; </script> '; } // --------------------------------- } // ---------------------------------------------------- } // ------------------------------------------------------------ ?>
INFO: das Speichern ist noch nicht dabei, nur eine DEBUG-Ausgabe der $_POST Werte
nach dem Klick auf Speichern-Button ... To-Do ... URL + Meta-TAGs Daten Speichern (in MySQL)
und .... jetzt würde ich das ganze gerne noch ohne Browser-Reload hinbekommen,
also per Ajax im Hintergrund die Meta-Tags auslesen und mit JS in Formular schreiben
... ein kleiner Teil (mit JS in Formular schreiben ) ist ja schon dabei ... :) ...
Beitrag zuletzt geändert: 6.3.2013 19:33:31 von webfav -
Diskutiere mit und stelle Fragen: Jetzt kostenlos anmelden!
lima-city: Gratis werbefreier Webspace für deine eigene Homepage