![JAR search and dependency download from the Maven repository](/logo.png)
com.liferay.osgi.service.tracker.collections.internal.map.ServiceTrackerMapImpl Maven / Gradle / Ivy
/**
* Copyright (c) 2000-present Liferay, Inc. 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.
*/
package com.liferay.osgi.service.tracker.collections.internal.map;
import com.liferay.osgi.service.tracker.collections.EagerServiceTrackerCustomizer;
import com.liferay.osgi.service.tracker.collections.internal.ServiceTrackerManager;
import com.liferay.osgi.service.tracker.collections.internal.ServiceTrackerUtil;
import com.liferay.osgi.service.tracker.collections.map.KeyedServiceReferenceServiceTuple;
import com.liferay.osgi.service.tracker.collections.map.ServiceReferenceMapper;
import com.liferay.osgi.service.tracker.collections.map.ServiceTrackerBucket;
import com.liferay.osgi.service.tracker.collections.map.ServiceTrackerBucketFactory;
import com.liferay.osgi.service.tracker.collections.map.ServiceTrackerMap;
import com.liferay.osgi.service.tracker.collections.map.ServiceTrackerMapListener;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Collections;
import java.util.List;
import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ConcurrentMap;
import org.osgi.framework.BundleContext;
import org.osgi.framework.ServiceReference;
import org.osgi.util.tracker.ServiceTracker;
import org.osgi.util.tracker.ServiceTrackerCustomizer;
/**
* @author Carlos Sierra Andrés
*/
public class ServiceTrackerMapImpl
implements ServiceTrackerMap {
public ServiceTrackerMapImpl(
BundleContext bundleContext, Class clazz, String filterString,
ServiceReferenceMapper serviceReferenceMapper,
ServiceTrackerCustomizer serviceTrackerCustomizer,
ServiceTrackerBucketFactory serviceTrackerMapBucketFactory,
ServiceTrackerMapListener serviceTrackerMapListener) {
_serviceReferenceMapper = serviceReferenceMapper;
_serviceTrackerCustomizer = serviceTrackerCustomizer;
_serviceTrackerMapBucketFactory = serviceTrackerMapBucketFactory;
_serviceTrackerMapListener = serviceTrackerMapListener;
_serviceTracker = ServiceTrackerUtil.createServiceTracker(
bundleContext, clazz, filterString,
new ServiceReferenceServiceTrackerCustomizer());
boolean trackAllServices = false;
if (clazz == null) {
trackAllServices = true;
}
_serviceTrackerManager = new ServiceTrackerManager(
_serviceTracker, trackAllServices);
if (_serviceTrackerCustomizer instanceof
EagerServiceTrackerCustomizer) {
_serviceTrackerManager.open();
}
}
@Override
public void close() {
_serviceTrackerManager.close();
}
@Override
public boolean containsKey(K key) {
_serviceTrackerManager.open();
return _serviceTrackerBuckets.containsKey(key);
}
@Override
public R getService(K key) {
_serviceTrackerManager.open();
ServiceTrackerBucket serviceTrackerBucket =
_serviceTrackerBuckets.get(key);
if (serviceTrackerBucket == null) {
return null;
}
return serviceTrackerBucket.getContent();
}
@Override
public Set keySet() {
_serviceTrackerManager.open();
return Collections.unmodifiableSet(_serviceTrackerBuckets.keySet());
}
@Override
public Collection values() {
_serviceTrackerManager.open();
return Collections.unmodifiableCollection(_getServices());
}
private Collection _getServices() {
Collection services = new ArrayList<>();
for (ServiceTrackerBucket serviceTrackerBucket :
_serviceTrackerBuckets.values()) {
services.add(serviceTrackerBucket.getContent());
}
return services;
}
private void _removeKeys(
KeyedServiceReferenceServiceTuple
keyedServiceReferenceServiceTuple) {
List emittedKeys =
keyedServiceReferenceServiceTuple.getEmittedKeys();
for (K emittedKey : emittedKeys) {
ServiceTrackerBucket serviceTrackerBucket =
_serviceTrackerBuckets.get(emittedKey);
if (serviceTrackerBucket == null) {
continue;
}
serviceTrackerBucket.remove(keyedServiceReferenceServiceTuple);
if (serviceTrackerBucket.isDisposable()) {
_serviceTrackerBuckets.remove(emittedKey);
}
if (_serviceTrackerMapListener != null) {
_serviceTrackerMapListener.keyRemoved(
ServiceTrackerMapImpl.this, emittedKey,
keyedServiceReferenceServiceTuple.getService(),
serviceTrackerBucket.getContent());
}
}
emittedKeys.clear();
}
private void _storeKey(
K key,
KeyedServiceReferenceServiceTuple
keyedServiceReferenceServiceTuple) {
ServiceTrackerBucket serviceTrackerBucket =
_serviceTrackerBuckets.get(key);
if (serviceTrackerBucket == null) {
ServiceTrackerBucket newServiceTrackerBucket =
_serviceTrackerMapBucketFactory.create();
serviceTrackerBucket = _serviceTrackerBuckets.putIfAbsent(
key, newServiceTrackerBucket);
if (serviceTrackerBucket == null) {
serviceTrackerBucket = newServiceTrackerBucket;
}
}
serviceTrackerBucket.store(keyedServiceReferenceServiceTuple);
keyedServiceReferenceServiceTuple.addEmittedKey(key);
}
private final ServiceReferenceMapper _serviceReferenceMapper;
private final ServiceTracker
> _serviceTracker;
private final ConcurrentMap>
_serviceTrackerBuckets = new ConcurrentHashMap<>();
private final ServiceTrackerCustomizer _serviceTrackerCustomizer;
private final ServiceTrackerManager _serviceTrackerManager;
private final ServiceTrackerBucketFactory
_serviceTrackerMapBucketFactory;
private final ServiceTrackerMapListener
_serviceTrackerMapListener;
private class DefaultEmitter implements ServiceReferenceMapper.Emitter {
public DefaultEmitter(ServiceReference serviceReference) {
_serviceReference = serviceReference;
}
@Override
public void emit(K key) {
if (_keyedServiceReferenceServiceTuple == null) {
if (!_invokedServiceTrackerCustomizer) {
TS service = _serviceTrackerCustomizer.addingService(
_serviceReference);
_invokedServiceTrackerCustomizer = true;
if (service == null) {
return;
}
_keyedServiceReferenceServiceTuple =
new KeyedServiceReferenceServiceTuple<>(
_serviceReference, service);
}
else {
return;
}
}
_storeKey(key, _keyedServiceReferenceServiceTuple);
if (_serviceTrackerMapListener != null) {
ServiceTrackerBucket serviceTrackerBucket =
_serviceTrackerBuckets.get(key);
_serviceTrackerMapListener.keyEmitted(
ServiceTrackerMapImpl.this, key,
_keyedServiceReferenceServiceTuple.getService(),
serviceTrackerBucket.getContent());
}
}
public KeyedServiceReferenceServiceTuple
getServiceReferenceServiceTuple() {
return _keyedServiceReferenceServiceTuple;
}
private boolean _invokedServiceTrackerCustomizer;
private KeyedServiceReferenceServiceTuple
_keyedServiceReferenceServiceTuple;
private final ServiceReference _serviceReference;
}
private class ServiceReferenceServiceTrackerCustomizer
implements ServiceTrackerCustomizer
> {
@Override
@SuppressWarnings({"rawtypes", "unchecked"})
public KeyedServiceReferenceServiceTuple addingService(
ServiceReference serviceReference) {
DefaultEmitter defaultEmitter = new DefaultEmitter(
serviceReference);
_serviceReferenceMapper.map(
(ServiceReference)serviceReference, defaultEmitter);
return defaultEmitter.getServiceReferenceServiceTuple();
}
@Override
@SuppressWarnings({"rawtypes", "unchecked"})
public void modifiedService(
ServiceReference serviceReference,
final KeyedServiceReferenceServiceTuple
keyedServiceReferenceServiceTuple) {
_removeKeys(keyedServiceReferenceServiceTuple);
_serviceTrackerCustomizer.modifiedService(
serviceReference,
keyedServiceReferenceServiceTuple.getService());
_serviceReferenceMapper.map(
(ServiceReference)serviceReference,
new ServiceReferenceMapper.Emitter() {
@Override
public void emit(K key) {
_storeKey(key, keyedServiceReferenceServiceTuple);
}
});
}
@Override
public void removedService(
ServiceReference serviceReference,
KeyedServiceReferenceServiceTuple
keyedServiceReferenceServiceTuple) {
_removeKeys(keyedServiceReferenceServiceTuple);
_serviceTrackerCustomizer.removedService(
serviceReference,
keyedServiceReferenceServiceTuple.getService());
}
}
}
© 2015 - 2025 Weber Informatics LLC | Privacy Policy