1 /*
2  * Copyright (C) 2007 The Guava Authors
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 package com.google.common.collect;
18 
19 import static com.google.common.base.Preconditions.checkNotNull;
20 
21 import com.google.common.collect.Synchronized.SynchronizedCollection;
22 import com.google.common.collect.Synchronized.SynchronizedSet;
23 import com.google.common.testing.SerializableTester;
24 
25 import junit.framework.TestCase;
26 
27 import java.io.Serializable;
28 import java.util.Collection;
29 import java.util.HashMap;
30 import java.util.Map;
31 import java.util.Set;
32 
33 /**
34  * Tests for {@code Synchronized#map}.
35  *
36  * @author Mike Bostock
37  */
38 public class SynchronizedMapTest extends TestCase {
39   public final Object mutex = new Integer(1); // something Serializable
40 
create()41   protected <K, V> Map<K, V> create() {
42     TestMap<K, V> inner = new TestMap<K, V>(new HashMap<K, V>(), mutex);
43     Map<K, V> outer = Synchronized.map(inner, mutex);
44     return outer;
45   }
46 
47   static class TestMap<K, V> extends ForwardingMap<K, V>
48       implements Serializable {
49     public final Object mutex;
50     private Map<K, V> delegate;
TestMap(Map<K, V> delegate, Object mutex)51     public TestMap(Map<K, V> delegate, Object mutex) {
52       checkNotNull(mutex);
53       this.delegate = delegate;
54       this.mutex = mutex;
55     }
56 
delegate()57     @Override protected Map<K, V> delegate() {
58       return delegate;
59     }
60 
size()61     @Override public int size() {
62       assertTrue(Thread.holdsLock(mutex));
63       return super.size();
64     }
65 
isEmpty()66     @Override public boolean isEmpty() {
67       assertTrue(Thread.holdsLock(mutex));
68       return super.isEmpty();
69     }
70 
remove(Object object)71     @Override public V remove(Object object) {
72       assertTrue(Thread.holdsLock(mutex));
73       return super.remove(object);
74     }
75 
clear()76     @Override public void clear() {
77       assertTrue(Thread.holdsLock(mutex));
78       super.clear();
79     }
80 
containsKey(Object key)81     @Override public boolean containsKey(Object key) {
82       assertTrue(Thread.holdsLock(mutex));
83       return super.containsKey(key);
84     }
85 
containsValue(Object value)86     @Override public boolean containsValue(Object value) {
87       assertTrue(Thread.holdsLock(mutex));
88       return super.containsValue(value);
89     }
90 
get(Object key)91     @Override public V get(Object key) {
92       assertTrue(Thread.holdsLock(mutex));
93       return super.get(key);
94     }
95 
put(K key, V value)96     @Override public V put(K key, V value) {
97       assertTrue(Thread.holdsLock(mutex));
98       return super.put(key, value);
99     }
100 
putAll(Map<? extends K, ? extends V> map)101     @Override public void putAll(Map<? extends K, ? extends V> map) {
102       assertTrue(Thread.holdsLock(mutex));
103       super.putAll(map);
104     }
105 
keySet()106     @Override public Set<K> keySet() {
107       assertTrue(Thread.holdsLock(mutex));
108       return super.keySet();
109     }
110 
values()111     @Override public Collection<V> values() {
112       assertTrue(Thread.holdsLock(mutex));
113       return super.values();
114     }
115 
entrySet()116     @Override public Set<Entry<K, V>> entrySet() {
117       assertTrue(Thread.holdsLock(mutex));
118       return super.entrySet();
119     }
120 
equals(Object obj)121     @Override public boolean equals(Object obj) {
122       assertTrue(Thread.holdsLock(mutex));
123       return super.equals(obj);
124     }
125 
hashCode()126     @Override public int hashCode() {
127       assertTrue(Thread.holdsLock(mutex));
128       return super.hashCode();
129     }
130 
toString()131     @Override public String toString() {
132       assertTrue(Thread.holdsLock(mutex));
133       return super.toString();
134     }
135 
136     private static final long serialVersionUID = 0;
137   }
138 
139   /*
140    * This is somewhat of a weak test; we verify that all of the methods are
141    * correct, but not that they're actually forwarding correctly. We also rely
142    * on the other tests (e.g., SynchronizedSetTest) to verify that the
143    * collection views are synchronized correctly.
144    */
145 
testSize()146   public void testSize() {
147     create().size();
148   }
149 
testIsEmpty()150   public void testIsEmpty() {
151     create().isEmpty();
152   }
153 
testRemove()154   public void testRemove() {
155     create().remove(null);
156   }
157 
testClear()158   public void testClear() {
159     create().clear();
160   }
161 
testContainsKey()162   public void testContainsKey() {
163     create().containsKey(null);
164   }
165 
testContainsValue()166   public void testContainsValue() {
167     create().containsValue(null);
168   }
169 
testGet()170   public void testGet() {
171     create().get(null);
172   }
173 
testPut()174   public void testPut() {
175     create().put(null, null);
176   }
177 
testPutAll()178   public void testPutAll() {
179     create().putAll(new HashMap<String, Integer>());
180   }
181 
testKeySet()182   public void testKeySet() {
183     Map<String, Integer> map = create();
184     Set<String> keySet = map.keySet();
185     assertTrue(keySet instanceof SynchronizedSet);
186     assertSame(mutex, ((SynchronizedSet<?>) keySet).mutex);
187   }
188 
testValues()189   public void testValues() {
190     Map<String, Integer> map = create();
191     Collection<Integer> values = map.values();
192     assertTrue(values instanceof SynchronizedCollection);
193     assertSame(mutex, ((SynchronizedCollection<?>) values).mutex);
194   }
195 
testEntrySet()196   public void testEntrySet() {
197     Map<String, Integer> map = create();
198     Set<Map.Entry<String, Integer>> entrySet = map.entrySet();
199     assertTrue(entrySet instanceof SynchronizedSet);
200     assertSame(mutex, ((SynchronizedSet<?>) entrySet).mutex);
201   }
202 
testEquals()203   public void testEquals() {
204     create().equals(new HashMap<String, Integer>());
205   }
206 
testHashCode()207   public void testHashCode() {
208     create().hashCode();
209   }
210 
testToString()211   public void testToString() {
212     create().toString();
213   }
214 
testSerialization()215   public void testSerialization() {
216     SerializableTester.reserializeAndAssert(create());
217   }
218 }
219