Estoy tratando de convertir xml a json en php. Si hago una conversión simple usando xml simple y json_encode ninguno de los atributos en el show xml.
$xml = simplexml_load_file("states.xml");
echo json_encode($xml);
Así que estoy tratando de analizarlo manualmente de esta manera.
foreach($xml->children() as $state)
{
$states[]= array('state' => $state->name);
}
echo json_encode($states);
y la salida para el estado es {"state":{"0":"Alabama"}}
más que{"state":"Alabama"}
¿Qué estoy haciendo mal?
XML:
<?xml version="1.0" ?>
<states>
<state id="AL">
<name>Alabama</name>
</state>
<state id="AK">
<name>Alaska</name>
</state>
</states>
Salida:
[{"state":{"0":"Alabama"}},{"state":{"0":"Alaska"}
volcado 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"
}
}
}
var_dump
funciona bien.)Respuestas:
Json & Array de XML en 3 líneas:
fuente
<person my-attribute='name'>John</person>
se interpreta como<person>John</person>
.@attributes
clave, por lo que funciona de manera absolutamente perfecta y hermosa. 3 líneas cortas de código resuelven mi problema maravillosamente.<list><item><a>123</a><a>456</a></item><item><a>123</a></item></list>
->{"item":[{"a":["123","456"]},{"a":"123"}]}
. Una solución en php.net por ratfactor resuelve ese problema almacenando siempre elementos en una matriz.Perdón por responder una publicación anterior, pero este artículo describe un enfoque relativamente breve, conciso y fácil de mantener. Lo probé yo mismo y funciona bastante bien.
http://lostechies.com/seanbiefeld/2011/10/21/simple-xml-to-json-with-php/
fuente
Me lo imaginé. json_encode maneja los objetos de manera diferente a las cadenas. Lanzo el objeto a una cadena y funciona ahora.
fuente
Supongo que llego un poco tarde a la fiesta, pero he escrito una pequeña función para realizar esta tarea. También se ocupa de los atributos, el contenido del texto e incluso si varios nodos con el mismo nombre de nodo son hermanos.
Descargo de responsabilidad: no soy un nativo de PHP, así que por favor tenga en cuenta los errores simples.
Ejemplo de uso:
Entrada de ejemplo (myfile.xml):
Salida de ejemplo:
Bastante impreso:
Quirks a tener en cuenta: varias etiquetas con el mismo nombre de etiqueta pueden ser hermanos. Es probable que otras soluciones eliminen todas menos la última hermana. Para evitar esto, todos y cada uno de los nodos, incluso si solo tiene un hijo, es una matriz que contiene un objeto para cada instancia del nombre de etiqueta. (Ver múltiples "" elementos en el ejemplo)
Incluso el elemento raíz, del cual solo debe existir uno en un documento XML válido, se almacena como una matriz con un objeto de la instancia, solo para tener una estructura de datos coherente.
Para poder distinguir entre el contenido del nodo XML y los atributos XML, los atributos de cada objeto se almacenan en "$" y el contenido en el elemento secundario "_".
Editar: olvidé mostrar la salida para sus datos de entrada de ejemplo
fuente
$xml = simplexml_load_file("myfile.xml",'SimpleXMLElement',LIBXML_NOCDATA);
.Fatal error: Uncaught Error: Call to a member function getName() on bool
... creo que una versión php falla :-( .. por favor ayuda!Un error común es olvidar que
json_encode()
no respeta elementos con un valor de texto y atributo (s). Escogerá uno de esos, lo que significa dataloss. La siguiente función resuelve ese problema. Si uno decide ir porjson_encode
/decode
way, se recomienda la siguiente función.al hacerlo,
<foo bar="3">Lorem</foo>
no terminará como{"foo":"Lorem"}
en su JSON.fuente
$dom
? De donde vino eso?Intenta usar esto
O
Puede usar esta biblioteca: https://github.com/rentpost/xml2array
fuente
He utilizado TypeConverter de Miles Johnson para este propósito. Es instalable usando Composer .
Podrías escribir algo como esto usándolo:
fuente
Optimizando la respuesta de Antonio Max:
fuente
Si desea convertir solo una parte específica del XML a JSON, puede usar XPath para recuperar esto y convertirlo a JSON.
Tenga en cuenta que si su Xpath es incorrecto, esto morirá con un error. Entonces, si está depurando esto a través de llamadas AJAX, le recomiendo que también registre los cuerpos de respuesta.
fuente
fuente
La mejor solución que funciona como un encanto
Fuente
fuente
Esta es una mejora de la solución más votada por Antonio Max, que también funciona con XML que tiene espacios de nombres (reemplazando los dos puntos con un guión bajo). También tiene algunas opciones adicionales (y analiza
<person my-attribute='name'>John</person>
correctamente).fuente
<element/>
, no aborda los elementos que comienzan con, o contienen guiones bajos, lo cual está permitido en XML. No puede detectar CDATA. Y como he dicho, es LENTO. Es una complejidad O (n ^ 2) debido al análisis interno.¡Todas las soluciones aquí tienen problemas!
... Cuando la representación necesita una interpretación XML perfecta (sin problemas con los atributos) y para reproducir todo el texto-etiqueta-texto-etiqueta-texto -... y el orden de las etiquetas. También recuerde aquí que el objeto JSON "es un conjunto desordenado" (no repite las teclas y las teclas no pueden tener un orden predefinido) ... Incluso el xml2json de ZF está equivocado (!) Porque no preserva exactamente la estructura XML.
Todas las soluciones aquí tienen problemas con este XML simple,
... La solución @FTav parece mejor que la solución de 3 líneas, pero también tiene un pequeño error cuando se prueba con este XML.
La solución anterior es la mejor (para una representación sin pérdidas)
La solución, hoy conocida como jsonML , es utilizada por el proyecto Zorba y otros, y fue presentada por primera vez en ~ 2006 o ~ 2007, por (por separado) Stephen McKamey y John Snelson .
Produce
Ver http://jsonML.org o github.com/mckamey/jsonml . Las reglas de producción de este JSON se basan en el elemento JSON-analog,
Esta sintaxis es una definición y recurrencia de elementos , con
element-list ::= element ',' element-list | element
.fuente
Después de investigar un poco todas las respuestas, se me ocurrió una solución que funcionaba bien con mis funciones de JavaScript en todos los navegadores (incluidas las consolas / herramientas de desarrollo):
Básicamente, crea un nuevo DOMDocument, carga y un archivo XML en él y atraviesa cada uno de los nodos y los niños obteniendo los datos / parámetros y exportándolos a JSON sin los molestos signos "@".
Enlace al archivo XML .
fuente
Esta solución maneja espacios de nombres, atributos y produce resultados consistentes con elementos repetitivos (siempre en matriz, incluso si solo hay una ocurrencia). Inspirado en el sxiToArray () de ratfactor .
Ejemplo:
fuente
La respuesta de FTav le pareció la más útil, ya que es muy personalizable, pero su función xml2js tiene algunos defectos. Por ejemplo, si los elementos secundarios tienen nombres de etiqueta iguales, todos se almacenarán en un solo objeto, esto significa que el orden de los elementos no se conservará. En algunos casos, realmente queremos preservar el orden, por lo que es mejor almacenar los datos de cada elemento en un objeto separado:
Así es como funciona. Estructura xml inicial:
Resultado JSON:
fuente
Parece que la
$state->name
variable contiene una matriz. Puedes usardentro del
foreach
para probar eso.Si ese es el caso, puede cambiar la línea dentro
foreach
depara corregirlo
fuente
fuente
Si es usuario de ubuntu, instale el lector xml (tengo php 5.6. Si tiene otro, busque el paquete e instálelo)
fuente