Usamos cookies para medir audiência e melhorar sua experiência. Você pode aceitar ou recusar a qualquer momento. Veja sobre o iMasters.
Olá pessoal! Estou construindo um leitor de Feeds. Até pouco tempo ia tudo certo, até resolver que queria que esse leitor exibisse a imagem do determinado post.
Porém, ao dar uma pesquisada nos feeds de alguns sites (todos pelo FeedBurner) encontrei a imagem dos posts dentro da tag <content:ecoded>. Contudo, o caminho da imagem está em HTML (<img src="http://... />)
Então meu problema é o seguinte, como eu vou chamar essa imagem? O PHP não reconhece o ":" da tag e não sei com importo apenas a URL da imagem.
O código até agora está assim:
$title = $xml->channel->item[$i]->title;
$link = $xml->channel->item[$i]->link;
$hora = $xml->channel->item[$i]->pubDate;
$description = $xml->channel->item[$i]->description;
$imagem = $xml->channel->item[$i]-> ...??? ; <- ESSE É O PROBLEMA
$hora = strftime("%Y/%m/%d %H:%M:%S", strtotime($hora));
Alguém pode me dar uma ajudinha de como eu importo apenas a URL da imagem??
Obrigado!! :D
<item>
<title>Título..............</title>
<link>[http://www.sitedeexemplo.com](http://www.sitedeexemplo.com)
<comments></comments>
<pubDate></pubDate>
<dc:creator></dc:creator>
<category></category>
<category></category>
<guid isPermaLink="false"></guid>
<description><description>
<content:encoded><![CDATA[<p><a href="link"><img src="URL DA IMAGEM" alt="" border="0" /><a>
</content:encoded> -> **É aqui que o bicho pega :D, gostaria de pegar a "URL DA IMAGEM"**
<slash:comments>0</slash:comments>
</item>
Eu gostaria de importar apenas a informação "URL DA IMAGEM", na tag <content:encoded>. Porém, como faço isso em PHP?
Olha não tenho certeza se e assim mesmo mais faça o teste por que eu nem sei para que isso ira servir
crie um arquivo com a extensão .php
Ha se puder falar para que isso serve eu agradeço
<?php include_once("conexao.php");
header("Content-Type: application/xml; charset=UTF-8");
echo '<?xml version="1.0" encoding="UTF-8"?>';
?>
<?php
$seleciona = mysql_query("SELECT * FROM tabela ORDER BY id DESC");
$conta = mysql_num_rows($seleciona);
if($conta <= 0){
echo "Não ha urls";
}else{
while($mostra = mysql_fetch_array($seleciona)){
echo"
<item>
<title>".$mostra['titulo-img']." - seusite</title>
<link>http://www.sitedeexemplo.com</link>
<comments></comments>
<pubDate>".$mostra['data-criado']."</pubDate>
<dc:creator>".$mostra['autor']."</dc:creator>
<category>".$mostra['categoria1']."</category>
<category>".$mostra['categoria2']."</category>
<guid isPermaLink=\"false\"></guid>
<description><description>
<content:encoded><! [CDATA [<p><a href=\"www.site.com.br/pasta-img/".$mostra['url-img']."\"><img src=\"pasta-img/".$mostra['url-img']."\" alt=\"".$mostra['titulo-img']."\" border="0" /><a></ p>]]>
</content:encoded>
<slash:comments>0</slash:comments>
</item>";
}
?>Você pode utilizar a classe DOMDocument para fazer isso:
Exemplo:
<?php
$xml = <<<XML
<?xml version="1.0" encoding="UTF-8"?>
<item>
<title>Título..............</title>
<link>http://www.sitedeexemplo.com</link>
<content:encoded><a href="link"><img src="URL DA IMAGEM" alt="" border="0" /><a></content:encoded>
</item>
XML;
$DOMDocument = new DOMDocument( '1.0', 'UTF-8' );
$DOMDocument->preserveWhiteSpace = false;
$DOMDocument->loadXML( $xml, LIBXML_NOWARNING | LIBXML_NOERROR );
$result = array( );
foreach( $DOMDocument->getElementsByTagName( 'item' ) as $content )
{
$nodes = array( );
foreach( $content->childNodes as $child )
{
if( $child->nodeName == 'encoded' )
{
preg_match( '/src="([^"]+)/', $child->nodeValue, $match );
$nodes[ $child->nodeName ] = $match[ 1 ];
}
else
{
$nodes[ $child->nodeName ] = $child->nodeValue;
}
}
$result[ ] = $nodes;
}
var_dump( $result );
?>
Saída:
array
0 =>
array
'title' => string 'Título..............' (length=21)
'link' => string 'http://www.sitedeexemplo.com' (length=28)
'encoded' => string 'URL DA IMAGEM' (length=13)Carlos, não seria melhor usar XPath ?
:mellow:
Hehehe, esqueci de que ele queria apenas o src da imagem :yay:
Bom, o script fica muito simples
<?php
$DOMDocument = new DOMDocument( '1.0', 'UTF-8' );
$DOMDocument->preserveWhiteSpace = false;
$DOMDocument->loadXML( $xml, LIBXML_NOWARNING | LIBXML_NOERROR );
$DOMXPath = new DOMXPath( $DOMDocument );
preg_match( '/src="(?P<src>[^"]+)/', $DOMXPath->query( './/encoded' )->item( 0 )->nodeValue, $match );
var_dump( $match[ 'src' ] ); // string 'URL DA IMAGEM' (length=13)
?>
:thumbsup:Carlos, tentei a função DOM e deu certo!
Porém, eu carrego vários endereços de FEEDS diferentes e nem todos apresentam a tag <content:encoded> no XML, e quando esses feeds passam pela função DOM dá o seguinte erro:
PHP Warning: DOMXPath::query() [<a href='domxpath.query'>domxpath.query</a>]: Undefined namespace prefix in Web\importar-feeds.php on line 69
PHP Warning: DOMXPath::query() [<a href='domxpath.query'>domxpath.query</a>]: Invalid expression in
Wer\importar-feeds.php on line 69
Existe alguma função que verifica a linha "$imagem_path = $DOMXPath->query(".//channel/item[$i]/content:encoded");", se for verdadeiro executar o script, se for falso, ou seja, a tag não existir no respectivo XML, dar um "continue;" no loop
É só você fazer uma verificação
<?php
$DOMXPath = new DOMXPath( $DOMDocument );
$src = $DOMXPath->query( './/encoded' );
if( $src->length )
{
preg_match( '/src="(?P<src>[^"]+)/', $src->item( 0 )->nodeValue, $match );
var_dump( $match[ 'src' ] ); // string 'URL DA IMAGEM' (length=13)
}
?>$DOMXPath = new DOMXPath( $DOMDocument );
$imagem_path = $DOMXPath->query('.//channel/item[$i]/content:encoded');
/** Apos Carregado, nova instancia de DOMXPath*/
if ($imagem_path->length) {
preg_match( '/src="(?P<src>[^"]+)/', $imagem_path->nodeValue, $match );
$imagem = print_r ( $match[ 'src' ] ) ;
}else{
continue;
} //Se a imagem não existir no feed, continua
Olá de novo! =D
Esse é meu código, não tem muito segredo do IF acima, porém, se o $imagem_path não for válido, o PHP não chega no IF, o erro aparece antes da verificação. Seria questão de output? To meio perdido aqui rsrs
valeeu! =D
Então seria melhor utilizar foreach
<?php
$xml = <<<XML
<?xml version="1.0" encoding="UTF-8"?>
<root>
<item>
<title>Título..............</title>
<link>http://www.sitedeexemplo.com</link>
</item>
<item>
<title>Título..............</title>
<link>http://www.sitedeexemplo.com</link>
<content:encoded><a href="link"><img src="URL DA IMAGEM" alt="" border="0" /><a></content:encoded>
</item>
<item>
<title>Título..............</title>
<link>http://www.sitedeexemplo.com</link>
<content:encoded></content:encoded>
</item>
<item>
<title>Título..............</title>
<link>http://www.sitedeexemplo.com</link>
<content:encoded><a href="link"><img src="URL DA IMAGEM" alt="" border="0" /><a></content:encoded>
</item>
</root>
XML;
$DOMDocument = new DOMDocument( '1.0', 'UTF-8' );
$DOMDocument->preserveWhiteSpace = false;
$DOMDocument->loadXML( $xml, LIBXML_NOWARNING | LIBXML_NOERROR | LIBXML_NOEMPTYTAG | LIBXML_NOBLANKS );
$DOMXPath = new DOMXPath( $DOMDocument );
foreach( $DOMXPath->query( './/encoded' ) as $content )
{
foreach( $content->childNodes as $child )
{
preg_match( '/src="([^"]+)/', $child->nodeValue, $match );
$nodes[ ] = $match[ 1 ];
}
}
var_dump( $nodes );
?>
Saída
array
0 => string 'URL DA IMAGEM' (length=13)
1 => string 'URL DA IMAGEM' (length=13)Olá de novo! =D
Desculpe a persistência, porém, meu continua. Caso o feed que eu estou analisando não tenha a tag <content:encoded> o php retorna um erro. Tentei verificar com um IF porém tbm não deu certo.
Veja
$DOMDocument = new DOMDocument( '1.0', 'utf-8' );
/*
* Não preservar espaços em branco redundantes
*/
$DOMDocument->preserveWhiteSpace = false;
/*
* Carrega o XML com o link do RSS do Forum
*/
$DOMDocument->load( $feeds );
/*
* Apos Carregado, nova instancia de DOMXPath
*/
$DOMXPath = new DOMXPath( $DOMDocument );
/*
* Então, faço uma consulta, que no caso seria
* ./ = elemento raiz { <rss> }
* /channel = elemento filho de { rss }
* /item = elemento filho de channel, e pai de qualquer tag que esteje dentro dele
* [1] Exibir apenas o primeiro.. Apenas pra output
*/
foreach($DOMXPath->query(".//channel/item[$j]/content:encoded" ) as $RSSNodes ){
/*
* Então como já cheguei nos filhos de item
* Pra cada um deles, vai ser attribuido a variavel $RSSNode ..
* Como já expliquei na parte1, ->nodeValue, resgata o valor dos elementos.
*/
foreach( $RSSNodes->childNodes as $RSSNode ){
preg_match( '/src="(?P<src>[^"]+)/', $RSSNode->nodeValue, $match );
$imagem = print_r ( $match[ 'src' ] ) ;
echo "<br />";
}
}
Posso colocar IF ou qualquer outra coisa, porém quando ele chega na linha
foreach($DOMXPath->query(".//channel/item[$j]/content:encoded" ) as $RSSNodes ){
retorna um erro, pois não encontra a expressão .//channel/item[$j]/content:encoded
Será que posso verificar um feed se existe a tag <content:encoded> antes de ele entrar nesse erro?
Cara, está te faltando ler um pouco mais as respostas, eu te dei um exemplo funcionando em que não existe a tag <content:encoded> e em outra ela não possui valor.
Se as constantes colocadas junto com o método loadXML estão lá é por um motivo e você não deve simplesmente deixá-las de fora. Não sabe para que serve? Procure por libxml option constants.
$DOMDocument->loadXML( $xml, LIBXML_NOWARNING | LIBXML_NOERROR | LIBXML_NOEMPTYTAG | LIBXML_NOBLANKS );
Cara ... é melhor usar:
libxml_use_internal_errors ( true ) ;
Olá! Realmente deixei de fora esses atributos do XML. Porém, não sei se é por causa que carrego ENDEREÇOS DE FEEDS diferentes, continuava ocorrendo o mesmo erro, talvez precise desativar alguma outra função de erros que não está presente no respectivo código acima. Porém, antes de começar a leitura do XML fiz uma verificação:
$codigo_fonte = file_get_contents($feeds);
$pos = strpos($codigo_fonte, "<content:encoded>");
if ($pos===true){...}
Funcionou. Bem, agora é só partir em pesquisas sobre esses atributos de ERROS no XML.
Obrigado pelas respostas e solução!!! :thumbsup:
Configure seu código para exibir TODAS as mensagens de erro, adicionando este código à primeira linha do script.
Tem como postar o xml?