1461
|
1 package goodjava.lucene.logging;
|
|
2
|
|
3 import java.io.File;
|
|
4 import java.io.RandomAccessFile;
|
|
5 import java.io.IOException;
|
|
6 import java.util.List;
|
|
7 import java.util.ArrayList;
|
|
8 import java.util.Map;
|
|
9 import java.util.LinkedHashMap;
|
|
10 import org.apache.lucene.index.Term;
|
|
11 import org.apache.lucene.search.Query;
|
|
12 import org.apache.lucene.search.MatchAllDocsQuery;
|
|
13 import org.apache.lucene.search.TermQuery;
|
|
14 import org.apache.lucene.search.PrefixQuery;
|
|
15 import org.apache.lucene.search.WildcardQuery;
|
|
16 import org.apache.lucene.search.TermRangeQuery;
|
|
17 import org.apache.lucene.search.PhraseQuery;
|
|
18 import org.apache.lucene.search.NumericRangeQuery;
|
|
19 import org.apache.lucene.search.BooleanQuery;
|
|
20 import org.apache.lucene.search.BooleanClause;
|
|
21 import org.apache.lucene.util.BytesRef;
|
1465
|
22 import goodjava.logging.Logger;
|
|
23 import goodjava.logging.LoggerFactory;
|
1461
|
24
|
|
25
|
1462
|
26 public class LogFile extends RandomAccessFile {
|
1465
|
27 private static final Logger logger = LoggerFactory.getLogger(LogFile.class);
|
|
28 public final File file;
|
1461
|
29 private long end;
|
|
30
|
|
31 public LogFile(File file,String mode) throws IOException {
|
|
32 super(file,mode);
|
1465
|
33 this.file = file;
|
1461
|
34 init();
|
|
35 }
|
|
36
|
|
37 private void init() throws IOException {
|
|
38 if( length() == 0 ) {
|
|
39 end = 8;
|
|
40 writeLong(end);
|
|
41 } else {
|
|
42 seek(0L);
|
|
43 end = readLong();
|
|
44 gotoEnd();
|
|
45 }
|
|
46 }
|
|
47
|
1465
|
48 public String toString() {
|
|
49 return "LogFile<" + file.getName() + ">";
|
|
50 }
|
|
51
|
1461
|
52 public void gotoStart() throws IOException {
|
|
53 seek(8L);
|
|
54 }
|
|
55
|
|
56 public void gotoEnd() throws IOException {
|
|
57 seek(end);
|
|
58 }
|
|
59
|
|
60 public void commit() throws IOException {
|
|
61 end = getFilePointer();
|
|
62 seek(0L);
|
|
63 writeLong(end);
|
|
64 gotoEnd();
|
|
65 }
|
|
66
|
|
67 public boolean hasMore() throws IOException {
|
|
68 return getFilePointer() < end;
|
|
69 }
|
|
70
|
|
71 private static final int TYPE_NULL = 0;
|
|
72 private static final int TYPE_STRING = 1;
|
|
73 private static final int TYPE_INT = 2;
|
|
74 private static final int TYPE_LONG = 3;
|
|
75 private static final int TYPE_FLOAT = 4;
|
|
76 private static final int TYPE_DOUBLE = 5;
|
|
77 private static final int TYPE_BYTES = 6;
|
|
78 private static final int TYPE_LIST = 7;
|
|
79 private static final int TYPE_QUERY_MATCH_ALL_DOCS = 8;
|
|
80 private static final int TYPE_QUERY_TERM = 9;
|
|
81 private static final int TYPE_QUERY_PREFIX = 10;
|
|
82 private static final int TYPE_QUERY_WILDCARD = 11;
|
|
83 private static final int TYPE_QUERY_TERM_RANGE = 12;
|
|
84 private static final int TYPE_QUERY_PHRASE = 13;
|
|
85 private static final int TYPE_QUERY_NUMERIC_RANGE = 14;
|
|
86 private static final int TYPE_QUERY_BOOLEAN = 15;
|
|
87
|
|
88 public void writeObject(Object obj) throws IOException {
|
|
89 if( obj==null ) {
|
|
90 writeByte(TYPE_NULL);
|
|
91 return;
|
|
92 }
|
|
93 if( obj instanceof String ) {
|
|
94 writeByte(TYPE_STRING);
|
|
95 writeUTF((String)obj);
|
|
96 return;
|
|
97 }
|
|
98 if( obj instanceof Integer ) {
|
|
99 writeByte(TYPE_INT);
|
|
100 writeInt((Integer)obj);
|
|
101 return;
|
|
102 }
|
|
103 if( obj instanceof Long ) {
|
|
104 writeByte(TYPE_LONG);
|
|
105 writeLong((Long)obj);
|
|
106 return;
|
|
107 }
|
|
108 if( obj instanceof Float ) {
|
|
109 writeByte(TYPE_FLOAT);
|
|
110 writeFloat((Float)obj);
|
|
111 return;
|
|
112 }
|
|
113 if( obj instanceof Double ) {
|
|
114 writeByte(TYPE_DOUBLE);
|
|
115 writeDouble((Double)obj);
|
|
116 return;
|
|
117 }
|
|
118 if( obj instanceof byte[] ) {
|
|
119 writeByte(TYPE_BYTES);
|
|
120 writeByteArray((byte[])obj);
|
|
121 return;
|
|
122 }
|
|
123 if( obj instanceof List ) {
|
|
124 writeByte(TYPE_LIST);
|
|
125 writeList((List)obj);
|
|
126 return;
|
|
127 }
|
|
128 if( obj instanceof MatchAllDocsQuery ) {
|
|
129 writeByte(TYPE_QUERY_MATCH_ALL_DOCS);
|
|
130 return;
|
|
131 }
|
|
132 if( obj instanceof TermQuery ) {
|
|
133 writeByte(TYPE_QUERY_TERM);
|
|
134 TermQuery query = (TermQuery)obj;
|
|
135 writeTerm( query.getTerm() );
|
|
136 return;
|
|
137 }
|
|
138 if( obj instanceof PrefixQuery ) {
|
|
139 writeByte(TYPE_QUERY_PREFIX);
|
|
140 PrefixQuery query = (PrefixQuery)obj;
|
|
141 writeTerm( query.getPrefix() );
|
|
142 return;
|
|
143 }
|
|
144 if( obj instanceof WildcardQuery ) {
|
|
145 writeByte(TYPE_QUERY_TERM_RANGE);
|
|
146 WildcardQuery query = (WildcardQuery)obj;
|
|
147 writeTerm( query.getTerm() );
|
|
148 return;
|
|
149 }
|
|
150 if( obj instanceof TermRangeQuery ) {
|
|
151 writeByte(TYPE_QUERY_TERM_RANGE);
|
|
152 TermRangeQuery query = (TermRangeQuery)obj;
|
|
153 writeUTF( query.getField() );
|
|
154 writeBytesRef( query.getLowerTerm() );
|
|
155 writeBytesRef( query.getUpperTerm() );
|
|
156 writeBoolean( query.includesLower() );
|
|
157 writeBoolean( query.includesUpper() );
|
|
158 return;
|
|
159 }
|
|
160 if( obj instanceof PhraseQuery ) {
|
|
161 writeByte(TYPE_QUERY_PHRASE);
|
|
162 PhraseQuery query = (PhraseQuery)obj;
|
|
163 Term[] terms = query.getTerms();
|
|
164 int[] positions = query.getPositions();
|
|
165 if( terms.length != positions.length )
|
|
166 throw new RuntimeException();
|
|
167 writeInt( terms.length );
|
|
168 for( int i=0; i<terms.length; i++ ) {
|
|
169 writeTerm( terms[i] );
|
|
170 writeInt( positions[i] );
|
|
171 }
|
|
172 return;
|
|
173 }
|
|
174 if( obj instanceof NumericRangeQuery ) {
|
|
175 writeByte(TYPE_QUERY_NUMERIC_RANGE);
|
|
176 NumericRangeQuery query = (NumericRangeQuery)obj;
|
|
177 writeUTF( query.getField() );
|
|
178 writeObject( query.getMin() );
|
|
179 writeObject( query.getMax() );
|
|
180 writeBoolean( query.includesMin() );
|
|
181 writeBoolean( query.includesMax() );
|
|
182 return;
|
|
183 }
|
|
184 if( obj instanceof BooleanQuery ) {
|
|
185 writeByte(TYPE_QUERY_BOOLEAN);
|
|
186 BooleanQuery query = (BooleanQuery)obj;
|
|
187 BooleanClause[] a = query.getClauses();
|
|
188 writeInt(a.length);
|
|
189 for( BooleanClause bc : a ) {
|
|
190 writeQuery( bc.getQuery() );
|
|
191 writeUTF( bc.getOccur().name() );
|
|
192 }
|
|
193 return;
|
|
194 }
|
|
195 throw new IllegalArgumentException("invalid type for "+obj);
|
|
196 }
|
|
197
|
|
198 public Object readObject() throws IOException {
|
|
199 int type = readByte();
|
1462
|
200 return readObject(type);
|
|
201 }
|
|
202
|
|
203 protected Object readObject(int type) throws IOException {
|
1461
|
204 switch(type) {
|
|
205 case TYPE_NULL:
|
|
206 return null;
|
|
207 case TYPE_STRING:
|
|
208 return readUTF();
|
|
209 case TYPE_INT:
|
|
210 return readInt();
|
|
211 case TYPE_LONG:
|
|
212 return readLong();
|
|
213 case TYPE_FLOAT:
|
|
214 return readFloat();
|
|
215 case TYPE_DOUBLE:
|
|
216 return readDouble();
|
|
217 case TYPE_BYTES:
|
|
218 return readByteArray();
|
|
219 case TYPE_LIST:
|
|
220 return readList();
|
|
221 case TYPE_QUERY_MATCH_ALL_DOCS:
|
|
222 return new MatchAllDocsQuery();
|
|
223 case TYPE_QUERY_TERM:
|
|
224 return new TermQuery( readTerm() );
|
|
225 case TYPE_QUERY_PREFIX:
|
|
226 return new PrefixQuery( readTerm() );
|
|
227 case TYPE_QUERY_WILDCARD:
|
|
228 return new WildcardQuery( readTerm() );
|
|
229 case TYPE_QUERY_TERM_RANGE:
|
|
230 {
|
|
231 String field = readUTF();
|
|
232 BytesRef lowerTerm = readBytesRef();
|
|
233 BytesRef upperTerm = readBytesRef();
|
|
234 boolean includeLower = readBoolean();
|
|
235 boolean includeUpper = readBoolean();
|
|
236 return new TermRangeQuery(field,lowerTerm,upperTerm,includeLower,includeUpper);
|
|
237 }
|
|
238 case TYPE_QUERY_PHRASE:
|
|
239 {
|
|
240 PhraseQuery query = new PhraseQuery();
|
|
241 int n = readInt();
|
|
242 for( int i=0; i<n; i++ ) {
|
|
243 Term term = readTerm();
|
|
244 int position = readInt();
|
|
245 query.add(term,position);
|
|
246 }
|
|
247 return query;
|
|
248 }
|
|
249 case TYPE_QUERY_NUMERIC_RANGE:
|
|
250 {
|
|
251 String field = readUTF();
|
|
252 Number min = (Number)readObject();
|
|
253 Number max = (Number)readObject();
|
|
254 boolean minInclusive = readBoolean();
|
|
255 boolean maxInclusive = readBoolean();
|
|
256 Number n = min!=null ? min : max;
|
|
257 if( n instanceof Integer )
|
|
258 return NumericRangeQuery.newIntRange(field,(Integer)min,(Integer)max,minInclusive,maxInclusive);
|
|
259 if( n instanceof Long )
|
|
260 return NumericRangeQuery.newLongRange(field,(Long)min,(Long)max,minInclusive,maxInclusive);
|
|
261 if( n instanceof Float )
|
|
262 return NumericRangeQuery.newFloatRange(field,(Float)min,(Float)max,minInclusive,maxInclusive);
|
|
263 if( n instanceof Double )
|
|
264 return NumericRangeQuery.newDoubleRange(field,(Double)min,(Double)max,minInclusive,maxInclusive);
|
|
265 throw new RuntimeException("bad numeric type for "+n);
|
|
266 }
|
|
267 case TYPE_QUERY_BOOLEAN:
|
|
268 {
|
|
269 BooleanQuery query = new BooleanQuery();
|
|
270 int n = readInt();
|
|
271 for( int i=0; i<n; i++ ) {
|
|
272 Query subquery = readQuery();
|
|
273 BooleanClause.Occur occur = BooleanClause.Occur.valueOf( readUTF() );
|
|
274 query.add(subquery,occur);
|
|
275 }
|
|
276 return query;
|
|
277 }
|
|
278 default:
|
|
279 throw new RuntimeException("invalid type "+type);
|
|
280 }
|
|
281 }
|
|
282
|
|
283 public void writeByteArray(byte[] bytes) throws IOException {
|
|
284 writeInt(bytes.length);
|
|
285 write(bytes);
|
|
286 }
|
|
287
|
|
288 public byte[] readByteArray() throws IOException {
|
|
289 int len = readInt();
|
|
290 byte[] bytes = new byte[len];
|
|
291 readFully(bytes);
|
|
292 return bytes;
|
|
293 }
|
|
294
|
|
295 public void writeList(List list) throws IOException {
|
|
296 writeInt(list.size());
|
|
297 for( Object obj : list ) {
|
|
298 writeObject(obj);
|
|
299 }
|
|
300 }
|
|
301
|
|
302 public List readList() throws IOException {
|
|
303 final int size = readInt();
|
|
304 List list = new ArrayList(size);
|
|
305 for( int i=0; i<size; i++ ) {
|
|
306 list.add( readObject() );
|
|
307 }
|
|
308 return list;
|
|
309 }
|
|
310
|
|
311 public void writeMap(Map map) throws IOException {
|
|
312 writeInt(map.size());
|
|
313 for( Object obj : map.entrySet() ) {
|
|
314 Map.Entry entry = (Map.Entry)obj;
|
|
315 writeObject( entry.getKey() );
|
|
316 writeObject( entry.getValue() );
|
|
317 }
|
|
318 }
|
|
319
|
|
320 public Map readMap() throws IOException {
|
|
321 final int size = readInt();
|
|
322 Map map = new LinkedHashMap();
|
|
323 for( int i=0; i<size; i++ ) {
|
|
324 Object key = readObject();
|
|
325 Object value = readObject();
|
|
326 map.put(key,value);
|
|
327 }
|
|
328 return map;
|
|
329 }
|
|
330
|
|
331 public void writeQuery(Query query) throws IOException {
|
|
332 writeObject(query);
|
|
333 }
|
|
334
|
|
335 public Query readQuery() throws IOException {
|
|
336 return (Query)readObject();
|
|
337 }
|
|
338
|
|
339 public void writeBytesRef(BytesRef br) throws IOException {
|
|
340 writeInt(br.length);
|
|
341 write(br.bytes,0,br.length);
|
|
342 }
|
|
343
|
|
344 public BytesRef readBytesRef() throws IOException {
|
|
345 return new BytesRef( readByteArray() );
|
|
346 }
|
|
347
|
|
348 public void writeTerm(Term term) throws IOException {
|
|
349 writeUTF(term.field());
|
|
350 writeBytesRef( term.bytes() );
|
|
351 }
|
|
352
|
|
353 public Term readTerm() throws IOException {
|
|
354 String key = readUTF();
|
|
355 BytesRef value = readBytesRef();
|
|
356 return new Term(key,value);
|
|
357 }
|
|
358
|
|
359 }
|