Se você tiver atualizado para o Firebase Authentication com Identity Platform, poderá adicionar a autenticação multifator por SMS ao seu aplicativo Flutter.
A autenticação multifator (MFA) aumenta a segurança do seu aplicativo. Embora os invasores frequentemente comprometam senhas e contas sociais, interceptar uma mensagem de texto é mais difícil.
Antes de você começar
Habilite pelo menos um provedor que ofereça suporte à autenticação multifator. Todos os provedores oferecem suporte a MFA, exceto autenticação por telefone, autenticação anônima e Apple Game Center.
Certifique-se de que seu aplicativo esteja verificando os e-mails dos usuários. A MFA requer verificação de e-mail. Isso evita que atores mal-intencionados se registrem em um serviço com um e-mail que não sejam de sua propriedade e, em seguida, bloqueiem o proprietário real adicionando um segundo fator.
Android : se você ainda não definiu o hash SHA-256 do seu aplicativo no console do Firebase , faça-o. Consulte Autenticando seu cliente para obter informações sobre como encontrar o hash SHA-256 do seu aplicativo.
iOS : no Xcode, habilite notificações push para seu projeto e certifique-se de que sua chave de autenticação de APNs esteja configurada com Firebase Cloud Messaging (FCM) . Além disso, você deve ativar os modos de segundo plano para notificações remotas. Para ver uma explicação detalhada desta etapa, consulte a documentação do Firebase iOS Phone Auth .
Web : verifique se você adicionou o domínio de seus aplicativos no console do Firebase , em Domínios de redirecionamento OAuth .
Habilitando a autenticação multifator
Abra a página Autenticação > Método de login do console do Firebase.
Na seção Avançado , habilite a autenticação multifator de SMS .
Você também deve inserir os números de telefone com os quais testará seu aplicativo. Embora opcional, é altamente recomendável registrar números de telefone de teste para evitar limitações durante o desenvolvimento.
Se você ainda não autorizou o domínio do seu aplicativo, adicione-o à lista de permissões na página Autenticação > Configurações do console do Firebase.
Escolhendo um padrão de inscrição
Você pode escolher se seu aplicativo requer autenticação multifator e como e quando inscrever seus usuários. Alguns padrões comuns incluem:
Inscreva o segundo fator do usuário como parte do registro. Use este método se seu aplicativo exigir autenticação multifator para todos os usuários.
Ofereça uma opção ignorável para inscrever um segundo fator durante o registro. Os aplicativos que desejam incentivar, mas não exigem, a autenticação multifator podem preferir essa abordagem.
Forneça a capacidade de adicionar um segundo fator na conta do usuário ou na página de gerenciamento de perfil, em vez da tela de inscrição. Isso minimiza o atrito durante o processo de registro, ao mesmo tempo que disponibiliza a autenticação multifator para usuários sensíveis à segurança.
Exigir a adição incremental de um segundo fator quando o usuário desejar acessar recursos com maiores requisitos de segurança.
Inscrevendo um segundo fator
Para inscrever um novo fator secundário para um usuário:
Autentique novamente o usuário.
Peça ao usuário que insira seu número de telefone.
Obtenha uma sessão multifatorial para o usuário:
final multiFactorSession = await user.multiFactor.getSession();
Verifique o número de telefone com uma sessão multifatorial e seus retornos de chamada:
await FirebaseAuth.instance.verifyPhoneNumber( multiFactorSession: multiFactorSession, phoneNumber: phoneNumber, verificationCompleted: (_) {}, verificationFailed: (_) {}, codeSent: (String verificationId, int? resendToken) async { // The SMS verification code has been sent to the provided phone number. // ... }, codeAutoRetrievalTimeout: (_) {}, );
Assim que o código SMS for enviado, peça ao usuário para verificar o código:
final credential = PhoneAuthProvider.credential( verificationId: verificationId, smsCode: smsCode, );
Conclua a inscrição:
await user.multiFactor.enroll( PhoneMultiFactorGenerator.getAssertion( credential, ), );
O código abaixo mostra um exemplo completo de inscrição de um segundo fator:
final session = await user.multiFactor.getSession();
final auth = FirebaseAuth.instance;
await auth.verifyPhoneNumber(
multiFactorSession: session,
phoneNumber: phoneController.text,
verificationCompleted: (_) {},
verificationFailed: (_) {},
codeSent: (String verificationId, int? resendToken) async {
// See `firebase_auth` example app for a method of retrieving user's sms code:
// https://github.com/firebase/flutterfire/blob/master/packages/firebase_auth/firebase_auth/example/lib/auth.dart#L591
final smsCode = await getSmsCodeFromUser(context);
if (smsCode != null) {
// Create a PhoneAuthCredential with the code
final credential = PhoneAuthProvider.credential(
verificationId: verificationId,
smsCode: smsCode,
);
try {
await user.multiFactor.enroll(
PhoneMultiFactorGenerator.getAssertion(
credential,
),
);
} on FirebaseAuthException catch (e) {
print(e.message);
}
}
},
codeAutoRetrievalTimeout: (_) {},
);
Parabéns! Você registrou com êxito um segundo fator de autenticação para um usuário.
Conectando usuários com um segundo fator
Para fazer login em um usuário com verificação SMS de dois fatores:
Faça login do usuário com seu primeiro fator e, em seguida, capture a exceção
FirebaseAuthMultiFactorException
. Este erro contém um resolvedor, que pode ser usado para obter os segundos fatores registrados do usuário. Ele também contém uma sessão subjacente que prova que o usuário foi autenticado com sucesso com seu primeiro fator.Por exemplo, se o primeiro fator do usuário for email e senha:
try { await _auth.signInWithEmailAndPassword( email: emailController.text, password: passwordController.text, ); // User is not enrolled with a second factor and is successfully // signed in. // ... } on FirebaseAuthMultiFactorException catch (e) { // The user is a multi-factor user. Second factor challenge is required final resolver = e.resolver // ... }
Se o usuário tiver vários fatores secundários inscritos, pergunte qual deles usar:
final session = e.resolver.session; final hint = e.resolver.hints[selectedHint];
Envie uma mensagem de verificação para o telefone do usuário com a dica e a sessão multifatorial:
await FirebaseAuth.instance.verifyPhoneNumber( multiFactorSession: session, multiFactorInfo: hint, verificationCompleted: (_) {}, verificationFailed: (_) {}, codeSent: (String verificationId, int? resendToken) async { // ... }, codeAutoRetrievalTimeout: (_) {}, );
Chame
resolver.resolveSignIn()
para concluir a autenticação secundária:final smsCode = await getSmsCodeFromUser(context); if (smsCode != null) { // Create a PhoneAuthCredential with the code final credential = PhoneAuthProvider.credential( verificationId: verificationId, smsCode: smsCode, ); try { await e.resolver.resolveSignIn( PhoneMultiFactorGenerator.getAssertion(credential) ); } on FirebaseAuthException catch (e) { print(e.message); } }
O código abaixo mostra um exemplo completo de login de um usuário multifator:
try {
await _auth.signInWithEmailAndPassword(
email: emailController.text,
password: passwordController.text,
);
} on FirebaseAuthMultiFactorException catch (e) {
setState(() {
error = '${e.message}';
});
final firstHint = e.resolver.hints.first;
if (firstHint is! PhoneMultiFactorInfo) {
return;
}
await FirebaseAuth.instance.verifyPhoneNumber(
multiFactorSession: e.resolver.session,
multiFactorInfo: firstHint,
verificationCompleted: (_) {},
verificationFailed: (_) {},
codeSent: (String verificationId, int? resendToken) async {
// See `firebase_auth` example app for a method of retrieving user's sms code:
// https://github.com/firebase/flutterfire/blob/master/packages/firebase_auth/firebase_auth/example/lib/auth.dart#L591
final smsCode = await getSmsCodeFromUser(context);
if (smsCode != null) {
// Create a PhoneAuthCredential with the code
final credential = PhoneAuthProvider.credential(
verificationId: verificationId,
smsCode: smsCode,
);
try {
await e.resolver.resolveSignIn(
PhoneMultiFactorGenerator.getAssertion(
credential,
),
);
} on FirebaseAuthException catch (e) {
print(e.message);
}
}
},
codeAutoRetrievalTimeout: (_) {},
);
} catch (e) {
...
}
Parabéns! Você fez login com êxito em um usuário usando autenticação multifator.
Qual é o próximo
- Gerencie usuários multifatoriais de maneira programática com o Admin SDK.