E81086713E446D36F62B2AA2A3502B5EB155

          Java雜家

          雜七雜八。。。一家之言

          BlogJava 首頁 新隨筆 聯系 聚合 管理
            40 Posts :: 1 Stories :: 174 Comments :: 0 Trackbacks

          考慮這樣一個使用場景,假如要查看所有進入weblogic上請求的(注意不是訪問某個特定web app的)一些請求頭是否設置,如果沒有設置則返回以定制的頁面.否則正常處理.
          這么一個簡單的需求在Tomcat下是很容易實現的,但是在weblogic下就比較奢侈了.
          你可能想到weblogic中:
          1)weblogic.security.net.ConnectionFilter
          但是在ConnectionFilter中得到的信息太少了,根本不能查看請求頭

          2)提供IdentityAsserter Provider,實現weblogic.security.spi.IdentityAsserter
          這個可以拿到看到你配置的特定的請求頭了,但是還是不能查看完整請求,也不能寫Response
          weblogic9.1好像提供weblogic.security.spi.IdentityAsserterV2,這個類的assertIdentity()方法有個ContextHandler類,通過它可以訪問到
          HttpServletRequest,HttpServletResponse了,但是為了啟用你的IdentityAsserter Provider,你必須在你要攔截的web應用中配置安全屬性(web.xml)并且還得auth-method為CLIENT-CERT模式.
          這種方式一般用來實現單點登陸.

          那么,難道還有別的方法?
          是的,下面介紹一種特別的方法(基于weblogic 7.1的,weblogic8.1也可以,但是要改動一點點)

          weblogic domain的配置文件config.xml在<domain>元素下有一個<StartupClass>元素,用于設置一個容器啟動類
            <StartupClass ClassName="com.yovn.labs.wls.startup.Startup"
                  FailureIsFatal
          ="true" LoadBeforeAppDeployments="true"
                  Name
          ="MyStartup Class" Targets="myserver"/>

          意義一目了然,就不多說了.

          那么,在com.yovn.labs.wls.startup.Startup中干什么呢?

          先通過weblogic.socket.JVMSocketManager.java來看看Weblogic是怎么管理Socket的
          package weblogic.socket;

          import weblogic.com.ProtocolHandlerDCOM;
          import weblogic.iiop.ProtocolHandlerIIOP;
          import weblogic.iiop.ProtocolHandlerIIOPS;
          import weblogic.ldap.ProtocolHandlerLDAP;
          import weblogic.rjvm.Protocol;
          import weblogic.rjvm.t3.ProtocolHandlerT3;
          import weblogic.rjvm.t3.ProtocolHandlerT3S;
          import weblogic.servlet.internal.ProtocolHandlerHTTP;
          import weblogic.servlet.internal.ProtocolHandlerHTTPS;
          import weblogic.utils.AssertionError;


          public final class JVMSocketManager
          {

              
          private static final boolean DEBUG = false;
              
          private static final ProtocolHandler discHandlers[];
              
          public static final int numDiscProtocols;
              
          private static final ProtocolHandler defHandlers[];
              
          public static final int numDefProtocols;

              
          public JVMSocketManager()
              {
              }

              
          static ProtocolHandler[] getDefaultProtocolHandlers()
              {
                  
          return defHandlers;
              }

              
          static ProtocolHandler[] getDiscriminatingProtocolHandlers()
              {
                  
          return discHandlers;
              }

              
          public static int[] makePortArray(int i, int j, int k, int l, int i1, int j1, int k1)
              {
                  
          int ai[] = new int[7];
                  ai[
          0= i;
                  ai[
          1= j;
                  ai[
          2= k;
                  ai[
          3= l;
                  ai[
          4= i1;
                  ai[
          5= j1;
                  ai[
          6= k1;
                  
          return ai;
              }

              
          static
              {
                  
          try
                  {
                      discHandlers 
          = (new ProtocolHandler[] {
                          ProtocolHandlerT3S.theHandler(), ProtocolHandlerT3.theHandler(), ProtocolHandlerIIOPS.theHandler(), ProtocolHandlerIIOP.theHandler(), ProtocolHandlerDCOM.theHandler(), ProtocolHandlerLDAP.theHandler()
                      });
                      numDiscProtocols 
          = discHandlers.length;
                      defHandlers 
          = (new ProtocolHandler[] {
                          ProtocolHandlerHTTPS.theHandler(), ProtocolHandlerHTTP.theHandler()
                      });
                      numDefProtocols 
          = defHandlers.length;
                  }
                  
          catch(Throwable throwable)
                  {
                      
          throw new AssertionError("Protocol registration failed", throwable);
                  }
              }
          }

          很顯然,它的protocol handler是通過一個final 數組來管理,加入我在Startup類里修改defHandlers里的第二個元素,那么處理HTTP請求的protocol handler就可以被換掉了
          來看我們的代碼:

          package com.yovn.labs.wls.startup;

          import java.lang.reflect.Field;

          import weblogic.socket.JVMSocketManager;
          import weblogic.socket.ProtocolHandler;

          import com.yovn.labs.wls.protocol.ProtocolHandlerHTTP;



          /**
           * 
          @author yovn
           *
           
          */
          public class Startup {

              
          /**
               * 
          @param args
               * 
          @throws NoSuchFieldException
               * 
          @throws SecurityException
               
          */
              
          public static void main(String[] args) throws Exception {
                  Field f
          =JVMSocketManager.class.getDeclaredField("defHandlers");
                  f.setAccessible(
          true);
                  ProtocolHandler[] handlers
          =(ProtocolHandler[])f.get(null);
                 
                  System.err.println(
          "[Startup]===================================================:Mystart up class!");
                  System.err.println(
          "[Startup]===================================================:default http handler is "+handlers[1]+"!");
                  handlers[
          1]=ProtocolHandlerHTTP.theHandler();
                  System.err.println(
          "[Startup]===================================================:now, http handler is "+handlers[1]+"!");

              }

          }


          好,現在HTTP Protocol Handler換成我們的 com.yovn.labs.wls.protocol.ProtocolHandlerHTTP類了
          接下來就看我們的handler代碼了
          package com.yovn.labs.wls.protocol;
          import java.io.IOException;
          import java.net.ProtocolException;
          import java.net.Socket;

          //import weblogic.protocol.configuration.NetworkChannel;//在weblogic8.1中
          import weblogic.rjvm.NetworkChannel;//在weblogic7.1中
          import weblogic.socket.MuxableSocket;
          import weblogic.socket.ProtocolHandler;
          import weblogic.utils.io.Chunk;



          public class ProtocolHandlerHTTP
              
          implements ProtocolHandler
          {

              
          private static ProtocolHandler theOne = null;
              
          protected static String PROTOCOL_NAME = "HTTP";
           

              
          public ProtocolHandlerHTTP()
              {
              }

              
          public static ProtocolHandler theHandler()
              {
                  
          if(theOne == null)
                      
          synchronized(ProtocolHandlerHTTP.class)
                      {
                          
          if(theOne == null)
                              theOne 
          = new ProtocolHandlerHTTP();
                      }
                  
          return theOne;
              }

             

              
          public int getHeaderLength()
              {
                  
          return 0;
              }

              
          public String getProtocolName()
              {
                  
          return PROTOCOL_NAME;
              }

              
          public boolean claimSocket(Chunk chunk, Socket socket)
                  
          throws IOException
              {
                  
          return true;
              }

              
          public boolean canReadHeaders(byte abyte0[], int i)
              {
                  
          return true;
              }

              
          public MuxableSocket createSocket(Chunk chunk, Socket socket, NetworkChannel networkchannel)
                  
          throws IOException
              {
                  
          if(!networkchannel.isProtocolEnabled(2&& !networkchannel.isDefaultChannel())
                  {
                      
          throw new ProtocolException("HTTP is disabled");
                  } 
          else
                  {
                      MuxableSocketHTTP muxablesockethttp 
          = new MuxableSocketHTTP(chunk, socket, networkchannel);
                      
          return muxablesockethttp;
                  }
              }

            

          }

          這段代碼在要求創建MuxableSocket時創建了一個com.yovn.labs.wls.protocol.MuxableSocketHTTP,這個類里面就是我們做一些有意義的事情的地方了
          來看代碼:

          package com.yovn.labs.wls.protocol;

          import java.io.IOException;
          import java.io.InputStream;
          import java.io.OutputStream;
          import java.lang.reflect.Field;
          import java.net.Socket;
          import java.net.SocketException;

          import weblogic.rjvm.NetworkChannel;
          import weblogic.servlet.internal.RequestParser;
          import weblogic.servlet.internal.ServletRequestImpl;
          import weblogic.socket.MaxMessageSizeExceededException;
          import weblogic.socket.MuxableSocket;
          import weblogic.utils.io.Chunk;

          /**
           * 
          @author yovn
           *
           
          */
          public class MuxableSocketHTTP implements MuxableSocket {

              
          private final MuxableSocket delegate;//the internal implementation
              private Field countF;
              
          private Field bufF;
              
          private Field sockF;
             
             

              
          /* (non-Javadoc)
               * @see weblogic.socket.MuxableSocket#dispatch()
               
          */
              
          public void dispatch() {

                  
          try {
                      
          byte[] buf=(byte[])bufF.get(delegate);
                      
          int count=countF.getInt(delegate);
                     
                      ServletRequestImpl servletrequestimpl 
          = new ServletRequestImpl();
                      RequestParser requestparser 
          = new RequestParser(servletrequestimpl,buf, count);
                      
          if(requestparser.parse()<0)
                      {
                          Socket sock
          =(Socket)sockF.get(delegate);
                          OutputStream out
          =sock.getOutputStream();
                          sendError(out,
          500,"Internal error");
                          out.close();
                          
          return;
                      }
                      String accessV
          =servletrequestimpl.getHeader("access");
                      
          if(accessV==null)
                      {
                          Socket sock
          =(Socket)sockF.get(delegate);
                          OutputStream out
          =sock.getOutputStream();
                          sendMessage(out,
          "You have not set 'access' header");
                          out.close();
                          
          return;
                      }
          //            System.out.println("+================================request first Line:"+servletrequestimpl.getFirstLine()+",request:"+servletrequestimpl.getRequestURI());
                  } catch (Exception e) {
                     
                      e.printStackTrace();
                  }
                 
                 
                  delegate.dispatch();
                 

              }
             
               
          void  sendMessage(OutputStream out,String msg) throws IOException
               {
                   String s
          ="HTTP/1.1 "+200+" OK\r\n\r\n";
                   out.write(s.getBytes());
                   out.write(msg.getBytes());
                   out.flush();
               }
               
               
          void  sendError(OutputStream out,int code,String msg) throws IOException
               {
                   String s
          ="HTTP/1.1 "+code+" "+msg+"\r\n\r\n";
                   out.write(s.getBytes());
                   out.flush();
               }
             
             
             
               
          public MuxableSocketHTTP(Chunk chunk1, Socket socket, NetworkChannel networkchannel)
               
          throws IOException
               {
               
          //create our delegation first
                   delegate=new weblogic.servlet.internal.MuxableSocketHTTP(chunk1,socket,networkchannel);
                   
                   
          //initiate private fields
                   try {
                      countF
          =weblogic.servlet.internal.MuxableSocketHTTP.class.getDeclaredField("count");
                      bufF
          =weblogic.servlet.internal.MuxableSocketHTTP.class.getDeclaredField("buf");
                      sockF
          =weblogic.servlet.internal.MuxableSocketHTTP.class.getDeclaredField("sock");
                      sockF.setAccessible(
          true);
                      countF.setAccessible(
          true);
                      bufF.setAccessible(
          true);
                  } 
          catch (SecurityException e) {
                      
          // TODO Auto-generated catch block
                      e.printStackTrace();
                  } 
          catch (NoSuchFieldException e) {
                      
          // TODO Auto-generated catch block
                      e.printStackTrace();
                  }
               }

              
          /* (non-Javadoc)
               * @see weblogic.socket.MuxableSocket#endOfStream()
               
          */
              
          public void endOfStream() {
                  delegate.endOfStream();

              }

              
          /* (non-Javadoc)
               * @see weblogic.socket.MuxableSocket#getBuffer()
               
          */
              
          public byte[] getBuffer() {
                 
                  
          return delegate.getBuffer();
              }

              
          /* (non-Javadoc)
               * @see weblogic.socket.MuxableSocket#getBufferOffset()
               
          */
              
          public int getBufferOffset() {
                 
                  
          return delegate.getBufferOffset();
              }

              
          /* (non-Javadoc)
               * @see weblogic.socket.MuxableSocket#getCompleteMessageTimeoutMillis()
               
          */
              
          public int getCompleteMessageTimeoutMillis() {
             
                  
          return delegate.getCompleteMessageTimeoutMillis();
              }

              
          /* (non-Javadoc)
               * @see weblogic.socket.MuxableSocket#getIdleTimeoutMillis()
               
          */
              
          public int getIdleTimeoutMillis() {
                 
                  
          return delegate.getIdleTimeoutMillis();
              }

              
          /* (non-Javadoc)
               * @see weblogic.socket.MuxableSocket#getMaxMessageSize()
               
          */
              
          public int getMaxMessageSize() {
             
                  
          return delegate.getMaxMessageSize();
              }

              
          /* (non-Javadoc)
               * @see weblogic.socket.MuxableSocket#getRawSocket()
               
          */
              
          public Socket getRawSocket() {
             
                  
          return delegate.getRawSocket();
              }

              
          /* (non-Javadoc)
               * @see weblogic.socket.MuxableSocket#getReRegisterMX()
               
          */
              
          public MuxableSocket getReRegisterMX() {
             
                  
          return delegate.getReRegisterMX();
              }

              
          /* (non-Javadoc)
               * @see weblogic.socket.MuxableSocket#getSocket()
               
          */
              
          public Socket getSocket() {
             
                  
          return delegate.getSocket();
              }

              
          public void ensureForceClose() {
                  delegate.ensureForceClose();
                 
              }

              
          public boolean isClosed() {
             
                  
          return delegate.isClosed();
              }

             
              
          /* (non-Javadoc)
               * @see weblogic.socket.MuxableSocket#getSocketInputStream()
               
          */
              
          public InputStream getSocketInputStream() {
                 
                  
          return delegate.getSocketInputStream();
              }

              
          /* (non-Javadoc)
               * @see weblogic.socket.MuxableSocket#hasException(java.lang.Throwable)
               
          */
              
          public void hasException(Throwable arg0) {
                  delegate.hasException(arg0);

              }

              
          /* (non-Javadoc)
               * @see weblogic.socket.MuxableSocket#incrementBufferOffset(int)
               
          */
              
          public void incrementBufferOffset(int arg0)
                      
          throws MaxMessageSizeExceededException {
                  delegate.incrementBufferOffset(arg0);

              }

              
          /* (non-Javadoc)
               * @see weblogic.socket.MuxableSocket#isMessageComplete()
               
          */
              
          public boolean isMessageComplete() {
                 
                  
          return delegate.isMessageComplete();
              }

              
          /* (non-Javadoc)
               * @see weblogic.socket.MuxableSocket#setReRegisterMX(weblogic.socket.MuxableSocket)
               
          */
              
          public void setReRegisterMX(MuxableSocket arg0) {
                  delegate.setReRegisterMX(arg0);

              }

              
          /* (non-Javadoc)
               * @see weblogic.socket.MuxableSocket#setSoTimeout(int)
               
          */
              
          public void setSoTimeout(int arg0) throws SocketException {
             
                  delegate.setSoTimeout(arg0);
              }

             


          }


          主體在dispatch()方法里,我們先創建weblogic內部的MuxableSocketHttp作為我們真正的實現,然后利用RequestParser,ServletRequestImpl來解析
          HTTP請求,解析后就可以查看詳細的請求內容了,我們簡單的檢查一下一個特定的request header是否設置如果沒有,則告知沒有設置,否則正常處理.

          好了,把上面的程序編譯,打包,扔到你的weblogic domain下,修該domain的config.xml如本文開頭所示.把你打好的包,加入你的weblogic類路徑,啟動weblogic.

          Ok,現在你在瀏覽器里隨便請求一個weblogic上的地址,你會看到如下頁面:

          You have not set 'access' header

          我們再來寫個測試程序,如下:

          package com.yovn.labs.wls.test;

          import java.io.ByteArrayOutputStream;
          import java.io.InputStream;
          import java.net.HttpURLConnection;
          import java.net.URL;

          /**
           * 
          @author yovn
           *
           
          */
          public class TestAccess {

              
          /**
               * 
          @param args
               
          */
              
          public static void main(String[] args)throws Exception {
                  URL url
          =new URL("http://localhost:7001/console");
                  HttpURLConnection conn
          =( HttpURLConnection)url.openConnection();
                  conn.addRequestProperty(
          "access""pass");
                  InputStream in
          =conn.getInputStream();
                  
          int len=0;
                  ByteArrayOutputStream bao
          =new ByteArrayOutputStream(1024*4);
                  
          byte[] bytes=new byte[1024];
                  
          while((len=in.read(bytes))>0)
                  {
                      bao.write(bytes,
          0,len);
                  }
                 
                  in.close();
                  conn.disconnect();
                 
                  System.out.println(bao.toString());
                 
                 
                 

              }

          }

          由于這個程序設置了'access'請求頭,所打印出來內容就是正常請求該地址所產生的內容.

          下載:
          code and jar


          posted on 2007-04-03 22:48 DoubleH 閱讀(7973) 評論(2)  編輯  收藏

          Feedback

          # re: WebLogic中攔截全局http請求[未登錄] 2007-04-04 15:20 azure
          very good  回復  更多評論
            

          # re: WebLogic中攔截全局http請求[未登錄] 2011-09-13 21:47 111
          請問樓主,在WebSphere完成上述功能,該如何做呢?  回復  更多評論
            


          只有注冊用戶登錄后才能發表評論。


          網站導航:
           
          主站蜘蛛池模板: 金堂县| 固始县| 广东省| 原阳县| 民权县| 永川市| 五大连池市| 巫山县| 奈曼旗| 隆回县| 合川市| 旬阳县| 嘉义市| 泰来县| 瑞昌市| 阳信县| 普宁市| 都匀市| 阳春市| 荆门市| 铁岭县| 德惠市| 静海县| 太谷县| 历史| 潞西市| 招远市| 乌拉特后旗| 响水县| 山丹县| 桂阳县| 万全县| 平罗县| 汤原县| 天柱县| 隆化县| 宁波市| 邵东县| 华池县| 阿拉善右旗| 琼海市|