Pergunta

Autenticação baseada em formulário para sites

Acreditamos que o Stack Overflow não deve ser apenas um recurso para questões técnicas muito específicas, mas também para orientações gerais sobre como resolver variações de problemas comuns."Autenticação baseada em formulário para sites" deve ser um bom tópico para tal experiência.

Deve incluir tópicos como:

  • Como fazer login
  • Como sair
  • Como permanecer logado
  • Gerenciar cookies (incluindo configurações recomendadas)
  • Criptografia SSL/HTTPS
  • Como armazenar senhas
  • Usando perguntas secretas
  • Funcionalidade de nome de usuário/senha esquecida
  • Uso de nonces prevenir falsificações de solicitação entre sites (CSRF)
  • OpenID
  • Caixa de seleção "Lembrar de mim"
  • Preenchimento automático de nomes de usuário e senhas do navegador
  • URLs secretos (públicos URL protegido por resumo)
  • Verificando a força da senha
  • Validação de e-mail
  • e muito mais sobre autenticação baseada em formulário...

Não deve incluir coisas como:

  • Funções e autorização
  • Autenticação básica HTTP

Por favor, ajude-nos:

  1. Sugerindo subtópicos
  2. Enviando bons artigos sobre este assunto
  3. Editando a resposta oficial
Foi útil?

Solução

PARTE I:Como fazer login

Assumiremos que você já sabe como construir um formulário HTML de login+senha que envia os valores para um script no lado do servidor para autenticação.As seções abaixo tratarão de padrões de autenticação prática e sólida e de como evitar as armadilhas de segurança mais comuns.

Para HTTPS ou não para HTTPS?

A menos que a conexão já seja segura (ou seja, encapsulada através de HTTPS usando SSL/TLS), os valores do seu formulário de login serão enviados em texto não criptografado, o que permite que qualquer pessoa que esteja espionando a linha entre o navegador e o servidor web possa ler os logins à medida que eles passam. através.Este tipo de escuta telefônica é feito rotineiramente pelos governos, mas, em geral, não abordaremos fios “de sua propriedade”, a não ser para dizer o seguinte:Se você estiver protegendo algo importante, use HTTPS.

Em essência, o único prático Uma maneira de se proteger contra escutas telefônicas/sniffing de pacotes durante o login é usar HTTPS ou outro esquema de criptografia baseado em certificado (por exemplo, TLS) ou um esquema de resposta a desafios comprovado e testado (por exemplo, o Diffie-Hellmanbaseado em SRP). Qualquer outro método pode ser facilmente contornado por um invasor espião.

Claro, se você estiver disposto a ser um pouco impraticável, também poderá empregar alguma forma de esquema de autenticação de dois fatores (por exemplo,o aplicativo Google Authenticator, um livro de códigos físico do 'estilo da guerra fria' ou um dongle gerador de chave RSA).Se aplicado corretamente, isso poderia funcionar mesmo com uma conexão não segura, mas é difícil imaginar que um desenvolvedor estaria disposto a implementar a autenticação de dois fatores, mas não o SSL.

(Não) Crie sua própria criptografia/hashing JavaScript

Dado o custo diferente de zero e a dificuldade técnica percebida de configurar um certificado SSL em seu site, alguns desenvolvedores ficam tentados a implementar seus próprios esquemas de hash ou criptografia no navegador para evitar a passagem de logins em texto não criptografado por uma rede não segura.

Embora este seja um pensamento nobre, é essencialmente inútil (e pode ser um falha de segurança), a menos que seja combinado com um dos itens acima - isto é, protegendo a linha com criptografia forte ou usando um mecanismo de resposta a desafios testado e comprovado (se você não sabe o que é isso, saiba que é um dos conceitos mais difíceis de provar, mais difíceis de projetar e mais difíceis de implementar em segurança digital).

Embora seja verdade que o hash da senha pode ser eficaz contra divulgação de senha, é vulnerável a ataques de repetição, ataques/sequestros Man-In-The-Middle (se um invasor puder injetar alguns bytes em sua página HTML insegura antes que ela chegue ao seu navegador, ele pode simplesmente comentar o hash no JavaScript), ou ataques de força bruta (já que você está entregando ao invasor o nome de usuário, o salt e a senha com hash).

CAPTCHAS contra a humanidade

CAPTCHA destina-se a impedir uma categoria específica de ataque:dicionário automatizado/tentativa e erro de força bruta sem operador humano.Não há dúvida de que esta é uma ameaça real, no entanto, existem maneiras de lidar com isso perfeitamente que não exigem um CAPTCHA, esquemas de otimização de login do lado do servidor especificamente projetados de maneira adequada - discutiremos isso mais tarde.

Saiba que as implementações de CAPTCHA não são criadas da mesma forma;muitas vezes não são solucionáveis ​​por humanos, a maioria deles é na verdade ineficaz contra bots, todos eles são ineficazes contra mão de obra barata do terceiro mundo (de acordo com OWASP, a taxa atual de trabalho explorador é de US$ 12 por 500 testes), e algumas implementações podem ser tecnicamente ilegais em alguns países (ver Folha de dicas de autenticação OWASP).Se você precisar usar um CAPTCHA, use o do Google reCAPTCHA, uma vez que é difícil de OCR por definição (uma vez que usa digitalizações de livros já classificadas incorretamente por OCR) e se esforça ao máximo para ser fácil de usar.

Pessoalmente, costumo achar os CAPTCHAS irritantes e usá-los apenas como último recurso quando um usuário não consegue fazer login várias vezes e os atrasos de limitação são maximizados.Isto acontecerá raramente o suficiente para ser aceitável e fortalece o sistema como um todo.

Armazenamento de senhas/verificação de logins

Isso pode finalmente ser de conhecimento comum depois de todos os hacks e vazamentos de dados de usuários altamente divulgados que vimos nos últimos anos, mas é preciso dizer:Não armazene senhas em texto não criptografado em seu banco de dados.Os bancos de dados de usuários são rotineiramente hackeados, vazados ou coletados por meio de injeção de SQL e, se você estiver armazenando senhas brutas em texto simples, o jogo termina instantaneamente para a segurança de seu login.

Então, se você não consegue armazenar a senha, como verificar se a combinação de login + senha POSTada no formulário de login está correta?A resposta é hash usando um função de derivação de chave.Sempre que um novo usuário é criado ou uma senha é alterada, você pega a senha e a executa através de um KDF, como Argon2, bcrypt, scrypt ou PBKDF2, transformando a senha em texto simples ("correcthorsebatterystaple") em uma string longa e de aparência aleatória , que é muito mais seguro para armazenar em seu banco de dados.Para verificar um login, você executa a mesma função hash na senha inserida, desta vez passando o salt e compara a string hash resultante com o valor armazenado em seu banco de dados.Argon2, bcrypt e scrypt já armazenam o salt com o hash.Veja isso artigo em sec.stackexchange para obter informações mais detalhadas.

A razão pela qual um sal é usado é que o hash em si não é suficiente - você desejará adicionar um chamado 'sal' para proteger o hash contra tabelas arco-íris.Um salt evita efetivamente que duas senhas que correspondam exatamente sejam armazenadas como o mesmo valor de hash, evitando que todo o banco de dados seja verificado de uma só vez se um invasor estiver executando um ataque de adivinhação de senha.

Um hash criptográfico não deve ser usado para armazenamento de senhas porque as senhas selecionadas pelo usuário não são fortes o suficiente (ou seja,geralmente não contêm entropia suficiente) e um ataque de adivinhação de senha pode ser concluído em um tempo relativamente curto por um invasor com acesso aos hashes.É por isso que os KDFs são usados ​​- estes efetivamente "esticar a chave", o que significa que cada senha adivinhada por um invasor causa múltiplas repetições do algoritmo hash, por exemplo, 10.000 vezes, o que faz com que o invasor adivinhe a senha 10.000 vezes mais lentamente.

Dados da sessão - "Você está logado como Spiderman69"

Depois que o servidor verificar o login e a senha no banco de dados do usuário e encontrar uma correspondência, o sistema precisará lembrar que o navegador foi autenticado.Este fato só deve ser armazenado no lado do servidor nos dados da sessão.

Se você não está familiarizado com os dados da sessão, veja como funciona:Uma única string gerada aleatoriamente é armazenada em um cookie expirado e usada para fazer referência a uma coleção de dados – os dados da sessão – que são armazenados no servidor.Se você estiver usando uma estrutura MVC, isso sem dúvida já foi resolvido.

Se possível, certifique-se de que o cookie da sessão tenha os sinalizadores seguro e somente HTTP definidos quando enviado ao navegador.O sinalizador HttpOnly fornece alguma proteção contra a leitura do cookie por meio de ataque XSS.O sinalizador seguro garante que o cookie seja enviado de volta somente via HTTPS e, portanto, protege contra ataques de detecção de rede.O valor do cookie não deve ser previsível.Quando for apresentado um cookie referenciando uma sessão inexistente, o seu valor deverá ser substituído imediatamente para evitar fixação de sessão.

PARTE II:Como permanecer conectado - a infame caixa de seleção "Lembrar-me"

Cookies de login persistentes (funcionalidade "lembrar de mim") são uma zona de perigo;por um lado, eles são tão seguros quanto os logins convencionais quando os usuários entendem como lidar com eles;e por outro lado, representam um enorme risco de segurança nas mãos de utilizadores descuidados, que podem utilizá-los em computadores públicos e esquecer-se de sair, e que podem não saber o que são cookies de navegador ou como eliminá-los.

Pessoalmente, gosto de logins persistentes nos sites que visito regularmente, mas sei como lidar com eles com segurança.Se você tem certeza de que seus usuários sabem o mesmo, você pode usar logins persistentes com a consciência tranquila.Caso contrário, bem, então você pode seguir a filosofia de que os usuários que são descuidados com suas credenciais de login causam isso a si mesmos caso sejam hackeados.Não é como se fôssemos às casas de nossos usuários e arrancassemos todos aqueles post-its com senhas que eles alinhavam na borda de seus monitores.

É claro que alguns sistemas não podem se dar ao luxo de ter qualquer contas hackeadas;para esses sistemas, não há como justificar logins persistentes.

Se você decidir implementar cookies de login persistentes, faça o seguinte:

  1. Primeiro, reserve um tempo para ler Artigo da Iniciativa Paragon sobre o assunto.Você precisará acertar vários elementos, e o artigo faz um ótimo trabalho ao explicar cada um.

  2. E só para reiterar uma das armadilhas mais comuns, NÃO ARMAZENE O COOKIE DE LOGIN PERSISTENTE (TOKEN) NO SEU BANCO DE DADOS, APENAS UM HASH DELE! O token de login é equivalente a senha, portanto, se um invasor colocar as mãos em seu banco de dados, ele poderá usar os tokens para fazer login em qualquer conta, como se fossem combinações de login e senha em texto não criptografado.Portanto, use hashing (de acordo com https://security.stackexchange.com/a/63438/5002 um hash fraco servirá perfeitamente para esse propósito) ao armazenar tokens de login persistentes.

PARTE III:Usando perguntas secretas

Não implemente 'perguntas secretas'.O recurso de ‘perguntas secretas’ é um antipadrão de segurança.Leia o artigo no link número 4 da lista de LEITURA OBRIGATÓRIA.Você pode perguntar a Sarah Palin sobre isso, depois de seu Yahoo!conta de e-mail foi hackeada durante uma campanha presidencial anterior porque a resposta à sua pergunta de segurança era..."Escola Secundária Wasilla"!

Mesmo com perguntas específicas do usuário, é altamente provável que a maioria dos usuários escolha:

  • Uma pergunta secreta 'padrão', como o nome de solteira da mãe ou o animal de estimação favorito

  • Uma curiosidade simples que qualquer um pode extrair de seu blog, perfil do LinkedIn ou similar

  • Qualquer pergunta que seja mais fácil de responder do que adivinhar a senha.Qual, para qualquer senha decente, é toda pergunta que você pode imaginar

Concluindo, as questões de segurança são inerentemente inseguras em praticamente todas as suas formas e variações e não devem ser empregadas em um esquema de autenticação por qualquer motivo.

A verdadeira razão pela qual existem questões de segurança é que elas economizam convenientemente o custo de algumas chamadas de suporte de usuários que não conseguem acessar seu e-mail para obter um código de reativação.Isto à custa da segurança e da reputação de Sarah Palin.Vale a pena?Provavelmente não.

PARTE IV:Funcionalidade de senha esquecida

Eu já mencionei por que você deveria nunca use perguntas de segurança para lidar com senhas de usuários esquecidas/perdidas;também é desnecessário dizer que você nunca deve enviar e-mails aos usuários com suas senhas reais.Existem pelo menos mais duas armadilhas comuns a serem evitadas neste campo:

  1. Não reiniciar uma senha esquecida para uma senha forte gerada automaticamente - essas senhas são notoriamente difíceis de lembrar, o que significa que o usuário deve alterá-la ou anotá-la - digamos, em um Post-It amarelo brilhante na borda do monitor.Em vez de definir uma nova senha, deixe os usuários escolherem uma nova imediatamente – que é o que eles desejam fazer de qualquer maneira.(Uma exceção a isso pode ser se os usuários estiverem usando universalmente um gerenciador de senhas para armazenar/gerenciar senhas que normalmente seriam impossíveis de lembrar sem anotá-las).

  2. Sempre faça hash do código/token da senha perdida no banco de dados. DE NOVO, esse código é outro exemplo de senha equivalente, portanto DEVE ser hash caso um invasor coloque as mãos em seu banco de dados.Quando um código de senha perdida for solicitado, envie o código de texto simples para o endereço de e-mail do usuário, faça o hash e salve o hash em seu banco de dados - e jogue fora o original.Assim como uma senha ou um token de login persistente.

Uma nota final:sempre certifique-se de que sua interface para inserir o 'código de senha perdida' seja pelo menos tão segura quanto o próprio formulário de login, ou um invasor simplesmente usará isso para obter acesso.Certificar-se de gerar 'códigos de senha perdida' muito longos (por exemplo, 16 caracteres alfanuméricos que diferenciam maiúsculas de minúsculas) é um bom começo, mas considere adicionar o mesmo esquema de limitação que você usa para o próprio formulário de login.

PARTE V:Verificando a força da senha

Primeiro, você vai querer ler este pequeno artigo para verificar a realidade: As 500 senhas mais comuns

Ok, talvez a lista não seja a canônico lista das senhas mais comuns em qualquer sistema em qualquer lugar, mas é uma boa indicação de quão mal as pessoas escolherão suas senhas quando não houver uma política aplicada em vigor.Além disso, a lista parece assustadoramente próxima de casa quando comparada com análises disponíveis publicamente de senhas roubadas recentemente.

Então:Sem requisitos mínimos de força de senha, 2% dos usuários usam uma das 20 senhas mais comuns.Significado:se um invasor fizer apenas 20 tentativas, 1 em cada 50 contas em seu site poderá ser quebrada.

Impedir isso requer calcular a entropia de uma senha e depois aplicar um limite.O Instituto Nacional de Padrões e Tecnologia (NIST) Publicação Especial 800-63 tem um conjunto de sugestões muito boas.Isso, quando combinado com uma análise de dicionário e layout de teclado (por exemplo, 'qwertyuiop' é uma senha incorreta), pode rejeitar 99% de todas as senhas mal selecionadas a um nível de 18 bits de entropia.Simplesmente calculando a força da senha e mostrando um medidor de força visual para um usuário é bom, mas insuficiente.A menos que seja aplicado, muitos usuários provavelmente irão ignorá-lo.

E para uma visão refrescante da facilidade de uso de senhas de alta entropia, Randall Munroe Força da senha xkcd é altamente recomendado.

Utilize Troy Hunt Fui enganado pela API para verificar as senhas dos usuários em relação às senhas comprometidas em violações de dados públicos.

PARTE VI:Muito mais - ou:Evitando tentativas de login rápido

Primeiro, dê uma olhada nos números: Velocidades de recuperação de senha - Por quanto tempo sua senha permanecerá válida

Se você não tiver tempo para consultar as tabelas desse link, aqui está a lista delas:

  1. Leva praticamente nenhum tempo quebrar uma senha fraca, mesmo se você a quebrar com um ábaco

  2. Leva praticamente nenhum tempo para quebrar uma senha alfanumérica de 9 caracteres, se for sem distinção entre maiúsculas e minúsculas

  3. Leva praticamente nenhum tempo para quebrar uma senha complexa, com símbolos, letras e números, maiúsculas e minúsculas, se for menos de 8 caracteres (um PC desktop pode pesquisar todo o keyspace em até 7 caracteres em questão de dias ou até horas)

  4. No entanto, levaria muito tempo para quebrar até mesmo uma senha de 6 caracteres, se você estivesse limitado a uma tentativa por segundo!

Então, o que podemos aprender com esses números?Bem, muitos, mas podemos nos concentrar na parte mais importante:o fato de impedir um grande número de tentativas de login sucessivas e rápidas (ou seja,o força bruta ataque) realmente não é tão difícil.Mas impedi-lo certo não é tão fácil quanto parece.

De modo geral, você tem três opções que são eficazes contra ataques de força bruta (e ataques de dicionário, mas como você já está empregando uma política de senhas fortes, eles não devem ser um problema):

  • Apresente um CAPTCHA depois de N tentativas fracassadas (irritante como o inferno e muitas vezes ineficaz - mas estou me repetindo aqui)

  • Bloqueio de contas e exigindo verificação de e-mail após N tentativas fracassadas (este é um DoS ataque esperando para acontecer)

  • E finalmente, limitação de login:isto é, definir um atraso de tempo entre tentativas após N tentativas fracassadas (sim, ataques DoS ainda são possíveis, mas pelo menos são muito menos prováveis ​​e muito mais complicados de serem executados).

Melhor prática nº 1: Um pequeno atraso que aumenta com o número de tentativas malsucedidas, como:

  • 1 tentativa falhada = sem atraso
  • 2 tentativas fracassadas = atraso de 2 segundos
  • 3 tentativas fracassadas = atraso de 4 segundos
  • 4 tentativas fracassadas = atraso de 8 segundos
  • 5 tentativas fracassadas = atraso de 16 segundos
  • etc.

Um ataque DoS a este esquema seria muito impraticável, uma vez que o tempo de bloqueio resultante é ligeiramente maior que a soma dos tempos de bloqueio anteriores.

Esclarecer:O atraso é não um atraso antes de retornar a resposta ao navegador.É mais como um tempo limite ou período refratário durante o qual as tentativas de login em uma conta específica ou de um endereço IP específico não serão aceitas ou avaliadas.Ou seja, as credenciais corretas não retornarão em um login bem-sucedido e as credenciais incorretas não desencadearão um aumento de atraso.

Melhor prática nº 2: Um atraso de tempo médio que entra em vigor após N tentativas fracassadas, como:

  • 1-4 tentativas fracassadas = sem atraso
  • 5 tentativas fracassadas = atraso de 15 a 30 minutos

Um ataque DoS a este esquema seria bastante impraticável, mas certamente factível.Além disso, pode ser relevante observar que um atraso tão longo pode ser muito irritante para um usuário legítimo.Usuários esquecidos não gostarão de você.

Melhor prática nº 3: Combinando as duas abordagens - um atraso fixo e curto que entra em vigor após N tentativas fracassadas, como:

  • 1-4 tentativas fracassadas = sem atraso
  • Mais de 5 tentativas fracassadas = atraso de 20 segundos

Ou um atraso crescente com um limite superior fixo, como:

  • 1 tentativa falhada = atraso de 5 segundos
  • 2 tentativas fracassadas = atraso de 15 segundos
  • Mais de 3 tentativas fracassadas = atraso de 45 segundos

Este esquema final foi retirado das sugestões de melhores práticas do OWASP (link 1 da lista OBRIGATÓRIA) e deve ser considerado uma melhor prática, mesmo que seja reconhecidamente restritivo.

Como regra geral, porém, eu diria:quanto mais forte for sua política de senha, menos você terá que incomodar os usuários com atrasos.Se você precisar de senhas fortes (alfanuméricos com distinção entre maiúsculas e minúsculas + números e símbolos obrigatórios) com mais de 9 caracteres, poderá fornecer aos usuários de 2 a 4 tentativas de senha sem atraso antes de ativar a limitação.

DoS atacando este esquema final de limitação de login seria muito impraticável.E como toque final, sempre permita a passagem de logins persistentes (cookies) (e/ou um formulário de login verificado por CAPTCHA), para que usuários legítimos não sejam atrasados enquanto o ataque está em andamento.Dessa forma, o ataque DoS, muito impraticável, torna-se um extremamente ataque impraticável.

Além disso, faz sentido fazer uma limitação mais agressiva nas contas de administrador, uma vez que esses são os pontos de entrada mais atraentes

PARTE VII:Ataques distribuídos de força bruta

Apenas como um aparte, os invasores mais avançados tentarão contornar a limitação de login 'difundindo suas atividades':

  • Distribuir as tentativas em uma botnet para evitar sinalização de endereço IP

  • Em vez de escolher um usuário e tentar as 50.000 senhas mais comuns (o que não é possível, devido à nossa limitação), eles escolherão A senha mais comum e a testarão com 50.000 usuários.Dessa forma, eles não apenas contornam medidas de tentativas máximas, como CAPTCHAs e otimização de login, mas também aumentam suas chances de sucesso, já que a senha mais comum número 1 é muito mais provável do que a número 49.995.

  • Espaçar as solicitações de login para cada conta de usuário, digamos, com 30 segundos de intervalo, para passar despercebido

Aqui, a melhor prática seria registrando o número de logins com falha, em todo o sistema, e usando uma média da frequência de login incorreto do seu site como base para um limite máximo que você impõe a todos os usuários.

Muito abstrato?Deixe-me reformular:

Digamos que seu site teve uma média de 120 logins incorretos por dia nos últimos 3 meses.Usando isso (média de execução), seu sistema pode definir o limite global para 3 vezes isso - ou seja.360 tentativas fracassadas em um período de 24 horas.Então, se o número total de tentativas fracassadas em todas as contas exceder esse número em um dia (ou melhor ainda, monitore a taxa de aceleração e acione em um limite calculado), ele ativa a aceleração de login em todo o sistema - o que significa pequenos atrasos para TODOS os usuários (ainda assim, com exceção de logins de cookies e/ou logins de backup CAPTCHA).

Eu também postei uma pergunta com mais detalhes e uma boa discussão sobre como evitar armadilhas complicadas na defesa contra ataques de força bruta distribuídos

PARTE VIII:Autenticação de dois fatores e provedores de autenticação

As credenciais podem ser comprometidas, seja por explorações, senhas anotadas e perdidas, laptops com chaves roubadas ou usuários inserindo logins em sites de phishing.Os logins podem ser ainda mais protegidos com autenticação de dois fatores, que usa fatores fora de banda, como códigos de uso único recebidos de uma chamada telefônica, mensagem SMS, aplicativo ou dongle.Vários provedores oferecem serviços de autenticação de dois fatores.

A autenticação pode ser completamente delegada a um serviço de logon único, onde outro provedor cuida da coleta de credenciais.Isso empurra o problema para um terceiro confiável.Google e Twitter fornecem serviços de SSO baseados em padrões, enquanto o Facebook fornece uma solução proprietária semelhante.

LINKS OBRIGATÓRIOS sobre autenticação na Web

  1. Guia OWASP para autenticação / Folha de dicas de autenticação OWASP
  2. O que fazer e o que não fazer na autenticação de cliente na Web (artigo de pesquisa muito legível do MIT)
  3. Wikipédia:Cookie HTTP
  4. Perguntas de conhecimento pessoal para autenticação alternativa:Questões de segurança na era do Facebook (artigo de pesquisa muito legível de Berkeley)

Outras dicas

Artigo Definitivo

Enviando credenciais

A única maneira prática de enviar credenciais de forma 100% segura é usando SSL.Usar JavaScript para fazer hash da senha não é seguro.Armadilhas comuns para hash de senha do lado do cliente:

  • Se a conexão entre o cliente e o servidor não estiver criptografada, tudo o que você faz é vulnerável a ataques man-in-the-middle.Um invasor pode substituir o javascript recebido para quebrar o hash ou enviar todas as credenciais para seu servidor, pode ouvir as respostas do cliente e representar os usuários perfeitamente, etc.etc.SSL com autoridades de certificação confiáveis ​​foi projetado para evitar ataques MitM.
  • A senha com hash recebida pelo servidor é menos seguro se você não fizer trabalho adicional e redundante no servidor.

Existe outro método seguro chamado PRS, mas é patenteado (embora seja licenciado gratuitamente) e há poucas boas implementações disponíveis.

Armazenando senhas

Nunca armazene senhas como texto simples no banco de dados.Nem mesmo que você não se importe com a segurança do seu próprio site.Suponha que alguns de seus usuários reutilizarão a senha de suas contas bancárias online.Portanto, armazene a senha com hash e jogue fora a original.E certifique-se de que a senha não apareça nos logs de acesso ou nos logs de aplicativos.OWASP recomenda o uso de Argon2 como sua primeira escolha para novas aplicações.Se não estiver disponível, PBKDF2 ou scrypt deverá ser usado.E finalmente, se nenhuma das opções acima estiver disponível, use bcrypt.

Hashes por si só também são inseguros.Por exemplo, senhas idênticas significam hashes idênticos – isso torna as tabelas de pesquisa de hash uma forma eficaz de quebrar muitas senhas de uma só vez.Em vez disso, armazene o salgado cerquilha.Um salt é uma string anexada à senha antes do hash - use um salt diferente (aleatório) por usuário.O salt é um valor público, então você pode armazená-lo com o hash no banco de dados.Ver aqui para saber mais sobre isso.

Isso significa que você não pode enviar ao usuário suas senhas esquecidas (porque você só tem o hash).Não redefina a senha do usuário, a menos que você tenha autenticado o usuário (os usuários devem provar que são capazes de ler e-mails enviados para o endereço de e-mail armazenado (e validado).)

Questões de segurança

As perguntas de segurança são inseguras – evite usá-las.Por que?Qualquer coisa que uma pergunta de segurança faça, uma senha faz melhor.Ler PARTE III:Usando perguntas secretas em @Jens Roland responde aqui neste wiki.

Cookies de sessão

Depois que o usuário faz login, o servidor envia ao usuário um cookie de sessão.O servidor pode recuperar o nome de usuário ou id do cookie, mas ninguém mais pode gerar tal cookie (mecanismos de explicação TODO).

Cookies podem ser sequestrados:eles são tão seguros quanto o resto da máquina do cliente e outras comunicações.Eles podem ser lidos do disco, detectados no tráfego de rede, eliminados por um ataque de script entre sites, phishing de um DNS envenenado para que o cliente envie seus cookies para os servidores errados.Não envie cookies persistentes.Os cookies devem expirar ao final da sessão do cliente (fechamento do navegador ou saída do domínio).

Se quiser fazer login automático de seus usuários, você pode definir um cookie persistente, mas ele deve ser diferente de um cookie de sessão completa.Você pode definir um sinalizador adicional de que o usuário efetuou login automaticamente e precisa fazer login de verdade para operações confidenciais.Isso é popular entre sites de compras que desejam fornecer a você uma experiência de compra personalizada e integrada, mas ainda assim proteger seus dados financeiros.Por exemplo, quando você volta a visitar a Amazon, eles mostram uma página que parece que você está logado, mas quando você faz um pedido (ou altera seu endereço de entrega, cartão de crédito etc.), eles pedem que você confirme sua senha.

Os sites financeiros, como bancos e cartões de crédito, por outro lado, possuem apenas dados confidenciais e não devem permitir login automático ou modo de baixa segurança.

Lista de recursos externos

Primeiro, uma forte advertência de que esta resposta não é a mais adequada para esta pergunta exata.Definitivamente não deveria ser a resposta principal!

Irei em frente e mencionarei a proposta da Mozilla ID do navegador (ou talvez mais precisamente, o Protocolo de e-mail verificado) no espírito de encontrar um caminho de atualização para melhores abordagens de autenticação no futuro.

Vou resumir desta forma:

  1. Mozilla é uma organização sem fins lucrativos com valores que se alinham bem com a busca de boas soluções para este problema.
  2. A realidade hoje é que a maioria dos sites usa autenticação baseada em formulário
  3. A autenticação baseada em formulário tem uma grande desvantagem, que é um risco aumentado de phishing.Os usuários são solicitados a inserir informações confidenciais em uma área controlada por uma entidade remota, em vez de em uma área controlada por seu Agente de Usuário (navegador).
  4. Como os navegadores são implicitamente confiáveis ​​(a ideia de um User Agent é agir em nome do usuário), eles podem ajudar a melhorar esta situação.
  5. A principal força que impede o progresso aqui é impasse de implantação.As soluções devem ser decompostas em etapas que proporcionem algum benefício incremental por si só.
  6. O método descentralizado mais simples para expressar uma identidade incorporada à infraestrutura da Internet é o nome de domínio.
  7. Como segundo nível de expressão de identidade, cada domínio gerencia seu próprio conjunto de contas.
  8. O formulário “conta@domínio” é conciso e suportado por uma ampla gama de protocolos e esquemas URI.Esse identificador é, obviamente, mais universalmente reconhecido como um endereço de e-mail.
  9. Os provedores de e-mail já são os principais provedores de identidade online de fato.Os fluxos atuais de redefinição de senha geralmente permitem que você assuma o controle de uma conta se você puder provar que controla o endereço de e-mail associado a essa conta.
  10. O Protocolo de E-mail Verificado foi proposto para fornecer um método seguro, baseado em criptografia de chave pública, para agilizar o processo de provar ao domínio B que você possui uma conta no domínio A.
  11. Para navegadores que não suportam o protocolo de e-mail verificado (atualmente todos eles), a Mozilla fornece um shim que implementa o protocolo no código JavaScript do lado do cliente.
  12. Para serviços de e-mail que não suportam o protocolo de e-mail verificado, o protocolo permite que terceiros atuem como intermediários confiáveis, afirmando que verificaram a propriedade de uma conta por um usuário.Não é desejável ter um grande número desses terceiros;esse recurso destina-se apenas a permitir um caminho de atualização e é muito preferível que os próprios serviços de e-mail forneçam essas afirmações.
  13. A Mozilla oferece seu próprio serviço para agir como um terceiro confiável.Os Provedores de Serviços (isto é, Partes Confiantes) que implementam o Protocolo de E-mail Verificado podem optar por confiar ou não nas afirmações da Mozilla.O serviço da Mozilla verifica a propriedade da conta dos usuários usando os meios convencionais de envio de um e-mail com um link de confirmação.
  14. Os Provedores de Serviços podem, é claro, oferecer este protocolo como uma opção além de qualquer outro(s) método(s) de autenticação que desejem oferecer.
  15. Um grande benefício da interface do usuário buscado aqui é o “seletor de identidade”.Quando um usuário visita um site e opta por se autenticar, seu navegador mostra uma seleção de endereços de e-mail (“pessoal”, “trabalho”, “ativismo político”, etc.) que ele pode usar para se identificar no site.
  16. Outro grande benefício da interface do usuário buscado como parte desse esforço é ajudando o navegador a saber mais sobre a sessão do usuário – com quem eles estão conectados atualmente, principalmente – então pode exibir isso no navegador Chrome.
  17. Devido à natureza distribuída deste sistema, ele evita o aprisionamento a grandes sites como Facebook, Twitter, Google, etc.Qualquer indivíduo pode possuir seu próprio domínio e, portanto, atuar como seu próprio provedor de identidade.

Esta não é estritamente “autenticação baseada em formulário para sites”.Mas é um esforço para fazer a transição da norma atual de autenticação baseada em formulário para algo mais seguro:autenticação suportada pelo navegador.

Pensei em compartilhar esta solução que descobri estar funcionando perfeitamente.

Eu chamo isso de Campo fictício (embora eu não tenha inventado isso, então não me dê crédito).

Resumidamente:você só precisa inserir isso em seu <form> e verifique se está vazio ao validar:

<input type="text" name="email" style="display:none" />

O truque é enganar um bot fazendo-o pensar que precisa inserir dados em um campo obrigatório, por isso chamei a entrada de "e-mail".Se você já possui um campo chamado email que está usando, tente nomear o campo fictício com outro nome, como "empresa", "telefone" ou "endereço de email".Basta escolher algo que você sabe que não precisa e que parece algo que as pessoas normalmente achariam lógico preencher em um formulário da web.Agora esconda o input campo usando CSS ou JavaScript/jQuery - o que for melhor para você - basta não definir a entrada type para hidden ou então o bot não cairá nessa.

Ao validar o formulário (no lado do cliente ou do servidor), verifique se o campo fictício foi preenchido para determinar se foi enviado por um humano ou por um bot.

Exemplo:

No caso de um humano:O usuário não verá o campo fictício (no meu caso denominado "email") e não tentará preenchê-lo.Portanto, o valor do campo fictício ainda deve estar vazio quando o formulário for enviado.

No caso de um bot: O bot verá um campo cujo tipo é text e um nome email (ou como você o chamou) e tentará logicamente preenchê-lo com dados apropriados.Não importa se você estilizou o formulário de entrada com algum CSS sofisticado, os desenvolvedores web fazem isso o tempo todo.Qualquer que seja o valor no campo fictício, não nos importamos, desde que seja maior que 0 personagens.

Usei esse método em um livro de visitas em combinação com CAPTCHA, e não vi uma única postagem de spam desde então.Eu já havia usado uma solução somente CAPTCHA, mas acabou resultando em cerca de cinco postagens de spam a cada hora.Adicionar o campo fictício no formulário impediu (pelo menos até agora) que todo o spam aparecesse.

Acredito que isso também pode ser usado perfeitamente com um formulário de login/autenticação.

Aviso:É claro que este método não é 100% infalível.Os bots podem ser programados para ignorar campos de entrada com o estilo display:none aplicado a ele.Você também deve pensar nas pessoas que usam alguma forma de preenchimento automático (como a maioria dos navegadores tem embutido!) Para preencher automaticamente todos os campos do formulário para eles.Eles poderiam muito bem escolher um campo fictício.

Você também pode variar um pouco, deixando o campo fictício visível, mas fora dos limites da tela, mas isso depende totalmente de você.

Seja criativo!

Não creio que a resposta acima esteja "errada", mas existem grandes áreas de autenticação que não são abordadas (ou melhor, a ênfase está em "como implementar sessões de cookies", e não em "quais opções estão disponíveis e quais são as negociações -desligados".

Minhas edições/respostas sugeridas são

  • O problema está mais na configuração da conta do que na verificação de senha.
  • O uso da autenticação de dois fatores é muito mais seguro do que meios mais inteligentes de criptografia de senha
  • Não tente implementar seu próprio formulário de login ou armazenamento de bancos de dados de senhas, a menos que os dados que estão sendo armazenados não tenham valor na criação de contas e auto-gerados (ou seja, estilo web 2.0 como o Facebook, Flickr, etc.)

    1. A Autenticação Digest é uma abordagem baseada em padrões suportada em todos os principais navegadores e servidores, que não envia uma senha mesmo por um canal seguro.

Isso evita qualquer necessidade de "sessões" ou cookies, pois o próprio navegador criptografará novamente a comunicação a cada vez.É a abordagem de desenvolvimento mais “leve”.

Contudo, não recomendo isto, exceto para serviços públicos e de baixo valor.Este é um problema com algumas das outras respostas acima - não tente reimplementar mecanismos de autenticação do lado do servidor - este problema foi resolvido e é suportado pela maioria dos principais navegadores.Não use cookies.Não armazene nada em seu próprio banco de dados gerado manualmente.Basta perguntar, por solicitação, se a solicitação está autenticada.Todo o resto deve ser suportado por configuração e software confiável de terceiros.

Então ...

Primeiro, estamos confundindo a criação inicial de uma conta (com uma senha) com a nova verificação da senha posteriormente.Se eu for o Flickr e estiver criando seu site pela primeira vez, o novo usuário terá acesso ao valor zero (espaço web em branco).Eu realmente não me importo se a pessoa que cria a conta está mentindo sobre seu nome.Se estou criando uma conta na intranet/extranet do hospital, o valor está em todos os prontuários, então fazer preocupa-se com a identidade (*) do criador da conta.

Esta é a parte muito difícil.O apenas solução decente é uma rede de confiança.Por exemplo, você ingressa no hospital como médico.Você cria uma página da web hospedada em algum lugar com sua foto, seu número de passaporte e uma chave pública, e faz o hash de todos eles com a chave privada.Em seguida, você visita o hospital e o administrador do sistema analisa seu passaporte, verifica se a foto corresponde a você e, em seguida, faz o hash da página da web/hash da foto com a chave privada do hospital.A partir de agora podemos trocar chaves e tokens com segurança.Assim como qualquer pessoa que confia no hospital (aliás, existe o molho secreto).O administrador do sistema também pode fornecer uma RSA dongle ou outra autenticação de dois fatores.

Mas este é um muito de um aborrecimento e não muito web 2.0.No entanto, é a única forma segura de criar novas contas que tenham acesso a informações valiosas que não são criadas por você mesmo.

  1. Kerberos e SPNEGO - mecanismos de logon único com terceiros confiáveis ​​- basicamente o usuário verifica em relação a um terceiro confiável.(NB, isso não é de forma alguma confiável OAuth)

  2. PRS - uma espécie de autenticação de senha inteligente sem terceiros confiáveis.Mas aqui estamos entrando no reino de “é mais seguro usar a autenticação de dois fatores, mesmo que seja mais caro”

  3. SSL lado do cliente - fornece aos clientes um certificado de chave pública (suporte em todos os principais navegadores - mas levanta questões sobre a segurança da máquina cliente).

No final das contas, há uma troca: qual é o custo de uma violação de segurança versus o custo de implementação de abordagens mais seguras.Um dia, poderemos ver um verdadeiro PKI amplamente aceito e, portanto, não há mais formulários e bancos de dados de autenticação próprios.Um dia...

Ao fazer hash, não use algoritmos de hash rápidos, como MD5 (existem muitas implementações de hardware).Use algo como SHA-512.Para senhas, hashes mais lentos são melhores.

Quanto mais rápido você criar hashes, mais rápido qualquer verificador de força bruta poderá funcionar.Hashes mais lentos irão, portanto, desacelerar a força bruta.Um algoritmo de hash lento tornará a força bruta impraticável para senhas mais longas (8 dígitos +)

Um bom artigo sobre estimativa realista da força da senha é:

Blog de tecnologia do Dropbox »Arquivo do blog» zxcvbn:estimativa realista da força da senha

Minha regra favorita em relação aos sistemas de autenticação:use senhas, não senhas.Fácil de lembrar, difícil de decifrar.Mais informações: Codificação de terror:Senhas vs.Frases secretas

Gostaria de acrescentar uma sugestão que usei, baseada na defesa em profundidade.Você não precisa ter o mesmo sistema de autenticação e autenticação para administradores que os usuários normais.Você pode ter um formulário de login separado em um URL separado, executando código separado para solicitações que concederão privilégios elevados.Este pode fazer escolhas que seriam uma dor total para usuários regulares.Um deles que usei foi embaralhar o URL de login para acesso de administrador e enviar por e-mail ao administrador o novo URL.Interrompe qualquer ataque de força bruta imediatamente, pois seu novo URL pode ser arbitrariamente difícil (sequência aleatória muito longa), mas o único inconveniente do usuário administrador é seguir um link em seu e-mail.O invasor não sabe mais para onde fazer o POST.

Não sei se era melhor responder como resposta ou como comentário.Optei pela primeira opção.

Em relação ao poing PARTE IV:Funcionalidade de senha esquecida na primeira resposta, eu destacaria os ataques de temporização.

No Lembre-se da sua senha formulários, um invasor poderia verificar uma lista completa de e-mails e detectar quais estão registrados no sistema (veja o link abaixo).

Em relação ao Formulário de Senha Esquecida, acrescentaria que é uma boa ideia igualar os tempos entre consultas bem-sucedidas e malsucedidas com alguma função de atraso.

https://crypto.stanford.edu/~dabo/papers/webtiming.pdf

Gostaria de acrescentar um comentário muito importante:-

  • "Em um corporativo, intra- net setting", a maioria, se não todos os itens acima, podem não se aplicar!

Muitas empresas implantam sites “somente para uso interno” que são, na verdade, “aplicativos corporativos” que foram implementados por meio de URLs.Esses URLs podem (supostamente...) só serão resolvidos dentro da “rede interna da empresa”. (Qual rede inclui magicamente todos os 'guerreiros da estrada' conectados por VPN.)

Quando um usuário está devidamente conectado à rede acima mencionada, sua identidade ("autenticação") é [já...] "conclusivamente conhecido", assim como sua permissão ("autorização") fazer certas coisas...como ..."para acessar este site."

Este serviço de “autenticação + autorização” pode ser fornecido por diversas tecnologias diferentes, como LDAP (Microsoft OpenDirectory), ou Kerberos.

Do seu ponto de vista, você simplesmente sabe disso:que qualquer um quem legitimamente acessa seu site deve ser acompanhado por [um ambiente que contém magicamente ...] um "token". (ou seja A ausência de tal token deve ser motivo imediato para 404 Not Found.)

O valor do token não faz sentido para você, mas, caso seja necessário, "existem meios apropriados" pelos quais o seu site pode "[com autoridade] perguntar a alguém que conhece (LDAP...etc.)" sobre qualquer e cada (!) dúvida que você possa ter.Em outras palavras, você faz não aproveite-se qualquer "Lógica caseira". Em vez disso, você pergunta a autoridade e confia implicitamente em seu veredicto.

Uh, hein...isso é bastante uma mudança mental da "Internet selvagem e confusa".

Usar Conexão OpenID ou Acesso gerenciado pelo usuário.

Porque nada é mais eficiente do que não fazer nada.

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top