Ir para conteúdo

POWERED BY:

Arquivado

Este tópico foi arquivado e está fechado para novas respostas.

Andrey Knupp Vital

[Resolvido] DOMDocument - XML { PHP }, Parte - 2

Recommended Posts

Então gente, como falei na Parte 1 Sobre

Como anexar filhos a um Elemento, é navegar pelo XML, nessa parte, vou fazer um exemplo mais pratico de como encontrar

um elemento por uma definição mais avançada, e aí que entra o XPath , alguém conhece ? já ouviu falar ?

ok, é ele quem usamos para poder navegar no documento de uma maneira mais fácil .. e achar alguns elementos no documento

também mais facilmente, vejam o seguinte .. na aula passada . tínhamos o seguinte Heredoc com uma estrutura XML de um álbum

aí vem a cabeça 'do que adianta guardar fotografias de usuário, álbuns. sendo que não podemos identificar de quem é aquele álbum ?'

quem pensa isso tá muito enganado, ou quem acha que não é possível ... ^_^

 

Então, nos paramos no seguinte XML na parte anterior ..

<?php
$XML = <<<XML
<?xml version="1.0" encoding="utf-8"?>
<albums>
  <album usuario="0669">
       <capa src="meuPrimeiroAlbum.jpg" />
       <foto id="1" classificacao="5" src="umaFoto1.jpg" />
       <foto id="2" classificacao="5" src="umaFoto2.jpg" />
       <foto id="3" classificacao="4" src="umaFoto3.jpg" />
       <foto id="4" classificacao="2" src="umaFoto4.jpg" />
       <foto id="5" classificacao="1" src="umaFoto5.jpg" />
       <foto id="6" classificacao="2" src="umaFoto6.jpg"/> 
  </album>
</albums>
XML;

 

Quem viu a parte anterior, eu deixei explicado como navegar nesse XML usando métodos normais como getElementsByTagName, entre outros ..

Mais agora um exemplo mais pratico é mais focado, vamos usar um DOMXPath, para encontrar os albuns do usuário, vou armazenar o ID do usuário

em uma variável normalmente, mais quem for tentar fazer isso usando XML

no que certamente guarda em uma session, ou cookie .. da pra fazer do mesmo jeito, então vamos começar

eu tenho apenas 1 álbum então vamos criar outros álbuns, porem com id's de usuário diferentes, para terem uma noção melhor

de como funciona a seleção desses elementos com XML.

 

Então, temos o seguinte código

<?php
        #Instancia da classe DOMDocument, versão 1.0, codificaçao utf-8
        $DOMDocument = new DOMDocument( '1.0', 'utf-8' );

        #formatOutput como true para uma boa idençao
        $DOMDocument->formatOutput = true;

        #Não preservar espaços em branco redundantes
        $DOMDocument->preserveWhiteSpace = false;

        #Carrega um xml da string heredox $XML
        $DOMDocument->loadXML( $XML );

        #Pega o filho de albums, no caso é album
        $Albums = $DOMDocument->getElementsByTagName( 'albums' )->item(0);

        #Então cria um novo album 
        $AlbumTag =  $DOMDocument->createElement( 'album' );

        #Coloco o id de usuario que pertençe a tal album
        $AlbumTag->setAttribute( 'usuario', 1589 );

        #Anexa o elemento pai 'album' em 'albums'
        $Album = $Albums->appendChild( $AlbumTag );

        #Então, cria o elemento capa, que sera anexado para album
        $Capa = $DOMDocument->createElement( 'capa' );

        #Seta o attributo src, no caso um path para capa do album
        $Capa->setAttribute( 'src', 'capas/umaCapa.jpg' );

        #Em album, anexa a tag Capa
        $Album->appendChild( $Capa );

        #Array de fotos, usado apenas pra addiantar o trabalho . 
        $Fotos = Array( 'fotoDoUsuario1589.jpg', 'fotoDoUsuario1589.png', 'fotoDoUsuario1598.jpg' );

        #Array de classificaçoes
        $Classificacoes = Array( 5, 2, 3 );
        /*
         * Loop para criar cada tag foto de acordo com a quantidade no array
         */
        for( $x = 0; $x < sizeOf($Fotos); ++$x ){
             $FotoTag = $DOMDocument->createElement( 'foto' );
             $FotoTag->setAttribute( 'id', $x+1 );
             $FotoTag->setAttribute( 'classificacao', $Classificacoes[$x] );
             $FotoTag->setAttribute( 'src', $Fotos[$x] );
             $Album->appendChild( $FotoTag );
        }
        #Imprime o xml apos as modificaçoes
        echo $DOMDocument->saveXML();

 

Temos o seguinte output apos o codigo executado ..

<?xml version="1.0" encoding="utf-8"?> 
<albums> 
 <album usuario="0669"> 
   <capa src="meuPrimeiroAlbum.jpg"/> 
   <foto id="1" classificacao="5" src="umaFoto1.jpg"/> 
   <foto id="2" classificacao="5" src="umaFoto2.jpg"/> 
   <foto id="3" classificacao="4" src="umaFoto3.jpg"/> 
   <foto id="4" classificacao="2" src="umaFoto4.jpg"/> 
   <foto id="5" classificacao="1" src="umaFoto5.jpg"/> 
   <foto id="6" classificacao="2" src="umaFoto6.jpg"/> 
 </album> 
 <album usuario="1589"> 
   <capa src="capas/umaCapa.jpg"/> 
   <foto id="1" classificacao="5" src="fotoDoUsuario1589.jpg"/> 
   <foto id="2" classificacao="2" src="fotoDoUsuario1589.png"/> 
   <foto id="3" classificacao="3" src="fotoDoUsuario1598.jpg"/> 
 </album> 
</albums>

 

Agora temos 2 álbuns, de dois usuários diferentes, no caso é pouco, mais e neles que vamos trabalhar ..

Após o usuário se logar, ele tem que ter a possibilidade de ver os álbuns criados, alterar, é remover ..

tal foto, ou álbum, mais primeiro, temos que saber qual álbum é de quem .. sem isso não valeria de nada salvar

essas informações no XML para um fluxo de usuários usando seu sistema, pois você não teria como identificar

esses álbuns pra tal Usuário, então mãos a obra, vamos identificar qual álbum pertence a qual usuário, é montar um array com essas

informações retornadas após a consulta

 

Então, o XPath é uma linguagem para endereçar elementos de documentos XML

utiliza expressões de caminho define uma biblioteca de funções

publicada como W3C Recommendation em Novembro/1999

projetada para ser utilizada por XSLT, XPointer e outros parsers de XML

 

Então para o seguinte XML vou falar algumas coisas que sei sobre o XPath ..

Para o seguinte XML

<?xml version="1.0" encoding="utf-8"?> 
<albums> 
 <album usuario="0669"> 
   <capa src="meuPrimeiroAlbum.jpg"/> 
   <foto id="1" classificacao="5" src="umaFoto1.jpg"/> 
   <foto id="2" classificacao="5" src="umaFoto2.jpg"/> 
   <foto id="3" classificacao="4" src="umaFoto3.jpg"/> 
   <foto id="4" classificacao="2" src="umaFoto4.jpg"/> 
   <foto id="5" classificacao="1" src="umaFoto5.jpg"/> 
   <foto id="6" classificacao="2" src="umaFoto6.jpg"/> 
 </album> 
 <album usuario="1589"> 
   <capa src="capas/umaCapa.jpg"/> 
   <foto id="1" classificacao="5" src="fotoDoUsuario1589.jpg"/> 
   <foto id="2" classificacao="2" src="fotoDoUsuario1589.png"/> 
   <foto id="3" classificacao="3" src="fotoDoUsuario1598.jpg"/> 
 </album> 
</albums> 

  • Expressões de caminho:
    • /albums = "selecione o elemento raiz ("albums")
    • /albums/album = "selecione todos os elementos "albums" de "album"
    • /albums/album/foto = "selecione todos os elementos "foto" de todos os elementos "album" de "albums"

  • Funçoes Basicas para trabalhar com cadeias de caracteres, números e valores Booleanos
    • /album/foto[@id>1] = "selecione todos os elementos "album"
      que possuem um elemento "foto" com o attributo id maior do que 1"
    • Os operadores vocês já conhecem, são os mesmos
    • < = menor
    • <= = menor ou igual a
    • = = igual a
    • != = diferente de
    • > = maior
    • >= = maior ou igual

  • Expressões booleanas
    • Operador [ or ], Disjunçao, Exemplo ( @id < 1 or @id > 3 )
    • Operador [ and ], conjunçao, Exemplo ( @id = 1 and @classificacao = 3 )

  • Funções sobre conjuntos de elementos
    • local-name() retorna o nome local de um nó. Um nó normalmente consiste de um prefixo, seguido de ":", seguido de um nome local
    • name() retorna o nome de um nó
    • namespace-uri() retorna a URI do namespace de um dado nó
    • position() retorna a posição, na lista de nós, do nó que está sendo processado

  • Funções pré-definidas, Funções sobre cadeias de caracteres
    • concat(), retorna a concatenação dos argumentos, Exemplo: string=concat( valor 1, valor 2, ..)
    • contains(), retorna verdadeiro, se o segundo argumento está contido no primeiro Exemplo: bool=contains( valor, substr )
    • normalize-space(), remove os brancos do começo e do fim da cadeia, Exemplo: normalize-space(' O Exemplo ') = 'O Exemplo'

  • Funçoes pré-definidas, Funçoes numéricas
    • ceiling(), retorna o menor inteiro maior ou igual ao argumento Exemplo: numero = ceiling( numero )
    • floor(), retorna o maior inteiro que não é maior do que o argumento Exemplo: numero = floor( numero )
    • number(), converte o argumento para numérico Exemplo: number = numero( valor )
    • round(), arredonda o argumento para o inteiro mais próximo Exemplo: round(3.14) = 3
    • sum(), retorna o valor total conjunto de nós Exemplo: sum(/cd/preco)

  • Funções pré-definidas, Funções Booleanas
    • boolean(),converte o argumento para boolean e retorna false ou true Exemplo: bool=boolean(valor)
    • false(), constante false
    • true(), constante true
    • not(), negação Exemplo: bool=not( condiçao ), not( false() )
    • lang(), retorna true, se a língua do argumento é aquela especificada em xsl:lang, caso contrário retorna false Exemplo: bool=lang( linguagem )


  • Funçoes pré-definidas, Funções sobre conjuntos de nós

    • count(), retorna o número de nós de um conjunto de nós id=count( listaDeElementos )
    • id(), seleciona elementos pelo seu unique ID Exemplo: listaDeElementos=id( valor )
    • last(), retorna a posição do último nó da lista de nós em processamento Exemplo: elemento[last()]

  • Outros tipos de expressões, Expressões numéricas

    • Operador [+] ( adição ) Exemplo: 6+4 = 10
    • Operador [-] ( subtração ) Exemplo: 6-4 = 2
    • Operador
    • ( multiplicação ) Exemplo: 6*4 = 24
    • Operador [div] ( divisão ) Exemplo: 8 div 4 = 2
    • Operador [mod] ( resto da divisão ) Exemplo: 5 mod 2 = 1

  • Expressões de caminho de localização
    • album ( todos os elementos "album" filhos do nó corrente )
    • * ( todos os elementos filhos do nó corrente )
    • text() ( todos os elementos cujo conteúdo é texto e que são filhos do nó corrente )
    • ../@local ( o atributo "local" do pai do nó corrente )
    • valor[@moeda=dolar] ( todos os elementos "valor" filhos do nó corrente com um atributo "moeda" com valor "dolar" )
    • leilao[5][@local=SP] ( quinto elemento "leilao" filho do nó corrente, se ele tiver um atributo "local" com valor "SP" )
    • leilao[@local and @leiloeiro] ( todos os elementos "leilao" filhos do nó corrente que tenham atributos "local" e "leiloeiro" )

  • Expressões de caminho de localização, Sintaxe abreviada para caminhos de localização
    • child::, Exemplo: album abrevia child::album
    • Abreviação ( @ ) , Expressão: attribute:: | Exemplo: valor[@moeda=dolar] abrevia child::valor[attribute::moeda=dolar]
    • Abreviação ( . ), Expressão: self::node() | Exemplo: .//album abrevia self::node()/descendent-or-self::node()/child::album
    • Abreviação ( .. ), Expressão: parent::node() | Exemplo: ../album abrevia parent::node()/child::album
    • Abreviação ( // ), Expressão: /descendant-or-self::node()/ | Exemplo: //album abrevia /descendent-or-self::node()/child::album
    • child::valor[valor=1000] todos os elementos filhos do nó corrente com elemento "valor" igual a 1000
    • child::album[position()=1] primeiro elemento "album" filho do nó corrente
    • child::album[position()=last()] último elemento "album" filho do nó corrente
    • child::album[position()=last()-1] penúltimo elemento "album" filho do nó corrente
    • child::album[position()=last()<6] 5 primeiros elementos "album" filhos do nó corrente
    • /descendant::album[position()=7] sétimo elemento "album" no documento
    • child::valor[attribute::moeda=dolar] todos os elementos "valor" do nó corrente cujo atributo "moeda" possui valor "dolar"
    • child::album = todos os elementos "album" filhos do nó corrente
    • child::* = todos os filhos do nó corrente
    • attribute::id = atributo "id" do nó corrente (se não existir, retorna o conjunto vazio)
    • attribute::* = todos os atributos do nó corrente
    • child::text() = os nós de texto que são filhos do nó corrente
    • child::node() = os filhos do nó corrente
    • descendant::album = todos os elementos "album" descendentes do nó corrente
    • ancestor::album = todos os elementos "album" ancestrais do nó corrente
    • child::*/child::valor = elementos "valor" netos do nó corrente
    • / = raiz do documento

    • Predicados
    • um predicado filtra um conjunto de nós, criando um novo conjunto de nós
    • um predicado é envolto em " [ " e " ] ", colchetes

    • Eixos: define um conjunto de nós, com relação ao nó corrente
    • ancestor, ancestrais do nó corrente
    • parent, pai do nó corrente
    • child, filhos do nó corrente
    • descendant, descendentes do nó corrente
    • following, tudo que ocorre no documento após o tag de final do nó corrente
    • attribute, atributos do nó corrente
    • namespace, todos os namespaces do nó corrente

    • Caminho de localização, um passo consiste de:
    • um eixo: especifica o relacionamento, na árvore,entre o nó corrente e os nós selecionados pelo passo
    • um teste de nó: especifica um tipo de nó ou um nome de elemento para os nós a serem selecionados pelo passo
    • zero ou mais predicados:utilizam expressões para refinar o conjunto de nós selecionados pelo passo
    • Sintaxe de um passo eixo::testeDeNó[pedicados]
    • exemplo: child::valor[valor=1000]

Então, vemos o codigo

<?php
        #Armazeno uma variavel com o ID pra tal usuário
        $IDUsuario = 1589;
        foreach( $DOMXPath->query(".//album[@usuario=".$IDUsuario."]/foto/parent::node()") as $Nodes ){
                 foreach( $Nodes->childNodes as $Node ){
                          echo 'Elemento (', $Node->nodeName, ')',' Attributo src = ', $Node->getAttribute('src'), '<br />';
                 }
        }

Retorna

  Citar

Elemento (capa) Attributo src = capas/umaCapa.jpg

Elemento (foto) Attributo src = fotoDoUsuario1589.jpg

Elemento (foto) Attributo src = fotoDoUsuario1589.png

Elemento (foto) Attributo src = fotoDoUsuario1598.jpg

 

Estamos selecionando o elemento album, onde o attributo usuario é igual a $IDUsuario, então avanço para tag foto, e seus parentes

Passando isso para um array, ficaria

<?php
        #Armazeno uma variavel com o ID pra tal usuário
        $IDUsuario = 1589;
        foreach( $DOMXPath->query(".//album[@usuario=".$IDUsuario."]/foto/parent::node()") as $Nodes ){
                 foreach( $Nodes->childNodes as $Node ){
                          $FotosSRC[] = $Node->getAttribute('src');
                          $FotosID[] = $Node->getAttribute('id');
                          $FotosClassificacao[] = $Node->getAttribute('classificacao');
                 }
                 $Fotos[] = $FotosSRC;
                 $Id[] = $FotosID;
                 $classificacao[] = $FotosClassificacao;
        }
        echo '<pre>';
        print_r( $Fotos );
        print_r( $Id ) ;
        print_r( $classificacao );

 

Retorna:

Array
(
   [0] => Array
       (
           [0] => capas/umaCapa.jpg
           [1] => fotoDoUsuario1589.jpg
           [2] => fotoDoUsuario1589.png
           [3] => fotoDoUsuario1598.jpg
       )

)
Array
(
   [0] => Array
       (
           [0] => 
           [1] => 1
           [2] => 2
           [3] => 3
       )

)
Array
(
   [0] => Array
       (
           [0] => 
           [1] => 5
           [2] => 2
           [3] => 3
       )

)

 

Enfim .. por enquanto é só , vou dar mais exemplos na parte3 !

Aguardem ..

Compartilhar este post


Link para o post
Compartilhar em outros sites

×

Informação importante

Ao usar o fórum, você concorda com nossos Termos e condições.