it compiles
[org.ibex.mail.git] / src / org / ibex / mail / Query.java
1 package org.ibex.mail;
2 import java.util.*;
3 import org.ibex.mail.target.*;
4
5 /**
6  *  [immutable] This class encapsulates a query against a mailbox.
7  *
8  *  The default implementation of Mailbox.query() simply retrieves
9  *  each message and calls Query.match() on it to filter out any
10  *  messages which do not match.
11  *
12  *  Production-quality Mailbox implementations will want to inspect
13  *  the Query object passed to Mailbox.query() to perform more
14  *  efficient queries.
15  */
16 public class Query {
17
18     public static Query not(Query q)      { return new Query(NOT, new Query[] { q },      0, 0, 0, null, null, null, null, null); }
19     public static Query and(Query q1, Query q2) { return new Query(AND, new Query[] {q1,q2},0,0,0,null, null, null, null, null); }
20     public static Query and(Query[] q)   { return new Query(AND, q,             0, 0, 0, null, null, null, null, null ); }
21     public static Query or(Query q1, Query q2)  { return new Query(OR,new Query[] {q1,q2},0, 0, 0, null, null, null, null, null); }
22     public static Query or(Query[] q)    { return new Query(OR,  q,                      0, 0, 0, null, null, null, null, null); }
23     public static Query uid(int min, int max)  { return new Query(UID, null, min, max, 0, null, null, null, null, null); }
24     public static Query messagenum(int min, int max) { return new Query(MESSAGENUM,null,min,max,0,null,null,null,null, null); }
25     public static Query sent(Date earliest, Date latest) { return new Query(SENT,null,0,0,0,null,null,earliest,latest,null); }
26     public static Query arrival(Date earliest, Date latest){return new Query(ARRIVAL,null,0,0,0,null,null, earliest,latest,null);}
27     public static Query header(String name, String val)  { return new Query(HEADER, null, 0, 0, 0, name, val, null, null, null);}
28     public static Query size(int min, int max)       { return new Query(SIZE, null, min, max, 0, null, null, null, null, null);}
29     public static Query flags(int flags)             { return new Query(FLAGS, null, 0, 0, flags, null, null, null, null, null);}
30     public static Query body(String text)            { return new Query(BODY, null, 0, 0, 0, null, text, null, null, null);}
31     public static Query full(String text)            { return new Query(FULL, null, 0, 0, 0, null, text, null, null, null);}
32     public static Query set(int[] set)               { return new Query(SET,  null, 0 ,0 ,0, null, null, null, null, set);}
33     public static Query all() { return new Query(ALL, null, 0, 0, 0, null, null, null, null, null); }
34
35     private Query(int type, Query[] q,int min,int max, int flags, String key, String text, Date earliest, Date latest, int[] set) {
36         this.type = type; this.q = q; this.min = min; this.max = max; this.flags = flags; this.key = key; this.text = text;
37         this.earliest = earliest; this.latest = latest; this.set = set; }
38
39     public static final int ALL        = 0;
40     public static final int NOT        = 1;
41     public static final int AND        = 2;
42     public static final int OR         = 3;
43     public static final int UID        = 4;
44     public static final int MESSAGENUM = 5; 
45     public static final int SENT       = 6;
46     public static final int ARRIVAL    = 7;
47     public static final int HEADER     = 8;
48     public static final int SIZE       = 9;
49     public static final int FLAGS      = 10;
50     public static final int BODY       = 11;
51     public static final int FULL       = 12;
52     public static final int SET        = 13;
53
54     public final int type;
55     public final Query[] q;
56     public final int min;
57     public final int max;
58     public final int flags;
59     public final String key;
60     public final String text;
61     public final Date earliest;
62     public final Date latest;
63     public final int[] set;
64
65     public boolean match(Mailbox.Iterator it) {
66         switch(type) {
67             case ALL:        return true;
68             case NOT:        return !q[0].match(it);
69             case OR:         for(int i=0; i<q.length; i++) if (q[i].match(it)) return true; return false;
70             case AND:        for(int i=0; i<q.length; i++) if (!q[i].match(it)) return false; return true;
71             case UID:        return it.uid()        >= min && it.uid() <= max;
72             case MESSAGENUM: return it.num()       >= min && it.num() <= max;
73             case SENT:       return (latest == null || it.cur().sent().before(latest))
74                                  &&(earliest == null || it.cur().sent().after(earliest));
75             case ARRIVAL:    return (latest == null || it.cur().arrived().before(latest))
76                                  &&(earliest == null || it.cur().arrived().after(earliest));
77             case SIZE:       return it.cur().size() >= min && it.cur().size() <= max;
78             case FLAGS:      return it.getFlag(flags);
79             case HEADER:     return it.cur().headers.get(key) != null && ((String)it.cur().headers.get(key)).indexOf(text) != -1;
80             case BODY:       return it.cur().body.indexOf(text) != -1;
81             case FULL:       return it.cur().body.indexOf(text) != -1 || it.cur().allHeaders.indexOf(text) != -1;
82             case SET:        for(int i=0; i<set.length; i++) if (set[i] == it.num()) return true; return false;
83             default:         throw new Error("this should not happen");
84         }
85     }
86
87 }