All Downloads are FREE. Search and download functionalities are using the official Maven repository.

org.jivesoftware.openfire.auth.HybridAuthProvider Maven / Gradle / Ivy

The newest version!
/*
 * Copyright (C) 2005-2008 Jive Software. All rights reserved.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package org.jivesoftware.openfire.auth;

import java.util.HashSet;
import java.util.Set;

import org.jivesoftware.openfire.user.UserNotFoundException;
import org.jivesoftware.util.ClassUtils;
import org.jivesoftware.util.JiveGlobals;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

/**
 * The hybrid auth provider allows up to three AuthProvider implementations to
 * be strung together to do chained authentication checking. The algorithm is
 * as follows:
 * 
    *
  1. Attempt authentication using the primary provider. If that fails: *
  2. If the secondary provider is defined, attempt authentication (otherwise return). * If that fails: *
  3. If the tertiary provider is defined, attempt authentication. *
* * This class related to, but is distinct from {@link MappedAuthProvider}. The Hybrid variant of the provider iterates * over providers, operating on the first applicable instance. The Mapped variant, however, maps each user to exactly * one provider. * * To enable this provider, set the provider.auth.className system property to * org.jivesoftware.openfire.auth.HybridAuthProvider. * * The primary, secondary, and tertiary providers are configured be setting system properties similar to * the following: * *
    *
  • hybridAuthProvider.primaryProvider = org.jivesoftware.openfire.auth.DefaultAuthProvider
  • *
  • hybridAuthProvider.secondaryProvider = org.jivesoftware.openfire.auth.NativeAuthProvider
  • *
* * Each of the chained providers can have a list of override users. If a user is in * an override list, authentication will only be attempted with the associated provider * (bypassing the chaining logic).

* * The full list of properties: *

    *
  • hybridAuthProvider.primaryProvider.className (required) -- the class name * of the auth provider. *
  • hybridAuthProvider.primaryProvider.overrideList -- a comma-delimitted list * of usernames for which authentication will only be tried with this provider. *
  • hybridAuthProvider.secondaryProvider.className -- the class name * of the auth provider. *
  • hybridAuthProvider.secondaryProvider.overrideList -- a comma-delimitted list * of usernames for which authentication will only be tried with this provider. *
  • hybridAuthProvider.tertiaryProvider.className -- the class name * of the auth provider. *
  • hybridAuthProvider.tertiaryProvider.overrideList -- a comma-delimitted list * of usernames for which authentication will only be tried with this provider. *
* * The primary provider is required, but all other properties are optional. Each provider * should be configured as it is normally, using whatever XML configuration options it specifies. * * @author Matt Tucker */ public class HybridAuthProvider implements AuthProvider { private static final Logger Log = LoggerFactory.getLogger(HybridAuthProvider.class); private AuthProvider primaryProvider; private AuthProvider secondaryProvider; private AuthProvider tertiaryProvider; private Set primaryOverrides = new HashSet<>(); private Set secondaryOverrides = new HashSet<>(); private Set tertiaryOverrides = new HashSet<>(); public HybridAuthProvider() { // Convert XML based provider setup to Database based JiveGlobals.migrateProperty("hybridAuthProvider.primaryProvider.className"); JiveGlobals.migrateProperty("hybridAuthProvider.secondaryProvider.className"); JiveGlobals.migrateProperty("hybridAuthProvider.tertiaryProvider.className"); JiveGlobals.migrateProperty("hybridAuthProvider.primaryProvider.overrideList"); JiveGlobals.migrateProperty("hybridAuthProvider.secondaryProvider.overrideList"); JiveGlobals.migrateProperty("hybridAuthProvider.tertiaryProvider.overrideList"); // Load primary, secondary, and tertiary auth providers. String primaryClass = JiveGlobals.getProperty( "hybridAuthProvider.primaryProvider.className"); if (primaryClass == null) { Log.error("A primary AuthProvider must be specified. Authentication will be disabled."); return; } try { Class c = ClassUtils.forName(primaryClass); primaryProvider = (AuthProvider)c.newInstance(); Log.debug("Primary auth provider: " + primaryClass); } catch (Exception e) { Log.error("Unable to load primary auth provider: " + primaryClass + ". Authentication will be disabled.", e); return; } String secondaryClass = JiveGlobals.getProperty( "hybridAuthProvider.secondaryProvider.className"); if (secondaryClass != null) { try { Class c = ClassUtils.forName(secondaryClass); secondaryProvider = (AuthProvider)c.newInstance(); Log.debug("Secondary auth provider: " + secondaryClass); } catch (Exception e) { Log.error("Unable to load secondary auth provider: " + secondaryClass, e); } } String tertiaryClass = JiveGlobals.getProperty( "hybridAuthProvider.tertiaryProvider.className"); if (tertiaryClass != null) { try { Class c = ClassUtils.forName(tertiaryClass); tertiaryProvider = (AuthProvider)c.newInstance(); Log.debug("Tertiary auth provider: " + tertiaryClass); } catch (Exception e) { Log.error("Unable to load tertiary auth provider: " + tertiaryClass, e); } } // Now, load any overrides. String overrideList = JiveGlobals.getProperty( "hybridAuthProvider.primaryProvider.overrideList", ""); for (String user: overrideList.split(",")) { primaryOverrides.add(user.trim().toLowerCase()); } if (secondaryProvider != null) { overrideList = JiveGlobals.getProperty( "hybridAuthProvider.secondaryProvider.overrideList", ""); for (String user: overrideList.split(",")) { secondaryOverrides.add(user.trim().toLowerCase()); } } if (tertiaryProvider != null) { overrideList = JiveGlobals.getProperty( "hybridAuthProvider.tertiaryProvider.overrideList", ""); for (String user: overrideList.split(",")) { tertiaryOverrides.add(user.trim().toLowerCase()); } } } @Override public void authenticate(String username, String password) throws UnauthorizedException, ConnectionException, InternalUnauthenticatedException { // Check overrides first. if (primaryOverrides.contains(username.toLowerCase())) { primaryProvider.authenticate(username, password); return; } else if (secondaryOverrides.contains(username.toLowerCase())) { secondaryProvider.authenticate(username, password); return; } else if (tertiaryOverrides.contains(username.toLowerCase())) { tertiaryProvider.authenticate(username, password); return; } // Now perform normal try { primaryProvider.authenticate(username, password); } catch (UnauthorizedException ue) { if (secondaryProvider != null) { try { secondaryProvider.authenticate(username, password); } catch (UnauthorizedException ue2) { if (tertiaryProvider != null) { tertiaryProvider.authenticate(username, password); } else { throw ue2; } } } else { throw ue; } } } @Override public String getPassword(String username) throws UserNotFoundException, UnsupportedOperationException { throw new UnsupportedOperationException(); } @Override public void setPassword(String username, String password) throws UserNotFoundException, UnsupportedOperationException { throw new UnsupportedOperationException(); } @Override public boolean supportsPasswordRetrieval() { return false; } @Override public boolean isScramSupported() { // TODO Auto-generated method stub return false; } @Override public String getSalt(String username) throws UnsupportedOperationException, UserNotFoundException { throw new UnsupportedOperationException(); } @Override public int getIterations(String username) throws UnsupportedOperationException, UserNotFoundException { throw new UnsupportedOperationException(); } @Override public String getServerKey(String username) throws UnsupportedOperationException, UserNotFoundException { throw new UnsupportedOperationException(); } @Override public String getStoredKey(String username) throws UnsupportedOperationException, UserNotFoundException { throw new UnsupportedOperationException(); } boolean isProvider(final Class clazz) { return (primaryProvider != null && clazz.isAssignableFrom(primaryProvider.getClass())) || (secondaryProvider != null && clazz.isAssignableFrom(secondaryProvider.getClass())) ||(tertiaryProvider != null && clazz.isAssignableFrom(tertiaryProvider.getClass())); } }




© 2015 - 2024 Weber Informatics LLC | Privacy Policy