Laravel中的post接收请求中处理xml数据格式

3,144 阅读1分钟

#1 使用原生的php方法

    /**
     * 接收飞猪订单
     * @param Request $request
     * @return \Illuminate\Http\JsonResponse
     */
    public function receive(Request $request)
    {
        $xml = file_get_contents("php://input");
        //TODO
    }

#2 使用Laravel中Illuminate\Http\Request类封装的方法

    /**
     * 接收飞猪订单
     * @param Request $request
     * @return \Illuminate\Http\JsonResponse
     */
    public function receive(Request $request)
    {
        $xml   = $request->getContent();
        //parse XML to array method1
        //step1 parse to SimpleXMLElement 
        $obj        = simplexml_load_string($xml);
        //JsonSerializable
        $json       = json_encode($obj);
        //get array data
        $respData   = json_decode($json, true);
        //TODO
        
        //parse XML to array method2
        $respData   = XmlToArray::convert($xml, true);
    }

#3 Parse Xml to array

<?php
namespace App\Helpers;

use DOMDocument;

/**
 * Class XmlToArray
 * @package App\Helpers
 * demo: $array = XmlToArray::convert($xml);
 */
class XmlToArray
{
    /**
     * Convert valid XML to an array.
     *
     * @param string $xml
     * @param bool $outputRoot
     * @return array
     */
    public static function convert($xml, $outputRoot = false)
    {
        $array = self::xmlStringToArray($xml);
        if (!$outputRoot && array_key_exists('@root', $array)) {
            unset($array['@root']);
        }
        return $array;
    }

    protected static function xmlStringToArray($xmlstr)
    {
        $doc = new DOMDocument();
        $doc->loadXML($xmlstr);
        $root = $doc->documentElement;
        $output = self::domNodeToArray($root);
        $output['@root'] = $root->tagName;
        return $output;
    }

    protected static function domNodeToArray($node)
    {
        $output = [];
        switch ($node->nodeType) {
            case XML_CDATA_SECTION_NODE:
            case XML_TEXT_NODE:
                $output = trim($node->textContent);
                break;
            case XML_ELEMENT_NODE:
                for ($i = 0, $m = $node->childNodes->length; $i < $m; $i++) {
                    $child = $node->childNodes->item($i);
                    $v = self::domNodeToArray($child);
                    if (isset($child->tagName)) {
                        $t = $child->tagName;
                        if (!isset($output[$t])) {
                            $output[$t] = [];
                        }
                        $output[$t][] = $v;
                    } elseif ($v || $v === '0') {
                        $output = (string) $v;
                    }
                }
                if ($node->attributes->length && !is_array($output)) { // Has attributes but isn't an array
                    $output = ['@content' => $output]; // Change output into an array.
                }
                if (is_array($output)) {
                    if ($node->attributes->length) {
                        $a = [];
                        foreach ($node->attributes as $attrName => $attrNode) {
                            $a[$attrName] = (string) $attrNode->value;
                        }
                        $output['@attributes'] = $a;
                    }
                    foreach ($output as $t => $v) {
                        if (is_array($v) && count($v) == 1 && $t != '@attributes') {
                            $output[$t] = $v[0];
                        }
                    }
                }
                break;
        }
        return $output;
    }
}

#4简易方法

$arrayData = json_decode(json_encode(simplexml_load_string($xmlData)), true);