{"record":{"id":"653bd10d56a50219","repo":"spring-projects/spring-security","slug":"unauthenticated-or-no-response-token","errorCode":null,"errorMessage":"Unauthenticated or no response token","messagePattern":"Unauthenticated or no response token","errorType":"exception","errorClass":"IllegalStateException","httpStatus":null,"severity":"error","filePath":"kerberos/kerberos-core/src/main/java/org/springframework/security/kerberos/authentication/KerberosServiceRequestToken.java","lineNumber":173,"sourceCode":"\tpublic @Nullable KerberosTicketValidation getTicketValidation() {\n\t\treturn this.ticketValidation;\n\t}\n\n\t/**\n\t * Determines whether an authenticated token has a response token.\n\t * @return whether a response token is available\n\t */\n\tpublic boolean hasResponseToken() {\n\t\treturn this.ticketValidation != null && this.ticketValidation.responseToken() != null;\n\t}\n\n\t/**\n\t * Gets the (Base64) encoded response token assuming one is available.\n\t * @return encoded response token\n\t */\n\tpublic String getEncodedResponseToken() {\n\t\tif (!hasResponseToken()) {\n\t\t\tthrow new IllegalStateException(\"Unauthenticated or no response token\");\n\t\t}\n\t\tif (this.ticketValidation == null) {\n\t\t\tthrow new IllegalStateException(\"Ticket validation is not available\");\n\t\t}\n\t\treturn Base64.getEncoder().encodeToString(this.ticketValidation.responseToken());\n\t}\n\n\t/**\n\t * Unwraps an encrypted message using the gss context.\n\t * @param data the data\n\t * @param offset data offset\n\t * @param length data length\n\t * @return the decrypted message\n\t * @throws PrivilegedActionException if jaas throws and error\n\t */\n\tpublic byte[] decrypt(final byte[] data, final int offset, final int length) throws PrivilegedActionException {\n\t\tKerberosTicketValidation validation = getTicketValidation();\n\t\tif (validation == null) {","sourceCodeStart":155,"sourceCodeEnd":191,"githubUrl":"https://github.com/spring-projects/spring-security/blob/96852e8860138a482cb13d1479573f24ff6443c6/kerberos/kerberos-core/src/main/java/org/springframework/security/kerberos/authentication/KerberosServiceRequestToken.java#L155-L191","documentation":"getEncodedResponseToken returns the Base64-encoded mutual-authentication response token from the validated ticket. It throws IllegalStateException if the token has no response token (authentication didn't produce one) or ticket validation data is missing — i.e. it was called on a token that was never successfully authenticated.","triggerScenarios":"Calling getEncodedResponseToken() on a KerberosServiceRequestToken before successful authentication, or after validation that produced a null responseToken (e.g. SunJaasKerberosTicketValidator without mutual authentication enabled).","commonSituations":"Custom success handlers (onAuthenticationSuccess) assuming a response token always exists; using a ticket validator that doesn't return a response token so the SPNEGO 'continue required' handshake can't complete (e.g. with browsers expecting mutual auth).","solutions":["Guard with token.hasResponseToken() before calling getEncodedResponseToken().","Enable mutual authentication in the ticket validator so a response token is produced (setVerbose/mutualAuthentication settings depending on validator).","Verify the token passed to the success handler is the authenticated KerberosServiceRequestToken with ticketValidation set.","If mutual auth is not needed, skip response-token emission instead of calling this method."],"exampleFix":"// before\nString token = kerberosToken.getEncodedResponseToken();\nresponse.addHeader(\"WWW-Authenticate\", \"Negotiate \" + token);\n// after\nif (kerberosToken.hasResponseToken()) {\n  response.addHeader(\"WWW-Authenticate\",\n      \"Negotiate \" + kerberosToken.getEncodedResponseToken());\n}","handlingStrategy":"validation","validationCode":"if (kerberosToken.hasResponseToken()) {\n  String b64 = kerberosToken.getEncodedResponseToken();\n} // else skip WWW-Authenticate: Negotiate response","typeGuard":null,"tryCatchPattern":"try {\n  String encoded = kerberosToken.getEncodedResponseToken();\n  response.setHeader(\"WWW-Authenticate\", \"Negotiate \" + encoded);\n} catch (IllegalStateException e) {\n  LOG.debug(\"No mutual-auth response token available; skipping\", e);\n}","preventionTips":["Always call hasResponseToken() before getEncodedResponseToken().","Enable mutual authentication in the ticket validator for SPNEGO handshakes.","Only handle KerberosServiceRequestTokens that completed authentication."],"tags":["kerberos","spnego","invalid-state"],"backgroundTag":"invalid-state-transition","analyzedSha":"96852e8860138a482cb13d1479573f24ff6443c6","analyzedAt":"2026-09-10T23:25:23.477Z","contentChangedAt":"2026-09-10T23:25:23.477Z","schemaVersion":2},"datasetVersion":"2026-09-14T16:17:12.679Z"}