From: Tony Tkacik Date: Tue, 3 Jun 2014 13:29:53 +0000 (+0000) Subject: Merge "Fix logging in NetconfDeviceSalFacade" X-Git-Tag: release/helium~717 X-Git-Url: https://git.opendaylight.org/gerrit/gitweb?p=controller.git;a=commitdiff_plain;h=412323d01e3caa3e0d0801760f957f865629b9da;hp=9f0d57f4f0c2a0f1c1cf63e65de8915b2a580c76 Merge "Fix logging in NetconfDeviceSalFacade" --- diff --git a/opendaylight/md-sal/model/model-flow-base/src/main/yang/opendaylight-match-types.yang b/opendaylight/md-sal/model/model-flow-base/src/main/yang/opendaylight-match-types.yang index b02b0dc25c..efe1ce3e3a 100644 --- a/opendaylight/md-sal/model/model-flow-base/src/main/yang/opendaylight-match-types.yang +++ b/opendaylight/md-sal/model/model-flow-base/src/main/yang/opendaylight-match-types.yang @@ -269,6 +269,12 @@ module opendaylight-match-types { } } + grouping "tcp-flag-match-fields" { + leaf tcp-flag { + type uint16; + } + } + grouping match { leaf in-port { type inv:node-connector-id; @@ -340,5 +346,9 @@ module opendaylight-match-types { container "protocol-match-fields" { uses "protocol-match-fields"; } + + container tcp-flag-match { + uses "tcp-flag-match-fields"; + } } } \ No newline at end of file diff --git a/opendaylight/md-sal/model/model-flow-base/src/main/yang/opendaylight-table-types.yang b/opendaylight/md-sal/model/model-flow-base/src/main/yang/opendaylight-table-types.yang index e74b548342..c271f8f4d0 100644 --- a/opendaylight/md-sal/model/model-flow-base/src/main/yang/opendaylight-table-types.yang +++ b/opendaylight/md-sal/model/model-flow-base/src/main/yang/opendaylight-table-types.yang @@ -188,6 +188,10 @@ module opendaylight-table-types { base match-field; description "Match for IPv6 Extension Header pseudo-field"; } + identity tcp_flag { + base match-field; + description "TCP Flag Match"; + } grouping set-field-match { list set-field-match { diff --git a/opendaylight/md-sal/sal-binding-broker/src/main/java/org/opendaylight/controller/sal/binding/impl/AbstractNotificationListenerRegistration.java b/opendaylight/md-sal/sal-binding-broker/src/main/java/org/opendaylight/controller/sal/binding/impl/AbstractNotificationListenerRegistration.java new file mode 100644 index 0000000000..5e7c91374f --- /dev/null +++ b/opendaylight/md-sal/sal-binding-broker/src/main/java/org/opendaylight/controller/sal/binding/impl/AbstractNotificationListenerRegistration.java @@ -0,0 +1,41 @@ +/* + * Copyright (c) 2014 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.controller.sal.binding.impl; + +import org.opendaylight.controller.sal.binding.api.NotificationListener; +import org.opendaylight.yangtools.concepts.AbstractListenerRegistration; +import org.opendaylight.yangtools.yang.binding.Notification; + +import com.google.common.base.Preconditions; + +/** + * Abstract implementation of {@link NotificationListenerRegistration}. + * + * @param Notification type + */ +abstract class AbstractNotificationListenerRegistration extends AbstractListenerRegistration> implements NotificationListenerRegistration { + private final Class type; + + protected AbstractNotificationListenerRegistration(final Class type, final NotificationListener listener) { + super(listener); + this.type = Preconditions.checkNotNull(type); + } + + @Override + public Class getType() { + return type; + } + + @Override + @SuppressWarnings("unchecked") + public void notify(final Notification notification) { + if (!isClosed()) { + getInstance().onNotification((T)notification); + } + } +} diff --git a/opendaylight/md-sal/sal-binding-broker/src/main/java/org/opendaylight/controller/sal/binding/impl/AggregatedNotificationListenerRegistration.java b/opendaylight/md-sal/sal-binding-broker/src/main/java/org/opendaylight/controller/sal/binding/impl/AggregatedNotificationListenerRegistration.java new file mode 100644 index 0000000000..f0db891f14 --- /dev/null +++ b/opendaylight/md-sal/sal-binding-broker/src/main/java/org/opendaylight/controller/sal/binding/impl/AggregatedNotificationListenerRegistration.java @@ -0,0 +1,57 @@ +/* + * Copyright (c) 2014 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.controller.sal.binding.impl; + +import org.opendaylight.controller.sal.binding.api.NotificationListener; +import org.opendaylight.yangtools.yang.binding.Notification; + +import com.google.common.base.Preconditions; + +/** + * An aggregated listener registration. This is a result of registering an invoker which can handle multiple + * interfaces at the same time. In order to support correct delivery, we need to maintain per-type registrations + * which get squashed if a notification which implements multiple interfaces is encountered. + * + * We take care of that by implementing alternate {@link #hashCode()}/{@link #equals(Object)}, which resolve + * to the backing aggregator. + * + * @param Notification type + * @param Aggregator type + */ +abstract class AggregatedNotificationListenerRegistration extends AbstractNotificationListenerRegistration { + private final A aggregator; + + protected AggregatedNotificationListenerRegistration(final Class type, final NotificationListener listener, final A aggregator) { + super(type, listener); + this.aggregator = Preconditions.checkNotNull(aggregator); + } + + protected A getAggregator() { + return aggregator; + } + + @Override + public int hashCode() { + return aggregator.hashCode(); + } + + @Override + public boolean equals(final Object obj) { + if (this == obj) { + return true; + } + if (obj == null) { + return false; + } + if (!this.getClass().equals(obj.getClass())) { + return false; + } + + return aggregator.equals(((AggregatedNotificationListenerRegistration)obj).aggregator); + } +} diff --git a/opendaylight/md-sal/sal-binding-broker/src/main/java/org/opendaylight/controller/sal/binding/impl/GeneratedListenerRegistration.java b/opendaylight/md-sal/sal-binding-broker/src/main/java/org/opendaylight/controller/sal/binding/impl/GeneratedListenerRegistration.java deleted file mode 100644 index 5325ed3c3a..0000000000 --- a/opendaylight/md-sal/sal-binding-broker/src/main/java/org/opendaylight/controller/sal/binding/impl/GeneratedListenerRegistration.java +++ /dev/null @@ -1,39 +0,0 @@ -/** - * 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.controller.sal.binding.impl; - -import org.opendaylight.controller.sal.binding.spi.NotificationInvokerFactory.NotificationInvoker; -import org.opendaylight.yangtools.concepts.AbstractObjectRegistration; -import org.opendaylight.yangtools.concepts.ListenerRegistration; -import org.opendaylight.yangtools.yang.binding.NotificationListener; - -import com.google.common.base.Preconditions; - -class GeneratedListenerRegistration extends AbstractObjectRegistration implements ListenerRegistration { - private NotificationBrokerImpl notificationBroker; - private final NotificationInvoker invoker; - - public GeneratedListenerRegistration(final NotificationListener instance, final NotificationInvoker invoker, final NotificationBrokerImpl broker) { - super(instance); - this.invoker = Preconditions.checkNotNull(invoker); - this.notificationBroker = Preconditions.checkNotNull(broker); - } - - public NotificationInvoker getInvoker() { - // There is a race with NotificationBrokerImpl: - // the invoker can be closed here - return invoker; - } - - @Override - protected void removeRegistration() { - notificationBroker.unregisterListener(this); - notificationBroker = null; - invoker.close(); - } -} diff --git a/opendaylight/md-sal/sal-binding-broker/src/main/java/org/opendaylight/controller/sal/binding/impl/GenericNotificationRegistration.java b/opendaylight/md-sal/sal-binding-broker/src/main/java/org/opendaylight/controller/sal/binding/impl/GenericNotificationRegistration.java deleted file mode 100644 index 448adfa02e..0000000000 --- a/opendaylight/md-sal/sal-binding-broker/src/main/java/org/opendaylight/controller/sal/binding/impl/GenericNotificationRegistration.java +++ /dev/null @@ -1,36 +0,0 @@ -/** - * 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.controller.sal.binding.impl; - -import org.opendaylight.controller.sal.binding.api.NotificationListener; -import org.opendaylight.yangtools.concepts.AbstractObjectRegistration; -import org.opendaylight.yangtools.concepts.ListenerRegistration; -import org.opendaylight.yangtools.yang.binding.Notification; - -import com.google.common.base.Preconditions; - -class GenericNotificationRegistration extends AbstractObjectRegistration> implements ListenerRegistration> { - private final Class type; - private NotificationBrokerImpl notificationBroker; - - public GenericNotificationRegistration(final Class type, final NotificationListener instance, final NotificationBrokerImpl broker) { - super(instance); - this.type = Preconditions.checkNotNull(type); - this.notificationBroker = Preconditions.checkNotNull(broker); - } - - public Class getType() { - return type; - } - - @Override - protected void removeRegistration() { - notificationBroker.unregisterListener(this); - notificationBroker = null; - } -} diff --git a/opendaylight/md-sal/sal-binding-broker/src/main/java/org/opendaylight/controller/sal/binding/impl/ListenerMapGeneration.java b/opendaylight/md-sal/sal-binding-broker/src/main/java/org/opendaylight/controller/sal/binding/impl/ListenerMapGeneration.java new file mode 100644 index 0000000000..4d893aa7be --- /dev/null +++ b/opendaylight/md-sal/sal-binding-broker/src/main/java/org/opendaylight/controller/sal/binding/impl/ListenerMapGeneration.java @@ -0,0 +1,106 @@ +/** + * Copyright (c) 2014 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.controller.sal.binding.impl; + +import java.util.Arrays; +import java.util.Collection; +import java.util.HashSet; +import java.util.Set; + +import org.opendaylight.yangtools.yang.binding.Notification; + +import com.google.common.base.Predicate; +import com.google.common.cache.CacheBuilder; +import com.google.common.cache.CacheLoader; +import com.google.common.cache.LoadingCache; +import com.google.common.collect.ImmutableMultimap; +import com.google.common.collect.ImmutableSet; +import com.google.common.collect.Iterables; +import com.google.common.collect.Multimap; + +/** + * An immutable view of the current generation of listeners. + */ +final class ListenerMapGeneration { + private static final int CACHE_MAX_ENTRIES = 1000; + + /** + * Constant map of notification type to subscribed listeners. + */ + private final Multimap, NotificationListenerRegistration> typeToListeners; + + /** + * Dynamic cache of notification implementation to matching listeners. This cache loads entries based on + * the contents of the {@link #typeToListeners} map. + */ + private final LoadingCache, Iterable>> implementationToListeners = + CacheBuilder.newBuilder() + .weakKeys() + .maximumSize(CACHE_MAX_ENTRIES) + .build(new CacheLoader, Iterable>>() { + @Override + public Iterable> load(final Class key) { + final Set> regs = new HashSet<>(); + + for (final Class type : getNotificationTypes(key)) { + @SuppressWarnings("unchecked") + final Collection> l = typeToListeners.get((Class) type); + if (l != null) { + regs.addAll(l); + } + } + + return ImmutableSet.copyOf(regs); + } + }); + + ListenerMapGeneration() { + typeToListeners = ImmutableMultimap.of(); + } + + ListenerMapGeneration(final Multimap, NotificationListenerRegistration> listeners) { + this.typeToListeners = ImmutableMultimap.copyOf(listeners); + } + + /** + * Current listeners. Exposed for creating the next generation. + * + * @return Current type-to-listener map. + */ + Multimap, NotificationListenerRegistration> getListeners() { + return typeToListeners; + } + + /** + * Look up the listeners which need to see this notification delivered. + * + * @param notification Notification object + * @return Iterable of listeners, guaranteed to be nonnull. + */ + public Iterable> listenersFor(final Notification notification) { + // Safe to use, as our loader does not throw checked exceptions + return implementationToListeners.getUnchecked(notification.getClass()); + } + + public Iterable> getKnownTypes() { + return typeToListeners.keySet(); + } + + private static Iterable> getNotificationTypes(final Class cls) { + final Class[] ifaces = cls.getInterfaces(); + return Iterables.filter(Arrays.asList(ifaces), new Predicate>() { + @Override + public boolean apply(final Class input) { + if (Notification.class.equals(input)) { + return false; + } + return Notification.class.isAssignableFrom(input); + } + }); + } +} \ No newline at end of file diff --git a/opendaylight/md-sal/sal-binding-broker/src/main/java/org/opendaylight/controller/sal/binding/impl/NotificationBrokerImpl.java b/opendaylight/md-sal/sal-binding-broker/src/main/java/org/opendaylight/controller/sal/binding/impl/NotificationBrokerImpl.java index d3b68002c3..258ba51777 100644 --- a/opendaylight/md-sal/sal-binding-broker/src/main/java/org/opendaylight/controller/sal/binding/impl/NotificationBrokerImpl.java +++ b/opendaylight/md-sal/sal-binding-broker/src/main/java/org/opendaylight/controller/sal/binding/impl/NotificationBrokerImpl.java @@ -7,90 +7,82 @@ */ package org.opendaylight.controller.sal.binding.impl; -import java.util.Arrays; -import java.util.Collections; -import java.util.HashSet; import java.util.Set; import java.util.concurrent.ExecutorService; +import java.util.concurrent.atomic.AtomicReference; + +import javax.annotation.concurrent.GuardedBy; import org.opendaylight.controller.sal.binding.api.NotificationListener; import org.opendaylight.controller.sal.binding.api.NotificationProviderService; import org.opendaylight.controller.sal.binding.codegen.impl.SingletonHolder; import org.opendaylight.controller.sal.binding.spi.NotificationInvokerFactory.NotificationInvoker; +import org.opendaylight.yangtools.concepts.AbstractListenerRegistration; import org.opendaylight.yangtools.concepts.ListenerRegistration; -import org.opendaylight.yangtools.concepts.Registration; import org.opendaylight.yangtools.concepts.util.ListenerRegistry; import org.opendaylight.yangtools.yang.binding.Notification; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import com.google.common.base.Preconditions; -import com.google.common.base.Predicate; import com.google.common.collect.HashMultimap; -import com.google.common.collect.Iterables; import com.google.common.collect.Multimap; -import com.google.common.collect.Multimaps; public class NotificationBrokerImpl implements NotificationProviderService, AutoCloseable { private static final Logger LOG = LoggerFactory.getLogger(NotificationBrokerImpl.class); private final ListenerRegistry interestListeners = ListenerRegistry.create(); + private final AtomicReference listeners = new AtomicReference<>(new ListenerMapGeneration()); + private final ExecutorService executor; - private final Multimap, NotificationListener> listeners = - Multimaps.synchronizedSetMultimap(HashMultimap., NotificationListener>create()); - private ExecutorService executor; - - @Deprecated public NotificationBrokerImpl(final ExecutorService executor) { - this.setExecutor(executor); - } - - public void setExecutor(final ExecutorService executor) { this.executor = Preconditions.checkNotNull(executor); } - public Iterable> getNotificationTypes(final Notification notification) { - final Class[] ifaces = notification.getClass().getInterfaces(); - return Iterables.filter(Arrays.asList(ifaces), new Predicate>() { - @Override - public boolean apply(final Class input) { - if (Notification.class.equals(input)) { - return false; - } - return Notification.class.isAssignableFrom(input); - } - }); - } - @Override public void publish(final Notification notification) { - this.publish(notification, executor); + publish(notification, executor); } @Override public void publish(final Notification notification, final ExecutorService service) { - Iterable> listenerToNotify = Collections.emptySet(); - for (final Class type : getNotificationTypes(notification)) { - listenerToNotify = Iterables.concat(listenerToNotify, listeners.get(((Class) type))); + for (NotificationListenerRegistration r : listeners.get().listenersFor(notification)) { + service.submit(new NotifyTask(r, notification)); } + } + + @GuardedBy("this") + private Multimap, NotificationListenerRegistration> mutableListeners() { + return HashMultimap.create(listeners.get().getListeners()); + } - final Set tasks = new HashSet<>(); - for (NotificationListener l : listenerToNotify) { - tasks.add(new NotifyTask(l, notification)); + private final void addRegistrations(final NotificationListenerRegistration... registrations) { + synchronized (this) { + final Multimap, NotificationListenerRegistration> newListeners = + mutableListeners(); + for (NotificationListenerRegistration reg : registrations) { + newListeners.put(reg.getType(), reg); + } + + listeners.set(new ListenerMapGeneration(newListeners)); } - for (final NotifyTask task : tasks) { - service.submit(task); + // Notifications are dispatched out of lock... + for (NotificationListenerRegistration reg : registrations) { + announceNotificationSubscription(reg.getType()); } } - @Override - public Registration> registerNotificationListener(final Class notificationType, final NotificationListener listener) { - final GenericNotificationRegistration reg = new GenericNotificationRegistration(notificationType, listener, this); - this.listeners.put(notificationType, listener); - this.announceNotificationSubscription(notificationType); - return reg; + private synchronized void removeRegistrations(final NotificationListenerRegistration... registrations) { + final Multimap, NotificationListenerRegistration> newListeners = + mutableListeners(); + + for (NotificationListenerRegistration reg : registrations) { + newListeners.remove(reg.getType(), reg); + } + + listeners.set(new ListenerMapGeneration(newListeners)); } private void announceNotificationSubscription(final Class notification) { @@ -105,37 +97,63 @@ public class NotificationBrokerImpl implements NotificationProviderService, Auto } @Override - public Registration registerNotificationListener(final org.opendaylight.yangtools.yang.binding.NotificationListener listener) { - final NotificationInvoker invoker = SingletonHolder.INVOKER_FACTORY.invokerFor(listener); - for (final Class notifyType : invoker.getSupportedNotifications()) { - listeners.put(notifyType, invoker.getInvocationProxy()); - announceNotificationSubscription(notifyType); - } + public ListenerRegistration registerInterestListener(final NotificationInterestListener interestListener) { + final ListenerRegistration registration = this.interestListeners.register(interestListener); - return new GeneratedListenerRegistration(listener, invoker, this); + for (final Class notification : listeners.get().getKnownTypes()) { + interestListener.onNotificationSubscribtion(notification); + } + return registration; } - protected boolean unregisterListener(final GenericNotificationRegistration reg) { - return listeners.remove(reg.getType(), reg.getInstance()); + @Override + public NotificationListenerRegistration registerNotificationListener(final Class notificationType, final NotificationListener listener) { + final NotificationListenerRegistration reg = new AbstractNotificationListenerRegistration(notificationType, listener) { + @Override + protected void removeRegistration() { + removeRegistrations(this); + } + }; + + addRegistrations(reg); + return reg; } - protected void unregisterListener(final GeneratedListenerRegistration reg) { - final NotificationInvoker invoker = reg.getInvoker(); - for (final Class notifyType : invoker.getSupportedNotifications()) { - this.listeners.remove(notifyType, invoker.getInvocationProxy()); + @Override + public ListenerRegistration registerNotificationListener(final org.opendaylight.yangtools.yang.binding.NotificationListener listener) { + final NotificationInvoker invoker = SingletonHolder.INVOKER_FACTORY.invokerFor(listener); + final Set> types = invoker.getSupportedNotifications(); + final NotificationListenerRegistration[] regs = new NotificationListenerRegistration[types.size()]; + + // Populate the registrations... + int i = 0; + for (Class type : types) { + regs[i] = new AggregatedNotificationListenerRegistration(type, invoker.getInvocationProxy(), regs) { + @Override + protected void removeRegistration() { + // Nothing to do, will be cleaned up by parent (below) + } + }; + ++i; } + + // ... now put them to use ... + addRegistrations(regs); + + // ... finally return the parent registration + return new AbstractListenerRegistration(listener) { + @Override + protected void removeRegistration() { + removeRegistrations(regs); + for (ListenerRegistration reg : regs) { + reg.close(); + } + } + }; } @Override public void close() { } - @Override - public ListenerRegistration registerInterestListener(final NotificationInterestListener interestListener) { - final ListenerRegistration registration = this.interestListeners.register(interestListener); - for (final Class notification : listeners.keySet()) { - interestListener.onNotificationSubscribtion(notification); - } - return registration; - } } diff --git a/opendaylight/md-sal/sal-binding-broker/src/main/java/org/opendaylight/controller/sal/binding/impl/NotificationListenerRegistration.java b/opendaylight/md-sal/sal-binding-broker/src/main/java/org/opendaylight/controller/sal/binding/impl/NotificationListenerRegistration.java new file mode 100644 index 0000000000..3dba868c6f --- /dev/null +++ b/opendaylight/md-sal/sal-binding-broker/src/main/java/org/opendaylight/controller/sal/binding/impl/NotificationListenerRegistration.java @@ -0,0 +1,35 @@ +/* + * Copyright (c) 2014 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.controller.sal.binding.impl; + +import org.opendaylight.controller.sal.binding.api.NotificationListener; +import org.opendaylight.yangtools.concepts.ListenerRegistration; +import org.opendaylight.yangtools.yang.binding.Notification; + +/** + * A registration of a {@link NotificationListener}. Allows query of the type + * of the notification and dispatching the notification atomically with regard + * to unregistration. + * + * @param Type of notification + */ +interface NotificationListenerRegistration extends ListenerRegistration> { + /** + * Return the interface class of the notification type. + * + * @return Notification type. + */ + Class getType(); + + /** + * Dispatch a notification to the listener. + * + * @param notification Notification to be dispatched + */ + void notify(Notification notification); +} diff --git a/opendaylight/md-sal/sal-binding-broker/src/main/java/org/opendaylight/controller/sal/binding/impl/NotifyTask.java b/opendaylight/md-sal/sal-binding-broker/src/main/java/org/opendaylight/controller/sal/binding/impl/NotifyTask.java index 5f0de6bc16..2622a71e55 100644 --- a/opendaylight/md-sal/sal-binding-broker/src/main/java/org/opendaylight/controller/sal/binding/impl/NotifyTask.java +++ b/opendaylight/md-sal/sal-binding-broker/src/main/java/org/opendaylight/controller/sal/binding/impl/NotifyTask.java @@ -7,7 +7,6 @@ */ package org.opendaylight.controller.sal.binding.impl; -import org.opendaylight.controller.sal.binding.api.NotificationListener; import org.opendaylight.yangtools.yang.binding.Notification; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -18,37 +17,37 @@ import com.google.common.base.Preconditions; class NotifyTask implements Runnable { private static final Logger LOG = LoggerFactory.getLogger(NotifyTask.class); - private final NotificationListener listener; + private final NotificationListenerRegistration registration; private final Notification notification; - public NotifyTask(final NotificationListener listener, final Notification notification) { - this.listener = Preconditions.checkNotNull(listener); + public NotifyTask(final NotificationListenerRegistration registration, final Notification notification) { + this.registration = Preconditions.checkNotNull(registration); this.notification = Preconditions.checkNotNull(notification); } @SuppressWarnings("unchecked") - private NotificationListener getListener() { - return (NotificationListener)listener; + private NotificationListenerRegistration getRegistration() { + return (NotificationListenerRegistration)registration; } @Override public void run() { if (LOG.isDebugEnabled()) { - LOG.debug("Delivering notification {} to {}", notification, listener); + LOG.debug("Delivering notification {} to {}", notification, registration.getInstance()); } else { - LOG.trace("Delivering notification {} to {}", notification.getClass().getName(), listener); + LOG.trace("Delivering notification {} to {}", notification.getClass().getName(), registration.getInstance()); } try { - getListener().onNotification(notification); + getRegistration().notify(notification); } catch (final Exception e) { - LOG.error("Unhandled exception thrown by listener: {}", listener, e); + LOG.error("Unhandled exception thrown by listener: {}", registration.getInstance(), e); } if (LOG.isDebugEnabled()) { - LOG.debug("Notification delivered {} to {}", notification, listener); + LOG.debug("Notification delivered {} to {}", notification, registration.getInstance()); } else { - LOG.trace("Notification delivered {} to {}", notification.getClass().getName(), listener); + LOG.trace("Notification delivered {} to {}", notification.getClass().getName(), registration.getInstance()); } } @@ -56,7 +55,7 @@ class NotifyTask implements Runnable { public int hashCode() { final int prime = 31; int result = 1; - result = prime * result + ((listener== null) ? 0 : listener.hashCode()); + result = prime * result + ((registration== null) ? 0 : registration.hashCode()); result = prime * result + ((notification== null) ? 0 : notification.hashCode()); return result; } @@ -70,10 +69,10 @@ class NotifyTask implements Runnable { if (getClass() != obj.getClass()) return false; NotifyTask other = (NotifyTask) obj; - if (listener == null) { - if (other.listener != null) + if (registration == null) { + if (other.registration != null) return false; - } else if (!listener.equals(other.listener)) + } else if (!registration.equals(other.registration)) return false; if (notification == null) { if (other.notification != null) @@ -86,7 +85,7 @@ class NotifyTask implements Runnable { @Override public String toString() { return Objects.toStringHelper(this) - .add("listener", listener) + .add("listener", registration) .add("notification", notification.getClass()) .toString(); }