Logo do site

Seu software tem licença... ou só uma data no código?

Publicado em: 12/09/2026 21:33
Última atualização: 12/09/2026 21:49
tecnologia
software

Se você desenvolve aplicações desktop, talvez já tenha usado — ou pelo menos pensado em usar — alguma solução criativa para controlar licenças: uma data fixa no código, um licenca.txt no FTP, uma flag em uma planilha, um arquivo local...

Funciona? Dependendo do projeto, até funciona. O problema aparece quando você precisa suspender uma licença, trocar o computador autorizado, controlar vários clientes ou simplesmente parar de gerar uma nova build toda vez que alguma coisa muda.

Foi justamente para simplificar esse cenário que criei o Gerenciador de Licenças do yuri97.com. A ideia é você integrar uma API à sua aplicação e deixar o gerenciamento das licenças centralizado.

Fluxo de ativação e validação de licença
Fluxo de ativação e validação de licença

Como funciona?

O fluxo envolve três partes:

  1. yuri97.com: emite as licenças e fornece a API de validação.
  2. Você: cadastra as licenças e integra a API ao seu software.
  3. Seu cliente: informa o token de ativação e utiliza a aplicação no dispositivo autorizado.

Você pode cadastrar até 5 licenças gratuitamente. Em breve pretendo disponibilizar planos pagos para quem precisar de limites maiores.

Para projetos pequenos e médios, isso também pode ser mais interessante do que hospedar e manter um sistema web completo apenas para gerenciar licenças. Você evita ter que cuidar de outra aplicação, banco de dados, API e infraestrutura somente para resolver esse problema.

1. Ativando a licença

Ao criar uma licença no painel, você recebe um token de ativação para fornecer ao cliente.

Na primeira execução, sua aplicação gera um fingerprint do dispositivo e envia os dois valores para a API. O token de ativação expira em 1 dia e deve ser usado apenas nessa etapa.

Endpoint

URL_DO_ENDPOINT = "https://yuri97.com/api/licenses/token/refresh"

Exemplo com cURL

curl -X POST "URL_DO_ENDPOINT" \
  -H "Authorization: Bearer TOKEN_DE_ATIVACAO" \
  -H "Content-Type: application/json" \
  -d '{"fingerprint":"FINGERPRINT_DO_DISPOSITIVO"}'

# Resposta:
# { "token": "NOVO_TOKEN_ASSINADO", "public_key": "..." }

Se tudo estiver correto, a licença é vinculada ao fingerprint e a API retorna um novo token assinado. A partir daqui, o token de ativação não deve mais ser usado.

2. Validando a licença

Nas próximas consultas, envie sempre o último token retornado pela API junto com o mesmo fingerprint. Cada resposta bem-sucedida retorna outro token, que substitui o anterior.

curl -X POST "URL_DO_ENDPOINT" \
  -H "Authorization: Bearer ULTIMO_TOKEN_RETORNADO" \
  -H "Content-Type: application/json" \
  -d '{"fingerprint":"O_MESMO_FINGERPRINT"}'

Em outras palavras, sua aplicação precisa basicamente guardar o fingerprint e sempre substituir o token salvo pelo último recebido.

  • 200: licença válida; salve o novo token.
  • 401: a licença ou o dispositivo foi recusado.
  • 400: normalmente indica algum problema com o token enviado.

Uma possibilidade é consultar a API periodicamente enquanto o programa estiver aberto — por exemplo, a cada 1 ou 2 minutos. O intervalo ideal depende do seu software e de quão rapidamente você precisa detectar uma suspensão ou revogação.

3. E se ficar sem internet?

Defina limites de tolerância na sua aplicação

A API depende de conexão, mas isso não significa necessariamente que seu programa precise fechar no primeiro timeout.

Uma estratégia possível é implementar um offline grace period: depois de uma validação bem-sucedida, sua aplicação permite algum tempo de uso sem conseguir consultar novamente o servidor.

Isso é uma decisão da sua aplicação, não uma garantia de funcionamento offline oferecida pelo serviço.

Algumas ideias que podem ser úteis:

  • diferenciar falta de internet de uma resposta 401;
  • guardar quando ocorreu a última validação bem-sucedida;
  • definir um limite de tempo para funcionamento offline;
  • tentar validar novamente assim que a conexão voltar.

O prazo também depende bastante do projeto. Um sistema que opera continuamente pode aceitar apenas algumas horas offline, enquanto uma aplicação usada em campo talvez precise tolerar alguns dias.

Quanto maior esse período, maior também a janela em que uma licença revogada poderá continuar sendo utilizada. É um equilíbrio que cabe ao desenvolvedor definir.

4. Fingerprint e troca de computador

O fingerprint serve para vincular a licença ao dispositivo onde ela foi ativada. Procure gerar um identificador estável usando informações da máquina que não mudem facilmente.

IP, hostname ou endereço MAC isoladamente costumam ser escolhas frágeis. Uma alternativa é combinar identificadores do sistema/hardware e gerar um hash desse conjunto.

Se o cliente trocar de computador, você pode voltar a licença para pending no painel e gerar um novo token de ativação.

5. Não confie em qualquer resposta

Aceitar respostas sem HTTPS/TLS compromete seu sistema.

Aqui entra uma parte importante que às vezes passa despercebida em sistemas de licenciamento: não adianta perguntar para uma API se você não tem alguma garantia de que está realmente conversando com a sua API.

Imagine que alguém redirecione o domínio utilizado pelo programa para um servidor controlado por ele. Se sua aplicação ignora erros de certificado HTTPS/TLS, esse servidor poderia tentar se passar pela API verdadeira e responder que a licença está sempre válida.

Por isso, uma recomendação importante é não desabilitar a validação do certificado HTTPS/TLS. Alterar DNS ou o arquivo hosts não deveria ser suficiente para enganar uma aplicação que verifica corretamente a identidade do servidor.

6. E a chave pública?

Os tokens podem ser assinados criptograficamente. Se sua aplicação validar essa assinatura usando a chave pública oficial, você ganha uma camada adicional: não basta alguém criar uma resposta parecida com a da API; o token recebido também precisa possuir uma assinatura válida.

Existe, porém, outro detalhe interessante: se você simplesmente salvar public_key.pem ao lado de license.jwt e confiar cegamente nos dois arquivos, alguém com controle sobre a máquina pode substituir ambos.

Uma abordagem mais resistente é utilizar uma chave pública oficial conhecida pela aplicação como âncora de confiança, em vez de aceitar qualquer chave pública encontrada localmente.

Isso não torna um programa desktop impossível de modificar. O usuário controla a máquina onde o executável roda e alguém suficientemente determinado pode tentar alterar o próprio programa para remover as verificações.

O objetivo aqui não é criar uma proteção impossível de quebrar, mas evitar que contornar o licenciamento seja tão simples quanto editar um TXT, mudar uma data ou apontar um domínio para localhost.

7. Algumas recomendações

Não existe uma única implementação correta para todo software. Dependendo do valor da aplicação, perfil dos clientes e necessidade de funcionamento offline, você pode combinar diferentes camadas:

  • HTTPS/TLS com validação normal de certificado;
  • tokens assinados criptograficamente;
  • validação local da assinatura quando fizer sentido;
  • fingerprint do dispositivo;
  • consultas periódicas à API;
  • um grace period offline adequado ao seu cenário.

Para aplicações mais sensíveis, outras técnicas como assinatura do executável, verificações de integridade e proteção contra adulteração também podem ser consideradas.

O importante é entender as limitações de cada abordagem e escolher o nível de proteção que faça sentido para o seu projeto.

8. Quer implementar com IA?

Se estiver usando ChatGPT, Cursor, Copilot ou outro assistente, você pode explicar o protocolo e pedir para ele implementar a integração na linguagem e arquitetura do seu projeto.

Implemente a integração da minha aplicação desktop com a API de licenciamento abaixo.

Endpoint:
https://yuri97.com/api/licenses/token/refresh

Fluxo de ativação:

1. Quando a aplicação ainda não possuir uma licença ativada, solicite ao usuário o TOKEN_DE_ATIVACAO por meio de um campo ou tela apropriada à interface existente.

2. Gere um fingerprint estável do dispositivo.

3. Envie uma requisição POST para o endpoint usando o token informado pelo usuário:

Authorization: Bearer TOKEN_DE_ATIVACAO
Content-Type: application/json

Body:
{ "fingerprint": "FINGERPRINT" }

4. Se a ativação for bem-sucedida, salve o token assinado retornado pela API. O TOKEN_DE_ATIVACAO é descartável e não deve ser utilizado novamente.

Validações seguintes:

5. Envie sempre o último token retornado pela API junto com o mesmo fingerprint.

6. Após cada resposta 200, substitua o token armazenado pelo novo token retornado.

7. Em caso de 401, considere a licença recusada e impeça o uso normal da aplicação.

8. Diferencie uma recusa da API de erros de conexão.

9. Se apropriado para a aplicação, implemente um período de tolerância offline baseado na última validação bem-sucedida.

Segurança:

10. Nunca desabilite a validação HTTPS/TLS.

11. Se implementar validação criptográfica local dos tokens, utilize uma chave pública oficial e confiável como âncora de confiança, sem aceitar arbitrariamente uma chave substituível armazenada junto do token.

Integre esse fluxo respeitando a interface, arquitetura, convenções e mecanismos de armazenamento já existentes no projeto.

Chega de licenca.txt? 😅

Data fixa no código, TXT no FTP, flag numa planilha... às vezes uma gambiarra resolve perfeitamente o problema daquele projeto pequeno. Não vou julgar — provavelmente todo desenvolvedor já fez algo parecido. 😅

Mas quando o software começa a crescer, ter um lugar central para ativar, suspender, revogar e acompanhar licenças facilita bastante a vida.

O Gerenciador de Licenças do yuri97.com nasceu justamente com essa proposta: oferecer uma alternativa simples para adicionar esse controle a aplicações desktop sem precisar construir e hospedar todo um sistema de licenciamento do zero.

Você pode começar gratuitamente com até 5 licenças. E, conforme a ferramenta evoluir, pretendo oferecer planos com limites maiores.

Teste o Gerenciador de Licenças.