Autenticação de API, token único VS tokens dinâmicos

13

Estamos trabalhando em um novo projeto, somos dois desenvolvedores líderes e entramos em uma encruzilhada sobre como usar um token para proteger a comunicação entre o servidor e o cliente.

Primeira sugestão: (o token estático do AKA)

  1. o cliente solicita um token primário, enviando o nome de usuário e a senha e o current_time (essa variável será salva no banco de dados do servidor e também no lado do cliente) para a API, o servidor interpreta a entrada e renderiza um token (por exemplo: 58f52c075aca5d3e07869598c4d66648) o salva no banco de dados e o retorna ao cliente.

  2. Agora, o cliente salva o token primário e cria um novo token de hash usando o token primário + a variável current_time enviada na solicitação de autenticação (vamos chamar esse novo token, main_token) também o servidor faz o mesmo e cria o mesmo token usando o mesmo algoritmo .

  3. Sempre que o cliente consulta a API do servidor, ele envia o main_token para o servidor, agora o servidor compara o token gerado nele com o main_token enviado pelo cliente, se corresponder, significa que o usuário é real

Segunda sugestão: (token dinâmico)

  1. O cliente gera duas chaves aleatórias ($ key1 = rand (10000,90000); $ key2 = rand (10000,90000);) Em cada solicitação na API, o cliente cria um hash usando o tipo de consulta e as duas chaves com um algoritmo complexo e envia essas duas chaves + o hash para o servidor

  2. O servidor, usando o mesmo algoritmo usado no cliente, cria um hash e compara com o enviado pelo cliente; se corresponder, o servidor continuará a lidar com a consulta


Agora, a pergunta é: qual é a maneira mais lógica e segura de usar para proteger as solicitações de API?

SAFAD
fonte
2
Como o segundo é um meio de autenticação? Não deve ser algo proveniente do servidor que os usos do cliente na técnica auth, caso contrário, não há nenhuma maneira de saber se o cliente acaba de fazer-se a chave. Na segunda técnica, o que o servidor se origina quando o logon é concluído ao fornecer ao cliente para garantir que o cliente é o mesmo para o qual foi fornecido?
Jimmy Hoffa
1
Talvez esteja faltando alguma coisa ... mas por que não usar o OAuth como mecanismo de autenticação? É padrão e haverá bibliotecas para seus clientes usarem em todos os idiomas.
Icode4food

Respostas:

14

Eu realmente gosto da primeira abordagem em geral.

  • é simples de entender e implementar
  • é seguro (que eu saiba)
  • é uma abordagem não incomum que eu já vi usada no passado

Uma coisa que não vi mencionada sobre a primeira que você deve ter em mente: o carimbo de data / hora usado para hash do token precisa ter uma validade TTL extremamente curta (como 1 segundo) para verificar se a mensagem não foi enviada com o mesmo timestamp e token de uma mensagem 12 horas antes; obviamente, seria calculado como legítimo, mas não é neste caso.

Se essas são as duas únicas opções que você está considerando, eu gostaria de ter certeza de que também analisou outras abordagens, pois há muitas. Mais do que eu vou listar de fato. Essas são algumas abordagens de autenticação comuns que valem a pena ser estudadas apenas para verificar se elas se encaixam melhor no seu objetivo e se nada mais as compreende, podem lhe dar algumas idéias para ajudar a reforçar a abordagem que você usar.

Observe que eu não sou especialista em segurança.


OAuth / Federado

Nessa abordagem, você tem um garantidor de terceiros, onde o código de consumo solicita o token / cert / o que você possui e o passa para você. Nesse momento, tudo o que você precisa fazer é perguntar à terceira parte se a chave que você recebeu foi legítimo.

Pró:

  • Baseado em padrões
  • Problemas serão encontrados por outras pessoas nos sistemas de outras pessoas, para que você descubra se a insegurança acontece
  • Muito menos trabalho de autenticação será necessário para você

Vigarista:

  • Você precisa lidar com um prestador de serviços de terceiros e sua API, ou criar e hospedar seu próprio "terceiro" para separar a autenticação do seu serviço principal.
  • Para muitos serviços, um exagero, mas conceitualmente vale a pena considerar

Certificados assíncronos

Aqui, seus clientes criptografarão suas comunicações com um certificado público que você compartilhou com eles quando criaram um usuário. Do seu lado, você descriptografaria usando a chave privada associada ao usuário. Geralmente, você iniciaria a comunicação com uma resposta de desafio para mostrar que eles podem criptografar / descriptografar conforme o esperado, identificando-os como eles afirmam ser. Embora sejam possíveis abordagens "síncronas" que não usem a resposta de desafio, elas têm um pouco menos de segurança e alguns problemas de sincronização de tempo, o que pode torná-las mais complicadas.

da Novell (sim, eu sei, romance? Sério?)

Os tokens usam uma variável como base para gerar a senha descartável. Essa variável é chamada de desafio. Os dois métodos principais para determinar a variável usada para gerar a senha são assíncronos ou síncronos.

Com o método assíncrono ou de resposta ao desafio, o software do servidor envia ao token um desafio externo - uma variável gerada aleatoriamente - para o dispositivo do token criptografar. O token usa essa variável de desafio, o algoritmo de criptografia e o segredo compartilhado para gerar a resposta - a senha criptografada corretamente.

Com o método síncrono, a variável de desafio usada para gerar a senha é determinada internamente pelo token e pelo servidor. Uma combinação de contador de tempo, contador de eventos ou contador de tempo e eventos em cada dispositivo é usada como base para a variável de desafio. Como o token e o servidor determinam separadamente e internamente a variável de desafio de seus próprios contadores, é muito importante que os contadores de tempo e os contadores de eventos permaneçam sincronizados. Como é muito fácil o servidor e o token ficarem fora de sincronia, a maioria das implementações permite uma certa variação entre os contadores. Geralmente, um pequeno intervalo ou janela desses valores de contador é usado para calcular a senha. No entanto, se o token e o servidor ficarem fora de sincronia além desta janela,

Pró:

  • Os certificados têm raízes de CA que os tornam confiáveis ​​e difíceis de criar
  • Existem instalações padrão nos sistemas operacionais para gerenciar e manter facilmente os armazenamentos de certificados
  • Abordagem bem estudada, muita informação disponível
  • Expiração, juntamente com uma variedade de outras coisas, são instalações embutidas de certificados padrão, geralmente são robustas

Vigarista:

  • Pode ser difícil trabalhar com certificados de forma programática
  • Dependendo se você precisar de uma CA externa, pode não estar livre
  • Pode ser necessário manter os armazenamentos de certificados manualmente para garantir que as relações de confiança raiz esperadas sejam configuradas

NTLM

Não ria, se este é um serviço menor ou interno e você está em um ambiente Windows, não há nada de errado em usar a autenticação NTLM padrão para garantir o acesso. Especialmente se você estiver trabalhando com o IIS, essa é a abordagem mais simples. Fácil de manter e configurar também em um web.config.

Pró:

  • Extremamente fácil de configurar, implementar e manter

Vigarista:

  • Interoperabilidade mínima
  • Não é suficiente para autenticação pública

Nonces

Ao trabalhar com nonces em sua abordagem de autenticação, você fornece um método para obter um nonce no serviço. Esse método retorna uma sequência ou parte de dados arbitrária exclusiva ("a nonce") em cada solicitação. Agora, toda solicitação para outros métodos exige que um nonce seja recuperado e usado no algoritmo de criptografia para a solicitação. O valor aqui é que o servidor controla os nonces usados ​​e nunca permite a reutilização de um nonce; isso evita completamente os ataques de repetição porque, uma vez que uma solicitação com um nonce é feita, uma solicitação com esse nonce nunca pode ser feita novamente. Conforme os nonces são solicitados, eles são adicionados a uma lista de nonces disponíveis, à medida que são usados, são movidos da lista disponível para a lista usada.

Pró:

  • Replay ataques de Thwarts muito bem
  • Não é totalmente difícil de implementar ou entender

Vigarista:

  • Requer que os clientes façam duas solicitações para cada solicitação (embora possam ser diminuídas exigindo nonces para apenas determinadas solicitações)
  • Requer gerenciamento de nonces, que deve ser transacional
  • Afeta negativamente o desempenho ao exigir solicitações extras para nonces (a transacionalidade aumenta ainda mais o custo de recursos do trabalho com nonces)
Jimmy Hoffa
fonte
Suspeito que o TTL precise ser maior que um segundo, embora menor que um minuto (assumindo HTTP / HTTPS como o transporte). O TTL depende do intervalo de tempo do transporte (ou seja, muito mais tempo para email do que para conexão direta).
Donal Fellows
1
Você esqueceu kerberos . E eu colocaria um aviso excepcionalmente forte contra a rolagem de seu próprio pacote de autenticação / token, como a pergunta sugere. A autenticação RYO é muito fácil de errar; um exemplo seria usar um espaço de chave de propagação de apenas 80.000 valores numéricos de 5 dígitos (do segundo caso do OP). Você também deve ter cuidado com os hashes que usa (do 1º caso). Muitos agora são quebrados trivialmente nas pesquisas de tabela do arco-íris.
1
Muito obrigado pela resposta. Saí desse projeto, mas manterei essa pergunta nos meus favoritos. Lamento não ter aceitado sua resposta, pois é muito completa. Mas, o que há com o romance ser ruim? :(
SAFAD
@SAFAD nada de ruim na Novell, fiquei surpreso ao procurar recursos sobre detalhes de segurança que encontrei algo moderno da Novell, achei que a empresa havia morrido há muito tempo. há muito tempo agora. Aprecio a aceitação da mesma forma, pois Glen acima menciona que poderia ser mais completo, mas tentei fornecer uma visão simplista das abordagens normais. Kerberos é um muito grande supervisão e boas choice..perhaps eu vou adicioná-lo agora ..
Jimmy Hoffa