Fork me on GitHub

User Actions

Overview

Oak 1.10 comes with an extension to the Jackrabbit user management API that allows to perform additional actions or validations for user specific operations such as

  • disable (or enable) a user
  • allowing a given principal to impersonate the target user
  • revoke the ability to impersonate the target user for a given principal

UserAction API

The following public interface is provided by Oak in the package org.apache.jackrabbit.oak.spi.security.user.action:

The UserAction interface extends from AuthorizableAction and itself allows to perform validations or write additional application specific content while executing user specific operations. Therefore these actions are executed as part of the transient user management modifications. This contrasts to org.apache.jackrabbit.oak.spi.commit.CommitHooks which in turn are only triggered once modifications are persisted.

Consequently, implementations of the UserAction interface are expected to adhere to this rule and perform transient repository operations or validation. They must not force changes to be persisted by calling org.apache.jackrabbit.oak.api.Root.commit().

Any user actions are executed with the editing session and the target operation will fail if any of the configured actions fails (e.g. due to insufficient permissions by the editing Oak ContentSession).

Default Implementations

Oak 1.10 doesn't provide any base implementation for UserAction.

XML Import

During import the user actions are called in the same way as when the corresponding API calls are invoked.

Pluggability

Refer to Authorizable Actions | Pluggability for details on how to plug a new user action into the system.

Examples
Example Action

This example action removes the profile nodes upon disabling the user:

ClearProfilesAction extends AbstractAuthorizableAction implements UserAction {

    @Override
    public void onDisable(@NotNull User user, @Nullable String disableReason, @NotNull Root root, @NotNull NamePathMapper namePathMapper) throws RepositoryException {
        if (disableReason != null) {
            Tree t = root.getTree(user.getPath());
            if (t.exists() && t.hasChild("profiles")) {
                t.getChild("profiles").remove();
            }
        }
    }
}