Sign in with Klarna integration

Integrate Sign in with Klarna to enable secure authentication on your website.

Offer Sign in with Klarna by displaying the Klarna “Sign in with Klarna” button wherever you want users to log in or register. Consumers simply click the button to authenticate via Klarna, granting permission to share selected profile data (e.g. name, email, billing address, shipping address) so they can create or sign in to your site in a single step.

Registration banners and modalsSign-in processRegistration at Checkout

Before you integrate Sign in with Klarna, check that you meet the following prerequisites:

  1. Ensure you have already integrated a Klarna payment solution into your checkout.
  2. Confirm you have access to the Klarna Portal.
  3. Make sure you have completed all the necessary steps in the Sign in with Klarna app.
  4. Verify that you have a valid client identifier, based on your client type.
  5. Confirm you have an active API key.
  6. Add Terms and Conditions for web SDK.

If you’ve previously generated a client identifier for your store, you can use it to build your Sign in with Klarna integration.

For a comprehensive, step-by-step walkthrough of these prerequisites, refer to the detailed integration guide.

sequenceDiagram autonumber participant C as Customer participant P as Partner participant K as Klarna P->>K: Integrate with SIWK through Web SDK K->>P: Render SIWK Button C->>K: Click on SIWK Button K->>K: Open popup OR redirect to login page K->>C: Login Page C->>K: Login to Klarna<br>Klarna user account K->>K: Flow completed with success or failure alt if flow is opened in redirect mode K->>P: Redirect to partner's redirect_url Note over K,P: Partner's redirect page will need to have the<br>Web SDK integrated to handle the callback K->>K: Klarna SDK handles the redirect back end alt if login is successful K->>P: trigger `klarna.Identity.on("signin")` callback with tokens else if login is not successful K->>P: trigger `klarna.Identity.on("error")` callback with error end

The simplest and fastest way to start using Sign in with Klarna is to use the minimal template below.

This guide applies to the PUBLIC client type. If your client is set to CONFIDENTIAL, please refer to the next section.
Basic example: Assume that you are serving these 2 files from your web server.

You would need to also obtain the `CLIENT_SECRET`.

After obtaining the code response, pass it to your server to perform the token exchange. Here’s a JavaScript snippet demonstrating how to send a request to the token endpoint for the exchange:

JAVASCRIPT
// An example of the request to exchange for the token.

const { URLSearchParams } = require('url');
const fetch = require('node-fetch');
const encodedParams = new URLSearchParams();

encodedParams.set('grant_type', 'authorization_code');
encodedParams.set('client_id', '[YOUR CLIENT ID]');
encodedParams.set('client_secret', '[YOUR API KEY]');
encodedParams.set('code', 'krn:login:eu1:code:eed137f6-8f06-4791-8180-576a89e....');

Sign in with Klarna ideally will start in a Popup window to avoid users leaving the merchant's website. However, due to various reasons popup window can be blocked. Thus, having a redirect callback page is REQUIRED to allow users to continue their sign in flow in case their popup is blocked. You can use the callback.html template provided in the example above.

To successfully implement the REDIRECT mode, below prerequisites must be met:

  • The redirect URL must match exactly with one of the URLs whitelisted for your client.
  • The redirect URL must be either passed to the button method with the redirectUri property or klarna-identity-button element with data-redirect-uri attribute.
  • The redirect URL page must contain the Web SDK and event handler for signin must be registered.

The Sign in with Klarna flow can be initiated in two main modes: DEVICE_BEST or REDIRECT.

DEVICE_BEST (default)

DEVICE_BEST allows Web SDK to automatically decide the most suitable mode, based on user's device configurations. For instance, Web SDK may opt for a REDIRECT if popup blockers are enabled or the page is loaded in an web frame.

By default, DEVICE_BEST mode starts the flow in a popup window for web browsers. This is ideal for merchants who don't want their customers to leave their website. However, if the popup is blocked, Web SDK will switch to REDIRECT mode and the user will be redirected to the login page on the current tab.

REDIRECT

REDIRECT mode redirects the user to the login page on the current tab. However, user will be redirected back to the merchant's redirect callback page at the end of the sign in flow with Authorization tokens or OAuth2Error parameters.

Please note that you can also just load the Web SDK script without the dataset attributes and use the init method to initialise the Web SDK.

JAVASCRIPT
<script type="module">
    const { KlarnaSDK } = await import("https://js.klarna.com/web-sdk/v2/klarna.mjs");
    const klarna = await KlarnaSDK({
        clientId: "[YOUR CLIENT ID]",
    });
</script>

After initialising the Web SDK, all Sign in with Klarna related API can be found under the Identity namespace.

See all details on WebSDK specifications

Web SDK provides a flexible API that allows merchants to integrate Sign in with Klarna based on their preference.

Web SDK provides a default button that has all functionalities built-in and styled based on official Klarna design guidelines.

1.1. Using element

Web SDK registers a custom web component klarna-identity-button, that renders the Sign in with Klarna button where it is mounted.

MARKUP
<klarna-identity-button
  id="klarna-identity-button"
  data-scope="openid offline_access payment:request:create profile:name"
  data-redirect-uri="http://localhost:3000/callback.html"
  data-locale="en-GB"
  ></klarna-identity-button>

1.2. Creating the button programmatically

Web SDK provides the button method that allows to create and mount the Sign in with Klarna button programmatically.

JAVASCRIPT
const siwkButton = klarna.Identity.button({
    id: "klarna-identity-button",
    scope: "openid offline_access payment:request:create profile:name",
    redirectUri: "http://localhost:3000/callback.html",
    locale: "en-GB"
});

siwkButton.mount("#button-container");

If the button method is called more than once with the configuration object, it will create multiple button instances. If you do not need more than one button, please make sure the button method is only called once.

If you do need multiple buttons make sure you provide an id attribute to each button instance.

You can provide a string button id to the button method, to retrieve an existing button instance. For more information, see the Identity API Overview > Type Definitions.

If a merchant wants to use a custom button matching with Klarna's but also with their own design guidelines, they can use the attach method that is provided by Web SDK. The attach method will register the necessary event handlers to start the sign in flow.

Please refer to our Custom button article for essential design considerations.

JAVASCRIPT
const siwkButton = klarna.Identity.button({
    id: "klarna-identity-button",
    scope: "openid offline_access payment:request:create profile:name",
    redirectUri: "http://localhost:3000/callback.html",
    locale: "en-GB"
});

// notice, we are using the `attach` method
// and providing a button id instead of a container id
siwkButton.attach("#merchants-custom-button-id");

Web SDK Identity API can emit two events: signin and error which can be handled as below:

JAVASCRIPT
// 1. Listen for `signin` event to receive signin response object
klarna.Identity.on("signin", async (signinResponse) => {
    console.log(signinResponse);
});

// 2. Listen for `error` event to handle error object
klarna.Identity.on("error", async (error) => {
    console.log(error);
});

Sign in with Klarna buttons can emit two events: ready and click.

JAVASCRIPT
// Please notice that we can retrieve the button instance,
// by providing the button instance id to the button method
const siwkButton = klarna.Identity.button("klarna-identity-button");

siwkButton.on('ready', async () => {
    // handle ready event
})

siwkButton.on('click', async () => {
    // handle click event

The table below lists the available scopes and how they correspond to claims and permissions.

ScopeClaimsTypeCan be toggled off
profile:namegiven_namestringNo
profile:namefamily_namestringNo
profile:emailemailstring (Email)No
profile:emailemail_verifiedboolean
No
profile:phonephonestring (E. 164)No
profile:phonephone_verifiedboolean
No
profile:date_of_birthdate_of_birthstring (ISO 8601)Yes
profile:billing_addressstreet_addressstringYes
profile:billing_addressstreet_address2string
Yes
profile:billing_addresspostal_codestring
Yes
profile:billing_addresscitystring
Yes
profile:billing_addressregionstring
Yes
profile:billing_addresscountrystring (ISO 3166-1 alpha-2)
Yes
profile:shipping_addressstreet_addressstringYes
profile:shipping_addressstreet_address2stringYes
profile:shipping_addresspostal_codestringYes
profile:shipping_addresscitystringYes
profile:shipping_addressregionstringYes
profile:shipping_addresscountrystring (ISO 3166-1 alpha-2)Yes
profile:national_idnational_idstringYes
profile:countrycountrystring (ISO 3166-1 alpha-2)Yes
profile:localelocalestring (ISO 3166)Yes

Remember to always add 'openid', 'offline_access' and 'customer:login' scopes to receive full functionality of Sign in with Klarna.

The mock-ups below show how users will see required versus optional scopes when entering the Sign in with Klarna flow.

Required scopes in Sign in with KlarnaOptional scopes in Sign in with Klarna

Before using data from the id_token, it needs to be validated. More about it under Token Validation.

Upon completing the sign-in process, utilise a specific claim (such as phone, email, or national identification number for Sweden) as a unique customer identifier.

Make sure you are handling the following scenarios to ensure seamless integration:

  • New Users: If the identifier does not match any existing user in your database, check if the consumer consented to share all the data you requested. If additional information is required, remember to show your onboarding UI after Sign in with Klarna flow. Once onboarding is complete, create a new user account using the data returned from Klarna and store the user_account_linking_refresh_token within that record.
  • Existing Klarna Users: In cases where the identifier is already linked to a Klarna account, Sign in with Klarna always returns fresh customer data. Update your user record with this data to ensure that the information in your database remains current.
  • Existing Users: For users already in your database but not connected to Klarna, consider these approaches:
Account MergingUser Confirmation for Merging
Merge the account automatically, add customer data from Klarna that was missing in the existing record and save the user_account_linking_refresh_token in itPrompt the user to confirm if they wish to merge their existing account. If yes, follow Account Merging above. If not, ask them to login with a different Klarna account

By carefully managing these scenarios, you can provide a fluid and integrated user experience, leveraging the comprehensive data and functionality offered through the Sign in with Klarna.

To receive a new set of tokens, perform a token exchange through a POST request to the token endpoint. Remember to always save the new refresh_token in the database, since the old one will be invalid.
Access tokens are opaque - they are random strings that you cannot decode. Validation should only be performed on the id_token. You do not have to validate the access token before using it.

JAVASCRIPT
const data = new URLSearchParams();

data.append("refresh_token", "<your refresh token>");
data.append("client_id", "<your client id>");
data.append("grant_type", "refresh_token");

fetch("https://login.klarna.com/eu/lp/idp/oauth2/token", {
  method: "POST",
  headers: {

At any point of time you can request the latest user data using the /userinfo endpoint. It requires a valid access_token as authorization and returns the same data structure as you can find in the id_token. Remember to get the fresh access_token, described in step 5. Integrate in purchase flow, using /userinfo. Using a new access_token in the /userinfo ensures you get the most up to date information we have for the customer without requiring them to re-login.

JAVASCRIPT
fetch("https://login.klarna.com/eu/lp/idp/userinfo", {
  headers: {
    Authorization: "Bearer <access token>",
  }
})

Validate id_token: validating an OAuth 2.0 token using a JWKS (JSON Web Key Set) endpoint, such as the one provided by Klarna, involves several steps. Here's an outline of how you might proceed:

  • Retrieve JWKS - Make a HTTP GET request to the JWKS endpoint to retrieve the public keys. The response should be a JSON object containing a keys array.
  • Parse JWKS - parse the JSON response to extract the keys, which will be in JWK (JSON Web Key) format.
  • Decode access token - decode the access token to obtain the header, which contains the Key ID or kid, which identifies the key within the JWKS that was used to sign the token.
  • Find the signing key - use the kid from the token's header to find the corresponding key in JWKS.
  • Verify signature - use the public key to verify the signature of the access_token. This usually requires using a library that supports JWT and the necessary cryptographic algorithms.
  • Check claims - if the signature is valid, check the claims in the verified token to ensure they meet your requirements. Make sure to verify expiration time, audience, issuer and the signing algorithm.

Node sample implementation

JAVASCRIPT
const jwt = require('jsonwebtoken');

const jwkToPem = require('jwk-to-pem');
async function verifyTokenWithJWKS(token, jwksUri) {
  try {
    // Decode the token header without verification
    const { header } = jwt.decode(token, { complete: true });
    if (!header || !header.kid) {
      throw new Error('Invalid token header');
    }

In case the customer already has an account with you, based on a an identifier match, such as email or mobile number, and now want to sign in with Klarna, you should allow the connection of the accounts by merging the accounts in the back-end, rather than reject the sign in.

This should allow the customer to be able to sign in to the connected account using both sign in methods.

Once a customer has logged in with Klarna, always utilize the data you collect to improve the customer’s experience. Use the information available to pre-fill the customer’s profile and checkout form fields is a basic use case to leverage the data available:

Data collectionPre-filled profilePre-filled checkout

Once the customer creates their account and is redirected back to the Partner’s platform, they should be taken directly to a personalized shopping experience, in a logged-in state.

Customer signs in with Klarna accountPersonalized shopping experience

There shouldn’t be any additional steps after the customer creates their account. Especially not asking for the same information that was provided during account creation, or asking to verify already verified details.

After a purchase is complete, many customers find it valuable to have a way to track their order and access their purchase history. For those who have checked out as guests, the order confirmation page provides a seamless opportunity to invite them to create an account using Sign in with Klarna.

By implementing the Sign in with Klarna button on the success page, you can offer customers a quick and secure way to set up an account after their purchase, enhancing their post-purchase experience and opening up new engagement opportunities.

Creating an account provides customers with access to past and future purchases, personalized order updates, and exclusive promotions. For your business, it enables deeper customer relationships, higher retention rates, and more effective communication. Adding SIWK at this critical touchpoint can make a significant impact on customer loyalty and engagement.

Invite customers to create an account using Sign in with KlarnaCustomer sets up an accountPersonalized experience with access to more data

Enabling account creation on the order confirmation screen allows customers to:

  • Track orders easily – Once logged in, customers can monitor their purchases, delivery status, and history from a single account.
  • Enjoy a personalized experience – Customers can receive targeted promotions and order updates.
  • Save time – Returning customers won’t need to re-enter information in future transactions.

For your business, this is a unique opportunity to convert guest customers into account holders, increasing the chance of future interactions and building a stronger, loyal customer base.

To integrate the Sign in with Klarna button on the order confirmation screen, you should embed the SIWK button in a visible, user-friendly location on the order confirmation (or “thank you”) page on your website where customers land after completing a purchase. A sample prompt could be, "Create an account to view your order history and enjoy a more personalized experience.".

Use Klarna’s SDK to authenticate users via the SIWK button. Once authenticated, check for an existing user account. If none exists, prompt them to complete the quick setup to create a new account tied to their recent purchase.

Finally, provide a confirmation message once the account is created, such as "Your account has been set up! You can now track this and future orders in your account.". Consider redirecting users to their new account profile or order history page to immediately reinforce the benefits of having an account.

​​