![JAR search and dependency download from the Maven repository](/logo.png)
org.apache.tuscany.sca.extensibility.ServiceHelper Maven / Gradle / Ivy
The newest version!
/*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/
package org.apache.tuscany.sca.extensibility;
import java.lang.reflect.Constructor;
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;
import java.util.Collection;
import java.util.Map;
import org.apache.tuscany.sca.core.ExtensionPointRegistry;
import org.apache.tuscany.sca.core.LifeCycleListener;
/**
* A helper for handling service lifecycle and instantiations
* @tuscany.spi.extension.asclient
*/
public class ServiceHelper {
private ServiceHelper() {
}
/**
* Start the service instance
* @param instance
*/
public static boolean start(Object instance) {
if (instance instanceof LifeCycleListener) {
((LifeCycleListener)instance).start();
return true;
}
return false;
}
/**
* Stop the service instance
* @param instance
*/
public static boolean stop(Object instance) {
if (instance instanceof LifeCycleListener) {
((LifeCycleListener)instance).stop();
return true;
}
return false;
}
/**
* Stop a collection of service instances
* @param instances
*/
public static void stop(Collection extends Object> instances) {
if (instances == null) {
return;
}
for (Object instance : instances) {
if (instance instanceof LifeCycleListener) {
((LifeCycleListener)instance).stop();
}
}
}
/**
* Create a service instance with one parameter
* @param cls The service type
* @param parameterType The parameter type
* @param parameter The parameter value
* @return The newly created service instance
* @throws Exception
*/
public static T newInstance(Class cls, Class> parameterType, Object parameter) throws Exception {
Constructor constructor = cls.getConstructor(parameterType);
return constructor.newInstance(parameter);
}
/**
* Create a service instance with an array of parameters
* @param cls The service type
* @param parameterTypes An array of parameter types
* @param parameters An array of parameter values
* @return The newly created service instance
* @throws Exception
*/
public static T newInstance(Class cls, Class> parameterTypes[], Object... parameters) throws Exception {
Constructor constructor = cls.getConstructor(parameterTypes);
return constructor.newInstance(parameters);
}
/**
* Create a service instance with the default no-arg constructor
* @param cls The service type
* @return The newly created service instance
* @throws Exception
*/
public static T newInstance(Class cls) throws Exception {
Constructor constructor = cls.getConstructor();
return constructor.newInstance();
}
private final static Class>[] ARG_TYPES = new Class>[] {ExtensionPointRegistry.class, Map.class};
/**
* Create a service instance from the service declaration
* @param
* @param registry The extension point registry
* @param sd The service declaration
* @return The newly created service instance
* @throws Exception
*/
public static T newInstance(ExtensionPointRegistry registry, ServiceDeclaration sd) throws Exception {
Class cls = (Class)sd.loadClass();
T instance = null;
try {
// Try constructor(ExtensionPointRegistry.class)
instance = newInstance(cls, ExtensionPointRegistry.class, registry);
} catch (NoSuchMethodException e) {
try {
// Try Try constructor(ExtensionPointRegistry.class, Map.class)
instance = newInstance(cls, ARG_TYPES, registry, sd.getAttributes());
} catch (NoSuchMethodException e1) {
// Try constructor()
instance = newInstance(cls);
}
}
return instance;
}
public static T newLazyInstance(ExtensionPointRegistry registry, ServiceDeclaration sd, Class serviceType) {
return serviceType.cast(Proxy.newProxyInstance(serviceType.getClassLoader(),
new Class>[] {serviceType, LifeCycleListener.class},
new InvocationHandlerImpl(registry, serviceType, sd)));
}
private static class InvocationHandlerImpl implements InvocationHandler {
private ExtensionPointRegistry registry;
private Class> type;
private ServiceDeclaration sd;
private Object instance;
private final static Method STOP_METHOD = getMethod(LifeCycleListener.class, "stop");
private final static Method START_METHOD = getMethod(LifeCycleListener.class, "start");
private final static Method EQUALS_METHOD = getMethod(Object.class, "equals");
private final static Method HASHCODE_METHOD = getMethod(Object.class, "hashCode");
private final static Method TOSTRING_METHOD = getMethod(Object.class, "toString");
private static Method getMethod(Class> type, String name) {
Method[] methods = type.getMethods();
for (Method method : methods) {
if (name.equals(method.getName())) {
return method;
}
}
return null;
}
public InvocationHandlerImpl(ExtensionPointRegistry registry, Class> type, ServiceDeclaration sd) {
super();
this.registry = registry;
this.sd = sd;
this.type = type;
}
private Object getAttribute(Method method) throws Exception {
if (method.getParameterTypes().length != 0) {
return null;
}
String name = method.getName();
if (name.equals("getModelType") && method.getReturnType() == Class.class) {
return sd.loadClass(sd.getAttributes().get("model"));
} else if (name.equals("getArtifactType")) {
return ServiceDeclarationParser.getQName(sd.getAttributes().get("qname"));
}
return null;
}
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
synchronized (this) {
// Check if the method is to get the qname/model attribute
Object value = getAttribute(method);
if (value != null) {
return value;
}
if (instance == null && method.getDeclaringClass() == type) {
// Only initialize the instance when a method on the service type is invoked
instance = newInstance(registry, sd);
start(instance);
}
if (method.equals(EQUALS_METHOD)) {
return proxy == args[0];
} else if (method.equals(HASHCODE_METHOD)) {
return System.identityHashCode(proxy);
} else if (method.equals(TOSTRING_METHOD)) {
return "Proxy: " + sd.toString();
}
if (instance == null) {
return null;
}
}
if (method.equals(STOP_METHOD)) {
stop(instance);
return null;
} else if (method.equals(START_METHOD)) {
// Skip the start()
return null;
} else {
return method.invoke(instance, args);
}
}
}
}
© 2015 - 2025 Weber Informatics LLC | Privacy Policy