Home | History | Annotate | Download | only in testing
      1 /*
      2  * Copyright (C) 2009 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.testing;
     18 
     19 import com.google.common.collect.testing.features.CollectionFeature;
     20 import com.google.common.collect.testing.features.CollectionSize;
     21 import com.google.common.collect.testing.features.MapFeature;
     22 
     23 import junit.framework.Test;
     24 import junit.framework.TestSuite;
     25 
     26 import java.io.Serializable;
     27 import java.lang.reflect.Method;
     28 import java.util.Collection;
     29 import java.util.Collections;
     30 import java.util.Comparator;
     31 import java.util.EnumMap;
     32 import java.util.HashMap;
     33 import java.util.LinkedHashMap;
     34 import java.util.Map;
     35 import java.util.Map.Entry;
     36 import java.util.concurrent.ConcurrentHashMap;
     37 
     38 /**
     39  * Generates a test suite covering the {@link Map} implementations in the
     40  * {@link java.util} package. Can be subclassed to specify tests that should
     41  * be suppressed.
     42  *
     43  * @author Kevin Bourrillion
     44  */
     45 public class TestsForMapsInJavaUtil {
     46 
     47   public static Test suite() {
     48     return new TestsForMapsInJavaUtil().allTests();
     49   }
     50 
     51   public Test allTests() {
     52     TestSuite suite = new TestSuite("java.util Maps");
     53     suite.addTest(testsForEmptyMap());
     54     suite.addTest(testsForSingletonMap());
     55     suite.addTest(testsForHashMap());
     56     suite.addTest(testsForLinkedHashMap());
     57     suite.addTest(testsForEnumMap());
     58     suite.addTest(testsForConcurrentHashMap());
     59     return suite;
     60   }
     61 
     62   protected Collection<Method> suppressForEmptyMap() {
     63     return Collections.emptySet();
     64   }
     65   protected Collection<Method> suppressForSingletonMap() {
     66     return Collections.emptySet();
     67   }
     68   protected Collection<Method> suppressForHashMap() {
     69     return Collections.emptySet();
     70   }
     71   protected Collection<Method> suppressForLinkedHashMap() {
     72     return Collections.emptySet();
     73   }
     74   protected Collection<Method> suppressForTreeMapNatural() {
     75     return Collections.emptySet();
     76   }
     77   protected Collection<Method> suppressForTreeMapWithComparator() {
     78     return Collections.emptySet();
     79   }
     80   protected Collection<Method> suppressForEnumMap() {
     81     return Collections.emptySet();
     82   }
     83   protected Collection<Method> suppressForConcurrentHashMap() {
     84     return Collections.emptySet();
     85   }
     86   protected Collection<Method> suppressForConcurrentSkipListMap() {
     87     return Collections.emptySet();
     88   }
     89 
     90   public Test testsForEmptyMap() {
     91     return MapTestSuiteBuilder
     92         .using(new TestStringMapGenerator() {
     93             @Override protected Map<String, String> create(
     94                 Entry<String, String>[] entries) {
     95               return Collections.emptyMap();
     96             }
     97           })
     98         .named("emptyMap")
     99         .withFeatures(
    100             CollectionFeature.SERIALIZABLE,
    101             CollectionSize.ZERO)
    102         .suppressing(suppressForEmptyMap())
    103         .createTestSuite();
    104   }
    105 
    106   public Test testsForSingletonMap() {
    107     return MapTestSuiteBuilder
    108         .using(new TestStringMapGenerator() {
    109             @Override protected Map<String, String> create(
    110                 Entry<String, String>[] entries) {
    111               return Collections.singletonMap(
    112                   entries[0].getKey(), entries[0].getValue());
    113             }
    114           })
    115         .named("singletonMap")
    116         .withFeatures(
    117             MapFeature.ALLOWS_NULL_KEYS,
    118             MapFeature.ALLOWS_NULL_VALUES,
    119             MapFeature.ALLOWS_ANY_NULL_QUERIES,
    120             CollectionFeature.SERIALIZABLE,
    121             CollectionSize.ONE)
    122         .suppressing(suppressForSingletonMap())
    123         .createTestSuite();
    124   }
    125 
    126   public Test testsForHashMap() {
    127     return MapTestSuiteBuilder
    128         .using(new TestStringMapGenerator() {
    129             @Override protected Map<String, String> create(
    130                 Entry<String, String>[] entries) {
    131               return toHashMap(entries);
    132             }
    133           })
    134         .named("HashMap")
    135         .withFeatures(
    136             MapFeature.GENERAL_PURPOSE,
    137             MapFeature.ALLOWS_NULL_KEYS,
    138             MapFeature.ALLOWS_NULL_VALUES,
    139             MapFeature.ALLOWS_ANY_NULL_QUERIES,
    140             MapFeature.FAILS_FAST_ON_CONCURRENT_MODIFICATION,
    141             CollectionFeature.SUPPORTS_ITERATOR_REMOVE,
    142             CollectionFeature.SERIALIZABLE,
    143             CollectionSize.ANY)
    144         .suppressing(suppressForHashMap())
    145         .createTestSuite();
    146   }
    147 
    148   public Test testsForLinkedHashMap() {
    149     return MapTestSuiteBuilder
    150         .using(new TestStringMapGenerator() {
    151             @Override protected Map<String, String> create(
    152                 Entry<String, String>[] entries) {
    153               return populate(new LinkedHashMap<String, String>(), entries);
    154             }
    155           })
    156         .named("LinkedHashMap")
    157         .withFeatures(
    158             MapFeature.GENERAL_PURPOSE,
    159             MapFeature.ALLOWS_NULL_KEYS,
    160             MapFeature.ALLOWS_NULL_VALUES,
    161             MapFeature.ALLOWS_ANY_NULL_QUERIES,
    162             MapFeature.FAILS_FAST_ON_CONCURRENT_MODIFICATION,
    163             CollectionFeature.SUPPORTS_ITERATOR_REMOVE,
    164             CollectionFeature.KNOWN_ORDER,
    165             CollectionFeature.SERIALIZABLE,
    166             CollectionSize.ANY)
    167         .suppressing(suppressForLinkedHashMap())
    168         .createTestSuite();
    169   }
    170 
    171   public Test testsForEnumMap() {
    172     return MapTestSuiteBuilder
    173         .using(new TestEnumMapGenerator() {
    174             @Override protected Map<AnEnum, String> create(
    175                 Entry<AnEnum, String>[] entries) {
    176               return populate(
    177                   new EnumMap<AnEnum, String>(AnEnum.class), entries);
    178             }
    179           })
    180         .named("EnumMap")
    181         .withFeatures(
    182             MapFeature.GENERAL_PURPOSE,
    183             MapFeature.ALLOWS_NULL_VALUES,
    184             MapFeature.RESTRICTS_KEYS,
    185             CollectionFeature.SUPPORTS_ITERATOR_REMOVE,
    186             CollectionFeature.KNOWN_ORDER,
    187             CollectionFeature.SERIALIZABLE,
    188             CollectionSize.ANY)
    189         .suppressing(suppressForEnumMap())
    190         .createTestSuite();
    191   }
    192 
    193   public Test testsForConcurrentHashMap() {
    194     return MapTestSuiteBuilder
    195         .using(new TestStringMapGenerator() {
    196           @Override protected Map<String, String> create(
    197               Entry<String, String>[] entries) {
    198             return populate(new ConcurrentHashMap<String, String>(), entries);
    199           }
    200         })
    201         .named("ConcurrentHashMap")
    202         .withFeatures(
    203             MapFeature.GENERAL_PURPOSE,
    204             CollectionFeature.SUPPORTS_ITERATOR_REMOVE,
    205             CollectionFeature.SERIALIZABLE,
    206             CollectionSize.ANY)
    207         .suppressing(suppressForConcurrentHashMap())
    208         .createTestSuite();
    209   }
    210 
    211   // TODO: IdentityHashMap, AbstractMap
    212 
    213   private static Map<String, String> toHashMap(
    214       Entry<String, String>[] entries) {
    215     return populate(new HashMap<String, String>(), entries);
    216   }
    217 
    218   // TODO: call conversion constructors or factory methods instead of using
    219   // populate() on an empty map
    220   private static <T, M extends Map<T, String>> M populate(
    221       M map, Entry<T, String>[] entries) {
    222     for (Entry<T, String> entry : entries) {
    223       map.put(entry.getKey(), entry.getValue());
    224     }
    225     return map;
    226   }
    227 
    228   static <T> Comparator<T> arbitraryNullFriendlyComparator() {
    229     return new NullFriendlyComparator<T>();
    230   }
    231 
    232   private static final class NullFriendlyComparator<T> implements Comparator<T>, Serializable {
    233     @Override
    234     public int compare(T left, T right) {
    235       return String.valueOf(left).compareTo(String.valueOf(right));
    236     }
    237   }
    238 }
    239