Pular para o conteúdo principal

Primeiros passos para integração - Rest PKI Core

Este artigo leva você do zero até uma primeira chamada bem-sucedida ao Rest PKI Core. Você vai:

  1. Obter as credenciais: o endpoint da instância e uma chave de API
  2. Configurar a biblioteca cliente da sua linguagem de programação ou chamar a API REST diretamente
  3. Fazer uma primeira chamada para verificar se está tudo pronto

Como a integração funciona​

A sua aplicação se comunica com o Rest PKI Core por uma API REST, autenticada por uma chave de API. As chamadas são sempre feitas pelo backend da aplicação: a chave de API dá acesso à sua organização e, por isso, nunca deve chegar a um navegador ou a um aplicativo móvel.

Quando uma operação depende do usuário, como escolher um certificado e assinar um documento ou tirar uma selfie para uma verificação biométrica, você não precisa construir essas páginas. O backend cria uma sessão, o Rest PKI Core retorna uma URL e o usuário é enviado a uma página hospedada pelo Rest PKI Core. Quando termina, o usuário volta à sua aplicação, que obtém os resultados pela API. Veja sessões de assinatura e sessões de biometria.

Obtenha as credenciais​

Você precisa de dois parâmetros:

ParâmetroDescrição
EndpointEndereço da instância do Rest PKI Core. Na instância SaaS, é https://core.pki.rest/. Numa instância própria, é o endereço do dashboard dela, como https://restpki.suaempresa.com.br/
Chave de APIChave que identifica a aplicação e autentica as chamadas dela. Tem o formato MyApp|0f3c…: um prefixo tirado do nome da aplicação, um | e 64 caracteres hexadecimais

Se você usa a instância SaaS e a sua empresa ainda não tem acesso a ela, entre em contato com o nosso suporte ao desenvolvedor. Se você usa uma instância on-premises própria e ainda não tem uma organização com a qual trabalhar, veja Criação de organização.

Crie uma chave de API​

As chaves de API pertencem a aplicações. Assim que conseguir entrar no dashboard, crie uma aplicação para o seu sistema e uma chave para ela:

  1. Entre no dashboard da instância
  2. No menu lateral, clique em Aplicações e depois em Adicionar
  3. Em Nova Aplicação, preencha um Nome para a aplicação. Se for pedida uma Organização, escolha aquela em que o seu sistema vai trabalhar
  4. Em Papéis, marque Operador (veja Escolhendo os papéis abaixo)
  5. Clique em Criar
  6. Na página da aplicação, clique em Chaves e depois em Adicionar
  7. Em Nova Chave de Aplicação, preencha uma Descrição (por exemplo, o ambiente que vai usar a chave) e escolha uma Expiração (veja Expiração da chave abaixo); depois clique em Criar
  8. Copie a chave exibida no diálogo Chave criada e guarde-a em um local seguro. Não será possível vê-la novamente: se você a perder, crie uma nova chave
Mantenha a chave de API em segredo

Quem tiver a chave pode agir sobre a sua organização com os papéis da aplicação dela. Guarde-a como guardaria uma senha: num cofre de segredos como o Azure Key Vault, numa variável de ambiente ou, durante o desenvolvimento, nos segredos do usuário (user secrets) do .NET. Nunca faça commit dela no controle de versão e nunca a envie a um navegador ou a um aplicativo móvel.

Escolhendo os papéis​

Os papéis de uma aplicação definem o que as chaves dela podem fazer. Dê à aplicação apenas os papéis de que ela precisa:

PapelO que permite
OperadorAs operações de uma integração: criar e usar sessões de assinatura, assinar documentos, inspecionar assinaturas, autenticar usuários com certificados, emitir carimbos de tempo, executar sessões de biometria, adicionar marcas e carimbos aos documentos e consultar transações. É o papel de que a maioria das integrações precisa
MonitorConsultar transações, sessões de biometria, cadastros em lote e faturas, sem executar nenhuma operação
GerenteTudo o que um Operador faz, além de gerenciar as configurações da organização e os contextos de segurança. Pode ver aplicações e usuários, mas não gerenciá-los
AdministradorTudo, inclusive gerenciar aplicações e usuários

Expiração da chave​

A Expiração de uma chave pode ser Em 1 ano, Em 2 anos ou Nunca expira. Quando uma chave expira, as chamadas feitas com ela passam a falhar com HTTP 401; por isso, se escolher uma chave que expira, planeje a substituição dela: uma aplicação pode ter mais de uma chave, o que permite criar a nova chave e passar o sistema a usá-la antes que a antiga expire.

Escolha como chamar a API​

As APIs do Rest PKI Core são REST simples com JSON, mas você não precisa lidar com HTTP diretamente. A Lacuna oferece bibliotecas cliente que encapsulam a API nas convenções de cada linguagem, junto com projetos de exemplo que as usam:

LinguagemPacoteCódigo-fonteExemplos
.NETLacuna.RestPkiCore.Client no NuGet—PkiSuiteSamples/dotnet
PHPlacuna/restpkicore-client no PackagistGitHubPkiSuiteSamples/php
Javacom.lacunasoftware.restpki:restpkicore-client no Maven CentralGitHubPkiSuiteSamples/java
Node.jsrestpki-core-client no npmGitHubPkiSuiteSamples/nodejs

Vá para a seção da sua linguagem:

Para qualquer outra linguagem, chame a API diretamente.

.NET​

Adicione ao seu projeto o pacote do NuGet Lacuna.RestPkiCore.Client:

dotnet add package Lacuna.RestPkiCore.Client

O pacote é compilado para o .NET Standard 2.0, então roda no .NET 5 ou posterior, no .NET Core 2.0 ou posterior e no .NET Framework 4.6.1 ou posterior (a Microsoft recomenda a 4.7.2 ou posterior para bibliotecas .NET Standard 2.0).

observação

O pacote se chama Lacuna.RestPkiCore.Client, mas as classes dele ficam no namespace Lacuna.RestPki.Client.

Aplicações ASP.NET Core​

Registre os serviços do Rest PKI Core no Program.cs, vinculando as opções deles à seção de configuração RestPki:

builder.Services.AddRestPki().Configure(builder.Configuration.GetSection("RestPki"));

Em seguida, adicione a seção ao appsettings.json, sem a chave de API:

{
"RestPki": {
"Endpoint": "https://core.pki.rest/"
}
}

Forneça a chave de API por uma fonte que fique fora do controle de versão. Durante o desenvolvimento, use os segredos do usuário:

dotnet user-secrets set "RestPki:ApiKey" "YOUR_API_KEY"

Em produção, defina a variável de ambiente RestPki__ApiKey ou use um cofre de segredos como o Azure Key Vault. O ASP.NET Core combina essas fontes na mesma seção RestPki.

Onde a aplicação precisar chamar o Rest PKI Core, peça um IRestPkiService por injeção de dependência:

using Lacuna.RestPki.Client;

public class SignatureController : Controller {

private readonly IRestPkiService restPkiService;

public SignatureController(IRestPkiService restPkiService) {
this.restPkiService = restPkiService;
}

...
}

O AddRestPki() também registra o IRestBioService, o serviço usado nas sessões de biometria.

dica

Se preferir definir as opções no código, passe-as ao AddRestPki(): builder.Services.AddRestPki(options => { options.Endpoint = ...; options.ApiKey = ...; });

Outras aplicações .NET​

Se a aplicação não usa a injeção de dependência do ASP.NET Core, como numa aplicação .NET Framework ou de console, obtenha um IRestPkiService da classe estática RestPkiServiceFactory:

using Lacuna.RestPki.Client;

var restPkiService = RestPkiServiceFactory.GetService(new RestPkiOptions() {
Endpoint = ConfigurationManager.AppSettings["RestPkiEndpoint"],
ApiKey = ConfigurationManager.AppSettings["RestPkiApiKey"],
});

Neste exemplo, os parâmetros vêm da seção appSettings do arquivo web.config ou app.config, mas podem vir de onde você preferir. Para sessões de biometria, use RestPkiServiceFactory.GetBioService(), que recebe os mesmos parâmetros.

Cada chamada à RestPkiServiceFactory cria um novo cliente HTTP; por isso, crie o serviço uma vez e reutilize-o, por exemplo num campo estático, em vez de criar um a cada requisição.

Opções​

O RestPkiOptions tem as propriedades a seguir, que também podem ser definidas na seção de configuração RestPki:

PropriedadeDescrição
EndpointEndereço da instância do Rest PKI Core. Se o endereço tiver um caminho, termine-o com uma barra (https://suaempresa.com.br/restpki/); caso contrário, o último segmento do caminho é descartado
ApiKeyA chave de API da aplicação
CultureNameCultura das respostas da API, como en-US, pt-BR ou es-ES (veja Cultura abaixo). Também disponível como Culture, do tipo CultureInfo
TimeoutSecondsQuanto tempo esperar por cada resposta, em segundos. Se não for definido, o cliente espera 60 segundos. Também disponível como Timeout, do tipo TimeSpan

Cultura​

O cliente informa ao Rest PKI Core qual cultura usar em cada chamada e, por padrão, usa a cultura da thread atual (Thread.CurrentThread.CurrentUICulture). Isso funciona bem quando a aplicação define a cultura de cada requisição, como o ASP.NET Core faz com a localização de requisições (request localization).

Para usar sempre a mesma cultura, independentemente da thread, defina CultureName. No ASP.NET Core, adicione a propriedade à seção de configuração:

{
"RestPki": {
"Endpoint": "https://core.pki.rest/",
"CultureName": "en-US"
}
}

Nos demais casos, defina-a no RestPkiOptions:

var restPkiService = RestPkiServiceFactory.GetService(new RestPkiOptions() {
...,
CultureName = "en-US",
});

Erros​

Os métodos do IRestPkiService podem lançar as seguintes exceções:

ExceçãoQuando
RestPkiExceptionV2A API rejeitou a requisição (HTTP 422). Compare a propriedade ErrorCode, do tipo ErrorCodesV2, com os códigos de erro. A propriedade ErrorMessage descreve o erro em inglês e serve para os seus logs, não para os seus usuários
ValidationExceptionUm certificado ou uma assinatura não passou na validação. A propriedade ValidationResults indica o que falhou
RestForbiddenOperationExceptionA aplicação não tem um papel que permita a operação (HTTP 403, veja Escolhendo os papéis)
RestErrorExceptionQualquer outro erro HTTP, como 401 por uma chave de API ausente ou inválida. A propriedade StatusCode tem o código de status HTTP (veja Códigos de status HTTP)
RestUnreachableExceptionNão foi possível acessar o endpoint: verifique o endereço do endpoint e a sua rede
TimeoutExceptionA resposta demorou mais que TimeoutSeconds

RestPkiExceptionV2 e ValidationException ficam no namespace Lacuna.RestPki.Client, e as demais classes Rest…Exception, no namespace Lacuna.RestClient. Todas derivam de Lacuna.RestClient.RestException; para tratar qualquer erro da API num único lugar, capture RestException (e TimeoutException, que é uma exceção padrão do .NET).

PHP​

Adicione ao seu projeto o pacote do Composer lacuna/restpkicore-client (se ainda não tem o Composer, obtenha-o aqui):

composer require lacuna/restpkicore-client

O pacote requer o PHP 5.5 ou posterior e usa o Guzzle 6 ou 7 para fazer as chamadas HTTP. Ele é de código aberto, hospedado no GitHub: fique à vontade para fazer um fork se precisar personalizá-lo.

Crie um RestPkiService, que implementa RestPkiServiceInterface, passando a ele um RestPkiCoreClient construído com o endpoint e a chave de API:

use Lacuna\RestPki\RestPkiOptions;
use Lacuna\RestPki\RestPkiCoreClient;
use Lacuna\RestPki\RestPkiService;

$options = new RestPkiOptions('https://core.pki.rest/', getenv('RESTPKI_API_KEY'));
$client = new RestPkiCoreClient($options);
$service = new RestPkiService($client);

Neste exemplo, a chave de API vem da variável de ambiente RESTPKI_API_KEY, o que a mantém fora do código.

Cultura​

Para definir a cultura das respostas da API, passe-a como terceiro parâmetro do RestPkiOptions:

$options = new RestPkiOptions('https://core.pki.rest/', getenv('RESTPKI_API_KEY'), 'en-US');

Erros​

Todas as exceções a seguir ficam no namespace Lacuna\RestPki:

ExceçãoQuando
RestPkiExceptionA API rejeitou a requisição (HTTP 422). getErrorCode() retorna o código de erro e getDetail() descreve o erro, para os seus logs
ValidationExceptionUm certificado ou uma assinatura não passou na validação
RestErrorExceptionQualquer outro erro HTTP. getStatusCode() retorna o código de status HTTP (veja Códigos de status HTTP)
RestUnreachableExceptionNão foi possível acessar o endpoint

Exemplos em PHP​

No nosso repositório de exemplos, as pastas cujo nome termina em -rest-core usam o Rest PKI Core. O endpoint e a chave de API são definidos na entrada restPkiNg do config.php.

Java​

Adicione ao seu projeto o pacote com.lacunasoftware.restpki:restpkicore-client, do Maven Central. Ele requer o Java 8 ou posterior.

Com o Gradle, no build.gradle:

repositories {
mavenCentral()
}

dependencies {
implementation 'com.lacunasoftware.restpki:restpkicore-client:1.4.0'
}

Com o Maven, no pom.xml:

<dependency>
<groupId>com.lacunasoftware.restpki</groupId>
<artifactId>restpkicore-client</artifactId>
<version>1.4.0</version>
</dependency>

Consulte o Maven Central para saber qual é a versão mais recente.

aviso

Não confunda com o com.lacunasoftware.restpki:restpki-core-client, um pacote mais antigo que não é mais atualizado.

O pacote é de código aberto, hospedado no GitHub: fique à vontade para fazer um fork se precisar personalizá-lo.

Obtenha um RestPkiService de RestPkiServiceFactory.getService(), passando um RestPkiOptions com o endpoint e a chave de API:

import com.lacunasoftware.restpkicore.RestPkiOptions;
import com.lacunasoftware.restpkicore.RestPkiService;
import com.lacunasoftware.restpkicore.RestPkiServiceFactory;

RestPkiOptions options = new RestPkiOptions();
options.setEndpoint("https://core.pki.rest/");
options.setApiKey(System.getenv("RESTPKI_API_KEY"));
RestPkiService service = RestPkiServiceFactory.getService(options);

Neste exemplo, a chave de API vem da variável de ambiente RESTPKI_API_KEY, o que a mantém fora do código. Se a aplicação acessa a internet por um proxy, defina-o com options.setProxy().

Cultura​

Para definir a cultura das respostas da API, chame setCulture():

options.setCulture("en-US");

Erros​

Os métodos do RestPkiService declaram throws Exception. Estas são as exceções que eles lançam, todas no pacote com.lacunasoftware.restpkicore:

ExceçãoQuando
RestPkiExceptionA API rejeitou a requisição (HTTP 422). getErrorCode() retorna o código de erro
ValidationExceptionUm certificado ou uma assinatura não passou na validação
RestResourceNotFoundExceptionO recurso não foi encontrado (HTTP 404)
RestErrorExceptionQualquer outro erro HTTP. getStatusCode() retorna o código de status HTTP (veja Códigos de status HTTP)
RestUnreachableExceptionNão foi possível acessar o endpoint

Exemplos em Java​

No nosso repositório de exemplos, os controllers cujo nome termina em CoreController, como SignatureSessionRestCoreController, usam o Rest PKI Core. O endpoint e a chave de API são definidos em rest-pki-core, no application.yml.

Chamando a API diretamente​

As APIs do Rest PKI Core são RESTful, recebem e retornam JSON e, por isso, são fáceis de chamar em qualquer linguagem de programação moderna. Se a aplicação usa uma linguagem sem biblioteca cliente, chame-as diretamente:

  • URL: acrescente o caminho relativo da API ao endpoint. Por exemplo, api/signature-sessions na instância SaaS é https://core.pki.rest/api/signature-sessions
  • Autenticação: passe a chave de API no header X-Api-Key de todas as requisições
  • Corpo: envie JSON com o header Content-Type: application/json

Por exemplo:

POST https://core.pki.rest/api/signature-sessions
X-Api-Key: MyApp|0f3c...
Content-Type: application/json

Todas as APIs, com as requisições e respostas, estão descritas na referência da API. Numa instância própria, a referência fica no caminho swagger do endpoint, como https://restpki.suaempresa.com.br/swagger.

Códigos de status HTTP​

A API responde com os seguintes códigos de status HTTP:

CódigoSignificado
200 (OK)A requisição foi bem-sucedida. A resposta depende da API: veja a referência da API
400 (Bad Request)A requisição está malformada; por exemplo, falta um campo obrigatório
401 (Unauthorized)A chave de API está ausente, é inválida ou expirou
403 (Forbidden)A chave de API é válida, mas a aplicação dela não tem um papel que permita a operação (veja Escolhendo os papéis)
422 (Unprocessable Entity)A API rejeitou a requisição, normalmente por causa de um parâmetro que precisa ser corrigido. O corpo é um ErrorModel
500 (Internal Server Error)Ocorreu um erro inesperado. O campo exceptionCode do corpo ajuda a diagnosticar o problema: informe-o ao entrar em contato com o suporte

ErrorModel​

Quando a API responde com 422 (Unprocessable Entity), o corpo é um ErrorModel, chamado ErrorModelV2 na referência da API, com os seguintes campos:

CampoTipoDescrição
codestringO código de erro (veja os códigos de erro). Escreva o tratamento de erros com base neste campo
messagestringDescrição do erro, em inglês. Serve para os seus logs, não para os seus usuários, já que não é localizada
detailsobjectInformações adicionais sobre o erro, quando houver
validationResultsobjectQuando o código é ValidationError, os resultados da validação do certificado ou da assinatura que falhou

Por exemplo:

{
"code": "SignatureSessionNotFound",
"message": "Signature session not found: 00000000-0000-0000-0000-000000000000"
}

Cultura​

A API observa o header de requisição Accept-Language, que muda a cultura dos textos que a API retorna. As culturas suportadas são:

  • en-US (ou apenas en)
  • pt-BR (ou apenas pt)
  • es-ES (ou apenas es)
observação

As mensagens de erro não são afetadas por esse header; por isso, devem ser registradas no log, e não exibidas aos seus usuários. Para mostrar um erro a um usuário, associe o code dele a uma mensagem própria.

Faça uma primeira chamada​

Com as credenciais e a biblioteca cliente prontas, verifique se tudo funciona.

Primeiro, verifique o endpoint: abra o endereço api/system/info do endpoint num navegador, como https://core.pki.rest/api/system/info. Esse endereço não exige chave de API e retorna a versão da instância:

{"productName":"Lacuna Rest PKI Core","productVersion":"5.0.5 RTM","spaVersion":"...","timestamp":"..."}

Depois, verifique a chave de API criando uma sessão de assinatura. Em .NET:

using Lacuna.RestPki.Api.SignatureSessions;

var response = await restPkiService.CreateSignatureSessionAsync(new CreateSignatureSessionRequest() {
ReturnUrl = "https://localhost:5001/signature-callback",
});

// Send the user to response.RedirectUrl

Chamando a API diretamente:

curl -X POST "https://core.pki.rest/api/signature-sessions" \
-H "X-Api-Key: YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '{ "returnUrl": "https://localhost:5001/signature-callback" }'

A resposta traz o ID da sessão e a URL da página de assinatura dela:

{
"sessionId": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
"redirectUrl": "https://core.pki.rest/..."
}

Abra a redirectUrl num navegador para ver a página em que os seus usuários vão assinar. Se, em vez disso, a chamada falhar:

  • 401: a chave de API não foi enviada ou está errada. Verifique se você copiou a chave inteira, incluindo o nome da aplicação antes do |
  • 403: a aplicação não tem o papel Operador (veja Escolhendo os papéis)
  • Endpoint inacessível: verifique o endereço do endpoint e se o seu servidor consegue acessá-lo

Próximos passos​

Ver em Markdown