/* * Copyright (c) 2001-2004 Caucho Technology, Inc. All rights reserved. * * The Apache Software License, Version 1.1 * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The end-user documentation included with the redistribution, if * any, must include the following acknowlegement: * "This product includes software developed by the * Caucho Technology (http://www.caucho.com/)." * Alternately, this acknowlegement may appear in the software itself, * if and wherever such third-party acknowlegements normally appear. * * 4. The names "Hessian", "Resin", and "Caucho" must not be used to * endorse or promote products derived from this software without prior * written permission. For written permission, please contact * info@caucho.com. * * 5. Products derived from this software may not be called "Resin" * nor may "Resin" appear in their names without prior written * permission of Caucho Technology. * * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE * DISCLAIMED. IN NO EVENT SHALL CAUCHO TECHNOLOGY OR ITS CONTRIBUTORS * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, * OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT * OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN * IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. * * @author Scott Ferguson */ package com.caucho.services.server; import java.io.InputStream; import java.lang.reflect.Method; import java.util.HashMap; /** * Proxy class for Hessian services. */ abstract public class AbstractSkeleton { private Class _apiClass; private Class _homeClass; private Class _objectClass; private HashMap _methodMap = new HashMap(); /** * Create a new hessian skeleton. * * @param apiClass the API interface */ protected AbstractSkeleton(Class apiClass) { _apiClass = apiClass; Method []methodList = apiClass.getMethods(); for (int i = 0; i < methodList.length; i++) { Method method = methodList[i]; if (_methodMap.get(method.getName()) == null) _methodMap.put(method.getName(), methodList[i]); Class []param = method.getParameterTypes(); String mangledName = method.getName() + "__" + param.length; _methodMap.put(mangledName, methodList[i]); _methodMap.put(mangleName(method, false), methodList[i]); } } /** * Returns the API class of the current object. */ public String getAPIClassName() { return _apiClass.getName(); } /** * Returns the API class of the factory/home. */ public String getHomeClassName() { if (_homeClass != null) return _homeClass.getName(); else return getAPIClassName(); } /** * Sets the home API class. */ public void setHomeClass(Class homeAPI) { _homeClass = homeAPI; } /** * Returns the API class of the object URLs */ public String getObjectClassName() { if (_objectClass != null) return _objectClass.getName(); else return getAPIClassName(); } /** * Sets the object API class. */ public void setObjectClass(Class objectAPI) { _objectClass = objectAPI; } /** * Returns the method by the mangled name. * * @param mangledName the name passed by the protocol */ protected Method getMethod(String mangledName) { return (Method) _methodMap.get(mangledName); } /** * Creates a unique mangled method name based on the method name and * the method parameters. * * @param method the method to mangle * @param isFull if true, mangle the full classname * * @return a mangled string. */ public static String mangleName(Method method, boolean isFull) { StringBuffer sb = new StringBuffer(); sb.append(method.getName()); Class []params = method.getParameterTypes(); for (int i = 0; i < params.length; i++) { sb.append('_'); sb.append(mangleClass(params[i], isFull)); } return sb.toString(); } /** * Mangles a classname. */ public static String mangleClass(Class cl, boolean isFull) { String name = cl.getName(); if (name.equals("boolean") || name.equals("java.lang.Boolean")) return "boolean"; else if (name.equals("int") || name.equals("java.lang.Integer") || name.equals("short") || name.equals("java.lang.Short") || name.equals("byte") || name.equals("java.lang.Byte")) return "int"; else if (name.equals("long") || name.equals("java.lang.Long")) return "long"; else if (name.equals("float") || name.equals("java.lang.Float") || name.equals("double") || name.equals("java.lang.Double")) return "double"; else if (name.equals("java.lang.String") || name.equals("com.caucho.util.CharBuffer") || name.equals("char") || name.equals("java.lang.Character") || name.equals("java.io.Reader")) return "string"; else if (name.equals("java.util.Date") || name.equals("com.caucho.util.QDate")) return "date"; else if (InputStream.class.isAssignableFrom(cl) || name.equals("[B")) return "binary"; else if (cl.isArray()) { return "[" + mangleClass(cl.getComponentType(), isFull); } else if (name.equals("org.w3c.dom.Node") || name.equals("org.w3c.dom.Element") || name.equals("org.w3c.dom.Document")) return "xml"; else if (isFull) return name; else { int p = name.lastIndexOf('.'); if (p > 0) return name.substring(p + 1); else return name; } } public String toString() { return getClass().getSimpleName() + "[" + _apiClass.getName() + "]"; } }