Integrating LINE Login with your web app

Note: This guide describes how to integrate LINE Login v2.1 which supports the OpenID Connect protocol and allows you to retrieve user information with ID tokens. To integrate LINE Login v2 with your web app, see Integrating LINE Login v2.

This page explains how to integrate LINE Login with your web application. If you don’t have an existing application and would like to try LINE Login on a sample application, go to Try LINE Login for web.

Login flow

The LINE Login process for web (web login) is based on the OAuth 2.0 authorization code grant flow and the OpenID Connect protocol. Your application must be able to make requests server-side and receive data from the LINE Platform. The following is an overview of the web login flow.

LINE Login auth flow

These are the steps involved in the web login process.

  1. Your application directs the user to the LINE Login authorization URL with the required query parameters.
  2. The LINE Login dialog is opened in a browser and the user logs in to be authenticated. After the LINE Platform validates the user’s credentials, the user must also agree to grant the requested permissions to your app.
  3. The LINE Platform redirects the user back to your app via redirect_uri with the authorization code and state in the query string.
  4. Your application requests an access token from the https://api.line.me/oauth2/v2.1/token endpoint with the authorization code.
  5. The LINE Platform validates your application’s request and returns an access token.

Once you have retrieved an access token, you can use it to call the Social API.

Before you begin

To start integrating your application with LINE Login, make sure you have completed the following.

Configuring your channel

To specify where to redirect the user after login, set a callback URL from the "App settings" page of the console.

Note: You can set multiple callback URLs.

Redirect settings

Making an authorization request

To authenticate the user and request permissions of your app, redirect the user to the following authorization URL with the required query parameters. You can redirect the user using a LINE Login button or with a direct link.

https://access.line.me/oauth2/v2.1/authorize

You must include the required query parameters in the URL.

Parameter Type Required Description
response_type String Yes code. This tells the LINE Platform to return an authorization code.
client_id String Yes Channel ID. Unique identifier for your channel issued by LINE.
redirect_uri String Yes Callback URL. URL that users are redirected to after authentication and authorization. Must match one of the the callback URLs registered for your channel in the console.
state String Yes A unique alphanumeric string used to prevent cross-site request forgery. This value should be randomly-generated by your application. Cannot be a URL-encoded string.
scope String Yes Permissions granted by the user. You can specify multiple scopes using the URL encoded whitespace character (%20). Note: The profile scope must be included. For more information, see scopes.
nonce String No A string used to prevent replay attacks. This value is returned in an ID token.
prompt String No consent. Used to force the consent screen to be displayed even if the user has already granted all requested permissions.

Scopes

The following scopes can be specified in the scope parameter. Note: You must include the profile scope.

  • profile: Required. Permission to get the user's profile information.
  • openid: Used to retrieve an ID token. For more information, see ID token.

Note: The permissions to set the email and phone scopes will be configurable on the console soon.

Example authorization request

The following is an example of an authorization URL with query parameters.

https://access.line.me/oauth2/v2.1/authorize?response_type=code&client_id=1234567890&redirect_uri=https%3A%2F%2Fexample.com%2Fauth&state=12345abcde&scope=openid%20profile&nonce=09876xyz

Authentication and authorization process

When the user is redirected to the authorization URL, the LINE Platform automatically checks the user's session to determine the user's login status. If the user is not logged in to LINE, the LINE Platform redirects the user to the LINE Login dialog for authentication. The user must then log in to LINE with an email and password. If the user has a session and is already logged in to LINE, a confirmation screen is displayed instead of the LINE Login dialog.

Once the user logs in, a consent screen is displayed to request the permissions specified in scope. However, if the user has already granted all the permissions requested by the channel, the consent screen is not displayed.

Consent screen

Receiving the authorization code

Once the user is authenticated and authorization is complete, the HTTP status code 302 and the following query parameters are returned in the callback URL.

Parameter Type Description
code String Authorization code used to get an access token. Valid for 10 minutes.
state String State parameter included in the authorization URL of original request. Your application should verify that this value matches the one in the original request.

The following is an example response.

HTTTP/1.1 302 Found
Location : https://client.example.org/cb?code=abcd1234&state=0987poi

Error response

If the user denies the permissions requested by your application, the following parameters are returned in the callback URL query string.

Parameter Type Required Description
error String Yes Error code.
error_description String No Human-readable ASCII encoded text description of the error.
state String No OAuth 2.0 state value. Required if the authorization Request included the state parameter.

This is an example of an error response.

https://example.com/callback?error=access_denied&error_description=The+user+has+denied+the+approval&state=0987poi

If the user denies the permissions requested by your application, your application should handle the error appropriately.

Getting an access token

To get an access token, make an HTTP POST request with the authorization code. Once you have an access token, you can use it to make API calls. The access token is issued at the following endpoint.

Request

POST https://api.line.me/oauth2/v2.1/token

Request header Description
Content-Type application/x-www-form-urlencoded

Request body

The information in the request body is in a form-urlencoded format.

Parameters Type Required Description
grant_type String Yes authorization_code. Specifies the grant type.
code String Yes Authorization code
redirect_uri String Yes Callback URL
client_id String Yes Channel ID. Found in the console.
client_secret String Yes Channel secret. Found in the console.

Example request

This an example of an HTTP POST request to get an access token.

curl -X POST https://api.line.me/oauth2/v2.1/token \
-H 'Content-Type: application/x-www-form-urlencoded' \
-d 'grant_type=authorization_code' \
-d 'code=xxx' \
-d 'redirect_uri=xxx' \
-d 'client_id=xxx' \
-d 'client_secret=xxx'

Response

The LINE Platform validates the request and returns an access token and other data as shown in the table below.

Field Type Description
access_token String Access token. Valid for 30 days.
expires_in Number Amount of time in seconds until the access token expires.
id_token String JSON Web Token (JWT) that includes information about the user. This field is returned only if openid is specified in the scope. For more information, see ID tokens.
refresh_token String Token used to get a new access token. Valid up until 10 days after the access token expires.
scope String Permissions granted by the user.
token_type String Bearer

The following is an example JSON response.

{
    "access_token": "bNl4YEFPI/hjFWhTqexp4MuEw5YPs...",
    "expires_in": 2592000,
    "id_token": "eyJhbGciOiJIUzI1NiJ9...",
    "refresh_token": "Aa1FdeggRhTnPNNpxr8p",
    "scope": "profile",
    "token_type": "Bearer"
}

ID tokens

ID tokens are JSON web tokens (JWT) with information about the user. The ID token consists of a header, payload, and signature separated by period (.) characters. Each part is a base64url-encoded value. For more information, see the JWT specification.

The following is an example of a decoded header value. In this example, the header declares that the encoded object uses the HMAC SHA-256 algorithm. LINE Login only uses HMAC SHA-256.

{
  "alg": "HS256"
}
Payload

The user's information is found in the payload section.

Field Description
iss https://access.line.me. URL where the ID token is generated.
sub User ID for which the ID token is generated
aud Channel ID
exp The expiry date of the token. UNIX time.
iat Time that the ID token was generated. UNIX time.
nonce The nonce value specified in the authorization URL. Not included if the nonce value was not specified in the authorization request.
name User's display name.
picture User's profile image URL.

The following is an example of a decoded payload section.

{
    "iss": "https://access.line.me", 
    "sub": "U1234567890abcdef1234567890abcdef ",
    "aud": "1234567890", 
    "exp": 1504169092, 
    "iat": 1504263657, 
    "nonce": "0987654asdf", 
    "name": "Taro Line", 
    "picture": "https://sample_line.me/aBcdefg123456", 
}
Signature

The signature is used to verify the validity of the response. The signature is a base64url-encoded hash computed using the HMAC SHA-256 algorithm with the base64url-encoded header + "." + payload as the value and the channel secret as a key. To ensure the security of your app, you should always verify the signature of the token.

Decoding and validating ID tokens

To decode and validate ID tokens, you can either use a JWT library or follow the instructions below.

Use a JWT library

You can use the publicly available JWT libraries to decode and verify your ID tokens. The following is an example of how to decode an ID token using a library for Python.

import jwt

decoded_id_token = jwt.decode(id_token,
                              channel_secret,
                              audience=channel_id,
                              issuer='https://access.line.me',
                              algorithms=['HS256'])

# check nonce (Optional. But strongly recommended)
nonce = '_stored_in_session_'
expected_nonce = decoded_id_token.get('nonce')
if nonce != decoded_id_token.get('nonce'):
    raise RuntimeError('invalid nonce')

Decode and validate ID token

  1. Split the header, payload, and signature sections using the period (.) character.
  2. Base64-URL decode each section
  3. Compute the hash using the base64url-encoded header + "." + payload as the value and the channel secret as a key. Verify that the value is the same as the decoded signature.
  4. Confirm that the ID token was sent from LINE by checking that the value of iss is https://access.line.me.
  5. Confirm that the ID token is for your channel by checking that aud matches your channel ID.
  6. To prevent replay attacks, confirm that the value of nonce is the same as the nonce value specified in the authorization request. Store the nonce value with the user session. Although this step is optional, we strongly recommend including the nonce value.
  7. To confirm the validity of the ID token, confirm that the exp value is greater than the UNIX timestamp at the time of verification.

The following is an example using Python 3.

import base64
import hashlib
import hmac
import json
import time


def base64url_decode(target):
    rem = len(target) % 4
    if rem > 0:
        target += '=' * (4 - rem)

    return base64.urlsafe_b64decode(target)


def check_signature(key, target, signature):
    calc_signature = hmac.new(
        key.encode('utf-8'),
        target.encode('utf-8'),
        hashlib.sha256
    ).digest()

    return hmac.compare_digest(signature, calc_signature)


def decode_id_token(id_token, channel_id, channel_secret, nonce=None):
    # step 1
    header, payload, signature = id_token.split('.')

    # step 2
    header_decoded = base64url_decode(header)
    payload_decoded = base64url_decode(payload)
    signature_decoded = base64url_decode(signature)

    # step 3
    valid_signature = check_signature(channel_secret,
                                      header + '.' + payload,
                                      signature_decoded)
    if not valid_signature:
        raise RuntimeError('invalid signature')

    payload_json = json.loads(payload_decoded.decode('utf-8'))

    # step 4
    if payload_json.get('iss') != 'https://access.line.me':
        raise RuntimeError('invalid iss')

    # step 5
    if payload_json.get('aud') != channel_id:
        raise RuntimeError('invalid aud')

    # step 6
    if int(time.time()) > payload_json.get('exp'):
        raise RuntimeError('invalid exp')

    # step 7 (Optional. But strongly recommended)
    if nonce is not None:
        if payload_json.get('nonce') != nonce:
            raise RuntimeError('invalid nonce')

    return payload_json

Next steps

After getting an access token, use it to call the Social API to log out the user, manage access tokens, and get user profile information. For more information, see the following pages.