[jboss-user] [JCA/JBoss] - one data source with multiple database users

diemon do-not-reply at jboss.com
Mon May 19 05:53:33 EDT 2008


Hello
I have problem with configuring JBoss 4.2.1+Seam 2.0.1+Oracle 10 to use one data source with multiple users. I have configured *-ds.xml file with

  | <datasources>
  | <local-tx-datasource>
  |   <jndi-name>myDatasource</jndi-name>
  |     <connection-url>jdbc:oracle:thin:@server:1521:db</connection-url>
  |     <driver-class>oracle.jdbc.driver.OracleDriver</driver-class>
  |     <security-domain>MyRealm</security-domain>
  | </local-tx-datasource>
  | </datasources>
  | 
and added to login-config.xml:

  | <authentication>
  |   <login-module code = "my.login.module.MyLoginModule" flag = "required">
  |     <module-option name="sysUserName">user</module-option>
  |     <module-option name="sysPassword">pass</module-option>
  |     <module-option name="managedConnectionFactoryName">jboss.jca:service=LocalTxCM,name=myDatasource</module-option>
  |   </login-module>
  | </authentication>
  | 
my login module code is as follows:

  | import java.security.AccessController;
  | import java.security.Principal;
  | import java.security.PrivilegedAction;
  | import java.security.acl.Group;
  | import java.util.Map;
  | 
  | import javax.management.MBeanServer;
  | import javax.management.MBeanServerFactory;
  | import javax.management.MalformedObjectNameException;
  | import javax.management.ObjectName;
  | import javax.resource.spi.ManagedConnectionFactory;
  | import javax.resource.spi.security.PasswordCredential;
  | import javax.security.auth.Subject;
  | import javax.security.auth.callback.CallbackHandler;
  | import javax.security.auth.login.LoginException;
  | 
  | import org.jboss.mx.util.MBeanServerLocator;
  | import org.jboss.seam.security.Identity;
  | import org.jboss.security.SecurityAssociation;
  | import org.jboss.security.SimplePrincipal;
  | import org.jboss.security.auth.spi.AbstractServerLoginModule;
  | 
  | public class MyLoginModule extends AbstractServerLoginModule {
  | 
  | 	private static final org.apache.log4j.Logger log = org.apache.log4j.Logger
  | 			.getLogger(my.login.module.MyLoginModule.class);
  | 
  | 	/* used at jboss startup */
  | 	private static boolean sysMode = true;
  | 
  | 	private String sysUserName;
  | 	private String sysPassword;
  | 	private String userName;
  | 	private String password;
  | 
  | 	private MBeanServer server;
  | 	private ObjectName managedConnectionFactoryName;
  | 	private ManagedConnectionFactory mcf;
  | 
  | 	public SkorLoginModule() {}
  | 
  | 	@Override
  | 	public void initialize(Subject subject, CallbackHandler handler, Map sharedState, Map options) {
  | 
  | 		super.initialize(subject, callbackHandler, sharedState, options);
  | 
  | 		String name = (String) options.get("managedConnectionFactoryName");
  | 		try {
  | 			managedConnectionFactoryName = new ObjectName(name);
  | 		} catch (MalformedObjectNameException mone) {
  | 			throw new IllegalArgumentException("Malformed ObjectName: " + name);
  | 		}
  | 
  | 		sysUserName = (String)options.get("sysUserName");
  | 		if (sysUserName == null) {
  | 			throw new IllegalArgumentException("Must supply a system user name!");
  | 		}
  | 		userName = (String)options.get("sysUserName");
  | 
  | 		sysPassword = (String)options.get("sysPassword");
  | 		if (sysPassword == null) {
  | 			throw new IllegalArgumentException("Must supply a system user password!");
  | 		}
  | 		password = (String)options.get("sysPassword");
  | 
  | 		server = MBeanServerLocator.locateJBoss();
  | 		getMcf();
  | 	}
  | 
  | 	@Override
  | 	public boolean login() throws LoginException {
  | 
  | 		setUserNameAndPassword();
  | 		log.info("login(): userName=" + userName + ", sysMode=" + sysMode);
  | 
  | 		Principal principal = new SimplePrincipal(userName);
  | 
  | 		PasswordCredential credential = new 
  | 		PasswordCredential(userName, password.toCharArray());
  | 		credential.setManagedConnectionFactory(getMcf());
  | 
  | 		subject.getPrincipals().add(principal);
  | 		subject.getPrivateCredentials().add(credential);
  | 
  | 		super.loginOk = true;
  | 		return true;
  | 	}
  | 
  | 	protected ManagedConnectionFactory getMcf() {
  | 
  | 		if (mcf == null) {
  | 			try {
  | 				mcf = (ManagedConnectionFactory)server.getAttribute(managedConnectionFactoryName, "ManagedConnectionFactory");
  | 			} catch (Exception e) {
  | 				throw new IllegalArgumentException("Managed Connection Factory not found: " + managedConnectionFactoryName);
  | 			}
  | 		}
  | 		return mcf;
  | 	}
  | 
  | 	@Override
  | 	protected Principal getIdentity() {
  | 
  | 		setUserNameAndPassword();
  | 		log.info("getIdentity(): userName=" + userName + ", sysMode=" + sysMode);
  | 
  | 		return new SimplePrincipal(userName);
  | 	}
  | 
  | 	@Override
  | 	protected Group[] getRoleSets() throws LoginException {
  | 		return new Group[] {};
  | 	}
  | 
  | 	private void setUserNameAndPassword() {
  | 		if (sysMode) {
  | 			userName = sysUserName;
  | 			password = sysPassword;
  | 		} else {
  | 			String[] ss = Identity.instance().getUsername().split(" ");
  | 			String s = ss[0].substring(0, 1).toLowerCase();
  | 			s += ss[1].toLowerCase();
  | 			userName = s;
  | 			password = s;
  | 		}
  | 	}
  | }
  | 

The problem is that when I try to switch user with:

  | org.jboss.seam.security.Identity.instance().setUsername("User Name");
  | SkorLoginModule.setSysMode(false);
  | try {
  | 	LoginContext loginContext = new LoginContext("MyRealm");
  | 	loginContext.login();
  | } catch (LoginException e) {
  | 	System.out.println("error");
  | }
  | 
  | 
there aren't created any sub-pools for every user. There is one physical db connection. When I try to flush cache from JaasSecurityManager, the connection i reseted and previously logged in user is disconnected.
Another question is: when should I invoke loginContext.login() because now it's invoked in a stateless bean which authenticate method is configured in seam's compoments.xml file as:

  | <security:identity authenticate-method="#{authenticator.authenticate}"
  |                            security-rules="#{securityRules}"/>
  | 
I think the authenticate method should be invoked somewhere else - in authenticator bean the entity manager is already injected by @PersistenceContext annotation.

Thanks in advance for any help.

View the original post : http://www.jboss.com/index.html?module=bb&op=viewtopic&p=4151703#4151703

Reply to the post : http://www.jboss.com/index.html?module=bb&op=posting&mode=reply&p=4151703



More information about the jboss-user mailing list