Correios, SEDEX e o tão famigerado Cálculo de Frete

Opa?

Nesta vida de desenvolvedor web alguns desafio tendem a surgir em nosso caminho, um deles sem dúvida será este que abordarei aqui, de forma rápida de direta, o Cálculo de Frete dos Correios. Com base em cep de origem, cep de destino e o peso da encomenda, obteremos o valor do SEDEX. Recurso muito utilizado em lojas virtuais e sistemas com delivery na web =)

Algo que muitas pessoas não sabem, é que os Correios disponibilizam um serviço de consulta web, com resposta em XML(as possibilidades iniciam aí :P), de forma simples, acessado via URL, sem webservices, ai vai um exemplo deste acesso:

http://www.correios.com.br/encomendas/precos/calculo.cfm?resposta=xml&servico=40010& cepOrigem=17012-350&cepDestino=01102-000&peso=0.31

Percebam que ao acessarmos o endereço acima, obtemos um XML simples, com todos os dados necessários para a consulta. Tudo que devemos fazer é completar a URL acima com nossos dados, da seguinte forma:

servico=40010 é sedex, outros serviços tem que procurar no site dos correios
cepOrigem=17012-350 -> CEP de Origem (do teu cliente no caso)
cepDestino=88818-400 -> de quem vai receber
peso=0.62 -> peso da encomenda

Uma vez com nossa requisição devidamente configurada, basta tratarmos o XML da forma mais interessante para seu projeto. Javascript, Flash, PHP, Java, Ruby on Rails e por aí vai =P

Neste caso, criaremos uma função de exemplo em PHP para tratarmos esta resposta, e obtermos os dados de forma fácil e direta. Aí vai ela "mastigadinha":

PHP:
  1. <?php
  2.    
  3.     function getSEDEX($cepOrigem = "88818-520", $cepDestino = "88818-400", $peso = 0.5)
  4.     {
  5.         $urlCorreios = "http://www.correios.com.br/encomendas/precos/calculo.cfm?resposta=xml&servico=40010&cepOrigem=%s&cepDestino=%s&peso=%s";
  6.        
  7.         $urlCorreios = sprintf($urlCorreios, $cepOrigem, $cepDestino, $peso);
  8.        
  9.         //carregando url dos correios...
  10.         //caso o seu servidor não permita o uso da função file para url's externas
  11.         //recomenda-se a utilização de CURL - http://www.php.net/manual/en/ref.curl.php
  12.         $carrega = file($urlCorreios) or die("Problemas em obter os dados dos correios");
  13.        
  14.         //tratando string xml obtida. Removendo espaços e linhas para facilitar...
  15.         $conteudo = trim(str_replace(array("\n", chr(13)), "", implode($carrega, "")));
  16.        
  17.         if(strlen($conteudo) <1) return false;
  18.        
  19.         //informações de origem tratadas com RegExp...
  20.         preg_match_all("/<uf_origem>(.+)<\/uf_origem>/", $conteudo, $uf_origem);
  21.         preg_match_all("/<local_origem>(.+)<\/local_origem>/", $conteudo, $local_origem);
  22.         preg_match_all("/<cep_origem>(.+)<\/cep_origem>/", $conteudo, $cep_origem);
  23.        
  24.         //informações de destino tratadas com RegExp...
  25.         preg_match_all("/<uf_destino>(.+)<\/uf_destino>/", $conteudo, $uf_destino);
  26.         preg_match_all("/<local_destino>(.+)<\/local_destino>/", $conteudo, $local_destino);
  27.         preg_match_all("/<cep_destino>(.+)<\/cep_destino>/", $conteudo, $cep_destino);
  28.        
  29.         //informações sobre a encomenda tratadas com RegExp...
  30.         preg_match_all("/<peso>(.+)<\/peso>/", $conteudo, $peso);
  31.         preg_match_all("/<preco_postal>(.+)<\/preco_postal>/", $conteudo, $preco_postal);   
  32.        
  33.         //objeto contendo as informações sobre o frete...
  34.         $sedex = array(
  35.             "uf_origem" => $uf_origem[1][0],
  36.             "local_origem" => $local_origem[1][0],
  37.             "cep_origem" => $cep_origem[1][0],
  38.             "uf_destino" => $uf_destino[1][0],
  39.             "local_destino" => $local_destino[1][0],
  40.             "cep_destino" => $cep_destino[1][0],
  41.             "peso" => floatval($peso[1][0]),
  42.             "valor" => floatval($preco_postal[1][0])
  43.         );
  44.        
  45.         return $sedex;
  46.     }
  47.    
  48.     //informações processadas. Cep de Origem, Cep destino, Peso...
  49.     $sedex = getSEDEX("88818-520", "88818-400", 0.750);
  50.    
  51.     //enfim exibimos o valor de nossa encomenda...
  52.     echo "R$ " . number_format($sedex["valor"], 2, ",", ","); //valor do sedex, já formatado em reais...
  53.  
  54. ?>

Uma vez com a função getSEDEX executada, obtemos todos os dados tratado no retorno da mesma.

Fácil não?

Abracetas... ;)

10 Comments

rssComments RSS transmitTrackBack Identifier URI


Blz? Mas como pegar os dados de dias uteis de um cep para outro?

Obrigado

Comment by Marcelo on 06/04/2008 3:08 pm


Cara muito obrigado!

Comment by Fabio Issamu Oshiro on 24/04/2008 2:49 pm


Boa noite,
achei sua função muito boa.. me ajudou muito, só que tenho um dúvida e gostaria de sua ajuda.
caso a pessoal digite um cep inválido por exemplo: 000, o xml me retornaria um cod de erro diferente de 0, como poderia capiturar o propriedade "codigo" do xml? assim verificaria se codigo é diferente de 0 e informaria que o cep é inválido.. fui claro? obrigado!

Comment by Jannier on 25/04/2008 8:28 pm


Rapaz, você não sabe como essa rotina me ajudou no site que estou construindo. Parabéns.

Comment by Luciano on 13/05/2008 1:10 am


é impressão minha ou essa página fornecida pelo correios fica offline direto?

Comment by Bruno on 15/06/2008 4:56 pm


meu servidor esta com file-access desabilitado.
tem como ativar vai ".htaccess"?
se não, como faço para utilizar cURL?

Comment by Felipe Roberto on 28/06/2008 12:26 pm


Perfeito, obrigado pela ajuda.

Comment by Rodrigo on 20/07/2008 11:06 pm


Materia legal, acho que isso vai ajudar um pouco

function SEDEX($cepOrigem, $cepDestino , $peso){
$f = "http://www.correios.com.br/encomendas/precos/calculo.cfm?resposta=xml&servico=40010&cepOrigem=$cepOrigem&cepDestino=$cepDestino&peso=$peso";
$entry = utf8_encode(simplexml_load_file($f));
$descricao = $entry->dados_postais->preco_postal;
return $descricao;
}
echo SEDEX('88818-520', '88818-400', '0.5');

Comment by Ariel on 02/08/2008 7:29 am


ops: tire a funcão utf8_encode da linha 3. tava so fazendo uns testes e esqueci de tirar....

Comment by Ariel on 02/08/2008 7:35 am


Para quem quiser os outros códigos do Sedex segue ae.

40010 -> SEDEX
40290 -> SEDEX Hoje
40215 -> SEDEX 10
40045 -> SEDEX a Cobrar
41017 -> Encomenda Normal

Aquele abraço

Comment by Tiago on 11/08/2008 4:23 pm

addLeave a comment