/* * JBoss, the OpenSource EJB server * * Distributable under LGPL license. * See terms of license at gnu.org. */ package org.jboss.ejb.plugins.jrmp.interfaces; import java.io.IOException; import java.io.ObjectOutput; import java.io.ObjectInput; import java.lang.reflect.Method; import java.rmi.MarshalledObject; import javax.naming.InitialContext; import javax.ejb.EJBObject; import javax.ejb.EJBHome; import javax.naming.Name; import org.jboss.ejb.plugins.jrmp.server.JRMPContainerInvoker; /** * An EJB stateful session bean proxy class. * * @author Rickard Öberg (rickard.oberg@telkel.com) * @author Marc Fleury * @author Jason Dillon <jason@planet57.com> * @version $Revision: 1.20 $ */ public class StatefulSessionProxy extends BeanProxy { // Constants ----------------------------------------------------- /** Serial Version Identifier. */ private static final long serialVersionUID = 1379411137308931705L; // Attributes ---------------------------------------------------- /** JBoss generated identifier. */ protected Object id; // Static -------------------------------------------------------- // Constructors -------------------------------------------------- /** * No-argument constructor for externalization. */ public StatefulSessionProxy() {} /** * Construct a StatefulSessionProxy. * * @param name The JNDI name of the container that we proxy for. * @param container The remote interface of the invoker for which * this is a proxy for. * @param id JBoss generated identifier. * @param optimize True if the proxy will attempt to optimize * VM-local calls. */ public StatefulSessionProxy(final String name, final ContainerRemote container, final Object id, final boolean optimize) { super(name, container, optimize); this.id = id; } // Public -------------------------------------------------------- /** * InvocationHandler implementation. * * @param proxy The proxy object. * @param m The method being invoked. * @param args The arguments for the method. * * @throws Throwable Any exception or error thrown while processing. */ public final Object invoke(final Object proxy, final Method m, Object[] args) throws Throwable { // Normalize args to always be an array // Isn't this a bug in the proxy call?? if (args == null) args = EMPTY_ARGS; // Implement local methods if (m.equals(TO_STRING)) { return name + ":" + id.toString(); } else if (m.equals(EQUALS)) { return invoke(proxy, IS_IDENTICAL, args); } else if (m.equals(HASH_CODE)) { return new Integer(id.hashCode()); } // Implement local EJB calls else if (m.equals(GET_HANDLE)) { return new StatefulHandleImpl(initialContextHandle, name, id); } else if (m.equals(GET_EJB_HOME)) { return getEJBHome(); } else if (m.equals(GET_PRIMARY_KEY)) { // MF FIXME // The spec says that SSB PrimaryKeys should not be returned and the call should throw an exception // However we need to expose the field *somehow* so we can check for "isIdentical" // For now we use a non-spec compliant implementation and just return the key as is // See jboss1.0 for the PKHolder and the hack to be spec-compliant and yet solve the problem // This should be the following call //throw new RemoteException("Session Beans do not expose their keys, RTFS"); // This is how it was solved in jboss1.0 // throw new PKHolder("RTFS", id); // This is non-spec compliant but will do for now return id; } else if (m.equals(IS_IDENTICAL)) { // MF FIXME // See above, this is not correct but works for now (do jboss1.0 PKHolder hack in here) return isIdentical(args[0], id); } // If not taken care of, go on and call the container else { return invokeContainer(id, m, args); } } // Package protected --------------------------------------------- // Protected ----------------------------------------------------- /** * Externalization support. * * @param out * * @throws IOException */ public void writeExternal(final ObjectOutput out) throws IOException { super.writeExternal(out); out.writeObject(id); } /** * Externalization support. * * @param in * * @throws IOException * @throws ClassNotFoundException */ public void readExternal(final ObjectInput in) throws IOException, ClassNotFoundException { super.readExternal(in); id = in.readObject(); } // Private ------------------------------------------------------- // Inner classes ------------------------------------------------- }