001: //The contents of this file are subject to the Mozilla Public License Version 1.1
002: //(the "License"); you may not use this file except in compliance with the
003: //License. You may obtain a copy of the License at http://www.mozilla.org/MPL/
004: //
005: //Software distributed under the License is distributed on an "AS IS" basis,
006: //WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
007: //for the specific language governing rights and
008: //limitations under the License.
009: //
010: //The Original Code is "The Columba Project"
011: //
012: //The Initial Developers of the Original Code are Frederik Dietz and Timo Stich.
013: //Portions created by Frederik Dietz and Timo Stich are Copyright (C) 2003.
014: //
015: //All Rights Reserved.
016: package org.columba.mail.pop3.command;
017:
018: import java.io.IOException;
019: import java.net.SocketException;
020: import java.text.MessageFormat;
021: import java.util.Iterator;
022: import java.util.List;
023: import java.util.logging.Logger;
024:
025: import javax.swing.Action;
026:
027: import org.columba.api.command.IWorkerStatusChangeListener;
028: import org.columba.api.command.IWorkerStatusController;
029: import org.columba.api.command.WorkerStatusChangedEvent;
030: import org.columba.core.command.Command;
031: import org.columba.core.command.CommandCancelledException;
032: import org.columba.core.command.CommandProcessor;
033: import org.columba.core.command.DefaultCommandReference;
034: import org.columba.core.command.StatusObservableImpl;
035: import org.columba.core.command.Worker;
036: import org.columba.core.logging.Logging;
037: import org.columba.mail.command.IMailFolderCommandReference;
038: import org.columba.mail.command.MailFolderCommandReference;
039: import org.columba.mail.command.POP3CommandReference;
040: import org.columba.mail.folder.IMailbox;
041: import org.columba.mail.mailchecking.MailCheckingManager;
042: import org.columba.mail.message.ColumbaMessage;
043: import org.columba.mail.pop3.POP3Server;
044: import org.columba.mail.util.MailResourceLoader;
045:
046: /**
047: * @author freddy
048: */
049: public class FetchNewMessagesCommand extends Command {
050:
051: /** JDK 1.4+ logging framework logger, used for logging. */
052: private static final Logger LOG = Logger
053: .getLogger("org.columba.mail.pop3.command");
054:
055: POP3Server server;
056:
057: int totalMessageCount;
058:
059: int newMessageCount;
060:
061: Action action;
062:
063: /**
064: * Constructor for FetchNewMessages.
065: *
066: * @param frameMediator
067: * @param references
068: */
069: public FetchNewMessagesCommand(Action action,
070: DefaultCommandReference reference) {
071: super (reference);
072:
073: POP3CommandReference r = (POP3CommandReference) getReference();
074:
075: server = r.getServer();
076:
077: priority = Command.DAEMON_PRIORITY;
078:
079: this .action = action;
080: }
081:
082: /**
083: * @see org.columba.api.command.Command#execute(Worker)
084: */
085: public void execute(IWorkerStatusController worker)
086: throws Exception {
087: POP3CommandReference r = (POP3CommandReference) getReference();
088:
089: server = r.getServer();
090:
091: // register interest on status bar information
092: ((StatusObservableImpl) server.getObservable())
093: .setWorker(worker);
094:
095: log(MailResourceLoader.getString("statusbar", "message",
096: "authenticating"));
097:
098: try {
099: // login and get # of messages on server
100: totalMessageCount = server.getMessageCount();
101:
102: if (worker.cancelled())
103: throw new CommandCancelledException();
104:
105: // synchronize local UID list with server UID list
106: List newMessagesUidList = synchronize();
107:
108: if (worker.cancelled())
109: throw new CommandCancelledException();
110:
111: if (Logging.DEBUG) {
112: LOG.fine(newMessagesUidList.toString());
113: }
114:
115: if (worker.cancelled())
116: throw new CommandCancelledException();
117: // only download new messages
118: downloadNewMessages(newMessagesUidList, worker);
119:
120: // Delete old message from server if the feature is enabled
121: server.cleanUpServer();
122:
123: // logout cleanly
124: logout();
125:
126: // display downloaded message count in statusbar
127: if (newMessageCount == 0) {
128: log(MailResourceLoader.getString("statusbar",
129: "message", "no_new_messages"));
130: } else {
131: log(MessageFormat.format(MailResourceLoader.getString(
132: "statusbar", "message", "fetched_count"),
133: new Object[] { new Integer(newMessageCount) }));
134: }
135:
136: // get inbox-folder from pop3-server preferences
137: IMailbox inboxFolder = server.getFolder();
138:
139: // notify listeners
140: IMailFolderCommandReference ref = new MailFolderCommandReference(
141: inboxFolder, newMessagesUidList.toArray());
142: MailCheckingManager.getInstance()
143: .fireNewMessageArrived(ref);
144:
145: } catch (CommandCancelledException e) {
146: server.logout();
147:
148: // clear statusbar message
149: server.getObservable().clearMessage();
150: } catch (Exception e) {
151: // clear statusbar message
152: server.getObservable().clearMessage();
153: throw e;
154: }
155: /*
156: * catch (IOException e) { String name = e.getClass().getName();
157: * JOptionPane.showMessageDialog(null, e.getLocalizedMessage(),
158: * name.substring(name.lastIndexOf(".")), JOptionPane.ERROR_MESSAGE); //
159: * clear statusbar message server.getObservable().clearMessage(); }
160: */
161: finally {
162: /*
163: * // always enable the menuitem again
164: * r[0].getPOP3ServerController().enableActions(true);
165: */
166: }
167: }
168:
169: protected void log(String message) {
170: server.getObservable().setMessage(
171: server.getFolderName() + ": " + message);
172: }
173:
174: public void downloadMessage(Object serverUID,
175: IWorkerStatusController worker) throws Exception {
176: // server message numbers start with 1
177: // whereas List numbers start with 0
178: // -> always increase fetch number
179: IWorkerStatusChangeListener listener = new IWorkerStatusChangeListener() {
180: public void workerStatusChanged(WorkerStatusChangedEvent e) {
181: if (e.getSource().cancelled()) {
182: try {
183: server.dropConnection();
184: } catch (IOException e1) {
185: }
186: }
187:
188: }
189: };
190:
191: // important for cancel
192: worker.addWorkerStatusChangeListener(listener);
193:
194: // download message
195: ColumbaMessage message;
196: try {
197: message = server.getMessage(serverUID, worker);
198: } catch (SocketException e) {
199: if (!worker.cancelled())
200: throw e;
201: else
202: throw new CommandCancelledException();
203: }
204: // not needed anymore
205: worker.removeWorkerStatusChangeListener(listener);
206:
207: if (message == null) {
208: LOG.severe("Message with UID=" + serverUID
209: + " isn't on the server.");
210:
211: return;
212: }
213:
214: message.getHeader().getFlags().setSeen(false);
215:
216: // get inbox-folder from pop3-server preferences
217: IMailbox inboxFolder = server.getFolder();
218:
219: // start command which adds message to folder
220: // and calls apply-filter on this specific message
221: IMailFolderCommandReference r = new MailFolderCommandReference(
222: inboxFolder, message);
223:
224: CommandProcessor.getInstance().addOp(
225: new AddPOP3MessageCommand(r));
226: }
227:
228: protected int calculateTotalSize(List uidList) throws Exception {
229: int totalSize = 0;
230:
231: Iterator it = uidList.iterator();
232:
233: while (it.hasNext()) {
234: totalSize += server.getMessageSize(it.next());
235: }
236:
237: return totalSize;
238: }
239:
240: public void downloadNewMessages(List newMessagesUIDList,
241: IWorkerStatusController worker) throws Exception {
242: LOG.fine("need to fetch " + newMessagesUIDList.size()
243: + " messages.");
244:
245: int totalSize = calculateTotalSize(newMessagesUIDList);
246:
247: worker.setProgressBarMaximum(totalSize);
248: worker.setProgressBarValue(0);
249:
250: newMessageCount = newMessagesUIDList.size();
251:
252: for (int i = 0; i < newMessageCount; i++) {
253:
254: if (worker.cancelled())
255: throw new CommandCancelledException();
256:
257: // which UID should be downloaded next
258: Object serverUID = newMessagesUIDList.get(i);
259:
260: LOG.fine("fetch message with UID=" + serverUID);
261:
262: log(MessageFormat.format(MailResourceLoader.getString(
263: "statusbar", "message", "fetch_messages"),
264: new Object[] { new Integer(i + 1),
265: new Integer(newMessageCount) }));
266:
267: int size = server.getMessageSize(serverUID);
268:
269: if (server.getAccountItem().getPopItem().getBoolean(
270: "enable_limit")) {
271: // check if message isn't too big to download
272: int maxSize = server.getAccountItem().getPopItem()
273: .getInteger("limit");
274:
275: // if message-size is bigger skip download of this message
276: if (size > maxSize) {
277: LOG.fine("skipping download of message, too big");
278:
279: continue;
280: }
281: }
282:
283: // now download the message
284: downloadMessage(serverUID, worker);
285:
286: if (!server.getAccountItem().getPopItem().getBoolean(
287: "leave_messages_on_server")) {
288: // delete message from server
289: server.deleteMessage(serverUID);
290:
291: LOG.fine("deleted message with uid=" + serverUID);
292: }
293: }
294: }
295:
296: public List synchronize() throws Exception {
297: log(MailResourceLoader.getString("statusbar", "message",
298: "fetch_uid_list"));
299:
300: LOG.fine("synchronize local UID-list with remote UID-list");
301:
302: // synchronize local UID-list with server
303: List newMessagesUIDList = server.synchronize();
304:
305: return newMessagesUIDList;
306: }
307:
308: public void logout() throws Exception {
309: server.logout();
310:
311: LOG.fine("logout");
312:
313: log(MailResourceLoader.getString("statusbar", "message",
314: "logout"));
315:
316: if (newMessageCount == 0) {
317: log(MailResourceLoader.getString("statusbar", "message",
318: "no_new_messages"));
319: }
320: }
321:
322: /**
323: * @see org.columba.api.command.Command#updateGUI()
324: */
325: public void updateGUI() throws Exception {
326: if (action != null) {
327: action.setEnabled(true);
328: }
329: }
330: }
|