spring 事件模式 源代码导读

一,jdk 事件对象基类
package java.util;

import java.io.Serializable;

public class EventObject
  implements Serializable
{
  protected transient Object source;

  public Object getSource()
  {
    return this.source;
  }

  public EventObject(Object paramObject)
  {
    if (paramObject == null)
      throw new IllegalArgumentException("null source");
    this.source = paramObject;
  }

  public String toString()
  {
    return getClass().getName() + "[source=" + this.source + "]";
  }
}
2。spring事件基类
public abstract class ApplicationEvent extends EventObject {

	/** use serialVersionUID from Spring 1.2 for interoperability */
	private static final long serialVersionUID = 7099057708183571937L;

	/** System time when the event happened */
	private final long timestamp;


	/**
	 * Create a new ApplicationEvent.
	 * @param source the component that published the event (never <code>null</code>)
	 */
	public ApplicationEvent(Object source) {
		super(source);
		this.timestamp = System.currentTimeMillis();
	}


	/**
	 * Return the system time in milliseconds when the event happened.
	 */
	public final long getTimestamp() {
		return this.timestamp;
	}

}
3,ApplicationContextEvent基类
public abstract class ApplicationContextEvent extends ApplicationEvent {

	/**
	 * Create a new ContextStartedEvent.
	 * @param source the <code>ApplicationContext</code> that the event is raised for
	 * (must not be <code>null</code>)
	 */
	public ApplicationContextEvent(ApplicationContext source) {
		super(source);
	}

	/**
	 * Get the <code>ApplicationContext</code> that the event was raised for.
	 */
	public final ApplicationContext getApplicationContext() {
		return (ApplicationContext) getSource();
	}

}
4。容器关闭事件
public class ContextClosedEvent extends ApplicationContextEvent {

	/**
	 * Creates a new ContextClosedEvent.
	 * @param source the <code>ApplicationContext</code> that has been closed
	 * (must not be <code>null</code>)
	 */
	public ContextClosedEvent(ApplicationContext source) {
		super(source);
	}

}
5,AbstractApplicationContext中fireclose事件

	public void publishEvent(ApplicationEvent event) {
		Assert.notNull(event, "Event must not be null");
		if (logger.isTraceEnabled()) {
			logger.trace("Publishing event in " + getDisplayName() + ": " + event);
		}
		getApplicationEventMulticaster().multicastEvent(event);
		if (this.parent != null) {
			this.parent.publishEvent(event);
		}
	}

6,事件处理监听器控制器(SimpleApplicationEventMulticaster)
	@SuppressWarnings("unchecked")
	public void multicastEvent(final ApplicationEvent event) {
		for (final ApplicationListener listener : getApplicationListeners(event)) {
			Executor executor = getTaskExecutor();
			if (executor != null) {
				executor.execute(new Runnable() {
					@SuppressWarnings("unchecked")
					public void run() {
						listener.onApplicationEvent(event);
					}
				});
			}
			else {
				listener.onApplicationEvent(event);
			}
		}
	}
7。AbstractApplicationEventMulticaster获取注冊close事件的监听器
	protected Collection<applicationlistener> getApplicationListeners(ApplicationEvent event) {
		Class<? extends ApplicationEvent> eventType = event.getClass();
		Class sourceType = event.getSource().getClass();
		ListenerCacheKey cacheKey = new ListenerCacheKey(eventType, sourceType);
		ListenerRetriever retriever = this.retrieverCache.get(cacheKey);
		if (retriever != null) {
			return retriever.getApplicationListeners();
		}
		else {
			retriever = new ListenerRetriever(true);
			LinkedList<applicationlistener> allListeners = new LinkedList<applicationlistener>();
			synchronized (this.defaultRetriever) {
				for (ApplicationListener listener : this.defaultRetriever.applicationListeners) {
					if (supportsEvent(listener, eventType, sourceType)) {
						retriever.applicationListeners.add(listener);
						allListeners.add(listener);
					}
				}
				if (!this.defaultRetriever.applicationListenerBeans.isEmpty()) {
					BeanFactory beanFactory = getBeanFactory();
					for (String listenerBeanName : this.defaultRetriever.applicationListenerBeans) {
						ApplicationListener listener = beanFactory.getBean(listenerBeanName, ApplicationListener.class);
						if (!allListeners.contains(listener) && supportsEvent(listener, eventType, sourceType)) {
							retriever.applicationListenerBeans.add(listenerBeanName);
							allListeners.add(listener);
						}
					}
				}
				OrderComparator.sort(allListeners);
				this.retrieverCache.put(cacheKey, retriever);
			}
			return allListeners;
		}
	}



二,
1,监听器基类
public  interface EventListener
{
}
2,spring监听器基类
public interface ApplicationListener<e extends="" applicationevent=""> extends EventListener {

	/**
	 * Handle an application event.
	 * @param event the event to respond to
	 */
	void onApplicationEvent(E event);

}
3。AbstractApplicationContext加入监听
	public void addApplicationListener(ApplicationListener<?> listener) {
		if (this.applicationEventMulticaster != null) {
			this.applicationEventMulticaster.addApplicationListener(listener);
		}
		else {
			this.applicationListeners.add(listener);
		}
	}
4,加入listenner到AbstractApplicationEventMulticaster
public void addApplicationListener(ApplicationListener listener) {
		synchronized (this.defaultRetriever) {
			this.defaultRetriever.applicationListeners.add(listener);
			this.retrieverCache.clear();
		}
	}
5,监听处理类注冊入口AbstractApplicationContext
		public Object postProcessAfterInitialization(Object bean, String beanName) {
			if (bean instanceof ApplicationListener) {
				// potentially not detected as a listener by getBeanNamesForType retrieval
				Boolean flag = this.singletonNames.get(beanName);
				if (Boolean.TRUE.equals(flag)) {
					// singleton bean (top-level or inner): register on the fly
					addApplicationListener((ApplicationListener<?>) bean);
				}
				else if (flag == null) {
					if (logger.isWarnEnabled() && !containsBean(beanName)) {
						// inner bean with other scope - can't reliably process events
						logger.warn("Inner bean '" + beanName + "' implements ApplicationListener interface " +
								"but is not reachable for event multicasting by its containing ApplicationContext " +
								"because it does not have singleton scope. Only top-level listener beans are allowed " +
								"to be of non-singleton scope.");
					}
					this.singletonNames.put(beanName, Boolean.FALSE);
				}
			}
			return bean;
		}

</e></applicationlistener></applicationlistener></applicationlistener>
原文地址:https://www.cnblogs.com/mthoutai/p/6857898.html