+ if (s.equals("NOT")) return Query.not(query(max, maxuid));
+ if (s.equals("OR")) return Query.or(query(max, maxuid), query(max, maxuid)); // FIXME parse rest of list
+ if (s.equals("AND")) return Query.and(query(max, maxuid), query(max, maxuid));
+
+ if (s.startsWith("UN")) { not = true; s = s.substring(2); }
+ if (s.equals("ANSWERED")) q = Query.answered();
+ else if (s.equals("DELETED")) q = Query.deleted();
+ else if (s.equals("ALL")) q = Query.all();
+ else if (s.equals("DRAFT")) q = Query.draft();
+ else if (s.equals("FLAGGED")) q = Query.flagged();
+ else if (s.equals("RECENT")) q = Query.recent();
+ else if (s.equals("SEEN")) q = Query.seen();
+ else if (s.equals("OLD")) { not = true; q = Query.recent(); }
+ else if (s.equals("NEW")) q = Query.and(Query.recent(), Query.not(Query.seen()));
+ else if (s.equals("KEYWORD")) q = Query.header("keyword", token().flag());
+ else if (s.equals("HEADER")) q = Query.header(token().astring(), token().astring());
+ else if (s.equals("BCC")) q = Query.header("bcc", token().astring());
+ else if (s.equals("CC")) q = Query.header("cc", token().astring());
+ else if (s.equals("FROM")) q = Query.header("from", token().astring());
+ else if (s.equals("TO")) q = Query.header("to", token().astring());
+ else if (s.equals("SUBJECT")) q = Query.header("subject", token().astring());
+ else if (s.equals("LARGER")) q = Query.size(token().n(), Integer.MAX_VALUE);
+ else if (s.equals("SMALLER")) q = Query.size(Integer.MIN_VALUE, token().n());
+ else if (s.equals("BODY")) q = Query.body(token().astring());
+ else if (s.equals("TEXT")) q = Query.full(token().astring());
+ else if (s.equals("BEFORE")) q = Query.arrival(new Date(0), token().date());
+ else if (s.equals("SINCE")) q = Query.arrival(token().date(), new Date(Long.MAX_VALUE));
+ else if (s.equals("ON")) { Date d = token().date(); q = Query.arrival(d, new Date(d.getTime() + 24 * 60 * 60)); }
+ else if (s.equals("SENTBEFORE")) q = Query.sent(new Date(0), token().date());
+ else if (s.equals("SENTSINCE")) q = Query.sent(token().date(), new Date(Long.MAX_VALUE));
+ else if (s.equals("SENTON")) { Date d = token().date(); q = Query.sent(d, new Date(d.getTime() + 24 * 60 * 60)); }
+ else if (s.equals("UID")) q = Query.uid(token().set(max));
+ q = not ? Query.not(q) : q;
+ ret = ret == null ? q : Query.and(ret, q);