Exemplo de Integração com ViaCEP usando FWRest

Hoje vou mostrar como consultar dados de um endereço diretamente do CEP usando o AdvPL e a função FWRest.

Pessoal, o grande Thiago Andrade (LinkedIn), fez uma integração recentemente com a API gratuita da ViaCEP, que retorna informações através de um CEP disponibilizado.

Essa integração usa o FWRest com GET, confira o exemplo abaixo desenvolvido buscando informações do CEP 03.062-010.

//=================================================================================
/*/{Protheus.doc} zViaCep
[API.VIACEP] [GET] Conecta na Api gratuita da ViaCep para retornar dados de um Endereço
a partir do CEP.
Documentação: https://viacep.com.br/
Campos Disponiveis na API:  
BAIRRO, CEP, COMPLEMENTO, GIA, IBGE, LOCALIDADE, LOGRADOURO, UF, UNIDADE
  
Uso: Incluir/Atualizar CC2 quando necessário
  
@author     Thiago.Andrrade
@since      24/07/2020
/*/
//=================================================================================
User Function zViaCep()
    Local aArea         := GetArea()
    Local aHeader       := {}
    Local cCep          := '03062010'
    Local cCodMun       := ''
    Local oRestClient   := FWRest():New("https://viacep.com.br/ws")
    Local oJsObj
  
    aadd(aHeader,'User-Agent: Mozilla/4.0 (compatible; Protheus '+GetBuild()+')')
    aAdd(aHeader,'Content-Type: application/json; charset=utf-8')
        
    ////////////////////////////////////////////////////////////////
    //[GET] Consulta Dados na Api
    oRestClient:setPath("/"+cCep+"/json/")
    If oRestClient:Get(aHeader)
        //Deserealiza o Json
        FWJsonDeserialize(oRestClient:CRESULT,@oJsObj)
  
        //Recebe Dados do Json
        cCodMun := SubStr(oJsObj:IBGE,3,5)
  
        /*oJsObj:BAIRRO
        oJsObj:CEP
        oJsObj:COMPLEMENTO
        oJsObj:GIA
        oJsObj:IBGE
        oJsObj:LOCALIDADE
        oJsObj:LOGRADOURO
        oJsObj:UF
        oJsObj:UNIDADE*/
  
        FreeObj(oJsObj)
    Else
        ConOut("Erro Api ViaCep: "+oRestClient:GetLastError())
    Endif
  
    RestArea(aArea)
Return

Update – Janeiro de 2022

Pessoal, o grande Súlivan Simões ( LinkedIn ), fez uma adaptação na rotina, para utilizar JsonObject, e já retornando todos os campos. Segue abaixo a função:

#Include 'Totvs.ch'

/*/{Protheus.doc} zViaCep

[API.VIACEP] [GET] Conecta na Api gratuita da ViaCep para retornar dados de um Endereço
a partir do CEP.
Documentação: https://viacep.com.br/
Campos Disponiveis na API:  
BAIRRO, CEP, COMPLEMENTO, GIA, IBGE, LOCALIDADE, LOGRADOURO, UF, UNIDADE

@type function
@author Thiago.Andrrade (autor da funcionalidade original)
@author Súlivan (resposável por adaptar o fonte)
@since 24/07/2020 [data da criação da rotina]

@example
	u_zViaCep('37600000')
    u_zViaCep('31015-104')
    u_zViaCep('31015.025')
    u_zViaCep('31010 514')
    u_zViaCep(FwFldGet('A1_CEP'))

    Exemplo para chamar em gatilhos do Protheus para preencher o código do municipio por exemplo
    Regra:   u_zViaCep(FwFldGet('A1_CEP'))['ibge']

	  @obs : MANUTENÇÕES FEITAS NO CÓDIGO:
     --------------------------------------------------------------------------------------------					     
     Data: 26/01/2021
     Responsável: Súlivan
     Log: * Retirado o uso da função FWJsonDeserialize que está em deprecate
          * Rotina adaptada para receber parametros
          * Adicionado return para retornar as informações concedidas pela API               
          * Incluso mais logs na rotina.     
     --------------------------------------------------------------------------------------------
/*/
User Function zViaCep(cCep)

    Local aArea         := GetArea()
    Local aHeader       := {}    
    Local oRestClient   := FWRest():New("https://viacep.com.br/ws")
    Local oJson         := JsonObject():New()
    
    Default cCep        := ''

    fConOut("[U_zViaCep] - Entrou na função que consulta as informações do endereco pelo CEP")

    //Retira espaços,traços e pontos caso receba assim dos parametros
    cCep := StrTran(StrTran(StrTran(cCep," ",""),"-",""),".","")

    aadd(aHeader,'User-Agent: Mozilla/4.0 (compatible; Protheus '+GetBuild()+')')
    aAdd(aHeader,'Content-Type: application/json; charset=utf-8')

    //[GET] Consulta Dados na Api
    oRestClient:setPath("/"+cCep+"/json/")
    If oRestClient:Get(aHeader)
         
        oJson:FromJson(oRestClient:CRESULT)          

        //Se as keys não existirem, cria elas com conteudo vazio.
        oJson['cep']        := Iif( ValType(oJson['cep'])         != "U", oJson['cep']        , "")
        oJson['logradouro'] := Iif( ValType(oJson['logradouro'])  != "U", oJson['logradouro'] , "")
        oJson['complemento']:= Iif( ValType(oJson['complemento']) != "U", oJson['complemento'], "")
        oJson['bairro']     := Iif( ValType(oJson['bairro'])      != "U", oJson['bairro']     , "")
        oJson['localidade'] := Iif( ValType(oJson['localidade'])  != "U", oJson['localidade'] , "")
        oJson['uf']         := Iif( ValType(oJson['uf'])          != "U", oJson['uf']         , "")
        oJson['ibge']       := Iif( ValType(oJson['ibge'])        != "U", SubStr(oJson['ibge'],3,5), "")
        oJson['gia']        := Iif( ValType(oJson['gia'])         != "U", oJson['gia']        , "") 
        oJson['ddd']        := Iif( ValType(oJson['ddd'])         != "U", oJson['ddd']        , "")
        oJson['siafi']      := Iif( ValType(oJson['siafi'])       != "U", oJson['siafi']      , "")

        VarInfo("[U_zViaCep] - Resultado da consulta ->",oJson)
    Else
        fConOut("[U_zViaCep] - ** Erro Api ViaCep: "+oRestClient:GetLastError())
    Endif  

   oJson['erro']:=  Iif( ValType(oJson['cep']) == "U", "Api não retornou dados do cep: "+cValTochar(cCep) ,"")      

    fConOut("[U_zViaCep] - Finalizou na função que consulta as informações do endereco pelo CEP") 

    FreeObj(oRestClient)
    RestArea(aArea)
Return oJson

Static Function fConOut(cLog)
	
	Default cLog := "Log empty"
		
	FwLogMsg("INFO", /*cTransactionId*/, "fConOut", FunName(), "", "01", cLog, 0, 0, {})
	 		
Return

Bom pessoal, por hoje é só.

Abraços e até a próxima.

Dan (Daniel Atilio)
Especialista em Engenharia de Software pela FIB. Entusiasta de soluções Open Source. E blogueiro nas horas vagas.

4 Responses

  1. Felipe disse:

    Como atualizo o campo de CLientes na SA1 ?

  2. Súlivan disse:

    Grande artigo.
    Top!

Deixe uma resposta