【PHP8.x】Dom\Entity::publicIdプロパティの使い方
publicIdプロパティの使い方について、初心者にもわかりやすく解説します。
基本的な使い方
publicIdプロパティは、Dom\Entityオブジェクトが表すエンティティの公開識別子(Public Identifier)を保持するプロパティです。XMLドキュメントにおいてエンティティとは、特定の文字列や構造を再利用可能な形で定義する要素を指します。このpublicIdは、主にXMLドキュメントの構造に関するルールを定義する外部のDTD(Document Type Definition)や、他の外部エンティティを識別するために使用されます。
具体的には、XMLドキュメントが準拠すべき外部のリソースを特定する情報として活用されます。例えば、ウェブページでよく見かけるHTMLドキュメントのDOCTYPE宣言において、「-//W3C//DTD XHTML 1.0 Transitional//EN」のような文字列は公開識別子の一例です。これは、特定のDTDを指し示すために用いられ、ドキュメントの妥当性を検証したり、レンダリングルールを適用したりする際に重要な役割を果たします。
このプロパティは読み取り専用であり、プログラムからDom\Entityオブジェクトが持つ公開識別子の文字列を取得することができます。XMLドキュメントを解析する際、そのドキュメントがどの外部の仕様やリソースを参照しているかを確認したい場合に、このプロパティから得られる情報が役立ちます。公開識別子は、リソースの絶対的な場所を示すシステム識別子とは異なり、より抽象的な識別子として機能します。
構文(syntax)
1<?php 2$publicIdValue = $entity->publicId; 3?>
引数(parameters)
引数なし
引数はありません
戻り値(return)
string
このプロパティは、DOMエンティティの公開識別子を表す文字列を返します。
サンプルコード
PHP Dom\Entity publicId を取得する
1<?php 2 3/** 4 * XML ドキュメントから Dom\Entity の Public ID を取得するサンプル。 5 * システムエンジニアを目指す初心者向けに、Dom\Entity::publicId プロパティの 6 * 利用方法と、それが public プロパティであることを示します。 7 */ 8function demonstrateDomEntityPublicId(): void 9{ 10 // XML ドキュメントと内部 DTD (Document Type Definition) を定義します。 11 // ここでは 'example_entity' というエンティティを PUBLIC 識別子付きで定義しています。 12 // `PUBLIC "urn:example:publicId:v1"` の部分がこのエンティティの Public ID です。 13 $xmlString = <<<XML 14<?xml version="1.0" encoding="UTF-8"?> 15<!DOCTYPE root [ 16 <!ENTITY example_entity PUBLIC "urn:example:publicId:v1" "system_identifier.dtd"> 17 <!ENTITY private_entity "This is a private entity content."> 18]> 19<root> 20 &example_entity; 21 <message>Hello from &private_entity;</message> 22</root> 23XML; 24 25 // Dom\Document オブジェクトを作成します。 26 $dom = new Dom\Document(); 27 28 // XML 文字列をロードします。 29 // ロードに失敗した場合はエラーメッセージを表示して終了します。 30 if (!$dom->loadXML($xmlString)) { 31 echo "エラー: XMLのロードに失敗しました。\n"; 32 return; 33 } 34 35 // ドキュメントタイプ (<!DOCTYPE ...> の情報) を取得します。 36 $docType = $dom->doctype; 37 38 if ($docType === null) { 39 echo "情報: ドキュメントタイプ (DOCTYPE) がXMLに見つかりませんでした。\n"; 40 return; 41 } 42 43 // ドキュメントタイプから定義されているエンティティのリストを取得します。 44 // これは Dom\NamedNodeMap (名前付きノードのマップ) として返されます。 45 $entities = $docType->entities; 46 47 if ($entities === null || $entities->length === 0) { 48 echo "情報: DTD内にエンティティが定義されていません。\n"; 49 return; 50 } 51 52 // 定義したエンティティ 'example_entity' を名前で取得します。 53 // Dom\NamedNodeMap::getNamedItem() メソッドを使用して、指定した名前のノードを取得します。 54 $entity = $entities->getNamedItem('example_entity'); 55 56 // 取得したノードが期待通り Dom\Entity クラスのインスタンスであるかを確認します。 57 if ($entity instanceof Dom\Entity) { 58 // Dom\Entity::publicId は public プロパティであるため、 59 // オブジェクトの外部から直接アクセスして値を取得できます。 60 echo "エンティティ 'example_entity' の Public ID: '" . $entity->publicId . "'\n"; 61 } else { 62 echo "エラー: エンティティ 'example_entity' が見つからないか、Dom\\Entity 型ではありません。\n"; 63 } 64 65 // Public ID が設定されていないエンティティの例も見てみましょう。 66 $privateEntity = $entities->getNamedItem('private_entity'); 67 if ($privateEntity instanceof Dom\Entity) { 68 // PUBLIC 識別子が設定されていない場合、publicId プロパティは空文字列になります。 69 echo "エンティティ 'private_entity' の Public ID: '" . $privateEntity->publicId . "' (空文字列)\n"; 70 } else { 71 echo "エラー: エンティティ 'private_entity' が見つからないか、Dom\\Entity 型ではありません。\n"; 72 } 73} 74 75// サンプルコードを実行します。 76demonstrateDomEntityPublicId(); 77
Dom\Entity::publicId プロパティは、PHP 8で導入された新しいDom拡張機能において、XMLドキュメントのDTD(Document Type Definition)で定義されるエンティティのPublic IDを取得するために使用されます。Public IDとは、外部のDTDファイルなどのリソースを一意に特定するための公開識別子で、XMLパーサーが特定のリソースを見つける際に役立ちます。
このプロパティは引数を取らず、戻り値としてstring型のPublic IDを返します。もしエンティティにPublic IDが設定されていない場合は、空文字列が返されます。
publicId プロパティは、その名前が示す通りpublicなプロパティです。これは、Dom\Entityクラスのインスタンスが作成された後、例えば $entity という変数に格納されている場合に、$entity->publicId のようにクラスの外部から直接アクセスして値を取得できることを意味します。
サンプルコードでは、まずPublic IDを持つエンティティと持たないエンティティの両方を含むXML文字列を作成しています。次に、Dom\DocumentオブジェクトにこのXMLをロードし、$dom->doctypeからドキュメントタイプ、さらに$docType->entitiesからエンティティのリストを取得しています。特定のエンティティ(例えばexample_entity)を取得した後、$entity->publicIdと直接アクセスすることで、そのPublic IDが取得され、表示されています。Public IDを持たないprivate_entityに対して同様にアクセスすると、空文字列が返されることも確認できます。これにより、XMLドキュメント内のエンティティ情報をプログラムで簡単に取得し、利用する方法を学ぶことができます。
Dom\Entity::publicIdプロパティはpublicアクセス可能であるため、オブジェクトから$entity->publicIdのように直接値を読み取ることができます。このプロパティは、XMLの<!DOCTYPE ... <!ENTITY name PUBLIC "識別子" "システム識別子"> ... ]>のようにPUBLIC識別子を持つエンティティに対してのみ具体的な値(文字列)を返します。PUBLIC識別子のないエンティティの場合、publicIdは空文字列("")となりますので、値がない場合と混同しないよう注意が必要です。また、サンプルコードにあるように、XMLドキュメントのロード失敗や、DOCTYPEが存在しない、あるいは目的のエンティティが見つからないといった状況も考慮し、loadXML()の戻り値チェックや各オブジェクトのNULLチェック、instanceofによる型確認を適切に行うことで、より安全で安定したプログラムを作成できます。
PHP Dom\Entity publicIdでパブリックIDを取得する
1<?php 2 3/** 4 * Dom\Entity::publicId プロパティの使用例 5 * 6 * この関数は、XMLドキュメントをパースし、 7 * ドキュメント型定義 (DTD) で定義されたエンティティの 8 * パブリックIDを取得する方法を示します。 9 * 10 * パブリックID (Public ID) は、XMLやSGMLの外部エンティティを識別するために使用される公開識別子です。 11 * 通常、DTD(Document Type Definition)で定義される外部エンティティに関連付けられ、 12 * エンティティが何であるかを示す標準的な文字列形式です。 13 * 例えば、HTMLのDOCTYPE宣言でよく見られる "-//W3C//DTD HTML 4.01//EN" などがこれにあたります。 14 * 15 * @return void 16 */ 17function demonstrateDomEntityPublicId(): void 18{ 19 // 外部エンティティを参照するXMLドキュメントの定義 20 // ここで 'publicEntity' は PUBLIC ID "-//MYORG//ENTITIES MyExample//EN" を持ちます。 21 $xmlString = <<<XML 22<?xml version="1.0" encoding="UTF-8"?> 23<!DOCTYPE doc [ 24 <!ENTITY publicEntity PUBLIC "-//MYORG//ENTITIES MyExample//EN" "example.txt"> 25 <!ENTITY systemEntity SYSTEM "another.txt"> 26]> 27<doc> 28 <item>&publicEntity;</item> 29 <item>&systemEntity;</item> 30</doc> 31XML; 32 33 // PHP 8で推奨される Dom\Document クラスを使用 34 $dom = new Dom\Document(); 35 // 外部エンティティのロードを有効にする 36 // これにより、DTDで定義された外部エンティティ情報がパースされます。 37 $dom->resolveExternals = true; 38 39 // XMLのロードを試行し、失敗した場合はエラーメッセージを出力 40 // Dom\Document::loadXML はエラー時に false を返すことがあります。 41 // エラーメッセージをより詳細に取得するには libxml_get_errors() などを使用できますが、 42 // ここではシンプルに boolean の戻り値で判定します。 43 if (!$dom->loadXML($xmlString)) { 44 echo "エラー: XMLのロードに失敗しました。\n"; 45 return; 46 } 47 48 // ドキュメントタイプ定義 (DTD) を取得 49 $doctype = $dom->doctype; 50 51 // DTDが存在し、その中にエンティティが定義されているかを確認 52 if ($doctype && $doctype->entities) { 53 echo "--- XMLドキュメント内のエンティティを検索中 ---\n"; 54 // ドキュメントタイプエンティティのコレクションをループ 55 foreach ($doctype->entities as $entity) { 56 // PHP 8の Dom\Document を使用した場合、エンティティは Dom\Entity 型になります。 57 if ($entity instanceof Dom\Entity) { 58 echo "エンティティ名: " . $entity->nodeName . "\n"; 59 echo " システムID: " . ($entity->systemId ?: 'N/A') . "\n"; 60 // Dom\Entity::publicId プロパティにアクセスし、パブリックIDを取得 61 echo " パブリックID: " . ($entity->publicId ?: 'N/A') . "\n"; 62 echo "----------------------------------------\n"; 63 } else { 64 // 想定外の型のエンティティが見つかった場合の警告 65 echo "警告: 予期しない型のエンティティが見つかりました: " . get_class($entity) . "\n"; 66 } 67 } 68 } else { 69 echo "XMLドキュメントにDTDまたはエンティティが見つかりませんでした。\n"; 70 } 71} 72 73// 関数を実行して、Dom\Entity::publicId の動作を確認 74demonstrateDomEntityPublicId(); 75
Dom\Entity::publicIdプロパティは、PHPのDOM拡張機能において、XMLドキュメントのドキュメント型定義 (DTD) で定義された外部エンティティの「パブリックID」を取得するために使用されます。パブリックIDとは、XMLやSGMLで外部エンティティを一意に識別するための公開された文字列識別子で、例えば標準的なDTDや特定の文書タイプを示す際などに利用されます。このプロパティには引数はありません。
サンプルコードでは、外部エンティティとパブリックIDが定義されたXMLをDom\Documentクラスにロードしています。$dom->resolveExternals = true;を設定することで、外部エンティティ情報が適切に解析されるようにしています。XMLのロードに成功すると、$dom->doctype->entitiesコレクションから個々のDom\Entityオブジェクトを取得できます。そのDom\EntityオブジェクトのpublicIdプロパティにアクセスすることで、該当するエンティティに割り当てられたパブリックIDの文字列値を取得しています。このプロパティは、パブリックIDが見つかった場合はそのIDをstring型で返し、定義されていない場合は空の文字列を返します。これにより、XMLが参照する外部定義の標準的な識別子をプログラムで確認することが可能になります。
Dom\Entity::publicIdプロパティは、XMLの外部エンティティを識別する公開識別子で、DTDで定義されたエンティティにのみ存在します。この情報を正しく取得するには、Dom\DocumentでXMLをロードする前に、$dom->resolveExternals = true;を設定することが重要です。この設定がないと、外部エンティティの情報が正しく解析されず、publicIdも取得できませんのでご注意ください。XMLのロードは失敗する可能性がありますので、loadXMLメソッドの戻り値を必ず確認し、エラーハンドリングを行う習慣をつけましょう。publicIdは存在しないエンティティの場合、空文字列となりますので、表示時には適切な代替値を検討してください。これは、リソースの場所を示すsystemIdとは異なる概念であると理解しておくと良いでしょう。