View Javadoc

1   package net.sf.josceleton.core.impl.async;
2   
3   import java.util.Collection;
4   import java.util.HashMap;
5   import java.util.HashSet;
6   import java.util.Map;
7   
8   import net.sf.josceleton.core.api.async.AsyncFor;
9   import net.sf.josceleton.core.api.async.Listener;
10  
11  import org.apache.commons.logging.Log;
12  import org.apache.commons.logging.LogFactory;
13  
14  /**
15   * Can either be used as an super class (and extending from it) or by delegating to a private member instance.
16   * 
17   * @since 0.4
18   */
19  public class DefaultAsyncFor<K, L extends Listener> implements AsyncFor<K, L> {
20  	
21  	private static final Log LOG = LogFactory.getLog(DefaultAsync.class);
22  	
23  	
24  	private final Map<K, Collection<L>> listenersByKey = new HashMap<K, Collection<L>>();
25  	
26  
27  	/** {@inheritDoc} from {@link AsyncFor} */
28  	@Override public final void addListenerFor(final K key, final L listener) {
29  		this.beforeAddListener(key, listener);
30  		this.initListenersFor(key);
31  		
32  		final Collection<L> registeredListeners = this.listenersByKey.get(key);
33  		final boolean wasChanged = registeredListeners.add(listener);
34  		if(wasChanged == false) {
35  			LOG.warn("Not added listener [" + listener + "] as it was yet added for key [" + key + "]!");
36  		}
37  	}
38  
39  	/** {@inheritDoc} from {@link AsyncFor} */
40  	@Override public final void removeListenerFor(final K key, final L listener) {
41  		this.beforeRemoveListener(key, listener);
42  		
43  		final Collection<L> registeredListeners = this.listenersByKey.get(key);
44  		if(registeredListeners == null) {
45  			LOG.warn("Not removed listener [" + listener + "] as _nothing_ was yet added for key [" + key + "]!");
46  			return;
47  		}
48  		
49  		final boolean wasRemoved = registeredListeners.remove(listener);
50  		if(wasRemoved == false) {
51  			LOG.warn("Not removed listener [" + listener + "] as it was not yet added for key [" + key + "]!");
52  		}
53  	}
54  	/**
55  	 * @since 0.4
56  	 */
57  	protected final Collection<L> getListenersFor(final K key) {
58  		this.initListenersFor(key);
59  		return this.listenersByKey.get(key);
60  	}
61  	
62  	private void initListenersFor(final K key) {
63  		if(this.listenersByKey.containsKey(key) == false) {
64  			this.listenersByKey.put(key, new HashSet<L>());
65  		}
66  	}
67  	
68  	
69  	/**
70  	 * Will be used to check if <code>Closeable</code> was not yet closed.
71  	 * 
72  	 * @since 0.4
73  	 */
74  	@SuppressWarnings("unused")
75  	protected void beforeAddListener(final K key, final L listener) {
76  		// can be overridden
77  	}
78  
79  	/**
80  	 * Will be used to check if <code>Closeable</code> was not yet closed.
81  	 * 
82  	 * @since 0.4
83  	 */
84  	@SuppressWarnings("unused")
85  	protected void beforeRemoveListener(final K key, final L listener) {
86  		// can be overridden
87  	}
88  
89  }