spring-remoting入门(http-invoker,hessian,burlap)

这里简单介绍一下sping remoting的三种实现,http-invoker,hessian,burlap,spring对hessian,burlap做好很好的封装,很容易使用,下面介绍一下他们的配置

一、服务器端配置(applicationContext.xml):

<pre name="code" class="html"><?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
	xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
	xmlns:p="http://www.springframework.org/schema/p"
	xmlns:mvc="http://www.springframework.org/schema/mvc"
	xmlns:context="http://www.springframework.org/schema/context"
	
	xsi:schemaLocation="
		http://www.springframework.org/schema/beans
		http://www.springframework.org/schema/beans/spring-beans.xsd
		http://www.springframework.org/schema/mvc
		http://www.springframework.org/schema/mvc/spring-mvc.xsd
		http://www.springframework.org/schema/context
		http://www.springframework.org/schema/context/spring-context.xsd">
		
	<context:component-scan base-package="com.plateno.service" />
	
	<bean id="beanNameUrlHandlerMapping" class="org.springframework.web.servlet.handler.BeanNameUrlHandlerMapping"/>
	<!-- 类似rmi方式,采用java序列化,数据量较大 -->
	<bean name="/httpInvokerService" class="org.springframework.remoting.httpinvoker.HttpInvokerServiceExporter">
		<property name="service" ref="remoteService"/>
		<property name="serviceInterface" value="com.plateno.platform.service.RemoteService"/>
	</bean>
	<!-- 采用hessian序列化,数据量最小 -->
	<bean name="/hessianService" class="org.springframework.remoting.caucho.HessianServiceExporter">
		<property name="service" ref="remoteService"/>
		<property name="serviceInterface" value="com.plateno.platform.service.RemoteService"/>
	</bean> 
	<!-- xml传输数据,数据量比httpinvoker方式小 -->
	<bean name="/burlapService" class="org.springframework.remoting.caucho.BurlapServiceExporter">
		<property name="service" ref="remoteService"/>
		<property name="serviceInterface" value="com.plateno.platform.service.RemoteService"/>
	</bean>  
	
	<mvc:interceptors>
		<mvc:interceptor>
			<mvc:mapping path="/**"/>
			<bean class="com.plateno.interceptor.CommonInterceptor"/>
		</mvc:interceptor>
	</mvc:interceptors>
	
</beans>


 二、服务器端配置(web.xml) 
<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
	xmlns="http://java.sun.com/xml/ns/javaee"
	xmlns:web="http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd"
	xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd"
	id="WebApp_ID" version="2.5">
	
	<context-param>
		<param-name>contextConfigLocation</param-name>
		<param-value>classpath:applicationContext.xml</param-value>
	</context-param>
	<listener>
		<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
	</listener>
	
	<servlet>
		<servlet-name>springmvc</servlet-name>
		<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
		<init-param>
			<param-name>contextConfigLocation</param-name>
			<param-value>classpath:spring-mvc.xml</param-value>
		</init-param>
	</servlet>
	
	<servlet-mapping>
		<servlet-name>springmvc</servlet-name>
		<url-pattern>/</url-pattern>
	</servlet-mapping>
	
</web-app>
三、写一个service,再写一个serviceImpl就ok了。


四、客户端配置:

<pre name="code" class="html"><bean id="httpInvokerProxyFactoryBean" class="org.springframework.remoting.httpinvoker.HttpInvokerProxyFactoryBean">
		<property name="serviceUrl" value="http://localhost:9999/server/httpInvokerService"/>
		<property name="serviceInterface" value="com.plateno.platform.service.RemoteService"/>
	</bean> 
	
	<bean id="hessianProxyFactoryBean" class="org.springframework.remoting.caucho.HessianProxyFactoryBean">
		<property name="serviceUrl" value="http://localhost:9999/server/hessianService"/>
		<property name="serviceInterface" value="com.plateno.platform.service.RemoteService"/>
	</bean>
	
	<bean id="burlapProxyFactoryBean" class="org.springframework.remoting.caucho.BurlapProxyFactoryBean">
		<property name="serviceUrl" value="http://localhost:9999/server/burlapService"/>
		<property name="serviceInterface" value="com.plateno.platform.service.RemoteService"/>
	</bean>


 五、测试类: 

@Autowired
	private RemoteService remoteService;
	@RequestMapping(value="/test")
	public ModelAndView test(@RequestParam(value="name", required=false) String name) {
		UserDTO dto = remoteService.getUser("hello");
		System.out.println(dto);
		Map<String, Object> model = new HashMap<String, Object>();
		return new ModelAndView("test/hello", model);
	}


加载@@@@@@@@

如果按照上面的方式,每发布一个接口,就得往xml文件写配置,很麻烦,下面来介绍工程自动发布接口,程序员像在一个工程写代码一个,写接口,写实现,客户端调用就ok了

1、给定包名,扫描包名下面的类(接口)参照spring实现:

package com.plateno.util;

import java.util.ArrayList;
import java.util.List;

import org.springframework.context.annotation.ClassPathScanningCandidateComponentProvider;
import org.springframework.core.io.Resource;
import org.springframework.core.io.support.PathMatchingResourcePatternResolver;
import org.springframework.core.io.support.ResourcePatternResolver;
import org.springframework.core.type.ClassMetadata;
import org.springframework.core.type.classreading.CachingMetadataReaderFactory;
import org.springframework.core.type.classreading.MetadataReader;
import org.springframework.core.type.classreading.MetadataReaderFactory;


public class ClassPathScanning extends ClassPathScanningCandidateComponentProvider {

	private List<String> classNameSet = new ArrayList<String>(20);
	private List<Class<?>> clzSet = new ArrayList<Class<?>>(20);
	public ClassPathScanning(boolean useDefaultFilters) {
		super(useDefaultFilters);
	}
	static final String DEFAULT_RESOURCE_PATTERN = "**/*.class";
	private String resourcePattern = DEFAULT_RESOURCE_PATTERN;
	private ResourcePatternResolver resourcePatternResolver = new PathMatchingResourcePatternResolver();
	private MetadataReaderFactory metadataReaderFactory = new CachingMetadataReaderFactory(this.resourcePatternResolver);
	
	public void getClassFromPackage(String basePackage) {
		try {
			String packageSearchPath = ResourcePatternResolver.CLASSPATH_ALL_URL_PREFIX +
					resolveBasePackage(basePackage) + "/" + this.resourcePattern;
			Resource[] resources = this.resourcePatternResolver.getResources(packageSearchPath);
			for(Resource r : resources) {
				if(r.isReadable()) {
					MetadataReader metadataReader = this.metadataReaderFactory.getMetadataReader(r);
					ClassMetadata classMetadata = metadataReader.getClassMetadata();
					if(!classMetadata.isIndependent()) {
						continue;
					}
					String className = classMetadata.getClassName();
					int index = className.lastIndexOf(".");
					if(index > 0) {
						String name = className.substring(index+1);
						name = name.substring(0, 1).toLowerCase() + name.substring(1);
						classNameSet.add(name);
						clzSet.add(Class.forName(className));
					}
				}
			}
		} catch(Exception e) {
			e.printStackTrace();
		}
	}

	public List<String> getClassNameSet() {
		return classNameSet;
	}

	public List<Class<?>> getClzSet() {
		return clzSet;
	}
	
}

2、服务端发布接口:

package com.plateno.util;

import java.util.List;

import org.springframework.beans.BeansException;
import org.springframework.beans.factory.BeanNameAware;
import org.springframework.beans.factory.InitializingBean;
import org.springframework.beans.factory.config.BeanFactoryPostProcessor;
import org.springframework.beans.factory.config.ConfigurableListableBeanFactory;
import org.springframework.context.ApplicationContext;
import org.springframework.context.ApplicationContextAware;
import org.springframework.remoting.caucho.BurlapServiceExporter;
import org.springframework.remoting.caucho.HessianServiceExporter;
import org.springframework.remoting.httpinvoker.HttpInvokerServiceExporter;

public class BeanFactoryProxyServer implements BeanFactoryPostProcessor,ApplicationContextAware {

	private ApplicationContext applicationContext;
	private ConfigurableListableBeanFactory beanFactory;
	private String basePackage = "com.plateno.platform.service";
	@Override
	public void postProcessBeanFactory(
			ConfigurableListableBeanFactory beanFactory) throws BeansException {
		this.beanFactory = beanFactory;
//		httpInvoker();
//		hessian();
		burlap();
	}
	
	private void httpInvoker() {
		ClassPathScanning scann = new ClassPathScanning(true);
		scann.getClassFromPackage(basePackage);
		List<String> classNameSet = scann.getClassNameSet();
		List<Class<?>> clzSet = scann.getClzSet();
		for(int i=0; i<classNameSet.size(); i++) {
			Class<?> clz = clzSet.get(i);
			String className = classNameSet.get(i);
			HttpInvokerServiceExporter exporter = new HttpInvokerServiceExporter();
			exporter.setService(this.applicationContext.getBean(className));
			exporter.setServiceInterface(clz);
			exporter.afterPropertiesSet();
			beanFactory.registerSingleton("/" + className, exporter);
		}
		
	}
	private void hessian() {
		ClassPathScanning scann = new ClassPathScanning(true);
		scann.getClassFromPackage(basePackage);
		List<String> classNameSet = scann.getClassNameSet();
		List<Class<?>> clzSet = scann.getClzSet();
		for(int i=0; i<classNameSet.size(); i++) {
			Class<?> clz = clzSet.get(i);
			String className = classNameSet.get(i);
			HessianServiceExporter exporter = new HessianServiceExporter();
			exporter.setService(this.applicationContext.getBean(className));
			exporter.setServiceInterface(clz);
			exporter.afterPropertiesSet();
			beanFactory.registerSingleton("/" + className, exporter);
		}
	}
	private void burlap() {
		ClassPathScanning scann = new ClassPathScanning(true);
		scann.getClassFromPackage(basePackage);
		List<String> classNameSet = scann.getClassNameSet();
		List<Class<?>> clzSet = scann.getClzSet();
		for(int i=0; i<classNameSet.size(); i++) {
			Class<?> clz = clzSet.get(i);
			String className = classNameSet.get(i);
			BurlapServiceExporter exporter = new BurlapServiceExporter();
			exporter.setService(this.applicationContext.getBean(className));
			exporter.setServiceInterface(clz);
			exporter.afterPropertiesSet();
			beanFactory.registerSingleton("/" + className, exporter);
		}
	}

	@Override
	public void setApplicationContext(ApplicationContext applicationContext)
			throws BeansException {
		this.applicationContext = applicationContext;
		
	}
}

3、客户端配置:

package com.plateno.util;

import java.util.List;

import org.springframework.beans.BeansException;
import org.springframework.beans.factory.config.BeanFactoryPostProcessor;
import org.springframework.beans.factory.config.ConfigurableListableBeanFactory;
import org.springframework.remoting.caucho.BurlapProxyFactoryBean;
import org.springframework.remoting.caucho.HessianProxyFactoryBean;
import org.springframework.remoting.httpinvoker.HttpInvokerProxyFactoryBean;

public class BeanFactoryProxyClient implements BeanFactoryPostProcessor {

	private ConfigurableListableBeanFactory beanFactory;
	private String basePackage = "com.plateno.platform.service";
	private String baseUrl = "http://localhost:9999/server/";
	@Override
	public void postProcessBeanFactory(
			ConfigurableListableBeanFactory beanFactory) throws BeansException {
		this.beanFactory = beanFactory;
//		httpInvoker();
//		hessian();
		burlap();
	}
	private void httpInvoker() {
		ClassPathScanning scann = new ClassPathScanning(true);
		scann.getClassFromPackage(basePackage);
		List<String> classNameSet = scann.getClassNameSet();
		List<Class<?>> clzSet = scann.getClzSet();
		for(int i=0; i<classNameSet.size(); i++) {
			Class<?> clz = clzSet.get(i);
			String className = classNameSet.get(i);
			HttpInvokerProxyFactoryBean factoryBean = new HttpInvokerProxyFactoryBean();
			factoryBean.setServiceInterface(clz);
			factoryBean.setServiceUrl(baseUrl + className);
			factoryBean.afterPropertiesSet();
			beanFactory.registerSingleton(className, factoryBean.getObject());
		}
	}
	private void hessian() {
		ClassPathScanning scann = new ClassPathScanning(true);
		scann.getClassFromPackage(basePackage);
		List<String> classNameSet = scann.getClassNameSet();
		List<Class<?>> clzSet = scann.getClzSet();
		for(int i=0; i<classNameSet.size(); i++) {
			Class<?> clz = clzSet.get(i);
			String className = classNameSet.get(i);
			HessianProxyFactoryBean factoryBean = new HessianProxyFactoryBean();
			factoryBean.setServiceInterface(clz);
			factoryBean.setServiceUrl(baseUrl + className);
			factoryBean.afterPropertiesSet();
			beanFactory.registerSingleton(className, factoryBean.getObject());
		}
	}
	private void burlap() {
		ClassPathScanning scann = new ClassPathScanning(true);
		scann.getClassFromPackage(basePackage);
		List<String> classNameSet = scann.getClassNameSet();
		List<Class<?>> clzSet = scann.getClzSet();
		for(int i=0; i<classNameSet.size(); i++) {
			Class<?> clz = clzSet.get(i);
			String className = classNameSet.get(i);
			BurlapProxyFactoryBean factoryBean = new BurlapProxyFactoryBean();
			factoryBean.setServiceInterface(clz);
			factoryBean.setServiceUrl(baseUrl + className);
			factoryBean.afterPropertiesSet();
			beanFactory.registerSingleton(className, factoryBean.getObject());
		}
	}

}

4、把服务端跟客户端配置在spring配置文件,然后程序就能用了,简化了很多。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值