Connecting to Kerberos-secured database instances
In enterprises, it is common to use Kerberos for authentication. Typically, Kerberos authentication is enabled as part of ActiveDirectory authentication in Windows or MIT Kerberos and Heimdal in Linux and MacOS. This guide explains how to configure Synthesized for connecting to a Kerberos-secured database instance.
Prerequisites
-
Basic understanding of Kerberos authentication. Refer to the official documentation for more information.
-
Network access from the Worker instance to the Kerberos Key Distribution Center (KDC) server. In Active Directory-based setups, this is typically an Active Directory Domain Controller server.
-
Known Kerberos configuration: realm, KDC server, and the database client principal credentials for the database instance.
Overview
Kerberos authentication differs from direct username/password authentication in that the Java process must obtain a ticket from a Key Distribution Center (KDC) server. In most setups, the KDC server address must be known and the server must be reachable from the Java process.
To configure Kerberos authentication in Worker, you will need to:
-
create the Kerberos configuration files for Java
-
pass the configuration files to the Java process that connects to the database instance
-
adjust the JDBC connection string to activate Kerberos authentication
Below, these steps are explained in more detail. For an even greater level of detail, refer to the official SQL Server JDBC + Kerberos guide.
| Once JAAS is correctly configured, a data source can be created via the UI as usual. The username must match the principal username, and the password may contain any symbols. |
Creating configuration files
Configuring Kerberos authentication inside the Worker container comprises the following parts, one configuration file per part:
-
the Kerberos client underpinning the login module.
-
the Java Kerberos login module.
Both are plain text files that can be created in any editor of your choice.
Kerberos configuration file
The Kerberos client in Java is configured using the krb5.conf file. The following is the minimal configuration required to connect to a Kerberos-secured SQL Server instance:
[libdefaults]
default_realm = DEV.LOCAL
dns_lookup_kdc = false
dns_lookup_realm = false
[realms]
DEV.LOCAL = {
kdc = win.dev.local
}
[domain_realm]
.dev.local = DEV.LOCAL
dev.local = DEV.LOCAL
In the example above, both the database client principal and the database instance are assumed to be in the DEV.LOCAL realm.
The kdc setting specifies the KDC server address, which is the name win.dev.local.
Please note that Kerberos heavily relies on DNS names, so the KDC address is a DNS name rather than IP address.
|
Depending on the environment, the |
Configuring JAAS to work with Kerberos
The Java Authentication and Authorization Service (JAAS) requires configuring a built-in Kerberos login module. Below we provide JAAS configuration examples. Please refer to JAAS file options reference for more information.
The following is an example of a minimal JAAS configuration file:
-
SQL Server
-
PostgreSQL
SQLJDBCDriver {
com.sun.security.auth.module.Krb5LoginModule required
useTicketCache=false
doNotPrompt=false;
};
pgjdbc {
com.sun.security.auth.module.Krb5LoginModule required
useTicketCache=false
doNotPrompt=false;
};
In the file above, a configuration entry is identified by the name (i.e. pgjdbc, SQLJDBCDriver) that is significant to the driver. This value can be overridden in the JDBC connection string, and the name in the JAAS configuration file must match the overridden name. If there is a mismatch, the Kerberos login module will not be found, and the authentication will fail. See the section on building the JDBC connection string below for more information.
The minimal JAAS configuration file shown above does not explicitly specify credentials. As a result, it may prompt the user to enter a password for the KDC unless credentials are already available on the running OS, which is often insufficient for most server deployments. To address this, credentials can be provided via JAAS by configuring either a Kerberos ticket cache or a keytab file.
Option 1: Using ticket cache
The first option is to use an existing TGT cache. In this case, the JAAS configuration should include both useTicketCache set to true and the ticketCache mount location. The configuration for this case:
-
SQL Server
-
PostgreSQL
SQLJDBCDriver {
com.sun.security.auth.module.Krb5LoginModule required
useTicketCache=true
ticketCache="/app/tickets/krb5cc_user"
doNotPrompt=true;
};
pgjdbc {
com.sun.security.auth.module.Krb5LoginModule required
useTicketCache=true
ticketCache="/app/tickets/krb5cc_user"
doNotPrompt=true;
};
The ticket cache should be mounted along with the proper configuration file to the Worker Docker container. See Passing configuration files to the Java process.
|
The ticket cache should be renewed periodically, as the KDC issues time-limited TGT in most setups. |
Option 2: Using keytab
You can use a keytab provided by the KDC administrator. In this setup, the JAAS configuration should specify option useKeyTab set to true and contain a valid location for the keytab and the user principal along with several other options:
-
SQL Server
-
PostgreSQL
SQLJDBCDriver {
com.sun.security.auth.module.Krb5LoginModule required
useKeyTab=true
keyTab="/app/keytabs/user.keytab"
principal="user@DEV.LOCAL"
storeKey=true
isInitiator=true
doNotPrompt=true;
};
pgjdbc {
com.sun.security.auth.module.Krb5LoginModule required
useKeyTab=true
keyTab="/app/keytabs/user.keytab"
principal="user@DEV.LOCAL"
storeKey=true
isInitiator=true
doNotPrompt=true;
};
In this case, the TGTs will be managed automatically by the Java process.
Passing configuration files to the Java process
The Worker Java process (server or agent) runs inside a Docker container. To pass the configuration files to the Java process, you need to mount the files as volumes when starting the container. Once mounted, the files' paths inside the container must be passed as special Java properties to the JVM instance. Assuming that the krb5.conf, jaas.conf, and either ticket cache krb5cc_user or keytab user.keytab (depending on the choice of credential provisioning) are located in the same directory as docker-compose.yaml, the following examples show how to start the Worker container with the configuration files mounted using the Docker Compose syntax:
-
Using ticket cache
-
Using keytab
services:
agent:
environment:
JAVA_TOOL_OPTIONS: >
-Djava.security.krb5.conf=/app/krb5.conf
-Djava.security.auth.login.config=/app/jaas.conf
volumes:
- ./krb5.conf:/app/krb5.conf
- ./jaas.conf:/app/jaas.conf
- ./krb5cc_user:/app/tickets/krb5cc_user:ro
services:
agent:
environment:
JAVA_TOOL_OPTIONS: >
-Djava.security.krb5.conf=/app/krb5.conf
-Djava.security.auth.login.config=/app/jaas.conf
volumes:
- ./krb5.conf:/app/krb5.conf
- ./jaas.conf:/app/jaas.conf
- ./user.keytab:/app/keytabs/user.keytab:ro
In the examples above, the volumes section mounts the local files krb5.conf and jaas.conf to the /app directory inside the container. The java.security.krb5.conf and java.security.auth.login.config are the Java properties to specify the location of the Kerberos and JAAS configuration files, respectively. The JAVA_TOOL_OPTIONS environment variable is an easy way to pass Java properties to the JVM without modifying the application’s startup script.
Building a JDBC connection string
For comprehensive tuning of the JDBC connection string, please refer to the corresponding documentation page
- SQL Server
-
The JDBC connection string must include additional parameters to use Kerberos authentication:
-
integratedSecurity=true- the connection should use Windows authentication. -
authenticationScheme=JavaKerberos- the connection should use Java built-in Kerberos authentication module.
-
The following is an example of a JDBC connection string that uses Kerberos authentication:
jdbc:sqlserver://;serverName=my.database.local;databaseName=input;integratedSecurity=true;authenticationScheme=JavaKerberos
- PostgreSQL
-
PostgreSQL doesn’t require specific options specified in the JDBC connection string.
Overriding the JAAS configuration name
In some cases, a non-default JAAS configuration name is required. For instance, when multiple JAAS configurations are present on the same Worker instance, each configuration must have a distinct name. The examples below show how to specify the configuration name in the JDBC connection string.
-
SQL Server
-
PostgreSQL
jdbc:sqlserver://;serverName=my.database.local;databaseName=input;integratedSecurity=true;authenticationScheme=JavaKerberos;jaasConfigurationName=MyFancyKerberosConfig
jdbc:postgresql://my.database.local:5432/input?jaasApplicationName=MyFancyKerberosConfig
The corresponding JAAS configuration file will need to be updated to match the new name:
MyFancyKerberosConfig {
com.sun.security.auth.module.Krb5LoginModule required
useTicketCache=true
doNotPrompt=true;
};
MyOtherKerberosConfig {
...
}