Como consumir API de CPF em Kotlin para aplicações Android nativas

Aprenda a consumir a API de consulta de CPF em Kotlin para aplicações Android nativas usando Retrofit e OkHttp com exemplos completos.

Redação CPFHub.io
Redação CPFHub.io
··7 min de leitura
Como consumir API de CPF em Kotlin para aplicações Android nativas

Para consumir a API de CPF em Kotlin no Android, configure o Retrofit com OkHttp usando a base URL https://api.cpfhub.io/, adicione o header x-api-key nas requisições e modele a resposta com data classes para os campos cpf, name, gender e birthDate. Com coroutines e ViewModel, a chamada fica segura na thread principal e o estado da UI é gerenciado de forma reativa.

Introdução

O Kotlin se consolidou como a linguagem principal para o desenvolvimento de aplicações Android nativas. Aplicativos que lidam com cadastro de usuários, onboarding digital ou transações financeiras frequentemente precisam validar o CPF do usuário para garantir a identidade e prevenir fraudes.

Integrar uma API de consulta de CPF em um aplicativo Android é uma prática recomendada para fintechs, e-commerces e qualquer plataforma que colete dados pessoais de usuários brasileiros.


Pré-requisitos

  • Android Studio -- Com suporte a Kotlin configurado.

  • Kotlin 1.8+ -- Versão recomendada para projetos modernos.

  • Conta na CPFHub.io -- Para obter a chave de API. O plano gratuito oferece 50 consultas/mês.

  • Dependências -- Retrofit, OkHttp, Gson ou Moshi para serialização JSON.

Adicionando dependências no build.gradle

dependencies {
    implementation("com.squareup.retrofit2:retrofit:2.9.0")
    implementation("com.squareup.retrofit2:converter-gson:2.9.0")
    implementation("com.squareup.okhttp3:okhttp:4.12.0")
    implementation("com.squareup.okhttp3:logging-interceptor:4.12.0")
    implementation("org.jetbrains.kotlinx:kotlinx-coroutines-android:1.7.3")
}

Adicione a permissão de internet no AndroidManifest.xml:

<uses-permission android:name="android.permission.INTERNET" />

Modelando a resposta da API

Crie as data classes que representam a resposta JSON da API.

data class CpfResponse(
    val success: Boolean,
    val data: CpfData?
)

data class CpfData(
    val cpf: String,
    val name: String,
    val nameUpper: String,
    val gender: String,
    val birthDate: String,
    val day: Int,
    val month: Int,
    val year: Int
)

A resposta da API tem o seguinte formato:

{
    "success": true,
    "data": {
    "cpf": "12345678900",
    "name": "João da Silva",
    "nameUpper": "JOÃO DA SILVA",
    "gender": "M",
    "birthDate": "15/06/1990",
    "day": 15,
    "month": 6,
    "year": 1990
    }
}

Definindo a interface do serviço com Retrofit

Crie uma interface que define o endpoint da API:

import retrofit2.http.GET
import retrofit2.http.Header
import retrofit2.http.Path

interface CpfHubService {

    @GET("cpf/{cpf}")
    suspend fun consultarCpf(
    @Path("cpf") cpf: String,
    @Header("x-api-key") apiKey: String,
    @Header("Accept") accept: String = "application/json"
    ): CpfResponse
}

Configurando o Retrofit com OkHttp

Crie um objeto singleton para configurar o Retrofit com timeout e interceptor de logs:

import okhttp3.OkHttpClient
import okhttp3.logging.HttpLoggingInterceptor
import retrofit2.Retrofit
import retrofit2.converter.gson.GsonConverterFactory
import java.util.concurrent.TimeUnit

object CpfHubClient {

    private const val BASE_URL = "https://api.cpfhub.io/"

    private val loggingInterceptor = HttpLoggingInterceptor().apply {
    level = HttpLoggingInterceptor.Level.BODY
    }

    private val httpClient = OkHttpClient.Builder()
    .connectTimeout(10, TimeUnit.SECONDS)
    .readTimeout(10, TimeUnit.SECONDS)
    .writeTimeout(10, TimeUnit.SECONDS)
    .addInterceptor(loggingInterceptor)
    .build()

    private val retrofit = Retrofit.Builder()
    .baseUrl(BASE_URL)
    .client(httpClient)
    .addConverterFactory(GsonConverterFactory.create())
    .build()

    val service: CpfHubService = retrofit.create(CpfHubService::class.java)
}

Criando o repository

Encapsule a lógica de chamada à API em um repository para separar responsabilidades:

class CpfRepository {

    private val service = CpfHubClient.service

    suspend fun consultar(cpf: String, apiKey: String): Result<CpfData> {
    return try {
    val response = service.consultarCpf(cpf, apiKey)
    if (response.success && response.data != null) {
    Result.success(response.data)
    } else {
    Result.failure(Exception("CPF não encontrado ou inválido."))
    }
    } catch (e: Exception) {
    Result.failure(e)
    }
    }
}

Implementando o ViewModel

Utilize um ViewModel com coroutines para gerenciar o estado da consulta:

import androidx.lifecycle.ViewModel
import androidx.lifecycle.viewModelScope
import kotlinx.coroutines.flow.MutableStateFlow
import kotlinx.coroutines.flow.StateFlow
import kotlinx.coroutines.launch

class CpfViewModel : ViewModel() {

    private val repository = CpfRepository()

    private val _estado = MutableStateFlow<CpfEstado>(CpfEstado.Idle)
    val estado: StateFlow<CpfEstado> = _estado

    fun consultarCpf(cpf: String) {
    val cpfLimpo = cpf.replace(Regex("\\D"), "")
    if (cpfLimpo.length != 11) {
    _estado.value = CpfEstado.Erro("CPF deve ter 11 dígitos.")
    return
    }

    _estado.value = CpfEstado.Carregando

    viewModelScope.launch {
    val resultado = repository.consultar(cpfLimpo, "SUA_CHAVE_DE_API")
    resultado.fold(
    onSuccess = { dados ->
    _estado.value = CpfEstado.Sucesso(dados)
    },
    onFailure = { erro ->
    _estado.value = CpfEstado.Erro(
    erro.message ?: "Erro desconhecido."
    )
    }
    )
    }
    }
}

sealed class CpfEstado {
    object Idle : CpfEstado()
    object Carregando : CpfEstado()
    data class Sucesso(val dados: CpfData) : CpfEstado()
    data class Erro(val mensagem: String) : CpfEstado()
}

Integrando na Activity ou Fragment

import androidx.activity.viewModels
import androidx.appcompat.app.AppCompatActivity
import androidx.lifecycle.lifecycleScope
import kotlinx.coroutines.flow.collectLatest
import kotlinx.coroutines.launch

class MainActivity : AppCompatActivity() {

    private val viewModel: CpfViewModel by viewModels()

    override fun onCreate(savedInstanceState: Bundle?) {
    super.onCreate(savedInstanceState)
    setContentView(R.layout.activity_main)

    lifecycleScope.launch {
    viewModel.estado.collectLatest { estado ->
    when (estado) {
    is CpfEstado.Idle -> { /* Estado inicial */ }
    is CpfEstado.Carregando -> {
    // Mostrar indicador de carregamento
    }
    is CpfEstado.Sucesso -> {
    val dados = estado.dados
    // Exibir nome, data de nascimento, gênero
    }
    is CpfEstado.Erro -> {
    // Exibir mensagem de erro
    }
    }
    }
    }

    // Ao clicar no botão de consulta
    // viewModel.consultarCpf(editTextCpf.text.toString())
    }
}

Boas práticas para Android

  • Chave de API segura -- Nunca inclua a chave diretamente no código-fonte. Utilize o local.properties ou variáveis de ambiente no build. Para produção, considere um back-end intermediário. Consulte as diretrizes de segurança para desenvolvedores Android para proteção de credenciais sensíveis.

  • Timeout -- Configure timeout no OkHttp para evitar que o app fique travado.

  • Coroutines -- Sempre faça chamadas de rede em coroutines, nunca na thread principal.

  • Tratamento de erros -- Implemente tratamento para timeout, ausência de conexão e códigos de erro HTTP (401, 500). A API CPFHub.io não retorna 401 para autenticação inválida — retorna 403; erros de rede ou timeout devem ser capturados no bloco catch.

  • ProGuard/R8 -- Mantenha as data classes no arquivo de regras para evitar problemas de serialização.


Perguntas frequentes

Por que usar Retrofit em vez de OkHttp diretamente para consumir a API de CPF no Android?

O Retrofit adiciona uma camada declarativa sobre o OkHttp: você define a interface com anotações (@GET, @Header, @Path) e ele gera o código de requisição automaticamente, incluindo conversão JSON com Gson ou Moshi. Para chamadas simples como a da CPFHub.io, isso reduz o boilerplate e facilita testes unitários com mocks.

Como evitar que a chave de API apareça no APK?

Nunca declare a chave como constante no código-fonte. Use local.properties para armazená-la durante o desenvolvimento e injete via BuildConfig no build do Gradle. Em produção, a abordagem mais segura é criar um endpoint no seu próprio back-end que faz a chamada à CPFHub.io — assim a chave nunca sai do servidor.

A consulta de CPF pode ser feita diretamente do app Android ou precisa de um back-end?

Tecnicamente pode ser feita direto do app, mas para produção recomenda-se um back-end intermediário. Isso protege a chave de API, permite aplicar regras de negócio antes de expor o resultado e facilita o cache de consultas recentes para evitar chamadas desnecessárias.

O que acontece se o usuário fizer a consulta sem conexão com a internet?

O OkHttp lançará uma exceção de IOException que deve ser capturada no bloco catch do repository. Trate esse cenário exibindo uma mensagem amigável como "Verifique sua conexão e tente novamente" em vez de deixar o app travar. O CpfEstado.Erro do ViewModel é o lugar certo para propagar essa mensagem até a UI.


Conclusão

Consumir a API de consulta de CPF da CPFHub.io em Kotlin é direto: Retrofit gerencia as chamadas, OkHttp controla timeout e logging, e o padrão ViewModel + StateFlow mantém a UI reativa e o ciclo de vida do Android sob controle. O resultado é uma integração robusta e testável que valida o CPF do usuário em tempo real durante o onboarding.

Cadastre-se em cpfhub.io — 50 consultas mensais gratuitas, sem cartão de crédito — e integre a validação de CPF ao seu app Android nativo ainda hoje.

CPFHub.io

Pronto para integrar a API?

50 consultas gratuitas para testar agora. Sem cartão de crédito. Acesso imediato à documentação.

Redação CPFHub.io

Sobre a redação

Redação CPFHub.io

Time editorial especializado em APIs de CPF, identidade digital e compliance no mercado brasileiro. Produzimos guias técnicos, análises regulatórias e tutoriais sobre LGPD e KYC para desenvolvedores e líderes de produto.

WhatsAppFale conosco via WhatsApp