Estou tentando geocodificar entidades (empresa) através do CEP brasileiro respectivamente, utilizando uma API pública chamada BrasilAPI .
Esta é uma amostra fictícia dos dados:
data AMOSTRA_ENTIDADE;
infile datalines delimiter=',';
length CODEMPRESA 3.
NOMEEMPRESA $9
CEP $8;
input CODEMPRESA
NOMEEMPRESA $
CEP;
datalines;
1,EMPRESA A,71577090
2,EMPRESA B,01026010
10,EMPRESA C,01000000
100,EMPRESA D,92300000
110,EMPRESA E,29010580
;
run;
Recentemente descobri o proc http SAS para esta tarefa, não sei se existe outro. Com isso tentei fazer o seguinte trecho de código para realizar a requisição na API seguindo estes exemplos que encontrei:
%macro get_lat_long(cep);
%let site="https://brasilapi.com.br/api/cep/v2/&cep.";
%put NOTE: &site.;
filename resp temp;
proc http
url = &site
method = get
out = resp;
debug level=1;
run;
libname resp json;
data _null_;
infile resp;
input;
put _infile_;
run;
%mend get_lat_long;
data COORDENADAS_ENTIDADE;
set AMOSTRA_ENTIDADE;
length macro_call $200;
macro_call = cats('%consulta_lat_long(',CEP,')');
call execute(macro_call);
rc = dosubl(macro_call);
run;
retorno do código acima:
Minha dúvida é, como fazer essas requisições no SAS para retornar o JSON e outras informações vindas da requisição na API?
O que eu tenho de entrada:
O que estou procurando na saída:
Por favor, se possível, gostaria que exemplos fossem executados no SAS Enterprise Guide e no SAS Viya, tenho o sas enterprise guide 8.3 e o sas viya 3.5 disponíveis. Agradeço antecipadamente por sua ajuda!
@romartins - creo que seria mais fácil usar o mecanismo LIBNAME JSON e o PROC APPEND. Ohla só:
%macro get_lat_long(cep);
%let site="https://brasilapi.com.br/api/cep/v2/&cep.";
%put NOTE: &site.;
filename resp temp;
proc http url = &site method = get out = resp;
debug level=1;
run;
/*Atribui um libref*/
libname resp json;
/* Verifique se um registro foi encontrado*/
libname resp json;
proc sql noprint;
select count(*) into :nobs
from dictionary.columns
where libname='RESP' and memname='ROOT' and lowcase(Name)='city';
;
quit;
/* Se não encontrado*/
%if &nobs =0 %then %do;
data work.N_ENCONT;
cep =&cep;
city='NÃO ENCONTRADO';
run;
proc append data=work.N_ENCONT
out=work.COORDENADAS_ENTIDADE force;
run;
%end;
%else %do;
/* Se foi encontrado*/
proc append data=resp.root (drop = ordinal:)
out=work.COORDENADAS_ENTIDADE force;
run;
%end;
libname resp;
filename resp;
%mend get_lat_long;
/*Limpe o WORK*/
proc datasets library=work kill nolist nodetails;
run;
/*Prepare os dados de amostra*/
data AMOSTRA_ENTIDADE;
infile datalines delimiter=',';
length CODEMPRESA 3. NOMEEMPRESA $9 CEP $8;
input CODEMPRESA NOMEEMPRESA $ CEP;
datalines;
1,EMPRESA A,71577090
2,EMPRESA B,01026010
10,EMPRESA C,01000000
100,EMPRESA D,92300000
110,EMPRESA E,29010580
;
run;
/*Crie a tabela de resultados vazia com colunas de tamanho adequado*/
proc sql;
create table COORDENADAS_ENTIDADE
(cep char(8),
state char(2),
city char(50),
neighborhood char(50),
street char(50),
service char(50))
;
quit;
/*Comece a aquisição dos dados*/
data _null_;
set AMOSTRA_ENTIDADE;
length macro_call $200;
macro_call = cats('%get_lat_long(',CEP,')');
/* call execute(macro_call);*/
rc = dosubl(macro_call);
run;
title "AMOSTRA_ENTIDADE";
proc print data=work.AMOSTRA_ENTIDADE;
run;
title "COORDENADAS_ENTIDADE";
proc print data=work.COORDENADAS_ENTIDADE;
run;
E o resultado:
Obs | CODEMPRESA | NOMEEMPRESA | CEP |
---|---|---|---|
1 | 1 | EMPRESA A | 71577090 |
2 | 2 | EMPRESA B | 01026010 |
3 | 10 | EMPRESA C | 01000000 |
4 | 100 | EMPRESA D | 92300000 |
5 | 110 | EMPRESA E | 29010580 |
COORDENADAS_ENTIDADE
Obs | cep | state | city | neighborhood | street | service |
---|---|---|---|---|---|---|
1 | 71577090 | DF | Brasília | Paranoá | ADE Conjunto 9 | correios |
2 | 01026010 | SP | São Paulo | Centro | Avenida Mercúrio | correios |
3 | NÃO ENCONTRADO | |||||
4 | NÃO ENCONTRADO | |||||
5 | 29010580 | ES | Vitória | Centro | Escadaria Doutor Luiz Castelar da Silva | correios |
May the SAS be with you!
Mark
@romartins - creo que seria mais fácil usar o mecanismo LIBNAME JSON e o PROC APPEND. Ohla só:
%macro get_lat_long(cep);
%let site="https://brasilapi.com.br/api/cep/v2/&cep.";
%put NOTE: &site.;
filename resp temp;
proc http url = &site method = get out = resp;
debug level=1;
run;
/*Atribui um libref*/
libname resp json;
/* Verifique se um registro foi encontrado*/
libname resp json;
proc sql noprint;
select count(*) into :nobs
from dictionary.columns
where libname='RESP' and memname='ROOT' and lowcase(Name)='city';
;
quit;
/* Se não encontrado*/
%if &nobs =0 %then %do;
data work.N_ENCONT;
cep =&cep;
city='NÃO ENCONTRADO';
run;
proc append data=work.N_ENCONT
out=work.COORDENADAS_ENTIDADE force;
run;
%end;
%else %do;
/* Se foi encontrado*/
proc append data=resp.root (drop = ordinal:)
out=work.COORDENADAS_ENTIDADE force;
run;
%end;
libname resp;
filename resp;
%mend get_lat_long;
/*Limpe o WORK*/
proc datasets library=work kill nolist nodetails;
run;
/*Prepare os dados de amostra*/
data AMOSTRA_ENTIDADE;
infile datalines delimiter=',';
length CODEMPRESA 3. NOMEEMPRESA $9 CEP $8;
input CODEMPRESA NOMEEMPRESA $ CEP;
datalines;
1,EMPRESA A,71577090
2,EMPRESA B,01026010
10,EMPRESA C,01000000
100,EMPRESA D,92300000
110,EMPRESA E,29010580
;
run;
/*Crie a tabela de resultados vazia com colunas de tamanho adequado*/
proc sql;
create table COORDENADAS_ENTIDADE
(cep char(8),
state char(2),
city char(50),
neighborhood char(50),
street char(50),
service char(50))
;
quit;
/*Comece a aquisição dos dados*/
data _null_;
set AMOSTRA_ENTIDADE;
length macro_call $200;
macro_call = cats('%get_lat_long(',CEP,')');
/* call execute(macro_call);*/
rc = dosubl(macro_call);
run;
title "AMOSTRA_ENTIDADE";
proc print data=work.AMOSTRA_ENTIDADE;
run;
title "COORDENADAS_ENTIDADE";
proc print data=work.COORDENADAS_ENTIDADE;
run;
E o resultado:
Obs | CODEMPRESA | NOMEEMPRESA | CEP |
---|---|---|---|
1 | 1 | EMPRESA A | 71577090 |
2 | 2 | EMPRESA B | 01026010 |
3 | 10 | EMPRESA C | 01000000 |
4 | 100 | EMPRESA D | 92300000 |
5 | 110 | EMPRESA E | 29010580 |
COORDENADAS_ENTIDADE
Obs | cep | state | city | neighborhood | street | service |
---|---|---|---|---|---|---|
1 | 71577090 | DF | Brasília | Paranoá | ADE Conjunto 9 | correios |
2 | 01026010 | SP | São Paulo | Centro | Avenida Mercúrio | correios |
3 | NÃO ENCONTRADO | |||||
4 | NÃO ENCONTRADO | |||||
5 | 29010580 | ES | Vitória | Centro | Escadaria Doutor Luiz Castelar da Silva | correios |
May the SAS be with you!
Mark
Ah I see, as I was trying to return the JSON text, I thought I wouldn't need the JSON libname. Thanks for the tip! I believe then, that it will be better to work with the tables directly than with the JSON text.
Are you ready for the spotlight? We're accepting content ideas for SAS Innovate 2025 to be held May 6-9 in Orlando, FL. The call is open until September 25. Read more here about why you should contribute and what is in it for you!
Learn how use the CAT functions in SAS to join values from multiple variables into a single value.
Find more tutorials on the SAS Users YouTube channel.