4. Parsing the ID Token

The ID token returned during token exchange is a JSON Web Signature (JWS), which is also encrypted using JSON Web Encryption (JWE). The JWE and JWS components are represented using compact serialization form, as specified in section 3.1 of RFC 7516.

To reduce complexity, we recommend that you use a JWT parsing library to decrypt the token and to verify the signature, instead of implementing the decryption and signature verification yourself. You may refer to this list to look for a suitable JWT library for your programming language, though you must also ensure that your library of choice supports decryption of JWTs encrypted using JWE.

JWT Claims

The decrypted JWT will have the following claims:

Claim
Description
Data Type

sub

The principal that is the subject of the JWT. Contains a globally unique identifier for the user.

String

aud

The client ID of your registered client, provided by Singpass during app onboarding.

A 32-character case-sensitive alphanumeric string.

iss

The issuer identifier of our authorization server.

String

iat

The unix timestamp, in seconds, at which we issued this JWT.

Number

exp

The unix timestamp, in seconds, on or after which this JWT must not be accepted for processing.

Number

amr

Authentication method references. Example values are ["face"], ["fv"], ["fv-alt"], ["otp"], ["pwd","fv"], ["pwd","otp-email"], ["pwd","sms"], ["pwd","swk"], ["pwd"], ["sso"]. Note that this list is non-exhaustive, and we reserves the right to introduce new values without prior notice to you.

Array of strings

nonce

This is the same nonce that you used in your authorization request.

String

sub_account

This contains some information related to the user's identifiers. This is only returned if the sub_account scope is requested.

Object containing key-value pairs. See the section below for full details.

Sample ID token
{
  "aud" : "gnY6Erichpb5t4NFRP9R4L7aEC9N0FQH",
  "iss" : "https://id.singpass.gov.sg/fapi",
  "exp" : 1727322545,
  "iat" : 1727321945,
  "nonce" : "L5nmQfcetDDIeincoqvCrFyGv+nHobkv4XocNYPCXaQ="
  "sub" : "1c0cee38-3a8f-4f8a-83bc-7a0e4c59d6a9",
  "sub_account": {
    "account_type": "SC/PR",
    "uinfin": "S1234567G"
  }
}

The sub_account Claim

The sub_account claim is an object that will always contain an account_type property, which reflects the user's residency status or type of pass that they are holding. However, the other values returned in this object will contain different values depending on the user's account_type , as explained below.

Singapore Citizen or Permanent Resident

A user who is a Singapore Citizen or Permanent Resident will have an account_type of SC/PR. The only other property returned in the sub_account claim is uinfin:

Property
Description
Data Type

uinfin

The user's NRIC number

9-character alphanumeric string.

Sample sub_account for Singapore Citizen or Permanent Resident
"sub_account": {
  "account_type": "SC/PR",
  "uinfin": "S1234567G"
}

FIN Holders

A user who is a FIN holder will have one of the following account_type values, which correspond to the pass type that they have:

account_type
Pass type

FIN-EP

Employment Pass

FIN-WP

Work Permit

FIN-SP

Special Pass

LTVP

Long-term Visit Pass

LTVP+

Long-term Visit Pass Plus

STP

Student Pass

IEO

Immigration Exemption Order

Similar to Singapore Citizens and Permanent Residents, the only other property returned in the sub_account claim is uinfin:

Property
Description
Data Type

uinfin

The user's FIN number

9-character alphanumeric string.

Sample sub_account for FIN holder
"sub_account": {
  "account_type": "FIN-EP",
  "uinfin": "G0874953C"
}

Singapore Foreign Account Holders

A user who has a Singapore Foreign Account will have an account_type of SFA. The other properties returned in the sub_account claim are as follows:

Property
Description
Data Type

foreign_id

The user's foreign ID number

String

foreign_id_coi

The country of issuance of the user's foreign ID

2-letter country code.

Sample sub_account for Singapore Foreign Account holder
"sub_account": {
  "account_type": "SFA",
  "foreign_id": "K28394589",
  "foreign_id_coi": "TK"
}

Verification Checks

If you are using a certified OIDC Relying Party library, these checks will be automatically performed by the library, though you must pass the nonce to the library for it to perform the nonce check.

In order to ensure that the ID token is valid, you must perform the following checks:

  1. Verify that the iss claim matches the issuer identifier of our authorization server, which you can obtain from the issuer field in the OpenID configuration of our authorization server.

  2. Verify that the aud claim matches your client ID.

  3. Ensure that the current time is before the timestamp in the exp claim.

  4. Ensure that the nonce claim is the same as the nonce that you had sent in the authorization request.

If you are integrating with Singpass Login, then the flow ends here. If you are integrating with Myinfo (v5), then the next and final step would be to retrieve the user's information using the /userinfo endpoint.

Last updated

Was this helpful?