ServerUtils.java :  » Web-Server » xsocket » org » xsocket » connection » http » server » Java Open Source

Java Open Source » Web Server » xsocket 
xsocket » org » xsocket » connection » http » server » ServerUtils.java
/*
 *  Copyright (c) xsocket.org, 2006 - 2008. All rights reserved.
 *
 *  This library is free software; you can redistribute it and/or
 *  modify it under the terms of the GNU Lesser General Public
 *  License as published by the Free Software Foundation; either
 *  version 2.1 of the License, or (at your option) any later version.
 *
 *  This library is distributed in the hope that it will be useful,
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 *  Lesser General Public License for more details.
 *
 *  You should have received a copy of the GNU Lesser General Public
 *  License along with this library; if not, write to the Free Software
 *  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
 *
 * Please refer to the LGPL license at: http://www.gnu.org/copyleft/lesser.txt
 * The latest copy of this software may be found on http://www.xsocket.org/
 */
package org.xsocket.connection.http.server;




import java.lang.reflect.Field;
import java.lang.reflect.Method;
import java.util.Map;
import java.util.logging.Level;
import java.util.logging.Logger;

import org.xsocket.Execution;
import org.xsocket.Resource;
import org.xsocket.connection.IServer;
import org.xsocket.connection.http.HttpUtils;
import org.xsocket.connection.http.IHttpConnectHandler;
import org.xsocket.connection.http.IHttpConnection;
import org.xsocket.connection.http.IHttpConnectionTimeoutHandler;
import org.xsocket.connection.http.IHttpDisconnectHandler;
import org.xsocket.connection.http.IHttpHandler;
import org.xsocket.connection.http.InvokeOn;
import org.xsocket.connection.http.HttpRequest;
import org.xsocket.connection.http.server.HttpProtocolAdapter;
import org.xsocket.connection.http.server.IHttpRequestHandler;




/**
 * A utility class
 *
 * @author grro@xsocket.org
 */
final class ServerUtils {

  private static final Logger LOG = Logger.getLogger(ServerUtils.class.getName());


  @SuppressWarnings("unchecked")
  private static final Map<Class, RequestHandlerInfo> serverHandlerInfoCache = HttpUtils.newMapCache(25);


  @SuppressWarnings("unchecked")
  private static final Map<Class, HttpHandlerInfo> httpHandlerInfoCache = HttpUtils.newMapCache(25);



  public static final HttpHandlerInfo EMPTY_HTTP_HANDLER_INFO = new HttpHandlerInfo(null);
  public static final RequestHandlerInfo SERVER_HANDLER_INFO_NONTHREADED_MESSAGE_RECEIVED = new RequestHandlerInfo(false, true);


  private static String componentInfo = null;



  private ServerUtils() { }


  /**
   * get version string
   *
   * @return the version string
   */
  public static String getVersionInfo() {
    return HttpUtils.getVersionInfo();
  }


  /**
   * get the component info
   * @return the component info
   */
  public static String getComponentInfo() {
    if (componentInfo == null) {
      componentInfo = "xSocket-http/" + ServerUtils.getVersionInfo();
    }

    return componentInfo;
  }



  /**
   * injects a server field
   *
   * @param handler   the handler
   * @param server    the server to inject
   */
  static void injectServerField(Object handler, IServer server) {
    Field[] fields = handler.getClass().getDeclaredFields();
    for (Field field : fields) {
      if (field.isAnnotationPresent(Resource.class)) {
        Resource res = field.getAnnotation(Resource.class);
        if ((field.getType() == IServer.class) || (res.type() == IServer.class)) {
          field.setAccessible(true);
          try {
            field.set(handler, server);
          } catch (IllegalAccessException iae) {
            LOG.warning("could not set HandlerContext for attribute " + field.getName() + ". Reason " + iae.toString());
          }
        }
      }
    }
  }


  /**
   * inject a protocol adapter
   *
   * @param handler   the handler
   * @param adapter   the adapter to inject
   */
  static void injectProtocolAdapter(Object handler, HttpProtocolAdapter adapter) {
    Field[] fields = handler.getClass().getDeclaredFields();
    for (Field field : fields) {
      if (field.isAnnotationPresent(Resource.class)) {
        Resource res = field.getAnnotation(Resource.class);
        if ((field.getType() == HttpProtocolAdapter.class) || (res.type() == HttpProtocolAdapter.class)) {
          field.setAccessible(true);
          try {
            field.set(handler, adapter);
          } catch (IllegalAccessException iae) {
            LOG.warning("could not set HandlerContext for attribute " + field.getName() + ". Reason " + iae.toString());
          }
        }
      }
    }
  }






  @SuppressWarnings("unchecked")
  static HttpHandlerInfo getHttpHandlerInfo(IHttpHandler httpHandler) {
    if (httpHandler == null) {
      return EMPTY_HTTP_HANDLER_INFO;
    }

    HttpHandlerInfo httpHandlerInfo = httpHandlerInfoCache.get(httpHandler.getClass());

    if (httpHandlerInfo == null) {
      httpHandlerInfo = new HttpHandlerInfo((Class<IHttpHandler>) httpHandler.getClass());
      httpHandlerInfoCache.put(httpHandler.getClass(), httpHandlerInfo);
    }

    return httpHandlerInfo;
  }



  @SuppressWarnings("unchecked")
  static RequestHandlerInfo getServerHandlerInfo(IHttpHandler serverHandler) {
    if (serverHandler == null) {
      return SERVER_HANDLER_INFO_NONTHREADED_MESSAGE_RECEIVED;
    }

    RequestHandlerInfo serverHandlerInfo = serverHandlerInfoCache.get(serverHandler.getClass());

    if (serverHandlerInfo == null) {
      serverHandlerInfo = new RequestHandlerInfo((Class<IHttpRequestHandler>) serverHandler.getClass());
      serverHandlerInfoCache.put(serverHandler.getClass(), serverHandlerInfo);
    }

    return serverHandlerInfo;
  }



  static final class RequestHandlerInfo {

    private boolean isInvokeOnMessageReceived = false;;
    private boolean isMultithreaded = true;



    @SuppressWarnings("unchecked")
    public RequestHandlerInfo(Class clazz) {

      if (IHttpRequestHandler.class.isAssignableFrom(clazz)) {
        isMultithreaded = isOnRequestMultithreaded((Class<IHttpRequestHandler>) clazz);
        isInvokeOnMessageReceived = isInvokeOnMessageReceived((Class<IHttpRequestHandler>) clazz);
      }
    }

    public RequestHandlerInfo(boolean isMultithreaded, boolean invokeOnMessageReceived) {
      this.isMultithreaded = isMultithreaded;
      this.isInvokeOnMessageReceived = invokeOnMessageReceived;
    }



    static boolean isOnRequestMultithreaded(Class<IHttpRequestHandler> serverHandlerClass) {
      int mode = IHttpRequestHandler.DEFAULT_EXECUTION_MODE;

      Execution execution = serverHandlerClass.getAnnotation(Execution.class);
      if (execution != null) {
        mode = execution.value();
      }
 
      try {
        Method meth = serverHandlerClass.getMethod("onRequest", new Class[] { HttpRequest.class, IHttpResponseContext.class });
        execution = meth.getAnnotation(Execution.class);
        if (execution != null) {
          mode = execution.value();
        }

      } catch (NoSuchMethodException nsme) {
        if (LOG.isLoggable(Level.FINE)) {
          LOG.fine("shouldn't occure because body handler has to have such a method " + nsme.toString());
        }
      }

      return (mode == Execution.MULTITHREADED);
    }



    static boolean isInvokeOnMessageReceived(Class<IHttpRequestHandler> serverHandlerClass) {
      int mode = IHttpRequestHandler.DEFAULT_INVOKE_ON_MODE;

      InvokeOn invokeOn = serverHandlerClass.getAnnotation(InvokeOn.class);
      if (invokeOn != null) {
        mode = invokeOn.value();
      }

      try {
        Method meth = serverHandlerClass.getMethod("onRequest", new Class[] { HttpRequest.class, IHttpResponseContext.class });
        invokeOn = meth.getAnnotation(InvokeOn.class);
        if (invokeOn != null) {
          mode = invokeOn.value();
        }

      } catch (NoSuchMethodException nsme) {
        if (LOG.isLoggable(Level.FINE)) {
          LOG.fine("shouldn't occure because response handler has to have such a method " + nsme.toString());
        }
      }

      return (mode == InvokeOn.MESSAGE_RECEIVED);
    }


    public boolean isInvokeOnMessageReceived() {
      return  isInvokeOnMessageReceived;
    }

    public boolean isMultithreaded() {
      return isMultithreaded;
    }
  }



  static final class HttpHandlerInfo {

    private boolean isConnectHandler = false;
    private boolean isConnectHandlerMultithreaded = true;

    private boolean isDisconnectHandler = false;
    private boolean isDisconnectHandlerMultithreaded = true;

    private boolean isConnectionTimoutHandler = false;
    private boolean isConnectionTimoutHandlerMultithreaded = true;

    private boolean isRequestTimoutHandler = false;
    private boolean isRequestTimoutHandlerMultithreaded = true;


    @SuppressWarnings("unchecked")
    public HttpHandlerInfo(Class clazz) {

      if (clazz == null) {
        return;
      }


      if (IHttpConnectHandler.class.isAssignableFrom(clazz)) {
        isConnectHandler = true;
        isConnectHandlerMultithreaded = isOnConnectMultithreaded(clazz);
      }

      if (IHttpDisconnectHandler.class.isAssignableFrom(clazz)) {
        isDisconnectHandler = true;
        isDisconnectHandlerMultithreaded = isOnDisconnectMultithreaded(clazz);
      }

      if (IHttpConnectionTimeoutHandler.class.isAssignableFrom(clazz)) {
        isConnectionTimoutHandler = true;
        isConnectionTimoutHandlerMultithreaded = isOnConnectionTimeoutMultithreaded(clazz);
      }
      
      if (IHttpRequestTimeoutHandler.class.isAssignableFrom(clazz)) {
        isRequestTimoutHandler = true;
        isRequestTimoutHandlerMultithreaded = isOnRequestTimeoutMultithreaded(clazz);
      }
    }





    static boolean isOnConnectMultithreaded(Class<IHttpRequestHandler> serverHandlerClass) {
      int mode = IHttpRequestHandler.DEFAULT_EXECUTION_MODE;

      Execution execution = serverHandlerClass.getAnnotation(Execution.class);
      if (execution != null) {
        mode = execution.value();
      }

      try {
        Method meth = serverHandlerClass.getMethod("onConnect", new Class[] { IHttpConnection.class });
        execution = meth.getAnnotation(Execution.class);
        if (execution != null) {
          mode = execution.value();
        }

      } catch (NoSuchMethodException nsme) {
        if (LOG.isLoggable(Level.FINE)) {
          LOG.fine("shouldn't occure because body handler has to have such a method " + nsme.toString());
        }
      }

      return (mode == Execution.MULTITHREADED);
    }


    static boolean isOnDisconnectMultithreaded(Class<IHttpRequestHandler> serverHandlerClass) {
      int mode = IHttpRequestHandler.DEFAULT_EXECUTION_MODE;

      Execution execution = serverHandlerClass.getAnnotation(Execution.class);
      if (execution != null) {
        mode = execution.value();
      }

      try {
        Method meth = serverHandlerClass.getMethod("onDisconnect", new Class[] { IHttpConnection.class });
        execution = meth.getAnnotation(Execution.class);
        if (execution != null) {
          mode = execution.value();
        }

      } catch (NoSuchMethodException nsme) {
        if (LOG.isLoggable(Level.FINE)) {
          LOG.fine("shouldn't occure because body handler has to have such a method " + nsme.toString());
        }
      }

      return (mode == Execution.MULTITHREADED);
    }


    static boolean isOnRequestTimeoutMultithreaded(Class<IHttpRequestHandler> serverHandlerClass) {
      int mode = IHttpRequestHandler.DEFAULT_EXECUTION_MODE;

      Execution execution = serverHandlerClass.getAnnotation(Execution.class);
      if (execution != null) {
        mode = execution.value();
      }

      try {
        Method meth = serverHandlerClass.getMethod("onRequestTimeout", new Class[] { IHttpConnection.class });
        execution = meth.getAnnotation(Execution.class);
        if (execution != null) {
          mode = execution.value();
        }

      } catch (NoSuchMethodException nsme) {
        if (LOG.isLoggable(Level.FINE)) {
          LOG.fine("shouldn't occure because body handler has to have such a method " + nsme.toString());
        }
      }

      return (mode == Execution.MULTITHREADED);
    }


    static boolean isOnConnectionTimeoutMultithreaded(Class<IHttpRequestHandler> serverHandlerClass) {
      int mode = IHttpRequestHandler.DEFAULT_EXECUTION_MODE;

      Execution execution = serverHandlerClass.getAnnotation(Execution.class);
      if (execution != null) {
        mode = execution.value();
      }

      try {
        Method meth = serverHandlerClass.getMethod("onConnectionTimeout", new Class[] { IHttpConnection.class });
        execution = meth.getAnnotation(Execution.class);
        if (execution != null) {
          mode = execution.value();
        }

      } catch (NoSuchMethodException nsme) {
        if (LOG.isLoggable(Level.FINE)) {
          LOG.fine("shouldn't occure because body handler has to have such a method " + nsme.toString());
        }
      }

      return (mode == Execution.MULTITHREADED);
    }

    public boolean isConnectHandler() {
      return isConnectHandler;
    }

    public boolean isConnectHandlerMultithreaded() {
      return isConnectHandlerMultithreaded;
    }

    public boolean isDisconnectHandler() {
      return isDisconnectHandler;
    }

    public boolean isDisconnectHandlerMultithreaded() {
      return isDisconnectHandlerMultithreaded;
    }

    public boolean isConnectionTimeoutHandler() {
      return isConnectionTimoutHandler;
    }

    public boolean isConnectionTimeoutHandlerMultithreaded() {
      return isConnectionTimoutHandlerMultithreaded;
    }
    
    public boolean isRequestTimeoutHandler() {
      return isRequestTimoutHandler;
    }
    
    public boolean isREquestTimeoutHandlerMultithreaded() {
      return isRequestTimoutHandlerMultithreaded;
    }
  }

}
java2s.com  | Contact Us | Privacy Policy
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.