comparison src/luan/modules/lucene/LuceneIndex.java @ 1271:48f302bdc187

fix indexed_only_field
author Franklin Schmidt <fschmidt@gmail.com>
date Mon, 12 Nov 2018 21:19:52 -0700
parents 9fa8b8389578
children 25746915a241
comparison
equal deleted inserted replaced
1270:d410747a671a 1271:48f302bdc187
70 import luan.modules.Utils; 70 import luan.modules.Utils;
71 import luan.Luan; 71 import luan.Luan;
72 import luan.LuanState; 72 import luan.LuanState;
73 import luan.LuanTable; 73 import luan.LuanTable;
74 import luan.LuanFunction; 74 import luan.LuanFunction;
75 import luan.LuanCloner;
75 import luan.LuanException; 76 import luan.LuanException;
76 import luan.LuanRuntimeException; 77 import luan.LuanRuntimeException;
77 import org.slf4j.Logger; 78 import org.slf4j.Logger;
78 import org.slf4j.LoggerFactory; 79 import org.slf4j.LoggerFactory;
79 80
92 private DirectoryReader reader; 93 private DirectoryReader reader;
93 private IndexSearcher searcher; 94 private IndexSearcher searcher;
94 private final ThreadLocal<IndexSearcher> threadLocalSearcher = new ThreadLocal<IndexSearcher>(); 95 private final ThreadLocal<IndexSearcher> threadLocalSearcher = new ThreadLocal<IndexSearcher>();
95 private boolean isClosed = true; 96 private boolean isClosed = true;
96 private final MultiFieldParser mfp; 97 private final MultiFieldParser mfp;
97 public final LuanTable indexed_only_fields;
98 private final Analyzer analyzer; 98 private final Analyzer analyzer;
99 private final Exception created = new Exception("created"); 99 private final Exception created = new Exception("created");
100 100
101 private static ConcurrentMap<File,AtomicInteger> globalWriteCounters = new ConcurrentHashMap<File,AtomicInteger>(); 101 private static ConcurrentMap<File,AtomicInteger> globalWriteCounters = new ConcurrentHashMap<File,AtomicInteger>();
102 private File fileDir; 102 private File fileDir;
103 private int writeCount; 103 private int writeCount;
104 104
105 private final ConcurrentMap<String,Map<String,LuanFunction>> indexedOnlyFields = new ConcurrentHashMap<String,Map<String,LuanFunction>>();
106 private final LuanState luanMine = new LuanState();
107 private final LuanCloner cloner = new LuanCloner(LuanCloner.Type.COMPLETE);
108
105 public LuceneIndex(LuanState luan,String indexDirStr,FieldParser defaultFieldParser,String[] defaultFields) 109 public LuceneIndex(LuanState luan,String indexDirStr,FieldParser defaultFieldParser,String[] defaultFields)
106 throws LuanException, IOException 110 throws LuanException, IOException
107 { 111 {
108 indexed_only_fields = new LuanTable(luan); // not good, not thread safe
109 mfp = defaultFieldParser==null ? new MultiFieldParser() : new MultiFieldParser(defaultFieldParser,defaultFields); 112 mfp = defaultFieldParser==null ? new MultiFieldParser() : new MultiFieldParser(defaultFieldParser,defaultFields);
110 mfp.fields.put( "type", STRING_FIELD_PARSER ); 113 mfp.fields.put( "type", STRING_FIELD_PARSER );
111 mfp.fields.put( "id", NumberFieldParser.LONG ); 114 mfp.fields.put( "id", NumberFieldParser.LONG );
112 File indexDir = new File(indexDirStr); 115 File indexDir = new File(indexDirStr);
113 this.indexDir = indexDir; 116 this.indexDir = indexDir;
176 wrote(); 179 wrote();
177 writeLock.unlock(); 180 writeLock.unlock();
178 } 181 }
179 } 182 }
180 183
184 public void indexed_only_field(String type,String field,LuanFunction fn) {
185 fn = (LuanFunction)cloner.get(fn);
186 indexedOnlyFields.putIfAbsent(type,new ConcurrentHashMap<String,LuanFunction>());
187 Map<String,LuanFunction> map = indexedOnlyFields.get(type);
188 map.put(field,fn);
189 }
190
181 public void save(LuanState luan,LuanTable doc) throws LuanException, IOException { 191 public void save(LuanState luan,LuanTable doc) throws LuanException, IOException {
182 Set indexedOnlySet = new HashSet(); 192 Set indexedOnlySet = new HashSet();
183 Object typeObj = doc.get("type"); 193 Object typeObj = doc.get("type");
184 if( typeObj==null ) 194 if( typeObj==null )
185 throw new LuanException("missing 'type' field"); 195 throw new LuanException("missing 'type' field");
186 if( !(typeObj instanceof String) ) 196 if( !(typeObj instanceof String) )
187 throw new LuanException("type must be string"); 197 throw new LuanException("type must be string");
188 String type = (String)typeObj; 198 String type = (String)typeObj;
189 Object indexedOnlyObj = indexed_only_fields.get(type); 199 Map<String,LuanFunction> map = indexedOnlyFields.get(type);
190 if( indexedOnlyObj != null ) { 200 if( map != null ) {
191 if( !(indexedOnlyObj instanceof LuanTable) ) 201 for( Map.Entry<String,LuanFunction> entry : map.entrySet() ) {
192 throw new LuanException("indexed_only_fields elements must be tables"); 202 String name = entry.getKey();
193 LuanTable indexedOnly = (LuanTable)indexedOnlyObj; 203 LuanFunction fn = entry.getValue();
194 for( Map.Entry<Object,Object> entry : indexedOnly.iterable() ) { 204 Object value = Luan.first(fn.call(luan,new Object[]{doc}));
195 Object key = entry.getKey();
196 if( !(key instanceof String) )
197 throw new LuanException("indexed_only_fields."+type+" entries must be strings");
198 String name = (String)key;
199 Object value = entry.getValue();
200 if( !(value instanceof LuanFunction) )
201 throw new LuanException("indexed_only_fields."+type+" values must be functions");
202 LuanFunction fn = (LuanFunction)value;
203 value = Luan.first(fn.call(luan,new Object[]{doc}));
204 doc.put( name, value ); 205 doc.put( name, value );
205 indexedOnlySet.add(name); 206 indexedOnlySet.add(name);
206 } 207 }
207 } 208 }
208 Object obj = doc.get("id"); 209 Object obj = doc.get("id");