blob: 5e2f0b5388dacd0f390f1f9e1201e5c8cdd142ed [file] [log] [blame]
package test.util;
import org.apache.yoko.orb.OBPortableServer.POAHelper;
import org.junit.Assert;
import org.omg.CORBA.BAD_PARAM;
import org.omg.CORBA.ORB;
import org.omg.CORBA.ORBPackage.InvalidName;
import org.omg.CORBA.SystemException;
import org.omg.CORBA.portable.InputStream;
import org.omg.CORBA.portable.OutputStream;
import org.omg.CORBA.portable.ResponseHandler;
import org.omg.CORBA.portable.UnknownException;
import org.omg.PortableServer.POA;
import org.omg.PortableServer.POAManagerPackage.AdapterInactive;
import org.omg.PortableServer.POAPackage.ObjectNotActive;
import org.omg.PortableServer.POAPackage.ServantAlreadyActive;
import org.omg.PortableServer.POAPackage.ServantNotActive;
import org.omg.PortableServer.POAPackage.WrongPolicy;
import org.omg.PortableServer.Servant;
import javax.rmi.CORBA.Tie;
import javax.rmi.CORBA.Util;
import javax.rmi.CORBA.ValueHandler;
import java.lang.reflect.Method;
import java.rmi.NoSuchObjectException;
import java.rmi.Remote;
import java.rmi.RemoteException;
import java.util.*;
public abstract class Skellington extends Servant implements Tie, Remote {
private final Collection<Class<? extends Remote>> interfaceClasses;
private final String[] ids;
public Skellington() {
Set<Class<? extends Remote>> ifaces = new HashSet<>();
for (Class<?> c = this.getClass(); c != Object.class; c = c.getSuperclass()) {
NEXT_CLASS: for (Class<?> iface: c.getInterfaces()) {
if (Remote.class.isAssignableFrom(iface)) {
for (Method m : iface.getMethods()) {
if (Arrays.asList(m.getExceptionTypes()).contains(RemoteException.class))
continue;
continue NEXT_CLASS;
}
// there were no non-remote methods, so add the interface
ifaces.add((Class<? extends Remote>)iface);
}
}
}
final ValueHandler vh = Util.createValueHandler();
this.interfaceClasses = Collections.unmodifiableSet(ifaces);
this.ids = new String[interfaceClasses.size()];
int index = 0;
for (Class<?> c : interfaceClasses)
this.ids[index++] = vh.getRMIRepositoryID(c);
}
public Skellington(Class<? extends Remote>... interfaces) {
final ValueHandler vh = Util.createValueHandler();
ids = new String[interfaces.length];
List<Class<? extends Remote>> iflst = new ArrayList<>();
for (int i = 0; i < interfaces.length; i++) {
Assert.assertTrue(interfaces[i].isInterface());
iflst.add(interfaces[i]);
ids[i] = vh.getRMIRepositoryID(interfaces[i]);
}
this.interfaceClasses = Collections.unmodifiableList(iflst);
}
@Override
public String[] _all_interfaces(POA poa, byte[] objectId) {
return ids.clone();
}
@Override
public org.omg.CORBA.Object thisObject() {
return _this_object();
}
@Override
public void deactivate() throws NoSuchObjectException {
try{
_poa().deactivate_object(_poa().servant_to_id(this));
} catch (WrongPolicy |ObjectNotActive |ServantNotActive ignored){}
}
@Override
public ORB orb() {return _orb();}
@Override
public void orb(ORB orb) {
try {
((org.omg.CORBA_2_3.ORB)orb).set_delegate(this);
} catch(ClassCastException e) {
throw new BAD_PARAM("POA Servant requires an instance of org.omg.CORBA_2_3.ORB");
}
}
@Override
public void setTarget(Remote target) {
throw new UnsupportedOperationException();
}
@Override
public Remote getTarget() {
return this;
}
@Override
public OutputStream _invoke(String method, InputStream _in, ResponseHandler reply) throws SystemException {
try {
return dispatch(method, (org.omg.CORBA_2_3.portable.InputStream) _in, reply);
} catch (SystemException ex) {
throw ex;
} catch (Throwable ex) {
throw new UnknownException(ex);
}
}
public String publish(ORB serverORB) throws InvalidName, AdapterInactive, ServantAlreadyActive, WrongPolicy {
POA rootPOA = POAHelper.narrow(serverORB.resolve_initial_references("RootPOA"));
rootPOA.the_POAManager().activate();
rootPOA.activate_object(this);
return serverORB.object_to_string(thisObject());
}
protected abstract OutputStream dispatch(String method, org.omg.CORBA_2_3.portable.InputStream in, ResponseHandler reply) throws RemoteException;
}