/* * Lokomo OneCMDB - An Open Source Software for Configuration * Management of Datacenter Resources * * Copyright (C) 2006 Lokomo Systems AB * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA * 02110-1301 USA. * * Lokomo Systems AB can be contacted via e-mail: info@lokomo.com or via * paper mail: Lokomo Systems AB, Sv�rdv�gen 27, SE-182 33 * Danderyd, Sweden. * */ package org.onecmdb.core.internal.session; import java.util.ArrayList; import java.util.Arrays; import java.util.GregorianCalendar; import java.util.HashSet; import java.util.List; import java.util.Set; import org.acegisecurity.Authentication; import org.acegisecurity.AuthenticationException; import org.acegisecurity.AuthenticationManager; import org.acegisecurity.GrantedAuthority; import org.acegisecurity.context.SecurityContextHolder; import org.acegisecurity.providers.UsernamePasswordAuthenticationToken; import org.acegisecurity.userdetails.UserDetails; import org.apache.commons.logging.Log; import org.apache.commons.logging.LogFactory; import org.onecmdb.core.IAttribute; import org.onecmdb.core.IAuthorizationService; import org.onecmdb.core.ICi; import org.onecmdb.core.IModelService; import org.onecmdb.core.IOneCmdbContext; import org.onecmdb.core.IService; import org.onecmdb.core.ISession; import org.onecmdb.core.IValue; import org.onecmdb.core.internal.UsernamePassword; import org.onecmdb.core.internal.authorization.RBACSession; import org.onecmdb.core.internal.model.Path; import org.onecmdb.core.internal.model.QueryCriteria; import org.onecmdb.core.internal.model.QueryResult; import org.springframework.beans.BeansException; import org.springframework.beans.factory.InitializingBean; import org.springframework.context.ApplicationContext; import org.springframework.context.ApplicationContextAware; /** * The session may be used from several threads. Make sure it is implemented * thereafter. * * <p>This implementation relies on IoC to call initialization and validation * methods.</p> * * @author nogun * */ public class Session implements ISession, ApplicationContextAware, InitializingBean { IOneCmdbContext onecmdb; private Log log = LogFactory.getLog(this.getClass()); // {{{ temporary holds authentication details UsernamePassword _creds = new UsernamePassword(); // }}} private Authentication _anonymousToken; private AuthenticationManager _manager; private ApplicationContext _appctx; final private GregorianCalendar _created = new GregorianCalendar(); // Should not store it here.... private Authentication authentication = null; private RBACSession rbacSession; public Session(String userId, IOneCmdbContext cmdb) { _creds.setUsername(userId); this.onecmdb = cmdb; } public Session(String userId, String password, IOneCmdbContext cmdb) { _creds.setUsername(userId); _creds.setPassword(password); this.onecmdb = cmdb; } /** perform validations */ public void afterPropertiesSet() throws Exception { if (_appctx == null) { throw new NullPointerException("No application context available"); } if (_manager == null) { _manager = (AuthenticationManager) _appctx.getBean("authenticationManager"); if (_manager == null) { throw new NullPointerException("Authentication manager not set"); } } if (_anonymousToken == null) { _anonymousToken = (Authentication) _appctx.getBean("anonymousToken"); if (_anonymousToken == null) { throw new NullPointerException("Anonymous token not available"); } } } public ISession newSession() { ISession session = this.onecmdb.createSession(); return(session); } public void init() { logout(); } public void setOneCmdb(IOneCmdbContext oneCmdb) { this.onecmdb = oneCmdb; } // }}} END IOC public IService getService(Class<? extends IService> type) { return onecmdb.getService(this, type); } public RBACSession getRBACSession() { return(rbacSession); } public UserDetails getPrincipal() { Object object = getAuthorization().getPrincipal(); if (object instanceof UserDetails) { return((UserDetails)object); } throw new IllegalAccessError("No UserDetails found!"); } private Authentication getAuthorization() { if (this.authentication != null) { return(this.authentication); } Authentication auth = SecurityContextHolder.getContext().getAuthentication(); return auth == null ? _anonymousToken : auth; } public boolean isAnonymous() { return getAuthorization().equals(_anonymousToken); } public void login() throws AuthenticationException { Authentication auth = new UsernamePasswordAuthenticationToken( _creds.getUsername(), _creds.getPassword()); try { auth = _manager.authenticate(auth); } catch (AuthenticationException ae) { log.info("Login FAILED for user<" + _creds.getUsername()); throw ae; } log.info("Login OK for user<" + _creds.getUsername() + ">"); // Should not be store here but need it..... this.authentication = auth; SecurityContextHolder.getContext().setAuthentication(auth); try { List<String> roleNames = new ArrayList<String>(); for (GrantedAuthority grantedAuth : getPrincipal().getAuthorities()) { String name = grantedAuth.getAuthority(); if (name != null) { log.info("<" + _creds.getUsername() + "> granted role " + name); if (!roleNames.contains(name)) { roleNames.add(name); } } } IAuthorizationService authService = (IAuthorizationService)getService(IAuthorizationService.class); if (authService != null) { rbacSession = authService.setupRBAC(this, roleNames); log.info("<" + _creds.getUsername() + ">"); log.info(rbacSession.toString()); /* System.out.println("<" + _creds.getUsername() + ">"); System.out.println(rbacSession.toString()); */ } } catch (Throwable t) { t.printStackTrace(); } } public void logout() { if (this.authentication != null) { log.info("Logout user<" + getUsername() +">"); } this.authentication = null; SecurityContextHolder.getContext().setAuthentication(_anonymousToken); } public Authentication getSubject() { return getAuthorization(); } public Set<GrantedAuthority> getRoles() { return new HashSet<GrantedAuthority>(Arrays.asList( getSubject().getAuthorities())); } public void setAuthenticationManager(AuthenticationManager manager) { _manager = manager; } public String getUsername() { if (isAnonymous()) { return _creds.getUsername(); } Object p = getSubject().getPrincipal(); if (p instanceof UserDetails ) { UserDetails u = (UserDetails) p; return u.getUsername(); } return null; } public void setApplicationContext(ApplicationContext applicationContext) throws BeansException { if (_appctx == null) { _appctx = applicationContext; } } public GregorianCalendar getDateCreated() { return _created; } public UsernamePassword getAuthentication() { return _creds; } }