org.apache.openejb.client.EJBHomeHandler Maven / Gradle / Ivy
The newest version!
/**
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership.
* The ASF licenses this file to You 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.apache.openejb.client;
import org.apache.openejb.client.proxy.ProxyManager;
import javax.ejb.EJBException;
import javax.ejb.EJBHome;
import javax.ejb.Handle;
import java.io.Externalizable;
import java.io.IOException;
import java.io.ObjectInput;
import java.io.ObjectOutput;
import java.lang.reflect.Method;
import java.rmi.RemoteException;
import java.util.concurrent.ThreadPoolExecutor;
@SuppressWarnings("NullArgumentToVariableArgMethod")
public abstract class EJBHomeHandler extends EJBInvocationHandler implements Externalizable {
private static final long serialVersionUID = 4212515330775330214L;
protected static final Method GETEJBMETADATA = getMethod(EJBHome.class, "getEJBMetaData", null);
protected static final Method GETHOMEHANDLE = getMethod(EJBHome.class, "getHomeHandle", null);
@SuppressWarnings("RedundantArrayCreation")
protected static final Method REMOVE_W_KEY = getMethod(EJBHome.class, "remove", new Class[]{Object.class});
@SuppressWarnings("RedundantArrayCreation")
protected static final Method REMOVE_W_HAND = getMethod(EJBHome.class, "remove", new Class[]{Handle.class});
protected static final Method GETHANDLER = getMethod(EJBHomeProxy.class, "getEJBHomeHandler", null);
protected ThreadPoolExecutor executor;
public EJBHomeHandler() {
}
public EJBHomeHandler(final ThreadPoolExecutor executor, final EJBMetaDataImpl ejb, final ServerMetaData server, final ClientMetaData client, final JNDIContext.AuthenticationInfo auth) {
super(ejb, server, client, auth);
this.executor = executor;
}
public static EJBHomeHandler createEJBHomeHandler(final ThreadPoolExecutor executor,
final EJBMetaDataImpl ejb,
final ServerMetaData server,
final ClientMetaData client,
final JNDIContext.AuthenticationInfo auth) {
switch (ejb.type) {
case EJBMetaDataImpl.BMP_ENTITY:
case EJBMetaDataImpl.CMP_ENTITY:
return new EntityEJBHomeHandler(executor, ejb, server, client, auth);
case EJBMetaDataImpl.STATEFUL:
return new StatefulEJBHomeHandler(executor, ejb, server, client, auth);
case EJBMetaDataImpl.STATELESS:
return new StatelessEJBHomeHandler(executor, ejb, server, client, auth);
case EJBMetaDataImpl.SINGLETON:
return new SingletonEJBHomeHandler(executor, ejb, server, client, auth);
}
throw new IllegalStateException("Uknown bean type code '" + ejb.type + "' : " + ejb.toString());
}
// protected abstract EJBObjectHandler newEJBObjectHandler();
public EJBHomeProxy createEJBHomeProxy() {
try {
// Interface class must be listed first otherwise the proxy code will select
// the openejb system class loader for proxy creation instead of the
// application class loader
final Class[] interfaces = new Class[]{ejb.homeClass, EJBHomeProxy.class};
return (EJBHomeProxy) ProxyManager.newProxyInstance(interfaces, this);
} catch (final IllegalAccessException e) {
throw new ClientRuntimeException("Unable to create proxy for " + ejb.homeClass, e);
}
}
@Override
protected Object _invoke(final Object proxy, final Method method, final Object[] args) throws Throwable {
final String methodName = method.getName();
try {
if (method.getDeclaringClass() == Object.class) {
if (method.equals(TOSTRING)) {
return "proxy=" + this;
} else if (method.equals(EQUALS)) {
return Boolean.FALSE;
} else if (method.equals(HASHCODE)) {
return this.hashCode();
} else {
throw new UnsupportedOperationException("Unkown method: " + method);
}
} else if (method.getDeclaringClass() == EJBHomeProxy.class) {
if (method.equals(GETHANDLER)) {
return this;
} else if (methodName.equals("writeReplace")) {
return new EJBHomeProxyHandle(this);
} else if (methodName.equals("readResolve")) {
throw new UnsupportedOperationException("Unkown method: " + method);
} else {
throw new UnsupportedOperationException("Unkown method: " + method);
}
}
/*-------------------------------------------------------*/
/*-- CREATE ------------- .create() ---*/
if (methodName.startsWith("create")) {
return create(method, args, proxy);
/*-- FIND X --------------- .find() ---*/
} else if (methodName.startsWith("find")) {
return findX(method, args, proxy);
/*-- GET EJB METADATA ------ EJBHome.getEJBMetaData() ---*/
} else if (method.equals(GETEJBMETADATA)) {
return getEJBMetaData(method, args, proxy);
/*-- GET HOME HANDLE -------- EJBHome.getHomeHandle() ---*/
} else if (method.equals(GETHOMEHANDLE)) {
return getHomeHandle(method, args, proxy);
/*-- REMOVE ------------------------ EJBHome.remove() ---*/
} else if (method.equals(REMOVE_W_HAND)) {
return removeWithHandle(method, args, proxy);
} else if (method.equals(REMOVE_W_KEY)) {
return removeByPrimaryKey(method, args, proxy);
/*-- UNKOWN ---------------------------------------------*/
} else {
return homeMethod(method, args, proxy);
}
} catch (final SystemException e) {
invalidateReference();
throw convertException(getCause(e), method);
/*
* Application exceptions must be reported dirctly to the client. They
* do not impact the viability of the proxy.
*/
} catch (final ApplicationException ae) {
throw convertException(getCause(ae), method);
/*
* A system exception would be highly unusual and would indicate a sever
* problem with the container system.
*/
} catch (final SystemError se) {
invalidateReference();
if (remote) {
throw new RemoteException("Container has suffered a SystemException", getCause(se));
} else {
throw new EJBException("Container has suffered a SystemException").initCause(getCause(se));
}
} catch (final Throwable oe) {
if (remote) {
throw new RemoteException("Unknown Client Exception", oe);
} else {
throw new EJBException("Unknown Client Exception").initCause(oe);
}
}
}
public Object homeMethod(final Method method, final Object[] args, final Object proxy) throws Throwable {
final EJBRequest req = new EJBRequest(RequestMethodCode.EJB_HOME_METHOD, ejb, method, args, null, client.getSerializer());
final EJBResponse res = request(req);
switch (res.getResponseCode()) {
case ResponseCodes.EJB_ERROR:
throw new SystemError((ThrowableArtifact) res.getResult());
case ResponseCodes.EJB_SYS_EXCEPTION:
throw new SystemException((ThrowableArtifact) res.getResult());
case ResponseCodes.EJB_APP_EXCEPTION:
throw new ApplicationException((ThrowableArtifact) res.getResult());
case ResponseCodes.EJB_OK:
return res.getResult();
default:
throw new RemoteException("Received invalid response code from server: " + res.getResponseCode());
}
}
/*-------------------------------------------------*/
/* Home interface methods */
/*-------------------------------------------------*/
protected Object create(final Method method, final Object[] args, final Object proxy) throws Throwable {
final EJBRequest req = new EJBRequest(RequestMethodCode.EJB_HOME_CREATE, ejb, method, args, null, client.getSerializer());
final EJBResponse res = request(req);
switch (res.getResponseCode()) {
case ResponseCodes.EJB_ERROR:
throw new SystemError((ThrowableArtifact) res.getResult());
case ResponseCodes.EJB_SYS_EXCEPTION:
throw new SystemException((ThrowableArtifact) res.getResult());
case ResponseCodes.EJB_APP_EXCEPTION:
throw new ApplicationException((ThrowableArtifact) res.getResult());
case ResponseCodes.EJB_OK:
final Object primKey = res.getResult();
final EJBObjectHandler handler = EJBObjectHandler.createEJBObjectHandler(executor, ejb, server, client, primKey, authenticationInfo);
handler.setEJBHomeProxy((EJBHomeProxy) proxy);
return handler.createEJBObjectProxy();
default:
throw new RemoteException("Received invalid response code from server: " + res.getResponseCode());
}
}
protected abstract Object findX(Method method, Object[] args, Object proxy) throws Throwable;
/*-------------------------------------------------*/
/* EJBHome methods */
/*-------------------------------------------------*/
protected Object getEJBMetaData(final Method method, final Object[] args, final Object proxy) throws Throwable {
return ejb;
}
protected Object getHomeHandle(final Method method, final Object[] args, final Object proxy) throws Throwable {
return new EJBHomeHandle((EJBHomeProxy) proxy);
}
protected abstract Object removeWithHandle(Method method, Object[] args, Object proxy) throws Throwable;
protected abstract Object removeByPrimaryKey(Method method, Object[] args, Object proxy) throws Throwable;
@Override
public void readExternal(final ObjectInput in) throws IOException, ClassNotFoundException {
}
@Override
public void writeExternal(final ObjectOutput out) throws IOException {
}
}
© 2015 - 2024 Weber Informatics LLC | Privacy Policy