Skip to content

Instantly share code, notes, and snippets.

@KevCui
Last active September 7, 2020 09:08
Show Gist options
  • Star 2 You must be signed in to star a gist
  • Fork 1 You must be signed in to fork a gist
  • Save KevCui/767ebcdf8afb1df2a2abb4e95d9a70e3 to your computer and use it in GitHub Desktop.
Save KevCui/767ebcdf8afb1df2a2abb4e95d9a70e3 to your computer and use it in GitHub Desktop.
A Bash script to decode JWT token
#!/usr/bin/env bash
# HOW TO USE:
# ~$ chmod +x jwtDecoder.sh
# ~$ ./jwtDecoder.sh "<JWT token>"
padding() {
# $1: base64 string
local m p=""
m=$(( ${#1} % 4 ))
[[ "$m" == 2 ]] && p="=="
[[ "$m" == 3 ]] && p="="
echo "${1}${p}"
}
if [[ -z $(command -v jq) ]]; then
echo "This script will NOT work on your machine."
echo "Please install jq first: https://stedolan.github.io/jq/download/"
exit 1
fi
clear
input=("${@}")
input=("${input//$'\n'/}")
input=("${input//' '/}")
token=$(IFS=$'\n'; echo "${input[*]}")
echo -e "JWT token:\\n${token}"
IFS='.' read -ra ADDR <<< "$token"
base64 -d <<< "$(padding "${ADDR[0]}")" | jq
base64 -d <<< "$(padding "${ADDR[1]}")" | jq
echo "Signature: ${ADDR[2]}"
@stokito
Copy link

stokito commented Jan 18, 2020

The last section of the JWT is a signature and it is failed to parse in last command jq '.' 2> /dev/null but this is hidden by redirecting error to dev/null.
Instead we can just take section by index

IFS='.' read -ra ADDR <<< "$token"
JWT_HEADER=$(echo "${ADDR[0]}" | base64 -d 2> /dev/null)
JWT_PAYLOAD=$(echo "${ADDR[1]}" | base64 -d 2> /dev/null)
JWT_SIGNATURE="${ADDR[2]}"
echo "JWT Header:"
echo "${JWT_HEADER}" | jq '.'
echo "JWT Payload:"
echo "${JWT_PAYLOAD}" | jq '.'
echo "JWT Signature:"
echo "${JWT_SIGNATURE}"

JWT_SUB=$(echo "$JWT_PAYLOAD" | jq -r .sub)
JWT_EMAIL=$(echo "$JWT_PAYLOAD" | jq -r .email)
echo "sub: $JWT_SUB email: $JWT_EMAIL"

@KevCui
Copy link
Author

KevCui commented Jul 12, 2020

@stokito Thanks for the info 👍

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment