1/*- 2 * See the file LICENSE for redistribution information. 3 * 4 * Copyright (c) 2000-2009 Oracle. All rights reserved. 5 * 6 * $Id$ 7 */ 8 9package com.sleepycat.collections.test; 10 11import java.util.Map; 12 13import junit.framework.Test; 14import junit.framework.TestCase; 15 16import com.sleepycat.bind.serial.StoredClassCatalog; 17import com.sleepycat.bind.serial.test.MarshalledObject; 18import com.sleepycat.collections.StoredCollection; 19import com.sleepycat.collections.StoredContainer; 20import com.sleepycat.collections.StoredIterator; 21import com.sleepycat.collections.StoredMap; 22import com.sleepycat.collections.TransactionRunner; 23import com.sleepycat.collections.TransactionWorker; 24import com.sleepycat.collections.TupleSerialFactory; 25import com.sleepycat.compat.DbCompat; 26import com.sleepycat.db.Database; 27import com.sleepycat.db.DatabaseConfig; 28import com.sleepycat.db.Environment; 29import com.sleepycat.db.SecondaryConfig; 30import com.sleepycat.db.SecondaryDatabase; 31import com.sleepycat.util.test.SharedTestUtils; 32import com.sleepycat.util.test.TestEnv; 33 34/** 35 * @author Mark Hayes 36 */ 37public class JoinTest extends TestCase 38 implements TransactionWorker { 39 40 private static final String MATCH_DATA = "d4"; // matches both keys = "yes" 41 private static final String MATCH_KEY = "k4"; // matches both keys = "yes" 42 private static final String[] VALUES = {"yes", "yes"}; 43 44 public static void main(String[] args) { 45 junit.framework.TestResult tr = 46 junit.textui.TestRunner.run(suite()); 47 if (tr.errorCount() > 0 || 48 tr.failureCount() > 0) { 49 System.exit(1); 50 } else { 51 System.exit(0); 52 } 53 } 54 55 public static Test suite() { 56 return new JoinTest(); 57 } 58 59 private Environment env; 60 private TransactionRunner runner; 61 private StoredClassCatalog catalog; 62 private TupleSerialFactory factory; 63 private Database store; 64 private SecondaryDatabase index1; 65 private SecondaryDatabase index2; 66 private StoredMap storeMap; 67 private StoredMap indexMap1; 68 private StoredMap indexMap2; 69 70 public JoinTest() { 71 72 super("JoinTest"); 73 } 74 75 @Override 76 public void setUp() 77 throws Exception { 78 79 SharedTestUtils.printTestName(getName()); 80 env = TestEnv.TXN.open(getName()); 81 runner = new TransactionRunner(env); 82 createDatabase(); 83 } 84 85 @Override 86 public void tearDown() { 87 88 try { 89 if (index1 != null) { 90 index1.close(); 91 } 92 if (index2 != null) { 93 index2.close(); 94 } 95 if (store != null) { 96 store.close(); 97 } 98 if (catalog != null) { 99 catalog.close(); 100 } 101 if (env != null) { 102 env.close(); 103 } 104 } catch (Exception e) { 105 System.out.println("Ignored exception during tearDown: " + e); 106 } finally { 107 /* Ensure that GC can cleanup. */ 108 index1 = null; 109 index2 = null; 110 store = null; 111 catalog = null; 112 env = null; 113 runner = null; 114 factory = null; 115 storeMap = null; 116 indexMap1 = null; 117 indexMap2 = null; 118 } 119 } 120 121 @Override 122 public void runTest() 123 throws Exception { 124 125 runner.run(this); 126 } 127 128 public void doWork() { 129 createViews(); 130 writeAndRead(); 131 } 132 133 private void createDatabase() 134 throws Exception { 135 136 catalog = new StoredClassCatalog(openDb("catalog.db")); 137 factory = new TupleSerialFactory(catalog); 138 assertSame(catalog, factory.getCatalog()); 139 140 store = openDb("store.db"); 141 index1 = openSecondaryDb(store, "index1.db", "1"); 142 index2 = openSecondaryDb(store, "index2.db", "2"); 143 } 144 145 private Database openDb(String file) 146 throws Exception { 147 148 DatabaseConfig config = new DatabaseConfig(); 149 DbCompat.setTypeBtree(config); 150 config.setTransactional(true); 151 config.setAllowCreate(true); 152 153 return DbCompat.testOpenDatabase(env, null, file, null, config); 154 } 155 156 private SecondaryDatabase openSecondaryDb(Database primary, 157 String file, 158 String keyName) 159 throws Exception { 160 161 SecondaryConfig secConfig = new SecondaryConfig(); 162 DbCompat.setTypeBtree(secConfig); 163 secConfig.setTransactional(true); 164 secConfig.setAllowCreate(true); 165 DbCompat.setSortedDuplicates(secConfig, true); 166 secConfig.setKeyCreator(factory.getKeyCreator(MarshalledObject.class, 167 keyName)); 168 169 return DbCompat.testOpenSecondaryDatabase 170 (env, null, file, null, primary, secConfig); 171 } 172 173 private void createViews() { 174 storeMap = factory.newMap(store, String.class, 175 MarshalledObject.class, true); 176 indexMap1 = factory.newMap(index1, String.class, 177 MarshalledObject.class, true); 178 indexMap2 = factory.newMap(index2, String.class, 179 MarshalledObject.class, true); 180 } 181 182 private void writeAndRead() { 183 // write records: Data, PrimaryKey, IndexKey1, IndexKey2 184 assertNull(storeMap.put(null, 185 new MarshalledObject("d1", "k1", "no", "yes"))); 186 assertNull(storeMap.put(null, 187 new MarshalledObject("d2", "k2", "no", "no"))); 188 assertNull(storeMap.put(null, 189 new MarshalledObject("d3", "k3", "no", "yes"))); 190 assertNull(storeMap.put(null, 191 new MarshalledObject("d4", "k4", "yes", "yes"))); 192 assertNull(storeMap.put(null, 193 new MarshalledObject("d5", "k5", "yes", "no"))); 194 195 Object o; 196 Map.Entry e; 197 198 // join values with index maps 199 o = doJoin((StoredCollection) storeMap.values()); 200 assertEquals(MATCH_DATA, ((MarshalledObject) o).getData()); 201 202 // join keySet with index maps 203 o = doJoin((StoredCollection) storeMap.keySet()); 204 assertEquals(MATCH_KEY, o); 205 206 // join entrySet with index maps 207 o = doJoin((StoredCollection) storeMap.entrySet()); 208 e = (Map.Entry) o; 209 assertEquals(MATCH_KEY, e.getKey()); 210 assertEquals(MATCH_DATA, ((MarshalledObject) e.getValue()).getData()); 211 } 212 213 private Object doJoin(StoredCollection coll) { 214 215 StoredContainer[] indices = { indexMap1, indexMap2 }; 216 StoredIterator i = coll.join(indices, VALUES, null); 217 try { 218 assertTrue(i.hasNext()); 219 Object result = i.next(); 220 assertNotNull(result); 221 assertFalse(i.hasNext()); 222 return result; 223 } finally { i.close(); } 224 } 225} 226