diff --git a/src/java/org/jivesoftware/spark/ChatManager.java b/src/java/org/jivesoftware/spark/ChatManager.java index 82bb5cf3..7582cdee 100644 --- a/src/java/org/jivesoftware/spark/ChatManager.java +++ b/src/java/org/jivesoftware/spark/ChatManager.java @@ -21,30 +21,20 @@ package org.jivesoftware.spark; import org.jivesoftware.resource.SparkRes; import org.jivesoftware.smack.SmackException; +import org.jivesoftware.smack.XMPPException; import org.jivesoftware.smack.chat.Chat; import org.jivesoftware.smack.chat.ChatManagerListener; -import org.jivesoftware.smack.XMPPException; import org.jivesoftware.smack.packet.Message; import org.jivesoftware.smack.packet.Presence; import org.jivesoftware.smackx.chatstates.ChatState; import org.jivesoftware.smackx.chatstates.ChatStateListener; +import org.jivesoftware.smackx.muc.MultiUserChat; import org.jivesoftware.smackx.muc.MultiUserChatManager; import org.jivesoftware.smackx.xdata.Form; -import org.jivesoftware.smackx.muc.MultiUserChat; import org.jivesoftware.smackx.xdata.packet.DataForm; import org.jivesoftware.spark.component.tabbedPane.SparkTab; import org.jivesoftware.spark.decorator.DefaultTabHandler; -import org.jivesoftware.spark.ui.ChatContainer; -import org.jivesoftware.spark.ui.ChatRoom; -import org.jivesoftware.spark.ui.ChatRoomListener; -import org.jivesoftware.spark.ui.ChatRoomNotFoundException; -import org.jivesoftware.spark.ui.ContactItem; -import org.jivesoftware.spark.ui.ContactItemHandler; -import org.jivesoftware.spark.ui.ContactList; -import org.jivesoftware.spark.ui.GlobalMessageListener; -import org.jivesoftware.spark.ui.MessageFilter; -import org.jivesoftware.spark.ui.SparkTabHandler; -import org.jivesoftware.spark.ui.TranscriptWindowInterceptor; +import org.jivesoftware.spark.ui.*; import org.jivesoftware.spark.ui.conferences.RoomInvitationListener; import org.jivesoftware.spark.ui.rooms.ChatRoomImpl; import org.jivesoftware.spark.ui.rooms.GroupChatRoom; @@ -57,23 +47,14 @@ import org.jivesoftware.sparkimpl.settings.local.LocalPreferences; import org.jivesoftware.sparkimpl.settings.local.SettingsManager; import org.jxmpp.util.XmppStringUtils; -import java.awt.Color; -import java.awt.Component; +import javax.swing.*; +import java.awt.*; import java.net.URI; import java.net.URISyntaxException; -import java.util.ArrayList; -import java.util.Collection; -import java.util.Collections; -import java.util.HashSet; -import java.util.Iterator; +import java.util.*; import java.util.List; -import java.util.Set; import java.util.concurrent.CopyOnWriteArrayList; -import javax.swing.Icon; -import javax.swing.SwingUtilities; -import javax.swing.UIManager; - /** * Handles the Chat Management of each individual Workspace. The ChatManager is responsible * for creation and removal of chat rooms, transcripts, and transfers and room invitations. @@ -380,15 +361,6 @@ public class ChatManager implements ChatManagerListener { messageFilters.remove(filter); } - /** - * Returns a Collection of MessageFilters registered to Spark. - * - * @return the Collection of MessageFilters. - */ - public Collection getMessageFilters() { - return messageFilters; - } - /** * Adds a new GlobalMessageListener. * @@ -413,9 +385,18 @@ public class ChatManager implements ChatManagerListener { * @param chatRoom the ChatRoom where the message was sent to. * @param message the Message */ - public void fireGlobalMessageReceievedListeners(ChatRoom chatRoom, Message message) { - for (GlobalMessageListener listener : globalMessageListeners) { - listener.messageReceived(chatRoom, message); + public void fireGlobalMessageReceievedListeners( ChatRoom chatRoom, Message message ) + { + for ( GlobalMessageListener listener : globalMessageListeners ) + { + try + { + listener.messageReceived( chatRoom, message ); + } + catch ( Exception e ) + { + Log.error( "A GlobalMessageListener ('" + listener + "') threw an exception while processing an incoming chat message (from '" + message.getFrom() + "') in a chat room ('" + chatRoom + "').", e ); + } } } @@ -425,9 +406,18 @@ public class ChatManager implements ChatManagerListener { * @param chatRoom the ChatRoom where the message was sent from. * @param message the Message sent. */ - public void fireGlobalMessageSentListeners(ChatRoom chatRoom, Message message) { - for (GlobalMessageListener listener : globalMessageListeners) { - listener.messageSent(chatRoom, message); + public void fireGlobalMessageSentListeners( ChatRoom chatRoom, Message message ) + { + for ( GlobalMessageListener listener : globalMessageListeners ) + { + try + { + listener.messageSent( chatRoom, message ); + } + catch ( Exception e ) + { + Log.error( "A GlobalMessageListener ('" + listener + "') threw an exception while processing an outgoing chat message (to '" + message.getTo() + "') in a chat room ('" + chatRoom + "').", e ); + } } } @@ -437,20 +427,28 @@ public class ChatManager implements ChatManagerListener { * @param room the room the message belongs to. * @param message the message to filter. */ - public void filterIncomingMessage(ChatRoom room, Message message) { - // Fire Message Filters - final ChatManager chatManager = SparkManager.getChatManager(); - Iterator filters = chatManager.getMessageFilters().iterator(); - try { - cancelledNotification(message.getFrom(), ChatState.paused); + public void filterIncomingMessage( ChatRoom room, Message message ) + { + try + { + // TODO This probably does not belong here (but in a filter?) + cancelledNotification( message.getFrom(), ChatState.paused ); } - catch (Exception e) { - Log.error(e); + catch ( Exception e ) + { + Log.error( e ); } - // Notify MessageFilters. - while (filters.hasNext()) { - (filters.next()).filterIncoming(room, message); + for ( final MessageFilter filter : messageFilters ) + { + try + { + filter.filterIncoming( room, message ); + } + catch ( Exception e ) + { + Log.error( "A MessageFilter ('" + filter + "') threw an exception while processing an incoming chat message (from '" + message.getFrom() + "') in a chat room ('" + room + "').", e ); + } } } @@ -460,11 +458,18 @@ public class ChatManager implements ChatManagerListener { * @param room the ChatRoom the message belongs too. * @param message the Message being sent. */ - public void filterOutgoingMessage(ChatRoom room, Message message) { - // Fire Message Filters - final ChatManager chatManager = SparkManager.getChatManager(); - for (Object o : chatManager.getMessageFilters()) { - ((MessageFilter) o).filterOutgoing(room, message); + public void filterOutgoingMessage( ChatRoom room, Message message ) + { + for ( final MessageFilter filter : messageFilters ) + { + try + { + filter.filterOutgoing( room, message ); + } + catch ( Exception e ) + { + Log.error( "A MessageFilter ('" + filter + "') threw an exception while processing an outgoing chat message (from '" + message.getFrom() + "') in a chat room ('" + room + "').", e ); + } } } @@ -542,11 +547,20 @@ public class ChatManager implements ChatManagerListener { public void removeContactItemHandler(ContactItemHandler handler) { contactItemHandlers.remove(handler); } - - public void fireMessageReceived(Message message) { - for (ChatMessageHandler handler : chatMessageHandlers) { - handler.messageReceived(message); - } + + public void fireMessageReceived( Message message ) + { + for ( ChatMessageHandler handler : chatMessageHandlers ) + { + try + { + handler.messageReceived( message ); + } + catch ( Exception e ) + { + Log.error( "A ChatMessageHandler ('" + handler + "') threw an exception while processing this message: " + message, e ); + } + } } /** @@ -556,10 +570,20 @@ public class ChatManager implements ChatManagerListener { * @param presence the new presence. * @return true if it was handled. */ - public boolean fireContactItemPresenceChanged(ContactItem item, Presence presence) { - for (ContactItemHandler handler : contactItemHandlers) { - if (handler.handlePresence(item, presence)) { - return true; + public boolean fireContactItemPresenceChanged( ContactItem item, Presence presence ) + { + for ( ContactItemHandler handler : contactItemHandlers ) + { + try + { + if ( handler.handlePresence( item, presence ) ) + { + return true; + } + } + catch ( Exception e ) + { + Log.error( "A ContactItemHandler ('" + handler + "') threw an exception while processing a presence change (ContactItem: '" + item + "', presence: [" + presence + "])", e ); } } @@ -572,10 +596,20 @@ public class ChatManager implements ChatManagerListener { * @param item the ContactItem that was double clicked. * @return true if the event was intercepted and handled. */ - public boolean fireContactItemDoubleClicked(ContactItem item) { - for (ContactItemHandler handler : contactItemHandlers) { - if (handler.handleDoubleClick(item)) { - return true; + public boolean fireContactItemDoubleClicked( ContactItem item ) + { + for ( ContactItemHandler handler : contactItemHandlers ) + { + try + { + if ( handler.handleDoubleClick( item ) ) + { + return true; + } + } + catch ( Exception e ) + { + Log.error( "A ContactItemHandler ('" + handler + "') threw an exception while processing a double click on ContactItem: '" + item + "'.", e ); } } @@ -588,11 +622,21 @@ public class ChatManager implements ChatManagerListener { * @param jid the jid. * @return the icon of the handler. */ - public Icon getIconForContactHandler(String jid) { - for (ContactItemHandler handler : contactItemHandlers) { - Icon icon = handler.getIcon(jid); - if (icon != null) { - return icon; + public Icon getIconForContactHandler( String jid ) + { + for ( ContactItemHandler handler : contactItemHandlers ) + { + try + { + Icon icon = handler.getIcon( jid ); + if ( icon != null ) + { + return icon; + } + } + catch ( Exception e ) + { + Log.error( "A ContactItemHandler ('" + handler + "') threw an exception while processing an icon request for: '" + jid + "'.", e ); } } @@ -605,11 +649,21 @@ public class ChatManager implements ChatManagerListener { * @param presence the presence. * @return the icon. */ - public Icon getTabIconForContactHandler(Presence presence) { - for (ContactItemHandler handler : contactItemHandlers) { - Icon icon = handler.getTabIcon(presence); - if (icon != null) { - return icon; + public Icon getTabIconForContactHandler( Presence presence ) + { + for ( ContactItemHandler handler : contactItemHandlers ) + { + try + { + Icon icon = handler.getTabIcon( presence ); + if ( icon != null ) + { + return icon; + } + } + catch ( Exception e ) + { + Log.error( "A ContactItemHandler ('" + handler + "') threw an exception while processing a tab icon request for: '" + presence + "'.", e ); } } @@ -749,18 +803,29 @@ public class ChatManager implements ChatManagerListener { * * @param component the component within the tab. */ - public void notifySparkTabHandlers(Component component) { - final SparkTab tab = chatContainer.getTabContainingComponent(component); - if (tab == null) { + public void notifySparkTabHandlers( Component component ) + { + final SparkTab tab = chatContainer.getTabContainingComponent( component ); + if ( tab == null ) + { return; } boolean isChatFrameInFocus = getChatContainer().getChatFrame().isInFocus(); boolean isSelectedTab = getChatContainer().getSelectedComponent() == component; - for (SparkTabHandler decorator : sparkTabHandlers) { - boolean isHandled = decorator.isTabHandled(tab, component, isSelectedTab, isChatFrameInFocus); - if (isHandled) { - tab.validateTab(); - return; + for ( SparkTabHandler decorator : sparkTabHandlers ) + { + try + { + boolean isHandled = decorator.isTabHandled( tab, component, isSelectedTab, isChatFrameInFocus ); + if ( isHandled ) + { + tab.validateTab(); + return; + } + } + catch ( Exception e ) + { + Log.error( "A SparkTabHandler ('" + decorator + "') threw an exception.", e ); } } } diff --git a/src/java/org/jivesoftware/spark/ui/TranscriptWindow.java b/src/java/org/jivesoftware/spark/ui/TranscriptWindow.java index f78c6c8e..3723fb4b 100644 --- a/src/java/org/jivesoftware/spark/ui/TranscriptWindow.java +++ b/src/java/org/jivesoftware/spark/ui/TranscriptWindow.java @@ -19,36 +19,6 @@ */ package org.jivesoftware.spark.ui; -import java.awt.Color; -import java.awt.Component; -import java.awt.Font; -import java.awt.Toolkit; -import java.awt.datatransfer.StringSelection; -import java.awt.event.ActionEvent; -import java.awt.event.MouseEvent; -import java.io.BufferedWriter; -import java.io.File; -import java.io.FileWriter; -import java.text.SimpleDateFormat; -import java.util.Date; -import java.util.Iterator; -import java.util.List; - -import javax.swing.AbstractAction; -import javax.swing.Action; -import javax.swing.JComponent; -import javax.swing.JFileChooser; -import javax.swing.JOptionPane; -import javax.swing.JPopupMenu; -import javax.swing.KeyStroke; -import javax.swing.UIManager; -import javax.swing.text.BadLocationException; -import javax.swing.text.Document; -import javax.swing.text.SimpleAttributeSet; -import javax.swing.text.Style; -import javax.swing.text.StyleConstants; -import javax.swing.text.StyledDocument; - import org.jdesktop.swingx.calendar.DateUtils; import org.jivesoftware.Spark; import org.jivesoftware.resource.Default; @@ -67,6 +37,20 @@ import org.jivesoftware.sparkimpl.settings.local.LocalPreferences; import org.jivesoftware.sparkimpl.settings.local.SettingsManager; import org.jxmpp.util.XmppStringUtils; +import javax.swing.*; +import javax.swing.text.*; +import java.awt.*; +import java.awt.datatransfer.StringSelection; +import java.awt.event.ActionEvent; +import java.awt.event.MouseEvent; +import java.io.BufferedWriter; +import java.io.File; +import java.io.FileWriter; +import java.text.SimpleDateFormat; +import java.util.Date; +import java.util.Iterator; +import java.util.List; + /** * The TranscriptWindow class. Provides a default implementation * of a Chat Window. In general, extensions could override this class @@ -168,11 +152,20 @@ public class TranscriptWindow extends ChatArea implements ContextMenuListener { */ public void insertMessage(String nickname, Message message, Color foreground, Color background) { // Check interceptors. - for (TranscriptWindowInterceptor interceptor : SparkManager.getChatManager().getTranscriptWindowInterceptors()) { - boolean handled = interceptor.isMessageIntercepted(this, nickname, message); - if (handled) { - // Do nothing. - return; + for (TranscriptWindowInterceptor interceptor : SparkManager.getChatManager().getTranscriptWindowInterceptors()) + { + try + { + boolean handled = interceptor.isMessageIntercepted( this, nickname, message ); + if ( handled ) + { + // Do nothing. + return; + } + } + catch ( Exception e ) + { + Log.error( "A TranscriptWindowInterceptor ('" + interceptor + "') threw an exception while processing a chat message (current user: '" + nickname + "').", e ); } }