[php] PHP에서 XML을 JSON으로 변환

PHP에서 XML을 json으로 변환하려고합니다. 간단한 xml 및 json_encode를 사용하여 간단한 변환을 수행하면 xml의 속성이 표시되지 않습니다.

$xml = simplexml_load_file("states.xml");
echo json_encode($xml);

그래서 나는 이것을 수동으로 파싱하려고합니다.

foreach($xml->children() as $state)
{
    $states[]= array('state' => $state->name); 
}       
echo json_encode($states);

상태 출력은 {"state":{"0":"Alabama"}}오히려{"state":"Alabama"}

내가 뭘 잘못하고 있죠?

XML :

<?xml version="1.0" ?>
<states>
    <state id="AL">     
    <name>Alabama</name>
    </state>
    <state id="AK">
        <name>Alaska</name>
    </state>
</states>

산출:

[{"state":{"0":"Alabama"}},{"state":{"0":"Alaska"}

var 덤프 :

object(SimpleXMLElement)#1 (1) {
["state"]=>
array(2) {
[0]=>
object(SimpleXMLElement)#3 (2) {
  ["@attributes"]=>
  array(1) {
    ["id"]=>
    string(2) "AL"
  }
  ["name"]=>
  string(7) "Alabama"
}
[1]=>
object(SimpleXMLElement)#2 (2) {
  ["@attributes"]=>
  array(1) {
    ["id"]=>
    string(2) "AK"
  }
  ["name"]=>
  string(6) "Alaska"
}
}
}



답변

3 줄로 된 XML의 JSON 및 배열 :

$xml = simplexml_load_string($xml_string);
$json = json_encode($xml);
$array = json_decode($json,TRUE);


답변

이전 게시물에 답변 해 주셔서 죄송하지만이 기사에서는 비교적 짧고 간결하며 유지 관리가 쉬운 접근 방식에 대해 간략하게 설명합니다. 나는 그것을 직접 테스트하고 잘 작동합니다.

http://lostechies.com/seanbiefeld/2011/10/21/simple-xml-to-json-with-php/

<?php
class XmlToJson {
    public function Parse ($url) {
        $fileContents= file_get_contents($url);
        $fileContents = str_replace(array("\n", "\r", "\t"), '', $fileContents);
        $fileContents = trim(str_replace('"', "'", $fileContents));
        $simpleXml = simplexml_load_string($fileContents);
        $json = json_encode($simpleXml);

        return $json;
    }
}
?>


답변

나는 그것을 알아. json_encode는 문자열과 다르게 객체를 처리합니다. 객체를 문자열로 캐스팅하면 이제 작동합니다.

foreach($xml->children() as $state)
{
    $states[]= array('state' => (string)$state->name);
}
echo json_encode($states);


답변

나는 파티에 조금 늦었다 고 생각하지만이 작업을 수행하기 위해 작은 기능을 작성했습니다. 또한 속성, 텍스트 내용 및 동일한 node-name을 가진 여러 노드가 형제 인 경우에도 처리합니다.

면책 조항 :
저는 PHP 네이티브가 아니므로 간단한 실수를 감수하십시오.

function xml2js($xmlnode) {
    $root = (func_num_args() > 1 ? false : true);
    $jsnode = array();

    if (!$root) {
        if (count($xmlnode->attributes()) > 0){
            $jsnode["$"] = array();
            foreach($xmlnode->attributes() as $key => $value)
                $jsnode["$"][$key] = (string)$value;
        }

        $textcontent = trim((string)$xmlnode);
        if (count($textcontent) > 0)
            $jsnode["_"] = $textcontent;

        foreach ($xmlnode->children() as $childxmlnode) {
            $childname = $childxmlnode->getName();
            if (!array_key_exists($childname, $jsnode))
                $jsnode[$childname] = array();
            array_push($jsnode[$childname], xml2js($childxmlnode, true));
        }
        return $jsnode;
    } else {
        $nodename = $xmlnode->getName();
        $jsnode[$nodename] = array();
        array_push($jsnode[$nodename], xml2js($xmlnode, true));
        return json_encode($jsnode);
    }
}   

사용 예 :

$xml = simplexml_load_file("myfile.xml");
echo xml2js($xml);

입력 예 (myfile.xml) :

<family name="Johnson">
    <child name="John" age="5">
        <toy status="old">Trooper</toy>
        <toy status="old">Ultrablock</toy>
        <toy status="new">Bike</toy>
    </child>
</family>

출력 예 :

{"family":[{"$":{"name":"Johnson"},"child":[{"$":{"name":"John","age":"5"},"toy":[{"$":{"status":"old"},"_":"Trooper"},{"$":{"status":"old"},"_":"Ultrablock"},{"$":{"status":"new"},"_":"Bike"}]}]}]}

꽤 인쇄 :

{
    "family" : [{
            "$" : {
                "name" : "Johnson"
            },
            "child" : [{
                    "$" : {
                        "name" : "John",
                        "age" : "5"
                    },
                    "toy" : [{
                            "$" : {
                                "status" : "old"
                            },
                            "_" : "Trooper"
                        }, {
                            "$" : {
                                "status" : "old"
                            },
                            "_" : "Ultrablock"
                        }, {
                            "$" : {
                                "status" : "new"
                            },
                            "_" : "Bike"
                        }
                    ]
                }
            ]
        }
    ]
}

유의 사항 :
동일한 태그 이름을 가진 여러 태그가 형제 일 수 있습니다. 다른 솔루션은 마지막 형제를 제외한 모든 솔루션을 삭제합니다. 이를 방지하기 위해 하나의 자식 만있는 경우에도 각각의 모든 단일 노드는 tagname의 각 인스턴스에 대한 객체를 보유하는 배열입니다. (예에서 여러 개의 “”요소 참조)

유효한 XML 문서에 하나만 있어야하는 루트 요소조차도 일관된 데이터 구조를 갖기 위해 인스턴스의 객체와 함께 배열로 저장됩니다.

XML 노드 컨텐츠와 XML 속성을 구별 할 수 있도록 각 오브젝트 속성은 “$”에 저장되고 “_”하위의 컨텐츠에 저장됩니다.

편집 :
예제 입력 데이터의 출력을 표시하는 것을 잊었습니다 .

{
    "states" : [{
            "state" : [{
                    "$" : {
                        "id" : "AL"
                    },
                    "name" : [{
                            "_" : "Alabama"
                        }
                    ]
                }, {
                    "$" : {
                        "id" : "AK"
                    },
                    "name" : [{
                            "_" : "Alaska"
                        }
                    ]
                }
            ]
        }
    ]
}


답변

일반적인 함정은 json_encode()텍스트 값 속성을 가진 요소를 존중하지 않는 것입니다 . 데이터 손실을 의미하는 것 중 하나를 선택합니다. 아래 기능은 그 문제를 해결합니다. json_encode/ decode길 을 가기로 결정 하면 다음 기능이 권장됩니다.

function json_prepare_xml($domNode) {
  foreach($domNode->childNodes as $node) {
    if($node->hasChildNodes()) {
      json_prepare_xml($node);
    } else {
      if($domNode->hasAttributes() && strlen($domNode->nodeValue)){
         $domNode->setAttribute("nodeValue", $node->textContent);
         $node->nodeValue = "";
      }
    }
  }
}

$dom = new DOMDocument();
$dom->loadXML( file_get_contents($xmlfile) );
json_prepare_xml($dom);
$sxml = simplexml_load_string( $dom->saveXML() );
$json = json_decode( json_encode( $sxml ) );

그렇게하면 JSON <foo bar="3">Lorem</foo>처럼 끝나지 않습니다 {"foo":"Lorem"}.


답변

이것을 사용해보십시오

$xml = ... // Xml file data

// first approach
$Json = json_encode(simplexml_load_string($xml));

---------------- OR -----------------------

// second approach
$Json = json_encode(simplexml_load_string($xml, "SimpleXMLElement", LIBXML_NOCDATA));

echo $Json;

또는

이 라이브러리를 사용할 수 있습니다 : https://github.com/rentpost/xml2array


답변

이 목적으로 Miles Johnson의 TypeConverter 를 사용했습니다. Composer를 사용하여 설치할 수 있습니다.

이것을 사용하여 다음과 같이 작성할 수 있습니다.

<?php
require 'vendor/autoload.php';
use mjohnson\utility\TypeConverter;

$xml = file_get_contents("file.xml");
$arr = TypeConverter::xmlToArray($xml, TypeConverter::XML_GROUP);
echo json_encode($arr);