package com.52jolynn;
import java.lang.reflect.Proxy;
import java.rmi.server.RemoteObjectInvocationHandler;
import org.springframework.beans.factory.BeanClassLoaderAware;
import org.springframework.beans.factory.FactoryBean;
import org.springframework.remoting.rmi.RmiClientInterceptor;
import org.springframework.remoting.rmi.RmiInvocationWrapper_Stub;
import org.springframework.util.ClassUtils;
import lombok.extern.slf4j.Slf4j;
import sun.rmi.server.UnicastRef;
import sun.rmi.transport.LiveRef;
import sun.rmi.transport.tcp.TCPEndpoint;
@Slf4j
public class RmiNatProxyFactoryBean extends RmiClientInterceptor implements FactoryBean<Object>, BeanClassLoaderAware {
private ClassLoader beanClassLoader = ClassUtils.getDefaultClassLoader();
private Object serviceProxy;
private String natHost;
public RmiNatProxyFactoryBean(String natHost) {
this.natHost = natHost;
}
public void setBeanClassLoader(ClassLoader classLoader) {
this.beanClassLoader = classLoader;
}
public void afterPropertiesSet() {
super.afterPropertiesSet();
if (this.getServiceInterface() == null) {
throw new IllegalArgumentException("Property 'serviceInterface' is required");
} else {
RmiInvocationWrapper_Stub stub = (RmiInvocationWrapper_Stub) getStub();
UnicastRef ref = (UnicastRef) stub.getRef();
LiveRef liveRef = ref.getLiveRef();
int port = liveRef.getPort();
log.debug("live ref port: {}, natHost: {}, natPort: {}", port, natHost, natPort);
Class[] interfaces = new Class[] { this.getServiceInterface() };
//取回来的stub要重新设置地址
RemoteObjectInvocationHandler nroih = new RemoteObjectInvocationHandler(
new UnicastRef(new LiveRef(liveRef.getObjID(), new TCPEndpoint(natHost, port), false)));
this.serviceProxy = Proxy.newProxyInstance(this.beanClassLoader, interfaces, nroih);
}
}
public Object getObject() {
return this.serviceProxy;
}
public Class getObjectType() {
return this.getServiceInterface();
}
public boolean isSingleton() {
return true;
}
}
10-08
4040