上篇写到用cfx自带的拦截器。这次我们用自定义的拦截器,以后工作中会经常用到
在服务器端自定义拦截器
发布:
package com.lzh.ws;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import javax.jws.WebService;
import org.apache.cxf.binding.soap.SoapMessage;
import org.apache.cxf.endpoint.Server;
import org.apache.cxf.interceptor.Interceptor;
import org.apache.cxf.interceptor.LoggingInInterceptor;
import org.apache.cxf.interceptor.LoggingOutInterceptor;
import org.apache.cxf.jaxws.JaxWsServerFactoryBean;
import org.apache.cxf.phase.AbstractPhaseInterceptor;
@WebService(endpointInterface="com.lzh.ws.WebServiceTest")
public class WebServiceTestImpl implements WebServiceTest {
private static HashMap<User, ArrayList> map;
private static User user;
private static ArrayList<Dog> list;
static{
user = new User(1,"刘中华");
Dog dog1=new Dog(001,"小狗",12);
Dog dog2=new Dog(002,"大狗",22);
list=new ArrayList<Dog>();
list.add(dog1);
list.add(dog2);
map=new HashMap<User, ArrayList>();
map.put(user, list);
}
public int add(int i, int j) {
// TODO Auto-generated method stub
return i+j;
}
public List<Dog> getDogByUser(User u) {
// TODO Auto-generated method stub
if(user.equals(u)){
ArrayList<Dog> list = map.get(u);
return list;
}
return null;
}
public static void main(String[] args) {
String url="http://localhost:9999/web";
// EndpointImpl endpointImpl = (EndpointImpl) Endpoint.publish(url, new WebServiceTestImpl());
/**
* 注意,一定要是JaxWsServerFactoryBean这个类,这个类是cfx的类,不能用Endpoint这个类,这个是java自带的。
* 给一个url和实体类.class 必须实体类的!!!!!!!
*
* */
JaxWsServerFactoryBean factory = new JaxWsServerFactoryBean();
factory.setAddress(url);
factory.setServiceClass(WebServiceTestImpl.class);
/**
* 添加拦截器,getInInterceptors()得到拦截器集合list。然后添加的是日志in 和 日志out
*/
/* factory.getInInterceptors().add(new LoggingInInterceptor());
factory.getOutInterceptors().add(new LoggingOutInterceptor());*/
/**
* 添加自定义拦截器 AuthInInterceptor类是自定义的,需要继承AbstractPhaseInterceptor<SoapMessage>类
*/
factory.getInInterceptors().add(new AuthInInterceptor());
/**
* 创建服务,启动
*/
Server server = factory.create();
server.start();
System.out.println("发布webservice成功!");
}
public HashMap<String, Dog> getDogMap() {
HashMap<String, Dog> map= new HashMap<String, Dog>();
int i=0;
for(Dog d:list){
map.put("第 "+ i++ +"条狗" + "",d);
}
return map;
}
}
AuthInInterceptor拦截器类 名字随便起
package com.lzh.ws;
import org.apache.cxf.binding.soap.SoapMessage;
import org.apache.cxf.interceptor.Fault;
import org.apache.cxf.phase.AbstractPhaseInterceptor;
import org.apache.cxf.phase.Phase;
public class AuthInInterceptor extends AbstractPhaseInterceptor<SoapMessage>{
public AuthInInterceptor() {
super(Phase.PRE_INVOKE); //调用之前拦截 SOAP信息
// TODO Auto-generated constructor stub
}
//SoapMessage 是SOAP消息,就是客户端访问服务端的时候的信息,我们要做的就是在访问服务器之前解析这个消息,看看有没有我们所需要的东西,比如账号,密码之类的。没有就不让访问。他是xml文件。带的信息是在heard里面,不是在body里面
public void handleMessage(SoapMessage msg) throws Fault {
// TODO Auto-generated method stub
//所携带的额外信息实在头部的,所以要得到headers,他是个list集合。如果没有就抛异常
List<Header> headers = msg.getHeaders();
if(headers==null||headers.size()<1){
throw new Fault(new Exception("没有header,调用不了"));
}
Header header = headers.get(0);
Element element = (Element) header.getObject();
NodeList userId = element.getElementsByTagName("userId");
NodeList userPass = element.getElementsByTagName("userPass");
if(userId.getLength() != 1){
throw new Fault(new Exception("用户格式不对"));
}
if(userPass.getLength() != 1){
throw new Fault(new Exception("密码格式不对"));
}
String u = userId.item(0).getTextContent();
String p = userPass.item(0).getTextContent();
if(u.equals("lzh") && p.equals("123")){
System.out.println("成功");
}else{
throw new Fault(new Exception("不对!!!!"));
}
}
}
客户端要也要添加自定义拦截器,添加头部信息
package com.lzh.ws.client;
import java.util.List;
import org.apache.cxf.frontend.ClientProxy;
import org.apache.cxf.interceptor.LoggingInInterceptor;
import org.apache.cxf.interceptor.LoggingOutInterceptor;
import com.lzh.ws.Dog;
import com.lzh.ws.Entry;
import com.lzh.ws.StringDog;
import com.lzh.ws.User;
import com.lzh.ws.WebServiceTest;
import com.lzh.ws.WebServiceTestImplService;
public class Client {
public static void main(String[] args) {
// TODO Auto-generated method stub
WebServiceTestImplService impl = new WebServiceTestImplService();
WebServiceTest implPort = impl.getWebServiceTestImplPort();
/**
* 添加日志拦截器 先创建一个代理类,是cfx的类,参数是上面的implPort(这个类是webService的远程代理),
*/
org.apache.cxf.endpoint.Client proxy = ClientProxy.getClient(implPort);
proxy.getOutInterceptors().add(new YanZhengInInterceptor("lzh","123"));
proxy.getOutInterceptors().add(new LoggingOutInterceptor());
int add = implPort.add(1, 2);
System.out.println(add);
User user = new User();
user.setId(1);
user.setName("刘中华");
List<Dog> list = implPort.getDogByUser(user);
for(Dog d:list){
System.out.println(d.getName());
}
System.out.println("-------------");
StringDog dogMap = implPort.getDogMap();
for(Entry e:dogMap.getList()){
System.out.println(e.getValue().getName());
}
}
}
客户端拦截器YanZhengInInterceptor
package com.lzh.ws.client;
import java.util.List;
import javax.xml.namespace.QName;
import org.apache.cxf.binding.soap.SoapMessage;
import org.apache.cxf.headers.Header;
import org.apache.cxf.helpers.DOMUtils;
import org.apache.cxf.interceptor.Fault;
import org.apache.cxf.phase.AbstractPhaseInterceptor;
import org.apache.cxf.phase.Phase;
import org.w3c.dom.Document;
import org.w3c.dom.Element;
public class YanZhengInInterceptor extends AbstractPhaseInterceptor<SoapMessage> {
private String username;
private String pass;
public YanZhengInInterceptor(String username,String pass) {
super(Phase.PREPARE_SEND); //在消息发送之前调用
this.username=username;
this.pass=pass;
}
public void handleMessage(SoapMessage msg) throws Fault {
// TODO Auto-generated method stub
List<Header> headers = msg.getHeaders();
/**
* 得到了soap对象就要把验证信息添加到头部。他是个xml片段。
*/
Document doc = DOMUtils.createDocument();
//创建头部
Element authHeader = doc.createElement("authHeader");
//创建username和userpass 并赋值 创建元素的名字要和服务器那边解析的要一致
Element userId = doc.createElement("userId");
userId.setTextContent(username);
Element userPass = doc.createElement("userPass");
userPass.setTextContent(pass);
//把创建的子元素添加到头部。
authHeader.appendChild(userPass);
authHeader.appendChild(userId);
//把创建的头部添加到头部
headers.add(new Header(new QName("刘中华"), authHeader));
/**
* 所得到的格式比如是:
* <soap:Envelope>
* <soap:Header>
* <authHeader>
* <userPass>1234</userPass>
* <userId>lzh</userId>
* </authHeader>
* </soap:Header>
* <soap:Body>
* <ns2:add xmlns:ns2="http://ws.lzh.com/">
* <arg0>1</arg0>
* <arg1>2</arg1>
* </ns2:add>
* </soap:Body>
* </soap:Envelope>
*/
}
}