📄 policy.java
字号:
/* * $Id: Policy.java 10489 2008-01-23 17:53:38Z dfeist $ * -------------------------------------------------------------------------------------- * Copyright (c) MuleSource, Inc. All rights reserved. http://www.mulesource.com * * The software in this package is published under the terms of the CPAL v1.0 * license, a copy of which has been included with this distribution in the * LICENSE.txt file. */package org.mule.context.notification;import org.mule.api.context.notification.ServerNotification;import org.mule.api.context.notification.ServerNotificationListener;import java.util.Collection;import java.util.HashMap;import java.util.HashSet;import java.util.Iterator;import java.util.Map;import java.util.Set;import edu.emory.mathcs.backport.java.util.concurrent.ConcurrentHashMap;import edu.emory.mathcs.backport.java.util.concurrent.ConcurrentMap;/** * For a particular configuration, this describes what events should be delivered where. * It is read-only and a lazy instance is cached by the * {@link Configuration} */class Policy{ // map from event to set of senders private Map eventToSenders = new HashMap(); // these are cumulative - set values should never change, they are just a cache of known info // they are co and contra-variant wrt to exact event type (see code below). private ConcurrentMap knownEventsExact = new ConcurrentHashMap(); private ConcurrentMap knownEventsSuper = new ConcurrentHashMap(); /** * For each listener, we check each interface and see what events can be delivered. * * @param interfaceToEvents * @param listenerSubscriptionPairs * @param disabledInterfaces * @param disabledEvents */ Policy(Map interfaceToEvents, Set listenerSubscriptionPairs, Set disabledInterfaces, Set disabledEvents) { for (Iterator pairs = listenerSubscriptionPairs.iterator(); pairs.hasNext();) { ListenerSubscriptionPair pair = (ListenerSubscriptionPair) pairs.next(); ServerNotificationListener listener = pair.getListener(); for (Iterator interfaces = interfaceToEvents.keySet().iterator(); interfaces.hasNext();) { Class iface = (Class) interfaces.next(); if (notASubclassOfAnyClassInSet(disabledInterfaces, iface)) { if (iface.isAssignableFrom(listener.getClass())) { for (Iterator events = ((Collection) interfaceToEvents.get(iface)).iterator(); events.hasNext();) { Class event = (Class) events.next(); if (notASubclassOfAnyClassInSet(disabledEvents, event)) { knownEventsExact.put(event, Boolean.TRUE); knownEventsSuper.put(event, Boolean.TRUE); if (!eventToSenders.containsKey(event)) { eventToSenders.put(event, new HashSet()); } ((Collection) eventToSenders.get(event)).add(new Sender(pair)); } } } } } } } protected static boolean notASubclassOfAnyClassInSet(Set set, Class clazz) { for (Iterator iterator = set.iterator(); iterator.hasNext();) { Class disabled = (Class) iterator.next(); if (disabled.isAssignableFrom(clazz)) { return false; } } return true; } protected static boolean notASuperclassOfAnyClassInSet(Set set, Class clazz) { for (Iterator iterator = set.iterator(); iterator.hasNext();) { Class disabled = (Class) iterator.next(); if (clazz.isAssignableFrom(disabled)) { return false; } } return true; } void dispatch(ServerNotification notification) { if (null != notification) { Class notfnClass = notification.getClass(); // search if we don't know about this event, or if we do know it is used if ((!knownEventsExact.containsKey(notfnClass)) || ((Boolean) knownEventsExact.get(notfnClass)).booleanValue()) { boolean found = false; for (Iterator events = eventToSenders.keySet().iterator(); events.hasNext();) { Class event = (Class) events.next(); if (event.isAssignableFrom(notfnClass)) { found = true; for (Iterator senders = ((Collection) eventToSenders.get(event)).iterator(); senders.hasNext();) { ((Sender) senders.next()).dispatch(notification); } } } knownEventsExact.put(notfnClass, Boolean.valueOf(found)); } } } /** * This returns a very "conservative" value - it is true if the notification or any subclass would be * accepted. So if it returns false then you can be sure that there is no need to send the * notification. On the other hand, if it returns true there is no guarantee that the notification * "really" will be dispatched to any listener. * * @param notfnClass Either the notification class being generated or some superclass * @return false if there is no need to dispatch the notification */ boolean isNotificationEnabled(Class notfnClass) { if (!knownEventsSuper.containsKey(notfnClass)) { boolean found = false; // this is exhaustive because we initialise to include all events handled. for (Iterator events = knownEventsSuper.keySet().iterator(); events.hasNext() && !found;) { Class event = (Class) events.next(); found = ((Boolean) knownEventsSuper.get(event)).booleanValue() && notfnClass.isAssignableFrom(event); } knownEventsSuper.put(notfnClass, Boolean.valueOf(found)); } if (!knownEventsExact.containsKey(notfnClass)) { boolean found = false; for (Iterator events = eventToSenders.keySet().iterator(); events.hasNext() && !found;) { Class event = (Class) events.next(); found = event.isAssignableFrom(notfnClass); } knownEventsExact.put(notfnClass, Boolean.valueOf(found)); } return ((Boolean) knownEventsSuper.get(notfnClass)).booleanValue() || ((Boolean) knownEventsExact.get(notfnClass)).booleanValue(); }}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -