重新验证由Firebase Admin SDK创建的用户。

huangapple go评论69阅读模式
英文:

How do I re authenticate a user created by firebase admin sdk

问题

I've moved all my user creation and authentication to Firebase using the admin SDK and google identity provider. I can create a user fine, and I'm adding a password (also still my code for creating a password is in there, I can't figure out how to reauthenticate a user. I've seen some answers to use EmailAuthProvider, however that class doesn't exist. My create user code

fun createUser(request: HttpServletRequest?, response: HttpServletResponse?, createUserRequest: CreateUserRequest): User {

    val hashedPassword = PasswordUtil.hashPassword(createUserRequest.password.trim())

    val user: User = Mapper.convert(createUserRequest)
    val trimmedEmail = user.email.trim()
    user.email = trimmedEmail

    usersRepo.save(user)

    CoroutineScope(Dispatchers.IO).launch {
        FirestoreClient.getFirestore().collection("users").document(user.id.toString()).set(user)
    }

    val auth = FirebaseAuth.getInstance()

    val request = CreateRequest()
        .setUid(user.id.toString())
        .setDisplayName(user.username)
        .setEmailVerified(false)
        .setEmail(user.email)
        .setPassword(createUserRequest.password)

    auth.createUser(request)

    val password = Password()
    password.password = hashedPassword
    password.user = user
    passwordsRepo.save(password)

    CoroutineScope(Dispatchers.IO).launch {
        try {
            marketplace.generateUsersWallets(user)
        } catch (e: Exception) {
            e.printStackTrace()
        }
    }

    val link = FirebaseAuth.getInstance().generateEmailVerificationLink(user.email)
    awsSesService.sendEmailVerification(user.email, link)

    return user
}

The packages I'm using are

 //firebase
implementation("com.google.firebase:firebase-admin:9.1.1")
// Import the BoM for the Firebase platform
implementation(platform("com.google.firebase:firebase-bom:30.4.1"))

implementation("com.google.firebase:firebase-firestore-ktx")

FirebaseAuth works fine for sign up, but how do I log them back in?
thanks

英文:

I've moved all my user creation and authentication to Firebase using the admin SDK and google identity provider. I can create a user fine, and I'm adding a password (also still my code for creating a password is in there, I can't figure out how to re authenticate a user. I've seen some answers to use EmailAuthProvider, however that class doesn't exist. My create user code

fun createUser(request: HttpServletRequest?, response: HttpServletResponse?, createUserRequest: CreateUserRequest): User {

        val hashedPassword = PasswordUtil.hashPassword(createUserRequest.password.trim())

        val user: User = Mapper.convert(createUserRequest)
        val trimmedEmail = user.email.trim()
        user.email = trimmedEmail

        usersRepo.save(user)

        CoroutineScope(Dispatchers.IO).launch {
            FirestoreClient.getFirestore().collection("users").document(user.id.toString()).set(user)
        }

        val auth = FirebaseAuth.getInstance()

        val request = CreateRequest()
            .setUid(user.id.toString())
            .setDisplayName(user.username)
            .setEmailVerified(false)
            .setEmail(user.email)
            .setPassword(createUserRequest.password)

        auth.createUser(request)

        val password = Password()
        password.password = hashedPassword
        password.user = user
        passwordsRepo.save(password)

        CoroutineScope(Dispatchers.IO).launch {
            try {
                marketplace.generateUsersWallets(user)
            } catch (e: Exception) {
                e.printStackTrace()
            }
        }

        val link = FirebaseAuth.getInstance().generateEmailVerificationLink(user.email)
        awsSesService.sendEmailVerification(user.email, link)

        return user
    }

The packages I'm using are

 //firebase
    implementation("com.google.firebase:firebase-admin:9.1.1")
    // Import the BoM for the Firebase platform
    implementation(platform("com.google.firebase:firebase-bom:30.4.1"))

    implementation("com.google.firebase:firebase-firestore-ktx")

FirebaseAuth works fine for sign up, but how do I log them back in?
thanks

答案1

得分: 1

Here is the translated code without the comments:

@Throws(IllegalArgumentException::class, FirebaseAuthException::class)
fun login(request: HttpServletRequest, response: HttpServletResponse, loginUserRequest: LoginUserRequest): User? = runBlocking {
    val userRecord = FirebaseAuth.getInstance().getUserByEmail(loginUserRequest.email)

    if (userRecord != null) {
        val user = usersRepo.findUserById(userRecord.uid.toUUID())

        if (user != null) {
            try {
                googleIdentityService.apiClient.signInWithEmailAndPassword(SignInRequest(userRecord.email.toString(), loginUserRequest.password))

                val customToken = FirebaseAuth.getInstance().createCustomToken(user.id.toString())
                response.setHeader("JWT", customToken)

                return@runBlocking user
            } catch (e: Exception) {
                e.printStackTrace()
            }
        }
    }
    throw ResponseStatusException(HttpStatus.NOT_FOUND, "invalid email or password")
}

Please note that the code has been translated, and any variable or class names remain in their original form.

英文:

Working code, only part missing is making the REST api call which you can do any, point should be clear though

 /**
 * Logs in a user if the password hash is equal
 */
@Throws(IllegalArgumentException::class, FirebaseAuthException::class)
fun login(request: HttpServletRequest, response: HttpServletResponse, loginUserRequest: LoginUserRequest): User? = runBlocking {

    //find the user in google
    val userRecord = FirebaseAuth.getInstance().getUserByEmail(loginUserRequest.email)

    if (userRecord != null) {
        //find the user by our UUID
        val user = usersRepo.findUserById(userRecord.uid.toUUID())

        if (user != null) { //log them in

            try {

                googleIdentityService.apiClient.signInWithEmailAndPassword(SignInRequest(userRecord.email.toString(), loginUserRequest.password))

                val customToken = FirebaseAuth.getInstance().createCustomToken(user.id.toString())
                response.setHeader("JWT", customToken)

                return@runBlocking user

            } catch (e: Exception) {
                e.printStackTrace()
            }
        }
    }
    throw ResponseStatusException(HttpStatus.NOT_FOUND, "invalid email or password")
}

答案2

得分: 0

我基本上找到了答案,我不知道为什么谷歌将这个信息隐藏起来。基本上,管理 SDK 无法进行身份验证,但是 Google 身份 REST API 可以。
https://cloud.google.com/identity-platform/docs/use-rest-api#section-sign-in-email-password

现在奇怪的是,没有办法像 Firebase SDK 中那样登录并获得自定义的 JWT 令牌,而是会得到一个包含 IdToken 和刷新令牌的有效负载。现在,由于自定义令牌的整个目的是让客户端使用它们进行登录,然后发送 Id 令牌,所以你必须进行两次循环,首先使用电子邮件/密码登录,然后如果成功,创建一个新的自定义令牌。完成后,我会发布完整的代码。

英文:

Well I basically found the answer, I have no idea why google has this buried away. Basically the admin sdk's can't authenticate, however the google identity rest api can.
https://cloud.google.com/identity-platform/docs/use-rest-api#section-sign-in-email-password

Now the weird part is there isn't a way to sign in and get a custom JWT token back as you would in the firebase SDK, instead you get a payload with an IdToken and Refresh token. Now since the whole point of custom tokens is for clients to sign in with them and then send the id token you kind of have to make two loops, sign in with email/password, then if that passes create a new custom token. Ill post finished code when completed

huangapple
  • 本文由 发表于 2023年4月17日 20:45:28
  • 转载请务必保留本文链接:https://go.coder-hub.com/76035301.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定