Save This Page
Home » apache-tomcat-6.0.16-src » javax » mail » [javadoc | source]
    1   /**
    2    *
    3    * Copyright 2003-2004 The Apache Software Foundation
    4    *
    5    *  Licensed under the Apache License, Version 2.0 (the "License");
    6    *  you may not use this file except in compliance with the License.
    7    *  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 javax.mail;
   19   
   20   import java.util.ArrayList;
   21   import java.util.List;
   22   import javax.mail.Flags.Flag;
   23   import javax.mail.event.ConnectionEvent;
   24   import javax.mail.event.ConnectionListener;
   25   import javax.mail.event.FolderEvent;
   26   import javax.mail.event.FolderListener;
   27   import javax.mail.event.MessageChangedEvent;
   28   import javax.mail.event.MessageChangedListener;
   29   import javax.mail.event.MessageCountEvent;
   30   import javax.mail.event.MessageCountListener;
   31   import javax.mail.search.SearchTerm;
   32   
   33   /**
   34    * An abstract representation of a folder in a mail system; subclasses would
   35    * implement Folders for each supported protocol.
   36    * <p/>
   37    * Depending on protocol and implementation, folders may contain other folders, messages,
   38    * or both as indicated by the {@link Folder#HOLDS_FOLDERS} and {@link Folder#HOLDS_MESSAGES} flags.
   39    * If the immplementation supports hierarchical folders, the format of folder names is
   40    * implementation dependent; however, components of the name are separated by the
   41    * delimiter character returned by {@link Folder#getSeparator()}.
   42    * <p/>
   43    * The case-insensitive folder name "INBOX" is reserved to refer to the primary folder
   44    * for the current user on the current server; not all stores will provide an INBOX
   45    * and it may not be available at all times.
   46    *
   47    * @version $Rev: 126350 $ $Date: 2005-01-24 22:35:47 -0800 (Mon, 24 Jan 2005) $
   48    */
   49   public abstract class Folder {
   50       /**
   51        * Flag that indicates that a folder can contain messages.
   52        */
   53       public static final int HOLDS_MESSAGES = 1;
   54       /**
   55        * Flag that indicates that a folder can contain other folders.
   56        */
   57       public static final int HOLDS_FOLDERS = 2;
   58   
   59       /**
   60        * Flag indicating that this folder cannot be modified.
   61        */
   62       public static final int READ_ONLY = 1;
   63       /**
   64        * Flag indictaing that this folder can be modified.
   65        * Question: what does it mean if both are set?
   66        */
   67       public static final int READ_WRITE = 2;
   68   
   69       /**
   70        * The store that this folder is part of.
   71        */
   72       protected Store store;
   73       /**
   74        * The current mode of this folder.
   75        * When open, this can be {@link #READ_ONLY} or {@link #READ_WRITE};
   76        * otherwise is set to -1.
   77        */
   78       protected int mode = -1;
   79   
   80       private final List connectionListeners = new ArrayList(2);
   81       private final List folderListeners = new ArrayList(2);
   82       private final List messageChangedListeners = new ArrayList(2);
   83       private final List messageCountListeners = new ArrayList(2);
   84       private final EventQueue queue = new EventQueue();
   85   
   86       /**
   87        * Constructor that initializes the Store.
   88        *
   89        * @param store the store that this folder is part of
   90        */
   91       protected Folder(Store store) {
   92           this.store = store;
   93       }
   94   
   95       /**
   96        * Return the name of this folder.
   97        * This can be invoked when the folder is closed.
   98        *
   99        * @return this folder's name
  100        */
  101       public abstract String getName();
  102   
  103       /**
  104        * Return the full absolute name of this folder.
  105        * This can be invoked when the folder is closed.
  106        *
  107        * @return the full name of this folder
  108        */
  109       public abstract String getFullName();
  110   
  111       /**
  112        * Return the URLName for this folder, which includes the location of the store.
  113        *
  114        * @return the URLName for this folder
  115        * @throws MessagingException
  116        */
  117       public URLName getURLName() throws MessagingException {
  118           // todo shouldn't this include the full name of the folder?
  119           return store.getURLName();
  120       }
  121   
  122       /**
  123        * Return the store that this folder is part of.
  124        *
  125        * @return the store this folder is part of
  126        */
  127       public Store getStore() {
  128           return store;
  129       }
  130   
  131       /**
  132        * Return the parent for this folder; if the folder is at the root of a heirarchy
  133        * this returns null.
  134        * This can be invoked when the folder is closed.
  135        *
  136        * @return this folder's parent
  137        * @throws MessagingException
  138        */
  139       public abstract Folder getParent() throws MessagingException;
  140   
  141       /**
  142        * Check to see if this folder physically exists in the store.
  143        * This can be invoked when the folder is closed.
  144        *
  145        * @return true if the folder really exists
  146        * @throws MessagingException if there was a problem accessing the store
  147        */
  148       public abstract boolean exists() throws MessagingException;
  149   
  150       /**
  151        * Return a list of folders from this Folder's namespace that match the supplied pattern.
  152        * Patterns may contain the following wildcards:
  153        * <ul><li>'%' which matches any characater except hierarchy delimiters</li>
  154        * <li>'*' which matches any character including hierarchy delimiters</li>
  155        * </ul>
  156        * This can be invoked when the folder is closed.
  157        *
  158        * @param pattern the pattern to search for
  159        * @return a, possibly empty, array containing Folders that matched the pattern
  160        * @throws MessagingException if there was a problem accessing the store
  161        */
  162       public abstract Folder[] list(String pattern) throws MessagingException;
  163   
  164       /**
  165        * Return a list of folders to which the user is subscribed and which match the supplied pattern.
  166        * If the store does not support the concept of subscription then this should match against
  167        * all folders; the default implementation of this method achieves this by defaulting to the
  168        * {@link #list(String)} method.
  169        *
  170        * @param pattern the pattern to search for
  171        * @return a, possibly empty, array containing subscribed Folders that matched the pattern
  172        * @throws MessagingException if there was a problem accessing the store
  173        */
  174       public Folder[] listSubscribed(String pattern) throws MessagingException {
  175           return list(pattern);
  176       }
  177   
  178       /**
  179        * Convenience method that invokes {@link #list(String)} with the pattern "%".
  180        *
  181        * @return a, possibly empty, array of subfolders
  182        * @throws MessagingException if there was a problem accessing the store
  183        */
  184       public Folder[] list() throws MessagingException {
  185           return list("%");
  186       }
  187   
  188       /**
  189        * Convenience method that invokes {@link #listSubscribed(String)} with the pattern "%".
  190        *
  191        * @return a, possibly empty, array of subscribed subfolders
  192        * @throws MessagingException if there was a problem accessing the store
  193        */
  194       public Folder[] listSubscribed() throws MessagingException {
  195           return listSubscribed("%");
  196       }
  197   
  198       /**
  199        * Return the character used by this folder's Store to separate path components.
  200        *
  201        * @return the name separater character
  202        * @throws MessagingException if there was a problem accessing the store
  203        */
  204       public abstract char getSeparator() throws MessagingException;
  205   
  206       /**
  207        * Return the type of this folder, indicating whether it can contain subfolders,
  208        * messages, or both. The value returned is a bitmask with the appropriate bits set.
  209        *
  210        * @return the type of this folder
  211        * @throws MessagingException if there was a problem accessing the store
  212        * @see #HOLDS_FOLDERS
  213        * @see #HOLDS_MESSAGES
  214        */
  215       public abstract int getType() throws MessagingException;
  216   
  217       /**
  218        * Create a new folder capable of containing subfoldera and/or messages as
  219        * determined by the type parameter. Any hierarchy defined by the folder
  220        * name will be recursively created.
  221        * If the folder was sucessfully created, a {@link FolderEvent#CREATED CREATED FolderEvent}
  222        * is sent to all FolderListeners registered with this Folder or with the Store.
  223        *
  224        * @param type the type, indicating if this folder should contain subfolders, messages or both
  225        * @return true if the folder was sucessfully created
  226        * @throws MessagingException if there was a problem accessing the store
  227        */
  228       public abstract boolean create(int type) throws MessagingException;
  229   
  230       /**
  231        * Determine if the user is subscribed to this Folder. The default implementation in
  232        * this class always returns true.
  233        *
  234        * @return true is the user is subscribed to this Folder
  235        */
  236       public boolean isSubscribed() {
  237           return true;
  238       }
  239   
  240       /**
  241        * Set the user's subscription to this folder.
  242        * Not all Stores support subscription; the default implementation in this class
  243        * always throws a MethodNotSupportedException
  244        *
  245        * @param subscribed whether to subscribe to this Folder
  246        * @throws MessagingException          if there was a problem accessing the store
  247        * @throws MethodNotSupportedException if the Store does not support subscription
  248        */
  249       public void setSubscribed(boolean subscribed) throws MessagingException {
  250           throw new MethodNotSupportedException();
  251       }
  252   
  253       /**
  254        * Check to see if this Folder conatins messages with the {@link Flag.RECENT} flag set.
  255        * This can be used when the folder is closed to perform a light-weight check for new mail;
  256        * to perform an incremental check for new mail the folder must be opened.
  257        *
  258        * @return true if the Store has recent messages
  259        * @throws MessagingException if there was a problem accessing the store
  260        */
  261       public abstract boolean hasNewMessages() throws MessagingException;
  262   
  263       /**
  264        * Get the Folder determined by the supplied name; if the name is relative
  265        * then it is interpreted relative to this folder. This does not check that
  266        * the named folder actually exists.
  267        *
  268        * @param name the name of the folder to return
  269        * @return the named folder
  270        * @throws MessagingException if there was a problem accessing the store
  271        */
  272       public abstract Folder getFolder(String name) throws MessagingException;
  273   
  274       /**
  275        * Delete this folder and possibly any subfolders. This operation can only be
  276        * performed on a closed folder.
  277        * If recurse is true, then all subfolders are deleted first, then any messages in
  278        * this folder are removed and it is finally deleted; {@link FolderEvent#DELETED}
  279        * events are sent as appropriate.
  280        * If recurse is false, then the behaviour depends on the folder type and store
  281        * implementation as followd:
  282        * <ul>
  283        * <li>If the folder can only conrain messages, then all messages are removed and
  284        * then the folder is deleted; a {@link FolderEvent#DELETED} event is sent.</li>
  285        * <li>If the folder can onlu contain subfolders, then if it is empty it will be
  286        * deleted and a {@link FolderEvent#DELETED} event is sent; if the folder is not
  287        * empty then the delete fails and this method returns false.</li>
  288        * <li>If the folder can contain both subfolders and messages, then if the folder
  289        * does not contain any subfolders, any messages are deleted, the folder itself
  290        * is deleted and a {@link FolderEvent#DELETED} event is sent; if the folder does
  291        * contain subfolders then the implementation may choose from the following three
  292        * behaviors:
  293        * <ol>
  294        * <li>it may return false indicting the operation failed</li>
  295        * <li>it may remove all messages within the folder, send a {@link FolderEvent#DELETED}
  296        * event, and then return true to indicate the delete was performed. Note this does
  297        * not delete the folder itself and the {@link #exists()} operation for this folder
  298        * will return true</li>
  299        * <li>it may remove all messages within the folder as per the previous option; in
  300        * addition it may change the type of the Folder to only HOLDS_FOLDERS indictaing
  301        * that messages may no longer be added</li>
  302        * </li>
  303        * </ul>
  304        * FolderEvents are sent to all listeners registered with this folder or
  305        * with the Store.
  306        *
  307        * @param recurse whether subfolders should be recursively deleted as well
  308        * @return true if the delete operation succeeds
  309        * @throws MessagingException if there was a problem accessing the store
  310        */
  311       public abstract boolean delete(boolean recurse) throws MessagingException;
  312   
  313       /**
  314        * Rename this folder; the folder must be closed.
  315        * If the rename is successfull, a {@link FolderEvent#RENAMED} event is sent to
  316        * all listeners registered with this folder or with the store.
  317        *
  318        * @param newName the new name for this folder
  319        * @return true if the rename succeeded
  320        * @throws MessagingException if there was a problem accessing the store
  321        */
  322       public abstract boolean renameTo(Folder newName) throws MessagingException;
  323   
  324       /**
  325        * Open this folder; the folder must be able to contain messages and
  326        * must currently be closed. If the folder is opened successfully then
  327        * a {@link ConnectionEvent#OPENED} event is sent to listeners registered
  328        * with this Folder.
  329        * <p/>
  330        * Whether the Store allows multiple connections or if it allows multiple
  331        * writers is implementation defined.
  332        *
  333        * @param mode READ_ONLY or READ_WRITE
  334        * @throws MessagingException if there was a problem accessing the store
  335        */
  336       public abstract void open(int mode) throws MessagingException;
  337   
  338       /**
  339        * Close this folder; it must already be open.
  340        * A {@link ConnectionEvent#CLOSED} event is sent to all listeners registered
  341        * with this folder.
  342        *
  343        * @param expunge whether to expunge all deleted messages
  344        * @throws MessagingException if there was a problem accessing the store; the folder is still closed
  345        */
  346       public abstract void close(boolean expunge) throws MessagingException;
  347   
  348       /**
  349        * Indicates that the folder has been opened.
  350        *
  351        * @return true if the folder is open
  352        */
  353       public abstract boolean isOpen();
  354   
  355       /**
  356        * Return the mode of this folder ass passed to {@link #open(int)}, or -1 if
  357        * the folder is closed.
  358        *
  359        * @return the mode this folder was opened with
  360        */
  361       public int getMode() {
  362           return mode;
  363       }
  364   
  365       /**
  366        * Get the flags supported by this folder.
  367        *
  368        * @return the flags supported by this folder, or null if unknown
  369        * @see Flags
  370        */
  371       public abstract Flags getPermanentFlags();
  372   
  373       /**
  374        * Return the number of messages this folder contains.
  375        * If this operation is invoked on a closed folder, the implementation
  376        * may choose to return -1 to avoid the expense of opening the folder.
  377        *
  378        * @return the number of messages, or -1 if unknown
  379        * @throws MessagingException if there was a problem accessing the store
  380        */
  381       public abstract int getMessageCount() throws MessagingException;
  382   
  383       /**
  384        * Return the numbew of messages in this folder that have the {@link Flag.RECENT} flag set.
  385        * If this operation is invoked on a closed folder, the implementation
  386        * may choose to return -1 to avoid the expense of opening the folder.
  387        * The default implmentation of this method iterates over all messages
  388        * in the folder; subclasses should override if possible to provide a more
  389        * efficient implementation.
  390        *
  391        * @return the number of new messages, or -1 if unknown
  392        * @throws MessagingException if there was a problem accessing the store
  393        */
  394       public int getNewMessageCount() throws MessagingException {
  395           return getCount(Flags.Flag.RECENT, true);
  396       }
  397   
  398       /**
  399        * Return the numbew of messages in this folder that do not have the {@link Flag.SEEN} flag set.
  400        * If this operation is invoked on a closed folder, the implementation
  401        * may choose to return -1 to avoid the expense of opening the folder.
  402        * The default implmentation of this method iterates over all messages
  403        * in the folder; subclasses should override if possible to provide a more
  404        * efficient implementation.
  405        *
  406        * @return the number of new messages, or -1 if unknown
  407        * @throws MessagingException if there was a problem accessing the store
  408        */
  409       public int getUnreadMessageCount() throws MessagingException {
  410           return getCount(Flags.Flag.SEEN, false);
  411       }
  412   
  413       /**
  414        * Return the numbew of messages in this folder that have the {@link Flag.DELETED} flag set.
  415        * If this operation is invoked on a closed folder, the implementation
  416        * may choose to return -1 to avoid the expense of opening the folder.
  417        * The default implmentation of this method iterates over all messages
  418        * in the folder; subclasses should override if possible to provide a more
  419        * efficient implementation.
  420        *
  421        * @return the number of new messages, or -1 if unknown
  422        * @throws MessagingException if there was a problem accessing the store
  423        */
  424       public int getDeletedMessageCount() throws MessagingException {
  425           return getCount(Flags.Flag.DELETED, true);
  426       }
  427   
  428       private int getCount(Flag flag, boolean value) throws MessagingException {
  429           if (!isOpen()) {
  430               return -1;
  431           }
  432           Message[] messages = getMessages();
  433           int total = 0;
  434           for (int i = 0; i < messages.length; i++) {
  435               if (messages[i].getFlags().contains(flag) == value) {
  436                   total++;
  437               }
  438           }
  439           return total;
  440       }
  441   
  442       /**
  443        * Retrieve the message with the specified index in this Folder;
  444        * messages indices start at 1 not zero.
  445        * Clients should note that the index for a specific message may change
  446        * if the folder is expunged; {@link Message} objects should be used as
  447        * references instead.
  448        *
  449        * @param index the index of the message to fetch
  450        * @return the message
  451        * @throws MessagingException if there was a problem accessing the store
  452        */
  453       public abstract Message getMessage(int index) throws MessagingException;
  454   
  455       /**
  456        * Retrieve messages with index between start and end inclusive
  457        *
  458        * @param start index of first message
  459        * @param end   index of last message
  460        * @return an array of messages from start to end inclusive
  461        * @throws MessagingException if there was a problem accessing the store
  462        */
  463       public Message[] getMessages(int start, int end) throws MessagingException {
  464           Message[] result = new Message[end - start + 1];
  465           for (int i = 0; i < result.length; i++) {
  466               result[i] = getMessage(start++);
  467           }
  468           return result;
  469       }
  470   
  471       /**
  472        * Retrieve messages with the specified indices.
  473        *
  474        * @param ids the indices of the messages to fetch
  475        * @return the specified messages
  476        * @throws MessagingException if there was a problem accessing the store
  477        */
  478       public Message[] getMessages(int ids[]) throws MessagingException {
  479           Message[] result = new Message[ids.length];
  480           for (int i = 0; i < ids.length; i++) {
  481               result[i] = getMessage(ids[i]);
  482           }
  483           return result;
  484       }
  485   
  486       /**
  487        * Retrieve all messages.
  488        *
  489        * @return all messages in this folder
  490        * @throws MessagingException if there was a problem accessing the store
  491        */
  492       public Message[] getMessages() throws MessagingException {
  493           return getMessages(1, getMessageCount());
  494       }
  495   
  496       /**
  497        * Append the supplied messages to this folder. A {@link MessageCountEvent} is sent
  498        * to all listeners registered with this folder when all messages have been appended.
  499        * If the array contains a previously expunged message, it must be re-appended to the Store
  500        * and implementations must not abort this operation.
  501        *
  502        * @param messages the messages to append
  503        * @throws MessagingException if there was a problem accessing the store
  504        */
  505       public abstract void appendMessages(Message[] messages) throws MessagingException;
  506   
  507       /**
  508        * Hint to the store to prefetch information on the supplied messaged.
  509        * Subclasses should override this method to provide an efficient implementation;
  510        * the default implementation in this class simply returns.
  511        *
  512        * @param messages messages for which information should be fetched
  513        * @param profile  the information to fetch
  514        * @throws MessagingException if there was a problem accessing the store
  515        * @see FetchProfile
  516        */
  517       public void fetch(Message[] messages, FetchProfile profile) throws MessagingException {
  518           return;
  519       }
  520   
  521       /**
  522        * Set flags on the messages to the supplied value; all messages must belong to this folder.
  523        * This method may be overridden by subclasses that can optimize the setting
  524        * of flags on multiple messages at once; the default implementation simply calls
  525        * {@link Message#setFlags(Flags, boolean)} for each supplied messages.
  526        *
  527        * @param messages whose flags should be set
  528        * @param flags    the set of flags to modify
  529        * @param value    the value the flags should be set to
  530        * @throws MessagingException if there was a problem accessing the store
  531        */
  532       public void setFlags(Message[] messages, Flags flags, boolean value) throws MessagingException {
  533           for (int i = 0; i < messages.length; i++) {
  534               Message message = messages[i];
  535               message.setFlags(flags, value);
  536           }
  537       }
  538   
  539       /**
  540        * Set flags on a range of messages to the supplied value.
  541        * This method may be overridden by subclasses that can optimize the setting
  542        * of flags on multiple messages at once; the default implementation simply
  543        * gets each message and then calls {@link Message#setFlags(Flags, boolean)}.
  544        *
  545        * @param start first message end set
  546        * @param end   last message end set
  547        * @param flags the set of flags end modify
  548        * @param value the value the flags should be set end
  549        * @throws MessagingException if there was a problem accessing the store
  550        */
  551       public void setFlags(int start, int end, Flags flags, boolean value) throws MessagingException {
  552           for (int i = start; i <= end; i++) {
  553               Message message = getMessage(i);
  554               message.setFlags(flags, value);
  555           }
  556       }
  557   
  558       /**
  559        * Set flags on a set of messages to the supplied value.
  560        * This method may be overridden by subclasses that can optimize the setting
  561        * of flags on multiple messages at once; the default implementation simply
  562        * gets each message and then calls {@link Message#setFlags(Flags, boolean)}.
  563        *
  564        * @param ids   the indexes of the messages to set
  565        * @param flags the set of flags end modify
  566        * @param value the value the flags should be set end
  567        * @throws MessagingException if there was a problem accessing the store
  568        */
  569       public void setFlags(int ids[], Flags flags, boolean value) throws MessagingException {
  570           for (int i = 0; i < ids.length; i++) {
  571               Message message = getMessage(ids[i]);
  572               message.setFlags(flags, value);
  573           }
  574       }
  575   
  576       /**
  577        * Copy the specified messages to another folder.
  578        * The default implementation simply appends the supplied messages to the
  579        * target folder using {@link #appendMessages(Message[])}.
  580        * @param messages the messages to copy
  581        * @param folder the folder to copy to
  582        * @throws MessagingException if there was a problem accessing the store
  583        */
  584       public void copyMessages(Message[] messages, Folder folder) throws MessagingException {
  585           folder.appendMessages(messages);
  586       }
  587   
  588       /**
  589        * Permanently delete all supplied messages that have the DELETED flag set from the Store.
  590        * The original message indices of all messages actually deleted are returned and a
  591        * {@link MessageCountEvent} event is sent to all listeners with this folder. The expunge
  592        * may cause the indices of all messaged that remain in the folder to change.
  593        *
  594        * @return the original indices of messages that were actually deleted
  595        * @throws MessagingException if there was a problem accessing the store
  596        */
  597       public abstract Message[] expunge() throws MessagingException;
  598   
  599       /**
  600        * Search this folder for messages matching the supplied search criteria.
  601        * The default implementation simply invoke <code>search(term, getMessages())
  602        * applying the search over all messages in the folder; subclasses may provide
  603        * a more efficient mechanism.
  604        *
  605        * @param term the search criteria
  606        * @return an array containing messages that match the criteria
  607        * @throws MessagingException if there was a problem accessing the store
  608        */
  609       public Message[] search(SearchTerm term) throws MessagingException {
  610           return search(term, getMessages());
  611       }
  612   
  613       /**
  614        * Search the supplied messages for those that match the supplied criteria;
  615        * messages must belong to this folder.
  616        * The default implementation iterates through the messages, returning those
  617        * whose {@link Message#match(javax.mail.search.SearchTerm)} method returns true;
  618        * subclasses may provide a more efficient implementation.
  619        *
  620        * @param term the search criteria
  621        * @param messages the messages to search
  622        * @return an array containing messages that match the criteria
  623        * @throws MessagingException if there was a problem accessing the store
  624        */
  625       public Message[] search(SearchTerm term, Message[] messages) throws MessagingException {
  626           List result = new ArrayList(messages.length);
  627           for (int i = 0; i < messages.length; i++) {
  628               Message message = messages[i];
  629               if (message.match(term)) {
  630                   result.add(message);
  631               }
  632           }
  633           return (Message[]) result.toArray(new Message[result.size()]);
  634       }
  635   
  636       public void addConnectionListener(ConnectionListener listener) {
  637           connectionListeners.add(listener);
  638       }
  639   
  640       public void removeConnectionListener(ConnectionListener listener) {
  641           connectionListeners.remove(listener);
  642       }
  643   
  644       protected void notifyConnectionListeners(int type) {
  645           queue.queueEvent(new ConnectionEvent(this, type), connectionListeners);
  646       }
  647   
  648       public void addFolderListener(FolderListener listener) {
  649           folderListeners.add(listener);
  650       }
  651   
  652       public void removeFolderListener(FolderListener listener) {
  653           folderListeners.remove(listener);
  654       }
  655   
  656       protected void notifyFolderListeners(int type) {
  657           queue.queueEvent(new FolderEvent(this, this, type), folderListeners);
  658       }
  659   
  660       protected void notifyFolderRenamedListeners(Folder newFolder) {
  661           queue.queueEvent(new FolderEvent(this, this, newFolder, FolderEvent.RENAMED), folderListeners);
  662       }
  663   
  664       public void addMessageCountListener(MessageCountListener listener) {
  665           messageCountListeners.add(listener);
  666       }
  667   
  668       public void removeMessageCountListener(MessageCountListener listener) {
  669           messageCountListeners.remove(listener);
  670       }
  671   
  672       protected void notifyMessageAddedListeners(Message[] messages) {
  673           queue.queueEvent(new MessageCountEvent(this, MessageCountEvent.ADDED, false, messages), messageChangedListeners);
  674       }
  675   
  676       protected void notifyMessageRemovedListeners(boolean removed, Message[] messages) {
  677           queue.queueEvent(new MessageCountEvent(this, MessageCountEvent.REMOVED, removed, messages), messageChangedListeners);
  678       }
  679   
  680       public void addMessageChangedListener(MessageChangedListener listener) {
  681           messageChangedListeners.add(listener);
  682       }
  683   
  684       public void removeMessageChangedListener(MessageChangedListener listener) {
  685           messageChangedListeners.remove(listener);
  686       }
  687   
  688       protected void notifyMessageChangedListeners(int type, Message message) {
  689           queue.queueEvent(new MessageChangedEvent(this, type, message), messageChangedListeners);
  690       }
  691   
  692       /**
  693        * Unregisters all listeners.
  694        */
  695       protected void finalize() throws Throwable {
  696           queue.stop();
  697           connectionListeners.clear();
  698           folderListeners.clear();
  699           messageChangedListeners.clear();
  700           messageCountListeners.clear();
  701           store = null;
  702           super.finalize();
  703       }
  704   
  705       /**
  706        * Returns the full name of this folder; if null, returns the value from the superclass.
  707        * @return a string form of this folder
  708        */
  709       public String toString() {
  710           String name = getFullName();
  711           return name == null ? super.toString() : name;
  712       }
  713   }

Save This Page
Home » apache-tomcat-6.0.16-src » javax » mail » [javadoc | source]