PHP 8.4.1 Released!

DOMNode::C14N

(PHP 5 >= 5.2.0, PHP 7, PHP 8)

DOMNode::C14NCanonise des nœuds en une chaîne

Description

public DOMNode::C14N(
    bool $exclusive = false,
    bool $withComments = false,
    ?array $xpath = null,
    ?array $nsPrefixes = null
): string|false

Canonise des nœuds en une chaîne de caractères.

Liste de paramètres

exclusive

Active l'analyse des seuls nœuds correspondant à l'Xpath ou aux préfixes d'espace de noms fournis.

withComments

Conserve les commentaires dans la sortie.

xpath

Un tableau de XPaths pour filtrer les nœuds. Chaque entrée dans ce tableau est un tableau associatif avec :

  • Une clé query requise contenant l'expression XPath en tant que chaîne de caractères.
  • Une clé namespaces optionnelle contenant un tableau qui mappe les préfixes de l'espace de noms (clés) aux URI de l'espace de noms (valeurs).

nsPrefixes

Un tableau de préfixes d'espaces de noms utilisés pour filtrer les nœuds.

Valeurs de retour

Retourne les nœuds canonisés, sous la forme d'une chaîne de caractères ou false si une erreur survient

Exemples

Exemple #1 Exemple avec une requête XPath

Cet exemple démontre une utilisation avancée par la canonicalisation et le filtrage des nœuds via une requête XPath.

<?php

$dom
= new DOMDocument();
$dom->loadXML(<<<XML
<root xmlns:food="urn:food">
<!-- déclaration d'espace de noms redondante qui sera canonisée -->
<food:fruit xmlns:food="urn:food">Pomme</food:fruit>
<food:fruit>Orange</food:fruit>
<food:fruit>Poire</food:fruit>
<!-- légumes ici -->
<food:vegetable>Laitue</food:vegetable>
</root>
XML);

echo
$dom->C14N(true, false, [
"query" => ".//f:fruit|.//f:fruit/text()",
"namespaces" => ["f" => "urn:food"],
]);
?>

L'exemple ci-dessus va afficher :

<food:fruit>Pomme</food:fruit><food:fruit>Orange</food:fruit><food:fruit>Poire</food:fruit>

Voir aussi

add a note

User Contributed Notes 3 notes

up
21
Rijk
11 years ago
When working with (malformed) HTML, you're probably better off using DOMDocument's saveHTML() method instead. C14N() will attempt to make your HTML valid XML, for example by converting <br> to <br></br>.

So instead of:
$html = $Node->C14N();

Use:
$html = $Node->ownerDocument->saveHTML( $Node );
up
16
jorda at edpsciences dot org
9 years ago
C14N() returns an empty string if the node is not included in the document tree:
<?php
$d
= new DOMDocument('1.0');
$d->loadXML('<foo></foo>');
$n = $d->createElement('bar');
var_dump($n->C14N());
$d->documentElement->appendChild($n);
var_dump($n->C14N());
?>
output:
string(0) ""
string(11) "<bar></bar>"
up
3
lordbaco
8 years ago
[edit by nielsdos: This has been fixed starting in PHP 8.4]

Good to know:

<< Due to a known issue in XML canonicalization in PHP, processing large metadata files in SimpleSAMLphp takes a big amount of resources, with that amount growing approximately by the square of the number of entities in the metadata set >>
https://simplesamlphp.org/metaprocessing

<< The C14N() function appears to have a runtime that is O(N^2) (or possibly worse?) depending on input size, which means that it becomes very slow as the input grows. For example, an input with around 196000 nodes takes about 290 seconds, while an input with 486000 nodes takes 2200 seconds. >>
https://bugs.php.net/bug.php?id=53655

We had the same issue with a 4.1 MB XML (105k lines). The sample code of ticket #53655 takes 1h36 minute to canonicalize it!
To Top