简体   繁体   中英

How to validate xml with php

I have made an api with xml based request for my website.

but sometimes, some customers send me an invalid xml and I want to return a good response.

how can I validate xml?

edited:

Ok, I think I asked wrong question, I want to validate nodes and if some nodes missing then I return best response.

I used to validate this with php and I have to check every nodes. but this way is very hard to modify.

it is my xml example:

<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<mashhadhost>
    <create>
        <name>example.ir</name>
        <period>60</period>
        <ns>
            <hostAttr>
                <hostName>ns1.example.ir</hostName>
                <hostAddr ip="v4">192.0.2.2</hostAddr>
            </hostAttr>
        </ns>
        <contact type="holder">ex61-irnic</contact>
        <contact type="admin">ex61-irnic</contact>
        <contact type="tech">ex61-irnic</contact>
        <contact type="bill">ex61-irnic</contact>
    </create>
    <auth>
        <code>TOKEN</code>
    </auth>
</mashhadhost>

Unfortunately XMLReader didn't validate lots of things in my case.

Here a small piece of class I wrote a while ago:

/**
 * Class XmlValidator
 * @author Francesco Casula <fra.casula@gmail.com>
 */
class XmlValidator
{
    /**
     * @param string $xmlFilename Path to the XML file
     * @param string $version 1.0
     * @param string $encoding utf-8
     * @return bool
     */
    public function isXMLFileValid($xmlFilename, $version = '1.0', $encoding = 'utf-8')
    {
        $xmlContent = file_get_contents($xmlFilename);
        return $this->isXMLContentValid($xmlContent, $version, $encoding);
    }

    /**
     * @param string $xmlContent A well-formed XML string
     * @param string $version 1.0
     * @param string $encoding utf-8
     * @return bool
     */
    public function isXMLContentValid($xmlContent, $version = '1.0', $encoding = 'utf-8')
    {
        if (trim($xmlContent) == '') {
            return false;
        }

        libxml_use_internal_errors(true);

        $doc = new DOMDocument($version, $encoding);
        $doc->loadXML($xmlContent);

        $errors = libxml_get_errors();
        libxml_clear_errors();

        return empty($errors);
    }
}

It works fine with streams and vfsStream as well for testing purposes.

If you want to check only if the document is well formed (you don't care about the DTD validity, and don't even have a DTD to validate against) use Domdocument to validate your file, rather than XMLReader, because XMLReader will stream you document and don't load it at once, so isValid() method will only check the first node. You can try a code like this:

 $doc = new \DOMDocument();

 if(@$doc->load($filePath)){
     var_dump("$filePath is a valid XML document");
} else {
      var_dump("$filePath is NOT a valid document");
}

You can use XMLReader::isValid() .

<?php
    $xml = XMLReader::open('xmlfile.xml');

    // You must to use it
    $xml->setParserProperty(XMLReader::VALIDATE, true);

    var_dump($xml->isValid());
?>

The PHP documentation has exactly what you need!

XML DOMDocument::validate

I'm sure that you have already defined the proper DTD, right?

<?php
$dom = new DOMDocument;
$dom->Load('book.xml');
if ($dom->validate()) {
    echo "This document is valid!\n";
}
?>

You can use PHP function:-

$xmlcontents = XMLReader::open('filename.xml');

$xmlcontents->setParserProperty(XMLReader::VALIDATE, true);

var_dump($xmlcontents->isValid());

Source:- http://php.net/manual/en/xmlreader.isvalid.php

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM