> For the complete documentation index, see [llms.txt](https://docs.facephi.com/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.facephi.com/sdks/backend-sdk/selphid/technical_documentation/api_reference.md).

# Guía de referencia de la API

## 1. Introducción

Este documento incluye la descripción de la API de las bibliotecas proporcionadas en el producto **FacePhi SelphID SDK**.

## 2. Descripción de la API de SelphID (Front-end)

**SelphID SDK** es un conjunto de bibliotecas de servidor que utiliza la información generada por los Widgets de **FacePhi** para aplicaciones nativas o web. Como se describe en las siguientes secciones, se proporcionan algunos componentes denominados Widgets para la captura facial (Selphi) y la captura de documentos de identidad (SelphID), que pueden integrarse en el front-end de cualquier aplicación.

### 2.1. Widget Selphi

Mediante el widget **Selphi**, que incorpora el mecanismo de detección y extracción facial y de vida del usuario, se puede obtener la siguiente información a través de las propiedades que se indican a continuación:

* **`Image` property:** Representa la imagen del usuario con la pose facial más frontal detectada.
* **`TemplateRaw` property:** Representa la biometric template tokenizada del usuario con la pose facial más frontal detectada. Esta plantilla se utiliza para realizar la autenticación biométrica con SelphID SDK.

> **Nota**
>
> Adicionalmente, se proporciona una funcionalidad tokenizada **generateTemplateRaw** (ver API) que permite convertir una imagen o un buffer de datos en un buffer de datos tokenizado en forma de `templateRaw`. Este `templateRaw` puede utilizarse en varias funcionalidades de SelphID SDK.

### 2.2. Widget SelphID

Mediante el widget **SelphID**, que incorpora el mecanismo automático de detección y captura de documentos, se puede obtener la siguiente información a través de las propiedades que se indican a continuación:

* **`TokenOCR` property:** Representa un token (marca de tiempo + cifrado AES256) que contiene los datos detectados en el documento mediante el OCR realizado.
* **`TokenFrontDocument` property:** Representa la imagen tokenizada (marca de tiempo + cifrado AES256) del anverso del documento ajustada a los bordes del documento.
* **`TokenBackDocument` property:** Representa la imagen tokenizada (marca de tiempo + cifrado AES256) del reverso del documento ajustada a los bordes del documento.
* **`TokenFaceImage` property:** Representa la imagen tokenizada (marca de tiempo + cifrado AES256) de la fotografía del usuario en el documento. Este token se utiliza para realizar la autenticación biométrica con el SDK.
* **`TokenRawFrontDocument` property:** Representa la imagen tokenizada (marca de tiempo + cifrado AES256) del anverso del documento sin recortar a los bordes del documento, es decir, tal y como fue capturada por la cámara.
* **`TokenRawBackDocument` property:** Representa la imagen tokenizada (marca de tiempo + cifrado AES256) del reverso del documento sin recortar a los bordes del documento, es decir, tal y como fue capturada por la cámara.

## 3. Descripción de la API de SelphID (Back-end)

A continuación se describe la API de las bibliotecas proporcionadas en SelphID, detallando los métodos que el integrador puede utilizar para incorporar las funcionalidades de reconocimiento facial, extracción de información en documentos de identidad y validación de documentos.

### 3.1. Inicialización de las bibliotecas

`SelphIDVerifier` representa la clase principal de las bibliotecas, que contiene todos los métodos disponibles para cada una de las funcionalidades.

La inicialización de las bibliotecas puede realizarse de tres formas diferentes en función de las variables de entorno configuradas:

#### 3.1.1. Inicialización mediante el método `loadWithConfigPath()`

> **Pasos previos**
>
> Configure las variables de entorno y el archivo config.cfg (configuración del SDK para instalación On-premise):
>
> * `FACEPHI_SELPHID_INSTALL_PATH`
> * `FACEPHI_SELPHID_INSTALL_BIN`
> * `LD_LIBRARY_PATH`
> * `PATH`

```java
public static void main(String[] args) {
  // Instantiate a SelphIDVerifier object.
  SelphIDVerifier verifier = new SelphIDVerifier();

  // Specifies the path where the configuration file is located.
  String configurationFilePath =
    "C:/Program Files/FacePhi/Sdk/SelphId/x.x.x.x/config/config.cfg";

  // Load the library indicating the path where to look for the config file.
  verifier.loadWithConfigPath(configurationFilePath);

  // Make use of the library.

  // Unload the library when you have finished.
  verifier.unload();
}
```

#### 3.1.2. Inicialización mediante el método `load()`

> **Pasos previos**
>
> Configure las variables de entorno y el archivo config.cfg (configuración del SDK para instalación On-premise):
>
> * `FACEPHI_SELPHID_INSTALL_PATH`
> * `FACEPHI_SELPHID_INSTALL_BIN`
> * `LD_LIBRARY_PATH`
> * `PATH`
>
> No es necesario especificar la ruta del archivo de configuración, ya que se buscará automáticamente en la siguiente ruta: `FACEPHI_SELPHID_INSTALL_PATH`/config/selphid.cfg

```java
public static void main(String[] args) {
  // Instantiate a SelphIDVerifier object.
  SelphIDVerifier verifier = new SelphIDVerifier();

  // Load the library.
  verifier.load();

  // Make use of the library.

  // Unload the library when you have finished.
  verifier.unload();
}
```

#### 3.1.3. Inicialización mediante el método `loadFromEnvVars()`

> **Pasos previos**
>
> Configure las variables de entorno (configuración del SDK para instalación On-premise):
>
> * `FACEPHI_SELPHID_INSTALL_PATH`
> * `FACEPHI_SELPHID_INSTALL_BIN`
> * `LD_LIBRARY_PATH`
> * `PATH`
> * `FACEPHI_SELPHID_DEBUGPATH_KEY`
> * `FACEPHI_SELPHID_USAGEPATH_KEY`
> * `FACEPHI_SELPHID_FACIALLIVENESS_PATH_KEY`
> * `FACEPHI_SELPHID_FACIAL_LICPATH_KEY`
>
> En lugar de configurar el archivo config.cfg, estas variables se establecen directamente como variables de entorno.

```java
public static void main(String[] args) {
  // Instantiate a SelphIDVerifier object.
  SelphIDVerifier verifier = new SelphIDVerifier();

  // Load the library.
  verifier.loadFromEnvVars();

  // Make use of the library.

  // Unload the library when you have finished.
  verifier.unload();
}
```

> **Importante**
>
> La inicialización de las bibliotecas mediante el método `load()`, `loadWithConfigPath()` o `loadFromEnvVars()` solo debe realizarse una vez durante el ciclo de vida de su aplicación.
>
> Una vez finalizados todos los procesos que implican el uso de estas bibliotecas, es importante liberar los recursos asociados a ellas; **no olvide descargar (unload) la biblioteca antes de cerrar la aplicación**.
>
> La finalización de las bibliotecas mediante el método `unload()` solo debe realizarse una vez durante el ciclo de vida de su aplicación. **Una vez invocado el método `unload()`, ya no es posible realizar un `load()`**.
>
> Si se produce alguna condición que impida cargar correctamente las bibliotecas, se lanzará una `SelphIDException`. Para conocer los tipos de excepción, consulte la sección correspondiente [3.10. Descripción de SelphIDException](#310-descripción-de-selphidexception) en la API proporcionada.

### 3.2. Métodos de extracción facial

Para realizar la extracción de los datos faciales de un usuario, el integrador dispone de diferentes métodos en la clase `SelphIDVerifier`. El integrador deberá utilizar uno u otro método en función de los datos generados en el cliente. A continuación se describen cada una de las posibles situaciones.

> **Nota**
>
> El resultado de estos métodos será siempre un objeto `SelphIDFacialExtractionResult`, explicado en [3.9.1. SelphIDFacialExtractionResult](#391-selphidfacialextractionresult).

#### 3.2.1. Extracción facial mediante una imagen

El método a utilizar es el siguiente:

```java
SelphIDFacialExtractionResult r = extractFacialWithImageBuffer(
  byte[] imageBuffer,
  SelphIDVerifierOptions options
);
```

Los pasos necesarios para realizar una extracción facial mediante una imagen son los siguientes (método de ejemplo):

> **Pasos previos**
>
> * Obtenga la imagen (cadena en base64) a través de la propiedad Image utilizando el widget Selphi.
> * Envíe la cadena en base64 de la imagen al servidor.

```java
String extractBiometricFacialTemplate(String imageBase64) {
  // Decode base64 to get the byte array corresponding to the image on the server.
  byte[] imageBuffer = Base64.getDecoder().decode(
    imageBase64.getBytes());

  // Create the SelphIDVerifierOptions and configure it if needed.
  SelphIDVerifierOptions options = new SelphIDVerifierOptions();

  // Extraction
  // Check 3.1. section to initializate SelphIDVerifier.
  SelphIDFacialExtractionResult r = verifier.extractFacialWithImageBuffer(imageBuffer, options);

  // Explore the information obtained in SelphIDFacialExtractionResult like facial position.
  Rectangle facePostion = r.getFaceRectangle();

  // Return the biometric facial template.
  return r.getFacialTemplate();
}
```

#### 3.2.2. Extracción facial mediante una plantilla

El método a utilizar es el siguiente:

```java
SelphIDFacialExtractionResult r = extractFacialWithRawTemplate(
  byte[] rawTemplateBuffer,
  SelphIDVerifierOptions options
);
```

Los pasos necesarios para realizar una extracción facial mediante una biometric template son los siguientes (método de ejemplo):

> **Pasos previos**
>
> * Obtenga la biometric template (cadena en base64) a través de la propiedad TemplateRaw utilizando el widget Selphi.
> * Envíe la cadena en base64 de la biometric template al servidor.

```java
String extractBiometricFacialTemplate(String templateRawBase64) {
  // Decode base64 to get the byte array corresponding to the template.
  byte[] rawTemplateBuffer = Base64.getDecoder().decode(
    templateRawBase64.getBytes());

  // Create the SelphIDVerifierOptions and configure it if needed.
  SelphIDVerifierOptions options = new SelphIDVerifierOptions();

  // Extraction
  // Check 3.1. section to initializate SelphIDVerifier.
  SelphIDFacialExtractionResult r = verifier.extractFacialWithRawTemplate(rawTemplateBuffer, options);

  // Explore the information obtained in SelphIDFacialExtractionResult like facial position.
  Rectangle facePostion = r.getFaceRectangle();

  // Return the biometric facial template.
  return r.getFacialTemplate();
}
```

### 3.3. Métodos de autenticación facial

Para realizar la autenticación facial de un usuario, el integrador dispone de diferentes métodos en la clase `SelphIDVerifier`. El integrador deberá utilizar uno u otro método en función de los datos generados en el cliente. Cada una de las posibles situaciones se describe en los siguientes subapartados.

> **Nota**
>
> El resultado de estos métodos será siempre un objeto `SelphIDFacialAuthenticationResult`, explicado en [3.9.2. SelphIDFacialAuthenticationResult](#392-selphidfacialauthenticationresult).

#### 3.3.1. Autenticación facial mediante imágenes

```java
SelphIDFacialAuthenticationResult r = authenticateFacialWithImageBuffers(
  byte[] imageQuery,
  byte[] imageTarget,
  SelphIDVerifierOptions options
);
```

Los pasos necesarios para realizar una autenticación facial mediante dos imágenes son los siguientes (método de ejemplo):

> **Pasos previos**
>
> * Obtenga la primera imagen (cadena en base64) a través de la propiedad Image utilizando el widget Selphi.
> * Obtenga la segunda imagen (cadena en base64) a través de la propiedad Image utilizando el widget Selphi.
> * Envíe ambas cadenas en base64 al servidor.

```java
boolean isMatch(String firstImageBase64, String secondImageBase64) {
  // Decode base64 to get the byte array corresponding to each image on the server.
  byte[] imageQuery = Base64.getDecoder().decode(
    firstImageBase64.getBytes());
  byte[] imageTarget = Base64.getDecoder().decode(
    secondImageBase64.getBytes());

  // Create the SelphIDVerifierOptions and configure it if needed.
  SelphIDVerifierOptions options = new SelphIDVerifierOptions();

  // Extraction
  // Check 3.1. section to initializate SelphIDVerifier.
  SelphIDFacialAuthenticationResult r = verifier.authenticateFacialWithImageBuffers(
    imageQuery, imageTarget, options);

  // Explore the information obtained in SelphIDFacialAuthenticationResult like similarity
  float similarity = r.getSimilarity();

  // Return if images are matching
  return r.getFacialAuthenticationStatus() == FacialAuthenticationStatus.Positive;
}
```

#### 3.3.2. Autenticación facial mediante biometric templates

El método a utilizar es el siguiente:

```java
SelphIDFacialAuthenticationResult r = authenticateFacialWithRawTemplates(
  byte[] templateQuery,
  byte[] templateTarget,
  SelphIDVerifierOptions options
);
```

Los pasos necesarios para realizar una autenticación facial mediante dos biometric templates son los siguientes (método de ejemplo):

> **Pasos previos**
>
> * Obtenga la primera biometric template (cadena en base64) a través de la propiedad TemplateRaw utilizando el widget Selphi.
> * Obtenga la segunda biometric template (cadena en base64) a través de la propiedad TemplateRaw utilizando el widget Selphi.
> * Envíe ambas cadenas en base64 al servidor.

```java
boolean isMatch(String firstTemplateRawBase64, String secondTemplateRawBase64) {
  // Decode base64 to get the byte array corresponding to each image on the server.
  byte[] templateQuery = Base64.getDecoder().decode(
    firstTemplateRawBase64.getBytes());
  byte[] templateTarget = Base64.getDecoder().decode(
    secondTemplateRawBase64.getBytes());

  // Create the SelphIDVerifierOptions and configure it if needed.
  SelphIDVerifierOptions options = new SelphIDVerifierOptions();

  // Extraction
  // Check 3.1. section to initializate SelphIDVerifier.
  SelphIDFacialAuthenticationResult r = verifier.authenticateFacialWithRawTemplates(
    templateQuery, templateTarget, options);

  // Explore the information obtained in SelphIDFacialAuthenticationResult like similarity
  float similarity = r.getSimilarity();

  // Return if images are matching
  return r.getFacialAuthenticationStatus() == FacialAuthenticationStatus.Positive;
}
```

#### 3.3.3. Autenticación facial mediante una imagen y una biometric template

El método a utilizar es el siguiente:

```java
SelphIDFacialAuthenticationResult r = authenticateFacialWithImageRawTemplate(
  byte[] imageQuery,
  byte[] templateTarget,
  SelphIDVerifierOptions options
);
```

Los pasos necesarios para realizar una autenticación facial mediante una imagen y una biometric template son los siguientes (método de ejemplo):

> **Pasos previos**
>
> * Obtenga la imagen (cadena en base64) a través de la propiedad Image utilizando el widget Selphi.
> * Obtenga la biometric template (cadena en base64) a través de la propiedad TemplateRaw utilizando el widget Selphi.
> * Envíe ambas cadenas en base64 al servidor.

```java
boolean isMatch(String imageBase64, String templateRawBase64) {
  // Decode base64 to get the byte array corresponding to each image on the server.
  byte[] imageQuery = Base64.getDecoder().decode(
    imageBase64.getBytes());
  byte[] templateTarget = Base64.getDecoder().decode(
    templateRawBase64.getBytes());

  // Create the SelphIDVerifierOptions and configure it if needed.
  SelphIDVerifierOptions options = new SelphIDVerifierOptions();

  // Extraction
  // Check 3.1. section to initializate SelphIDVerifier.
  SelphIDFacialAuthenticationResult r = verifier.authenticateFacialWithImageRawTemplate(
    imageQuery, templateTarget, options);

  // Explore the information obtained in SelphIDFacialAuthenticationResult like similarity
  float similarity = r.getSimilarity();

  // Return if images are matching
  return r.getFacialAuthenticationStatus() == FacialAuthenticationStatus.Positive;
}
```

#### 3.3.4. Autenticación facial mediante la fotografía del documento y una imagen

El método a utilizar es el siguiente:

```java
SelphIDFacialAuthenticationResult r = authenticateFacialWithRawDocumentImage(
  byte[] rawDocument,
  byte[] imageTarget,
  SelphIDVerifierOptions options
);
```

Los pasos necesarios para realizar una autenticación facial mediante la fotografía del documento y una imagen son los siguientes (método de ejemplo):

> **Pasos previos**
>
> * Obtenga el token de la fotografía del documento (cadena en base64) a través de la propiedad TokenFaceImage utilizando el widget SelphID.
> * Obtenga la imagen (cadena en base64) a través de la propiedad Image utilizando el widget Selphi.
> * Envíe ambas cadenas en base64 al servidor.

```java
boolean isMatch(String tokenFaceImageBase64, String imageBase64) {
  // Decode base64 to get the byte array corresponding to each image on the server.
  byte[] rawDocument = Base64.getDecoder().decode(
    firstImageBase64.getBytes());
  byte[] imageTarget = Base64.getDecoder().decode(
    secondImageBase64.getBytes());

  // Create the SelphIDVerifierOptions and configure it if needed.
  SelphIDVerifierOptions options = new SelphIDVerifierOptions();

  // Extraction
  // Check 3.1. section to initializate SelphIDVerifier.
  SelphIDFacialAuthenticationResult r = verifier.authenticateFacialWithRawDocumentImage(
    rawDocument, imageTarget, options);

  // Explore the information obtained in SelphIDFacialAuthenticationResult like similarity
  float similarity = r.getSimilarity();

  // Return if images are matching
  return r.getFacialAuthenticationStatus() == FacialAuthenticationStatus.Positive;
}
```

#### 3.3.5. Autenticación facial mediante la fotografía del documento y una biometric template

El método a utilizar es el siguiente:

```java
SelphIDFacialAuthenticationResult r = authenticateFacialWithRawDocumentRawTemplate(
  byte[] rawDocument,
  byte[] templateTarget,
  SelphIDVerifierOptions options
);
```

* Los pasos necesarios para realizar la autenticación facial mediante la fotografía del documento y la biometric template del usuario son los siguientes (método de ejemplo):

> **Pasos previos**
>
> * Obtenga el token de la fotografía del documento (cadena en base64) a través de la propiedad TokenFaceImage utilizando el widget SelphID.
> * Obtenga la biometric template (cadena en base64) a través de la propiedad TemplateRaw utilizando el widget Selphi.
> * Envíe ambas cadenas en base64 al servidor.

```java
boolean isMatch(String rawDocumentBase64, String templateTargetBase64) {
  // Decode base64 to get the byte array corresponding to each image on the server.
  byte[] rawDocument = Base64.getDecoder().decode(
    rawDocumentBase64.getBytes());
  byte[] templateTarget = Base64.getDecoder().decode(
    templateTargetBase64.getBytes());

  // Create the SelphIDVerifierOptions and configure it if needed.
  SelphIDVerifierOptions options = new SelphIDVerifierOptions();

  // Extraction
  // Check 3.1. section to initializate SelphIDVerifier.
  SelphIDFacialAuthenticationResult r = verifier.authenticateFacialWithRawDocumentRawTemplate(
    rawDocument, templateTarget, options);

  // Explore the information obtained in SelphIDFacialAuthenticationResult like similarity
  float similarity = r.getSimilarity();

  // Return if images are matching
  return r.getFacialAuthenticationStatus() == FacialAuthenticationStatus.Positive;
}
```

## 3.4. Método de extracción de datos del documento

Para obtener los datos del documento necesarios en los procesos de onboarding digital, el integrador dispone de un método en la clase `SelphIDVerifier`.

> **Nota**
>
> El resultado de este método será un objeto `SelphIDDocumentResult` que contiene todos los datos detectados en el documento. Para más información, consulte la sección [3.9.3. SelphIDDocumentResult](#393-selphiddocumentresult).

#### 3.4.1. Obtención de los datos detectados en un documento

El método a utilizar es el siguiente:

```java
SelphIDDocumentResult extractDocumentWithRawDocument(
  byte[] rawDocumentBuffer,
  SelphIDVerifierOptions selphIDVerifierOptions
);
```

Los pasos necesarios para obtener los datos de un documento son los siguientes (método de ejemplo):

> **Pasos previos**
>
> * Obtenga el valor de la propiedad `TokenOCR` (cadena en base64) utilizando el widget SelphID.
> * Envíe la cadena en base64 al servidor.

```java
void printDocumentData(String tokenOCRBase64) {
  // Decode base64 to obtain the byte array corresponding to the token on the server.
  byte[] rawDocumentBuffer = Base64.getDecoder().decode(
    tokenOCRBase64.getBytes());

  // Create the SelphIDVerifierOptions and configure it if needed.
  SelphIDVerifierOptions options = new SelphIDVerifierOptions();

  // Extraction
  // Check 3.1. section to initializate SelphIDVerifier.
  SelphIDDocumentResult r = verifier.extractDocumentWithRawDocument(
    rawDocumentBuffer, options);

  // Explore the information obtained in SelphIDDocumentResult.

  // Get document keys.
  String[] keys = r.listDocumentKeys();

  // Print document data.
  for(int x=0; x<keys.length; x++) {
    System.out.println(
      keys[x] + ": " + getDocumentValue(keys[x]);
    );
  }
}
```

## 3.5. Métodos de evaluación de vida

Para evaluar la vida del usuario en el servidor, funcionalidad necesaria en el proceso de onboarding digital para evitar el fraude mediante foto o vídeo, el integrador dispone de un método para este fin en la clase `SelphIDVerifier`.

> **Nota**
>
> El resultado de estos métodos será siempre un objeto `SelphIDFacialLivenessResult`, explicado en [3.9.4. SelphIDFacialAuthenticationResult](#394-selphidfaciallivenessresult).

#### 3.5.1. Evaluación de vida a partir de una imagen

```java
SelphIDFacialLivenessResult r = evaluatePassiveLivenesWithImageBuffer(
  byte[] imageBuffer
);
```

Los pasos necesarios para realizar una autenticación facial mediante dos imágenes son los siguientes (método de ejemplo):

> **Pasos previos**
>
> * Obtenga una imagen del usuario (cadena en base64) utilizando el widget Selphi.
> * Envíe la cadena en base64 de la imagen al servidor.

```java
boolean isAlive(String imageBase64) {
  // Decode the base64 image to get the byte array.
  byte[] imageBuffer = Base64.getDecoder().decode(
    imageBase64.getBytes());

  // Evaluate
  // Check 3.1. section to initializate SelphIDVerifier.
  SelphIDFacialLivenessResult r = verifier.evaluatePassiveLivenesWithImageBuffer(
    imageBuffer);

  // Return if is alive
  return r.getFacialLivenessDiagnostic == FacialLivenessDiagnostic.Live;
}
```

#### 3.5.2. Evaluación de vida a partir de una imagen tokenizada

> A partir de la versión `6.21.0`, la imagen tokenizada incorpora un mecanismo de defensa contra ataques de inyección. Si se detecta un token no válido, se devolverá `NoneBecauseTokenDataError` o `NoneBecauseTokenSecurity` como diagnóstico.

```java
SelphIDFacialLivenessResult r = evaluatePassiveLivenessWithTokenBuffer(
  byte[] tokenBuffer
);
```

Los pasos necesarios para realizar una autenticación facial mediante dos imágenes son los siguientes (método de ejemplo):

> **Pasos previos**
>
> * Obtenga una imagen del usuario (cadena en base64) utilizando el widget Selphi.
> * Envíe la cadena en base64 de la imagen al servidor.

```java
boolean isAlive(String imageBase64) {
  // Decode the base64 image to get the byte array.
  byte[] tokenBuffer = Base64.getDecoder().decode(
    imageBase64.getBytes());

  // Evaluate
  // Check 3.1. section to initializate SelphIDVerifier.
  SelphIDFacialLivenessResult r = verifier.evaluatePassiveLivenessWithTokenBuffer(
    tokenBuffer);

  // Return if is alive
  return r.getFacialLivenessDiagnostic == FacialLivenessDiagnostic.Live;
}
```

## 3.6. Métodos de identificación 1:N

Para realizar búsquedas 1:N que permitan identificar un determinado patrón biométrico frente a una base de datos y obtener así un conjunto de candidatos con un mayor porcentaje de similitud, el integrador dispone de diferentes métodos en la clase `SelphIDIdentifier`.

```java
public class SelphIDIdentifier {
  // True if gallery has been created correctly.
  boolean createGallery(String galleryID) {}

  // True if gallery has been created correctly.
  boolean createGalleryWithPath(String galleryID, String galleryFilePath) {}

  // True if gallery has been removed correctly.
  boolean clearGallery(String galleryID) {}

  // Get all galleries for identification.
  String[] getAllGalleries() {}

  // True if each gallery have been removed correctly.
  boolean clearAllGalleries() {}

  // Feed a gallery with a new template using SelphIDFacialExtractionResult
  int enrollWithExtractionResult(String galleryID, String templateID, SelphIDFacialExtractionResult extractionResult) {}

  // Feed a gallery with a new template using byte[] template
  int enrollWithFacialTemplate(String galleryID, String templateID, byte[] facialTemplateBuffer) {}

  // Check if a person exists in the gallery via SelphIDFacialExtractionResult.
  SelphIDIdentifierResult identifyWithExtractionResult(String galleryID, SelphIDFacialExtractionResult extractionResult, SelphIDIdentifierOptions identifierOptions) {}

  // Check if a person exists in the gallery via byte[] template.
  SelphIDIdentifierResult identifyWithFacialTemplate(String galleryID, byte[] facialTemplateBuffer, SelphIDIdentifierOptions identifierOptions) {}

  SelphIDFacialGalleryInfo getGalleryInfo(String galleryID) {}

  boolean removeWithGalleryIndex(String galleryID, int templateIndex) {}

  boolean removeWithTemplateID(String galleryID, String templateID) {}
}
```

#### 3.6.1. Construcción de la galería de búsqueda

Como paso previo para realizar operaciones de identificación, debe crearse una galería y registrar en ella el conjunto de patrones biométricos sobre los que se realizará la búsqueda. Para incorporar plantillas a la galería puede utilizar los siguientes métodos:

```java
public class SelphIDIdentifier {
  int enrollWithExtractionResult(
    String galleryID,
    String templateID,
    SelphIDFacialExtractionResult extractionResult
  ) {}

  int enrollWithFacialTemplate(
    String galleryID,
    String templateID,
    byte[] facialTemplateBuffer
  ) {}
}
```

En ambos métodos se especificará el identificador de la galería a la que se debe añadir la plantilla, así como un identificador lógico referido a la lógica de negocio de la aplicación, de forma que los candidatos obtenidos como resultado de una búsqueda en la galería puedan vincularse a él.

```java
// 1. Create the gallery.
String galleryID = "my-new-id-or-uuid-1";
createGallery(galleryID);

// 2. Generate the facial templates from the images if you do not have them.
byte[] image1 = ...;
byte[] image2 = ...;
SelphIDVerifierOptions options = new SelphIDVerifierOptions();

SelphIDFacialExtractionResult extractionResult1 = extractFacialWithImageBuffer(
  image1, options);

SelphIDFacialExtractionResult extractionResult2 = extractFacialWithImageBuffer(
  image2, options);

// 3. The obtained facial templates will be added to the gallery by using any of the following methods of the `SelphIDIdentifier` class (you need to initializate it).

//    3.1. Create / Generate the template ID that will have in gallery
String templateID1 = "my-new-id-or-uuid-2";
String templateID2 = "my-new-id-or-uuid-3";

//    3.2. Insert the templates into the gallery with enrollWithExtractionResult
identifier.enrollWithExtractionResult(galleryID, templateID1, extractionResult1);

//    3.3. Insert the templates into the gallery with enrollWithFacialTemplate
byte[] facialTemplateBuffer = extractionResult2.getFacialTemplate();

identifier.enrollWithFacialTemplate(galleryID, templateID2, facialTemplateBuffer);
```

> **Nota**
>
> Para registrar una biometric template en una galería, será necesario generar el patrón facial equivalente o FacialTemplate mediante cualquiera de los siguientes métodos de la clase `SelphIDVerifier`:
>
> * `ExtractFacialWithRawTemplate`
> * `ExtractFacialWithImageBuffer`
>
> Consulte la sección [3.2.1. Extracción facial mediante una imagen](#321-extracción-facial-mediante-una-imagen).

#### 3.6.2. Identificación de una plantilla frente a una galería de búsqueda

El proceso de búsqueda se realizará mediante cualquiera de los dos métodos siguientes de la clase `SelphIDIdentifier`:

```java
public class SelphIDIdentifier {
  SelphIDIdentifierResult identifyWithExtractionResult(
    String galleryID,
    SelphIDFacialExtractionResult extractionResult,
    SelphIDIdentifierOptions identifierOptions
  ) {}

  SelphIDIdentifierResult identifyWithFacialTemplate(
    String galleryID,
    byte[] facialTemplateBuffer,
    SelphIDIdentifierOptions identifierOptions
  ) {}
}
```

Se especificará el identificador de la galería y un objeto `SelphIDIdentifierOptions` con las siguientes opciones de búsqueda:

* `MaxIdentificationCandidates`, para indicar el número máximo de candidatos devueltos, ordenados de mayor a menor porcentaje de similitud.
* `MinIdentificationSimilarity`, para indicar el umbral mínimo de similitud en la comparación para que un candidato se incluya en el conjunto de resultados.

> **Nota**
>
> Por defecto, `MaxIdentificationCandidates` será `20` y `MinIdentificationSimilarity` será `0f`.

A continuación veremos un ejemplo con ambos métodos:

```java
// 1. For an existing gallery we only need its ID and the image to search for that person in the gallery.
String galleryID = "galleryID";
byte[] imageToSearch = ...;
SelphIDIdentifierOptions identifierOptions = new SelphIDIdentifierOptions();

// 2. Configure the SelphIDIdentifierOptions
identifierOptions.setMaxIdentificationCandidates(5);
identifierOptions.setMinIdentificationSimilarity(0.6f);

// 3. Extract the facial template
SelphIDVerifierOptions verifierOptions = new SelphIDVerifierOptions();

SelphIDFacialExtractionResult extractionResult = identifier.extractFacialWithImageBuffer(
  imageToSearch, verifierOptions);

// 4. Search it with the identifyWithExtractionResult or identifyWithFacialTemplate if you alredy have the facial template.
SelphIDIdentifierResult result = identifier.identifyWithExtractionResult(
  galleryID, extractionResult, identifierOptions);

byte[] facialTemplateBuffer = extractionResult.getFacialTemplate();
SelphIDIdentifierResult result = identifyWithFacialTemplate(
  galleryID, facialTemplateBuffer, identifierOptions);

// 5. View the results. We obtain an array with all possible coincidence, so if for example we want to get the first coincidence:
if (result.size() > 0) {
  FacialAuthenticationStatus authenticate = identifierResult.getFacialAuthenticationStatus(0);
  float similarity = result.getSimilarity(0);
  String templateId = result.getTemplateID(0);
}
```

> **Nota**
>
> Para saber más sobre `SelphIDIdentifierResult`, consulte la sección [3.9.5. SelphIDIdentifierResult](#395-selphididentifierresult).

#### 3.6.3. Eliminar una plantilla de la galería

El proceso de eliminación consiste en bloquear una biometric template de una galería específica para que no se tenga en cuenta en los procesos de identificación. Si utilizamos la variable de entorno `FACEPHI_SELPHID_GALLERY_REMOVE_METHOD=noerase`, esta eliminación no reduce el tamaño de la galería ni el indexado de las biometric templates asociadas. Por el contrario, omitir esta variable o utilizar `FACEPHI_SELPHID_GALLERY_REMOVE_METHOD=erase` reducirá el tamaño de la galería tras la eliminación, alterando el indexado de las plantillas.

```java
public class SelphIDIdentifier {
  boolean removeWithGalleryIndex(
    String galleryID,
    int templateIndex
  ) {}

  boolean removeWithTemplateID(
    String galleryID,
    String templateID
  ) {}

}
```

El proceso de eliminación se realiza con el siguiente método de la clase `SelphIDIdentifier`:

```java
// For a example we are going to remove an specific user.
String galleryID = "galleryID";
byte[] facialTemplateBuffer = ...;
SelphIDIdentifierOptions identifierOptions = new SelphIDIdentifierOptions();
identifierOptions.setMaxIdentificationCandidates(1);
identifierOptions.setMinIdentificationSimilarity(0.5f);

// Search the coincidence template in gallery.
SelphIDIdentifierResult identifierResult = identifier.identifyWithFacialTemplate(
  galleryID, facialTemplateBuffer, identifierOptions);

// If coincidence have been found and it is matching, it will be removed.
if (result.size() > 0 &&
  identifierResult.getFacialAuthenticationStatus(0) == FacialAuthenticationStatus.Positive) {
  // Get the index of the template
  int templateIndex = identifierResult.getGalleryIndex(0);

  boolean removed = removeWithGalleryIndex(galleryID, templateIndex);

  if (removed) {
    System.out.println("Template correctly removed.");
  }
}
```

#### 3.6.4. Consultar y eliminar plantillas obsoletas

A partir de la versión `6.17.0`, cada patrón biométrico almacena la marca de tiempo (reloj del sistema) en la que fue indexado en la galería. Esto permite consultar y eliminar plantillas "caducadas" según criterios específicos.

```java
public class SelphIDIdentifier {
  String[] listObsoleteGalleryTemplateIDs(
    String galleryID,
    int intervalSeconds
  ) {}

  String[] removeObsoleteGalleryTemplateIDs(
    String galleryID,
    int intervalSeconds
  ) {}
}
```

En ambos casos, se listarán los ID de plantilla cuyas marcas de tiempo sean anteriores al intervalo indicado (en segundos). En el caso de `removeObsoleteGalleryTemplateIDs()`, la operación será atómica y eliminará todos los patrones obsoletos en una única operación. Si se ha configurado `FACEPHI_SELPHID_GALLERY_REMOVE_METHOD=erase`, se reducirá el tamaño de la galería y se reindexarán los patrones restantes.

```java
// For a example we are going to remove an specific user.
String galleryID = "galleryID";

// Remove all biometric patterns older than a day
String [] obsoleteIDs = removeObsoleteGalleryTemplateIDs(galleryID, 24 * 3600);

if (obsoleteIDs.length > 0) {
  System.out.println("Biometric patterns removed from gallery.");
  for (int i = 0; i < obsoleteIDs.length; ++i)
    System.out.println(obsoleteIDs[i]);
}
```

#### 3.6.5. Consultar información de una galería

El objetivo del proceso de consulta de una galería es servir de paso previo para poder realizar otras consultas sobre ella.

El proceso se realizará con la siguiente clase de `SelphIDIdentifier`:

```java
public class SelphIDIdentifier {
  SelphIDFacialGalleryInfo getGalleryInfo(
    String galleryID
  ) {}
}
```

Debe utilizarse un identificador de galería para consultar la galería específica. A continuación veremos en qué consiste el objeto `SelphIDFacialGalleryInfo`:

```java
public class SelphIDFacialGalleryInfo {
  // Gets if gallery is valid.
  boolean getValidGallery();

  // Gets gallery ID.
  String getGalleryID();

  // Gets gallery size.
  int getGallerySize();

  // Obtain a template with the index.
  String getTemplateID(int index);

  // Obtain all indices from a gallery that matches a exact value.
  int[] getIndicesWithTemplateID(String templateID);
}
```

#### 3.6.6. Consultar los índices que coinciden con un `templateID` específico

El proceso de consulta de todos los índices de una galería que coinciden con un valor exacto de `templateID` debe realizarse con el siguiente método de `SelphIDFacialGalleryInfo` que hemos visto en la [sección anterior](#365-consultar-información-de-una-galería):

> **Importante**
>
> A partir de SelphID `6.15.0`, **no se permiten elementos con templateID duplicado**.

```java
public class SelphIDFacialGalleryInfo {
  int[] getIndicesWithTemplateID(
    String templateID
  );
}
```

Debe especificarse un `templateID` que coincida con el `templateID` que se busca en la galería.

Para ello, es necesario disponer de una instancia de `SelphIDFacialGalleryInfo` con datos válidos:

```java
String galleryID = "galleryID";
String templateID = "templateID";

SelphIDFacialGalleryInfo galleryInfo = identifier.getGalleryInfo(galleryID);

int[] indicesTemplateID = galleryInfo.getIndicesWithTemplateID(templateID);
```

## 3.7. Orquestador

El orquestador permite obtener, en la misma llamada, la autenticación facial y la prueba de vida de la persona. Podemos optar por realizar la prueba con una imagen y una plantilla, o con dos plantillas.

> **Importante**
>
> La prueba de vida solo se realizará tras una autenticación exitosa.

```java
SelphIDVerifierResult r = verifySelphIDWithImageRawTemplate(
  byte[] imageBuffer,
  byte[] templateTarget,
  SelphIDVerifierOptions options
);

SelphIDVerifierResult r = verifySelphIDWithRawTemplates(
  byte[] templateQuery,
  byte[] templateTarget,
  SelphIDVerifierOptions options
);
```

> **Nota**
>
> Para más información sobre `SelphIDVerifierResult`, consulte la sección [3.9.6. SelphIDVerifierResult](#396-selphidverifierresult).

## 3.8. API Tracking

A partir de la versión 4.1.0, SelphID-SDK incorpora la funcionalidad de seguimiento de eventos (event tracking) que permite monitorizar y visualizar la actividad de la API a través de una interfaz web. La licencia de SelphID incluirá todos los datos necesarios para acceder a la plataforma (en la versión single-tenant).

Todos los métodos anteriores de otras versiones de la API siguen vigentes. Se han añadido algunos métodos duplicados que ahora reciben un nuevo parámetro en el que se encuentran datos tokenizados con la información esencial para comunicarse con el servidor de tracking. Este parámetro se denomina `extraData`.

### 3.8.1. Versión Multi-tenant

A partir de la versión 4.3.0, SelphID-SDK permite dos modos de funcionamiento respecto al registro de eventos mediante API-Tracking:

* **Single-tenant**: Los datos de conexión al servicio de API Tracking están cifrados dentro de la licencia de SelphID-SDK y se utilizarán en todas las llamadas al servicio.
* **Multi-tenant**: Los datos de conexión se recibirán en cada llamada a través de la aplicación móvil. Esto permitirá que el SDK registre eventos en diferentes servidores en función del cliente que realiza la llamada.

> **Importante**
>
> Para habilitar el modo multi-tenant, los datos de tracking no deben incluirse en la licencia de SelphID-SDK. De lo contrario, se activará el modo single-tenant al iniciar el backend.

A partir de la versión 5.0.0, es posible alternar entre los modos Single-tenant y Multi-tenant en tiempo de ejecución, utilizando estos métodos de `SelphIDVerifier`:

```java
void setMultitenantMode(boolean multiTenant);

boolean isMultitenantEnabled();
```

### 3.8.2. Registro

Con el siguiente método se permite el descifrado de los datos tokenizados en `rawDocumentBuffer`, tales como: OCR, imágenes del documento, etc. En el parámetro `extraData` deben enviarse los datos necesarios para el servicio de tracking.

```java
SelphIDDocumentResult r = extractDocumentWithRawDocument(
  byte[] rawDocumentBuffer,
  byte[] extraData,
  SelphIDVerifierOptions options
);
```

Los siguientes métodos reciben una imagen cifrada `rawTemplateBufferTarget` o una imagen sin cifrar `imageBufferTarget`, para compararla con la imagen extraída del documento `rawDocumentBufferQuery`. En ambos casos, los datos necesarios para el servicio de tracking deben enviarse en el parámetro `extraData`.

```java
SelphIDFacialAuthenticationResult r = authenticateFacialWithRawDocumentRawTemplate(
  byte[] rawDocumentBufferQuery,
  byte[] rawTemplateBufferTarget,
  byte[] extraData,
  SelphIDVerifierOptions options
);

SelphIDFacialAuthenticationResult r = authenticateFacialWithRawDocumentImage(
  byte[] rawDocumentBufferQuery,
  byte[] imageBufferTarget,
  byte[] extraData,
  SelphIDVerifierOptions options
);
```

### 3.8.3. SelphIDVerifierOptions

Los siguientes métodos, añadidos a la clase `SelphIDVerifierOptions`, permiten que la información insertada por el cliente se represente en los servidores de tracking, en el caso de uso de registro.

```java
public class SelphIDVerifierOptions {
  void setElapsedTimeAllowed(int elapsedTimeAllowed);
  void setFutureTimeAllowed(int futureTimeAllowed);
  void setFacialDetectionType(FacialDetectionType facialDetectionType);
  void setMinFaceAbs(int minFaceAbs);
  void setMinFaceRel(float minFaceRel);
  void setFalseDetectRate(float rate);
  void setMinIODThreshold(int minIODThreshold);
  void setMaxPoseThreshold(int maxPoseThreshold);
  void setMinimumFacialQuality(int minimumFacialQuality);
  void setAnalyticsDetection(boolean analyticsDetection);
  void setFacialTemplateRawExtraction(boolean facialTemplateRawExtraction);
  void setOptionalDataClientInformation(String json);
  void setCustomFacialAuthenticationThreshold(int customFacialAuthenticationThreshold);
  void setLivenessDepth(LivenessDepth livenessDepth);
}
```

El parámetro de entrada del método `setOptionalDataClientInformation` debe ser un JSON bien formado que aceptará las siguientes claves:

```json
{
  "address": "String",
  "birthDate": "String",
  "birthPlace": "String",
  "city": "String",
  "documentNumber": "String",
  "name": "String",
  "nationality": "String",
  "surname": "String"
}
```

> **Nota**
>
> Cualquier otra clave será ignorada. En el futuro se dará soporte a más claves.

A partir de la versión `6.17.0`, se añadió la propiedad `futureTimeAllowed`. Esto permite establecer un intervalo de tiempo (en segundos) durante el cual se aceptarán plantillas e imágenes tokenizadas con una fecha futura, devolviendo `true` en el método `getValidTimeStamp()`. Esto tiene como objetivo mitigar las diferencias de zona horaria entre dispositivos. Este valor puede configurarse globalmente mediante la variable de entorno `FACEPHI_SELPHID_FUTURE_TIME_ALLOWED=3600`.

A partir de la versión `6.18.0`, podemos especificar qué pipelines de Liveness queremos ejecutar para cada operación mediante `setLivenessDepth()`. En el caso de `None` (valor por defecto), se aplicará la configuración global establecida por `FACEPHI_SELPHID_FACIALLIVENESS_DEPTH`.

### 3.8.4. Autenticación

Los siguientes métodos están disponibles para realizar la autenticación. Los parámetros `rawTemplateBuffer` reciben la imagen cifrada, y el parámetro `imagebufferQuery` recibe la imagen sin cifrar. En ambos casos, los datos necesarios para el servicio de tracking deben enviarse en el parámetro `extraData`.

```java
SelphIDFacialAuthenticationResult r = authenticateFacialWithRawTemplates(
  byte[] rawTemplateBufferQuery,
  byte[] rawTemplateBufferTarget,
  byte[] extraData,
  SelphIDVerifierOptions options
);

SelphIDFacialAuthenticationResult r = authenticateFacialWithImageRawTemplate(
  byte[] imageBufferQuery,
  byte[] rawTemplateBufferTarget,
  byte[] extraData,
  SelphIDVerifierOptions options
);
```

### 3.8.5. Passive liveness

Los siguientes métodos están disponibles para realizar la prueba de vida pasiva. El parámetro `tokenBuffer` recibe la imagen cifrada e `imageBuffer` la imagen sin cifrar. En ambos casos, los datos necesarios para el servicio de tracking deben enviarse en el parámetro `extraData`.

```java
SelphIDFacialLivenessResult r = evaluatePassiveLivenessWithTokenBuffer(
  byte[] tokenBuffer,
  byte[] extraData
);

SelphIDFacialLivenessResult r = evaluatePassiveLivenesWithImageBuffer(
  byte[] imageBuffer,
  byte[] extraData
);
```

### 3.8.6. Eventos personalizados

A partir de la versión 4.5.0, SelphID implementa la posibilidad de enviar eventos personalizados a la API de Tracking, no vinculados a ninguna operación interna del SDK. Todas las operaciones de eventos personalizados devuelven un código de estado y un mensaje, dentro de un objeto `SelphIDApiTrackingResult`.

El siguiente método permite enviar a la API de Tracking el evento de **Autenticación facial**, utilizando los parámetros `authStatus` y `similarity`. También podemos registrar en el servicio de API Tracking la(s) imagen(es) implicada(s) en la autenticación. Ambas imágenes son opcionales, aceptando buffers nulos o vacíos.

```java
SelphIDApiTrackingResult r = authenticateFacialTrackingEvent(
  TrackingFamily family,
  FacialAuthenticationStatus authStatus,
  float similarity,
  String source,
  byte[] imageBufferQuery,
  byte[] imageBufferTarget,
  byte[] extraData
);
```

Valores posibles de `TrackingFamily`:

```java
public enum TrackingFamily {
  OnBoarding,
  Authentication
}
```

El siguiente método permite enviar a la API de Tracking el evento de **Liveness**, utilizando los parámetros `diagnostic` y `similarity`. También podemos registrar en el servicio de API Tracking la imagen implicada en el proceso de vida, aunque es opcional, aceptando un buffer nulo o vacío.

```java
SelphIDApiTrackingResult r = evaluatePassiveLivenessTrackingEvent(
  TrackingFamily family,
  FacialLivenessDiagnostic diagnostic,
  String source,
  byte[] imageBuffer,
  byte[] extraData
);
```

El siguiente método permite enviar a la API de Tracking el evento de **Autenticación por voz**, utilizando el parámetro `probability`. También podemos registrar en el servicio de API Tracking las pistas de audio implicadas en el proceso de autenticación por voz. Ambos buffers son opcionales, aceptando valores nulos o vacíos.

```java
SelphIDApiTrackingResult r = voiceAuthenticationTrackingEvent(
  float probabiliy,
  String source,
  byte[] audioDataBufferQuery,
  byte[] audioDataBufferTarget,
  byte[] extraData
);
```

El siguiente método permite enviar un evento personalizado de OCR al servidor de API Tracking.

```java
SelphIDApiTrackingResult r =  ocrTrackingEvent(
  String ocrDataJson,
  String source,
  byte[] extraData
);
```

`ocrDataJson` es un diccionario clave-valor en formato JSON bien formado. Acepta cualquier tipo de nombre de clave con cualquier valor de cadena:

```json
{
  "OCR_Key1": "OCR_Value1",
  "OCR_Key2": "OCR_Value2",
  "OCR_Key3": "OCR_Value3",
  "OCR_Key4": "OCR_Value4",
  "OCR_Key5": "OCR_Value5"
}
```

El siguiente método permite enviar un evento personalizado SECURITY\_INFO\_DATA al servidor de API Tracking:

```java
  SelphIDApiTrackingResult r = securityInfoTrackingEvent(
  String securityDataJson,
  boolean succeed,
  String source,
  byte[] extraData
  );
```

`securityDataJson` son los datos de seguridad en formato JSON:

```json
{
  "Security_Key1": "Security_Value1",
  "Security_Key2": "Security_Value2",
  "Security_Key3": "Security_Value3",
  "Security_Key4": "Security_Value4",
  "Security_Key5": "Security_Value5"
}
```

`succeed` es un valor booleano que indica si la obtención de los datos de seguridad se ha realizado correctamente o no, y `source` es el nombre del servicio o del origen de los datos de seguridad.

Para todas las operaciones de eventos personalizados, podemos modificar el campo cifrado `eventSource` dentro del token `extraData`.

```java
byte[] extraData2 = setTrackingEventSource(
  String eventSource,
  byte[] extraData
);
```

Dentro de los eventos personalizados, se ofrece la posibilidad de **cerrar la operación** mediante el siguiente método:

```java
SelphIDApiTrackingResult r = finishTrackingEvent(
  TrackingFamily family,
  OperationResultStatus status,
  OperationResultReason reason,
  byte[] extraData
);
```

Este método registrará en el servicio de API Tracking los eventos de **Resultado de la operación** (Operation result) y **Finalización de cambio de paso** (Step change finish), que cierran la operación.

> **Importante**
>
> El significado de estos atributos, incluidos dichos enums, lo determinará el usuario.

Valores posibles de `OperationResultStatus`:

```java
public enum OperationResultStatus {
  Succeeded,

  // Denied.
  Denied,

  // Error.
  Error,

  // Cancelled.
  Cancelled
}
```

Valores posibles de `OperationResultReason`:

```java
public enum OperationResultReason {
  // We do not specify a concrete reason.
  None,

  // Some error using the SDK.
  InternalError,

  // The operation was canceled by the user.
  CancelledByUser,

  // The set timeout has expired.
  Timeout,

  // Document validation failed.
  DocumentValidationNotPassed,

  // Error during document validation.
  DocumentValidationError,

  // Authentication failed.
  AuthenticationNotPassed,

  // Error during authentication.
  AuthenticationError,

  // Liveness failed.
  LivenessNotPassed,

  // Error during liveness.
  LivenessError
}
```

### 3.8.7. Servidor proxy

Desde la versión 4.5.5 de SelphID-SDK, es posible enviar solicitudes a la API de Tracking a través de un servidor proxy. Para configurar los parámetros del proxy, utilice el siguiente método:

```java
setTrackingProxy(
        String proxyHost,
        int proxyPort,
        String proxyUser,
        String proxyPass);
```

Para deshabilitar el proxy, debe pasarse una cadena vacía como parámetro `proxyHost`.

## 3.9. Descripción de los resultados de la API

Las siguientes propiedades, en las clases de resultado, permiten evaluar los resultados de cada uno de los métodos mencionados anteriormente.

A partir de la versión `6.18.0`, además de verificar la validez de un token mediante `getValidTimeStamp()`, ahora podemos obtener la marca de tiempo incrustada en el propio token mediante `getTokenTimeStamp()`. Esto afecta a:

* `SelphIDFacialExtractionResult`.
* `SelphIDFacialAuthenticationResult`.
* `SelphIDDocumentResult`.
* `SelphIDFacialLivenessResult`.

### 3.9.1. SelphIDFacialExtractionResult

Presenta diferentes propiedades para evaluar el resultado de la extracción facial:

```java
public class SelphIDFacialExtractionResult {
  // Indicates whether the extraction was able to process successfully.
  boolean getExtractionOK() {}

  // Biometric pattern of the detected person.
  byte[] getFacialTemplate() {}

  // Value (0, 1) that indicates the degree of reliability of the extraction.
  float getFaceConfidence() {}

  // Location of landmark points detected in the image.
  Point getLeftEye() {}
  Point getRightEye() {}
  Point getChin() {}
  Point getNose() {}
  Point getLeftMouth() {}
  Point getRigthMouth() {}

  // Interocular distance.
  int getIOD() {}

  // Orientation of the face with respect to the camera. Possible values are as follows:
  FacialPose getFacialPose() {}

  // Face Orientation Angles.
  float getYaw() {}
  float getPitch() {}
  float getRoll() {}

  // Value (0, 1) that indicates the quality of the input image.
  float getImageQuality() {}

  // Indicates the quality of the detected face. Possible values are as follows:
  FacialQuality getFacialQuality() {}

  // Indicates if the person wears glasses. Possible values are as follows:
  FacialGlasses getGlasses() {}

  // Numerical value indicating the approximate age of the person.
  int getAge() {}

  // Gender of the person. Possible values are as follows:
  FacialGender getGender() {}

  // Value (0, 1) that indicating the probability that the person wears a mask.
  float getFacialMask() {}

  // Gets if the time stamp is valid.
  boolean getValidTimeStamp() {}

  // Gets the token time stamp.
  long getTokenTimeStamp() {}
}
```

Valores posibles de `FacialPose`:

```java
public enum FacialPose {
  // Unknown or not computed.
  None,

  // Looking straight ahead.
  Frontal,

  // Person looking to the right.
  RightAngled,

  // Person looking to the left.
  LeftAngled
}
```

Valores posibles de `FacialQuality`:

```java
public enum FacialQuality {
  None,
  Bad,
  Regular,
  Good
}
```

Valores posibles de `Glasses`:

```java
public enum Glasses {
  None,
  Eyes,
  Sun
}
```

Valores posibles de `Gender`:

```java
public enum Gender {
  None,
  Male,
  Female
}
```

### 3.9.2. SelphIDFacialAuthenticationResult

Presenta diferentes propiedades para evaluar el resultado de la autenticación biométrica:

```java
public class SelphIDFacialAuthenticationResult {
  // Results of a facial authentication process.
  FacialAuthenticationStatus getFacialAuthenticationStatus() {}

  // Similarity value between 0 and 1 representing the similarity between the faces of the two images.
  float getSimilarity() {}

  // Gets if the time stamp is valid.
  boolean getValidTimeStamp() {}

  // Gets the token time stamp.
  long getTokenTimeStamp() {}
}
```

> **Importante**
>
> Para evaluar el resultado debe utilizar la propiedad `FacialAuthenticationStatus`; el valor `similarity` solo se utiliza con fines estadísticos.

Valores posibles de `FacialAuthenticationStatus`:

```java
public enum FacialAuthenticationStatus {
  // Biometric authentication could not be performed.
  None,

  // Negative Authentication result.
  Negative,

  // DEPRECATED.
  Uncertain,

  // Positive Authentication result.
  Positive,

  // Biometric authentication could not be performed because the maximum allowed angle between faces of each image provided was exceeded.
  NoneBecausePoseExceeded,

  // Biometric authentication could not be performed because biometric feature extraction could not be performed on any of the images provided.
  NoneBecauseInvalidExtractions
}
```

### 3.9.3. SelphIDDocumentResult

Presenta diferentes métodos para recuperar las imágenes utilizadas en el proceso y los datos leídos del documento. Los métodos son los siguientes:

```java
public class SelphIDDocumentResult {
  // Obtains all the keys associated with each of the read data from the document.
  String[] listDocumentKeys() {}

  // Obtains a certain data read from the document by means of its associated key.
  String getDocumentValue(String key) {}

  // Obtains all the keys associated with each of the read images from the document.
  String[] listImageKeys() {}

  // Obtains a certain image of the document by means of its associated key.
  byte[] getImage(String key) {}

  // Gets the ExtraData key list.
  String[] listExtraDataKeys() {}

  // Gets the ExtraData value for the key provided.
  String getExtraDataValue(String key) {}

  // Gets if the time stamp is valid.
  boolean getValidTimeStamp() {}

  // Gets the token time stamp.
  long getTokenTimeStamp() {}
}
```

### 3.9.4. SelphIDFacialLivenessResult

Presenta la propiedad `FacialLivenessDiagnostic` para evaluar el resultado del diagnóstico de prueba de vida pasiva.

```java
public class SelphIDFacialLivenessResult {
  // Gets facial liveness diagnostic.
  FacialLivenessDiagnostic getFacialLivenessDiagnostic() {}

  // Added in 6.18.0
  // Gets additional information when facial liveness diagnostic is NoLive.
  SelphIDNoLiveDetails getNoLiveDetails() {}

  // Gets the valid timestamp
  boolean getValidTimeStamp() {}

  // Gets the token time stamp.
  long getTokenTimeStamp() {}
}
```

Valores posibles de `FacialLivenessDiagnostic`:

```java
public enum FacialLivenessDiagnostic {
  // Liveness Diagnostic could not be evaluated.
  None,

  // A fraud condition has been detected, a video or a photograph.
  // DEPRECATED > use "NoLive".
  Spoof,

  // DEPRECATED.
  Uncertain,

  // The subject passes the liveness diagnostic.
  Live,

  // Liveness could not be evaluated because of the low quality of the images used.
  NoneBecauseBadQuality,

  // Liveness could not be evaluated as the face is too close to the camera.
  NoneBecauseFaceTooClose,

  // Liveness could not be evaluated as no faces were detected in the images used.
  NoneBecauseFaceNotFound,

  // Liveness could not be evaluated as very small faces were detected in the images used.
  NoneBecauseFaceTooSmall,

  // Liveness could not be evaluated because the angle between faces was exceeded.
  NoneBecauseAngleTooLarge,

  // Liveness could not be evaluated because of the format of the images used.
  NoneBecauseImageDataError,

  // Liveness could not be evaluated due to an internal error.
  NoneBecauseInternalError,

  // Liveness could not be evaluated due to an error in the processing of the images used.
  NoneBecauseImagePreprocessError,

  // Liveness could not be evaluated because there are too many people at the scene.
  NoneBecauseTooManyFaces,

  // Liveness could not be evaluated as the face is too close to the image borders.
  NoneBecauseFaceTooCloseToBorder,

  // Liveness could not be evaluated as the image used is cropped.
  NoneBecauseFaceCropped,

  // The proof of life could not be evaluated due to a licensing error.
  NoneBecauseLicenseError,

  // Liveness could not be evaluated because the person's face is occluded.
  NoneBecauseFaceOccluded,

  // The image does not correspond to a real person.
  NoLive,

  // Liveness could not be evaluated because the person's eyes are closed.
  NoneBecauseEyesClosed,

  // Liveness could not be evaluated because the person's eyes are occluded.
  NoneBecauseEyesOccluded,

  // None due to token data error or malformed.
  NoneBecauseTokenDataError,

  // None due to token's internal security measures have been broken.
  NoneBecauseTokenSecurity
}
```

A partir de la versión 6.18.0, se incluye la estructura `SelphIDNoLiveDetails` con información adicional sobre el caso `NoLive`. En el caso `Live`, también podemos consultar las puntuaciones (scores) del pipeline.

```java
// SelphID details for FacialLivenessDiagnostic::NoLive case.
public class SelphIDNoLiveDetails {
  // High-level main cause of the NoLive diagnostic.
  NoLiveMainCause getNoLiveMainCause() {}

  // Status of the facial Presentation Attack Detection (fPAD).
  FPadStatus getFPadStatus() {}

  // Normalized fPAD score (0..1), if available.
  float getFPadScore() {}

  // Status of the facial Manipulation Attack Detection (fMAD).
  FMadStatus getFMadStatus() {}

  // Normalized fMAD score (0..1), if available.
  float getFMadScore() {}

  // Normalized coercion score (0..1), if available.
  float getCoercionScore() {}

  // Human-readable reason message, for logs/backoffice.
  String getReasonMessage() {}
}
```

### 3.9.5. SelphIDIdentifierResult

Presenta diferentes métodos para obtener la información de comparación de cada uno de los candidatos devueltos como resultado de una búsqueda 1:N. Son los siguientes:

```java
public class SelphIDIdentifierResult {
  // Gets the number of candidates obtained in the search.
  int size() {}

  // Gets similarity from result index.
  float getSimilarity(int index) {}

  // Gets gallery index from result index.
  int getGalleryIndex(int index) {}

  // Gets templateID from result index.
  String getTemplateID(int index) {}

  // Gets the status code from the comparison made between the search template and the indicated candidate.
  FacialAuthenticationStatus getFacialAuthenticationStatus(int index) {}

  // Obtains additional information in case the biometric comparison between the search template and the indicated candidate was positive.
  FacialAuthenticationDetail getFacialAuthenticationDetail(int index) {}
}
```

Valores posibles de `FacialAuthenticationStatus`:

```java
public enum FacialAuthenticationStatus {
  // The biometric comparison could not be performed.
  None,

  // The facial patterns do not match.
  Negative,

  // DEPRECATED.
  Uncertain,

  // Facial patterns do match.
  Positive,

  // The biometric comparison could not be performed because the face in some of the captures is located at a too high rotation angle with respect to the camera.
  NoneBecausePoseExceed,

  // The biometric comparison could not be performed because no face could be detected in any of the captures made.
  NoneBecauseInvalidExtractions
}
```

Valores posibles de `FacialAuthenticationDetail`:

```java
public enum FacialAuthenticationDetail {
  // The comparison was not successful.
  None,

  // The facial patterns do match with a low percentage of similarity.
  PositiveLowSecurityLevel,

  // The facial patterns do match with an average percentage of similarity.
  PositiveMediumSecurityLevel,

  // Facial patterns do match with a high percentage of similarity.,
  PositiveHighSecurityLevel
}
```

### 3.9.6. SelphIDVerifierResult

Presenta diferentes métodos para obtener información del orquestador. Son los siguientes:

```java
public class SelphIDVerifierResult {
  // Obtains information about the document.
  SelphIDDocumentResult getSelphIDDocumentResult() {}

  // Obtains information about the authentication process.
  SelphIDFacialAuthenticationResult GetSelphIDFacialAuthenticationResult() {}

  // Obtains information about the liveness process.
  SelphIDFacialLivenessResult GetSelphIDFacialLivenessResult() {}
}
```

> **Nota**
>
> Para más información:
>
> * [3.9.2. SelphIDFacialAuthenticationResult](#392-selphidfacialauthenticationresult)
> * [3.9.3. SelphIDDocumentResult](#393-selphiddocumentresult)
> * [3.9.4. SelphIDFacialLivenessResult](#394-selphidfaciallivenessresult)

### 3.9.7. SelphIDApiTrackingResult

Presenta diferentes métodos para obtener información de la operación de API Tracking. Son los siguientes:

```java
public class SelphIDApiTrackingResult {
  // Obtains the tracking request HTTP result.
  int GetTrackingStatus() {}

  // Obtains the tracking request message.
  String GetTrackingMessage() {}
}
```

## 3.10. Descripción de SelphIDException

Si se produce un error dentro de SelphID-SDK, se lanzará la excepción SelphIDException.

```java
public class SelphIDException extends Exception {
  // Get the type of exception that occurred.
  SelphIDExceptionType getExceptionType() {}
}
```

Valores posibles de `SelphIDExceptionType`:

```java
public enum SelphIDExceptionType {
  // Error in license content.
  ErrorLicenseContent,

  // License has been expired.
  ErrorLicenseExpired,

  // Error in license HostID.
  ErrorLicenseHostID,

  // Error in facial template.
  ErrorFacialTemplate,

  // Error loading library.
  // DEPRECATED.
  ErrorLoadingLibrary,

  // Error in license usage logging.
  ErrorLicenseUsageLogging,

  // Facial image with error or invalid.
  ErrorFacialImage,

  // Error in document data.
  ErrorDocumentData,

  // Error in network license.
  ErrorLicenseNetwork,

  // Error because network license connections have been exceeded.
  ErrorLicenseNetworkConnectionsExceeded,

  // Gallery size reached.
  ErrorLicenseGallerySizeReached,

  // Invalid options.
  ErrorInvalidOptions,

  // Error license is too old.
  ErrorLicenseTooOld,

  // Error because a feature is unavailable.
  ErrorUnavailableFeature,

  // Error because incompatible facial template.
  ErrorIncompatibleFacialTemplate,

  // Error when access to configuration file.
  ErrorConfigurationFileAccess,

  // Error when accessing to API Tracking data.
  ErrorTrackingFileAccess,

  // Error when loading API Tracking configuration file.
  // DEPRECATED.
  ErrorLoadingTrackingFile,

  // SelphID configuration variables are empty (config file or environment variables).
  ErrorConfigVarsEmpty,

  // `FACEPHI_SELPHID_INSTALL_PATH` key is empty.
  ErrorInstallPathEmpty,

  // `FACEPHI_SELPHID_FACIALLIVENESS_PATH_KEY` key is empty.
  ErrorLivenessDataPathEmpty,

  // Error when loading the facial authentication library.
  ErrorLoadingFacialLibrary,

  // Error when loading the liveness library.
  ErrorLoadingLivenessLibrary,

  // Internal error when execute the facial extraction.
  ErrorProcessingFacial,

  // Internal error when execute the liveness check.
  ErrorProcessingLiveness,

  // Error when accessing a gallery in disk.
  ErrorGalleryFile
}
```
