decode command
Purpose: To inspect the contents of a JWT and optionally verify its signature.
When to Use
Use the decode command when you need to:
- Troubleshoot API authentication failures — See what user information is embedded in the JWT
- Verify token validity — Check if a token has expired or is not yet valid
- Confirm signature integrity — Ensure the JWT hasn't been tampered with
- Inspect claims — View all the information embedded in the JWT (user ID, directory, email, groups, etc.)
Syntax
qs-jwt decode [options]Full Help
➜ demo-dir ./qs-jwt decode --help
Usage: qs-jwt decode [options]
Decode a JWT and display its contents. Optionally verify the signature using a public key.
Options:
--jwt <token> The JWT string to decode
--jwt-file <file> Path to a file containing the JWT
--cert-publickey-file <file> Path to a file containing the public key for signature verification
--cert-publickey <key> Public key string for signature verification
--expected-audience <audience> Expected audience value to verify (requires a public key)
--loglevel <level> Logging level (choices: "error", "warning", "info", "verbose", "debug", default: "info")
--minimal-output Output as JSON only, without additional formatting
-h, --help display help for commandRequired Options (one of)
You must provide either --jwt or --jwt-file, but not both.
--jwt <token>: The JWT string to decode--jwt-file <file>: Path to a file containing the JWT
Optional Options
--cert-publickey-file <file>: Path to a file containing the public key for signature verification--cert-publickey <key>: Public key string for signature verification--expected-audience <audience>: Expected audience value to verify (requires a public key)--loglevel <level>: Logging level (error,warning,info,verbose,debug). Default:info--minimal-output: Output as JSON only, without additional formatting
Usage Examples
Basic Decoding
Decode a JWT and display its contents:
qs-jwt decode --jwt "eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9.eyJ1c2VySWQiOiJqb2huc21pdGgiLCJ1c2VyRGlyZWN0b3J5IjoiTVlESVIifQ.signature"Or read from a file:
qs-jwt decode --jwt-file /path/to/token.txtVerifying Signature
Verify that the JWT was signed with a specific public key:
qs-jwt decode --jwt "eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9..." \
--cert-publickey-file /path/to/publickey.pemVerifying Audience
Verify that the JWT audience matches your expected value:
qs-jwt decode --jwt "eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9..." \
--cert-publickey-file /path/to/publickey.pem \
--expected-audience "my-qlik-sense-app"JSON Output
Output the decoded JWT as JSON (useful for scripting):
qs-jwt decode --jwt "eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9..." --minimal-outputOutput Format
Normal Output
When running without --minimal-output, the command displays:
- JWT Header — Contains metadata about the token (algorithm, type, key ID)
- JWT Payload — Contains the claims (user information, timestamps, audience, etc.)
- Signature Verification (if public key provided) — Shows verification status and details
Example:
JWT Header:
{
"alg": "RS256",
"typ": "JWT",
"kid": "qs-jwt-key-2024"
}
JWT Payload:
{
"userId": "johnsmith",
"userDirectory": "MYDIR",
"name": "John Smith",
"email": "john.smith@example.com",
"iat": "1717948800 (2024-06-09T12:00:00.000Z)",
"exp": "1717952400 (2024-06-09T13:00:00.000Z)",
"aud": "my-qlik-sense-app",
"iss": "qs-jwt"
}
Signature Verification:
Status: ✅ Valid
Algorithm: RS256 (verified)
Key ID: qs-jwt-key-2024
Integrity: Token has not been tampered with
Validity:
Issued: 2024-06-09T12:00:00.000Z
Expires: 2024-06-09T13:00:00.000Z
Current: ✅ Token is currently valid
Audience: my-qlik-sense-app ✅
Issuer: qs-jwtMinimal Output (JSON)
When using --minimal-output, the command outputs a JSON object:
{
"header": { "alg": "RS256", "typ": "JWT", "kid": "qs-jwt-key-2024" },
"payload": {
"userId": "johnsmith",
"userDirectory": "MYDIR",
"name": "John Smith",
"email": "john.smith@example.com",
"iat": 1717948800,
"exp": 1717952400,
"aud": "my-qlik-sense-app",
"iss": "qs-jwt"
},
"verification": {
"status": "valid",
"algorithm": "RS256",
"keyId": "qs-jwt-key-2024",
"integrity": true,
"issuedAt": "2024-06-09T12:00:00.000Z",
"expiresAt": "2024-06-09T13:00:00.000Z",
"notBefore": "N/A",
"currentlyValid": true,
"audience": "my-qlik-sense-app",
"audienceMatch": true,
"issuer": "qs-jwt"
}
}Understanding the Output
JWT Header
The header contains metadata about the token:
- alg — The algorithm used to sign the token (e.g., RS256)
- typ — The token type (always "JWT")
- kid — Key ID (optional) — identifies which key was used to sign the token
JWT Payload
The payload contains the claims (data) embedded in the token:
- userId — The user ID that will be authenticated
- userDirectory — The user directory in Qlik Sense
- name — The user's display name
- email — The user's email address
- iat — Issued at time (Unix timestamp)
- exp — Expiration time (Unix timestamp)
- nbf — Not before time (optional — when the token becomes valid)
- aud — Audience (must match the Qlik Sense virtual proxy configuration)
- iss — Issuer (must match the Qlik Sense configuration)
- group — Groups the user belongs to (optional)
Signature Verification
When a public key is provided, the command verifies:
- Status — ✅ Valid or ❌ Invalid
- Algorithm — The algorithm used (confirmed as verified)
- Key ID — Which key was used (if present in header)
- Integrity — Whether the token has been tampered with
- Validity — Time-based validity:
- Issued — When the token was created
- Expires — When the token expires
- Current — Whether the token is currently valid (not expired)
- Audience — The audience claim (✅ if it matches
--expected-audience) - Issuer — Who issued the token
Common Error Messages
"Invalid JWT format. Expected 3 parts separated by dots"
The JWT is malformed. A valid JWT has three parts separated by dots: header.payload.signature. This error may also occur if you try to decode a JWE (encrypted) token, which is not supported.
"Failed to decode JWT. Token may be malformed"
The JWT structure is invalid or the base64 encoding is incorrect.
"jwt expired"
The token is expired. In the decode output this appears under Signature Verification as Reason: jwt expired.
"jwt audience invalid"
The audience in the JWT doesn't match --expected-audience. In the decode output this appears as Reason: jwt audience invalid. expected: ....
This could mean:
- The JWT was created for a different Qlik Sense virtual proxy
- The
--expected-audiencevalue is incorrect
"invalid signature"
The signature doesn't match the provided public key. In the decode output this appears as Reason: invalid signature.
Tips
Use the public key from your Qlik Sense configuration
The same public key that's configured in your Qlik Sense virtual proxy should be used for verification.
Check expiration times
If API calls are failing with authentication errors, first check if the JWT has expired.
Verify audience matches
The audience in the JWT must exactly match the audience configured in your Qlik Sense virtual proxy.
Use minimal output for scripting
When integrating with scripts or automation, use --minimal-output to get clean JSON that's easy to parse.
Store JWTs securely
JWTs provide authentication access to Qlik Sense. Treat them like passwords and don't log or expose them unnecessarily.