entaxy-public/platform/runtime/base/base-support/src/main/java/ru/entaxy/platform/base/support/osgi/OSGIUtils.java

190 lines
6.1 KiB
Java

/*-
* ~~~~~~licensing~~~~~~
* base-support
* ==========
* Copyright (C) 2020 - 2023 EmDev LLC
* ==========
* You may not use this file except in accordance with the License Terms of the Copyright
* Holder located at: https://entaxy.ru/eula . All copyrights, all intellectual property
* rights to the Software and any copies are the property of the Copyright Holder. Unless
* it is explicitly allowed the Copyright Holder, the User is prohibited from using the
* Software for commercial purposes to provide services to third parties.
*
* The Copyright Holder hereby declares that the Software is provided on an "AS IS".
* Under no circumstances does the Copyright Holder guarantee or promise that the
* Software provided by him will be suitable or not suitable for the specific purposes
* of the User, that the Software will meet all commercial and personal subjective
* expectations of the User, that the Software will work properly, without technical
* errors, quickly and uninterruptedly.
*
* Under no circumstances shall the Copyright Holder or its Affiliates is not liable
* to the User for any direct or indirect losses of the User, his expenses or actual
* damage, including, downtime; loss of bussines; lost profit; lost earnings; loss
* or damage to data, property, etc.
* ~~~~~~/licensing~~~~~~
*/
package ru.entaxy.platform.base.support.osgi;
import org.osgi.framework.BundleContext;
import org.osgi.framework.Constants;
import org.osgi.framework.FrameworkUtil;
import org.osgi.framework.ServiceReference;
import org.osgi.util.tracker.ServiceTracker;
import ru.entaxy.platform.base.support.CommonUtils;
public class OSGIUtils {
protected static abstract class ServicesEntryPoint<T extends ServicesEntryPoint<T>> {
protected Class<?> serviceClass = null;
protected String serviceClassName = null;
protected String filter = null;
protected int wait = -1;
protected BundleContext bundleContext = FrameworkUtil.getBundle(OSGIUtils.class).getBundleContext();
public T ofClass(Class<?> clazz) {
this.serviceClass = clazz;
return this.getBuilder();
}
public T ofClass(String className) /* throws Exception */ {
this.serviceClassName = className;
// BundleWiring wiring = this.bundleContext.getBundle().adapt(BundleWiring.class);
// ClassLoader cl = wiring.getClassLoader();
// this.serviceClass = cl.loadClass(this.serviceClassName);
return this.getBuilder();
}
public T bundleContext(BundleContext context) {
if (context == null)
this.bundleContext = FrameworkUtil.getBundle(OSGIUtils.class).getBundleContext();
else
this.bundleContext = context;
return getBuilder();
}
protected abstract T getBuilder();
}
public static class ServicesFindHelper extends ServicesEntryPoint<ServicesFindHelper> {
@Override
protected ServicesFindHelper getBuilder() {
return this;
}
protected String getClassFilter() {
String className = (this.serviceClass != null)
?this.serviceClass.getName()
:this.serviceClassName;
return "(" +
(CommonUtils.isValid(className)
?(Constants.OBJECTCLASS + "=" + className)
:"")
+ ")";
}
public ServicesFindHelper filter(String filter) {
this.filter = filter;
return this;
}
public ServicesFindHelper waitService(int millis) {
this.wait = millis;
return this;
}
public <T> T get() throws Exception {
String classFilter = getClassFilter();
String finalFilter = "";
if (CommonUtils.isValid(classFilter))
if (CommonUtils.isValid(this.filter))
finalFilter = String.format("(&%s%s)", classFilter, this.filter);
else
finalFilter = "(" + classFilter + ")";
else
if (CommonUtils.isValid(this.filter))
finalFilter = "(" + this.filter + ")";
else
finalFilter = "";
if (wait > 0) {
// wait for service
ServiceTracker tracker;
if (CommonUtils.isValid(this.filter))
tracker = new ServiceTracker<>(this.bundleContext, this.bundleContext.createFilter(finalFilter), null);
else
tracker = new ServiceTracker<>(this.bundleContext, this.bundleContext.createFilter(classFilter), null);
tracker.open();
tracker.waitForService(this.wait);
ServiceReference<?> connectionManagerServiceReference =
tracker.getServiceReference();
tracker.close();
return (T)bundleContext.getService(connectionManagerServiceReference);
} else {
ServiceReference<?>[] serviceReferences;
ServiceReference<?> serviceReference;
if (this.serviceClass != null)
this.serviceClassName = this.serviceClass.getName();
if (!CommonUtils.isValid(this.serviceClassName))
return null;
if (CommonUtils.isValid(this.filter)) {
serviceReferences = this.bundleContext.getServiceReferences(serviceClassName, this.filter);
serviceReference = serviceReferences.length>0
?serviceReferences[0]
:null;
} else {
serviceReference = this.bundleContext.getServiceReference(serviceClassName);
}
if (serviceReference == null)
return null;
return (T) this.bundleContext.getService(serviceReference);
}
}
}
public static class ServicesHelper extends ServicesEntryPoint<ServicesFindHelper> {
private ServicesFindHelper findHelper = new ServicesFindHelper();
@Override
public ServicesFindHelper ofClass(Class<?> clazz) {
return findHelper.ofClass(clazz);
}
@Override
public ServicesFindHelper ofClass(String className) {
return findHelper.ofClass(className);
}
@Override
protected ServicesFindHelper getBuilder() {
return findHelper;
}
}
static public <T> T getService(Class<T> serviceClass) {
BundleContext bundleContext = FrameworkUtil.getBundle(OSGIUtils.class).getBundleContext();
return getService(bundleContext, serviceClass);
}
static public <T> T getService(BundleContext bundleContext, Class<T> serviceClass) {
T result = null;
ServiceReference<T> ref = bundleContext.getServiceReference(serviceClass);
if (ref != null) {
result = bundleContext.getService(ref);
}
return result;
}
static public ServicesHelper services() {
return new ServicesHelper();
}
}