Como pegar parte do conteúdo (dados) de outro site com PHP
28 de março de 2008 11 comentários
Pegar parte do conteúdo de outro site foi a tarefa que tive que fazer. Pensei que seria bem fácil, mas as coisas não saíram exatamente como eu planejava… Felizmente, consegui! Aprenda, você, também, como coletar informações de outros sites na internet.
A missão: pegar parte do conteúdo de um site
Hoje, no trabalho, tive a missão de “puxar” alguns dados de um site para “enxertar” num trecho de um web site que estou ajudando a desenvolver. Quando a tarefa me foi passada, logo lembrei de uma ocasião em que um amigo fez a mesma coisa (e, na época, ele me explicou, mais ou menos, com o fez). Pensei que seria muito fácil realizar a tarefa, mas, na hora, “lembrei” que não sou tão bom quanto o Gevã… rsrs
A solução: funções nativas do PHP e expressões regulares
Passei para pesquisas na web, procurando desesperadamente material de referência sobre expressões regulares (que, como verão, é um dos pilares para se conseguir pegar parte do conteúdo de outro site). Procura daqui, procura de lá, até bate-papo com o Gevã rolou para eu tentar entender melhor as tais expressões regulares. Até que, utilizando um pouco de “gambiarra”, consegui realizar meu objetivo.
A primeira coisa a se fazer, é pegar o conteúdo da página inteira que se quer “manipular”. Para tal, usa-se, por exemplo, a função file_get_contents(). Jogando o conteúdo do site numa variável, ficaria assim (vou fazer o exemplo com o mesmo site que tive que mexer):
1 | $url = file_get_contents('http://www.bcb.gov.br/'); |
Pronto, agora a variável $url contém, em string, todo o conteúdo da página inicial do BCB.
Expressões regulares
Até aqui foi fácil; o difícil foi pegar somente o trecho da página que eu queria… Para isso, é preciso usar expressões regulares!
Caso você não saiba o que são expressões regulares, aí vai uma sucinta (e incompleta…) explicação de o que são expressões regulares, da Wikipédia:
Uma expressão regular, na Informática, define um padrão a ser usado para procurar ou substituir palavras ou grupos de palavras. É um meio preciso de se fazer buscas de determinadas porções de texto.
Com as expressões regulares é possível identificar trechos de palavras ou grupos de palavras que correspondem (”match“) a um determinado padrão (”pattern“), que é “regular”.
O PHP tem várias funções nativas para trabalhar com expressões regulares. Basta saber para o que cada uma serve e usar da meneira correta.
Bem, o próximo passo para resolução do problema é identificar o padrão que se quer extrair do site. No caso, eu precisei de uma tabela com algumas taxas cambiais (encontra-se à direita, no site do BCB). Observando o código fonte, vi que as informações estão em uma tabela (abordagem semanticamente correta!); além disso, esta tabela está envolta entre os comentários HTML “<!- - INICIO INDICADORES - ->” e “<!- - FIMINDICADORES - ->”. Isso é uma coisa boa, já que facilita bastante a “identificação do padrão”.
Explicando melhor: o padrão procurado, no caso, é tudo o que está entre os comentários HTML “<!- - INICIO INDICADORES - ->” e “<!- - FIMINDICADORES - ->”. Toda a tabela está aí, para a minha felicidade! :-)
Então, tudo o que é preciso fazer é utilizar uma função PHP (para o caso, escolhi a preg_match_all()) para procurar uma expressão regular dentro da variável $url, que contém toda a primeira página do site em que está a tabela.
Depois de muito tempo testando vááárias expressões regulares, cheguei à conclusão que faria uma pequena mutreta. Mas, antes, deixe-me mostrar como está o código até agora.
1 2 | $url = file_get_contents('http://www.bcb.gov.br/'); preg_match_all('/ORES-->(.+)<!--/s', $url, $conteudo); |
Explicando: o primeiro argumento da função, é o padrão que quero procurar; o segundo, é onde vou procurar; o terceiro, guarda em um array todas as ocorrências da expressão procurada. Para a maioria dos casos, talvez já estivesse bom, por aqui; entretanto, no problema que tive, ainda é preciso mais algumas linhas de código.
No momento, a variável $conteudo contém um array com as ocorrências encontradas. Usando um print_r(), descobri em qual posição, exatamente, o que eu procurava estava: $conteudo[0][0].
Fazendo uma “mutreta”
Para fazer a tal “mutreta”, jogo o conteúdo desta posição da matriz para uma outra variável (para facilitar a manipulação).
1 2 3 | $url = file_get_contents('http://www.bcb.gov.br/'); preg_match_all('/ORES-->(.+)<!--/s', $url, $conteudo); $exibir = $conteudo[0][0]; |
Havia trechos do que me foi retornado (ou seja, da tabela com as taxas cambiais) que eu não queria que aparecessem no site (como alguns links). Então, resolvi retirá-los através da função str_replace(), que substitui trechos de strings. É possível, como argumento, passar um array. Então, por enquanto e quase no fim, o código está assim:
1 2 3 4 5 | $url = file_get_contents('http://www.bcb.gov.br/'); preg_match_all('/ORES-->(.+)<!--/s', $url, $conteudo); $exibir = $conteudo[0][0]; $retirar = array('mais moedas','atas Copom','mais detalhes','ORES-->','<!--'); $exibir = str_replace($retirar, '', $exibir); |
Ou seja: sempre que aparecer alguns dos itens do array $retirar em $exibir, será substituído por “” (nada…). Perceba que os últimos dois elementos do array são “poluições” desnecessárias, que vieram devido à minha preguiça de fazer uma expressão regular mais elaborada. :-)
Finalizando…
Depois disso, basta mandar exibir na tela o que “sobrou” do conteúdo retira da página inicial do site do BCB.
1 2 3 4 5 6 | $url = file_get_contents('http://www.bcb.gov.br/'); preg_match_all('/ORES-->(.+)<!--/s', $url, $conteudo); $exibir = $conteudo[0][0]</span>; $retirar = array('mais moedas','atas Copom','mais detalhes','ORES-->','<!--'); $exibir = str_replace($retirar, '', $exibir); echo $exibir; |
E se o servidor não permite a função file_get_contents() ?
Há muitos servidores que, por motivos diversos (principalmente “segurança”), não permitem que se utilize a função file_get_contents(). Para esses casos, é possível colocar numa variável alguma página externa utilizando o seguinte código (depois você procura as explicações no manual oficial do PHP):
1 2 3 4 5 6 7 | $ch = curl_init(); $timeout = 0; curl_setopt($ch, CURLOPT_URL, 'O_SITE_QUE_VOCE_QUER'); curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1); curl_setopt($ch, CURLOPT_CONNECTTIMEOUT, $timeout); $conteudo = curl_exec ($ch); curl_close($ch); |
Então, o conteúdo da página “O_SITE_QUE_VOCE_QUER” estará na variável $conteudo.
Conclusão
Então, pessoal, para se retirar uma parte do conteúdo de um web site (utilizando PHP), os passos são:
- Saber em qual página está o conteúdo que se precisa;
- Jogar o conteúdo do site em uma variável;
- Extrair o trecho que se quer utilizando expressões regulares;
- Se preciso, cortar mais algumas coisas do resultado da ER;
- Exibir em tela o resultado final.
O grande pulo do gato, neste caso, é saber mexer com expressões regulares; coisa que, sinto informar, só se aprende fazendo! E fazendo muito! Leia as referências no fim deste artigo e procure na internet mais material a respeito.
Uma outra coisa importante é o seguinte: tenha sempre em mente que, como você está pegando o conteúdo de um site, caso este altere sua estrutura, muito provavelmente será preciso alterar a expressão regular, também.
Fique ciente de uma coisa: se você, desenvolvedor web, ainda não precisou usar expressões regulares, pode ter certeza de que sua hora vai chegar!
Referências Nacionais
Expressões Regulares - Guia de Consulta Rápida
Este é o guia de Aurélio Marinho Jargas, excelente para se aprender expressões regulares e para se consultar nos momentos de aperto!
Artigo do Viva o Linux, de Marcelo Santos Araujo, com uma introdução sobre expressões regulares.
Referências Internacionais
Site especialmente dedicado às expressões regulares.
Biblioteca virtual de expressões regulares.
Para testar expressões regulares em tempo real!















Excelente, sr.Tárcio! Você pegou um limão e fez uma limonada. O artigo ficou muito bom, parabéns!
Muito obrigado, Seu Gevã!
50% é crédito seu! =D
Abraços!
Vale lembrar que com a utilização de XHTML na estrutura das páginas isso é desnecessário, uma vez que a extração dos dados pode ser feita exatamente da mesma maneira que se extrai os dados de um XML.
@ Rafael Eduardo Kassner
Oi, Rafael, tudo bem?!
Muito interessante isso que você falou! Poderia dar um exemplo para podermos aprender?
Abraços!
Valeu a mão!
Quem quiser se aprofundar, vai aí um ótimo link sobre ER:
http://guia-er.sourceforge.net/
Pra mim foi muito útil!
@ Juliano
Obrigado por relembrar o site do Aurélio. Melhor, mesmo, é comprar o livrinho de referência que ele fez mas, para consultas online, é muito bom!
Obrigado pela visita!
Muito bom msm o tuto.
consegui fazer direitinho!
agora tem uma coisa, eu n to conseguindo colocar o conteudo salvo na minha página.
como que eu falo isso?
eu estou simplesmente colcando o codigo php na minha index.html
estou errado? qual a maneira certa de fazer isso?!
@ Felipe Conde
Na verdade, Felipe, não há “conteúdo salvo”; como o script pega o conteúdo de outro site, ele é inserido dinamicamente, então, ele se altera caso o conteúdo do “site alvo” seja alterado.
Quanto ao local onde será exibido, você mesmo define. Seguindo o exemplo do artigo, caso esteja usando com file_get_contents(), o conteúdo fica na variável $exibir; caso esteja usando curl(), então é em $conteudo.
Show de bola o tuto.
Fui tentar fazer uma adaptação para a cotação agropecuaria (http://www.ruralnetwork.com.br/commodities2_canal_boi.asp), mas da o seguinte erro: failed to open stream: Invalid argument.
Poderia me da uma ajudinha?
Segue o codigo:
$url = file_get_contents (”https://www.ruralnetwork.com.br/commodities2_canal_boi.asp”);
preg_match_all(’/data:(.+)/’, $url, $cotacao);
print_r ($cotacao);
Vlw´s
@ Gabriel
Gabriel, provavelmente o fato de ser “https” deve influenciar nisso. Dê uma olhadinha nesta discussão para começar a busca pela informação! ;-)
Boa sorte e obrigado por comentar!
Trackback em 26 de agosto de 2008