(八)CXF添加自定義攔截器

前面咱們說到CXF添加內置的攔截器,今天的話,咱們來說下如何添加自定義攔截器;java

 

咱們的實例是客戶端訪問服務端webservice接口要加權限認證。web

 

咱們思路先說下。咱們能夠經過在SOAP消息的Header頭信息中添加自定義信息,而後發送到服務端端,服務器端經過獲取apache

Header頭消息,而後進行認證;這裏的添加消息,和獲取消息認證,咱們都是經過自定義攔截器來實現;服務器

 

OK下面咱們來實現下:app

 

首先是服務器端:frontend

 

 

咱們自定義攔截器:MyInterceptordom

package com.wishwzp.interceptor;

import java.util.List;

import org.apache.cxf.binding.soap.SoapMessage;
import org.apache.cxf.headers.Header;
import org.apache.cxf.interceptor.Fault;
import org.apache.cxf.phase.AbstractPhaseInterceptor;
import org.apache.cxf.phase.Phase;
import org.w3c.dom.Element;
import org.w3c.dom.NodeList;

/**
 * 自定義攔截器
 * @author Administrator
 *
 */
public class MyInterceptor extends AbstractPhaseInterceptor<SoapMessage> {

    public MyInterceptor() {
        // 在調用方法以前調用攔截器
        super(Phase.PRE_INVOKE);  
        
    }

    /**
     * 攔截獲取消息
     */
    @SuppressWarnings("null")
    public void handleMessage(SoapMessage message) throws Fault {
        List<Header> headers=message.getHeaders();
        if(headers==null && headers.size()==0){
            throw new Fault(new IllegalArgumentException("沒有Header,攔截器實施攔截"));
        }
        Header firstHeader=headers.get(0);
        Element ele=(Element) firstHeader.getObject();
        NodeList uList=ele.getElementsByTagName("userName");
        NodeList pList=ele.getElementsByTagName("password");
        if(uList.getLength()!=1){
            throw new Fault(new IllegalArgumentException("用戶名格式不對"));
        }
        if(pList.getLength()!=1){
            throw new Fault(new IllegalArgumentException("密碼格式不對"));
        }
        String userName=uList.item(0).getTextContent();
        String password=pList.item(0).getTextContent();
        
        if(!userName.equals("wishwzp")||!password.equals("123456")){
            throw new Fault(new IllegalArgumentException("用戶名或者密碼不正確"));
        }
    }

}

這裏的話,咱們主要是獲取Header頭消息,而後獲取userName和password節點,而後獲取值,進行權限判斷,假如認證不經過,咱們拋出異常;測試

 

在Server類裏,咱們要添加一個in 攔截器,在進入的時候,咱們要進行驗證;this

 

package com.wishwzp.webservice;

import javax.xml.ws.Endpoint;

import org.apache.cxf.interceptor.LoggingInInterceptor;
import org.apache.cxf.interceptor.LoggingOutInterceptor;
import org.apache.cxf.jaxws.JaxWsServerFactoryBean;

import com.wishwzp.interceptor.MyInterceptor;
import com.wishwzp.webservice.impl.HelloWorldImpl;

public class Server {
 
    public static void main(String[] args) {
        System.out.println("web service start");  
        HelloWorld implementor = new HelloWorldImpl();  
        String address = "http://192.168.0.110/helloWorld";  
        //Endpoint.publish(address, implementor);  // JDK實現   暴露webservice接口
        JaxWsServerFactoryBean factoryBean = new JaxWsServerFactoryBean();
        factoryBean.setAddress(address); // 設置暴露地址
        factoryBean.setServiceClass(HelloWorld.class); // 接口類
        factoryBean.setServiceBean(implementor); // 設置實現類
        factoryBean.getInInterceptors().add(new LoggingInInterceptor()); // 添加in攔截器 日誌攔截器
        factoryBean.getOutInterceptors().add(new LoggingOutInterceptor()); // 添加out攔截器
        
        factoryBean.getInInterceptors().add(new MyInterceptor()); // 添加自定義攔截器
        
        factoryBean.create();
        System.out.println("web service started");  
    }
}

 

接下來是修改客戶端代碼:spa

 

咱們一樣要添加一個自定義攔截器:AddHeaderInterceptor

package com.wishwzp.interceptor;

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 AddHeaderInterceptor extends AbstractPhaseInterceptor<SoapMessage> {

    private String userName;
    private String password;
    
    public AddHeaderInterceptor(String userName,String password) {
        super(Phase.PREPARE_SEND); // 發送SOAP消息以前調用攔截器
        this.userName=userName;
        this.password=password;
    }

    public void handleMessage(SoapMessage message) throws Fault {
        List<Header> headerList=message.getHeaders();
        
        Document doc=DOMUtils.createDocument();
        Element ele=doc.createElement("authHeader");
        Element uElement=doc.createElement("userName");
        uElement.setTextContent(userName);
        Element pElement=doc.createElement("password");
        pElement.setTextContent(password);
        
        ele.appendChild(uElement);
        ele.appendChild(pElement);
        
        headerList.add(new Header(new QName("wishwzp"),ele));
        
    }
    
    

}

這裏的話,咱們主要是在攔截器裏建立頭消息;

 

Client類裏咱們要修改下,加下Out 攔截器:

package com.wishwzp.webservice;

import java.util.List;

import org.apache.cxf.frontend.ClientProxy;
import org.apache.cxf.interceptor.LoggingInInterceptor;
import org.apache.cxf.interceptor.LoggingOutInterceptor;

import com.wishwzp.interceptor.AddHeaderInterceptor;

public class Client {
    
    public static void main(String[] args) {
        HelloWorldService service=new HelloWorldService();
        HelloWorld helloWorld=service.getHelloWorldPort();
        
        org.apache.cxf.endpoint.Client client=ClientProxy.getClient(helloWorld);
        //client.getInInterceptors().add(new LoggingInInterceptor()); // 添加in攔截器 日誌攔截器
        
        client.getOutInterceptors().add(new AddHeaderInterceptor("wishwzp","123")); // 添加自定義攔截器
        
        client.getOutInterceptors().add(new LoggingOutInterceptor()); // 添加out攔截器
        
        //System.out.println(helloWorld.say("wishwzp測試"));
//        User user=new User();
//        user.setUserName("jack");
//        user.setPassword("123456");
//        List<Role> roleList=helloWorld.getRoleByUser(user);
//        for(Role role:roleList){
//            System.out.println(role.getId()+","+role.getRoleName());
//        }
        MyRoleArray array=helloWorld.getRoles();
        List<MyRole> roleList=array.item;
        for(int i=0;i<roleList.size();i++){
            MyRole my=roleList.get(i);
            System.out.print(my.key+":");
            for(Role r:my.value){
                System.out.print(r.getId()+","+r.getRoleName()+" ");
            }
            System.out.println();
        }
    }

}

OK這樣就完整了自定義攔截器實現權限認證;

 

先運行Server類,和之前同樣;

 

假如咱們把  client.getOutInterceptors().add(new AddHeaderInterceptor("wishwzp","123456")); // 添加自定義攔截器

密碼改爲 123 

 

而後運行Client類,會報錯;

 

用戶名或者密碼不正確;

相關文章
相關標籤/搜索