Versions Compared

Key

  • This line was added.
  • This line was removed.
  • Formatting was changed.

...

At the time of writing this CEP, Cassandra lacks a mechanism how to prevent a user from creating a password which does not follow a certain security policy. As of now, a password might be anything. While passwords for users might be generated as part of company processes and they should adhere to organisational password complexity policies, it does not mean that it is enforced from Cassandra itself. More to it, once a password is set, even though it might follow some security guidelines upon its creation, it might be changed afterwards to a password which is less secure by "alter role" statements. Last but not least, it is a good practice to change passwords every now and then to prevent unauthorised access when credentials are leaked unknowingly. However, upon changing a password, it should not be possible to reuse them - each new password for a user should be unique from the recent ones in order to not "recycle" them.

...

When it comes to password validator, while custom guardrails are reconfigurable as such, we do not want to have it reconfigurable. The reconfiguration of password validators in runtime seems to be not desirable, the primary reason for this is we want to prevent rogue actors to lower the security standards intentionally. The enablement of reconfigurability is not up to an implementation of a custom guardrail itself. It is rather done by not exposing a respective JMX method on GuardrailsMBean which acts as way to achieve that. If implementors of any other custom guardrail need to have it reconfigurable in runtime, they are welcomed to do so by providing respective JMX methods on GuardrailsMBean and by calling "reconfigure" method on CustomGuardrail like this:

This is method of CustomGuardrail class:

    /**
     * Reconfigures this custom guardrail. After the successful finish of this method, every
     * new call to this guardrail will use new configuration for its validator.
     * <p>
     * New configuration is merged into the old one. Values for the keys in the old configuration
     * are replaced by the values of the same key in the new configuration.
     *
     * @param newConfig if null or the configuration is an empty map, no reconfiguration happens.
     */
    void reconfigure(@Nullable Map<String, Object> newConfig)
    {
        if (newConfig == null || newConfig.isEmpty())
            return;

        Map<String, Object> mergedMap = new HashMap<>(validator.get().getParameters());
        mergedMap.putAll(newConfig);

        ValueValidator<VALUE> newValidator = ValueValidator.getValidator(name, new CustomGuardrailConfig(mergedMap));
        validator.set(newValidator);
    }

We want to be able to reconfigure a validator in such a way that we might override only parameters which we want to change and leave other configuration parameters intact. ValueValidator.getValidator is a static method which instantiates a validator by reflection taking the value of class_name parameter. "validator" variable is field in CustomGuardrail class. "validator" is AtomicReference. By this way, we can just switch one validator for another in runtime. Once switched, every subsequent validation will use new validatorthe desired outcome would be to not be able to replace one validator for another if it is less "strict" than the current one. We do not want to enable a user to lower the strictness of password validators intentionally nor by accident. An operator might only increase the strictness, not decrease it. Hence, while reconfiguration should be possible, it should not be possible under all circumstances. The idea is to call a method on the current validator which returns true if a new validator (as a parameter of that method) can replace the one that method is called on, otherwise it would return false. Based on the returned value, reconfiguration would take place and the old validator would be switched for a new one or an exception would be thrown.

Validation of a new value against the previous values

...

cqlsh> GENERATE HASHED PASSWORD;

 password   |             salted_hash
------------+-------------------------
 Lr5l:73&oM |      where will be hash

(1 rows) 


We will not include the last two commands into the initial implementation.


The advantage of this approach:

...

There is working validation as well as generation via implemented. The code contains both hash_password tool shown. However, we expect that to be rewritten so respective CQL statements will be changed as discussed above.modifications as well as the changes for CQL statements (CREATE / ALTER role ... WITH GENERATED PASSWORD)

Compatibility, Deprecation, and Migration Plan

...