> For the complete documentation index, see [llms.txt](https://docs.caf.io/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.caf.io/caf-sdk/android/comecando-com-o-sdk.md).

# Começando com o SDK

## Conheça o CafSDK

Essa documentação técnica aborda a **implementação do CafSDK para Android**, com detalhes sobre a configuração, inicialização, execução dos fluxos de captura e personalizações avançadas.

Atualmente, o CafSDK integra 2 módulos principais: **Face Liveness (FL)** e **Document Detector (DD)**, executados de forma sequencial com uma interface de configuração unificada.

## O que é Face Liveness

É o módulo que valida a autenticidade de um rosto capturado por aplicativo de foto, garantindo que a imagem corresponda à uma pessoa real.

### Características técnicas:

* Configuração de URLs para autenticação (`authBaseUrl`) e verificação de prova de vida (liveness) (`livenessBaseUrl`).
* Flags para habilitar captura de tela (screen capture) e modo de depuração (debug mode).
* Suporte à múltiplos provedores de autenticação.

## O que é Document Detector

É o módulo que permite a captura e o processamento de documentos (Ex.: RG, CPF, Passaporte, etc.).

### Características técnicas:

* Configuração de um fluxo de etapas (flow) definidas por `DocumentDetectorStep` para a captura do documento.
* Parâmetros operacionais, como timeout, flags de captura manual, entre outras configurações.
* Possibilidade de uso da câmera para validações de enquadramento, ou upload de arquivo do documento.

***

## Comece a usar o SDK

### Adicione a dependência

Para que seu projeto Android utilize o CafSDK, é preciso configurar corretamente os repositórios Maven e declarar as dependências do SDK no seu projeto. Essa etapa garante que os artefatos (bibliotecas) sejam baixados e integrados durante o build.

### Requisitos para adicionar

#### Para Face Liveness

Os requisitos mínimos para o módulo **Caf Face Liveness**, incluem:

| Requisito                                           | Versão |
| --------------------------------------------------- | ------ |
| Android SDK API - versão mínima (minSdk)            | 26     |
| Android SDK API - versão para compilar (compileSDK) | 34     |
| Kotlin                                              | 1.9.10 |
| Gradle                                              | 8.4    |
| Android Gradle Plugin (AGP)                         | 8.3.2  |

{% hint style="warning" %}
`versionName` e `versionCode` são obrigatórios para o funcionamento correto do SDK.
{% endhint %}

#### Para Document Detector

Os requisitos mínimos para o módulo **Caf** **Document Detector**, incluem:

| Requisito                                           | Versão |
| --------------------------------------------------- | ------ |
| Android SDK API - versão mínima (minSdk)            | 26     |
| Android SDK API - versão para compilar (compileSDK) | 34     |
| Kotlin                                              | 1.9.10 |
| Gradle                                              | 8.4    |
| Android Gradle Plugin (AGP)                         | 8.3.2  |

### Passo a passo para adicionar

#### Passo 1 - Adicionar o repositório Maven

Nessa etapa, é preciso informar ao Gradle onde localizar os artefatos do CafSDK e de dependências adicionais que podem ser utilizadas (como os relacionados ao Caf Face Liveness ou ao FingerPrintJS).

Para isso, configure o arquivo `settings.gradle.kts` do projeto (geralmente localizado no nível raiz), incluindo os seguintes repositórios:

* **Repositório Caf:** onde estão hospedados os artefatos do CafSDK.
* **Repositório iProov:** necessário se você estiver utilizando o módulo CafFaceLiveness, que depende dos artefatos da iProov para um processamento seguro.
* **Repositório do FingerPrintJS:** dependência interna dos módulos.
* **JitPack:** para dependências hospedadas via JitPack (Github).

**Exemplo de configuração:**

```kotlin
repositories {
    // Repositório Caf – artefatos oficiais do CafSDK
    maven { url = uri("https://repo.combateafraude.com/android/release") }
    
    // Repositório iProov – utilizado no caso do uso do CafFaceLiveness
    maven { url = uri("https://raw.githubusercontent.com/iProov/android/master/maven/") }
    
    // Repositório do FingerPrintJS 
    maven { setUrl("https://maven.fpregistry.io/releases") }
    
    // JitPack – para dependências adicionais que estejam hospedadas via JitPack
    maven { setUrl("https://jitpack.io") }
}
```

#### Mais detalhes

* **Flexibilidade:** essa configuração permite que o projeto baixe todas as dependências necessárias de diferentes fontes, garantindo compatibilidade e versões atualizadas.
* **Manutenção:** caso haja atualizações nos repositórios ou mudanças na estrutura de publicação, basta atualizar essa seção para refletir as novas URLs.
* **Contexto:** a inclusão dos repositórios é feita uma única vez no nível do projeto, garantindo que todos os módulos possam acessar os artefatos necessários.

#### Passo 2 - Incluir a dependência no CafSDK

Após configurar os repositórios, é necessário declarar as dependências específicas do CafSDK no arquivo `build.gradle.kts` do módulo da sua aplicação.

Essa etapa declara quais módulos do SDK serão utilizados, permitindo que o Gradle gerencie as versões e resolva as dependências corretamente.

**Exemplo de declaração de dependências:**

```kotlin
dependencies {
    // Declaração do Caf BoM (Bill of Materials) para gerenciar as versões de forma centralizada.
    implementation(platform("io.caf.sdk:caf-sdk-bom:1.3.0"))
    
    // Declaração dos módulos que serão utilizados na aplicação.
    
    // Se você utiliza Protobuf Java:
    implementation("io.caf.sdk:caffaceliveness-lite") // ou use "io.caf.sdk:caffaceliveness-ui-lite" se desejar com a interface customizada.
    // Se você utiliza Protobuf JavaLite, adicione a dependência correspondente:
    // implementation("io.caf.sdk:caffaceliveness-core") // ou "io.caf.sdk:caffaceliveness-ui-core" se desejar com a interface customizada.
    
    // Dependência do módulo Document Detector:
    implementation("io.caf.sdk:document-detector") // versão com interface customizada ainda não disponível
}
```

### Pontos importantes

**Caf BoM (Bill of Materials)**\
Utilizar o BoM ajuda a centralizar a gestão das versões de todos os módulos do CafSDK. Assim, todas as dependências relacionadas ao SDK usarão a mesma versão definida, evitando conflitos e facilitando atualizações.

**Módulos de Captura**

**Caf Face Liveness:** escolha a dependência apropriada, de acordo com o tipo de Java que sua aplicação usa (Protobuf Java ou JavaLite).

* A versão "Lite" é otimizada para desempenho e tamanho. Também usa internamente a versão do Protobuf o JavaLite.
* A versão "Core" pode oferecer funcionalidades adicionais ou compatibilidade com outros recursos, pois utiliza o Protobuf Java (versão completa).
* Também é possível escolher entre a versão padrão ou a versão que contém as interfaces gráficas da Caf (indicada pelo sufixo `-ui`), conforme a necessidade de personalização da experiência do usuário.

**Caf Document Detector:** até o momento, apenas o SDK sem interface gráfica está disponível. Teremos novidades em breve.

**Verificação de versão**\
Sempre confira a versão mais recente do CafSDK na página de [release notes *alterar link*](https://docs.caf.io/caf-sdk/android/cafsdk) para garantir que está utilizando as versões mais atualizadas e compatíveis.

Essa configuração assegura que seu projeto esteja preparado para integrar o CafSDK, garantindo que todos os artefatos necessários sejam localizados e incorporados durante o build. Caso ocorra alguma alteração nos repositórios ou novas dependências sejam introduzidas, atualize as configurações.

***

## Como inicializar o SDK

### Permissões

Para que os módulos operem corretamente, algumas permissões precisam ser declaradas no arquivo **AndroidManifest.xml**,confira:

**Para Face Liveness**

| Permissão                     | Descrição                                                                        | Necessidade |
| ----------------------------- | -------------------------------------------------------------------------------- | ----------- |
| `android.permission.CAMERA`   | Permite acesso à câmera para capturar imagens e verificação de face (liveness).  | Obrigatório |
| `android.permission.INTERNET` | Permite a comunicação com os serviços de autenticação e verificação (HTTPS/WSS). | Obrigatório |

**Para Document Detector**

| Permissão                                  | Descrição                                                                                    | Necessidade          |
| ------------------------------------------ | -------------------------------------------------------------------------------------------- | -------------------- |
| `android.permission.CAMERA`                | Permite o acesso à câmera para capturar imagens dos documentos.                              | Somente para captura |
| `android.permission.INTERNET`              | Permite que imagens capturadas sejam enviadas aos servidores para processamento e validação. | Obrigatório          |
| `android.permission.READ_EXTERNAL_STORAGE` | Permite acesso a arquivos e imagens armazenadas para processamento, se necessário.           | Somente para upload  |

### Configurações

É preciso configurar o SDK para que ele entenda qual o fluxo de execução e os parâmetros específicos de cada módulo. O processo de inicialização é dividido em 2 partes: a configuração global e a configuração específica dos módulos.

**Configuração global**

Nesta etapa, você cria um objeto do tipo `CafSdkConfiguration`, que serve como contêiner central para todas as configurações do fluxo de captura.

1. **Ordem de apresentação dos módulos (presentationOrder):**
   * Defina a sequência na qual os módulos serão executados. Essa ordem é crucial para garantir que o fluxo de captura siga a lógica de negócio definida pelo seu projeto.
   * Por exemplo, se o fluxo exige que o documento seja capturado antes da verificação de liveness, a ordem deve colocar o módulo **Document Detector** antes do **Face Liveness**.
   * Importante: dependendo da implementação, podem acontecer variações de nomes, como `CafModuleType.FACE_LIVENESS` ou `CafModuleType.FACE_LIVENESS_UI`, que indicam se uma versão sem interface ou uma versão com interface será utilizada.

**Exemplo de código para criação da configuração global:**

```kotlin
val sdkConfiguration = CafSdkConfiguration(
    presentationOrder = listOf(
        CafModuleType.FACE_LIVENESS,         // ou CafModuleType.FACE_LIVENESS_UI dependendo do que for desejado
        CafModuleType.DOCUMENT_DETECTOR,
    )
)
```

#### Configuração específica de módulos

Após definir as configurações globais, é preciso configurar os módulos individualmente. Essa configuração específica permite ajustar parâmetros operacionais específicos, garantindo que eles se comportem conforme os requisitos do seu fluxo de captura.

#### Configuração Document Detector

O módulo **Document Detector** é responsável por capturar e processar documentos. Sua configuração envolve diversos parâmetros.

**Parâmetro obrigatório:**

* **Fluxo de captura (flow):**
  * Define uma lista de etapas ([`DocumentDetectorStep _alterar link_`](https://docs.caf.io/caf-sdk/android/cafsdk)) que especifica qual documento será capturado.
  * Esse fluxo pode ser customizado conforme os tipos de documentos a serem validados pela aplicação.
* **Parâmetros operacionais:**
  * `useAdb`, `useDebug` e `useDeveloperMode` são flags que ativam modos específicos para testes e desenvolvimento, permitindo maior flexibilidade durante a fase de integração.
  * `manualCaptureEnabled` e `manualCaptureTime` controlam se a captura manual é permitida e, em caso afirmativo, definem o tempo limite (em segundos) para que a pessoa usuária realize a ação manualmente.
  * `requestTimeout` define o tempo máximo (em segundos) que o sistema aguardará por uma resposta do servidor.
  * `showPopup` determina se um pop-up de confirmação ou instrução será exibido para a pessoa usuária após a captura do documento.

**Exemplo de código para configuração do Document Detector:**

```kotlin
sdkConfiguration.setDocumentDetectorConfig(
    CafDocumentDetectorConfig(
        flow = listOf(DocumentDetectorStep(Document.RG_FRONT), DocumentDetectorStep(Document.RG_BACK)),
        useAdb = true,
        useDebug = true,
        useDeveloperMode = true,
        manualCaptureEnabled = true,
        manualCaptureTime = 45,
        requestTimeout = 60,
        showPopup = true
    )
)
```

**Configuração Face Liveness**

A configuração do módulo **Face Liveness** é essencial para garantir a segurança e a confiabilidade do processo de verificação facial, já que ele tem a função de validar se a face capturada pertence a uma pessoa real. Os principais parâmetros são:

* **Loading (Tela de carregamento):**
  * A flag `loading` define se uma tela de carregamento deve ser exibida enquanto o módulo realiza o processamento. Isso melhora a experiência da pessoa usuária, ao informar que o processo está em andamento.
* **URLs de serviço:**
  * `authBaseUrl` e `livenessBaseUrl` são os endpoints para os serviços de autenticação e verificação de liveness, respectivamente.
  * Esses valores devem ser configurados com URLs válidas, onde o `authBaseUrl` geralmente utiliza o protocolo HTTPS para segurança, e o `livenessBaseUrl` utiliza WSS (WebSocket seguro).
* **Certificados:**
  * Ao atribuir valores nas urls de serviço, também é necessário informar a lista `certificates`, com certificados digitais que garante comunicações seguras e com servidores confiáveis.
* **Opções adicionais:**
  * `screenCaptureEnabled` ativa ou desativa a capacidade de capturar a tela durante o processo de verificação.
  * `debugModeEnabled` permite que logs e informações adicionais sejam disponibilizados durante a execução, facilitando a depuração.

**Exemplo de código para configuração do Face Liveness:**

```kotlin
sdkConfiguration.setFaceLivenessConfig(
    CafFaceLivenessConfig(
        loading = true,                                         // Exibe tela de carregamento durante o processamento
        authBaseUrl = "https://seu-auth-base-url.com",          // Endpoint para autenticação
        livenessBaseUrl = "wss://seu-liveness-base-url.com",    // Endpoint para verificação de liveness
        certificates = listOf("certificado1", "certificado2"),  
        screenCaptureEnabled = true,                            // Permite captura de tela se necessário
        debugModeEnabled = true                                 // Habilita modo debug para logs detalhados
    )
)
```

Essas configurações iniciais são fundamentais para garantir que o SDK opere conforme o esperado. Cada parâmetro foi pensado para oferecer flexibilidade e segurança, permitindo que o fluxo de captura seja adaptado às necessidades específicas da sua aplicação.

Ao finalizar essas configurações, o SDK estará pronto para ser inicializado e executado, garantindo uma integração robusta e eficiente com os módulos.

***

## Inicialização do Builder

A inicialização do Builder é a etapa onde o fluxo de captura do CafSDK é configurado para a execução. Utilizando a classe `CafSdkProvider.Builder`, você configura os parâmetros essenciais que definem o comportamento do fluxo e prepara o SDK para ser iniciado.

### Parâmetros essenciais

* **mobileToken:** token que autentica a requisição e garante que apenas clientes autorizados iniciem o fluxo.
* **personId:** identificador único de usuário para o qual o fluxo será executado.
* **environment:** define o ambiente de execução, por exemplo, `CafEnvironment.PROD` para produção. Isso possibilita a alternância entre ambientes de desenvolvimento, homologação e produção.
* **configuration:** o objeto `CafSdkConfiguration` previamente configurado, contém tanto a ordem de execução dos módulos quanto as configurações específicas.
* **callback:** um callback unificado, onde todos os eventos gerados pelos módulos (como carregamento, sucesso, erro e cancelamento) são tratados de forma centralizada.

**Exemplo detalhado de código:**

```kotlin
val sdkBuilder = CafSdkProvider.Builder(
    mobileToken = "seu-mobile-token",    // Token de autenticação
    personId = "seu-person-id",          // Identificador do usuário
    environment = CafEnvironment.PROD,   // Ambiente de produção
    configuration = sdkConfiguration,    // Configuração global com ordem e parâmetros dos módulos
    callback = ::callbackEvent
).build()
```

### Callback unificado

O callback unificado é um dos pilares do CafSDK, responsável por notificar a aplicação sobre o estado de cada etapa do fluxo de captura. Ele centraliza os eventos disparados pelos módulos e permite que o desenvolvedor implemente lógicas de resposta, registros de log e tratamento de erros.

#### Tipos de eventos no Callback:

* **Log:** captura mensagens de log com diferentes níveis (DEBUG, USAGE, INFO). Essas mensagens ajudam a identificar o comportamento interno do fluxo.
* **Loading:** indica o início do processamento de um módulo. Útil para exibir indicadores visuais de progresso.
* **Loaded:** confirma que determinada ação foi realizada. Útil para ocultar identificadores visuais de progresso.
* **Success:** ao finalizar com êxito, cada módulo dispara um evento contendo um objeto [`CafUnifiedResponse _alterar link_`](https://docs.caf.io/caf-sdk/android/cafsdk).
* **Error:** caso ocorra um problema durante a execução, esse evento é disparado com a mensagem de erro, permitindo que a aplicação trate a falha.
* **Cancelled:** indica que o usuário ou o sistema interrompeu o fluxo, possibilitando ações de recuperação ou notificações.

**Exemplos de códigos:**

```kotlin
private fun callbackEvent(event: CafUnifiedEvent): Unit = when(event) {
        is CafUnifiedEvent.Log -> {
            // Logs informativos, úteis para depuração e monitoramento
            log("[LOG] ${event.level}: ${event.message}")
        }
        is CafUnifiedEvent.Loading -> {
            // Indica alguma execução foi iniciada internamente (pode exibir uma tela de carregamento)
            log("[LOADING] Iniciando módulo...")
        }
        is CafUnifiedEvent.Loaded -> {
            // Indica execução interna foi concluída (pode ocultar uma tela de carregamento)
            log("[LOADED] Módulo carregado.")
        }
        is CafUnifiedEvent.Success -> {
            // Quando o módulo é concluído com sucesso, o callback recebe o nome do módulo e os resultados
            log("[SUCCESS] Módulo: ${event.response.moduleName}")
            log("[SUCCESS] Resultado: ${event.response.result}")
        }
        is CafUnifiedEvent.Error -> {
            // Captura erros ocorridos durante a execução e permite implementar lógica de tratamento de falhas
            log("[ERROR] ${event.message}")
        }
        is CafUnifiedEvent.Cancelled -> {
            // Informa que a operação foi cancelada pelo usuário ou por alguma falha na execução
            log("[CANCELLED] Operação cancelada.")
        }
    }
```

### Início do fluxo configurado

Após a construção do objeto `sdkBuilder` com todas as configurações e o callback definidos, o fluxo de captura é iniciado chamando o método `start()`. Esse método recebe o contexto (é recomendado o contexto da aplicação), e dá início à execução sequencial dos módulos configurados.

**Código para iniciar o fluxo:**

```kotlin
sdkBuilder.start(this)
```

#### Detalhes do processo

* **Contexto:** o parâmetro passado para `start()` deve ser um contexto válido (por exemplo, a instância atual da `aplicação`), permitindo que o SDK exiba as telas de captura e gerencie as transições de UI.
* **Execução sequencial:** o SDK inicia os módulos na ordem definida em `presentationOrder`. Cada módulo é executado sequencialmente e, ao concluir, aciona o próximo, garantindo que o fluxo siga a lógica estabelecida.
* **Integração com o Callback:** durante a execução, o SDK utiliza o callback unificado para enviar os eventos correspondentes (loading, loaded, success, etc.), permitindo que a aplicação reaja em tempo real conforme o estado do fluxo.

## Concluir uma sessão

A finalização ou conclusão de uma sessão no CafSDK ocorre quando todos os módulos configurados foram executados, ou quando ocorre um erro/cancelamento no fluxo.

**Definição de sessão completa**

* **Execução completa:** a sessão é considerada concluída quando cada módulo no fluxo de captura dispara um evento `Success`, indicando que todas as operações foram realizadas com êxito.
* **Interrupção do fluxo:** se ocorrer um erro ou se a pessoa usuária cancelar o processo em algum ponto, a sessão é interrompida e o evento `Error` ou `Cancelled` é disparado, permitindo que a aplicação tome as medidas necessárias.

**Eventos de Finalização**

* **Success:**\
  Cada módulo que termina com sucesso envia um evento do tipo `CafUnifiedEvent.Success`, que inclui:
  * `moduleName:` identifica o módulo que completou a operação (Ex.: `"documentDetector"` ou `"faceLiveness"`).
  * `result:` um mapa (`Map<String, Any>`) contendo os dados do resultado obtido pela execução do módulo. Esses dados podem incluir informações relevantes para o processo, como imagens capturadas ou resultados da validação.
* **Error/Cancelled:**\
  Caso o fluxo seja interrompido por uma falha ou cancelamento:
  * **Error:** um evento `CafUnifiedEvent.Error` é disparado com uma mensagem descritiva do problema, permitindo implementar lógicas de recuperação ou notificações aos usuários.
  * **Cancelled:** se o processo for cancelado (por exemplo, pela pessoa usuária), o evento `CafUnifiedEvent.Cancelled` é disparado, permitindo a limpeza de recursos ou a exibição de mensagens informativas.

{% hint style="info" %}
Essas etapas garantem que você tenha uma visão completa e técnica do processo de inicialização e finalização do fluxo do CafSDK, permitindo uma integração simplificada e a implementação de estratégias adequadas para o tratamento de cada etapa do fluxo de captura.
{% endhint %}

## Exemplo de uma implementação

```kotlin
    private fun startCaf() {
        val sdkConfiguration = CafSdkConfiguration(
            presentationOrder = listOf(CafModuleType.FACE_LIVENESS, CafModuleType.DOCUMENT_DETECTOR)
        ).apply {
            setDocumentDetectorConfig(
                CafDocumentDetectorConfig(
                    flow = listOf(DocumentDetectorStep(Document.RG_FRONT), DocumentDetectorStep(Document.RG_BACK)),
                    useAdb = true,
                    useDebug = true,
                    useDeveloperMode = true,
                    manualCaptureEnabled = true,
                    manualCaptureTime = 45,
                    requestTimeout = 60,
                    showPopup = true
                )
            )
            setFaceLivenessConfig(
                CafFaceLivenessConfig(
                    loading = true,
                    debugModeEnabled = true
                )
            )
        }
        CafSdkProvider.Builder(
            mobileToken = MOBILE_TOKEN,
            personId = PERSON_ID,
            environment = CafEnvironment.PROD,
            configuration = sdkConfiguration,
            callback = ::callbackEvent
        )
            .build()
            .start(requireContext().applicationContext)
    }

    private fun callbackEvent(event: CafUnifiedEvent): Unit = when (event) {
        is CafUnifiedEvent.Log -> {
            // Logs informativos, úteis para depuração e monitoramento
            log("[LOG] ${event.level}: ${event.message}")
        }

        is CafUnifiedEvent.Loading -> {
            // Indica que um módulo iniciou seu processo (pode exibir uma tela de carregamento)
            log("[LOADING] Iniciando módulo...")
        }

        is CafUnifiedEvent.Loaded -> {
            // Notifica que o módulo terminou de carregar e está pronto para execução
            log("[LOADED] Módulo carregado.")
        }

        is CafUnifiedEvent.Success -> {
            // Quando o módulo é concluído com sucesso, o callback recebe o nome do módulo e os resultados
            log("[SUCCESS] Módulo: ${event.response.moduleName}")
            log("[SUCCESS] Resultado: ${event.response.result}")
        }

        is CafUnifiedEvent.Error -> {
            // Captura erros ocorridos durante a execução e permite implementar lógica de tratamento de falhas
            log("[ERROR] ${event.message}")
        }

        is CafUnifiedEvent.Cancelled -> {
            // Informa que a operação foi cancelada pelo usuário ou por alguma falha na execução
            log("[CANCELLED] Operação cancelada.")
        }
    }
```

***

## Personalização avançada de fluxo

Saiba como personalizar e ajustar o fluxo de captura do CafSDK para atender requisitos específicos de negócio e experiência do usuário.

**Ordem de execução**

* A ordem em que os módulos serão executados é definida no campo `presentationOrder` do objeto `CafSdkConfiguration`.
* Essa sequência é fundamental, pois impacta diretamente na lógica do fluxo. Por exemplo, se o processo exige que o documento seja capturado antes da verificação facial, a ordem deve refletir essa prioridade.

**Exemplo de código:**

```kotlin
val sdkConfiguration = CafSdkConfiguration(
    presentationOrder = listOf(
        CafModuleType.DOCUMENT_DETECTOR,
        CafModuleType.FACE_LIVENESS
    ),
    colorConfig = CafColorConfiguration(
        primaryColor = "#0000FF",
        secondaryColor = "#00FF00"
    )
)
```

**Configuração específica**

Para personalizar os módulos individualmente, utilize os métodos `setDocumentDetectorConfig` e `setFaceLivenessConfig`. Eles permitem ajustar parâmetros críticos, como:

* **Tempo de captura:** define o tempo limite para que o usuário realize a captura manual.
* **Timeout:** estabelece o limite máximo de espera para a resposta de um serviço.
* **Flags de depuração:** habilitam ou desabilitam modos de depuração para facilitar a identificação de problemas durante o desenvolvimento.
* **Layout e outros parâmetros:** permitem configurar elementos visuais e operacionais específicos de cada módulo.

**Personalização visual**

Com o objeto `CafColorConfiguration`, é possível alinhar a identidade visual do fluxo de captura com a marca da sua aplicação.

Essa personalização garante que os elementos visuais (botões, fundos e indicadores) mantenham consistência com o design do aplicativo.

**Logging e monitoramento**

O callback unificado implementa diferentes níveis de log (DEBUG, USAGE, INFO), o que possibilita uma visão detalhada de cada etapa do fluxo.

Esses logs são essenciais para integrar com ferramentas de monitoramento, ajustar o desempenho ou identificar problemas em tempo real.

**Exemplo no Callback:**

```kotlin
callback = { event ->
    when (event) {
        is CafUnifiedEvent.Log -> {
            // Níveis de log possibilitam um monitoramento granular do fluxo
            log("[LOG] ${event.level}: ${event.message}")
        }
        // Outros casos são tratados conforme mostrado em seções anteriores...
    }
}
```

***

## Configuração do Face Liveness

A integração do módulo **Caf Face Liveness (FL)** é realizada por sua configuração no objeto `CafSdkConfiguration`. Assim que definido, o fluxo executa automaticamente o módulo na posição correspondente definida na ordem de apresentação.

A configuração do Face Liveness é feita por meio do objeto `CafFaceLivenessConfig`, onde são informados os parâmetros que o SDK utilizará durante sua execução. Confira os principais métodos de configuração disponíveis:

| Método                    | Tipo                    | Descrição                                                                                                     |
| ------------------------- | ----------------------- | ------------------------------------------------------------------------------------------------------------- |
| `setLoading`              | Boolean                 | Habilita ou desabilita a tela de carregamento. O padrão é `false`.                                            |
| `setAuthBaseUrl`          | String                  | Define a URL do proxy reverso para autenticação. Deve utilizar o protocolo HTTPS.                             |
| `setLivenessBaseUrl`      | String                  | Define a URL do proxy reverso para a verificação de Face Liveness. Deve utilizar o protocolo WSS.             |
| `setCertificates`         | List                    | Define os certificados codificados em Base64 (SHA-256) para o proxy reverso.                                  |
| `setScreenCaptureEnabled` | Boolean                 | Habilita ou desabilita a captura de tela. O padrão é `false`.                                                 |
| `setDebugModeEnabled`     | Boolean                 | Habilita ou desabilita a geração de logs para auxiliar na depuração durante a integração. O padrão é `false`. |
| `setSdkType`              | CafFaceLivenessPlatform | Informa qual plataforma está executando o SDK. O padrão é `CafFaceLivenessPlatform.NATIVE_ANDROID`.           |

**Exemplo de configuração para Face Liveness:**

```kotlin
sdkConfiguration.setFaceLivenessConfig(
    CafFaceLivenessConfig(
        loading = true,
        authBaseUrl = "https://seu-auth-base-url.com",
        livenessBaseUrl = "wss://seu-liveness-base-url.com",
        certificates = listOf("certificado1", "certificado2"),
        screenCaptureEnabled = true,
        debugModeEnabled = true
    )
)
```

### Resultado

Após a execução bem-sucedida do módulo, é disparado um evento do tipo `CafUnifiedEvent.Success`, que contém:

* **moduleName:** o nome identificador do módulo (Ex.: `"faceLiveness"`).
* **result:** um mapa (`Map<String, Any>`) com os dados da verificação.

Então, esses dados são processados pelo callback unificado, permitindo a atualização da interface da pessoa usuária ou a continuidade do fluxo, conforme necessário.

## Configurações personalizadas - Face Liveness

Use configurações personalizadas para direcionar as requisições através de proxies seguros e garantir que os protocolos corretos (WSS para Face Liveness e HTTPS para autenticação) sejam utilizados.

### Configuração de Proxy reverso

Essa configuração avançada permite que você direcione as conexões do módulo Face Liveness através de um proxy reverso, utilizando o protocolo WSS (Web Socket Secure). Siga as etapas para configurar corretamente:

1. **URL do Proxy:** defina seu proxy para se comunicar com o endpoint desejado. Por exemplo, você pode utilizar:`wss://us.rp.secure.iproov.me/ws` ou outro URL compatível.
2. **Configuração da URL do Face Liveness:** use o método `.setLivenessBaseUrl` para configurar a URL do Face Liveness. Lembre-se de que o protocolo deve ser **WSS**.
3. **Definição dos certificados:**&#x74; use o método `.setCertificates` para definir os certificados necessários. Esses certificados devem ser os hashes SHA256 codificados em Base64 dos certificados do proxy.

#### Exemplo de código:

```kotlin
sdkConfiguration.setFaceLivenessConfig(
    CafFaceLivenessConfig(
        livenessBaseUrl = "wss://my.proxy.io/ws/",
        certificates = listOf(
            "4d69f16113bed7d62ca56feb68d32a0fcb7293d3960=",
            "50f71c5dda30741ee4be1ac378e12539b0d1d511f99=",
            "9f85e26c1ae41f7ac97adc4099be7f2a40759510ab9="
        )
    )
)
```

### Proxy reverso para autenticação

Para a comunicação de autenticação, é necessário configurar o proxy reverso com uma URL HTTPS. Essa configuração direciona as requisições de autenticação para o ambiente adequado.

1. **URL do Proxy:** defina o seu proxy para se comunicar. Por exemplo, você pode utilizar: `https://api.public.caf.io/` .
2. **Configuração da URL de autenticação:** use o método `.setAuthBaseUrl` para especificar a URL de autenticação, garantindo que o protocolo HTTPS seja utilizado.

#### Exemplo de código:

```kotlin
sdkConfiguration.setFaceLivenessConfig(
    CafFaceLivenessConfig(
        authBaseUrl = "https://my.proxy.io/v1/faces/"
    )
)
```

> **Observação:** na prática, ambas as configurações (para autenticação e para Face Liveness) podem ser combinadas em uma única instância de `CafFaceLivenessConfig`.

## Estruturas de configuração

Ao usar o módulo de UI (com sufixo `-ui`), você estará utilizando telas proprietárias da Caf, que têm algumas possibilidades de personalização. Confira os detalhes:

### CafFaceLivenessInstructionsScreen

Essa estrutura permite personalizar a tela de instruções do Face Liveness.

| Propriedade   | Tipo            | Descrição                                                                                                                                             | Valor padrão |
| ------------- | --------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------- | ------------ |
| `image`       | `String?`       | Imagem exibida no cabeçalho da tela. O valor pode ser uma URL, o ID do resource (no formato string) ou o nome do resource presente na pasta drawable. | `null`       |
| `title`       | `String?`       | Título da tela (Ex.: "Instruções para Escanear o Rosto").                                                                                             | `null`       |
| `description` | `String?`       | Texto descritivo breve (ex.: "Siga os passos abaixo").                                                                                                | `null`       |
| `steps`       | `List<String>?` | Lista ordenada de instruções (Ex.: listOf ("Mantenha o telefone estável"; "Boa iluminação").                                                          | `null`       |
| `buttonText`  | `String?`       | Texto para o botão de confirmação (Ex.: "Iniciar escaneamento").                                                                                      | `null`       |

### CafColorConfiguration

Essa estrutura permite personalizar as cores globais de todas as interfaces. As cores seguem o padrão `RGB` ou `ARGB`.

| Propriedade       | Tipo     | Descrição                                           | Formato                     |
| ----------------- | -------- | --------------------------------------------------- | --------------------------- |
| `primaryColor`    | `String` | Cor principal para botões e destaques.              | Código Hex (ex.: `#FF0000`) |
| `secondaryColor`  | `String` | Cor secundária para elementos complementares.       | Código Hex                  |
| `backgroundColor` | `String` | Cor de fundo da tela.                               | Código Hex                  |
| `contentColor`    | `String` | Cor utilizada para textos e ícones.                 | Código Hex                  |
| `mediumColor`     | `String` | Cor neutra para elementos como barras de progresso. | Código Hex                  |

## Exemplos de código

Confira no exemplo como configurar o módulo Face Liveness com instruções, proxy reverso (para autenticação e verificação) e personalização da interface.

```kotlin
val sdkConfiguration = CafSdkConfiguration(
      presentationOrder = listOf(...),
      colorConfig = CafColorConfiguration(
         primaryColor = "#FF0000",
         secondaryColor = "#00FF00",
         backgroundColor = "#FFFFFF",
         contentColor = "#000000",
         mediumColor = "#D1D1D1"
      )
)
sdkConfiguration.setFaceLivenessConfig(
   CafFaceLivenessConfig(
      loading = true,
      authBaseUrl = "https://seu-auth-base-url.com",
      livenessBaseUrl = "wss://seu-liveness-base-url.com",
      certificates = listOf("certificado1", "certificado2"),
      screenCaptureEnabled = true,
      debugModeEnabled = true
   )
)
sdkConfiguration.setCafFaceLivenessInstructionsScreen(
   CafFaceLivenessInstructionsScreen(
      image = R.drawable.scan_icon.toString()
      title = "Escaneie seu Rosto",
      description = "Siga os passos abaixo:",
      steps = listOf("Mantenha o telefone estável", "Garanta boa iluminação"),
      buttonText = "Iniciar Escaneamento",
   )
)
```

***

## Mais informações

### Requisitos de certificados

* **Certificados:** devem ser os hashes SHA-256 codificados em Base64 do SPKI (Subject Public Key Info) do certificado.

### Aplicação dos protocolos

* **Face Liveness:** a URL para Face Liveness **deve** **utilizar** o protocolo `wss://`.
* **Autenticação:** a URL para autenticação **deve** **utilizar** o protocolo `https://`.

***

## Configuração do Document Detector

O módulo **Caf Document Detector (DD)** é configurado de forma semelhante ao Face Liveness, mas com foco na captura e processamento de documentos.

### Configuração e execução

No `CafSdkConfiguration`, configure os parâmetros específicos do Document Detector, que determinam o comportamento da captura de documentos.

#### Parâmetros principais:

* `flow`: uma lista de etapas (`DocumentDetectorStep`) que define qual documento e quais ângulos ou partes devem ser capturados.
* `useAdb`, `useDebug` e `useDeveloperMode`: flags que auxiliam no desenvolvimento e na execução em ambientes de teste.
* `manualCaptureEnabled` e `manualCaptureTime`: configuram se a captura manual é permitida e qual o tempo limite para a ação.
* `requestTimeout`: tempo máximo para aguardar respostas de servidores ou ações de usuários.
* `showPopup`: determina se uma mensagem de confirmação ou instrução será apresentada à pessoa usuária.

**Exemplo de configuração para Document Detector:**

```kotlin
sdkConfiguration.setDocumentDetectorConfig(
    CafDocumentDetectorConfig(
        flow = listOf(DocumentDetectorStep(Document.RG_FRONT)),
        useAdb = true,
        useDebug = true,
        useDeveloperMode = true,
        manualCaptureEnabled = true,
        manualCaptureTime = 45,
        requestTimeout = 60,
        showPopup = true
    )
)
```

### Resultado

* Ao concluir a captura e o processamento do documento, o módulo Document Detector dispara um evento `CafUnifiedEvent.Success`.
* Esse evento inclui o `moduleName` (Ex.: `"documentDetector"`) e um `result` contendo os dados capturados.
* O callback unificado pode então usar essas informações para avançar para o próximo passo ou para armazenar os resultados conforme necessário.

## Configurações personalizadas - Document Detector

Para configurar o Caf Document Detector, use a estrutura `CafDocumentDetectorConfig`, que inclui:

* Etapas do fluxo de captura de documentos.
* Personalização do layout da interface (UI).
* Mensagens de feedback.
* Comportamento do upload.
* Configurações de proxy.

### Configuração principal

Propriedades do `CafDocumentDetectorConfig`.

| Propriedade                  | Tipo                     | Descrição                                                      | Padrão           |
| ---------------------------- | ------------------------ | -------------------------------------------------------------- | ---------------- |
| `flow`                       | `[DocumentDetectorStep]` | Lista ordenada das etapas de captura de documentos.            | `[]`             |
| `layout`                     | `DocumentDetectorLayout` | Personalização de UI (cores, botões, fontes).                  | Default layout   |
| `uploadSettings`             | `CafUploadSettings`      | Controla o comportamento do upload de documento.               | `enable: false`  |
| `manualCaptureEnabled`       | `Bool`                   | Habilita o botão de captura manual.                            | `true`           |
| `manualCaptureTime`          | `TimeInterval`           | Tempo limite (segundos) para captura manual.                   | `45`             |
| `requestTimeout`             | `TimeInterval`           | Tempo limite da requisição HTTP.                               | `60`             |
| `showPopup`                  | `Bool`                   | Exibe/oculta o pop-up de instruções iniciais.                  | `true`           |
| `proxySettings`              | `CafProxySettings?`      | Configuração de proxy reverso (host, port, auth).              | `nil`            |
| `previewShow`                | `Bool`                   | Habilita a tela de preview após a captura.                     | `false`          |
| `previewTitle`               | `String?`                | Texto do título na tela de preview.                            | `nil`            |
| `previewSubtitle`            | `String?`                | Texto do subtítulo na tela de preview.                         | `nil`            |
| `previewConfirmLabel`        | `String?`                | Texto para o botão de confirmação no preview.                  | `nil`            |
| `previewRetryLabel`          | `String?`                | Texto para o botão de nova tentativa no preview.               | `nil`            |
| `messageSettings`            | `CafMessageSettings`     | Mensagens de feedback personalizáveis.                         | Default messages |
| `enableMultiLanguage`        | `Bool`                   | Habilita a tradução automática das mensagens padrão.           | `true`           |
| `allowedPassportCountryList` | `[CafCountryCodes]?`     | Lista de países de passaportes permitidos (Ex.: `.BR`, `.US`). | `nil`            |

### Personalização de layout

Propriedades do `DocumentDetectorLayout`.

| Propriedade              | Tipo                     | Descrição                                                     | Padrão            |
| ------------------------ | ------------------------ | ------------------------------------------------------------- | ----------------- |
| `closeButtonImage`       | `UIImage?`               | Imagem para o botão fechar.                                   | System default    |
| `closeButtonColor`       | `UIColor?`               | Cor para o botão fechar.                                      | Primary color     |
| `closeButtonSize`        | `CGFloat?`               | Tamanho (width/height) para o botão fechar.                   | `44`              |
| `closeButtonContentMode` | `UIView.ContentMode?`    | Modo de conteúdo para a imagem do botão fechar.               | `.scaleAspectFit` |
| `uploadBackGroundColor`  | `UIColor`                | Cor de fundo durante o upload.                                | Primary color     |
| `previewBackGroundColor` | `UIColor`                | Cor de fundo na tela de preview.                              | `.white`          |
| `primaryColor`           | `UIColor`                | Cor para botões/indicadores de progresso.                     | `#34D690` (green) |
| `feedbackColors`         | `DocumentFeedbackColors` | Cores para sobreposições de feedback (default/error/success). | Predefined colors |
| `font`                   | `String?`                | Nome da fonte personalizada (Ex.: "Avenir-Bold").             | System font       |

#### Exemplo de código:

```swift
let layout = DocumentDetectorLayout()
layout.closeButtonImage = UIImage(named: "close_icon")
layout.primaryColor = .blue
layout.font = "Helvetica-Bold"
layout.feedbackColors = DocumentFeedbackColors(
    defaultColor: .gray, 
    errorColor: .red, 
    successColor: .green
)
```

### Personalização de mensagem

Propriedades do `CafMessageSettings`.

| Propriedade                 | Descrição                                   | Valor padrão                      |
| --------------------------- | ------------------------------------------- | --------------------------------- |
| `waitMessage`               | Exibido durante a inicialização do SDK.     | "Aguarde" (Waiting)               |
| `fitTheDocumentMessage`     | Informa para alinhar o documento à máscara. | "Encaixe o documento na marcação" |
| `verifyingQualityMessage`   | Exibido durante a verificação de qualidade. | "Verificando qualidade…"          |
| `lowQualityDocumentMessage` | Exibido em caso de falha na captura.        | "Ops, tente novamente"            |
| `sensorLuminosityMessage`   | Aviso de baixa luminosidade.                | "Ambiente muito escuro"           |
| `sensorOrientationMessage`  | Aviso de orientação do dispositivo.         | "Celular não está na horizontal"  |
| `aiScanDocumentMessage`     | Mensagem para escanear um documento.        | "Escaneie um documento"           |
| `aiGetCloserMessage`        | Mensagem para se aproximar.                 | "Se aproxime do documento"        |
| `aiCapturedMessage`         | Confirmação de captura bem-sucedida.        | "Capturando o documento"          |

**Lista completa**: mais de 20 mensagens. Use `.set[MessageName](message: String)` para personalizar qualquer texto.

#### Exemplo de código:

```swift
let messages = CafMessageSettings()
        .setWaitMessage(message: "Please wait...")
        .setLowQualityDocumentMessage(message: "Poor quality. Retry.")
```

## Fluxo de captura de documento

Propriedades do `DocumentDetectorStep`.

| Propriedade     | Tipo          | Descrição                                         | Obrigatório  |
| --------------- | ------------- | ------------------------------------------------- | ------------ |
| `document`      | `CafDocument` | Tipo de documento para captura (Ex.: `.RG_FRONT`) | Sim          |
| `stepLabel`     | `String?`     | Texto exibido na parte inferior da tela.          | Não          |
| `illustration`  | `UIImage?`    | Imagem exibida no pop-up de instrução.            | Não          |
| `showStepLabel` | `Bool`        | Alterna a visibilidade do rótulo da etapa.        | Não (`true`) |

#### Exemplo de código:

```swift
let step = DocumentDetectorStep(
    document: .RG_FRONT,
    stepLabel: "Front of ID",
    illustration: UIImage(named: "id_front_icon")
)
```

## Configurações de upload

Propriedades do `CafUploadSettings`.

| Propriedade       | Tipo           | Descrição                                             | Padrão            |
| ----------------- | -------------- | ----------------------------------------------------- | ----------------- |
| `enable`          | `Bool`         | Ativa a funcionalidade de carregamento de documentos. | `false`           |
| `compress`        | `Bool`         | Comprime os arquivos antes do upload.                 | `true`            |
| `fileFormats`     | `[FileFormat]` | Formatos permitido: `.png`, `.jpeg`, `.pdf`.          | Todos os formatos |
| `maximumFileSize` | `Int`          | Tamanho máximo do arquivo em KB.                      | `10000` (10MB)    |

#### Exemplo de código:

```swift
let uploadSettings = CafUploadSettings(
    enable: true,
    fileFormats: [.jpeg, .pdf],
    maximumFileSize: 5000
)
```

## Configurações de Proxy

Propriedades do `CafProxySettings`.

| Propriedade | Tipo      | Descrição                      | Obrigatório |
| ----------- | --------- | ------------------------------ | ----------- |
| `hostname`  | `String`  | Proxy host (Ex.: "proxy.com"). | Sim         |
| `port`      | `Int`     | Porta do Proxy (Ex.: `8080`).  | Sim         |
| `user`      | `String?` | Authentication username.       | Não         |
| `password`  | `String?` | Authentication password.       | Não         |

#### Exemplo de código:

```swift
let proxy = CafProxySettings(hostname: "my.proxy.io", port: 443)
    .setAutentication(user: "admin", password: "secret")
```

## Documentos suportados no Document Detector

Use esses valores estáticos de `CafDocument`:

| Tipo de documento | Descrição                                     |
| ----------------- | --------------------------------------------- |
| `.RG_FRONT`       | Front of Brazilian ID (RG)                    |
| `.RG_BACK`        | Back of Brazilian ID (RG)                     |
| `.RG_FULL`        | Brazilian ID (opened, showing front and back) |
| `.CNH_FRONT`      | Front of Brazilian Driver’s License (CNH)     |
| `.CNH_BACK`       | Back of Brazilian Driver’s License (CNH)      |
| `.CNH_FULL`       | Brazilian Driver’s License (opened)           |
| `.CRLV`           | Brazilian Vehicle Registration (CRLV)         |
| `.RNE_FRONT`      | Front of Brazilian Foreigner ID (RNE)         |
| `.RNE_BACK`       | Back of Brazilian Foreigner ID (RNE)          |
| `.CTPS_FRONT`     | Front of Brazilian Work Card (CTPS)           |
| `.CTPS_BACK`      | Back of Brazilian Work Card (CTPS)            |
| `.PASSPORT`       | Passport (any country)                        |
| `.ANY`            | Generic document (no specific validation)     |

#### Exemplo de código:

```swift
let layout = DocumentDetectorLayout()
layout.primaryColor = .blue
layout.closeButtonImage = UIImage(named: "close")

let config = CafDocumentDetectorConfig(
    flow: [
        DocumentDetectorStep(document: .RG_FRONT),
        DocumentDetectorStep(document: .RG_BACK)
    ],
    layout: layout,
    uploadSettings: CafUploadSettings(enable: true),
    proxySettings: CafProxySettings(hostname: "proxy.example.com", port: 8443),
    messageSettings: CafMessageSettings()
        .setWaitMessage(message: "Initializing...")
        .setLowQualityDocumentMessage(message: "Retry capture")
)
```

***

## Recursos adicionais

### ProGuard/R8 Rules

Confira o bloco de código com as regras ProGuard/R8 necessárias para que o CafSDK e suas dependências funcionem corretamente mesmo após a ofuscação e otimização do código. Essas regras preservam informações essenciais (como assinaturas, anotações e classes internas) e evitam que classes críticas sejam removidas ou alteradas.

```proguard
# The Android pre-handler for exceptions is loaded reflectively (via ServiceLoader).
-keep class kotlinx.coroutines.experimental.android.AndroidExceptionPreHandler { *; }

### GSON ##################################################################
# Gson uses generic type information stored in a class file when working with fields.
# ProGuard removes such information by default, so configure it to keep all of it.
-keepattributes Signature
# For using GSON @Expose annotation
-keepattributes *Annotation*
### END GSON ##################################################################

### Retrofit ##################################################################
# Preserve generic signatures, inner classes, and enclosing methods for Retrofit reflection.
-keepattributes Signature, InnerClasses, EnclosingMethod
# Retain runtime-visible annotations on methods and parameters.
-keepattributes RuntimeVisibleAnnotations, RuntimeVisibleParameterAnnotations
# Keep annotation default values.
-keepattributes AnnotationDefault
# Retain service method parameters for interfaces with Retrofit annotations.
-keepclassmembers,allowshrinking,allowobfuscation interface * {
    @retrofit2.http.* <methods>;
}
# Suppress warnings for build tooling and certain JSR 305 annotations.
-dontwarn org.codehaus.mojo.animal_sniffer.IgnoreJRERequirement
-dontwarn javax.annotation.**
-dontwarn kotlin.Unit
-dontwarn retrofit2.KotlinExtensions
-dontwarn retrofit2.KotlinExtensions$*
# Explicitly keep Retrofit interfaces to prevent nullification by R8.
-if interface * { @retrofit2.http.* <methods>; }
-keep,allowobfuscation interface <1>
-if interface * { @retrofit2.http.* <methods>; }
-keep,allowobfuscation interface * extends <1>
# Preserve continuations used by Kotlin suspend functions.
-keep,allowobfuscation,allowshrinking class kotlin.coroutines.Continuation
# For R8 full mode: keep generic return types for Retrofit methods.
-if interface * { @retrofit2.http.* public *** *(...); }
-keep,allowoptimization,allowshrinking,allowobfuscation class <3>
# Preserve Retrofit Response class.
-keep,allowobfuscation,allowshrinking class retrofit2.Response
### END Retrofit ##############################################################

### OkHttp ####################################################################
# Suppress warnings for JSR 305 annotations.
-dontwarn javax.annotation.**
# Adapt resource filenames for internal public suffix database.
-adaptresourcefilenames okhttp3/internal/publicsuffix/PublicSuffixDatabase.gz
# Suppress warnings for Animal Sniffer and platform-specific classes.
-dontwarn org.codehaus.mojo.animal_sniffer.*
-dontwarn okhttp3.internal.platform.**
-dontwarn org.conscrypt.**
-dontwarn org.bouncycastle.**
-dontwarn org.openjsse.**
# Keep all OkHttp and Okio classes.
-keep class okhttp3.** { *; }
-dontwarn okhttp3.**
-keep class okio.** { *; }
-dontwarn okio.**
-dontwarn javax.annotation.Nullable
-dontwarn javax.annotation.ParametersAreNonnullByDefault
### END OkHttp ################################################################

### Kotlin Serialization ######################################################
# Keep Companion objects for serializable classes.
-if @kotlinx.serialization.Serializable class **
-keepclassmembers class <1> {
    static <1>$Companion Companion;
}
# Keep serializer functions on companion objects.
-if @kotlinx.serialization.Serializable class ** {
    static **$* *;
}
-keepclassmembers class <2>$<3> {
    kotlinx.serialization.KSerializer serializer(...);
}
# Retain INSTANCE and serializer for serializable objects.
-if @kotlinx.serialization.Serializable class ** {
    public static ** INSTANCE;
}
-keepclassmembers class <1> {
    public static <1> INSTANCE;
    kotlinx.serialization.KSerializer serializer(...);
}
# Preserve Companion objects in kotlinx.serialization.json.
-keepclassmembers class kotlinx.serialization.json.** {
    *** Companion;
}
-keepclasseswithmembers class kotlinx.serialization.json.** {
    kotlinx.serialization.KSerializer serializer(...);
}
# Preserve serializer lookup for serializable classes (adjust package name as needed).
-keepclassmembers @kotlinx.serialization.Serializable class packeage.** {
    *** Companion;
    *** INSTANCE;
    kotlinx.serialization.KSerializer serializer(...);
}
### END Kotlin Serialization #################################################

### AutoValue ################################################################
-dontwarn com.google.auto.**
-dontwarn autovalue.shaded.com.**
-dontwarn sun.misc.Unsafe
-dontwarn javax.lang.model.element.Modifier
### END AutoValue ############################################################

### CAF - Combate a Fraude ######################################################
# Keep exceptions attributes.
-keepattributes Exceptions
# Preserve all classes, interfaces, and class members for CAF modules.
-keep class com.caf.facelivenessiproov.** { *; }
-keep class com.combateafraude.documentdetector.** { *; }
-keep class com.combateafraude.** { *; }
-keep interface com.combateafraude.** { *; }
-keepclassmembers class com.combateafraude.** { *; }
# Suppress warnings for java.nio.file and certain OkHttp internal classes.
-dontwarn java.nio.file.*
-dontwarn com.squareup.okhttp.internal.Platform
# Keep fields in classes extending GeneratedMessageLite (for Tink usage).
-keepclassmembers class * extends com.google.crypto.tink.shaded.protobuf.GeneratedMessageLite {
  <fields>;
}
# Preserve TensorFlow classes.
-keep class org.tensorflow.** { *; }
-keep class org.tensorflow.**$* { *; }
-dontwarn org.tensorflow.**
# Preserve IProov classes and Protobuf classes.
-keep public class com.iproov.sdk.IProov { public *; }
-keep class com.iproov.** { *; }
-keep class com.iproov.**$* { *; }
-keep class com.google.protobuf.** { *; }
-keep class com.google.protobuf.**$* { *; }
-dontwarn com.google.protobuf.**
# Suppress warnings for concurrent Flow classes.
-dontwarn java.util.concurrent.Flow*
# Preserve Kotlin and kotlinx classes.
-keep class kotlin.** { *; }
-keep class kotlinx.** { *; }
### END CAF - Combate a Fraude ##################################################
```

***

## Suporte técnico e Dicas de uso

**Suporte técnico**\
Em caso de dúvidas ou dificuldades na integração, entre em contato com o suporte técnico da Caf.

**Dicas de uso**

* **Realize testes:** execute testes em dispositivos reais para validar os requisitos e o desempenho do fluxo.
* **Explore customizações:** utilize as opções de customização avançada para adaptar o fluxo às necessidades do seu projeto.
* **Monitore o desempenho:** integre ferramentas de monitoramento para acompanhar os logs e o desempenho do fluxo em produção.


---

# Agent Instructions
This documentation is published with GitBook. GitBook is the documentation platform designed so that both humans and AI agents can read, navigate, and reason over technical content effectively. Learn more at gitbook.com.

## Querying This Documentation
If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter, and the optional `goal` query parameter:

```
GET https://docs.caf.io/caf-sdk/android/comecando-com-o-sdk.md?ask=<question>&goal=<endgoal>
```

`ask` is the immediate question: it should be specific, self-contained, and written in natural language.
`goal` is optional and describes the broader end goal you are ultimately trying to accomplish on behalf of the user. GitBook uses it to tailor the answer towards what is most useful for that goal.

The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
