文字列操作

html

【PHP】Webページを取得してjson-ldを抜き出し連想配列にセットする方法

更新日:2023/03/20

PHPでWebページを読み込み、json-ldを取得する方法をお伝えします。

 

手順

次の流れで、Webページ内のjson-ldを連想配列で取得します。

  1. file_get_contents()でWebページを読み込む
  2. preg_match()でjson-ldを抜き出す
  3. json_decode()でjsonを連想配列に変換する

流れは簡単ですが、正規表現のパターンを考えるのが難しそうですね。

 

コード

流れをそのままコードに置き換えます。

function get_json_ld( $url ){
        // Webページ読み込み
    $html = file_get_contents($url);

    if( $html === false )
        return false; // 読み込み失敗
    
        // json-ldの抜き出し
    $pattern = '#<script\s[^>]*type=(["\'])application/ld\+json\1\s*>(.*?)</script>#s';
    if( preg_match($pattern, $html , $matches) !== 1 )
        return false; // json-ldが存在しない
    
       // jsonデコード
    $ld = json_decode($matches[2],true);
    if( $ld === null ) return false; // デコード失敗

    return $ld;
}

流れ上でエラーが発生したときは、全てfalseを返しています。
戻り値で失敗原因を把握したいときは、エラーコード等を返すといいかもしれません。

正規表現のパターンはそれほど難しくなかったのですが、"application/ld+json"で注意する点が二つありました。

  • '/'が含まれるので、正規表現の開始と終了に'/'を使用しない。またはエスケープする
  • '+'は正規表現のメタ文字なので、エスケープが必要

2つ目に気が付かなくて、しばらく悩みました。

なお、現在はほとんどのWebページはUTF-8でエンコードされていますが、時々異なるページがあります。
エンコードが異なると、日本語が文字化けします。
今回のコードには文字化け対策がされていません。

Webページの文字化け対策は次のページで紹介しています。
【PHP】file_get_contents()で取得したWebページの文字化け対策

 

テスト

僕のサイトもjson-ldを利用しているので、適当なページでテストしてみます。

$url = 'https://note.affi-sapo-sv.com/php-remove-newline-code.php';
$ld = get_json_ld($url);

if( $ld === false ) echo '取得失敗';
else var_dump($ld);

結果は次のようになりました。

array(2) {
  [0]=>
  array(10) {
    ["@context"]=>
    string(17) "http://schema.org"
    ["@type"]=>
    string(7) "Article"
    ["mainEntityOfPage"]=>        
    array(2) {
      ["@type"]=>
      string(7) "WebPage"
      ["@id"]=>
      string(57) "https://note.affi-sapo-sv.com/php-remove-newline-code.php"
    }
    ["headline"]=>
    string(60) "【PHP】文字列から改行コードを削除する方法"
    ["image"]=>
    array(4) {
      ["@type"]=>
      string(11) "ImageObject"
      ["url"]=>
      string(72) "https://note.affi-sapo-sv.com/logos/php-remove-newline-code-php-logo.jpg"
      ["height"]=>
      int(840)
      ["width"]=>
      int(1200)
    }
    ["datePublished"]=>
    string(23) "2023-03-17T17:40:12+900"
    ["dateModified"]=>
    string(23) "2023-03-17T17:40:12+900"
    ["author"]=>
    array(3) {
      ["url"]=>
      string(29) "https://note.affi-sapo-sv.com"
      ["@type"]=>
      string(6) "Person"
      ["name"]=>
      string(15) "けーちゃん"
    }
    ["publisher"]=>
    array(3) {
      ["@type"]=>
      string(12) "Organization"
      ["name"]=>
      string(48) "けーちゃんのプログラム開発ノート"
      ["logo"]=>
      array(4) {
        ["@type"]=>
        string(11) "ImageObject"
        ["url"]=>
        string(41) "https://note.affi-sapo-sv.com/favicon.ico"
        ["width"]=>
        string(2) "48"
        ["height"]=>
        string(2) "48"
      }
    }
    ["description"]=>
    string(348) "改行コードはプラットホームにより異なります。PHPで文字列から改行を削除するときは様々な改行コードに対応させる必要があり、自分で考えるのは少し難しいかもしれません。そこで今回は、PHPで文字列から 
改行を削除するときの定番コードを紹介します。"
  }
  [1]=>
  array(3) {
    ["@context"]=>
    string(18) "https://schema.org"
    ["@type"]=>
    string(14) "BreadcrumbList"
    ["itemListElement"]=>
    array(4) {
      [0]=>
      array(4) {
        ["@type"]=>
        string(8) "ListItem"
        ["position"]=>
        int(1)
        ["name"]=>
        string(12) "TOPページ"
        ["item"]=>
        string(29) "https://note.affi-sapo-sv.com"
      }
      [1]=>
      array(4) {
        ["@type"]=>
        string(8) "ListItem"
        ["position"]=>
        int(2)
        ["name"]=>
        string(21) "プログラミング"
        ["item"]=>
        string(54) "https://note.affi-sapo-sv.com/category/programming.php"
      }
      [2]=>
      array(4) {
        ["@type"]=>
        string(8) "ListItem"
        ["position"]=>
        int(3)
        ["name"]=>
        string(3) "PHP"
        ["item"]=>
        string(46) "https://note.affi-sapo-sv.com/category/php.php"
      }
      [3]=>
      array(4) {
        ["@type"]=>
        string(8) "ListItem"
        ["position"]=>
        int(4)
        ["name"]=>
        string(60) "【PHP】文字列から改行コードを削除する方法"
        ["item"]=>
        string(57) "https://note.affi-sapo-sv.com/php-remove-newline-code.php"
      }
    }
  }
}

上手く取得できました。

 

階層で値を取得する

実際には、json-ldを連想配列で取得するのが目的ではありません。
その配列から何らかの値を取得するのが、目的ですね。

そこでページのロゴ画像を取得してみます。

今回は、次のページで紹介している自作コードを使用します。

$imageUrl = get_array_all_find_hierarchy_key_value( $ld , array( 'image' , 'url' ) );
print_r( $imageUrl );
// Array
// (
//    [0] => https://note.affi-sapo-sv.com/logos/php-remove-newline-code-php-logo.jpg
// )

取得できました。

更新日:2023/03/20

書いた人(管理人):けーちゃん

スポンサーリンク

記事の内容について

null

こんにちはけーちゃんです。
説明するのって難しいですね。

「なんか言ってることおかしくない?」
たぶん、こんなご意見あると思います。

裏付けを取りながら記事を作成していますが、僕の勘違いだったり、そもそも情報源の内容が間違えていたりで、正確でないことが多いと思います。
そんなときは、ご意見もらえたら嬉しいです。

掲載コードについては事前に動作確認をしていますが、貼り付け後に体裁を整えるなどをした結果動作しないものになっていることがあります。
生暖かい視線でスルーするか、ご指摘ください。

ご意見、ご指摘はこちら。
https://note.affi-sapo-sv.com/info.php

 

このサイトは、リンクフリーです。大歓迎です。