Developing a control authentication handler
Implement the ControlAuthenticator interface to create a control authentication handler.
This example demonstrates how to implement a control authentication handler in Java™.
-
Edit the etc/Server.xml configuration file to include a
name that the control authentication handler can register with.
Include the control-authentication-handler element in the list of authentication handlers. The order of the list defines the order in which the authentication handlers are called. The value of the handler-name attribute is the name that your control authentication handler registers as. For example:
<security> <authentication-handlers> <-- Include a local authentication handler that can authenticate the control client --> <authentication-handler class="com.example.LocalHandler" /> <-- Register your control authentication handler --> <control-authentication-handler handler-name="before-system-handler" /> </authentication-handlers> </security>
The client that registers your control authentication handler must first authenticate with the Diffusion™ server. Configure a local authentication handler that allows the client to connect.
-
Start the Diffusion server.
- On UNIX®-based systems, run the diffusion.sh command in the diffusion_installation_dir/bin directory.
- On Windows™ systems, run the diffusion.bat command in the diffusion_installation_dir\bin directory.
-
Create a simple client that registers a control authentication handler with
the Diffusion server. You will need to create a Java class that implements
ControlAuthenticator.
package com.pushtechnology.diffusion.examples; import java.nio.charset.Charset; import java.util.Arrays; import java.util.HashMap; import java.util.Map; import java.util.Set; import java.util.concurrent.TimeUnit; import com.pushtechnology.diffusion.client.Diffusion; import com.pushtechnology.diffusion.client.callbacks.Stream; import com.pushtechnology.diffusion.client.features.control.clients.AuthenticationControl; import com.pushtechnology.diffusion.client.features.control.clients.AuthenticationControl.ControlAuthenticator; import com.pushtechnology.diffusion.client.session.Session; import com.pushtechnology.diffusion.client.types.Credentials; public final class ControlAuthenticationClient { private ControlAuthenticationClient() { } /** * Main entry point for the control client. */ // CHECKSTYLE.OFF: UncommentedMain public static void main(final String[] args) throws Exception { // The control client connects to the server using the principal 'admin' // which is authenticated by the system authentication handler (see // etc/SystemAuthentication.store). // The principal must have REGISTER_HANDLER and AUTHENTICATE permissions. final Session session = Diffusion.sessions() .principal("admin") .password("password") .open("ws://diffusion.example.com:80"); session.feature(AuthenticationControl.class).setAuthenticationHandler( "after-system-handler", new ExampleControlAuthenticationHandler()).get(10, TimeUnit.SECONDS); while (true) { Thread.sleep(60000); } } /** * An example of a control authentication handler. * <p> * This shows a simple example using a table of permitted principals with * their passwords. It also demonstrates how the handler can change the * properties of the client being authenticated. */ private static class ExampleControlAuthenticationHandler extends Stream.Default implements ControlAuthenticator { private static final Map<String, byte[]> PASSWORDS = new HashMap<>(); static { PASSWORDS.put("manager", "password".getBytes(Charset.forName("UTF-8"))); PASSWORDS.put("guest", "asecret".getBytes(Charset.forName("UTF-8"))); PASSWORDS.put("brian", "boru".getBytes(Charset.forName("UTF-8"))); PASSWORDS.put("another", "apassword".getBytes(Charset.forName("UTF-8"))); } @Override public void authenticate( String principal, Credentials credentials, Map<String, String> sessionProperties, Map<String, String> proposedProperties, Callback callback) { final byte[] passwordBytes = PASSWORDS.get(principal); if (passwordBytes != null && credentials.getType() == Credentials.Type.PLAIN_PASSWORD && Arrays.equals(credentials.toBytes(), passwordBytes)) { if ("manager".equals(principal)) { // manager allows all proposed properties callback.allow(proposedProperties); } else if ("brian".equals(principal)) { // brian is allowed all proposed properties and also gets // the 'super' role added final Map<String, String> result = new HashMap<>(proposedProperties); final Set<String> roles = Diffusion.stringToRoles( sessionProperties.get(Session.ROLES)); roles.add("super"); result.put(Session.ROLES, Diffusion.rolesToString(roles)); callback.allow(result); } else { // all others authenticated but ignoring proposed properties callback.allow(); } } else { // Any principal not in the table is denied. callback.deny(); } } } }
-
Start your client.
It connects to the Diffusion server and registers the control authentication handler with the name after-system-handler.