I have a Tomcat application running on a RHEL9 host that is trying to connect to a Windows Server running MSSQL using integrated authentication via a JDBC connection on JDK 8. I've thoroughly reviewed the configuration, but I can't determine why I'm consistently encountering this error when the application starts.
ERROR - failed to connect to DB, reason is probably not the database absence. cause: Cannot login with Kerberos principal not_used, check your credentials. Kerberos Login failed: Integrated authentication failed. ClientConnectionId
I have supplied a Jaas Config to the JVM with these settings via setenv.sh export CATALINA_OPTS="$CATALINA_OPTS -Djava.security.auth.login.config=/opt/tomcat/bin/jaas.conf -Djava.security.krb5.conf=/etc/krb5.conf -Djava.security.debug=all"
My JaaS config looks like this:
SqlJaasConf {
com.sun.security.auth.module.Krb5LoginModule required
useKeyTab=true
keyTab="/etc/krb5.keytab"
principal="[email protected]"
doNotPrompt=true
storeKey=true
useTicketCache=false;
};
My krb5.conf on my RHEL server file looks like this:
[logging]
default = FILE:/var/log/krb5libs.log
kdc = FILE:/var/log/krb5kdc.log
admin_server = FILE:/var/log/kadmind.log
[libdefaults]
default_realm = TEST.CORP
dns_lookup_realm = false
dns_lookup_kdc = false
ticket_lifetime = 30d
renew_lifetime = 30d
rdns = false
forwardable = true
udp_preference_limit = 0
rdns = false
default_tkt_enctypes = aes256-cts-hmac-sha1-96 aes128-cts-hmac-sha1-96 rc4-hmac
default_tgs_enctypes = aes256-cts-hmac-sha1-96 aes128-cts-hmac-sha1-96 rc4-hmac
permitted_enctypes = aes256-cts-hmac-sha1-96 aes128-cts-hmac-sha1-96 rc4-hmac
[realms]
TEST.CORP = {
kdc = 172.31.82.203
admin_server = 172.31.82.203
}
[domain_realm]
.test.corp = TEST.CORP
test.corp = TEST.CORP
I can resolve the domains in each host and I have firewall connectivity between them. Also checked that I have a kerberos ticket.
Ticket cache: KCM:0
Default principal: [email protected]
Valid starting Expires Service principal
09/02/2024 21:54:56 10/02/2024 21:54:56 krbtgt/[email protected]
renew until 10/02/2024 21:54:56
Also confirmed I have a Service Principle on the Windows AD box.
C:\Users\Administrator>setspn -L DBUser
Registered ServicePrincipalNames for CN=DBUser,CN=Users,DC=test,DC=corp:
MSSQLSvc/ip-172-31-18-241.ec2.internal:1433
My connection string looks like this:
jdbc:sqlserver://172.31.23.171:1433;databaseName=master;integratedSecurity=true;authenticationScheme=JavaKerberos;ServerSpn=MSSQLSvc/ip-172-31-18-241.ec2.internal:1433;jaasLoginConfigName=SqlJaasConf;realm=TEST.CORP
Few things I have done:
sqlcmd -S 172.31.23.171 -d master -G -C
and can login and run SQL Commands.!connect jdbc:sqlserver://172.31.23.171:1433;databaseName=master;integratedSecurity=true;authenticationScheme=JavaKerberos;ServerSpn=MSSQLSvc/ip-172-31-18-241.ec2.internal:1433 [email protected] ""
If I remove the creds, it fails.
What is going on here? How do I debug?
SPN value MSSQLSvc/ip-172-31-18-241.ec2.internal:1433 is not compliant with your infrastructure, you try to access TEST.CORP domain, the SPN you want to access should have TEST.CORP FQDN extension such as MSSQLSvc/SQL1.TEST.CORP:1433 where SQL1 should be the hostname.
The ticket you have seems to be the Ticket Granting Ticket (TGT). Your program now should request a TGS (Ticket Granting Service) ticket using the TGT, but since the SPN is problematic, it can not.
Generally Kerberos works over DNS, so it is better that your code should connect to a DNS FQDN instead of an IP address.
You can check the Windows side of the connection on the Security event Logs of the domain controller to which your code tries to get a TGS ticket. You may also enable Kerberos Logging via ref: https://learn.microsoft.com/en-us/troubleshoot/windows-server/active-directory/enable-kerberos-event-logging