View Javadoc

1   /*
2    * Licensed to the Apache Software Foundation (ASF) under one or more
3    * contributor license agreements.  See the NOTICE file distributed with
4    * this work for additional information regarding copyright ownership.
5    * The ASF licenses this file to You under the Apache License, Version 2.0
6    * (the "License"); you may not use this file except in compliance with
7    * the License.  You may obtain a copy of the License at
8    *
9    *      http://www.apache.org/licenses/LICENSE-2.0
10   *
11   * Unless required by applicable law or agreed to in writing, software
12   * distributed under the License is distributed on an "AS IS" BASIS,
13   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14   * See the License for the specific language governing permissions and
15   * limitations under the License.
16   */
17  
18  package org.apache.commons.net.imap;
19  
20  import java.io.IOException;
21  
22  /**
23   * The IMAPClient class provides the basic functionalities found in an
24   * IMAP client.
25   */
26  public class IMAPClient extends IMAP
27  {
28  
29      // --------- commands available in all states
30  
31      /**
32       * Send a CAPABILITY command to the server.
33       * @return {@code true} if the command was successful,{@code false} if not.
34       * @exception IOException If a network I/O error occurs
35       */
36      public boolean capability() throws IOException
37      {
38          return doCommand (IMAPCommand.CAPABILITY);
39      }
40  
41      /**
42       * Send a NOOP command to the server.  This is useful for keeping
43       * a connection alive since most IMAP servers will timeout after 10
44       * minutes of inactivity.
45       * @return {@code true} if the command was successful,{@code false} if not.
46       * @exception IOException If a network I/O error occurs.
47       */
48      public boolean noop() throws IOException
49      {
50          return doCommand (IMAPCommand.NOOP);
51      }
52  
53      /**
54       * Send a LOGOUT command to the server.  To fully disconnect from the server
55       * you must call disconnect().
56       * A logout attempt is valid in any state.  If
57       * the client is in the not authenticated or authenticated state, it enters the
58       * logout on a successful logout.
59       * @return {@code true} if the command was successful,{@code false} if not.
60       * @exception IOException If a network I/O error occurs.
61       */
62      public boolean logout() throws IOException
63      {
64          return doCommand (IMAPCommand.LOGOUT);
65      }
66  
67      // --------- commands available in the not-authenticated state
68      // STARTTLS skipped - see IMAPSClient.
69      // AUTHENTICATE skipped - see AuthenticatingIMAPClient.
70  
71      /**
72       * Login to the IMAP server with the given username and password.  You
73       * must first connect to the server with
74       * {@link org.apache.commons.net.SocketClient#connect  connect }
75       * before attempting to login.  A login attempt is only valid if
76       * the client is in the NOT_AUTH_STATE.
77       * After logging in, the client enters the AUTH_STATE.
78       * <p>
79       * @param username  The account name being logged in to.
80       * @param password  The plain text password of the account.
81       * @return True if the login attempt was successful, false if not.
82       * @exception IOException If a network I/O error occurs in the process of
83       *            logging in.
84       */
85      public boolean login(String username, String password) throws IOException
86      {
87          if (getState() != IMAP.IMAPState.NOT_AUTH_STATE)
88          {
89              return false;
90          }
91  
92          if (!doCommand(IMAPCommand.LOGIN, username + " " + password))
93          {
94              return false;
95          }
96  
97          setState(IMAP.IMAPState.AUTH_STATE);
98  
99          return true;
100     }
101 
102     // --------- commands available in the authenticated state
103 
104     /**
105      * Send a SELECT command to the server.
106      * @param mailboxName The mailbox name to select.
107      * @return {@code true} if the command was successful,{@code false} if not.
108      * @exception IOException If a network I/O error occurs.
109      */
110     public boolean select(String mailboxName) throws IOException
111     {
112         return doCommand (IMAPCommand.SELECT, mailboxName);
113     }
114 
115     /**
116      * Send an EXAMINE command to the server.
117      * @param mailboxName The mailbox name to examine.
118      * @return {@code true} if the command was successful,{@code false} if not.
119      * @exception IOException If a network I/O error occurs.
120      */
121     public boolean examine(String mailboxName) throws IOException
122     {
123         return doCommand (IMAPCommand.EXAMINE, mailboxName);
124     }
125 
126     /**
127      * Send a CREATE command to the server.
128      * @param mailboxName The mailbox name to create.
129      * @return {@code true} if the command was successful,{@code false} if not.
130      * @exception IOException If a network I/O error occurs.
131      */
132     public boolean create(String mailboxName) throws IOException
133     {
134         return doCommand (IMAPCommand.CREATE, mailboxName);
135     }
136 
137     /**
138      * Send a DELETE command to the server.
139      * @param mailboxName The mailbox name to delete.
140      * @return {@code true} if the command was successful,{@code false} if not.
141      * @exception IOException If a network I/O error occurs.
142      */
143     public boolean delete(String mailboxName) throws IOException
144     {
145         return doCommand (IMAPCommand.DELETE, mailboxName);
146     }
147 
148     /**
149      * Send a RENAME command to the server.
150      * @param oldMailboxName The existing mailbox name to rename.
151      * @param newMailboxName The new mailbox name.
152      * @return {@code true} if the command was successful,{@code false} if not.
153      * @exception IOException If a network I/O error occurs.
154      */
155     public boolean rename(String oldMailboxName, String newMailboxName) throws IOException
156     {
157         return doCommand (IMAPCommand.RENAME, oldMailboxName + " " + newMailboxName);
158     }
159 
160     /**
161      * Send a SUBSCRIBE command to the server.
162      * @param mailboxName The mailbox name to subscribe to.
163      * @return {@code true} if the command was successful,{@code false} if not.
164      * @exception IOException If a network I/O error occurs.
165      */
166     public boolean subscribe(String mailboxName) throws IOException
167     {
168         return doCommand (IMAPCommand.SUBSCRIBE, mailboxName);
169     }
170 
171     /**
172      * Send a UNSUBSCRIBE command to the server.
173      * @param mailboxName The mailbox name to unsubscribe from.
174      * @return {@code true} if the command was successful,{@code false} if not.
175      * @exception IOException If a network I/O error occurs.
176      */
177     public boolean unsubscribe(String mailboxName) throws IOException
178     {
179         return doCommand (IMAPCommand.UNSUBSCRIBE, mailboxName);
180     }
181 
182     /**
183      * Send a LIST command to the server.
184      * @param refName The reference name.
185      * @param mailboxName The mailbox name.
186      * @return {@code true} if the command was successful,{@code false} if not.
187      * @exception IOException If a network I/O error occurs.
188      */
189     public boolean list(String refName, String mailboxName) throws IOException
190     {
191         return doCommand (IMAPCommand.LIST, refName + " " + mailboxName);
192     }
193 
194     /**
195      * Send an LSUB command to the server.
196      * @param refName The reference name.
197      * @param mailboxName The mailbox name.
198      * @return {@code true} if the command was successful,{@code false} if not.
199      * @exception IOException If a network I/O error occurs.
200      */
201     public boolean lsub(String refName, String mailboxName) throws IOException
202     {
203         return doCommand (IMAPCommand.LSUB, refName + " " + mailboxName);
204     }
205 
206     /**
207      * Send a STATUS command to the server.
208      * @param mailboxName The reference name.
209      * @param itemNames The status data item names.
210      * @return {@code true} if the command was successful,{@code false} if not.
211      * @exception IOException If a network I/O error occurs.
212      */
213     public boolean status(String mailboxName, String[] itemNames) throws IOException
214     {
215         if (itemNames == null || itemNames.length < 1) {
216             throw new IllegalArgumentException("STATUS command requires at least one data item name");
217         }
218 
219         StringBuilder sb = new StringBuilder();
220         sb.append(mailboxName);
221 
222         sb.append(" (");
223         for ( int i = 0; i < itemNames.length; i++ )
224         {
225             if (i > 0) {
226                 sb.append(" ");
227             }
228             sb.append(itemNames[i]);
229         }
230         sb.append(")");
231 
232         return doCommand (IMAPCommand.STATUS, sb.toString());
233     }
234 
235     /**
236      * Send an APPEND command to the server.
237      * @param mailboxName The mailbox name.
238      * @param flags The flag parenthesized list (optional).
239      * @param datetime The date/time string (optional).
240      * @return {@code true} if the command was successful,{@code false} if not.
241      * @exception IOException If a network I/O error occurs.
242      */
243     public boolean append(String mailboxName, String flags, String datetime) throws IOException
244     {
245         String args = mailboxName;
246         if (flags != null) {
247             args += " " + flags;
248         }
249         if (datetime != null) {
250             if (datetime.charAt(0) == '{') {
251                 args += " " + datetime;
252             } else {
253                 args += " {" + datetime + "}";
254             }
255         }
256         return doCommand (IMAPCommand.APPEND, args);
257     }
258 
259     /**
260      * Send an APPEND command to the server.
261      * @param mailboxName The mailbox name.
262      * @return {@code true} if the command was successful,{@code false} if not.
263      * @exception IOException If a network I/O error occurs.
264      */
265     public boolean append(String mailboxName) throws IOException
266     {
267         return append(mailboxName, null, null);
268     }
269 
270     // --------- commands available in the selected state
271 
272     /**
273      * Send a CHECK command to the server.
274      * @return {@code true} if the command was successful,{@code false} if not.
275      * @exception IOException If a network I/O error occurs.
276      */
277     public boolean check() throws IOException
278     {
279         return doCommand (IMAPCommand.CHECK);
280     }
281 
282     /**
283      * Send a CLOSE command to the server.
284      * @return {@code true} if the command was successful,{@code false} if not.
285      * @exception IOException If a network I/O error occurs.
286      */
287     public boolean close() throws IOException
288     {
289         return doCommand (IMAPCommand.CLOSE);
290     }
291 
292     /**
293      * Send an EXPUNGE command to the server.
294      * @return {@code true} if the command was successful,{@code false} if not.
295      * @exception IOException If a network I/O error occurs.
296      */
297     public boolean expunge() throws IOException
298     {
299         return doCommand (IMAPCommand.EXPUNGE);
300     }
301 
302     /**
303      * Send a SEARCH command to the server.
304      * @param charset The charset (optional).
305      * @param criteria The search criteria.
306      * @return {@code true} if the command was successful,{@code false} if not.
307      * @exception IOException If a network I/O error occurs.
308      */
309     public boolean search(String charset, String criteria) throws IOException
310     {
311         String args = "";
312         if (charset != null) {
313             args += "CHARSET " + charset;
314         }
315         args += criteria;
316         return doCommand (IMAPCommand.SEARCH, args);
317     }
318 
319     /**
320      * Send a SEARCH command to the server.
321      * @param criteria The search criteria.
322      * @return {@code true} if the command was successful,{@code false} if not.
323      * @exception IOException If a network I/O error occurs.
324      */
325     public boolean search(String criteria) throws IOException
326     {
327         return search(null, criteria);
328     }
329 
330     /**
331      * Send a FETCH command to the server.
332      * @param sequenceSet The sequence set to fetch.
333      * @param itemNames The item names for the FETCH command.
334      * @return {@code true} if the command was successful,{@code false} if not.
335      * @exception IOException If a network I/O error occurs.
336      */
337     public boolean fetch(String sequenceSet, String itemNames) throws IOException
338     {
339         return doCommand (IMAPCommand.FETCH, sequenceSet + " " + itemNames);
340     }
341 
342     /**
343      * Send a STORE command to the server.
344      * @param sequenceSet The sequence set to store.
345      * @param itemNames The item names for the STORE command.
346      * @param itemValues The item values for the STORE command.
347      * @return {@code true} if the command was successful,{@code false} if not.
348      * @exception IOException If a network I/O error occurs.
349      */
350     public boolean store(String sequenceSet, String itemNames, String itemValues)
351         throws IOException
352     {
353         return doCommand (IMAPCommand.STORE, sequenceSet + " " + itemNames + " " + itemValues);
354     }
355 
356     /**
357      * Send a COPY command to the server.
358      * @param sequenceSet The sequence set to fetch.
359      * @param mailboxName The mailbox name.
360      * @return {@code true} if the command was successful,{@code false} if not.
361      * @exception IOException If a network I/O error occurs.
362      */
363     public boolean copy(String sequenceSet, String mailboxName) throws IOException
364     {
365         return doCommand (IMAPCommand.COPY, sequenceSet + " " + mailboxName);
366     }
367 
368     /**
369      * Send a UID command to the server.
370      * @param command The command for UID.
371      * @param commandArgs The arguments for the command.
372      * @return {@code true} if the command was successful,{@code false} if not.
373      * @exception IOException If a network I/O error occurs.
374      */
375     public boolean uid(String command, String commandArgs) throws IOException
376     {
377         return doCommand (IMAPCommand.UID, command + " " + commandArgs);
378     }
379 
380     /**
381      * The status data items defined in RFC 3501.
382      */
383     public enum STATUS_DATA_ITEMS
384     {
385         /** The number of messages in the mailbox. */
386         MESSAGES,
387         /** The number of messages with the \Recent flag set. */
388         RECENT,
389         /** The next unique identifier value of the mailbox. */
390         UIDNEXT,
391         /** The unique identifier validity value of the mailbox. */
392         UIDVALIDITY,
393         /** The number of messages which do not have the \Seen flag set. */
394         UNSEEN;
395     }
396 
397     /**
398      * The search criteria defined in RFC 3501.
399      */
400     public enum SEARCH_CRITERIA
401     {
402         /** All messages in the mailbox. */
403         ALL,
404         /** Messages with the \Answered flag set. */
405         ANSWERED,
406         /**
407          * Messages that contain the specified string in the envelope
408          * structure's BCC field.
409          */
410         BCC,
411         /**
412          * Messages whose internal date (disregarding time and timezone)
413          * is earlier than the specified date.
414          */
415         BEFORE,
416         /**
417          * Messages that contain the specified string in the body of the
418          * message.
419          */
420         BODY,
421         /**
422          * Messages that contain the specified string in the envelope
423          * structure's CC field.
424          */
425         CC,
426         /** Messages with the \Deleted flag set. */
427         DELETED,
428         /** Messages with the \Draft flag set. */
429         DRAFT,
430         /** Messages with the \Flagged flag set. */
431         FLAGGED,
432         /**
433          * Messages that contain the specified string in the envelope
434          * structure's FROM field.
435          */
436         FROM,
437         /**
438          * Messages that have a header with the specified field-name (as
439          * defined in [RFC-2822]) and that contains the specified string
440          * in the text of the header (what comes after the colon).  If the
441          * string to search is zero-length, this matches all messages that
442          * have a header line with the specified field-name regardless of
443          * the contents.
444          */
445         HEADER,
446         /** Messages with the specified keyword flag set. */
447         KEYWORD,
448         /**
449          * Messages with an [RFC-2822] size larger than the specified
450          * number of octets.
451          */
452         LARGER,
453         /**
454          * Messages that have the \Recent flag set but not the \Seen flag.
455          * This is functionally equivalent to "(RECENT UNSEEN)".
456          */
457         NEW,
458         /** Messages that do not match the specified search key. */
459         NOT,
460         /**
461          * Messages that do not have the \Recent flag set.  This is
462          * functionally equivalent to "NOT RECENT" (as opposed to "NOT
463          * NEW").
464          */
465         OLD,
466         /**
467          * Messages whose internal date (disregarding time and timezone)
468          * is within the specified date.
469          */
470         ON,
471         /** Messages that match either search key. */
472         OR,
473         /** Messages that have the \Recent flag set. */
474         RECENT,
475         /** Messages that have the \Seen flag set. */
476         SEEN,
477         /**
478          * Messages whose [RFC-2822] Date: header (disregarding time and
479          * timezone) is earlier than the specified date.
480          */
481         SENTBEFORE,
482         /**
483          * Messages whose [RFC-2822] Date: header (disregarding time and
484          * timezone) is within the specified date.
485          */
486         SENTON,
487         /**
488          * Messages whose [RFC-2822] Date: header (disregarding time and
489          * timezone) is within or later than the specified date.
490          */
491         SENTSINCE,
492         /**
493          * Messages whose internal date (disregarding time and timezone)
494          * is within or later than the specified date.
495          */
496         SINCE,
497         /**
498          * Messages with an [RFC-2822] size smaller than the specified
499          * number of octets.
500          */
501         SMALLER,
502         /**
503          * Messages that contain the specified string in the envelope
504          * structure's SUBJECT field.
505          */
506         SUBJECT,
507         /**
508          * Messages that contain the specified string in the header or
509          * body of the message.
510          */
511         TEXT,
512         /**
513          * Messages that contain the specified string in the envelope
514          * structure's TO field.
515          */
516         TO,
517         /**
518          * Messages with unique identifiers corresponding to the specified
519          * unique identifier set.  Sequence set ranges are permitted.
520          */
521         UID,
522         /** Messages that do not have the \Answered flag set. */
523         UNANSWERED,
524         /** Messages that do not have the \Deleted flag set. */
525         UNDELETED,
526         /** Messages that do not have the \Draft flag set. */
527         UNDRAFT,
528         /** Messages that do not have the \Flagged flag set. */
529         UNFLAGGED,
530         /** Messages that do not have the specified keyword flag set. */
531         UNKEYWORD,
532         /** Messages that do not have the \Seen flag set. */
533         UNSEEN;
534     }
535 
536     /**
537      * The message data item names for the FETCH command defined in RFC 3501.
538      */
539     public enum FETCH_ITEM_NAMES
540     {
541         /** Macro equivalent to: (FLAGS INTERNALDATE RFC822.SIZE ENVELOPE). */
542         ALL,
543         /** Macro equivalent to: (FLAGS INTERNALDATE RFC822.SIZE). */
544         FAST,
545         /** Macro equivalent to: (FLAGS INTERNALDATE RFC822.SIZE ENVELOPE BODY). */
546         FULL,
547         /** Non-extensible form of BODYSTRUCTURE or the text of a particular body section. */
548         BODY,
549         /** The [MIME-IMB] body structure of the message. */
550         BODYSTRUCTURE,
551         /** The envelope structure of the message. */
552         ENVELOPE,
553         /** The flags that are set for this message. */
554         FLAGS,
555         /** The internal date of the message. */
556         INTERNALDATE,
557         /** A prefix for RFC-822 item names. */
558         RFC822,
559         /** The unique identifier for the message. */
560         UID;
561     }
562 
563 }
564 /* kate: indent-width 4; replace-tabs on; */