/**
 *                                                                            
 * Copyright (c) 2011, 2016 - Loetz GmbH&Co.KG (69115 Heidelberg, Germany)
 *                                                                            
 * All rights reserved. This program and the accompanying materials           
 * are made available under the terms of the Eclipse Public License v1.0       
 * which accompanies this distribution, and is available at                  
 * http://www.eclipse.org/legal/epl-v10.html                                 
 *                                                                            
 * Contributors:   
 * Christophe Loetz (Loetz GmbH&Co.KG) - initial implementation 
 */
package org.eclipse.osbp.authentication.providerimpl;

import java.util.ArrayList;
import java.util.Collection;
import java.util.Collections;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;
import java.util.Set;

import org.apache.shiro.SecurityUtils;
import org.apache.shiro.authc.AuthenticationException;
import org.apache.shiro.authc.credential.DefaultPasswordService;
import org.apache.shiro.authz.AuthorizationInfo;
import org.apache.shiro.config.Ini;
import org.apache.shiro.mgt.SecurityManager;
import org.apache.shiro.realm.AuthenticatingRealm;
import org.apache.shiro.subject.Subject;
import org.apache.shiro.util.ThreadContext;
import org.apache.shiro.web.config.WebIniSecurityManagerFactory;
import org.apache.shiro.web.mgt.DefaultWebSecurityManager;
import org.eclipse.osbp.authentication.account.dtos.UserAccountDto;
import org.eclipse.osbp.authentication.account.dtos.UserAccountFilterDto;
import org.eclipse.osbp.authentication.shiro.extensions.StaticRealm;
import org.eclipse.osbp.authentication.shiro.extensionsimpl.PortalUsernamePasswordToken;
import org.eclipse.osbp.authentication.shiro.extensionsimpl.UserAccessAuthorizationRealm;
import org.eclipse.osbp.authentication.vaadin.SubjectProvider;
import org.eclipse.osbp.authentication.vaadin.VaadinSessionManager;
import org.eclipse.osbp.authentication.vaadin.VaadinSessionProvider;
import org.eclipse.osbp.core.api.persistence.IPersistenceService;
import org.eclipse.osbp.dsl.dto.lib.impl.DtoServiceAccess;
import org.eclipse.osbp.jpa.services.Query;
import org.eclipse.osbp.preferences.ProductConfiguration;
import org.eclipse.osbp.runtime.common.filter.IDTOServiceWithMutablePersistence;
import org.eclipse.osbp.ui.api.complexdatacontainer.IComplexDataContainerChangedListener;
import org.eclipse.osbp.ui.api.useraccess.AbstractAuthorization;
import org.eclipse.osbp.ui.api.useraccess.AbstractAuthorization.Action;
import org.eclipse.osbp.ui.api.useraccess.AbstractAuthorization.Group;
import org.eclipse.osbp.ui.api.useraccess.AbstractPosition;
import org.eclipse.osbp.ui.api.useraccess.IOrganizationService;
import org.eclipse.osbp.ui.api.useraccess.IPosition;
import org.eclipse.osbp.ui.api.useraccess.ISubOrganization;
import org.eclipse.osbp.ui.api.useraccess.IUserAccessService;
import org.eclipse.osbp.ui.api.userfilter.UserFilterMap;
import org.osgi.service.component.annotations.Component;
import org.osgi.service.component.annotations.Reference;
import org.osgi.service.component.annotations.ReferenceCardinality;
import org.osgi.service.component.annotations.ReferencePolicy;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.vaadin.server.Page;

/**
 * The Class UserAccessService.
 */
@Component(service = IUserAccessService.class)
public class UserAccessService extends UserProtocol implements IUserAccessService {

	/** The Constant LOGGER. */
	private static final Logger LOGGER = LoggerFactory.getLogger(UserAccessService.class);

	/** The subject provider. */
	private SubjectProvider subjectProvider;

	/** The Constant USER_KEY. */
	private static final String USER_KEY = "user";

	/** The Constant USER_FILTER_MAP_KEY. */
	private static final String USER_FILTER_MAP_KEY = "userFilterMap";

	/** The Constant POSITION_KEY. */
	private static final String POSITION_KEY = "position";

	/** The Constant ROLES_KEY. */
	private static final String ROLES_KEY = "roles";

	/** The Constant PERMISSIONS_KEY. */
	private static final String AUTHORIZATION_KEY = "authorization";

	/** The Constant AUTHENTICATED_BY_REALM. */
	private static final String AUTHENTICATED_BY_REALM = "realm";

	/** The Constant USER_DEFAULT_PERSPECTIVE. */
	private static final String USER_DEFAULT_PERSPECTIVE = "defaultPerspective";

	
	/** The Constant sOrganizationServices. */
	protected static final Map<String, IOrganizationService> sOrganizationServices = new HashMap<>();

	/** The listeners which are listening for changed complex data changes. */
	protected static final Set<IComplexDataContainerChangedListener> complexDataContainerChangedListeners = new HashSet<>();

	/**
	 * Gets the organization services.
	 *
	 * @return the organization services
	 */
	public static Set<IOrganizationService> getOrganizationServices() {
		return new HashSet<>(sOrganizationServices.values());
	}


	/**
	 * Instantiates a new user access service.
	 */
	public UserAccessService() {
		super();
	}

	protected void activate() {
		// We use a factory that can injects a .ini file and
		// returns a SecurityManager instance
		Ini ini = new Ini();
		ini.load(ProductConfiguration.getShiroConfiguration(StaticRealm.class.getCanonicalName()));
		WebIniSecurityManagerFactory sFactory = new WebIniSecurityManagerFactory(ini);
		// the following line works with reflection and looks for shiro in the
		// current bundle. no osgi possible in this version.
		SecurityManager sSecurityManager = sFactory.getInstance();
		VaadinSessionProvider vaadinSessionProvider = new VaadinSessionProvider();
		VaadinSessionManager vaadinSessionManager = new VaadinSessionManager(vaadinSessionProvider);
		// the vaadin session embeds the shiro subject
		((DefaultWebSecurityManager) sSecurityManager).setSessionManager(vaadinSessionManager);
		subjectProvider = new SubjectProvider(vaadinSessionProvider);
		SecurityUtils.setSecurityManager(sSecurityManager);
		LOGGER.debug("security manager is set");
		UserProtocol.persistenceService.registerPersistenceUnit(persistenceId, UserProtocol.class);
		if (UserProtocol.dtoUserAccountDtoService == null) {
			UserProtocol.dtoUserAccountDtoService = (IDTOServiceWithMutablePersistence<UserAccountDto>) DtoServiceAccess
					.getService(UserAccountDto.class);
		}
		// for password encryption
		if (UserProtocol.passwordService == null) {
			UserProtocol.passwordService = new DefaultPasswordService();
		}

	}

	protected void deactivate() {
		LOGGER.debug("useraccessservice deactivated");
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see
	 * org.eclipse.osbp.ui.api.useraccess.IUserAccessService#getAuthorizations()
	 */
	@Override
	public AuthorizationInfo getAuthorizations() {
		AuthorizationInfo info = null;
		AuthenticatingRealm realm = null;
		if (isAuthenticated()) {
			try {
				info = (AuthorizationInfo) ThreadContext.get(AUTHORIZATION_KEY);
			} catch (Exception e) {
				LOGGER.info("");
			}
			try {
				realm = (AuthenticatingRealm) ThreadContext.get(AUTHENTICATED_BY_REALM);
			} catch (Exception e) {
				LOGGER.info("");
			}
			if (info == null) {
				info = new AuthorizationInformation(
						(realm instanceof UserAccessAuthorizationRealm)
								? ((UserAccessAuthorizationRealm) realm).getPortalId() : "",
						subjectProvider.get().getPrincipals(), getPosition(), getAuthorization());
				ThreadContext.put(AUTHORIZATION_KEY, info);
			}
		}
		return info;
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see
	 * org.eclipse.osbp.ui.api.useraccess.IUserAccessService#isAuthenticated()
	 */
	@Override
	public boolean isAuthenticated() {
		return subjectProvider.get().isAuthenticated();
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see
	 * org.eclipse.osbp.ui.api.useraccess.IUserAccessService#authenticate(java
	 * .lang.String, java.lang.String, java.lang.String)
	 */
	@Override
	public boolean authenticate(String portal, String username, String password) {
		PortalUsernamePasswordToken token = new PortalUsernamePasswordToken(
				Page.getCurrent().getWebBrowser().getAddress(), portal, username, password);
		token.setRememberMe(false);
		token.setUserProtocol(this);
		AuthenticatingRealm realm = null;
		try {
			Subject subject = subjectProvider.get();
			subject.login(token);
			realm = token.getAuthenticatedByRealm();
			UserAccountDto user = null;
			UserFilterMap userFilterMap = null;
			AbstractPosition position = null;
			String defaultPerspective = null;
			Collection<String> roles = null;
			AbstractAuthorization authorization = null;
			if (realm instanceof UserAccessAuthorizationRealm) {
				user = ((UserAccessAuthorizationRealm) realm).findUserAccount(username);
				userFilterMap = createFilterMap(user);
				position = ((UserAccessAuthorizationRealm) realm).findPositionForUser(username);
				defaultPerspective = user.getDefaultPerspective();
				authorization = ((UserAccessAuthorizationRealm) realm).findPermissionsForUser(username);
			}
			if (position != null) {
				roles = position.getRoles();
			}
			setSessionAttribute(AUTHENTICATED_BY_REALM, token.getAuthenticatedByRealm());
			setSessionAttribute(USER_KEY, user);
			setSessionAttribute(USER_FILTER_MAP_KEY, userFilterMap);
			setSessionAttribute(POSITION_KEY, position);
			setSessionAttribute(ROLES_KEY, roles);
			setSessionAttribute(AUTHORIZATION_KEY, authorization);
			setSessionAttribute(USER_DEFAULT_PERSPECTIVE, defaultPerspective);

			if (LOGGER.isDebugEnabled()) {
				LOGGER.debug(subjectProvider.get().getSession().getAttributeKeys().toString());
			}
			trackSuccessfulLoginAttempt(username);
			if (LOGGER.isDebugEnabled()) {
				if (isGranted(Group.ENTITY, Action.CREATABLE,
						"org.eclipse.osbp.authentication.account.entities.UserAccount")) {
					LOGGER.debug("UserAccount is creatable");
				} else {
					LOGGER.debug("UserAccount is not creatable");
				}
				if (isVetoed(Group.ENTITY, Action.DISABLED,
						"org.eclipse.osbp.authentication.account.entities.UserAccount", "superuser")) {
					LOGGER.debug("superuser from UserAccount is disabled");
				} else {
					LOGGER.debug("superuser from UserAccount is not disabled");
				}
			}
			return true;
		} catch (AuthenticationException ae) { // NOSONAR
			// captcha
			int cnt = trackFailedLoginAttempt(username);
			if (cnt > ProductConfiguration.getMaxLoginAttempts()) {
				lockAccount(username, true);
			}
			try {
				// NOSONAR
				// wait exponentially along failed logins up to a maximum of
				// 18,2 hours to prevent "Rapid-Fire Login Attempts"
				// http://stackoverflow.com/questions/549/the-definitive-guide-to-form-based-website-authentication

				Long sleepLong = (long) (1000.0 * Math.max(5, Math.pow(2, Math.min(cnt, 16))));
				Long sleepLongSecs = sleepLong / 1000;
				LOGGER.info("User '{}' is locked for {} seconds now ... pls. wait", username, sleepLongSecs.toString());
				Thread.sleep(sleepLong);
			} catch (InterruptedException e) { // NOSONAR
				// Empty by design
			}
			LOGGER.error("Authentication: " + ae.getLocalizedMessage());
		}
		return false;
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see
	 * org.eclipse.osbp.ui.api.useraccess.IUserAccessService#authenticate(int,
	 * java.lang.String, java.lang.String)
	 */
	@Override
	public boolean authenticate(int portalId, String username, String password) {
		return authenticate(Integer.toString(portalId), username, password);
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see
	 * org.eclipse.osbp.ui.api.useraccess.IUserAccessService#authenticate(java
	 * .lang.String, java.lang.String)
	 */
	@Override
	public boolean authenticate(String username, String password) {
		return authenticate("", username, password);
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see
	 * org.eclipse.osbp.ui.api.useraccess.IUserAccessService#setSessionAttribute
	 * (java.lang.String, java.lang.Object)
	 */
	@Override
	public void setSessionAttribute(String key, Object value) {
		subjectProvider.get().getSession().setAttribute(key, value);
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see
	 * org.eclipse.osbp.ui.api.useraccess.IUserAccessService#getSessionAttribute
	 * (java.lang.String)
	 */
	@Override
	public Object getSessionAttribute(String key) {
		return subjectProvider.get().getSession().getAttribute(key);
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see org.eclipse.osbp.ui.api.useraccess.IUserAccessService#logout()
	 */
	@Override
	public void logout() {
		Subject subject = subjectProvider.get();
		try {
			setSessionAttribute(AUTHENTICATED_BY_REALM, null);
			setSessionAttribute(USER_KEY, null);
			setSessionAttribute(POSITION_KEY, null);
			setSessionAttribute(ROLES_KEY, null);
			setSessionAttribute(AUTHORIZATION_KEY, null);
		} catch (Exception e) {
			LOGGER.info("");
		}
		try {
			subject.logout();
		} catch (Exception e) {
			LOGGER.info("");
		}
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see org.eclipse.osbp.ui.api.useraccess.IUserAccessService#getUser()
	 */
	@Override
	public UserAccountDto getUser() {
		UserAccountDto user = (UserAccountDto) getSessionAttribute(USER_KEY);
		if (user == null) {
			LOGGER.error("Authentication getUser returned null");
		}
		return user;
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see org.eclipse.osbp.ui.api.useraccess.IUserAccessService#getUserName()
	 */
	@Override
	public String getUserName() {
		UserAccountDto user = (UserAccountDto) getSessionAttribute(USER_KEY);
		if (user != null) {
			return user.getUserName();
		}
		return "";
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see
	 * org.eclipse.osbp.ui.api.useraccess.IUserAccessService#getProfileimageId()
	 */
	@Override
	public String getProfileimageId() {
		UserAccountDto user = getUser();
		if (user != null) {
			return user.getProfileimage();
		}
		return "";
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see
	 * org.eclipse.osbp.ui.api.useraccess.IUserAccessService#getPositionName()
	 */
	@Override
	public String getPositionName() {
		UserAccountDto user = getUser();
		if (user != null) {
			return user.getPosition();
		}
		return "";
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see org.eclipse.osbp.ui.api.useraccess.IUserAccessService#getId()
	 */
	@Override
	public String getId() {
		UserAccountDto user = getUser();
		if (user != null) {
			return user.getId();
		}
		return "";
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see org.eclipse.osbp.ui.api.useraccess.IUserAccessService#getEmail()
	 */
	@Override
	public String getEmail() {
		UserAccountDto user = getUser();
		if (user != null) {
			return user.getEmail();
		}
		return "";
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see org.eclipse.osbp.ui.api.useraccess.IUserAccessService#getLocaleTag()
	 */
	@Override
	public String getLocaleTag() {
		UserAccountDto user = getUser();
		if (user != null) {
			return user.getLocaleTag();
		}
		return "";
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see org.eclipse.osbp.ui.api.useraccess.IUserAccessService#
	 * getLayoutingStrategy ()
	 */
	@Override
	public String getLayoutingStrategy() {
		UserAccountDto user = getUser();
		if (user != null) {
			return user.getLayoutingStrategy();
		}
		return "";
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see
	 * org.eclipse.osbp.ui.api.useraccess.IUserAccessService#getFocusingStrategy
	 * ()
	 */
	@Override
	public String getFocusingStrategy() {
		UserAccountDto user = getUser();
		if (user != null) {
			return user.getFocusingStrategy();
		}
		return "";
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see org.eclipse.osbp.ui.api.useraccess.IUserAccessService#getTheme()
	 */
	@Override
	public String getTheme() {
		UserAccountDto user = getUser();
		if (user != null) {
			return user.getTheme();
		}
		return "";
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see
	 * org.eclipse.osbp.ui.api.useraccess.IUserAccessService#getPrintService()
	 */
	@Override
	public String getPrintService() {
		UserAccountDto user = getUser();
		if (user != null) {
			return user.getPrintService();
		}
		return "";
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see org.eclipse.osbp.ui.api.useraccess.IUserAccessService#isSuperuser()
	 */
	@Override
	public boolean isSuperuser() {
		UserAccountDto user = getUser();
		if (user != null) {
			return user.getSuperuser();
		}
		return false;
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see org.eclipse.osbp.ui.api.useraccess.IUserAccessService#isSupervisor()
	 */
	@Override
	public boolean isSupervisor() {
		UserAccountDto user = getUser();
		if (user != null) {
			return user.getSupervisor();
		}
		return false;
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see org.eclipse.osbp.ui.api.useraccess.IUserAccessService#getPosition()
	 */
	@Override
	public AbstractPosition getPosition() {
		return (AbstractPosition) getSessionAttribute(POSITION_KEY);
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see
	 * org.eclipse.osbp.ui.api.useraccess.IUserAccessService#getPerspective()
	 */
	@Override
	public String getPerspective() {
		UserAccountDto user = getUser();
		if (user != null) {
			return user.getDefaultPerspective();
		}
		return "";
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see
	 * org.eclipse.osbp.ui.api.useraccess.IUserAccessService#getExtraPassword()
	 */
	@Override
	public String getExtraPassword() {
		UserAccountDto user = getUser();
		if (user != null) {
			return user.getExtraPassword();
		}
		return "";
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see
	 * org.eclipse.osbp.ui.api.useraccess.IUserAccessService#getExtraPassword()
	 */
	@Override
	public boolean isPasswordReset() {
		UserAccountDto user = getUser();
		if (user != null) {
			return user.getPasswordReset();
		}
		return false;
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see org.eclipse.osbp.ui.api.useraccess.IUserAccessService#getRoles()
	 */
	@SuppressWarnings("unchecked")
	@Override
	public Collection<String> getRoles() {
		return (Collection<String>) getSessionAttribute(ROLES_KEY);
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see
	 * org.eclipse.osbp.ui.api.useraccess.IUserAccessService#getPermissions()
	 */
	@Override
	public AbstractAuthorization getAuthorization() {
		return (AbstractAuthorization) getSessionAttribute(AUTHORIZATION_KEY);
	}

	@Override
	public boolean isGranted(Group group, Action action, String objectDescriptor) {
		if (getAuthorization() == null) { // administrator
			return true;
		}
		return getAuthorization().isApplicableGrant(group, action, objectDescriptor);
	}

	@Override
	public boolean isVetoed(Group group, Action action, String objectDescriptor, String propertyDescriptor) {
		if (getAuthorization() == null) { // administrator
			return false;
		}
		return getAuthorization().isApplicableVeto(group, action, objectDescriptor, propertyDescriptor);
	}

	/**
	 * Gets the organization service.
	 *
	 * @return the organization service
	 */
	public final IOrganizationService getOrganizationService() {
		if (UserAccessService.sOrganizationServices.size() == 1) {
			return UserAccessService.sOrganizationServices.entrySet().iterator().next().getValue();
		}
		return null;
	}

	/**
	 * Gets the authentication realm.
	 *
	 * @return the authentication realm
	 */
	private AuthenticatingRealm getAuthenticationRealm() {
		return (AuthenticatingRealm) getSessionAttribute(AUTHENTICATED_BY_REALM);
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see org.eclipse.osbp.ui.api.useraccess.IUserAccessService#getAllUsers()
	 */
	@Override
	public Set<String> getAllUsers() {
		AuthenticatingRealm realm = getAuthenticationRealm();
		if (realm instanceof UserAccessAuthorizationRealm) {
			return ((UserAccessAuthorizationRealm) realm).getAllUsers();
		}
		return Collections.emptySet();
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see org.eclipse.osbp.ui.api.useraccess.IUserAccessService#
	 * getAllUsersPositions ()
	 */
	@Override
	public Map<String, String> getAllUsersPositions() {
		AuthenticatingRealm realm = getAuthenticationRealm();
		if (realm instanceof UserAccessAuthorizationRealm) {
			return ((UserAccessAuthorizationRealm) realm).getAllUsersPositions();
		}
		return Collections.emptyMap();
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see org.eclipse.osbp.ui.api.useraccess.IUserAccessService#getAllEmails()
	 */
	@Override
	public Set<String> getAllEmails() {
		AuthenticatingRealm realm = getAuthenticationRealm();
		if (realm instanceof UserAccessAuthorizationRealm) {
			return ((UserAccessAuthorizationRealm) realm).getAllEmails();
		}
		return Collections.emptySet();
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see org.eclipse.osbp.ui.api.useraccess.IUserAccessService#
	 * findUsersForPosition (java.lang.String)
	 */
	@Override
	public Set<String> findUsersForPosition(String position) {
		AuthenticatingRealm realm = getAuthenticationRealm();
		if (realm instanceof UserAccessAuthorizationRealm) {
			return ((UserAccessAuthorizationRealm) realm).findUsersForPosition(position);
		}
		return Collections.emptySet();
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see
	 * org.eclipse.osbp.ui.api.useraccess.IUserAccessService#getAllPositions()
	 */
	@Override
	public Set<AbstractPosition> getAllPositions() {
		AuthenticatingRealm realm = getAuthenticationRealm();
		if (realm instanceof UserAccessAuthorizationRealm) {
			Set<AbstractPosition> retcode = new HashSet<>();
			for (Entry<String, IOrganizationService> entrySet : UserAccessService.sOrganizationServices.entrySet()) {
				String organizationID = ProductConfiguration.getAuthenticationOrganizationId();
				ISubOrganization organization = entrySet.getValue().getOrganization(organizationID);
				if (organization != null) {
					for (IPosition position : organization.getPositions()) {
						retcode.add((AbstractPosition) position);
					}
				}
			}
			if (retcode.isEmpty()) {
				retcode = null;
			}
			return retcode;
		}
		return Collections.emptySet();
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see
	 * org.eclipse.osbp.ui.api.useraccess.IUserAccessService#findPositionForUser
	 * (java.lang.String)
	 */
	@Override
	public AbstractPosition findPositionForUser(String username) {
		AuthenticatingRealm realm = getAuthenticationRealm();
		if (realm instanceof UserAccessAuthorizationRealm) {
			return ((UserAccessAuthorizationRealm) realm).findPositionForUser(username);
		}
		return null;
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see org.eclipse.osbp.ui.api.useraccess.IUserAccessService#
	 * findPositionForPositionName(java.lang.String)
	 */
	@Override
	public AbstractPosition findPositionForPositionName(String positionName) {
		AuthenticatingRealm realm = getAuthenticationRealm();
		if (realm instanceof UserAccessAuthorizationRealm) {
			return ((UserAccessAuthorizationRealm) realm).findPositionForPositionName(positionName);
		}
		return null;
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see
	 * org.eclipse.osbp.ui.api.useraccess.IUserAccessService#findRolesForUser
	 * (java.lang.String)
	 */
	@Override
	public Collection<String> findRolesForUser(String username) {
		AuthenticatingRealm realm = getAuthenticationRealm();
		if (realm instanceof UserAccessAuthorizationRealm) {
			return ((UserAccessAuthorizationRealm) realm).findRolesForUser(username);
		}
		return Collections.emptyList();
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see org.eclipse.osbp.ui.api.useraccess.IUserAccessService#
	 * findPermissionsForUser (java.lang.String)
	 */
	@Override
	public AbstractAuthorization findPermissionsForUser(String username) {
		AuthenticatingRealm realm = getAuthenticationRealm();
		if (realm instanceof UserAccessAuthorizationRealm) {
			return ((UserAccessAuthorizationRealm) realm).findPermissionsForUser(username);
		}
		return null;
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see
	 * org.eclipse.osbp.ui.api.useraccess.IUserAccessService#getUserFilterMap()
	 */
	@Override
	public UserFilterMap getUserFilterMap() {
		UserFilterMap userFilterMap = (UserFilterMap) getSessionAttribute(USER_FILTER_MAP_KEY);
		if (userFilterMap == null) {
			LOGGER.error("Authentication getUserFilterMap returned null");
		}
		return userFilterMap;
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see org.eclipse.osbp.ui.api.useraccess.IUserAccessService#
	 * checkUsernameUniqueness (java.lang.String)
	 */
	@Override
	public boolean checkLoggedInUsernameExists(String username) {
		AuthenticatingRealm realm = getAuthenticationRealm();
		if (realm instanceof UserAccessAuthorizationRealm) {
			return ((UserAccessAuthorizationRealm) realm).checkUsernameExists(username);
		}
		return false;
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see org.eclipse.osbp.ui.api.useraccess.IUserAccessService#
	 * checkUsernameUniqueness (java.lang.String)
	 */
	@Override
	public boolean checkNotLoggedInUsernameExists(String username) {
		UserAccountDto userAccount = findUserAccount(username);
		return (userAccount != null);
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see org.eclipse.osbp.ui.api.useraccess.IUserAccessService#
	 * checkEmailUniqueness (java.lang.String)
	 */
	@Override
	public boolean checkEmailExists(String email) {
		AuthenticatingRealm realm = getAuthenticationRealm();
		if (realm instanceof UserAccessAuthorizationRealm) {
			return ((UserAccessAuthorizationRealm) realm).checkEmailExists(email);
		}
		return false;
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see org.eclipse.osbp.ui.api.useraccess.IUserAccessService#
	 * getAllUserAccountRoles ()
	 */
	@Override
	public Map<String, Collection<String>> getAllUserAccountRoles() { // NOSONAR
		Map<String, Collection<String>> userRolesMap = new HashMap<>();
		List<String> adminRoles = new ArrayList<>();
		Query query = new Query();
		int size = UserProtocol.getDtoUserAccountDtoService().size(query);
		Collection<UserAccountDto> users = UserProtocol.getDtoUserAccountDtoService().getByIndex(0, size, query);
		for (UserAccountDto user : users) {
			if (user.getUserName() != null && user.getPosition() != null) {
				boolean needsDefault = true;
				for (Entry<String, IOrganizationService> entrySet : UserAccessService.sOrganizationServices.entrySet()) {
					// as positions in organigram are not allowed to have spaces

					String organizationID = ProductConfiguration.getAuthenticationOrganizationId();
					ISubOrganization organization = entrySet.getValue().getOrganization(organizationID);
					if (organization != null) {
						IPosition position = organization.getPositionByLinkAlias(user.getPosition());
						if (position != null && position instanceof AbstractPosition) {
							userRolesMap.put(user.getUserName(), ((AbstractPosition) position).getRoles());
							needsDefault = false;
						}
					}
				}
				if (needsDefault) {
					List<String> userRoles = new ArrayList<>();
					userRoles.add(IUserAccessService.DEFAULTUSERROLE);
					userRolesMap.put(user.getUserName(), userRoles);
				}
			}
		}
		// finally, add the admin and assign all roles
		for (Entry<String, IOrganizationService> entrySet : UserAccessService.sOrganizationServices.entrySet()) {
			adminRoles.addAll(entrySet.getValue().getRoles());
		}
		// if the organizations provide no roles
		if (adminRoles.isEmpty()) {
			adminRoles.add(IUserAccessService.DEFAULTUSERROLE);
			adminRoles.add(IUserAccessService.DEFAULTADMINROLE);
		}
		userRolesMap.put(IUserAccessService.ADMINISTRATOR, adminRoles);
		return userRolesMap;
	}

	/**
	 * Helper Method that converts the user account filter strings into a map.
	 *
	 * @param user
	 *            the user
	 * @return the filter map
	 */
	private UserFilterMap createFilterMap(UserAccountDto user) {
		UserFilterMap filterMap = new UserFilterMap();
		for (UserAccountFilterDto filter : user.getUserAccountFilter()) {
			String[] splitFilter = filter.getFilter().split(":");
			if (filter.getInvers()) {
				List<String> notFilterValueList = filterMap.getNotFilterMap().get(splitFilter[0]);
				notFilterValueList = ((notFilterValueList != null) ? notFilterValueList : new ArrayList<>());
				notFilterValueList.add(splitFilter[1]);
				filterMap.getNotFilterMap().put(splitFilter[0], notFilterValueList);
			} else {
				List<String> inFilterValueList = filterMap.getInFilterMap().get(splitFilter[0]);
				inFilterValueList = ((inFilterValueList != null) ? inFilterValueList : new ArrayList<>());
				inFilterValueList.add(splitFilter[1]);
				filterMap.getInFilterMap().put(splitFilter[0], inFilterValueList);
			}
		}
		return filterMap;
	}

	/**
	 * Bind persistence service.
	 *
	 * @param persistenceService
	 *            the persistence service
	 */
	@Reference(cardinality = ReferenceCardinality.MANDATORY, policy = ReferencePolicy.STATIC)
	public synchronized void bindPersistenceService(final IPersistenceService persistenceService) {
		UserProtocol.persistenceService = persistenceService;
		LOGGER.debug("UserProtocolPersistenceService bound");
	}

	/**
	 * Unbind persistence service.
	 *
	 * @param persistenceService
	 *            the persistence service
	 */
	public synchronized void unbindPersistenceService(final IPersistenceService persistenceService) { // NOSONAR
		UserProtocol.persistenceService = null;
		LOGGER.debug("UserProtocolPersistenceService unbound");
	}

	/**
	 * Bind organization service.
	 *
	 * @param organization
	 *            the organization
	 */
	@Reference(cardinality = ReferenceCardinality.OPTIONAL, policy = ReferencePolicy.DYNAMIC)
	public void bindOrganizationService(IOrganizationService organization) {
		LOGGER.debug(UserAccessService.class.getCanonicalName() + ": " + organization.getClass().getCanonicalName() + " bound");
		sOrganizationServices.put(organization.getClass().getCanonicalName(), organization);
		triggerComplexDataContainerChangedListeners();
	}

	/**
	 * Unbind organization service.
	 *
	 * @param organization
	 *            the organization
	 */
	public void unbindOrganizationService(IOrganizationService organization) {
		LOGGER.debug(UserAccessService.class.getCanonicalName() + ": " + organization.getClass().getCanonicalName() + " unbound");
		sOrganizationServices.remove(organization.getClass().getCanonicalName());
		triggerComplexDataContainerChangedListeners();
	}

	public void addComplexDataContainerChangedListener(IComplexDataContainerChangedListener listener) {
		complexDataContainerChangedListeners.add(listener); 
	}

	public void removeComplexDataContainerChangedListener(IComplexDataContainerChangedListener listener) {
		complexDataContainerChangedListeners.remove(listener);
	}

	public static void triggerComplexDataContainerChangedListeners() {
		for	(IComplexDataContainerChangedListener listener : complexDataContainerChangedListeners) {
			listener.complexDataContainerChanged();
		}
	}
	
}
