/*
* Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved.
*
* This program and the accompanying materials are made available under the
* terms of the Eclipse Public License v1.0 which accompanies this distribution,
* and is available at http://www.eclipse.org/legal/epl-v10.html
*/
package org.opendaylight.yangtools.util;
import java.util.Collections;
import java.util.EventListener;
import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ConcurrentMap;
import org.opendaylight.yangtools.concepts.AbstractObjectRegistration;
import org.opendaylight.yangtools.concepts.ListenerRegistration;
public class ListenerRegistry<T extends EventListener> implements Iterable<ListenerRegistration<T>> {
private final ConcurrentMap<ListenerRegistration<? extends T>,ListenerRegistration<? extends T>> listeners;
final Set<ListenerRegistration<T>> unmodifiableView;
@SuppressWarnings("unchecked")
public ListenerRegistry() {
listeners = new ConcurrentHashMap<>();
// This conversion is known to be safe.
@SuppressWarnings("rawtypes")
final Set rawSet = Collections.unmodifiableSet(listeners.keySet());
unmodifiableView = rawSet;
}
public Iterable<ListenerRegistration<T>> getListeners() {
return unmodifiableView;
}
public ListenerRegistration<T> register(final T listener) {
if (listener == null) {
throw new IllegalArgumentException("Listener should not be null.");
}
final ListenerRegistrationImpl<T> ret = new ListenerRegistrationImpl<>(listener);
listeners.put(ret,ret);
return ret;
}
public <L extends T> ListenerRegistration<L> registerWithType(final L listener) {
final ListenerRegistrationImpl<L> ret = new ListenerRegistrationImpl<>(listener);
listeners.put(ret,ret);
return ret;
}
@Override
public java.util.Iterator<ListenerRegistration<T>> iterator() {
return unmodifiableView.iterator();
}
@SuppressWarnings("rawtypes")
private void remove(final ListenerRegistrationImpl registration) {
listeners.remove(registration);
}
private class ListenerRegistrationImpl<P extends EventListener> extends AbstractObjectRegistration<P> implements
ListenerRegistration<P> {
public ListenerRegistrationImpl(final P instance) {
super(instance);
}
@Override
protected void removeRegistration() {
ListenerRegistry.this.remove(this);
}
}
public static <T extends EventListener> ListenerRegistry<T> create() {
return new ListenerRegistry<>();
}
}