Pobieranie meta tagów, część 2

01 listopada 2008

Czas najwyższy zaprezentować bardziej rozbudowaną funkcję od tej, którą pokazałem we wpisie Jak najlepiej pobrać meta tagi jakiejś strony www?.

Wprowadzone zmiany:

  • Z jednej funkcji zrobiły się dwie. Pierwsza odpowiada za prawidłowe odczytanie kodowania strony, druga pobiera resztę meta tagów.
  • Przekonałem się jednak do wyrażeń regularnych a więc jest już tylko jedna wersja kodu, która działa zarówno na PHP 4 jak i PHP 5.
  • Napisałem na nowo wyrażenia regularne. Teraz funkcje są bardziej odporne na błędy osób definiujących meta tagi. Nie przeszkadzają zbędne spacje, różna kolejność wartości, braki cudzysłowów, dodatkowe, niestandardowe wartości itd.

Kod PHP:

PHP:
  1. function pobierz_kodowanie($tresc) {
  2.  
  3.   $metatagi = array();
  4.  
  5.   if($tresc) {
  6.     // pobieranie meta tagow typu http-equiv
  7.     preg_match_all('/<[\s]*meta[\s]+(http\-equiv|content)="?([^>"]+?)"?[\s]+(http\-equiv|content)="?([^>"]+?)"?[\s]*\/?[\s]*>/si', $tresc, $wynik, PREG_SET_ORDER);
  8.  
  9.     if(is_array($wynik) AND count($wynik)> 0) {
  10.       foreach($wynik AS $key => $value) {
  11.         $explode = explode(';', $value[4]);
  12.    
  13.         if(count($explode)> 0) {
  14.           if(strpos($explode[0], 'charset') !== FALSE) {
  15.             $metatagi['charset'] = strtoupper(substr(trim($explode[0]), 8));
  16.             $metatagi['content-type'] = trim($explode[1]);
  17.      
  18.         return $metatagi;
  19.           }
  20.           elseif(strpos($explode[1], 'charset') !== FALSE) {
  21.         $metatagi['charset'] = strtoupper(substr(trim($explode[1]), 8));
  22.         $metatagi['content-type'] = trim($explode[0]);
  23.      
  24.         return $metatagi;
  25.           }
  26.         }
  27.       }
  28.     }
  29.   }
  30.   return FALSE;
  31. }
  32.  
  33. function pobierz_metatagi($tresc, $metatagi = array()) {
  34.  
  35.   if($tresc) {
  36.     // pobieranie zawartosci tagu <title>...</title>
  37.     preg_match('/<title>([^<]+?)<\/title>/si', $tresc, $title);
  38.    
  39.     if($title[1]) {
  40.       $metatagi['title'] = trim($title[1]);
  41.     }
  42.    
  43.     // wyciagamy reszte meta tagow
  44.     preg_match_all('/<[\s]*meta[\w\s="-]+?(name|content)="?([^>"]+)"?[\w\s="-]+?(content|name)="?([^>"]+)"?[\w\s="\/-]*>/si', $tresc, $wynik, PREG_SET_ORDER);
  45.    
  46.     if(is_array($wynik) AND count($wynik)> 0) {
  47.       foreach($wynik AS $key => $value) {
  48.      
  49.         if(strtolower($value[3]) == 'content') {
  50.           $metatagi[trim(strtolower($value[2]))] = trim($value[4]);
  51.         }
  52.         else {
  53.           $metatagi[trim(strtolower($value[4]))] = trim($value[2]);
  54.     }
  55.       }
  56.     }
  57.  
  58.     // rozbicie slow kluczowych na tablice
  59.     if($metatagi['keywords']) {
  60.       $tagi = array();
  61.       $keywords = explode(',', $metatagi['keywords']);
  62.      
  63.       foreach($keywords AS $tag) {
  64.         $tag = trim($tag);
  65.         if($tag) {
  66.           $tagi[] = $tag;
  67.         }
  68.       }
  69.       $tagi = array_unique($tagi);
  70.      
  71.       if(count($tagi)> 0) {
  72.         $metatagi['keywords'] = $tagi;
  73.       }
  74.     }
  75.   }
  76.  
  77.   return $metatagi;
  78. }

Funkcja pobierz_kodowanie() przyjmuje jedną wartość, ciąg znaków. Szuka w niej meta tagu odpowiedzialnego za definicję kodowania strony. Zwraca FALSE (jeżeli nic nie znajdzie) lub tablicę PHP o takiej strukturze:

CODE:
  1. Array
  2. (
  3.     [charset] => UTF-8
  4.     [content-type] => text/html
  5. )

Kodowanie jest zapisane zawsze wielkimi literami.

Funkcja pobierz_metatagi() przyjmuje string (źródło z którego ma wyciągnąć informację) oraz, opcjonalnie, tablicę PHP w której można przekazać inne meta tagi (chociażby te zwrócone przez funkcję pobierz_kodowanie()).

Sposób użycia (do pobrania źródła strony użyłem standardowo mojej funkcji otworz_adres() o której poczytasz tu: Funkcja pobierająca stronę www):

PHP:
  1. $zrodlo = otworz_adres('http://www.tarnaski.eu/');
  2. $kodowanie = pobierz_kodowanie($zrodlo);
  3.  
  4. if($kodowanie != FALSE AND $kodowanie['charset'] != 'UTF-8') {
  5.   $zrodlo = iconv($kodowanie['charset'], 'UTF-8', $zrodlo);
  6. }
  7. $metatagi = pobierz_metatagi($zrodlo, $kodowanie);
  8.  
  9.  
  10. print_r($metatagi);

Wynik:

CODE:
  1. Array
  2. (
  3.     [charset] => UTF-8
  4.     [content-type] => text/html
  5.     [title] => Mariusz Tarnaski
  6.     [generator] => WordPress 2.6
  7.     [description] => Blog na każdy temat chociaż chciałbym się skupiać przede wszystkim na mojej pasji jaką jest tworzenie stron Internetowych.
  8.     [keywords] => Array
  9.         (
  10.             [0] => Mariusz
  11.             [1] => Tarnaski
  12.             [2] => MariuszT
  13.             [3] => pozycjonowanie
  14.             [4] => tworzenie stron www
  15.             [5] => komputery
  16.             [6] => internet
  17.         )
  18.  
  19.     [verify-v1] => D2ohrgDDepMDX6HH4qxpF3K3tHNuIkINWKWc+VDTqKM=
  20. )

Za ewentualną zmianę kodowania odpowiada funkcja iconv() a więc musi ona być dostępna na serwerze (raczej już nie ma z tym problemów na większości serwerów). Zmiana kodowania jest przeprowadzana tylko wtedy gdy funkcja pobierz_kodowanie() znalazła jakieś informacje o kodowaniu (nie zwróciła FALSE) lub kodowanie jest inne niż to, które nas interesuje (w moim przypadku jest to UTF-8).

Dlaczego rozbiłem to na dwie funkcje? Bo mam dzięki temu większe możliwości. Teraz mogę przekodować całe źródło, pobrać meta tagi i przeprowadzać dalsze operacje na źródle już o odpowiednim kodowaniu.

Funkcje nie zwracają wartości meta tagów typu http-equiv, oczywiście poza meta tagiem definiującym kodowanie. Nie dodałem tej funkcjonalności bo do niczego mi to nie jest potrzebne.

Ten wpis nie ma komentarzy... ale możesz być pierwszy

Odpowiedz



Podobne wpisy: