Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Klarna not always returns idToken in klarna event handler after successfull Klarna sign in #15

Open
mAdutskevich opened this issue Jan 20, 2025 · 2 comments

Comments

@mAdutskevich
Copy link

mAdutskevich commented Jan 20, 2025

Klarna event handler doesn't always return idToken after pressing custom Klarna button on Android in v2.6.24, 2.6.25.
Sometimes it returns KlarnaSignInToken with the idToken in params, sometimes KlarnaSignInUserAuth with empty params object, and sometimes KlarnaSignInUserCancelled.

Quite often the event KlarnaSignInToken(with idToken) goes right after KlarnaSignInUserAuth and It is possible to get the idToken, but sometimes the event KlarnaSignInToken is absent(only KlarnaSignInUserAuth appears) and I can't get the idToken. It works in absolutely another way in iOS which always return klarnaToken event with idToken.

val eventHandler = object : KlarnaEventHandler {
    override fun onEvent(klarnaComponent: KlarnaComponent, event: KlarnaProductEvent) {
        Log.d("Test", event.toString())
    }
}

It looks very unstable.
How to always get the id token after succesfull sign in?

Platform: Android
Evnvironments: playground, production
Sdk versions: 2.6.24, 2.6.25

@mAdutskevich mAdutskevich changed the title Klarna not always returns idToken in klarna event handler Klarna not always returns idToken in klarna event handler after successfull Klarna sign in Jan 20, 2025
@NMGuner
Copy link
Member

NMGuner commented Jan 20, 2025

Hi @mAdutskevich, all sign-in flows will lead to SDK sending you the tokens via the SIGN_IN_TOKEN event, although the scenario of when this doesn't happen in your case is unclear at the moment. I assume it can due to several reasons including errors, network or user delays etc. hence what I would suggest you to implement event handling based on "action" as documented here. Also consider any errors sent from the SDK, as some of the errors (any fatal one) would also prevent SDK from completing the happy path for successful sign in or would give you another indicator of what has happened in the sign-in process.

If these actions and errors does not help you, please provide local logs(SDK logging level configuration) or session IDs with us, and we will be able to help you with analyzing those and the logs we have on our side for the session.

@mikeAdutskevich
Copy link

mikeAdutskevich commented Jan 21, 2025

Hi @NMGuner,

I checked the explicit errors in my code by try/catch, but haven't catched any.
Network delays seems to be low probable and since the first sign-in flow with filling all the necessary inputs is working I excluded the network from the suspects.
User delay - don't actually understand how to check it, could you provide more details?

This is my code for android module

package expo.modules.klarnaauth

import android.util.Log
import expo.modules.kotlin.modules.Module
import expo.modules.kotlin.modules.ModuleDefinition

import com.klarna.mobile.sdk.api.KlarnaRegion
import com.klarna.mobile.sdk.KlarnaMobileSDKError
import com.klarna.mobile.sdk.api.KlarnaEnvironment
import com.klarna.mobile.sdk.api.KlarnaProductEvent
import com.klarna.mobile.sdk.api.KlarnaEventHandler
import com.klarna.mobile.sdk.api.KlarnaLoggingLevel
import com.klarna.mobile.sdk.api.signin.KlarnaSignInSDK
import com.klarna.mobile.sdk.api.signin.KlarnaSignInEvent
import com.klarna.mobile.sdk.api.component.KlarnaComponent
import com.klarna.mobile.sdk.api.signin.model.KlarnaSignInToken

class ExpoKlarnaAuthModule : Module() {
    override fun definition() = ModuleDefinition {
        Name("ExpoKlarnaAuth")

        Events("onChange")

        Function("klarnaSignIn") {
                returnURL: String,
                clientId: String,
                scope: String,
                market: String,
                klarnaEnv: String,
                region: String?,
                locale: String?,
            ->
            klarnaSignIn(
                returnURL,
                clientId,
                scope,
                market,
                klarnaEnv,
                region,
                locale,
            )
        }

        View(ExpoKlarnaAuthView::class) {}
    }

    private fun klarnaSignIn(
        returnURL: String,
        clientId: String,
        scope: String,
        market: String,
        klarnaEnv: String,
        region: String?,
        locale: String?,
    ) {
        val activity = appContext.currentActivity

        if (activity == null) {
            sendErrorEvent("NO_ACTIVITY")

            return
        }

        val eventHandler = object : KlarnaEventHandler {
            override fun onEvent(klarnaComponent: KlarnaComponent, event: KlarnaProductEvent) {
                Log.d("KlarnaMobileSDKCustom1", event.toString())

                when (event.action) {
                    KlarnaSignInEvent.SIGN_IN_TOKEN -> sendTokenEvent(event)
                    KlarnaSignInEvent.USER_CANCELLED -> sendErrorEvent(KlarnaSignInEvent.USER_CANCELLED)

                    else -> {
                        sendSuccessEvent(event.action)
                    }
                }
            }

            override fun onError(klarnaComponent: KlarnaComponent, error: KlarnaMobileSDKError) {
                Log.d("KlarnaMobileSDKCustom3", error.toString())
                sendErrorEvent(error.name)
            }
        }

         activity.runOnUiThread {
            try {
                val klarnaSignInSDK = KlarnaSignInSDK(
                    activity,
                    returnURL,
                    eventHandler,
                    getKlarnaEnvironment(klarnaEnv),
                    getKlarnaRegion(region),
                    null,
                    null,
                    KlarnaLoggingLevel.Verbose
                )

                klarnaSignInSDK.signIn(clientId, scope, market, locale)
            } catch (e: Exception) {
                sendErrorEvent("UNEXPECTED_ERROR")
            }
        }
    }

    private fun sendErrorEvent(message: String) {
        sendEvent("onChange", mapOf("status" to "ERROR", "message" to message))
    }

    private fun sendSuccessEvent(message: String) {
        sendEvent("onChange", mapOf("status" to "SUCCESS", "message" to message))
    }

    private fun sendTokenEvent(event: KlarnaProductEvent) {
        val token = event.params[KlarnaSignInEvent.ParamKey.KlarnaSignInToken] as? KlarnaSignInToken
        Log.d("KlarnaMobileSDKCustom2", token?.idToken.toString())

        try {
            sendEvent("onChange", mapOf(
                "status" to "SUCCESS",
                "message" to event.action,
                "accessToken" to token?.accessToken,
                "idToken" to token?.idToken,
                "refreshToken" to token?.refreshToken,
                "scope" to token?.scope,
                "tokenType" to token?.tokenType,
                "expiresIn" to token?.expiresIn
            ))
        } catch (e: Exception) {
            Log.d("KlarnaMobileSDKCustom4", "UNEXPECTED_ERROR")
            sendErrorEvent("UNEXPECTED_ERROR")
        }
    }

    private fun getKlarnaEnvironment(env: String): KlarnaEnvironment {
        return when (env.uppercase()) {
            "DEMO" -> KlarnaEnvironment.DEMO
            "PLAYGROUND" -> KlarnaEnvironment.PLAYGROUND
            "PRODUCTION" -> KlarnaEnvironment.PRODUCTION
            "STAGING" -> KlarnaEnvironment.STAGING
            else -> KlarnaEnvironment.getDefault()
        }
    }

    private fun getKlarnaRegion(region: String?): KlarnaRegion? {
        return when (region?.uppercase()) {
            "EU" -> KlarnaRegion.EU
            "NA" -> KlarnaRegion.NA
            "OC" -> KlarnaRegion.OC
            else -> null
        }
    }
}

This is logs from klarnaSignInSDK:

Pixel-6a-API-32-Android-12_2025-01-21_140841.txt
Pixel-6a-API-32-Android-12_2025-01-21_140745.txt

Will appreciate any help here

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants