Skip to content


Switch branches/tags

Name already in use

A tag already exists with the provided branch name. Many Git commands accept both tag and branch names, so creating this branch may cause unexpected behavior. Are you sure you want to create this branch?

Latest commit


Git stats


Failed to load latest commit information.
Latest commit message
Commit time

Instaclustr LDAP Authenticator

LDAP Authenticator for Apache Cassandra


This is a pluggable authentication implementation for Apache Cassandra, providing a way to authenticate and create users based on a configured LDAP server. This implementation provides authentication only. Role management must be performed through the usual Cassandra role management— CassandraAuthorizer. See How it works for more details.

Project Structure and Building

This project consists of 5 modules; the base module is the module on which all other implementation modules depend. It contains core implementation which is necessary as all concrete modules are reusing it.

The base module depends on Cassandra dependency—version 3.0.18 but its scope is provided as these classes will be present when such plugin as a whole is put on a class path of Cassandra in runtime.

There are four implementation modules:

  • cassandra-2.2 - builds against version 2.2.19

  • cassandra-3.0 - builds against version 3.0.25

  • cassandra-3.11 - builds against version 3.11.11

  • cassandra-4.0 - builds against version 4.0.0

Project is built as:

$ mvn clean install

This does not invoke integration tests. For integration tests to run, please specify it profile:

$ mvn clean install -Pit

Integration tests will expect a Docker installation to be present (or a way to connect to one). There is a Docker container started with the LDAP server running against which an integration test, per module, is started.

Configuration of Plugins

After build, the respective JAR to place to Cassandra CLASSPATH (e.g. by placing it to libs directory of Cassandra installation) is located in the target directory of each build as casandra-ldap-{c* version}.jar. This JAR already contains artifacts from base so you do not need to take care of it-one JAR is enough. You may at most probably use a plugin built against a respective version for other Cassandra versions of the same minor release, so you might use 3.11.8 plugin for 3.11.4, for example.

The configuration is ridden by a configuration file and system properties which you need to start Cassandra with to point that plugin to a configuration file to read properties from.

The system property is If not set, it will try to resolve $CASSANDRA_CONF/

The content of the configuration file is as follows:

property name explanation


Ldap server URI. Specify ldaps when using a secure LDAP port (strongly recommended), example: ldap://,dc=org


defaults to com.sun.jndi.ldap.LdapCtxFactory


Service user distinguished name. This user will be a SUPERUSER and be used for looking up user details on authentication, example: cn=admin,dc=example,dc=org


Service user password


template for searching in LDAP, explanation further in this readme, defaults to (cn=%s)


relevant for Cassandra 3.11 and 4.0 plugins, defaults to false


consistency level to use for retrieval of a role to check if it can log in - defaults to LOCAL_ONE


number of rounds to hash passwords


defaults to false, if it is true, SPI mechanism will look on class path to load custom implementation of LDAPUserRetriever.

Configuration of Cassandra

If is strongly recommended to use NetworkTopologyStrategy for your system_auth keyspace.

Please be sure that system_auth keyspace uses NetworkTopologyStrategy with number of replicas equal to number of nodes in DC. If it is not the case, you can alter your keyspace as follows:

ALTER KEYSPACE system_auth WITH replication = {'class': 'NetworkTopologyStrategy', 'dc1': '3'}  AND durable_writes = true;

After this, repair system_auth keyspace so it all propagates to other nodes.

You need to restart your cluster in a rolling fashion. For each node, you need to add one of these configurations into cassandra.yaml for each node:

Cassandra 2.2

authenticator: Cassandra22LDAPAuthenticator
role_manager: LDAPCassandraRoleManager
authorizer: CassandraAuthorizer

Cassandra 3.0

authenticator: Cassandra30LDAPAuthenticator
role_manager: LDAPCassandraRoleManager
authorizer: CassandraAuthorizer

Cassandra 3.11

authenticator: LDAPAuthenticator
authorizer: CassandraAuthorizer
role_manager: LDAPCassandraRoleManager

Cassandra 4.0

authenticator: LDAPAuthenticator
authorizer: CassandraAuthorizer
role_manager: LDAPCassandraRoleManager

For 3.11 and 4, configure credential caching parameters in cassandra.yaml if necessary and if you want that cache to be enabled (as per configuration parameters). [Re]start Cassandra.


For fast testing there is Debian OpenLDAP Docker container

docker run -e LDAP_ADMIN_PASSWORD=admin --rm -d -p 389:389 --name ldap1 osixia/openldap

The ldap.configuration file in the conf directory does not need to be changed, and with the above docker run it will work out of the box. You just have to put it in $CASSANDRA_CONF or set respective configuration property as described above.

Explanation of filter_template property

filter_template property is by default (cn=%s) where %s will be replaced by name you want to log in with. For example if you do cqlsh -u myuserinldap, a search filter for LDAP will be (cn=myuserinldap). You may have a different search filter based on your need, a lot of people use e.g. SAM or something similar. If you try to log in with cqlsh -u cn=myuserinldap, there will be no replacement done and this will be used as a search filter instead.

How it Works

LDAPAuthenticator currently supports plain text authorization requests only in the form of a username and password. This request is made to the LDAP server over plain text, so you should be using client encryption on the Cassandra side and secure ldap (ldaps) on the LDAP side.

Credentials are sent from your client to the Cassandra server and then tested against the LDAP server for authentication using a specified service account. This service account should be configured in the file using the service_dn and service_password properties. If service_dn is set, such a role will be created in database, when not already present, upon node’s start.

service_dn account, which will be automatically created, will be super user in Cassandra.

All "normal" roles are not affected—they behave exactly as you are used to.

If the LDAP server connection is lost or there is another communication error while talking to LDAP server, the operator still has a possibility of logging in via cassandra user as usual, and until the LDAP server is not back again; Users meant to be authenticated against the LDAP server will not be able to log in but all "normal" users will be able to login and the disruption of LDAP communication will not affect their ability to do so as they live in Cassandra natively.

In case a user specifies just test as login name (or any other name, for that matter), it will try to authenticate against database first and if not successful against LDAP using filter filter_template which defaults to (cn=%s)

It is possible to delete administration role (e.g. role cassandra) but if one does that, all administration operations are only able to be done via LDAP account. In case LDAP is down, the operator would not have any control over DB as cassandra is not present anymore. In such case, it is recommended to create another admin-like user with a strong password before the cassandra role is deleted. A plugin is internally creating new roles when somebody from LDAP logs in and it is not in DB yet. For this functionality, there needs to be some admin-like user which writes them system_auth.roles table. If you delete cassandra user, there is suddenly not such user. You have to restart node and specify this property:


Where dba is new superuser which is able to write to system_auth.roles and acts as Cassandra admin.

Upon login via LDAP user, this plugin will create a dummy role just to be able to play as a normal Cassandra role with all its permissions and so on. Passwords for LDAP users are not stored in Cassandra, obviously.

Credentials are cached for implementations for Cassandra 3.11 and 4.0 so that way we are not hitting LDAP server all the time when there is a lot of login attempts with same login name. An administrator can increase relevant validity settings in cassandra.yaml to increase these periods even more.

SPI for LDAP server implementations (advanced)

In order to talk to a LDAP server, there is DefaultLDAPServer class in base module which all modules are using. However, it might not be enough - there is a lot of LDAP servers out there and their internals and configuration might render the default implementation incompatible. If you have special requirements, you might provide your own implementation by implementing LDAPUserRetriever. You have to have load_ldap_service set to true as well.

To tell LDAP plugin to use your implementation, you need to create a file in src/main/resources/META-INF/services called LDAPUserRetriever and the content of that file needs to be just one line - the fully qualified class name (with package) of your custom implementation.

After you build such plugin, the SPI mechanism upon plugin’s initialisation during Cassandra node startup will pick up your custom LDAP server connection / authentication logic.

Further Information