claims= verifier.verify(jwt);
+} catch (JWTVerifyException e) {
+ // Invalid Token
+}
+```
-- [java-jwt JavaDocs](https://javadoc.io/doc/com.auth0/java-jwt/latest)
-## Feedback
+### Why another JSON Web Token implementation for Java?
-### Contributing
+We believe existing JWT implementations in Java are either too complex or not tested enough.
+This library aims to be simple and achieve the right level of abstraction.
-We appreciate feedback and contribution to this repo! Before you get started, please see the following:
+## Issue Reporting
-- [Auth0's general contribution guidelines](https://github.com/auth0/open-source-template/blob/master/GENERAL-CONTRIBUTING.md)
-- [Auth0's code of conduct guidelines]((https://github.com/auth0/open-source-template/blob/master/CODE-OF-CONDUCT.md))
+If you have found a bug or if you have a feature request, please report them at this repository issues section. Please do not report security vulnerabilities on the public GitHub issue tracker. The [Responsible Disclosure Program](https://auth0.com/whitehat) details the procedure for disclosing security issues.
-### Raise an issue
-To provide feedback or report a bug, [please raise an issue on our issue tracker](https://github.com/auth0/java-jwt/issues).
+## Author
-### Vulnerability Reporting
-Please do not report security vulnerabilities on the public Github issue tracker. The [Responsible Disclosure Program](https://auth0.com/whitehat) details the procedure for disclosing security issues.
+[Auth0](https://auth0.com/)
----
+## License
-
-
-
-
-
-
-
-Auth0 is an easy to implement, adaptable authentication and authorization platform. To learn more checkout Why Auth0?
-
-This project is licensed under the MIT license. See the LICENSE file for more info.
+This project is licensed under the MIT license. See the [LICENSE](LICENSE.txt) file for more info.
diff --git a/build.gradle b/build.gradle
deleted file mode 100644
index c938b200..00000000
--- a/build.gradle
+++ /dev/null
@@ -1,9 +0,0 @@
-// Top-level build file where you can add configuration options common to all sub-projects/modules.
-
-allprojects {
- group = 'com.auth0'
-
- repositories {
- mavenCentral()
- }
-}
diff --git a/.codecov.yml b/codecov.yml
similarity index 71%
rename from .codecov.yml
rename to codecov.yml
index de278af2..63e5785f 100644
--- a/.codecov.yml
+++ b/codecov.yml
@@ -5,12 +5,10 @@ coverage:
status:
patch:
default:
- if_no_uploads: success
- if_ci_failed: error
+ if_no_uploads: error
changes: true
project:
default:
target: auto
- threshold: 1%
if_no_uploads: error
comment: false
\ No newline at end of file
diff --git a/config/checkstyle/checkstyle.xml b/config/checkstyle/checkstyle.xml
deleted file mode 100644
index b97ccc37..00000000
--- a/config/checkstyle/checkstyle.xml
+++ /dev/null
@@ -1,358 +0,0 @@
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
\ No newline at end of file
diff --git a/gradle.properties b/gradle.properties
deleted file mode 100644
index 74a5a049..00000000
--- a/gradle.properties
+++ /dev/null
@@ -1,38 +0,0 @@
-# Project-wide Gradle settings.
-
-# IDE (e.g. Android Studio) users:
-# Gradle settings configured through the IDE *will override*
-# any settings specified in this file.
-
-# For more details on how to configure your build environment visit
-# http://www.gradle.org/docs/current/userguide/build_environment.html
-
-# Specifies the JVM arguments used for the daemon process.
-# The setting is particularly useful for tweaking memory settings.
-org.gradle.jvmargs=-Xmx1536m
-
-# When configured, Gradle will run in incubating parallel mode.
-# This option should only be used with decoupled projects. More details, visit
-# http://www.gradle.org/docs/current/userguide/multi_project_builds.html#sec:decoupled_projects
-# org.gradle.parallel=true
-
-GROUP=com.auth0
-POM_ARTIFACT_ID=java-jwt
-
-POM_NAME=java jwt
-POM_DESCRIPTION=Java client library for the Auth0 platform
-POM_PACKAGING=jar
-
-POM_URL=https://github.com/auth0/java-jwt
-POM_SCM_URL=https://github.com/auth0/java-jwt
-
-POM_SCM_CONNECTION=scm:git:https://github.com/auth0/java-jwt.git
-POM_SCM_DEV_CONNECTION=scm:git:https://github.com/auth0/java-jwt.git
-
-POM_LICENCE_NAME=The MIT License (MIT)
-POM_LICENCE_URL=https://raw.githubusercontent.com/auth0/java-jwt/master/LICENSE
-POM_LICENCE_DIST=repo
-
-POM_DEVELOPER_ID=auth0
-POM_DEVELOPER_NAME=Auth0
-POM_DEVELOPER_EMAIL=oss@auth0.com
\ No newline at end of file
diff --git a/gradle/maven-publish.gradle b/gradle/maven-publish.gradle
deleted file mode 100644
index a9ad38d3..00000000
--- a/gradle/maven-publish.gradle
+++ /dev/null
@@ -1,113 +0,0 @@
-apply plugin: 'maven-publish'
-apply plugin: 'signing'
-
-task('sourcesJar', type: Jar, dependsOn: classes) {
- archiveClassifier = 'sources'
- from sourceSets.main.allSource
-}
-
-task('javadocJar', type: Jar, dependsOn: javadoc) {
- archiveClassifier = 'javadoc'
- from javadoc.getDestinationDir()
-}
-tasks.withType(Javadoc).configureEach {
- javadocTool = javaToolchains.javadocToolFor {
- // Use latest JDK for javadoc generation
- languageVersion = JavaLanguageVersion.of(17)
- }
-}
-
-javadoc {
- // Specify the Java version that the project will use
- options.addStringOption('-release', "11")
-}
-artifacts {
- archives sourcesJar, javadocJar
-}
-
-
-final releaseRepositoryUrl = "https://oss.sonatype.org/service/local/staging/deploy/maven2/"
-final snapshotRepositoryUrl = "https://oss.sonatype.org/content/repositories/snapshots/"
-
-publishing {
- publications {
- mavenJava(MavenPublication) {
-
- groupId = GROUP
- artifactId = POM_ARTIFACT_ID
- version = getVersionName()
-
- artifact("$buildDir/libs/${project.name}-${version}.jar")
- artifact sourcesJar
- artifact javadocJar
-
- pom {
- name = POM_NAME
- packaging = POM_PACKAGING
- description = POM_DESCRIPTION
- url = POM_URL
-
- licenses {
- license {
- name = POM_LICENCE_NAME
- url = POM_LICENCE_URL
- distribution = POM_LICENCE_DIST
- }
- }
-
- developers {
- developer {
- id = POM_DEVELOPER_ID
- name = POM_DEVELOPER_NAME
- email = POM_DEVELOPER_EMAIL
- }
- }
-
- scm {
- url = POM_SCM_URL
- connection = POM_SCM_CONNECTION
- developerConnection = POM_SCM_DEV_CONNECTION
- }
-
- pom.withXml {
- def dependenciesNode = asNode().appendNode('dependencies')
-
- project.configurations.implementation.allDependencies.each {
- def dependencyNode = dependenciesNode.appendNode('dependency')
- dependencyNode.appendNode('groupId', it.group)
- dependencyNode.appendNode('artifactId', it.name)
- dependencyNode.appendNode('version', it.version)
- }
- }
- }
- }
- }
- repositories {
- maven {
- name = "sonatype"
- url = version.endsWith('SNAPSHOT') ? snapshotRepositoryUrl : releaseRepositoryUrl
- credentials {
- username = System.getenv("MAVEN_USERNAME")
- password = System.getenv("MAVEN_PASSWORD")
- }
- }
- }
-}
-
-signing {
- def signingKey = System.getenv("SIGNING_KEY")
- def signingPassword = System.getenv("SIGNING_PASSWORD")
- useInMemoryPgpKeys(signingKey, signingPassword)
-
- sign publishing.publications.mavenJava
-}
-
-javadoc {
- if(JavaVersion.current().isJava9Compatible()) {
- options.addBooleanOption('html5', true)
- }
-}
-
-tasks.named('publish').configure {
- dependsOn tasks.named('assemble')
-}
\ No newline at end of file
diff --git a/gradle/versioning.gradle b/gradle/versioning.gradle
deleted file mode 100644
index 3441ae11..00000000
--- a/gradle/versioning.gradle
+++ /dev/null
@@ -1,17 +0,0 @@
-def getVersionFromFile() {
- def versionFile = rootProject.file('.version')
- return versionFile.text.readLines().first().trim()
-}
-
-def isSnapshot() {
- return hasProperty('isSnapshot') ? isSnapshot.toBoolean() : true
-}
-
-def getVersionName() {
- return isSnapshot() ? project.version+"-SNAPSHOT" : project.version
-}
-
-ext {
- getVersionName = this.&getVersionName
- getVersionFromFile = this.&getVersionFromFile
-}
\ No newline at end of file
diff --git a/gradle/wrapper/gradle-wrapper.jar b/gradle/wrapper/gradle-wrapper.jar
deleted file mode 100644
index e708b1c0..00000000
Binary files a/gradle/wrapper/gradle-wrapper.jar and /dev/null differ
diff --git a/gradle/wrapper/gradle-wrapper.properties b/gradle/wrapper/gradle-wrapper.properties
deleted file mode 100644
index ec991f9a..00000000
--- a/gradle/wrapper/gradle-wrapper.properties
+++ /dev/null
@@ -1,5 +0,0 @@
-distributionBase=GRADLE_USER_HOME
-distributionPath=wrapper/dists
-distributionUrl=https\://services.gradle.org/distributions/gradle-6.9.2-bin.zip
-zipStoreBase=GRADLE_USER_HOME
-zipStorePath=wrapper/dists
diff --git a/gradlew b/gradlew
deleted file mode 100755
index 4f906e0c..00000000
--- a/gradlew
+++ /dev/null
@@ -1,185 +0,0 @@
-#!/usr/bin/env sh
-
-#
-# Copyright 2015 the original author or authors.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# https://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-#
-
-##############################################################################
-##
-## Gradle start up script for UN*X
-##
-##############################################################################
-
-# Attempt to set APP_HOME
-# Resolve links: $0 may be a link
-PRG="$0"
-# Need this for relative symlinks.
-while [ -h "$PRG" ] ; do
- ls=`ls -ld "$PRG"`
- link=`expr "$ls" : '.*-> \(.*\)$'`
- if expr "$link" : '/.*' > /dev/null; then
- PRG="$link"
- else
- PRG=`dirname "$PRG"`"/$link"
- fi
-done
-SAVED="`pwd`"
-cd "`dirname \"$PRG\"`/" >/dev/null
-APP_HOME="`pwd -P`"
-cd "$SAVED" >/dev/null
-
-APP_NAME="Gradle"
-APP_BASE_NAME=`basename "$0"`
-
-# Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
-DEFAULT_JVM_OPTS='"-Xmx64m" "-Xms64m"'
-
-# Use the maximum available, or set MAX_FD != -1 to use that value.
-MAX_FD="maximum"
-
-warn () {
- echo "$*"
-}
-
-die () {
- echo
- echo "$*"
- echo
- exit 1
-}
-
-# OS specific support (must be 'true' or 'false').
-cygwin=false
-msys=false
-darwin=false
-nonstop=false
-case "`uname`" in
- CYGWIN* )
- cygwin=true
- ;;
- Darwin* )
- darwin=true
- ;;
- MINGW* )
- msys=true
- ;;
- NONSTOP* )
- nonstop=true
- ;;
-esac
-
-CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar
-
-
-# Determine the Java command to use to start the JVM.
-if [ -n "$JAVA_HOME" ] ; then
- if [ -x "$JAVA_HOME/jre/sh/java" ] ; then
- # IBM's JDK on AIX uses strange locations for the executables
- JAVACMD="$JAVA_HOME/jre/sh/java"
- else
- JAVACMD="$JAVA_HOME/bin/java"
- fi
- if [ ! -x "$JAVACMD" ] ; then
- die "ERROR: JAVA_HOME is set to an invalid directory: $JAVA_HOME
-
-Please set the JAVA_HOME variable in your environment to match the
-location of your Java installation."
- fi
-else
- JAVACMD="java"
- which java >/dev/null 2>&1 || die "ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
-
-Please set the JAVA_HOME variable in your environment to match the
-location of your Java installation."
-fi
-
-# Increase the maximum file descriptors if we can.
-if [ "$cygwin" = "false" -a "$darwin" = "false" -a "$nonstop" = "false" ] ; then
- MAX_FD_LIMIT=`ulimit -H -n`
- if [ $? -eq 0 ] ; then
- if [ "$MAX_FD" = "maximum" -o "$MAX_FD" = "max" ] ; then
- MAX_FD="$MAX_FD_LIMIT"
- fi
- ulimit -n $MAX_FD
- if [ $? -ne 0 ] ; then
- warn "Could not set maximum file descriptor limit: $MAX_FD"
- fi
- else
- warn "Could not query maximum file descriptor limit: $MAX_FD_LIMIT"
- fi
-fi
-
-# For Darwin, add options to specify how the application appears in the dock
-if $darwin; then
- GRADLE_OPTS="$GRADLE_OPTS \"-Xdock:name=$APP_NAME\" \"-Xdock:icon=$APP_HOME/media/gradle.icns\""
-fi
-
-# For Cygwin or MSYS, switch paths to Windows format before running java
-if [ "$cygwin" = "true" -o "$msys" = "true" ] ; then
- APP_HOME=`cygpath --path --mixed "$APP_HOME"`
- CLASSPATH=`cygpath --path --mixed "$CLASSPATH"`
-
- JAVACMD=`cygpath --unix "$JAVACMD"`
-
- # We build the pattern for arguments to be converted via cygpath
- ROOTDIRSRAW=`find -L / -maxdepth 1 -mindepth 1 -type d 2>/dev/null`
- SEP=""
- for dir in $ROOTDIRSRAW ; do
- ROOTDIRS="$ROOTDIRS$SEP$dir"
- SEP="|"
- done
- OURCYGPATTERN="(^($ROOTDIRS))"
- # Add a user-defined pattern to the cygpath arguments
- if [ "$GRADLE_CYGPATTERN" != "" ] ; then
- OURCYGPATTERN="$OURCYGPATTERN|($GRADLE_CYGPATTERN)"
- fi
- # Now convert the arguments - kludge to limit ourselves to /bin/sh
- i=0
- for arg in "$@" ; do
- CHECK=`echo "$arg"|egrep -c "$OURCYGPATTERN" -`
- CHECK2=`echo "$arg"|egrep -c "^-"` ### Determine if an option
-
- if [ $CHECK -ne 0 ] && [ $CHECK2 -eq 0 ] ; then ### Added a condition
- eval `echo args$i`=`cygpath --path --ignore --mixed "$arg"`
- else
- eval `echo args$i`="\"$arg\""
- fi
- i=`expr $i + 1`
- done
- case $i in
- 0) set -- ;;
- 1) set -- "$args0" ;;
- 2) set -- "$args0" "$args1" ;;
- 3) set -- "$args0" "$args1" "$args2" ;;
- 4) set -- "$args0" "$args1" "$args2" "$args3" ;;
- 5) set -- "$args0" "$args1" "$args2" "$args3" "$args4" ;;
- 6) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" ;;
- 7) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" ;;
- 8) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" ;;
- 9) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" "$args8" ;;
- esac
-fi
-
-# Escape application args
-save () {
- for i do printf %s\\n "$i" | sed "s/'/'\\\\''/g;1s/^/'/;\$s/\$/' \\\\/" ; done
- echo " "
-}
-APP_ARGS=`save "$@"`
-
-# Collect all arguments for the java command, following the shell quoting and substitution rules
-eval set -- $DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS "\"-Dorg.gradle.appname=$APP_BASE_NAME\"" -classpath "\"$CLASSPATH\"" org.gradle.wrapper.GradleWrapperMain "$APP_ARGS"
-
-exec "$JAVACMD" "$@"
diff --git a/gradlew.bat b/gradlew.bat
deleted file mode 100644
index ac1b06f9..00000000
--- a/gradlew.bat
+++ /dev/null
@@ -1,89 +0,0 @@
-@rem
-@rem Copyright 2015 the original author or authors.
-@rem
-@rem Licensed under the Apache License, Version 2.0 (the "License");
-@rem you may not use this file except in compliance with the License.
-@rem You may obtain a copy of the License at
-@rem
-@rem https://www.apache.org/licenses/LICENSE-2.0
-@rem
-@rem Unless required by applicable law or agreed to in writing, software
-@rem distributed under the License is distributed on an "AS IS" BASIS,
-@rem WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-@rem See the License for the specific language governing permissions and
-@rem limitations under the License.
-@rem
-
-@if "%DEBUG%" == "" @echo off
-@rem ##########################################################################
-@rem
-@rem Gradle startup script for Windows
-@rem
-@rem ##########################################################################
-
-@rem Set local scope for the variables with windows NT shell
-if "%OS%"=="Windows_NT" setlocal
-
-set DIRNAME=%~dp0
-if "%DIRNAME%" == "" set DIRNAME=.
-set APP_BASE_NAME=%~n0
-set APP_HOME=%DIRNAME%
-
-@rem Resolve any "." and ".." in APP_HOME to make it shorter.
-for %%i in ("%APP_HOME%") do set APP_HOME=%%~fi
-
-@rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
-set DEFAULT_JVM_OPTS="-Xmx64m" "-Xms64m"
-
-@rem Find java.exe
-if defined JAVA_HOME goto findJavaFromJavaHome
-
-set JAVA_EXE=java.exe
-%JAVA_EXE% -version >NUL 2>&1
-if "%ERRORLEVEL%" == "0" goto execute
-
-echo.
-echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
-echo.
-echo Please set the JAVA_HOME variable in your environment to match the
-echo location of your Java installation.
-
-goto fail
-
-:findJavaFromJavaHome
-set JAVA_HOME=%JAVA_HOME:"=%
-set JAVA_EXE=%JAVA_HOME%/bin/java.exe
-
-if exist "%JAVA_EXE%" goto execute
-
-echo.
-echo ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME%
-echo.
-echo Please set the JAVA_HOME variable in your environment to match the
-echo location of your Java installation.
-
-goto fail
-
-:execute
-@rem Setup the command line
-
-set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar
-
-
-@rem Execute Gradle
-"%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %*
-
-:end
-@rem End local scope for the variables with windows NT shell
-if "%ERRORLEVEL%"=="0" goto mainEnd
-
-:fail
-rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of
-rem the _cmd.exe /c_ return code!
-if not "" == "%GRADLE_EXIT_CONSOLE%" exit 1
-exit /b 1
-
-:mainEnd
-if "%OS%"=="Windows_NT" endlocal
-
-:omega
diff --git a/lib/.gitignore b/lib/.gitignore
deleted file mode 100644
index 796b96d1..00000000
--- a/lib/.gitignore
+++ /dev/null
@@ -1 +0,0 @@
-/build
diff --git a/lib/build.gradle b/lib/build.gradle
deleted file mode 100644
index 83093fc1..00000000
--- a/lib/build.gradle
+++ /dev/null
@@ -1,244 +0,0 @@
-buildscript {
- repositories {
- jcenter()
- }
-
- dependencies {
- // https://github.com/melix/japicmp-gradle-plugin/issues/36
- classpath 'com.google.guava:guava:31.1-jre'
- }
-}
-
-plugins {
- id 'java'
- id 'jacoco'
- id 'checkstyle'
- id 'me.champeau.gradle.japicmp' version '0.4.1'
-}
-
-sourceSets {
- jmh {
-
- }
-}
-
-configurations {
- jmhImplementation {
- extendsFrom implementation
- }
-}
-
-checkstyle {
- toolVersion '10.0'
-}
-//We are disabling lint checks for tests
-tasks.named("checkstyleTest").configure({
- enabled = false
-})
-tasks.named("checkstyleJmh").configure({
- enabled = false
-})
-
-apply from: rootProject.file('gradle/versioning.gradle')
-
-version = getVersionFromFile()
-group = GROUP
-logger.lifecycle("Using version ${version} for ${name} group $group")
-
-import me.champeau.gradle.japicmp.JapicmpTask
-
-project.afterEvaluate {
-
- def versions = project.ext.testInJavaVersions
- for (pluginJavaTestVersion in versions) {
- def taskName = "testInJava-${pluginJavaTestVersion}"
- tasks.register(taskName, Test) {
- def versionToUse = taskName.split("-").getAt(1) as Integer
- description = "Runs unit tests on Java version ${versionToUse}."
- project.logger.quiet("Test will be running in ${versionToUse}")
- group = 'verification'
- javaLauncher.set(javaToolchains.launcherFor {
- languageVersion = JavaLanguageVersion.of(versionToUse)
- })
- shouldRunAfter(tasks.named('test'))
- }
- tasks.named('check') {
- dependsOn(taskName)
- }
- }
-
- project.configure(project) {
- def baselineVersion = project.ext.baselineCompareVersion
- task('apiDiff', type: JapicmpTask, dependsOn: 'jar') {
- oldClasspath.from(files(getBaselineJar(project, baselineVersion)))
- newClasspath.from(files(jar.archiveFile))
- onlyModified = true
- failOnModification = true
- ignoreMissingClasses = true
- htmlOutputFile = file("$buildDir/reports/apiDiff/apiDiff.html")
- txtOutputFile = file("$buildDir/reports/apiDiff/apiDiff.txt")
- doLast {
- project.logger.quiet("Comparing against baseline version ${baselineVersion}")
- }
- }
- }
-}
-
-private static File getBaselineJar(Project project, String baselineVersion) {
- // Use detached configuration: https://github.com/square/okhttp/blob/master/build.gradle#L270
- def group = project.group
- try {
- def baseline = "${project.group}:${project.name}:$baselineVersion"
- project.group = 'virtual_group_for_japicmp'
- def dependency = project.dependencies.create(baseline + "@jar")
- return project.configurations.detachedConfiguration(dependency).files.find {
- it.name == "${project.name}-${baselineVersion}.jar"
- }
- } finally {
- project.group = group
- }
-}
-
-ext {
- baselineCompareVersion = '4.1.0'
- testInJavaVersions = [8, 11, 17, 21]
-}
-
-java {
- toolchain {
- languageVersion = JavaLanguageVersion.of(11)
- }
-}
-
-compileJava {
- exclude 'module-info.java'
- // Required to be compatible with JDK 8+
- options.release = 8
-}
-
-javadoc {
- // Exclude internal implementation package from javadoc
- excludes = ['com/auth0/jwt/impl', 'module-info.java']
-}
-
-dependencies {
- implementation 'com.fasterxml.jackson.core:jackson-core:2.15.4'
- implementation 'com.fasterxml.jackson.core:jackson-databind:2.15.4'
-
- testImplementation 'org.bouncycastle:bcprov-jdk15on:1.70'
- testImplementation 'junit:junit:4.13.2'
- testImplementation 'net.jodah:concurrentunit:0.4.6'
- testImplementation 'org.hamcrest:hamcrest:2.2'
- testImplementation 'org.mockito:mockito-core:4.4.0'
-
- jmhImplementation sourceSets.main.output
- jmhImplementation 'org.openjdk.jmh:jmh-core:1.35'
- jmhAnnotationProcessor 'org.openjdk.jmh:jmh-generator-annprocess:1.35'
-}
-
-jacoco {
- toolVersion = "0.8.10"
-}
-
-jacocoTestReport {
- reports {
- xml.enabled = true
- html.enabled = true
- }
-}
-
-test {
- testLogging {
- events "skipped", "failed", "standardError"
- exceptionFormat "short"
- }
-}
-
-task compileModuleInfoJava(type: JavaCompile) {
- classpath = files()
- source = 'src/main/java/module-info.java'
- destinationDir = compileJava.destinationDir
- doLast {
- def descriptor = new File(compileJava.destinationDir, 'module-info.class')
- def dest = new File(compileJava.destinationDir, 'META-INF/versions/9')
- ant.move file: descriptor, todir: dest
- }
-
- doFirst {
- options.compilerArgs = [
- '--release', '9',
- '--module-path', compileJava.classpath.asPath
- ]
- }
-}
-
-compileTestJava {
- options.release = 8
- options.compilerArgs = ["-Xlint:deprecation"]
-}
-
-def testJava8 = tasks.register('testJava8', Test) {
- description = 'Runs unit tests on Java 8.'
- group = 'verification'
-
- javaLauncher.set(javaToolchains.launcherFor {
- languageVersion = JavaLanguageVersion.of(8)
- })
- shouldRunAfter(tasks.named('test'))
-}
-
-def testJava17 = tasks.register('testJava17', Test) {
- description = 'Runs unit tests on Java 17.'
- group = 'verification'
-
- javaLauncher.set(javaToolchains.launcherFor {
- languageVersion = JavaLanguageVersion.of(17)
- })
- shouldRunAfter(tasks.named('test'))
-}
-
-def testJava21 = tasks.register('testJava21', Test) {
- description = 'Runs unit tests on Java 21.'
- group = 'verification'
-
- javaLauncher.set(javaToolchains.launcherFor {
- languageVersion = JavaLanguageVersion.of(21)
- })
- shouldRunAfter(tasks.named('test'))
-}
-
-tasks.named('check') {
- dependsOn(testJava8)
- dependsOn(testJava17)
- dependsOn(testJava21)
-}
-
-jar {
- manifest.attributes('Multi-Release': 'true')
-}
-
-compileModuleInfoJava.dependsOn compileJava
-classes.dependsOn compileModuleInfoJava
-
-// you can pass any arguments JMH accepts via Gradle args.
-// Example: ./gradlew runJMH --args="-lrf"
-tasks.register('runJMH', JavaExec) {
- description 'Run JMH benchmarks.'
- group 'verification'
-
- main 'org.openjdk.jmh.Main'
- classpath sourceSets.jmh.runtimeClasspath
-
- args project.hasProperty("args") ? project.property("args").split() : ""
-}
-tasks.register('jmhHelp', JavaExec) {
- description 'Prints the available command line options for JMH.'
- group 'help'
-
- main 'org.openjdk.jmh.Main'
- classpath sourceSets.jmh.runtimeClasspath
-
- args '-h'
-}
-
-apply from: rootProject.file('gradle/maven-publish.gradle')
diff --git a/lib/src/jmh/java/com/auth0/jwt/benchmark/JWTDecoderBenchmark.java b/lib/src/jmh/java/com/auth0/jwt/benchmark/JWTDecoderBenchmark.java
deleted file mode 100644
index 81d3737a..00000000
--- a/lib/src/jmh/java/com/auth0/jwt/benchmark/JWTDecoderBenchmark.java
+++ /dev/null
@@ -1,20 +0,0 @@
-package com.auth0.jwt.benchmark;
-
-import com.auth0.jwt.JWT;
-import org.openjdk.jmh.annotations.Benchmark;
-import org.openjdk.jmh.annotations.BenchmarkMode;
-import org.openjdk.jmh.annotations.Mode;
-import org.openjdk.jmh.infra.Blackhole;
-
-/**
- * This class is a JMH benchmark for decoding JWTs.
- */
-public class JWTDecoderBenchmark {
- private static final String TOKEN = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiYWRtaW4iOnRydWV9.TJVA95OrM7E2cBab30RMHrHDcEfxjoYZgeFONFh7HgQ";
-
- @Benchmark
- @BenchmarkMode(Mode.Throughput)
- public void throughputDecodeTime(Blackhole blackhole) {
- blackhole.consume(JWT.decode(TOKEN));
- }
-}
diff --git a/lib/src/main/java/com/auth0/jwt/HeaderParams.java b/lib/src/main/java/com/auth0/jwt/HeaderParams.java
deleted file mode 100644
index 1107f313..00000000
--- a/lib/src/main/java/com/auth0/jwt/HeaderParams.java
+++ /dev/null
@@ -1,29 +0,0 @@
-package com.auth0.jwt;
-
-/**
- * Contains constants representing the JWT header parameter names.
- */
-public final class HeaderParams {
-
- private HeaderParams() {}
-
- /**
- * The algorithm used to sign a JWT.
- */
- public static final String ALGORITHM = "alg";
-
- /**
- * The content type of the JWT.
- */
- public static final String CONTENT_TYPE = "cty";
-
- /**
- * The media type of the JWT.
- */
- public static final String TYPE = "typ";
-
- /**
- * The key ID of a JWT used to specify the key for signature validation.
- */
- public static final String KEY_ID = "kid";
-}
diff --git a/lib/src/main/java/com/auth0/jwt/JWT.java b/lib/src/main/java/com/auth0/jwt/JWT.java
deleted file mode 100644
index 696abe40..00000000
--- a/lib/src/main/java/com/auth0/jwt/JWT.java
+++ /dev/null
@@ -1,74 +0,0 @@
-package com.auth0.jwt;
-
-import com.auth0.jwt.algorithms.Algorithm;
-import com.auth0.jwt.exceptions.JWTDecodeException;
-import com.auth0.jwt.impl.JWTParser;
-import com.auth0.jwt.interfaces.DecodedJWT;
-import com.auth0.jwt.interfaces.Verification;
-
-/**
- * Exposes all the JWT functionalities.
- */
-@SuppressWarnings("WeakerAccess")
-public class JWT {
-
- private final JWTParser parser;
-
- /**
- * Constructs a new instance of the JWT library. Use this if you need to decode many JWT
- * tokens on the fly and do not wish to instantiate a new parser for each invocation.
- */
- public JWT() {
- parser = new JWTParser();
- }
-
- /**
- * Decode a given Json Web Token.
- *
- * Note that this method doesn't verify the token's signature!
- * Use it only if you trust the token or if you have already verified it.
- *
- * @param token with jwt format as string.
- * @return a decoded JWT.
- * @throws JWTDecodeException if any part of the token contained an invalid jwt
- * or JSON format of each of the jwt parts.
- */
- public DecodedJWT decodeJwt(String token) throws JWTDecodeException {
- return new JWTDecoder(parser, token);
- }
-
- /**
- * Decode a given Json Web Token.
- *
- * Note that this method doesn't verify the token's signature!
- * Use it only if you trust the token or if you have already verified it.
- *
- * @param token with jwt format as string.
- * @return a decoded JWT.
- * @throws JWTDecodeException if any part of the token contained an invalid jwt
- * or JSON format of each of the jwt parts.
- */
- public static DecodedJWT decode(String token) throws JWTDecodeException {
- return new JWTDecoder(token);
- }
-
- /**
- * Returns a {@link Verification} builder with the algorithm to be used to validate token signature.
- *
- * @param algorithm that will be used to verify the token's signature.
- * @return {@link Verification} builder
- * @throws IllegalArgumentException if the provided algorithm is null.
- */
- public static Verification require(Algorithm algorithm) {
- return JWTVerifier.init(algorithm);
- }
-
- /**
- * Returns a Json Web Token builder used to create and sign tokens.
- *
- * @return a token builder.
- */
- public static JWTCreator.Builder create() {
- return JWTCreator.init();
- }
-}
diff --git a/lib/src/main/java/com/auth0/jwt/JWTCreator.java b/lib/src/main/java/com/auth0/jwt/JWTCreator.java
deleted file mode 100644
index bfcb9147..00000000
--- a/lib/src/main/java/com/auth0/jwt/JWTCreator.java
+++ /dev/null
@@ -1,631 +0,0 @@
-package com.auth0.jwt;
-
-import com.auth0.jwt.algorithms.Algorithm;
-import com.auth0.jwt.exceptions.JWTCreationException;
-import com.auth0.jwt.exceptions.SignatureGenerationException;
-import com.auth0.jwt.impl.*;
-import com.fasterxml.jackson.core.JsonProcessingException;
-import com.fasterxml.jackson.databind.MapperFeature;
-import com.fasterxml.jackson.databind.ObjectMapper;
-import com.fasterxml.jackson.databind.json.JsonMapper;
-import com.fasterxml.jackson.databind.module.SimpleModule;
-
-import java.nio.charset.StandardCharsets;
-import java.time.Instant;
-import java.util.*;
-import java.util.Map.Entry;
-
-/**
- * The JWTCreator class holds the sign method to generate a complete JWT (with Signature)
- * from a given Header and Payload content.
- *
- * This class is thread-safe.
- */
-@SuppressWarnings("WeakerAccess")
-public final class JWTCreator {
-
- private final Algorithm algorithm;
- private final String headerJson;
- private final String payloadJson;
-
- private static final ObjectMapper mapper;
- private static final SimpleModule module;
-
- static {
- module = new SimpleModule();
- module.addSerializer(PayloadClaimsHolder.class, new PayloadSerializer());
- module.addSerializer(HeaderClaimsHolder.class, new HeaderSerializer());
-
- mapper = JsonMapper.builder()
- .configure(MapperFeature.SORT_PROPERTIES_ALPHABETICALLY, true)
- .build()
- .registerModule(module);
- }
-
- private JWTCreator(Algorithm algorithm, Map headerClaims, Map payloadClaims)
- throws JWTCreationException {
- this.algorithm = algorithm;
- try {
- headerJson = mapper.writeValueAsString(new HeaderClaimsHolder(headerClaims));
- payloadJson = mapper.writeValueAsString(new PayloadClaimsHolder(payloadClaims));
- } catch (JsonProcessingException e) {
- throw new JWTCreationException("Some of the Claims couldn't be converted to a valid JSON format.", e);
- }
- }
-
-
- /**
- * Initialize a JWTCreator instance.
- *
- * @return a JWTCreator.Builder instance to configure.
- */
- static JWTCreator.Builder init() {
- return new Builder();
- }
-
- /**
- * The Builder class holds the Claims that defines the JWT to be created.
- */
- public static class Builder {
- private final Map payloadClaims;
- private final Map headerClaims;
-
- Builder() {
- this.payloadClaims = new LinkedHashMap<>();
- this.headerClaims = new LinkedHashMap<>();
- }
-
- /**
- * Add specific Claims to set as the Header.
- * If provided map is null then nothing is changed
- *
- * @param headerClaims the values to use as Claims in the token's Header.
- * @return this same Builder instance.
- */
- public Builder withHeader(Map headerClaims) {
- if (headerClaims == null) {
- return this;
- }
-
- for (Map.Entry entry : headerClaims.entrySet()) {
- if (entry.getValue() == null) {
- this.headerClaims.remove(entry.getKey());
- } else {
- this.headerClaims.put(entry.getKey(), entry.getValue());
- }
- }
-
- return this;
- }
-
- /**
- * Add specific Claims to set as the Header.
- * If provided json is null then nothing is changed
- *
- * @param headerClaimsJson the values to use as Claims in the token's Header.
- * @return this same Builder instance.
- * @throws IllegalArgumentException if json value has invalid structure
- */
- public Builder withHeader(String headerClaimsJson) throws IllegalArgumentException {
- if (headerClaimsJson == null) {
- return this;
- }
-
- try {
- Map headerClaims = mapper.readValue(headerClaimsJson, LinkedHashMap.class);
- return withHeader(headerClaims);
- } catch (JsonProcessingException e) {
- throw new IllegalArgumentException("Invalid header JSON", e);
- }
- }
-
- /**
- * Add a specific Key Id ("kid") claim to the Header.
- * If the {@link Algorithm} used to sign this token was instantiated with a KeyProvider,
- * the 'kid' value will be taken from that provider and this one will be ignored.
- *
- * @param keyId the Key Id value.
- * @return this same Builder instance.
- */
- public Builder withKeyId(String keyId) {
- this.headerClaims.put(HeaderParams.KEY_ID, keyId);
- return this;
- }
-
- /**
- * Add a specific Issuer ("iss") claim to the Payload.
- *
- * @param issuer the Issuer value.
- * @return this same Builder instance.
- */
- public Builder withIssuer(String issuer) {
- addClaim(RegisteredClaims.ISSUER, issuer);
- return this;
- }
-
- /**
- * Add a specific Subject ("sub") claim to the Payload.
- *
- * @param subject the Subject value.
- * @return this same Builder instance.
- */
- public Builder withSubject(String subject) {
- addClaim(RegisteredClaims.SUBJECT, subject);
- return this;
- }
-
- /**
- * Add a specific Audience ("aud") claim to the Payload.
- *
- * @param audience the Audience value.
- * @return this same Builder instance.
- */
- public Builder withAudience(String... audience) {
- addClaim(RegisteredClaims.AUDIENCE, audience);
- return this;
- }
-
- /**
- * Add a specific Expires At ("exp") claim to the payload. The claim will be written as seconds since the epoch.
- * Milliseconds will be truncated by rounding down to the nearest second.
- *
- * @param expiresAt the Expires At value.
- * @return this same Builder instance.
- */
- public Builder withExpiresAt(Date expiresAt) {
- addClaim(RegisteredClaims.EXPIRES_AT, expiresAt);
- return this;
- }
-
- /**
- * Add a specific Expires At ("exp") claim to the payload. The claim will be written as seconds since the epoch;
- * Milliseconds will be truncated by rounding down to the nearest second.
- *
- * @param expiresAt the Expires At value.
- * @return this same Builder instance.
- */
- public Builder withExpiresAt(Instant expiresAt) {
- addClaim(RegisteredClaims.EXPIRES_AT, expiresAt);
- return this;
- }
-
- /**
- * Add a specific Not Before ("nbf") claim to the Payload. The claim will be written as seconds since the epoch;
- * Milliseconds will be truncated by rounding down to the nearest second.
- *
- * @param notBefore the Not Before value.
- * @return this same Builder instance.
- */
- public Builder withNotBefore(Date notBefore) {
- addClaim(RegisteredClaims.NOT_BEFORE, notBefore);
- return this;
- }
-
- /**
- * Add a specific Not Before ("nbf") claim to the Payload. The claim will be written as seconds since the epoch;
- * Milliseconds will be truncated by rounding down to the nearest second.
- *
- * @param notBefore the Not Before value.
- * @return this same Builder instance.
- */
- public Builder withNotBefore(Instant notBefore) {
- addClaim(RegisteredClaims.NOT_BEFORE, notBefore);
- return this;
- }
-
- /**
- * Add a specific Issued At ("iat") claim to the Payload. The claim will be written as seconds since the epoch;
- * Milliseconds will be truncated by rounding down to the nearest second.
- *
- * @param issuedAt the Issued At value.
- * @return this same Builder instance.
- */
- public Builder withIssuedAt(Date issuedAt) {
- addClaim(RegisteredClaims.ISSUED_AT, issuedAt);
- return this;
- }
-
- /**
- * Add a specific Issued At ("iat") claim to the Payload. The claim will be written as seconds since the epoch;
- * Milliseconds will be truncated by rounding down to the nearest second.
- *
- * @param issuedAt the Issued At value.
- * @return this same Builder instance.
- */
- public Builder withIssuedAt(Instant issuedAt) {
- addClaim(RegisteredClaims.ISSUED_AT, issuedAt);
- return this;
- }
-
- /**
- * Add a specific JWT Id ("jti") claim to the Payload.
- *
- * @param jwtId the Token Id value.
- * @return this same Builder instance.
- */
- public Builder withJWTId(String jwtId) {
- addClaim(RegisteredClaims.JWT_ID, jwtId);
- return this;
- }
-
- /**
- * Add a custom Claim value.
- *
- * @param name the Claim's name.
- * @param value the Claim's value.
- * @return this same Builder instance.
- * @throws IllegalArgumentException if the name is null.
- */
- public Builder withClaim(String name, Boolean value) throws IllegalArgumentException {
- assertNonNull(name);
- addClaim(name, value);
- return this;
- }
-
- /**
- * Add a custom Claim value.
- *
- * @param name the Claim's name.
- * @param value the Claim's value.
- * @return this same Builder instance.
- * @throws IllegalArgumentException if the name is null.
- */
- public Builder withClaim(String name, Integer value) throws IllegalArgumentException {
- assertNonNull(name);
- addClaim(name, value);
- return this;
- }
-
- /**
- * Add a custom Claim value.
- *
- * @param name the Claim's name.
- * @param value the Claim's value.
- * @return this same Builder instance.
- * @throws IllegalArgumentException if the name is null.
- */
- public Builder withClaim(String name, Long value) throws IllegalArgumentException {
- assertNonNull(name);
- addClaim(name, value);
- return this;
- }
-
- /**
- * Add a custom Claim value.
- *
- * @param name the Claim's name.
- * @param value the Claim's value.
- * @return this same Builder instance.
- * @throws IllegalArgumentException if the name is null.
- */
- public Builder withClaim(String name, Double value) throws IllegalArgumentException {
- assertNonNull(name);
- addClaim(name, value);
- return this;
- }
-
- /**
- * Add a custom Claim value.
- *
- * @param name the Claim's name.
- * @param value the Claim's value.
- * @return this same Builder instance.
- * @throws IllegalArgumentException if the name is null.
- */
- public Builder withClaim(String name, String value) throws IllegalArgumentException {
- assertNonNull(name);
- addClaim(name, value);
- return this;
- }
-
- /**
- * Add a custom Claim value. The claim will be written as seconds since the epoch.
- * Milliseconds will be truncated by rounding down to the nearest second.
- *
- * @param name the Claim's name.
- * @param value the Claim's value.
- * @return this same Builder instance.
- * @throws IllegalArgumentException if the name is null.
- */
- public Builder withClaim(String name, Date value) throws IllegalArgumentException {
- assertNonNull(name);
- addClaim(name, value);
- return this;
- }
-
- /**
- * Add a custom Claim value. The claim will be written as seconds since the epoch.
- * Milliseconds will be truncated by rounding down to the nearest second.
- *
- * @param name the Claim's name.
- * @param value the Claim's value.
- * @return this same Builder instance.
- * @throws IllegalArgumentException if the name is null.
- */
- public Builder withClaim(String name, Instant value) throws IllegalArgumentException {
- assertNonNull(name);
- addClaim(name, value);
- return this;
- }
-
- /**
- * Add a custom Map Claim with the given items.
- *
- * Accepted nested types are {@linkplain Map} and {@linkplain List} with basic types
- * {@linkplain Boolean}, {@linkplain Integer}, {@linkplain Long}, {@linkplain Double},
- * {@linkplain String} and {@linkplain Date}. {@linkplain Map}s cannot contain null keys or values.
- * {@linkplain List}s can contain null elements.
- *
- * @param name the Claim's name.
- * @param map the Claim's key-values.
- * @return this same Builder instance.
- * @throws IllegalArgumentException if the name is null, or if the map contents does not validate.
- */
- public Builder withClaim(String name, Map map) throws IllegalArgumentException {
- assertNonNull(name);
- // validate map contents
- if (map != null && !validateClaim(map)) {
- throw new IllegalArgumentException("Expected map containing Map, List, Boolean, Integer, "
- + "Long, Double, String and Date");
- }
- addClaim(name, map);
- return this;
- }
-
- /**
- * Add a custom List Claim with the given items.
- *
- * Accepted nested types are {@linkplain Map} and {@linkplain List} with basic types
- * {@linkplain Boolean}, {@linkplain Integer}, {@linkplain Long}, {@linkplain Double},
- * {@linkplain String} and {@linkplain Date}. {@linkplain Map}s cannot contain null keys or values.
- * {@linkplain List}s can contain null elements.
- *
- * @param name the Claim's name.
- * @param list the Claim's list of values.
- * @return this same Builder instance.
- * @throws IllegalArgumentException if the name is null, or if the list contents does not validate.
- */
- public Builder withClaim(String name, List> list) throws IllegalArgumentException {
- assertNonNull(name);
- // validate list contents
- if (list != null && !validateClaim(list)) {
- throw new IllegalArgumentException("Expected list containing Map, List, Boolean, Integer, "
- + "Long, Double, String and Date");
- }
- addClaim(name, list);
- return this;
- }
-
- /**
- * Add a custom claim with null value.
- *
- * @param name the Claim's name.
- * @return this same Builder instance.
- * @throws IllegalArgumentException if the name is null
- */
- public Builder withNullClaim(String name) throws IllegalArgumentException {
- assertNonNull(name);
- addClaim(name, null);
- return this;
- }
-
- /**
- * Add a custom Array Claim with the given items.
- *
- * @param name the Claim's name.
- * @param items the Claim's value.
- * @return this same Builder instance.
- * @throws IllegalArgumentException if the name is null.
- */
- public Builder withArrayClaim(String name, String[] items) throws IllegalArgumentException {
- assertNonNull(name);
- addClaim(name, items);
- return this;
- }
-
- /**
- * Add a custom Array Claim with the given items.
- *
- * @param name the Claim's name.
- * @param items the Claim's value.
- * @return this same Builder instance.
- * @throws IllegalArgumentException if the name is null.
- */
- public Builder withArrayClaim(String name, Integer[] items) throws IllegalArgumentException {
- assertNonNull(name);
- addClaim(name, items);
- return this;
- }
-
- /**
- * Add a custom Array Claim with the given items.
- *
- * @param name the Claim's name.
- * @param items the Claim's value.
- * @return this same Builder instance.
- * @throws IllegalArgumentException if the name is null
- */
- public Builder withArrayClaim(String name, Long[] items) throws IllegalArgumentException {
- assertNonNull(name);
- addClaim(name, items);
- return this;
- }
-
- /**
- * Add specific Claims to set as the Payload. If the provided map is null then
- * nothing is changed.
- *
- * Accepted types are {@linkplain Map} and {@linkplain List} with basic types
- * {@linkplain Boolean}, {@linkplain Integer}, {@linkplain Long}, {@linkplain Double},
- * {@linkplain String} and {@linkplain Date}.
- * {@linkplain Map}s and {@linkplain List}s can contain null elements.
- *
- *
- *
- * If any of the claims are invalid, none will be added.
- *
- *
- * @param payloadClaims the values to use as Claims in the token's payload.
- * @return this same Builder instance.
- * @throws IllegalArgumentException if any of the claim keys or null,
- * or if the values are not of a supported type.
- */
- public Builder withPayload(Map payloadClaims) throws IllegalArgumentException {
- if (payloadClaims == null) {
- return this;
- }
-
- if (!validatePayload(payloadClaims)) {
- throw new IllegalArgumentException("Claim values must only be of types Map, List, Boolean, Integer, "
- + "Long, Double, String, Date, Instant, and Null");
- }
-
- // add claims only after validating all claims so as not to corrupt the claims map of this builder
- for (Map.Entry entry : payloadClaims.entrySet()) {
- addClaim(entry.getKey(), entry.getValue());
- }
-
- return this;
- }
-
- /**
- * Add specific Claims to set as the Payload. If the provided json is null then
- * nothing is changed.
- *
- *
- * If any of the claims are invalid, none will be added.
- *
- *
- * @param payloadClaimsJson the values to use as Claims in the token's payload.
- * @return this same Builder instance.
- * @throws IllegalArgumentException if any of the claim keys or null,
- * or if the values are not of a supported type,
- * or if json value has invalid structure.
- */
- public Builder withPayload(String payloadClaimsJson) throws IllegalArgumentException {
- if (payloadClaimsJson == null) {
- return this;
- }
-
- try {
- Map payloadClaims = mapper.readValue(payloadClaimsJson, LinkedHashMap.class);
- return withPayload(payloadClaims);
- } catch (JsonProcessingException e) {
- throw new IllegalArgumentException("Invalid payload JSON", e);
- }
- }
-
- private boolean validatePayload(Map payload) {
- for (Map.Entry entry : payload.entrySet()) {
- String key = entry.getKey();
- assertNonNull(key);
-
- Object value = entry.getValue();
- if (value instanceof List && !validateClaim((List>) value)) {
- return false;
- } else if (value instanceof Map && !validateClaim((Map, ?>) value)) {
- return false;
- } else if (!isSupportedType(value)) {
- return false;
- }
- }
- return true;
- }
-
- private static boolean validateClaim(Map, ?> map) {
- // do not accept null values in maps
- for (Entry, ?> entry : map.entrySet()) {
- Object value = entry.getValue();
- if (!isSupportedType(value)) {
- return false;
- }
-
- if (!(entry.getKey() instanceof String)) {
- return false;
- }
- }
- return true;
- }
-
- private static boolean validateClaim(List> list) {
- // accept null values in list
- for (Object object : list) {
- if (!isSupportedType(object)) {
- return false;
- }
- }
- return true;
- }
-
- private static boolean isSupportedType(Object value) {
- if (value instanceof List) {
- return validateClaim((List>) value);
- } else if (value instanceof Map) {
- return validateClaim((Map, ?>) value);
- } else {
- return isBasicType(value);
- }
- }
-
- private static boolean isBasicType(Object value) {
- if (value == null) {
- return true;
- } else {
- Class> c = value.getClass();
-
- if (c.isArray()) {
- return c == Integer[].class || c == Long[].class || c == String[].class;
- }
- return c == String.class || c == Integer.class || c == Long.class || c == Double.class
- || c == Date.class || c == Instant.class || c == Boolean.class;
- }
- }
-
- /**
- * Creates a new JWT and signs it with the given algorithm.
- *
- * @param algorithm used to sign the JWT
- * @return a new JWT token
- * @throws IllegalArgumentException if the provided algorithm is null.
- * @throws JWTCreationException if the claims could not be converted to a valid JSON
- * or there was a problem with the signing key.
- */
- public String sign(Algorithm algorithm) throws IllegalArgumentException, JWTCreationException {
- if (algorithm == null) {
- throw new IllegalArgumentException("The Algorithm cannot be null.");
- }
- headerClaims.put(HeaderParams.ALGORITHM, algorithm.getName());
- if (!headerClaims.containsKey(HeaderParams.TYPE)) {
- headerClaims.put(HeaderParams.TYPE, "JWT");
- }
- String signingKeyId = algorithm.getSigningKeyId();
- if (signingKeyId != null) {
- withKeyId(signingKeyId);
- }
- return new JWTCreator(algorithm, headerClaims, payloadClaims).sign();
- }
-
- private void assertNonNull(String name) {
- if (name == null) {
- throw new IllegalArgumentException("The Custom Claim's name can't be null.");
- }
- }
-
- private void addClaim(String name, Object value) {
- payloadClaims.put(name, value);
- }
- }
-
- private String sign() throws SignatureGenerationException {
- String header = Base64.getUrlEncoder().withoutPadding()
- .encodeToString(headerJson.getBytes(StandardCharsets.UTF_8));
- String payload = Base64.getUrlEncoder().withoutPadding()
- .encodeToString(payloadJson.getBytes(StandardCharsets.UTF_8));
-
- byte[] signatureBytes = algorithm.sign(header.getBytes(StandardCharsets.UTF_8),
- payload.getBytes(StandardCharsets.UTF_8));
- String signature = Base64.getUrlEncoder().withoutPadding().encodeToString((signatureBytes));
-
- return String.format("%s.%s.%s", header, payload, signature);
- }
-}
diff --git a/lib/src/main/java/com/auth0/jwt/JWTDecoder.java b/lib/src/main/java/com/auth0/jwt/JWTDecoder.java
deleted file mode 100644
index cc283095..00000000
--- a/lib/src/main/java/com/auth0/jwt/JWTDecoder.java
+++ /dev/null
@@ -1,156 +0,0 @@
-package com.auth0.jwt;
-
-import com.auth0.jwt.exceptions.JWTDecodeException;
-import com.auth0.jwt.impl.JWTParser;
-import com.auth0.jwt.interfaces.Claim;
-import com.auth0.jwt.interfaces.DecodedJWT;
-import com.auth0.jwt.interfaces.Header;
-import com.auth0.jwt.interfaces.Payload;
-
-import java.io.Serializable;
-import java.nio.charset.StandardCharsets;
-import java.time.Instant;
-import java.util.Base64;
-import java.util.Date;
-import java.util.List;
-import java.util.Map;
-
-/**
- * The JWTDecoder class holds the decode method to parse a given JWT token into it's JWT representation.
- *
- * This class is thread-safe.
- */
-@SuppressWarnings("WeakerAccess")
-final class JWTDecoder implements DecodedJWT, Serializable {
-
- private static final long serialVersionUID = 1873362438023312895L;
-
- private final String[] parts;
- private final Header header;
- private final Payload payload;
-
- JWTDecoder(String jwt) throws JWTDecodeException {
- this(new JWTParser(), jwt);
- }
-
- JWTDecoder(JWTParser converter, String jwt) throws JWTDecodeException {
- parts = TokenUtils.splitToken(jwt);
- String headerJson;
- String payloadJson;
- try {
- headerJson = new String(Base64.getUrlDecoder().decode(parts[0]), StandardCharsets.UTF_8);
- payloadJson = new String(Base64.getUrlDecoder().decode(parts[1]), StandardCharsets.UTF_8);
- } catch (NullPointerException e) {
- throw new JWTDecodeException("The UTF-8 Charset isn't initialized.", e);
- } catch (IllegalArgumentException e) {
- throw new JWTDecodeException("The input is not a valid base 64 encoded string.", e);
- }
- header = converter.parseHeader(headerJson);
- payload = converter.parsePayload(payloadJson);
- }
-
- @Override
- public String getAlgorithm() {
- return header.getAlgorithm();
- }
-
- @Override
- public String getType() {
- return header.getType();
- }
-
- @Override
- public String getContentType() {
- return header.getContentType();
- }
-
- @Override
- public String getKeyId() {
- return header.getKeyId();
- }
-
- @Override
- public Claim getHeaderClaim(String name) {
- return header.getHeaderClaim(name);
- }
-
- @Override
- public String getIssuer() {
- return payload.getIssuer();
- }
-
- @Override
- public String getSubject() {
- return payload.getSubject();
- }
-
- @Override
- public List getAudience() {
- return payload.getAudience();
- }
-
- @Override
- public Date getExpiresAt() {
- return payload.getExpiresAt();
- }
-
- @Override
- public Instant getExpiresAtAsInstant() {
- return payload.getExpiresAtAsInstant();
- }
-
- @Override
- public Date getNotBefore() {
- return payload.getNotBefore();
- }
-
- @Override
- public Instant getNotBeforeAsInstant() {
- return payload.getNotBeforeAsInstant();
- }
-
- @Override
- public Date getIssuedAt() {
- return payload.getIssuedAt();
- }
-
- @Override
- public Instant getIssuedAtAsInstant() {
- return payload.getIssuedAtAsInstant();
- }
-
- @Override
- public String getId() {
- return payload.getId();
- }
-
- @Override
- public Claim getClaim(String name) {
- return payload.getClaim(name);
- }
-
- @Override
- public Map getClaims() {
- return payload.getClaims();
- }
-
- @Override
- public String getHeader() {
- return parts[0];
- }
-
- @Override
- public String getPayload() {
- return parts[1];
- }
-
- @Override
- public String getSignature() {
- return parts[2];
- }
-
- @Override
- public String getToken() {
- return String.format("%s.%s.%s", parts[0], parts[1], parts[2]);
- }
-}
diff --git a/lib/src/main/java/com/auth0/jwt/JWTVerifier.java b/lib/src/main/java/com/auth0/jwt/JWTVerifier.java
deleted file mode 100644
index bf180300..00000000
--- a/lib/src/main/java/com/auth0/jwt/JWTVerifier.java
+++ /dev/null
@@ -1,500 +0,0 @@
-package com.auth0.jwt;
-
-import com.auth0.jwt.algorithms.Algorithm;
-import com.auth0.jwt.exceptions.*;
-import com.auth0.jwt.impl.JWTParser;
-import com.auth0.jwt.interfaces.Claim;
-import com.auth0.jwt.interfaces.DecodedJWT;
-import com.auth0.jwt.impl.ExpectedCheckHolder;
-import com.auth0.jwt.interfaces.Verification;
-
-import java.time.Clock;
-import java.time.Duration;
-import java.time.Instant;
-import java.time.temporal.ChronoUnit;
-import java.util.*;
-import java.util.function.BiPredicate;
-
-/**
- * The JWTVerifier class holds the verify method to assert that a given Token has not only a proper JWT format,
- * but also its signature matches.
- *
- * This class is thread-safe.
- *
- * @see com.auth0.jwt.interfaces.JWTVerifier
- */
-public final class JWTVerifier implements com.auth0.jwt.interfaces.JWTVerifier {
- private final Algorithm algorithm;
- final List expectedChecks;
- private final JWTParser parser;
-
- JWTVerifier(Algorithm algorithm, List expectedChecks) {
- this.algorithm = algorithm;
- this.expectedChecks = Collections.unmodifiableList(expectedChecks);
- this.parser = new JWTParser();
- }
-
- /**
- * Initialize a {@link Verification} instance using the given Algorithm.
- *
- * @param algorithm the Algorithm to use on the JWT verification.
- * @return a {@link Verification} instance to configure.
- * @throws IllegalArgumentException if the provided algorithm is null.
- */
- static Verification init(Algorithm algorithm) throws IllegalArgumentException {
- return new BaseVerification(algorithm);
- }
-
- /**
- * {@link Verification} implementation that accepts all the expected Claim values for verification, and
- * builds a {@link com.auth0.jwt.interfaces.JWTVerifier} used to verify a JWT's signature and expected claims.
- *
- * Note that this class is not thread-safe. Calling {@link #build()} returns an instance of
- * {@link com.auth0.jwt.interfaces.JWTVerifier} which can be reused.
- */
- public static class BaseVerification implements Verification {
- private final Algorithm algorithm;
- private final List expectedChecks;
- private long defaultLeeway;
- private final Map customLeeways;
- private boolean ignoreIssuedAt;
- private Clock clock;
-
- BaseVerification(Algorithm algorithm) throws IllegalArgumentException {
- if (algorithm == null) {
- throw new IllegalArgumentException("The Algorithm cannot be null.");
- }
-
- this.algorithm = algorithm;
- this.expectedChecks = new ArrayList<>();
- this.customLeeways = new HashMap<>();
- this.defaultLeeway = 0;
- }
-
- @Override
- public Verification withIssuer(String... issuer) {
- List value = isNullOrEmpty(issuer) ? null : Arrays.asList(issuer);
- addCheck(RegisteredClaims.ISSUER, ((claim, decodedJWT) -> {
- if (verifyNull(claim, value)) {
- return true;
- }
- if (value == null || !value.contains(claim.asString())) {
- throw new IncorrectClaimException(
- "The Claim 'iss' value doesn't match the required issuer.", RegisteredClaims.ISSUER, claim);
- }
- return true;
- }));
- return this;
- }
-
- @Override
- public Verification withSubject(String subject) {
- addCheck(RegisteredClaims.SUBJECT, (claim, decodedJWT) ->
- verifyNull(claim, subject) || subject.equals(claim.asString()));
- return this;
- }
-
- @Override
- public Verification withAudience(String... audience) {
- List value = isNullOrEmpty(audience) ? null : Arrays.asList(audience);
- addCheck(RegisteredClaims.AUDIENCE, ((claim, decodedJWT) -> {
- if (verifyNull(claim, value)) {
- return true;
- }
- if (!assertValidAudienceClaim(decodedJWT.getAudience(), value, true)) {
- throw new IncorrectClaimException("The Claim 'aud' value doesn't contain the required audience.",
- RegisteredClaims.AUDIENCE, claim);
- }
- return true;
- }));
- return this;
- }
-
- @Override
- public Verification withAnyOfAudience(String... audience) {
- List value = isNullOrEmpty(audience) ? null : Arrays.asList(audience);
- addCheck(RegisteredClaims.AUDIENCE, ((claim, decodedJWT) -> {
- if (verifyNull(claim, value)) {
- return true;
- }
- if (!assertValidAudienceClaim(decodedJWT.getAudience(), value, false)) {
- throw new IncorrectClaimException("The Claim 'aud' value doesn't contain the required audience.",
- RegisteredClaims.AUDIENCE, claim);
- }
- return true;
- }));
- return this;
- }
-
- @Override
- public Verification acceptLeeway(long leeway) throws IllegalArgumentException {
- assertPositive(leeway);
- this.defaultLeeway = leeway;
- return this;
- }
-
- @Override
- public Verification acceptExpiresAt(long leeway) throws IllegalArgumentException {
- assertPositive(leeway);
- customLeeways.put(RegisteredClaims.EXPIRES_AT, leeway);
- return this;
- }
-
- @Override
- public Verification acceptNotBefore(long leeway) throws IllegalArgumentException {
- assertPositive(leeway);
- customLeeways.put(RegisteredClaims.NOT_BEFORE, leeway);
- return this;
- }
-
- @Override
- public Verification acceptIssuedAt(long leeway) throws IllegalArgumentException {
- assertPositive(leeway);
- customLeeways.put(RegisteredClaims.ISSUED_AT, leeway);
- return this;
- }
-
- @Override
- public Verification ignoreIssuedAt() {
- this.ignoreIssuedAt = true;
- return this;
- }
-
- @Override
- public Verification withJWTId(String jwtId) {
- addCheck(RegisteredClaims.JWT_ID, ((claim, decodedJWT) ->
- verifyNull(claim, jwtId) || jwtId.equals(claim.asString())));
- return this;
- }
-
- @Override
- public Verification withClaimPresence(String name) throws IllegalArgumentException {
- assertNonNull(name);
- //since addCheck already checks presence, we just return true
- withClaim(name, ((claim, decodedJWT) -> true));
- return this;
- }
-
- @Override
- public Verification withNullClaim(String name) throws IllegalArgumentException {
- assertNonNull(name);
- withClaim(name, ((claim, decodedJWT) -> claim.isNull()));
- return this;
- }
-
- @Override
- public Verification withClaim(String name, Boolean value) throws IllegalArgumentException {
- assertNonNull(name);
- addCheck(name, ((claim, decodedJWT) -> verifyNull(claim, value)
- || value.equals(claim.asBoolean())));
- return this;
- }
-
- @Override
- public Verification withClaim(String name, Integer value) throws IllegalArgumentException {
- assertNonNull(name);
- addCheck(name, ((claim, decodedJWT) -> verifyNull(claim, value)
- || value.equals(claim.asInt())));
- return this;
- }
-
- @Override
- public Verification withClaim(String name, Long value) throws IllegalArgumentException {
- assertNonNull(name);
- addCheck(name, ((claim, decodedJWT) -> verifyNull(claim, value)
- || value.equals(claim.asLong())));
- return this;
- }
-
- @Override
- public Verification withClaim(String name, Double value) throws IllegalArgumentException {
- assertNonNull(name);
- addCheck(name, ((claim, decodedJWT) -> verifyNull(claim, value)
- || value.equals(claim.asDouble())));
- return this;
- }
-
- @Override
- public Verification withClaim(String name, String value) throws IllegalArgumentException {
- assertNonNull(name);
- addCheck(name, ((claim, decodedJWT) -> verifyNull(claim, value)
- || value.equals(claim.asString())));
- return this;
- }
-
- @Override
- public Verification withClaim(String name, Date value) throws IllegalArgumentException {
- return withClaim(name, value != null ? value.toInstant() : null);
- }
-
- @Override
- public Verification withClaim(String name, Instant value) throws IllegalArgumentException {
- assertNonNull(name);
- // Since date-time claims are serialized as epoch seconds,
- // we need to compare them with only seconds-granularity
- addCheck(name,
- ((claim, decodedJWT) -> verifyNull(claim, value)
- || value.truncatedTo(ChronoUnit.SECONDS).equals(claim.asInstant())));
- return this;
- }
-
- @Override
- public Verification withClaim(String name, BiPredicate predicate)
- throws IllegalArgumentException {
- assertNonNull(name);
- addCheck(name, ((claim, decodedJWT) -> verifyNull(claim, predicate)
- || predicate.test(claim, decodedJWT)));
- return this;
- }
-
- @Override
- public Verification withArrayClaim(String name, String... items) throws IllegalArgumentException {
- assertNonNull(name);
- addCheck(name, ((claim, decodedJWT) -> verifyNull(claim, items)
- || assertValidCollectionClaim(claim, items)));
- return this;
- }
-
- @Override
- public Verification withArrayClaim(String name, Integer... items) throws IllegalArgumentException {
- assertNonNull(name);
- addCheck(name, ((claim, decodedJWT) -> verifyNull(claim, items)
- || assertValidCollectionClaim(claim, items)));
- return this;
- }
-
- @Override
- public Verification withArrayClaim(String name, Long... items) throws IllegalArgumentException {
- assertNonNull(name);
- addCheck(name, ((claim, decodedJWT) -> verifyNull(claim, items)
- || assertValidCollectionClaim(claim, items)));
- return this;
- }
-
- @Override
- public JWTVerifier build() {
- return this.build(Clock.systemUTC());
- }
-
- /**
- * Creates a new and reusable instance of the JWTVerifier with the configuration already provided.
- * ONLY FOR TEST PURPOSES.
- *
- * @param clock the instance that will handle the current time.
- * @return a new JWTVerifier instance with a custom {@link java.time.Clock}
- */
- public JWTVerifier build(Clock clock) {
- this.clock = clock;
- addMandatoryClaimChecks();
- return new JWTVerifier(algorithm, expectedChecks);
- }
-
- /**
- * Fetches the Leeway set for claim or returns the {@link BaseVerification#defaultLeeway}.
- *
- * @param name Claim for which leeway is fetched
- * @return Leeway value set for the claim
- */
- public long getLeewayFor(String name) {
- return customLeeways.getOrDefault(name, defaultLeeway);
- }
-
- private void addMandatoryClaimChecks() {
- long expiresAtLeeway = getLeewayFor(RegisteredClaims.EXPIRES_AT);
- long notBeforeLeeway = getLeewayFor(RegisteredClaims.NOT_BEFORE);
- long issuedAtLeeway = getLeewayFor(RegisteredClaims.ISSUED_AT);
-
- expectedChecks.add(constructExpectedCheck(RegisteredClaims.EXPIRES_AT, (claim, decodedJWT) ->
- assertValidInstantClaim(RegisteredClaims.EXPIRES_AT, claim, expiresAtLeeway, true)));
- expectedChecks.add(constructExpectedCheck(RegisteredClaims.NOT_BEFORE, (claim, decodedJWT) ->
- assertValidInstantClaim(RegisteredClaims.NOT_BEFORE, claim, notBeforeLeeway, false)));
- if (!ignoreIssuedAt) {
- expectedChecks.add(constructExpectedCheck(RegisteredClaims.ISSUED_AT, (claim, decodedJWT) ->
- assertValidInstantClaim(RegisteredClaims.ISSUED_AT, claim, issuedAtLeeway, false)));
- }
- }
-
- private boolean assertValidCollectionClaim(Claim claim, Object[] expectedClaimValue) {
- List claimArr;
- Object[] claimAsObject = claim.as(Object[].class);
-
- // Jackson uses 'natural' mapping which uses Integer if value fits in 32 bits.
- if (expectedClaimValue instanceof Long[]) {
- // convert Integers to Longs for comparison with equals
- claimArr = new ArrayList<>(claimAsObject.length);
- for (Object cao : claimAsObject) {
- if (cao instanceof Integer) {
- claimArr.add(((Integer) cao).longValue());
- } else {
- claimArr.add(cao);
- }
- }
- } else {
- claimArr = Arrays.asList(claim.as(Object[].class));
- }
- List valueArr = Arrays.asList(expectedClaimValue);
- return claimArr.containsAll(valueArr);
- }
-
- private boolean assertValidInstantClaim(String claimName, Claim claim, long leeway, boolean shouldBeFuture) {
- Instant claimVal = claim.asInstant();
- Instant now = clock.instant().truncatedTo(ChronoUnit.SECONDS);
- boolean isValid;
- if (shouldBeFuture) {
- isValid = assertInstantIsFuture(claimVal, leeway, now);
- if (!isValid) {
- throw new TokenExpiredException(String.format("The Token has expired on %s.", claimVal), claimVal);
- }
- } else {
- isValid = assertInstantIsLessThanOrEqualToNow(claimVal, leeway, now);
- if (!isValid) {
- throw new IncorrectClaimException(
- String.format("The Token can't be used before %s.", claimVal), claimName, claim);
- }
- }
- return true;
- }
-
- private boolean assertInstantIsFuture(Instant claimVal, long leeway, Instant now) {
- return claimVal == null || now.minus(Duration.ofSeconds(leeway)).isBefore(claimVal);
- }
-
- private boolean assertInstantIsLessThanOrEqualToNow(Instant claimVal, long leeway, Instant now) {
- return !(claimVal != null && now.plus(Duration.ofSeconds(leeway)).isBefore(claimVal));
- }
-
- private boolean assertValidAudienceClaim(
- List actualAudience,
- List expectedAudience,
- boolean shouldContainAll
- ) {
- if (actualAudience == null || expectedAudience == null) {
- return false;
- }
-
- if (shouldContainAll) {
- return actualAudience.containsAll(expectedAudience);
- } else {
- return !Collections.disjoint(actualAudience, expectedAudience);
- }
- }
-
- private void assertPositive(long leeway) {
- if (leeway < 0) {
- throw new IllegalArgumentException("Leeway value can't be negative.");
- }
- }
-
- private void assertNonNull(String name) {
- if (name == null) {
- throw new IllegalArgumentException("The Custom Claim's name can't be null.");
- }
- }
-
- private void addCheck(String name, BiPredicate predicate) {
- expectedChecks.add(constructExpectedCheck(name, (claim, decodedJWT) -> {
- if (claim.isMissing()) {
- throw new MissingClaimException(name);
- }
- return predicate.test(claim, decodedJWT);
- }));
- }
-
- private ExpectedCheckHolder constructExpectedCheck(String claimName, BiPredicate check) {
- return new ExpectedCheckHolder() {
- @Override
- public String getClaimName() {
- return claimName;
- }
-
- @Override
- public boolean verify(Claim claim, DecodedJWT decodedJWT) {
- return check.test(claim, decodedJWT);
- }
- };
- }
-
- private boolean verifyNull(Claim claim, Object value) {
- return value == null && claim.isNull();
- }
-
- private boolean isNullOrEmpty(String[] args) {
- if (args == null || args.length == 0) {
- return true;
- }
- boolean isAllNull = true;
- for (String arg : args) {
- if (arg != null) {
- isAllNull = false;
- break;
- }
- }
- return isAllNull;
- }
- }
-
-
- /**
- * Perform the verification against the given Token, using any previous configured options.
- *
- * @param token to verify.
- * @return a verified and decoded JWT.
- * @throws AlgorithmMismatchException if the algorithm stated in the token's header is not equal to
- * the one defined in the {@link JWTVerifier}.
- * @throws SignatureVerificationException if the signature is invalid.
- * @throws TokenExpiredException if the token has expired.
- * @throws MissingClaimException if a claim to be verified is missing.
- * @throws IncorrectClaimException if a claim contained a different value than the expected one.
- */
- @Override
- public DecodedJWT verify(String token) throws JWTVerificationException {
- DecodedJWT jwt = new JWTDecoder(parser, token);
- return verify(jwt);
- }
-
- /**
- * Perform the verification against the given decoded JWT, using any previous configured options.
- *
- * @param jwt to verify.
- * @return a verified and decoded JWT.
- * @throws AlgorithmMismatchException if the algorithm stated in the token's header is not equal to
- * the one defined in the {@link JWTVerifier}.
- * @throws SignatureVerificationException if the signature is invalid.
- * @throws TokenExpiredException if the token has expired.
- * @throws MissingClaimException if a claim to be verified is missing.
- * @throws IncorrectClaimException if a claim contained a different value than the expected one.
- */
- @Override
- public DecodedJWT verify(DecodedJWT jwt) throws JWTVerificationException {
- verifyAlgorithm(jwt, algorithm);
- algorithm.verify(jwt);
- verifyClaims(jwt, expectedChecks);
- return jwt;
- }
-
- private void verifyAlgorithm(DecodedJWT jwt, Algorithm expectedAlgorithm) throws AlgorithmMismatchException {
- if (!expectedAlgorithm.getName().equals(jwt.getAlgorithm())) {
- throw new AlgorithmMismatchException(
- "The provided Algorithm doesn't match the one defined in the JWT's Header.");
- }
- }
-
- private void verifyClaims(DecodedJWT jwt, List expectedChecks)
- throws TokenExpiredException, InvalidClaimException {
- for (ExpectedCheckHolder expectedCheck : expectedChecks) {
- boolean isValid;
- String claimName = expectedCheck.getClaimName();
- Claim claim = jwt.getClaim(claimName);
-
- isValid = expectedCheck.verify(claim, jwt);
-
- if (!isValid) {
- throw new IncorrectClaimException(
- String.format("The Claim '%s' value doesn't match the required one.", claimName),
- claimName,
- claim
- );
- }
- }
- }
-}
diff --git a/lib/src/main/java/com/auth0/jwt/RegisteredClaims.java b/lib/src/main/java/com/auth0/jwt/RegisteredClaims.java
deleted file mode 100644
index c5509716..00000000
--- a/lib/src/main/java/com/auth0/jwt/RegisteredClaims.java
+++ /dev/null
@@ -1,55 +0,0 @@
-package com.auth0.jwt;
-
-/**
- * Contains constants representing the name of the Registered Claim Names as defined in Section 4.1 of
- * RFC 7529
- */
-public final class RegisteredClaims {
-
- private RegisteredClaims() {
- }
-
- /**
- * The "iss" (issuer) claim identifies the principal that issued the JWT.
- * Refer RFC 7529 Section 4.1.1
- */
- public static final String ISSUER = "iss";
-
- /**
- * The "sub" (subject) claim identifies the principal that is the subject of the JWT.
- * Refer RFC 7529 Section 4.1.2
- */
- public static final String SUBJECT = "sub";
-
- /**
- * The "aud" (audience) claim identifies the recipients that the JWT is intended for.
- * Refer RFC 7529 Section 4.1.3
- */
- public static final String AUDIENCE = "aud";
-
- /**
- * The "exp" (expiration time) claim identifies the expiration time on or after which the JWT MUST NOT be
- * accepted for processing.
- * Refer RFC 7529 Section 4.1.4
- */
- public static final String EXPIRES_AT = "exp";
-
- /**
- * The "nbf" (not before) claim identifies the time before which the JWT MUST NOT be accepted for processing.
- * Refer RFC 7529 Section 4.1.5
- */
- public static final String NOT_BEFORE = "nbf";
-
- /**
- * The "iat" (issued at) claim identifies the time at which the JWT was issued.
- * Refer RFC 7529 Section 4.1.6
- */
- public static final String ISSUED_AT = "iat";
-
- /**
- * The "jti" (JWT ID) claim provides a unique identifier for the JWT.
- * Refer RFC 7529 Section 4.1.7
- */
- public static final String JWT_ID = "jti";
-
-}
diff --git a/lib/src/main/java/com/auth0/jwt/TokenUtils.java b/lib/src/main/java/com/auth0/jwt/TokenUtils.java
deleted file mode 100644
index e62b9832..00000000
--- a/lib/src/main/java/com/auth0/jwt/TokenUtils.java
+++ /dev/null
@@ -1,47 +0,0 @@
-package com.auth0.jwt;
-
-import com.auth0.jwt.exceptions.JWTDecodeException;
-
-abstract class TokenUtils {
-
- /**
- * Splits the given token on the "." chars into a String array with 3 parts.
- *
- * @param token the string to split.
- * @return the array representing the 3 parts of the token.
- * @throws JWTDecodeException if the Token doesn't have 3 parts.
- */
- static String[] splitToken(String token) throws JWTDecodeException {
- if (token == null) {
- throw new JWTDecodeException("The token is null.");
- }
-
- char delimiter = '.';
-
- int firstPeriodIndex = token.indexOf(delimiter);
- if (firstPeriodIndex == -1) {
- throw wrongNumberOfParts(0);
- }
-
- int secondPeriodIndex = token.indexOf(delimiter, firstPeriodIndex + 1);
- if (secondPeriodIndex == -1) {
- throw wrongNumberOfParts(2);
- }
-
- // too many ?
- if (token.indexOf(delimiter, secondPeriodIndex + 1) != -1) {
- throw wrongNumberOfParts("> 3");
- }
-
- String[] parts = new String[3];
- parts[0] = token.substring(0, firstPeriodIndex);
- parts[1] = token.substring(firstPeriodIndex + 1, secondPeriodIndex);
- parts[2] = token.substring(secondPeriodIndex + 1);
-
- return parts;
- }
-
- private static JWTDecodeException wrongNumberOfParts(Object partCount) {
- return new JWTDecodeException(String.format("The token was expected to have 3 parts, but got %s.", partCount));
- }
-}
diff --git a/lib/src/main/java/com/auth0/jwt/algorithms/Algorithm.java b/lib/src/main/java/com/auth0/jwt/algorithms/Algorithm.java
deleted file mode 100644
index 248af7c5..00000000
--- a/lib/src/main/java/com/auth0/jwt/algorithms/Algorithm.java
+++ /dev/null
@@ -1,398 +0,0 @@
-package com.auth0.jwt.algorithms;
-
-import com.auth0.jwt.exceptions.SignatureGenerationException;
-import com.auth0.jwt.exceptions.SignatureVerificationException;
-import com.auth0.jwt.interfaces.DecodedJWT;
-import com.auth0.jwt.interfaces.ECDSAKeyProvider;
-import com.auth0.jwt.interfaces.RSAKeyProvider;
-
-import java.security.interfaces.*;
-
-/**
- * The Algorithm class represents an algorithm to be used in the Signing or Verification process of a Token.
- *
- * This class and its subclasses are thread-safe.
- */
-@SuppressWarnings("WeakerAccess")
-public abstract class Algorithm {
-
- private final String name;
- private final String description;
-
- /**
- * Creates a new Algorithm instance using SHA256withRSA. Tokens specify this as "RS256".
- *
- * @param keyProvider the provider of the Public Key and Private Key for the verify and signing instance.
- * @return a valid RSA256 Algorithm.
- * @throws IllegalArgumentException if the provided Key is null.
- */
- public static Algorithm RSA256(RSAKeyProvider keyProvider) throws IllegalArgumentException {
- return new RSAAlgorithm("RS256", "SHA256withRSA", keyProvider);
- }
-
- /**
- * Creates a new Algorithm instance using SHA256withRSA. Tokens specify this as "RS256".
- *
- * @param publicKey the key to use in the verify instance.
- * @param privateKey the key to use in the signing instance.
- * @return a valid RSA256 Algorithm.
- * @throws IllegalArgumentException if both provided Keys are null.
- */
- public static Algorithm RSA256(RSAPublicKey publicKey, RSAPrivateKey privateKey) throws IllegalArgumentException {
- return RSA256(RSAAlgorithm.providerForKeys(publicKey, privateKey));
- }
-
- /**
- * Creates a new Algorithm instance using SHA256withRSA. Tokens specify this as "RS256".
- *
- * @param key the key to use in the verify or signing instance.
- * @return a valid RSA256 Algorithm.
- * @throws IllegalArgumentException if the Key Provider is null.
- */
- public static Algorithm RSA256(RSAKey key) throws IllegalArgumentException {
- RSAPublicKey publicKey = key instanceof RSAPublicKey ? (RSAPublicKey) key : null;
- RSAPrivateKey privateKey = key instanceof RSAPrivateKey ? (RSAPrivateKey) key : null;
- return RSA256(publicKey, privateKey);
- }
-
- /**
- * Creates a new Algorithm instance using SHA384withRSA. Tokens specify this as "RS384".
- *
- * @param keyProvider the provider of the Public Key and Private Key for the verify and signing instance.
- * @return a valid RSA384 Algorithm.
- * @throws IllegalArgumentException if the Key Provider is null.
- */
- public static Algorithm RSA384(RSAKeyProvider keyProvider) throws IllegalArgumentException {
- return new RSAAlgorithm("RS384", "SHA384withRSA", keyProvider);
- }
-
- /**
- * Creates a new Algorithm instance using SHA384withRSA. Tokens specify this as "RS384".
- *
- * @param publicKey the key to use in the verify instance.
- * @param privateKey the key to use in the signing instance.
- * @return a valid RSA384 Algorithm.
- * @throws IllegalArgumentException if both provided Keys are null.
- */
- public static Algorithm RSA384(RSAPublicKey publicKey, RSAPrivateKey privateKey) throws IllegalArgumentException {
- return RSA384(RSAAlgorithm.providerForKeys(publicKey, privateKey));
- }
-
- /**
- * Creates a new Algorithm instance using SHA384withRSA. Tokens specify this as "RS384".
- *
- * @param key the key to use in the verify or signing instance.
- * @return a valid RSA384 Algorithm.
- * @throws IllegalArgumentException if the provided Key is null.
- */
- public static Algorithm RSA384(RSAKey key) throws IllegalArgumentException {
- RSAPublicKey publicKey = key instanceof RSAPublicKey ? (RSAPublicKey) key : null;
- RSAPrivateKey privateKey = key instanceof RSAPrivateKey ? (RSAPrivateKey) key : null;
- return RSA384(publicKey, privateKey);
- }
-
- /**
- * Creates a new Algorithm instance using SHA512withRSA. Tokens specify this as "RS512".
- *
- * @param keyProvider the provider of the Public Key and Private Key for the verify and signing instance.
- * @return a valid RSA512 Algorithm.
- * @throws IllegalArgumentException if the Key Provider is null.
- */
- public static Algorithm RSA512(RSAKeyProvider keyProvider) throws IllegalArgumentException {
- return new RSAAlgorithm("RS512", "SHA512withRSA", keyProvider);
- }
-
- /**
- * Creates a new Algorithm instance using SHA512withRSA. Tokens specify this as "RS512".
- *
- * @param publicKey the key to use in the verify instance.
- * @param privateKey the key to use in the signing instance.
- * @return a valid RSA512 Algorithm.
- * @throws IllegalArgumentException if both provided Keys are null.
- */
- public static Algorithm RSA512(RSAPublicKey publicKey, RSAPrivateKey privateKey) throws IllegalArgumentException {
- return RSA512(RSAAlgorithm.providerForKeys(publicKey, privateKey));
- }
-
- /**
- * Creates a new Algorithm instance using SHA512withRSA. Tokens specify this as "RS512".
- *
- * @param key the key to use in the verify or signing instance.
- * @return a valid RSA512 Algorithm.
- * @throws IllegalArgumentException if the provided Key is null.
- */
- public static Algorithm RSA512(RSAKey key) throws IllegalArgumentException {
- RSAPublicKey publicKey = key instanceof RSAPublicKey ? (RSAPublicKey) key : null;
- RSAPrivateKey privateKey = key instanceof RSAPrivateKey ? (RSAPrivateKey) key : null;
- return RSA512(publicKey, privateKey);
- }
-
- /**
- * Creates a new Algorithm instance using HmacSHA256. Tokens specify this as "HS256".
- *
- * @param secret the secret bytes to use in the verify or signing instance.
- * Ensure the length of the secret is at least 256 bit long
- * @return a valid HMAC256 Algorithm.
- * @throws IllegalArgumentException if the provided Secret is null.
- */
- public static Algorithm HMAC256(String secret) throws IllegalArgumentException {
- return new HMACAlgorithm("HS256", "HmacSHA256", secret);
- }
-
- /**
- * Creates a new Algorithm instance using HmacSHA256. Tokens specify this as "HS256".
- *
- * @param secret the secret bytes to use in the verify or signing instance.
- * Ensure the length of the secret is at least 256 bit long
- * @return a valid HMAC256 Algorithm.
- * @throws IllegalArgumentException if the provided Secret is null.
- */
- public static Algorithm HMAC256(byte[] secret) throws IllegalArgumentException {
- return new HMACAlgorithm("HS256", "HmacSHA256", secret);
- }
-
- /**
- * Creates a new Algorithm instance using HmacSHA384. Tokens specify this as "HS384".
- *
- * @param secret the secret bytes to use in the verify or signing instance.
- * Ensure the length of the secret is at least 384 bit long
- * @return a valid HMAC384 Algorithm.
- * @throws IllegalArgumentException if the provided Secret is null.
- */
- public static Algorithm HMAC384(String secret) throws IllegalArgumentException {
- return new HMACAlgorithm("HS384", "HmacSHA384", secret);
- }
-
- /**
- * Creates a new Algorithm instance using HmacSHA384. Tokens specify this as "HS384".
- *
- * @param secret the secret bytes to use in the verify or signing instance.
- * Ensure the length of the secret is at least 384 bit long
- * @return a valid HMAC384 Algorithm.
- * @throws IllegalArgumentException if the provided Secret is null.
- */
- public static Algorithm HMAC384(byte[] secret) throws IllegalArgumentException {
- return new HMACAlgorithm("HS384", "HmacSHA384", secret);
- }
-
- /**
- * Creates a new Algorithm instance using HmacSHA512. Tokens specify this as "HS512".
- *
- * @param secret the secret bytes to use in the verify or signing instance.
- * Ensure the length of the secret is at least 512 bit long
- * @return a valid HMAC512 Algorithm.
- * @throws IllegalArgumentException if the provided Secret is null.
- */
- public static Algorithm HMAC512(String secret) throws IllegalArgumentException {
- return new HMACAlgorithm("HS512", "HmacSHA512", secret);
- }
-
- /**
- * Creates a new Algorithm instance using HmacSHA512. Tokens specify this as "HS512".
- *
- * @param secret the secret bytes to use in the verify or signing instance.
- * Ensure the length of the secret is at least 512 bit long
- * @return a valid HMAC512 Algorithm.
- * @throws IllegalArgumentException if the provided Secret is null.
- */
- public static Algorithm HMAC512(byte[] secret) throws IllegalArgumentException {
- return new HMACAlgorithm("HS512", "HmacSHA512", secret);
- }
-
-
- /**
- * Creates a new Algorithm instance using SHA256withECDSA. Tokens specify this as "ES256".
- *
- * @param keyProvider the provider of the Public Key and Private Key for the verify and signing instance.
- * @return a valid ECDSA256 Algorithm.
- * @throws IllegalArgumentException if the Key Provider is null.
- */
- public static Algorithm ECDSA256(ECDSAKeyProvider keyProvider) throws IllegalArgumentException {
- return new ECDSAAlgorithm("ES256", "SHA256withECDSA", 32, keyProvider);
- }
-
- /**
- * Creates a new Algorithm instance using SHA256withECDSA. Tokens specify this as "ES256".
- *
- * @param publicKey the key to use in the verify instance.
- * @param privateKey the key to use in the signing instance.
- * @return a valid ECDSA256 Algorithm.
- * @throws IllegalArgumentException if the provided Key is null.
- */
- public static Algorithm ECDSA256(ECPublicKey publicKey, ECPrivateKey privateKey) throws IllegalArgumentException {
- return ECDSA256(ECDSAAlgorithm.providerForKeys(publicKey, privateKey));
- }
-
- /**
- * Creates a new Algorithm instance using SHA256withECDSA. Tokens specify this as "ES256".
- *
- * @param key the key to use in the verify or signing instance.
- * @return a valid ECDSA256 Algorithm.
- * @throws IllegalArgumentException if the provided Key is null.
- */
- public static Algorithm ECDSA256(ECKey key) throws IllegalArgumentException {
- ECPublicKey publicKey = key instanceof ECPublicKey ? (ECPublicKey) key : null;
- ECPrivateKey privateKey = key instanceof ECPrivateKey ? (ECPrivateKey) key : null;
- return ECDSA256(publicKey, privateKey);
- }
-
- /**
- * Creates a new Algorithm instance using SHA384withECDSA. Tokens specify this as "ES384".
- *
- * @param keyProvider the provider of the Public Key and Private Key for the verify and signing instance.
- * @return a valid ECDSA384 Algorithm.
- * @throws IllegalArgumentException if the Key Provider is null.
- */
- public static Algorithm ECDSA384(ECDSAKeyProvider keyProvider) throws IllegalArgumentException {
- return new ECDSAAlgorithm("ES384", "SHA384withECDSA", 48, keyProvider);
- }
-
- /**
- * Creates a new Algorithm instance using SHA384withECDSA. Tokens specify this as "ES384".
- *
- * @param publicKey the key to use in the verify instance.
- * @param privateKey the key to use in the signing instance.
- * @return a valid ECDSA384 Algorithm.
- * @throws IllegalArgumentException if the provided Key is null.
- */
- public static Algorithm ECDSA384(ECPublicKey publicKey, ECPrivateKey privateKey) throws IllegalArgumentException {
- return ECDSA384(ECDSAAlgorithm.providerForKeys(publicKey, privateKey));
- }
-
- /**
- * Creates a new Algorithm instance using SHA384withECDSA. Tokens specify this as "ES384".
- *
- * @param key the key to use in the verify or signing instance.
- * @return a valid ECDSA384 Algorithm.
- * @throws IllegalArgumentException if the provided Key is null.
- */
- public static Algorithm ECDSA384(ECKey key) throws IllegalArgumentException {
- ECPublicKey publicKey = key instanceof ECPublicKey ? (ECPublicKey) key : null;
- ECPrivateKey privateKey = key instanceof ECPrivateKey ? (ECPrivateKey) key : null;
- return ECDSA384(publicKey, privateKey);
- }
-
- /**
- * Creates a new Algorithm instance using SHA512withECDSA. Tokens specify this as "ES512".
- *
- * @param keyProvider the provider of the Public Key and Private Key for the verify and signing instance.
- * @return a valid ECDSA512 Algorithm.
- * @throws IllegalArgumentException if the Key Provider is null.
- */
- public static Algorithm ECDSA512(ECDSAKeyProvider keyProvider) throws IllegalArgumentException {
- return new ECDSAAlgorithm("ES512", "SHA512withECDSA", 66, keyProvider);
- }
-
- /**
- * Creates a new Algorithm instance using SHA512withECDSA. Tokens specify this as "ES512".
- *
- * @param publicKey the key to use in the verify instance.
- * @param privateKey the key to use in the signing instance.
- * @return a valid ECDSA512 Algorithm.
- * @throws IllegalArgumentException if the provided Key is null.
- */
- public static Algorithm ECDSA512(ECPublicKey publicKey, ECPrivateKey privateKey) throws IllegalArgumentException {
- return ECDSA512(ECDSAAlgorithm.providerForKeys(publicKey, privateKey));
- }
-
- /**
- * Creates a new Algorithm instance using SHA512withECDSA. Tokens specify this as "ES512".
- *
- * @param key the key to use in the verify or signing instance.
- * @return a valid ECDSA512 Algorithm.
- * @throws IllegalArgumentException if the provided Key is null.
- */
- public static Algorithm ECDSA512(ECKey key) throws IllegalArgumentException {
- ECPublicKey publicKey = key instanceof ECPublicKey ? (ECPublicKey) key : null;
- ECPrivateKey privateKey = key instanceof ECPrivateKey ? (ECPrivateKey) key : null;
- return ECDSA512(publicKey, privateKey);
- }
-
-
- public static Algorithm none() {
- return new NoneAlgorithm();
- }
-
- protected Algorithm(String name, String description) {
- this.name = name;
- this.description = description;
- }
-
- /**
- * Getter for the Id of the Private Key used to sign the tokens.
- * This is usually specified as the `kid` claim in the Header.
- *
- * @return the Key Id that identifies the Signing Key or null if it's not specified.
- */
- public String getSigningKeyId() {
- return null;
- }
-
- /**
- * Getter for the name of this Algorithm, as defined in the JWT Standard. i.e. "HS256"
- *
- * @return the algorithm name.
- */
- public String getName() {
- return name;
- }
-
- /**
- * Getter for the description of this Algorithm,
- * required when instantiating a Mac or Signature object. i.e. "HmacSHA256"
- *
- * @return the algorithm description.
- */
- String getDescription() {
- return description;
- }
-
- @Override
- public String toString() {
- return description;
- }
-
- /**
- * Verify the given token using this Algorithm instance.
- *
- * @param jwt the already decoded JWT that it's going to be verified.
- * @throws SignatureVerificationException if the Token's Signature is invalid,
- * meaning that it doesn't match the signatureBytes,
- * or if the Key is invalid.
- */
- public abstract void verify(DecodedJWT jwt) throws SignatureVerificationException;
-
- /**
- * Sign the given content using this Algorithm instance.
- *
- * @param headerBytes an array of bytes representing the base64 encoded header content
- * to be verified against the signature.
- * @param payloadBytes an array of bytes representing the base64 encoded payload content
- * to be verified against the signature.
- * @return the signature in a base64 encoded array of bytes
- * @throws SignatureGenerationException if the Key is invalid.
- */
- public byte[] sign(byte[] headerBytes, byte[] payloadBytes) throws SignatureGenerationException {
- // default implementation; keep around until sign(byte[]) method is removed
- byte[] contentBytes = new byte[headerBytes.length + 1 + payloadBytes.length];
-
- System.arraycopy(headerBytes, 0, contentBytes, 0, headerBytes.length);
- contentBytes[headerBytes.length] = (byte) '.';
- System.arraycopy(payloadBytes, 0, contentBytes, headerBytes.length + 1, payloadBytes.length);
-
- return sign(contentBytes);
- }
-
- /**
- * Sign the given content using this Algorithm instance.
- * To get the correct JWT Signature, ensure the content is in the format {HEADER}.{PAYLOAD}
- *
- * @param contentBytes an array of bytes representing the base64 encoded content
- * to be verified against the signature.
- * @return the signature in a base64 encoded array of bytes
- * @throws SignatureGenerationException if the Key is invalid.
- */
-
- public abstract byte[] sign(byte[] contentBytes) throws SignatureGenerationException;
-
-}
diff --git a/lib/src/main/java/com/auth0/jwt/algorithms/CryptoHelper.java b/lib/src/main/java/com/auth0/jwt/algorithms/CryptoHelper.java
deleted file mode 100644
index 7b8c5c2a..00000000
--- a/lib/src/main/java/com/auth0/jwt/algorithms/CryptoHelper.java
+++ /dev/null
@@ -1,208 +0,0 @@
-package com.auth0.jwt.algorithms;
-
-import javax.crypto.Mac;
-import javax.crypto.spec.SecretKeySpec;
-import java.nio.charset.StandardCharsets;
-import java.security.*;
-
-/**
- * Class used to perform the signature hash calculations.
- *
- * This class is thread-safe.
- */
-class CryptoHelper {
-
- private static final byte JWT_PART_SEPARATOR = (byte) 46;
-
- /**
- * Verify signature for JWT header and payload.
- *
- * @param algorithm algorithm name.
- * @param secretBytes algorithm secret.
- * @param header JWT header.
- * @param payload JWT payload.
- * @param signatureBytes JWT signature.
- * @return true if signature is valid.
- * @throws NoSuchAlgorithmException if the algorithm is not supported.
- * @throws InvalidKeyException if the given key is inappropriate for initializing the specified algorithm.
- */
-
- boolean verifySignatureFor(
- String algorithm,
- byte[] secretBytes,
- String header,
- String payload,
- byte[] signatureBytes
- ) throws NoSuchAlgorithmException, InvalidKeyException {
- return verifySignatureFor(algorithm, secretBytes,
- header.getBytes(StandardCharsets.UTF_8), payload.getBytes(StandardCharsets.UTF_8), signatureBytes);
- }
-
- /**
- * Verify signature for JWT header and payload.
- *
- * @param algorithm algorithm name.
- * @param secretBytes algorithm secret.
- * @param headerBytes JWT header.
- * @param payloadBytes JWT payload.
- * @param signatureBytes JWT signature.
- * @return true if signature is valid.
- * @throws NoSuchAlgorithmException if the algorithm is not supported.
- * @throws InvalidKeyException if the given key is inappropriate for initializing the specified algorithm.
- */
-
- boolean verifySignatureFor(
- String algorithm,
- byte[] secretBytes,
- byte[] headerBytes,
- byte[] payloadBytes,
- byte[] signatureBytes
- ) throws NoSuchAlgorithmException, InvalidKeyException {
- return MessageDigest.isEqual(createSignatureFor(algorithm, secretBytes, headerBytes, payloadBytes),
- signatureBytes);
- }
-
- /**
- * Verify signature for JWT header and payload.
- *
- * @param algorithm algorithm name.
- * @param publicKey algorithm public key.
- * @param header JWT header.
- * @param payload JWT payload.
- * @param signatureBytes JWT signature.
- * @return true if signature is valid.
- * @throws NoSuchAlgorithmException if the algorithm is not supported.
- * @throws InvalidKeyException if the given key is inappropriate for initializing the specified algorithm.
- */
- boolean verifySignatureFor(
- String algorithm,
- PublicKey publicKey,
- String header,
- String payload,
- byte[] signatureBytes
- ) throws NoSuchAlgorithmException, InvalidKeyException, SignatureException {
- return verifySignatureFor(algorithm, publicKey, header.getBytes(StandardCharsets.UTF_8),
- payload.getBytes(StandardCharsets.UTF_8), signatureBytes);
- }
-
- /**
- * Verify signature for JWT header and payload using a public key.
- *
- * @param algorithm algorithm name.
- * @param publicKey the public key to use for verification.
- * @param headerBytes JWT header.
- * @param payloadBytes JWT payload.
- * @param signatureBytes JWT signature.
- * @return true if signature is valid.
- * @throws NoSuchAlgorithmException if the algorithm is not supported.
- * @throws InvalidKeyException if the given key is inappropriate for initializing the specified algorithm.
- */
- boolean verifySignatureFor(
- String algorithm,
- PublicKey publicKey,
- byte[] headerBytes,
- byte[] payloadBytes,
- byte[] signatureBytes
- ) throws NoSuchAlgorithmException, InvalidKeyException, SignatureException {
- final Signature s = Signature.getInstance(algorithm);
- s.initVerify(publicKey);
- s.update(headerBytes);
- s.update(JWT_PART_SEPARATOR);
- s.update(payloadBytes);
- return s.verify(signatureBytes);
- }
-
- /**
- * Create signature for JWT header and payload using a private key.
- *
- * @param algorithm algorithm name.
- * @param privateKey the private key to use for signing.
- * @param headerBytes JWT header.
- * @param payloadBytes JWT payload.
- * @return the signature bytes.
- * @throws NoSuchAlgorithmException if the algorithm is not supported.
- * @throws InvalidKeyException if the given key is inappropriate for initializing the specified algorithm.
- * @throws SignatureException if this signature object is not initialized properly
- * or if this signature algorithm is unable to process the input data provided.
- */
- byte[] createSignatureFor(
- String algorithm,
- PrivateKey privateKey,
- byte[] headerBytes,
- byte[] payloadBytes
- ) throws NoSuchAlgorithmException, InvalidKeyException, SignatureException {
- final Signature s = Signature.getInstance(algorithm);
- s.initSign(privateKey);
- s.update(headerBytes);
- s.update(JWT_PART_SEPARATOR);
- s.update(payloadBytes);
- return s.sign();
- }
-
- /**
- * Create signature for JWT header and payload.
- *
- * @param algorithm algorithm name.
- * @param secretBytes algorithm secret.
- * @param headerBytes JWT header.
- * @param payloadBytes JWT payload.
- * @return the signature bytes.
- * @throws NoSuchAlgorithmException if the algorithm is not supported.
- * @throws InvalidKeyException if the given key is inappropriate for initializing the specified algorithm.
- */
- byte[] createSignatureFor(
- String algorithm,
- byte[] secretBytes,
- byte[] headerBytes,
- byte[] payloadBytes
- ) throws NoSuchAlgorithmException, InvalidKeyException {
- final Mac mac = Mac.getInstance(algorithm);
- mac.init(new SecretKeySpec(secretBytes, algorithm));
- mac.update(headerBytes);
- mac.update(JWT_PART_SEPARATOR);
- return mac.doFinal(payloadBytes);
- }
-
- /**
- * Create signature.
- * To get the correct JWT Signature, ensure the content is in the format {HEADER}.{PAYLOAD}
- *
- * @param algorithm algorithm name.
- * @param secretBytes algorithm secret.
- * @param contentBytes the content to be signed.
- * @return the signature bytes.
- * @throws NoSuchAlgorithmException if the algorithm is not supported.
- * @throws InvalidKeyException if the given key is inappropriate for initializing the specified algorithm.
- */
- byte[] createSignatureFor(String algorithm, byte[] secretBytes, byte[] contentBytes)
- throws NoSuchAlgorithmException, InvalidKeyException {
- final Mac mac = Mac.getInstance(algorithm);
- mac.init(new SecretKeySpec(secretBytes, algorithm));
- return mac.doFinal(contentBytes);
- }
-
- /**
- * Create signature using a private key.
- * To get the correct JWT Signature, ensure the content is in the format {HEADER}.{PAYLOAD}
- *
- * @param algorithm algorithm name.
- * @param privateKey the private key to use for signing.
- * @param contentBytes the content to be signed.
- * @return the signature bytes.
- * @throws NoSuchAlgorithmException if the algorithm is not supported.
- * @throws InvalidKeyException if the given key is inappropriate for initializing the specified algorithm.
- * @throws SignatureException if this signature object is not initialized properly
- * or if this signature algorithm is unable to process the input data provided.
- */
-
- byte[] createSignatureFor(
- String algorithm,
- PrivateKey privateKey,
- byte[] contentBytes
- ) throws NoSuchAlgorithmException, InvalidKeyException, SignatureException {
- final Signature s = Signature.getInstance(algorithm);
- s.initSign(privateKey);
- s.update(contentBytes);
- return s.sign();
- }
-}
diff --git a/lib/src/main/java/com/auth0/jwt/algorithms/ECDSAAlgorithm.java b/lib/src/main/java/com/auth0/jwt/algorithms/ECDSAAlgorithm.java
deleted file mode 100644
index b3046097..00000000
--- a/lib/src/main/java/com/auth0/jwt/algorithms/ECDSAAlgorithm.java
+++ /dev/null
@@ -1,306 +0,0 @@
-package com.auth0.jwt.algorithms;
-
-import com.auth0.jwt.exceptions.SignatureGenerationException;
-import com.auth0.jwt.exceptions.SignatureVerificationException;
-import com.auth0.jwt.interfaces.DecodedJWT;
-import com.auth0.jwt.interfaces.ECDSAKeyProvider;
-
-import java.math.BigInteger;
-import java.security.InvalidKeyException;
-import java.security.NoSuchAlgorithmException;
-import java.security.SignatureException;
-import java.security.interfaces.ECPrivateKey;
-import java.security.interfaces.ECPublicKey;
-import java.util.Base64;
-
-/**
- * Subclass representing an Elliptic Curve signing algorithm
- *
- * This class is thread-safe.
- */
-class ECDSAAlgorithm extends Algorithm {
-
- private final ECDSAKeyProvider keyProvider;
- private final CryptoHelper crypto;
- private final int ecNumberSize;
-
- //Visible for testing
- ECDSAAlgorithm(CryptoHelper crypto, String id, String algorithm, int ecNumberSize, ECDSAKeyProvider keyProvider)
- throws IllegalArgumentException {
- super(id, algorithm);
- if (keyProvider == null) {
- throw new IllegalArgumentException("The Key Provider cannot be null.");
- }
- this.keyProvider = keyProvider;
- this.crypto = crypto;
- this.ecNumberSize = ecNumberSize;
- }
-
- ECDSAAlgorithm(String id, String algorithm, int ecNumberSize, ECDSAKeyProvider keyProvider)
- throws IllegalArgumentException {
- this(new CryptoHelper(), id, algorithm, ecNumberSize, keyProvider);
- }
-
- @Override
- public void verify(DecodedJWT jwt) throws SignatureVerificationException {
- try {
- byte[] signatureBytes = Base64.getUrlDecoder().decode(jwt.getSignature());
- ECPublicKey publicKey = keyProvider.getPublicKeyById(jwt.getKeyId());
- if (publicKey == null) {
- throw new IllegalStateException("The given Public Key is null.");
- }
- validateSignatureStructure(signatureBytes, publicKey);
- boolean valid = crypto.verifySignatureFor(
- getDescription(), publicKey, jwt.getHeader(), jwt.getPayload(), JOSEToDER(signatureBytes));
-
- if (!valid) {
- throw new SignatureVerificationException(this);
- }
- } catch (NoSuchAlgorithmException | SignatureException | InvalidKeyException
- | IllegalStateException | IllegalArgumentException e) {
- throw new SignatureVerificationException(this, e);
- }
- }
-
- @Override
- public byte[] sign(byte[] headerBytes, byte[] payloadBytes) throws SignatureGenerationException {
- try {
- ECPrivateKey privateKey = keyProvider.getPrivateKey();
- if (privateKey == null) {
- throw new IllegalStateException("The given Private Key is null.");
- }
- byte[] signature = crypto.createSignatureFor(getDescription(), privateKey, headerBytes, payloadBytes);
- return DERToJOSE(signature);
- } catch (NoSuchAlgorithmException | SignatureException | InvalidKeyException | IllegalStateException e) {
- throw new SignatureGenerationException(this, e);
- }
- }
-
- @Override
- public byte[] sign(byte[] contentBytes) throws SignatureGenerationException {
- try {
- ECPrivateKey privateKey = keyProvider.getPrivateKey();
- if (privateKey == null) {
- throw new IllegalStateException("The given Private Key is null.");
- }
- byte[] signature = crypto.createSignatureFor(getDescription(), privateKey, contentBytes);
- return DERToJOSE(signature);
- } catch (NoSuchAlgorithmException | SignatureException | InvalidKeyException | IllegalStateException e) {
- throw new SignatureGenerationException(this, e);
- }
- }
-
- @Override
- public String getSigningKeyId() {
- return keyProvider.getPrivateKeyId();
- }
-
- //Visible for testing
- byte[] DERToJOSE(byte[] derSignature) throws SignatureException {
- // DER Structure: http://crypto.stackexchange.com/a/1797
- boolean derEncoded = derSignature[0] == 0x30 && derSignature.length != ecNumberSize * 2;
- if (!derEncoded) {
- throw new SignatureException("Invalid DER signature format.");
- }
-
- final byte[] joseSignature = new byte[ecNumberSize * 2];
-
- //Skip 0x30
- int offset = 1;
- if (derSignature[1] == (byte) 0x81) {
- //Skip sign
- offset++;
- }
-
- //Convert to unsigned. Should match DER length - offset
- int encodedLength = derSignature[offset++] & 0xff;
- if (encodedLength != derSignature.length - offset) {
- throw new SignatureException("Invalid DER signature format.");
- }
-
- //Skip 0x02
- offset++;
-
- //Obtain R number length (Includes padding) and skip it
- int rlength = derSignature[offset++];
- if (rlength > ecNumberSize + 1) {
- throw new SignatureException("Invalid DER signature format.");
- }
- int rpadding = ecNumberSize - rlength;
- //Retrieve R number
- System.arraycopy(derSignature, offset + Math.max(-rpadding, 0),
- joseSignature, Math.max(rpadding, 0), rlength + Math.min(rpadding, 0));
-
- //Skip R number and 0x02
- offset += rlength + 1;
-
- //Obtain S number length. (Includes padding)
- int slength = derSignature[offset++];
- if (slength > ecNumberSize + 1) {
- throw new SignatureException("Invalid DER signature format.");
- }
- int spadding = ecNumberSize - slength;
- //Retrieve R number
- System.arraycopy(derSignature, offset + Math.max(-spadding, 0), joseSignature,
- ecNumberSize + Math.max(spadding, 0), slength + Math.min(spadding, 0));
-
- return joseSignature;
- }
-
- /**
- * Added check for extra protection against CVE-2022-21449.
- * This method ensures the signature's structure is as expected.
- *
- * @param joseSignature is the signature from the JWT
- * @param publicKey public key used to verify the JWT
- * @throws SignatureException if the signature's structure is not as per expectation
- */
- // Visible for testing
- void validateSignatureStructure(byte[] joseSignature, ECPublicKey publicKey) throws SignatureException {
- // check signature length, moved this check from JOSEToDER method
- if (joseSignature.length != ecNumberSize * 2) {
- throw new SignatureException("Invalid JOSE signature format.");
- }
-
- if (isAllZeros(joseSignature)) {
- throw new SignatureException("Invalid signature format.");
- }
-
- // get R
- byte[] rBytes = new byte[ecNumberSize];
- System.arraycopy(joseSignature, 0, rBytes, 0, ecNumberSize);
- if (isAllZeros(rBytes)) {
- throw new SignatureException("Invalid signature format.");
- }
-
- // get S
- byte[] sBytes = new byte[ecNumberSize];
- System.arraycopy(joseSignature, ecNumberSize, sBytes, 0, ecNumberSize);
- if (isAllZeros(sBytes)) {
- throw new SignatureException("Invalid signature format.");
- }
-
- //moved this check from JOSEToDER method
- int rPadding = countPadding(joseSignature, 0, ecNumberSize);
- int sPadding = countPadding(joseSignature, ecNumberSize, joseSignature.length);
- int rLength = ecNumberSize - rPadding;
- int sLength = ecNumberSize - sPadding;
-
- int length = 2 + rLength + 2 + sLength;
- if (length > 255) {
- throw new SignatureException("Invalid JOSE signature format.");
- }
-
- BigInteger order = publicKey.getParams().getOrder();
- BigInteger r = new BigInteger(1, rBytes);
- BigInteger s = new BigInteger(1, sBytes);
-
- // R and S must be less than N
- if (order.compareTo(r) < 1) {
- throw new SignatureException("Invalid signature format.");
- }
-
- if (order.compareTo(s) < 1) {
- throw new SignatureException("Invalid signature format.");
- }
- }
-
- //Visible for testing
- byte[] JOSEToDER(byte[] joseSignature) throws SignatureException {
- // Retrieve R and S number's length and padding.
- int rPadding = countPadding(joseSignature, 0, ecNumberSize);
- int sPadding = countPadding(joseSignature, ecNumberSize, joseSignature.length);
- int rLength = ecNumberSize - rPadding;
- int sLength = ecNumberSize - sPadding;
-
- int length = 2 + rLength + 2 + sLength;
-
- final byte[] derSignature;
- int offset;
- if (length > 0x7f) {
- derSignature = new byte[3 + length];
- derSignature[1] = (byte) 0x81;
- offset = 2;
- } else {
- derSignature = new byte[2 + length];
- offset = 1;
- }
-
- // DER Structure: http://crypto.stackexchange.com/a/1797
- // Header with signature length info
- derSignature[0] = (byte) 0x30;
- derSignature[offset++] = (byte) (length & 0xff);
-
- // Header with "min R" number length
- derSignature[offset++] = (byte) 0x02;
- derSignature[offset++] = (byte) rLength;
-
- // R number
- if (rPadding < 0) {
- //Sign
- derSignature[offset++] = (byte) 0x00;
- System.arraycopy(joseSignature, 0, derSignature, offset, ecNumberSize);
- offset += ecNumberSize;
- } else {
- int copyLength = Math.min(ecNumberSize, rLength);
- System.arraycopy(joseSignature, rPadding, derSignature, offset, copyLength);
- offset += copyLength;
- }
-
- // Header with "min S" number length
- derSignature[offset++] = (byte) 0x02;
- derSignature[offset++] = (byte) sLength;
-
- // S number
- if (sPadding < 0) {
- //Sign
- derSignature[offset++] = (byte) 0x00;
- System.arraycopy(joseSignature, ecNumberSize, derSignature, offset, ecNumberSize);
- } else {
- System.arraycopy(joseSignature, ecNumberSize + sPadding, derSignature, offset,
- Math.min(ecNumberSize, sLength));
- }
-
- return derSignature;
- }
-
- private boolean isAllZeros(byte[] bytes) {
- for (byte b : bytes) {
- if (b != 0) {
- return false;
- }
- }
- return true;
- }
-
- private int countPadding(byte[] bytes, int fromIndex, int toIndex) {
- int padding = 0;
- while (fromIndex + padding < toIndex && bytes[fromIndex + padding] == 0) {
- padding++;
- }
- return (bytes[fromIndex + padding] & 0xff) > 0x7f ? padding - 1 : padding;
- }
-
- //Visible for testing
- static ECDSAKeyProvider providerForKeys(final ECPublicKey publicKey, final ECPrivateKey privateKey) {
- if (publicKey == null && privateKey == null) {
- throw new IllegalArgumentException("Both provided Keys cannot be null.");
- }
- return new ECDSAKeyProvider() {
- @Override
- public ECPublicKey getPublicKeyById(String keyId) {
- return publicKey;
- }
-
- @Override
- public ECPrivateKey getPrivateKey() {
- return privateKey;
- }
-
- @Override
- public String getPrivateKeyId() {
- return null;
- }
- };
- }
-}
diff --git a/lib/src/main/java/com/auth0/jwt/algorithms/HMACAlgorithm.java b/lib/src/main/java/com/auth0/jwt/algorithms/HMACAlgorithm.java
deleted file mode 100644
index 0306e7c4..00000000
--- a/lib/src/main/java/com/auth0/jwt/algorithms/HMACAlgorithm.java
+++ /dev/null
@@ -1,81 +0,0 @@
-package com.auth0.jwt.algorithms;
-
-import com.auth0.jwt.exceptions.SignatureGenerationException;
-import com.auth0.jwt.exceptions.SignatureVerificationException;
-import com.auth0.jwt.interfaces.DecodedJWT;
-
-import java.nio.charset.StandardCharsets;
-import java.security.InvalidKeyException;
-import java.security.NoSuchAlgorithmException;
-import java.util.Arrays;
-import java.util.Base64;
-
-/**
- * Subclass representing an Hash-based MAC signing algorithm
- *
- * This class is thread-safe.
- */
-class HMACAlgorithm extends Algorithm {
-
- private final CryptoHelper crypto;
- private final byte[] secret;
-
- //Visible for testing
- HMACAlgorithm(CryptoHelper crypto, String id, String algorithm, byte[] secretBytes)
- throws IllegalArgumentException {
- super(id, algorithm);
- if (secretBytes == null) {
- throw new IllegalArgumentException("The Secret cannot be null");
- }
- this.secret = Arrays.copyOf(secretBytes, secretBytes.length);
- this.crypto = crypto;
- }
-
- HMACAlgorithm(String id, String algorithm, byte[] secretBytes) throws IllegalArgumentException {
- this(new CryptoHelper(), id, algorithm, secretBytes);
- }
-
- HMACAlgorithm(String id, String algorithm, String secret) throws IllegalArgumentException {
- this(new CryptoHelper(), id, algorithm, getSecretBytes(secret));
- }
-
- //Visible for testing
- static byte[] getSecretBytes(String secret) throws IllegalArgumentException {
- if (secret == null) {
- throw new IllegalArgumentException("The Secret cannot be null");
- }
- return secret.getBytes(StandardCharsets.UTF_8);
- }
-
- @Override
- public void verify(DecodedJWT jwt) throws SignatureVerificationException {
- try {
- byte[] signatureBytes = Base64.getUrlDecoder().decode(jwt.getSignature());
- boolean valid = crypto.verifySignatureFor(
- getDescription(), secret, jwt.getHeader(), jwt.getPayload(), signatureBytes);
- if (!valid) {
- throw new SignatureVerificationException(this);
- }
- } catch (IllegalStateException | InvalidKeyException | NoSuchAlgorithmException | IllegalArgumentException e) {
- throw new SignatureVerificationException(this, e);
- }
- }
-
- @Override
- public byte[] sign(byte[] headerBytes, byte[] payloadBytes) throws SignatureGenerationException {
- try {
- return crypto.createSignatureFor(getDescription(), secret, headerBytes, payloadBytes);
- } catch (NoSuchAlgorithmException | InvalidKeyException e) {
- throw new SignatureGenerationException(this, e);
- }
- }
-
- @Override
- public byte[] sign(byte[] contentBytes) throws SignatureGenerationException {
- try {
- return crypto.createSignatureFor(getDescription(), secret, contentBytes);
- } catch (NoSuchAlgorithmException | InvalidKeyException e) {
- throw new SignatureGenerationException(this, e);
- }
- }
-}
diff --git a/lib/src/main/java/com/auth0/jwt/algorithms/NoneAlgorithm.java b/lib/src/main/java/com/auth0/jwt/algorithms/NoneAlgorithm.java
deleted file mode 100644
index 5c6c0fc5..00000000
--- a/lib/src/main/java/com/auth0/jwt/algorithms/NoneAlgorithm.java
+++ /dev/null
@@ -1,36 +0,0 @@
-package com.auth0.jwt.algorithms;
-
-import com.auth0.jwt.exceptions.SignatureGenerationException;
-import com.auth0.jwt.exceptions.SignatureVerificationException;
-import com.auth0.jwt.interfaces.DecodedJWT;
-import java.util.Base64;
-
-class NoneAlgorithm extends Algorithm {
-
- NoneAlgorithm() {
- super("none", "none");
- }
-
- @Override
- public void verify(DecodedJWT jwt) throws SignatureVerificationException {
- try {
- byte[] signatureBytes = Base64.getUrlDecoder().decode(jwt.getSignature());
-
- if (signatureBytes.length > 0) {
- throw new SignatureVerificationException(this);
- }
- } catch (IllegalArgumentException e) {
- throw new SignatureVerificationException(this, e);
- }
- }
-
- @Override
- public byte[] sign(byte[] headerBytes, byte[] payloadBytes) throws SignatureGenerationException {
- return new byte[0];
- }
-
- @Override
- public byte[] sign(byte[] contentBytes) throws SignatureGenerationException {
- return new byte[0];
- }
-}
diff --git a/lib/src/main/java/com/auth0/jwt/algorithms/RSAAlgorithm.java b/lib/src/main/java/com/auth0/jwt/algorithms/RSAAlgorithm.java
deleted file mode 100644
index ca892e60..00000000
--- a/lib/src/main/java/com/auth0/jwt/algorithms/RSAAlgorithm.java
+++ /dev/null
@@ -1,112 +0,0 @@
-package com.auth0.jwt.algorithms;
-
-import com.auth0.jwt.exceptions.SignatureGenerationException;
-import com.auth0.jwt.exceptions.SignatureVerificationException;
-import com.auth0.jwt.interfaces.DecodedJWT;
-import com.auth0.jwt.interfaces.RSAKeyProvider;
-
-import java.security.InvalidKeyException;
-import java.security.NoSuchAlgorithmException;
-import java.security.SignatureException;
-import java.security.interfaces.RSAPrivateKey;
-import java.security.interfaces.RSAPublicKey;
-import java.util.Base64;
-
-/**
- * Subclass representing an RSA signing algorithm
- *
- * This class is thread-safe.
- */
-class RSAAlgorithm extends Algorithm {
-
- private final RSAKeyProvider keyProvider;
- private final CryptoHelper crypto;
-
- //Visible for testing
- RSAAlgorithm(CryptoHelper crypto, String id, String algorithm, RSAKeyProvider keyProvider)
- throws IllegalArgumentException {
- super(id, algorithm);
- if (keyProvider == null) {
- throw new IllegalArgumentException("The Key Provider cannot be null.");
- }
- this.keyProvider = keyProvider;
- this.crypto = crypto;
- }
-
- RSAAlgorithm(String id, String algorithm, RSAKeyProvider keyProvider) throws IllegalArgumentException {
- this(new CryptoHelper(), id, algorithm, keyProvider);
- }
-
- @Override
- public void verify(DecodedJWT jwt) throws SignatureVerificationException {
- try {
- byte[] signatureBytes = Base64.getUrlDecoder().decode(jwt.getSignature());
- RSAPublicKey publicKey = keyProvider.getPublicKeyById(jwt.getKeyId());
- if (publicKey == null) {
- throw new IllegalStateException("The given Public Key is null.");
- }
- boolean valid = crypto.verifySignatureFor(
- getDescription(), publicKey, jwt.getHeader(), jwt.getPayload(), signatureBytes);
- if (!valid) {
- throw new SignatureVerificationException(this);
- }
- } catch (NoSuchAlgorithmException | SignatureException | InvalidKeyException
- | IllegalArgumentException | IllegalStateException e) {
- throw new SignatureVerificationException(this, e);
- }
- }
-
- @Override
- public byte[] sign(byte[] headerBytes, byte[] payloadBytes) throws SignatureGenerationException {
- try {
- RSAPrivateKey privateKey = keyProvider.getPrivateKey();
- if (privateKey == null) {
- throw new IllegalStateException("The given Private Key is null.");
- }
- return crypto.createSignatureFor(getDescription(), privateKey, headerBytes, payloadBytes);
- } catch (NoSuchAlgorithmException | SignatureException | InvalidKeyException | IllegalStateException e) {
- throw new SignatureGenerationException(this, e);
- }
- }
-
- @Override
- public byte[] sign(byte[] contentBytes) throws SignatureGenerationException {
- try {
- RSAPrivateKey privateKey = keyProvider.getPrivateKey();
- if (privateKey == null) {
- throw new IllegalStateException("The given Private Key is null.");
- }
- return crypto.createSignatureFor(getDescription(), privateKey, contentBytes);
- } catch (NoSuchAlgorithmException | SignatureException | InvalidKeyException | IllegalStateException e) {
- throw new SignatureGenerationException(this, e);
- }
- }
-
- @Override
- public String getSigningKeyId() {
- return keyProvider.getPrivateKeyId();
- }
-
- //Visible for testing
- static RSAKeyProvider providerForKeys(final RSAPublicKey publicKey, final RSAPrivateKey privateKey) {
- if (publicKey == null && privateKey == null) {
- throw new IllegalArgumentException("Both provided Keys cannot be null.");
- }
- return new RSAKeyProvider() {
- @Override
- public RSAPublicKey getPublicKeyById(String keyId) {
- return publicKey;
- }
-
- @Override
- public RSAPrivateKey getPrivateKey() {
- return privateKey;
- }
-
- @Override
- public String getPrivateKeyId() {
- return null;
- }
- };
- }
-}
diff --git a/lib/src/main/java/com/auth0/jwt/exceptions/AlgorithmMismatchException.java b/lib/src/main/java/com/auth0/jwt/exceptions/AlgorithmMismatchException.java
deleted file mode 100644
index d6b71205..00000000
--- a/lib/src/main/java/com/auth0/jwt/exceptions/AlgorithmMismatchException.java
+++ /dev/null
@@ -1,10 +0,0 @@
-package com.auth0.jwt.exceptions;
-
-/**
- * The exception that will be thrown if the exception doesn't match the one mentioned in the JWT Header.
- */
-public class AlgorithmMismatchException extends JWTVerificationException {
- public AlgorithmMismatchException(String message) {
- super(message);
- }
-}
diff --git a/lib/src/main/java/com/auth0/jwt/exceptions/IncorrectClaimException.java b/lib/src/main/java/com/auth0/jwt/exceptions/IncorrectClaimException.java
deleted file mode 100644
index 712e937b..00000000
--- a/lib/src/main/java/com/auth0/jwt/exceptions/IncorrectClaimException.java
+++ /dev/null
@@ -1,44 +0,0 @@
-package com.auth0.jwt.exceptions;
-
-import com.auth0.jwt.interfaces.Claim;
-
-/**
- * This exception is thrown when the expected value is not found while verifying the Claims.
- */
-public class IncorrectClaimException extends InvalidClaimException {
- private final String claimName;
-
- private final Claim claimValue;
-
- /**
- * Used internally to construct the IncorrectClaimException which is thrown when there is verification
- * failure for a Claim that exists.
- *
- * @param message The error message
- * @param claimName The Claim name for which verification failed
- * @param claim The Claim value for which verification failed
- */
- public IncorrectClaimException(String message, String claimName, Claim claim) {
- super(message);
- this.claimName = claimName;
- this.claimValue = claim;
- }
-
- /**
- * This method can be used to fetch the name for which the Claim verification failed.
- *
- * @return The claim name for which the verification failed.
- */
- public String getClaimName() {
- return claimName;
- }
-
- /**
- * This method can be used to fetch the value for which the Claim verification failed.
- *
- * @return The value for which the verification failed
- */
- public Claim getClaimValue() {
- return claimValue;
- }
-}
\ No newline at end of file
diff --git a/lib/src/main/java/com/auth0/jwt/exceptions/InvalidClaimException.java b/lib/src/main/java/com/auth0/jwt/exceptions/InvalidClaimException.java
deleted file mode 100644
index c5b8eb64..00000000
--- a/lib/src/main/java/com/auth0/jwt/exceptions/InvalidClaimException.java
+++ /dev/null
@@ -1,10 +0,0 @@
-package com.auth0.jwt.exceptions;
-
-/**
- * The exception that will be thrown while verifying Claims of a JWT.
- */
-public class InvalidClaimException extends JWTVerificationException {
- public InvalidClaimException(String message) {
- super(message);
- }
-}
\ No newline at end of file
diff --git a/lib/src/main/java/com/auth0/jwt/exceptions/JWTCreationException.java b/lib/src/main/java/com/auth0/jwt/exceptions/JWTCreationException.java
deleted file mode 100644
index c7e162ea..00000000
--- a/lib/src/main/java/com/auth0/jwt/exceptions/JWTCreationException.java
+++ /dev/null
@@ -1,10 +0,0 @@
-package com.auth0.jwt.exceptions;
-
-/**
- * The exception that is thrown when a JWT cannot be created.
- */
-public class JWTCreationException extends RuntimeException {
- public JWTCreationException(String message, Throwable cause) {
- super(message, cause);
- }
-}
diff --git a/lib/src/main/java/com/auth0/jwt/exceptions/JWTDecodeException.java b/lib/src/main/java/com/auth0/jwt/exceptions/JWTDecodeException.java
deleted file mode 100644
index 448714e9..00000000
--- a/lib/src/main/java/com/auth0/jwt/exceptions/JWTDecodeException.java
+++ /dev/null
@@ -1,14 +0,0 @@
-package com.auth0.jwt.exceptions;
-
-/**
- * The exception that is thrown when any part of the token contained an invalid JWT or JSON format.
- */
-public class JWTDecodeException extends JWTVerificationException {
- public JWTDecodeException(String message) {
- this(message, null);
- }
-
- public JWTDecodeException(String message, Throwable cause) {
- super(message, cause);
- }
-}
diff --git a/lib/src/main/java/com/auth0/jwt/exceptions/JWTVerificationException.java b/lib/src/main/java/com/auth0/jwt/exceptions/JWTVerificationException.java
deleted file mode 100644
index dd36dcd3..00000000
--- a/lib/src/main/java/com/auth0/jwt/exceptions/JWTVerificationException.java
+++ /dev/null
@@ -1,14 +0,0 @@
-package com.auth0.jwt.exceptions;
-
-/**
- * Parent to all the exception thrown while verifying a JWT.
- */
-public class JWTVerificationException extends RuntimeException {
- public JWTVerificationException(String message) {
- this(message, null);
- }
-
- public JWTVerificationException(String message, Throwable cause) {
- super(message, cause);
- }
-}
diff --git a/lib/src/main/java/com/auth0/jwt/exceptions/MissingClaimException.java b/lib/src/main/java/com/auth0/jwt/exceptions/MissingClaimException.java
deleted file mode 100644
index 3bcc2121..00000000
--- a/lib/src/main/java/com/auth0/jwt/exceptions/MissingClaimException.java
+++ /dev/null
@@ -1,23 +0,0 @@
-package com.auth0.jwt.exceptions;
-
-/**
- * This exception is thrown when the claim to be verified is missing.
- */
-public class MissingClaimException extends InvalidClaimException {
-
- private final String claimName;
-
- public MissingClaimException(String claimName) {
- super(String.format("The Claim '%s' is not present in the JWT.", claimName));
- this.claimName = claimName;
- }
-
- /**
- * This method can be used to fetch the name for which the Claim is missing during the verification.
- *
- * @return The name of the Claim that doesn't exist.
- */
- public String getClaimName() {
- return claimName;
- }
-}
diff --git a/lib/src/main/java/com/auth0/jwt/exceptions/SignatureGenerationException.java b/lib/src/main/java/com/auth0/jwt/exceptions/SignatureGenerationException.java
deleted file mode 100644
index 4b7668a0..00000000
--- a/lib/src/main/java/com/auth0/jwt/exceptions/SignatureGenerationException.java
+++ /dev/null
@@ -1,12 +0,0 @@
-package com.auth0.jwt.exceptions;
-
-import com.auth0.jwt.algorithms.Algorithm;
-
-/**
- * The exception that is thrown when signature is not able to be generated.
- */
-public class SignatureGenerationException extends JWTCreationException {
- public SignatureGenerationException(Algorithm algorithm, Throwable cause) {
- super("The Token's Signature couldn't be generated when signing using the Algorithm: " + algorithm, cause);
- }
-}
diff --git a/lib/src/main/java/com/auth0/jwt/exceptions/SignatureVerificationException.java b/lib/src/main/java/com/auth0/jwt/exceptions/SignatureVerificationException.java
deleted file mode 100644
index fa7c3cab..00000000
--- a/lib/src/main/java/com/auth0/jwt/exceptions/SignatureVerificationException.java
+++ /dev/null
@@ -1,16 +0,0 @@
-package com.auth0.jwt.exceptions;
-
-import com.auth0.jwt.algorithms.Algorithm;
-
-/**
- * The exception that is thrown if the Signature verification fails.
- */
-public class SignatureVerificationException extends JWTVerificationException {
- public SignatureVerificationException(Algorithm algorithm) {
- this(algorithm, null);
- }
-
- public SignatureVerificationException(Algorithm algorithm, Throwable cause) {
- super("The Token's Signature resulted invalid when verified using the Algorithm: " + algorithm, cause);
- }
-}
diff --git a/lib/src/main/java/com/auth0/jwt/exceptions/TokenExpiredException.java b/lib/src/main/java/com/auth0/jwt/exceptions/TokenExpiredException.java
deleted file mode 100644
index 42ab090d..00000000
--- a/lib/src/main/java/com/auth0/jwt/exceptions/TokenExpiredException.java
+++ /dev/null
@@ -1,22 +0,0 @@
-package com.auth0.jwt.exceptions;
-
-import java.time.Instant;
-
-/**
- * The exception that is thrown if the token is expired.
- */
-public class TokenExpiredException extends JWTVerificationException {
-
- private static final long serialVersionUID = -7076928975713577708L;
-
- private final Instant expiredOn;
-
- public TokenExpiredException(String message, Instant expiredOn) {
- super(message);
- this.expiredOn = expiredOn;
- }
-
- public Instant getExpiredOn() {
- return expiredOn;
- }
-}
diff --git a/lib/src/main/java/com/auth0/jwt/impl/BasicHeader.java b/lib/src/main/java/com/auth0/jwt/impl/BasicHeader.java
deleted file mode 100644
index 5a881ab5..00000000
--- a/lib/src/main/java/com/auth0/jwt/impl/BasicHeader.java
+++ /dev/null
@@ -1,71 +0,0 @@
-package com.auth0.jwt.impl;
-
-import com.auth0.jwt.interfaces.Claim;
-import com.auth0.jwt.interfaces.Header;
-import com.fasterxml.jackson.core.ObjectCodec;
-import com.fasterxml.jackson.databind.JsonNode;
-
-import java.io.Serializable;
-import java.util.Collections;
-import java.util.Map;
-
-import static com.auth0.jwt.impl.JsonNodeClaim.extractClaim;
-
-/**
- * The BasicHeader class implements the Header interface.
- */
-class BasicHeader implements Header, Serializable {
- private static final long serialVersionUID = -4659137688548605095L;
-
- private final String algorithm;
- private final String type;
- private final String contentType;
- private final String keyId;
- private final Map tree;
- private final ObjectCodec objectCodec;
-
- BasicHeader(
- String algorithm,
- String type,
- String contentType,
- String keyId,
- Map tree,
- ObjectCodec objectCodec
- ) {
- this.algorithm = algorithm;
- this.type = type;
- this.contentType = contentType;
- this.keyId = keyId;
- this.tree = tree == null ? Collections.emptyMap() : Collections.unmodifiableMap(tree);
- this.objectCodec = objectCodec;
- }
-
- Map getTree() {
- return tree;
- }
-
- @Override
- public String getAlgorithm() {
- return algorithm;
- }
-
- @Override
- public String getType() {
- return type;
- }
-
- @Override
- public String getContentType() {
- return contentType;
- }
-
- @Override
- public String getKeyId() {
- return keyId;
- }
-
- @Override
- public Claim getHeaderClaim(String name) {
- return extractClaim(name, tree, objectCodec);
- }
-}
diff --git a/lib/src/main/java/com/auth0/jwt/impl/ClaimsHolder.java b/lib/src/main/java/com/auth0/jwt/impl/ClaimsHolder.java
deleted file mode 100644
index 30f6ab18..00000000
--- a/lib/src/main/java/com/auth0/jwt/impl/ClaimsHolder.java
+++ /dev/null
@@ -1,19 +0,0 @@
-package com.auth0.jwt.impl;
-
-import java.util.HashMap;
-import java.util.Map;
-
-/**
- * The ClaimsHolder class is just a wrapper for the Map of Claims used for building a JWT.
- */
-public abstract class ClaimsHolder {
- private Map claims;
-
- protected ClaimsHolder(Map claims) {
- this.claims = claims == null ? new HashMap<>() : claims;
- }
-
- Map getClaims() {
- return claims;
- }
-}
diff --git a/lib/src/main/java/com/auth0/jwt/impl/ClaimsSerializer.java b/lib/src/main/java/com/auth0/jwt/impl/ClaimsSerializer.java
deleted file mode 100644
index b1f8e6d3..00000000
--- a/lib/src/main/java/com/auth0/jwt/impl/ClaimsSerializer.java
+++ /dev/null
@@ -1,86 +0,0 @@
-package com.auth0.jwt.impl;
-
-import com.fasterxml.jackson.core.JsonGenerator;
-import com.fasterxml.jackson.databind.SerializerProvider;
-import com.fasterxml.jackson.databind.ser.std.StdSerializer;
-
-import java.io.IOException;
-import java.time.Instant;
-import java.util.Date;
-import java.util.List;
-import java.util.Map;
-
-/**
- * Custom serializer used to write the resulting JWT.
- *
- * @param the type this serializer operates on.
- */
-public class ClaimsSerializer extends StdSerializer {
-
- public ClaimsSerializer(Class t) {
- super(t);
- }
-
- @Override
- public void serialize(T holder, JsonGenerator gen, SerializerProvider provider) throws IOException {
- gen.writeStartObject();
- for (Map.Entry entry : holder.getClaims().entrySet()) {
- writeClaim(entry, gen);
- }
- gen.writeEndObject();
- }
-
- /**
- * Writes the given entry to the JSON representation. Custom claim serialization handling can override this method
- * to provide use-case specific serialization. Implementors who override this method must write
- * the field name and the field value.
- *
- * @param entry The entry that corresponds to the JSON field to write
- * @param gen The {@code JsonGenerator} to use
- * @throws IOException if there is either an underlying I/O problem or encoding issue at format layer
- */
- protected void writeClaim(Map.Entry entry, JsonGenerator gen) throws IOException {
- gen.writeFieldName(entry.getKey());
- handleSerialization(entry.getValue(), gen);
- }
-
- private static void handleSerialization(Object value, JsonGenerator gen) throws IOException {
- if (value instanceof Date) {
- gen.writeNumber(dateToSeconds((Date) value));
- } else if (value instanceof Instant) { // EXPIRES_AT, ISSUED_AT, NOT_BEFORE, custom Instant claims
- gen.writeNumber(instantToSeconds((Instant) value));
- } else if (value instanceof Map) {
- serializeMap((Map, ?>) value, gen);
- } else if (value instanceof List) {
- serializeList((List>) value, gen);
- } else {
- gen.writeObject(value);
- }
- }
-
- private static void serializeMap(Map, ?> map, JsonGenerator gen) throws IOException {
- gen.writeStartObject();
- for (Map.Entry, ?> entry : map.entrySet()) {
- gen.writeFieldName((String) entry.getKey());
- Object value = entry.getValue();
- handleSerialization(value, gen);
- }
- gen.writeEndObject();
- }
-
- private static void serializeList(List> list, JsonGenerator gen) throws IOException {
- gen.writeStartArray();
- for (Object entry : list) {
- handleSerialization(entry, gen);
- }
- gen.writeEndArray();
- }
-
- private static long instantToSeconds(Instant instant) {
- return instant.getEpochSecond();
- }
-
- private static long dateToSeconds(Date date) {
- return date.getTime() / 1000;
- }
-}
diff --git a/lib/src/main/java/com/auth0/jwt/impl/ExpectedCheckHolder.java b/lib/src/main/java/com/auth0/jwt/impl/ExpectedCheckHolder.java
deleted file mode 100644
index 6737031c..00000000
--- a/lib/src/main/java/com/auth0/jwt/impl/ExpectedCheckHolder.java
+++ /dev/null
@@ -1,25 +0,0 @@
-package com.auth0.jwt.impl;
-
-import com.auth0.jwt.interfaces.Claim;
-import com.auth0.jwt.interfaces.DecodedJWT;
-
-/**
- * This holds the checks that are run to verify a JWT.
- */
-public interface ExpectedCheckHolder {
- /**
- * The claim name that will be checked.
- *
- * @return the claim name
- */
- String getClaimName();
-
- /**
- * The verification that will be run.
- *
- * @param claim the claim for which verification is done
- * @param decodedJWT the JWT on which verification is done
- * @return whether the verification passed or not
- */
- boolean verify(Claim claim, DecodedJWT decodedJWT);
-}
diff --git a/lib/src/main/java/com/auth0/jwt/impl/HeaderClaimsHolder.java b/lib/src/main/java/com/auth0/jwt/impl/HeaderClaimsHolder.java
deleted file mode 100644
index 9b480116..00000000
--- a/lib/src/main/java/com/auth0/jwt/impl/HeaderClaimsHolder.java
+++ /dev/null
@@ -1,12 +0,0 @@
-package com.auth0.jwt.impl;
-
-import java.util.Map;
-
-/**
- * Holds the header claims when serializing a JWT.
- */
-public final class HeaderClaimsHolder extends ClaimsHolder {
- public HeaderClaimsHolder(Map claims) {
- super(claims);
- }
-}
diff --git a/lib/src/main/java/com/auth0/jwt/impl/HeaderDeserializer.java b/lib/src/main/java/com/auth0/jwt/impl/HeaderDeserializer.java
deleted file mode 100644
index ad6e4ce0..00000000
--- a/lib/src/main/java/com/auth0/jwt/impl/HeaderDeserializer.java
+++ /dev/null
@@ -1,50 +0,0 @@
-package com.auth0.jwt.impl;
-
-import com.auth0.jwt.HeaderParams;
-import com.auth0.jwt.exceptions.JWTDecodeException;
-import com.auth0.jwt.interfaces.Header;
-import com.fasterxml.jackson.core.JsonParser;
-import com.fasterxml.jackson.core.type.TypeReference;
-import com.fasterxml.jackson.databind.DeserializationContext;
-import com.fasterxml.jackson.databind.JsonNode;
-import com.fasterxml.jackson.databind.deser.std.StdDeserializer;
-
-import java.io.IOException;
-import java.util.Map;
-
-/**
- * Jackson deserializer implementation for converting from JWT Header parts.
- *
- * This class is thread-safe.
- *
- * @see JWTParser
- */
-class HeaderDeserializer extends StdDeserializer {
-
- HeaderDeserializer() {
- super(Header.class);
- }
-
- @Override
- public Header deserialize(JsonParser p, DeserializationContext ctxt) throws IOException {
- Map tree = p.getCodec().readValue(p, new TypeReference>() {
- });
- if (tree == null) {
- throw new JWTDecodeException("Parsing the Header's JSON resulted on a Null map");
- }
-
- String algorithm = getString(tree, HeaderParams.ALGORITHM);
- String type = getString(tree, HeaderParams.TYPE);
- String contentType = getString(tree, HeaderParams.CONTENT_TYPE);
- String keyId = getString(tree, HeaderParams.KEY_ID);
- return new BasicHeader(algorithm, type, contentType, keyId, tree, p.getCodec());
- }
-
- String getString(Map tree, String claimName) {
- JsonNode node = tree.get(claimName);
- if (node == null || node.isNull()) {
- return null;
- }
- return node.asText(null);
- }
-}
diff --git a/lib/src/main/java/com/auth0/jwt/impl/HeaderSerializer.java b/lib/src/main/java/com/auth0/jwt/impl/HeaderSerializer.java
deleted file mode 100644
index 5c7cf0fc..00000000
--- a/lib/src/main/java/com/auth0/jwt/impl/HeaderSerializer.java
+++ /dev/null
@@ -1,10 +0,0 @@
-package com.auth0.jwt.impl;
-
-/**
- * Responsible for serializing a JWT's header representation to JSON.
- */
-public class HeaderSerializer extends ClaimsSerializer {
- public HeaderSerializer() {
- super(HeaderClaimsHolder.class);
- }
-}
diff --git a/lib/src/main/java/com/auth0/jwt/impl/JWTParser.java b/lib/src/main/java/com/auth0/jwt/impl/JWTParser.java
deleted file mode 100644
index 022520f5..00000000
--- a/lib/src/main/java/com/auth0/jwt/impl/JWTParser.java
+++ /dev/null
@@ -1,92 +0,0 @@
-package com.auth0.jwt.impl;
-
-import com.auth0.jwt.exceptions.JWTDecodeException;
-import com.auth0.jwt.interfaces.Header;
-import com.auth0.jwt.interfaces.JWTPartsParser;
-import com.auth0.jwt.interfaces.Payload;
-import com.fasterxml.jackson.annotation.JsonInclude;
-import com.fasterxml.jackson.databind.ObjectMapper;
-import com.fasterxml.jackson.databind.ObjectReader;
-import com.fasterxml.jackson.databind.SerializationFeature;
-import com.fasterxml.jackson.databind.module.SimpleModule;
-import java.io.IOException;
-
-/**
- * This class helps in decoding the Header and Payload of the JWT using
- * {@link HeaderSerializer} and {@link PayloadSerializer}.
- */
-public class JWTParser implements JWTPartsParser {
- private static final ObjectMapper DEFAULT_OBJECT_MAPPER = createDefaultObjectMapper();
- private static final ObjectReader DEFAULT_PAYLOAD_READER = DEFAULT_OBJECT_MAPPER.readerFor(Payload.class);
- private static final ObjectReader DEFAULT_HEADER_READER = DEFAULT_OBJECT_MAPPER.readerFor(Header.class);
-
- private final ObjectReader payloadReader;
- private final ObjectReader headerReader;
-
- public JWTParser() {
- this.payloadReader = DEFAULT_PAYLOAD_READER;
- this.headerReader = DEFAULT_HEADER_READER;
- }
-
- JWTParser(ObjectMapper mapper) {
- addDeserializers(mapper);
-
- this.payloadReader = mapper.readerFor(Payload.class);
- this.headerReader = mapper.readerFor(Header.class);
- }
-
- @Override
- public Payload parsePayload(String json) throws JWTDecodeException {
- if (json == null) {
- throw decodeException();
- }
-
- try {
- return payloadReader.readValue(json);
- } catch (IOException e) {
- throw decodeException(json);
- }
- }
-
- @Override
- public Header parseHeader(String json) throws JWTDecodeException {
- if (json == null) {
- throw decodeException();
- }
-
- try {
- return headerReader.readValue(json);
- } catch (IOException e) {
- throw decodeException(json);
- }
- }
-
- static void addDeserializers(ObjectMapper mapper) {
- SimpleModule module = new SimpleModule();
- module.addDeserializer(Payload.class, new PayloadDeserializer());
- module.addDeserializer(Header.class, new HeaderDeserializer());
- mapper.registerModule(module);
- }
-
- static ObjectMapper getDefaultObjectMapper() {
- return DEFAULT_OBJECT_MAPPER;
- }
-
- private static ObjectMapper createDefaultObjectMapper() {
- ObjectMapper mapper = new ObjectMapper();
- mapper.disable(SerializationFeature.FAIL_ON_EMPTY_BEANS);
- mapper.setSerializationInclusion(JsonInclude.Include.NON_EMPTY);
-
- addDeserializers(mapper);
-
- return mapper;
- }
-
- private static JWTDecodeException decodeException() {
- return decodeException(null);
- }
-
- private static JWTDecodeException decodeException(String json) {
- return new JWTDecodeException(String.format("The string '%s' doesn't have a valid JSON format.", json));
- }
-}
diff --git a/lib/src/main/java/com/auth0/jwt/impl/JsonNodeClaim.java b/lib/src/main/java/com/auth0/jwt/impl/JsonNodeClaim.java
deleted file mode 100644
index 0a7e22f3..00000000
--- a/lib/src/main/java/com/auth0/jwt/impl/JsonNodeClaim.java
+++ /dev/null
@@ -1,182 +0,0 @@
-package com.auth0.jwt.impl;
-
-import com.auth0.jwt.exceptions.JWTDecodeException;
-import com.auth0.jwt.interfaces.Claim;
-import com.fasterxml.jackson.core.JsonParser;
-import com.fasterxml.jackson.core.JsonProcessingException;
-import com.fasterxml.jackson.core.ObjectCodec;
-import com.fasterxml.jackson.core.type.TypeReference;
-import com.fasterxml.jackson.databind.JsonNode;
-
-import java.io.IOException;
-import java.lang.reflect.Array;
-import java.time.Instant;
-import java.util.ArrayList;
-import java.util.Date;
-import java.util.List;
-import java.util.Map;
-
-/**
- * The JsonNodeClaim retrieves a claim value from a JsonNode object.
- */
-class JsonNodeClaim implements Claim {
-
- private final ObjectCodec codec;
- private final JsonNode data;
-
- private JsonNodeClaim(JsonNode node, ObjectCodec codec) {
- this.data = node;
- this.codec = codec;
- }
-
- @Override
- public Boolean asBoolean() {
- return isMissing() || isNull() || !data.isBoolean() ? null : data.asBoolean();
- }
-
- @Override
- public Integer asInt() {
- return isMissing() || isNull() || !data.isNumber() ? null : data.asInt();
- }
-
- @Override
- public Long asLong() {
- return isMissing() || isNull() || !data.isNumber() ? null : data.asLong();
- }
-
- @Override
- public Double asDouble() {
- return isMissing() || isNull() || !data.isNumber() ? null : data.asDouble();
- }
-
- @Override
- public String asString() {
- return isMissing() || isNull() || !data.isTextual() ? null : data.asText();
- }
-
- @Override
- public Date asDate() {
- if (isMissing() || isNull() || !data.canConvertToLong()) {
- return null;
- }
- long seconds = data.asLong();
- return new Date(seconds * 1000);
- }
-
- @Override
- public Instant asInstant() {
- if (isMissing() || isNull() || !data.canConvertToLong()) {
- return null;
- }
- long seconds = data.asLong();
- return Instant.ofEpochSecond(seconds);
- }
-
- @Override
- @SuppressWarnings("unchecked")
- public T[] asArray(Class clazz) throws JWTDecodeException {
- if (isMissing() || isNull() || !data.isArray()) {
- return null;
- }
-
- T[] arr = (T[]) Array.newInstance(clazz, data.size());
- for (int i = 0; i < data.size(); i++) {
- try {
- arr[i] = codec.treeToValue(data.get(i), clazz);
- } catch (JsonProcessingException e) {
- throw new JWTDecodeException("Couldn't map the Claim's array contents to " + clazz.getSimpleName(), e);
- }
- }
- return arr;
- }
-
- @Override
- public List asList(Class clazz) throws JWTDecodeException {
- if (isMissing() || isNull() || !data.isArray()) {
- return null;
- }
-
- List list = new ArrayList<>();
- for (int i = 0; i < data.size(); i++) {
- try {
- list.add(codec.treeToValue(data.get(i), clazz));
- } catch (JsonProcessingException e) {
- throw new JWTDecodeException("Couldn't map the Claim's array contents to " + clazz.getSimpleName(), e);
- }
- }
- return list;
- }
-
- @Override
- public Map asMap() throws JWTDecodeException {
- if (isMissing() || isNull() || !data.isObject()) {
- return null;
- }
-
- TypeReference> mapType = new TypeReference>() {
- };
-
- try (JsonParser parser = codec.treeAsTokens(data)) {
- return parser.readValueAs(mapType);
- } catch (IOException e) {
- throw new JWTDecodeException("Couldn't map the Claim value to Map", e);
- }
- }
-
- @Override
- public T as(Class clazz) throws JWTDecodeException {
- try {
- if (isMissing() || isNull()) {
- return null;
- }
- return codec.treeToValue(data, clazz);
- } catch (JsonProcessingException e) {
- throw new JWTDecodeException("Couldn't map the Claim value to " + clazz.getSimpleName(), e);
- }
- }
-
- @Override
- public boolean isNull() {
- return !isMissing() && data.isNull();
- }
-
- @Override
- public boolean isMissing() {
- return data == null || data.isMissingNode();
- }
-
- @Override
- public String toString() {
- if (isMissing()) {
- return "Missing claim";
- } else if (isNull()) {
- return "Null claim";
- }
- return data.toString();
- }
-
- /**
- * Helper method to extract a Claim from the given JsonNode tree.
- *
- * @param claimName the Claim to search for.
- * @param tree the JsonNode tree to search the Claim in.
- * @param objectCodec the object codec in use for deserialization
- * @return a valid non-null Claim.
- */
- static Claim extractClaim(String claimName, Map tree, ObjectCodec objectCodec) {
- JsonNode node = tree.get(claimName);
- return claimFromNode(node, objectCodec);
- }
-
- /**
- * Helper method to create a Claim representation from the given JsonNode.
- *
- * @param node the JsonNode to convert into a Claim.
- * @param objectCodec the object codec in use for deserialization
- * @return a valid Claim instance. If the node is null or missing, a NullClaim will be returned.
- */
- static Claim claimFromNode(JsonNode node, ObjectCodec objectCodec) {
- return new JsonNodeClaim(node, objectCodec);
- }
-
-}
\ No newline at end of file
diff --git a/lib/src/main/java/com/auth0/jwt/impl/PayloadClaimsHolder.java b/lib/src/main/java/com/auth0/jwt/impl/PayloadClaimsHolder.java
deleted file mode 100644
index 7055a2ce..00000000
--- a/lib/src/main/java/com/auth0/jwt/impl/PayloadClaimsHolder.java
+++ /dev/null
@@ -1,12 +0,0 @@
-package com.auth0.jwt.impl;
-
-import java.util.Map;
-
-/**
- * Holds the payload claims when serializing a JWT.
- */
-public final class PayloadClaimsHolder extends ClaimsHolder {
- public PayloadClaimsHolder(Map claims) {
- super(claims);
- }
-}
diff --git a/lib/src/main/java/com/auth0/jwt/impl/PayloadDeserializer.java b/lib/src/main/java/com/auth0/jwt/impl/PayloadDeserializer.java
deleted file mode 100644
index b1d32a12..00000000
--- a/lib/src/main/java/com/auth0/jwt/impl/PayloadDeserializer.java
+++ /dev/null
@@ -1,91 +0,0 @@
-package com.auth0.jwt.impl;
-
-import com.auth0.jwt.RegisteredClaims;
-import com.auth0.jwt.exceptions.JWTDecodeException;
-import com.auth0.jwt.interfaces.Payload;
-import com.fasterxml.jackson.core.JsonParser;
-import com.fasterxml.jackson.core.JsonProcessingException;
-import com.fasterxml.jackson.core.ObjectCodec;
-import com.fasterxml.jackson.core.type.TypeReference;
-import com.fasterxml.jackson.databind.DeserializationContext;
-import com.fasterxml.jackson.databind.JsonNode;
-import com.fasterxml.jackson.databind.ObjectReader;
-import com.fasterxml.jackson.databind.deser.std.StdDeserializer;
-
-import java.io.IOException;
-import java.time.Instant;
-import java.util.*;
-
-/**
- * Jackson deserializer implementation for converting from JWT Payload parts.
- *
- * This class is thread-safe.
- *
- * @see JWTParser
- */
-class PayloadDeserializer extends StdDeserializer {
-
- PayloadDeserializer() {
- super(Payload.class);
- }
-
- @Override
- public Payload deserialize(JsonParser p, DeserializationContext ctxt) throws IOException {
- Map tree = p.getCodec().readValue(p, new TypeReference>() {
- });
- if (tree == null) {
- throw new JWTDecodeException("Parsing the Payload's JSON resulted on a Null map");
- }
-
- String issuer = getString(tree, RegisteredClaims.ISSUER);
- String subject = getString(tree, RegisteredClaims.SUBJECT);
- List audience = getStringOrArray(p.getCodec(), tree, RegisteredClaims.AUDIENCE);
- Instant expiresAt = getInstantFromSeconds(tree, RegisteredClaims.EXPIRES_AT);
- Instant notBefore = getInstantFromSeconds(tree, RegisteredClaims.NOT_BEFORE);
- Instant issuedAt = getInstantFromSeconds(tree, RegisteredClaims.ISSUED_AT);
- String jwtId = getString(tree, RegisteredClaims.JWT_ID);
-
- return new PayloadImpl(issuer, subject, audience, expiresAt, notBefore, issuedAt, jwtId, tree, p.getCodec());
- }
-
- List getStringOrArray(ObjectCodec codec, Map tree, String claimName)
- throws JWTDecodeException {
- JsonNode node = tree.get(claimName);
- if (node == null || node.isNull() || !(node.isArray() || node.isTextual())) {
- return null;
- }
- if (node.isTextual()) {
- return Collections.singletonList(node.asText());
- }
-
- List list = new ArrayList<>(node.size());
- for (int i = 0; i < node.size(); i++) {
- try {
- list.add(codec.treeToValue(node.get(i), String.class));
- } catch (JsonProcessingException e) {
- throw new JWTDecodeException("Couldn't map the Claim's array contents to String", e);
- }
- }
- return list;
- }
-
- Instant getInstantFromSeconds(Map tree, String claimName) {
- JsonNode node = tree.get(claimName);
- if (node == null || node.isNull()) {
- return null;
- }
- if (!node.canConvertToLong()) {
- throw new JWTDecodeException(
- String.format("The claim '%s' contained a non-numeric date value.", claimName));
- }
- return Instant.ofEpochSecond(node.asLong());
- }
-
- String getString(Map tree, String claimName) {
- JsonNode node = tree.get(claimName);
- if (node == null || node.isNull()) {
- return null;
- }
- return node.asText(null);
- }
-}
diff --git a/lib/src/main/java/com/auth0/jwt/impl/PayloadImpl.java b/lib/src/main/java/com/auth0/jwt/impl/PayloadImpl.java
deleted file mode 100644
index bfd9b0ea..00000000
--- a/lib/src/main/java/com/auth0/jwt/impl/PayloadImpl.java
+++ /dev/null
@@ -1,129 +0,0 @@
-package com.auth0.jwt.impl;
-
-import com.auth0.jwt.interfaces.Claim;
-import com.auth0.jwt.interfaces.Payload;
-import com.fasterxml.jackson.core.ObjectCodec;
-import com.fasterxml.jackson.databind.JsonNode;
-
-import java.io.Serializable;
-import java.time.Instant;
-import java.util.Collections;
-import java.util.Date;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-
-import static com.auth0.jwt.impl.JsonNodeClaim.extractClaim;
-
-/**
- * Decoder of string JSON Web Tokens into their POJO representations.
- *
- * This class is thread-safe.
- *
- * @see Payload
- */
-class PayloadImpl implements Payload, Serializable {
-
- private static final long serialVersionUID = 1659021498824562311L;
-
- private final String issuer;
- private final String subject;
- private final List audience;
- private final Instant expiresAt;
- private final Instant notBefore;
- private final Instant issuedAt;
- private final String jwtId;
- private final Map tree;
- private final ObjectCodec objectCodec;
-
- PayloadImpl(
- String issuer,
- String subject,
- List audience,
- Instant expiresAt,
- Instant notBefore,
- Instant issuedAt,
- String jwtId,
- Map tree,
- ObjectCodec objectCodec
- ) {
- this.issuer = issuer;
- this.subject = subject;
- this.audience = audience != null ? Collections.unmodifiableList(audience) : null;
- this.expiresAt = expiresAt;
- this.notBefore = notBefore;
- this.issuedAt = issuedAt;
- this.jwtId = jwtId;
- this.tree = tree != null ? Collections.unmodifiableMap(tree) : Collections.emptyMap();
- this.objectCodec = objectCodec;
- }
-
- Map getTree() {
- return tree;
- }
-
- @Override
- public String getIssuer() {
- return issuer;
- }
-
- @Override
- public String getSubject() {
- return subject;
- }
-
- @Override
- public List getAudience() {
- return audience;
- }
-
- @Override
- public Date getExpiresAt() {
- return (expiresAt != null) ? Date.from(expiresAt) : null;
- }
-
-
- @Override
- public Instant getExpiresAtAsInstant() {
- return expiresAt;
- }
-
- @Override
- public Date getIssuedAt() {
- return (issuedAt != null) ? Date.from(issuedAt) : null;
- }
-
- @Override
- public Instant getIssuedAtAsInstant() {
- return issuedAt;
- }
-
- @Override
- public Date getNotBefore() {
- return (notBefore != null) ? Date.from(notBefore) : null;
- }
-
- @Override
- public Instant getNotBeforeAsInstant() {
- return notBefore;
- }
-
- @Override
- public String getId() {
- return jwtId;
- }
-
- @Override
- public Claim getClaim(String name) {
- return extractClaim(name, tree, objectCodec);
- }
-
- @Override
- public Map getClaims() {
- Map claims = new HashMap<>(tree.size() * 2);
- for (String name : tree.keySet()) {
- claims.put(name, extractClaim(name, tree, objectCodec));
- }
- return Collections.unmodifiableMap(claims);
- }
-}
diff --git a/lib/src/main/java/com/auth0/jwt/impl/PayloadSerializer.java b/lib/src/main/java/com/auth0/jwt/impl/PayloadSerializer.java
deleted file mode 100644
index 24fe37b7..00000000
--- a/lib/src/main/java/com/auth0/jwt/impl/PayloadSerializer.java
+++ /dev/null
@@ -1,66 +0,0 @@
-package com.auth0.jwt.impl;
-
-import com.auth0.jwt.RegisteredClaims;
-import com.fasterxml.jackson.core.JsonGenerator;
-
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.List;
-import java.util.Map;
-
-/**
- * Jackson serializer implementation for converting into JWT Payload parts.
- *
- * This class is thread-safe.
- *
- * @see com.auth0.jwt.JWTCreator
- */
-public class PayloadSerializer extends ClaimsSerializer {
- public PayloadSerializer() {
- super(PayloadClaimsHolder.class);
- }
-
- @Override
- protected void writeClaim(Map.Entry entry, JsonGenerator gen) throws IOException {
- if (RegisteredClaims.AUDIENCE.equals(entry.getKey())) {
- writeAudience(gen, entry);
- } else {
- super.writeClaim(entry, gen);
- }
- }
-
- /**
- * Audience may be a list of strings or a single string. This is needed to properly handle the aud claim when
- * added with the {@linkplain com.auth0.jwt.JWTCreator.Builder#withPayload(Map)} method.
- */
- private void writeAudience(JsonGenerator gen, Map.Entry e) throws IOException {
- if (e.getValue() instanceof String) {
- gen.writeFieldName(e.getKey());
- gen.writeString((String) e.getValue());
- } else {
- List audArray = new ArrayList<>();
- if (e.getValue() instanceof String[]) {
- audArray = Arrays.asList((String[]) e.getValue());
- } else if (e.getValue() instanceof List) {
- List> audList = (List>) e.getValue();
- for (Object aud : audList) {
- if (aud instanceof String) {
- audArray.add((String) aud);
- }
- }
- }
- if (audArray.size() == 1) {
- gen.writeFieldName(e.getKey());
- gen.writeString(audArray.get(0));
- } else if (audArray.size() > 1) {
- gen.writeFieldName(e.getKey());
- gen.writeStartArray();
- for (String aud : audArray) {
- gen.writeString(aud);
- }
- gen.writeEndArray();
- }
- }
- }
-}
diff --git a/lib/src/main/java/com/auth0/jwt/impl/package-info.java b/lib/src/main/java/com/auth0/jwt/impl/package-info.java
deleted file mode 100644
index 334ccb8a..00000000
--- a/lib/src/main/java/com/auth0/jwt/impl/package-info.java
+++ /dev/null
@@ -1,7 +0,0 @@
-/**
- * Contains parts of the internal implementation of this library.
- *
- * Do not use any of the classes in this package. They might be removed
- * or changed at any point without prior warning.
- */
-package com.auth0.jwt.impl;
diff --git a/lib/src/main/java/com/auth0/jwt/interfaces/Claim.java b/lib/src/main/java/com/auth0/jwt/interfaces/Claim.java
deleted file mode 100644
index ca5244d6..00000000
--- a/lib/src/main/java/com/auth0/jwt/interfaces/Claim.java
+++ /dev/null
@@ -1,131 +0,0 @@
-package com.auth0.jwt.interfaces;
-
-import com.auth0.jwt.exceptions.JWTDecodeException;
-
-import java.time.Instant;
-import java.util.Date;
-import java.util.List;
-import java.util.Map;
-
-/**
- * The Claim class holds the value in a generic way so that it can be recovered in many representations.
- */
-public interface Claim {
-
- /**
- * Whether this Claim has a null value or not.
- * If the claim is not present, it will return false hence checking {@link Claim#isMissing} is advised as well
- *
- * @return whether this Claim has a null value or not.
- */
- boolean isNull();
-
- /**
- * Can be used to verify whether the Claim is found or not.
- * This will be true even if the Claim has {@code null} value associated to it.
- *
- * @return whether this Claim is present or not
- */
- boolean isMissing();
-
- /**
- * Get this Claim as a Boolean.
- * If the value isn't of type Boolean or it can't be converted to a Boolean, {@code null} will be returned.
- *
- * @return the value as a Boolean or null.
- */
- Boolean asBoolean();
-
- /**
- * Get this Claim as an Integer.
- * If the value isn't of type Integer or it can't be converted to an Integer, {@code null} will be returned.
- *
- * @return the value as an Integer or null.
- */
- Integer asInt();
-
- /**
- * Get this Claim as an Long.
- * If the value isn't of type Long or it can't be converted to a Long, {@code null} will be returned.
- *
- * @return the value as an Long or null.
- */
- Long asLong();
-
- /**
- * Get this Claim as a Double.
- * If the value isn't of type Double or it can't be converted to a Double, {@code null} will be returned.
- *
- * @return the value as a Double or null.
- */
- Double asDouble();
-
- /**
- * Get this Claim as a String.
- * If the value isn't of type String, {@code null} will be returned. For a String representation of non-textual
- * claim types, clients can call {@code toString()}.
- *
- * @return the value as a String or null if the underlying value is not a string.
- */
- String asString();
-
- /**
- * Get this Claim as a Date.
- * If the value can't be converted to a Date, {@code null} will be returned.
- *
- * @return the value as a Date or null.
- */
- Date asDate();
-
- /**
- * Get this Claim as an Instant.
- * If the value can't be converted to an Instant, {@code null} will be returned.
- *
- * @return the value as a Date or null.
- */
- default Instant asInstant() {
- Date date = asDate();
- return date != null ? date.toInstant() : null;
- }
-
- /**
- * Get this Claim as an Array of type T.
- * If the value isn't an Array, {@code null} will be returned.
- *
- * @param type
- * @param clazz the type class
- * @return the value as an Array or null.
- * @throws JWTDecodeException if the values inside the Array can't be converted to a class T.
- */
- T[] asArray(Class clazz) throws JWTDecodeException;
-
- /**
- * Get this Claim as a List of type T.
- * If the value isn't an Array, {@code null} will be returned.
- *
- * @param type
- * @param clazz the type class
- * @return the value as a List or null.
- * @throws JWTDecodeException if the values inside the List can't be converted to a class T.
- */
- List asList(Class clazz) throws JWTDecodeException;
-
- /**
- * Get this Claim as a generic Map of values.
- *
- * @return the value as instance of Map.
- * @throws JWTDecodeException if the value can't be converted to a Map.
- */
- Map asMap() throws JWTDecodeException;
-
- /**
- * Get this Claim as a custom type T.
- * This method will return null if {@link Claim#isMissing()} or {@link Claim#isNull()} is true
- *
- * @param type
- * @param clazz the type class
- * @return the value as instance of T.
- * @throws JWTDecodeException if the value can't be converted to a class T.
- */
- T as(Class clazz) throws JWTDecodeException;
-}
diff --git a/lib/src/main/java/com/auth0/jwt/interfaces/DecodedJWT.java b/lib/src/main/java/com/auth0/jwt/interfaces/DecodedJWT.java
deleted file mode 100644
index 04307b28..00000000
--- a/lib/src/main/java/com/auth0/jwt/interfaces/DecodedJWT.java
+++ /dev/null
@@ -1,37 +0,0 @@
-package com.auth0.jwt.interfaces;
-
-/**
- * Class that represents a Json Web Token that was decoded from it's string representation.
- */
-public interface DecodedJWT extends Payload, Header {
- /**
- * Getter for the String Token used to create this JWT instance.
- *
- * @return the String Token.
- */
- String getToken();
-
- /**
- * Getter for the Header contained in the JWT as a Base64 encoded String.
- * This represents the first part of the token.
- *
- * @return the Header of the JWT.
- */
- String getHeader();
-
- /**
- * Getter for the Payload contained in the JWT as a Base64 encoded String.
- * This represents the second part of the token.
- *
- * @return the Payload of the JWT.
- */
- String getPayload();
-
- /**
- * Getter for the Signature contained in the JWT as a Base64 encoded String.
- * This represents the third part of the token.
- *
- * @return the Signature of the JWT.
- */
- String getSignature();
-}
diff --git a/lib/src/main/java/com/auth0/jwt/interfaces/ECDSAKeyProvider.java b/lib/src/main/java/com/auth0/jwt/interfaces/ECDSAKeyProvider.java
deleted file mode 100644
index 55df451d..00000000
--- a/lib/src/main/java/com/auth0/jwt/interfaces/ECDSAKeyProvider.java
+++ /dev/null
@@ -1,10 +0,0 @@
-package com.auth0.jwt.interfaces;
-
-import java.security.interfaces.ECPrivateKey;
-import java.security.interfaces.ECPublicKey;
-
-/**
- * Elliptic Curve (EC) Public/Private Key provider.
- */
-public interface ECDSAKeyProvider extends KeyProvider {
-}
diff --git a/lib/src/main/java/com/auth0/jwt/interfaces/Header.java b/lib/src/main/java/com/auth0/jwt/interfaces/Header.java
deleted file mode 100644
index 52b3ba56..00000000
--- a/lib/src/main/java/com/auth0/jwt/interfaces/Header.java
+++ /dev/null
@@ -1,44 +0,0 @@
-package com.auth0.jwt.interfaces;
-
-/**
- * The Header class represents the 1st part of the JWT, where the Header value is held.
- */
-public interface Header {
-
- /**
- * Getter for the Algorithm "alg" claim defined in the JWT's Header. If the claim is missing it will return null.
- *
- * @return the Algorithm defined or null.
- */
- String getAlgorithm();
-
- /**
- * Getter for the Type "typ" claim defined in the JWT's Header. If the claim is missing it will return null.
- *
- * @return the Type defined or null.
- */
- String getType();
-
- /**
- * Getter for the Content Type "cty" claim defined in the JWT's Header. If the claim is missing it will return null.
- *
- * @return the Content Type defined or null.
- */
- String getContentType();
-
- /**
- * Get the value of the "kid" claim, or null if it's not available.
- *
- * @return the Key ID value or null.
- */
- String getKeyId();
-
- /**
- * Get a Private Claim given it's name. If the Claim wasn't specified in the Header, a 'null claim' will be
- * returned. All the methods of that claim will return {@code null}.
- *
- * @param name the name of the Claim to retrieve.
- * @return a non-null Claim.
- */
- Claim getHeaderClaim(String name);
-}
diff --git a/lib/src/main/java/com/auth0/jwt/interfaces/JWTPartsParser.java b/lib/src/main/java/com/auth0/jwt/interfaces/JWTPartsParser.java
deleted file mode 100644
index 33cd0d70..00000000
--- a/lib/src/main/java/com/auth0/jwt/interfaces/JWTPartsParser.java
+++ /dev/null
@@ -1,28 +0,0 @@
-package com.auth0.jwt.interfaces;
-
-import com.auth0.jwt.exceptions.JWTDecodeException;
-
-/**
- * The JWTPartsParser class defines which parts of the JWT should be converted
- * to its specific Object representation instance.
- */
-public interface JWTPartsParser {
-
- /**
- * Parses the given JSON into a {@link Payload} instance.
- *
- * @param json the content of the Payload in a JSON representation.
- * @return the Payload.
- * @throws JWTDecodeException if the json doesn't have a proper JSON format.
- */
- Payload parsePayload(String json) throws JWTDecodeException;
-
- /**
- * Parses the given JSON into a {@link Header} instance.
- *
- * @param json the content of the Header in a JSON representation.
- * @return the Header.
- * @throws JWTDecodeException if the json doesn't have a proper JSON format.
- */
- Header parseHeader(String json) throws JWTDecodeException;
-}
diff --git a/lib/src/main/java/com/auth0/jwt/interfaces/JWTVerifier.java b/lib/src/main/java/com/auth0/jwt/interfaces/JWTVerifier.java
deleted file mode 100644
index 2756ddd8..00000000
--- a/lib/src/main/java/com/auth0/jwt/interfaces/JWTVerifier.java
+++ /dev/null
@@ -1,40 +0,0 @@
-package com.auth0.jwt.interfaces;
-
-import com.auth0.jwt.exceptions.JWTVerificationException;
-
-
-/**
- * Used to verify the JWT for its signature and claims. Implementations must be thread-safe. Instances are created
- * using {@link Verification}.
- *
- *
- * try {
- * JWTVerifier verifier = JWTVerifier.init(Algorithm.RSA256(publicKey, privateKey)
- * .withIssuer("auth0")
- * .build();
- * DecodedJWT jwt = verifier.verify("token");
- * } catch (JWTVerificationException e) {
- * // invalid signature or claims
- * }
- *
- */
-public interface JWTVerifier {
-
- /**
- * Performs the verification against the given Token.
- *
- * @param token to verify.
- * @return a verified and decoded JWT.
- * @throws JWTVerificationException if any of the verification steps fail
- */
- DecodedJWT verify(String token) throws JWTVerificationException;
-
- /**
- * Performs the verification against the given {@link DecodedJWT}.
- *
- * @param jwt to verify.
- * @return a verified and decoded JWT.
- * @throws JWTVerificationException if any of the verification steps fail
- */
- DecodedJWT verify(DecodedJWT jwt) throws JWTVerificationException;
-}
diff --git a/lib/src/main/java/com/auth0/jwt/interfaces/KeyProvider.java b/lib/src/main/java/com/auth0/jwt/interfaces/KeyProvider.java
deleted file mode 100644
index 30a144a6..00000000
--- a/lib/src/main/java/com/auth0/jwt/interfaces/KeyProvider.java
+++ /dev/null
@@ -1,38 +0,0 @@
-package com.auth0.jwt.interfaces;
-
-import java.security.PrivateKey;
-import java.security.PublicKey;
-
-/**
- * Generic Public/Private Key provider.
- * While implementing, ensure the Private Key and Private Key ID doesn't change in between signing a token.
- *
- * @param the class that represents the Public Key
- * @param the class that represents the Private Key
- */
-interface KeyProvider {
-
- /**
- * Getter for the Public Key instance with the given Id. Used to verify the signature on the JWT verification stage.
- *
- * @param keyId the Key Id specified in the Token's Header or null if none is available.
- * Provides a hint on which Public Key to use to verify the token's signature.
- * @return the Public Key instance
- */
- U getPublicKeyById(String keyId);
-
- /**
- * Getter for the Private Key instance. Used to sign the content on the JWT signing stage.
- *
- * @return the Private Key instance
- */
- R getPrivateKey();
-
- /**
- * Getter for the Id of the Private Key used to sign the tokens.
- * This represents the `kid` claim and will be placed in the Header.
- *
- * @return the Key Id that identifies the Private Key or null if it's not specified.
- */
- String getPrivateKeyId();
-}
diff --git a/lib/src/main/java/com/auth0/jwt/interfaces/Payload.java b/lib/src/main/java/com/auth0/jwt/interfaces/Payload.java
deleted file mode 100644
index feb58c64..00000000
--- a/lib/src/main/java/com/auth0/jwt/interfaces/Payload.java
+++ /dev/null
@@ -1,104 +0,0 @@
-package com.auth0.jwt.interfaces;
-
-import java.time.Instant;
-import java.util.Date;
-import java.util.List;
-import java.util.Map;
-
-/**
- * The Payload class represents the 2nd part of the JWT, where the Payload value is held.
- */
-public interface Payload {
-
- /**
- * Get the value of the "iss" claim, or null if it's not available.
- *
- * @return the Issuer value or null.
- */
- String getIssuer();
-
- /**
- * Get the value of the "sub" claim, or null if it's not available.
- *
- * @return the Subject value or null.
- */
- String getSubject();
-
- /**
- * Get the value of the "aud" claim, or null if it's not available.
- *
- * @return the Audience value or null.
- */
- List getAudience();
-
- /**
- * Get the value of the "exp" claim, or null if it's not available.
- *
- * @return the Expiration Time value or null.
- */
- Date getExpiresAt();
-
- /**
- * Get the value of the "exp" claim as an {@linkplain Instant}, or null if it's not available.
- *
- * @return the Expiration Time value or null.
- */
- default Instant getExpiresAtAsInstant() {
- return getExpiresAt() != null ? getExpiresAt().toInstant() : null;
- }
-
- /**
- * Get the value of the "nbf" claim, or null if it's not available.
- *
- * @return the Not Before value or null.
- */
- Date getNotBefore();
-
- /**
- * Get the value of the "nbf" claim as an {@linkplain Instant}, or null if it's not available.
- *
- * @return the Not Before value or null.
- */
- default Instant getNotBeforeAsInstant() {
- return getNotBefore() != null ? getNotBefore().toInstant() : null;
- }
-
- /**
- * Get the value of the "iat" claim, or null if it's not available.
- *
- * @return the Issued At value or null.
- */
- Date getIssuedAt();
-
- /**
- * Get the value of the "iat" claim as an {@linkplain Instant}, or null if it's not available.
- *
- * @return the Issued At value or null.
- */
- default Instant getIssuedAtAsInstant() {
- return getIssuedAt() != null ? getIssuedAt().toInstant() : null;
- }
-
- /**
- * Get the value of the "jti" claim, or null if it's not available.
- *
- * @return the JWT ID value or null.
- */
- String getId();
-
- /**
- * Get a Claim given its name. If the Claim wasn't specified in the Payload, a 'null claim'
- * will be returned. All the methods of that claim will return {@code null}.
- *
- * @param name the name of the Claim to retrieve.
- * @return a non-null Claim.
- */
- Claim getClaim(String name);
-
- /**
- * Get the Claims defined in the Token.
- *
- * @return a non-null Map containing the Claims defined in the Token.
- */
- Map getClaims();
-}
diff --git a/lib/src/main/java/com/auth0/jwt/interfaces/RSAKeyProvider.java b/lib/src/main/java/com/auth0/jwt/interfaces/RSAKeyProvider.java
deleted file mode 100644
index 55376f4d..00000000
--- a/lib/src/main/java/com/auth0/jwt/interfaces/RSAKeyProvider.java
+++ /dev/null
@@ -1,10 +0,0 @@
-package com.auth0.jwt.interfaces;
-
-import java.security.interfaces.RSAPrivateKey;
-import java.security.interfaces.RSAPublicKey;
-
-/**
- * RSA Public/Private Key provider.
- */
-public interface RSAKeyProvider extends KeyProvider {
-}
diff --git a/lib/src/main/java/com/auth0/jwt/interfaces/Verification.java b/lib/src/main/java/com/auth0/jwt/interfaces/Verification.java
deleted file mode 100644
index b4adcf5c..00000000
--- a/lib/src/main/java/com/auth0/jwt/interfaces/Verification.java
+++ /dev/null
@@ -1,267 +0,0 @@
-package com.auth0.jwt.interfaces;
-
-import com.auth0.jwt.JWTVerifier;
-
-import java.time.Instant;
-import java.util.Date;
-import java.util.function.BiPredicate;
-
-/**
- * Constructs and holds the checks required for a JWT to be considered valid. Note that implementations are
- * not thread-safe. Once built by calling {@link #build()}, the resulting
- * {@link com.auth0.jwt.interfaces.JWTVerifier} is thread-safe.
- */
-public interface Verification {
-
- /**
- * Verifies whether the JWT contains an Issuer ("iss") claim that equals to the value provided.
- * This check is case-sensitive.
- *
- * @param issuer the required Issuer value.
- * @return this same Verification instance.
- */
- default Verification withIssuer(String issuer) {
- return withIssuer(new String[]{issuer});
- }
-
- /**
- * Verifies whether the JWT contains an Issuer ("iss") claim that contains all the values provided.
- * This check is case-sensitive. An empty array is considered as a {@code null}.
- *
- * @param issuer the required Issuer value. If multiple values are given, the claim must at least match one of them
- * @return this same Verification instance.
- */
- Verification withIssuer(String... issuer);
-
- /**
- * Verifies whether the JWT contains a Subject ("sub") claim that equals to the value provided.
- * This check is case-sensitive.
- *
- * @param subject the required Subject value
- * @return this same Verification instance.
- */
- Verification withSubject(String subject);
-
- /**
- * Verifies whether the JWT contains an Audience ("aud") claim that contains all the values provided.
- * This check is case-sensitive. An empty array is considered as a {@code null}.
- *
- * @param audience the required Audience value
- * @return this same Verification instance.
- */
- Verification withAudience(String... audience);
-
- /**
- * Verifies whether the JWT contains an Audience ("aud") claim contain at least one of the specified audiences.
- * This check is case-sensitive. An empty array is considered as a {@code null}.
- *
- * @param audience the required Audience value for which the "aud" claim must contain at least one value.
- * @return this same Verification instance.
- */
- Verification withAnyOfAudience(String... audience);
-
- /**
- * Define the default window in seconds in which the Not Before, Issued At and Expires At Claims
- * will still be valid. Setting a specific leeway value on a given Claim will override this value for that Claim.
- *
- * @param leeway the window in seconds in which the Not Before, Issued At and Expires At Claims will still be valid.
- * @return this same Verification instance.
- * @throws IllegalArgumentException if leeway is negative.
- */
- Verification acceptLeeway(long leeway) throws IllegalArgumentException;
-
- /**
- * Set a specific leeway window in seconds in which the Expires At ("exp") Claim will still be valid.
- * Expiration Date is always verified when the value is present.
- * This method overrides the value set with acceptLeeway
- *
- * @param leeway the window in seconds in which the Expires At Claim will still be valid.
- * @return this same Verification instance.
- * @throws IllegalArgumentException if leeway is negative.
- */
- Verification acceptExpiresAt(long leeway) throws IllegalArgumentException;
-
- /**
- * Set a specific leeway window in seconds in which the Not Before ("nbf") Claim will still be valid.
- * Not Before Date is always verified when the value is present.
- * This method overrides the value set with acceptLeeway
- *
- * @param leeway the window in seconds in which the Not Before Claim will still be valid.
- * @return this same Verification instance.
- * @throws IllegalArgumentException if leeway is negative.
- */
- Verification acceptNotBefore(long leeway) throws IllegalArgumentException;
-
- /**
- * Set a specific leeway window in seconds in which the Issued At ("iat") Claim will still be valid.
- * This method overrides the value set with {@link #acceptLeeway(long)}.
- * By default, the Issued At claim is always verified when the value is present,
- * unless disabled with {@link #ignoreIssuedAt()}.
- * If Issued At verification has been disabled, no verification of the Issued At claim will be performed,
- * and this method has no effect.
- *
- * @param leeway the window in seconds in which the Issued At Claim will still be valid.
- * @return this same Verification instance.
- * @throws IllegalArgumentException if leeway is negative.
- */
- Verification acceptIssuedAt(long leeway) throws IllegalArgumentException;
-
- /**
- * Verifies whether the JWT contains a JWT ID ("jti") claim that equals to the value provided.
- * This check is case-sensitive.
- *
- * @param jwtId the required ID value
- * @return this same Verification instance.
- */
- Verification withJWTId(String jwtId);
-
- /**
- * Verifies whether the claim is present in the JWT, with any value including {@code null}.
- *
- * @param name the Claim's name.
- * @return this same Verification instance
- * @throws IllegalArgumentException if the name is {@code null}.
- */
- Verification withClaimPresence(String name) throws IllegalArgumentException;
-
- /**
- * Verifies whether the claim is present with a {@code null} value.
- *
- * @param name the Claim's name.
- * @return this same Verification instance.
- * @throws IllegalArgumentException if the name is {@code null}.
- */
- Verification withNullClaim(String name) throws IllegalArgumentException;
-
- /**
- * Verifies whether the claim is equal to the given Boolean value.
- *
- * @param name the Claim's name.
- * @param value the Claim's value.
- * @return this same Verification instance.
- * @throws IllegalArgumentException if the name is {@code null}.
- */
- Verification withClaim(String name, Boolean value) throws IllegalArgumentException;
-
- /**
- * Verifies whether the claim is equal to the given Integer value.
- *
- * @param name the Claim's name.
- * @param value the Claim's value.
- * @return this same Verification instance.
- * @throws IllegalArgumentException if the name is {@code null}.
- */
- Verification withClaim(String name, Integer value) throws IllegalArgumentException;
-
- /**
- * Verifies whether the claim is equal to the given Long value.
- *
- * @param name the Claim's name.
- * @param value the Claim's value.
- * @return this same Verification instance.
- * @throws IllegalArgumentException if the name is {@code null}.
- */
- Verification withClaim(String name, Long value) throws IllegalArgumentException;
-
- /**
- * Verifies whether the claim is equal to the given Integer value.
- *
- * @param name the Claim's name.
- * @param value the Claim's value.
- * @return this same Verification instance.
- * @throws IllegalArgumentException if the name is {@code null}.
- */
- Verification withClaim(String name, Double value) throws IllegalArgumentException;
-
- /**
- * Verifies whether the claim is equal to the given String value.
- * This check is case-sensitive.
- *
- * @param name the Claim's name.
- * @param value the Claim's value.
- * @return this same Verification instance.
- * @throws IllegalArgumentException if the name is {@code null}.
- */
- Verification withClaim(String name, String value) throws IllegalArgumentException;
-
- /**
- * Verifies whether the claim is equal to the given Date value.
- * Note that date-time claims are serialized as seconds since the epoch;
- * when verifying date-time claim value, any time units more granular than seconds will not be considered.
- *
- * @param name the Claim's name.
- * @param value the Claim's value.
- * @return this same Verification instance.
- * @throws IllegalArgumentException if the name is {@code null}.
- */
- Verification withClaim(String name, Date value) throws IllegalArgumentException;
-
- /**
- * Verifies whether the claim is equal to the given Instant value.
- * Note that date-time claims are serialized as seconds since the epoch;
- * when verifying a date-time claim value, any time units more granular than seconds will not be considered.
- *
- * @param name the Claim's name.
- * @param value the Claim's value.
- * @return this same Verification instance.
- * @throws IllegalArgumentException if the name is {@code null}.
- */
- default Verification withClaim(String name, Instant value) throws IllegalArgumentException {
- return withClaim(name, value != null ? Date.from(value) : null);
- }
-
- /**
- * Executes the predicate provided and the validates the JWT if the predicate returns true.
- *
- * @param name the Claim's name
- * @param predicate the predicate check to be done.
- * @return this same Verification instance.
- * @throws IllegalArgumentException if the name is {@code null}.
- */
- Verification withClaim(String name, BiPredicate predicate) throws IllegalArgumentException;
-
- /**
- * Verifies whether the claim contain at least the given String items.
- *
- * @param name the Claim's name.
- * @param items the items the Claim must contain.
- * @return this same Verification instance.
- * @throws IllegalArgumentException if the name is {@code null}.
- */
- Verification withArrayClaim(String name, String... items) throws IllegalArgumentException;
-
- /**
- * Verifies whether the claim contain at least the given Integer items.
- *
- * @param name the Claim's name.
- * @param items the items the Claim must contain.
- * @return this same Verification instance.
- * @throws IllegalArgumentException if the name is {@code null}.
- */
- Verification withArrayClaim(String name, Integer... items) throws IllegalArgumentException;
-
- /**
- * Verifies whether the claim contain at least the given Long items.
- *
- * @param name the Claim's name.
- * @param items the items the Claim must contain.
- * @return this same Verification instance.
- * @throws IllegalArgumentException if the name is {@code null}.
- */
-
- Verification withArrayClaim(String name, Long ... items) throws IllegalArgumentException;
-
- /**
- * Skip the Issued At ("iat") claim verification. By default, the verification is performed.
- *
- * @return this same Verification instance.
- */
- Verification ignoreIssuedAt();
-
- /**
- * Creates a new and reusable instance of the JWTVerifier with the configuration already provided.
- *
- * @return a new {@link com.auth0.jwt.interfaces.JWTVerifier} instance.
- */
- JWTVerifier build();
-}
diff --git a/lib/src/main/java/module-info.java b/lib/src/main/java/module-info.java
deleted file mode 100644
index a1e30e31..00000000
--- a/lib/src/main/java/module-info.java
+++ /dev/null
@@ -1,8 +0,0 @@
-module com.auth0.jwt {
- requires com.fasterxml.jackson.databind;
-
- exports com.auth0.jwt;
- exports com.auth0.jwt.algorithms;
- exports com.auth0.jwt.exceptions;
- exports com.auth0.jwt.interfaces;
-}
diff --git a/lib/src/test/java/com/auth0/jwt/ConcurrentVerifyTest.java b/lib/src/test/java/com/auth0/jwt/ConcurrentVerifyTest.java
deleted file mode 100644
index 32ede1de..00000000
--- a/lib/src/test/java/com/auth0/jwt/ConcurrentVerifyTest.java
+++ /dev/null
@@ -1,162 +0,0 @@
-package com.auth0.jwt;
-
-import com.auth0.jwt.algorithms.Algorithm;
-import com.auth0.jwt.interfaces.DecodedJWT;
-import net.jodah.concurrentunit.Waiter;
-import org.junit.AfterClass;
-import org.junit.BeforeClass;
-import org.junit.Rule;
-import org.junit.Test;
-import org.junit.rules.ExpectedException;
-
-import java.security.interfaces.ECKey;
-import java.security.interfaces.RSAKey;
-import java.util.Collections;
-import java.util.List;
-import java.util.concurrent.*;
-
-import static com.auth0.jwt.PemUtils.readPublicKeyFromFile;
-
-//@Ignore("Skipping concurrency tests")
-public class ConcurrentVerifyTest {
-
- private static final long TIMEOUT = 10 * 1000 * 1000; //1 min
- private static final int THREAD_COUNT = 100;
- private static final int REPEAT_COUNT = 1000;
- private static final String PUBLIC_KEY_FILE = "src/test/resources/rsa-public.pem";
- private static final String PUBLIC_KEY_FILE_256 = "src/test/resources/ec256-key-public.pem";
- private static final String PUBLIC_KEY_FILE_384 = "src/test/resources/ec384-key-public.pem";
- private static final String PUBLIC_KEY_FILE_512 = "src/test/resources/ec512-key-public.pem";
-
- @Rule
- public ExpectedException exception = ExpectedException.none();
- private static ExecutorService executor;
-
- @BeforeClass
- public static void beforeAll() {
- executor = Executors.newFixedThreadPool(THREAD_COUNT);
- }
-
- @AfterClass
- public static void afterAll() {
- executor.shutdown();
- }
-
- @SuppressWarnings("Convert2Lambda")
- private void concurrentVerify(final JWTVerifier verifier, final String token) throws TimeoutException, InterruptedException {
- final Waiter waiter = new Waiter();
- List tasks = Collections.nCopies(REPEAT_COUNT, new VerifyTask(waiter, verifier, token));
- executor.invokeAll(tasks, TIMEOUT, TimeUnit.MILLISECONDS);
- waiter.await(TIMEOUT, REPEAT_COUNT);
- }
-
- private static class VerifyTask implements Callable {
-
- private final Waiter waiter;
- private final JWTVerifier verifier;
- private final String token;
-
- VerifyTask(Waiter waiter, final JWTVerifier verifier, final String token) {
- this.waiter = waiter;
- this.verifier = verifier;
- this.token = token;
- }
-
- @Override
- public DecodedJWT call() {
- DecodedJWT jwt = null;
- try {
- jwt = verifier.verify(token);
- waiter.assertNotNull(jwt);
- } catch (Exception e) {
- waiter.fail(e);
- }
- waiter.resume();
- return jwt;
- }
- }
-
- @Test
- public void shouldPassHMAC256Verification() throws Exception {
- Algorithm algorithm = Algorithm.HMAC256("secret");
- JWTVerifier verifier = JWTVerifier.init(algorithm).withIssuer("auth0").build();
- String token = "eyJhbGciOiJIUzI1NiIsImN0eSI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.mZ0m_N1J4PgeqWmi903JuUoDRZDBPB7HwkS4nVyWH1M";
-
- concurrentVerify(verifier, token);
- }
-
- @Test
- public void shouldPassHMAC384Verification() throws Exception {
- String token = "eyJhbGciOiJIUzM4NCIsImN0eSI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.uztpK_wUMYJhrRv8SV-1LU4aPnwl-EM1q-wJnqgyb5DHoDteP6lN_gE1xnZJH5vw";
- Algorithm algorithm = Algorithm.HMAC384("secret");
- JWTVerifier verifier = JWTVerifier.init(algorithm).withIssuer("auth0").build();
-
- concurrentVerify(verifier, token);
- }
-
- @Test
- public void shouldPassHMAC512Verification() throws Exception {
- String token = "eyJhbGciOiJIUzUxMiIsImN0eSI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.VUo2Z9SWDV-XcOc_Hr6Lff3vl7L9e5Vb8ThXpmGDFjHxe3Dr1ZBmUChYF-xVA7cAdX1P_D4ZCUcsv3IefpVaJw";
- Algorithm algorithm = Algorithm.HMAC512("secret");
- JWTVerifier verifier = JWTVerifier.init(algorithm).withIssuer("auth0").build();
-
- concurrentVerify(verifier, token);
- }
-
- @Test
- public void shouldPassRSA256Verification() throws Exception {
- String token = "eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.dxXF3MdsyW-AuvwJpaQtrZ33fAde9xWxpLIg9cO2tMLH2GSRNuLAe61KsJusZhqZB9Iy7DvflcmRz-9OZndm6cj_ThGeJH2LLc90K83UEvvRPo8l85RrQb8PcanxCgIs2RcZOLygERizB3pr5icGkzR7R2y6zgNCjKJ5_NJ6EiZsGN6_nc2PRK_DbyY-Wn0QDxIxKoA5YgQJ9qafe7IN980pXvQv2Z62c3XR8dYuaXBqhthBj-AbaFHEpZapN-V-TmuLNzR2MCB6Xr7BYMuCaqWf_XU8og4XNe8f_8w9Wv5vvgqMM1KhqVpG5VdMJv4o_L4NoCROHhtUQSLRh2M9cA";
- Algorithm algorithm = Algorithm.RSA256((RSAKey) readPublicKeyFromFile(PUBLIC_KEY_FILE, "RSA"));
- JWTVerifier verifier = JWTVerifier.init(algorithm).withIssuer("auth0").build();
-
- concurrentVerify(verifier, token);
- }
-
- @Test
- public void shouldPassRSA384Verification() throws Exception {
- String token = "eyJhbGciOiJSUzM4NCIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.TZlWjXObwGSQOiu2oMq8kiKz0_BR7bbBddNL6G8eZ_GoR82BXOZDqNrQr7lb_M-78XGBguWLWNIdYhzgxOUL9EoCJlrqVm9s9vo6G8T1sj1op-4TbjXZ61TwIvrJee9BvPLdKUJ9_fp1Js5kl6yXkst40Th8Auc5as4n49MLkipjpEhKDKaENKHpSubs1ripSz8SCQZSofeTM_EWVwSw7cpiM8Fy8jOPvWG8Xz4-e3ODFowvHVsDcONX_4FTMNbeRqDuHq2ZhCJnEfzcSJdrve_5VD5fM1LperBVslTrOxIgClOJ3RmM7-WnaizJrWP3D6Z9OLxPxLhM6-jx6tcxEw";
- Algorithm algorithm = Algorithm.RSA384((RSAKey) readPublicKeyFromFile(PUBLIC_KEY_FILE, "RSA"));
- JWTVerifier verifier = JWTVerifier.init(algorithm).withIssuer("auth0").build();
-
- concurrentVerify(verifier, token);
- }
-
- @Test
- public void shouldPassRSA512Verification() throws Exception {
- String token = "eyJhbGciOiJSUzUxMiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.mvL5LoMyIrWYjk5umEXZTmbyIrkbbcVPUkvdGZbu0qFBxGOf0nXP5PZBvPcOu084lvpwVox5n3VaD4iqzW-PsJyvKFgi5TnwmsbKchAp7JexQEsQOnTSGcfRqeUUiBZqRQdYsho71oAB3T4FnalDdFEpM-fztcZY9XqKyayqZLreTeBjqJm4jfOWH7KfGBHgZExQhe96NLq1UA9eUyQwdOA1Z0SgXe4Ja5PxZ6Fm37KnVDtDlNnY4JAAGFo6y74aGNnp_BKgpaVJCGFu1f1S5xCQ1HSvs8ZSdVWs5NgawW3wRd0kRt_GJ_Y3mIwiF4qUyHWGtsSHu_qjVdCTtbFyow";
- Algorithm algorithm = Algorithm.RSA512((RSAKey) readPublicKeyFromFile(PUBLIC_KEY_FILE, "RSA"));
- JWTVerifier verifier = JWTVerifier.init(algorithm).withIssuer("auth0").build();
-
- concurrentVerify(verifier, token);
- }
-
- @Test
- public void shouldPassECDSA256VerificationWithJOSESignature() throws Exception {
- String token = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9.4iVk3-Y0v4RT4_9IaQlp-8dZ_4fsTzIylgrPTDLrEvTHBTyVS3tgPbr2_IZfLETtiKRqCg0aQ5sh9eIsTTwB1g";
- ECKey key = (ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC");
- Algorithm algorithm = Algorithm.ECDSA256(key);
- JWTVerifier verifier = JWTVerifier.init(algorithm).withIssuer("auth0").build();
-
- concurrentVerify(verifier, token);
- }
-
- @Test
- public void shouldPassECDSA384VerificationWithJOSESignature() throws Exception {
- String token = "eyJhbGciOiJFUzM4NCJ9.eyJpc3MiOiJhdXRoMCJ9.50UU5VKNdF1wfykY8jQBKpvuHZoe6IZBJm5NvoB8bR-hnRg6ti-CHbmvoRtlLfnHfwITa_8cJMy6TenMC2g63GQHytc8rYoXqbwtS4R0Ko_AXbLFUmfxnGnMC6v4MS_z";
- ECKey key = (ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_384, "EC");
- Algorithm algorithm = Algorithm.ECDSA384(key);
- JWTVerifier verifier = JWTVerifier.init(algorithm).withIssuer("auth0").build();
-
- concurrentVerify(verifier, token);
- }
-
- @Test
- public void shouldPassECDSA512VerificationWithJOSESignature() throws Exception {
- String token = "eyJhbGciOiJFUzUxMiJ9.eyJpc3MiOiJhdXRoMCJ9.AeCJPDIsSHhwRSGZCY6rspi8zekOw0K9qYMNridP1Fu9uhrA1QrG-EUxXlE06yvmh2R7Rz0aE7kxBwrnq8L8aOBCAYAsqhzPeUvyp8fXjjgs0Eto5I0mndE2QHlgcMSFASyjHbU8wD2Rq7ZNzGQ5b2MZfpv030WGUajT-aZYWFUJHVg2";
- ECKey key = (ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_512, "EC");
- Algorithm algorithm = Algorithm.ECDSA512(key);
- JWTVerifier verifier = JWTVerifier.init(algorithm).withIssuer("auth0").build();
-
- concurrentVerify(verifier, token);
- }
-}
diff --git a/lib/src/test/java/com/auth0/jwt/JWTCreatorTest.java b/lib/src/test/java/com/auth0/jwt/JWTCreatorTest.java
deleted file mode 100644
index 53cd267b..00000000
--- a/lib/src/test/java/com/auth0/jwt/JWTCreatorTest.java
+++ /dev/null
@@ -1,1060 +0,0 @@
-package com.auth0.jwt;
-
-import com.auth0.jwt.algorithms.Algorithm;
-import com.auth0.jwt.interfaces.ECDSAKeyProvider;
-import com.auth0.jwt.interfaces.RSAKeyProvider;
-import com.fasterxml.jackson.databind.ObjectMapper;
-import com.fasterxml.jackson.databind.node.ObjectNode;
-import org.junit.Rule;
-import org.junit.Test;
-import org.junit.rules.ExpectedException;
-
-import java.nio.charset.StandardCharsets;
-import java.security.interfaces.ECPrivateKey;
-import java.security.interfaces.RSAPrivateKey;
-import java.time.Instant;
-import java.util.*;
-
-import static org.hamcrest.MatcherAssert.assertThat;
-import static org.hamcrest.Matchers.*;
-import static org.junit.Assert.assertTrue;
-import static org.mockito.Mockito.mock;
-import static org.mockito.Mockito.when;
-
-public class JWTCreatorTest {
-
- private static final String PRIVATE_KEY_FILE_RSA = "src/test/resources/rsa-private.pem";
- private static final String PRIVATE_KEY_FILE_EC_256 = "src/test/resources/ec256-key-private.pem";
-
- @Rule
- public ExpectedException exception = ExpectedException.none();
-
- @Test
- public void shouldThrowWhenRequestingSignWithoutAlgorithm() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("The Algorithm cannot be null");
- JWTCreator.init()
- .sign(null);
- }
-
- @Test
- public void shouldAddHeaderClaim() {
- Date date = new Date(123000);
- Instant instant = date.toInstant();
-
- List list = Arrays.asList(date, instant);
- Map map = new HashMap<>();
- map.put("date", date);
- map.put("instant", instant);
-
- List expectedSerializedList = Arrays.asList(date.getTime() / 1000, instant.getEpochSecond());
- Map expectedSerializedMap = new HashMap<>();
- expectedSerializedMap.put("date", date.getTime() / 1000);
- expectedSerializedMap.put("instant", instant.getEpochSecond());
-
- Map header = new HashMap<>();
- header.put("string", "string");
- header.put("int", 42);
- header.put("long", 4200000000L);
- header.put("double", 123.123);
- header.put("bool", true);
- header.put("date", date);
- header.put("instant", instant);
- header.put("list", list);
- header.put("map", map);
-
- String signed = JWTCreator.init()
- .withHeader(header)
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(signed, is(notNullValue()));
- String[] parts = signed.split("\\.");
- String headerJson = new String(Base64.getUrlDecoder().decode(parts[0]), StandardCharsets.UTF_8);
- assertThat(headerJson, JsonMatcher.hasEntry("string", "string"));
- assertThat(headerJson, JsonMatcher.hasEntry("int", 42));
- assertThat(headerJson, JsonMatcher.hasEntry("long", 4200000000L));
- assertThat(headerJson, JsonMatcher.hasEntry("double", 123.123));
- assertThat(headerJson, JsonMatcher.hasEntry("bool", true));
- assertThat(headerJson, JsonMatcher.hasEntry("date", 123));
- assertThat(headerJson, JsonMatcher.hasEntry("instant", 123));
- assertThat(headerJson, JsonMatcher.hasEntry("list", expectedSerializedList));
- assertThat(headerJson, JsonMatcher.hasEntry("map", expectedSerializedMap));
- }
-
- @Test
- public void shouldReturnBuilderIfNullMapIsProvided() {
- Map nullMap = null;
- String nullString = null;
- String signed = JWTCreator.init()
- .withHeader(nullMap)
- .withHeader(nullString)
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(signed, is(notNullValue()));
- }
-
- @Test
- public void shouldSupportJsonValueHeaderWithNestedDataStructure() {
- String stringClaim = "someClaim";
- Integer intClaim = 1;
- List nestedListClaims = Arrays.asList("1", "2");
- String claimsJson = "{\"stringClaim\": \"someClaim\", \"intClaim\": 1, \"nestedClaim\": { \"listClaim\": [ \"1\", \"2\" ]}}";
-
- String jwt = JWTCreator.init()
- .withHeader(claimsJson)
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(jwt, is(notNullValue()));
- String[] parts = jwt.split("\\.");
- String headerJson = new String(Base64.getUrlDecoder().decode(parts[0]), StandardCharsets.UTF_8);
-
- assertThat(headerJson, JsonMatcher.hasEntry("stringClaim", stringClaim));
- assertThat(headerJson, JsonMatcher.hasEntry("intClaim", intClaim));
- assertThat(headerJson, JsonMatcher.hasEntry("listClaim", nestedListClaims));
- }
-
- @Test
- public void shouldFailWithIllegalArgumentExceptionForInvalidJsonForHeaderClaims() {
- String invalidJson = "{ invalidJson }";
-
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("Invalid header JSON");
-
- JWTCreator.init()
- .withHeader(invalidJson)
- .sign(Algorithm.HMAC256("secret"));
- }
-
- @Test
- public void shouldOverwriteExistingHeaderIfHeaderMapContainsTheSameKey() {
- Map header = new HashMap<>();
- header.put(HeaderParams.KEY_ID, "xyz");
-
- String signed = JWTCreator.init()
- .withKeyId("abc")
- .withHeader(header)
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(signed, is(notNullValue()));
- String[] parts = signed.split("\\.");
- String headerJson = new String(Base64.getUrlDecoder().decode(parts[0]), StandardCharsets.UTF_8);
- assertThat(headerJson, JsonMatcher.hasEntry(HeaderParams.KEY_ID, "xyz"));
- }
-
-
- @Test
- public void shouldOverwriteExistingHeadersWhenSettingSameHeaderKey() {
- Map header = new HashMap<>();
- header.put(HeaderParams.KEY_ID, "xyz");
-
- String signed = JWTCreator.init()
- .withHeader(header)
- .withKeyId("abc")
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(signed, is(notNullValue()));
- String[] parts = signed.split("\\.");
- String headerJson = new String(Base64.getUrlDecoder().decode(parts[0]), StandardCharsets.UTF_8);
- assertThat(headerJson, JsonMatcher.hasEntry(HeaderParams.KEY_ID, "abc"));
- }
-
- @Test
- public void shouldRemoveHeaderIfTheValueIsNull() {
- Map header = new HashMap<>();
- header.put(HeaderParams.KEY_ID, null);
- header.put("test2", "isSet");
-
- String signed = JWTCreator.init()
- .withKeyId("test")
- .withHeader(header)
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(signed, is(notNullValue()));
- String[] parts = signed.split("\\.");
- String headerJson = new String(Base64.getUrlDecoder().decode(parts[0]), StandardCharsets.UTF_8);
- assertThat(headerJson, JsonMatcher.isNotPresent(HeaderParams.KEY_ID));
- assertThat(headerJson, JsonMatcher.hasEntry("test2", "isSet"));
- }
-
- @Test
- public void shouldAddKeyId() {
- String signed = JWTCreator.init()
- .withKeyId("56a8bd44da435300010000015f5ed")
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(signed, is(notNullValue()));
- String[] parts = signed.split("\\.");
- String headerJson = new String(Base64.getUrlDecoder().decode(parts[0]), StandardCharsets.UTF_8);
- assertThat(headerJson, JsonMatcher.hasEntry("kid", "56a8bd44da435300010000015f5ed"));
- }
-
- @Test
- public void shouldAddKeyIdIfAvailableFromRSAAlgorithms() throws Exception {
- RSAPrivateKey privateKey = (RSAPrivateKey) PemUtils.readPrivateKeyFromFile(PRIVATE_KEY_FILE_RSA, "RSA");
- RSAKeyProvider provider = mock(RSAKeyProvider.class);
- when(provider.getPrivateKeyId()).thenReturn("my-key-id");
- when(provider.getPrivateKey()).thenReturn(privateKey);
-
- String signed = JWTCreator.init()
- .sign(Algorithm.RSA256(provider));
-
- assertThat(signed, is(notNullValue()));
- String[] parts = signed.split("\\.");
- String headerJson = new String(Base64.getUrlDecoder().decode(parts[0]), StandardCharsets.UTF_8);
- assertThat(headerJson, JsonMatcher.hasEntry("kid", "my-key-id"));
- }
-
- @Test
- public void shouldNotOverwriteKeyIdIfAddedFromRSAAlgorithms() throws Exception {
- RSAPrivateKey privateKey = (RSAPrivateKey) PemUtils.readPrivateKeyFromFile(PRIVATE_KEY_FILE_RSA, "RSA");
- RSAKeyProvider provider = mock(RSAKeyProvider.class);
- when(provider.getPrivateKeyId()).thenReturn("my-key-id");
- when(provider.getPrivateKey()).thenReturn(privateKey);
-
- String signed = JWTCreator.init()
- .withKeyId("real-key-id")
- .sign(Algorithm.RSA256(provider));
-
- assertThat(signed, is(notNullValue()));
- String[] parts = signed.split("\\.");
- String headerJson = new String(Base64.getUrlDecoder().decode(parts[0]), StandardCharsets.UTF_8);
- assertThat(headerJson, JsonMatcher.hasEntry("kid", "my-key-id"));
- }
-
- @Test
- public void shouldAddKeyIdIfAvailableFromECDSAAlgorithms() throws Exception {
- ECPrivateKey privateKey = (ECPrivateKey) PemUtils.readPrivateKeyFromFile(PRIVATE_KEY_FILE_EC_256, "EC");
- ECDSAKeyProvider provider = mock(ECDSAKeyProvider.class);
- when(provider.getPrivateKeyId()).thenReturn("my-key-id");
- when(provider.getPrivateKey()).thenReturn(privateKey);
-
- String signed = JWTCreator.init()
- .sign(Algorithm.ECDSA256(provider));
-
- assertThat(signed, is(notNullValue()));
- String[] parts = signed.split("\\.");
- String headerJson = new String(Base64.getUrlDecoder().decode(parts[0]), StandardCharsets.UTF_8);
- assertThat(headerJson, JsonMatcher.hasEntry("kid", "my-key-id"));
- }
-
- @Test
- public void shouldNotOverwriteKeyIdIfAddedFromECDSAAlgorithms() throws Exception {
- ECPrivateKey privateKey = (ECPrivateKey) PemUtils.readPrivateKeyFromFile(PRIVATE_KEY_FILE_EC_256, "EC");
- ECDSAKeyProvider provider = mock(ECDSAKeyProvider.class);
- when(provider.getPrivateKeyId()).thenReturn("my-key-id");
- when(provider.getPrivateKey()).thenReturn(privateKey);
-
- String signed = JWTCreator.init()
- .withKeyId("real-key-id")
- .sign(Algorithm.ECDSA256(provider));
-
- assertThat(signed, is(notNullValue()));
- String[] parts = signed.split("\\.");
- String headerJson = new String(Base64.getUrlDecoder().decode(parts[0]), StandardCharsets.UTF_8);
- assertThat(headerJson, JsonMatcher.hasEntry("kid", "my-key-id"));
- }
-
- @Test
- public void shouldAddIssuer() {
- String signed = JWTCreator.init()
- .withIssuer("auth0")
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(signed, is(notNullValue()));
- assertThat(TokenUtils.splitToken(signed)[1], is("eyJpc3MiOiJhdXRoMCJ9"));
- }
-
- @Test
- public void shouldAddSubject() {
- String signed = JWTCreator.init()
- .withSubject("1234567890")
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(signed, is(notNullValue()));
- assertThat(TokenUtils.splitToken(signed)[1], is("eyJzdWIiOiIxMjM0NTY3ODkwIn0"));
- }
-
- @Test
- public void shouldAddAudience() {
- String signed = JWTCreator.init()
- .withAudience("Mark")
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(signed, is(notNullValue()));
- assertThat(TokenUtils.splitToken(signed)[1], is("eyJhdWQiOiJNYXJrIn0"));
-
-
- String signedArr = JWTCreator.init()
- .withAudience("Mark", "David")
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(signedArr, is(notNullValue()));
- assertThat(TokenUtils.splitToken(signedArr)[1], is("eyJhdWQiOlsiTWFyayIsIkRhdmlkIl19"));
- }
-
- @Test
- public void shouldAddExpiresAt() {
- String signed = JWTCreator.init()
- .withExpiresAt(new Date(1477592000))
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(signed, is(notNullValue()));
- assertThat(TokenUtils.splitToken(signed)[1], is("eyJleHAiOjE0Nzc1OTJ9"));
- }
-
- @Test
- public void shouldAddExpiresAtInstant() {
- String signed = JWTCreator.init()
- .withExpiresAt(Instant.ofEpochSecond(1477592))
- .sign(Algorithm.HMAC256("secret"));
-
- System.out.println(signed);
- assertThat(signed, is(notNullValue()));
- assertThat(TokenUtils.splitToken(signed)[1], is("eyJleHAiOjE0Nzc1OTJ9"));
- }
-
- @Test
- public void shouldAddNotBefore() {
- String signed = JWTCreator.init()
- .withNotBefore(new Date(1477592000))
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(signed, is(notNullValue()));
- assertThat(TokenUtils.splitToken(signed)[1], is("eyJuYmYiOjE0Nzc1OTJ9"));
- }
-
- @Test
- public void shouldAddNotBeforeInstant() {
- String signed = JWTCreator.init()
- .withNotBefore(Instant.ofEpochSecond(1477592))
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(signed, is(notNullValue()));
- assertThat(TokenUtils.splitToken(signed)[1], is("eyJuYmYiOjE0Nzc1OTJ9"));
- }
-
- @Test
- public void shouldAddIssuedAt() {
- String signed = JWTCreator.init()
- .withIssuedAt(new Date(1477592000))
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(signed, is(notNullValue()));
- assertThat(TokenUtils.splitToken(signed)[1], is("eyJpYXQiOjE0Nzc1OTJ9"));
- }
-
- @Test
- public void shouldAddIssuedAtInstant() {
- String signed = JWTCreator.init()
- .withIssuedAt(Instant.ofEpochSecond(1477592))
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(signed, is(notNullValue()));
- assertThat(TokenUtils.splitToken(signed)[1], is("eyJpYXQiOjE0Nzc1OTJ9"));
- }
-
- @Test
- public void shouldAddJWTId() {
- String signed = JWTCreator.init()
- .withJWTId("jwt_id_123")
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(signed, is(notNullValue()));
- assertThat(TokenUtils.splitToken(signed)[1], is("eyJqdGkiOiJqd3RfaWRfMTIzIn0"));
- }
-
- @Test
- public void shouldSetCorrectAlgorithmInTheHeader() {
- String signed = JWTCreator.init()
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(signed, is(notNullValue()));
- String[] parts = signed.split("\\.");
- String headerJson = new String(Base64.getUrlDecoder().decode(parts[0]), StandardCharsets.UTF_8);
- assertThat(headerJson, JsonMatcher.hasEntry("alg", "HS256"));
- }
-
- @Test
- public void shouldSetDefaultTypeInTheHeader() {
- String signed = JWTCreator.init()
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(signed, is(notNullValue()));
- String[] parts = signed.split("\\.");
- String headerJson = new String(Base64.getUrlDecoder().decode(parts[0]), StandardCharsets.UTF_8);
- assertThat(headerJson, JsonMatcher.hasEntry("typ", "JWT"));
- }
-
- @Test
- public void shouldSetCustomTypeInTheHeader() {
- Map header = Collections.singletonMap("typ", "passport");
- String signed = JWTCreator.init()
- .withHeader(header)
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(signed, is(notNullValue()));
- String[] parts = signed.split("\\.");
- String headerJson = new String(Base64.getUrlDecoder().decode(parts[0]), StandardCharsets.UTF_8);
- assertThat(headerJson, JsonMatcher.hasEntry("typ", "passport"));
- }
-
- @Test
- public void shouldSetEmptySignatureIfAlgorithmIsNone() {
- String signed = JWTCreator.init()
- .sign(Algorithm.none());
- assertThat(signed, is(notNullValue()));
- assertThat(TokenUtils.splitToken(signed)[2], is(""));
- }
-
- @Test
- public void shouldThrowOnNullCustomClaimName() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("The Custom Claim's name can't be null.");
- JWTCreator.init()
- .withClaim(null, "value");
- }
-
- @Test
- public void shouldAcceptCustomClaimOfTypeString() {
- String jwt = JWTCreator.init()
- .withClaim("name", "value")
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(jwt, is(notNullValue()));
- String[] parts = jwt.split("\\.");
- assertThat(parts[1], is("eyJuYW1lIjoidmFsdWUifQ"));
- }
-
- @Test
- public void shouldAcceptCustomClaimOfTypeInteger() {
- String jwt = JWTCreator.init()
- .withClaim("name", 123)
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(jwt, is(notNullValue()));
- String[] parts = jwt.split("\\.");
- assertThat(parts[1], is("eyJuYW1lIjoxMjN9"));
- }
-
- @Test
- public void shouldAcceptCustomClaimOfTypeLong() {
- String jwt = JWTCreator.init()
- .withClaim("name", Long.MAX_VALUE)
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(jwt, is(notNullValue()));
- String[] parts = jwt.split("\\.");
- assertThat(parts[1], is("eyJuYW1lIjo5MjIzMzcyMDM2ODU0Nzc1ODA3fQ"));
- }
-
- @Test
- public void shouldAcceptCustomClaimOfTypeDouble() {
- String jwt = JWTCreator.init()
- .withClaim("name", 23.45)
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(jwt, is(notNullValue()));
- String[] parts = jwt.split("\\.");
- assertThat(parts[1], is("eyJuYW1lIjoyMy40NX0"));
- }
-
- @Test
- public void shouldAcceptCustomClaimOfTypeBoolean() {
- String jwt = JWTCreator.init()
- .withClaim("name", true)
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(jwt, is(notNullValue()));
- String[] parts = jwt.split("\\.");
- assertThat(parts[1], is("eyJuYW1lIjp0cnVlfQ"));
- }
-
- @Test
- public void shouldAcceptCustomClaimOfTypeDate() {
- Date date = new Date(1478891521000L);
- String jwt = JWTCreator.init()
- .withClaim("name", date)
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(jwt, is(notNullValue()));
- String[] parts = jwt.split("\\.");
- assertThat(parts[1], is("eyJuYW1lIjoxNDc4ODkxNTIxfQ"));
- }
-
- @Test
- public void shouldAcceptCustomClaimOfTypeDateInstant() {
- Instant instant = Instant.ofEpochSecond(1478891521);
- String jwt = JWTCreator.init()
- .withClaim("name", instant)
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(jwt, is(notNullValue()));
- String[] parts = jwt.split("\\.");
- assertThat(parts[1], is("eyJuYW1lIjoxNDc4ODkxNTIxfQ"));
- }
-
- @Test
- public void shouldAcceptCustomArrayClaimOfTypeString() {
- String jwt = JWTCreator.init()
- .withArrayClaim("name", new String[]{"text", "123", "true"})
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(jwt, is(notNullValue()));
- String[] parts = jwt.split("\\.");
- assertThat(parts[1], is("eyJuYW1lIjpbInRleHQiLCIxMjMiLCJ0cnVlIl19"));
- }
-
- @Test
- public void shouldAcceptCustomArrayClaimOfTypeInteger() {
- String jwt = JWTCreator.init()
- .withArrayClaim("name", new Integer[]{1, 2, 3})
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(jwt, is(notNullValue()));
- String[] parts = jwt.split("\\.");
- assertThat(parts[1], is("eyJuYW1lIjpbMSwyLDNdfQ"));
- }
-
- @Test
- public void shouldAcceptCustomArrayClaimOfTypeLong() {
- String jwt = JWTCreator.init()
- .withArrayClaim("name", new Long[]{1L, 2L, 3L})
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(jwt, is(notNullValue()));
- String[] parts = jwt.split("\\.");
- assertThat(parts[1], is("eyJuYW1lIjpbMSwyLDNdfQ"));
- }
-
- @Test
- public void shouldAcceptCustomClaimOfTypeMap() {
- Map data = new HashMap<>();
- data.put("test1", "abc");
- data.put("test2", "def");
- String jwt = JWTCreator.init()
- .withClaim("data", data)
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(jwt, is(notNullValue()));
- String[] parts = jwt.split("\\.");
- assertThat(parts[1], is("eyJkYXRhIjp7InRlc3QyIjoiZGVmIiwidGVzdDEiOiJhYmMifX0"));
- }
-
- @Test
- public void shouldRefuseCustomClaimOfTypeUserPojo() {
- Map data = new HashMap<>();
- data.put("test1", new UserPojo("Michael", 255));
-
- exception.expect(IllegalArgumentException.class);
-
- JWTCreator.init()
- .withClaim("pojo", data)
- .sign(Algorithm.HMAC256("secret"));
- }
-
- @SuppressWarnings("unchecked")
- @Test
- public void shouldAcceptCustomMapClaimOfBasicObjectTypes() throws Exception {
- Map data = new HashMap<>();
-
- // simple types
- data.put("string", "abc");
- data.put("integer", 1);
- data.put("long", Long.MAX_VALUE);
- data.put("double", 123.456d);
- data.put("date", new Date(123000L));
- data.put("instant", Instant.ofEpochSecond(123));
- data.put("boolean", true);
-
- // array types
- data.put("intArray", new Integer[]{3, 5});
- data.put("longArray", new Long[]{Long.MAX_VALUE, Long.MIN_VALUE});
- data.put("stringArray", new String[]{"string"});
-
- data.put("list", Arrays.asList("a", "b", "c"));
-
- Map sub = new HashMap<>();
- sub.put("subKey", "subValue");
-
- data.put("map", sub);
-
- String jwt = JWTCreator.init()
- .withClaim("data", data)
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(jwt, is(notNullValue()));
- String[] parts = jwt.split("\\.");
-
- String body = new String(Base64.getUrlDecoder().decode(parts[1]), StandardCharsets.UTF_8);
- ObjectMapper mapper = new ObjectMapper();
- Map map = (Map) mapper.readValue(body, Map.class).get("data");
-
- assertThat(map.get("string"), is("abc"));
- assertThat(map.get("integer"), is(1));
- assertThat(map.get("long"), is(Long.MAX_VALUE));
- assertThat(map.get("double"), is(123.456d));
-
- assertThat(map.get("date"), is(123));
- assertThat(map.get("instant"), is(123));
- assertThat(map.get("boolean"), is(true));
-
- // array types
- assertThat(map.get("intArray"), is(Arrays.asList(3, 5)));
- assertThat(map.get("longArray"), is(Arrays.asList(Long.MAX_VALUE, Long.MIN_VALUE)));
- assertThat(map.get("stringArray"), is(Collections.singletonList("string")));
-
- // list
- assertThat(map.get("list"), is(Arrays.asList("a", "b", "c")));
- assertThat(map.get("map"), is(sub));
-
- }
-
- @SuppressWarnings("unchecked")
- @Test
- public void shouldAcceptCustomListClaimOfBasicObjectTypes() throws Exception {
- List data = new ArrayList<>();
-
- // simple types
- data.add("abc");
- data.add(1);
- data.add(Long.MAX_VALUE);
- data.add(123.456d);
- data.add(new Date(123000L));
- data.add(Instant.ofEpochSecond(123));
- data.add(true);
-
- // array types
- data.add(new Integer[]{3, 5});
- data.add(new Long[]{Long.MAX_VALUE, Long.MIN_VALUE});
- data.add(new String[]{"string"});
-
- data.add(Arrays.asList("a", "b", "c"));
-
- Map sub = new HashMap<>();
- sub.put("subKey", "subValue");
-
- data.add(sub);
-
- String jwt = JWTCreator.init()
- .withClaim("data", data)
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(jwt, is(notNullValue()));
- String[] parts = jwt.split("\\.");
-
- String body = new String(Base64.getUrlDecoder().decode(parts[1]), StandardCharsets.UTF_8);
- ObjectMapper mapper = new ObjectMapper();
- List list = (List) mapper.readValue(body, Map.class).get("data");
-
- assertThat(list.get(0), is("abc"));
- assertThat(list.get(1), is(1));
- assertThat(list.get(2), is(Long.MAX_VALUE));
- assertThat(list.get(3), is(123.456d));
- assertThat(list.get(4), is(123));
- assertThat(list.get(5), is(123));
- assertThat(list.get(6), is(true));
-
- // array types
- assertThat(list.get(7), is(Arrays.asList(3, 5)));
- assertThat(list.get(8), is(Arrays.asList(Long.MAX_VALUE, Long.MIN_VALUE)));
- assertThat(list.get(9), is(Arrays.asList("string")));
-
- // list
- assertThat(list.get(10), is(Arrays.asList("a", "b", "c")));
- assertThat(list.get(11), is(sub));
- }
-
- @Test
- public void shouldAcceptCustomClaimForNullListItem() {
- Map data = new HashMap<>();
- data.put("test1", Arrays.asList("a", null, "c"));
-
- JWTCreator.init()
- .withClaim("pojo", data)
- .sign(Algorithm.HMAC256("secret"));
- }
-
- @Test
- public void shouldRefuseCustomClaimForNullMapKey() {
- Map data = new HashMap<>();
- data.put(null, "subValue");
-
- exception.expect(IllegalArgumentException.class);
-
- JWTCreator.init()
- .withClaim("pojo", data)
- .sign(Algorithm.HMAC256("secret"));
- }
-
- @SuppressWarnings({"unchecked", "rawtypes"})
- @Test
- public void shouldRefuseCustomMapClaimForNonStringKey() {
- Map data = new HashMap<>();
- data.put(new Object(), "value");
-
- exception.expect(IllegalArgumentException.class);
-
- JWTCreator.init()
- .withClaim("pojo", (Map) data)
- .sign(Algorithm.HMAC256("secret"));
- }
-
- @Test
- public void shouldRefuseCustomListClaimForUnknownListElement() {
- List list = Collections.singletonList(new UserPojo("Michael", 255));
-
- exception.expect(IllegalArgumentException.class);
-
- JWTCreator.init()
- .withClaim("list", list)
- .sign(Algorithm.HMAC256("secret"));
- }
-
- @Test
- public void shouldRefuseCustomListClaimForUnknownListElementWrappedInAMap() {
- List list = Collections.singletonList(new UserPojo("Michael", 255));
-
- Map data = new HashMap<>();
- data.put("someList", list);
-
- exception.expect(IllegalArgumentException.class);
-
- JWTCreator.init()
- .withClaim("list", list)
- .sign(Algorithm.HMAC256("secret"));
- }
-
- @Test
- public void shouldRefuseCustomListClaimForUnknownArrayType() {
- List list = new ArrayList<>();
- list.add(new Object[]{"test"});
-
- exception.expect(IllegalArgumentException.class);
-
- JWTCreator.init()
- .withClaim("list", list)
- .sign(Algorithm.HMAC256("secret"));
- }
-
- @Test
- public void withPayloadShouldAddBasicClaim() {
- Map payload = new HashMap<>();
- payload.put("asd", 123);
- String jwt = JWTCreator.init()
- .withPayload(payload)
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(jwt, is(notNullValue()));
- String[] parts = jwt.split("\\.");
- String payloadJson = new String(Base64.getUrlDecoder().decode(parts[1]), StandardCharsets.UTF_8);
- assertThat(payloadJson, JsonMatcher.hasEntry("asd", 123));
- }
-
- @Test
- public void withPayloadShouldCreateJwtWithEmptyBodyIfPayloadNull() {
- Map nullMap = null;
- String nullString = null;
- String jwt = JWTCreator.init()
- .withPayload(nullMap)
- .withPayload(nullString)
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(jwt, is(notNullValue()));
- String[] parts = jwt.split("\\.");
- String payloadJson = new String(Base64.getUrlDecoder().decode(parts[1]), StandardCharsets.UTF_8);
- assertThat(payloadJson, is("{}"));
- }
-
- @Test
- public void withPayloadShouldOverwriteExistingClaimIfPayloadMapContainsTheSameKey() {
- Map payload = new HashMap<>();
- payload.put(HeaderParams.KEY_ID, "xyz");
-
- String jwt = JWTCreator.init()
- .withKeyId("abc")
- .withPayload(payload)
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(jwt, is(notNullValue()));
- String[] parts = jwt.split("\\.");
- String payloadJson = new String(Base64.getUrlDecoder().decode(parts[1]), StandardCharsets.UTF_8);
- assertThat(payloadJson, JsonMatcher.hasEntry(HeaderParams.KEY_ID, "xyz"));
- }
-
- @Test
- public void shouldOverwriteExistingPayloadWhenSettingSamePayloadKey() {
- Map payload = new HashMap<>();
- payload.put(RegisteredClaims.ISSUER, "xyz");
-
- String jwt = JWTCreator.init()
- .withPayload(payload)
- .withIssuer("abc")
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(jwt, is(notNullValue()));
- String[] parts = jwt.split("\\.");
- String payloadJson = new String(Base64.getUrlDecoder().decode(parts[1]), StandardCharsets.UTF_8);
- assertThat(payloadJson, JsonMatcher.hasEntry(RegisteredClaims.ISSUER, "abc"));
- }
-
- @Test
- public void withPayloadShouldNotAllowCustomType() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("Claim values must only be of types Map, List, Boolean, Integer, Long, Double, String, Date, Instant, and Null");
-
- Map payload = new HashMap<>();
- payload.put("entry", "value");
- payload.put("pojo", new UserPojo("name", 42));
- JWTCreator.init()
- .withPayload(payload)
- .sign(Algorithm.HMAC256("secret"));
- }
-
- @Test
- public void withPayloadShouldAllowNullListItems() {
- Map payload = new HashMap<>();
- payload.put("list", Arrays.asList("item1", null, "item2"));
- String jwt = JWTCreator.init()
- .withPayload(payload)
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(jwt, is(notNullValue()));
- String[] parts = jwt.split("\\.");
- String payloadJson = new String(Base64.getUrlDecoder().decode(parts[1]), StandardCharsets.UTF_8);
- assertThat(payloadJson, JsonMatcher.hasEntry("list", Arrays.asList("item1", null, "item2")));
- }
-
- @Test
- public void withPayloadShouldNotAllowListWithCustomType() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("Claim values must only be of types Map, List, Boolean, Integer, Long, Double, String, Date, Instant, and Null");
-
- Map payload = new HashMap<>();
- payload.put("list", Arrays.asList("item1", new UserPojo("name", 42)));
- JWTCreator.init()
- .withPayload(payload)
- .sign(Algorithm.HMAC256("secret"));
- }
-
- @Test
- public void withPayloadShouldNotAllowMapWithCustomType() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("Claim values must only be of types Map, List, Boolean, Integer, Long, Double, String, Date, Instant, and Null");
-
- Map payload = new HashMap<>();
- payload.put("entry", "value");
- payload.put("map", Collections.singletonMap("pojo", new UserPojo("name", 42)));
- JWTCreator.init()
- .withPayload(payload)
- .sign(Algorithm.HMAC256("secret"));
- }
-
- @Test
- public void withPayloadShouldAllowNestedSupportedTypes() {
- /*
- JWT:
- {
- "stringClaim": "string",
- "intClaim": 41,
- "listClaim": [
- 1, 2, {
- "nestedObjKey": true
- }
- ],
- "objClaim": {
- "objKey": ["nestedList1", "nestedList2"]
- }
- }
- */
-
- List> listClaim = Arrays.asList(1, 2, Collections.singletonMap("nestedObjKey", "nestedObjValue"));
- Map mapClaim = new HashMap<>();
- mapClaim.put("objKey", Arrays.asList("nestedList1", true));
-
- Map payload = new HashMap<>();
- payload.put("stringClaim", "string");
- payload.put("intClaim", 41);
- payload.put("listClaim", listClaim);
- payload.put("objClaim", mapClaim);
-
- String jwt = JWTCreator.init()
- .withPayload(payload)
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(jwt, is(notNullValue()));
- String[] parts = jwt.split("\\.");
- String payloadJson = new String(Base64.getUrlDecoder().decode(parts[1]), StandardCharsets.UTF_8);
- assertThat(payloadJson, JsonMatcher.hasEntry("stringClaim", "string"));
- assertThat(payloadJson, JsonMatcher.hasEntry("intClaim", 41));
- assertThat(payloadJson, JsonMatcher.hasEntry("listClaim", listClaim));
- assertThat(payloadJson, JsonMatcher.hasEntry("objClaim", mapClaim));
- }
-
- @Test
- public void withPayloadShouldSupportNullValuesEverywhere() {
- /*
- JWT:
- {
- "listClaim": [
- "answer to ultimate question of life",
- 42,
- null
- ],
- "claim": null,
- "listNestedClaim": [
- 1,
- 2,
- {
- "nestedObjKey": null
- }
- ],
- "objClaim": {
- "nestedObjKey": null,
- "objObjKey": {
- "nestedObjKey": null,
- "objListKey": [
- null,
- "nestedList2"
- ]
- },
- "objListKey": [
- null,
- "nestedList2"
- ]
- }
- }
- */
-
- List> listClaim = Arrays.asList("answer to ultimate question of life", 42, null);
- List> listNestedClaim = Arrays.asList(1, 2, Collections.singletonMap("nestedObjKey", null));
- List> objListKey = Arrays.asList(null, "nestedList2");
- HashMap objClaim = new HashMap<>();
- objClaim.put("nestedObjKey", null);
- objClaim.put("objListKey", objListKey);
- objClaim.put("objObjKey", new HashMap<>(objClaim));
-
-
- Map payload = new HashMap<>();
- payload.put("claim", null);
- payload.put("listClaim", listClaim);
- payload.put("listNestedClaim", listNestedClaim);
- payload.put("objClaim", objClaim);
-
- String jwt = JWTCreator.init()
- .withPayload(payload)
- .withHeader(payload)
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(jwt, is(notNullValue()));
- String[] parts = jwt.split("\\.");
- String payloadJson = new String(Base64.getUrlDecoder().decode(parts[1]), StandardCharsets.UTF_8);
- String headerJson = new String(Base64.getUrlDecoder().decode(parts[0]), StandardCharsets.UTF_8);
-
- assertThat(payloadJson, JsonMatcher.hasEntry("claim", null));
- assertThat(payloadJson, JsonMatcher.hasEntry("listClaim", listClaim));
- assertThat(payloadJson, JsonMatcher.hasEntry("listNestedClaim", listNestedClaim));
- assertThat(payloadJson, JsonMatcher.hasEntry("objClaim", objClaim));
-
- assertThat(headerJson, JsonMatcher.hasEntry("claim", null));
- assertThat(headerJson, JsonMatcher.hasEntry("listClaim", listClaim));
- assertThat(headerJson, JsonMatcher.hasEntry("listNestedClaim", listNestedClaim));
- assertThat(headerJson, JsonMatcher.hasEntry("objClaim", objClaim));
- }
-
- @Test
- public void withPayloadShouldSupportJsonValueWithNestedDataStructure() {
- String stringClaim = "someClaim";
- Integer intClaim = 1;
- List nestedListClaims = Arrays.asList("1", "2");
- String claimsJson = "{\"stringClaim\": \"someClaim\", \"intClaim\": 1, \"nestedClaim\": { \"listClaim\": [ \"1\", \"2\" ]}}";
-
- String jwt = JWTCreator.init()
- .withPayload(claimsJson)
- .sign(Algorithm.HMAC256("secret"));
-
- assertThat(jwt, is(notNullValue()));
- String[] parts = jwt.split("\\.");
- String payloadJson = new String(Base64.getUrlDecoder().decode(parts[1]), StandardCharsets.UTF_8);
-
- assertThat(payloadJson, JsonMatcher.hasEntry("stringClaim", stringClaim));
- assertThat(payloadJson, JsonMatcher.hasEntry("intClaim", intClaim));
- assertThat(payloadJson, JsonMatcher.hasEntry("listClaim", nestedListClaims));
- }
-
- @Test
- public void shouldFailWithIllegalArgumentExceptionForInvalidJsonForPayloadClaims() {
- String invalidJson = "{ invalidJson }";
-
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("Invalid payload JSON");
-
- JWTCreator.init()
- .withPayload(invalidJson)
- .sign(Algorithm.HMAC256("secret"));
- }
-
- @Test
- public void shouldCreatePayloadWithNullForMap() {
- String jwt = JWTCreator.init()
- .withClaim("name", (Map) null)
- .sign(Algorithm.HMAC256("secret"));
- assertThat(jwt, is(notNullValue()));
- assertTrue(JWT.decode(jwt).getClaim("name").isNull());
- }
-
- @Test
- public void shouldCreatePayloadWithNullForList() {
- String jwt = JWTCreator.init()
- .withClaim("name", (List>) null)
- .sign(Algorithm.HMAC256("secret"));
- assertThat(jwt, is(notNullValue()));
- assertTrue(JWT.decode(jwt).getClaim("name").isNull());
- }
-
- @Test
- public void shouldPreserveInsertionOrder() throws Exception {
- String taxonomyJson = "{\"class\": \"mammalia\", \"order\": \"carnivora\", \"family\": \"canidae\", \"genus\": \"vulpes\"}";
- List taxonomyClaims = Arrays.asList("class", "order", "family", "genus");
- List headerInsertionOrder = new ArrayList<>(taxonomyClaims);
- Map header = new LinkedHashMap<>();
- for (int i = 0; i < 10; i++) {
- String key = "h" + i;
- header.put(key, "v" + 1);
- headerInsertionOrder.add(key);
- }
-
- List payloadInsertionOrder = new ArrayList<>(taxonomyClaims);
- JWTCreator.Builder builder = JWTCreator.init()
- .withHeader(taxonomyJson)
- .withHeader(header)
- .withPayload(taxonomyJson);
- for (int i = 0; i < 10; i++) {
- String name = "c" + i;
- builder = builder.withClaim(name, "v" + i);
- payloadInsertionOrder.add(name);
- }
- String signed = builder.sign(Algorithm.HMAC256("secret"));
-
- assertThat(signed, is(notNullValue()));
- String[] parts = signed.split("\\.");
- Base64.Decoder urlDecoder = Base64.getUrlDecoder();
- String headerJson = new String(urlDecoder.decode(parts[0]), StandardCharsets.UTF_8);
- String payloadJson = new String(urlDecoder.decode(parts[1]), StandardCharsets.UTF_8);
-
- ObjectMapper objectMapper = new ObjectMapper();
-
- List headerFields = new ArrayList<>();
- objectMapper.readValue(headerJson, ObjectNode.class)
- .fieldNames().forEachRemaining(headerFields::add);
- headerFields.retainAll(headerInsertionOrder);
- assertThat("Header insertion order should be preserved",
- headerFields, is(equalTo(headerInsertionOrder)));
-
- List payloadFields = new ArrayList<>();
- objectMapper.readValue(payloadJson, ObjectNode.class)
- .fieldNames().forEachRemaining(payloadFields::add);
- payloadFields.retainAll(payloadInsertionOrder);
- assertThat("Claim insertion order should be preserved",
- payloadFields, is(equalTo(payloadInsertionOrder)));
- }
-}
diff --git a/lib/src/test/java/com/auth0/jwt/JWTDecoderTest.java b/lib/src/test/java/com/auth0/jwt/JWTDecoderTest.java
deleted file mode 100644
index cc427d60..00000000
--- a/lib/src/test/java/com/auth0/jwt/JWTDecoderTest.java
+++ /dev/null
@@ -1,416 +0,0 @@
-package com.auth0.jwt;
-
-import com.auth0.jwt.exceptions.JWTDecodeException;
-import com.auth0.jwt.interfaces.Claim;
-import com.auth0.jwt.interfaces.DecodedJWT;
-import org.hamcrest.collection.IsCollectionWithSize;
-import org.hamcrest.core.IsIterableContaining;
-import org.junit.Rule;
-import org.junit.Test;
-import org.junit.rules.ExpectedException;
-
-import java.io.*;
-import java.nio.charset.StandardCharsets;
-import java.time.Instant;
-import java.util.Base64;
-import java.util.Date;
-import java.util.List;
-import java.util.Map;
-
-import static org.hamcrest.MatcherAssert.assertThat;
-import static org.hamcrest.Matchers.*;
-
-public class JWTDecoderTest {
- @Rule
- public ExpectedException exception = ExpectedException.none();
-
- @Test
- public void getSubject() {
- DecodedJWT jwt = JWT.decode("eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiYWRtaW4iOnRydWV9.TJVA95OrM7E2cBab30RMHrHDcEfxjoYZgeFONFh7HgQ");
- assertThat(jwt.getSubject(), is(notNullValue()));
- assertThat(jwt.getSubject(), is("1234567890"));
- }
-
- // Exceptions
- @Test
- public void shouldThrowIfTheContentIsNotProperlyEncoded() {
- exception.expect(JWTDecodeException.class);
- exception.expectMessage(startsWith("The string '"));
- exception.expectMessage(endsWith("' doesn't have a valid JSON format."));
- JWT.decode("eyJ0eXAiOiJKV1QiLCJhbGciO-corrupted.eyJ0ZXN0IjoxMjN9.sLtFC2rLAzN0-UJ13OLQX6ezNptAQzespaOGwCnpqk");
- }
-
- @Test
- public void shouldThrowIfLessThan3Parts() {
- exception.expect(JWTDecodeException.class);
- exception.expectMessage("The token was expected to have 3 parts, but got 2.");
- JWT.decode("two.parts");
- }
-
- @Test
- public void shouldThrowIfMoreThan3Parts() {
- exception.expect(JWTDecodeException.class);
- exception.expectMessage("The token was expected to have 3 parts, but got > 3.");
- JWT.decode("this.has.four.parts");
- }
-
- @Test
- public void shouldThrowIfPayloadHasInvalidJSONFormat() {
- String validJson = "{}";
- String invalidJson = "}{";
- exception.expect(JWTDecodeException.class);
- exception.expectMessage(String.format("The string '%s' doesn't have a valid JSON format.", invalidJson));
- customJWT(validJson, invalidJson, "signature");
- }
-
- @Test
- public void shouldThrowIfHeaderHasInvalidJSONFormat() {
- String validJson = "{}";
- String invalidJson = "}{";
- exception.expect(JWTDecodeException.class);
- exception.expectMessage(String.format("The string '%s' doesn't have a valid JSON format.", invalidJson));
- customJWT(invalidJson, validJson, "signature");
- }
-
- @Test
- public void shouldThrowWhenHeaderNotValidBase64() {
- exception.expect(JWTDecodeException.class);
- exception.expectCause(isA(IllegalArgumentException.class));
-
- String jwt = "eyJhbGciOiJub25l+IiwiY3R5IjoiSldUIn0.eyJpc3MiOiJhdXRoMCJ9.Ox-WRXRaGAuWt2KfPvWiGcCrPqZtbp_4OnQzZXaTfss";
- JWT.decode(jwt);
- }
-
- @Test
- public void shouldThrowWhenPayloadNotValidBase64() {
- exception.expect(JWTDecodeException.class);
- exception.expectCause(isA(IllegalArgumentException.class));
-
- String jwt = "eyJhbGciOiJub25lIiwiY3R5IjoiSldUIn0.eyJpc3MiOiJhdXRo+MCJ9.Ox-WRXRaGAuWt2KfPvWiGcCrPqZtbp_4OnQzZXaTfss";
- JWT.decode(jwt);
- }
-
- // Parts
-
- @Test
- public void shouldGetStringToken() {
- DecodedJWT jwt = JWT.decode("eyJhbGciOiJIUzI1NiJ9.e30.XmNK3GpH3Ys_7wsYBfq4C3M6goz71I7dTgUkuIa5lyQ");
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getToken(), is(notNullValue()));
- assertThat(jwt.getToken(), is("eyJhbGciOiJIUzI1NiJ9.e30.XmNK3GpH3Ys_7wsYBfq4C3M6goz71I7dTgUkuIa5lyQ"));
- }
-
- @Test
- public void shouldGetHeader() {
- DecodedJWT jwt = JWT.decode("eyJhbGciOiJIUzI1NiJ9.e30.XmNK3GpH3Ys_7wsYBfq4C3M6goz71I7dTgUkuIa5lyQ");
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getHeader(), is("eyJhbGciOiJIUzI1NiJ9"));
- }
-
- @Test
- public void shouldGetPayload() {
- DecodedJWT jwt = JWT.decode("eyJhbGciOiJIUzI1NiJ9.e30.XmNK3GpH3Ys_7wsYBfq4C3M6goz71I7dTgUkuIa5lyQ");
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getPayload(), is("e30"));
- }
-
- @Test
- public void shouldGetSignature() {
- DecodedJWT jwt = JWT.decode("eyJhbGciOiJIUzI1NiJ9.e30.XmNK3GpH3Ys_7wsYBfq4C3M6goz71I7dTgUkuIa5lyQ");
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getSignature(), is("XmNK3GpH3Ys_7wsYBfq4C3M6goz71I7dTgUkuIa5lyQ"));
- }
-
- // Standard Claims
-
- @Test
- public void shouldGetIssuer() {
- DecodedJWT jwt = JWT.decode("eyJhbGciOiJIUzI1NiJ9.eyJpc3MiOiJKb2huIERvZSJ9.SgXosfRR_IwCgHq5lF3tlM-JHtpucWCRSaVuoHTbWbQ");
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getIssuer(), is("John Doe"));
- }
-
- @Test
- public void shouldGetSubject() {
- DecodedJWT jwt = JWT.decode("eyJhbGciOiJIUzI1NiJ9.eyJzdWIiOiJUb2szbnMifQ.RudAxkslimoOY3BLl2Ghny3BrUKu9I1ZrXzCZGDJtNs");
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getSubject(), is("Tok3ns"));
- }
-
- @Test
- public void shouldGetArrayAudience() {
- DecodedJWT jwt = JWT.decode("eyJhbGciOiJIUzI1NiJ9.eyJhdWQiOlsiSG9wZSIsIlRyYXZpcyIsIlNvbG9tb24iXX0.Tm4W8WnfPjlmHSmKFakdij0on2rWPETpoM7Sh0u6-S4");
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getAudience(), is(IsCollectionWithSize.hasSize(3)));
- assertThat(jwt.getAudience(), is(IsIterableContaining.hasItems("Hope", "Travis", "Solomon")));
- }
-
- @Test
- public void shouldGetStringAudience() {
- DecodedJWT jwt = JWT.decode("eyJhbGciOiJIUzI1NiJ9.eyJhdWQiOiJKYWNrIFJleWVzIn0.a4I9BBhPt1OB1GW67g2P1bEHgi6zgOjGUL4LvhE9Dgc");
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getAudience(), is(IsCollectionWithSize.hasSize(1)));
- assertThat(jwt.getAudience(), is(IsIterableContaining.hasItems("Jack Reyes")));
- }
-
- @Test
- public void shouldGetExpirationTime() {
- DecodedJWT jwt = JWT.decode("eyJhbGciOiJIUzI1NiJ9.eyJleHAiOjE0NzY3MjcwODZ9.L9dcPHEDQew2u9MkDCORFkfDGcSOsgoPqNY-LUMLEHg");
- assertThat(jwt, is(notNullValue()));
- long ms = 1476727086L * 1000;
- assertThat(jwt.getExpiresAt(), is(equalTo(new Date(ms))));
- assertThat(jwt.getExpiresAtAsInstant(), is(equalTo(Instant.ofEpochMilli(ms))));
- }
-
- @Test
- public void shouldGetNotBefore() {
- DecodedJWT jwt = JWT.decode("eyJhbGciOiJIUzI1NiJ9.eyJuYmYiOjE0NzY3MjcwODZ9.tkpD3iCPQPVqjnjpDVp2bJMBAgpVCG9ZjlBuMitass0");
- assertThat(jwt, is(notNullValue()));
- long ms = 1476727086L * 1000;
- assertThat(jwt.getNotBefore(), is(equalTo(new Date(ms))));
- assertThat(jwt.getNotBeforeAsInstant(), is(equalTo(Instant.ofEpochMilli(ms))));
- }
-
- @Test
- public void shouldGetIssuedAt() {
- DecodedJWT jwt = JWT.decode("eyJhbGciOiJIUzI1NiJ9.eyJpYXQiOjE0NzY3MjcwODZ9.KPjGoW665E8V5_27Jugab8qSTxLk2cgquhPCBfAP0_w");
- assertThat(jwt, is(notNullValue()));
- long ms = 1476727086L * 1000;
- assertThat(jwt.getIssuedAt(), is(equalTo(new Date(ms))));
- assertThat(jwt.getIssuedAtAsInstant(), is(equalTo(Instant.ofEpochMilli(ms))));
- }
-
- @Test
- public void shouldGetId() {
- DecodedJWT jwt = JWT.decode("eyJhbGciOiJIUzI1NiJ9.eyJqdGkiOiIxMjM0NTY3ODkwIn0.m3zgEfVUFOd-CvL3xG5BuOWLzb0zMQZCqiVNQQOPOvA");
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getId(), is("1234567890"));
- }
-
- @Test
- public void shouldGetContentType() {
- DecodedJWT jwt = JWT.decode("eyJhbGciOiJIUzI1NiIsImN0eSI6ImF3ZXNvbWUifQ.e30.AIm-pJDOaAyct9qKMlN-lQieqNDqc3d4erqUZc5SHAs");
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getContentType(), is("awesome"));
- }
-
- @Test
- public void shouldGetType() {
- DecodedJWT jwt = JWT.decode("eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXUyJ9.e30.WdFmrzx8b9v_a-r6EHC2PTAaWywgm_8LiP8RBRhYwkI");
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getType(), is("JWS"));
- }
-
- @Test
- public void shouldGetAlgorithm() {
- DecodedJWT jwt = JWT.decode("eyJhbGciOiJIUzI1NiJ9.e30.XmNK3GpH3Ys_7wsYBfq4C3M6goz71I7dTgUkuIa5lyQ");
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getAlgorithm(), is("HS256"));
- }
-
- // Private Claims
-
- @Test
- public void shouldGetMissingClaimIfClaimDoesNotExist() {
- DecodedJWT jwt = JWT.decode("eyJhbGciOiJIUzI1NiJ9.e30.K17vlwhE8FCMShdl1_65jEYqsQqBOVMPUU9IgG-QlTM");
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getClaim("notExisting"), is(notNullValue()));
- assertThat(jwt.getClaim("notExisting").isMissing(), is(true));
- assertThat(jwt.getClaim("notExisting").isNull(), is(false));
- }
-
- @Test
- public void shouldGetValidClaim() {
- DecodedJWT jwt = JWT.decode("eyJhbGciOiJIUzI1NiJ9.eyJvYmplY3QiOnsibmFtZSI6ImpvaG4ifX0.lrU1gZlOdlmTTeZwq0VI-pZx2iV46UWYd5-lCjy6-c4");
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getClaim("object"), is(notNullValue()));
- assertThat(jwt.getClaim("object"), is(instanceOf(Claim.class)));
- }
-
- @Test
- public void shouldNotGetNullClaimIfClaimIsEmptyObject() {
- DecodedJWT jwt = JWT.decode("eyJhbGciOiJIUzI1NiJ9.eyJvYmplY3QiOnt9fQ.d3nUeeL_69QsrHL0ZWij612LHEQxD8EZg1rNoY3a4aI");
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getClaim("object"), is(notNullValue()));
- assertThat(jwt.getClaim("object").isNull(), is(false));
- }
-
- @Test
- public void shouldGetCustomClaimOfTypeInteger() {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJuYW1lIjoxMjN9.XZAudnA7h3_Al5kJydzLjw6RzZC3Q6OvnLEYlhNW7HA";
- DecodedJWT jwt = JWT.decode(token);
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getClaim("name").asInt(), is(123));
- }
-
- @Test
- public void shouldGetCustomClaimOfTypeDouble() {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJuYW1lIjoyMy40NX0.7pyX2OmEGaU9q15T8bGFqRm-d3RVTYnqmZNZtxMKSlA";
- DecodedJWT jwt = JWT.decode(token);
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getClaim("name").asDouble(), is(23.45));
- }
-
- @Test
- public void shouldGetCustomClaimOfTypeBoolean() {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJuYW1lIjp0cnVlfQ.FwQ8VfsZNRqBa9PXMinSIQplfLU4-rkCLfIlTLg_MV0";
- DecodedJWT jwt = JWT.decode(token);
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getClaim("name").asBoolean(), is(true));
- }
-
- @Test
- public void shouldGetCustomClaimOfTypeDate() {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJuYW1lIjoxNDc4ODkxNTIxfQ.mhioumeok8fghQEhTKF3QtQAksSvZ_9wIhJmgZLhJ6c";
- Date date = new Date(1478891521000L);
- DecodedJWT jwt = JWT.decode(token);
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getClaim("name").asDate().getTime(), is(date.getTime()));
- }
-
- @Test
- public void shouldGetCustomClaimOfTypeInstant() {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJuYW1lIjoxNDc4ODkxNTIxfQ.mhioumeok8fghQEhTKF3QtQAksSvZ_9wIhJmgZLhJ6c";
- Instant instant = Instant.ofEpochSecond(1478891521L);
- DecodedJWT jwt = JWT.decode(token);
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getClaim("name").asInstant(), is(equalTo(instant)));
- }
-
- @Test
- public void shouldGetCustomArrayClaimOfTypeString() {
- String token = "eyJhbGciOiJIUzI1NiJ9.eyJuYW1lIjpbInRleHQiLCIxMjMiLCJ0cnVlIl19.lxM8EcmK1uSZRAPd0HUhXGZJdauRmZmLjoeqz4J9yAA";
- DecodedJWT jwt = JWT.decode(token);
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getClaim("name").asArray(String.class), arrayContaining("text", "123", "true"));
- }
-
- @Test
- public void shouldGetCustomArrayClaimOfTypeInteger() {
- String token = "eyJhbGciOiJIUzI1NiJ9.eyJuYW1lIjpbMSwyLDNdfQ.UEuMKRQYrzKAiPpPLhIVawWkKWA1zj0_GderrWUIyFE";
- DecodedJWT jwt = JWT.decode(token);
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getClaim("name").asArray(Integer.class), arrayContaining(1, 2, 3));
- }
-
- @Test
- public void shouldGetCustomMapClaim() {
- String token = "eyJhbGciOiJIUzI1NiJ9.eyJuYW1lIjp7InN0cmluZyI6InZhbHVlIiwibnVtYmVyIjoxLCJib29sZWFuIjp0cnVlLCJlbXB0eSI6bnVsbH19.6xkCuYZnu4RA0xZSxlYSYAqzy9JDWsDtIWqSCUZlPt8";
- DecodedJWT jwt = JWT.decode(token);
- assertThat(jwt, is(notNullValue()));
- Map map = jwt.getClaim("name").asMap();
- assertThat(map, hasEntry("string", "value"));
- assertThat(map, hasEntry("number", 1));
- assertThat(map, hasEntry("boolean", true));
- assertThat(map, hasEntry("empty", null));
- }
-
- @Test
- public void shouldGetCustomNullClaim() {
- String token = "eyJhbGciOiJIUzI1NiJ9.eyJuYW1lIjpudWxsfQ.X4ALHe7uYqEcXWFBnwBUNRKwmwrtDEGZ2aynRYYUx8c";
- DecodedJWT jwt = JWT.decode(token);
- assertThat(jwt.getClaim("name").isNull(), is(true));
- }
-
- @Test
- public void shouldGetListClaim() {
- String token = "eyJhbGciOiJIUzI1NiJ9.eyJuYW1lIjpbbnVsbCwiaGVsbG8iXX0.SpcuQRBGdTV0ofHdxBSnhWEUsQi89noZUXin2Thwb70";
- DecodedJWT jwt = JWT.decode(token);
- assertThat(jwt.getClaim("name").asList(String.class), contains(null, "hello"));
- }
-
- @Test
- public void shouldGetAvailableClaims() {
- DecodedJWT jwt = JWT.decode("eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJleHAiOjEyMzQ1Njc4OTAsImlhdCI6MTIzNDU2Nzg5MCwibmJmIjoxMjM0NTY3ODkwLCJqdGkiOiJodHRwczovL2p3dC5pby8iLCJhdWQiOiJodHRwczovL2RvbWFpbi5hdXRoMC5jb20iLCJzdWIiOiJsb2dpbiIsImlzcyI6ImF1dGgwIiwiZXh0cmFDbGFpbSI6IkpvaG4gRG9lIn0.2_0nxDPJwOk64U5V5V9pt8U92jTPJbGsHYQ35HYhbdE");
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getClaims(), is(notNullValue()));
- assertThat(jwt.getClaims(), is(instanceOf(Map.class)));
- assertThat(jwt.getClaims().get("exp"), is(notNullValue()));
- assertThat(jwt.getClaims().get("iat"), is(notNullValue()));
- assertThat(jwt.getClaims().get("nbf"), is(notNullValue()));
- assertThat(jwt.getClaims().get("jti"), is(notNullValue()));
- assertThat(jwt.getClaims().get("aud"), is(notNullValue()));
- assertThat(jwt.getClaims().get("sub"), is(notNullValue()));
- assertThat(jwt.getClaims().get("iss"), is(notNullValue()));
- assertThat(jwt.getClaims().get("extraClaim"), is(notNullValue()));
- }
-
- @Test
- public void shouldSerializeAndDeserialize() throws Exception {
- DecodedJWT originalJwt = JWT.decode("eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJleHAiOjEyMzQ1Njc4OTAsImlhdCI6MTIzNDU2Nzg5MCwibmJmIjoxMjM0NTY3ODkwLCJqdGkiOiJodHRwczovL2p3dC5pby8iLCJhdWQiOiJodHRwczovL2RvbWFpbi5hdXRoMC5jb20iLCJzdWIiOiJsb2dpbiIsImlzcyI6ImF1dGgwIiwiZXh0cmFDbGFpbSI6IkpvaG4gRG9lIn0.2_0nxDPJwOk64U5V5V9pt8U92jTPJbGsHYQ35HYhbdE");
-
- assertThat(originalJwt, is(instanceOf(Serializable.class)));
-
- byte[] serialized = serialize(originalJwt);
- DecodedJWT deserializedJwt = (DecodedJWT) deserialize(serialized);
-
- assertThat(originalJwt.getHeader(), is(equalTo(deserializedJwt.getHeader())));
- assertThat(originalJwt.getPayload(), is(equalTo(deserializedJwt.getPayload())));
- assertThat(originalJwt.getSignature(), is(equalTo(deserializedJwt.getSignature())));
- assertThat(originalJwt.getToken(), is(equalTo(deserializedJwt.getToken())));
- assertThat(originalJwt.getAlgorithm(), is(equalTo(deserializedJwt.getAlgorithm())));
- assertThat(originalJwt.getAudience(), is(equalTo(deserializedJwt.getAudience())));
- assertThat(originalJwt.getContentType(), is(equalTo(deserializedJwt.getContentType())));
- assertThat(originalJwt.getExpiresAt(), is(equalTo(deserializedJwt.getExpiresAt())));
- assertThat(originalJwt.getId(), is(equalTo(deserializedJwt.getId())));
- assertThat(originalJwt.getIssuedAt(), is(equalTo(deserializedJwt.getIssuedAt())));
- assertThat(originalJwt.getIssuer(), is(equalTo(deserializedJwt.getIssuer())));
- assertThat(originalJwt.getKeyId(), is(equalTo(deserializedJwt.getKeyId())));
- assertThat(originalJwt.getNotBefore(), is(equalTo(deserializedJwt.getNotBefore())));
- assertThat(originalJwt.getSubject(), is(equalTo(deserializedJwt.getSubject())));
- assertThat(originalJwt.getType(), is(equalTo(deserializedJwt.getType())));
- assertThat(originalJwt.getClaims().get("extraClaim").asString(),
- is(equalTo(deserializedJwt.getClaims().get("extraClaim").asString())));
- }
-
- @Test
- public void shouldDecodeHeaderClaims() {
- String jwt = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCIsImRhdGUiOjE2NDczNTgzMjUsInN0cmluZyI6InN0cmluZyIsImJvb2wiOnRydWUsImRvdWJsZSI6MTIzLjEyMywibGlzdCI6WzE2NDczNTgzMjVdLCJtYXAiOnsiZGF0ZSI6MTY0NzM1ODMyNSwiaW5zdGFudCI6MTY0NzM1ODMyNX0sImludCI6NDIsImxvbmciOjQyMDAwMDAwMDAsImluc3RhbnQiOjE2NDczNTgzMjV9.eyJpYXQiOjE2NDczNjA4ODF9.S2nZDM03ZDvLMeJLWOIqWZ9kmYHZUueyQiIZCCjYNL8";
-
- Instant expectedInstant = Instant.ofEpochSecond(1647358325);
- Date expectedDate = Date.from(expectedInstant);
-
- DecodedJWT decoded = JWT.decode(jwt);
- assertThat(decoded, is(notNullValue()));
- assertThat(decoded.getHeaderClaim("date").asDate(), is(expectedDate));
- assertThat(decoded.getHeaderClaim("instant").asInstant(), is(expectedInstant));
- assertThat(decoded.getHeaderClaim("string").asString(), is("string"));
- assertThat(decoded.getHeaderClaim("bool").asBoolean(), is(true));
- assertThat(decoded.getHeaderClaim("double").asDouble(), is(123.123));
- assertThat(decoded.getHeaderClaim("int").asInt(), is(42));
- assertThat(decoded.getHeaderClaim("long").asLong(), is(4200000000L));
-
- Map headerMap = decoded.getHeaderClaim("map").asMap();
- assertThat(headerMap, is(notNullValue()));
- assertThat(headerMap.size(), is(2));
- assertThat(headerMap, hasEntry("date", 1647358325));
- assertThat(headerMap, hasEntry("instant", 1647358325));
-
- List headerList = decoded.getHeaderClaim("list").asList(Object.class);
- assertThat(headerList, is(notNullValue()));
- assertThat(headerList.size(), is(1));
- assertThat(headerList, contains(1647358325));
- }
-
- //Helper Methods
-
- private DecodedJWT customJWT(String jsonHeader, String jsonPayload, String signature) {
- String header = Base64.getUrlEncoder().withoutPadding().encodeToString(jsonHeader.getBytes(StandardCharsets.UTF_8));
- String body = Base64.getUrlEncoder().withoutPadding().encodeToString(jsonPayload.getBytes(StandardCharsets.UTF_8));
- return JWT.decode(String.format("%s.%s.%s", header, body, signature));
- }
-
- private static byte[] serialize(Object obj) throws IOException {
- ByteArrayOutputStream b = new ByteArrayOutputStream();
- ObjectOutputStream o = new ObjectOutputStream(b);
- o.writeObject(obj);
- return b.toByteArray();
- }
-
- private static Object deserialize(byte[] bytes) throws IOException, ClassNotFoundException {
- ByteArrayInputStream b = new ByteArrayInputStream(bytes);
- ObjectInputStream o = new ObjectInputStream(b);
- return o.readObject();
- }
-
-}
\ No newline at end of file
diff --git a/lib/src/test/java/com/auth0/jwt/JWTTest.java b/lib/src/test/java/com/auth0/jwt/JWTTest.java
deleted file mode 100644
index 087f1e9e..00000000
--- a/lib/src/test/java/com/auth0/jwt/JWTTest.java
+++ /dev/null
@@ -1,524 +0,0 @@
-package com.auth0.jwt;
-
-import com.auth0.jwt.algorithms.Algorithm;
-import com.auth0.jwt.interfaces.DecodedJWT;
-import org.hamcrest.collection.IsCollectionWithSize;
-import org.hamcrest.core.IsIterableContaining;
-import org.junit.Rule;
-import org.junit.Test;
-import org.junit.rules.ExpectedException;
-
-import java.nio.charset.StandardCharsets;
-import java.security.interfaces.ECKey;
-import java.security.interfaces.RSAKey;
-import java.time.Clock;
-import java.time.Duration;
-import java.time.Instant;
-import java.time.ZoneId;
-import java.util.Base64;
-import java.util.Date;
-
-import static org.hamcrest.MatcherAssert.assertThat;
-import static org.hamcrest.Matchers.*;
-
-public class JWTTest {
-
- private static final String PUBLIC_KEY_FILE_RSA = "src/test/resources/rsa-public.pem";
- private static final String PRIVATE_KEY_FILE_RSA = "src/test/resources/rsa-private.pem";
-
- private static final String PUBLIC_KEY_FILE_EC_256 = "src/test/resources/ec256-key-public.pem";
- private static final String PUBLIC_KEY_FILE_EC_384 = "src/test/resources/ec384-key-public.pem";
- private static final String PUBLIC_KEY_FILE_EC_512 = "src/test/resources/ec512-key-public.pem";
- private static final String PRIVATE_KEY_FILE_EC_256 = "src/test/resources/ec256-key-private.pem";
- private static final String PRIVATE_KEY_FILE_EC_384 = "src/test/resources/ec384-key-private.pem";
- private static final String PRIVATE_KEY_FILE_EC_512 = "src/test/resources/ec512-key-private.pem";
-
- @Rule
- public ExpectedException exception = ExpectedException.none();
-
- // Decode
-
- @Test
- public void shouldDecodeAStringToken() {
- String token = "eyJhbGciOiJIUzI1NiIsImN0eSI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.mZ0m_N1J4PgeqWmi903JuUoDRZDBPB7HwkS4nVyWH1M";
- DecodedJWT jwt = JWT.decode(token);
-
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldDecodeAStringTokenUsingInstance() {
- String token = "eyJhbGciOiJIUzI1NiIsImN0eSI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.mZ0m_N1J4PgeqWmi903JuUoDRZDBPB7HwkS4nVyWH1M";
- JWT jwt = new JWT();
- DecodedJWT decodedJWT = jwt.decodeJwt(token);
-
- assertThat(decodedJWT, is(notNullValue()));
- }
-
- // getToken
- @Test
- public void shouldGetStringToken() {
- DecodedJWT jwt = JWT.decode("eyJhbGciOiJIUzI1NiJ9.e30.XmNK3GpH3Ys_7wsYBfq4C3M6goz71I7dTgUkuIa5lyQ");
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getToken(), is(notNullValue()));
- assertThat(jwt.getToken(), is("eyJhbGciOiJIUzI1NiJ9.e30.XmNK3GpH3Ys_7wsYBfq4C3M6goz71I7dTgUkuIa5lyQ"));
- }
-
- // getToken
- @Test
- public void shouldGetStringTokenUsingInstance() {
- JWT jwt = new JWT();
- DecodedJWT decodedJWT = jwt.decodeJwt("eyJhbGciOiJIUzI1NiJ9.e30.XmNK3GpH3Ys_7wsYBfq4C3M6goz71I7dTgUkuIa5lyQ");
- assertThat(decodedJWT, is(notNullValue()));
- assertThat(decodedJWT.getToken(), is(notNullValue()));
- assertThat(decodedJWT.getToken(), is("eyJhbGciOiJIUzI1NiJ9.e30.XmNK3GpH3Ys_7wsYBfq4C3M6goz71I7dTgUkuIa5lyQ"));
- }
-
- // Verify
-
- @Test
- public void shouldVerifyDecodedToken() throws Exception {
- String token = "eyJhbGciOiJSUzUxMiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.mvL5LoMyIrWYjk5umEXZTmbyIrkbbcVPUkvdGZbu0qFBxGOf0nXP5PZBvPcOu084lvpwVox5n3VaD4iqzW-PsJyvKFgi5TnwmsbKchAp7JexQEsQOnTSGcfRqeUUiBZqRQdYsho71oAB3T4FnalDdFEpM-fztcZY9XqKyayqZLreTeBjqJm4jfOWH7KfGBHgZExQhe96NLq1UA9eUyQwdOA1Z0SgXe4Ja5PxZ6Fm37KnVDtDlNnY4JAAGFo6y74aGNnp_BKgpaVJCGFu1f1S5xCQ1HSvs8ZSdVWs5NgawW3wRd0kRt_GJ_Y3mIwiF4qUyHWGtsSHu_qjVdCTtbFyow";
- DecodedJWT decodedJWT = JWT.decode(token);
- RSAKey key = (RSAKey) PemUtils.readPublicKeyFromFile(PUBLIC_KEY_FILE_RSA, "RSA");
- DecodedJWT jwt = JWT.require(Algorithm.RSA512(key))
- .build()
- .verify(decodedJWT);
-
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldAcceptNoneAlgorithm() {
- String token = "eyJhbGciOiJub25lIiwidHlwIjoiSldUIn0.eyJpc3MiOiJhdXRoMCJ9.";
- DecodedJWT jwt = JWT.require(Algorithm.none())
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldAcceptHMAC256Algorithm() {
- String token = "eyJhbGciOiJIUzI1NiIsImN0eSI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.mZ0m_N1J4PgeqWmi903JuUoDRZDBPB7HwkS4nVyWH1M";
- DecodedJWT jwt = JWT.require(Algorithm.HMAC256("secret"))
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldAcceptHMAC384Algorithm() {
- String token = "eyJhbGciOiJIUzM4NCIsImN0eSI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.uztpK_wUMYJhrRv8SV-1LU4aPnwl-EM1q-wJnqgyb5DHoDteP6lN_gE1xnZJH5vw";
- DecodedJWT jwt = JWT.require(Algorithm.HMAC384("secret"))
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldAcceptHMAC512Algorithm() {
- String token = "eyJhbGciOiJIUzUxMiIsImN0eSI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.VUo2Z9SWDV-XcOc_Hr6Lff3vl7L9e5Vb8ThXpmGDFjHxe3Dr1ZBmUChYF-xVA7cAdX1P_D4ZCUcsv3IefpVaJw";
- DecodedJWT jwt = JWT.require(Algorithm.HMAC512("secret"))
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- }
-
-
- @Test
- public void shouldAcceptRSA256Algorithm() throws Exception {
- String token = "eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.dxXF3MdsyW-AuvwJpaQtrZ33fAde9xWxpLIg9cO2tMLH2GSRNuLAe61KsJusZhqZB9Iy7DvflcmRz-9OZndm6cj_ThGeJH2LLc90K83UEvvRPo8l85RrQb8PcanxCgIs2RcZOLygERizB3pr5icGkzR7R2y6zgNCjKJ5_NJ6EiZsGN6_nc2PRK_DbyY-Wn0QDxIxKoA5YgQJ9qafe7IN980pXvQv2Z62c3XR8dYuaXBqhthBj-AbaFHEpZapN-V-TmuLNzR2MCB6Xr7BYMuCaqWf_XU8og4XNe8f_8w9Wv5vvgqMM1KhqVpG5VdMJv4o_L4NoCROHhtUQSLRh2M9cA";
- RSAKey key = (RSAKey) PemUtils.readPublicKeyFromFile(PUBLIC_KEY_FILE_RSA, "RSA");
- DecodedJWT jwt = JWT.require(Algorithm.RSA256(key))
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- }
-
-
- @Test
- public void shouldAcceptRSA384Algorithm() throws Exception {
- String token = "eyJhbGciOiJSUzM4NCIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.TZlWjXObwGSQOiu2oMq8kiKz0_BR7bbBddNL6G8eZ_GoR82BXOZDqNrQr7lb_M-78XGBguWLWNIdYhzgxOUL9EoCJlrqVm9s9vo6G8T1sj1op-4TbjXZ61TwIvrJee9BvPLdKUJ9_fp1Js5kl6yXkst40Th8Auc5as4n49MLkipjpEhKDKaENKHpSubs1ripSz8SCQZSofeTM_EWVwSw7cpiM8Fy8jOPvWG8Xz4-e3ODFowvHVsDcONX_4FTMNbeRqDuHq2ZhCJnEfzcSJdrve_5VD5fM1LperBVslTrOxIgClOJ3RmM7-WnaizJrWP3D6Z9OLxPxLhM6-jx6tcxEw";
- RSAKey key = (RSAKey) PemUtils.readPublicKeyFromFile(PUBLIC_KEY_FILE_RSA, "RSA");
- DecodedJWT jwt = JWT.require(Algorithm.RSA384(key))
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldAcceptRSA512Algorithm() throws Exception {
- String token = "eyJhbGciOiJSUzUxMiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.mvL5LoMyIrWYjk5umEXZTmbyIrkbbcVPUkvdGZbu0qFBxGOf0nXP5PZBvPcOu084lvpwVox5n3VaD4iqzW-PsJyvKFgi5TnwmsbKchAp7JexQEsQOnTSGcfRqeUUiBZqRQdYsho71oAB3T4FnalDdFEpM-fztcZY9XqKyayqZLreTeBjqJm4jfOWH7KfGBHgZExQhe96NLq1UA9eUyQwdOA1Z0SgXe4Ja5PxZ6Fm37KnVDtDlNnY4JAAGFo6y74aGNnp_BKgpaVJCGFu1f1S5xCQ1HSvs8ZSdVWs5NgawW3wRd0kRt_GJ_Y3mIwiF4qUyHWGtsSHu_qjVdCTtbFyow";
- RSAKey key = (RSAKey) PemUtils.readPublicKeyFromFile(PUBLIC_KEY_FILE_RSA, "RSA");
- DecodedJWT jwt = JWT.require(Algorithm.RSA512(key))
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- }
-
-
- @Test
- public void shouldAcceptECDSA256Algorithm() throws Exception {
- String token = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9.4iVk3-Y0v4RT4_9IaQlp-8dZ_4fsTzIylgrPTDLrEvTHBTyVS3tgPbr2_IZfLETtiKRqCg0aQ5sh9eIsTTwB1g";
- ECKey key = (ECKey) PemUtils.readPublicKeyFromFile(PUBLIC_KEY_FILE_EC_256, "EC");
- DecodedJWT jwt = JWT.require(Algorithm.ECDSA256(key))
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldAcceptECDSA384Algorithm() throws Exception {
- String token = "eyJhbGciOiJFUzM4NCJ9.eyJpc3MiOiJhdXRoMCJ9.50UU5VKNdF1wfykY8jQBKpvuHZoe6IZBJm5NvoB8bR-hnRg6ti-CHbmvoRtlLfnHfwITa_8cJMy6TenMC2g63GQHytc8rYoXqbwtS4R0Ko_AXbLFUmfxnGnMC6v4MS_z";
- ECKey key = (ECKey) PemUtils.readPublicKeyFromFile(PUBLIC_KEY_FILE_EC_384, "EC");
- DecodedJWT jwt = JWT.require(Algorithm.ECDSA384(key))
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldAcceptECDSA512Algorithm() throws Exception {
- String token = "eyJhbGciOiJFUzUxMiJ9.eyJpc3MiOiJhdXRoMCJ9.AeCJPDIsSHhwRSGZCY6rspi8zekOw0K9qYMNridP1Fu9uhrA1QrG-EUxXlE06yvmh2R7Rz0aE7kxBwrnq8L8aOBCAYAsqhzPeUvyp8fXjjgs0Eto5I0mndE2QHlgcMSFASyjHbU8wD2Rq7ZNzGQ5b2MZfpv030WGUajT-aZYWFUJHVg2";
- ECKey key = (ECKey) PemUtils.readPublicKeyFromFile(PUBLIC_KEY_FILE_EC_512, "EC");
- DecodedJWT jwt = JWT.require(Algorithm.ECDSA512(key))
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- }
-
-
- // Standard Claims
-
- @Test
- public void shouldGetAlgorithm() {
- String token = "eyJhbGciOiJIUzI1NiJ9.e30.XmNK3GpH3Ys_7wsYBfq4C3M6goz71I7dTgUkuIa5lyQ";
- DecodedJWT jwt = JWT.require(Algorithm.HMAC256("secret"))
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getAlgorithm(), is("HS256"));
- }
-
- @Test
- public void shouldGetSignature() {
- String token = "eyJhbGciOiJIUzI1NiJ9.e30.XmNK3GpH3Ys_7wsYBfq4C3M6goz71I7dTgUkuIa5lyQ";
- DecodedJWT jwt = JWT.require(Algorithm.HMAC256("secret"))
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getSignature(), is("XmNK3GpH3Ys_7wsYBfq4C3M6goz71I7dTgUkuIa5lyQ"));
- }
-
- @Test
- public void shouldGetIssuer() {
- String token = "eyJhbGciOiJIUzI1NiJ9.eyJpc3MiOiJKb2huIERvZSJ9.SgXosfRR_IwCgHq5lF3tlM-JHtpucWCRSaVuoHTbWbQ";
- DecodedJWT jwt = JWT.require(Algorithm.HMAC256("secret"))
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getIssuer(), is("John Doe"));
- }
-
- @Test
- public void shouldGetSubject() {
- String token = "eyJhbGciOiJIUzI1NiJ9.eyJzdWIiOiJUb2szbnMifQ.RudAxkslimoOY3BLl2Ghny3BrUKu9I1ZrXzCZGDJtNs";
- DecodedJWT jwt = JWT.require(Algorithm.HMAC256("secret"))
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getSubject(), is("Tok3ns"));
- }
-
- @Test
- public void shouldGetArrayAudience() {
- String token = "eyJhbGciOiJIUzI1NiJ9.eyJhdWQiOlsiSG9wZSIsIlRyYXZpcyIsIlNvbG9tb24iXX0.Tm4W8WnfPjlmHSmKFakdij0on2rWPETpoM7Sh0u6-S4";
- DecodedJWT jwt = JWT.require(Algorithm.HMAC256("secret"))
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getAudience(), is(IsCollectionWithSize.hasSize(3)));
- assertThat(jwt.getAudience(), is(IsIterableContaining.hasItems("Hope", "Travis", "Solomon")));
- }
-
- @Test
- public void shouldGetStringAudience() {
- String token = "eyJhbGciOiJIUzI1NiJ9.eyJhdWQiOiJKYWNrIFJleWVzIn0.a4I9BBhPt1OB1GW67g2P1bEHgi6zgOjGUL4LvhE9Dgc";
- DecodedJWT jwt = JWT.require(Algorithm.HMAC256("secret"))
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getAudience(), is(IsCollectionWithSize.hasSize(1)));
- assertThat(jwt.getAudience(), is(IsIterableContaining.hasItems("Jack Reyes")));
- }
-
- @Test
- public void shouldGetExpirationTime() {
- long seconds = 1477592L;
- Clock mockNow = Clock.fixed(Instant.ofEpochSecond(seconds - 1), ZoneId.of("UTC"));
-
- String token = "eyJhbGciOiJIUzI1NiJ9.eyJleHAiOjE0Nzc1OTJ9.x_ZjkPkKYUV5tdvc0l8go6D_z2kez1MQcOxokXrDc3k";
- JWTVerifier.BaseVerification verification = (JWTVerifier.BaseVerification) JWT.require(Algorithm.HMAC256("secret"));
- DecodedJWT jwt = verification
- .build(mockNow)
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getExpiresAt(), is(equalTo(new Date(seconds * 1000))));
- assertThat(jwt.getExpiresAtAsInstant(), is(equalTo(Instant.ofEpochSecond(seconds))));
-
- }
-
- @Test
- public void shouldGetNotBefore() {
- long seconds = 1477592;
- Clock clock = Clock.fixed(Instant.ofEpochSecond(seconds), ZoneId.of("UTC"));
-
- String token = "eyJhbGciOiJIUzI1NiJ9.eyJuYmYiOjE0Nzc1OTJ9.mWYSOPoNXstjKbZkKrqgkwPOQWEx3F3gMm6PMcfuJd8";
- JWTVerifier.BaseVerification verification = (JWTVerifier.BaseVerification) JWT.require(Algorithm.HMAC256("secret"));
- DecodedJWT jwt = verification
- .build(clock)
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getNotBefore(), is(equalTo(new Date(seconds * 1000))));
- assertThat(jwt.getNotBeforeAsInstant(), is(equalTo(Instant.ofEpochSecond(seconds))));
- }
-
- @Test
- public void shouldGetIssuedAt() {
- long seconds = 1477592;
- Clock clock = Clock.fixed(Instant.ofEpochSecond(seconds), ZoneId.of("UTC"));
-
- String token = "eyJhbGciOiJIUzI1NiJ9.eyJpYXQiOjE0Nzc1OTJ9.5o1CKlLFjKKcddZzoarQ37pq7qZqNPav3sdZ_bsZaD4";
- JWTVerifier.BaseVerification verification = (JWTVerifier.BaseVerification) JWT.require(Algorithm.HMAC256("secret"));
- DecodedJWT jwt = verification
- .build(clock)
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getIssuedAt(), is(equalTo(new Date(seconds * 1000))));
- assertThat(jwt.getIssuedAtAsInstant(), is(equalTo(Instant.ofEpochSecond(seconds))));
- }
-
- @Test
- public void shouldGetId() {
- String token = "eyJhbGciOiJIUzI1NiJ9.eyJqdGkiOiIxMjM0NTY3ODkwIn0.m3zgEfVUFOd-CvL3xG5BuOWLzb0zMQZCqiVNQQOPOvA";
- JWTVerifier.BaseVerification verification = (JWTVerifier.BaseVerification) JWT.require(Algorithm.HMAC256("secret"));
- DecodedJWT jwt = verification
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getId(), is("1234567890"));
- }
-
- @Test
- public void shouldGetContentType() {
- String token = "eyJhbGciOiJIUzI1NiIsImN0eSI6ImF3ZXNvbWUifQ.e30.AIm-pJDOaAyct9qKMlN-lQieqNDqc3d4erqUZc5SHAs";
- DecodedJWT jwt = JWT.require(Algorithm.HMAC256("secret"))
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getContentType(), is("awesome"));
- }
-
- @Test
- public void shouldGetType() {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXUyJ9.e30.WdFmrzx8b9v_a-r6EHC2PTAaWywgm_8LiP8RBRhYwkI";
- DecodedJWT jwt = JWT.require(Algorithm.HMAC256("secret"))
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getType(), is("JWS"));
- }
-
- @Test
- public void shouldGetKeyId() {
- String token = "eyJhbGciOiJIUzI1NiIsImtpZCI6ImtleSJ9.e30.von1Vt9tq9cn5ZYdX1f4cf2EE7fUvb5BCBlKOTm9YWs";
- DecodedJWT jwt = JWT.require(Algorithm.HMAC256("secret"))
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getKeyId(), is("key"));
- }
-
- @Test
- public void shouldGetCustomClaims() {
- String token = "eyJhbGciOiJIUzI1NiIsImlzQWRtaW4iOnRydWV9.eyJpc0FkbWluIjoibm9wZSJ9.YDKBAgUDbh0PkhioDcLNzdQ8c2Gdf_yS6zdEtJQS3F0";
- DecodedJWT jwt = JWT.require(Algorithm.HMAC256("secret"))
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- assertThat(jwt.getHeaderClaim("isAdmin"), notNullValue());
- assertThat(jwt.getHeaderClaim("isAdmin").asBoolean(), is(true));
- assertThat(jwt.getClaim("isAdmin"), notNullValue());
- assertThat(jwt.getClaim("isAdmin").asString(), is("nope"));
- }
-
- // Sign
-
- @Test
- public void shouldCreateAnEmptyHMAC256SignedToken() {
- String signed = JWT.create().sign(Algorithm.HMAC256("secret"));
- assertThat(signed, is(notNullValue()));
-
- String[] parts = signed.split("\\.");
- String headerJson = new String(Base64.getUrlDecoder().decode(parts[0]), StandardCharsets.UTF_8);
- assertThat(headerJson, JsonMatcher.hasEntry("alg", "HS256"));
- assertThat(headerJson, JsonMatcher.hasEntry("typ", "JWT"));
- assertThat(parts[1], is("e30"));
-
- JWTVerifier verified = JWT.require(Algorithm.HMAC256("secret"))
- .build();
- assertThat(verified, is(notNullValue()));
- }
-
- @Test
- public void shouldCreateAnEmptyHMAC384SignedToken() {
- String signed = JWT.create().sign(Algorithm.HMAC384("secret"));
- assertThat(signed, is(notNullValue()));
-
- String[] parts = signed.split("\\.");
- String headerJson = new String(Base64.getUrlDecoder().decode(parts[0]), StandardCharsets.UTF_8);
- assertThat(headerJson, JsonMatcher.hasEntry("alg", "HS384"));
- assertThat(headerJson, JsonMatcher.hasEntry("typ", "JWT"));
- assertThat(parts[1], is("e30"));
-
- JWTVerifier verified = JWT.require(Algorithm.HMAC384("secret"))
- .build();
- assertThat(verified, is(notNullValue()));
- }
-
- @Test
- public void shouldCreateAnEmptyHMAC512SignedToken() {
- String signed = JWT.create().sign(Algorithm.HMAC512("secret"));
- assertThat(signed, is(notNullValue()));
-
- String[] parts = signed.split("\\.");
- String headerJson = new String(Base64.getUrlDecoder().decode(parts[0]), StandardCharsets.UTF_8);
- assertThat(headerJson, JsonMatcher.hasEntry("alg", "HS512"));
- assertThat(headerJson, JsonMatcher.hasEntry("typ", "JWT"));
- assertThat(parts[1], is("e30"));
-
- JWTVerifier verified = JWT.require(Algorithm.HMAC512("secret"))
- .build();
- assertThat(verified, is(notNullValue()));
- }
-
- @Test
- public void shouldCreateAnEmptyRSA256SignedToken() throws Exception {
- String signed = JWT.create().sign(Algorithm.RSA256((RSAKey) PemUtils.readPrivateKeyFromFile(PRIVATE_KEY_FILE_RSA, "RSA")));
- assertThat(signed, is(notNullValue()));
-
- String[] parts = signed.split("\\.");
- String headerJson = new String(Base64.getUrlDecoder().decode(parts[0]), StandardCharsets.UTF_8);
- assertThat(headerJson, JsonMatcher.hasEntry("alg", "RS256"));
- assertThat(headerJson, JsonMatcher.hasEntry("typ", "JWT"));
- assertThat(parts[1], is("e30"));
-
- JWTVerifier verified = JWT.require(Algorithm.RSA256((RSAKey) PemUtils.readPublicKeyFromFile(PUBLIC_KEY_FILE_RSA, "RSA")))
- .build();
- assertThat(verified, is(notNullValue()));
- }
-
- @Test
- public void shouldCreateAnEmptyRSA384SignedToken() throws Exception {
- String signed = JWT.create().sign(Algorithm.RSA384((RSAKey) PemUtils.readPrivateKeyFromFile(PRIVATE_KEY_FILE_RSA, "RSA")));
- assertThat(signed, is(notNullValue()));
-
- String[] parts = signed.split("\\.");
- String headerJson = new String(Base64.getUrlDecoder().decode(parts[0]), StandardCharsets.UTF_8);
- assertThat(headerJson, JsonMatcher.hasEntry("alg", "RS384"));
- assertThat(headerJson, JsonMatcher.hasEntry("typ", "JWT"));
- assertThat(parts[1], is("e30"));
-
- JWTVerifier verified = JWT.require(Algorithm.RSA384((RSAKey) PemUtils.readPublicKeyFromFile(PUBLIC_KEY_FILE_RSA, "RSA")))
- .build();
- assertThat(verified, is(notNullValue()));
- }
-
- @Test
- public void shouldCreateAnEmptyRSA512SignedToken() throws Exception {
- String signed = JWT.create().sign(Algorithm.RSA512((RSAKey) PemUtils.readPrivateKeyFromFile(PRIVATE_KEY_FILE_RSA, "RSA")));
- assertThat(signed, is(notNullValue()));
-
- String[] parts = signed.split("\\.");
- String headerJson = new String(Base64.getUrlDecoder().decode(parts[0]), StandardCharsets.UTF_8);
- assertThat(headerJson, JsonMatcher.hasEntry("alg", "RS512"));
- assertThat(headerJson, JsonMatcher.hasEntry("typ", "JWT"));
- assertThat(parts[1], is("e30"));
-
- JWTVerifier verified = JWT.require(Algorithm.RSA512((RSAKey) PemUtils.readPublicKeyFromFile(PUBLIC_KEY_FILE_RSA, "RSA")))
- .build();
- assertThat(verified, is(notNullValue()));
- }
-
- @Test
- public void shouldCreateAnEmptyECDSA256SignedToken() throws Exception {
- String signed = JWT.create().sign(Algorithm.ECDSA256((ECKey) PemUtils.readPrivateKeyFromFile(PRIVATE_KEY_FILE_EC_256, "EC")));
- assertThat(signed, is(notNullValue()));
-
- String[] parts = signed.split("\\.");
- String headerJson = new String(Base64.getUrlDecoder().decode(parts[0]), StandardCharsets.UTF_8);
- assertThat(headerJson, JsonMatcher.hasEntry("alg", "ES256"));
- assertThat(headerJson, JsonMatcher.hasEntry("typ", "JWT"));
- assertThat(parts[1], is("e30"));
-
- JWTVerifier verified = JWT.require(Algorithm.ECDSA256((ECKey) PemUtils.readPublicKeyFromFile(PUBLIC_KEY_FILE_EC_256, "EC")))
- .build();
- assertThat(verified, is(notNullValue()));
- }
-
- @Test
- public void shouldCreateAnEmptyECDSA384SignedToken() throws Exception {
- String signed = JWT.create().sign(Algorithm.ECDSA384((ECKey) PemUtils.readPrivateKeyFromFile(PRIVATE_KEY_FILE_EC_384, "EC")));
- assertThat(signed, is(notNullValue()));
-
- String[] parts = signed.split("\\.");
- String headerJson = new String(Base64.getUrlDecoder().decode(parts[0]), StandardCharsets.UTF_8);
- assertThat(headerJson, JsonMatcher.hasEntry("alg", "ES384"));
- assertThat(headerJson, JsonMatcher.hasEntry("typ", "JWT"));
- assertThat(parts[1], is("e30"));
-
- JWTVerifier verified = JWT.require(Algorithm.ECDSA384((ECKey) PemUtils.readPublicKeyFromFile(PUBLIC_KEY_FILE_EC_384, "EC")))
- .build();
- assertThat(verified, is(notNullValue()));
- }
-
- @Test
- public void shouldCreateAnEmptyECDSA512SignedToken() throws Exception {
- String signed = JWT.create().sign(Algorithm.ECDSA512((ECKey) PemUtils.readPrivateKeyFromFile(PRIVATE_KEY_FILE_EC_512, "EC")));
- assertThat(signed, is(notNullValue()));
-
- String[] parts = signed.split("\\.");
- String headerJson = new String(Base64.getUrlDecoder().decode(parts[0]), StandardCharsets.UTF_8);
- assertThat(headerJson, JsonMatcher.hasEntry("alg", "ES512"));
- assertThat(headerJson, JsonMatcher.hasEntry("typ", "JWT"));
- assertThat(parts[1], is("e30"));
-
- JWTVerifier verified = JWT.require(Algorithm.ECDSA512((ECKey) PemUtils.readPublicKeyFromFile(PUBLIC_KEY_FILE_EC_512, "EC")))
- .build();
- assertThat(verified, is(notNullValue()));
- }
-}
diff --git a/lib/src/test/java/com/auth0/jwt/JWTVerifierTest.java b/lib/src/test/java/com/auth0/jwt/JWTVerifierTest.java
deleted file mode 100644
index 732d6365..00000000
--- a/lib/src/test/java/com/auth0/jwt/JWTVerifierTest.java
+++ /dev/null
@@ -1,1317 +0,0 @@
-package com.auth0.jwt;
-
-import com.auth0.jwt.algorithms.Algorithm;
-import com.auth0.jwt.exceptions.*;
-import com.auth0.jwt.interfaces.Claim;
-import com.auth0.jwt.interfaces.DecodedJWT;
-import com.auth0.jwt.interfaces.Verification;
-import org.junit.Rule;
-import org.junit.Test;
-import org.junit.rules.ExpectedException;
-
-import java.time.Clock;
-import java.time.Duration;
-import java.time.Instant;
-import java.time.ZoneId;
-import java.util.Collections;
-import java.util.Date;
-import java.util.function.BiPredicate;
-
-import static org.hamcrest.MatcherAssert.assertThat;
-import static org.hamcrest.Matchers.*;
-import static org.junit.Assert.assertThrows;
-import static org.mockito.Mockito.mock;
-
-public class JWTVerifierTest {
-
- private final Clock mockNow = Clock.fixed(Instant.ofEpochSecond(1477592), ZoneId.of("UTC"));
- private final Clock mockOneSecondEarlier = Clock.offset(mockNow, Duration.ofSeconds(-1));
- private final Clock mockOneSecondLater = Clock.offset(mockNow, Duration.ofSeconds(1));
-
- @Rule
- public ExpectedException exception = ExpectedException.none();
-
- @Test
- public void shouldThrowWhenInitializedWithoutAlgorithm() {
- IllegalArgumentException e = assertThrows(null, IllegalArgumentException.class, () ->
- JWTVerifier.init(null));
- assertThat(e.getMessage(), is("The Algorithm cannot be null."));
- }
-
- @Test
- public void shouldThrowWhenAlgorithmDoesntMatchTheTokensAlgorithm() {
- AlgorithmMismatchException e = assertThrows(null, AlgorithmMismatchException.class, () -> {
- JWTVerifier verifier = JWTVerifier.init(Algorithm.HMAC512("secret")).build();
- verifier.verify("eyJhbGciOiJIUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9.s69x7Mmu4JqwmdxiK6sesALO7tcedbFsKEEITUxw9ho");
- });
- assertThat(e.getMessage(), is("The provided Algorithm doesn't match the one defined in the JWT's Header."));
- }
-
- @Test
- public void shouldValidateIssuer() {
- String token = "eyJhbGciOiJIUzI1NiIsImN0eSI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.mZ0m_N1J4PgeqWmi903JuUoDRZDBPB7HwkS4nVyWH1M";
- DecodedJWT jwt = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withIssuer("auth0")
- .build()
- .verify(token);
- assertThat(jwt, is(notNullValue()));
-
- // "iss": ["auth0", "okta"]
- IncorrectClaimException e = assertThrows(null, IncorrectClaimException.class, ()-> {
- String token1 = "eyJhbGciOiJIUzI1NiIsImN0eSI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.mZ0m_N1J4PgeqWmi903JuUoDRZDBPB7HwkS4nVyWH1M";
- JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withIssuer((String[]) null)
- .build()
- .verify(token1);
- });
-
- assertThat(e.getClaimName(), is("iss"));
- }
-
- @Test
- public void shouldValidateMultipleIssuers() {
- String auth0Token = "eyJhbGciOiJIUzI1NiIsImN0eSI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.mZ0m_N1J4PgeqWmi903JuUoDRZDBPB7HwkS4nVyWH1M";
- String otherIssuertoken = "eyJhbGciOiJIUzI1NiIsImN0eSI6IkpXVCJ9.eyJpc3MiOiJvdGhlcklzc3VlciJ9.k4BCOJJl-c0_Y-49VD_mtt-u0QABKSV5i3W-RKc74co";
- JWTVerifier verifier = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withIssuer("otherIssuer", "auth0")
- .build();
-
- assertThat(verifier.verify(auth0Token), is(notNullValue()));
- assertThat(verifier.verify(otherIssuertoken), is(notNullValue()));
- }
-
- @Test
- public void shouldThrowOnInvalidIssuer() {
- IncorrectClaimException e = assertThrows(null, IncorrectClaimException.class, () -> {
- String token = "eyJhbGciOiJIUzI1NiIsImN0eSI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.mZ0m_N1J4PgeqWmi903JuUoDRZDBPB7HwkS4nVyWH1M";
- JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withIssuer("invalid")
- .build()
- .verify(token);
- });
- assertThat(e.getMessage(), is("The Claim 'iss' value doesn't match the required issuer."));
- assertThat(e.getClaimName(), is(RegisteredClaims.ISSUER));
- assertThat(e.getClaimValue().asString(), is("auth0"));
- }
-
- @Test
- public void shouldThrowOnNullIssuer() {
- IncorrectClaimException e = assertThrows(null, IncorrectClaimException.class, () -> {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJpc3MiOm51bGx9.OoiCLipSfflWxkFX2rytvtwEiJ8eAL0opkdXY_ap0qA";
- JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withIssuer("auth0")
- .build()
- .verify(token);
- });
- assertThat(e.getMessage(), is("The Claim 'iss' value doesn't match the required issuer."));
- assertThat(e.getClaimName(), is(RegisteredClaims.ISSUER));
- assertThat(e.getClaimValue().isNull(), is(true));
- }
-
- @Test
- public void shouldThrowOnMissingIssuer() {
- MissingClaimException e = assertThrows(null, MissingClaimException.class, () -> {
- String jwt = JWTCreator.init()
- .sign(Algorithm.HMAC256("secret"));
-
- JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withIssuer("nope")
- .build()
- .verify(jwt);
- });
- assertThat(e.getMessage(), is("The Claim 'iss' is not present in the JWT."));
- assertThat(e.getClaimName(), is("iss"));
- }
-
- @Test
- public void shouldValidateSubject() {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIn0.Rq8IxqeX7eA6GgYxlcHdPFVRNFFZc5rEI3MQTZZbK3I";
- DecodedJWT jwt = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withSubject("1234567890")
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldThrowOnInvalidSubject() {
- IncorrectClaimException e = assertThrows(null, IncorrectClaimException.class, () -> {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIn0.Rq8IxqeX7eA6GgYxlcHdPFVRNFFZc5rEI3MQTZZbK3I";
- JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withSubject("invalid")
- .build()
- .verify(token);
- });
- assertThat(e.getMessage(), is("The Claim 'sub' value doesn't match the required one."));
- assertThat(e.getClaimName(), is(RegisteredClaims.SUBJECT));
- assertThat(e.getClaimValue().asString(), is("1234567890"));
- }
-
- @Test
- public void shouldAcceptAudienceWhenWithAudienceContainsAll() {
- // Token 'aud': ["Mark"]
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJhdWQiOiJNYXJrIn0.xWB6czYI0XObbVhLAxe55TwChWZg7zO08RxONWU2iY4";
- DecodedJWT jwt = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withAudience("Mark")
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
-
- // Token 'aud': ["Mark", "David"]
- String tokenArr = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJhdWQiOlsiTWFyayIsIkRhdmlkIl19.6WfbIt8m61f9WlCYIQn5CThvw4UNyC66qrPaoinfssw";
- DecodedJWT jwtArr = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withAudience("Mark", "David")
- .build()
- .verify(tokenArr);
-
- assertThat(jwtArr, is(notNullValue()));
- }
-
- @Test
- public void shouldAllowWithAnyOfAudienceVerificationToOverrideWithAudience() {
- // Token 'aud' = ["Mark", "David", "John"]
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJhdWQiOlsiTWFyayIsIkRhdmlkIiwiSm9obiJdfQ.DX5xXiCaYvr54x_iL0LZsJhK7O6HhAdHeDYkgDeb0Rw";
- Verification verification = JWTVerifier.init(Algorithm.HMAC256("secret")).withAudience("Mark", "Jim");
-
- Exception exception = null;
- try {
- verification.build().verify(token);
- } catch (Exception e) {
- exception = e;
-
- }
-
- assertThat(exception, is(notNullValue()));
- assertThat(exception, is(instanceOf(IncorrectClaimException.class)));
- assertThat(exception.getMessage(), is("The Claim 'aud' value doesn't contain the required audience."));
-
- DecodedJWT jwt = JWTVerifier.init(Algorithm.HMAC256("secret")).withAnyOfAudience("Mark", "Jim").build().verify(token);
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldAllowWithAudienceVerificationToOverrideWithAnyOfAudience() {
- // Token 'aud' = ["Mark", "David", "John"]
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJhdWQiOlsiTWFyayIsIkRhdmlkIiwiSm9obiJdfQ.DX5xXiCaYvr54x_iL0LZsJhK7O6HhAdHeDYkgDeb0Rw";
- Verification verification = JWTVerifier.init(Algorithm.HMAC256("secret")).withAnyOfAudience("Jim");
-
- Exception exception = null;
- try {
- verification.build().verify(token);
- } catch (Exception e) {
- exception = e;
-
- }
-
- assertThat(exception, is(notNullValue()));
- assertThat(exception, is(instanceOf(IncorrectClaimException.class)));
- assertThat(exception.getMessage(), is("The Claim 'aud' value doesn't contain the required audience."));
-
- DecodedJWT jwt = JWTVerifier.init(Algorithm.HMAC256("secret")).withAudience("Mark").build().verify(token);
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldAcceptAudienceWhenWithAudienceAndPartialExpected() {
- // Token 'aud' = ["Mark", "David", "John"]
- String tokenArr = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJhdWQiOlsiTWFyayIsIkRhdmlkIiwiSm9obiJdfQ.DX5xXiCaYvr54x_iL0LZsJhK7O6HhAdHeDYkgDeb0Rw";
- DecodedJWT jwtArr = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withAudience("John")
- .build()
- .verify(tokenArr);
-
- assertThat(jwtArr, is(notNullValue()));
- }
-
- @Test
- public void shouldAcceptAudienceWhenAnyOfAudienceAndAllContained() {
- // Token 'aud' = ["Mark", "David", "John"]
- String tokenArr = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJhdWQiOlsiTWFyayIsIkRhdmlkIiwiSm9obiJdfQ.DX5xXiCaYvr54x_iL0LZsJhK7O6HhAdHeDYkgDeb0Rw";
- DecodedJWT jwtArr = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withAnyOfAudience("Mark", "David", "John")
- .build()
- .verify(tokenArr);
-
- assertThat(jwtArr, is(notNullValue()));
- }
-
- @Test
- public void shouldThrowWhenAudienceHasNoneOfExpectedAnyOfAudience() {
- IncorrectClaimException e = assertThrows(null, IncorrectClaimException.class, () -> {
- // Token 'aud' = ["Mark", "David", "John"]
- String tokenArr = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJhdWQiOlsiTWFyayIsIkRhdmlkIiwiSm9obiJdfQ.DX5xXiCaYvr54x_iL0LZsJhK7O6HhAdHeDYkgDeb0Rw";
- JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withAnyOfAudience("Joe", "Jim")
- .build()
- .verify(tokenArr);
- });
- assertThat(e.getMessage(), is("The Claim 'aud' value doesn't contain the required audience."));
- assertThat(e.getClaimName(), is(RegisteredClaims.AUDIENCE));
- assertThat(e.getClaimValue().asArray(String.class), is(new String[] {"Mark","David","John"}));
- }
-
- @Test
- public void shouldThrowWhenAudienceClaimDoesNotContainAllExpected() {
- IncorrectClaimException e = assertThrows(null, IncorrectClaimException.class, () -> {
- // Token 'aud' = ["Mark", "David", "John"]
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJhdWQiOlsiTWFyayIsIkRhdmlkIiwiSm9obiJdfQ.DX5xXiCaYvr54x_iL0LZsJhK7O6HhAdHeDYkgDeb0Rw";
- JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withAudience("Mark", "Joe")
- .build()
- .verify(token);
- });
- assertThat(e.getMessage(), is("The Claim 'aud' value doesn't contain the required audience."));
- assertThat(e.getClaimName(), is(RegisteredClaims.AUDIENCE));
- assertThat(e.getClaimValue().asArray(String.class), is(new String[] {"Mark","David","John"}));
- }
-
- @Test
- public void shouldThrowWhenAudienceClaimIsNull() {
- IncorrectClaimException e = assertThrows(null, IncorrectClaimException.class, () -> {
- // Token 'aud': null
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwiYXVkIjpudWxsfQ.bpPyquk3b8KepErKgTidjJ1ZwiOGuoTxam2_x7cElKI";
- JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withAudience("nope")
- .build()
- .verify(token);
- });
- assertThat(e.getMessage(), is("The Claim 'aud' value doesn't contain the required audience."));
- assertThat(e.getClaimName(), is(RegisteredClaims.AUDIENCE));
- assertThat(e.getClaimValue().isNull(), is(true));
- }
-
- @Test
- public void shouldThrowWhenAudienceClaimIsMissing(){
- MissingClaimException e = assertThrows(null, MissingClaimException.class, () -> {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIn0.Rq8IxqeX7eA6GgYxlcHdPFVRNFFZc5rEI3MQTZZbK3I";
- JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withAudience("nope")
- .build()
- .verify(token);
- });
- assertThat(e.getMessage(), is("The Claim 'aud' is not present in the JWT."));
- assertThat(e.getClaimName(), is("aud"));
- }
-
- @Test
- public void shouldThrowWhenAudienceClaimIsNullWithAnAudience() {
- IncorrectClaimException e = assertThrows(null, IncorrectClaimException.class, () -> {
- // Token 'aud': [null]
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwiYXVkIjpbbnVsbF19.2cBf7FbkX52h8Vmjnl1DY1PYe_J_YP0KsyeoeYmuca8";
- JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withAnyOfAudience("nope")
- .build()
- .verify(token);
- });
- assertThat(e.getMessage(), is("The Claim 'aud' value doesn't contain the required audience."));
- assertThat(e.getClaimName(), is(RegisteredClaims.AUDIENCE));
- assertThat(e.getClaimValue().asArray(String.class), is(new String[] {null}));
- }
-
- @Test
- public void shouldThrowWhenExpectedEmptyList() {
- IncorrectClaimException e = assertThrows(null, IncorrectClaimException.class, () -> {
- // Token 'aud': 'wide audience'
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJhdWQiOiJ3aWRlIGF1ZGllbmNlIn0.c9anq03XepcuEKWEVsPk9cck0sIIfrT6hHbBsCar49o";
- JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withAnyOfAudience(new String[0])
- .build()
- .verify(token);
- });
- assertThat(e.getMessage(), is("The Claim 'aud' value doesn't contain the required audience."));
- assertThat(e.getClaimName(), is(RegisteredClaims.AUDIENCE));
- assertThat(e.getClaimValue().asString(), is("wide audience"));
- }
-
- @Test
- public void shouldNotReplaceWhenMultipleChecksAreAdded() {
- JWTVerifier verifier = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withAudience((String[]) null)
- .withAudience()
- .withAnyOfAudience((String[]) null)
- .withAnyOfAudience()
- .build();
-
- assertThat(verifier.expectedChecks.size(), is(7)); //3 extra mandatory checks exp, nbf, iat
- }
-
- @Test
- public void shouldThrowOnNullCustomClaimName() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("The Custom Claim's name can't be null.");
- JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withClaim(null, "value");
- }
-
- @Test
- public void shouldThrowWhenExpectedArrayClaimIsMissing() {
- MissingClaimException e = assertThrows(null, MissingClaimException.class, () -> {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJhcnJheSI6WzEsMiwzXX0.wKNFBcMdwIpdF9rXRxvexrzSM6umgSFqRO1WZj992YM";
- JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withArrayClaim("missing", 1, 2, 3)
- .build()
- .verify(token);
- });
- assertThat(e.getMessage(), is("The Claim 'missing' is not present in the JWT."));
- assertThat(e.getClaimName(), is("missing"));
- }
-
- @Test
- public void shouldThrowWhenExpectedClaimIsMissing() {
- MissingClaimException e = assertThrows(null, MissingClaimException.class, () -> {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJjbGFpbSI6InRleHQifQ.aZ27Ze35VvTqxpaSIK5ZcnYHr4SrvANlUbDR8fw9qsQ";
- JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withClaim("missing", "text")
- .build()
- .verify(token);
- });
- assertThat(e.getMessage(), is("The Claim 'missing' is not present in the JWT."));
- assertThat(e.getClaimName(), is("missing"));
- }
-
- @Test
- public void shouldThrowOnInvalidCustomClaimValueOfTypeString() {
- IncorrectClaimException e = assertThrows(null, IncorrectClaimException.class, () -> {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJuYW1lIjpbInNvbWV0aGluZyJdfQ.3ENLez6tU_fG0SVFrGmISltZPiXLSHaz_dyn-XFTEGQ";
- JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withClaim("name", "value")
- .build()
- .verify(token);
- });
- assertThat(e.getMessage(), is("The Claim 'name' value doesn't match the required one."));
- assertThat(e.getClaimName(), is("name"));
- assertThat(e.getClaimValue().asArray(String.class), is(new String[] {"something"}));
- }
-
- @Test
- public void shouldThrowOnInvalidCustomClaimValueOfTypeInteger() {
- IncorrectClaimException e = assertThrows(null, IncorrectClaimException.class, () -> {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJuYW1lIjpbInNvbWV0aGluZyJdfQ.3ENLez6tU_fG0SVFrGmISltZPiXLSHaz_dyn-XFTEGQ";
- JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withClaim("name", 123)
- .build()
- .verify(token);
- });
- assertThat(e.getMessage(), is("The Claim 'name' value doesn't match the required one."));
- assertThat(e.getClaimName(), is("name"));
- assertThat(e.getClaimValue().asArray(String.class), is(new String[] {"something"}));
- }
-
- @Test
- public void shouldThrowOnInvalidCustomClaimValueOfTypeDouble() {
- IncorrectClaimException e = assertThrows(null, IncorrectClaimException.class, () -> {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJuYW1lIjpbInNvbWV0aGluZyJdfQ.3ENLez6tU_fG0SVFrGmISltZPiXLSHaz_dyn-XFTEGQ";
- JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withClaim("name", 23.45)
- .build()
- .verify(token);
- });
- assertThat(e.getMessage(), is("The Claim 'name' value doesn't match the required one."));
- assertThat(e.getClaimName(), is("name"));
- assertThat(e.getClaimValue().asArray(String.class), is(new String[] {"something"}));
- }
-
- @Test
- public void shouldThrowOnInvalidCustomClaimValueOfTypeBoolean() {
- IncorrectClaimException e = assertThrows(null, IncorrectClaimException.class, () -> {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJuYW1lIjpbInNvbWV0aGluZyJdfQ.3ENLez6tU_fG0SVFrGmISltZPiXLSHaz_dyn-XFTEGQ";
- JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withClaim("name", true)
- .build()
- .verify(token);
- });
- assertThat(e.getMessage(), is("The Claim 'name' value doesn't match the required one."));
- assertThat(e.getClaimName(), is("name"));
- assertThat(e.getClaimValue().asArray(String.class), is(new String[] {"something"}));
- }
-
-
- @Test
- public void shouldThrowOnInvalidCustomClaimValueOfTypeDate() {
- IncorrectClaimException e = assertThrows(null, IncorrectClaimException.class, () -> {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJuYW1lIjpbInNvbWV0aGluZyJdfQ.3ENLez6tU_fG0SVFrGmISltZPiXLSHaz_dyn-XFTEGQ";
- JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withClaim("name", new Date())
- .build()
- .verify(token);
- });
- assertThat(e.getMessage(), is("The Claim 'name' value doesn't match the required one."));
- assertThat(e.getClaimName(), is("name"));
- assertThat(e.getClaimValue().asArray(String.class), is(new String[] {"something"}));
- }
-
- @Test
- public void shouldThrowOnInvalidCustomClaimValue() {
- IncorrectClaimException e = assertThrows(null, IncorrectClaimException.class, () -> {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJuYW1lIjpbInNvbWV0aGluZyJdfQ.3ENLez6tU_fG0SVFrGmISltZPiXLSHaz_dyn-XFTEGQ";
- JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withClaim("name", "check")
- .build()
- .verify(token);
- });
- assertThat(e.getMessage(), is("The Claim 'name' value doesn't match the required one."));
- assertThat(e.getClaimName(), is("name"));
- assertThat(e.getClaimValue().asArray(String.class), is(new String[] {"something"}));
- }
-
- @Test
- public void shouldValidateCustomClaimOfTypeString() {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJuYW1lIjoidmFsdWUifQ.Jki8pvw6KGbxpMinufrgo6RDL1cu7AtNMJYVh6t-_cE";
- DecodedJWT jwt = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withClaim("name", "value")
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldValidateCustomClaimOfTypeInteger() {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJuYW1lIjoxMjN9.XZAudnA7h3_Al5kJydzLjw6RzZC3Q6OvnLEYlhNW7HA";
- DecodedJWT jwt = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withClaim("name", 123)
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldValidateCustomClaimOfTypeLong() {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJuYW1lIjo5MjIzMzcyMDM2ODU0Nzc2MDB9.km-IwQ5IDnTZFmuJzhSgvjTzGkn_Z5X29g4nAuVC56I";
- DecodedJWT jwt = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withClaim("name", 922337203685477600L)
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldValidateCustomClaimOfTypeDouble() {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJuYW1lIjoyMy40NX0.7pyX2OmEGaU9q15T8bGFqRm-d3RVTYnqmZNZtxMKSlA";
- DecodedJWT jwt = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withClaim("name", 23.45)
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldValidateCustomClaimOfTypeBoolean() {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJuYW1lIjp0cnVlfQ.FwQ8VfsZNRqBa9PXMinSIQplfLU4-rkCLfIlTLg_MV0";
- DecodedJWT jwt = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withClaim("name", true)
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldValidateCustomClaimOfTypeDate() {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJuYW1lIjoxNDc4ODkxNTIxfQ.mhioumeok8fghQEhTKF3QtQAksSvZ_9wIhJmgZLhJ6c";
- Date date = new Date(1478891521123L);
- DecodedJWT jwt = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withClaim("name", date)
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldNotRemoveCustomClaimOfTypeDateWhenNull() {
- JWTVerifier verifier = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withClaim("name", new Date())
- .withClaim("name", (Date) null)
- .build();
-
- assertThat(verifier.expectedChecks, is(notNullValue()));
- assertThat(verifier.expectedChecks.size(), is(5));
- }
-
- @Test
- public void shouldValidateCustomArrayClaimOfTypeString() {
- String token = "eyJhbGciOiJIUzI1NiJ9.eyJuYW1lIjpbInRleHQiLCIxMjMiLCJ0cnVlIl19.lxM8EcmK1uSZRAPd0HUhXGZJdauRmZmLjoeqz4J9yAA";
- DecodedJWT jwt = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withArrayClaim("name", "text", "123", "true")
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldValidateCustomArrayClaimOfTypeInteger() {
- String token = "eyJhbGciOiJIUzI1NiJ9.eyJuYW1lIjpbMSwyLDNdfQ.UEuMKRQYrzKAiPpPLhIVawWkKWA1zj0_GderrWUIyFE";
- DecodedJWT jwt = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withArrayClaim("name", 1, 2, 3)
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldValidateCustomArrayClaimOfTypeLong() {
- String token = "eyJhbGciOiJIUzI1NiJ9.eyJuYW1lIjpbNTAwMDAwMDAwMDAxLDUwMDAwMDAwMDAwMiw1MDAwMDAwMDAwMDNdfQ.vzV7S0gbV9ZAVxChuIt4XZuSVTxMH536rFmoHzxmayM";
- DecodedJWT jwt = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withArrayClaim("name", 500000000001L, 500000000002L, 500000000003L)
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldValidateCustomArrayClaimOfTypeLongWhenValueIsInteger() {
- String token = "eyJhbGciOiJIUzI1NiJ9.eyJuYW1lIjpbMSwyLDNdfQ.UEuMKRQYrzKAiPpPLhIVawWkKWA1zj0_GderrWUIyFE";
- DecodedJWT jwt = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withArrayClaim("name", 1L, 2L, 3L)
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldValidateCustomArrayClaimOfTypeLongWhenValueIsIntegerAndLong() {
- String token = "eyJhbGciOiJIUzI1NiJ9.eyJuYW1lIjpbMSw1MDAwMDAwMDAwMDIsNTAwMDAwMDAwMDAzXX0.PQjb2rPPpYjM2sItZEzZcjS2YbfPCp6xksTSPjpjTQA";
- DecodedJWT jwt = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withArrayClaim("name", 1L, 500000000002L, 500000000003L)
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- }
-
- // Generic Delta
- @Test
- public void shouldAddDefaultLeewayToDateClaims() {
- Algorithm algorithm = mock(Algorithm.class);
- JWTVerifier.BaseVerification verification = (JWTVerifier.BaseVerification) JWTVerifier.init(algorithm);
- JWTVerifier verifier = verification
- .build();
-
- assertThat(verifier.expectedChecks, is(notNullValue()));
- assertThat(verification.getLeewayFor(RegisteredClaims.ISSUED_AT), is(0L));
- assertThat(verification.getLeewayFor(RegisteredClaims.EXPIRES_AT), is(0L));
- assertThat(verification.getLeewayFor(RegisteredClaims.NOT_BEFORE), is(0L));
- }
-
- @Test
- public void shouldAddCustomLeewayToDateClaims() {
- Algorithm algorithm = mock(Algorithm.class);
- JWTVerifier.BaseVerification verification = (JWTVerifier.BaseVerification) JWTVerifier.init(algorithm);
- JWTVerifier verifier = verification
- .acceptLeeway(1234L)
- .build();
-
- assertThat(verifier.expectedChecks, is(notNullValue()));
- assertThat(verification.getLeewayFor(RegisteredClaims.ISSUED_AT), is(1234L));
- assertThat(verification.getLeewayFor(RegisteredClaims.EXPIRES_AT), is(1234L));
- assertThat(verification.getLeewayFor(RegisteredClaims.NOT_BEFORE), is(1234L));
- }
-
- @Test
- public void shouldOverrideDefaultIssuedAtLeeway() {
- Algorithm algorithm = mock(Algorithm.class);
- JWTVerifier.BaseVerification verification = (JWTVerifier.BaseVerification) JWTVerifier.init(algorithm);
- JWTVerifier verifier = verification
- .acceptLeeway(1234L)
- .acceptIssuedAt(9999L)
- .build();
-
- assertThat(verifier.expectedChecks, is(notNullValue()));
- assertThat(verification.getLeewayFor(RegisteredClaims.ISSUED_AT), is(9999L));
- assertThat(verification.getLeewayFor(RegisteredClaims.EXPIRES_AT), is(1234L));
- assertThat(verification.getLeewayFor(RegisteredClaims.NOT_BEFORE), is(1234L));
- }
-
- @Test
- public void shouldOverrideDefaultExpiresAtLeeway() {
- Algorithm algorithm = mock(Algorithm.class);
- JWTVerifier.BaseVerification verification = (JWTVerifier.BaseVerification) JWTVerifier.init(algorithm);
- JWTVerifier verifier = verification
- .acceptLeeway(1234L)
- .acceptExpiresAt(9999L)
- .build();
-
- assertThat(verifier.expectedChecks, is(notNullValue()));
- assertThat(verification.getLeewayFor(RegisteredClaims.ISSUED_AT), is(1234L));
- assertThat(verification.getLeewayFor(RegisteredClaims.EXPIRES_AT), is(9999L));
- assertThat(verification.getLeewayFor(RegisteredClaims.NOT_BEFORE), is(1234L));
- }
-
- @Test
- public void shouldOverrideDefaultNotBeforeLeeway() {
- Algorithm algorithm = mock(Algorithm.class);
- JWTVerifier.BaseVerification verification = (JWTVerifier.BaseVerification) JWTVerifier.init(algorithm);
- JWTVerifier verifier = verification
- .acceptLeeway(1234L)
- .acceptNotBefore(9999L)
- .build();
-
- assertThat(verifier.expectedChecks, is(notNullValue()));
- assertThat(verification.getLeewayFor(RegisteredClaims.ISSUED_AT), is(1234L));
- assertThat(verification.getLeewayFor(RegisteredClaims.EXPIRES_AT), is(1234L));
- assertThat(verification.getLeewayFor(RegisteredClaims.NOT_BEFORE), is(9999L));
- }
-
- @Test
- public void shouldThrowOnNegativeCustomLeeway() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("Leeway value can't be negative.");
- Algorithm algorithm = mock(Algorithm.class);
- JWTVerifier.init(algorithm)
- .acceptLeeway(-1);
- }
-
- // Expires At
-
- @Test
- public void shouldValidateExpiresAtWithLeeway() {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJleHAiOjE0Nzc1OTJ9.isvT0Pqx0yjnZk53mUFSeYFJLDs-Ls9IsNAm86gIdZo";
- JWTVerifier.BaseVerification verification = (JWTVerifier.BaseVerification) JWTVerifier.init(Algorithm.HMAC256("secret"))
- .acceptExpiresAt(2);
- DecodedJWT jwt = verification
- .build(mockOneSecondLater)
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldValidateExpiresAtIfPresent() {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJleHAiOjE0Nzc1OTJ9.isvT0Pqx0yjnZk53mUFSeYFJLDs-Ls9IsNAm86gIdZo";
- JWTVerifier.BaseVerification verification = (JWTVerifier.BaseVerification) JWTVerifier.init(Algorithm.HMAC256("secret"));
- DecodedJWT jwt = verification
- .build(mockOneSecondEarlier)
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldThrowWhenExpiresAtIsNow() {
- // exp must be > now
- TokenExpiredException e = assertThrows(null, TokenExpiredException.class, () -> {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJleHAiOjE0Nzc1OTJ9.isvT0Pqx0yjnZk53mUFSeYFJLDs-Ls9IsNAm86gIdZo";
- JWTVerifier.BaseVerification verification = (JWTVerifier.BaseVerification) JWTVerifier.init(Algorithm.HMAC256("secret"));
- verification
- .build(mockNow)
- .verify(token);
- });
- assertThat(e.getMessage(), is("The Token has expired on 1970-01-18T02:26:32Z."));
- assertThat(e.getExpiredOn(), is(Instant.ofEpochSecond(1477592L)));
- }
-
- @Test
- public void shouldThrowOnInvalidExpiresAtIfPresent() {
- TokenExpiredException e = assertThrows(null, TokenExpiredException.class, () -> {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJleHAiOjE0Nzc1OTJ9.isvT0Pqx0yjnZk53mUFSeYFJLDs-Ls9IsNAm86gIdZo";
- JWTVerifier.BaseVerification verification = (JWTVerifier.BaseVerification) JWTVerifier.init(Algorithm.HMAC256("secret"));
- verification
- .build(mockOneSecondLater)
- .verify(token);
- });
- assertThat(e.getMessage(), is("The Token has expired on 1970-01-18T02:26:32Z."));
- assertThat(e.getExpiredOn(), is(Instant.ofEpochSecond(1477592L)));
- }
-
- @Test
- public void shouldThrowOnNegativeExpiresAtLeeway() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("Leeway value can't be negative.");
- Algorithm algorithm = mock(Algorithm.class);
- JWTVerifier.init(algorithm)
- .acceptExpiresAt(-1);
- }
-
- // Not before
- @Test
- public void shouldValidateNotBeforeWithLeeway() {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJuYmYiOjE0Nzc1OTJ9.wq4ZmnSF2VOxcQBxPLfeh1J2Ozy1Tj5iUaERm3FKaw8";
- JWTVerifier.BaseVerification verification = (JWTVerifier.BaseVerification) JWTVerifier.init(Algorithm.HMAC256("secret"))
- .acceptNotBefore(2);
- DecodedJWT jwt = verification
- .build(mockOneSecondEarlier)
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldThrowOnInvalidNotBeforeIfPresent() {
- IncorrectClaimException e = assertThrows(null, IncorrectClaimException.class, () -> {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJuYmYiOjE0Nzc1OTJ9.wq4ZmnSF2VOxcQBxPLfeh1J2Ozy1Tj5iUaERm3FKaw8";
- JWTVerifier.BaseVerification verification = (JWTVerifier.BaseVerification) JWTVerifier.init(Algorithm.HMAC256("secret"));
- verification
- .build(mockOneSecondEarlier)
- .verify(token);
- });
- assertThat(e.getMessage(), is("The Token can't be used before 1970-01-18T02:26:32Z."));
- assertThat(e.getClaimName(), is(RegisteredClaims.NOT_BEFORE));
- assertThat(e.getClaimValue().asLong(), is(1477592L));
- }
-
- @Test
- public void shouldValidateNotBeforeIfPresent() {
- String token = "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJuYmYiOjE0Nzc1OTN9.f4zVV0TbbTG5xxDjSoGZ320JIMchGoQCWrnT5MyQdT0";
- JWTVerifier.BaseVerification verification = (JWTVerifier.BaseVerification) JWTVerifier.init(Algorithm.HMAC256("secret"));
- DecodedJWT jwt = verification
- .build(mockOneSecondLater)
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldAcceptNotBeforeEqualToNow() {
- String token = "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJuYmYiOjE0Nzc1OTJ9.71XBtRmkAa4iKnyhbS4NPW-Xr26eAVAdHZgmupS7a5o";
- JWTVerifier.BaseVerification verification = (JWTVerifier.BaseVerification) JWTVerifier.init(Algorithm.HMAC256("secret"));
- DecodedJWT jwt = verification
- .build(mockNow)
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldThrowOnNegativeNotBeforeLeeway() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("Leeway value can't be negative.");
- Algorithm algorithm = mock(Algorithm.class);
- JWTVerifier.init(algorithm)
- .acceptNotBefore(-1);
- }
-
- // Issued At with future date
- @Test
- public void shouldThrowOnFutureIssuedAt() {
- IncorrectClaimException e = assertThrows(null, IncorrectClaimException.class, () -> {
- String token = "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpYXQiOjE0Nzc1OTJ9.CWq-6pUXl1bFg81vqOUZbZrheO2kUBd2Xr3FUZmvudE";
- JWTVerifier.BaseVerification verification = (JWTVerifier.BaseVerification) JWTVerifier.init(Algorithm.HMAC256("secret"));
-
- DecodedJWT jwt = verification.build(mockOneSecondEarlier).verify(token);
- assertThat(jwt, is(notNullValue()));
- });
- assertThat(e.getMessage(), is("The Token can't be used before 1970-01-18T02:26:32Z."));
- assertThat(e.getClaimName(), is(RegisteredClaims.ISSUED_AT));
- assertThat(e.getClaimValue().asLong(), is(1477592L));
- }
-
- // Issued At with future date and ignore flag
- @Test
- public void shouldSkipIssuedAtVerificationWhenFlagIsPassed() {
- String token = "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpYXQiOjE0Nzc1OTJ9.CWq-6pUXl1bFg81vqOUZbZrheO2kUBd2Xr3FUZmvudE";
- JWTVerifier.BaseVerification verification = (JWTVerifier.BaseVerification) JWTVerifier.init(Algorithm.HMAC256("secret"));
- verification.ignoreIssuedAt();
-
- DecodedJWT jwt = verification.build(mockOneSecondEarlier).verify(token);
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldThrowOnInvalidIssuedAtIfPresent() {
- IncorrectClaimException e = assertThrows(null, IncorrectClaimException.class, () -> {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJpYXQiOjE0Nzc1OTJ9.0WJky9eLN7kuxLyZlmbcXRL3Wy8hLoNCEk5CCl2M4lo";
- JWTVerifier.BaseVerification verification = (JWTVerifier.BaseVerification) JWTVerifier.init(Algorithm.HMAC256("secret"));
- verification
- .build(mockOneSecondEarlier)
- .verify(token);
- });
- assertThat(e.getMessage(), is("The Token can't be used before 1970-01-18T02:26:32Z."));
- assertThat(e.getClaimName(), is(RegisteredClaims.ISSUED_AT));
- assertThat(e.getClaimValue().asLong(), is(1477592L));
- }
-
- @Test
- public void shouldOverrideAcceptIssuedAtWhenIgnoreIssuedAtFlagPassedAndSkipTheVerification() {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJpYXQiOjE0Nzc1OTJ9.0WJky9eLN7kuxLyZlmbcXRL3Wy8hLoNCEk5CCl2M4lo";
- JWTVerifier.BaseVerification verification = (JWTVerifier.BaseVerification) JWTVerifier.init(Algorithm.HMAC256("secret"))
- .acceptIssuedAt(1)
- .ignoreIssuedAt();
- DecodedJWT jwt = verification
- .build(mockOneSecondEarlier)
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldValidateIssuedAtIfPresent() {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJpYXQiOjE0Nzc1OTJ9.0WJky9eLN7kuxLyZlmbcXRL3Wy8hLoNCEk5CCl2M4lo";
- JWTVerifier.BaseVerification verification = (JWTVerifier.BaseVerification) JWTVerifier.init(Algorithm.HMAC256("secret"));
- DecodedJWT jwt = verification
- .build(mockNow)
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldThrowOnNegativeIssuedAtLeeway() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("Leeway value can't be negative.");
- Algorithm algorithm = mock(Algorithm.class);
- JWTVerifier.init(algorithm)
- .acceptIssuedAt(-1);
- }
-
- @Test
- public void shouldValidateJWTId() {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJqdGkiOiJqd3RfaWRfMTIzIn0.0kegfXUvwOYioP8PDaLMY1IlV8HOAzSVz3EGL7-jWF4";
- DecodedJWT jwt = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withJWTId("jwt_id_123")
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldThrowOnInvalidJWTId() {
- IncorrectClaimException e = assertThrows(null, IncorrectClaimException.class, () -> {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJqdGkiOiJqd3RfaWRfMTIzIn0.0kegfXUvwOYioP8PDaLMY1IlV8HOAzSVz3EGL7-jWF4";
- JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withJWTId("invalid")
- .build()
- .verify(token);
- });
- assertThat(e.getMessage(), is("The Claim 'jti' value doesn't match the required one."));
- assertThat(e.getClaimName(), is("jti"));
- assertThat(e.getClaimValue().asString(), is("jwt_id_123"));
- }
-
- @Test
- public void shouldNotRemoveClaimWhenPassingNull() {
- Algorithm algorithm = mock(Algorithm.class);
- JWTVerifier verifier = JWTVerifier.init(algorithm)
- .withIssuer("iss")
- .withIssuer((String) null)
- .build();
-
- assertThat(verifier.expectedChecks, is(notNullValue()));
- assertThat(verifier.expectedChecks.size(), is(5));
-
- verifier = JWTVerifier.init(algorithm)
- .withIssuer("iss")
- .withIssuer((String[]) null)
- .build();
-
- assertThat(verifier.expectedChecks, is(notNullValue()));
- assertThat(verifier.expectedChecks.size(), is(5));
- }
-
- @Test
- public void shouldNotRemoveIssuerWhenPassingNullReference() {
- Algorithm algorithm = mock(Algorithm.class);
- JWTVerifier verifier = JWTVerifier.init(algorithm)
- .withIssuer((String) null)
- .build();
-
- assertThat(verifier.expectedChecks, is(notNullValue()));
- assertThat(verifier.expectedChecks.size(), is(4));
-
- verifier = JWTVerifier.init(algorithm)
- .withIssuer((String[]) null)
- .build();
-
- assertThat(verifier.expectedChecks, is(notNullValue()));
- assertThat(verifier.expectedChecks.size(), is(4));
-
- verifier = JWTVerifier.init(algorithm)
- .withIssuer()
- .build();
-
- assertThat(verifier.expectedChecks, is(notNullValue()));
- assertThat(verifier.expectedChecks.size(), is(4));
-
- String emptyIss = " ";
- verifier = JWTVerifier.init(algorithm)
- .withIssuer(emptyIss)
- .build();
-
- assertThat(verifier.expectedChecks, is(notNullValue()));
- }
-
- @Test
- public void shouldSkipClaimValidationsIfNoClaimsRequired() {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.e30.t-IDcSemACt8x4iTMCda8Yhe3iZaWbvV5XKSTbuAn0M";
- DecodedJWT jwt = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .build()
- .verify(token);
-
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldThrowWhenVerifyingClaimPresenceButClaimNotPresent() {
- MissingClaimException e = assertThrows(null, MissingClaimException.class, () -> {
- String jwt = JWTCreator.init()
- .withClaim("custom", "")
- .sign(Algorithm.HMAC256("secret"));
-
- JWTVerifier verifier = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withClaimPresence("missing")
- .build();
-
- verifier.verify(jwt);
- });
- assertThat(e.getMessage(), is("The Claim 'missing' is not present in the JWT."));
- assertThat(e.getClaimName(), is("missing"));
- }
-
- @Test
- public void shouldThrowWhenVerifyingClaimPresenceWhenClaimNameIsNull() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("The Custom Claim's name can't be null.");
-
- JWTCreator.init()
- .withClaim("custom", "value")
- .sign(Algorithm.HMAC256("secret"));
-
- JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withClaimPresence(null);
- }
-
- @Test
- public void shouldVerifyStringClaimPresence() {
- String jwt = JWTCreator.init()
- .withClaim("custom", "")
- .sign(Algorithm.HMAC256("secret"));
-
- JWTVerifier verifier = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withClaimPresence("custom")
- .build();
-
- DecodedJWT decodedJWT = verifier.verify(jwt);
- assertThat(decodedJWT, is(notNullValue()));
- }
-
- @Test
- public void shouldVerifyBooleanClaimPresence() {
- String jwt = JWTCreator.init()
- .withClaim("custom", true)
- .sign(Algorithm.HMAC256("secret"));
-
- JWTVerifier verifier = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withClaimPresence("custom")
- .build();
-
- DecodedJWT decodedJWT = verifier.verify(jwt);
- assertThat(decodedJWT, is(notNullValue()));
- }
-
- @Test
- public void shouldVerifyIntegerClaimPresence() {
- String jwt = JWTCreator.init()
- .withClaim("custom", 123)
- .sign(Algorithm.HMAC256("secret"));
-
- JWTVerifier verifier = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withClaimPresence("custom")
- .build();
-
- DecodedJWT decodedJWT = verifier.verify(jwt);
- assertThat(decodedJWT, is(notNullValue()));
- }
-
- @Test
- public void shouldVerifyLongClaimPresence() {
- String jwt = JWTCreator.init()
- .withClaim("custom", 922337203685477600L)
- .sign(Algorithm.HMAC256("secret"));
-
- JWTVerifier verifier = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withClaimPresence("custom")
- .build();
-
- DecodedJWT decodedJWT = verifier.verify(jwt);
- assertThat(decodedJWT, is(notNullValue()));
- }
-
- @Test
- public void shouldVerifyDoubleClaimPresence() {
- String jwt = JWTCreator.init()
- .withClaim("custom", 12.34)
- .sign(Algorithm.HMAC256("secret"));
-
- JWTVerifier verifier = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withClaimPresence("custom")
- .build();
-
- DecodedJWT decodedJWT = verifier.verify(jwt);
- assertThat(decodedJWT, is(notNullValue()));
- }
-
- @Test
- public void shouldVerifyListClaimPresence() {
- String jwt = JWTCreator.init()
- .withClaim("custom", Collections.singletonList("item"))
- .sign(Algorithm.HMAC256("secret"));
-
- JWTVerifier verifier = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withClaimPresence("custom")
- .build();
-
- DecodedJWT decodedJWT = verifier.verify(jwt);
- assertThat(decodedJWT, is(notNullValue()));
- }
-
- @Test
- public void shouldVerifyMapClaimPresence() {
- String jwt = JWTCreator.init()
- .withClaim("custom", Collections.singletonMap("key", "value"))
- .sign(Algorithm.HMAC256("secret"));
-
- JWTVerifier verifier = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withClaimPresence("custom")
- .build();
-
- DecodedJWT decodedJWT = verifier.verify(jwt);
- assertThat(decodedJWT, is(notNullValue()));
- }
-
- @Test
- public void shouldVerifyStandardClaimPresence() {
- String jwt = JWTCreator.init()
- .withClaim("aud", "any value")
- .sign(Algorithm.HMAC256("secret"));
-
- JWTVerifier verifier = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withClaimPresence("aud")
- .build();
-
- DecodedJWT decodedJWT = verifier.verify(jwt);
- assertThat(decodedJWT, is(notNullValue()));
- }
-
- @Test
- public void shouldSuccessfullyVerifyClaimWithPredicate() {
- String jwt = JWTCreator.init()
- .withClaim("claimName", "claimValue")
- .sign(Algorithm.HMAC256("secret"));
-
- JWTVerifier verifier = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withClaim("claimName", (claim, decodedJWT) -> "claimValue".equals(claim.asString()))
- .build();
-
- DecodedJWT decodedJWT = verifier.verify(jwt);
- assertThat(decodedJWT, is(notNullValue()));
- }
-
- @Test
- public void shouldThrowWhenPredicateReturnsFalse() {
- IncorrectClaimException e = assertThrows(null, IncorrectClaimException.class, () -> {
- String jwt = JWTCreator.init()
- .withClaim("claimName", "claimValue")
- .sign(Algorithm.HMAC256("secret"));
-
- JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withClaim("claimName", (claim, decodedJWT) -> "nope".equals(claim.asString()))
- .build()
- .verify(jwt);
- });
- assertThat(e.getMessage(), is("The Claim 'claimName' value doesn't match the required one."));
- assertThat(e.getClaimName(), is("claimName"));
- assertThat(e.getClaimValue().asString(), is("claimValue"));
- }
-
- @Test
- public void shouldNotRemovePredicateCheckForNull() {
- JWTVerifier verifier = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withClaim("claimName", (claim, decodedJWT) -> "nope".equals(claim.asString()))
- .withClaim("claimName", (BiPredicate) null)
- .build();
-
- assertThat(verifier.expectedChecks, is(notNullValue()));
- assertThat(verifier.expectedChecks.size(), is(5));
- }
-
- @Test
- public void shouldSuccessfullyVerifyClaimWithNull() {
- String jwt = JWTCreator.init()
- .withNullClaim("claimName")
- .sign(Algorithm.HMAC256("secret"));
-
- JWTVerifier verifier = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withNullClaim("claimName")
- .build();
-
- DecodedJWT decodedJWT = verifier.verify(jwt);
- assertThat(decodedJWT, is(notNullValue()));
- }
-
- @Test
- public void shouldThrowWhenNullClaimHasValue() {
- IncorrectClaimException e = assertThrows(null, IncorrectClaimException.class, () -> {
- String jwt = JWTCreator.init()
- .withClaim("claimName", "value")
- .sign(Algorithm.HMAC256("secret"));
-
- JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withNullClaim("claimName")
- .build()
- .verify(jwt);
- });
- assertThat(e.getMessage(), is("The Claim 'claimName' value doesn't match the required one."));
- assertThat(e.getClaimName(), is("claimName"));
- assertThat(e.getClaimValue().asString(), is("value"));
- }
-
- @Test
- public void shouldThrowWhenNullClaimIsMissing() {
- MissingClaimException e = assertThrows(null, MissingClaimException.class, () -> {
- String jwt = JWTCreator.init()
- .withClaim("claimName", "value")
- .sign(Algorithm.HMAC256("secret"));
-
- JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withNullClaim("anotherClaimName")
- .build()
- .verify(jwt);
- });
- assertThat(e.getMessage(), is("The Claim 'anotherClaimName' is not present in the JWT."));
- assertThat(e.getClaimName(), is("anotherClaimName"));
- }
-
- @Test
- public void shouldCheckForNullValuesForSubject() {
- // sub = null
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOm51bGx9.y5brmQQ05OYwVvlTg83njUrz6tfpdyWNh17LHU6DxmI";
- DecodedJWT jwt = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withSubject(null)
- .build()
- .verify(token);
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldCheckForNullValuesInIssuer() {
- // iss = null
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJpc3MiOm51bGx9.OoiCLipSfflWxkFX2rytvtwEiJ8eAL0opkdXY_ap0qA";
- DecodedJWT jwt = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withIssuer((String) null)
- .withIssuer((String[]) null)
- .withIssuer()
- .build()
- .verify(token);
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldCheckForNullValuesInJwtId() {
- // jti = null
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJqdGkiOm51bGx9.z_MDyl8uPGH0q0jeB54wbYt3bwKXamU_3MO8LofGvZs";
- DecodedJWT jwt = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withJWTId(null)
- .build()
- .verify(token);
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldCheckForNullValuesInCustomClaims() {
- // jti = null
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJjdXN0b20iOm51bGx9.inAuN3Q9UZ6WgbB63O43B1ero2MTqnfzzumr_5qYIls";
- DecodedJWT jwt = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withClaim("custom", (Boolean) null)
- .withClaim("custom", (Integer) null)
- .withClaim("custom", (Long) null)
- .withClaim("custom", (Double) null)
- .withClaim("custom", (String) null)
- .withClaim("custom", (Date) null)
- .withClaim("custom", (Instant) null)
- .withClaim("custom", (BiPredicate) null)
- .withArrayClaim("custom", (String[]) null)
- .withArrayClaim("custom", (Integer[]) null)
- .withArrayClaim("custom", (Long[]) null)
- .build()
- .verify(token);
- assertThat(jwt, is(notNullValue()));
- }
-
-
- @Test
- public void shouldCheckForNullValuesForAudience() {
- // aud = null
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwiYXVkIjpudWxsfQ.bpPyquk3b8KepErKgTidjJ1ZwiOGuoTxam2_x7cElKI";
- DecodedJWT jwt = JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withAudience((String[]) null)
- .withAudience((String) null)
- .withAudience()
- .withAnyOfAudience((String[]) null)
- .withAnyOfAudience((String) null)
- .withAnyOfAudience()
- .build()
- .verify(token);
- assertThat(jwt, is(notNullValue()));
- }
-
- @Test
- public void shouldCheckForClaimPresenceEvenForNormalClaimChecks() {
- MissingClaimException e = assertThrows(null, MissingClaimException.class, () -> {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwiYXVkIjpudWxsfQ.bpPyquk3b8KepErKgTidjJ1ZwiOGuoTxam2_x7cElKI";
- JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withClaim("custom", true)
- .build()
- .verify(token);
- });
- assertThat(e.getClaimName(), is("custom"));
- }
-
- @Test
- public void shouldCheckForWrongLongClaim() {
- IncorrectClaimException e = assertThrows(null, IncorrectClaimException.class, () -> {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJjdXN0b20iOjF9.00btiK0sv8pQ2T-hOr9GC5x2osi7--Bsk4pS5cTikqQ";
- JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withClaim("custom", 2L)
- .build()
- .verify(token);
- });
- assertThat(e.getClaimName(), is("custom"));
- assertThat(e.getClaimValue().asLong(), is(1L));
- }
-
- @Test
- public void shouldCheckForWrongLongArrayClaim() {
- IncorrectClaimException e = assertThrows(null, IncorrectClaimException.class, () -> {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJjdXN0b20iOlsxXX0.R9ZSmgtJng062rcEc59u4VKCq89Yk5VlkN9BuMTMvr0";
- JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withArrayClaim("custom", 2L)
- .build()
- .verify(token);
- });
- assertThat(e.getClaimName(), is("custom"));
- }
-
- @Test
- public void shouldCheckForWrongStringArrayClaim() {
- IncorrectClaimException e = assertThrows(null, IncorrectClaimException.class, () -> {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJjdXN0b20iOlsxXX0.R9ZSmgtJng062rcEc59u4VKCq89Yk5VlkN9BuMTMvr0";
- JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withArrayClaim("custom", "2L")
- .build()
- .verify(token);
- });
- assertThat(e.getClaimName(), is("custom"));
- }
-
- @Test
- public void shouldCheckForWrongIntegerArrayClaim() {
- IncorrectClaimException e = assertThrows(null, IncorrectClaimException.class, () -> {
- String token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJjdXN0b20iOlsxXX0.R9ZSmgtJng062rcEc59u4VKCq89Yk5VlkN9BuMTMvr0";
- JWTVerifier.init(Algorithm.HMAC256("secret"))
- .withArrayClaim("custom", 2)
- .build()
- .verify(token);
- });
- assertThat(e.getClaimName(), is("custom"));
- }
-}
diff --git a/lib/src/test/java/com/auth0/jwt/JsonMatcher.java b/lib/src/test/java/com/auth0/jwt/JsonMatcher.java
deleted file mode 100644
index b09ab187..00000000
--- a/lib/src/test/java/com/auth0/jwt/JsonMatcher.java
+++ /dev/null
@@ -1,140 +0,0 @@
-package com.auth0.jwt;
-
-import org.hamcrest.Description;
-import org.hamcrest.Matcher;
-import org.hamcrest.TypeSafeDiagnosingMatcher;
-
-import java.lang.reflect.Array;
-import java.util.Iterator;
-import java.util.List;
-import java.util.Map;
-
-public class JsonMatcher extends TypeSafeDiagnosingMatcher {
-
- private final String entry;
- private final String key;
- private final Matcher matcher;
-
- private JsonMatcher(String key, Object value, Matcher valueMatcher) {
- this.key = key;
- this.matcher = valueMatcher;
- if (value != null) {
- String stringValue = objectToString(value);
- entry = getStringKey(key) + stringValue;
- } else {
- entry = null;
- }
- }
-
- @Override
- protected boolean matchesSafely(String item, Description mismatchDescription) {
- if (item == null) {
- mismatchDescription.appendText("JSON was null");
- return false;
- }
- if (matcher != null) {
- if (!matcher.matches(item)) {
- matcher.describeMismatch(item, mismatchDescription);
- return false;
- }
- if (!item.contains(getStringKey(key))) {
- mismatchDescription.appendText("JSON didn't contained the key ").appendValue(key);
- return false;
- }
- }
- if (entry != null && !item.contains(entry)) {
- mismatchDescription.appendText("JSON was ").appendValue(item);
- return false;
- }
-
- return true;
- }
-
- @Override
- public void describeTo(Description description) {
- if (matcher == null) {
- description.appendText("A JSON with entry ")
- .appendValue(entry);
- } else {
- matcher.describeTo(description);
- }
- }
-
- public static JsonMatcher hasEntry(String key, Object value) {
- return new JsonMatcher(key, value, null);
- }
-
- public static JsonMatcher hasEntry(String key, Matcher valueMatcher) {
- return new JsonMatcher(key, null, valueMatcher);
- }
-
- public static JsonMatcher isNotPresent(String key) {
- return new JsonMatcher(key, null, null);
- }
-
- private String getStringKey(String key) {
- return "\"" + key + "\":";
- }
-
- private String objectToString(Object value) {
- String stringValue;
- if (value == null) {
- stringValue = "null";
- } else if (value instanceof String) {
- stringValue = "\"" + value + "\"";
- } else if (value instanceof Map) {
- stringValue = mapToString((Map) value);
- } else if (value instanceof Array) {
- stringValue = arrayToString((Object[]) value);
- } else if (value instanceof List) {
- stringValue = listToString((List) value);
- } else {
- stringValue = value.toString();
- }
- return stringValue;
- }
-
- private String arrayToString(Object[] array) {
- StringBuilder sb = new StringBuilder();
- sb.append("[");
- for (int i = 0; i < array.length; i++) {
- Object o = array[i];
- sb.append(objectToString(o));
- if (i + 1 < array.length) {
- sb.append(",");
- }
- }
- sb.append("]");
- return sb.toString();
- }
-
- private String listToString(List list) {
- StringBuilder sb = new StringBuilder();
- sb.append("[");
- Iterator it = list.iterator();
- while (it.hasNext()) {
- Object o = it.next();
- sb.append(objectToString(o));
- if (it.hasNext()) {
- sb.append(",");
- }
- }
- sb.append("]");
- return sb.toString();
- }
-
- private String mapToString(Map map) {
- StringBuilder sb = new StringBuilder();
- sb.append("{");
- Iterator> it = map.entrySet().iterator();
- while (it.hasNext()) {
- Map.Entry e = it.next();
- sb.append("\"" + e.getKey() + "\":" + objectToString(e.getValue()));
- if (it.hasNext()) {
- sb.append(",");
- }
- }
- sb.append("}");
- return sb.toString();
- }
-}
\ No newline at end of file
diff --git a/lib/src/test/java/com/auth0/jwt/PemUtils.java b/lib/src/test/java/com/auth0/jwt/PemUtils.java
deleted file mode 100644
index 6c92e05e..00000000
--- a/lib/src/test/java/com/auth0/jwt/PemUtils.java
+++ /dev/null
@@ -1,72 +0,0 @@
-package com.auth0.jwt;
-
-import org.bouncycastle.util.io.pem.PemObject;
-import org.bouncycastle.util.io.pem.PemReader;
-
-import java.io.File;
-import java.io.FileNotFoundException;
-import java.io.FileReader;
-import java.io.IOException;
-import java.security.KeyFactory;
-import java.security.NoSuchAlgorithmException;
-import java.security.PrivateKey;
-import java.security.PublicKey;
-import java.security.spec.EncodedKeySpec;
-import java.security.spec.InvalidKeySpecException;
-import java.security.spec.PKCS8EncodedKeySpec;
-import java.security.spec.X509EncodedKeySpec;
-
-public class PemUtils {
-
- private static byte[] parsePEMFile(File pemFile) throws IOException {
- if (!pemFile.isFile() || !pemFile.exists()) {
- throw new FileNotFoundException(String.format("The file '%s' doesn't exist.", pemFile.getAbsolutePath()));
- }
- PemReader reader = new PemReader(new FileReader(pemFile));
- PemObject pemObject = reader.readPemObject();
- byte[] content = pemObject.getContent();
- reader.close();
- return content;
- }
-
- private static PublicKey getPublicKey(byte[] keyBytes, String algorithm) {
- PublicKey publicKey = null;
- try {
- KeyFactory kf = KeyFactory.getInstance(algorithm);
- EncodedKeySpec keySpec = new X509EncodedKeySpec(keyBytes);
- publicKey = kf.generatePublic(keySpec);
- } catch (NoSuchAlgorithmException e) {
- System.out.println("Could not reconstruct the public key, the given algorithm could not be found.");
- } catch (InvalidKeySpecException e) {
- System.out.println("Could not reconstruct the public key");
- }
-
- return publicKey;
- }
-
- private static PrivateKey getPrivateKey(byte[] keyBytes, String algorithm) {
- PrivateKey privateKey = null;
- try {
- KeyFactory kf = KeyFactory.getInstance(algorithm);
- EncodedKeySpec keySpec = new PKCS8EncodedKeySpec(keyBytes);
- privateKey = kf.generatePrivate(keySpec);
- } catch (NoSuchAlgorithmException e) {
- System.out.println("Could not reconstruct the private key, the given algorithm could not be found.");
- } catch (InvalidKeySpecException e) {
- System.out.println("Could not reconstruct the private key");
- }
-
- return privateKey;
- }
-
- public static PublicKey readPublicKeyFromFile(String filepath, String algorithm) throws IOException {
- byte[] bytes = PemUtils.parsePEMFile(new File(filepath));
- return PemUtils.getPublicKey(bytes, algorithm);
- }
-
- public static PrivateKey readPrivateKeyFromFile(String filepath, String algorithm) throws IOException {
- byte[] bytes = PemUtils.parsePEMFile(new File(filepath));
- return PemUtils.getPrivateKey(bytes, algorithm);
- }
-
-}
diff --git a/lib/src/test/java/com/auth0/jwt/TokenUtilsTest.java b/lib/src/test/java/com/auth0/jwt/TokenUtilsTest.java
deleted file mode 100644
index 01806ddc..00000000
--- a/lib/src/test/java/com/auth0/jwt/TokenUtilsTest.java
+++ /dev/null
@@ -1,94 +0,0 @@
-package com.auth0.jwt;
-
-import com.auth0.jwt.exceptions.JWTDecodeException;
-import org.junit.Rule;
-import org.junit.Test;
-import org.junit.rules.ExpectedException;
-
-import static org.hamcrest.Matchers.*;
-import static org.hamcrest.MatcherAssert.assertThat;
-
-public class TokenUtilsTest {
-
- @Rule
- public ExpectedException exception = ExpectedException.none();
-
- @Test
- public void toleratesEmptyFirstPart() {
- String token = ".eyJpc3MiOiJhdXRoMCJ9.W1mx_Y0hbAMbPmfW9whT605AAcxB7REFuJiDAHk2Sdc";
- String[] parts = TokenUtils.splitToken(token);
-
- assertThat(parts, is(notNullValue()));
- assertThat(parts, is(arrayWithSize(3)));
- assertThat(parts[0], is(""));
- assertThat(parts[1], is("eyJpc3MiOiJhdXRoMCJ9"));
- assertThat(parts[2], is("W1mx_Y0hbAMbPmfW9whT605AAcxB7REFuJiDAHk2Sdc"));
- }
-
- @Test
- public void toleratesEmptySecondPart() {
- String token = "eyJhbGciOiJub25lIiwidHlwIjoiSldUIn0..W1mx_Y0hbAMbPmfW9whT605AAcxB7REFuJiDAHk2Sdc";
- String[] parts = TokenUtils.splitToken(token);
-
- assertThat(parts, is(notNullValue()));
- assertThat(parts, is(arrayWithSize(3)));
- assertThat(parts[0], is("eyJhbGciOiJub25lIiwidHlwIjoiSldUIn0"));
- assertThat(parts[1], is(""));
- assertThat(parts[2], is("W1mx_Y0hbAMbPmfW9whT605AAcxB7REFuJiDAHk2Sdc"));
- }
-
- @Test
- public void shouldSplitToken() {
- String token = "eyJhbGciOiJub25lIiwidHlwIjoiSldUIn0.eyJpc3MiOiJhdXRoMCJ9.W1mx_Y0hbAMbPmfW9whT605AAcxB7REFuJiDAHk2Sdc";
- String[] parts = TokenUtils.splitToken(token);
-
- assertThat(parts, is(notNullValue()));
- assertThat(parts, is(arrayWithSize(3)));
- assertThat(parts[0], is("eyJhbGciOiJub25lIiwidHlwIjoiSldUIn0"));
- assertThat(parts[1], is("eyJpc3MiOiJhdXRoMCJ9"));
- assertThat(parts[2], is("W1mx_Y0hbAMbPmfW9whT605AAcxB7REFuJiDAHk2Sdc"));
- }
-
- @Test
- public void shouldSplitTokenWithEmptySignature() {
- String token = "eyJhbGciOiJub25lIiwidHlwIjoiSldUIn0.eyJpc3MiOiJhdXRoMCJ9.";
- String[] parts = TokenUtils.splitToken(token);
-
- assertThat(parts, is(notNullValue()));
- assertThat(parts, is(arrayWithSize(3)));
- assertThat(parts[0], is("eyJhbGciOiJub25lIiwidHlwIjoiSldUIn0"));
- assertThat(parts[1], is("eyJpc3MiOiJhdXRoMCJ9"));
- assertThat(parts[2], is(emptyString()));
- }
-
- @Test
- public void shouldThrowOnSplitTokenWithMoreThan3Parts() {
- exception.expect(JWTDecodeException.class);
- exception.expectMessage("The token was expected to have 3 parts, but got > 3.");
- String token = "this.has.four.parts";
- TokenUtils.splitToken(token);
- }
-
- @Test
- public void shouldThrowOnSplitTokenWithNoParts() {
- exception.expect(JWTDecodeException.class);
- exception.expectMessage("The token was expected to have 3 parts, but got 0.");
- String token = "notajwt";
- TokenUtils.splitToken(token);
- }
-
- @Test
- public void shouldThrowOnSplitTokenWith2Parts() {
- exception.expect(JWTDecodeException.class);
- exception.expectMessage("The token was expected to have 3 parts, but got 2.");
- String token = "two.parts";
- TokenUtils.splitToken(token);
- }
-
- @Test
- public void shouldThrowOnSplitTokenWithNullValue() {
- exception.expect(JWTDecodeException.class);
- exception.expectMessage("The token is null.");
- TokenUtils.splitToken(null);
- }
-}
\ No newline at end of file
diff --git a/lib/src/test/java/com/auth0/jwt/UserPojo.java b/lib/src/test/java/com/auth0/jwt/UserPojo.java
deleted file mode 100644
index beb72b50..00000000
--- a/lib/src/test/java/com/auth0/jwt/UserPojo.java
+++ /dev/null
@@ -1,42 +0,0 @@
-package com.auth0.jwt;
-
-public class UserPojo {
- private String name;
- private int id;
-
- @SuppressWarnings("unused")
- public UserPojo() {
- //Required Empty Constructor
- }
-
- public UserPojo(String name, int id) {
- this.name = name;
- this.id = id;
- }
-
- @Override
- public boolean equals(Object o) {
- if (this == o) return true;
- if (o == null || getClass() != o.getClass()) return false;
-
- UserPojo userPojo = (UserPojo) o;
-
- return id == userPojo.id && (name != null ? name.equals(userPojo.name) : userPojo.name == null);
- }
-
- public String getName() {
- return name;
- }
-
- public void setName(String name) {
- this.name = name;
- }
-
- public int getId() {
- return id;
- }
-
- public void setId(int id) {
- this.id = id;
- }
-}
\ No newline at end of file
diff --git a/lib/src/test/java/com/auth0/jwt/algorithms/AlgorithmTest.java b/lib/src/test/java/com/auth0/jwt/algorithms/AlgorithmTest.java
deleted file mode 100644
index e09661d3..00000000
--- a/lib/src/test/java/com/auth0/jwt/algorithms/AlgorithmTest.java
+++ /dev/null
@@ -1,576 +0,0 @@
-package com.auth0.jwt.algorithms;
-
-import com.auth0.jwt.interfaces.ECDSAKeyProvider;
-import com.auth0.jwt.interfaces.RSAKeyProvider;
-import org.junit.Rule;
-import org.junit.Test;
-import org.junit.rules.ExpectedException;
-import org.mockito.ArgumentCaptor;
-
-import java.io.ByteArrayOutputStream;
-import java.nio.charset.StandardCharsets;
-import java.security.interfaces.*;
-
-import static org.hamcrest.Matchers.*;
-import static org.hamcrest.MatcherAssert.assertThat;
-import static org.mockito.Mockito.mock;
-import static org.mockito.Mockito.withSettings;
-import static org.mockito.ArgumentMatchers.any;
-import static org.mockito.Mockito.when;
-
-public class AlgorithmTest {
-
- @Rule
- public ExpectedException exception = ExpectedException.none();
-
-
- @Test
- public void shouldThrowHMAC256InstanceWithNullSecretBytes() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("The Secret cannot be null");
- byte[] secret = null;
- Algorithm.HMAC256(secret);
- }
-
- @Test
- public void shouldThrowHMAC384InstanceWithNullSecretBytes() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("The Secret cannot be null");
- byte[] secret = null;
- Algorithm.HMAC384(secret);
- }
-
- @Test
- public void shouldThrowHMAC512InstanceWithNullSecretBytes() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("The Secret cannot be null");
- byte[] secret = null;
- Algorithm.HMAC512(secret);
- }
-
- @Test
- public void shouldThrowHMAC256InstanceWithNullSecret() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("The Secret cannot be null");
- String secret = null;
- Algorithm.HMAC256(secret);
- }
-
- @Test
- public void shouldThrowHMAC384InstanceWithNullSecret() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("The Secret cannot be null");
- String secret = null;
- Algorithm.HMAC384(secret);
- }
-
- @Test
- public void shouldThrowHMAC512InstanceWithNullSecret() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("The Secret cannot be null");
- String secret = null;
- Algorithm.HMAC512(secret);
- }
-
- @Test
- public void shouldThrowRSA256InstanceWithNullKey() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("Both provided Keys cannot be null.");
- RSAKey key = null;
- Algorithm.RSA256(key);
- }
-
- @Test
- public void shouldThrowRSA256InstanceWithNullKeys() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("Both provided Keys cannot be null.");
- Algorithm.RSA256(null, null);
- }
-
- @Test
- public void shouldThrowRSA256InstanceWithNullKeyProvider() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("The Key Provider cannot be null.");
- RSAKeyProvider provider = null;
- Algorithm.RSA256(provider);
- }
-
- @Test
- public void shouldThrowRSA384InstanceWithNullKey() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("Both provided Keys cannot be null.");
- RSAKey key = null;
- Algorithm.RSA384(key);
- }
-
- @Test
- public void shouldThrowRSA384InstanceWithNullKeys() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("Both provided Keys cannot be null.");
- Algorithm.RSA384(null, null);
- }
-
- @Test
- public void shouldThrowRSA384InstanceWithNullKeyProvider() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("The Key Provider cannot be null.");
- RSAKeyProvider provider = null;
- Algorithm.RSA384(provider);
- }
-
- @Test
- public void shouldThrowRSA512InstanceWithNullKey() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("Both provided Keys cannot be null.");
- RSAKey key = null;
- Algorithm.RSA512(key);
- }
-
- @Test
- public void shouldThrowRSA512InstanceWithNullKeys() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("Both provided Keys cannot be null.");
- Algorithm.RSA512(null, null);
- }
-
- @Test
- public void shouldThrowRSA512InstanceWithNullKeyProvider() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("The Key Provider cannot be null.");
- RSAKeyProvider provider = null;
- Algorithm.RSA512(provider);
- }
-
- @Test
- public void shouldThrowECDSA256InstanceWithNullKey() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("Both provided Keys cannot be null.");
- ECKey key = null;
- Algorithm.ECDSA256(key);
- }
-
- @Test
- public void shouldThrowECDSA256InstanceWithNullKeys() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("Both provided Keys cannot be null.");
- Algorithm.ECDSA256(null, null);
- }
-
- @Test
- public void shouldThrowECDSA256InstanceWithNullKeyProvider() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("The Key Provider cannot be null.");
- ECDSAKeyProvider provider = null;
- Algorithm.ECDSA256(provider);
- }
-
- @Test
- public void shouldThrowECDSA384InstanceWithNullKey() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("Both provided Keys cannot be null.");
- ECKey key = null;
- Algorithm.ECDSA384(key);
- }
-
- @Test
- public void shouldThrowECDSA384InstanceWithNullKeys() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("Both provided Keys cannot be null.");
- Algorithm.ECDSA384(null, null);
- }
-
- @Test
- public void shouldThrowECDSA384InstanceWithNullKeyProvider() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("The Key Provider cannot be null.");
- ECDSAKeyProvider provider = null;
- Algorithm.ECDSA384(provider);
- }
-
- @Test
- public void shouldThrowECDSA512InstanceWithNullKey() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("Both provided Keys cannot be null.");
- ECKey key = null;
- Algorithm.ECDSA512(key);
- }
-
- @Test
- public void shouldThrowECDSA512InstanceWithNullKeys() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("Both provided Keys cannot be null.");
- Algorithm.ECDSA512(null, null);
- }
-
- @Test
- public void shouldThrowECDSA512InstanceWithNullKeyProvider() {
- exception.expect(IllegalArgumentException.class);
- exception.expectMessage("The Key Provider cannot be null.");
- ECDSAKeyProvider provider = null;
- Algorithm.ECDSA512(provider);
- }
-
- @Test
- public void shouldCreateHMAC256AlgorithmWithBytes() {
- Algorithm algorithm = Algorithm.HMAC256("secret".getBytes(StandardCharsets.UTF_8));
-
- assertThat(algorithm, is(notNullValue()));
- assertThat(algorithm, is(instanceOf(HMACAlgorithm.class)));
- assertThat(algorithm.getDescription(), is("HmacSHA256"));
- assertThat(algorithm.getName(), is("HS256"));
- }
-
- @Test
- public void shouldCreateHMAC384AlgorithmWithBytes() {
- Algorithm algorithm = Algorithm.HMAC384("secret".getBytes(StandardCharsets.UTF_8));
-
- assertThat(algorithm, is(notNullValue()));
- assertThat(algorithm, is(instanceOf(HMACAlgorithm.class)));
- assertThat(algorithm.getDescription(), is("HmacSHA384"));
- assertThat(algorithm.getName(), is("HS384"));
- }
-
- @Test
- public void shouldCreateHMAC512AlgorithmWithBytes() {
- Algorithm algorithm = Algorithm.HMAC512("secret".getBytes(StandardCharsets.UTF_8));
-
- assertThat(algorithm, is(notNullValue()));
- assertThat(algorithm, is(instanceOf(HMACAlgorithm.class)));
- assertThat(algorithm.getDescription(), is("HmacSHA512"));
- assertThat(algorithm.getName(), is("HS512"));
- }
-
- @Test
- public void shouldCreateHMAC256AlgorithmWithString() {
- Algorithm algorithm = Algorithm.HMAC256("secret");
-
- assertThat(algorithm, is(notNullValue()));
- assertThat(algorithm, is(instanceOf(HMACAlgorithm.class)));
- assertThat(algorithm.getDescription(), is("HmacSHA256"));
- assertThat(algorithm.getName(), is("HS256"));
- }
-
- @Test
- public void shouldCreateHMAC384AlgorithmWithString() {
- Algorithm algorithm = Algorithm.HMAC384("secret");
-
- assertThat(algorithm, is(notNullValue()));
- assertThat(algorithm, is(instanceOf(HMACAlgorithm.class)));
- assertThat(algorithm.getDescription(), is("HmacSHA384"));
- assertThat(algorithm.getName(), is("HS384"));
- }
-
- @Test
- public void shouldCreateHMAC512AlgorithmWithString() {
- Algorithm algorithm = Algorithm.HMAC512("secret");
-
- assertThat(algorithm, is(notNullValue()));
- assertThat(algorithm, is(instanceOf(HMACAlgorithm.class)));
- assertThat(algorithm.getDescription(), is("HmacSHA512"));
- assertThat(algorithm.getName(), is("HS512"));
- }
-
- @Test
- public void shouldCreateRSA256AlgorithmWithPublicKey() {
- RSAKey key = mock(RSAKey.class, withSettings().extraInterfaces(RSAPublicKey.class));
- Algorithm algorithm = Algorithm.RSA256(key);
-
- assertThat(algorithm, is(notNullValue()));
- assertThat(algorithm, is(instanceOf(RSAAlgorithm.class)));
- assertThat(algorithm.getDescription(), is("SHA256withRSA"));
- assertThat(algorithm.getName(), is("RS256"));
- }
-
- @Test
- public void shouldCreateRSA256AlgorithmWithPrivateKey() {
- RSAKey key = mock(RSAKey.class, withSettings().extraInterfaces(RSAPrivateKey.class));
- Algorithm algorithm = Algorithm.RSA256(key);
-
- assertThat(algorithm, is(notNullValue()));
- assertThat(algorithm, is(instanceOf(RSAAlgorithm.class)));
- assertThat(algorithm.getDescription(), is("SHA256withRSA"));
- assertThat(algorithm.getName(), is("RS256"));
- }
-
- @Test
- public void shouldCreateRSA256AlgorithmWithBothKeys() {
- RSAPublicKey publicKey = mock(RSAPublicKey.class);
- RSAPrivateKey privateKey = mock(RSAPrivateKey.class);
- Algorithm algorithm = Algorithm.RSA256(publicKey, privateKey);
-
- assertThat(algorithm, is(notNullValue()));
- assertThat(algorithm, is(instanceOf(RSAAlgorithm.class)));
- assertThat(algorithm.getDescription(), is("SHA256withRSA"));
- assertThat(algorithm.getName(), is("RS256"));
- }
-
- @Test
- public void shouldCreateRSA256AlgorithmWithProvider() {
- RSAKeyProvider provider = mock(RSAKeyProvider.class);
- Algorithm algorithm = Algorithm.RSA256(provider);
-
- assertThat(algorithm, is(notNullValue()));
- assertThat(algorithm, is(instanceOf(RSAAlgorithm.class)));
- assertThat(algorithm.getDescription(), is("SHA256withRSA"));
- assertThat(algorithm.getName(), is("RS256"));
- }
-
- @Test
- public void shouldCreateRSA384AlgorithmWithPublicKey() {
- RSAKey key = mock(RSAKey.class, withSettings().extraInterfaces(RSAPublicKey.class));
- Algorithm algorithm = Algorithm.RSA384(key);
-
- assertThat(algorithm, is(notNullValue()));
- assertThat(algorithm, is(instanceOf(RSAAlgorithm.class)));
- assertThat(algorithm.getDescription(), is("SHA384withRSA"));
- assertThat(algorithm.getName(), is("RS384"));
- }
-
- @Test
- public void shouldCreateRSA384AlgorithmWithPrivateKey() {
- RSAKey key = mock(RSAKey.class, withSettings().extraInterfaces(RSAPrivateKey.class));
- Algorithm algorithm = Algorithm.RSA384(key);
-
- assertThat(algorithm, is(notNullValue()));
- assertThat(algorithm, is(instanceOf(RSAAlgorithm.class)));
- assertThat(algorithm.getDescription(), is("SHA384withRSA"));
- assertThat(algorithm.getName(), is("RS384"));
- }
-
- @Test
- public void shouldCreateRSA384AlgorithmWithBothKeys() {
- RSAPublicKey publicKey = mock(RSAPublicKey.class);
- RSAPrivateKey privateKey = mock(RSAPrivateKey.class);
- Algorithm algorithm = Algorithm.RSA384(publicKey, privateKey);
-
- assertThat(algorithm, is(notNullValue()));
- assertThat(algorithm, is(instanceOf(RSAAlgorithm.class)));
- assertThat(algorithm.getDescription(), is("SHA384withRSA"));
- assertThat(algorithm.getName(), is("RS384"));
- }
-
- @Test
- public void shouldCreateRSA384AlgorithmWithProvider() {
- RSAKeyProvider provider = mock(RSAKeyProvider.class);
- Algorithm algorithm = Algorithm.RSA384(provider);
-
- assertThat(algorithm, is(notNullValue()));
- assertThat(algorithm, is(instanceOf(RSAAlgorithm.class)));
- assertThat(algorithm.getDescription(), is("SHA384withRSA"));
- assertThat(algorithm.getName(), is("RS384"));
- }
-
- @Test
- public void shouldCreateRSA512AlgorithmWithPublicKey() {
- RSAKey key = mock(RSAKey.class, withSettings().extraInterfaces(RSAPublicKey.class));
- Algorithm algorithm = Algorithm.RSA512(key);
-
- assertThat(algorithm, is(notNullValue()));
- assertThat(algorithm, is(instanceOf(RSAAlgorithm.class)));
- assertThat(algorithm.getDescription(), is("SHA512withRSA"));
- assertThat(algorithm.getName(), is("RS512"));
- }
-
- @Test
- public void shouldCreateRSA512AlgorithmWithPrivateKey() {
- RSAKey key = mock(RSAKey.class, withSettings().extraInterfaces(RSAPrivateKey.class));
- Algorithm algorithm = Algorithm.RSA512(key);
-
- assertThat(algorithm, is(notNullValue()));
- assertThat(algorithm, is(instanceOf(RSAAlgorithm.class)));
- assertThat(algorithm.getDescription(), is("SHA512withRSA"));
- assertThat(algorithm.getName(), is("RS512"));
- }
-
- @Test
- public void shouldCreateRSA512AlgorithmWithBothKeys() {
- RSAPublicKey publicKey = mock(RSAPublicKey.class);
- RSAPrivateKey privateKey = mock(RSAPrivateKey.class);
- Algorithm algorithm = Algorithm.RSA512(publicKey, privateKey);
-
- assertThat(algorithm, is(notNullValue()));
- assertThat(algorithm, is(instanceOf(RSAAlgorithm.class)));
- assertThat(algorithm.getDescription(), is("SHA512withRSA"));
- assertThat(algorithm.getName(), is("RS512"));
- }
-
- @Test
- public void shouldCreateRSA512AlgorithmWithProvider() {
- RSAKeyProvider provider = mock(RSAKeyProvider.class);
- Algorithm algorithm = Algorithm.RSA512(provider);
-
- assertThat(algorithm, is(notNullValue()));
- assertThat(algorithm, is(instanceOf(RSAAlgorithm.class)));
- assertThat(algorithm.getDescription(), is("SHA512withRSA"));
- assertThat(algorithm.getName(), is("RS512"));
- }
-
- @Test
- public void shouldCreateECDSA256AlgorithmWithPublicKey() {
- ECKey key = mock(ECKey.class, withSettings().extraInterfaces(ECPublicKey.class));
- Algorithm algorithm = Algorithm.ECDSA256(key);
-
- assertThat(algorithm, is(notNullValue()));
- assertThat(algorithm, is(instanceOf(ECDSAAlgorithm.class)));
- assertThat(algorithm.getDescription(), is("SHA256withECDSA"));
- assertThat(algorithm.getName(), is("ES256"));
- }
-
- @Test
- public void shouldCreateECDSA256AlgorithmWithPrivateKey() {
- ECKey key = mock(ECKey.class, withSettings().extraInterfaces(ECPrivateKey.class));
- Algorithm algorithm = Algorithm.ECDSA256(key);
-
- assertThat(algorithm, is(notNullValue()));
- assertThat(algorithm, is(instanceOf(ECDSAAlgorithm.class)));
- assertThat(algorithm.getDescription(), is("SHA256withECDSA"));
- assertThat(algorithm.getName(), is("ES256"));
- }
-
- @Test
- public void shouldCreateECDSA256AlgorithmWithBothKeys() {
- ECPublicKey publicKey = mock(ECPublicKey.class);
- ECPrivateKey privateKey = mock(ECPrivateKey.class);
- Algorithm algorithm = Algorithm.ECDSA256(publicKey, privateKey);
-
- assertThat(algorithm, is(notNullValue()));
- assertThat(algorithm, is(instanceOf(ECDSAAlgorithm.class)));
- assertThat(algorithm.getDescription(), is("SHA256withECDSA"));
- assertThat(algorithm.getName(), is("ES256"));
- }
-
- @Test
- public void shouldCreateECDSA256AlgorithmWithProvider() {
- ECDSAKeyProvider provider = mock(ECDSAKeyProvider.class);
- Algorithm algorithm = Algorithm.ECDSA256(provider);
-
- assertThat(algorithm, is(notNullValue()));
- assertThat(algorithm, is(instanceOf(ECDSAAlgorithm.class)));
- assertThat(algorithm.getDescription(), is("SHA256withECDSA"));
- assertThat(algorithm.getName(), is("ES256"));
- }
-
- @Test
- public void shouldCreateECDSA384AlgorithmWithPublicKey() {
- ECKey key = mock(ECKey.class, withSettings().extraInterfaces(ECPublicKey.class));
- Algorithm algorithm = Algorithm.ECDSA384(key);
-
- assertThat(algorithm, is(notNullValue()));
- assertThat(algorithm, is(instanceOf(ECDSAAlgorithm.class)));
- assertThat(algorithm.getDescription(), is("SHA384withECDSA"));
- assertThat(algorithm.getName(), is("ES384"));
- }
-
- @Test
- public void shouldCreateECDSA384AlgorithmWithPrivateKey() {
- ECKey key = mock(ECKey.class, withSettings().extraInterfaces(ECPrivateKey.class));
- Algorithm algorithm = Algorithm.ECDSA384(key);
-
- assertThat(algorithm, is(notNullValue()));
- assertThat(algorithm, is(instanceOf(ECDSAAlgorithm.class)));
- assertThat(algorithm.getDescription(), is("SHA384withECDSA"));
- assertThat(algorithm.getName(), is("ES384"));
- }
-
- @Test
- public void shouldCreateECDSA384AlgorithmWithBothKeys() {
- ECPublicKey publicKey = mock(ECPublicKey.class);
- ECPrivateKey privateKey = mock(ECPrivateKey.class);
- Algorithm algorithm = Algorithm.ECDSA384(publicKey, privateKey);
-
- assertThat(algorithm, is(notNullValue()));
- assertThat(algorithm, is(instanceOf(ECDSAAlgorithm.class)));
- assertThat(algorithm.getDescription(), is("SHA384withECDSA"));
- assertThat(algorithm.getName(), is("ES384"));
- }
-
- @Test
- public void shouldCreateECDSA384AlgorithmWithProvider() {
- ECDSAKeyProvider provider = mock(ECDSAKeyProvider.class);
- Algorithm algorithm = Algorithm.ECDSA384(provider);
-
- assertThat(algorithm, is(notNullValue()));
- assertThat(algorithm, is(instanceOf(ECDSAAlgorithm.class)));
- assertThat(algorithm.getDescription(), is("SHA384withECDSA"));
- assertThat(algorithm.getName(), is("ES384"));
- }
-
- @Test
- public void shouldCreateECDSA512AlgorithmWithPublicKey() {
- ECKey key = mock(ECKey.class, withSettings().extraInterfaces(ECPublicKey.class));
- Algorithm algorithm = Algorithm.ECDSA512(key);
-
- assertThat(algorithm, is(notNullValue()));
- assertThat(algorithm, is(instanceOf(ECDSAAlgorithm.class)));
- assertThat(algorithm.getDescription(), is("SHA512withECDSA"));
- assertThat(algorithm.getName(), is("ES512"));
- }
-
- @Test
- public void shouldCreateECDSA512AlgorithmWithPrivateKey() {
- ECKey key = mock(ECKey.class, withSettings().extraInterfaces(ECPrivateKey.class));
- Algorithm algorithm = Algorithm.ECDSA512(key);
-
- assertThat(algorithm, is(notNullValue()));
- assertThat(algorithm, is(instanceOf(ECDSAAlgorithm.class)));
- assertThat(algorithm.getDescription(), is("SHA512withECDSA"));
- assertThat(algorithm.getName(), is("ES512"));
- }
-
- @Test
- public void shouldCreateECDSA512AlgorithmWithBothKeys() {
- ECPublicKey publicKey = mock(ECPublicKey.class);
- ECPrivateKey privateKey = mock(ECPrivateKey.class);
- Algorithm algorithm = Algorithm.ECDSA512(publicKey, privateKey);
-
- assertThat(algorithm, is(notNullValue()));
- assertThat(algorithm, is(instanceOf(ECDSAAlgorithm.class)));
- assertThat(algorithm.getDescription(), is("SHA512withECDSA"));
- assertThat(algorithm.getName(), is("ES512"));
- }
-
- @Test
- public void shouldCreateECDSA512AlgorithmWithProvider() {
- ECDSAKeyProvider provider = mock(ECDSAKeyProvider.class);
- Algorithm algorithm = Algorithm.ECDSA512(provider);
-
- assertThat(algorithm, is(notNullValue()));
- assertThat(algorithm, is(instanceOf(ECDSAAlgorithm.class)));
- assertThat(algorithm.getDescription(), is("SHA512withECDSA"));
- assertThat(algorithm.getName(), is("ES512"));
- }
-
- @Test
- public void shouldCreateNoneAlgorithm() {
- Algorithm algorithm = Algorithm.none();
-
- assertThat(algorithm, is(notNullValue()));
- assertThat(algorithm, is(instanceOf(NoneAlgorithm.class)));
- assertThat(algorithm.getDescription(), is("none"));
- assertThat(algorithm.getName(), is("none"));
- }
-
- @Test
- public void shouldForwardHeaderPayloadSignatureToSiblingSignMethodForBackwardsCompatibility() throws Exception {
- Algorithm algorithm = mock(Algorithm.class);
-
- ArgumentCaptor contentCaptor = ArgumentCaptor.forClass(byte[].class);
-
- byte[] header = new byte[]{0x00, 0x01, 0x02};
- byte[] payload = new byte[]{0x04, 0x05, 0x06};
-
- byte[] signature = new byte[]{0x10, 0x11, 0x12};
- when(algorithm.sign(any(byte[].class), any(byte[].class))).thenCallRealMethod();
- when(algorithm.sign(contentCaptor.capture())).thenReturn(signature);
-
- byte[] sign = algorithm.sign(header, payload);
-
- ByteArrayOutputStream bout = new ByteArrayOutputStream();
- bout.write(header);
- bout.write('.');
- bout.write(payload);
-
- assertThat(sign, is(signature));
- assertThat(contentCaptor.getValue(), is(bout.toByteArray()));
- }
-}
\ No newline at end of file
diff --git a/lib/src/test/java/com/auth0/jwt/algorithms/CryptoTestHelper.java b/lib/src/test/java/com/auth0/jwt/algorithms/CryptoTestHelper.java
deleted file mode 100644
index ef8e65e8..00000000
--- a/lib/src/test/java/com/auth0/jwt/algorithms/CryptoTestHelper.java
+++ /dev/null
@@ -1,35 +0,0 @@
-package com.auth0.jwt.algorithms;
-
-import java.nio.charset.StandardCharsets;
-import java.util.Base64;
-import java.util.regex.Matcher;
-import java.util.regex.Pattern;
-
-import static org.hamcrest.Matchers.*;
-import static org.hamcrest.MatcherAssert.assertThat;
-import static org.junit.Assert.fail;
-
-public abstract class CryptoTestHelper {
-
- private static final Pattern authHeaderPattern = Pattern.compile("^([\\w-]+)\\.([\\w-]+)\\.([\\w-]+)");
-
- public static String asJWT(Algorithm algorithm, String header, String payload) {
- byte[] signatureBytes = algorithm.sign(header.getBytes(StandardCharsets.UTF_8), payload.getBytes(StandardCharsets.UTF_8));
- String jwtSignature = Base64.getUrlEncoder().withoutPadding().encodeToString(signatureBytes);
- return String.format("%s.%s.%s", header, payload, jwtSignature);
- }
-
- public static void assertSignatureValue(String jwt, String expectedSignature) {
- String jwtSignature = jwt.substring(jwt.lastIndexOf('.') + 1);
- assertThat(jwtSignature, is(expectedSignature));
- }
-
- public static void assertSignaturePresent(String jwt) {
- Matcher matcher = authHeaderPattern.matcher(jwt);
- if (!matcher.find() || matcher.groupCount() < 3) {
- fail("No signature present in " + jwt);
- }
-
- assertThat(matcher.group(3), not(is(emptyString())));
- }
-}
diff --git a/lib/src/test/java/com/auth0/jwt/algorithms/ECDSAAlgorithmTest.java b/lib/src/test/java/com/auth0/jwt/algorithms/ECDSAAlgorithmTest.java
deleted file mode 100644
index 2e636c71..00000000
--- a/lib/src/test/java/com/auth0/jwt/algorithms/ECDSAAlgorithmTest.java
+++ /dev/null
@@ -1,1352 +0,0 @@
-package com.auth0.jwt.algorithms;
-
-import com.auth0.jwt.JWT;
-import com.auth0.jwt.exceptions.SignatureGenerationException;
-import com.auth0.jwt.exceptions.SignatureVerificationException;
-import com.auth0.jwt.interfaces.ECDSAKeyProvider;
-import com.auth0.jwt.interfaces.JWTVerifier;
-import org.hamcrest.Matchers;
-import org.hamcrest.collection.IsIn;
-import org.junit.Rule;
-import org.junit.Test;
-import org.junit.rules.ExpectedException;
-
-import java.io.ByteArrayOutputStream;
-import java.math.BigInteger;
-import java.nio.charset.StandardCharsets;
-import java.security.*;
-import java.security.interfaces.ECKey;
-import java.security.interfaces.ECPrivateKey;
-import java.security.interfaces.ECPublicKey;
-import java.security.spec.ECParameterSpec;
-import java.util.Arrays;
-import java.util.Base64;
-
-import static com.auth0.jwt.PemUtils.readPrivateKeyFromFile;
-import static com.auth0.jwt.PemUtils.readPublicKeyFromFile;
-import static com.auth0.jwt.algorithms.CryptoTestHelper.asJWT;
-import static com.auth0.jwt.algorithms.CryptoTestHelper.assertSignaturePresent;
-import static org.hamcrest.CoreMatchers.is;
-import static org.hamcrest.Matchers.isA;
-import static org.hamcrest.Matchers.nullValue;
-import static org.hamcrest.MatcherAssert.assertThat;
-import static org.junit.internal.matchers.ThrowableMessageMatcher.hasMessage;
-import static org.mockito.ArgumentMatchers.any;
-import static org.mockito.ArgumentMatchers.anyString;
-import static org.mockito.Mockito.mock;
-import static org.mockito.Mockito.when;
-
-public class ECDSAAlgorithmTest {
-
- private static final String PRIVATE_KEY_FILE_256 = "src/test/resources/ec256-key-private.pem";
- private static final String PUBLIC_KEY_FILE_256 = "src/test/resources/ec256-key-public.pem";
- private static final String INVALID_PUBLIC_KEY_FILE_256 = "src/test/resources/ec256-key-public-invalid.pem";
-
- private static final String PRIVATE_KEY_FILE_384 = "src/test/resources/ec384-key-private.pem";
- private static final String PUBLIC_KEY_FILE_384 = "src/test/resources/ec384-key-public.pem";
- private static final String INVALID_PUBLIC_KEY_FILE_384 = "src/test/resources/ec384-key-public-invalid.pem";
-
- private static final String PRIVATE_KEY_FILE_512 = "src/test/resources/ec512-key-private.pem";
- private static final String PUBLIC_KEY_FILE_512 = "src/test/resources/ec512-key-public.pem";
- private static final String INVALID_PUBLIC_KEY_FILE_512 = "src/test/resources/ec512-key-public-invalid.pem";
-
- @Rule
- public ExpectedException exception = ExpectedException.none();
-
- //JOSE Signatures obtained using Node 'jwa' lib: https://github.com/brianloveswords/node-jwa
- //DER Signatures obtained from source JOSE signature using 'ecdsa-sig-formatter' lib: https://github.com/Brightspace/node-ecdsa-sig-formatter
-
- //These tests use the default preferred SecurityProvider to handle ECDSA algorithms
-
- // Verify
-
- @Test
- public void shouldPassECDSA256VerificationWithJOSESignature() throws Exception {
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9.4iVk3-Y0v4RT4_9IaQlp-8dZ_4fsTzIylgrPTDLrEvTHBTyVS3tgPbr2_IZfLETtiKRqCg0aQ5sh9eIsTTwB1g";
- ECKey key = (ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC");
- Algorithm algorithm = Algorithm.ECDSA256(key);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldThrowOnECDSA256VerificationWithDERSignature() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA256withECDSA");
- exception.expectCause(isA(SignatureException.class));
- exception.expectCause(hasMessage(is("Invalid JOSE signature format.")));
-
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9.MEYCIQDiJWTf5jShFPj0hpCWn7x1nhxPMjKWCs9MMusS9AIhAMcFPJVLe2A9uvb8hl8sRO2IpGoKDRpDmyH14ixNPAHW";
- ECKey key = (ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC");
- Algorithm algorithm = Algorithm.ECDSA256(key);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldPassECDSA256VerificationWithJOSESignatureWithBothKeys() throws Exception {
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9.4iVk3-Y0v4RT4_9IaQlp-8dZ_4fsTzIylgrPTDLrEvTHBTyVS3tgPbr2_IZfLETtiKRqCg0aQ5sh9eIsTTwB1g";
- Algorithm algorithm = Algorithm.ECDSA256((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldThrowOnECDSA256VerificationWithDERSignatureWithBothKeys() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA256withECDSA");
- exception.expectCause(isA(SignatureException.class));
- exception.expectCause(hasMessage(is("Invalid JOSE signature format.")));
-
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9.MEYCIQDiJWTf5jShFPj0hpCWn7x1nhxPMjKWCs9MMusS9AIhAMcFPJVLe2A9uvb8hl8sRO2IpGoKDRpDmyH14ixNPAHW";
- Algorithm algorithm = Algorithm.ECDSA256((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldPassECDSA256VerificationWithProvidedPublicKey() throws Exception {
- ECDSAKeyProvider provider = mock(ECDSAKeyProvider.class);
- PublicKey publicKey = readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC");
- when(provider.getPublicKeyById("my-key-id")).thenReturn((ECPublicKey) publicKey);
- String jwt = "eyJhbGciOiJFUzI1NiIsImtpZCI6Im15LWtleS1pZCJ9.eyJpc3MiOiJhdXRoMCJ9.D_oU4CB0ZEsxHOjcWnmS3ZJvlTzm6WcGFx-HASxnvcB2Xu2WjI-axqXH9xKq45aPBDs330JpRhJmqBSc2K8MXQ";
- Algorithm algorithm = Algorithm.ECDSA256(provider);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA256VerificationWhenProvidedPublicKeyIsNull() {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA256withECDSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Public Key is null.")));
- ECDSAKeyProvider provider = mock(ECDSAKeyProvider.class);
- when(provider.getPublicKeyById("my-key-id")).thenReturn(null);
- String jwt = "eyJhbGciOiJFUzI1NiIsImtpZCI6Im15LWtleS1pZCJ9.eyJpc3MiOiJhdXRoMCJ9.D_oU4CB0ZEsxHOjcWnmS3ZJvlTzm6WcGFx-HASxnvcB2Xu2WjI-axqXH9xKq45aPBDs330JpRhJmqBSc2K8MXQ";
- Algorithm algorithm = Algorithm.ECDSA256(provider);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA256VerificationWithInvalidPublicKey() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA256withECDSA");
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9.W9qfN1b80B9hnMo49WL8THrOsf1vEjOhapeFemPMGySzxTcgfyudS5esgeBTO908X5SLdAr5jMwPUPBs9b6nNg";
- Algorithm algorithm = Algorithm.ECDSA256((ECKey) readPublicKeyFromFile(INVALID_PUBLIC_KEY_FILE_256, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA256VerificationWhenUsingPrivateKey() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA256withECDSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Public Key is null.")));
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9.W9qfN1b80B9hnMo49WL8THrOsf1vEjOhapeFemPMGySzxTcgfyudS5esgeBTO908X5SLdAr5jMwPUPBs9b6nNg";
- Algorithm algorithm = Algorithm.ECDSA256((ECKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA256VerificationOnInvalidJOSESignatureLength() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA256withECDSA");
- exception.expectCause(isA(SignatureException.class));
- exception.expectCause(hasMessage(is("Invalid JOSE signature format.")));
-
- byte[] bytes = new byte[63];
- new SecureRandom().nextBytes(bytes);
- String signature = Base64.getUrlEncoder().withoutPadding().encodeToString(bytes);
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9." + signature;
- Algorithm algorithm = Algorithm.ECDSA256((ECKey) readPublicKeyFromFile(INVALID_PUBLIC_KEY_FILE_256, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA256VerificationOnInvalidJOSESignature() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA256withECDSA");
-
- byte[] bytes = new byte[64];
- new SecureRandom().nextBytes(bytes);
- String signature = Base64.getUrlEncoder().withoutPadding().encodeToString(bytes);
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9." + signature;
- Algorithm algorithm = Algorithm.ECDSA256((ECKey) readPublicKeyFromFile(INVALID_PUBLIC_KEY_FILE_256, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA256VerificationOnInvalidDERSignature() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA256withECDSA");
-
- byte[] bytes = new byte[64];
- bytes[0] = 0x30;
- new SecureRandom().nextBytes(bytes);
- String signature = Base64.getUrlEncoder().withoutPadding().encodeToString(bytes);
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9." + signature;
- Algorithm algorithm = Algorithm.ECDSA256((ECKey) readPublicKeyFromFile(INVALID_PUBLIC_KEY_FILE_256, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldPassECDSA384VerificationWithJOSESignature() throws Exception {
- String jwt = "eyJhbGciOiJFUzM4NCJ9.eyJpc3MiOiJhdXRoMCJ9.50UU5VKNdF1wfykY8jQBKpvuHZoe6IZBJm5NvoB8bR-hnRg6ti-CHbmvoRtlLfnHfwITa_8cJMy6TenMC2g63GQHytc8rYoXqbwtS4R0Ko_AXbLFUmfxnGnMC6v4MS_z";
- ECKey key = (ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_384, "EC");
- Algorithm algorithm = Algorithm.ECDSA384(key);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldThrowOnECDSA384VerificationWithDERSignature() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA384withECDSA");
- exception.expectCause(isA(SignatureException.class));
- exception.expectCause(hasMessage(is("Invalid JOSE signature format.")));
-
- String jwt = "eyJhbGciOiJFUzM4NCJ9.eyJpc3MiOiJhdXRoMCJ9.MGUCMQDnRRTlUo10XXBKRjyNAEqm4dmh7ohkEmbk2gHxtH6GdGDq2L4IduahG2UtccCMH8CE2vHCTMuk3pzAtoOtxkB8rXPK2KF6m8LUuEdCqPwF2yxVJn8ZxpzAurDEv8w";
- ECKey key = (ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_384, "EC");
- Algorithm algorithm = Algorithm.ECDSA384(key);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldPassECDSA384VerificationWithJOSESignatureWithBothKeys() throws Exception {
- String jwt = "eyJhbGciOiJFUzM4NCJ9.eyJpc3MiOiJhdXRoMCJ9.50UU5VKNdF1wfykY8jQBKpvuHZoe6IZBJm5NvoB8bR-hnRg6ti-CHbmvoRtlLfnHfwITa_8cJMy6TenMC2g63GQHytc8rYoXqbwtS4R0Ko_AXbLFUmfxnGnMC6v4MS_z";
- Algorithm algorithm = Algorithm.ECDSA384((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_384, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_384, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldThrowOnECDSA384VerificationWithDERSignatureWithBothKeys() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA384withECDSA");
- exception.expectCause(isA(SignatureException.class));
- exception.expectCause(hasMessage(is("Invalid JOSE signature format.")));
-
- String jwt = "eyJhbGciOiJFUzM4NCJ9.eyJpc3MiOiJhdXRoMCJ9.MGUCMQDnRRTlUo10XXBKRjyNAEqm4dmh7ohkEmbk2gHxtH6GdGDq2L4IduahG2UccCMH8CE2vHCTMuk3pzAtoOtxkB8rXPK2KF6m8LUuEdCqPwF2yxVJn8ZxpzAurDEv8w";
- Algorithm algorithm = Algorithm.ECDSA384((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_384, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_384, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldPassECDSA384VerificationWithProvidedPublicKey() throws Exception {
- ECDSAKeyProvider provider = mock(ECDSAKeyProvider.class);
- PublicKey publicKey = readPublicKeyFromFile(PUBLIC_KEY_FILE_384, "EC");
- when(provider.getPublicKeyById("my-key-id")).thenReturn((ECPublicKey) publicKey);
- String jwt = "eyJhbGciOiJFUzM4NCIsImtpZCI6Im15LWtleS1pZCJ9.eyJpc3MiOiJhdXRoMCJ9.9kjGuFTPx3ylfpqL0eY9H7TGmPepjQOBKI8UPoEvby6N7dDLF5HxLohosNxxFymNT7LzpeSgOPAB0wJEwG2Nl2ukgdUOpZOf492wog_i5ZcZmAykd3g1QH7onrzd69GU";
- Algorithm algorithm = Algorithm.ECDSA384(provider);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA384VerificationWhenProvidedPublicKeyIsNull() {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA384withECDSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Public Key is null.")));
- ECDSAKeyProvider provider = mock(ECDSAKeyProvider.class);
- when(provider.getPublicKeyById("my-key-id")).thenReturn(null);
- String jwt = "eyJhbGciOiJFUzM4NCIsImtpZCI6Im15LWtleS1pZCJ9.eyJpc3MiOiJhdXRoMCJ9.9kjGuFTPx3ylfpqL0eY9H7TGmPepjQOBKI8UPoEvby6N7dDLF5HxLohosNxxFymNT7LzpeSgOPAB0wJEwG2Nl2ukgdUOpZOf492wog_i5ZcZmAykd3g1QH7onrzd69GU";
- Algorithm algorithm = Algorithm.ECDSA384(provider);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA384VerificationWithInvalidPublicKey() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA384withECDSA");
- String jwt = "eyJhbGciOiJFUzM4NCJ9.eyJpc3MiOiJhdXRoMCJ9._k5h1KyO-NE0R2_HAw0-XEc0bGT5atv29SxHhOGC9JDqUHeUdptfCK_ljQ01nLVt2OQWT2SwGs-TuyHDFmhPmPGFZ9wboxvq_ieopmYqhQilNAu-WF-frioiRz9733fU";
- Algorithm algorithm = Algorithm.ECDSA384((ECKey) readPublicKeyFromFile(INVALID_PUBLIC_KEY_FILE_384, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA384VerificationWhenUsingPrivateKey() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA384withECDSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Public Key is null.")));
- String jwt = "eyJhbGciOiJFUzM4NCJ9.eyJpc3MiOiJhdXRoMCJ9._k5h1KyO-NE0R2_HAw0-XEc0bGT5atv29SxHhOGC9JDqUHeUdptfCK_ljQ01nLVt2OQWT2SwGs-TuyHDFmhPmPGFZ9wboxvq_ieopmYqhQilNAu-WF-frioiRz9733fU";
- Algorithm algorithm = Algorithm.ECDSA384((ECKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_384, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA384VerificationOnInvalidJOSESignatureLength() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA384withECDSA");
- exception.expectCause(isA(SignatureException.class));
- exception.expectCause(hasMessage(is("Invalid JOSE signature format.")));
-
- byte[] bytes = new byte[95];
- new SecureRandom().nextBytes(bytes);
- String signature = Base64.getUrlEncoder().withoutPadding().encodeToString(bytes);
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9." + signature;
- Algorithm algorithm = Algorithm.ECDSA384((ECKey) readPublicKeyFromFile(INVALID_PUBLIC_KEY_FILE_384, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA384VerificationOnInvalidJOSESignature() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA384withECDSA");
-
- byte[] bytes = new byte[96];
- new SecureRandom().nextBytes(bytes);
- String signature = Base64.getUrlEncoder().withoutPadding().encodeToString(bytes);
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9." + signature;
- Algorithm algorithm = Algorithm.ECDSA384((ECKey) readPublicKeyFromFile(INVALID_PUBLIC_KEY_FILE_384, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA384VerificationOnInvalidDERSignature() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA384withECDSA");
-
- byte[] bytes = new byte[96];
- new SecureRandom().nextBytes(bytes);
- bytes[0] = 0x30;
- String signature = Base64.getUrlEncoder().withoutPadding().encodeToString(bytes);
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9." + signature;
- Algorithm algorithm = Algorithm.ECDSA384((ECKey) readPublicKeyFromFile(INVALID_PUBLIC_KEY_FILE_384, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldPassECDSA512VerificationWithJOSESignature() throws Exception {
- String jwt = "eyJhbGciOiJFUzUxMiJ9.eyJpc3MiOiJhdXRoMCJ9.AeCJPDIsSHhwRSGZCY6rspi8zekOw0K9qYMNridP1Fu9uhrA1QrG-EUxXlE06yvmh2R7Rz0aE7kxBwrnq8L8aOBCAYAsqhzPeUvyp8fXjjgs0Eto5I0mndE2QHlgcMSFASyjHbU8wD2Rq7ZNzGQ5b2MZfpv030WGUajT-aZYWFUJHVg2";
- ECKey key = (ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_512, "EC");
- Algorithm algorithm = Algorithm.ECDSA512(key);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldThrowOnECDSA512VerificationWithDERSignature() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA512withECDSA");
- exception.expectCause(isA(SignatureException.class));
- exception.expectCause(hasMessage(is("Invalid JOSE signature format.")));
-
- String jwt = "eyJhbGciOiJFUzUxMiJ9.eyJpc3MiOiJhdXRoMCJ9.MIGIAkIB4Ik8MixIeHBFIZkJjquymLzN6Q7DQr2pgw2uJ0UW726GsDVCsb4RTFeUTTrKaHZHtHPRoTuTEHCuerwvxo4EICQgGALKocz3lL8qfH1444LNBLaOSNJp3RNkB5YHDEhQEsox21PMA9kau2TcxkOW9jGX6b9N9FhlGo0mmWFhVCR1YNg";
- ECKey key = (ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_512, "EC");
- Algorithm algorithm = Algorithm.ECDSA512(key);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldPassECDSA512VerificationWithJOSESignatureWithBothKeys() throws Exception {
- String jwt = "eyJhbGciOiJFUzUxMiJ9.eyJpc3MiOiJhdXRoMCJ9.AeCJPDIsSHhwRSGZCY6rspi8zekOw0K9qYMNridP1Fu9uhrA1QrG-EUxXlE06yvmh2R7Rz0aE7kxBwrnq8L8aOBCAYAsqhzPeUvyp8fXjjgs0Eto5I0mndE2QHlgcMSFASyjHbU8wD2Rq7ZNzGQ5b2MZfpv030WGUajT-aZYWFUJHVg2";
- Algorithm algorithm = Algorithm.ECDSA512((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_512, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_512, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldThrowECDSA512VerificationWithDERSignatureWithBothKeys() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA512withECDSA");
- exception.expectCause(isA(SignatureException.class));
- exception.expectCause(hasMessage(is("Invalid JOSE signature format.")));
-
- String jwt = "eyJhbGciOiJFUzUxMiJ9.eyJpc3MiOiJhdXRoMCJ9.MIGIAkIB4Ik8MixIeHBFIZkJjquymLzN6Q7DQr2pgw2uJ0UW726GsDVCsb4RTFeUTTrKaHZHtHPRoTuTEHCuerwvxo4EICQgGALKocz3lL8qfH1444LNBLaOSNJp3RNkB5YHDEhQEsox21PMA9kau2TcxkOW9jGX6b9N9FhlGo0mmWFhVCR1YNg";
- Algorithm algorithm = Algorithm.ECDSA512((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_512, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_512, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldPassECDSA512VerificationWithProvidedPublicKey() throws Exception {
- ECDSAKeyProvider provider = mock(ECDSAKeyProvider.class);
- PublicKey publicKey = readPublicKeyFromFile(PUBLIC_KEY_FILE_512, "EC");
- when(provider.getPublicKeyById("my-key-id")).thenReturn((ECPublicKey) publicKey);
- String jwt = "eyJhbGciOiJFUzUxMiIsImtpZCI6Im15LWtleS1pZCJ9.eyJpc3MiOiJhdXRoMCJ9.AGxEwbsYa2bQ7Y7DAcTQnVD8PmLSlhJ20jg2OfdyPnqdXI8SgBaG6lGciq3_pofFhs1HEoFoJ33Jcluha24oMHIvAfwu8qbv_Wq3L2eI9Q0L0p6ul8Pd_BS8adRa2PgLc36xXGcRc7ID5YH-CYaQfsTp5YIaF0Po3h0QyCoQ6ZiYQkqm";
- Algorithm algorithm = Algorithm.ECDSA512(provider);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA512VerificationWhenProvidedPublicKeyIsNull() {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA512withECDSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Public Key is null.")));
- ECDSAKeyProvider provider = mock(ECDSAKeyProvider.class);
- when(provider.getPublicKeyById("my-key-id")).thenReturn(null);
- String jwt = "eyJhbGciOiJFUzUxMiIsImtpZCI6Im15LWtleS1pZCJ9.eyJpc3MiOiJhdXRoMCJ9.AGxEwbsYa2bQ7Y7DAcTQnVD8PmLSlhJ20jg2OfdyPnqdXI8SgBaG6lGciq3_pofFhs1HEoFoJ33Jcluha24oMHIvAfwu8qbv_Wq3L2eI9Q0L0p6ul8Pd_BS8adRa2PgLc36xXGcRc7ID5YH-CYaQfsTp5YIaF0Po3h0QyCoQ6ZiYQkqm";
- Algorithm algorithm = Algorithm.ECDSA512(provider);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA512VerificationWithInvalidPublicKey() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA512withECDSA");
- String jwt = "eyJhbGciOiJFUzUxMiJ9.eyJpc3MiOiJhdXRoMCJ9.AZgdopFFsN0amCSs2kOucXdpylD31DEm5ChK1PG0_gq5Mf47MrvVph8zHSVuvcrXzcE1U3VxeCg89mYW1H33Y-8iAF0QFkdfTUQIWKNObH543WNMYYssv3OtOj0znPv8atDbaF8DMYAtcT1qdmaSJRhx-egRE9HGZkinPh9CfLLLt58X";
- Algorithm algorithm = Algorithm.ECDSA512((ECKey) readPublicKeyFromFile(INVALID_PUBLIC_KEY_FILE_512, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA512VerificationWhenUsingPrivateKey() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA512withECDSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Public Key is null.")));
- String jwt = "eyJhbGciOiJFUzUxMiJ9.eyJpc3MiOiJhdXRoMCJ9.AZgdopFFsN0amCSs2kOucXdpylD31DEm5ChK1PG0_gq5Mf47MrvVph8zHSVuvcrXzcE1U3VxeCg89mYW1H33Y-8iAF0QFkdfTUQIWKNObH543WNMYYssv3OtOj0znPv8atDbaF8DMYAtcT1qdmaSJRhx-egRE9HGZkinPh9CfLLLt58X";
- Algorithm algorithm = Algorithm.ECDSA512((ECKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_512, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA512VerificationOnInvalidJOSESignatureLength() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA512withECDSA");
- exception.expectCause(isA(SignatureException.class));
- exception.expectCause(hasMessage(is("Invalid JOSE signature format.")));
-
- byte[] bytes = new byte[131];
- new SecureRandom().nextBytes(bytes);
- String signature = Base64.getUrlEncoder().withoutPadding().encodeToString(bytes);
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9." + signature;
- Algorithm algorithm = Algorithm.ECDSA512((ECKey) readPublicKeyFromFile(INVALID_PUBLIC_KEY_FILE_512, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA512VerificationOnInvalidJOSESignature() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA512withECDSA");
-
- byte[] bytes = new byte[132];
- new SecureRandom().nextBytes(bytes);
- String signature = Base64.getUrlEncoder().withoutPadding().encodeToString(bytes);
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9." + signature;
- Algorithm algorithm = Algorithm.ECDSA512((ECKey) readPublicKeyFromFile(INVALID_PUBLIC_KEY_FILE_512, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA512VerificationOnInvalidDERSignature() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA512withECDSA");
-
- byte[] bytes = new byte[132];
- new SecureRandom().nextBytes(bytes);
- bytes[0] = 0x30;
- String signature = Base64.getUrlEncoder().withoutPadding().encodeToString(bytes);
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9." + signature;
- Algorithm algorithm = Algorithm.ECDSA512((ECKey) readPublicKeyFromFile(INVALID_PUBLIC_KEY_FILE_512, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailJOSEToDERConversionOnInvalidJOSESignatureLength() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA256withECDSA");
- exception.expectCause(isA(SignatureException.class));
- exception.expectCause(hasMessage(is("Invalid JOSE signature format.")));
-
- byte[] bytes = new byte[256];
- new SecureRandom().nextBytes(bytes);
- String signature = Base64.getUrlEncoder().withoutPadding().encodeToString(bytes);
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9." + signature;
-
- ECPublicKey publicKey = (ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC");
- ECPrivateKey privateKey = mock(ECPrivateKey.class);
- ECDSAKeyProvider provider = ECDSAAlgorithm.providerForKeys(publicKey, privateKey);
- Algorithm algorithm = new ECDSAAlgorithm("ES256", "SHA256withECDSA", 128, provider);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldThrowOnVerifyWhenSignatureAlgorithmDoesNotExists() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: some-alg");
- exception.expectCause(isA(NoSuchAlgorithmException.class));
-
- CryptoHelper crypto = mock(CryptoHelper.class);
- when(crypto.verifySignatureFor(anyString(), any(PublicKey.class), any(String.class), any(String.class), any(byte[].class)))
- .thenThrow(NoSuchAlgorithmException.class);
-
- ECPublicKey publicKey = mock(ECPublicKey.class);
- when(publicKey.getParams()).thenReturn(mock(ECParameterSpec.class));
- byte[] a = new byte[64];
- Arrays.fill(a, Byte.MAX_VALUE);
- when(publicKey.getParams().getOrder()).thenReturn(new BigInteger(a));
- ECPrivateKey privateKey = mock(ECPrivateKey.class);
- ECDSAKeyProvider provider = ECDSAAlgorithm.providerForKeys(publicKey, privateKey);
- Algorithm algorithm = new ECDSAAlgorithm(crypto, "some-alg", "some-algorithm", 32, provider);
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9.4iVk3-Y0v4RT4_9IaQlp-8dZ_4fsTzIylgrPTDLrEvTHBTyVS3tgPbr2_IZfLETtiKRqCg0aQ5sh9eIsTTwB1g";
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldThrowOnVerifyWhenThePublicKeyIsInvalid() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: some-alg");
- exception.expectCause(isA(InvalidKeyException.class));
-
- CryptoHelper crypto = mock(CryptoHelper.class);
- when(crypto.verifySignatureFor(anyString(), any(PublicKey.class), any(String.class), any(String.class), any(byte[].class)))
- .thenThrow(InvalidKeyException.class);
-
- ECPublicKey publicKey = mock(ECPublicKey.class);
- when(publicKey.getParams()).thenReturn(mock(ECParameterSpec.class));
- byte[] a = new byte[64];
- Arrays.fill(a, Byte.MAX_VALUE);
- when(publicKey.getParams().getOrder()).thenReturn(new BigInteger(a));
- ECPrivateKey privateKey = mock(ECPrivateKey.class);
- ECDSAKeyProvider provider = ECDSAAlgorithm.providerForKeys(publicKey, privateKey);
- Algorithm algorithm = new ECDSAAlgorithm(crypto, "some-alg", "some-algorithm", 32, provider);
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9.4iVk3-Y0v4RT4_9IaQlp-8dZ_4fsTzIylgrPTDLrEvTHBTyVS3tgPbr2_IZfLETtiKRqCg0aQ5sh9eIsTTwB1g";
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldThrowOnVerifyWhenTheSignatureIsNotPrepared() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: some-alg");
- exception.expectCause(isA(SignatureException.class));
-
- CryptoHelper crypto = mock(CryptoHelper.class);
- when(crypto.verifySignatureFor(anyString(), any(PublicKey.class), any(String.class), any(String.class), any(byte[].class)))
- .thenThrow(SignatureException.class);
-
- ECPublicKey publicKey = mock(ECPublicKey.class);
- when(publicKey.getParams()).thenReturn(mock(ECParameterSpec.class));
- byte[] a = new byte[64];
- Arrays.fill(a, Byte.MAX_VALUE);
- when(publicKey.getParams().getOrder()).thenReturn(new BigInteger(a));
- ECPrivateKey privateKey = mock(ECPrivateKey.class);
- ECDSAKeyProvider provider = ECDSAAlgorithm.providerForKeys(publicKey, privateKey);
- Algorithm algorithm = new ECDSAAlgorithm(crypto, "some-alg", "some-algorithm", 32, provider);
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9.4iVk3-Y0v4RT4_9IaQlp-8dZ_4fsTzIylgrPTDLrEvTHBTyVS3tgPbr2_IZfLETtiKRqCg0aQ5sh9eIsTTwB1g";
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldThrowWhenSignatureNotValidBase64() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectCause(isA(IllegalArgumentException.class));
-
- String jwt = "eyJhbGciOiJFUzUxMiJ9.eyJpc3MiOiJhdXRoMCJ9.MIGIAkIB4Ik8MixIeHBFIZkJjquymLzN6Q7DQr2pgw2uJ0UW726GsDVCsb4RTFeUTTrKaHZHtHPRoTuTEHCuerwvxo4+EICQgGALKocz3lL8qfH1444LNBLaOSNJp3RNkB5YHDEhQEsox21PMA9kau2TcxkOW9jGX6b9N9FhlGo0mmWFhVCR1YNg";
- ECKey key = (ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_512, "EC");
- Algorithm algorithm = Algorithm.ECDSA512(key);
- algorithm.verify(JWT.decode(jwt));
- }
-
- //Sign
- private static final String ES256Header = "eyJhbGciOiJFUzI1NiJ9";
- private static final String ES384Header = "eyJhbGciOiJFUzM4NCJ9";
- private static final String ES512Header = "eyJhbGciOiJFUzUxMiJ9";
- private static final String auth0IssPayload = "eyJpc3MiOiJhdXRoMCJ9";
-
- private static final byte[] ES256HeaderBytes = ES256Header.getBytes(StandardCharsets.UTF_8);
- private static final byte[] ES384HeaderBytes = ES384Header.getBytes(StandardCharsets.UTF_8);
- private static final byte[] ES512HeaderBytes = ES512Header.getBytes(StandardCharsets.UTF_8);
- private static final byte[] auth0IssPayloadBytes = auth0IssPayload.getBytes(StandardCharsets.UTF_8);
-
-
- @Test
- public void shouldDoECDSA256Signing() throws Exception {
- Algorithm algorithm = Algorithm.ECDSA256((ECKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC"));
- Algorithm algorithmVerify = Algorithm.ECDSA256((ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC"));
- String jwt = asJWT(algorithm, ES256Header, auth0IssPayload);
-
- assertSignaturePresent(jwt);
- algorithmVerify.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldDoECDSA256SigningWithBothKeys() throws Exception {
- Algorithm algorithm = Algorithm.ECDSA256((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC"));
- byte[] signatureBytes = algorithm.sign(ES256HeaderBytes, auth0IssPayloadBytes);
- String jwtSignature = Base64.getUrlEncoder().withoutPadding().encodeToString(signatureBytes);
- String jwt = String.format("%s.%s.%s", ES256Header, auth0IssPayload, jwtSignature);
-
- assertSignaturePresent(jwt);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldDoECDSA256SigningWithProvidedPrivateKey() throws Exception {
- ECDSAKeyProvider provider = mock(ECDSAKeyProvider.class);
- PrivateKey privateKey = readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC");
- PublicKey publicKey = readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC");
- when(provider.getPrivateKey()).thenReturn((ECPrivateKey) privateKey);
- when(provider.getPublicKeyById(null)).thenReturn((ECPublicKey) publicKey);
- Algorithm algorithm = Algorithm.ECDSA256(provider);
-
- String jwt = asJWT(algorithm, ES256Header, auth0IssPayload);
-
- assertSignaturePresent(jwt);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailOnECDSA256SigningWhenProvidedPrivateKeyIsNull() {
- exception.expect(SignatureGenerationException.class);
- exception.expectMessage("The Token's Signature couldn't be generated when signing using the Algorithm: SHA256withECDSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Private Key is null.")));
-
- ECDSAKeyProvider provider = mock(ECDSAKeyProvider.class);
- when(provider.getPrivateKey()).thenReturn(null);
- Algorithm algorithm = Algorithm.ECDSA256(provider);
- algorithm.sign(new byte[0], new byte[0]);
- }
-
- @Test
- public void shouldFailOnECDSA256SigningWhenUsingPublicKey() throws Exception {
- exception.expect(SignatureGenerationException.class);
- exception.expectMessage("The Token's Signature couldn't be generated when signing using the Algorithm: SHA256withECDSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Private Key is null.")));
-
- Algorithm algorithm = Algorithm.ECDSA256((ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC"));
- algorithm.sign(new byte[0], new byte[0]);
- }
-
- @Test
- public void shouldDoECDSA384Signing() throws Exception {
- Algorithm algorithmSign = Algorithm.ECDSA384((ECKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_384, "EC"));
- Algorithm algorithmVerify = Algorithm.ECDSA384((ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_384, "EC"));
- String jwt = asJWT(algorithmSign, ES384Header, auth0IssPayload);
-
- assertSignaturePresent(jwt);
- algorithmVerify.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldDoECDSA384SigningWithBothKeys() throws Exception {
- Algorithm algorithm = Algorithm.ECDSA384((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_384, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_384, "EC"));
- String jwt = asJWT(algorithm, ES384Header, auth0IssPayload);
-
- assertSignaturePresent(jwt);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldDoECDSA384SigningWithProvidedPrivateKey() throws Exception {
- ECDSAKeyProvider provider = mock(ECDSAKeyProvider.class);
- PrivateKey privateKey = readPrivateKeyFromFile(PRIVATE_KEY_FILE_384, "EC");
- PublicKey publicKey = readPublicKeyFromFile(PUBLIC_KEY_FILE_384, "EC");
- when(provider.getPrivateKey()).thenReturn((ECPrivateKey) privateKey);
- when(provider.getPublicKeyById(null)).thenReturn((ECPublicKey) publicKey);
- Algorithm algorithm = Algorithm.ECDSA384(provider);
-
- String jwt = asJWT(algorithm, ES384Header, auth0IssPayload);
-
- assertSignaturePresent(jwt);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailOnECDSA384SigningWhenProvidedPrivateKeyIsNull() {
- exception.expect(SignatureGenerationException.class);
- exception.expectMessage("The Token's Signature couldn't be generated when signing using the Algorithm: SHA384withECDSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Private Key is null.")));
-
- ECDSAKeyProvider provider = mock(ECDSAKeyProvider.class);
- when(provider.getPrivateKey()).thenReturn(null);
- Algorithm algorithm = Algorithm.ECDSA384(provider);
- algorithm.sign(new byte[0], new byte[0]);
- }
-
- @Test
- public void shouldFailOnECDSA384SigningWhenUsingPublicKey() throws Exception {
- exception.expect(SignatureGenerationException.class);
- exception.expectMessage("The Token's Signature couldn't be generated when signing using the Algorithm: SHA384withECDSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Private Key is null.")));
-
- Algorithm algorithm = Algorithm.ECDSA384((ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_384, "EC"));
- algorithm.sign(new byte[0], new byte[0]);
- }
-
- @Test
- public void shouldDoECDSA512Signing() throws Exception {
- Algorithm algorithmSign = Algorithm.ECDSA512((ECKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_512, "EC"));
- Algorithm algorithmVerify = Algorithm.ECDSA512((ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_512, "EC"));
-
- String jwt = asJWT(algorithmSign, ES512Header, auth0IssPayload);
-
- assertSignaturePresent(jwt);
- algorithmVerify.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldDoECDSA512SigningWithBothKeys() throws Exception {
- Algorithm algorithm = Algorithm.ECDSA512((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_512, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_512, "EC"));
-
- String jwt = asJWT(algorithm, ES512Header, auth0IssPayload);
-
- assertSignaturePresent(jwt);
- algorithm.verify(JWT.decode(jwt));
- }
-
-
- @Test
- public void shouldDoECDSA512SigningWithProvidedPrivateKey() throws Exception {
- ECDSAKeyProvider provider = mock(ECDSAKeyProvider.class);
- PrivateKey privateKey = readPrivateKeyFromFile(PRIVATE_KEY_FILE_512, "EC");
- PublicKey publicKey = readPublicKeyFromFile(PUBLIC_KEY_FILE_512, "EC");
- when(provider.getPrivateKey()).thenReturn((ECPrivateKey) privateKey);
- when(provider.getPublicKeyById(null)).thenReturn((ECPublicKey) publicKey);
- Algorithm algorithm = Algorithm.ECDSA512(provider);
-
- String jwt = asJWT(algorithm, ES512Header, auth0IssPayload);
-
- assertSignaturePresent(jwt);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailOnECDSA512SigningWhenProvidedPrivateKeyIsNull() {
- exception.expect(SignatureGenerationException.class);
- exception.expectMessage("The Token's Signature couldn't be generated when signing using the Algorithm: SHA512withECDSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Private Key is null.")));
-
- ECDSAKeyProvider provider = mock(ECDSAKeyProvider.class);
- when(provider.getPrivateKey()).thenReturn(null);
- Algorithm algorithm = Algorithm.ECDSA512(provider);
- algorithm.sign(new byte[0], new byte[0]);
- }
-
- @Test
- public void shouldFailOnECDSA512SigningWhenUsingPublicKey() throws Exception {
- exception.expect(SignatureGenerationException.class);
- exception.expectMessage("The Token's Signature couldn't be generated when signing using the Algorithm: SHA512withECDSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Private Key is null.")));
-
- Algorithm algorithm = Algorithm.ECDSA512((ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_512, "EC"));
- algorithm.sign(new byte[0], new byte[0]);
- }
-
- @Test
- public void shouldThrowOnSignWhenSignatureAlgorithmDoesNotExists() throws Exception {
- exception.expect(SignatureGenerationException.class);
- exception.expectMessage("The Token's Signature couldn't be generated when signing using the Algorithm: some-algorithm");
- exception.expectCause(isA(NoSuchAlgorithmException.class));
-
- CryptoHelper crypto = mock(CryptoHelper.class);
- when(crypto.createSignatureFor(anyString(), any(PrivateKey.class), any(byte[].class), any(byte[].class)))
- .thenThrow(NoSuchAlgorithmException.class);
-
- ECPublicKey publicKey = mock(ECPublicKey.class);
- ECPrivateKey privateKey = mock(ECPrivateKey.class);
- ECDSAKeyProvider provider = ECDSAAlgorithm.providerForKeys(publicKey, privateKey);
- Algorithm algorithm = new ECDSAAlgorithm(crypto, "some-alg", "some-algorithm", 32, provider);
- algorithm.sign(ES256HeaderBytes, new byte[0]);
- }
-
- @Test
- public void shouldThrowOnSignWhenThePrivateKeyIsInvalid() throws Exception {
- exception.expect(SignatureGenerationException.class);
- exception.expectMessage("The Token's Signature couldn't be generated when signing using the Algorithm: some-algorithm");
- exception.expectCause(isA(InvalidKeyException.class));
-
- CryptoHelper crypto = mock(CryptoHelper.class);
- when(crypto.createSignatureFor(anyString(), any(PrivateKey.class), any(byte[].class), any(byte[].class)))
- .thenThrow(InvalidKeyException.class);
-
- ECPublicKey publicKey = mock(ECPublicKey.class);
- ECPrivateKey privateKey = mock(ECPrivateKey.class);
- ECDSAKeyProvider provider = ECDSAAlgorithm.providerForKeys(publicKey, privateKey);
- Algorithm algorithm = new ECDSAAlgorithm(crypto, "some-alg", "some-algorithm", 32, provider);
- algorithm.sign(ES256HeaderBytes, new byte[0]);
- }
-
- @Test
- public void shouldThrowOnSignWhenTheSignatureIsNotPrepared() throws Exception {
- exception.expect(SignatureGenerationException.class);
- exception.expectMessage("The Token's Signature couldn't be generated when signing using the Algorithm: some-algorithm");
- exception.expectCause(isA(SignatureException.class));
-
- CryptoHelper crypto = mock(CryptoHelper.class);
- when(crypto.createSignatureFor(anyString(), any(PrivateKey.class), any(byte[].class), any(byte[].class)))
- .thenThrow(SignatureException.class);
-
- ECPublicKey publicKey = mock(ECPublicKey.class);
- ECPrivateKey privateKey = mock(ECPrivateKey.class);
- ECDSAKeyProvider provider = ECDSAAlgorithm.providerForKeys(publicKey, privateKey);
- Algorithm algorithm = new ECDSAAlgorithm(crypto, "some-alg", "some-algorithm", 32, provider);
- algorithm.sign(ES256HeaderBytes, new byte[0]);
- }
-
- @Test
- public void shouldReturnNullSigningKeyIdIfCreatedWithDefaultProvider() {
- ECPublicKey publicKey = mock(ECPublicKey.class);
- ECPrivateKey privateKey = mock(ECPrivateKey.class);
- ECDSAKeyProvider provider = ECDSAAlgorithm.providerForKeys(publicKey, privateKey);
- Algorithm algorithm = new ECDSAAlgorithm("some-alg", "some-algorithm", 32, provider);
-
- assertThat(algorithm.getSigningKeyId(), is(nullValue()));
- }
-
- @Test
- public void shouldReturnSigningKeyIdFromProvider() {
- ECDSAKeyProvider provider = mock(ECDSAKeyProvider.class);
- when(provider.getPrivateKeyId()).thenReturn("keyId");
- Algorithm algorithm = new ECDSAAlgorithm("some-alg", "some-algorithm", 32, provider);
-
- assertThat(algorithm.getSigningKeyId(), is("keyId"));
- }
-
- @Test
- public void shouldThrowOnDERSignatureConversionIfDoesNotStartWithCorrectSequenceByte() throws Exception {
- exception.expect(SignatureException.class);
- exception.expectMessage("Invalid DER signature format.");
-
- ECDSAAlgorithm algorithm256 = (ECDSAAlgorithm) Algorithm.ECDSA256((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC"));
- String content256 = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9";
-
- byte[] signature = algorithm256.sign(content256.getBytes(), new byte[0]);
- signature[0] = (byte) 0x02;
- algorithm256.DERToJOSE(signature);
- }
-
- @Test
- public void shouldThrowOnDERSignatureConversionIfDoesNotHaveExpectedLength() throws Exception {
- ECDSAAlgorithm algorithm256 = (ECDSAAlgorithm) Algorithm.ECDSA256((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC"));
- byte[] derSignature = createDERSignature(32, false, false);
- int received = (int) derSignature[1];
- received--;
- derSignature[1] = (byte) received;
- exception.expect(SignatureException.class);
- exception.expectMessage("Invalid DER signature format.");
-
- algorithm256.DERToJOSE(derSignature);
- }
-
- @Test
- public void shouldThrowOnDERSignatureConversionIfRNumberDoesNotHaveExpectedLength() throws Exception {
- ECDSAAlgorithm algorithm256 = (ECDSAAlgorithm) Algorithm.ECDSA256((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC"));
- byte[] derSignature = createDERSignature(32, false, false);
- derSignature[3] = (byte) 34;
- exception.expect(SignatureException.class);
- exception.expectMessage("Invalid DER signature format.");
-
- algorithm256.DERToJOSE(derSignature);
- }
-
- @Test
- public void shouldThrowOnDERSignatureConversionIfSNumberDoesNotHaveExpectedLength() throws Exception {
- ECDSAAlgorithm algorithm256 = (ECDSAAlgorithm) Algorithm.ECDSA256((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC"));
- byte[] derSignature = createDERSignature(32, false, false);
- derSignature[4 + 32 + 1] = (byte) 34;
- exception.expect(SignatureException.class);
- exception.expectMessage("Invalid DER signature format.");
-
- algorithm256.DERToJOSE(derSignature);
- }
-
- @Test
- public void shouldThrowOnJOSESignatureConversionIfDoesNotHaveExpectedLength() throws Exception {
- ECPublicKey publicKey = (ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC");
- ECDSAAlgorithm algorithm256 = (ECDSAAlgorithm) Algorithm.ECDSA256(publicKey, (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC"));
- byte[] joseSignature = new byte[32 * 2 - 1];
- exception.expect(SignatureException.class);
- exception.expectMessage("Invalid JOSE signature format.");
-
- algorithm256.validateSignatureStructure(joseSignature, publicKey);
- }
-
- @Test
- public void shouldSignAndVerifyWithECDSA256() throws Exception {
- ECDSAAlgorithm algorithm256 = (ECDSAAlgorithm) Algorithm.ECDSA256((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC"));
- String header256 = "eyJhbGciOiJFUzI1NiJ9";
- String body = "eyJpc3MiOiJhdXRoMCJ9";
-
- for (int i = 0; i < 10; i++) {
- String jwt = asJWT(algorithm256, header256, body);
- algorithm256.verify(JWT.decode(jwt));
- }
- }
-
- @Test
- public void shouldSignAndVerifyWithECDSA384() throws Exception {
- ECDSAAlgorithm algorithm384 = (ECDSAAlgorithm) Algorithm.ECDSA384((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_384, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_384, "EC"));
- String header384 = "eyJhbGciOiJFUzM4NCJ9";
- String body = "eyJpc3MiOiJhdXRoMCJ9";
-
- for (int i = 0; i < 10; i++) {
- String jwt = asJWT(algorithm384, header384, body);
- algorithm384.verify(JWT.decode(jwt));
- }
- }
-
- @Test
- public void shouldSignAndVerifyWithECDSA512() throws Exception {
- ECDSAAlgorithm algorithm512 = (ECDSAAlgorithm) Algorithm.ECDSA512((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_512, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_512, "EC"));
- String header512 = "eyJhbGciOiJFUzUxMiJ9";
- String body = "eyJpc3MiOiJhdXRoMCJ9";
-
- for (int i = 0; i < 10; i++) {
- String jwt = asJWT(algorithm512, header512, body);
- algorithm512.verify(JWT.decode(jwt));
- }
- }
-
- @Test
- public void shouldDecodeECDSA256JOSE() throws Exception {
- ECDSAAlgorithm algorithm256 = (ECDSAAlgorithm) Algorithm.ECDSA256((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC"));
-
- //Without padding
- byte[] joseSignature = createJOSESignature(32, false, false);
- byte[] derSignature = algorithm256.JOSEToDER(joseSignature);
- assertValidDERSignature(derSignature, 32, false, false);
-
- //With R padding
- joseSignature = createJOSESignature(32, true, false);
- derSignature = algorithm256.JOSEToDER(joseSignature);
- assertValidDERSignature(derSignature, 32, true, false);
-
- //With S padding
- joseSignature = createJOSESignature(32, false, true);
- derSignature = algorithm256.JOSEToDER(joseSignature);
- assertValidDERSignature(derSignature, 32, false, true);
-
- //With both paddings
- joseSignature = createJOSESignature(32, true, true);
- derSignature = algorithm256.JOSEToDER(joseSignature);
- assertValidDERSignature(derSignature, 32, true, true);
- }
-
- @Test
- public void shouldDecodeECDSA256DER() throws Exception {
- ECDSAAlgorithm algorithm256 = (ECDSAAlgorithm) Algorithm.ECDSA256((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC"));
-
- //Without padding
- byte[] derSignature = createDERSignature(32, false, false);
- byte[] joseSignature = algorithm256.DERToJOSE(derSignature);
- assertValidJOSESignature(joseSignature, 32, false, false);
-
- //With R padding
- derSignature = createDERSignature(32, true, false);
- joseSignature = algorithm256.DERToJOSE(derSignature);
- assertValidJOSESignature(joseSignature, 32, true, false);
-
- //With S padding
- derSignature = createDERSignature(32, false, true);
- joseSignature = algorithm256.DERToJOSE(derSignature);
- assertValidJOSESignature(joseSignature, 32, false, true);
-
- //With both paddings
- derSignature = createDERSignature(32, true, true);
- joseSignature = algorithm256.DERToJOSE(derSignature);
- assertValidJOSESignature(joseSignature, 32, true, true);
- }
-
- @Test
- public void shouldDecodeECDSA384JOSE() throws Exception {
- ECDSAAlgorithm algorithm384 = (ECDSAAlgorithm) Algorithm.ECDSA384((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_384, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_384, "EC"));
-
- //Without padding
- byte[] joseSignature = createJOSESignature(48, false, false);
- byte[] derSignature = algorithm384.JOSEToDER(joseSignature);
- assertValidDERSignature(derSignature, 48, false, false);
-
- //With R padding
- joseSignature = createJOSESignature(48, true, false);
- derSignature = algorithm384.JOSEToDER(joseSignature);
- assertValidDERSignature(derSignature, 48, true, false);
-
- //With S padding
- joseSignature = createJOSESignature(48, false, true);
- derSignature = algorithm384.JOSEToDER(joseSignature);
- assertValidDERSignature(derSignature, 48, false, true);
-
- //With both paddings
- joseSignature = createJOSESignature(48, true, true);
- derSignature = algorithm384.JOSEToDER(joseSignature);
- assertValidDERSignature(derSignature, 48, true, true);
- }
-
- @Test
- public void shouldDecodeECDSA384DER() throws Exception {
- ECDSAAlgorithm algorithm384 = (ECDSAAlgorithm) Algorithm.ECDSA384((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_384, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_384, "EC"));
-
- //Without padding
- byte[] derSignature = createDERSignature(48, false, false);
- byte[] joseSignature = algorithm384.DERToJOSE(derSignature);
- assertValidJOSESignature(joseSignature, 48, false, false);
-
- //With R padding
- derSignature = createDERSignature(48, true, false);
- joseSignature = algorithm384.DERToJOSE(derSignature);
- assertValidJOSESignature(joseSignature, 48, true, false);
-
- //With S padding
- derSignature = createDERSignature(48, false, true);
- joseSignature = algorithm384.DERToJOSE(derSignature);
- assertValidJOSESignature(joseSignature, 48, false, true);
-
- //With both paddings
- derSignature = createDERSignature(48, true, true);
- joseSignature = algorithm384.DERToJOSE(derSignature);
- assertValidJOSESignature(joseSignature, 48, true, true);
- }
-
- @Test
- public void shouldDecodeECDSA512JOSE() throws Exception {
- ECDSAAlgorithm algorithm512 = (ECDSAAlgorithm) Algorithm.ECDSA512((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_512, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_512, "EC"));
-
- //Without padding
- byte[] joseSignature = createJOSESignature(66, false, false);
- byte[] derSignature = algorithm512.JOSEToDER(joseSignature);
- assertValidDERSignature(derSignature, 66, false, false);
-
- //With R padding
- joseSignature = createJOSESignature(66, true, false);
- derSignature = algorithm512.JOSEToDER(joseSignature);
- assertValidDERSignature(derSignature, 66, true, false);
-
- //With S padding
- joseSignature = createJOSESignature(66, false, true);
- derSignature = algorithm512.JOSEToDER(joseSignature);
- assertValidDERSignature(derSignature, 66, false, true);
-
- //With both paddings
- joseSignature = createJOSESignature(66, true, true);
- derSignature = algorithm512.JOSEToDER(joseSignature);
- assertValidDERSignature(derSignature, 66, true, true);
- }
-
- @Test
- public void shouldDecodeECDSA512DER() throws Exception {
- ECDSAAlgorithm algorithm512 = (ECDSAAlgorithm) Algorithm.ECDSA512((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_512, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_512, "EC"));
-
- //Without padding
- byte[] derSignature = createDERSignature(66, false, false);
- byte[] joseSignature = algorithm512.DERToJOSE(derSignature);
- assertValidJOSESignature(joseSignature, 66, false, false);
-
- //With R padding
- derSignature = createDERSignature(66, true, false);
- joseSignature = algorithm512.DERToJOSE(derSignature);
- assertValidJOSESignature(joseSignature, 66, true, false);
-
- //With S padding
- derSignature = createDERSignature(66, false, true);
- joseSignature = algorithm512.DERToJOSE(derSignature);
- assertValidJOSESignature(joseSignature, 66, false, true);
-
- //With both paddings
- derSignature = createDERSignature(66, true, true);
- joseSignature = algorithm512.DERToJOSE(derSignature);
- assertValidJOSESignature(joseSignature, 66, true, true);
- }
-
-
- //Test Helpers
- static void assertValidJOSESignature(byte[] joseSignature, int numberSize, boolean withRPadding, boolean withSPadding) {
- assertThat(joseSignature, is(Matchers.notNullValue()));
- assertThat(numberSize, is(IsIn.oneOf(32, 48, 66)));
-
- assertThat(joseSignature.length, is(numberSize * 2));
-
- byte[] rCopy = Arrays.copyOfRange(joseSignature, 0, numberSize);
- byte[] sCopy = Arrays.copyOfRange(joseSignature, numberSize, numberSize * 2);
-
- byte[] rNumber = new byte[numberSize];
- byte[] sNumber = new byte[numberSize];
- Arrays.fill(rNumber, (byte) 0x11);
- Arrays.fill(sNumber, (byte) 0x22);
- if (withRPadding) {
- rNumber[0] = (byte) 0;
- }
- if (withSPadding) {
- sNumber[0] = (byte) 0;
- }
- assertThat(Arrays.equals(rNumber, rCopy), is(true));
- assertThat(Arrays.equals(sNumber, sCopy), is(true));
- }
-
- static byte[] createDERSignature(int numberSize, boolean withRPadding, boolean withSPadding) {
- assertThat(numberSize, is(IsIn.oneOf(32, 48, 66)));
-
- int rLength = withRPadding ? numberSize - 1 : numberSize;
- int sLength = withSPadding ? numberSize - 1 : numberSize;
- int totalLength = 2 + (2 + rLength) + (2 + sLength);
-
- byte[] rNumber = new byte[rLength];
- byte[] sNumber = new byte[sLength];
- Arrays.fill(rNumber, (byte) 0x11);
- Arrays.fill(sNumber, (byte) 0x22);
-
- byte[] derSignature;
- int offset = 0;
- if (totalLength > 0x7f) {
- totalLength++;
- derSignature = new byte[totalLength];
- //Start sequence and sign
- derSignature[offset++] = (byte) 0x30;
- derSignature[offset++] = (byte) 0x81;
- } else {
- derSignature = new byte[totalLength];
- //Start sequence
- derSignature[offset++] = (byte) 0x30;
- }
-
- //Sequence length
- derSignature[offset++] = (byte) (totalLength - offset);
-
- //R number
- derSignature[offset++] = (byte) 0x02;
- derSignature[offset++] = (byte) rLength;
- System.arraycopy(rNumber, 0, derSignature, offset, rLength);
- offset += rLength;
-
- //S number
- derSignature[offset++] = (byte) 0x02;
- derSignature[offset++] = (byte) sLength;
- System.arraycopy(sNumber, 0, derSignature, offset, sLength);
-
- return derSignature;
- }
-
- static byte[] createJOSESignature(int numberSize, boolean withRPadding, boolean withSPadding) {
- assertThat(numberSize, is(IsIn.oneOf(32, 48, 66)));
-
- byte[] rNumber = new byte[numberSize];
- byte[] sNumber = new byte[numberSize];
- Arrays.fill(rNumber, (byte) 0x11);
- Arrays.fill(sNumber, (byte) 0x22);
- if (withRPadding) {
- rNumber[0] = (byte) 0;
- }
- if (withSPadding) {
- sNumber[0] = (byte) 0;
- }
- byte[] joseSignature = new byte[numberSize * 2];
- System.arraycopy(rNumber, 0, joseSignature, 0, numberSize);
- System.arraycopy(sNumber, 0, joseSignature, numberSize, numberSize);
- return joseSignature;
- }
-
- static void assertValidDERSignature(byte[] derSignature, int numberSize, boolean withRPadding, boolean withSPadding) {
- assertThat(derSignature, is(Matchers.notNullValue()));
- assertThat(numberSize, is(IsIn.oneOf(32, 48, 66)));
-
- int rLength = withRPadding ? numberSize - 1 : numberSize;
- int sLength = withSPadding ? numberSize - 1 : numberSize;
- int totalLength = 2 + (2 + rLength) + (2 + sLength);
- int offset = 0;
-
- //Start sequence
- assertThat(derSignature[offset++], is((byte) 0x30));
- if (totalLength > 0x7f) {
- //Add sign before sequence length
- totalLength++;
- assertThat(derSignature[offset++], is((byte) 0x81));
- }
- //Sequence length
- assertThat(derSignature[offset++], is((byte) (totalLength - offset)));
-
- //R number
- assertThat(derSignature[offset++], is((byte) 0x02));
- assertThat(derSignature[offset++], is((byte) rLength));
- byte[] rCopy = Arrays.copyOfRange(derSignature, offset, offset + rLength);
- offset += rLength;
-
- //S number
- assertThat(derSignature[offset++], is((byte) 0x02));
- assertThat(derSignature[offset++], is((byte) sLength));
- byte[] sCopy = Arrays.copyOfRange(derSignature, offset, offset + sLength);
-
-
- byte[] rNumber = new byte[rLength];
- byte[] sNumber = new byte[sLength];
- Arrays.fill(rNumber, (byte) 0x11);
- Arrays.fill(sNumber, (byte) 0x22);
- assertThat(Arrays.equals(rNumber, rCopy), is(true));
- assertThat(Arrays.equals(sNumber, sCopy), is(true));
- assertThat(derSignature.length, is(totalLength));
- }
-
- @Test
- public void shouldBeEqualSignatureMethodDecodeResults() throws Exception {
- // signatures are not deterministic in value, so instead of directly comparing the signatures,
- // check that both sign(..) methods can be used to create a jwt which can be
- // verified
- Algorithm algorithm = Algorithm.ECDSA256((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC"));
-
- String header = "eyJhbGciOiJFUzI1NiJ9";
- String payload = "eyJpc3MiOiJhdXRoMCJ9";
-
- byte[] headerBytes = header.getBytes(StandardCharsets.UTF_8);
- byte[] payloadBytes = payload.getBytes(StandardCharsets.UTF_8);
-
- ByteArrayOutputStream bout = new ByteArrayOutputStream();
- bout.write(headerBytes);
- bout.write('.');
- bout.write(payloadBytes);
-
- String jwtSignature1 = Base64.getUrlEncoder().withoutPadding().encodeToString(algorithm.sign(bout.toByteArray()));
- String jwt1 = String.format("%s.%s.%s", header, payload, jwtSignature1);
-
- algorithm.verify(JWT.decode(jwt1));
-
- String jwtSignature2 = Base64.getUrlEncoder().withoutPadding().encodeToString(algorithm.sign(headerBytes, payloadBytes));
- String jwt2 = String.format("%s.%s.%s", header, payload, jwtSignature2);
-
- algorithm.verify(JWT.decode(jwt2));
- }
-
- /**
- * Test deprecated signing method error handling.
- *
- * @see {@linkplain #shouldFailOnECDSA256SigningWhenProvidedPrivateKeyIsNull}
- * @throws Exception expected exception
- */
-
- @Test
- public void shouldFailOnECDSA256SigningWithDeprecatedMethodWhenProvidedPrivateKeyIsNull() {
- exception.expect(SignatureGenerationException.class);
- exception.expectMessage("The Token's Signature couldn't be generated when signing using the Algorithm: SHA256withECDSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Private Key is null.")));
-
- ECDSAKeyProvider provider = mock(ECDSAKeyProvider.class);
- when(provider.getPrivateKey()).thenReturn(null);
- Algorithm algorithm = Algorithm.ECDSA256(provider);
- algorithm.sign(new byte[0]);
- }
-
- @Test
- public void invalidECDSA256SignatureShouldFailTokenVerification() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectCause(isA(SignatureException.class));
-
- String jwtWithInvalidSig = "eyJhbGciOiJFUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiYWRtaW4iOnRydWUsImlhdCI6MTUxNjIzOTAyMn0._____wAAAAD__________7zm-q2nF56E87nKwvxjJVH_____AAAAAP__________vOb6racXnoTzucrC_GMlUQ";
-
- ECKey key256 = (ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC");
- ECKey key384 = (ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_384, "EC");
- ECKey key512 = (ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_512, "EC");
- JWTVerifier verifier256 = JWT.require(Algorithm.ECDSA256(key256)).build();
- JWTVerifier verifier384 = JWT.require(Algorithm.ECDSA256(key384)).build();
- JWTVerifier verifier512 = JWT.require(Algorithm.ECDSA256(key512)).build();
- verifier256.verify(jwtWithInvalidSig);
- verifier384.verify(jwtWithInvalidSig);
- verifier512.verify(jwtWithInvalidSig);
- }
-
- @Test
- public void emptyECDSA256SignatureShouldFailTokenVerification() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectCause(isA(SignatureException.class));
-
- String jwtWithInvalidSig = "eyJhbGciOiJFUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiYWRtaW4iOnRydWUsImlhdCI6MTUxNjIzOTAyMn0.AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA";
-
- ECKey key256 = (ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC");
- ECKey key384 = (ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_384, "EC");
- ECKey key512 = (ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_512, "EC");
- JWTVerifier verifier256 = JWT.require(Algorithm.ECDSA256(key256)).build();
- JWTVerifier verifier384 = JWT.require(Algorithm.ECDSA256(key384)).build();
- JWTVerifier verifier512 = JWT.require(Algorithm.ECDSA256(key512)).build();
- verifier256.verify(jwtWithInvalidSig);
- verifier384.verify(jwtWithInvalidSig);
- verifier512.verify(jwtWithInvalidSig);
- }
-
- @Test
- public void signatureWithAllZerosShouldFail() throws Exception {
- exception.expect(SignatureException.class);
- exception.expectMessage("Invalid signature format.");
-
- ECPublicKey pubKey = (ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC");
-
- ECDSAAlgorithm algorithm256 = (ECDSAAlgorithm) Algorithm.ECDSA256(pubKey, (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC"));
- byte[] signatureBytes = new byte[64];
- algorithm256.validateSignatureStructure(signatureBytes, pubKey);
- }
-
- @Test
- public void signatureWithRZeroShouldFail() throws Exception {
- exception.expect(SignatureException.class);
- exception.expectMessage("Invalid signature format.");
-
- ECPublicKey publicKey = (ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC");
- ECPrivateKey privateKey = (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC");
-
- String signedJwt = JWT.create().sign(Algorithm.ECDSA256(publicKey, privateKey));
-
- String[] chunks = signedJwt.split("\\.");
- byte[] signature = Base64.getUrlDecoder().decode(chunks[2]);
-
- byte[] sigWithBlankR = new byte[signature.length];
- for (int i = 0; i < signature.length; i++) {
- if (i < signature.length / 2) {
- sigWithBlankR[i] = 0;
- } else {
- sigWithBlankR[i] = signature[i];
- }
- }
-
- ECDSAAlgorithm algorithm256 = (ECDSAAlgorithm) Algorithm.ECDSA256(publicKey, privateKey);
- algorithm256.validateSignatureStructure(sigWithBlankR, publicKey);
- }
-
- @Test
- public void signatureWithSZeroShouldFail() throws Exception {
- exception.expect(SignatureException.class);
- exception.expectMessage("Invalid signature format.");
-
- ECPublicKey publicKey = (ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC");
- ECPrivateKey privateKey = (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC");
-
- String signedJwt = JWT.create().sign(Algorithm.ECDSA256(publicKey, privateKey));
-
- String[] chunks = signedJwt.split("\\.");
- byte[] signature = Base64.getUrlDecoder().decode(chunks[2]);
-
- byte[] sigWithBlankS = new byte[signature.length];
- for (int i = 0; i < signature.length; i++) {
- if (i < signature.length / 2) {
- sigWithBlankS[i] = signature[i];
- } else {
- sigWithBlankS[i] = 0;
- }
- }
-
- ECDSAAlgorithm algorithm256 = (ECDSAAlgorithm) Algorithm.ECDSA256(publicKey, privateKey);
- algorithm256.validateSignatureStructure(sigWithBlankS, publicKey);
- }
-
- @Test
- public void signatureWithRValueNotLessThanOrderShouldFail() throws Exception {
- exception.expect(SignatureException.class);
- exception.expectMessage("Invalid signature format.");
-
- ECPublicKey publicKey = (ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC");
- ECPrivateKey privateKey = (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC");
-
- String signedJwt = JWT.create().sign(Algorithm.ECDSA256(publicKey, privateKey));
- String jwtWithInvalidSig = signedJwt.substring(0, signedJwt.lastIndexOf('.') + 1) + "_____wAAAAD__________7zm-q2nF56E87nKwvxjJVH_____AAAAAP__________vOb6racXnoTzucrC_GMlUQ";
-
- String[] chunks = jwtWithInvalidSig.split("\\.");
- byte[] invalidSignature = Base64.getUrlDecoder().decode(chunks[2]);
-
- ECDSAAlgorithm algorithm256 = (ECDSAAlgorithm) Algorithm.ECDSA256(publicKey, privateKey);
- algorithm256.validateSignatureStructure(invalidSignature, publicKey);
- }
-
- @Test
- public void signatureWithSValueNotLessThanOrderShouldFail() throws Exception {
- exception.expect(SignatureException.class);
- exception.expectMessage("Invalid signature format.");
-
- ECPublicKey publicKey = (ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC");
- ECPrivateKey privateKey = (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC");
-
- String signedJwt = JWT.create().sign(Algorithm.ECDSA256(publicKey, privateKey));
- String jwtWithInvalidSig = signedJwt.substring(0, signedJwt.lastIndexOf('.') + 1) + "_____wAAAAD__________7zm-q2nF56E87nKwvxjJVH_____AAAAAP__________vOb6racXnoTzucrC_GMlUQ";
-
- String[] chunks = jwtWithInvalidSig.split("\\.");
- byte[] invalidSignature = Base64.getUrlDecoder().decode(chunks[2]);
- invalidSignature[0] = Byte.MAX_VALUE;
-
- ECDSAAlgorithm algorithm256 = (ECDSAAlgorithm) Algorithm.ECDSA256(publicKey, privateKey);
- algorithm256.validateSignatureStructure(invalidSignature, publicKey);
- }
-}
\ No newline at end of file
diff --git a/lib/src/test/java/com/auth0/jwt/algorithms/ECDSABouncyCastleProviderTests.java b/lib/src/test/java/com/auth0/jwt/algorithms/ECDSABouncyCastleProviderTests.java
deleted file mode 100644
index 3925eef3..00000000
--- a/lib/src/test/java/com/auth0/jwt/algorithms/ECDSABouncyCastleProviderTests.java
+++ /dev/null
@@ -1,1037 +0,0 @@
-package com.auth0.jwt.algorithms;
-
-import com.auth0.jwt.JWT;
-import com.auth0.jwt.exceptions.SignatureGenerationException;
-import com.auth0.jwt.exceptions.SignatureVerificationException;
-import com.auth0.jwt.interfaces.ECDSAKeyProvider;
-import org.bouncycastle.jce.provider.BouncyCastleProvider;
-import org.junit.AfterClass;
-import org.junit.BeforeClass;
-import org.junit.Rule;
-import org.junit.Test;
-import org.junit.rules.ExpectedException;
-
-import java.math.BigInteger;
-import java.nio.charset.StandardCharsets;
-import java.security.*;
-import java.security.interfaces.ECKey;
-import java.security.interfaces.ECPrivateKey;
-import java.security.interfaces.ECPublicKey;
-import java.security.spec.ECParameterSpec;
-import java.util.Arrays;
-import java.util.Base64;
-
-import static com.auth0.jwt.PemUtils.readPrivateKeyFromFile;
-import static com.auth0.jwt.PemUtils.readPublicKeyFromFile;
-import static com.auth0.jwt.algorithms.CryptoTestHelper.asJWT;
-import static com.auth0.jwt.algorithms.CryptoTestHelper.assertSignaturePresent;
-import static com.auth0.jwt.algorithms.ECDSAAlgorithmTest.*;
-import static org.hamcrest.CoreMatchers.is;
-import static org.hamcrest.Matchers.*;
-import static org.hamcrest.MatcherAssert.assertThat;
-import static org.junit.internal.matchers.ThrowableMessageMatcher.hasMessage;
-import static org.mockito.ArgumentMatchers.any;
-import static org.mockito.ArgumentMatchers.anyString;
-import static org.mockito.Mockito.mock;
-import static org.mockito.Mockito.when;
-
-public class ECDSABouncyCastleProviderTests {
-
- private static final String PRIVATE_KEY_FILE_256 = "src/test/resources/ec256-key-private.pem";
- private static final String PUBLIC_KEY_FILE_256 = "src/test/resources/ec256-key-public.pem";
- private static final String INVALID_PUBLIC_KEY_FILE_256 = "src/test/resources/ec256-key-public-invalid.pem";
-
- private static final String PRIVATE_KEY_FILE_384 = "src/test/resources/ec384-key-private.pem";
- private static final String PUBLIC_KEY_FILE_384 = "src/test/resources/ec384-key-public.pem";
- private static final String INVALID_PUBLIC_KEY_FILE_384 = "src/test/resources/ec384-key-public-invalid.pem";
-
- private static final String PRIVATE_KEY_FILE_512 = "src/test/resources/ec512-key-private.pem";
- private static final String PUBLIC_KEY_FILE_512 = "src/test/resources/ec512-key-public.pem";
- private static final String INVALID_PUBLIC_KEY_FILE_512 = "src/test/resources/ec512-key-public-invalid.pem";
-
- private static final String ES256K_JWT = "eyJraWQiOiJteS1rZXktaWQiLCJ0eXAiOiJKV1QiLCJhbGciOiJFUzI1NksifQ.e30.2ggPsc4xwQhYcgJueo3uQ14MpaVJ3AbEE8UE-wA9fc8SMibeW54gjZbikL-JBHqhEwc22Cp8DNOtadXsM81RGQ";
-
- @Rule
- public ExpectedException exception = ExpectedException.none();
- private static final Provider bcProvider = new BouncyCastleProvider();
-
- //JOSE Signatures obtained using Node 'jwa' lib: https://github.com/brianloveswords/node-jwa
- //DER Signatures obtained from source JOSE signature using 'ecdsa-sig-formatter' lib: https://github.com/Brightspace/node-ecdsa-sig-formatter
-
-
- //These tests add and use the BouncyCastle SecurityProvider to handle ECDSA algorithms
-
- @BeforeClass
- public static void setUp() {
- //Set BC as the preferred bcProvider
- Security.insertProviderAt(bcProvider, 1);
- }
-
- @AfterClass
- public static void tearDown() {
- Security.removeProvider(bcProvider.getName());
- }
-
- @Test
- public void shouldPreferBouncyCastleProvider() {
- assertThat(Security.getProviders()[0], is(equalTo(bcProvider)));
- }
-
- @Test
- public void shouldPassECDSA256VerificationWithJOSESignature() throws Exception {
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9.4iVk3-Y0v4RT4_9IaQlp-8dZ_4fsTzIylgrPTDLrEvTHBTyVS3tgPbr2_IZfLETtiKRqCg0aQ5sh9eIsTTwB1g";
- ECKey key = (ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC");
- Algorithm algorithm = Algorithm.ECDSA256(key);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldThrowOnECDSA256VerificationWithDERSignature() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA256withECDSA");
- exception.expectCause(isA(SignatureException.class));
- exception.expectCause(hasMessage(is("Invalid JOSE signature format.")));
-
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9.MEYCIQDiJWTf5jShFPj0hpCWn7x1nhxPMjKWCs9MMusS9AIhAMcFPJVLe2A9uvb8hl8sRO2IpGoKDRpDmyH14ixNPAHW";
- ECKey key = (ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC");
- Algorithm algorithm = Algorithm.ECDSA256(key);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldPassECDSA256VerificationWithJOSESignatureWithBothKeys() throws Exception {
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9.4iVk3-Y0v4RT4_9IaQlp-8dZ_4fsTzIylgrPTDLrEvTHBTyVS3tgPbr2_IZfLETtiKRqCg0aQ5sh9eIsTTwB1g";
- Algorithm algorithm = Algorithm.ECDSA256((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldThrowOnECDSA256VerificationWithDERSignatureWithBothKeys() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA256withECDSA");
- exception.expectCause(isA(SignatureException.class));
- exception.expectCause(hasMessage(is("Invalid JOSE signature format.")));
-
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9.MEYCIQDiJWTf5jShFPj0hpCWn7x1nhxPMjKWCs9MMusS9AIhAMcFPJVLe2A9uvb8hl8sRO2IpGoKDRpDmyH14ixNPAHW";
- Algorithm algorithm = Algorithm.ECDSA256((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldPassECDSA256VerificationWithProvidedPublicKey() throws Exception {
- ECDSAKeyProvider provider = mock(ECDSAKeyProvider.class);
- PublicKey publicKey = readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC");
- when(provider.getPublicKeyById("my-key-id")).thenReturn((ECPublicKey) publicKey);
- String jwt = "eyJhbGciOiJFUzI1NiIsImtpZCI6Im15LWtleS1pZCJ9.eyJpc3MiOiJhdXRoMCJ9.D_oU4CB0ZEsxHOjcWnmS3ZJvlTzm6WcGFx-HASxnvcB2Xu2WjI-axqXH9xKq45aPBDs330JpRhJmqBSc2K8MXQ";
- Algorithm algorithm = Algorithm.ECDSA256(provider);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA256VerificationWhenProvidedPublicKeyIsNull() {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA256withECDSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Public Key is null.")));
- ECDSAKeyProvider provider = mock(ECDSAKeyProvider.class);
- when(provider.getPublicKeyById("my-key-id")).thenReturn(null);
- String jwt = "eyJhbGciOiJFUzI1NiIsImtpZCI6Im15LWtleS1pZCJ9.eyJpc3MiOiJhdXRoMCJ9.D_oU4CB0ZEsxHOjcWnmS3ZJvlTzm6WcGFx-HASxnvcB2Xu2WjI-axqXH9xKq45aPBDs330JpRhJmqBSc2K8MXQ";
- Algorithm algorithm = Algorithm.ECDSA256(provider);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA256VerificationWithInvalidPublicKey() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA256withECDSA");
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9.W9qfN1b80B9hnMo49WL8THrOsf1vEjOhapeFemPMGySzxTcgfyudS5esgeBTO908X5SLdAr5jMwPUPBs9b6nNg";
- Algorithm algorithm = Algorithm.ECDSA256((ECKey) readPublicKeyFromFile(INVALID_PUBLIC_KEY_FILE_256, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA256VerificationWhenUsingPrivateKey() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA256withECDSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Public Key is null.")));
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9.W9qfN1b80B9hnMo49WL8THrOsf1vEjOhapeFemPMGySzxTcgfyudS5esgeBTO908X5SLdAr5jMwPUPBs9b6nNg";
- Algorithm algorithm = Algorithm.ECDSA256((ECKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA256VerificationOnInvalidJOSESignatureLength() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA256withECDSA");
- exception.expectCause(isA(SignatureException.class));
- exception.expectCause(hasMessage(is("Invalid JOSE signature format.")));
-
- byte[] bytes = new byte[63];
- new SecureRandom().nextBytes(bytes);
- String signature = Base64.getUrlEncoder().withoutPadding().encodeToString(bytes);
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9." + signature;
- Algorithm algorithm = Algorithm.ECDSA256((ECKey) readPublicKeyFromFile(INVALID_PUBLIC_KEY_FILE_256, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA256VerificationOnInvalidJOSESignature() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA256withECDSA");
-
- byte[] bytes = new byte[64];
- new SecureRandom().nextBytes(bytes);
- String signature = Base64.getUrlEncoder().withoutPadding().encodeToString(bytes);
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9." + signature;
- Algorithm algorithm = Algorithm.ECDSA256((ECKey) readPublicKeyFromFile(INVALID_PUBLIC_KEY_FILE_256, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA256VerificationOnInvalidDERSignature() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA256withECDSA");
-
- byte[] bytes = new byte[64];
- bytes[0] = 0x30;
- new SecureRandom().nextBytes(bytes);
- String signature = Base64.getUrlEncoder().withoutPadding().encodeToString(bytes);
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9." + signature;
- Algorithm algorithm = Algorithm.ECDSA256((ECKey) readPublicKeyFromFile(INVALID_PUBLIC_KEY_FILE_256, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldPassECDSA384VerificationWithJOSESignature() throws Exception {
- String jwt = "eyJhbGciOiJFUzM4NCJ9.eyJpc3MiOiJhdXRoMCJ9.50UU5VKNdF1wfykY8jQBKpvuHZoe6IZBJm5NvoB8bR-hnRg6ti-CHbmvoRtlLfnHfwITa_8cJMy6TenMC2g63GQHytc8rYoXqbwtS4R0Ko_AXbLFUmfxnGnMC6v4MS_z";
- ECKey key = (ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_384, "EC");
- Algorithm algorithm = Algorithm.ECDSA384(key);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldThrowOnECDSA384VerificationWithDERSignature() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA384withECDSA");
- exception.expectCause(isA(SignatureException.class));
- exception.expectCause(hasMessage(is("Invalid JOSE signature format.")));
-
- String jwt = "eyJhbGciOiJFUzM4NCJ9.eyJpc3MiOiJhdXRoMCJ9.MGUCMQDnRRTlUo10XXBKRjyNAEqm4dmh7ohkEmbk2gHxtH6GdGDq2L4IduahG2UtccCMH8CE2vHCTMuk3pzAtoOtxkB8rXPK2KF6m8LUuEdCqPwF2yxVJn8ZxpzAurDEv8w";
- ECKey key = (ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_384, "EC");
- Algorithm algorithm = Algorithm.ECDSA384(key);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldPassECDSA384VerificationWithJOSESignatureWithBothKeys() throws Exception {
- String jwt = "eyJhbGciOiJFUzM4NCJ9.eyJpc3MiOiJhdXRoMCJ9.50UU5VKNdF1wfykY8jQBKpvuHZoe6IZBJm5NvoB8bR-hnRg6ti-CHbmvoRtlLfnHfwITa_8cJMy6TenMC2g63GQHytc8rYoXqbwtS4R0Ko_AXbLFUmfxnGnMC6v4MS_z";
- Algorithm algorithm = Algorithm.ECDSA384((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_384, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_384, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldThrowOnECDSA384VerificationWithDERSignatureWithBothKeys() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA384withECDSA");
- exception.expectCause(isA(SignatureException.class));
- exception.expectCause(hasMessage(is("Invalid JOSE signature format.")));
-
- String jwt = "eyJhbGciOiJFUzM4NCJ9.eyJpc3MiOiJhdXRoMCJ9.MGUCMQDnRRTlUo10XXBKRjyNAEqm4dmh7ohkEmbk2gHxtH6GdGDq2L4IduahG2UtccCMH8CE2vHCTMuk3pzAtoOtxkB8rXPK2KF6m8LUuEdCqPwF2yxVJn8ZxpzAurDEv8w";
- Algorithm algorithm = Algorithm.ECDSA384((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_384, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_384, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldPassECDSA384VerificationWithProvidedPublicKey() throws Exception {
- ECDSAKeyProvider provider = mock(ECDSAKeyProvider.class);
- PublicKey publicKey = readPublicKeyFromFile(PUBLIC_KEY_FILE_384, "EC");
- when(provider.getPublicKeyById("my-key-id")).thenReturn((ECPublicKey) publicKey);
- String jwt = "eyJhbGciOiJFUzM4NCIsImtpZCI6Im15LWtleS1pZCJ9.eyJpc3MiOiJhdXRoMCJ9.9kjGuFTPx3ylfpqL0eY9H7TGmPepjQOBKI8UPoEvby6N7dDLF5HxLohosNxxFymNT7LzpeSgOPAB0wJEwG2Nl2ukgdUOpZOf492wog_i5ZcZmAykd3g1QH7onrzd69GU";
- Algorithm algorithm = Algorithm.ECDSA384(provider);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA384VerificationWhenProvidedPublicKeyIsNull() {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA384withECDSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Public Key is null.")));
- ECDSAKeyProvider provider = mock(ECDSAKeyProvider.class);
- when(provider.getPublicKeyById("my-key-id")).thenReturn(null);
- String jwt = "eyJhbGciOiJFUzM4NCIsImtpZCI6Im15LWtleS1pZCJ9.eyJpc3MiOiJhdXRoMCJ9.9kjGuFTPx3ylfpqL0eY9H7TGmPepjQOBKI8UPoEvby6N7dDLF5HxLohosNxxFymNT7LzpeSgOPAB0wJEwG2Nl2ukgdUOpZOf492wog_i5ZcZmAykd3g1QH7onrzd69GU";
- Algorithm algorithm = Algorithm.ECDSA384(provider);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA384VerificationWithInvalidPublicKey() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA384withECDSA");
- String jwt = "eyJhbGciOiJFUzM4NCJ9.eyJpc3MiOiJhdXRoMCJ9._k5h1KyO-NE0R2_HAw0-XEc0bGT5atv29SxHhOGC9JDqUHeUdptfCK_ljQ01nLVt2OQWT2SwGs-TuyHDFmhPmPGFZ9wboxvq_ieopmYqhQilNAu-WF-frioiRz9733fU";
- Algorithm algorithm = Algorithm.ECDSA384((ECKey) readPublicKeyFromFile(INVALID_PUBLIC_KEY_FILE_384, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA384VerificationWhenUsingPrivateKey() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA384withECDSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Public Key is null.")));
- String jwt = "eyJhbGciOiJFUzM4NCJ9.eyJpc3MiOiJhdXRoMCJ9._k5h1KyO-NE0R2_HAw0-XEc0bGT5atv29SxHhOGC9JDqUHeUdptfCK_ljQ01nLVt2OQWT2SwGs-TuyHDFmhPmPGFZ9wboxvq_ieopmYqhQilNAu-WF-frioiRz9733fU";
- Algorithm algorithm = Algorithm.ECDSA384((ECKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_384, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA384VerificationOnInvalidJOSESignatureLength() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA384withECDSA");
- exception.expectCause(isA(SignatureException.class));
- exception.expectCause(hasMessage(is("Invalid JOSE signature format.")));
-
- byte[] bytes = new byte[95];
- new SecureRandom().nextBytes(bytes);
- String signature = Base64.getUrlEncoder().withoutPadding().encodeToString(bytes);
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9." + signature;
- Algorithm algorithm = Algorithm.ECDSA384((ECKey) readPublicKeyFromFile(INVALID_PUBLIC_KEY_FILE_384, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA384VerificationOnInvalidJOSESignature() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA384withECDSA");
-
- byte[] bytes = new byte[96];
- new SecureRandom().nextBytes(bytes);
- String signature = Base64.getUrlEncoder().withoutPadding().encodeToString(bytes);
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9." + signature;
- Algorithm algorithm = Algorithm.ECDSA384((ECKey) readPublicKeyFromFile(INVALID_PUBLIC_KEY_FILE_384, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA384VerificationOnInvalidDERSignature() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA384withECDSA");
-
- byte[] bytes = new byte[96];
- new SecureRandom().nextBytes(bytes);
- bytes[0] = 0x30;
- String signature = Base64.getUrlEncoder().withoutPadding().encodeToString(bytes);
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9." + signature;
- Algorithm algorithm = Algorithm.ECDSA384((ECKey) readPublicKeyFromFile(INVALID_PUBLIC_KEY_FILE_384, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldPassECDSA512VerificationWithJOSESignature() throws Exception {
- String jwt = "eyJhbGciOiJFUzUxMiJ9.eyJpc3MiOiJhdXRoMCJ9.AeCJPDIsSHhwRSGZCY6rspi8zekOw0K9qYMNridP1Fu9uhrA1QrG-EUxXlE06yvmh2R7Rz0aE7kxBwrnq8L8aOBCAYAsqhzPeUvyp8fXjjgs0Eto5I0mndE2QHlgcMSFASyjHbU8wD2Rq7ZNzGQ5b2MZfpv030WGUajT-aZYWFUJHVg2";
- ECKey key = (ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_512, "EC");
- Algorithm algorithm = Algorithm.ECDSA512(key);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldThrowOnECDSA512VerificationWithDERSignature() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA512withECDSA");
- exception.expectCause(isA(SignatureException.class));
- exception.expectCause(hasMessage(is("Invalid JOSE signature format.")));
-
- String jwt = "eyJhbGciOiJFUzUxMiJ9.eyJpc3MiOiJhdXRoMCJ9.MIGIAkIB4Ik8MixIeHBFIZkJjquymLzN6Q7DQr2pgw2uJ0UW726GsDVCsb4RTFeUTTrKaHZHtHPRoTuTEHCuerwvxo4EICQgGALKocz3lL8qfH1444LNBLaOSNJp3RNkB5YHDEhQEsox21PMA9kau2TcxkOW9jGX6b9N9FhlGo0mmWFhVCR1YNg";
- ECKey key = (ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_512, "EC");
- Algorithm algorithm = Algorithm.ECDSA512(key);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldPassECDSA512VerificationWithJOSESignatureWithBothKeys() throws Exception {
- String jwt = "eyJhbGciOiJFUzUxMiJ9.eyJpc3MiOiJhdXRoMCJ9.AeCJPDIsSHhwRSGZCY6rspi8zekOw0K9qYMNridP1Fu9uhrA1QrG-EUxXlE06yvmh2R7Rz0aE7kxBwrnq8L8aOBCAYAsqhzPeUvyp8fXjjgs0Eto5I0mndE2QHlgcMSFASyjHbU8wD2Rq7ZNzGQ5b2MZfpv030WGUajT-aZYWFUJHVg2";
- Algorithm algorithm = Algorithm.ECDSA512((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_512, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_512, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldThrowECDSA512VerificationWithDERSignatureWithBothKeys() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA512withECDSA");
- exception.expectCause(isA(SignatureException.class));
- exception.expectCause(hasMessage(is("Invalid JOSE signature format.")));
-
- String jwt = "eyJhbGciOiJFUzUxMiJ9.eyJpc3MiOiJhdXRoMCJ9.MIGIAkIB4Ik8MixIeHBFIZkJjquymLzN6Q7DQr2pgw2uJ0UW726GsDVCsb4RTFeUTTrKaHZHtHPRoTuTEHCuerwvxo4EICQgGALKocz3lL8qfH1444LNBLaOSNJp3RNkB5YHDEhQEsox21PMA9kau2TcxkOW9jGX6b9N9FhlGo0mmWFhVCR1YNg";
- Algorithm algorithm = Algorithm.ECDSA512((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_512, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_512, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldPassECDSA512VerificationWithProvidedPublicKey() throws Exception {
- ECDSAKeyProvider provider = mock(ECDSAKeyProvider.class);
- PublicKey publicKey = readPublicKeyFromFile(PUBLIC_KEY_FILE_512, "EC");
- when(provider.getPublicKeyById("my-key-id")).thenReturn((ECPublicKey) publicKey);
- String jwt = "eyJhbGciOiJFUzUxMiIsImtpZCI6Im15LWtleS1pZCJ9.eyJpc3MiOiJhdXRoMCJ9.AGxEwbsYa2bQ7Y7DAcTQnVD8PmLSlhJ20jg2OfdyPnqdXI8SgBaG6lGciq3_pofFhs1HEoFoJ33Jcluha24oMHIvAfwu8qbv_Wq3L2eI9Q0L0p6ul8Pd_BS8adRa2PgLc36xXGcRc7ID5YH-CYaQfsTp5YIaF0Po3h0QyCoQ6ZiYQkqm";
- Algorithm algorithm = Algorithm.ECDSA512(provider);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA512VerificationWhenProvidedPublicKeyIsNull() {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA512withECDSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Public Key is null.")));
- ECDSAKeyProvider provider = mock(ECDSAKeyProvider.class);
- when(provider.getPublicKeyById("my-key-id")).thenReturn(null);
- String jwt = "eyJhbGciOiJFUzUxMiIsImtpZCI6Im15LWtleS1pZCJ9.eyJpc3MiOiJhdXRoMCJ9.AGxEwbsYa2bQ7Y7DAcTQnVD8PmLSlhJ20jg2OfdyPnqdXI8SgBaG6lGciq3_pofFhs1HEoFoJ33Jcluha24oMHIvAfwu8qbv_Wq3L2eI9Q0L0p6ul8Pd_BS8adRa2PgLc36xXGcRc7ID5YH-CYaQfsTp5YIaF0Po3h0QyCoQ6ZiYQkqm";
- Algorithm algorithm = Algorithm.ECDSA512(provider);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA512VerificationWithInvalidPublicKey() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA512withECDSA");
- String jwt = "eyJhbGciOiJFUzUxMiJ9.eyJpc3MiOiJhdXRoMCJ9.AZgdopFFsN0amCSs2kOucXdpylD31DEm5ChK1PG0_gq5Mf47MrvVph8zHSVuvcrXzcE1U3VxeCg89mYW1H33Y-8iAF0QFkdfTUQIWKNObH543WNMYYssv3OtOj0znPv8atDbaF8DMYAtcT1qdmaSJRhx-egRE9HGZkinPh9CfLLLt58X";
- Algorithm algorithm = Algorithm.ECDSA512((ECKey) readPublicKeyFromFile(INVALID_PUBLIC_KEY_FILE_512, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA512VerificationWhenUsingPrivateKey() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA512withECDSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Public Key is null.")));
- String jwt = "eyJhbGciOiJFUzUxMiJ9.eyJpc3MiOiJhdXRoMCJ9.AZgdopFFsN0amCSs2kOucXdpylD31DEm5ChK1PG0_gq5Mf47MrvVph8zHSVuvcrXzcE1U3VxeCg89mYW1H33Y-8iAF0QFkdfTUQIWKNObH543WNMYYssv3OtOj0znPv8atDbaF8DMYAtcT1qdmaSJRhx-egRE9HGZkinPh9CfLLLt58X";
- Algorithm algorithm = Algorithm.ECDSA512((ECKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_512, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA512VerificationOnInvalidJOSESignatureLength() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA512withECDSA");
- exception.expectCause(isA(SignatureException.class));
- exception.expectCause(hasMessage(is("Invalid JOSE signature format.")));
-
- byte[] bytes = new byte[131];
- new SecureRandom().nextBytes(bytes);
- String signature = Base64.getUrlEncoder().withoutPadding().encodeToString(bytes);
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9." + signature;
- Algorithm algorithm = Algorithm.ECDSA512((ECKey) readPublicKeyFromFile(INVALID_PUBLIC_KEY_FILE_512, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA512VerificationOnInvalidJOSESignature() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA512withECDSA");
-
- byte[] bytes = new byte[132];
- new SecureRandom().nextBytes(bytes);
- String signature = Base64.getUrlEncoder().withoutPadding().encodeToString(bytes);
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9." + signature;
- Algorithm algorithm = Algorithm.ECDSA512((ECKey) readPublicKeyFromFile(INVALID_PUBLIC_KEY_FILE_512, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailECDSA512VerificationOnInvalidDERSignature() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA512withECDSA");
-
- byte[] bytes = new byte[132];
- new SecureRandom().nextBytes(bytes);
- bytes[0] = 0x30;
- String signature = Base64.getUrlEncoder().withoutPadding().encodeToString(bytes);
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9." + signature;
- Algorithm algorithm = Algorithm.ECDSA512((ECKey) readPublicKeyFromFile(INVALID_PUBLIC_KEY_FILE_512, "EC"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailJOSEToDERConversionOnInvalidJOSESignatureLength() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA256withECDSA");
- exception.expectCause(isA(SignatureException.class));
- exception.expectCause(hasMessage(is("Invalid JOSE signature format.")));
-
- byte[] bytes = new byte[256];
- new SecureRandom().nextBytes(bytes);
- String signature = Base64.getUrlEncoder().withoutPadding().encodeToString(bytes);
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9." + signature;
-
- ECPublicKey publicKey = (ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC");
- ECPrivateKey privateKey = mock(ECPrivateKey.class);
- ECDSAKeyProvider provider = ECDSAAlgorithm.providerForKeys(publicKey, privateKey);
- Algorithm algorithm = new ECDSAAlgorithm("ES256", "SHA256withECDSA", 128, provider);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldThrowOnVerifyWhenSignatureAlgorithmDoesNotExists() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: some-alg");
- exception.expectCause(isA(NoSuchAlgorithmException.class));
-
- CryptoHelper crypto = mock(CryptoHelper.class);
- when(crypto.verifySignatureFor(anyString(), any(PublicKey.class), any(String.class), any(String.class), any(byte[].class)))
- .thenThrow(NoSuchAlgorithmException.class);
-
- ECPublicKey publicKey = mock(ECPublicKey.class);
- when(publicKey.getParams()).thenReturn(mock(ECParameterSpec.class));
- byte[] a = new byte[64];
- Arrays.fill(a, Byte.MAX_VALUE);
- when(publicKey.getParams().getOrder()).thenReturn(new BigInteger(a));
- ECPrivateKey privateKey = mock(ECPrivateKey.class);
- ECDSAKeyProvider provider = ECDSAAlgorithm.providerForKeys(publicKey, privateKey);
- Algorithm algorithm = new ECDSAAlgorithm(crypto, "some-alg", "some-algorithm", 32, provider);
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9.4iVk3-Y0v4RT4_9IaQlp-8dZ_4fsTzIylgrPTDLrEvTHBTyVS3tgPbr2_IZfLETtiKRqCg0aQ5sh9eIsTTwB1g";
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldThrowOnVerifyWhenThePublicKeyIsInvalid() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: some-alg");
- exception.expectCause(isA(InvalidKeyException.class));
-
- CryptoHelper crypto = mock(CryptoHelper.class);
- when(crypto.verifySignatureFor(anyString(), any(PublicKey.class), any(String.class), any(String.class), any(byte[].class)))
- .thenThrow(InvalidKeyException.class);
-
- ECPublicKey publicKey = mock(ECPublicKey.class);
- when(publicKey.getParams()).thenReturn(mock(ECParameterSpec.class));
- byte[] a = new byte[64];
- Arrays.fill(a, Byte.MAX_VALUE);
- when(publicKey.getParams().getOrder()).thenReturn(new BigInteger(a));
- ECPrivateKey privateKey = mock(ECPrivateKey.class);
- ECDSAKeyProvider provider = ECDSAAlgorithm.providerForKeys(publicKey, privateKey);
- Algorithm algorithm = new ECDSAAlgorithm(crypto, "some-alg", "some-algorithm", 32, provider);
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9.4iVk3-Y0v4RT4_9IaQlp-8dZ_4fsTzIylgrPTDLrEvTHBTyVS3tgPbr2_IZfLETtiKRqCg0aQ5sh9eIsTTwB1g";
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldThrowOnVerifyWhenTheSignatureIsNotPrepared() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: some-alg");
- exception.expectCause(isA(SignatureException.class));
-
- CryptoHelper crypto = mock(CryptoHelper.class);
- when(crypto.verifySignatureFor(anyString(), any(PublicKey.class), any(String.class), any(String.class), any(byte[].class)))
- .thenThrow(SignatureException.class);
-
- ECPublicKey publicKey = mock(ECPublicKey.class);
- when(publicKey.getParams()).thenReturn(mock(ECParameterSpec.class));
- byte[] a = new byte[64];
- Arrays.fill(a, Byte.MAX_VALUE);
- when(publicKey.getParams().getOrder()).thenReturn(new BigInteger(a));
- ECPrivateKey privateKey = mock(ECPrivateKey.class);
- ECDSAKeyProvider provider = ECDSAAlgorithm.providerForKeys(publicKey, privateKey);
- Algorithm algorithm = new ECDSAAlgorithm(crypto, "some-alg", "some-algorithm", 32, provider);
- String jwt = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9.4iVk3-Y0v4RT4_9IaQlp-8dZ_4fsTzIylgrPTDLrEvTHBTyVS3tgPbr2_IZfLETtiKRqCg0aQ5sh9eIsTTwB1g";
- algorithm.verify(JWT.decode(jwt));
- }
-
- //Sign
- private static final String ES256Header = "eyJhbGciOiJFUzI1NiJ9";
- private static final String ES384Header = "eyJhbGciOiJFUzM4NCJ9";
- private static final String ES512Header = "eyJhbGciOiJFUzUxMiJ9";
- private static final String auth0IssPayload = "eyJpc3MiOiJhdXRoMCJ9";
-
- @Test
- public void shouldDoECDSA256Signing() throws Exception {
- Algorithm algorithmSign = Algorithm.ECDSA256((ECKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC"));
- Algorithm algorithmVerify = Algorithm.ECDSA256((ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC"));
- String jwt = asJWT(algorithmSign, ES256Header, auth0IssPayload);
-
- assertSignaturePresent(jwt);
- algorithmVerify.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldDoECDSA256SigningWithBothKeys() throws Exception {
- Algorithm algorithm = Algorithm.ECDSA256((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC"));
- String jwt = asJWT(algorithm, ES256Header, auth0IssPayload);
-
- assertSignaturePresent(jwt);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldDoECDSA256SigningWithProvidedPrivateKey() throws Exception {
- ECDSAKeyProvider provider = mock(ECDSAKeyProvider.class);
- PrivateKey privateKey = readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC");
- PublicKey publicKey = readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC");
- when(provider.getPrivateKey()).thenReturn((ECPrivateKey) privateKey);
- when(provider.getPublicKeyById(null)).thenReturn((ECPublicKey) publicKey);
- Algorithm algorithm = Algorithm.ECDSA256(provider);
-
- String jwt = asJWT(algorithm, ES256Header, auth0IssPayload);
-
- assertSignaturePresent(jwt);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailOnECDSA256SigningWhenProvidedPrivateKeyIsNull() {
- exception.expect(SignatureGenerationException.class);
- exception.expectMessage("The Token's Signature couldn't be generated when signing using the Algorithm: SHA256withECDSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Private Key is null.")));
-
- ECDSAKeyProvider provider = mock(ECDSAKeyProvider.class);
- when(provider.getPrivateKey()).thenReturn(null);
- Algorithm algorithm = Algorithm.ECDSA256(provider);
- algorithm.sign(new byte[0], new byte[0]);
- }
-
- @Test
- public void shouldFailOnECDSA256SigningWhenUsingPublicKey() throws Exception {
- exception.expect(SignatureGenerationException.class);
- exception.expectMessage("The Token's Signature couldn't be generated when signing using the Algorithm: SHA256withECDSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Private Key is null.")));
-
- Algorithm algorithm = Algorithm.ECDSA256((ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC"));
- algorithm.sign(new byte[0], new byte[0]);
- }
-
- @Test
- public void shouldDoECDSA384Signing() throws Exception {
- Algorithm algorithmSign = Algorithm.ECDSA384((ECKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_384, "EC"));
- Algorithm algorithmVerify = Algorithm.ECDSA384((ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_384, "EC"));
- String jwt = asJWT(algorithmSign, ES384Header, auth0IssPayload);
-
- assertSignaturePresent(jwt);
- algorithmVerify.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldDoECDSA384SigningWithBothKeys() throws Exception {
- Algorithm algorithm = Algorithm.ECDSA384((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_384, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_384, "EC"));
- String jwt = asJWT(algorithm, ES384Header, auth0IssPayload);
-
- assertSignaturePresent(jwt);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldDoECDSA384SigningWithProvidedPrivateKey() throws Exception {
- ECDSAKeyProvider provider = mock(ECDSAKeyProvider.class);
- PrivateKey privateKey = readPrivateKeyFromFile(PRIVATE_KEY_FILE_384, "EC");
- PublicKey publicKey = readPublicKeyFromFile(PUBLIC_KEY_FILE_384, "EC");
- when(provider.getPrivateKey()).thenReturn((ECPrivateKey) privateKey);
- when(provider.getPublicKeyById(null)).thenReturn((ECPublicKey) publicKey);
- Algorithm algorithm = Algorithm.ECDSA384(provider);
-
- String jwt = asJWT(algorithm, ES384Header, auth0IssPayload);
-
- assertSignaturePresent(jwt);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailOnECDSA384SigningWhenProvidedPrivateKeyIsNull() {
- exception.expect(SignatureGenerationException.class);
- exception.expectMessage("The Token's Signature couldn't be generated when signing using the Algorithm: SHA384withECDSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Private Key is null.")));
-
- ECDSAKeyProvider provider = mock(ECDSAKeyProvider.class);
- when(provider.getPrivateKey()).thenReturn(null);
- Algorithm algorithm = Algorithm.ECDSA384(provider);
- algorithm.sign(new byte[0], new byte[0]);
- }
-
- @Test
- public void shouldFailOnECDSA384SigningWhenUsingPublicKey() throws Exception {
- exception.expect(SignatureGenerationException.class);
- exception.expectMessage("The Token's Signature couldn't be generated when signing using the Algorithm: SHA384withECDSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Private Key is null.")));
-
- Algorithm algorithm = Algorithm.ECDSA384((ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_384, "EC"));
- algorithm.sign(new byte[0], new byte[0]);
- }
-
- @Test
- public void shouldDoECDSA512Signing() throws Exception {
- Algorithm algorithmSign = Algorithm.ECDSA512((ECKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_512, "EC"));
- Algorithm algorithmVerify = Algorithm.ECDSA512((ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_512, "EC"));
-
- String jwt = asJWT(algorithmSign, ES512Header, auth0IssPayload);
-
- assertSignaturePresent(jwt);
- algorithmVerify.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldDoECDSA512SigningWithBothKeys() throws Exception {
- Algorithm algorithm = Algorithm.ECDSA512((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_512, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_512, "EC"));
- String jwt = asJWT(algorithm, ES512Header, auth0IssPayload);
-
- assertSignaturePresent(jwt);
- algorithm.verify(JWT.decode(jwt));
- }
-
-
- @Test
- public void shouldDoECDSA512SigningWithProvidedPrivateKey() throws Exception {
- ECDSAKeyProvider provider = mock(ECDSAKeyProvider.class);
- PrivateKey privateKey = readPrivateKeyFromFile(PRIVATE_KEY_FILE_512, "EC");
- PublicKey publicKey = readPublicKeyFromFile(PUBLIC_KEY_FILE_512, "EC");
- when(provider.getPrivateKey()).thenReturn((ECPrivateKey) privateKey);
- when(provider.getPublicKeyById(null)).thenReturn((ECPublicKey) publicKey);
- Algorithm algorithm = Algorithm.ECDSA512(provider);
- String jwt = asJWT(algorithm, ES512Header, auth0IssPayload);
-
- assertSignaturePresent(jwt);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailOnECDSA512SigningWhenProvidedPrivateKeyIsNull() {
- exception.expect(SignatureGenerationException.class);
- exception.expectMessage("The Token's Signature couldn't be generated when signing using the Algorithm: SHA512withECDSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Private Key is null.")));
-
- ECDSAKeyProvider provider = mock(ECDSAKeyProvider.class);
- when(provider.getPrivateKey()).thenReturn(null);
- Algorithm algorithm = Algorithm.ECDSA512(provider);
- algorithm.sign(new byte[0], new byte[0]);
- }
-
- @Test
- public void shouldFailOnECDSA512SigningWhenUsingPublicKey() throws Exception {
- exception.expect(SignatureGenerationException.class);
- exception.expectMessage("The Token's Signature couldn't be generated when signing using the Algorithm: SHA512withECDSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Private Key is null.")));
-
- Algorithm algorithm = Algorithm.ECDSA512((ECKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_512, "EC"));
- algorithm.sign(new byte[0], new byte[0]);
- }
-
- @Test
- public void shouldThrowOnSignWhenSignatureAlgorithmDoesNotExists() throws Exception {
- exception.expect(SignatureGenerationException.class);
- exception.expectMessage("The Token's Signature couldn't be generated when signing using the Algorithm: some-algorithm");
- exception.expectCause(isA(NoSuchAlgorithmException.class));
-
- CryptoHelper crypto = mock(CryptoHelper.class);
- when(crypto.createSignatureFor(anyString(), any(PrivateKey.class), any(byte[].class), any(byte[].class)))
- .thenThrow(NoSuchAlgorithmException.class);
-
- ECPublicKey publicKey = mock(ECPublicKey.class);
- ECPrivateKey privateKey = mock(ECPrivateKey.class);
- ECDSAKeyProvider provider = ECDSAAlgorithm.providerForKeys(publicKey, privateKey);
- Algorithm algorithm = new ECDSAAlgorithm(crypto, "some-alg", "some-algorithm", 32, provider);
- algorithm.sign(ES256Header.getBytes(StandardCharsets.UTF_8), new byte[0]);
- }
-
- @Test
- public void shouldThrowOnSignWhenThePrivateKeyIsInvalid() throws Exception {
- exception.expect(SignatureGenerationException.class);
- exception.expectMessage("The Token's Signature couldn't be generated when signing using the Algorithm: some-algorithm");
- exception.expectCause(isA(InvalidKeyException.class));
-
- CryptoHelper crypto = mock(CryptoHelper.class);
- when(crypto.createSignatureFor(anyString(), any(PrivateKey.class), any(byte[].class), any(byte[].class)))
- .thenThrow(InvalidKeyException.class);
-
- ECPublicKey publicKey = mock(ECPublicKey.class);
- ECPrivateKey privateKey = mock(ECPrivateKey.class);
- ECDSAKeyProvider provider = ECDSAAlgorithm.providerForKeys(publicKey, privateKey);
- Algorithm algorithm = new ECDSAAlgorithm(crypto, "some-alg", "some-algorithm", 32, provider);
- algorithm.sign(ES256Header.getBytes(StandardCharsets.UTF_8), new byte[0]);
- }
-
- @Test
- public void shouldThrowOnSignWhenTheSignatureIsNotPrepared() throws Exception {
- exception.expect(SignatureGenerationException.class);
- exception.expectMessage("The Token's Signature couldn't be generated when signing using the Algorithm: some-algorithm");
- exception.expectCause(isA(SignatureException.class));
-
- CryptoHelper crypto = mock(CryptoHelper.class);
- when(crypto.createSignatureFor(anyString(), any(PrivateKey.class), any(byte[].class), any(byte[].class)))
- .thenThrow(SignatureException.class);
-
- ECPublicKey publicKey = mock(ECPublicKey.class);
- ECPrivateKey privateKey = mock(ECPrivateKey.class);
- ECDSAKeyProvider provider = ECDSAAlgorithm.providerForKeys(publicKey, privateKey);
- Algorithm algorithm = new ECDSAAlgorithm(crypto, "some-alg", "some-algorithm", 32, provider);
- algorithm.sign(ES256Header.getBytes(StandardCharsets.UTF_8), new byte[0]);
- }
-
- @Test
- public void shouldReturnNullSigningKeyIdIfCreatedWithDefaultProvider() {
- ECPublicKey publicKey = mock(ECPublicKey.class);
- ECPrivateKey privateKey = mock(ECPrivateKey.class);
- ECDSAKeyProvider provider = ECDSAAlgorithm.providerForKeys(publicKey, privateKey);
- Algorithm algorithm = new ECDSAAlgorithm("some-alg", "some-algorithm", 32, provider);
-
- assertThat(algorithm.getSigningKeyId(), is(nullValue()));
- }
-
- @Test
- public void shouldReturnSigningKeyIdFromProvider() {
- ECDSAKeyProvider provider = mock(ECDSAKeyProvider.class);
- when(provider.getPrivateKeyId()).thenReturn("keyId");
- Algorithm algorithm = new ECDSAAlgorithm("some-alg", "some-algorithm", 32, provider);
-
- assertThat(algorithm.getSigningKeyId(), is("keyId"));
- }
-
- @Test
- public void shouldThrowOnDERSignatureConversionIfDoesNotStartWithCorrectSequenceByte() throws Exception {
- exception.expect(SignatureException.class);
- exception.expectMessage("Invalid DER signature format.");
-
- ECDSAAlgorithm algorithm256 = (ECDSAAlgorithm) Algorithm.ECDSA256((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC"));
- String content256 = "eyJhbGciOiJFUzI1NiJ9.eyJpc3MiOiJhdXRoMCJ9";
-
- byte[] signature = algorithm256.sign(content256.getBytes(), new byte[0]);
- signature[0] = (byte) 0x02;
- algorithm256.DERToJOSE(signature);
- }
-
- @Test
- public void shouldThrowOnDERSignatureConversionIfDoesNotHaveExpectedLength() throws Exception {
- ECDSAAlgorithm algorithm256 = (ECDSAAlgorithm) Algorithm.ECDSA256((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC"));
- byte[] derSignature = createDERSignature(32, false, false);
- int received = (int) derSignature[1];
- received--;
- derSignature[1] = (byte) received;
- exception.expect(SignatureException.class);
- exception.expectMessage("Invalid DER signature format.");
-
- algorithm256.DERToJOSE(derSignature);
- }
-
- @Test
- public void shouldThrowOnDERSignatureConversionIfRNumberDoesNotHaveExpectedLength() throws Exception {
- ECDSAAlgorithm algorithm256 = (ECDSAAlgorithm) Algorithm.ECDSA256((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC"));
- byte[] derSignature = createDERSignature(32, false, false);
- derSignature[3] = (byte) 34;
- exception.expect(SignatureException.class);
- exception.expectMessage("Invalid DER signature format.");
-
- algorithm256.DERToJOSE(derSignature);
- }
-
- @Test
- public void shouldThrowOnDERSignatureConversionIfSNumberDoesNotHaveExpectedLength() throws Exception {
- ECDSAAlgorithm algorithm256 = (ECDSAAlgorithm) Algorithm.ECDSA256((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC"));
- byte[] derSignature = createDERSignature(32, false, false);
- derSignature[4 + 32 + 1] = (byte) 34;
- exception.expect(SignatureException.class);
- exception.expectMessage("Invalid DER signature format.");
-
- algorithm256.DERToJOSE(derSignature);
- }
-
- @Test
- public void shouldThrowOnJOSESignatureConversionIfDoesNotHaveExpectedLength() throws Exception {
- ECPublicKey publicKey = (ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC");
- ECDSAAlgorithm algorithm256 = (ECDSAAlgorithm) Algorithm.ECDSA256(publicKey, (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC"));
- byte[] joseSignature = new byte[32 * 2 - 1];
- exception.expect(SignatureException.class);
- exception.expectMessage("Invalid JOSE signature format.");
-
- algorithm256.validateSignatureStructure(joseSignature, publicKey);
- }
-
- @Test
- public void shouldSignAndVerifyWithECDSA256() throws Exception {
- ECDSAAlgorithm algorithm256 = (ECDSAAlgorithm) Algorithm.ECDSA256((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC"));
- String header256 = "eyJhbGciOiJFUzI1NiJ9";
- String body = "eyJpc3MiOiJhdXRoMCJ9";
-
- for (int i = 0; i < 10; i++) {
- String jwt = asJWT(algorithm256, header256, body);
- algorithm256.verify(JWT.decode(jwt));
- }
- }
-
- @Test
- public void shouldSignAndVerifyWithECDSA384() throws Exception {
- ECDSAAlgorithm algorithm384 = (ECDSAAlgorithm) Algorithm.ECDSA384((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_384, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_384, "EC"));
- String header384 = "eyJhbGciOiJFUzM4NCJ9";
- String body = "eyJpc3MiOiJhdXRoMCJ9";
-
- for (int i = 0; i < 10; i++) {
- String jwt = asJWT(algorithm384, header384, body);
- algorithm384.verify(JWT.decode(jwt));
- }
- }
-
- @Test
- public void shouldSignAndVerifyWithECDSA512() throws Exception {
- ECDSAAlgorithm algorithm512 = (ECDSAAlgorithm) Algorithm.ECDSA512((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_512, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_512, "EC"));
- String header512 = "eyJhbGciOiJFUzUxMiJ9";
- String body = "eyJpc3MiOiJhdXRoMCJ9";
-
- for (int i = 0; i < 10; i++) {
- String jwt = asJWT(algorithm512, header512, body);
- algorithm512.verify(JWT.decode(jwt));
- }
- }
-
- @Test
- public void shouldDecodeECDSA256JOSE() throws Exception {
- ECDSAAlgorithm algorithm256 = (ECDSAAlgorithm) Algorithm.ECDSA256((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC"));
-
- //Without padding
- byte[] joseSignature = createJOSESignature(32, false, false);
- byte[] derSignature = algorithm256.JOSEToDER(joseSignature);
- assertValidDERSignature(derSignature, 32, false, false);
-
- //With R padding
- joseSignature = createJOSESignature(32, true, false);
- derSignature = algorithm256.JOSEToDER(joseSignature);
- assertValidDERSignature(derSignature, 32, true, false);
-
- //With S padding
- joseSignature = createJOSESignature(32, false, true);
- derSignature = algorithm256.JOSEToDER(joseSignature);
- assertValidDERSignature(derSignature, 32, false, true);
-
- //With both paddings
- joseSignature = createJOSESignature(32, true, true);
- derSignature = algorithm256.JOSEToDER(joseSignature);
- assertValidDERSignature(derSignature, 32, true, true);
- }
-
- @Test
- public void shouldDecodeECDSA256DER() throws Exception {
- ECDSAAlgorithm algorithm256 = (ECDSAAlgorithm) Algorithm.ECDSA256((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_256, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_256, "EC"));
-
- //Without padding
- byte[] derSignature = createDERSignature(32, false, false);
- byte[] joseSignature = algorithm256.DERToJOSE(derSignature);
- assertValidJOSESignature(joseSignature, 32, false, false);
-
- //With R padding
- derSignature = createDERSignature(32, true, false);
- joseSignature = algorithm256.DERToJOSE(derSignature);
- assertValidJOSESignature(joseSignature, 32, true, false);
-
- //With S padding
- derSignature = createDERSignature(32, false, true);
- joseSignature = algorithm256.DERToJOSE(derSignature);
- assertValidJOSESignature(joseSignature, 32, false, true);
-
- //With both paddings
- derSignature = createDERSignature(32, true, true);
- joseSignature = algorithm256.DERToJOSE(derSignature);
- assertValidJOSESignature(joseSignature, 32, true, true);
- }
-
- @Test
- public void shouldDecodeECDSA384JOSE() throws Exception {
- ECDSAAlgorithm algorithm384 = (ECDSAAlgorithm) Algorithm.ECDSA384((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_384, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_384, "EC"));
-
- //Without padding
- byte[] joseSignature = createJOSESignature(48, false, false);
- byte[] derSignature = algorithm384.JOSEToDER(joseSignature);
- assertValidDERSignature(derSignature, 48, false, false);
-
- //With R padding
- joseSignature = createJOSESignature(48, true, false);
- derSignature = algorithm384.JOSEToDER(joseSignature);
- assertValidDERSignature(derSignature, 48, true, false);
-
- //With S padding
- joseSignature = createJOSESignature(48, false, true);
- derSignature = algorithm384.JOSEToDER(joseSignature);
- assertValidDERSignature(derSignature, 48, false, true);
-
- //With both paddings
- joseSignature = createJOSESignature(48, true, true);
- derSignature = algorithm384.JOSEToDER(joseSignature);
- assertValidDERSignature(derSignature, 48, true, true);
- }
-
- @Test
- public void shouldDecodeECDSA384DER() throws Exception {
- ECDSAAlgorithm algorithm384 = (ECDSAAlgorithm) Algorithm.ECDSA384((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_384, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_384, "EC"));
-
- //Without padding
- byte[] derSignature = createDERSignature(48, false, false);
- byte[] joseSignature = algorithm384.DERToJOSE(derSignature);
- assertValidJOSESignature(joseSignature, 48, false, false);
-
- //With R padding
- derSignature = createDERSignature(48, true, false);
- joseSignature = algorithm384.DERToJOSE(derSignature);
- assertValidJOSESignature(joseSignature, 48, true, false);
-
- //With S padding
- derSignature = createDERSignature(48, false, true);
- joseSignature = algorithm384.DERToJOSE(derSignature);
- assertValidJOSESignature(joseSignature, 48, false, true);
-
- //With both paddings
- derSignature = createDERSignature(48, true, true);
- joseSignature = algorithm384.DERToJOSE(derSignature);
- assertValidJOSESignature(joseSignature, 48, true, true);
- }
-
- @Test
- public void shouldDecodeECDSA512JOSE() throws Exception {
- ECDSAAlgorithm algorithm512 = (ECDSAAlgorithm) Algorithm.ECDSA512((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_512, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_512, "EC"));
-
- //Without padding
- byte[] joseSignature = createJOSESignature(66, false, false);
- byte[] derSignature = algorithm512.JOSEToDER(joseSignature);
- assertValidDERSignature(derSignature, 66, false, false);
-
- //With R padding
- joseSignature = createJOSESignature(66, true, false);
- derSignature = algorithm512.JOSEToDER(joseSignature);
- assertValidDERSignature(derSignature, 66, true, false);
-
- //With S padding
- joseSignature = createJOSESignature(66, false, true);
- derSignature = algorithm512.JOSEToDER(joseSignature);
- assertValidDERSignature(derSignature, 66, false, true);
-
- //With both paddings
- joseSignature = createJOSESignature(66, true, true);
- derSignature = algorithm512.JOSEToDER(joseSignature);
- assertValidDERSignature(derSignature, 66, true, true);
- }
-
- @Test
- public void shouldDecodeECDSA512DER() throws Exception {
- ECDSAAlgorithm algorithm512 = (ECDSAAlgorithm) Algorithm.ECDSA512((ECPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE_512, "EC"), (ECPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE_512, "EC"));
-
- //Without padding
- byte[] derSignature = createDERSignature(66, false, false);
- byte[] joseSignature = algorithm512.DERToJOSE(derSignature);
- assertValidJOSESignature(joseSignature, 66, false, false);
-
- //With R padding
- derSignature = createDERSignature(66, true, false);
- joseSignature = algorithm512.DERToJOSE(derSignature);
- assertValidJOSESignature(joseSignature, 66, true, false);
-
- //With S padding
- derSignature = createDERSignature(66, false, true);
- joseSignature = algorithm512.DERToJOSE(derSignature);
- assertValidJOSESignature(joseSignature, 66, false, true);
-
- //With both paddings
- derSignature = createDERSignature(66, true, true);
- joseSignature = algorithm512.DERToJOSE(derSignature);
- assertValidJOSESignature(joseSignature, 66, true, true);
- }
-
-
-}
diff --git a/lib/src/test/java/com/auth0/jwt/algorithms/HMACAlgorithmTest.java b/lib/src/test/java/com/auth0/jwt/algorithms/HMACAlgorithmTest.java
deleted file mode 100644
index 9b6ac0c0..00000000
--- a/lib/src/test/java/com/auth0/jwt/algorithms/HMACAlgorithmTest.java
+++ /dev/null
@@ -1,309 +0,0 @@
-package com.auth0.jwt.algorithms;
-
-import com.auth0.jwt.JWT;
-import com.auth0.jwt.exceptions.SignatureGenerationException;
-import com.auth0.jwt.exceptions.SignatureVerificationException;
-import com.auth0.jwt.interfaces.DecodedJWT;
-import org.junit.Rule;
-import org.junit.Test;
-import org.junit.rules.ExpectedException;
-
-import java.io.ByteArrayOutputStream;
-import java.nio.charset.Charset;
-import java.nio.charset.StandardCharsets;
-import java.security.InvalidKeyException;
-import java.security.NoSuchAlgorithmException;
-
-import static com.auth0.jwt.algorithms.CryptoTestHelper.asJWT;
-import static com.auth0.jwt.algorithms.CryptoTestHelper.assertSignaturePresent;
-import static com.auth0.jwt.algorithms.CryptoTestHelper.assertSignatureValue;
-import static org.hamcrest.Matchers.*;
-import static org.hamcrest.MatcherAssert.assertThat;
-import static org.junit.Assert.assertArrayEquals;
-import static org.mockito.ArgumentMatchers.any;
-import static org.mockito.ArgumentMatchers.anyString;
-import static org.mockito.Mockito.mock;
-import static org.mockito.Mockito.when;
-
-public class HMACAlgorithmTest {
-
- @Rule
- public ExpectedException exception = ExpectedException.none();
-
- // Verify
-
- @Test
- public void shouldGetStringBytes() {
- String text = "abcdef123456!@#$%^";
- byte[] expectedBytes = text.getBytes(StandardCharsets.UTF_8);
- assertArrayEquals(expectedBytes, HMACAlgorithm.getSecretBytes(text));
- }
-
- @Test
- public void shouldCopyTheReceivedSecretArray() {
- String jwt = "eyJhbGciOiJIUzI1NiIsImN0eSI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.mZ0m_N1J4PgeqWmi903JuUoDRZDBPB7HwkS4nVyWH1M";
- byte[] secretArray = "secret".getBytes(Charset.defaultCharset());
- Algorithm algorithmString = Algorithm.HMAC256(secretArray);
-
- DecodedJWT decoded = JWT.decode(jwt);
- algorithmString.verify(decoded);
- secretArray[0] = secretArray[1];
- algorithmString.verify(decoded);
- }
-
- @Test
- public void shouldPassHMAC256Verification() {
- String jwt = "eyJhbGciOiJIUzI1NiIsImN0eSI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.mZ0m_N1J4PgeqWmi903JuUoDRZDBPB7HwkS4nVyWH1M";
- Algorithm algorithmString = Algorithm.HMAC256("secret");
- Algorithm algorithmBytes = Algorithm.HMAC256("secret".getBytes(StandardCharsets.UTF_8));
- DecodedJWT decoded = JWT.decode(jwt);
- algorithmString.verify(decoded);
- algorithmBytes.verify(decoded);
- }
-
- @Test
- public void shouldFailHMAC256VerificationWithInvalidSecretString() {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: HmacSHA256");
- String jwt = "eyJhbGciOiJIUzI1NiIsImN0eSI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.mZ0m_N1J4PgeqWmi903JuUoDRZDBPB7HwkS4nVyWH1M";
- Algorithm algorithm = Algorithm.HMAC256("not_real_secret");
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailHMAC256VerificationWithInvalidSecretBytes() {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: HmacSHA256");
- String jwt = "eyJhbGciOiJIUzI1NiIsImN0eSI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.mZ0m_N1J4PgeqWmi903JuUoDRZDBPB7HwkS4nVyWH1M";
- Algorithm algorithm = Algorithm.HMAC256("not_real_secret".getBytes(StandardCharsets.UTF_8));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldPassHMAC384Verification() {
- String jwt = "eyJhbGciOiJIUzM4NCIsImN0eSI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.uztpK_wUMYJhrRv8SV-1LU4aPnwl-EM1q-wJnqgyb5DHoDteP6lN_gE1xnZJH5vw";
- Algorithm algorithmString = Algorithm.HMAC384("secret");
- Algorithm algorithmBytes = Algorithm.HMAC384("secret".getBytes(StandardCharsets.UTF_8));
- DecodedJWT decoded = JWT.decode(jwt);
- algorithmString.verify(decoded);
- algorithmBytes.verify(decoded);
- }
-
- @Test
- public void shouldFailHMAC384VerificationWithInvalidSecretString() {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: HmacSHA384");
- String jwt = "eyJhbGciOiJIUzM4NCIsImN0eSI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.uztpK_wUMYJhrRv8SV-1LU4aPnwl-EM1q-wJnqgyb5DHoDteP6lN_gE1xnZJH5vw";
- Algorithm algorithm = Algorithm.HMAC384("not_real_secret");
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailHMAC384VerificationWithInvalidSecretBytes() {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: HmacSHA384");
- String jwt = "eyJhbGciOiJIUzM4NCIsImN0eSI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.uztpK_wUMYJhrRv8SV-1LU4aPnwl-EM1q-wJnqgyb5DHoDteP6lN_gE1xnZJH5vw";
- Algorithm algorithm = Algorithm.HMAC384("not_real_secret".getBytes(StandardCharsets.UTF_8));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldPassHMAC512Verification() {
- String jwt = "eyJhbGciOiJIUzUxMiIsImN0eSI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.VUo2Z9SWDV-XcOc_Hr6Lff3vl7L9e5Vb8ThXpmGDFjHxe3Dr1ZBmUChYF-xVA7cAdX1P_D4ZCUcsv3IefpVaJw";
- Algorithm algorithmString = Algorithm.HMAC512("secret");
- Algorithm algorithmBytes = Algorithm.HMAC512("secret".getBytes(StandardCharsets.UTF_8));
- DecodedJWT decoded = JWT.decode(jwt);
- algorithmString.verify(decoded);
- algorithmBytes.verify(decoded);
- }
-
- @Test
- public void shouldFailHMAC512VerificationWithInvalidSecretString() {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: HmacSHA512");
- String jwt = "eyJhbGciOiJIUzUxMiIsImN0eSI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.VUo2Z9SWDV-XcOc_Hr6Lff3vl7L9e5Vb8ThXpmGDFjHxe3Dr1ZBmUChYF-xVA7cAdX1P_D4ZCUcsv3IefpVaJw";
- Algorithm algorithm = Algorithm.HMAC512("not_real_secret");
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailHMAC512VerificationWithInvalidSecretBytes() {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: HmacSHA512");
- String jwt = "eyJhbGciOiJIUzUxMiIsImN0eSI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.VUo2Z9SWDV-XcOc_Hr6Lff3vl7L9e5Vb8ThXpmGDFjHxe3Dr1ZBmUChYF-xVA7cAdX1P_D4ZCUcsv3IefpVaJw";
- Algorithm algorithm = Algorithm.HMAC512("not_real_secret".getBytes(StandardCharsets.UTF_8));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldThrowOnVerifyWhenSignatureAlgorithmDoesNotExists() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: some-alg");
- exception.expectCause(isA(NoSuchAlgorithmException.class));
-
- CryptoHelper crypto = mock(CryptoHelper.class);
- when(crypto.verifySignatureFor(anyString(), any(byte[].class), any(String.class), any(String.class), any(byte[].class)))
- .thenThrow(NoSuchAlgorithmException.class);
-
- Algorithm algorithm = new HMACAlgorithm(crypto, "some-alg", "some-algorithm", "secret".getBytes(StandardCharsets.UTF_8));
- String jwt = "eyJhbGciOiJIUzI1NiIsImN0eSI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.mZ0m_N1J4PgeqWmi903JuUoDRZDBPB7HwkS4nVyWH1M";
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldThrowOnVerifyWhenTheSecretIsInvalid() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: some-alg");
- exception.expectCause(isA(InvalidKeyException.class));
-
- CryptoHelper crypto = mock(CryptoHelper.class);
- when(crypto.verifySignatureFor(anyString(), any(byte[].class), any(String.class), any(String.class), any(byte[].class)))
- .thenThrow(InvalidKeyException.class);
-
- Algorithm algorithm = new HMACAlgorithm(crypto, "some-alg", "some-algorithm", "secret".getBytes(StandardCharsets.UTF_8));
- String jwt = "eyJhbGciOiJIUzI1NiIsImN0eSI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.mZ0m_N1J4PgeqWmi903JuUoDRZDBPB7HwkS4nVyWH1M";
- algorithm.verify(JWT.decode(jwt));
- }
-
- // Sign
-
- private static final String HS256Header = "eyJhbGciOiJIUzI1NiJ9";
- private static final String HS384Header = "eyJhbGciOiJIUzM4NCJ9";
- private static final String HS512Header = "eyJhbGciOiJIUzUxMiJ9";
- private static final String auth0IssPayload = "eyJpc3MiOiJhdXRoMCJ9";
-
- @Test
- public void shouldDoHMAC256SigningWithBytes() {
- Algorithm algorithm = Algorithm.HMAC256("secret".getBytes(StandardCharsets.UTF_8));
-
- String jwt = asJWT(algorithm, HS256Header, auth0IssPayload);
- String expectedSignature = "s69x7Mmu4JqwmdxiK6sesALO7tcedbFsKEEITUxw9ho";
-
- assertSignaturePresent(jwt);
- assertSignatureValue(jwt, expectedSignature);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldDoHMAC384SigningWithBytes() {
- Algorithm algorithm = Algorithm.HMAC384("secret".getBytes(StandardCharsets.UTF_8));
-
- String jwt = asJWT(algorithm, HS384Header, auth0IssPayload);
- String expectedSignature = "4-y2Gxz_foN0jAOFimmBPF7DWxf4AsjM20zxNkHg8Zah5Q64G42P9GfjmUp4Hldt";
-
- assertSignaturePresent(jwt);
- assertSignatureValue(jwt, expectedSignature);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldDoHMAC512SigningWithBytes() {
- Algorithm algorithm = Algorithm.HMAC512("secret".getBytes(StandardCharsets.UTF_8));
-
- String jwt = asJWT(algorithm, HS512Header, auth0IssPayload);
- String expectedSignature = "OXWyxmf-VcVo8viOiTFfLaEy6mrQqLEos5R82Xsx8mtFxQadJAQ1aVniIWN8qT2GNE_pMQPcdzk4x7Cqxsp1dw";
-
- assertSignaturePresent(jwt);
- assertSignatureValue(jwt, expectedSignature);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldDoHMAC256SigningWithString() {
- Algorithm algorithm = Algorithm.HMAC256("secret");
-
- String jwt = asJWT(algorithm, HS256Header, auth0IssPayload);
- String expectedSignature = "s69x7Mmu4JqwmdxiK6sesALO7tcedbFsKEEITUxw9ho";
-
- assertSignaturePresent(jwt);
- assertSignatureValue(jwt, expectedSignature);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldDoHMAC384SigningWithString() {
- Algorithm algorithm = Algorithm.HMAC384("secret");
-
- String jwt = asJWT(algorithm, HS384Header, auth0IssPayload);
- String expectedSignature = "4-y2Gxz_foN0jAOFimmBPF7DWxf4AsjM20zxNkHg8Zah5Q64G42P9GfjmUp4Hldt";
-
- assertSignaturePresent(jwt);
- assertSignatureValue(jwt, expectedSignature);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldDoHMAC512SigningWithString() {
- Algorithm algorithm = Algorithm.HMAC512("secret");
-
- String jwt = asJWT(algorithm ,HS512Header, auth0IssPayload);
- String expectedSignature = "OXWyxmf-VcVo8viOiTFfLaEy6mrQqLEos5R82Xsx8mtFxQadJAQ1aVniIWN8qT2GNE_pMQPcdzk4x7Cqxsp1dw";
-
- assertSignaturePresent(jwt);
- assertSignatureValue(jwt, expectedSignature);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldThrowOnSignWhenSignatureAlgorithmDoesNotExists() throws Exception {
- exception.expect(SignatureGenerationException.class);
- exception.expectMessage("The Token's Signature couldn't be generated when signing using the Algorithm: some-algorithm");
- exception.expectCause(isA(NoSuchAlgorithmException.class));
-
- CryptoHelper crypto = mock(CryptoHelper.class);
- when(crypto.createSignatureFor(anyString(), any(byte[].class), any(byte[].class), any(byte[].class)))
- .thenThrow(NoSuchAlgorithmException.class);
-
- Algorithm algorithm = new HMACAlgorithm(crypto, "some-alg", "some-algorithm", "secret".getBytes(StandardCharsets.UTF_8));
- algorithm.sign(new byte[0], new byte[0]);
- }
-
- @Test
- public void shouldThrowOnSignWhenTheSecretIsInvalid() throws Exception {
- exception.expect(SignatureGenerationException.class);
- exception.expectMessage("The Token's Signature couldn't be generated when signing using the Algorithm: some-algorithm");
- exception.expectCause(isA(InvalidKeyException.class));
-
- CryptoHelper crypto = mock(CryptoHelper.class);
- when(crypto.createSignatureFor(anyString(), any(byte[].class), any(byte[].class), any(byte[].class)))
- .thenThrow(InvalidKeyException.class);
-
- Algorithm algorithm = new HMACAlgorithm(crypto, "some-alg", "some-algorithm", "secret".getBytes(StandardCharsets.UTF_8));
- algorithm.sign(new byte[0], new byte[0]);
- }
-
- @Test
- public void shouldReturnNullSigningKeyId() {
- assertThat(Algorithm.HMAC256("secret").getSigningKeyId(), is(nullValue()));
- }
-
- @Test
- public void shouldBeEqualSignatureMethodResults() throws Exception {
- Algorithm algorithm = Algorithm.HMAC256("secret");
-
- byte[] header = new byte[]{0x00, 0x01, 0x02};
- byte[] payload = new byte[]{0x04, 0x05, 0x06};
-
- ByteArrayOutputStream bout = new ByteArrayOutputStream();
- bout.write(header);
- bout.write('.');
- bout.write(payload);
-
- assertThat(algorithm.sign(bout.toByteArray()), is(algorithm.sign(header, payload)));
- }
-
-
- @Test
- public void shouldThrowWhenSignatureNotValidBase64() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectCause(isA(IllegalArgumentException.class));
-
- CryptoHelper crypto = mock(CryptoHelper.class);
- when(crypto.verifySignatureFor(anyString(), any(byte[].class), any(String.class), any(String.class), any(byte[].class)))
- .thenThrow(NoSuchAlgorithmException.class);
-
- Algorithm algorithm = new HMACAlgorithm(crypto, "some-alg", "some-algorithm", "secret".getBytes(StandardCharsets.UTF_8));
- String jwt = "eyJhbGciOiJIUzI1NiIsImN0eSI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.mZ0m_N1J4PgeqWm+i903JuUoDRZDBPB7HwkS4nVyWH1M";
- algorithm.verify(JWT.decode(jwt));
- }
-}
\ No newline at end of file
diff --git a/lib/src/test/java/com/auth0/jwt/algorithms/NoneAlgorithmTest.java b/lib/src/test/java/com/auth0/jwt/algorithms/NoneAlgorithmTest.java
deleted file mode 100644
index 263dc249..00000000
--- a/lib/src/test/java/com/auth0/jwt/algorithms/NoneAlgorithmTest.java
+++ /dev/null
@@ -1,57 +0,0 @@
-package com.auth0.jwt.algorithms;
-
-import com.auth0.jwt.JWT;
-import com.auth0.jwt.exceptions.JWTDecodeException;
-import com.auth0.jwt.exceptions.SignatureVerificationException;
-import org.junit.Rule;
-import org.junit.Test;
-import org.junit.rules.ExpectedException;
-
-import static org.hamcrest.Matchers.*;
-import static org.hamcrest.MatcherAssert.assertThat;
-
-public class NoneAlgorithmTest {
-
- @Rule
- public ExpectedException exception = ExpectedException.none();
-
- @Test
- public void shouldPassNoneVerification() {
- Algorithm algorithm = Algorithm.none();
- String jwt = "eyJhbGciOiJub25lIiwiY3R5IjoiSldUIn0.eyJpc3MiOiJhdXRoMCJ9.";
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailNoneVerificationWhenTokenHasTwoParts() {
- exception.expect(JWTDecodeException.class);
- exception.expectMessage("The token was expected to have 3 parts, but got 2.");
- String jwt = "eyJhbGciOiJub25lIiwiY3R5IjoiSldUIn0.eyJpc3MiOiJhdXRoMCJ9";
- Algorithm algorithm = Algorithm.none();
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailNoneVerificationWhenSignatureIsPresent() {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: none");
- String jwt = "eyJhbGciOiJub25lIiwiY3R5IjoiSldUIn0.eyJpc3MiOiJhdXRoMCJ9.Ox-WRXRaGAuWt2KfPvWiGcCrPqZtbp_4OnQzZXaTfss";
- Algorithm algorithm = Algorithm.none();
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldReturnNullSigningKeyId() {
- assertThat(Algorithm.none().getSigningKeyId(), is(nullValue()));
- }
-
- @Test
- public void shouldThrowWhenSignatureNotValidBase64() {
- exception.expect(SignatureVerificationException.class);
- exception.expectCause(isA(IllegalArgumentException.class));
-
- String jwt = "eyJhbGciOiJub25lIiwiY3R5IjoiSldUIn0.eyJpc3MiOiJhdXRoMCJ9.Ox-WRXRaGAuWt2KfPvW+iGcCrPqZtbp_4OnQzZXaTfss";
- Algorithm algorithm = Algorithm.none();
- algorithm.verify(JWT.decode(jwt));
- }
-}
\ No newline at end of file
diff --git a/lib/src/test/java/com/auth0/jwt/algorithms/RSAAlgorithmTest.java b/lib/src/test/java/com/auth0/jwt/algorithms/RSAAlgorithmTest.java
deleted file mode 100644
index 115de64c..00000000
--- a/lib/src/test/java/com/auth0/jwt/algorithms/RSAAlgorithmTest.java
+++ /dev/null
@@ -1,579 +0,0 @@
-package com.auth0.jwt.algorithms;
-
-import com.auth0.jwt.JWT;
-import com.auth0.jwt.exceptions.SignatureGenerationException;
-import com.auth0.jwt.exceptions.SignatureVerificationException;
-import com.auth0.jwt.interfaces.RSAKeyProvider;
-import org.junit.Rule;
-import org.junit.Test;
-import org.junit.rules.ExpectedException;
-
-import java.io.ByteArrayOutputStream;
-import java.security.*;
-import java.security.interfaces.RSAKey;
-import java.security.interfaces.RSAPrivateKey;
-import java.security.interfaces.RSAPublicKey;
-
-import static com.auth0.jwt.PemUtils.readPrivateKeyFromFile;
-import static com.auth0.jwt.PemUtils.readPublicKeyFromFile;
-import static org.hamcrest.Matchers.*;
-import static org.hamcrest.MatcherAssert.assertThat;
-import static org.junit.internal.matchers.ThrowableMessageMatcher.hasMessage;
-import static org.mockito.ArgumentMatchers.any;
-import static org.mockito.ArgumentMatchers.anyString;
-import static org.mockito.Mockito.mock;
-import static org.mockito.Mockito.when;
-import static com.auth0.jwt.algorithms.CryptoTestHelper.*;
-
-public class RSAAlgorithmTest {
-
- private static final String PRIVATE_KEY_FILE = "src/test/resources/rsa-private.pem";
- private static final String PUBLIC_KEY_FILE = "src/test/resources/rsa-public.pem";
- private static final String INVALID_PUBLIC_KEY_FILE = "src/test/resources/rsa-public_invalid.pem";
-
- @Rule
- public ExpectedException exception = ExpectedException.none();
-
- //Verify
-
- @Test
- public void shouldPassRSA256Verification() throws Exception {
- String jwt = "eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.dxXF3MdsyW-AuvwJpaQtrZ33fAde9xWxpLIg9cO2tMLH2GSRNuLAe61KsJusZhqZB9Iy7DvflcmRz-9OZndm6cj_ThGeJH2LLc90K83UEvvRPo8l85RrQb8PcanxCgIs2RcZOLygERizB3pr5icGkzR7R2y6zgNCjKJ5_NJ6EiZsGN6_nc2PRK_DbyY-Wn0QDxIxKoA5YgQJ9qafe7IN980pXvQv2Z62c3XR8dYuaXBqhthBj-AbaFHEpZapN-V-TmuLNzR2MCB6Xr7BYMuCaqWf_XU8og4XNe8f_8w9Wv5vvgqMM1KhqVpG5VdMJv4o_L4NoCROHhtUQSLRh2M9cA";
- Algorithm algorithm = Algorithm.RSA256((RSAKey) readPublicKeyFromFile(PUBLIC_KEY_FILE, "RSA"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldPassRSA256VerificationWithBothKeys() throws Exception {
- String jwt = "eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.dxXF3MdsyW-AuvwJpaQtrZ33fAde9xWxpLIg9cO2tMLH2GSRNuLAe61KsJusZhqZB9Iy7DvflcmRz-9OZndm6cj_ThGeJH2LLc90K83UEvvRPo8l85RrQb8PcanxCgIs2RcZOLygERizB3pr5icGkzR7R2y6zgNCjKJ5_NJ6EiZsGN6_nc2PRK_DbyY-Wn0QDxIxKoA5YgQJ9qafe7IN980pXvQv2Z62c3XR8dYuaXBqhthBj-AbaFHEpZapN-V-TmuLNzR2MCB6Xr7BYMuCaqWf_XU8og4XNe8f_8w9Wv5vvgqMM1KhqVpG5VdMJv4o_L4NoCROHhtUQSLRh2M9cA";
- Algorithm algorithm = Algorithm.RSA256((RSAPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE, "RSA"), (RSAPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE, "RSA"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldPassRSA256VerificationWithProvidedPublicKey() throws Exception {
- RSAKeyProvider provider = mock(RSAKeyProvider.class);
- PublicKey publicKey = readPublicKeyFromFile(PUBLIC_KEY_FILE, "RSA");
- when(provider.getPublicKeyById("my-key-id")).thenReturn((RSAPublicKey) publicKey);
- String jwt = "eyJhbGciOiJSUzI1NiIsImtpZCI6Im15LWtleS1pZCJ9.eyJpc3MiOiJhdXRoMCJ9.jXrbue3xJmnzWH9kU-uGeCTtgbQEKbch8uHd4Z52t86ncNyepfusl_bsyLJIcxMwK7odRzKiSE9efV9JaRSEDODDBdMeCzODFx82uBM7e46T1NLVSmjYIM7Hcfh81ZeTIk-hITvgtL6hvTdeJWOCZAB0bs18qSVW5SvursRUhY38xnhuNI6HOHCtqp7etxWAu6670L53I3GtXsmi6bXIzv_0v1xZcAFg4HTvXxfhfj3oCqkSs2nC27mHxBmQtmZKWmXk5HzVUyPRwTUWx5wHPT_hCsGer-CMCAyGsmOg466y1KDqf7ogpMYojfVZGWBsyA39LO1oWZ4Ryomkn8t5Vg";
- Algorithm algorithm = Algorithm.RSA256(provider);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailRSA256VerificationWhenProvidedPublicKeyIsNull() {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA256withRSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Public Key is null.")));
- RSAKeyProvider provider = mock(RSAKeyProvider.class);
- when(provider.getPublicKeyById("my-key-id")).thenReturn(null);
- String jwt = "eyJhbGciOiJSUzI1NiIsImtpZCI6Im15LWtleS1pZCJ9.eyJpc3MiOiJhdXRoMCJ9.jXrbue3xJmnzWH9kU-uGeCTtgbQEKbch8uHd4Z52t86ncNyepfusl_bsyLJIcxMwK7odRzKiSE9efV9JaRSEDODDBdMeCzODFx82uBM7e46T1NLVSmjYIM7Hcfh81ZeTIk-hITvgtL6hvTdeJWOCZAB0bs18qSVW5SvursRUhY38xnhuNI6HOHCtqp7etxWAu6670L53I3GtXsmi6bXIzv_0v1xZcAFg4HTvXxfhfj3oCqkSs2nC27mHxBmQtmZKWmXk5HzVUyPRwTUWx5wHPT_hCsGer-CMCAyGsmOg466y1KDqf7ogpMYojfVZGWBsyA39LO1oWZ4Ryomkn8t5Vg";
- Algorithm algorithm = Algorithm.RSA256(provider);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailRSA256VerificationWithInvalidPublicKey() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA256withRSA");
- String jwt = "eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.dxXF3MdsyW-AuvwJpaQtrZ33fAde9xWxpLIg9cO2tMLH2GSRNuLAe61KsJusZhqZB9Iy7DvflcmRz-9OZndm6cj_ThGeJH2LLc90K83UEvvRPo8l85RrQb8PcanxCgIs2RcZOLygERizB3pr5icGkzR7R2y6zgNCjKJ5_NJ6EiZsGN6_nc2PRK_DbyY-Wn0QDxIxKoA5YgQJ9qafe7IN980pXvQv2Z62c3XR8dYuaXBqhthBj-AbaFHEpZapN-V-TmuLNzR2MCB6Xr7BYMuCaqWf_XU8og4XNe8f_8w9Wv5vvgqMM1KhqVpG5VdMJv4o_L4NoCROHhtUQSLRh2M9cA";
- Algorithm algorithm = Algorithm.RSA256((RSAKey) readPublicKeyFromFile(INVALID_PUBLIC_KEY_FILE, "RSA"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailRSA256VerificationWhenUsingPrivateKey() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA256withRSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Public Key is null.")));
- String jwt = "eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.dxXF3MdsyW-AuvwJpaQtrZ33fAde9xWxpLIg9cO2tMLH2GSRNuLAe61KsJusZhqZB9Iy7DvflcmRz-9OZndm6cj_ThGeJH2LLc90K83UEvvRPo8l85RrQb8PcanxCgIs2RcZOLygERizB3pr5icGkzR7R2y6zgNCjKJ5_NJ6EiZsGN6_nc2PRK_DbyY-Wn0QDxIxKoA5YgQJ9qafe7IN980pXvQv2Z62c3XR8dYuaXBqhthBj-AbaFHEpZapN-V-TmuLNzR2MCB6Xr7BYMuCaqWf_XU8og4XNe8f_8w9Wv5vvgqMM1KhqVpG5VdMJv4o_L4NoCROHhtUQSLRh2M9cA";
- Algorithm algorithm = Algorithm.RSA256((RSAKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE, "RSA"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldPassRSA384Verification() throws Exception {
- String jwt = "eyJhbGciOiJSUzM4NCIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.TZlWjXObwGSQOiu2oMq8kiKz0_BR7bbBddNL6G8eZ_GoR82BXOZDqNrQr7lb_M-78XGBguWLWNIdYhzgxOUL9EoCJlrqVm9s9vo6G8T1sj1op-4TbjXZ61TwIvrJee9BvPLdKUJ9_fp1Js5kl6yXkst40Th8Auc5as4n49MLkipjpEhKDKaENKHpSubs1ripSz8SCQZSofeTM_EWVwSw7cpiM8Fy8jOPvWG8Xz4-e3ODFowvHVsDcONX_4FTMNbeRqDuHq2ZhCJnEfzcSJdrve_5VD5fM1LperBVslTrOxIgClOJ3RmM7-WnaizJrWP3D6Z9OLxPxLhM6-jx6tcxEw";
- Algorithm algorithm = Algorithm.RSA384((RSAKey) readPublicKeyFromFile(PUBLIC_KEY_FILE, "RSA"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldPassRSA384VerificationWithBothKeys() throws Exception {
- String jwt = "eyJhbGciOiJSUzM4NCIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.TZlWjXObwGSQOiu2oMq8kiKz0_BR7bbBddNL6G8eZ_GoR82BXOZDqNrQr7lb_M-78XGBguWLWNIdYhzgxOUL9EoCJlrqVm9s9vo6G8T1sj1op-4TbjXZ61TwIvrJee9BvPLdKUJ9_fp1Js5kl6yXkst40Th8Auc5as4n49MLkipjpEhKDKaENKHpSubs1ripSz8SCQZSofeTM_EWVwSw7cpiM8Fy8jOPvWG8Xz4-e3ODFowvHVsDcONX_4FTMNbeRqDuHq2ZhCJnEfzcSJdrve_5VD5fM1LperBVslTrOxIgClOJ3RmM7-WnaizJrWP3D6Z9OLxPxLhM6-jx6tcxEw";
- Algorithm algorithm = Algorithm.RSA384((RSAPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE, "RSA"), (RSAPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE, "RSA"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldPassRSA384VerificationWithProvidedPublicKey() throws Exception {
- RSAKeyProvider provider = mock(RSAKeyProvider.class);
- PublicKey publicKey = readPublicKeyFromFile(PUBLIC_KEY_FILE, "RSA");
- when(provider.getPublicKeyById("my-key-id")).thenReturn((RSAPublicKey) publicKey);
- String jwt = "eyJhbGciOiJSUzM4NCIsImtpZCI6Im15LWtleS1pZCJ9.eyJpc3MiOiJhdXRoMCJ9.ITNTVCT7ercumZKHV4-BXGkJwwa7fyF3CnSfEvm09fDFSkaseDxNo_75WLDmK9WM8RMHTPvkpHcTKm4guYEbC_la7RzFIKpU72bppzQojggSmWWXt_6zq50QP2t5HFMebote1zxhp8ccEdSCX5pyY6J2sm9kJ__HKK32KxIVCTjVCz-bFBS60oG35aYEySdKsxuUdWbD5FQ9I16Ony2x0EPvmlL3GPiAPmgjSFp3LtcBIbCDaoonM7iuDRGIQiDN_n2FKKb1Bt4_38uWPtTkwRpNalt6l53Y3JDdzGI5fMrMo3RQnQlAJxUJKD0eL6dRAA645IVIIXucHwuhgGGIVw";
- Algorithm algorithm = Algorithm.RSA384(provider);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailRSA384VerificationWhenProvidedPublicKeyIsNull() {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA384withRSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Public Key is null.")));
- RSAKeyProvider provider = mock(RSAKeyProvider.class);
- when(provider.getPublicKeyById("my-key-id")).thenReturn(null);
- String jwt = "eyJhbGciOiJSUzM4NCIsImtpZCI6Im15LWtleS1pZCJ9.eyJpc3MiOiJhdXRoMCJ9.ITNTVCT7ercumZKHV4-BXGkJwwa7fyF3CnSfEvm09fDFSkaseDxNo_75WLDmK9WM8RMHTPvkpHcTKm4guYEbC_la7RzFIKpU72bppzQojggSmWWXt_6zq50QP2t5HFMebote1zxhp8ccEdSCX5pyY6J2sm9kJ__HKK32KxIVCTjVCz-bFBS60oG35aYEySdKsxuUdWbD5FQ9I16Ony2x0EPvmlL3GPiAPmgjSFp3LtcBIbCDaoonM7iuDRGIQiDN_n2FKKb1Bt4_38uWPtTkwRpNalt6l53Y3JDdzGI5fMrMo3RQnQlAJxUJKD0eL6dRAA645IVIIXucHwuhgGGIVw";
- Algorithm algorithm = Algorithm.RSA384(provider);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailRSA384VerificationWithInvalidPublicKey() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA384withRSA");
- String jwt = "eyJhbGciOiJSUzM4NCIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.TZlWjXObwGSQOiu2oMq8kiKz0_BR7bbBddNL6G8eZ_GoR82BXOZDqNrQr7lb_M-78XGBguWLWNIdYhzgxOUL9EoCJlrqVm9s9vo6G8T1sj1op-4TbjXZ61TwIvrJee9BvPLdKUJ9_fp1Js5kl6yXkst40Th8Auc5as4n49MLkipjpEhKDKaENKHpSubs1ripSz8SCQZSofeTM_EWVwSw7cpiM8Fy8jOPvWG8Xz4-e3ODFowvHVsDcONX_4FTMNbeRqDuHq2ZhCJnEfzcSJdrve_5VD5fM1LperBVslTrOxIgClOJ3RmM7-WnaizJrWP3D6Z9OLxPxLhM6-jx6tcxEw";
- Algorithm algorithm = Algorithm.RSA384((RSAKey) readPublicKeyFromFile(INVALID_PUBLIC_KEY_FILE, "RSA"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailRSA384VerificationWhenUsingPrivateKey() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA384withRSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Public Key is null.")));
- String jwt = "eyJhbGciOiJSUzM4NCIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.TZlWjXObwGSQOiu2oMq8kiKz0_BR7bbBddNL6G8eZ_GoR82BXOZDqNrQr7lb_M-78XGBguWLWNIdYhzgxOUL9EoCJlrqVm9s9vo6G8T1sj1op-4TbjXZ61TwIvrJee9BvPLdKUJ9_fp1Js5kl6yXkst40Th8Auc5as4n49MLkipjpEhKDKaENKHpSubs1ripSz8SCQZSofeTM_EWVwSw7cpiM8Fy8jOPvWG8Xz4-e3ODFowvHVsDcONX_4FTMNbeRqDuHq2ZhCJnEfzcSJdrve_5VD5fM1LperBVslTrOxIgClOJ3RmM7-WnaizJrWP3D6Z9OLxPxLhM6-jx6tcxEw";
- Algorithm algorithm = Algorithm.RSA384((RSAKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE, "RSA"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldPassRSA512Verification() throws Exception {
- String jwt = "eyJhbGciOiJSUzUxMiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.mvL5LoMyIrWYjk5umEXZTmbyIrkbbcVPUkvdGZbu0qFBxGOf0nXP5PZBvPcOu084lvpwVox5n3VaD4iqzW-PsJyvKFgi5TnwmsbKchAp7JexQEsQOnTSGcfRqeUUiBZqRQdYsho71oAB3T4FnalDdFEpM-fztcZY9XqKyayqZLreTeBjqJm4jfOWH7KfGBHgZExQhe96NLq1UA9eUyQwdOA1Z0SgXe4Ja5PxZ6Fm37KnVDtDlNnY4JAAGFo6y74aGNnp_BKgpaVJCGFu1f1S5xCQ1HSvs8ZSdVWs5NgawW3wRd0kRt_GJ_Y3mIwiF4qUyHWGtsSHu_qjVdCTtbFyow";
- Algorithm algorithm = Algorithm.RSA512((RSAKey) readPublicKeyFromFile(PUBLIC_KEY_FILE, "RSA"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldPassRSA512VerificationWithBothKeys() throws Exception {
- String jwt = "eyJhbGciOiJSUzUxMiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.mvL5LoMyIrWYjk5umEXZTmbyIrkbbcVPUkvdGZbu0qFBxGOf0nXP5PZBvPcOu084lvpwVox5n3VaD4iqzW-PsJyvKFgi5TnwmsbKchAp7JexQEsQOnTSGcfRqeUUiBZqRQdYsho71oAB3T4FnalDdFEpM-fztcZY9XqKyayqZLreTeBjqJm4jfOWH7KfGBHgZExQhe96NLq1UA9eUyQwdOA1Z0SgXe4Ja5PxZ6Fm37KnVDtDlNnY4JAAGFo6y74aGNnp_BKgpaVJCGFu1f1S5xCQ1HSvs8ZSdVWs5NgawW3wRd0kRt_GJ_Y3mIwiF4qUyHWGtsSHu_qjVdCTtbFyow";
- Algorithm algorithm = Algorithm.RSA512((RSAPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE, "RSA"), (RSAPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE, "RSA"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldPassRSA512VerificationWithProvidedPublicKey() throws Exception {
- RSAKeyProvider provider = mock(RSAKeyProvider.class);
- PublicKey publicKey = readPublicKeyFromFile(PUBLIC_KEY_FILE, "RSA");
- when(provider.getPublicKeyById("my-key-id")).thenReturn((RSAPublicKey) publicKey);
- String jwt = "eyJhbGciOiJSUzUxMiIsImtpZCI6Im15LWtleS1pZCJ9.eyJpc3MiOiJhdXRoMCJ9.GpHv85Q8tAU_6hNWsmO0GEpO1qz9lmK3NKeAcemysz9MGo4FXWn8xbD8NjCfzZ8EWphm65M0NArKSjpKHO5-gcNsQxLBVfSED1vzcoaZH_Vy5Rp1M76dGH7JghB_66KrpfyMxer_yRJb-KXesNvIroDGilLQF2ENG-IfLF5nBKlDiVHmPaqr3pm1q20fNLhegkSRca4BJ5VdIlT6kOqE_ykVyCBqzD_oXp3LKO_ARnxoeB9SegIW1fy_3tuxSTKYsCZiOfiyVEXXblAuY3pSLZnGvgeBRnfvmWXDWhP0vVUFtYJBF09eULvvUMVqWcrjUG9gDzzzT7veiY_fHd_x8g";
- Algorithm algorithm = Algorithm.RSA512(provider);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailRSA512VerificationWhenProvidedPublicKeyIsNull() {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA512withRSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Public Key is null.")));
- RSAKeyProvider provider = mock(RSAKeyProvider.class);
- when(provider.getPublicKeyById("my-key-id")).thenReturn(null);
- String jwt = "eyJhbGciOiJSUzUxMiIsImtpZCI6Im15LWtleS1pZCJ9.eyJpc3MiOiJhdXRoMCJ9.GpHv85Q8tAU_6hNWsmO0GEpO1qz9lmK3NKeAcemysz9MGo4FXWn8xbD8NjCfzZ8EWphm65M0NArKSjpKHO5-gcNsQxLBVfSED1vzcoaZH_Vy5Rp1M76dGH7JghB_66KrpfyMxer_yRJb-KXesNvIroDGilLQF2ENG-IfLF5nBKlDiVHmPaqr3pm1q20fNLhegkSRca4BJ5VdIlT6kOqE_ykVyCBqzD_oXp3LKO_ARnxoeB9SegIW1fy_3tuxSTKYsCZiOfiyVEXXblAuY3pSLZnGvgeBRnfvmWXDWhP0vVUFtYJBF09eULvvUMVqWcrjUG9gDzzzT7veiY_fHd_x8g";
- Algorithm algorithm = Algorithm.RSA512(provider);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailRSA512VerificationWithInvalidPublicKey() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA512withRSA");
- String jwt = "eyJhbGciOiJSUzUxMiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.mvL5LoMyIrWYjk5umEXZTmbyIrkbbcVPUkvdGZbu0qFBxGOf0nXP5PZBvPcOu084lvpwVox5n3VaD4iqzW-PsJyvKFgi5TnwmsbKchAp7JexQEsQOnTSGcfRqeUUiBZqRQdYsho71oAB3T4FnalDdFEpM-fztcZY9XqKyayqZLreTeBjqJm4jfOWH7KfGBHgZExQhe96NLq1UA9eUyQwdOA1Z0SgXe4Ja5PxZ6Fm37KnVDtDlNnY4JAAGFo6y74aGNnp_BKgpaVJCGFu1f1S5xCQ1HSvs8ZSdVWs5NgawW3wRd0kRt_GJ_Y3mIwiF4qUyHWGtsSHu_qjVdCTtbFyow";
- Algorithm algorithm = Algorithm.RSA512((RSAKey) readPublicKeyFromFile(INVALID_PUBLIC_KEY_FILE, "RSA"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailRSA512VerificationWhenUsingPrivateKey() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: SHA512withRSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Public Key is null.")));
- String jwt = "eyJhbGciOiJSUzUxMiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.mvL5LoMyIrWYjk5umEXZTmbyIrkbbcVPUkvdGZbu0qFBxGOf0nXP5PZBvPcOu084lvpwVox5n3VaD4iqzW-PsJyvKFgi5TnwmsbKchAp7JexQEsQOnTSGcfRqeUUiBZqRQdYsho71oAB3T4FnalDdFEpM-fztcZY9XqKyayqZLreTeBjqJm4jfOWH7KfGBHgZExQhe96NLq1UA9eUyQwdOA1Z0SgXe4Ja5PxZ6Fm37KnVDtDlNnY4JAAGFo6y74aGNnp_BKgpaVJCGFu1f1S5xCQ1HSvs8ZSdVWs5NgawW3wRd0kRt_GJ_Y3mIwiF4qUyHWGtsSHu_qjVdCTtbFyow";
- Algorithm algorithm = Algorithm.RSA512((RSAKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE, "RSA"));
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldThrowWhenMacAlgorithmDoesNotExists() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: some-alg");
- exception.expectCause(isA(NoSuchAlgorithmException.class));
-
- CryptoHelper crypto = mock(CryptoHelper.class);
- when(crypto.verifySignatureFor(anyString(), any(PublicKey.class), any(String.class), any(String.class), any(byte[].class)))
- .thenThrow(NoSuchAlgorithmException.class);
-
- RSAPublicKey publicKey = mock(RSAPublicKey.class);
- RSAPrivateKey privateKey = mock(RSAPrivateKey.class);
- RSAKeyProvider provider = RSAAlgorithm.providerForKeys(publicKey, privateKey);
- Algorithm algorithm = new RSAAlgorithm(crypto, "some-alg", "some-algorithm", provider);
- String jwt = "eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.dxXF3MdsyW-AuvwJpaQtrZ33fAde9xWxpLIg9cO2tMLH2GSRNuLAe61KsJusZhqZB9Iy7DvflcmRz-9OZndm6cj_ThGeJH2LLc90K83UEvvRPo8l85RrQb8PcanxCgIs2RcZOLygERizB3pr5icGkzR7R2y6zgNCjKJ5_NJ6EiZsGN6_nc2PRK_DbyY-Wn0QDxIxKoA5YgQJ9qafe7IN980pXvQv2Z62c3XR8dYuaXBqhthBj-AbaFHEpZapN-V-TmuLNzR2MCB6Xr7BYMuCaqWf_XU8og4XNe8f_8w9Wv5vvgqMM1KhqVpG5VdMJv4o_L4NoCROHhtUQSLRh2M9cA";
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldThrowWhenThePublicKeyIsInvalid() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: some-alg");
- exception.expectCause(isA(InvalidKeyException.class));
-
- CryptoHelper crypto = mock(CryptoHelper.class);
- when(crypto.verifySignatureFor(anyString(), any(PublicKey.class), any(String.class), any(String.class), any(byte[].class)))
- .thenThrow(InvalidKeyException.class);
-
- RSAPublicKey publicKey = mock(RSAPublicKey.class);
- RSAPrivateKey privateKey = mock(RSAPrivateKey.class);
- RSAKeyProvider provider = RSAAlgorithm.providerForKeys(publicKey, privateKey);
- Algorithm algorithm = new RSAAlgorithm(crypto, "some-alg", "some-algorithm", provider);
- String jwt = "eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.dxXF3MdsyW-AuvwJpaQtrZ33fAde9xWxpLIg9cO2tMLH2GSRNuLAe61KsJusZhqZB9Iy7DvflcmRz-9OZndm6cj_ThGeJH2LLc90K83UEvvRPo8l85RrQb8PcanxCgIs2RcZOLygERizB3pr5icGkzR7R2y6zgNCjKJ5_NJ6EiZsGN6_nc2PRK_DbyY-Wn0QDxIxKoA5YgQJ9qafe7IN980pXvQv2Z62c3XR8dYuaXBqhthBj-AbaFHEpZapN-V-TmuLNzR2MCB6Xr7BYMuCaqWf_XU8og4XNe8f_8w9Wv5vvgqMM1KhqVpG5VdMJv4o_L4NoCROHhtUQSLRh2M9cA";
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldThrowWhenTheSignatureIsNotPrepared() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectMessage("The Token's Signature resulted invalid when verified using the Algorithm: some-alg");
- exception.expectCause(isA(SignatureException.class));
-
- CryptoHelper crypto = mock(CryptoHelper.class);
- when(crypto.verifySignatureFor(anyString(), any(PublicKey.class), any(String.class), any(String.class), any(byte[].class)))
- .thenThrow(SignatureException.class);
-
- RSAPublicKey publicKey = mock(RSAPublicKey.class);
- RSAPrivateKey privateKey = mock(RSAPrivateKey.class);
- RSAKeyProvider provider = RSAAlgorithm.providerForKeys(publicKey, privateKey);
- Algorithm algorithm = new RSAAlgorithm(crypto, "some-alg", "some-algorithm", provider);
- String jwt = "eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.dxXF3MdsyW-AuvwJpaQtrZ33fAde9xWxpLIg9cO2tMLH2GSRNuLAe61KsJusZhqZB9Iy7DvflcmRz-9OZndm6cj_ThGeJH2LLc90K83UEvvRPo8l85RrQb8PcanxCgIs2RcZOLygERizB3pr5icGkzR7R2y6zgNCjKJ5_NJ6EiZsGN6_nc2PRK_DbyY-Wn0QDxIxKoA5YgQJ9qafe7IN980pXvQv2Z62c3XR8dYuaXBqhthBj-AbaFHEpZapN-V-TmuLNzR2MCB6Xr7BYMuCaqWf_XU8og4XNe8f_8w9Wv5vvgqMM1KhqVpG5VdMJv4o_L4NoCROHhtUQSLRh2M9cA";
- algorithm.verify(JWT.decode(jwt));
- }
-
-
- //Sign
- private static final String RS256Header = "eyJhbGciOiJSUzI1NiJ9";
- private static final String RS384Header = "eyJhbGciOiJSUzM4NCJ9";
- private static final String RS512Header = "eyJhbGciOiJSUzUxMiJ9";
- private static final String auth0IssPayload = "eyJpc3MiOiJhdXRoMCJ9";
-
- @Test
- public void shouldDoRSA256Signing() throws Exception {
- Algorithm algorithmSign = Algorithm.RSA256((RSAKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE, "RSA"));
- Algorithm algorithmVerify = Algorithm.RSA256((RSAKey) readPublicKeyFromFile(PUBLIC_KEY_FILE, "RSA"));
-
- String jwt = asJWT(algorithmSign, RS256Header, auth0IssPayload);
- String expectedSignature = "ZB-Tr0vLtnf8I9fhSdSjU6HZei5xLYZQ6nZqM5O6Va0W9PgAqgRT7ShI9CjeYulRXPHvVmSl5EQuYuXdBzM0-H_3p_Nsl6tSMy4EyX2kkhEm6T0HhvarTh8CG0PCjn5p6FP5ZxWwhLcmRN70ItP6Z5MMO4CcJh1JrNxR4Fi4xQgt-CK2aVDMFXd-Br5yQiLVx1CX83w28OD9wssW3Rdltl5e66vCef0Ql6Q5I5e5F0nqGYT989a9fkNgLIx2F8k_az5x07BY59FV2SZg59nSiY7TZNjP8ot11Ew7HKRfPXOdh9eKRUVdhcxzqDePhyzKabU8TG5FP0SiWH5qVPfAgw";
-
- assertSignaturePresent(jwt);
- assertSignatureValue(jwt, expectedSignature);
- algorithmVerify.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldDoRSA256SigningWithBothKeys() throws Exception {
- Algorithm algorithm = Algorithm.RSA256((RSAPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE, "RSA"), (RSAPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE, "RSA"));
-
- String jwt = asJWT(algorithm, RS256Header, auth0IssPayload);
- String expectedSignature = "ZB-Tr0vLtnf8I9fhSdSjU6HZei5xLYZQ6nZqM5O6Va0W9PgAqgRT7ShI9CjeYulRXPHvVmSl5EQuYuXdBzM0-H_3p_Nsl6tSMy4EyX2kkhEm6T0HhvarTh8CG0PCjn5p6FP5ZxWwhLcmRN70ItP6Z5MMO4CcJh1JrNxR4Fi4xQgt-CK2aVDMFXd-Br5yQiLVx1CX83w28OD9wssW3Rdltl5e66vCef0Ql6Q5I5e5F0nqGYT989a9fkNgLIx2F8k_az5x07BY59FV2SZg59nSiY7TZNjP8ot11Ew7HKRfPXOdh9eKRUVdhcxzqDePhyzKabU8TG5FP0SiWH5qVPfAgw";
-
- assertSignaturePresent(jwt);
- assertSignatureValue(jwt, expectedSignature);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldDoRSA256SigningWithProvidedPrivateKey() throws Exception {
- RSAKeyProvider provider = mock(RSAKeyProvider.class);
- PrivateKey privateKey = readPrivateKeyFromFile(PRIVATE_KEY_FILE, "RSA");
- PublicKey publicKey = readPublicKeyFromFile(PUBLIC_KEY_FILE, "RSA");
- when(provider.getPrivateKey()).thenReturn((RSAPrivateKey) privateKey);
- when(provider.getPublicKeyById(null)).thenReturn((RSAPublicKey) publicKey);
- Algorithm algorithm = Algorithm.RSA256(provider);
-
- String jwt = asJWT(algorithm, RS256Header, auth0IssPayload);
-
- assertSignaturePresent(jwt);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailOnRSA256SigningWhenProvidedPrivateKeyIsNull() {
- exception.expect(SignatureGenerationException.class);
- exception.expectMessage("The Token's Signature couldn't be generated when signing using the Algorithm: SHA256withRSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Private Key is null.")));
-
- RSAKeyProvider provider = mock(RSAKeyProvider.class);
- when(provider.getPrivateKey()).thenReturn(null);
- Algorithm algorithm = Algorithm.RSA256(provider);
- algorithm.sign(new byte[0], new byte[0]);
- }
-
- @Test
- public void shouldFailOnRSA256SigningWhenUsingPublicKey() throws Exception {
- exception.expect(SignatureGenerationException.class);
- exception.expectMessage("The Token's Signature couldn't be generated when signing using the Algorithm: SHA256withRSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Private Key is null.")));
-
- Algorithm algorithm = Algorithm.RSA256((RSAKey) readPublicKeyFromFile(PUBLIC_KEY_FILE, "RSA"));
- algorithm.sign(new byte[0], new byte[0]);
- }
-
- @Test
- public void shouldDoRSA384Signing() throws Exception {
- Algorithm algorithmSign = Algorithm.RSA384((RSAKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE, "RSA"));
- Algorithm algorithmVerify = Algorithm.RSA384((RSAKey) readPublicKeyFromFile(PUBLIC_KEY_FILE, "RSA"));
-
- String jwt = asJWT(algorithmSign, RS384Header, auth0IssPayload);
- String expectedSignature = "Jx1PaTBnjd_U56MNjifFcY7w9ImDbseg0y8Ijr2pSiA1_wzQb_wy9undaWfzR5YqdIAXvjS8AGuZUAzIoTG4KMgOgdVyYDz3l2jzj6wI-lgqfR5hTy1w1ruMUQ4_wobpdxAiJ4fEbg8Mi_GljOiCO-P1HilxKnpiOJZidR8MQGwTInsf71tOUkK4x5UsdmUueuZbaU-CL5kPnRfXmJj9CcdxZbD9oMlbo23dwkP5BNMrS2LwGGzc9C_-ypxrBIOVilG3WZxcSmuG86LjcZbnL6LBEfph5NmKBgQav147uipb_7umBEr1m2dYiB_9u606n3bcoo3rnsYYK_Xfi1GAEQ";
-
- assertSignaturePresent(jwt);
- assertSignatureValue(jwt, expectedSignature);
- algorithmVerify.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldDoRSA384SigningWithBothKeys() throws Exception {
- Algorithm algorithm = Algorithm.RSA384((RSAPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE, "RSA"), (RSAPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE, "RSA"));
-
- String jwt = asJWT(algorithm, RS384Header, auth0IssPayload);
- String expectedSignature = "Jx1PaTBnjd_U56MNjifFcY7w9ImDbseg0y8Ijr2pSiA1_wzQb_wy9undaWfzR5YqdIAXvjS8AGuZUAzIoTG4KMgOgdVyYDz3l2jzj6wI-lgqfR5hTy1w1ruMUQ4_wobpdxAiJ4fEbg8Mi_GljOiCO-P1HilxKnpiOJZidR8MQGwTInsf71tOUkK4x5UsdmUueuZbaU-CL5kPnRfXmJj9CcdxZbD9oMlbo23dwkP5BNMrS2LwGGzc9C_-ypxrBIOVilG3WZxcSmuG86LjcZbnL6LBEfph5NmKBgQav147uipb_7umBEr1m2dYiB_9u606n3bcoo3rnsYYK_Xfi1GAEQ";
-
- assertSignaturePresent(jwt);
- assertSignatureValue(jwt, expectedSignature);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldDoRSA384SigningWithProvidedPrivateKey() throws Exception {
- RSAKeyProvider provider = mock(RSAKeyProvider.class);
- PrivateKey privateKey = readPrivateKeyFromFile(PRIVATE_KEY_FILE, "RSA");
- PublicKey publicKey = readPublicKeyFromFile(PUBLIC_KEY_FILE, "RSA");
- when(provider.getPrivateKey()).thenReturn((RSAPrivateKey) privateKey);
- when(provider.getPublicKeyById(null)).thenReturn((RSAPublicKey) publicKey);
- Algorithm algorithm = Algorithm.RSA384(provider);
-
- String jwt = asJWT(algorithm, RS384Header, auth0IssPayload);
-
- assertSignaturePresent(jwt);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailOnRSA384SigningWhenProvidedPrivateKeyIsNull() {
- exception.expect(SignatureGenerationException.class);
- exception.expectMessage("The Token's Signature couldn't be generated when signing using the Algorithm: SHA384withRSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Private Key is null.")));
-
- RSAKeyProvider provider = mock(RSAKeyProvider.class);
- when(provider.getPrivateKey()).thenReturn(null);
- Algorithm algorithm = Algorithm.RSA384(provider);
- algorithm.sign(new byte[0], new byte[0]);
- }
-
- @Test
- public void shouldFailOnRSA384SigningWhenUsingPublicKey() throws Exception {
- exception.expect(SignatureGenerationException.class);
- exception.expectMessage("The Token's Signature couldn't be generated when signing using the Algorithm: SHA384withRSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Private Key is null.")));
-
- Algorithm algorithm = Algorithm.RSA384((RSAKey) readPublicKeyFromFile(PUBLIC_KEY_FILE, "RSA"));
- algorithm.sign(new byte[0], new byte[0]);
- }
-
- @Test
- public void shouldDoRSA512Signing() throws Exception {
- Algorithm algorithmSign = Algorithm.RSA512((RSAKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE, "RSA"));
- Algorithm algorithmVerify = Algorithm.RSA512((RSAKey) readPublicKeyFromFile(PUBLIC_KEY_FILE, "RSA"));
-
- String jwt = asJWT(algorithmSign, RS512Header, auth0IssPayload);
- String expectedSignature = "THIPVYzNZ1Yo_dm0k1UELqV0txs3SzyMopCyHcLXOOdgYXF4MlGvBqu0CFvgSga72Sp5LpuC1Oesj40v_QDsp2GTGDeWnvvcv_eo-b0LPSpmT2h1Ibrmu-z70u2rKf28pkN-AJiMFqi8sit2kMIp1bwIVOovPvMTQKGFmova4Xwb3G526y_PeLlflW1h69hQTIVcI67ACEkAC-byjDnnYIklA-B4GWcggEoFwQRTdRjAUpifA6HOlvnBbZZlUd6KXwEydxVS-eh1odwPjB2_sfbyy5HnLsvNdaniiZQwX7QbwLNT4F72LctYdHHM1QCrID6bgfgYp9Ij9CRX__XDEA";
-
- assertSignaturePresent(jwt);
- assertSignatureValue(jwt, expectedSignature);
- algorithmVerify.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldDoRSA512SigningWithBothKeys() throws Exception {
- Algorithm algorithm = Algorithm.RSA512((RSAPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE, "RSA"), (RSAPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE, "RSA"));
-
- String jwt = asJWT(algorithm, RS512Header, auth0IssPayload);
- String expectedSignature = "THIPVYzNZ1Yo_dm0k1UELqV0txs3SzyMopCyHcLXOOdgYXF4MlGvBqu0CFvgSga72Sp5LpuC1Oesj40v_QDsp2GTGDeWnvvcv_eo-b0LPSpmT2h1Ibrmu-z70u2rKf28pkN-AJiMFqi8sit2kMIp1bwIVOovPvMTQKGFmova4Xwb3G526y_PeLlflW1h69hQTIVcI67ACEkAC-byjDnnYIklA-B4GWcggEoFwQRTdRjAUpifA6HOlvnBbZZlUd6KXwEydxVS-eh1odwPjB2_sfbyy5HnLsvNdaniiZQwX7QbwLNT4F72LctYdHHM1QCrID6bgfgYp9Ij9CRX__XDEA";
-
- assertSignaturePresent(jwt);
- assertSignatureValue(jwt, expectedSignature);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldDoRSA512SigningWithProvidedPrivateKey() throws Exception {
- RSAKeyProvider provider = mock(RSAKeyProvider.class);
- PrivateKey privateKey = readPrivateKeyFromFile(PRIVATE_KEY_FILE, "RSA");
- PublicKey publicKey = readPublicKeyFromFile(PUBLIC_KEY_FILE, "RSA");
- when(provider.getPrivateKey()).thenReturn((RSAPrivateKey) privateKey);
- when(provider.getPublicKeyById(null)).thenReturn((RSAPublicKey) publicKey);
- Algorithm algorithm = Algorithm.RSA512(provider);
-
- String jwt = asJWT(algorithm, RS512Header, auth0IssPayload);
-
- assertSignaturePresent(jwt);
- algorithm.verify(JWT.decode(jwt));
- }
-
- @Test
- public void shouldFailOnRSA512SigningWhenProvidedPrivateKeyIsNull() {
- exception.expect(SignatureGenerationException.class);
- exception.expectMessage("The Token's Signature couldn't be generated when signing using the Algorithm: SHA512withRSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Private Key is null.")));
-
- RSAKeyProvider provider = mock(RSAKeyProvider.class);
- when(provider.getPrivateKey()).thenReturn(null);
- Algorithm algorithm = Algorithm.RSA512(provider);
- algorithm.sign(new byte[0], new byte[0]);
- }
-
- @Test
- public void shouldFailOnRSA512SigningWhenUsingPublicKey() throws Exception {
- exception.expect(SignatureGenerationException.class);
- exception.expectMessage("The Token's Signature couldn't be generated when signing using the Algorithm: SHA512withRSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Private Key is null.")));
-
- Algorithm algorithm = Algorithm.RSA512((RSAKey) readPublicKeyFromFile(PUBLIC_KEY_FILE, "RSA"));
- algorithm.sign(new byte[0], new byte[0]);
- }
-
- @Test
- public void shouldThrowOnSignWhenSignatureAlgorithmDoesNotExists() throws Exception {
- exception.expect(SignatureGenerationException.class);
- exception.expectMessage("The Token's Signature couldn't be generated when signing using the Algorithm: some-algorithm");
- exception.expectCause(isA(NoSuchAlgorithmException.class));
-
- CryptoHelper crypto = mock(CryptoHelper.class);
- when(crypto.createSignatureFor(anyString(), any(PrivateKey.class), any(byte[].class), any(byte[].class)))
- .thenThrow(NoSuchAlgorithmException.class);
-
- RSAPublicKey publicKey = mock(RSAPublicKey.class);
- RSAPrivateKey privateKey = mock(RSAPrivateKey.class);
- RSAKeyProvider provider = RSAAlgorithm.providerForKeys(publicKey, privateKey);
- Algorithm algorithm = new RSAAlgorithm(crypto, "some-alg", "some-algorithm", provider);
- algorithm.sign(new byte[0], new byte[0]);
- }
-
- @Test
- public void shouldThrowOnSignWhenThePrivateKeyIsInvalid() throws Exception {
- exception.expect(SignatureGenerationException.class);
- exception.expectMessage("The Token's Signature couldn't be generated when signing using the Algorithm: some-algorithm");
- exception.expectCause(isA(InvalidKeyException.class));
-
- CryptoHelper crypto = mock(CryptoHelper.class);
- when(crypto.createSignatureFor(anyString(), any(PrivateKey.class), any(byte[].class), any(byte[].class)))
- .thenThrow(InvalidKeyException.class);
-
- RSAPublicKey publicKey = mock(RSAPublicKey.class);
- RSAPrivateKey privateKey = mock(RSAPrivateKey.class);
- RSAKeyProvider provider = RSAAlgorithm.providerForKeys(publicKey, privateKey);
- Algorithm algorithm = new RSAAlgorithm(crypto, "some-alg", "some-algorithm", provider);
- algorithm.sign(new byte[0], new byte[0]);
- }
-
- @Test
- public void shouldThrowOnSignWhenTheSignatureIsNotPrepared() throws Exception {
- exception.expect(SignatureGenerationException.class);
- exception.expectMessage("The Token's Signature couldn't be generated when signing using the Algorithm: some-algorithm");
- exception.expectCause(isA(SignatureException.class));
-
- CryptoHelper crypto = mock(CryptoHelper.class);
- when(crypto.createSignatureFor(anyString(), any(PrivateKey.class), any(byte[].class), any(byte[].class)))
- .thenThrow(SignatureException.class);
-
- RSAPublicKey publicKey = mock(RSAPublicKey.class);
- RSAPrivateKey privateKey = mock(RSAPrivateKey.class);
- RSAKeyProvider provider = RSAAlgorithm.providerForKeys(publicKey, privateKey);
- Algorithm algorithm = new RSAAlgorithm(crypto, "some-alg", "some-algorithm", provider);
- algorithm.sign(new byte[0], new byte[0]);
- }
-
- @Test
- public void shouldReturnNullSigningKeyIdIfCreatedWithDefaultProvider() {
- RSAPublicKey publicKey = mock(RSAPublicKey.class);
- RSAPrivateKey privateKey = mock(RSAPrivateKey.class);
- RSAKeyProvider provider = RSAAlgorithm.providerForKeys(publicKey, privateKey);
- Algorithm algorithm = new RSAAlgorithm("some-alg", "some-algorithm", provider);
-
- assertThat(algorithm.getSigningKeyId(), is(nullValue()));
- }
-
- @Test
- public void shouldReturnSigningKeyIdFromProvider() {
- RSAKeyProvider provider = mock(RSAKeyProvider.class);
- when(provider.getPrivateKeyId()).thenReturn("keyId");
- Algorithm algorithm = new RSAAlgorithm("some-alg", "some-algorithm", provider);
-
- assertThat(algorithm.getSigningKeyId(), is("keyId"));
- }
-
- @Test
- public void shouldBeEqualSignatureMethodResults() throws Exception {
- RSAPrivateKey privateKey = (RSAPrivateKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE, "RSA");
- RSAPublicKey publicKey = (RSAPublicKey) readPublicKeyFromFile(PUBLIC_KEY_FILE, "RSA");
-
- Algorithm algorithm = Algorithm.RSA256(publicKey, privateKey);
-
- byte[] header = new byte[]{0x00, 0x01, 0x02};
- byte[] payload = new byte[]{0x04, 0x05, 0x06};
-
- ByteArrayOutputStream bout = new ByteArrayOutputStream();
- bout.write(header);
- bout.write('.');
- bout.write(payload);
-
- assertThat(algorithm.sign(bout.toByteArray()), is(algorithm.sign(header, payload)));
- }
-
- /**
- * Test deprecated signing method error handling.
- *
- * @see {@linkplain #shouldFailOnRSA256SigningWhenProvidedPrivateKeyIsNull}
- */
-
- @Test
- public void shouldFailOnRSA256SigningWithDeprecatedMethodWhenProvidedPrivateKeyIsNull() {
- exception.expect(SignatureGenerationException.class);
- exception.expectMessage("The Token's Signature couldn't be generated when signing using the Algorithm: SHA256withRSA");
- exception.expectCause(isA(IllegalStateException.class));
- exception.expectCause(hasMessage(is("The given Private Key is null.")));
-
- RSAKeyProvider provider = mock(RSAKeyProvider.class);
- when(provider.getPrivateKey()).thenReturn(null);
- Algorithm algorithm = Algorithm.RSA256(provider);
- algorithm.sign(new byte[0]);
- }
-
- @Test
- public void shouldThrowWhenSignatureNotValidBase64() throws Exception {
- exception.expect(SignatureVerificationException.class);
- exception.expectCause(isA(IllegalArgumentException.class));
-
- String jwt = "eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJhdXRoMCJ9.dxXF3MdsyW-AuvwJpaQtrZ33fAde9xWxpLIg9cO2tMLH2GSRNu+LAe61KsJusZhqZB9Iy7DvflcmRz-9OZndm6cj_ThGeJH2LLc90K83UEvvRPo8l85RrQb8PcanxCgIs2RcZOLygERizB3pr5icGkzR7R2y6zgNCjKJ5_NJ6EiZsGN6_nc2PRK_DbyY-Wn0QDxIxKoA5YgQJ9qafe7IN980pXvQv2Z62c3XR8dYuaXBqhthBj-AbaFHEpZapN-V-TmuLNzR2MCB6Xr7BYMuCaqWf_XU8og4XNe8f_8w9Wv5vvgqMM1KhqVpG5VdMJv4o_L4NoCROHhtUQSLRh2M9cA";
- Algorithm algorithm = Algorithm.RSA256((RSAKey) readPrivateKeyFromFile(PRIVATE_KEY_FILE, "RSA"));
- algorithm.verify(JWT.decode(jwt));
- }
-}
\ No newline at end of file
diff --git a/lib/src/test/java/com/auth0/jwt/impl/BasicHeaderTest.java b/lib/src/test/java/com/auth0/jwt/impl/BasicHeaderTest.java
deleted file mode 100644
index c4a04d81..00000000
--- a/lib/src/test/java/com/auth0/jwt/impl/BasicHeaderTest.java
+++ /dev/null
@@ -1,141 +0,0 @@
-package com.auth0.jwt.impl;
-
-import com.fasterxml.jackson.databind.JsonNode;
-import com.fasterxml.jackson.databind.ObjectMapper;
-import com.fasterxml.jackson.databind.ObjectReader;
-import com.fasterxml.jackson.databind.node.NullNode;
-import com.fasterxml.jackson.databind.node.TextNode;
-import org.hamcrest.collection.IsMapContaining;
-import org.junit.Rule;
-import org.junit.Test;
-import org.junit.rules.ExpectedException;
-
-import java.util.HashMap;
-import java.util.Map;
-
-import static org.hamcrest.MatcherAssert.assertThat;
-import static org.hamcrest.Matchers.*;
-
-public class BasicHeaderTest {
-
- @Rule
- public ExpectedException exception = ExpectedException.none();
-
- private ObjectReader objectReader = new ObjectMapper().reader();
-
- @SuppressWarnings("Convert2Diamond")
- @Test
- public void shouldHaveUnmodifiableTreeWhenInstantiatedWithNonNullTree() {
- exception.expect(UnsupportedOperationException.class);
- BasicHeader header = new BasicHeader(null, null, null, null, new HashMap(), objectReader);
- header.getTree().put("something", null);
- }
-
- @Test
- public void shouldHaveUnmodifiableTreeWhenInstantiatedWithNullTree() {
- exception.expect(UnsupportedOperationException.class);
- BasicHeader header = new BasicHeader(null, null, null, null, null, objectReader);
- header.getTree().put("something", null);
- }
-
- @Test
- public void shouldHaveTree() {
- HashMap map = new HashMap<>();
- JsonNode node = NullNode.getInstance();
- map.put("key", node);
- BasicHeader header = new BasicHeader(null, null, null, null, map, objectReader);
-
- assertThat(header.getTree(), is(notNullValue()));
- assertThat(header.getTree(), is(IsMapContaining.hasEntry("key", node)));
- }
-
- @Test
- public void shouldGetAlgorithm() {
- BasicHeader header = new BasicHeader("HS256", null, null, null, null, objectReader);
-
- assertThat(header, is(notNullValue()));
- assertThat(header.getAlgorithm(), is(notNullValue()));
- assertThat(header.getAlgorithm(), is("HS256"));
- }
-
- @Test
- public void shouldGetNullAlgorithmIfMissing() {
- BasicHeader header = new BasicHeader(null, null, null, null, null, objectReader);
-
- assertThat(header, is(notNullValue()));
- assertThat(header.getAlgorithm(), is(nullValue()));
- }
-
- @Test
- public void shouldGetType() {
- BasicHeader header = new BasicHeader(null, "jwt", null, null, null, objectReader);
-
- assertThat(header, is(notNullValue()));
- assertThat(header.getType(), is(notNullValue()));
- assertThat(header.getType(), is("jwt"));
- }
-
- @Test
- public void shouldGetNullTypeIfMissing() {
- BasicHeader header = new BasicHeader(null, null, null, null, null, objectReader);
-
- assertThat(header, is(notNullValue()));
- assertThat(header.getType(), is(nullValue()));
- }
-
- @Test
- public void shouldGetContentType() {
- BasicHeader header = new BasicHeader(null, null, "content", null, null, objectReader);
-
- assertThat(header, is(notNullValue()));
- assertThat(header.getContentType(), is(notNullValue()));
- assertThat(header.getContentType(), is("content"));
- }
-
- @Test
- public void shouldGetNullContentTypeIfMissing() {
- BasicHeader header = new BasicHeader(null, null, null, null, null, objectReader);
-
- assertThat(header, is(notNullValue()));
- assertThat(header.getContentType(), is(nullValue()));
- }
-
- @Test
- public void shouldGetKeyId() {
- BasicHeader header = new BasicHeader(null, null, null, "key", null, objectReader);
-
- assertThat(header, is(notNullValue()));
- assertThat(header.getKeyId(), is(notNullValue()));
- assertThat(header.getKeyId(), is("key"));
- }
-
- @Test
- public void shouldGetNullKeyIdIfMissing() {
- BasicHeader header = new BasicHeader(null, null, null, null, null, objectReader);
-
- assertThat(header, is(notNullValue()));
- assertThat(header.getKeyId(), is(nullValue()));
- }
-
- @Test
- public void shouldGetExtraClaim() {
- Map tree = new HashMap<>();
- tree.put("extraClaim", new TextNode("extraValue"));
- BasicHeader header = new BasicHeader(null, null, null, null, tree, objectReader);
-
- assertThat(header, is(notNullValue()));
- assertThat(header.getHeaderClaim("extraClaim"), is(instanceOf(JsonNodeClaim.class)));
- assertThat(header.getHeaderClaim("extraClaim").asString(), is("extraValue"));
- }
-
- @Test
- public void shouldGetNotNullExtraClaimIfMissing() {
- Map tree = new HashMap<>();
- BasicHeader header = new BasicHeader(null, null, null, null, tree, objectReader);
-
- assertThat(header, is(notNullValue()));
- assertThat(header.getHeaderClaim("missing"), is(notNullValue()));
- assertThat(header.getHeaderClaim("missing").isMissing(), is(true));
- assertThat(header.getHeaderClaim("missing").isNull(), is(false));
- }
-}
\ No newline at end of file
diff --git a/lib/src/test/java/com/auth0/jwt/impl/HeaderDeserializerTest.java b/lib/src/test/java/com/auth0/jwt/impl/HeaderDeserializerTest.java
deleted file mode 100644
index 02d782a7..00000000
--- a/lib/src/test/java/com/auth0/jwt/impl/HeaderDeserializerTest.java
+++ /dev/null
@@ -1,119 +0,0 @@
-package com.auth0.jwt.impl;
-
-import com.auth0.jwt.exceptions.JWTDecodeException;
-import com.auth0.jwt.interfaces.Header;
-import com.fasterxml.jackson.core.JsonFactory;
-import com.fasterxml.jackson.core.JsonParser;
-import com.fasterxml.jackson.core.ObjectCodec;
-import com.fasterxml.jackson.core.type.TypeReference;
-import com.fasterxml.jackson.databind.DeserializationContext;
-import com.fasterxml.jackson.databind.JsonDeserializer;
-import com.fasterxml.jackson.databind.JsonNode;
-import com.fasterxml.jackson.databind.ObjectMapper;
-import com.fasterxml.jackson.databind.node.NullNode;
-import com.fasterxml.jackson.databind.node.TextNode;
-import org.junit.Before;
-import org.junit.Rule;
-import org.junit.Test;
-import org.junit.rules.ExpectedException;
-
-import java.io.StringReader;
-import java.util.HashMap;
-import java.util.Map;
-
-import static org.hamcrest.MatcherAssert.assertThat;
-import static org.hamcrest.Matchers.is;
-import static org.hamcrest.Matchers.notNullValue;
-import static org.hamcrest.Matchers.nullValue;
-import static org.mockito.ArgumentMatchers.any;
-import static org.mockito.ArgumentMatchers.eq;
-import static org.mockito.Mockito.mock;
-import static org.mockito.Mockito.when;
-
-public class HeaderDeserializerTest {
-
- @Rule
- public ExpectedException exception = ExpectedException.none();
- private HeaderDeserializer deserializer;
-
- @Before
- public void setUp() {
- deserializer = new HeaderDeserializer();
- }
-
- @Test
- public void shouldThrowOnNullTree() throws Exception {
- exception.expect(JWTDecodeException.class);
- exception.expectMessage("Parsing the Header's JSON resulted on a Null map");
-
- JsonDeserializer deserializer = new HeaderDeserializer();
- JsonParser parser = mock(JsonParser.class);
- ObjectCodec codec = mock(ObjectCodec.class);
- DeserializationContext context = mock(DeserializationContext.class);
-
- when(codec.readValue(eq(parser), any(TypeReference.class))).thenReturn(null);
- when(parser.getCodec()).thenReturn(codec);
-
- deserializer.deserialize(parser, context);
- }
-
-
- @Test
- public void shouldNotRemoveKnownPublicClaimsFromTree() throws Exception {
- String headerJSON = "{\n" +
- " \"alg\": \"HS256\",\n" +
- " \"typ\": \"jws\",\n" +
- " \"cty\": \"content\",\n" +
- " \"kid\": \"key\",\n" +
- " \"roles\": \"admin\"\n" +
- "}";
- StringReader reader = new StringReader(headerJSON);
- JsonParser jsonParser = new JsonFactory().createParser(reader);
- ObjectMapper mapper = new ObjectMapper();
- jsonParser.setCodec(mapper);
-
- Header header = deserializer.deserialize(jsonParser, mapper.getDeserializationContext());
-
- assertThat(header, is(notNullValue()));
- assertThat(header.getAlgorithm(), is("HS256"));
- assertThat(header.getType(), is("jws"));
- assertThat(header.getContentType(), is("content"));
- assertThat(header.getKeyId(), is("key"));
-
- assertThat(header.getHeaderClaim("roles").asString(), is("admin"));
- assertThat(header.getHeaderClaim("alg").asString(), is("HS256"));
- assertThat(header.getHeaderClaim("typ").asString(), is("jws"));
- assertThat(header.getHeaderClaim("cty").asString(), is("content"));
- assertThat(header.getHeaderClaim("kid").asString(), is("key"));
- }
-
- @Test
- public void shouldGetNullStringWhenParsingNullNode() {
- Map tree = new HashMap<>();
- NullNode node = NullNode.getInstance();
- tree.put("key", node);
-
- String text = deserializer.getString(tree, "key");
- assertThat(text, is(nullValue()));
- }
-
- @Test
- public void shouldGetNullStringWhenParsingNull() {
- Map tree = new HashMap<>();
- tree.put("key", null);
-
- String text = deserializer.getString(tree, "key");
- assertThat(text, is(nullValue()));
- }
-
- @Test
- public void shouldGetStringWhenParsingTextNode() {
- Map tree = new HashMap<>();
- TextNode node = new TextNode("something here");
- tree.put("key", node);
-
- String text = deserializer.getString(tree, "key");
- assertThat(text, is(notNullValue()));
- assertThat(text, is("something here"));
- }
-}
\ No newline at end of file
diff --git a/lib/src/test/java/com/auth0/jwt/impl/JWTParserTest.java b/lib/src/test/java/com/auth0/jwt/impl/JWTParserTest.java
deleted file mode 100644
index da62131a..00000000
--- a/lib/src/test/java/com/auth0/jwt/impl/JWTParserTest.java
+++ /dev/null
@@ -1,116 +0,0 @@
-package com.auth0.jwt.impl;
-
-import com.auth0.jwt.exceptions.JWTDecodeException;
-import com.auth0.jwt.interfaces.Header;
-import com.auth0.jwt.interfaces.Payload;
-import com.fasterxml.jackson.databind.Module;
-import com.fasterxml.jackson.databind.ObjectMapper;
-import com.fasterxml.jackson.databind.ObjectReader;
-import com.fasterxml.jackson.databind.SerializationFeature;
-import org.junit.Before;
-import org.junit.Rule;
-import org.junit.Test;
-import org.junit.rules.ExpectedException;
-
-import static com.auth0.jwt.impl.JWTParser.getDefaultObjectMapper;
-import static org.hamcrest.MatcherAssert.assertThat;
-import static org.hamcrest.Matchers.*;
-import static org.mockito.ArgumentMatchers.any;
-import static org.mockito.Mockito.mock;
-import static org.mockito.Mockito.verify;
-import static org.mockito.Mockito.when;
-
-public class JWTParserTest {
-
- @Rule
- public ExpectedException exception = ExpectedException.none();
- private JWTParser parser;
-
- @Before
- public void setUp() {
- parser = new JWTParser();
- }
-
- @Test
- public void shouldGetDefaultObjectMapper() {
- ObjectMapper mapper = getDefaultObjectMapper();
- assertThat(mapper, is(notNullValue()));
- assertThat(mapper, is(instanceOf(ObjectMapper.class)));
- assertThat(mapper.isEnabled(SerializationFeature.FAIL_ON_EMPTY_BEANS), is(false));
- }
-
- @Test
- public void shouldAddDeserializers() {
- ObjectMapper mapper = mock(ObjectMapper.class);
- JWTParser.addDeserializers(mapper);
- verify(mapper).registerModule(any(Module.class));
- }
-
- @Test
- public void shouldParsePayload() throws Exception {
- ObjectMapper mapper = mock(ObjectMapper.class);
- ObjectReader reader = mock(ObjectReader.class);
- when(mapper.readerFor(Payload.class)).thenReturn(reader);
- JWTParser parser = new JWTParser(mapper);
- parser.parsePayload("{}");
-
- verify(reader).readValue("{}");
- }
-
- @Test
- public void shouldThrowOnInvalidPayload() {
- String jsonPayload = "{{";
- exception.expect(JWTDecodeException.class);
- exception.expectMessage(String.format("The string '%s' doesn't have a valid JSON format.", jsonPayload));
- Payload payload = parser.parsePayload(jsonPayload);
- assertThat(payload, is(nullValue()));
- }
-
- @Test
- public void shouldParseHeader() throws Exception {
- ObjectMapper mapper = mock(ObjectMapper.class);
- ObjectReader reader = mock(ObjectReader.class);
- when(mapper.readerFor(Header.class)).thenReturn(reader);
- JWTParser parser = new JWTParser(mapper);
- parser.parseHeader("{}");
-
- verify(reader).readValue("{}");
- }
-
- @Test
- public void shouldThrowOnInvalidHeader() {
- String jsonHeader = "}}";
- exception.expect(JWTDecodeException.class);
- exception.expectMessage(String.format("The string '%s' doesn't have a valid JSON format.", jsonHeader));
- Header header = parser.parseHeader(jsonHeader);
- assertThat(header, is(nullValue()));
- }
-
- @Test
- public void shouldThrowWhenConvertingHeaderIfNullJson() {
- exception.expect(JWTDecodeException.class);
- exception.expectMessage("The string 'null' doesn't have a valid JSON format.");
- parser.parseHeader(null);
- }
-
- @Test
- public void shouldThrowWhenConvertingHeaderFromInvalidJson() {
- exception.expect(JWTDecodeException.class);
- exception.expectMessage("The string '}{' doesn't have a valid JSON format.");
- parser.parseHeader("}{");
- }
-
- @Test
- public void shouldThrowWhenConvertingPayloadIfNullJson() {
- exception.expect(JWTDecodeException.class);
- exception.expectMessage("The string 'null' doesn't have a valid JSON format.");
- parser.parsePayload(null);
- }
-
- @Test
- public void shouldThrowWhenConvertingPayloadFromInvalidJson() {
- exception.expect(JWTDecodeException.class);
- exception.expectMessage("The string '}{' doesn't have a valid JSON format.");
- parser.parsePayload("}{");
- }
-}
diff --git a/lib/src/test/java/com/auth0/jwt/impl/JsonNodeClaimTest.java b/lib/src/test/java/com/auth0/jwt/impl/JsonNodeClaimTest.java
deleted file mode 100644
index a0364953..00000000
--- a/lib/src/test/java/com/auth0/jwt/impl/JsonNodeClaimTest.java
+++ /dev/null
@@ -1,533 +0,0 @@
-package com.auth0.jwt.impl;
-
-import com.auth0.jwt.UserPojo;
-import com.auth0.jwt.exceptions.JWTDecodeException;
-import com.auth0.jwt.interfaces.Claim;
-import com.fasterxml.jackson.core.JsonParser;
-import com.fasterxml.jackson.core.type.TypeReference;
-import com.fasterxml.jackson.databind.JsonNode;
-import com.fasterxml.jackson.databind.ObjectMapper;
-import com.fasterxml.jackson.databind.node.JsonNodeType;
-import com.fasterxml.jackson.databind.node.MissingNode;
-import com.fasterxml.jackson.databind.node.NullNode;
-import com.fasterxml.jackson.databind.node.ObjectNode;
-import org.hamcrest.collection.IsMapContaining;
-import org.junit.Before;
-import org.junit.Rule;
-import org.junit.Test;
-import org.junit.rules.ExpectedException;
-import org.mockito.ArgumentMatchers;
-
-import java.io.IOException;
-import java.time.Instant;
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.Collections;
-import java.util.Date;
-import java.util.HashMap;
-import java.util.Map;
-
-import static com.auth0.jwt.impl.JWTParser.getDefaultObjectMapper;
-import static org.hamcrest.MatcherAssert.assertThat;
-import static org.hamcrest.Matchers.arrayContaining;
-import static org.hamcrest.Matchers.hasEntry;
-import static org.hamcrest.Matchers.hasItems;
-import static org.hamcrest.Matchers.hasKey;
-import static org.hamcrest.Matchers.instanceOf;
-import static org.hamcrest.Matchers.is;
-import static org.hamcrest.core.IsNull.notNullValue;
-import static org.hamcrest.core.IsNull.nullValue;
-import static org.junit.Assert.assertNull;
-import static org.mockito.Mockito.mock;
-import static org.mockito.Mockito.spy;
-import static org.mockito.Mockito.when;
-
-public class JsonNodeClaimTest {
-
- private ObjectMapper mapper;
-
- @Rule
- public ExpectedException exception = ExpectedException.none();
-
- @Before
- public void setUp() {
- mapper = getDefaultObjectMapper();
- }
-
- @Test
- public void shouldGetBooleanValue() {
- JsonNode value = mapper.valueToTree(true);
- Claim claim = claimFromNode(value);
-
- assertThat(claim.asBoolean(), is(notNullValue()));
- assertThat(claim.asBoolean(), is(true));
- }
-
- private Claim claimFromNode(JsonNode value) {
- return JsonNodeClaim.claimFromNode(value, mapper);
- }
-
- @Test
- public void shouldGetNullBooleanIfNotBooleanValue() {
- JsonNode objectValue = mapper.valueToTree(new Object());
- assertThat(claimFromNode(objectValue).asBoolean(), is(nullValue()));
- JsonNode stringValue = mapper.valueToTree("boolean");
- assertThat(claimFromNode(stringValue).asBoolean(), is(nullValue()));
- }
-
- @Test
- public void shouldGetIntValue() {
- JsonNode value = mapper.valueToTree(123);
- Claim claim = claimFromNode(value);
-
- assertThat(claim.asInt(), is(notNullValue()));
- assertThat(claim.asInt(), is(123));
- }
-
- @Test
- public void shouldGetNullIntIfNotIntValue() {
- JsonNode objectValue = mapper.valueToTree(new Object());
- assertThat(claimFromNode(objectValue).asInt(), is(nullValue()));
- JsonNode stringValue = mapper.valueToTree("123");
- assertThat(claimFromNode(stringValue).asInt(), is(nullValue()));
- }
-
- @Test
- public void shouldGetLongValue() {
- JsonNode value = mapper.valueToTree(Long.MAX_VALUE);
- Claim claim = claimFromNode(value);
-
- assertThat(claim.asLong(), is(notNullValue()));
- assertThat(claim.asLong(), is(Long.MAX_VALUE));
- }
-
- @Test
- public void shouldGetNullLongIfNotIntValue() {
- JsonNode objectValue = mapper.valueToTree(new Object());
- assertThat(claimFromNode(objectValue).asLong(), is(nullValue()));
- JsonNode stringValue = mapper.valueToTree("" + Long.MAX_VALUE);
- assertThat(claimFromNode(stringValue).asLong(), is(nullValue()));
- }
-
- @Test
- public void shouldGetDoubleValue() {
- JsonNode value = mapper.valueToTree(1.5);
- Claim claim = claimFromNode(value);
-
- assertThat(claim.asDouble(), is(notNullValue()));
- assertThat(claim.asDouble(), is(1.5));
- }
-
- @Test
- public void shouldGetNullDoubleIfNotDoubleValue() {
- JsonNode objectValue = mapper.valueToTree(new Object());
- assertThat(claimFromNode(objectValue).asDouble(), is(nullValue()));
- JsonNode stringValue = mapper.valueToTree("123.23");
- assertThat(claimFromNode(stringValue).asDouble(), is(nullValue()));
- }
-
- @Test
- public void shouldGetNumericDateValue() {
- long seconds = 1476824844L;
- JsonNode value = mapper.valueToTree(seconds);
- Claim claim = claimFromNode(value);
-
- assertThat(claim.asDate(), is(new Date(seconds * 1000)));
- assertThat(claim.asInstant(), is(Instant.ofEpochSecond(seconds)));
- }
-
- @Test
- public void shouldGetNullIfNotNumericDateValue() {
- JsonNode objectValue = mapper.valueToTree(new Object());
- assertThat(claimFromNode(objectValue).asDate(), is(nullValue()));
- assertThat(claimFromNode(objectValue).asInstant(), is(nullValue()));
- JsonNode stringValue = mapper.valueToTree("1476824844");
- assertThat(claimFromNode(stringValue).asDate(), is(nullValue()));
- assertThat(claimFromNode(stringValue).asInstant(), is(nullValue()));
- }
-
- @Test
- public void shouldGetStringValue() {
- JsonNode value = mapper.valueToTree("string");
- Claim claim = claimFromNode(value);
-
- assertThat(claim.asString(), is(notNullValue()));
- assertThat(claim.asString(), is("string"));
- }
-
- @Test
- public void shouldGetNullStringIfNotStringValue() {
- JsonNode objectValue = mapper.valueToTree(new Object());
- assertThat(claimFromNode(objectValue).asString(), is(nullValue()));
- JsonNode intValue = mapper.valueToTree(12345);
- assertThat(claimFromNode(intValue).asString(), is(nullValue()));
- }
-
- @Test
- public void shouldGetArrayValueOfCustomClass() {
- JsonNode value = mapper.valueToTree(new UserPojo[]{new UserPojo("George", 1), new UserPojo("Mark", 2)});
- Claim claim = claimFromNode(value);
-
- assertThat(claim.asArray(UserPojo.class), is(notNullValue()));
- assertThat(claim.asArray(UserPojo.class), is(arrayContaining(new UserPojo("George", 1), new UserPojo("Mark", 2))));
- }
-
- @Test
- public void shouldGetArrayValue() {
- JsonNode value = mapper.valueToTree(new String[]{"string1", "string2"});
- Claim claim = claimFromNode(value);
-
- assertThat(claim.asArray(String.class), is(notNullValue()));
- assertThat(claim.asArray(String.class), is(arrayContaining("string1", "string2")));
- }
-
- @Test
- public void shouldGetNullArrayIfNullValue() {
- JsonNode value = mapper.valueToTree(null);
- Claim claim = claimFromNode(value);
-
- assertThat(claim.asArray(String.class), is(nullValue()));
- }
-
- @Test
- public void shouldGetNullArrayIfNonArrayValue() {
- JsonNode value = mapper.valueToTree(1);
- Claim claim = claimFromNode(value);
-
- assertThat(claim.asArray(String.class), is(nullValue()));
- }
-
- @Test
- public void shouldThrowIfArrayClassMismatch() {
- JsonNode value = mapper.valueToTree(new String[]{"keys", "values"});
- Claim claim = claimFromNode(value);
-
- exception.expect(JWTDecodeException.class);
- claim.asArray(UserPojo.class);
- }
-
- @Test
- public void shouldGetListValueOfCustomClass() {
- JsonNode value = mapper.valueToTree(Arrays.asList(new UserPojo("George", 1), new UserPojo("Mark", 2)));
- Claim claim = claimFromNode(value);
-
- assertThat(claim.asList(UserPojo.class), is(notNullValue()));
- assertThat(claim.asList(UserPojo.class), is(hasItems(new UserPojo("George", 1), new UserPojo("Mark", 2))));
- }
-
- @Test
- public void shouldGetListValue() {
- JsonNode value = mapper.valueToTree(Arrays.asList("string1", "string2"));
- Claim claim = claimFromNode(value);
-
- assertThat(claim.asList(String.class), is(notNullValue()));
- assertThat(claim.asList(String.class), is(hasItems("string1", "string2")));
- }
-
- @Test
- public void shouldGetNullListIfNullValue() {
- JsonNode value = mapper.valueToTree(null);
- Claim claim = claimFromNode(value);
-
- assertThat(claim.asList(String.class), is(nullValue()));
- }
-
- @Test
- public void shouldGetNullListIfNonArrayValue() {
- JsonNode value = mapper.valueToTree(1);
- Claim claim = claimFromNode(value);
-
- assertThat(claim.asList(String.class), is(nullValue()));
- }
-
- @Test
- public void shouldThrowIfListClassMismatch() {
- JsonNode value = mapper.valueToTree(new String[]{"keys", "values"});
- Claim claim = claimFromNode(value);
-
- exception.expect(JWTDecodeException.class);
- claim.asList(UserPojo.class);
- }
-
- @Test
- public void shouldGetNullMapIfNullValue() {
- JsonNode value = mapper.valueToTree(null);
- Claim claim = claimFromNode(value);
-
- assertThat(claim.asMap(), is(nullValue()));
- }
-
- @Test
- public void shouldGetNullMapIfNonArrayValue() {
- JsonNode value = mapper.valueToTree(1);
- Claim claim = claimFromNode(value);
-
- assertThat(claim.asMap(), is(nullValue()));
- }
-
- @Test
- public void shouldGetMapValue() {
- Map map = new HashMap<>();
- map.put("text", "extraValue");
- map.put("number", 12);
- map.put("boolean", true);
- map.put("object", Collections.singletonMap("something", "else"));
-
- JsonNode value = mapper.valueToTree(map);
- Claim claim = claimFromNode(value);
-
- assertThat(claim, is(notNullValue()));
- Map backMap = claim.asMap();
- assertThat(backMap, is(notNullValue()));
- assertThat(backMap, hasEntry("text", (Object) "extraValue"));
- assertThat(backMap, hasEntry("number", (Object) 12));
- assertThat(backMap, hasEntry("boolean", (Object) true));
- assertThat(backMap, hasKey("object"));
- assertThat((Map) backMap.get("object"), IsMapContaining.hasEntry("something", (Object) "else"));
- }
-
- @Test
- public void shouldThrowIfAnExtraordinaryExceptionHappensWhenParsingAsGenericMap() throws Exception {
- JsonNode value = mock(ObjectNode.class);
- when(value.getNodeType()).thenReturn(JsonNodeType.OBJECT);
-
- ObjectMapper mockedMapper = mock(ObjectMapper.class);
-
- JsonNodeClaim claim = (JsonNodeClaim) JsonNodeClaim.claimFromNode(value, mockedMapper);
- JsonNodeClaim spiedClaim = spy(claim);
-
- JsonParser mockedParser = mock(JsonParser.class);
- when(mockedMapper.treeAsTokens(value)).thenReturn(mockedParser);
- when(mockedParser.readValueAs(ArgumentMatchers.any(TypeReference.class))).thenThrow(IOException.class);
-
- exception.expect(JWTDecodeException.class);
- spiedClaim.asMap();
- }
-
- @Test
- public void shouldGetCustomClassValue() {
- JsonNode value = mapper.valueToTree(new UserPojo("john", 123));
- Claim claim = claimFromNode(value);
-
- assertThat(claim, is(notNullValue()));
- assertThat(claim.as(UserPojo.class).getName(), is("john"));
- assertThat(claim.as(UserPojo.class).getId(), is(123));
- }
-
- @Test
- public void shouldThrowIfCustomClassMismatch() {
- JsonNode value = mapper.valueToTree(new UserPojo("john", 123));
- Claim claim = claimFromNode(value);
-
- exception.expect(JWTDecodeException.class);
- claim.as(String.class);
- }
-
- @Test
- public void shouldReturnNullForMissingAndNullClaims() {
- JsonNode missingValue = MissingNode.getInstance();
- Claim missingClaim = claimFromNode(missingValue);
- assertThat(missingClaim.isMissing(), is(true));
- assertThat(missingClaim.isNull(), is(false));
- assertNull(missingClaim.as(String.class));
- assertNull(missingClaim.asString());
- assertNull(missingClaim.asBoolean());
- assertNull(missingClaim.asDate());
- assertNull(missingClaim.asDouble());
- assertNull(missingClaim.asLong());
- assertNull(missingClaim.asInt());
- assertNull(missingClaim.asInstant());
- assertNull(missingClaim.asMap());
- assertNull(missingClaim.asList(String.class));
- assertNull(missingClaim.asArray(String.class));
-
- JsonNode nullValue = mapper.valueToTree(null);
- Claim nullClaim = claimFromNode(nullValue);
- assertThat(nullClaim.isMissing(), is(false));
- assertThat(nullClaim.isNull(), is(true));
- assertNull(nullClaim.as(String.class));
- assertNull(nullClaim.asString());
- assertNull(nullClaim.asBoolean());
- assertNull(nullClaim.asDate());
- assertNull(nullClaim.asDouble());
- assertNull(nullClaim.asLong());
- assertNull(nullClaim.asInt());
- assertNull(nullClaim.asInstant());
- assertNull(nullClaim.asMap());
- assertNull(nullClaim.asList(String.class));
- assertNull(nullClaim.asArray(String.class));
- }
-
- @Test
- public void shouldReturnNullForInvalidArrayValue() {
- JsonNode value = mapper.valueToTree(new UserPojo("john", 123));
- Claim claim = claimFromNode(value);
- assertNull(claim.asArray(String.class));
- }
-
- @SuppressWarnings({"unchecked", "RedundantCast"})
- @Test
- public void shouldGetAsMapValue() {
- JsonNode value = mapper.valueToTree(Collections.singletonMap("key", new UserPojo("john", 123)));
- Claim claim = claimFromNode(value);
-
- assertThat(claim, is(notNullValue()));
- Map map = claim.as(Map.class);
- assertThat(((Map) map.get("key")), hasEntry("name", (Object) "john"));
- assertThat(((Map) map.get("key")), hasEntry("id", (Object) 123));
- }
-
- @Test
- public void shouldReturnBaseClaimWhenParsingMissingNode() {
- JsonNode value = MissingNode.getInstance();
- Claim claim = claimFromNode(value);
-
- assertThat(claim, is(notNullValue()));
- assertThat(claim.isMissing(), is(true));
- assertThat(claim.isNull(), is(false));
- }
-
- @Test
- public void shouldReturnBaseClaimWhenParsingNullNode() {
- JsonNode value = NullNode.getInstance();
- Claim claim = claimFromNode(value);
-
- assertThat(claim, is(notNullValue()));
- assertThat(claim.isNull(), is(true));
- assertThat(claim.isMissing(), is(false));
- }
-
- @Test
- public void shouldReturnBaseClaimWhenParsingNullValue() {
- JsonNode value = mapper.valueToTree(null);
- Claim claim = claimFromNode(value);
-
- assertThat(claim, is(notNullValue()));
- assertThat(claim.isNull(), is(true));
- assertThat(claim.isMissing(), is(false));
- }
-
- @Test
- public void shouldReturnNonNullClaimWhenParsingObject() {
- JsonNode value = mapper.valueToTree(new Object());
- Claim claim = claimFromNode(value);
-
- assertThat(claim, is(notNullValue()));
- assertThat(claim, is(instanceOf(JsonNodeClaim.class)));
- assertThat(claim.isNull(), is(false));
- assertThat(claim.isMissing(), is(false));
- }
-
- @Test
- public void shouldReturnNonNullClaimWhenParsingArray() {
- JsonNode value = mapper.valueToTree(new String[]{});
- Claim claim = claimFromNode(value);
-
- assertThat(claim, is(notNullValue()));
- assertThat(claim, is(instanceOf(JsonNodeClaim.class)));
- assertThat(claim.isNull(), is(false));
- assertThat(claim.isMissing(), is(false));
- }
-
- @Test
- public void shouldReturnNonNullClaimWhenParsingList() {
- JsonNode value = mapper.valueToTree(new ArrayList());
- Claim claim = claimFromNode(value);
-
- assertThat(claim, is(notNullValue()));
- assertThat(claim, is(instanceOf(JsonNodeClaim.class)));
- assertThat(claim.isNull(), is(false));
- assertThat(claim.isMissing(), is(false));
- }
-
- @Test
- public void shouldReturnNonNullClaimWhenParsingStringValue() {
- JsonNode value = mapper.valueToTree("");
- Claim claim = claimFromNode(value);
-
- assertThat(claim, is(notNullValue()));
- assertThat(claim, is(instanceOf(JsonNodeClaim.class)));
- assertThat(claim.isNull(), is(false));
- assertThat(claim.isMissing(), is(false));
- }
-
- @Test
- public void shouldReturnNonNullClaimWhenParsingIntValue() {
- JsonNode value = mapper.valueToTree(Integer.MAX_VALUE);
- Claim claim = claimFromNode(value);
-
- assertThat(claim, is(notNullValue()));
- assertThat(claim, is(instanceOf(JsonNodeClaim.class)));
- assertThat(claim.isNull(), is(false));
- assertThat(claim.isMissing(), is(false));
- }
-
- @Test
- public void shouldReturnNonNullClaimWhenParsingDoubleValue() {
- JsonNode value = mapper.valueToTree(Double.MAX_VALUE);
- Claim claim = claimFromNode(value);
-
- assertThat(claim, is(notNullValue()));
- assertThat(claim, is(instanceOf(JsonNodeClaim.class)));
- assertThat(claim.isNull(), is(false));
- assertThat(claim.isMissing(), is(false));
- }
-
- @Test
- public void shouldReturnNonNullClaimWhenParsingDateValue() {
- JsonNode value = mapper.valueToTree(new Date());
- Claim claim = claimFromNode(value);
-
- assertThat(claim, is(notNullValue()));
- assertThat(claim, is(instanceOf(JsonNodeClaim.class)));
- assertThat(claim.isNull(), is(false));
- assertThat(claim.isMissing(), is(false));
- }
-
- @Test
- public void shouldReturnNonNullClaimWhenParsingBooleanValue() {
- JsonNode value = mapper.valueToTree(Boolean.TRUE);
- Claim claim = claimFromNode(value);
-
- assertThat(claim, is(notNullValue()));
- assertThat(claim, is(instanceOf(JsonNodeClaim.class)));
- assertThat(claim.isNull(), is(false));
- assertThat(claim.isMissing(), is(false));
- }
-
- @Test
- public void shouldReturnNullIsTrue() {
- JsonNode value = mapper.valueToTree(null);
- Claim claim = claimFromNode(value);
-
- assertThat(claim, is(notNullValue()));
- assertThat(claim, is(instanceOf(JsonNodeClaim.class)));
- assertThat(claim.isNull(), is(true));
- assertThat(claim.isMissing(), is(false));
- }
-
- @Test
- public void shouldDelegateToJsonNodeToString() {
- JsonNode value = mapper.valueToTree(new UserPojo("john", 123));
- Claim claim = claimFromNode(value);
- assertThat(claim.toString(), is(value.toString()));
- }
-
- @Test
- public void shouldConvertToString() {
- JsonNode value = mapper.valueToTree(new UserPojo("john", 123));
- JsonNode nullValue = mapper.valueToTree(null);
- JsonNode missingValue = MissingNode.getInstance();
-
- Claim claim = claimFromNode(value);
- Claim nullClaim = claimFromNode(nullValue);
- Claim missingClaim = claimFromNode(missingValue);
-
- assertThat(claim.toString(), is("{\"name\":\"john\",\"id\":123}"));
- assertThat(nullClaim.isNull(), is(true));
- assertThat(nullClaim.toString(), is("Null claim"));
- assertThat(missingClaim.isMissing(), is(true));
- assertThat(missingClaim.toString(), is("Missing claim"));
-
- }
-}
\ No newline at end of file
diff --git a/lib/src/test/java/com/auth0/jwt/impl/PayloadClaimsHolderTest.java b/lib/src/test/java/com/auth0/jwt/impl/PayloadClaimsHolderTest.java
deleted file mode 100644
index 2f053830..00000000
--- a/lib/src/test/java/com/auth0/jwt/impl/PayloadClaimsHolderTest.java
+++ /dev/null
@@ -1,32 +0,0 @@
-package com.auth0.jwt.impl;
-
-import org.hamcrest.collection.IsMapContaining;
-import org.junit.Test;
-
-import java.util.HashMap;
-import java.util.Map;
-
-import static org.hamcrest.Matchers.*;
-import static org.hamcrest.MatcherAssert.assertThat;
-
-public class PayloadClaimsHolderTest {
-
- @Test
- public void shouldGetClaims() {
- HashMap claims = new HashMap<>();
- claims.put("iss", "auth0");
- ClaimsHolder holder = new PayloadClaimsHolder(claims);
- assertThat(holder, is(notNullValue()));
- assertThat(holder.getClaims(), is(notNullValue()));
- assertThat(holder.getClaims(), is(instanceOf(Map.class)));
- assertThat(holder.getClaims(), is(IsMapContaining.hasEntry("iss", "auth0")));
- }
-
- @Test
- public void shouldGetNotNullClaims() {
- ClaimsHolder holder = new PayloadClaimsHolder(null);
- assertThat(holder, is(notNullValue()));
- assertThat(holder.getClaims(), is(notNullValue()));
- assertThat(holder.getClaims(), is(instanceOf(Map.class)));
- }
-}
\ No newline at end of file
diff --git a/lib/src/test/java/com/auth0/jwt/impl/PayloadDeserializerTest.java b/lib/src/test/java/com/auth0/jwt/impl/PayloadDeserializerTest.java
deleted file mode 100644
index c3e04013..00000000
--- a/lib/src/test/java/com/auth0/jwt/impl/PayloadDeserializerTest.java
+++ /dev/null
@@ -1,274 +0,0 @@
-package com.auth0.jwt.impl;
-
-import com.auth0.jwt.exceptions.JWTDecodeException;
-import com.auth0.jwt.interfaces.Payload;
-import com.fasterxml.jackson.core.JsonFactory;
-import com.fasterxml.jackson.core.JsonParser;
-import com.fasterxml.jackson.core.ObjectCodec;
-import com.fasterxml.jackson.core.type.TypeReference;
-import com.fasterxml.jackson.databind.DeserializationContext;
-import com.fasterxml.jackson.databind.JsonNode;
-import com.fasterxml.jackson.databind.ObjectMapper;
-import com.fasterxml.jackson.databind.node.*;
-import org.hamcrest.collection.IsCollectionWithSize;
-import org.hamcrest.collection.IsEmptyCollection;
-import org.hamcrest.core.IsIterableContaining;
-import org.junit.Before;
-import org.junit.Rule;
-import org.junit.Test;
-import org.junit.rules.ExpectedException;
-
-import java.io.StringReader;
-import java.time.Instant;
-import java.util.*;
-
-import static org.hamcrest.Matchers.*;
-import static org.hamcrest.MatcherAssert.assertThat;
-import static org.mockito.ArgumentMatchers.any;
-import static org.mockito.ArgumentMatchers.eq;
-import static org.mockito.Mockito.mock;
-import static org.mockito.Mockito.when;
-
-public class PayloadDeserializerTest {
-
- @Rule
- public ExpectedException exception = ExpectedException.none();
- private PayloadDeserializer deserializer;
-
- private ObjectMapper objectMapper;
-
- @Before
- public void setUp() {
- objectMapper = new ObjectMapper();
- deserializer = new PayloadDeserializer();
- }
-
- @Test
- public void shouldThrowOnNullTree() throws Exception {
- exception.expect(JWTDecodeException.class);
- exception.expectMessage("Parsing the Payload's JSON resulted on a Null map");
-
- JsonParser parser = mock(JsonParser.class);
- ObjectCodec codec = mock(ObjectCodec.class);
- DeserializationContext context = mock(DeserializationContext.class);
-
- when(codec.readValue(eq(parser), any(TypeReference.class))).thenReturn(null);
- when(parser.getCodec()).thenReturn(codec);
-
- deserializer.deserialize(parser, context);
- }
-
- @Test
- public void shouldThrowWhenParsingArrayWithObjectValue() throws Exception {
- exception.expect(JWTDecodeException.class);
- exception.expectMessage("Couldn't map the Claim's array contents to String");
-
- ObjectMapper mapper = new ObjectMapper();
- JsonNode jsonNode = mapper.readTree("{\"some\" : \"random\", \"properties\" : \"inside\"}");
- Map tree = new HashMap<>();
- List subNodes = new ArrayList<>();
- subNodes.add(jsonNode);
- ArrayNode arrNode = new ArrayNode(JsonNodeFactory.instance, subNodes);
- tree.put("key", arrNode);
-
- deserializer.getStringOrArray(objectMapper, tree, "key");
- }
-
- @Test
- public void shouldNotRemoveKnownPublicClaimsFromTree() throws Exception {
- String payloadJSON = "{\n" +
- " \"iss\": \"auth0\",\n" +
- " \"sub\": \"emails\",\n" +
- " \"aud\": \"users\",\n" +
- " \"iat\": 10101010,\n" +
- " \"exp\": 11111111,\n" +
- " \"nbf\": 10101011,\n" +
- " \"jti\": \"idid\",\n" +
- " \"roles\":\"admin\" \n" +
- "}";
- StringReader reader = new StringReader(payloadJSON);
- JsonParser jsonParser = new JsonFactory().createParser(reader);
- ObjectMapper mapper = new ObjectMapper();
- jsonParser.setCodec(mapper);
-
- Payload payload = deserializer.deserialize(jsonParser, mapper.getDeserializationContext());
-
- assertThat(payload, is(notNullValue()));
- assertThat(payload.getIssuer(), is("auth0"));
- assertThat(payload.getSubject(), is("emails"));
- assertThat(payload.getAudience(), is(IsIterableContaining.hasItem("users")));
- assertThat(payload.getIssuedAt().getTime(), is(10101010L * 1000));
- assertThat(payload.getExpiresAt().getTime(), is(11111111L * 1000));
- assertThat(payload.getNotBefore().getTime(), is(10101011L * 1000));
- assertThat(payload.getIssuedAtAsInstant().getEpochSecond(), is(10101010L));
- assertThat(payload.getExpiresAtAsInstant().getEpochSecond(), is(11111111L));
- assertThat(payload.getNotBeforeAsInstant().getEpochSecond(), is(10101011L));
- assertThat(payload.getId(), is("idid"));
-
- assertThat(payload.getClaim("roles").asString(), is("admin"));
- assertThat(payload.getClaim("iss").asString(), is("auth0"));
- assertThat(payload.getClaim("sub").asString(), is("emails"));
- assertThat(payload.getClaim("aud").asString(), is("users"));
- assertThat(payload.getClaim("iat").asDouble(), is(10101010D));
- assertThat(payload.getClaim("exp").asDouble(), is(11111111D));
- assertThat(payload.getClaim("nbf").asDouble(), is(10101011D));
- assertThat(payload.getClaim("jti").asString(), is("idid"));
- }
-
- @Test
- public void shouldGetStringArrayWhenParsingArrayNode() {
- Map tree = new HashMap<>();
- List subNodes = new ArrayList<>();
- TextNode textNode1 = new TextNode("one");
- TextNode textNode2 = new TextNode("two");
- subNodes.add(textNode1);
- subNodes.add(textNode2);
- ArrayNode arrNode = new ArrayNode(JsonNodeFactory.instance, subNodes);
- tree.put("key", arrNode);
-
- List values = deserializer.getStringOrArray(objectMapper, tree, "key");
- assertThat(values, is(notNullValue()));
- assertThat(values, is(IsCollectionWithSize.hasSize(2)));
- assertThat(values, is(IsIterableContaining.hasItems("one", "two")));
- }
-
- @Test
- public void shouldGetStringArrayWhenParsingTextNode() {
- Map tree = new HashMap<>();
- TextNode textNode = new TextNode("something");
- tree.put("key", textNode);
-
- List values = deserializer.getStringOrArray(objectMapper, tree, "key");
- assertThat(values, is(notNullValue()));
- assertThat(values, is(IsCollectionWithSize.hasSize(1)));
- assertThat(values, is(IsIterableContaining.hasItems("something")));
- }
-
- @Test
- public void shouldGetEmptyStringInArrayWhenParsingEmptyTextNode() {
- Map tree = new HashMap<>();
- TextNode textNode = new TextNode("");
- tree.put("key", textNode);
-
- List values = deserializer.getStringOrArray(objectMapper, tree, "key");
- assertThat(values, is(notNullValue()));
- assertThat(values, is(IsIterableContaining.hasItem("")));
- }
-
- @Test
- public void shouldGetNullArrayWhenParsingNullNode() {
- Map tree = new HashMap<>();
- NullNode node = NullNode.getInstance();
- tree.put("key", node);
-
- List values = deserializer.getStringOrArray(objectMapper, tree, "key");
- assertThat(values, is(nullValue()));
- }
-
- @Test
- public void shouldGetNullArrayWhenParsingNullNodeValue() {
- Map tree = new HashMap<>();
- tree.put("key", null);
-
- List values = deserializer.getStringOrArray(objectMapper, tree, "key");
- assertThat(values, is(nullValue()));
- }
-
- @Test
- public void shouldGetNullArrayWhenParsingNonArrayOrTextNode() {
- Map tree = new HashMap<>();
- IntNode node = new IntNode(456789);
- tree.put("key", node);
-
- List values = deserializer.getStringOrArray(objectMapper, tree, "key");
- assertThat(values, is(nullValue()));
- }
-
- @Test
- public void shouldGetNullInstantWhenParsingNullNode() {
- Map tree = new HashMap<>();
- NullNode node = NullNode.getInstance();
- tree.put("key", node);
-
- Instant instant = deserializer.getInstantFromSeconds(tree, "key");
- assertThat(instant, is(nullValue()));
- }
-
- @Test
- public void shouldGetNullInstantWhenParsingNull() {
- Map tree = new HashMap<>();
- tree.put("key", null);
-
- Instant instant = deserializer.getInstantFromSeconds(tree, "key");
- assertThat(instant, is(nullValue()));
- }
-
- @Test
- public void shouldThrowWhenParsingNonNumericNode() {
- exception.expect(JWTDecodeException.class);
- exception.expectMessage("The claim 'key' contained a non-numeric date value.");
-
- Map tree = new HashMap<>();
- TextNode node = new TextNode("123456789");
- tree.put("key", node);
-
- deserializer.getInstantFromSeconds(tree, "key");
- }
-
- @Test
- public void shouldGetInstantWhenParsingNumericNode() {
- Map tree = new HashMap<>();
- long seconds = 1478627949 / 1000;
- LongNode node = new LongNode(seconds);
- tree.put("key", node);
-
- Instant instant = deserializer.getInstantFromSeconds(tree, "key");
- assertThat(instant, is(notNullValue()));
- assertThat(instant.toEpochMilli(), is(seconds * 1000));
- }
-
-
- @Test
- public void shouldGetLargeInstantWhenParsingNumericNode() {
- Map tree = new HashMap<>();
- long seconds = Integer.MAX_VALUE + 10000L;
- LongNode node = new LongNode(seconds);
- tree.put("key", node);
-
- Instant instant = deserializer.getInstantFromSeconds(tree, "key");
- assertThat(instant, is(notNullValue()));
- assertThat(instant.toEpochMilli(), is(seconds * 1000));
- assertThat(instant.toEpochMilli(), is(2147493647L * 1000));
- }
-
- @Test
- public void shouldGetNullStringWhenParsingNullNode() {
- Map tree = new HashMap<>();
- NullNode node = NullNode.getInstance();
- tree.put("key", node);
-
- String text = deserializer.getString(tree, "key");
- assertThat(text, is(nullValue()));
- }
-
- @Test
- public void shouldGetNullStringWhenParsingNull() {
- Map tree = new HashMap<>();
- tree.put("key", null);
-
- String text = deserializer.getString(tree, "key");
- assertThat(text, is(nullValue()));
- }
-
- @Test
- public void shouldGetStringWhenParsingTextNode() {
- Map tree = new HashMap<>();
- TextNode node = new TextNode("something here");
- tree.put("key", node);
-
- String text = deserializer.getString(tree, "key");
- assertThat(text, is(notNullValue()));
- assertThat(text, is("something here"));
- }
-
-}
\ No newline at end of file
diff --git a/lib/src/test/java/com/auth0/jwt/impl/PayloadImplTest.java b/lib/src/test/java/com/auth0/jwt/impl/PayloadImplTest.java
deleted file mode 100644
index 5ad7ac68..00000000
--- a/lib/src/test/java/com/auth0/jwt/impl/PayloadImplTest.java
+++ /dev/null
@@ -1,194 +0,0 @@
-package com.auth0.jwt.impl;
-
-import com.auth0.jwt.interfaces.Claim;
-import com.fasterxml.jackson.databind.JsonNode;
-import com.fasterxml.jackson.databind.ObjectMapper;
-import com.fasterxml.jackson.databind.ObjectReader;
-import com.fasterxml.jackson.databind.node.TextNode;
-import org.hamcrest.collection.IsCollectionWithSize;
-import org.hamcrest.core.IsIterableContaining;
-import org.junit.Before;
-import org.junit.Rule;
-import org.junit.Test;
-import org.junit.rules.ExpectedException;
-
-import java.time.Instant;
-import java.util.*;
-
-import static com.auth0.jwt.impl.JWTParser.getDefaultObjectMapper;
-import static org.hamcrest.MatcherAssert.assertThat;
-import static org.hamcrest.Matchers.*;
-
-public class PayloadImplTest {
-
- @Rule
- public ExpectedException exception = ExpectedException.none();
-
- private PayloadImpl payload;
- private final Instant expiresAt = Instant.now().plusSeconds(10);
- private final Instant notBefore = Instant.now();
- private final Instant issuedAt = Instant.now();
-
- private ObjectMapper objectMapper;
-
- @Before
- public void setUp() {
- objectMapper = getDefaultObjectMapper();
-
- Map tree = new HashMap<>();
- tree.put("extraClaim", new TextNode("extraValue"));
- payload = new PayloadImpl("issuer", "subject", Collections.singletonList("audience"), expiresAt, notBefore, issuedAt, "jwtId", tree, objectMapper);
- }
-
- @Test
- public void shouldHaveUnmodifiableTree() {
- exception.expect(UnsupportedOperationException.class);
- PayloadImpl payload = new PayloadImpl(null, null, null, null, null, null, null, new HashMap<>(), objectMapper);
- payload.getTree().put("something", null);
- }
-
- @Test
- public void shouldHaveUnmodifiableAudience() {
- exception.expect(UnsupportedOperationException.class);
- PayloadImpl payload = new PayloadImpl(null, null, new ArrayList<>(), null, null, null, null, null, objectMapper);
- payload.getAudience().add("something");
- }
-
- @Test
- public void shouldGetIssuer() {
- assertThat(payload, is(notNullValue()));
- assertThat(payload.getIssuer(), is("issuer"));
- }
-
- @Test
- public void shouldGetNullIssuerIfMissing() {
- PayloadImpl payload = new PayloadImpl(null, null, null, null, null, null, null, null, objectMapper);
- assertThat(payload, is(notNullValue()));
- assertThat(payload.getIssuer(), is(nullValue()));
- }
-
- @Test
- public void shouldGetSubject() {
- assertThat(payload, is(notNullValue()));
- assertThat(payload.getSubject(), is("subject"));
- }
-
- @Test
- public void shouldGetNullSubjectIfMissing() {
- PayloadImpl payload = new PayloadImpl(null, null, null, null, null, null, null, null, objectMapper);
- assertThat(payload, is(notNullValue()));
- assertThat(payload.getSubject(), is(nullValue()));
- }
-
- @Test
- public void shouldGetAudience() {
- assertThat(payload, is(notNullValue()));
-
- assertThat(payload.getAudience(), is(IsCollectionWithSize.hasSize(1)));
- assertThat(payload.getAudience(), is(IsIterableContaining.hasItems("audience")));
- }
-
- @Test
- public void shouldGetNullAudienceIfMissing() {
- PayloadImpl payload = new PayloadImpl(null, null, null, null, null, null, null, null, objectMapper);
- assertThat(payload, is(notNullValue()));
- assertThat(payload.getAudience(), is(nullValue()));
- }
-
- @Test
- public void shouldGetExpiresAt() {
- assertThat(payload, is(notNullValue()));
- assertThat(payload.getExpiresAt(), is(Date.from(expiresAt)));
- assertThat(payload.getExpiresAtAsInstant(), is(expiresAt));
- }
-
- @Test
- public void shouldGetNullExpiresAtIfMissing() {
- PayloadImpl payload = new PayloadImpl(null, null, null, null, null, null, null, null, objectMapper);
- assertThat(payload, is(notNullValue()));
- assertThat(payload.getExpiresAt(), is(nullValue()));
- assertThat(payload.getExpiresAtAsInstant(), is(nullValue()));
- }
-
- @Test
- public void shouldGetNotBefore() {
- assertThat(payload, is(notNullValue()));
- assertThat(payload.getNotBefore(), is(Date.from(notBefore)));
- assertThat(payload.getNotBeforeAsInstant(), is(notBefore));
- }
-
- @Test
- public void shouldGetNullNotBeforeIfMissing() {
- PayloadImpl payload = new PayloadImpl(null, null, null, null, null, null, null, null, objectMapper);
- assertThat(payload, is(notNullValue()));
- assertThat(payload.getNotBefore(), is(nullValue()));
- assertThat(payload.getNotBeforeAsInstant(), is(nullValue()));
- }
-
- @Test
- public void shouldGetIssuedAt() {
- assertThat(payload, is(notNullValue()));
- assertThat(payload.getIssuedAt(), is(Date.from(issuedAt)));
- assertThat(payload.getIssuedAtAsInstant(), is(issuedAt));
- }
-
- @Test
- public void shouldGetNullIssuedAtIfMissing() {
- PayloadImpl payload = new PayloadImpl(null, null, null, null, null, null, null, null, objectMapper);
- assertThat(payload, is(notNullValue()));
- assertThat(payload.getIssuedAt(), is(nullValue()));
- assertThat(payload.getIssuedAtAsInstant(), is(nullValue()));
- }
-
- @Test
- public void shouldGetJWTId() {
- assertThat(payload, is(notNullValue()));
- assertThat(payload.getId(), is("jwtId"));
- }
-
- @Test
- public void shouldGetNullJWTIdIfMissing() {
- PayloadImpl payload = new PayloadImpl(null, null, null, null, null, null, null, null, objectMapper);
- assertThat(payload, is(notNullValue()));
- assertThat(payload.getId(), is(nullValue()));
- }
-
- @Test
- public void shouldGetExtraClaim() {
- assertThat(payload, is(notNullValue()));
- assertThat(payload.getClaim("extraClaim"), is(instanceOf(JsonNodeClaim.class)));
- assertThat(payload.getClaim("extraClaim").asString(), is("extraValue"));
- }
-
- @Test
- public void shouldGetNotNullExtraClaimIfMissing() {
- PayloadImpl payload = new PayloadImpl(null, null, null, null, null, null, null, null, objectMapper);
- assertThat(payload, is(notNullValue()));
- assertThat(payload.getClaim("missing"), is(notNullValue()));
- assertThat(payload.getClaim("missing").isMissing(), is(true));
- assertThat(payload.getClaim("missing").isNull(), is(false));
- }
-
- @Test
- public void shouldGetClaims() {
- Map tree = new HashMap<>();
- tree.put("extraClaim", new TextNode("extraValue"));
- tree.put("sub", new TextNode("auth0"));
- PayloadImpl payload = new PayloadImpl(null, null, null, null, null, null, null, tree, objectMapper);
- assertThat(payload, is(notNullValue()));
- Map claims = payload.getClaims();
- assertThat(claims, is(notNullValue()));
-
- assertThat(claims.get("extraClaim"), is(notNullValue()));
- assertThat(claims.get("sub"), is(notNullValue()));
- }
-
- @Test
- public void shouldNotAllowToModifyClaimsMap() {
- assertThat(payload, is(notNullValue()));
- Map claims = payload.getClaims();
- assertThat(claims, is(notNullValue()));
- exception.expect(UnsupportedOperationException.class);
- claims.put("name", null);
- }
-}
\ No newline at end of file
diff --git a/lib/src/test/java/com/auth0/jwt/impl/PayloadSerializerTest.java b/lib/src/test/java/com/auth0/jwt/impl/PayloadSerializerTest.java
deleted file mode 100644
index 45761de0..00000000
--- a/lib/src/test/java/com/auth0/jwt/impl/PayloadSerializerTest.java
+++ /dev/null
@@ -1,289 +0,0 @@
-package com.auth0.jwt.impl;
-
-import com.auth0.jwt.UserPojo;
-import com.fasterxml.jackson.core.JsonFactory;
-import com.fasterxml.jackson.core.JsonGenerator;
-import com.fasterxml.jackson.databind.ObjectMapper;
-import com.fasterxml.jackson.databind.SerializerProvider;
-import org.junit.Before;
-import org.junit.Test;
-
-import java.io.StringWriter;
-import java.util.*;
-
-import static org.hamcrest.MatcherAssert.assertThat;
-import static org.hamcrest.Matchers.*;
-
-public class PayloadSerializerTest {
-
- private StringWriter writer;
- private PayloadSerializer serializer;
- private JsonGenerator jsonGenerator;
- private SerializerProvider serializerProvider;
-
- @Before
- public void setUp() throws Exception {
- writer = new StringWriter();
- serializer = new PayloadSerializer();
- jsonGenerator = new JsonFactory().createGenerator(writer);
- ObjectMapper mapper = new ObjectMapper();
- jsonGenerator.setCodec(mapper);
- serializerProvider = mapper.getSerializerProvider();
- }
-
- @Test
- public void shouldSerializeEmptyMap() throws Exception {
- PayloadClaimsHolder holder = new PayloadClaimsHolder(new HashMap<>());
- serializer.serialize(holder, jsonGenerator, serializerProvider);
- jsonGenerator.flush();
-
- assertThat(writer.toString(), is(equalTo("{}")));
- }
-
- @Test
- public void shouldSerializeStringAudienceAsString() throws Exception {
- PayloadClaimsHolder holder = holderFor("aud", "auth0");
- serializer.serialize(holder, jsonGenerator, serializerProvider);
- jsonGenerator.flush();
-
- assertThat(writer.toString(), is(equalTo("{\"aud\":\"auth0\"}")));
- }
-
- @Test
- public void shouldSerializeSingleItemAudienceAsArray() throws Exception {
- PayloadClaimsHolder holder = holderFor("aud", new String[]{"auth0"});
- serializer.serialize(holder, jsonGenerator, serializerProvider);
- jsonGenerator.flush();
-
- assertThat(writer.toString(), is(equalTo("{\"aud\":\"auth0\"}")));
- }
-
- @Test
- public void shouldSerializeMultipleItemsAudienceAsArray() throws Exception {
- PayloadClaimsHolder holder = holderFor("aud", new String[]{"auth0", "auth10"});
- serializer.serialize(holder, jsonGenerator, serializerProvider);
- jsonGenerator.flush();
-
- assertThat(writer.toString(), is(equalTo("{\"aud\":[\"auth0\",\"auth10\"]}")));
- }
-
- @Test
- public void shouldSkipSerializationOnEmptyAudience() throws Exception {
- PayloadClaimsHolder holder = holderFor("aud", new String[0]);
- serializer.serialize(holder, jsonGenerator, serializerProvider);
- jsonGenerator.flush();
-
- assertThat(writer.toString(), is(equalTo("{}")));
- }
-
- @Test
- public void shouldSerializeSingleItemAudienceAsArrayWhenAList() throws Exception {
- PayloadClaimsHolder holder = holderFor("aud", Collections.singletonList("auth0"));
- serializer.serialize(holder, jsonGenerator, serializerProvider);
- jsonGenerator.flush();
-
- assertThat(writer.toString(), is(equalTo("{\"aud\":\"auth0\"}")));
- }
-
- @Test
- public void shouldSerializeMultipleItemsAudienceAsArrayWhenAList() throws Exception {
- PayloadClaimsHolder holder = holderFor("aud", Arrays.asList("auth0", "auth10"));
- serializer.serialize(holder, jsonGenerator, serializerProvider);
- jsonGenerator.flush();
-
- assertThat(writer.toString(), is(equalTo("{\"aud\":[\"auth0\",\"auth10\"]}")));
- }
-
- @Test
- public void shouldSkipSerializationOnEmptyAudienceWhenList() throws Exception {
- PayloadClaimsHolder holder = holderFor("aud", new ArrayList<>());
- serializer.serialize(holder, jsonGenerator, serializerProvider);
- jsonGenerator.flush();
-
- assertThat(writer.toString(), is(equalTo("{}")));
- }
-
- @Test
- public void shouldSkipNonStringsOnAudienceWhenSingleItemList() throws Exception {
- PayloadClaimsHolder holder = holderFor("aud", Collections.singletonList(2));
- serializer.serialize(holder, jsonGenerator, serializerProvider);
- jsonGenerator.flush();
-
- assertThat(writer.toString(), is(equalTo("{}")));
- }
-
- @Test
- public void shouldSkipNonStringsOnAudienceWhenList() throws Exception {
- PayloadClaimsHolder holder = holderFor("aud", Arrays.asList("auth0", 2, "auth10"));
- serializer.serialize(holder, jsonGenerator, serializerProvider);
- jsonGenerator.flush();
-
- assertThat(writer.toString(), is(equalTo("{\"aud\":[\"auth0\",\"auth10\"]}")));
- }
-
- @Test
- public void shouldSkipNonStringsOnAudience() throws Exception {
- PayloadClaimsHolder holder = holderFor("aud", 4);
- serializer.serialize(holder, jsonGenerator, serializerProvider);
- jsonGenerator.flush();
-
- assertThat(writer.toString(), is(equalTo("{}")));
- }
-
- @Test
- public void shouldSerializeNotBeforeDateInSeconds() throws Exception {
- PayloadClaimsHolder holder = holderFor("nbf", new Date(1478874000));
- serializer.serialize(holder, jsonGenerator, serializerProvider);
- jsonGenerator.flush();
-
- assertThat(writer.toString(), is(equalTo("{\"nbf\":1478874}")));
- }
-
- @Test
- public void shouldSerializeIssuedAtDateInSeconds() throws Exception {
- PayloadClaimsHolder holder = holderFor("iat", new Date(1478874000));
- serializer.serialize(holder, jsonGenerator, serializerProvider);
- jsonGenerator.flush();
-
- assertThat(writer.toString(), is(equalTo("{\"iat\":1478874}")));
- }
-
- @Test
- public void shouldSerializeExpiresAtDateInSeconds() throws Exception {
- PayloadClaimsHolder holder = holderFor("exp", new Date(1478874000));
- serializer.serialize(holder, jsonGenerator, serializerProvider);
- jsonGenerator.flush();
-
- assertThat(writer.toString(), is(equalTo("{\"exp\":1478874}")));
- }
-
- @Test
- public void shouldSerializeCustomDateInSeconds() throws Exception {
- PayloadClaimsHolder holder = holderFor("birthdate", new Date(1478874000));
- serializer.serialize(holder, jsonGenerator, serializerProvider);
- jsonGenerator.flush();
-
- assertThat(writer.toString(), is(equalTo("{\"birthdate\":1478874}")));
- }
-
- @Test
- public void shouldSerializeDatesUsingLong() throws Exception {
- long secs = Integer.MAX_VALUE + 10000L;
- Date date = new Date(secs * 1000L);
- Map claims = new HashMap<>();
- claims.put("iat", date);
- claims.put("nbf", date);
- claims.put("exp", date);
- claims.put("ctm", date);
- claims.put("map", Collections.singletonMap("date", date));
- claims.put("list", Collections.singletonList(date));
-
- Map nestedInMap = new HashMap<>();
- nestedInMap.put("list", Collections.singletonList(date));
- claims.put("nestedInMap", nestedInMap);
-
- List nestedInList = new ArrayList<>();
- nestedInList.add(Collections.singletonMap("nested", date));
- claims.put("nestedInList", nestedInList);
-
- PayloadClaimsHolder holder = new PayloadClaimsHolder(claims);
- serializer.serialize(holder, jsonGenerator, serializerProvider);
- jsonGenerator.flush();
-
- String json = writer.toString();
- System.out.println(json);
-
- assertThat(json, containsString("\"iat\":2147493647"));
- assertThat(json, containsString("\"nbf\":2147493647"));
- assertThat(json, containsString("\"exp\":2147493647"));
- assertThat(json, containsString("\"ctm\":2147493647"));
- assertThat(json, containsString("\"map\":{\"date\":2147493647"));
- assertThat(json, containsString("\"list\":[2147493647]"));
- assertThat(json, containsString("\"nestedInMap\":{\"list\":[2147493647]}"));
- assertThat(json, containsString("\"nestedInList\":[{\"nested\":2147493647}]"));
- }
-
- @Test
- public void shouldSerializeStrings() throws Exception {
- PayloadClaimsHolder holder = holderFor("name", "Auth0 Inc");
- serializer.serialize(holder, jsonGenerator, serializerProvider);
- jsonGenerator.flush();
-
- assertThat(writer.toString(), is(equalTo("{\"name\":\"Auth0 Inc\"}")));
- }
-
- @Test
- public void shouldSerializeIntegers() throws Exception {
- PayloadClaimsHolder holder = holderFor("number", 12345);
- serializer.serialize(holder, jsonGenerator, serializerProvider);
- jsonGenerator.flush();
-
- assertThat(writer.toString(), is(equalTo("{\"number\":12345}")));
- }
-
- @Test
- public void shouldSerializeDoubles() throws Exception {
- PayloadClaimsHolder holder = holderFor("fraction", 23.45);
- serializer.serialize(holder, jsonGenerator, serializerProvider);
- jsonGenerator.flush();
-
- assertThat(writer.toString(), is(equalTo("{\"fraction\":23.45}")));
- }
-
- @Test
- public void shouldSerializeBooleans() throws Exception {
- PayloadClaimsHolder holder = holderFor("pro", true);
- serializer.serialize(holder, jsonGenerator, serializerProvider);
- jsonGenerator.flush();
-
- assertThat(writer.toString(), is(equalTo("{\"pro\":true}")));
- }
-
- @Test
- public void shouldSerializeNulls() throws Exception {
- PayloadClaimsHolder holder = holderFor("id", null);
- serializer.serialize(holder, jsonGenerator, serializerProvider);
- jsonGenerator.flush();
-
- assertThat(writer.toString(), is(equalTo("{\"id\":null}")));
- }
-
- @Test
- public void shouldSerializeCustomArrayOfObject() throws Exception {
- UserPojo user1 = new UserPojo("Michael", 1);
- UserPojo user2 = new UserPojo("Lucas", 2);
- PayloadClaimsHolder holder = holderFor("users", new UserPojo[]{user1, user2});
- serializer.serialize(holder, jsonGenerator, serializerProvider);
- jsonGenerator.flush();
-
- assertThat(writer.toString(), is(equalTo("{\"users\":[{\"name\":\"Michael\",\"id\":1},{\"name\":\"Lucas\",\"id\":2}]}")));
- }
-
- @Test
- public void shouldSerializeCustomListOfObject() throws Exception {
- UserPojo user1 = new UserPojo("Michael", 1);
- UserPojo user2 = new UserPojo("Lucas", 2);
- PayloadClaimsHolder holder = holderFor("users", Arrays.asList(user1, user2));
- serializer.serialize(holder, jsonGenerator, serializerProvider);
- jsonGenerator.flush();
-
- assertThat(writer.toString(), is(equalTo("{\"users\":[{\"name\":\"Michael\",\"id\":1},{\"name\":\"Lucas\",\"id\":2}]}")));
- }
-
- @Test
- public void shouldSerializeCustomObject() throws Exception {
- UserPojo user = new UserPojo("Michael", 1);
- PayloadClaimsHolder holder = holderFor("users", user);
- serializer.serialize(holder, jsonGenerator, serializerProvider);
- jsonGenerator.flush();
-
- assertThat(writer.toString(), is(equalTo("{\"users\":{\"name\":\"Michael\",\"id\":1}}")));
- }
-
- private PayloadClaimsHolder holderFor(String key, Object value) {
- Map map = new HashMap<>();
- map.put(key, value);
- return new PayloadClaimsHolder(map);
- }
-
-}
\ No newline at end of file
diff --git a/lib/src/test/java/com/auth0/jwt/interfaces/ClaimTest.java b/lib/src/test/java/com/auth0/jwt/interfaces/ClaimTest.java
deleted file mode 100644
index 61541ccf..00000000
--- a/lib/src/test/java/com/auth0/jwt/interfaces/ClaimTest.java
+++ /dev/null
@@ -1,98 +0,0 @@
-package com.auth0.jwt.interfaces;
-
-import com.auth0.jwt.exceptions.JWTDecodeException;
-import org.junit.Test;
-
-import java.util.Date;
-import java.util.List;
-import java.util.Map;
-
-import static org.hamcrest.MatcherAssert.assertThat;
-import static org.hamcrest.Matchers.*;
-
-public class ClaimTest {
-
- @Test
- public void shouldGetInstantUsingDefault() {
- Date date = new Date(1646667492000L);
- Claim claim = new ClaimImplForTest(date);
- assertThat(claim.asInstant(), is(date.toInstant()));
- }
-
- @Test
- public void shouldGetNullInstantUsingDefault() {
- Claim claim = new ClaimImplForTest(null);
- assertThat(claim.asInstant(), is(nullValue()));
- }
-
- /**
- * Implementation that does not override {@code asInstant()}
- */
- static class ClaimImplForTest implements Claim {
- private final Date date;
-
- ClaimImplForTest(Date date) {
- this.date = date;
- }
-
- @Override
- public boolean isNull() {
- return false;
- }
-
- @Override
- public boolean isMissing() {
- return false;
- }
-
- @Override
- public Boolean asBoolean() {
- return null;
- }
-
- @Override
- public Integer asInt() {
- return null;
- }
-
- @Override
- public Long asLong() {
- return null;
- }
-
- @Override
- public Double asDouble() {
- return null;
- }
-
- @Override
- public String asString() {
- return null;
- }
-
- @Override
- public Date asDate() {
- return date;
- }
-
- @Override
- public T[] asArray(Class clazz) throws JWTDecodeException {
- return null;
- }
-
- @Override
- public List asList(Class clazz) throws JWTDecodeException {
- return null;
- }
-
- @Override
- public Map asMap() throws JWTDecodeException {
- return null;
- }
-
- @Override
- public T as(Class tClazz) throws JWTDecodeException {
- return null;
- }
- }
-}
diff --git a/lib/src/test/java/com/auth0/jwt/interfaces/PayloadTest.java b/lib/src/test/java/com/auth0/jwt/interfaces/PayloadTest.java
deleted file mode 100644
index c5d2bd00..00000000
--- a/lib/src/test/java/com/auth0/jwt/interfaces/PayloadTest.java
+++ /dev/null
@@ -1,83 +0,0 @@
-package com.auth0.jwt.interfaces;
-
-import org.junit.Test;
-
-import java.util.Date;
-import java.util.List;
-import java.util.Map;
-
-import static org.hamcrest.MatcherAssert.assertThat;
-import static org.hamcrest.Matchers.*;
-
-public class PayloadTest {
-
- @Test
- public void shouldGetInstantFromDefault() {
- Date date = new Date(1646667492000L);
- Payload payload = new PayloadImplForTest(date);
- assertThat(payload.getExpiresAtAsInstant(), is(date.toInstant()));
- assertThat(payload.getIssuedAtAsInstant(), is(date.toInstant()));
- assertThat(payload.getNotBeforeAsInstant(), is(date.toInstant()));
- }
-
- @Test
- public void shouldGetInstantFromDefaultAsNu() {
- Payload payload = new PayloadImplForTest(null);
- assertThat(payload.getExpiresAtAsInstant(), is(nullValue()));
- assertThat(payload.getIssuedAtAsInstant(), is(nullValue()));
- assertThat(payload.getNotBeforeAsInstant(), is(nullValue()));
- }
-
- static class PayloadImplForTest implements Payload {
- private final Date date;
-
- PayloadImplForTest(Date date) {
- this.date = date;
- }
-
- @Override
- public String getIssuer() {
- return null;
- }
-
- @Override
- public String getSubject() {
- return null;
- }
-
- @Override
- public List getAudience() {
- return null;
- }
-
- @Override
- public Date getExpiresAt() {
- return date;
- }
-
- @Override
- public Date getNotBefore() {
- return date;
- }
-
- @Override
- public Date getIssuedAt() {
- return date;
- }
-
- @Override
- public String getId() {
- return null;
- }
-
- @Override
- public Claim getClaim(String name) {
- return null;
- }
-
- @Override
- public Map getClaims() {
- return null;
- }
- }
-}
diff --git a/lib/src/test/java/com/auth0/jwt/interfaces/VerificationTest.java b/lib/src/test/java/com/auth0/jwt/interfaces/VerificationTest.java
deleted file mode 100644
index 11acb029..00000000
--- a/lib/src/test/java/com/auth0/jwt/interfaces/VerificationTest.java
+++ /dev/null
@@ -1,171 +0,0 @@
-package com.auth0.jwt.interfaces;
-
-import com.auth0.jwt.JWTVerifier;
-import org.junit.Test;
-
-import java.time.Instant;
-import java.util.Date;
-import java.util.HashMap;
-import java.util.Map;
-import java.util.function.BiPredicate;
-
-import static org.hamcrest.MatcherAssert.assertThat;
-import static org.hamcrest.Matchers.hasEntry;
-import static org.hamcrest.Matchers.instanceOf;
-import static org.junit.Assert.assertThrows;
-
-/**
- * Tests for any default method implementations in the {@link Verification} interface.
- */
-public class VerificationTest {
-
- @Test
- public void withInstantClaimShouldUseDefaultImpl() {
- Instant instant = Instant.ofEpochSecond(1478891521);
- Verification verification = new VerificationImplForTest()
- .withClaim("name", instant);
-
- assertThat(verification, instanceOf(VerificationImplForTest.class));
- assertThat(((VerificationImplForTest)verification).expectedClaims, hasEntry("name", Date.from(instant)));
- }
-
- @Test
- public void withInstantClaimShouldUseDefaultImplAndHandleNull() {
- Verification verification = new VerificationImplForTest()
- .withClaim("name", (Instant) null);
-
- assertThat(verification, instanceOf(VerificationImplForTest.class));
- assertThat(((VerificationImplForTest)verification).expectedClaims, hasEntry("name", null));
- }
-
- @Test
- public void withIssuerStringDefaultImplShouldDelegate() {
- Verification verification = new VerificationImplForTest()
- .withIssuer("string");
-
- assertThat(verification, instanceOf(VerificationImplForTest.class));
- assertThat(((VerificationImplForTest)verification).expectedClaims, hasEntry("iss", new String[]{"string"}));
- }
-
- static class VerificationImplForTest implements Verification {
-
- private final Map expectedClaims = new HashMap<>();
-
- @Override
- public Verification withIssuer(String... issuer) {
- expectedClaims.put("iss", issuer);
- return this;
- }
-
- @Override
- public Verification withSubject(String subject) {
- return null;
- }
-
- @Override
- public Verification withAudience(String... audience) {
- return null;
- }
-
- @Override
- public Verification withAnyOfAudience(String... audience) {
- return null;
- }
-
- @Override
- public Verification acceptLeeway(long leeway) throws IllegalArgumentException {
- return null;
- }
-
- @Override
- public Verification acceptExpiresAt(long leeway) throws IllegalArgumentException {
- return null;
- }
-
- @Override
- public Verification acceptNotBefore(long leeway) throws IllegalArgumentException {
- return null;
- }
-
- @Override
- public Verification acceptIssuedAt(long leeway) throws IllegalArgumentException {
- return null;
- }
-
- @Override
- public Verification withJWTId(String jwtId) {
- return null;
- }
-
- @Override
- public Verification withClaimPresence(String name) throws IllegalArgumentException {
- return null;
- }
-
- @Override
- public Verification withNullClaim(String name) throws IllegalArgumentException {
- return null;
- }
-
- @Override
- public Verification withClaim(String name, Boolean value) throws IllegalArgumentException {
- return null;
- }
-
- @Override
- public Verification withClaim(String name, Integer value) throws IllegalArgumentException {
- return null;
- }
-
- @Override
- public Verification withClaim(String name, Long value) throws IllegalArgumentException {
- return null;
- }
-
- @Override
- public Verification withClaim(String name, Double value) throws IllegalArgumentException {
- return null;
- }
-
- @Override
- public Verification withClaim(String name, String value) throws IllegalArgumentException {
- return null;
- }
-
- @Override
- public Verification withClaim(String name, Date value) throws IllegalArgumentException {
- this.expectedClaims.put(name, value);
- return this;
- }
-
- @Override
- public Verification withArrayClaim(String name, String... items) throws IllegalArgumentException {
- return null;
- }
-
- @Override
- public Verification withArrayClaim(String name, Integer... items) throws IllegalArgumentException {
- return null;
- }
-
- @Override
- public Verification withArrayClaim(String name, Long... items) throws IllegalArgumentException {
- return null;
- }
-
- @Override
- public Verification withClaim(String name, BiPredicate predicate) throws IllegalArgumentException {
- return null;
- }
-
- @Override
- public Verification ignoreIssuedAt() {
- return null;
- }
-
- @Override
- public JWTVerifier build() {
- return null;
- }
- }
-}
diff --git a/lib/src/test/resources/ec256-key-pair.pem b/lib/src/test/resources/ec256-key-pair.pem
deleted file mode 100644
index 63e8673f..00000000
--- a/lib/src/test/resources/ec256-key-pair.pem
+++ /dev/null
@@ -1,5 +0,0 @@
------BEGIN EC PRIVATE KEY-----
-MHcCAQEEIDxiRgJuF9X7wbgtc0qTv+CM8ej13zTGoimkuUVJBahBoAoGCCqGSM49
-AwEHoUQDQgAEQgb5npLHd0Bk61bNnjK632uwmBfrF7I8hoPgaOZjyhh+BrPDO6CL
-6D/aW/yPObXXm7SpZogmRwGROcOA3yUleg==
------END EC PRIVATE KEY-----
diff --git a/lib/src/test/resources/ec256-key-private.pem b/lib/src/test/resources/ec256-key-private.pem
deleted file mode 100644
index 756361a1..00000000
--- a/lib/src/test/resources/ec256-key-private.pem
+++ /dev/null
@@ -1,5 +0,0 @@
------BEGIN PRIVATE KEY-----
-MIGHAgEAMBMGByqGSM49AgEGCCqGSM49AwEHBG0wawIBAQQgPGJGAm4X1fvBuC1z
-SpO/4Izx6PXfNMaiKaS5RUkFqEGhRANCAARCBvmeksd3QGTrVs2eMrrfa7CYF+sX
-sjyGg+Bo5mPKGH4Gs8M7oIvoP9pb/I85tdebtKlmiCZHAZE5w4DfJSV6
------END PRIVATE KEY-----
diff --git a/lib/src/test/resources/ec256-key-public-invalid.pem b/lib/src/test/resources/ec256-key-public-invalid.pem
deleted file mode 100644
index 8e4f6a97..00000000
--- a/lib/src/test/resources/ec256-key-public-invalid.pem
+++ /dev/null
@@ -1,4 +0,0 @@
------BEGIN PUBLIC KEY-----
-MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEoBUyo8CQAFPeYPvv78ylh5MwFZjT
-CLQeb042TjiMJxG+9DLFmRSMlBQ9T/RsLLc+PmpB1+7yPAR+oR5gZn3kJQ==
------END PUBLIC KEY-----
diff --git a/lib/src/test/resources/ec256-key-public.pem b/lib/src/test/resources/ec256-key-public.pem
deleted file mode 100644
index 34401f77..00000000
--- a/lib/src/test/resources/ec256-key-public.pem
+++ /dev/null
@@ -1,4 +0,0 @@
------BEGIN PUBLIC KEY-----
-MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEQgb5npLHd0Bk61bNnjK632uwmBfr
-F7I8hoPgaOZjyhh+BrPDO6CL6D/aW/yPObXXm7SpZogmRwGROcOA3yUleg==
------END PUBLIC KEY-----
diff --git a/lib/src/test/resources/ec384-key-pair.pem b/lib/src/test/resources/ec384-key-pair.pem
deleted file mode 100644
index 8c124080..00000000
--- a/lib/src/test/resources/ec384-key-pair.pem
+++ /dev/null
@@ -1,6 +0,0 @@
------BEGIN EC PRIVATE KEY-----
-MIGkAgEBBDCVWQsOJHjKD0I4cXOYJm4G8i5c7IMhFbxFq57OUlrTVmND43dvvNW1
-oQ6i6NiXEQWgBwYFK4EEACKhZANiAASezSGlAu4wAaJe4676mQM0F/5slI+Ekdpt
-RJdfsQP9mNxe7RdzHgcSw7j/Wxa45nlnFnFrPPL4viJKOBRxMB1jjVA9my9PixxJ
-GoB22qDQwFbP8ldmEp6abwdBsXNaePM=
------END EC PRIVATE KEY-----
diff --git a/lib/src/test/resources/ec384-key-private.pem b/lib/src/test/resources/ec384-key-private.pem
deleted file mode 100644
index 9482bfa8..00000000
--- a/lib/src/test/resources/ec384-key-private.pem
+++ /dev/null
@@ -1,6 +0,0 @@
------BEGIN PRIVATE KEY-----
-MIG2AgEAMBAGByqGSM49AgEGBSuBBAAiBIGeMIGbAgEBBDCVWQsOJHjKD0I4cXOY
-Jm4G8i5c7IMhFbxFq57OUlrTVmND43dvvNW1oQ6i6NiXEQWhZANiAASezSGlAu4w
-AaJe4676mQM0F/5slI+EkdptRJdfsQP9mNxe7RdzHgcSw7j/Wxa45nlnFnFrPPL4
-viJKOBRxMB1jjVA9my9PixxJGoB22qDQwFbP8ldmEp6abwdBsXNaePM=
------END PRIVATE KEY-----
diff --git a/lib/src/test/resources/ec384-key-public-invalid.pem b/lib/src/test/resources/ec384-key-public-invalid.pem
deleted file mode 100644
index 1f4b6853..00000000
--- a/lib/src/test/resources/ec384-key-public-invalid.pem
+++ /dev/null
@@ -1,5 +0,0 @@
------BEGIN PUBLIC KEY-----
-MHYwEAYHKoZIzj0CAQYFK4EEACIDYgAEJ0tamPyAJVUhDO1DlceSYCdA9WKVX6nO
-K4VYetXvqmMKdyVkaoA4Gl02KoVLujiSSSAE6oK/Hf7x2fagaE9LgJdJxg07Ip+T
-C6cgFi2HHDeXG7djB5Zl1TKA9/w/8iW5
------END PUBLIC KEY-----
diff --git a/lib/src/test/resources/ec384-key-public.pem b/lib/src/test/resources/ec384-key-public.pem
deleted file mode 100644
index 511596e7..00000000
--- a/lib/src/test/resources/ec384-key-public.pem
+++ /dev/null
@@ -1,5 +0,0 @@
------BEGIN PUBLIC KEY-----
-MHYwEAYHKoZIzj0CAQYFK4EEACIDYgAEns0hpQLuMAGiXuOu+pkDNBf+bJSPhJHa
-bUSXX7ED/ZjcXu0Xcx4HEsO4/1sWuOZ5ZxZxazzy+L4iSjgUcTAdY41QPZsvT4sc
-SRqAdtqg0MBWz/JXZhKemm8HQbFzWnjz
------END PUBLIC KEY-----
diff --git a/lib/src/test/resources/ec512-key-pair.pem b/lib/src/test/resources/ec512-key-pair.pem
deleted file mode 100644
index 1428daae..00000000
--- a/lib/src/test/resources/ec512-key-pair.pem
+++ /dev/null
@@ -1,7 +0,0 @@
------BEGIN EC PRIVATE KEY-----
-MIHbAgEBBEHzl1DpZSQJ8YhCbN/uvo5SOu0BjDDX9Gub6zsBW6B2TxRzb5sBeQaW
-VscDUZha4Xr1HEWpVtua9+nEQU/9Aq9Pl6AHBgUrgQQAI6GBiQOBhgAEAJhvCa6S
-89ePqlLO6MRV9KQqHvdAITDAf/WRDcvCmfrrNuov+j4gQXO12ohIukPCHM9rYms8
-Eqciz3gaxVTxZD4CAA8i2k9H6ew9iSh1qXa1kLxiyzMBqmAmmg4u/SroD6OleG56
-SwZVbWx+KIINB6r/PQVciGX8FjwgR/mbLHotVZYD
------END EC PRIVATE KEY-----
diff --git a/lib/src/test/resources/ec512-key-private.pem b/lib/src/test/resources/ec512-key-private.pem
deleted file mode 100644
index bde90986..00000000
--- a/lib/src/test/resources/ec512-key-private.pem
+++ /dev/null
@@ -1,7 +0,0 @@
------BEGIN PRIVATE KEY-----
-MIHtAgEAMBAGByqGSM49AgEGBSuBBAAjBIHVMIHSAgEBBEHzl1DpZSQJ8YhCbN/u
-vo5SOu0BjDDX9Gub6zsBW6B2TxRzb5sBeQaWVscDUZha4Xr1HEWpVtua9+nEQU/9
-Aq9Pl6GBiQOBhgAEAJhvCa6S89ePqlLO6MRV9KQqHvdAITDAf/WRDcvCmfrrNuov
-+j4gQXO12ohIukPCHM9rYms8Eqciz3gaxVTxZD4CAA8i2k9H6ew9iSh1qXa1kLxi
-yzMBqmAmmg4u/SroD6OleG56SwZVbWx+KIINB6r/PQVciGX8FjwgR/mbLHotVZYD
------END PRIVATE KEY-----
diff --git a/lib/src/test/resources/ec512-key-public-invalid.pem b/lib/src/test/resources/ec512-key-public-invalid.pem
deleted file mode 100644
index f976d7f5..00000000
--- a/lib/src/test/resources/ec512-key-public-invalid.pem
+++ /dev/null
@@ -1,6 +0,0 @@
------BEGIN PUBLIC KEY-----
-MIGbMBAGByqGSM49AgEGBSuBBAAjA4GGAAQBgtBWt9rVtdQPdeoChvCXnXHvkg/F
-41AAubIVd+3yTvLFmxuHuaor9CHl7FlT3532mUG+GG0EEw5UuYkFrg/ABBgAfuVf
-wO1u0V0wJPkmpxcnZoojFaAOKcsBvUvDulbBh0HhAyd+nlfZquvV43uwFVpn2Cjb
-Lx+/AT1PE6Muqy4JkGU=
------END PUBLIC KEY-----
diff --git a/lib/src/test/resources/ec512-key-public.pem b/lib/src/test/resources/ec512-key-public.pem
deleted file mode 100644
index 360209ae..00000000
--- a/lib/src/test/resources/ec512-key-public.pem
+++ /dev/null
@@ -1,6 +0,0 @@
------BEGIN PUBLIC KEY-----
-MIGbMBAGByqGSM49AgEGBSuBBAAjA4GGAAQAmG8JrpLz14+qUs7oxFX0pCoe90Ah
-MMB/9ZENy8KZ+us26i/6PiBBc7XaiEi6Q8Icz2tiazwSpyLPeBrFVPFkPgIADyLa
-T0fp7D2JKHWpdrWQvGLLMwGqYCaaDi79KugPo6V4bnpLBlVtbH4ogg0Hqv89BVyI
-ZfwWPCBH+Zssei1VlgM=
------END PUBLIC KEY-----
diff --git a/lib/src/test/resources/rsa-private.pem b/lib/src/test/resources/rsa-private.pem
deleted file mode 100644
index e4519683..00000000
--- a/lib/src/test/resources/rsa-private.pem
+++ /dev/null
@@ -1,28 +0,0 @@
------BEGIN PRIVATE KEY-----
-MIIEvwIBADANBgkqhkiG9w0BAQEFAASCBKkwggSlAgEAAoIBAQC4ZtdaIrd1BPIJ
-tfnF0TjIK5inQAXZ3XlCrUlJdP+XHwIRxdv1FsN12XyMYO/6ymLmo9ryoQeIrsXB
-XYqlET3zfAY+diwCb0HEsVvhisthwMU4gZQu6TYW2s9LnXZB5rVtcBK69hcSlA2k
-ZudMZWxZcj0L7KMfO2rIvaHw/qaVOE9j0T257Z8Kp2CLF9MUgX0ObhIsdumFRLaL
-DvDUmBPr2zuh/34j2XmWwn1yjN/WvGtdfhXW79Ki1S40HcWnygHgLV8sESFKUxxQ
-mKvPUTwDOIwLFL5WtE8Mz7N++kgmDcmWMCHc8kcOIu73Ta/3D4imW7VbKgHZo9+K
-3ESFE3RjAgMBAAECggEBAJTEIyjMqUT24G2FKiS1TiHvShBkTlQdoR5xvpZMlYbN
-tVWxUmrAGqCQ/TIjYnfpnzCDMLhdwT48Ab6mQJw69MfiXwc1PvwX1e9hRscGul36
-ryGPKIVQEBsQG/zc4/L2tZe8ut+qeaK7XuYrPp8bk/X1e9qK5m7j+JpKosNSLgJj
-NIbYsBkG2Mlq671irKYj2hVZeaBQmWmZxK4fw0Istz2WfN5nUKUeJhTwpR+JLUg4
-ELYYoB7EO0Cej9UBG30hbgu4RyXA+VbptJ+H042K5QJROUbtnLWuuWosZ5ATldwO
-u03dIXL0SH0ao5NcWBzxU4F2sBXZRGP2x/jiSLHcqoECgYEA4qD7mXQpu1b8XO8U
-6abpKloJCatSAHzjgdR2eRDRx5PMvloipfwqA77pnbjTUFajqWQgOXsDTCjcdQui
-wf5XAaWu+TeAVTytLQbSiTsBhrnoqVrr3RoyDQmdnwHT8aCMouOgcC5thP9vQ8Us
-rVdjvRRbnJpg3BeSNimH+u9AHgsCgYEA0EzcbOltCWPHRAY7B3Ge/AKBjBQr86Kv
-TdpTlxePBDVIlH+BM6oct2gaSZZoHbqPjbq5v7yf0fKVcXE4bSVgqfDJ/sZQu9Lp
-PTeV7wkk0OsAMKk7QukEpPno5q6tOTNnFecpUhVLLlqbfqkB2baYYwLJR3IRzboJ
-FQbLY93E8gkCgYB+zlC5VlQbbNqcLXJoImqItgQkkuW5PCgYdwcrSov2ve5r/Acz
-FNt1aRdSlx4176R3nXyibQA1Vw+ztiUFowiP9WLoM3PtPZwwe4bGHmwGNHPIfwVG
-m+exf9XgKKespYbLhc45tuC08DATnXoYK7O1EnUINSFJRS8cezSI5eHcbQKBgQDC
-PgqHXZ2aVftqCc1eAaxaIRQhRmY+CgUjumaczRFGwVFveP9I6Gdi+Kca3DE3F9Pq
-PKgejo0SwP5vDT+rOGHN14bmGJUMsX9i4MTmZUZ5s8s3lXh3ysfT+GAhTd6nKrIE
-kM3Nh6HWFhROptfc6BNusRh1kX/cspDplK5x8EpJ0QKBgQDWFg6S2je0KtbV5PYe
-RultUEe2C0jYMDQx+JYxbPmtcopvZQrFEur3WKVuLy5UAy7EBvwMnZwIG7OOohJb
-vkSpADK6VPn9lbqq7O8cTedEHttm6otmLt8ZyEl3hZMaL3hbuRj6ysjmoFKx6CrX
-rK0/Ikt5ybqUzKCMJZg2VKGTxg==
------END PRIVATE KEY-----
\ No newline at end of file
diff --git a/lib/src/test/resources/rsa-public.pem b/lib/src/test/resources/rsa-public.pem
deleted file mode 100644
index e8d62885..00000000
--- a/lib/src/test/resources/rsa-public.pem
+++ /dev/null
@@ -1,9 +0,0 @@
------BEGIN PUBLIC KEY-----
-MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAuGbXWiK3dQTyCbX5xdE4
-yCuYp0AF2d15Qq1JSXT/lx8CEcXb9RbDddl8jGDv+spi5qPa8qEHiK7FwV2KpRE9
-83wGPnYsAm9BxLFb4YrLYcDFOIGULuk2FtrPS512Qea1bXASuvYXEpQNpGbnTGVs
-WXI9C+yjHztqyL2h8P6mlThPY9E9ue2fCqdgixfTFIF9Dm4SLHbphUS2iw7w1JgT
-69s7of9+I9l5lsJ9cozf1rxrXX4V1u/SotUuNB3Fp8oB4C1fLBEhSlMcUJirz1E8
-AziMCxS+VrRPDM+zfvpIJg3JljAh3PJHDiLu902v9w+Iplu1WyoB2aPfitxEhRN0
-YwIDAQAB
------END PUBLIC KEY-----
diff --git a/lib/src/test/resources/rsa-public_invalid.pem b/lib/src/test/resources/rsa-public_invalid.pem
deleted file mode 100644
index eab17cf7..00000000
--- a/lib/src/test/resources/rsa-public_invalid.pem
+++ /dev/null
@@ -1,9 +0,0 @@
------BEGIN PUBLIC KEY-----
-MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAxzYuc22QSst/dS7geYYK
-5l5kLxU0tayNdixkEQ17ix+CUcUbKIsnyftZxaCYT46rQtXgCaYRdJcbB3hmyrOa
-vkhTpX79xJZnQmfuamMbZBqitvscxW9zRR9tBUL6vdi/0rpoUwPMEh8+Bw7CgYR0
-FK0DhWYBNDfe9HKcyZEv3max8Cdq18htxjEsdYO0iwzhtKRXomBWTdhD5ykd/fAC
-VTr4+KEY+IeLvubHVmLUhbE5NgWXxrRpGasDqzKhCTmsa2Ysf712rl57SlH0Wz/M
-r3F7aM9YpErzeYLrl0GhQr9BVJxOvXcVd4kmY+XkiCcrkyS1cnghnllh+LCwQu1s
-YwIDAQAB
------END PUBLIC KEY-----
diff --git a/opslevel.yml b/opslevel.yml
deleted file mode 100644
index 009a5ec0..00000000
--- a/opslevel.yml
+++ /dev/null
@@ -1,6 +0,0 @@
----
-version: 1
-repository:
- owner: dx_sdks
- tier:
- tags:
diff --git a/pom.xml b/pom.xml
new file mode 100644
index 00000000..b1c69ea2
--- /dev/null
+++ b/pom.xml
@@ -0,0 +1,158 @@
+
+ 4.0.0
+
+
+ org.sonatype.oss
+ oss-parent
+ 9
+
+
+ com.auth0
+ java-jwt
+ 2.3.1-SNAPSHOT
+
+ Java JWT
+ Java implementation of JSON Web Token developed against draft-ietf-oauth-json-web-token-08.
+
+ http://www.jwt.io
+
+
+ 1.7
+ 1.7
+ com.auth0.jwt.internal
+
+
+
+
+ The MIT License
+ http://www.opensource.org/licenses/mit-license.php
+ repo
+
+
+
+
+ https://github.com/auth0/java-jwt
+ scm:git:git@github.com:auth0/java-jwt.git
+ scm:git:git@github.com:auth0/java-jwt.git
+
+
+
+
+
+ com.fasterxml.jackson.core
+ jackson-databind
+ 2.0.1
+
+
+
+ org.bouncycastle
+ bcprov-jdk15on
+ 1.52
+
+
+
+ commons-codec
+ commons-codec
+ 1.10
+
+
+
+ org.apache.commons
+ commons-lang3
+ 3.4
+
+
+
+
+
+ junit
+ junit
+ 4.12
+ test
+
+
+
+
+
+
+
+ org.apache.maven.plugins
+ maven-compiler-plugin
+ 3.1
+
+ ${java.source.version}
+ ${java.target.version}
+ UTF-8
+
+
+
+ org.jacoco
+ jacoco-maven-plugin
+ 0.7.7.201606060606
+
+
+
+ prepare-agent
+
+
+
+ report
+ test
+
+ report
+
+
+
+
+
+ org.apache.maven.plugins
+ maven-shade-plugin
+ 2.2
+
+
+ package
+
+ shade
+
+
+
+
+ *:*
+
+ META-INF/*.SF
+ META-INF/*.DSA
+ META-INF/*.RSA
+
+
+
+ false
+ true
+
+
+ com.fasterxml.jackson
+ ${repackage.base}.com.fasterxml.jackson
+
+
+ org.apache.commons.codec
+ ${repackage.base}.org.apache.commons.codec
+
+
+ org.apache.commons.io
+ ${repackage.base}.org.apache.commons.io
+
+
+ org.apache.commons.lang3
+ ${repackage.base}.org.apache.commons.lang3
+
+
+ org.bouncycastle
+ ${repackage.base}.org.bouncycastle
+
+
+
+
+
+
+
+
+
diff --git a/settings.gradle b/settings.gradle
deleted file mode 100644
index d3c4c85b..00000000
--- a/settings.gradle
+++ /dev/null
@@ -1,8 +0,0 @@
-pluginManagement {
- repositories {
- gradlePluginPortal()
- }
-}
-
-include ':java-jwt'
-project(':java-jwt').projectDir = new File(rootProject.projectDir, '/lib')
diff --git a/src/main/java/com/auth0/jwt/Algorithm.java b/src/main/java/com/auth0/jwt/Algorithm.java
new file mode 100644
index 00000000..b3009a73
--- /dev/null
+++ b/src/main/java/com/auth0/jwt/Algorithm.java
@@ -0,0 +1,33 @@
+package com.auth0.jwt;
+
+import org.apache.commons.lang3.Validate;
+
+/**
+ * Supported Library Algorithms
+ *
+ * https://docs.oracle.com/javase/7/docs/technotes/guides/security/StandardNames.html#KeyPairGenerator
+ */
+public enum Algorithm {
+
+ HS256("HmacSHA256"), HS384("HmacSHA384"), HS512("HmacSHA512"), RS256("SHA256withRSA"), RS384("SHA384withRSA"), RS512("SHA512withRSA");
+
+ private Algorithm(final String value) {
+ this.value = value;
+ }
+
+ private String value;
+
+ public String getValue() {
+ return value;
+ }
+
+ public static Algorithm findByName(final String name) throws JWTAlgorithmException {
+ Validate.notNull(name);
+ try {
+ return Algorithm.valueOf(name);
+ } catch (IllegalArgumentException e) {
+ throw new JWTAlgorithmException("Unsupported algorithm: " + name);
+ }
+ }
+
+}
diff --git a/src/main/java/com/auth0/jwt/JWTAlgorithmException.java b/src/main/java/com/auth0/jwt/JWTAlgorithmException.java
new file mode 100644
index 00000000..fec47b3e
--- /dev/null
+++ b/src/main/java/com/auth0/jwt/JWTAlgorithmException.java
@@ -0,0 +1,20 @@
+package com.auth0.jwt;
+
+/**
+ * Represents Exception related to Algorithm - for example JWT header algorithm is unsupported / missing
+ */
+public class JWTAlgorithmException extends JWTVerifyException {
+
+
+ public JWTAlgorithmException() {}
+
+ public JWTAlgorithmException(final String message, final Throwable cause) {
+ super(message, cause);
+ }
+
+ public JWTAlgorithmException(final String message) {
+ super(message);
+ }
+
+}
+
diff --git a/src/main/java/com/auth0/jwt/JWTAudienceException.java b/src/main/java/com/auth0/jwt/JWTAudienceException.java
new file mode 100644
index 00000000..622d73b7
--- /dev/null
+++ b/src/main/java/com/auth0/jwt/JWTAudienceException.java
@@ -0,0 +1,36 @@
+package com.auth0.jwt;
+
+import com.fasterxml.jackson.databind.JsonNode;
+import org.apache.commons.lang3.Validate;
+
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * Represents Exception related to Audience - for example illegal audience on JWT Verification
+ */
+public class JWTAudienceException extends JWTVerifyException {
+
+ private JsonNode audienceNode;
+
+ public JWTAudienceException(final JsonNode audienceNode) {
+ this.audienceNode = audienceNode;
+ }
+
+ public JWTAudienceException(final String message, final JsonNode audienceNode) {
+ super(message);
+ this.audienceNode = audienceNode;
+ }
+
+ public List getAudience() {
+ final ArrayList audience = new ArrayList<>();
+ if (audienceNode.isArray()) {
+ for (final JsonNode jsonNode : audienceNode) {
+ audience.add(jsonNode.textValue());
+ }
+ } else if (audienceNode.isTextual()) {
+ audience.add(audienceNode.textValue());
+ }
+ return audience;
+ }
+}
diff --git a/src/main/java/com/auth0/jwt/JWTExpiredException.java b/src/main/java/com/auth0/jwt/JWTExpiredException.java
new file mode 100644
index 00000000..41086eef
--- /dev/null
+++ b/src/main/java/com/auth0/jwt/JWTExpiredException.java
@@ -0,0 +1,23 @@
+package com.auth0.jwt;
+
+
+/**
+ * Represents Exception related to Expiration - for example JWT token has expired
+ */
+public class JWTExpiredException extends JWTVerifyException {
+
+ private long expiration;
+
+ public JWTExpiredException(final long expiration) {
+ this.expiration = expiration;
+ }
+
+ public JWTExpiredException(final String message, final long expiration) {
+ super(message);
+ this.expiration = expiration;
+ }
+
+ public long getExpiration() {
+ return expiration;
+ };
+}
diff --git a/src/main/java/com/auth0/jwt/JWTIssuerException.java b/src/main/java/com/auth0/jwt/JWTIssuerException.java
new file mode 100644
index 00000000..13463ddc
--- /dev/null
+++ b/src/main/java/com/auth0/jwt/JWTIssuerException.java
@@ -0,0 +1,22 @@
+package com.auth0.jwt;
+
+/**
+ * Represents Exception related to Issuer - for example issuer mismatch / missing upon verification
+ */
+public class JWTIssuerException extends JWTVerifyException {
+
+ private final String issuer;
+
+ public JWTIssuerException(final String issuer) {
+ this.issuer = issuer;
+ }
+
+ public JWTIssuerException(final String message, final String issuer) {
+ super(message);
+ this.issuer = issuer;
+ }
+
+ public String getIssuer() {
+ return issuer;
+ }
+}
diff --git a/src/main/java/com/auth0/jwt/JWTSigner.java b/src/main/java/com/auth0/jwt/JWTSigner.java
new file mode 100644
index 00000000..828128ad
--- /dev/null
+++ b/src/main/java/com/auth0/jwt/JWTSigner.java
@@ -0,0 +1,362 @@
+package com.auth0.jwt;
+
+import com.fasterxml.jackson.databind.ObjectMapper;
+import com.fasterxml.jackson.databind.node.JsonNodeFactory;
+import com.fasterxml.jackson.databind.node.ObjectNode;
+import org.apache.commons.codec.binary.Base64;
+import org.apache.commons.lang3.StringUtils;
+import org.apache.commons.lang3.Validate;
+import org.bouncycastle.jce.provider.BouncyCastleProvider;
+
+import javax.crypto.Mac;
+import javax.crypto.spec.SecretKeySpec;
+import java.io.IOException;
+import java.io.UnsupportedEncodingException;
+import java.net.URI;
+import java.net.URISyntaxException;
+import java.security.*;
+import java.util.*;
+
+/**
+ * Handles JWT Sign Operation
+ *
+ * Default algorithm when none provided is HMAC SHA-256 ("HS256")
+ *
+ * See associated library test cases for clear examples on usage
+ *
+ */
+public class JWTSigner {
+
+ static {
+ if (Security.getProvider(BouncyCastleProvider.PROVIDER_NAME) == null) {
+ Security.addProvider(new BouncyCastleProvider());
+ }
+ }
+
+ private byte[] secret;
+ private PrivateKey privateKey;
+
+ // Default algorithm HMAC SHA-256 ("HS256")
+ protected final static Algorithm DEFAULT_ALGORITHM = Algorithm.HS256;
+
+ public JWTSigner(final String secret) {
+ this(secret.getBytes());
+ }
+
+ public JWTSigner(final byte[] secret) {
+ Validate.notNull(secret);
+ this.secret = secret;
+ }
+
+ public JWTSigner(final PrivateKey privateKey) {
+ this.privateKey = privateKey;
+ }
+
+ /**
+ * Generate a JSON Web Token.
+ *
+ * @param claims A map of the JWT claims that form the payload. Registered claims
+ * must be of appropriate Java datatype as following:
+ *
+ * iss, sub: String
+ * exp, nbf, iat, jti: numeric, eg. Long
+ * aud: String, or Collection<String>
+ *
+ * All claims with a null value are left out the JWT.
+ * Any claims set automatically as specified in
+ * the "options" parameter override claims in this map.
+ * @param options Allow choosing the signing algorithm, and automatic setting of some registered claims.
+ */
+ public String sign(final Map claims, final Options options) {
+ Validate.notNull(claims);
+ final Algorithm algorithm = (options != null && options.algorithm != null) ? options.algorithm : DEFAULT_ALGORITHM;
+ final List segments = new ArrayList<>();
+ try {
+ segments.add(encodedHeader(algorithm));
+ segments.add(encodedPayload(claims, options));
+ segments.add(encodedSignature(join(segments, "."), algorithm));
+ return join(segments, ".");
+ } catch (Exception e) {
+ throw new RuntimeException(e);
+ }
+ }
+
+ /**
+ * Generate a JSON Web Token using the default algorithm HMAC SHA-256 ("HS256")
+ * and no claims automatically set.
+ */
+ public String sign(final Map claims) {
+ Validate.notNull(claims);
+ return sign(claims, null);
+ }
+
+ /**
+ * Generate the header part of a JSON web token.
+ */
+ private String encodedHeader(final Algorithm algorithm) throws UnsupportedEncodingException {
+ Validate.notNull(algorithm);
+ // create the header
+ final ObjectNode header = JsonNodeFactory.instance.objectNode();
+ header.put("typ", "JWT");
+ header.put("alg", algorithm.name());
+ return base64UrlEncode(header.toString().getBytes("UTF-8"));
+ }
+
+ /**
+ * Generate the JSON web token payload string from the claims.
+ *
+ * @param options
+ */
+ private String encodedPayload(final Map _claims, final Options options) throws IOException {
+ final Map claims = new HashMap<>(_claims);
+ enforceStringOrURI(claims, "iss");
+ enforceStringOrURI(claims, "sub");
+ enforceStringOrURICollection(claims, "aud");
+ enforceIntDate(claims, "exp");
+ enforceIntDate(claims, "nbf");
+ enforceIntDate(claims, "iat");
+ enforceString(claims, "jti");
+ if (options != null) {
+ processPayloadOptions(claims, options);
+ }
+ final String payload = new ObjectMapper().writeValueAsString(claims);
+ return base64UrlEncode(payload.getBytes("UTF-8"));
+ }
+
+ private void processPayloadOptions(final Map claims, final Options options) {
+ Validate.notNull(claims);
+ Validate.notNull(options);
+ final long now = System.currentTimeMillis() / 1000l;
+ if (options.expirySeconds != null)
+ claims.put("exp", now + options.expirySeconds);
+ if (options.notValidBeforeLeeway != null)
+ claims.put("nbf", now - options.notValidBeforeLeeway);
+ if (options.isIssuedAt())
+ claims.put("iat", now);
+ if (options.isJwtId())
+ claims.put("jti", UUID.randomUUID().toString());
+ }
+
+ // consider cleanup
+ private void enforceIntDate(final Map claims, final String claimName) {
+ Validate.notNull(claims);
+ Validate.notNull(claimName);
+ final Object value = handleNullValue(claims, claimName);
+ if (value == null)
+ return;
+ if (!(value instanceof Number)) {
+ throw new IllegalStateException(String.format("Claim '%s' is invalid: must be an instance of Number", claimName));
+ }
+ final long longValue = ((Number) value).longValue();
+ if (longValue < 0)
+ throw new IllegalStateException(String.format("Claim '%s' is invalid: must be non-negative", claimName));
+ claims.put(claimName, longValue);
+ }
+
+ // consider cleanup
+ private void enforceStringOrURICollection(final Map claims, final String claimName) {
+ final Object values = handleNullValue(claims, claimName);
+ if (values == null)
+ return;
+ if (values instanceof Collection) {
+ @SuppressWarnings({"unchecked"})
+ final Iterator iterator = ((Collection) values).iterator();
+ while (iterator.hasNext()) {
+ Object value = iterator.next();
+ String error = checkStringOrURI(value);
+ if (error != null)
+ throw new IllegalStateException(String.format("Claim 'aud' element is invalid: %s", error));
+ }
+ } else {
+ enforceStringOrURI(claims, "aud");
+ }
+ }
+
+ // consider cleanup
+ private void enforceStringOrURI(final Map claims, final String claimName) {
+ final Object value = handleNullValue(claims, claimName);
+ if (value == null)
+ return;
+ final String error = checkStringOrURI(value);
+ if (error != null)
+ throw new IllegalStateException(String.format("Claim '%s' is invalid: %s", claimName, error));
+ }
+
+ // consider cleanup
+ private void enforceString(final Map claims, final String claimName) {
+ final Object value = handleNullValue(claims, claimName);
+ if (value == null)
+ return;
+ if (!(value instanceof String))
+ throw new IllegalStateException(String.format("Claim '%s' is invalid: not a string", claimName));
+ }
+
+ // consider cleanup
+ private Object handleNullValue(final Map claims, final String claimName) {
+ if (!claims.containsKey(claimName))
+ return null;
+ final Object value = claims.get(claimName);
+ if (value == null) {
+ claims.remove(claimName);
+ return null;
+ }
+ return value;
+ }
+
+ // consider cleanup
+ private String checkStringOrURI(final Object value) {
+ if (!(value instanceof String))
+ return "not a string";
+ final String stringOrUri = (String) value;
+ if (!stringOrUri.contains(":"))
+ return null;
+ try {
+ new URI(stringOrUri);
+ } catch (URISyntaxException e) {
+ return "not a valid URI";
+ }
+ return null;
+ }
+
+ /**
+ * Sign the header and payload
+ */
+ private String encodedSignature(final String signingInput, final Algorithm algorithm) throws NoSuchAlgorithmException, InvalidKeyException,
+ NoSuchProviderException, SignatureException, JWTAlgorithmException {
+ Validate.notNull(signingInput);
+ Validate.notNull(algorithm);
+ switch (algorithm) {
+ case HS256:
+ case HS384:
+ case HS512:
+ return base64UrlEncode(signHmac(algorithm, signingInput, secret));
+ case RS256:
+ case RS384:
+ case RS512:
+ return base64UrlEncode(signRs(algorithm, signingInput, privateKey));
+ default:
+ throw new JWTAlgorithmException("Unsupported signing method");
+ }
+ }
+
+ /**
+ * Safe URL encode a byte array to a String
+ */
+ private String base64UrlEncode(final byte[] str) {
+ Validate.notNull(str);
+ return new String(Base64.encodeBase64URLSafe(str));
+ }
+
+ /**
+ * Sign an input string using HMAC and return the encrypted bytes
+ */
+ private static byte[] signHmac(final Algorithm algorithm, final String msg, final byte[] secret) throws NoSuchAlgorithmException, InvalidKeyException {
+ Validate.notNull(algorithm);
+ Validate.notNull(msg);
+ Validate.notNull(secret);
+ final Mac mac = Mac.getInstance(algorithm.getValue());
+ mac.init(new SecretKeySpec(secret, algorithm.getValue()));
+ return mac.doFinal(msg.getBytes());
+ }
+
+ /**
+ * Sign an input string using RSA and return the encrypted bytes
+ */
+ private static byte[] signRs(final Algorithm algorithm, final String msg, final PrivateKey privateKey) throws NoSuchProviderException,
+ NoSuchAlgorithmException, InvalidKeyException, SignatureException {
+ Validate.notNull(algorithm);
+ Validate.notNull(msg);
+ Validate.notNull(privateKey);
+ final byte[] messageBytes = msg.getBytes();
+ final Signature signature = Signature.getInstance(algorithm.getValue(), "BC");
+ signature.initSign(privateKey);
+ signature.update(messageBytes);
+ return signature.sign();
+ }
+
+ private String join(final List input, final String separator) {
+ Validate.notNull(input);
+ Validate.notNull(separator);
+ return StringUtils.join(input.iterator(), separator);
+ }
+
+ /**
+ * An option object for JWT signing operation. Allow choosing the algorithm, and/or specifying
+ * claims to be automatically set.
+ */
+ public static class Options {
+
+ private Algorithm algorithm;
+ private Integer expirySeconds;
+ private Integer notValidBeforeLeeway;
+ private boolean issuedAt;
+ private boolean jwtId;
+
+ public Algorithm getAlgorithm() {
+ return algorithm;
+ }
+
+ /**
+ * Algorithm to sign JWT with.
+ */
+ public Options setAlgorithm(final Algorithm algorithm) {
+ this.algorithm = algorithm;
+ return this;
+ }
+
+
+ public Integer getExpirySeconds() {
+ return expirySeconds;
+ }
+
+ /**
+ * Set JWT claim "exp" to current timestamp plus this value.
+ * Overrides content of claims
in sign()
.
+ */
+ public Options setExpirySeconds(final Integer expirySeconds) {
+ this.expirySeconds = expirySeconds;
+ return this;
+ }
+
+ public Integer getNotValidBeforeLeeway() {
+ return notValidBeforeLeeway;
+ }
+
+ /**
+ * Set JWT claim "nbf" to current timestamp minus this value.
+ * Overrides content of claims
in sign()
.
+ */
+ public Options setNotValidBeforeLeeway(final Integer notValidBeforeLeeway) {
+ this.notValidBeforeLeeway = notValidBeforeLeeway;
+ return this;
+ }
+
+ public boolean isIssuedAt() {
+ return issuedAt;
+ }
+
+ /**
+ * Set JWT claim "iat" to current timestamp. Defaults to false.
+ * Overrides content of claims
in sign()
.
+ */
+ public Options setIssuedAt(final boolean issuedAt) {
+ this.issuedAt = issuedAt;
+ return this;
+ }
+
+ public boolean isJwtId() {
+ return jwtId;
+ }
+
+ /**
+ * Set JWT claim "jti" to a pseudo random unique value (type 4 UUID). Defaults to false.
+ * Overrides content of claims
in sign()
.
+ */
+ public Options setJwtId(final boolean jwtId) {
+ this.jwtId = jwtId;
+ return this;
+ }
+
+ }
+
+}
diff --git a/src/main/java/com/auth0/jwt/JWTVerifier.java b/src/main/java/com/auth0/jwt/JWTVerifier.java
new file mode 100644
index 00000000..0e0199fa
--- /dev/null
+++ b/src/main/java/com/auth0/jwt/JWTVerifier.java
@@ -0,0 +1,239 @@
+package com.auth0.jwt;
+
+import com.fasterxml.jackson.databind.JsonNode;
+import com.fasterxml.jackson.databind.ObjectMapper;
+import org.apache.commons.codec.binary.Base64;
+import org.apache.commons.lang3.Validate;
+import org.bouncycastle.jce.provider.BouncyCastleProvider;
+
+import javax.crypto.Mac;
+import javax.crypto.spec.SecretKeySpec;
+import java.io.IOException;
+import java.nio.charset.Charset;
+import java.security.*;
+import java.util.Map;
+
+/**
+ * Handles JWT Verification Operations
+ *
+ * Validates claims and signature
+ *
+ * See associated library test cases for clear examples on usage
+ *
+ */
+public class JWTVerifier {
+
+ static {
+ if (Security.getProvider(BouncyCastleProvider.PROVIDER_NAME) == null) {
+ Security.addProvider(new BouncyCastleProvider());
+ }
+ }
+
+ private byte[] secret;
+ private PublicKey publicKey;
+ private final String audience;
+ private final String issuer;
+ private final Base64 decoder = new Base64(true);
+
+ private final ObjectMapper mapper;
+
+
+ public JWTVerifier(final String secret, final String audience, final String issuer) {
+ this(secret.getBytes(Charset.forName("UTF-8")), audience, issuer);
+ }
+
+ public JWTVerifier(final String secret, final String audience) {
+ this(secret, audience, null);
+ }
+
+ public JWTVerifier(final String secret) {
+ this(secret, null, null);
+ }
+
+ public JWTVerifier(final byte[] secret, final String audience) {
+ this(secret, audience, null);
+ }
+
+ public JWTVerifier(final byte[] secret) {
+ this(secret, null, null);
+ }
+
+ public JWTVerifier(final byte[] secret, final String audience, final String issuer) {
+ if (secret == null || secret.length == 0) {
+ throw new IllegalArgumentException("Secret cannot be null or empty");
+ }
+ mapper = new ObjectMapper();
+ this.secret = secret;
+ this.audience = audience;
+ this.issuer = issuer;
+ }
+
+ public JWTVerifier(final PublicKey publicKey, final String audience, final String issuer) {
+ Validate.notNull(publicKey);
+ mapper = new ObjectMapper();
+ this.publicKey = publicKey;
+ this.audience = audience;
+ this.issuer = issuer;
+ }
+
+ public JWTVerifier(final PublicKey publicKey, final String audience) {
+ this(publicKey, audience, null);
+ }
+
+ public JWTVerifier(final PublicKey publicKey) {
+ this(publicKey, null, null);
+ }
+
+
+ /**
+ * Performs JWT validation
+ *
+ * @param token token to verify
+ * @throws SignatureException when signature is invalid
+ * @throws JWTVerifyException when expiration, issuer or audience are invalid
+ * @throws JWTAlgorithmException when the algorithm is missing or unsupported
+ * @throws IllegalStateException when token's structure is invalid or secret / public key does not match algorithm of token
+ */
+ @SuppressWarnings("WeakerAccess")
+ public Map verify(final String token) throws NoSuchAlgorithmException, InvalidKeyException, IllegalStateException,
+ IOException, SignatureException, JWTVerifyException {
+ if (token == null || "".equals(token)) {
+ throw new IllegalStateException("token not set");
+ }
+ final String[] pieces = token.split("\\.");
+ if (pieces.length != 3) {
+ throw new IllegalStateException("Wrong number of segments: " + pieces.length);
+ }
+ final JsonNode jwtHeader = decodeAndParse(pieces[0]);
+ final Algorithm algorithm = getAlgorithm(jwtHeader);
+ final JsonNode jwtPayload = decodeAndParse(pieces[1]);
+ verifySignature(pieces, algorithm);
+ verifyExpiration(jwtPayload);
+ verifyIssuer(jwtPayload);
+ verifyAudience(jwtPayload);
+ return mapper.treeToValue(jwtPayload, Map.class);
+ }
+
+ void verifySignature(final String[] pieces, final Algorithm algorithm) throws NoSuchAlgorithmException,
+ InvalidKeyException, SignatureException, JWTAlgorithmException, IllegalStateException {
+ Validate.notNull(pieces);
+ Validate.notNull(algorithm);
+ if (pieces.length != 3) {
+ throw new IllegalStateException("Wrong number of segments: " + pieces.length);
+ }
+ switch (algorithm) {
+ case HS256:
+ case HS384:
+ case HS512:
+ verifyHmac(algorithm, pieces, secret);
+ return;
+ case RS256:
+ case RS384:
+ case RS512:
+ verifyRs(algorithm, pieces, publicKey);
+ return;
+ default:
+ throw new JWTAlgorithmException("Unsupported signing method");
+ }
+ }
+
+ private void verifyHmac(final Algorithm algorithm, final String[] pieces, final byte[] secret) throws SignatureException, NoSuchAlgorithmException, InvalidKeyException {
+ if (secret == null || secret.length == 0) {
+ throw new IllegalStateException("Secret cannot be null or empty when using algorithm: " + algorithm.getValue());
+ }
+ final Mac hmac = Mac.getInstance(algorithm.getValue());
+ hmac.init(new SecretKeySpec(secret, algorithm.getValue()));
+ final byte[] sig = hmac.doFinal((pieces[0] + "." + pieces[1]).getBytes());
+ if (!MessageDigest.isEqual(sig, decoder.decode(pieces[2]))) {
+ throw new SignatureException("signature verification failed");
+ }
+ }
+
+ private void verifyRs(final Algorithm algorithm, final String[] pieces, final PublicKey publicKey) throws SignatureException, NoSuchAlgorithmException, InvalidKeyException, JWTAlgorithmException {
+ if (publicKey == null) {
+ throw new IllegalStateException("PublicKey cannot be null when using algorithm: " + algorithm.getValue());
+ }
+ final byte[] decodedSignatureBytes = new Base64(true).decode(pieces[2]);
+ final byte[] headerPayloadBytes = (pieces[0] + "." + pieces[1]).getBytes();
+ final boolean verified = verifySignatureWithPublicKey(this.publicKey, headerPayloadBytes, decodedSignatureBytes, algorithm);
+ if (!verified) {
+ throw new SignatureException("signature verification failed");
+ }
+ }
+
+ private boolean verifySignatureWithPublicKey(final PublicKey publicKey, final byte[] messageBytes, final byte[] signatureBytes, final Algorithm algorithm) throws InvalidKeyException, SignatureException, NoSuchAlgorithmException, JWTAlgorithmException {
+ Validate.notNull(publicKey);
+ Validate.notNull(messageBytes);
+ Validate.notNull(signatureBytes);
+ Validate.notNull(algorithm);
+ try {
+ final Signature signature = Signature.getInstance(algorithm.getValue(), "BC");
+ signature.initVerify(publicKey);
+ signature.update(messageBytes);
+ return signature.verify(signatureBytes);
+ } catch (NoSuchProviderException e) {
+ throw new JWTAlgorithmException(e.getMessage(), e.getCause());
+ }
+ }
+
+ void verifyExpiration(final JsonNode jwtClaims) throws JWTExpiredException {
+ Validate.notNull(jwtClaims);
+ final long expiration = jwtClaims.has("exp") ? jwtClaims.get("exp").asLong(0) : 0;
+ if (expiration != 0 && System.currentTimeMillis() / 1000L >= expiration) {
+ throw new JWTExpiredException("jwt expired", expiration);
+ }
+ }
+
+ void verifyIssuer(final JsonNode jwtClaims) throws JWTIssuerException {
+ Validate.notNull(jwtClaims);
+
+ if (this.issuer == null ) {
+ return;
+ }
+
+ final String issuerFromToken = jwtClaims.has("iss") ? jwtClaims.get("iss").asText() : null;
+
+ if (issuerFromToken == null || !issuer.equals(issuerFromToken)) {
+ throw new JWTIssuerException("jwt issuer invalid", issuerFromToken);
+ }
+ }
+
+ void verifyAudience(final JsonNode jwtClaims) throws JWTAudienceException {
+ Validate.notNull(jwtClaims);
+ if (audience == null) {
+ return;
+ }
+ final JsonNode audNode = jwtClaims.get("aud");
+ if (audNode == null) {
+ throw new JWTAudienceException("jwt audience invalid", null);
+ }
+ if (audNode.isArray()) {
+ for (final JsonNode jsonNode : audNode) {
+ if (audience.equals(jsonNode.textValue())) {
+ return;
+ }
+ }
+ } else if (audNode.isTextual()) {
+ if (audience.equals(audNode.textValue())) {
+ return;
+ }
+ }
+ throw new JWTAudienceException("jwt audience invalid", audNode);
+ }
+
+ Algorithm getAlgorithm(final JsonNode jwtHeader) throws JWTAlgorithmException {
+ Validate.notNull(jwtHeader);
+ final String algorithmName = jwtHeader.has("alg") ? jwtHeader.get("alg").asText() : null;
+ if (jwtHeader.get("alg") == null) {
+ throw new IllegalStateException("algorithm not set");
+ }
+ return Algorithm.findByName(algorithmName);
+ }
+
+ JsonNode decodeAndParse(final String b64String) throws IOException {
+ Validate.notNull(b64String);
+ final String jsonString = new String(decoder.decode(b64String), "UTF-8");
+ return mapper.readValue(jsonString, JsonNode.class);
+ }
+
+}
diff --git a/src/main/java/com/auth0/jwt/JWTVerifyException.java b/src/main/java/com/auth0/jwt/JWTVerifyException.java
new file mode 100644
index 00000000..9e18d6b8
--- /dev/null
+++ b/src/main/java/com/auth0/jwt/JWTVerifyException.java
@@ -0,0 +1,18 @@
+package com.auth0.jwt;
+
+/**
+ * Represents General Exception related to Verification
+ */
+public class JWTVerifyException extends Exception {
+
+ public JWTVerifyException() {}
+
+ public JWTVerifyException(final String message, final Throwable cause) {
+ super(message, cause);
+ }
+
+ public JWTVerifyException(final String message) {
+ super(message);
+ }
+
+}
diff --git a/src/main/java/com/auth0/jwt/pem/PemFileReader.java b/src/main/java/com/auth0/jwt/pem/PemFileReader.java
new file mode 100644
index 00000000..60eb9f33
--- /dev/null
+++ b/src/main/java/com/auth0/jwt/pem/PemFileReader.java
@@ -0,0 +1,38 @@
+package com.auth0.jwt.pem;
+
+import org.bouncycastle.util.io.pem.PemObject;
+import org.bouncycastle.util.io.pem.PemReader;
+import org.bouncycastle.util.io.pem.PemWriter;
+
+import java.io.*;
+
+/**
+ * Can read PEM from disk - depends on BouncyCastle PemReader
+ */
+class PemFileReader {
+
+ private PemObject pemObject;
+
+ public PemFileReader(final String filename) throws IOException {
+ final PemReader pemReader = new PemReader(new InputStreamReader(new FileInputStream(filename)));
+ try {
+ this.pemObject = pemReader.readPemObject();
+ } finally {
+ pemReader.close();
+ }
+ }
+
+ public void write(final String filename) throws IOException {
+ final PemWriter pemWriter = new PemWriter(new OutputStreamWriter(new FileOutputStream(filename)));
+ try {
+ pemWriter.writeObject(this.pemObject);
+ } finally {
+ pemWriter.close();
+ }
+ }
+
+ public PemObject getPemObject() {
+ return pemObject;
+ }
+
+}
diff --git a/src/main/java/com/auth0/jwt/pem/PemFileWriter.java b/src/main/java/com/auth0/jwt/pem/PemFileWriter.java
new file mode 100644
index 00000000..8b23df10
--- /dev/null
+++ b/src/main/java/com/auth0/jwt/pem/PemFileWriter.java
@@ -0,0 +1,31 @@
+package com.auth0.jwt.pem;
+
+import org.bouncycastle.util.io.pem.PemObject;
+import org.bouncycastle.util.io.pem.PemWriter;
+
+import java.io.FileOutputStream;
+import java.io.IOException;
+import java.io.OutputStreamWriter;
+import java.security.Key;
+
+/**
+ * Can write PEM to disk - depends on BouncyCastle PemWriter
+ */
+class PemFileWriter {
+
+ private PemObject pemObject;
+
+ public PemFileWriter(final Key key, final String description) {
+ this.pemObject = new PemObject(description, key.getEncoded());
+ }
+
+ public void write(final String filename) throws IOException {
+ final PemWriter pemWriter = new PemWriter(new OutputStreamWriter(new FileOutputStream(filename)));
+ try {
+ pemWriter.writeObject(this.pemObject);
+ } finally {
+ pemWriter.close();
+ }
+ }
+
+}
diff --git a/src/main/java/com/auth0/jwt/pem/PemReader.java b/src/main/java/com/auth0/jwt/pem/PemReader.java
new file mode 100644
index 00000000..90ca0486
--- /dev/null
+++ b/src/main/java/com/auth0/jwt/pem/PemReader.java
@@ -0,0 +1,68 @@
+package com.auth0.jwt.pem;
+
+import org.apache.commons.lang3.Validate;
+import org.bouncycastle.jce.provider.BouncyCastleProvider;
+
+import java.io.File;
+import java.io.IOException;
+import java.nio.file.Files;
+import java.security.*;
+import java.security.cert.X509Certificate;
+import java.security.spec.InvalidKeySpecException;
+import java.security.spec.PKCS8EncodedKeySpec;
+import java.security.spec.X509EncodedKeySpec;
+
+/**
+ * Read operations for PEM files
+ */
+public class PemReader {
+
+ static {
+ if (Security.getProvider(BouncyCastleProvider.PROVIDER_NAME) == null) {
+ Security.addProvider(new BouncyCastleProvider());
+ }
+ }
+
+ public static PrivateKey readPrivateKey(final String filePath) throws NoSuchProviderException, NoSuchAlgorithmException, IOException, InvalidKeySpecException {
+ Validate.notNull(filePath);
+ final KeyFactory factory = KeyFactory.getInstance("RSA", "BC");
+ final PrivateKey privateKey = readPrivateKeyFromFile(factory, filePath);
+ return privateKey;
+ }
+
+ public static PublicKey readPublicKey(final String filePath) throws NoSuchProviderException, NoSuchAlgorithmException, IOException, InvalidKeySpecException {
+ Validate.notNull(filePath);
+ final KeyFactory factory = KeyFactory.getInstance("RSA", "BC");
+ final PublicKey publicKey = readPublicKeyFromFile(factory, filePath);
+ return publicKey;
+ }
+
+ private static PrivateKey readPrivateKeyFromFile(final KeyFactory factory, final String filename) throws InvalidKeySpecException, IOException {
+ Validate.notNull(factory);
+ Validate.notNull(filename);
+ final PemFileReader pemFileReader = new PemFileReader(filename);
+ final byte[] content = pemFileReader.getPemObject().getContent();
+ final PKCS8EncodedKeySpec privKeySpec = new PKCS8EncodedKeySpec(content);
+ return factory.generatePrivate(privKeySpec);
+ }
+
+ private static PublicKey readPublicKeyFromFile(final KeyFactory factory, final String filename) throws InvalidKeySpecException, IOException {
+ Validate.notNull(factory);
+ Validate.notNull(filename);
+ final File file = new File(filename);
+ final byte[] data = Files.readAllBytes(file.toPath());
+ final X509Certificate cert = X509CertUtils.parse(new String(data));
+ if (cert != null) {
+ java.security.PublicKey publicKey = cert.getPublicKey();
+ return publicKey;
+ } else {
+ final PemFileReader pemFileReader = new PemFileReader(filename);
+ final byte[] content = pemFileReader.getPemObject().getContent();
+ final X509EncodedKeySpec pubKeySpec = new X509EncodedKeySpec(content);
+ return factory.generatePublic(pubKeySpec);
+ }
+
+
+ }
+
+}
diff --git a/src/main/java/com/auth0/jwt/pem/PemWriter.java b/src/main/java/com/auth0/jwt/pem/PemWriter.java
new file mode 100644
index 00000000..55856ce4
--- /dev/null
+++ b/src/main/java/com/auth0/jwt/pem/PemWriter.java
@@ -0,0 +1,34 @@
+package com.auth0.jwt.pem;
+
+import org.apache.commons.lang3.Validate;
+
+import java.io.IOException;
+import java.security.Key;
+import java.security.interfaces.RSAPrivateKey;
+import java.security.interfaces.RSAPublicKey;
+
+/**
+ * Write operations for PEM files
+ */
+public class PemWriter {
+
+ public static void writePrivateKey(final RSAPrivateKey privateKey, final String description, final String filename) throws IOException {
+ Validate.notNull(privateKey);
+ Validate.notNull(filename);
+ writePemFile(privateKey, description, filename);
+ }
+
+ public static void writePublicKey(final RSAPublicKey publicKey, final String description, final String filename) throws IOException {
+ Validate.notNull(publicKey);
+ Validate.notNull(filename);
+ writePemFile(publicKey, description, filename);
+ }
+
+ public static void writePemFile(final Key key, final String description, final String filename) throws IOException {
+ Validate.notNull(key);
+ Validate.notNull(filename);
+ final PemFileWriter pemFileWriter = new PemFileWriter(key, description);
+ pemFileWriter.write(filename);
+ }
+
+}
diff --git a/src/main/java/com/auth0/jwt/pem/X509CertUtils.java b/src/main/java/com/auth0/jwt/pem/X509CertUtils.java
new file mode 100644
index 00000000..ef65e476
--- /dev/null
+++ b/src/main/java/com/auth0/jwt/pem/X509CertUtils.java
@@ -0,0 +1,61 @@
+package com.auth0.jwt.pem;
+
+import org.apache.commons.codec.binary.Base64;
+
+import java.io.ByteArrayInputStream;
+import java.security.cert.Certificate;
+import java.security.cert.CertificateException;
+import java.security.cert.CertificateFactory;
+import java.security.cert.X509Certificate;
+
+
+/**
+ * X.509 certificate utilities.
+ */
+public class X509CertUtils {
+
+ private static final String PEM_BEGIN_MARKER = "-----BEGIN CERTIFICATE-----";
+ private static final String PEM_END_MARKER = "-----END CERTIFICATE-----";
+
+ /**
+ * Parses a DER-encoded X.509 certificate.
+ */
+ public static X509Certificate parse(final byte[] derEncodedCert) {
+ if (derEncodedCert == null || derEncodedCert.length == 0) {
+ return null;
+ }
+ try {
+ final CertificateFactory cf = CertificateFactory.getInstance("X.509");
+ final Certificate cert = cf.generateCertificate(new ByteArrayInputStream(derEncodedCert));
+ if (!(cert instanceof X509Certificate)) {
+ return null;
+ }
+ return (X509Certificate) cert;
+ } catch (CertificateException e) {
+ return null;
+ }
+ }
+
+ /**
+ * Parses a PEM-encoded X.509 certificate.
+ */
+ public static X509Certificate parse(final String pemEncodedCert) {
+ if (pemEncodedCert == null || pemEncodedCert.isEmpty()) {
+ return null;
+ }
+ final int markerStart = pemEncodedCert.indexOf(PEM_BEGIN_MARKER);
+ if (markerStart < 0) {
+ return null;
+ }
+ String buf = pemEncodedCert.substring(markerStart + PEM_BEGIN_MARKER.length());
+ final int markerEnd = buf.indexOf(PEM_END_MARKER);
+ if (markerEnd < 0) {
+ return null;
+ }
+ buf = buf.substring(0, markerEnd);
+ buf = buf.replaceAll("\\s", "");
+ return parse(new Base64(true).decodeBase64(buf));
+ }
+
+}
+
diff --git a/src/test/java/com/auth0/jwt/JWTRoundTripRsa256Test.java b/src/test/java/com/auth0/jwt/JWTRoundTripRsa256Test.java
new file mode 100644
index 00000000..722de2a4
--- /dev/null
+++ b/src/test/java/com/auth0/jwt/JWTRoundTripRsa256Test.java
@@ -0,0 +1,100 @@
+package com.auth0.jwt;
+
+import org.bouncycastle.jce.provider.BouncyCastleProvider;
+import org.junit.Before;
+import org.junit.Test;
+
+import java.io.File;
+import java.io.IOException;
+import java.security.*;
+import java.security.interfaces.RSAPrivateKey;
+import java.security.interfaces.RSAPublicKey;
+import java.security.spec.InvalidKeySpecException;
+import java.util.*;
+
+import static com.auth0.jwt.pem.PemReader.readPrivateKey;
+import static com.auth0.jwt.pem.PemReader.readPublicKey;
+import static com.auth0.jwt.pem.PemWriter.writePrivateKey;
+import static com.auth0.jwt.pem.PemWriter.writePublicKey;
+import static junit.framework.TestCase.*;
+
+/**
+ * Test that generates KeyPair - writes PEM files (private and public) to disk,
+ * then reads in those PEM files (private and public) and uses them to Sign a JWT
+ * and subsequently verify its correctness - hence "RoundTrip"
+ */
+public class JWTRoundTripRsa256Test {
+
+ private static final int KEY_SIZE = 2048;
+
+ static {
+ if (Security.getProvider(BouncyCastleProvider.PROVIDER_NAME) == null) {
+ Security.addProvider(new BouncyCastleProvider());
+ }
+ }
+
+ private File privateKeyPem;
+ private File publicKeyPem;
+
+ @Before
+ public void createPemFiles() throws NoSuchAlgorithmException, NoSuchProviderException, IOException {
+ // create key pair
+ final KeyPairGenerator generator = KeyPairGenerator.getInstance("RSA", "BC");
+ generator.initialize(KEY_SIZE);
+ final KeyPair keyPair = generator.generateKeyPair();
+ // write private key
+ final RSAPrivateKey privateKey = (RSAPrivateKey) keyPair.getPrivate();
+ privateKeyPem = File.createTempFile("id_rsa", "");
+ writePrivateKey(privateKey, "RSA PRIVATE KEY", privateKeyPem.getAbsolutePath());
+ // write public key
+ publicKeyPem = File.createTempFile("id_rsa", ".pub");
+ final RSAPublicKey publicKey = (RSAPublicKey) keyPair.getPublic();
+ writePublicKey(publicKey, "RSA PUBLIC KEY", publicKeyPem.getAbsolutePath());
+ }
+
+ @Test
+ public void roundTripCreatingSignedTokenAndVerifyingUsingRs256Algo() throws NoSuchProviderException, NoSuchAlgorithmException, IOException, InvalidKeySpecException, SignatureException, InvalidKeyException, JWTAlgorithmException, JWTVerifyException {
+ // read pem files
+ final PrivateKey privateKey = readPrivateKey(privateKeyPem.getAbsolutePath());
+ assertNotNull(privateKey);
+ final PublicKey publicKey = readPublicKey(publicKeyPem.getAbsolutePath());
+ assertNotNull(publicKey);
+ // create and sign a JWT
+ final String issuer = "https://arcseldon.auth0.com/";
+ final String clientId = "xGXMKfEdcOcacZEU7Uq1mgWOtpUxBlL4"; // this is the audience
+ final String name = "arcseldon";
+ final String email = "arcseldon+test@gmail.com";
+ final String subject = "auth0|576be978a93121cc48c7487d";
+ final List