diff --git a/bosh/src/main/java/org/jivesoftware/smack/BOSHConnection.java b/bosh/src/main/java/org/jivesoftware/smack/BOSHConnection.java index 5a0b8d3bc..bbbe206e7 100644 --- a/bosh/src/main/java/org/jivesoftware/smack/BOSHConnection.java +++ b/bosh/src/main/java/org/jivesoftware/smack/BOSHConnection.java @@ -22,6 +22,11 @@ import java.io.PipedReader; import java.io.PipedWriter; import java.io.Writer; +import javax.security.sasl.SaslException; + +import org.jivesoftware.smack.SmackException.NotConnectedException; +import org.jivesoftware.smack.SmackException.AlreadyLoggedInException; +import org.jivesoftware.smack.SmackException.ConnectionException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.ConnectionCreationListener; import org.jivesoftware.smack.ConnectionListener; @@ -29,9 +34,7 @@ import org.jivesoftware.smack.Roster; import org.jivesoftware.smack.XMPPException; import org.jivesoftware.smack.packet.Packet; import org.jivesoftware.smack.packet.Presence; -import org.jivesoftware.smack.packet.XMPPError; import org.jivesoftware.smack.util.StringUtils; - import org.igniterealtime.jbosh.BOSHClient; import org.igniterealtime.jbosh.BOSHClientConfig; import org.igniterealtime.jbosh.BOSHClientConnEvent; @@ -134,7 +137,7 @@ public class BOSHConnection extends XMPPConnection { this.config = config; } - public void connect() throws XMPPException { + public void connect() throws SmackException { if (connected) { throw new IllegalStateException("Already connected to a server."); } @@ -179,7 +182,7 @@ public class BOSHConnection extends XMPPConnection { .setAttribute(BodyQName.createWithPrefix(XMPP_BOSH_NS, "version", "xmpp"), "1.0") .build()); } catch (Exception e) { - throw new XMPPException("Can't connect to " + getServiceName(), e); + throw new ConnectionException(e); } // Wait for the response from the server @@ -197,9 +200,7 @@ public class BOSHConnection extends XMPPConnection { done = true; String errorMessage = "Timeout reached for the connection to " + getHost() + ":" + getPort() + "."; - throw new XMPPException( - errorMessage, - new XMPPError(XMPPError.Condition.remote_server_timeout, errorMessage)); + throw new SmackException(errorMessage); } } @@ -213,7 +214,7 @@ public class BOSHConnection extends XMPPConnection { } } - public Roster getRoster() { + public Roster getRoster() throws XMPPException, SmackException { if (roster == null) { return null; } @@ -276,12 +277,12 @@ public class BOSHConnection extends XMPPConnection { } public void login(String username, String password, String resource) - throws XMPPException { + throws XMPPException, SmackException, IOException { if (!isConnected()) { - throw new IllegalStateException("Not connected to server."); + throw new NotConnectedException(); } if (authenticated) { - throw new IllegalStateException("Already logged in to server."); + throw new AlreadyLoggedInException(); } // Do partial version of nameprep on the username. username = username.toLowerCase().trim(); @@ -295,7 +296,7 @@ public class BOSHConnection extends XMPPConnection { response = saslAuthentication.authenticate(resource, config.getCallbackHandler()); } } else { - throw new XMPPException("No non-anonymous SASL authentication mechanism available"); + throw new SaslException("No non-anonymous SASL authentication mechanism available"); } // Set the user. @@ -338,12 +339,12 @@ public class BOSHConnection extends XMPPConnection { } } - public void loginAnonymously() throws XMPPException { - if (!isConnected()) { - throw new IllegalStateException("Not connected to server."); + public void loginAnonymously() throws XMPPException, SmackException, IOException { + if (!isConnected()) { + throw new NotConnectedException(); } if (authenticated) { - throw new IllegalStateException("Already logged in to server."); + throw new AlreadyLoggedInException(); } String response; @@ -352,7 +353,7 @@ public class BOSHConnection extends XMPPConnection { } else { // Authenticate using Non-SASL - throw new XMPPException("No anonymous SASL authentication mechanism available"); + throw new SaslException("No anonymous SASL authentication mechanism available"); } // Set the user value. @@ -666,7 +667,7 @@ public class BOSHConnection extends XMPPConnection { listener.reconnectionSuccessful(); } } - catch (XMPPException e) { + catch (Exception e) { for (ConnectionListener listener : getConnectionListeners()) { listener.reconnectionFailed(e); } diff --git a/bosh/src/main/java/org/jivesoftware/smack/BOSHPacketReader.java b/bosh/src/main/java/org/jivesoftware/smack/BOSHPacketReader.java index 91aeaab33..ba8a21b1a 100644 --- a/bosh/src/main/java/org/jivesoftware/smack/BOSHPacketReader.java +++ b/bosh/src/main/java/org/jivesoftware/smack/BOSHPacketReader.java @@ -20,9 +20,10 @@ package org.jivesoftware.smack; import java.io.StringReader; import org.jivesoftware.smack.sasl.SASLMechanism.Challenge; -import org.jivesoftware.smack.sasl.SASLMechanism.Failure; +import org.jivesoftware.smack.sasl.SASLMechanism.SASLFailure; import org.jivesoftware.smack.sasl.SASLMechanism.Success; import org.jivesoftware.smack.util.PacketParserUtils; +import org.jivesoftware.smack.XMPPException.StreamErrorException; import org.xmlpull.v1.XmlPullParserFactory; import org.xmlpull.v1.XmlPullParser; import org.igniterealtime.jbosh.AbstractBody; @@ -106,12 +107,12 @@ public class BOSHPacketReader implements BOSHClientResponseListener { parseFeatures(parser); } else if (parser.getName().equals("failure")) { if ("urn:ietf:params:xml:ns:xmpp-sasl".equals(parser.getNamespace(null))) { - final Failure failure = PacketParserUtils.parseSASLFailure(parser); - connection.getSASLAuthentication().authenticationFailed(failure.getCondition()); + final SASLFailure failure = PacketParserUtils.parseSASLFailure(parser); + connection.getSASLAuthentication().authenticationFailed(failure); connection.processPacket(failure); } } else if (parser.getName().equals("error")) { - throw new XMPPException(PacketParserUtils.parseStreamError(parser)); + throw new StreamErrorException(PacketParserUtils.parseStreamError(parser)); } } } while (eventType != XmlPullParser.END_DOCUMENT); diff --git a/core/src/main/java/org/jivesoftware/smack/AccountManager.java b/core/src/main/java/org/jivesoftware/smack/AccountManager.java index 9cf1b19e4..3f86cb7e0 100644 --- a/core/src/main/java/org/jivesoftware/smack/AccountManager.java +++ b/core/src/main/java/org/jivesoftware/smack/AccountManager.java @@ -21,9 +21,9 @@ import java.util.Collection; import java.util.Collections; import java.util.HashMap; import java.util.Map; -import java.util.logging.Level; -import java.util.logging.Logger; +import org.jivesoftware.smack.SmackException.NoResponseException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.packet.IQ; import org.jivesoftware.smack.packet.Registration; import org.jivesoftware.smack.util.StringUtils; @@ -35,8 +35,6 @@ import org.jivesoftware.smack.util.StringUtils; * @author Matt Tucker */ public class AccountManager { - private static final Logger LOGGER = Logger.getLogger(AccountManager.class.getName()); - private XMPPConnection connection; private Registration info = null; @@ -74,8 +72,10 @@ public class AccountManager { * behavior is to only create new accounts before having logged in to a server. * * @return true if the server support creating new accounts. + * @throws XMPPErrorException + * @throws NoResponseException */ - public boolean supportsAccountCreation() { + public boolean supportsAccountCreation() throws NoResponseException, XMPPErrorException { // Check if we already know that the server supports creating new accounts if (accountCreationSupported) { return true; @@ -83,16 +83,11 @@ public class AccountManager { // No information is known yet (e.g. no stream feature was received from the server // indicating that it supports creating new accounts) so send an IQ packet as a way // to discover if this feature is supported - try { - if (info == null) { - getRegistrationInfo(); - accountCreationSupported = info.getType() != IQ.Type.ERROR; - } - return accountCreationSupported; - } - catch (XMPPException xe) { - return false; + if (info == null) { + getRegistrationInfo(); + accountCreationSupported = info.getType() != IQ.Type.ERROR; } + return accountCreationSupported; } /** @@ -118,21 +113,19 @@ public class AccountManager { * the user's email address. * * @return the required account attributes. + * @throws XMPPErrorException + * @throws NoResponseException */ - public Collection getAccountAttributes() { - try { - if (info == null) { - getRegistrationInfo(); - } - Map attributes = info.getAttributes(); - if (attributes != null) { - return Collections.unmodifiableSet(attributes.keySet()); - } + public Collection getAccountAttributes() throws NoResponseException, XMPPErrorException { + if (info == null) { + getRegistrationInfo(); } - catch (XMPPException xe) { - LOGGER.log(Level.SEVERE, "Error retrieving account attributes from server", xe); + Map attributes = info.getAttributes(); + if (attributes != null) { + return Collections.unmodifiableSet(attributes.keySet()); + } else { + return Collections.emptySet(); } - return Collections.emptySet(); } /** @@ -142,18 +135,14 @@ public class AccountManager { * @param name the name of the account attribute to return its value. * @return the value of the account attribute or null if an account * attribute wasn't found for the requested name. + * @throws XMPPErrorException + * @throws NoResponseException */ - public String getAccountAttribute(String name) { - try { - if (info == null) { - getRegistrationInfo(); - } - return info.getAttributes().get(name); + public String getAccountAttribute(String name) throws NoResponseException, XMPPErrorException { + if (info == null) { + getRegistrationInfo(); } - catch (XMPPException xe) { - LOGGER.log(Level.SEVERE, "Error retrieving account attribute " + name + " info from server", xe); - } - return null; + return info.getAttributes().get(name); } /** @@ -162,18 +151,14 @@ public class AccountManager { * that will complete the registration process. * * @return the account creation instructions, or null if there are none. + * @throws XMPPErrorException + * @throws NoResponseException */ - public String getAccountInstructions() { - try { - if (info == null) { - getRegistrationInfo(); - } - return info.getInstructions(); - } - catch (XMPPException xe) { - LOGGER.log(Level.SEVERE, "Error retrieving account instructions from server", xe); - return null; + public String getAccountInstructions() throws NoResponseException, XMPPErrorException { + if (info == null) { + getRegistrationInfo(); } + return info.getInstructions(); } /** @@ -186,12 +171,10 @@ public class AccountManager { * * @param username the username. * @param password the password. - * @throws XMPPException if an error occurs creating the account. + * @throws XMPPErrorException + * @throws NoResponseException */ - public void createAccount(String username, String password) throws XMPPException { - if (!supportsAccountCreation()) { - throw new XMPPException("Server does not support account creation."); - } + public void createAccount(String username, String password) throws NoResponseException, XMPPErrorException { // Create a map for all the required attributes, but give them blank values. Map attributes = new HashMap(); for (String attributeName : getAccountAttributes()) { @@ -208,20 +191,17 @@ public class AccountManager { * @param username the username. * @param password the password. * @param attributes the account attributes. - * @throws XMPPException if an error occurs creating the account. + * @throws XMPPErrorException if an error occurs creating the account. + * @throws NoResponseException if there was no response from the server. * @see #getAccountAttributes() */ public void createAccount(String username, String password, Map attributes) - throws XMPPException - { - if (!supportsAccountCreation()) { - throw new XMPPException("Server does not support account creation."); - } + throws NoResponseException, XMPPErrorException { Registration reg = new Registration(); reg.setType(IQ.Type.SET); reg.setTo(connection.getServiceName()); - attributes.put("username",username); - attributes.put("password",password); + attributes.put("username", username); + attributes.put("password", password); reg.setAttributes(attributes); connection.createPacketCollectorAndSend(reg).nextResultOrThrow(); } @@ -232,9 +212,10 @@ public class AccountManager { * support changing passwords; an XMPPException will be thrown when that is the case. * * @throws IllegalStateException if not currently logged-in to the server. - * @throws XMPPException if an error occurs when changing the password. + * @throws XMPPErrorException if an error occurs when changing the password. + * @throws NoResponseException if there was no response from the server. */ - public void changePassword(String newPassword) throws XMPPException { + public void changePassword(String newPassword) throws NoResponseException, XMPPErrorException { Registration reg = new Registration(); reg.setType(IQ.Type.SET); reg.setTo(connection.getServiceName()); @@ -251,12 +232,10 @@ public class AccountManager { * support deleting accounts; an XMPPException will be thrown when that is the case. * * @throws IllegalStateException if not currently logged-in to the server. - * @throws XMPPException if an error occurs when deleting the account. + * @throws XMPPErrorException if an error occurs when deleting the account. + * @throws NoResponseException if there was no response from the server. */ - public void deleteAccount() throws XMPPException { - if (!connection.isAuthenticated()) { - throw new IllegalStateException("Must be logged in to delete a account."); - } + public void deleteAccount() throws NoResponseException, XMPPErrorException { Registration reg = new Registration(); reg.setType(IQ.Type.SET); reg.setTo(connection.getServiceName()); @@ -269,10 +248,13 @@ public class AccountManager { /** * Gets the account registration info from the server. + * @throws XMPPErrorException + * @throws NoResponseException * * @throws XMPPException if an error occurs. + * @throws SmackException if there was no response from the server. */ - private synchronized void getRegistrationInfo() throws XMPPException { + private synchronized void getRegistrationInfo() throws NoResponseException, XMPPErrorException { Registration reg = new Registration(); reg.setTo(connection.getServiceName()); info = (Registration) connection.createPacketCollectorAndSend(reg).nextResultOrThrow(); diff --git a/core/src/main/java/org/jivesoftware/smack/PacketCollector.java b/core/src/main/java/org/jivesoftware/smack/PacketCollector.java index 718f8e38e..d402f6db0 100644 --- a/core/src/main/java/org/jivesoftware/smack/PacketCollector.java +++ b/core/src/main/java/org/jivesoftware/smack/PacketCollector.java @@ -20,6 +20,8 @@ package org.jivesoftware.smack; import java.util.concurrent.ArrayBlockingQueue; import java.util.concurrent.TimeUnit; +import org.jivesoftware.smack.SmackException.NoResponseException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.filter.PacketFilter; import org.jivesoftware.smack.packet.Packet; import org.jivesoftware.smack.packet.XMPPError; @@ -152,9 +154,10 @@ public class PacketCollector { * null will be returned. This method does also cancel the PacketCollector. * * @return the next available packet. - * @throws XMPPException + * @throws XMPPErrorException in case an error response. + * @throws NoResponseException if there was no response from the server. */ - public Packet nextResultOrThrow() throws XMPPException { + public Packet nextResultOrThrow() throws NoResponseException, XMPPErrorException { return nextResultOrThrow(connection.getPacketReplyTimeout()); } @@ -164,18 +167,19 @@ public class PacketCollector { * * @param timeout the amount of time to wait for the next packet (in milleseconds). * @return the next available packet. - * @throws XMPPException in case of no response or error response + * @throws NoResponseException if there was no response from the server. + * @throws XMPPErrorException in case an error response. */ - public Packet nextResultOrThrow(long timeout) throws XMPPException { + public Packet nextResultOrThrow(long timeout) throws NoResponseException, XMPPErrorException { Packet result = nextResult(timeout); cancel(); if (result == null) { - throw new XMPPException(SmackError.NO_RESPONSE_FROM_SERVER); + throw new NoResponseException(); } XMPPError xmppError = result.getError(); if (xmppError != null) { - throw new XMPPException(xmppError); + throw new XMPPErrorException(xmppError); } return result; diff --git a/core/src/main/java/org/jivesoftware/smack/ReconnectionManager.java b/core/src/main/java/org/jivesoftware/smack/ReconnectionManager.java index e43fabee6..a2ae412a4 100644 --- a/core/src/main/java/org/jivesoftware/smack/ReconnectionManager.java +++ b/core/src/main/java/org/jivesoftware/smack/ReconnectionManager.java @@ -16,7 +16,9 @@ */ package org.jivesoftware.smack; +import org.jivesoftware.smack.XMPPException.StreamErrorException; import org.jivesoftware.smack.packet.StreamError; + import java.util.Random; import java.util.logging.Logger; /** @@ -146,7 +148,7 @@ public class ReconnectionManager implements ConnectionListener { connection.connect(); } } - catch (XMPPException e) { + catch (Exception e) { // Fires the failed reconnection notification ReconnectionManager.this.notifyReconnectionFailed(e); } @@ -191,17 +193,13 @@ public class ReconnectionManager implements ConnectionListener { public void connectionClosedOnError(Exception e) { done = false; - if (e instanceof XMPPException) { - XMPPException xmppEx = (XMPPException) e; + if (e instanceof StreamErrorException) { + StreamErrorException xmppEx = (StreamErrorException) e; StreamError error = xmppEx.getStreamError(); + String reason = error.getCode(); - // Make sure the error is not null - if (error != null) { - String reason = error.getCode(); - - if ("conflict".equals(reason)) { - return; - } + if ("conflict".equals(reason)) { + return; } } diff --git a/core/src/main/java/org/jivesoftware/smack/Roster.java b/core/src/main/java/org/jivesoftware/smack/Roster.java index cc33b0c22..e7adb5599 100644 --- a/core/src/main/java/org/jivesoftware/smack/Roster.java +++ b/core/src/main/java/org/jivesoftware/smack/Roster.java @@ -30,6 +30,9 @@ import java.util.Set; import java.util.concurrent.ConcurrentHashMap; import java.util.concurrent.CopyOnWriteArrayList; +import org.jivesoftware.smack.SmackException.NoResponseException; +import org.jivesoftware.smack.SmackException.NotLoggedInException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.filter.IQReplyFilter; import org.jivesoftware.smack.filter.PacketFilter; import org.jivesoftware.smack.filter.PacketTypeFilter; @@ -186,17 +189,19 @@ public class Roster { * Reloads the entire roster from the server. This is an asynchronous operation, * which means the method will return immediately, and the roster will be * reloaded at a later point when the server responds to the reload request. - * - * @throws IllegalStateException if connection is not logged in or logged in anonymously + * + * @throws SmackException If not logged in. + * @throws IllegalStateException if logged in anonymously */ - public void reload() { + public void reload() throws XMPPException, SmackException { if (!connection.isAuthenticated()) { - throw new IllegalStateException("Not logged in to server."); + throw new NotLoggedInException(); } if (connection.isAnonymous()) { throw new IllegalStateException("Anonymous users can't have a roster."); } + RosterPacket packet = new RosterPacket(); if (rosterStore != null && connection.isRosterVersioningSupported()) { packet.setVersion(rosterStore.getRosterVersion()); @@ -235,18 +240,19 @@ public class Roster { * after a logout/login. This is due to the way that XMPP stores group information. * * @param name the name of the group. - * @return a new group. - * @throws IllegalStateException if connection is not logged in or logged in anonymously + * @return a new group, or null if the group already exists + * @throws NotLoggedInException If not logged in. + * @throws IllegalStateException if logged in anonymously */ - public RosterGroup createGroup(String name) { + public RosterGroup createGroup(String name) throws NotLoggedInException { if (!connection.isAuthenticated()) { - throw new IllegalStateException("Not logged in to server."); + throw new NotLoggedInException(); } if (connection.isAnonymous()) { throw new IllegalStateException("Anonymous users can't have a roster."); } if (groups.containsKey(name)) { - throw new IllegalArgumentException("Group with name " + name + " alread exists."); + return null; } RosterGroup group = new RosterGroup(name, connection); @@ -262,12 +268,15 @@ public class Roster { * @param name the nickname of the user. * @param groups the list of group names the entry will belong to, or null if the * the roster entry won't belong to a group. - * @throws XMPPException if an XMPP exception occurs. - * @throws IllegalStateException if connection is not logged in or logged in anonymously + * @throws NotLoggedInException + * @throws NoResponseException if there was no response from the server. + * @throws XMPPErrorException if an XMPP exception occurs. + * @throws NotLoggedInException If not logged in. + * @throws IllegalStateException if logged in anonymously */ - public void createEntry(String user, String name, String[] groups) throws XMPPException { + public void createEntry(String user, String name, String[] groups) throws NotLoggedInException, NoResponseException, XMPPErrorException { if (!connection.isAuthenticated()) { - throw new IllegalStateException("Not logged in to server."); + throw new NotLoggedInException(); } if (connection.isAnonymous()) { throw new IllegalStateException("Anonymous users can't have a roster."); @@ -300,12 +309,14 @@ public class Roster { * to send an updated subscription status. * * @param entry a roster entry. - * @throws XMPPException if an XMPP error occurs. + * @throws XMPPErrorException if an XMPP error occurs. + * @throws NotLoggedInException if not logged in. + * @throws NoResponseException SmackException if there was no response from the server. * @throws IllegalStateException if connection is not logged in or logged in anonymously */ - public void removeEntry(RosterEntry entry) throws XMPPException { + public void removeEntry(RosterEntry entry) throws NotLoggedInException, NoResponseException, XMPPErrorException { if (!connection.isAuthenticated()) { - throw new IllegalStateException("Not logged in to server."); + throw new NotLoggedInException(); } if (connection.isAnonymous()) { throw new IllegalStateException("Anonymous users can't have a roster."); @@ -654,7 +665,7 @@ public class Roster { private void addUpdateEntry(Collection addedEntries, Collection updatedEntries, RosterPacket.Item item, - RosterEntry entry) { + RosterEntry entry) throws SmackException { RosterEntry oldEntry = entries.put(item.getUser(), entry); if (oldEntry == null) { addedEntries.add(item.getUser()); @@ -922,10 +933,14 @@ public class Roster { Collection updatedEntries = new ArrayList(); Collection deletedEntries = new ArrayList(); - if (packet instanceof RosterPacket) { - nonemptyResult((RosterPacket) packet, addedEntries, updatedEntries, deletedEntries); - } else { - emptyResult(addedEntries, updatedEntries); + try { + if (packet instanceof RosterPacket) { + nonemptyResult((RosterPacket) packet, addedEntries, updatedEntries, deletedEntries); + } else { + emptyResult(addedEntries, updatedEntries); + } + } catch (SmackException e) { + return; } synchronized (Roster.this) { @@ -936,7 +951,7 @@ public class Roster { fireRosterChangedEvent(addedEntries, updatedEntries, deletedEntries); } - private void emptyResult(Collection addedEntries, Collection updatedEntries) { + private void emptyResult(Collection addedEntries, Collection updatedEntries) throws SmackException { for(RosterPacket.Item item : rosterStore.getEntries()){ RosterEntry entry = new RosterEntry(item.getUser(), item.getName(), item.getItemType(), item.getItemStatus(), Roster.this, connection); @@ -945,7 +960,7 @@ public class Roster { } private void addEntries(Collection addedEntries, Collection updatedEntries, - Collection deletedEntries, String version, Collection items) { + Collection deletedEntries, String version, Collection items) throws SmackException { for (RosterPacket.Item item : items) { RosterEntry entry = new RosterEntry(item.getUser(), item.getName(), item.getItemType(), item.getItemStatus(), Roster.this, connection); @@ -968,7 +983,9 @@ public class Roster { } } - private void nonemptyResult(RosterPacket packet, Collection addedEntries, Collection updatedEntries, Collection deletedEntries) { + private void nonemptyResult(RosterPacket packet, Collection addedEntries, + Collection updatedEntries, Collection deletedEntries) + throws SmackException { RosterPacket rosterPacket = (RosterPacket) packet; String version = rosterPacket.getVersion(); @@ -1021,7 +1038,12 @@ public class Roster { Collection deletedEntries = new ArrayList(); Item item = items.iterator().next(); - processPushItem(addedEntries, updatedEntries, deletedEntries, version, item); + try { + processPushItem(addedEntries, updatedEntries, deletedEntries, version, item); + } + catch (SmackException e) { + return; + } connection.sendPacket(IQ.createResultIQ(rosterPacket)); @@ -1032,7 +1054,7 @@ public class Roster { } private void processPushItem(Collection addedEntries, Collection updatedEntries, - Collection deletedEntries, String version, Item item) { + Collection deletedEntries, String version, Item item) throws SmackException { RosterEntry entry = new RosterEntry(item.getUser(), item.getName(), item.getItemType(), item.getItemStatus(), Roster.this, connection); diff --git a/core/src/main/java/org/jivesoftware/smack/RosterGroup.java b/core/src/main/java/org/jivesoftware/smack/RosterGroup.java index da9242cc6..b56e3e286 100644 --- a/core/src/main/java/org/jivesoftware/smack/RosterGroup.java +++ b/core/src/main/java/org/jivesoftware/smack/RosterGroup.java @@ -23,6 +23,8 @@ import java.util.Collections; import java.util.LinkedHashSet; import java.util.Set; +import org.jivesoftware.smack.SmackException.NoResponseException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.packet.IQ; import org.jivesoftware.smack.packet.RosterPacket; import org.jivesoftware.smack.util.StringUtils; @@ -158,9 +160,10 @@ public class RosterGroup { * to receive the updated roster. * * @param entry a roster entry. - * @throws XMPPException if an error occured while trying to add the entry to the group. + * @throws XMPPErrorException if an error occured while trying to add the entry to the group. + * @throws NoResponseException if there was no response from the server. */ - public void addEntry(RosterEntry entry) throws XMPPException { + public void addEntry(RosterEntry entry) throws NoResponseException, XMPPErrorException { PacketCollector collector = null; // Only add the entry if it isn't already in the list. synchronized (entries) { @@ -187,9 +190,10 @@ public class RosterGroup { * to receive the updated roster. * * @param entry a roster entry. - * @throws XMPPException if an error occurred while trying to remove the entry from the group. + * @throws XMPPErrorException if an error occurred while trying to remove the entry from the group. + * @throws NoResponseException if there was no response from the server. */ - public void removeEntry(RosterEntry entry) throws XMPPException { + public void removeEntry(RosterEntry entry) throws NoResponseException, XMPPErrorException { PacketCollector collector = null; // Only remove the entry if it's in the entry list. // Remove the entry locally, if we wait for RosterPacketListenerprocess>>Packet(Packet) diff --git a/core/src/main/java/org/jivesoftware/smack/SASLAuthentication.java b/core/src/main/java/org/jivesoftware/smack/SASLAuthentication.java index afa14cb11..8323d97cb 100644 --- a/core/src/main/java/org/jivesoftware/smack/SASLAuthentication.java +++ b/core/src/main/java/org/jivesoftware/smack/SASLAuthentication.java @@ -17,12 +17,17 @@ package org.jivesoftware.smack; +import org.jivesoftware.smack.SmackException.NoResponseException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.packet.Bind; import org.jivesoftware.smack.packet.Packet; import org.jivesoftware.smack.packet.Session; import org.jivesoftware.smack.sasl.*; +import org.jivesoftware.smack.sasl.SASLMechanism.SASLFailure; import javax.security.auth.callback.CallbackHandler; +import javax.security.sasl.SaslException; + import java.io.IOException; import java.lang.reflect.Constructor; import java.util.*; @@ -68,17 +73,13 @@ public class SASLAuthentication { * Boolean indicating if SASL negotiation has finished and was successful. */ private boolean saslNegotiated; - /** - * Boolean indication if SASL authentication has failed. When failed the server may end - * the connection. - */ - private boolean saslFailed; + private boolean resourceBinded; private boolean sessionSupported; /** * The SASL related error condition if there was one provided by the server. */ - private String errorCondition; + private SASLFailure saslFailure; static { @@ -205,15 +206,18 @@ public class SASLAuthentication { * @param resource the desired resource. * @param cbh the CallbackHandler used to get information from the user * @return the full JID provided by the server while binding a resource to the connection. - * @throws XMPPException if an error occures while authenticating. + * @throws IOException + * @throws XMPPErrorException + * @throws NoResponseException + * @throws SASLErrorException */ - public String authenticate(String resource, CallbackHandler cbh) - throws XMPPException { + public String authenticate(String resource, CallbackHandler cbh) throws IOException, + NoResponseException, XMPPErrorException, SASLErrorException { // Locate the SASLMechanism to use String selectedMechanism = null; for (String mechanism : mechanismsPreferences) { - if (implementedMechanisms.containsKey(mechanism) && - serverMechanisms.contains(mechanism)) { + if (implementedMechanisms.containsKey(mechanism) + && serverMechanisms.contains(mechanism)) { selectedMechanism = mechanism; break; } @@ -221,58 +225,55 @@ public class SASLAuthentication { if (selectedMechanism != null) { // A SASL mechanism was found. Authenticate using the selected mechanism and then // proceed to bind a resource + Class mechanismClass = implementedMechanisms.get(selectedMechanism); + + Constructor constructor; try { - Class mechanismClass = implementedMechanisms.get(selectedMechanism); - Constructor constructor = mechanismClass.getConstructor(SASLAuthentication.class); + constructor = mechanismClass.getConstructor(SASLAuthentication.class); currentMechanism = constructor.newInstance(this); - // Trigger SASL authentication with the selected mechanism. We use - // connection.getHost() since GSAPI requires the FQDN of the server, which - // may not match the XMPP domain. - currentMechanism.authenticate(connection.getHost(), cbh); - - // Wait until SASL negotiation finishes - synchronized (this) { - if (!saslNegotiated && !saslFailed) { - try { - wait(30000); - } - catch (InterruptedException e) { - // Ignore - } - } - } - - if (saslFailed) { - // SASL authentication failed and the server may have closed the connection - // so throw an exception - if (errorCondition != null) { - throw new XMPPException("SASL authentication " + - selectedMechanism + " failed: " + errorCondition); - } - else { - throw new XMPPException("SASL authentication failed using mechanism " + - selectedMechanism); - } - } - - if (saslNegotiated) { - // Bind a resource for this connection and - return bindResourceAndEstablishSession(resource); - } else { - // SASL authentication failed - } - } - catch (XMPPException e) { - throw e; } catch (Exception e) { - e.printStackTrace(); + throw new SaslException("Exception when creating the SASLAuthentication instance", + e); } + + // Trigger SASL authentication with the selected mechanism. We use + // connection.getHost() since GSAPI requires the FQDN of the server, which + // may not match the XMPP domain. + currentMechanism.authenticate(connection.getHost(), cbh); + + // Wait until SASL negotiation finishes + synchronized (this) { + if (!saslNegotiated && saslFailure == null) { + try { + wait(30000); + } + catch (InterruptedException e) { + // Ignore + } + } + } + + if (saslFailure != null) { + // SASL authentication failed and the server may have closed the connection + // so throw an exception + throw new SASLErrorException(selectedMechanism, saslFailure); + } + + if (saslNegotiated) { + // Bind a resource for this connection and + return bindResourceAndEstablishSession(resource); + } + else { + // SASL authentication failed + throw new SaslException(); + } + } else { - throw new XMPPException("SASL Authentication failed. No known authentication mechanisims."); + throw new SaslException( + "SASL Authentication failed. No known authentication mechanisims."); } - throw new XMPPException("SASL authentication failed"); } /** @@ -287,15 +288,20 @@ public class SASLAuthentication { * @param password the password to send to the server. * @param resource the desired resource. * @return the full JID provided by the server while binding a resource to the connection. - * @throws XMPPException if an error occures while authenticating. + * @throws XMPPErrorException + * @throws SASLErrorException + * @throws IOException + * @throws SaslException + * @throws SmackException */ public String authenticate(String username, String password, String resource) - throws XMPPException { + throws XMPPErrorException, SASLErrorException, SaslException, IOException, + SmackException { // Locate the SASLMechanism to use String selectedMechanism = null; for (String mechanism : mechanismsPreferences) { - if (implementedMechanisms.containsKey(mechanism) && - serverMechanisms.contains(mechanism)) { + if (implementedMechanisms.containsKey(mechanism) + && serverMechanisms.contains(mechanism)) { selectedMechanism = mechanism; break; } @@ -303,65 +309,56 @@ public class SASLAuthentication { if (selectedMechanism != null) { // A SASL mechanism was found. Authenticate using the selected mechanism and then // proceed to bind a resource + Class mechanismClass = implementedMechanisms.get(selectedMechanism); try { - Class mechanismClass = implementedMechanisms.get(selectedMechanism); Constructor constructor = mechanismClass.getConstructor(SASLAuthentication.class); currentMechanism = constructor.newInstance(this); - // Trigger SASL authentication with the selected mechanism. We use - // connection.getHost() since GSAPI requires the FQDN of the server, which - // may not match the XMPP domain. - - //The serviceName is basically the value that XMPP server sends to the client as being the location - //of the XMPP service we are trying to connect to. This should have the format: host [ "/" serv-name ] - //as per RFC-2831 guidelines - String serviceName = connection.getServiceName(); - currentMechanism.authenticate(username, connection.getHost(), serviceName, password); - - // Wait until SASL negotiation finishes - synchronized (this) { - if (!saslNegotiated && !saslFailed) { - try { - wait(30000); - } - catch (InterruptedException e) { - // Ignore - } - } - } - - if (saslFailed) { - // SASL authentication failed and the server may have closed the connection - // so throw an exception - if (errorCondition != null) { - throw new XMPPException("SASL authentication " + - selectedMechanism + " failed: " + errorCondition); - } - else { - throw new XMPPException("SASL authentication failed using mechanism " + - selectedMechanism); - } - } - - if (saslNegotiated) { - // Bind a resource for this connection and - return bindResourceAndEstablishSession(resource); - } - else { - // SASL authentication failed - throw new XMPPException("SASL authentication failed"); - } - } - catch (XMPPException e) { - throw e; } catch (Exception e) { + throw new SaslException("Exception when creating the SASLAuthentication instance", + e); + } + + // Trigger SASL authentication with the selected mechanism. We use + // connection.getHost() since GSAPI requires the FQDN of the server, which + // may not match the XMPP domain. + + // The serviceName is basically the value that XMPP server sends to the client as being + // the location of the XMPP service we are trying to connect to. This should have the + // format: host ["/" serv-name ] as per RFC-2831 guidelines + String serviceName = connection.getServiceName(); + currentMechanism.authenticate(username, connection.getHost(), serviceName, password); + + // Wait until SASL negotiation finishes + synchronized (this) { + if (!saslNegotiated && saslFailure == null) { + try { + wait(30000); + } + catch (InterruptedException e) { + // Ignore + } + } + } + + if (saslFailure != null) { + // SASL authentication failed and the server may have closed the connection + // so throw an exception + throw new SASLErrorException(selectedMechanism, saslFailure); + } + + if (saslNegotiated) { + // Bind a resource for this connection and + return bindResourceAndEstablishSession(resource); + } + else { // SASL authentication failed - throw new XMPPException("SASL authentication failed", e); + throw new SaslException(); } } else { - // No SASL method was found, throw an exception - throw new XMPPException("SASL authentication not supported by server"); + throw new SaslException( + "SASL Authentication failed. No known authentication mechanisims."); } } @@ -374,16 +371,19 @@ public class SASLAuthentication { * no username. * * @return the full JID provided by the server while binding a resource to the connection. - * @throws XMPPException if an error occures while authenticating. + * @throws SASLErrorException + * @throws IOException + * @throws SaslException + * @throws XMPPErrorException if an error occures while authenticating. + * @throws SmackException if there was no response from the server. */ - public String authenticateAnonymously() throws XMPPException { - try { + public String authenticateAnonymously() throws SASLErrorException, SaslException, IOException, SmackException, XMPPErrorException { currentMechanism = new SASLAnonymous(this); currentMechanism.authenticate(null,null,null,""); // Wait until SASL negotiation finishes synchronized (this) { - if (!saslNegotiated && !saslFailed) { + if (!saslNegotiated && saslFailure == null) { try { wait(5000); } @@ -393,15 +393,10 @@ public class SASLAuthentication { } } - if (saslFailed) { + if (saslFailure != null) { // SASL authentication failed and the server may have closed the connection // so throw an exception - if (errorCondition != null) { - throw new XMPPException("SASL authentication failed: " + errorCondition); - } - else { - throw new XMPPException("SASL authentication failed"); - } + throw new SASLErrorException(currentMechanism.toString(), saslFailure); } if (saslNegotiated) { @@ -409,14 +404,11 @@ public class SASLAuthentication { return bindResourceAndEstablishSession(null); } else { - throw new XMPPException("SASL authentication failed"); + throw new SaslException(); } - } catch (IOException e) { - throw new XMPPException("IOException while anonymous SASL authentication", e); - } } - private String bindResourceAndEstablishSession(String resource) throws XMPPException { + private String bindResourceAndEstablishSession(String resource) throws NoResponseException, XMPPErrorException { // Wait until server sends response containing the element synchronized (this) { if (!resourceBinded) { @@ -430,8 +422,9 @@ public class SASLAuthentication { } if (!resourceBinded) { - // Server never offered resource binding - throw new XMPPException("Resource binding not offered by server"); + // Server never offered resource binding, which is REQURIED in XMPP client and server + // implementations as per RFC6120 7.2 + throw new IllegalStateException("Resource binding not offered by server"); } Bind bindResource = new Bind(); @@ -497,12 +490,12 @@ public class SASLAuthentication { * Notification message saying that SASL authentication has failed. The server may have * closed the connection depending on the number of possible retries. * - * @param condition the error condition provided by the server. + * @param saslFailure the SASL failure as reported by the server + * @see RFC6120 6.5 */ - void authenticationFailed(String condition) { + void authenticationFailed(SASLFailure saslFailure) { synchronized (this) { - saslFailed = true; - errorCondition = condition; + this.saslFailure = saslFailure; // Wake up the thread that is waiting in the #authenticate method notify(); } @@ -540,7 +533,7 @@ public class SASLAuthentication { */ protected void init() { saslNegotiated = false; - saslFailed = false; + saslFailure = null; resourceBinded = false; sessionSupported = false; } diff --git a/core/src/main/java/org/jivesoftware/smack/SmackError.java b/core/src/main/java/org/jivesoftware/smack/SmackError.java deleted file mode 100644 index 95a3871fb..000000000 --- a/core/src/main/java/org/jivesoftware/smack/SmackError.java +++ /dev/null @@ -1,40 +0,0 @@ -/** - * - * Copyright the original author or authors - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package org.jivesoftware.smack; - -public enum SmackError { - NO_RESPONSE_FROM_SERVER("No response from server."); - - private String message; - - private SmackError(String errMessage) { - message = errMessage; - } - - public String getErrorMessage() { - return message; - } - - public static SmackError getErrorCode(String message) { - for (SmackError code : values()) { - if (code.message.equals(message)) { - return code; - } - } - return null; - } -} diff --git a/core/src/main/java/org/jivesoftware/smack/SmackException.java b/core/src/main/java/org/jivesoftware/smack/SmackException.java new file mode 100644 index 000000000..7e8131be0 --- /dev/null +++ b/core/src/main/java/org/jivesoftware/smack/SmackException.java @@ -0,0 +1,159 @@ +/** + * + * Copyright 2014 Florian Schmaus + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package org.jivesoftware.smack; + +import java.util.ArrayList; +import java.util.List; + +import org.jivesoftware.smack.util.dns.HostAddress; + +/** + * Smack uses SmackExceptions for errors that are not defined by any XMPP specification. + * + * @author Florian Schmaus + */ +public class SmackException extends Exception { + + /** + * + */ + private static final long serialVersionUID = 1844674365368214457L; + + /** + * Creates a new SmackException with the Throwable that was the root cause of the exception. + * + * @param wrappedThrowable the root cause of the exception. + */ + public SmackException(Throwable wrappedThrowable) { + super(wrappedThrowable); + } + + public SmackException(String message) { + super(message); + } + + public SmackException(String message, Throwable wrappedThrowable) { + super(message, wrappedThrowable); + } + + protected SmackException() { + } + + /** + * Exception thrown always when there was no response to an IQ request within the packet reply + * timeout of the used connection instance. + */ + public static class NoResponseException extends SmackException { + /** + * + */ + private static final long serialVersionUID = -6523363748984543636L; + + public NoResponseException() { + } + } + + public static class NotLoggedInException extends SmackException { + + /** + * + */ + private static final long serialVersionUID = 3216216839100019278L; + + public NotLoggedInException() { + } + } + + public static class AlreadyLoggedInException extends SmackException { + + /** + * + */ + private static final long serialVersionUID = 5011416918049935231L; + + public AlreadyLoggedInException() { + } + } + + public static class NotConnectedException extends SmackException { + + /** + * + */ + private static final long serialVersionUID = 9197980400776001173L; + + public NotConnectedException() { + } + } + + public static class IllegalStateChangeException extends SmackException { + + /** + * + */ + private static final long serialVersionUID = -1766023961577168927L; + + public IllegalStateChangeException() { + } + } + + public static class SecurityRequiredException extends SmackException { + + /** + * + */ + private static final long serialVersionUID = 384291845029773545L; + + public SecurityRequiredException() { + } + } + + public static class ConnectionException extends SmackException { + + /** + * + */ + private static final long serialVersionUID = 1686944201672697996L; + + private final List failedAddresses; + + public ConnectionException(Throwable wrappedThrowable) { + super(wrappedThrowable); + failedAddresses = new ArrayList(0); + } + + public ConnectionException(List failedAddresses) { + this.failedAddresses = failedAddresses; + } + + public List getFailedAddresses() { + return failedAddresses; + } + } + + public static class FeatureNotSupportedException extends SmackException { + + /** + * + */ + private static final long serialVersionUID = 4713404802621452016L; + + public FeatureNotSupportedException(String message) { + super(message); + } + } +} diff --git a/core/src/main/java/org/jivesoftware/smack/XMPPConnection.java b/core/src/main/java/org/jivesoftware/smack/XMPPConnection.java index eb8190a0e..29701edaf 100644 --- a/core/src/main/java/org/jivesoftware/smack/XMPPConnection.java +++ b/core/src/main/java/org/jivesoftware/smack/XMPPConnection.java @@ -16,6 +16,7 @@ */ package org.jivesoftware.smack; +import java.io.IOException; import java.io.Reader; import java.io.Writer; import java.lang.reflect.Constructor; @@ -38,6 +39,9 @@ import java.util.concurrent.atomic.AtomicInteger; import java.util.logging.Level; import java.util.logging.Logger; +import javax.security.sasl.SaslException; + +import org.jivesoftware.smack.SmackException.ConnectionException; import org.jivesoftware.smack.compression.XMPPInputOutputStream; import org.jivesoftware.smack.debugger.SmackDebugger; import org.jivesoftware.smack.filter.IQReplyFilter; @@ -357,9 +361,12 @@ public abstract class XMPPConnection { * Listeners will be preserved from a previous connection if the reconnection * occurs after an abrupt termination. * - * @throws XMPPException if an error occurs while trying to establish the connection. + * @throws XMPPException if an error occurs on the XMPP protocol level. + * @throws SmackException if an error occurs somehwere else besides XMPP protocol level. + * @throws IOException + * @throws ConnectionException with detailed information about the failed connection. */ - public abstract void connect() throws XMPPException; + public abstract void connect() throws SmackException, IOException, XMPPException; /** * Logs in to the server using the strongest authentication mode supported by @@ -382,9 +389,12 @@ public abstract class XMPPConnection { * * @param username the username. * @param password the password or null if using a CallbackHandler. - * @throws XMPPException if an error occurs. + * @throws XMPPException if an error occurs on the XMPP protocol level. + * @throws SmackException if an error occurs somehwere else besides XMPP protocol level. + * @throws IOException + * @throws SaslException */ - public void login(String username, String password) throws XMPPException { + public void login(String username, String password) throws XMPPException, SmackException, SaslException, IOException { login(username, password, "Smack"); } @@ -410,11 +420,12 @@ public abstract class XMPPConnection { * @param username the username. * @param password the password or null if using a CallbackHandler. * @param resource the resource. - * @throws XMPPException if an error occurs. - * @throws IllegalStateException if not connected to the server, or already logged in - * to the serrver. + * @throws XMPPException if an error occurs on the XMPP protocol level. + * @throws SmackException if an error occurs somehwere else besides XMPP protocol level. + * @throws IOException + * @throws SaslException */ - public abstract void login(String username, String password, String resource) throws XMPPException; + public abstract void login(String username, String password, String resource) throws XMPPException, SmackException, SaslException, IOException; /** * Logs in to the server anonymously. Very few servers are configured to support anonymous @@ -422,11 +433,12 @@ public abstract class XMPPConnection { * does succeed, your XMPP address will likely be in the form "123ABC@server/789XYZ" or * "server/123ABC" (where "123ABC" and "789XYZ" is a random value generated by the server). * - * @throws XMPPException if an error occurs or anonymous logins are not supported by the server. - * @throws IllegalStateException if not connected to the server, or already logged in - * to the serrver. + * @throws XMPPException if an error occurs on the XMPP protocol level. + * @throws SmackException if an error occurs somehwere else besides XMPP protocol level. + * @throws IOException + * @throws SaslException */ - public abstract void loginAnonymously() throws XMPPException; + public abstract void loginAnonymously() throws XMPPException, SmackException, SaslException, IOException; /** * Sends the specified packet to the server. @@ -470,8 +482,10 @@ public abstract class XMPPConnection { * {@link RosterListener}s will throw an IllegalStateException. * * @return the user's roster. + * @throws XMPPException if an error occurs on the XMPP protocol level. + * @throws SmackException if an error occurs somehwere else besides XMPP protocol level. */ - public abstract Roster getRoster(); + public abstract Roster getRoster() throws XMPPException, SmackException; /** * Returns the SASLAuthentication manager that is responsible for authenticating with diff --git a/core/src/main/java/org/jivesoftware/smack/XMPPException.java b/core/src/main/java/org/jivesoftware/smack/XMPPException.java index 87e675f65..694a0cb00 100644 --- a/core/src/main/java/org/jivesoftware/smack/XMPPException.java +++ b/core/src/main/java/org/jivesoftware/smack/XMPPException.java @@ -26,7 +26,7 @@ import org.jivesoftware.smack.packet.XMPPError; * and textual description of the problem, which are encapsulated in the XMPPError * class. When appropriate, an XMPPError instance is attached instances of this exception.

* - * When a stream error occured, the server will send a stream error to the client before + * When a stream error occurred, the server will send a stream error to the client before * closing the connection. Stream errors are unrecoverable errors. When a stream error * is sent to the client an XMPPException will be thrown containing the StreamError sent * by the server. @@ -34,17 +34,14 @@ import org.jivesoftware.smack.packet.XMPPError; * @see XMPPError * @author Matt Tucker */ -public class XMPPException extends Exception { +public abstract class XMPPException extends Exception { private static final long serialVersionUID = 6881651633890968625L; - private StreamError streamError = null; - private XMPPError error = null; - private SmackError smackError = null; /** * Creates a new XMPPException. */ - public XMPPException() { + protected XMPPException() { super(); } @@ -53,52 +50,10 @@ public class XMPPException extends Exception { * * @param message description of the exception. */ - public XMPPException(String message) { + protected XMPPException(String message) { super(message); } - /** - * Creates a new XMPPException with a Smack specific error code. - * - * @param code the root cause of the exception. - */ - public XMPPException(SmackError code) { - super(code.getErrorMessage()); - smackError = code; - } - - /** - * Creates a new XMPPException with the Throwable that was the root cause of the - * exception. - * - * @param wrappedThrowable the root cause of the exception. - */ - public XMPPException(Throwable wrappedThrowable) { - super(wrappedThrowable); - } - - /** - * Creates a new XMPPException with the stream error that was the root case of the - * exception. When a stream error is received from the server then the underlying - * TCP connection will be closed by the server. - * - * @param streamError the root cause of the exception. - */ - public XMPPException(StreamError streamError) { - super(); - this.streamError = streamError; - } - - /** - * Cretaes a new XMPPException with the XMPPError that was the root case of the - * exception. - * - * @param error the root cause of the exception. - */ - public XMPPException(XMPPError error) { - super(); - this.error = error; - } /** * Creates a new XMPPException with a description of the exception and the @@ -107,95 +62,116 @@ public class XMPPException extends Exception { * @param message a description of the exception. * @param wrappedThrowable the root cause of the exception. */ - public XMPPException(String message, Throwable wrappedThrowable) { + protected XMPPException(String message, Throwable wrappedThrowable) { super(message, wrappedThrowable); } - /** - * Creates a new XMPPException with a description of the exception, an XMPPError, - * and the Throwable that was the root cause of the exception. - * - * @param message a description of the exception. - * @param error the root cause of the exception. - * @param wrappedThrowable the root cause of the exception. - */ - public XMPPException(String message, XMPPError error, Throwable wrappedThrowable) { - super(message, wrappedThrowable); - this.error = error; - } + public static class XMPPErrorException extends XMPPException { + /** + * + */ + private static final long serialVersionUID = 212790389529249604L; + private final XMPPError error; - /** - * Creates a new XMPPException with a description of the exception and the - * XMPPException that was the root cause of the exception. - * - * @param message a description of the exception. - * @param error the root cause of the exception. - */ - public XMPPException(String message, XMPPError error) { - super(message); - this.error = error; - } - - /** - * Returns the XMPPError asscociated with this exception, or null if there - * isn't one. - * - * @return the XMPPError asscociated with this exception. - */ - public XMPPError getXMPPError() { - return error; - } - - /** - * Returns the SmackError asscociated with this exception, or null if there - * isn't one. - * - * @return the SmackError asscociated with this exception. - */ - public SmackError getSmackError() { - return smackError; - } - - /** - * Returns the StreamError asscociated with this exception, or null if there - * isn't one. The underlying TCP connection is closed by the server after sending the - * stream error to the client. - * - * @return the StreamError asscociated with this exception. - */ - public StreamError getStreamError() { - return streamError; - } - - public String getMessage() { - String msg = super.getMessage(); - // If the message was not set, but there is an XMPPError, return the - // XMPPError as the message. - if (msg == null && error != null) { - return error.toString(); + /** + * Creates a new XMPPException with the XMPPError that was the root case of the exception. + * + * @param error the root cause of the exception. + */ + public XMPPErrorException(XMPPError error) { + super(); + this.error = error; } - else if (msg == null && streamError != null) { + + /** + * Creates a new XMPPException with a description of the exception, an XMPPError, and the + * Throwable that was the root cause of the exception. + * + * @param message a description of the exception. + * @param error the root cause of the exception. + * @param wrappedThrowable the root cause of the exception. + */ + public XMPPErrorException(String message, XMPPError error, Throwable wrappedThrowable) { + super(message, wrappedThrowable); + this.error = error; + } + + /** + * Creates a new XMPPException with a description of the exception and the XMPPException + * that was the root cause of the exception. + * + * @param message a description of the exception. + * @param error the root cause of the exception. + */ + public XMPPErrorException(String message, XMPPError error) { + super(message); + this.error = error; + } + + /** + * Returns the XMPPError associated with this exception, or null if there isn't + * one. + * + * @return the XMPPError associated with this exception. + */ + public XMPPError getXMPPError() { + return error; + } + + @Override + public String getMessage() { + String superMessage = super.getMessage(); + if (superMessage != null) { + return superMessage; + } + else { + return error.toString(); + } + } + + @Override + public String toString() { + return getMessage(); + } + } + + public static class StreamErrorException extends XMPPException { + /** + * + */ + private static final long serialVersionUID = 3400556867134848886L; + private final StreamError streamError; + + /** + * Creates a new XMPPException with the stream error that was the root case of the + * exception. When a stream error is received from the server then the underlying connection + * will be closed by the server. + * + * @param streamError the root cause of the exception. + */ + public StreamErrorException(StreamError streamError) { + super(); + this.streamError = streamError; + } + + /** + * Returns the StreamError associated with this exception. The underlying TCP connection is + * closed by the server after sending the stream error to the client. + * + * @return the StreamError associated with this exception. + */ + public StreamError getStreamError() { + return streamError; + } + + @Override + public String getMessage() { return streamError.toString(); } - return msg; - } - public String toString() { - StringBuilder buf = new StringBuilder(); - String message = super.getMessage(); - if (message != null) { - buf.append(message).append(": "); + @Override + public String toString() { + return getMessage(); } - if (error != null) { - buf.append(error); - } - if (streamError != null) { - buf.append(streamError); - } - if (getCause() != null) { - buf.append("\n -- caused by: ").append(getCause()); - } - - return buf.toString(); } } diff --git a/core/src/main/java/org/jivesoftware/smack/packet/XMPPError.java b/core/src/main/java/org/jivesoftware/smack/packet/XMPPError.java index 8137860b6..02a6fdb64 100644 --- a/core/src/main/java/org/jivesoftware/smack/packet/XMPPError.java +++ b/core/src/main/java/org/jivesoftware/smack/packet/XMPPError.java @@ -292,15 +292,26 @@ public class XMPPError { public static final Condition unexpected_request = new Condition("unexpected-request"); public static final Condition request_timeout = new Condition("request-timeout"); - private String value; + private final String value; public Condition(String value) { this.value = value; } + @Override public String toString() { return value; } + + @Override + public boolean equals(Object other) { + return toString().equals(other.toString()); + } + + @Override + public int hashCode() { + return value.hashCode(); + } } diff --git a/core/src/main/java/org/jivesoftware/smack/sasl/SASLError.java b/core/src/main/java/org/jivesoftware/smack/sasl/SASLError.java new file mode 100644 index 000000000..94cfa7f4e --- /dev/null +++ b/core/src/main/java/org/jivesoftware/smack/sasl/SASLError.java @@ -0,0 +1,45 @@ +/** + * + * Copyright 2014 Florian Schmaus + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package org.jivesoftware.smack.sasl; + +public enum SASLError { + + aborted, + account_disabled, + credentials_expired, + encryption_required, + incorrect_encoding, + invalid_authzid, + invalid_mechanism, + malformed_request, + not_authorized, + temporary_auth_failure; + + @Override + public String toString() { + return this.name().replace('_', '-'); + } + + public static SASLError fromString(String string) { + string = string.replace('-', '_'); + for (SASLError error : SASLError.values()) { + if (error.name().equals(string)) + return error; + } + return null; + } +} diff --git a/core/src/main/java/org/jivesoftware/smack/sasl/SASLErrorException.java b/core/src/main/java/org/jivesoftware/smack/sasl/SASLErrorException.java new file mode 100644 index 000000000..87aa3dd77 --- /dev/null +++ b/core/src/main/java/org/jivesoftware/smack/sasl/SASLErrorException.java @@ -0,0 +1,59 @@ +/** + * + * Copyright 2014 Florian Schmaus + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package org.jivesoftware.smack.sasl; + +import java.util.HashMap; +import java.util.Map; + +import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.sasl.SASLMechanism.SASLFailure; + +public class SASLErrorException extends XMPPException { + + /** + * + */ + private static final long serialVersionUID = 6247573875760717257L; + + private final SASLFailure saslFailure; + private final String mechanism; + private final Map texts; + + public SASLErrorException(String mechanism, SASLFailure saslFailure) { + this.mechanism = mechanism; + this.saslFailure = saslFailure; + this.texts = new HashMap(); + } + + public SASLErrorException(String mechanism, SASLFailure saslFailure, Map texts) { + this.mechanism = mechanism; + this.saslFailure = saslFailure; + this.texts = texts; + } + + public SASLFailure getSASLFailure() { + return saslFailure; + } + + public String getMechanism() { + return mechanism; + } + + public Map getTexts() { + return texts; + } +} diff --git a/core/src/main/java/org/jivesoftware/smack/sasl/SASLGSSAPIMechanism.java b/core/src/main/java/org/jivesoftware/smack/sasl/SASLGSSAPIMechanism.java index 658b14b6d..1b7728dec 100644 --- a/core/src/main/java/org/jivesoftware/smack/sasl/SASLGSSAPIMechanism.java +++ b/core/src/main/java/org/jivesoftware/smack/sasl/SASLGSSAPIMechanism.java @@ -17,12 +17,13 @@ package org.jivesoftware.smack.sasl; import org.jivesoftware.smack.SASLAuthentication; -import org.jivesoftware.smack.XMPPException; import java.io.IOException; import java.util.Map; import java.util.HashMap; + import javax.security.sasl.Sasl; +import javax.security.sasl.SaslException; import javax.security.auth.callback.CallbackHandler; /** @@ -55,7 +56,7 @@ public class SASLGSSAPIMechanism extends SASLMechanism { * @param cbh the CallbackHandler (not used with GSSAPI) * @throws IOException If a network error occures while authenticating. */ - public void authenticate(String username, String host, CallbackHandler cbh) throws IOException, XMPPException { + public void authenticate(String username, String host, CallbackHandler cbh) throws IOException, SaslException { String[] mechanisms = { getName() }; Map props = new HashMap(); props.put(Sasl.SERVER_AUTH,"TRUE"); @@ -74,7 +75,7 @@ public class SASLGSSAPIMechanism extends SASLMechanism { * @param password the password of the user (ignored for GSSAPI) * @throws IOException If a network error occures while authenticating. */ - public void authenticate(String username, String host, String password) throws IOException, XMPPException { + public void authenticate(String username, String host, String password) throws IOException, SaslException { String[] mechanisms = { getName() }; Map props = new HashMap(); props.put(Sasl.SERVER_AUTH,"TRUE"); diff --git a/core/src/main/java/org/jivesoftware/smack/sasl/SASLMechanism.java b/core/src/main/java/org/jivesoftware/smack/sasl/SASLMechanism.java index 4f5e7176d..d9abec4bf 100644 --- a/core/src/main/java/org/jivesoftware/smack/sasl/SASLMechanism.java +++ b/core/src/main/java/org/jivesoftware/smack/sasl/SASLMechanism.java @@ -16,7 +16,6 @@ */ package org.jivesoftware.smack.sasl; -import org.jivesoftware.smack.XMPPException; import org.jivesoftware.smack.SASLAuthentication; import org.jivesoftware.smack.packet.Packet; import org.jivesoftware.smack.util.StringUtils; @@ -129,9 +128,9 @@ public abstract class SASLMechanism implements CallbackHandler { * serviceName format is: host [ "/" serv-name ] as per RFC-2831 * @param password the password for this account. * @throws IOException If a network error occurs while authenticating. - * @throws XMPPException If a protocol error occurs or the user is not authenticated. + * @throws SaslException */ - public void authenticate(String username, String host, String serviceName, String password) throws IOException, XMPPException { + public void authenticate(String username, String host, String serviceName, String password) throws IOException, SaslException { //Since we were not provided with a CallbackHandler, we will use our own with the given //information @@ -153,24 +152,20 @@ public abstract class SASLMechanism implements CallbackHandler { * @param host the hostname where the user account resides. * @param cbh the CallbackHandler to obtain user information. * @throws IOException If a network error occures while authenticating. - * @throws XMPPException If a protocol error occurs or the user is not authenticated. + * @throws SaslException If a protocol error occurs or the user is not authenticated. */ - public void authenticate(String host, CallbackHandler cbh) throws IOException, XMPPException { + public void authenticate(String host, CallbackHandler cbh) throws IOException, SaslException { String[] mechanisms = { getName() }; Map props = new HashMap(); sc = Sasl.createSaslClient(mechanisms, null, "xmpp", host, props, cbh); authenticate(); } - protected void authenticate() throws IOException, XMPPException { + protected void authenticate() throws IOException, SaslException { String authenticationText = null; - try { - if(sc.hasInitialResponse()) { - byte[] response = sc.evaluateChallenge(new byte[0]); - authenticationText = StringUtils.encodeBase64(response, false); - } - } catch (SaslException e) { - throw new XMPPException("SASL authentication failed", e); + if (sc.hasInitialResponse()) { + byte[] response = sc.evaluateChallenge(new byte[0]); + authenticationText = StringUtils.encodeBase64(response, false); } // Send the authentication to the server @@ -349,11 +344,19 @@ public abstract class SASLMechanism implements CallbackHandler { /** * A SASL failure stanza. */ - public static class Failure extends Packet { - final private String condition; + public static class SASLFailure extends Packet { + private final SASLError saslError; + private final String saslErrorString; - public Failure(String condition) { - this.condition = condition; + public SASLFailure(String saslError) { + SASLError error = SASLError.fromString(saslError); + if (error == null) { + // RFC6120 6.5 states that unknown condition must be treat as generic authentication failure. + this.saslError = SASLError.not_authorized; + } else { + this.saslError = error; + } + this.saslErrorString = saslError; } /** @@ -361,17 +364,22 @@ public abstract class SASLMechanism implements CallbackHandler { * * @return the SASL related error condition. */ - public String getCondition() { - return condition; + public SASLError getSASLError() { + return saslError; + } + + /** + * + * @return the SASL error as String + */ + public String getSASLErrorString() { + return saslErrorString; } public String toXML() { StringBuilder stanza = new StringBuilder(); stanza.append(""); - if (condition != null && - condition.trim().length() > 0) { - stanza.append("<").append(condition).append("/>"); - } + stanza.append("<").append(saslErrorString).append("/>"); stanza.append(""); return stanza.toString(); } diff --git a/core/src/main/java/org/jivesoftware/smack/util/PacketParserUtils.java b/core/src/main/java/org/jivesoftware/smack/util/PacketParserUtils.java index 78dee5ddc..24e91f910 100644 --- a/core/src/main/java/org/jivesoftware/smack/util/PacketParserUtils.java +++ b/core/src/main/java/org/jivesoftware/smack/util/PacketParserUtils.java @@ -42,7 +42,7 @@ import org.jivesoftware.smack.packet.XMPPError; import org.jivesoftware.smack.provider.IQProvider; import org.jivesoftware.smack.provider.PacketExtensionProvider; import org.jivesoftware.smack.provider.ProviderManager; -import org.jivesoftware.smack.sasl.SASLMechanism.Failure; +import org.jivesoftware.smack.sasl.SASLMechanism.SASLFailure; import org.xmlpull.v1.XmlPullParser; import org.xmlpull.v1.XmlPullParserException; @@ -636,7 +636,7 @@ public class PacketParserUtils { * @return a SASL Failure packet. * @throws Exception if an exception occurs while parsing the packet. */ - public static Failure parseSASLFailure(XmlPullParser parser) throws Exception { + public static SASLFailure parseSASLFailure(XmlPullParser parser) throws Exception { String condition = null; boolean done = false; while (!done) { @@ -653,7 +653,7 @@ public class PacketParserUtils { } } } - return new Failure(condition); + return new SASLFailure(condition); } /** diff --git a/core/src/test/java/org/jivesoftware/smack/ChatConnectionTest.java b/core/src/test/java/org/jivesoftware/smack/ChatConnectionTest.java index 5fa916810..1656ae68e 100644 --- a/core/src/test/java/org/jivesoftware/smack/ChatConnectionTest.java +++ b/core/src/test/java/org/jivesoftware/smack/ChatConnectionTest.java @@ -348,7 +348,7 @@ public class ChatConnectionTest { try { con.connect(); con.login("me", "secret"); - } catch (XMPPException e) { + } catch (Exception e) { // No need for handling in a dummy connection. } return con; diff --git a/core/src/test/java/org/jivesoftware/smack/DummyConnection.java b/core/src/test/java/org/jivesoftware/smack/DummyConnection.java index faa48189c..a299733aa 100644 --- a/core/src/test/java/org/jivesoftware/smack/DummyConnection.java +++ b/core/src/test/java/org/jivesoftware/smack/DummyConnection.java @@ -74,7 +74,7 @@ public class DummyConnection extends XMPPConnection { } @Override - public void connect() throws XMPPException { + public void connect() { connectionID = "dummy-" + new Random(new Date().getTime()).nextInt(); if (reconnect) { diff --git a/core/src/test/java/org/jivesoftware/smack/RosterTest.java b/core/src/test/java/org/jivesoftware/smack/RosterTest.java index 82702ac6e..f0b9b383a 100644 --- a/core/src/test/java/org/jivesoftware/smack/RosterTest.java +++ b/core/src/test/java/org/jivesoftware/smack/RosterTest.java @@ -520,8 +520,9 @@ public class RosterTest { * * @param connection the dummy connection of which the provided roster belongs to. * @param roster the roster (or buddy list) which should be initialized. + * @throws SmackException */ - public static void initRoster(DummyConnection connection, Roster roster) throws InterruptedException, XMPPException { + public static void initRoster(DummyConnection connection, Roster roster) throws InterruptedException, XMPPException, SmackException { roster.reload(); while (true) { final Packet sentPacket = connection.getSentPacket(); diff --git a/core/src/test/java/org/jivesoftware/smack/RosterVersioningTest.java b/core/src/test/java/org/jivesoftware/smack/RosterVersioningTest.java index 814dd2648..dc31c39b2 100644 --- a/core/src/test/java/org/jivesoftware/smack/RosterVersioningTest.java +++ b/core/src/test/java/org/jivesoftware/smack/RosterVersioningTest.java @@ -83,9 +83,11 @@ public class RosterVersioningTest { /** * Tests that receiving an empty roster result causes the roster to be populated * by all entries of the roster store. + * @throws SmackException + * @throws XMPPException */ @Test(timeout = 5000) - public void testEqualVersionStored() throws InterruptedException, IOException { + public void testEqualVersionStored() throws InterruptedException, IOException, XMPPException, SmackException { connection.getRoster().reload(); answerWithEmptyRosterResult(); @@ -116,9 +118,11 @@ public class RosterVersioningTest { /** * Tests that a non-empty roster result empties the store. + * @throws SmackException + * @throws XMPPException */ @Test(timeout = 5000) - public void testOtherVersionStored() throws InterruptedException { + public void testOtherVersionStored() throws InterruptedException, XMPPException, SmackException { connection.getRoster().reload(); Item vaglafItem = vaglafItem(); diff --git a/core/src/test/java/org/jivesoftware/smack/parsing/ParsingExceptionTest.java b/core/src/test/java/org/jivesoftware/smack/parsing/ParsingExceptionTest.java index accc4292d..25a538c4b 100644 --- a/core/src/test/java/org/jivesoftware/smack/parsing/ParsingExceptionTest.java +++ b/core/src/test/java/org/jivesoftware/smack/parsing/ParsingExceptionTest.java @@ -19,7 +19,7 @@ package org.jivesoftware.smack.parsing; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertNotNull; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smack.packet.PacketExtension; import org.jivesoftware.smack.provider.PacketExtensionProvider; import org.jivesoftware.smack.provider.ProviderManager; @@ -79,7 +79,7 @@ public class ParsingExceptionTest { @Override public PacketExtension parseExtension(XmlPullParser parser) throws Exception { - throw new XMPPException("Test Exception"); + throw new SmackException("Test Exception"); } } diff --git a/experimental/src/main/java/org/jivesoftware/smackx/carbons/CarbonManager.java b/experimental/src/main/java/org/jivesoftware/smackx/carbons/CarbonManager.java index 796c771b2..42c2c9735 100644 --- a/experimental/src/main/java/org/jivesoftware/smackx/carbons/CarbonManager.java +++ b/experimental/src/main/java/org/jivesoftware/smackx/carbons/CarbonManager.java @@ -20,11 +20,14 @@ import java.util.Collections; import java.util.Map; import java.util.WeakHashMap; +import org.jivesoftware.smack.SmackException; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.ConnectionCreationListener; import org.jivesoftware.smack.Manager; import org.jivesoftware.smack.PacketListener; import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.filter.IQReplyFilter; import org.jivesoftware.smack.packet.IQ; import org.jivesoftware.smack.packet.Message; @@ -95,15 +98,12 @@ public class CarbonManager extends Manager { * Returns true if XMPP Carbons are supported by the server. * * @return true if supported + * @throws SmackException if there was no response from the server. + * @throws XMPPException */ - public boolean isSupportedByServer() { - try { - return ServiceDiscoveryManager.getInstanceFor(connection()).supportsFeature( - connection().getServiceName(), CarbonExtension.NAMESPACE); - } - catch (XMPPException e) { - return false; - } + public boolean isSupportedByServer() throws XMPPException, SmackException { + return ServiceDiscoveryManager.getInstanceFor(connection()).supportsFeature( + connection().getServiceName(), CarbonExtension.NAMESPACE); } /** @@ -138,11 +138,14 @@ public class CarbonManager extends Manager { * You should first check for support using isSupportedByServer(). * * @param new_state whether carbons should be enabled or disabled + * @throws XMPPErrorException + * @throws NoResponseException * - * @throws XMPPException */ - public void setCarbonsEnabled(final boolean new_state) throws XMPPException { - if (enabled_state == new_state) return; + public synchronized void setCarbonsEnabled(final boolean new_state) throws NoResponseException, + XMPPErrorException { + if (enabled_state == new_state) + return; IQ setIQ = carbonsEnabledIQ(new_state); @@ -154,8 +157,9 @@ public class CarbonManager extends Manager { * Helper method to enable carbons. * * @throws XMPPException + * @throws SmackException if there was no response from the server. */ - public void enableCarbons() throws XMPPException { + public void enableCarbons() throws XMPPException, SmackException { setCarbonsEnabled(true); } @@ -163,8 +167,9 @@ public class CarbonManager extends Manager { * Helper method to disable carbons. * * @throws XMPPException + * @throws SmackException if there was no response from the server. */ - public void disableCarbons() throws XMPPException { + public void disableCarbons() throws XMPPException, SmackException { setCarbonsEnabled(false); } diff --git a/extensions/src/main/java/org/jivesoftware/smackx/address/MultipleRecipientManager.java b/extensions/src/main/java/org/jivesoftware/smackx/address/MultipleRecipientManager.java index d977af437..06dc2d9b0 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/address/MultipleRecipientManager.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/address/MultipleRecipientManager.java @@ -17,8 +17,11 @@ package org.jivesoftware.smackx.address; +import org.jivesoftware.smack.SmackException; +import org.jivesoftware.smack.SmackException.NoResponseException; +import org.jivesoftware.smack.SmackException.FeatureNotSupportedException; import org.jivesoftware.smack.XMPPConnection; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.packet.Message; import org.jivesoftware.smack.packet.Packet; import org.jivesoftware.smack.util.Cache; @@ -31,8 +34,6 @@ import org.jivesoftware.smackx.disco.packet.DiscoverItems; import java.util.ArrayList; import java.util.Iterator; import java.util.List; -import java.util.logging.Level; -import java.util.logging.Logger; /** * A MultipleRecipientManager allows to send packets to multiple recipients by making use of @@ -42,7 +43,6 @@ import java.util.logging.Logger; * @author Gaston Dombiak */ public class MultipleRecipientManager { - private static final Logger LOGGER = Logger.getLogger(MultipleRecipientManager.class.getName()); /** * Create a cache to hold the 100 most recently accessed elements for a period of @@ -65,39 +65,42 @@ public class MultipleRecipientManager { * list exists. * @param bcc the list of JIDs to include in the BCC list or null if no BCC * list exists. - * @throws XMPPException if server does not support JEP-33: Extended Stanza Addressing and + * @throws FeatureNotSupportedException if special XEP-33 features where requested, but the + * server does not support them. + * @throws XMPPErrorException if server does not support JEP-33: Extended Stanza Addressing and * some JEP-33 specific features were requested. + * @throws NoResponseException if there was no response from the server. */ - public static void send(XMPPConnection connection, Packet packet, List to, List cc, List bcc) - throws XMPPException { + public static void send(XMPPConnection connection, Packet packet, List to, List cc, List bcc) throws NoResponseException, XMPPErrorException, FeatureNotSupportedException + { send(connection, packet, to, cc, bcc, null, null, false); } /** - * Sends the specified packet to the list of specified recipients using the - * specified connection. If the server has support for JEP-33 then only one - * packet is going to be sent to the server with the multiple recipient instructions. - * However, if JEP-33 is not supported by the server then the client is going to send - * the packet to each recipient. - * + * Sends the specified packet to the list of specified recipients using the specified + * connection. If the server has support for JEP-33 then only one packet is going to be sent to + * the server with the multiple recipient instructions. However, if JEP-33 is not supported by + * the server then the client is going to send the packet to each recipient. + * * @param connection the connection to use to send the packet. - * @param packet the packet to send to the list of recipients. - * @param to the list of JIDs to include in the TO list or null if no TO - * list exists. - * @param cc the list of JIDs to include in the CC list or null if no CC - * list exists. - * @param bcc the list of JIDs to include in the BCC list or null if no BCC - * list exists. - * @param replyTo address to which all replies are requested to be sent or null - * indicating that they can reply to any address. - * @param replyRoom JID of a MUC room to which responses should be sent or null - * indicating that they can reply to any address. - * @param noReply true means that receivers should not reply to the message. - * @throws XMPPException if server does not support JEP-33: Extended Stanza Addressing and - * some JEP-33 specific features were requested. + * @param packet the packet to send to the list of recipients. + * @param to the list of JIDs to include in the TO list or null if no TO list exists. + * @param cc the list of JIDs to include in the CC list or null if no CC list exists. + * @param bcc the list of JIDs to include in the BCC list or null if no BCC list + * exists. + * @param replyTo address to which all replies are requested to be sent or null + * indicating that they can reply to any address. + * @param replyRoom JID of a MUC room to which responses should be sent or null + * indicating that they can reply to any address. + * @param noReply true means that receivers should not reply to the message. + * @throws XMPPErrorException if server does not support JEP-33: Extended Stanza Addressing and + * some JEP-33 specific features were requested. + * @throws NoResponseException if there was no response from the server. + * @throws FeatureNotSupportedException if special XEP-33 features where requested, but the + * server does not support them. */ public static void send(XMPPConnection connection, Packet packet, List to, List cc, List bcc, - String replyTo, String replyRoom, boolean noReply) throws XMPPException { + String replyTo, String replyRoom, boolean noReply) throws NoResponseException, XMPPErrorException, FeatureNotSupportedException { String serviceAddress = getMultipleRecipienServiceAddress(connection); if (serviceAddress != null) { // Send packet to target users using multiple recipient service provided by the server @@ -110,7 +113,7 @@ public class MultipleRecipientManager { (replyRoom != null && replyRoom.trim().length() > 0)) { // Some specified JEP-33 features were requested so throw an exception alerting // the user that this features are not available - throw new XMPPException("Extended Stanza Addressing not supported by server"); + throw new FeatureNotSupportedException("Extended Stanza Addressing not supported by server"); } // Send the packet to each individual recipient sendToIndividualRecipients(connection, packet, to, cc, bcc); @@ -125,20 +128,20 @@ public class MultipleRecipientManager { * @param connection the connection to use to send the reply. * @param original the previously received packet that was sent to multiple recipients. * @param reply the new message to send as a reply. - * @throws XMPPException if the original message was not sent to multiple recipients, or the - * original message cannot be replied or reply should be sent to a room. + * @throws SmackException + * @throws XMPPErrorException */ - public static void reply(XMPPConnection connection, Message original, Message reply) - throws XMPPException { + public static void reply(XMPPConnection connection, Message original, Message reply) throws SmackException, XMPPErrorException + { MultipleRecipientInfo info = getMultipleRecipientInfo(original); if (info == null) { - throw new XMPPException("Original message does not contain multiple recipient info"); + throw new SmackException("Original message does not contain multiple recipient info"); } if (info.shouldNotReply()) { - throw new XMPPException("Original message should not be replied"); + throw new SmackException("Original message should not be replied"); } if (info.getReplyRoom() != null) { - throw new XMPPException("Reply should be sent through a room"); + throw new SmackException("Reply should be sent through a room"); } // Any element from the initial message MUST be copied into the reply. if (original.getThread() != null) { @@ -280,8 +283,10 @@ public class MultipleRecipientManager { * @param connection the connection to use for disco. The connected server is going to be * queried. * @return the address of the multiple recipients service or null if none was found. + * @throws NoResponseException if there was no response from the server. + * @throws XMPPErrorException */ - private static String getMultipleRecipienServiceAddress(XMPPConnection connection) { + private static String getMultipleRecipienServiceAddress(XMPPConnection connection) throws NoResponseException, XMPPErrorException { String serviceName = connection.getServiceName(); String serviceAddress = (String) services.get(serviceName); if (serviceAddress == null) { @@ -290,33 +295,28 @@ public class MultipleRecipientManager { if (serviceAddress == null) { // Send the disco packet to the server itself - try { - DiscoverInfo info = ServiceDiscoveryManager.getInstanceFor(connection) - .discoverInfo(serviceName); - // Check if the server supports JEP-33 - if (info.containsFeature("http://jabber.org/protocol/address")) { - serviceAddress = serviceName; - } - else { - // Get the disco items and send the disco packet to each server item - DiscoverItems items = ServiceDiscoveryManager.getInstanceFor(connection) - .discoverItems(serviceName); - for (Iterator it = items.getItems(); it.hasNext();) { - DiscoverItems.Item item = it.next(); - info = ServiceDiscoveryManager.getInstanceFor(connection) - .discoverInfo(item.getEntityID(), item.getNode()); - if (info.containsFeature("http://jabber.org/protocol/address")) { - serviceAddress = serviceName; - break; - } + DiscoverInfo info = ServiceDiscoveryManager.getInstanceFor(connection).discoverInfo( + serviceName); + // Check if the server supports JEP-33 + if (info.containsFeature("http://jabber.org/protocol/address")) { + serviceAddress = serviceName; + } + else { + // Get the disco items and send the disco packet to each server item + DiscoverItems items = ServiceDiscoveryManager.getInstanceFor(connection).discoverItems( + serviceName); + for (Iterator it = items.getItems(); it.hasNext();) { + DiscoverItems.Item item = it.next(); + info = ServiceDiscoveryManager.getInstanceFor(connection).discoverInfo( + item.getEntityID(), item.getNode()); + if (info.containsFeature("http://jabber.org/protocol/address")) { + serviceAddress = serviceName; + break; } } - // Cache the discovered information - services.put(serviceName, serviceAddress == null ? "" : serviceAddress); - } - catch (XMPPException e) { - LOGGER.log(Level.SEVERE, "Error occurred retrieving multiple recipients service", e); } + // Cache the discovered information + services.put(serviceName, serviceAddress == null ? "" : serviceAddress); } } } diff --git a/extensions/src/main/java/org/jivesoftware/smackx/amp/AMPDeliverCondition.java b/extensions/src/main/java/org/jivesoftware/smackx/amp/AMPDeliverCondition.java index d8e705d71..81d709fb7 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/amp/AMPDeliverCondition.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/amp/AMPDeliverCondition.java @@ -16,8 +16,9 @@ */ package org.jivesoftware.smackx.amp; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smackx.amp.packet.AMPExtension; public class AMPDeliverCondition implements AMPExtension.Condition { @@ -28,9 +29,10 @@ public class AMPDeliverCondition implements AMPExtension.Condition { * Check if server supports deliver condition * @param connection Smack connection instance * @return true if deliver condition is supported. - * @throws XMPPException + * @throws XMPPErrorException + * @throws NoResponseException */ - public static boolean isSupported(XMPPConnection connection) throws XMPPException { + public static boolean isSupported(XMPPConnection connection) throws NoResponseException, XMPPErrorException { return AMPManager.isConditionSupported(connection, NAME); } diff --git a/extensions/src/main/java/org/jivesoftware/smackx/amp/AMPExpireAtCondition.java b/extensions/src/main/java/org/jivesoftware/smackx/amp/AMPExpireAtCondition.java index 83b098038..accf93dd1 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/amp/AMPExpireAtCondition.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/amp/AMPExpireAtCondition.java @@ -16,8 +16,9 @@ */ package org.jivesoftware.smackx.amp; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.util.XmppDateTime; import org.jivesoftware.smackx.amp.packet.AMPExtension; @@ -32,9 +33,10 @@ public class AMPExpireAtCondition implements AMPExtension.Condition { * Check if server supports expire-at condition * @param connection Smack connection instance * @return true if expire-at condition is supported. - * @throws XMPPException + * @throws XMPPErrorException + * @throws NoResponseException */ - public static boolean isSupported(XMPPConnection connection) throws XMPPException { + public static boolean isSupported(XMPPConnection connection) throws NoResponseException, XMPPErrorException { return AMPManager.isConditionSupported(connection, NAME); } diff --git a/extensions/src/main/java/org/jivesoftware/smackx/amp/AMPManager.java b/extensions/src/main/java/org/jivesoftware/smackx/amp/AMPManager.java index 51e2ab43a..2797edbaa 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/amp/AMPManager.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/amp/AMPManager.java @@ -16,9 +16,10 @@ */ package org.jivesoftware.smackx.amp; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.ConnectionCreationListener; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smackx.amp.packet.AMPExtension; import org.jivesoftware.smackx.disco.ServiceDiscoveryManager; import org.jivesoftware.smackx.disco.packet.DiscoverInfo; @@ -83,9 +84,10 @@ public class AMPManager { * @param connection active xmpp connection * @param action action to check * @return true if this action is supported. - * @throws XMPPException + * @throws XMPPErrorException + * @throws NoResponseException */ - public static boolean isActionSupported(XMPPConnection connection, AMPExtension.Action action) throws XMPPException { + public static boolean isActionSupported(XMPPConnection connection, AMPExtension.Action action) throws NoResponseException, XMPPErrorException { String featureName = AMPExtension.NAMESPACE + "?action=" + action.toString(); return isFeatureSupportedByServer(connection, featureName, AMPExtension.NAMESPACE); } @@ -95,17 +97,18 @@ public class AMPManager { * @param connection active xmpp connection * @param conditionName name of condition to check * @return true if this condition is supported. - * @throws XMPPException + * @throws XMPPErrorException + * @throws NoResponseException * @see AMPDeliverCondition * @see AMPExpireAtCondition * @see AMPMatchResourceCondition */ - public static boolean isConditionSupported(XMPPConnection connection, String conditionName) throws XMPPException { + public static boolean isConditionSupported(XMPPConnection connection, String conditionName) throws NoResponseException, XMPPErrorException { String featureName = AMPExtension.NAMESPACE + "?condition=" + conditionName; return isFeatureSupportedByServer(connection, featureName, AMPExtension.NAMESPACE); } - private static boolean isFeatureSupportedByServer(XMPPConnection connection, String featureName, String node) throws XMPPException { + private static boolean isFeatureSupportedByServer(XMPPConnection connection, String featureName, String node) throws NoResponseException, XMPPErrorException { ServiceDiscoveryManager discoveryManager = ServiceDiscoveryManager.getInstanceFor(connection); DiscoverInfo info = discoveryManager.discoverInfo(connection.getServiceName(), node); Iterator it = info.getFeatures(); diff --git a/extensions/src/main/java/org/jivesoftware/smackx/amp/AMPMatchResourceCondition.java b/extensions/src/main/java/org/jivesoftware/smackx/amp/AMPMatchResourceCondition.java index 66d81c0f8..e4987ddb8 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/amp/AMPMatchResourceCondition.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/amp/AMPMatchResourceCondition.java @@ -16,8 +16,9 @@ */ package org.jivesoftware.smackx.amp; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smackx.amp.packet.AMPExtension; public class AMPMatchResourceCondition implements AMPExtension.Condition { @@ -28,9 +29,10 @@ public class AMPMatchResourceCondition implements AMPExtension.Condition { * Check if server supports match-resource condition * @param connection Smack connection instance * @return true if match-resource condition is supported. - * @throws XMPPException + * @throws XMPPErrorException + * @throws NoResponseException */ - public static boolean isSupported(XMPPConnection connection) throws XMPPException { + public static boolean isSupported(XMPPConnection connection) throws NoResponseException, XMPPErrorException { return AMPManager.isConditionSupported(connection, NAME); } diff --git a/extensions/src/main/java/org/jivesoftware/smackx/bookmarks/BookmarkManager.java b/extensions/src/main/java/org/jivesoftware/smackx/bookmarks/BookmarkManager.java index 6bf85f418..1ef09cbc2 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/bookmarks/BookmarkManager.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/bookmarks/BookmarkManager.java @@ -17,8 +17,11 @@ package org.jivesoftware.smackx.bookmarks; +import org.jivesoftware.smack.SmackException; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smackx.iqprivate.PrivateDataManager; import java.util.*; @@ -46,13 +49,15 @@ public class BookmarkManager { * @param connection the connection for which the manager is desired. * @return Returns the BookmarkManager for a connection, if it doesn't * exist it is created. - * @throws XMPPException Thrown if the connection is null or has not yet been authenticated. + * @throws XMPPException + * @throws SmackException thrown has not been authenticated. + * @throws IllegalArgumentException when the connection is null. */ public synchronized static BookmarkManager getBookmarkManager(XMPPConnection connection) - throws XMPPException + throws XMPPException, SmackException { BookmarkManager manager = (BookmarkManager) bookmarkManagerMap.get(connection); - if(manager == null) { + if (manager == null) { manager = new BookmarkManager(connection); bookmarkManagerMap.put(connection, manager); } @@ -68,11 +73,15 @@ public class BookmarkManager { * storage:bookmarks namespace. * * @param connection the connection for persisting and retrieving bookmarks. - * @throws XMPPException thrown when the connection is null or has not been authenticated. + * @throws SmackException thrown has not been authenticated. + * @throws IllegalArgumentException when the connection is null. */ - private BookmarkManager(XMPPConnection connection) throws XMPPException { - if(connection == null || !connection.isAuthenticated()) { - throw new XMPPException("Invalid connection."); + private BookmarkManager(XMPPConnection connection) throws XMPPException, SmackException { + if (connection == null) { + throw new IllegalArgumentException("connection must not be null."); + } + if (!connection.isAuthenticated()) { + throw new SmackException("connection not authenticated."); } this.privateDataManager = new PrivateDataManager(connection); } @@ -81,11 +90,11 @@ public class BookmarkManager { * Returns all currently bookmarked conferences. * * @return returns all currently bookmarked conferences - * @throws XMPPException thrown when there was an error retrieving the current bookmarks from - * the server. + * @throws XMPPErrorException + * @throws NoResponseException * @see BookmarkedConference */ - public Collection getBookmarkedConferences() throws XMPPException { + public Collection getBookmarkedConferences() throws NoResponseException, XMPPErrorException { retrieveBookmarks(); return Collections.unmodifiableCollection(bookmarks.getBookmarkedConferences()); } @@ -98,11 +107,12 @@ public class BookmarkManager { * @param isAutoJoin whether or not to join this conference automatically on login * @param nickname the nickname to use for the user when joining the conference * @param password the password to use for the user when joining the conference - * @throws XMPPException thrown when there is an issue retrieving the current bookmarks from + * @throws XMPPErrorException thrown when there is an issue retrieving the current bookmarks from * the server. + * @throws NoResponseException if there was no response from the server. */ public void addBookmarkedConference(String name, String jid, boolean isAutoJoin, - String nickname, String password) throws XMPPException + String nickname, String password) throws NoResponseException, XMPPErrorException { retrieveBookmarks(); BookmarkedConference bookmark @@ -128,12 +138,13 @@ public class BookmarkManager { * Removes a conference from the bookmarks. * * @param jid the jid of the conference to be removed. - * @throws XMPPException thrown when there is a problem with the connection attempting to + * @throws XMPPErrorException thrown when there is a problem with the connection attempting to * retrieve the bookmarks or persist the bookmarks. + * @throws NoResponseException if there was no response from the server. * @throws IllegalArgumentException thrown when the conference being removed is a shared * conference */ - public void removeBookmarkedConference(String jid) throws XMPPException { + public void removeBookmarkedConference(String jid) throws NoResponseException, XMPPErrorException { retrieveBookmarks(); Iterator it = bookmarks.getBookmarkedConferences().iterator(); while(it.hasNext()) { @@ -153,9 +164,10 @@ public class BookmarkManager { * Returns an unmodifiable collection of all bookmarked urls. * * @return returns an unmodifiable collection of all bookmarked urls. - * @throws XMPPException thrown when there is a problem retriving bookmarks from the server. + * @throws XMPPErrorException thrown when there is a problem retriving bookmarks from the server. + * @throws NoResponseException if there was no response from the server. */ - public Collection getBookmarkedURLs() throws XMPPException { + public Collection getBookmarkedURLs() throws NoResponseException, XMPPErrorException { retrieveBookmarks(); return Collections.unmodifiableCollection(bookmarks.getBookmarkedURLS()); } @@ -166,10 +178,11 @@ public class BookmarkManager { * @param URL the url of the bookmark * @param name the name of the bookmark * @param isRSS whether or not the url is an rss feed - * @throws XMPPException thrown when there is an error retriving or saving bookmarks from or to + * @throws XMPPErrorException thrown when there is an error retriving or saving bookmarks from or to * the server + * @throws NoResponseException if there was no response from the server. */ - public void addBookmarkedURL(String URL, String name, boolean isRSS) throws XMPPException { + public void addBookmarkedURL(String URL, String name, boolean isRSS) throws NoResponseException, XMPPErrorException { retrieveBookmarks(); BookmarkedURL bookmark = new BookmarkedURL(URL, name, isRSS); List urls = bookmarks.getBookmarkedURLS(); @@ -191,10 +204,11 @@ public class BookmarkManager { * Removes a url from the bookmarks. * * @param bookmarkURL the url of the bookmark to remove - * @throws XMPPException thrown if there is an error retriving or saving bookmarks from or to + * @throws XMPPErrorException thrown if there is an error retriving or saving bookmarks from or to * the server. + * @throws NoResponseException if there was no response from the server. */ - public void removeBookmarkedURL(String bookmarkURL) throws XMPPException { + public void removeBookmarkedURL(String bookmarkURL) throws NoResponseException, XMPPErrorException { retrieveBookmarks(); Iterator it = bookmarks.getBookmarkedURLS().iterator(); while(it.hasNext()) { @@ -210,7 +224,7 @@ public class BookmarkManager { } } - private Bookmarks retrieveBookmarks() throws XMPPException { + private Bookmarks retrieveBookmarks() throws NoResponseException, XMPPErrorException { synchronized(bookmarkLock) { if(bookmarks == null) { bookmarks = (Bookmarks) privateDataManager.getPrivateData("storage", diff --git a/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/BytestreamManager.java b/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/BytestreamManager.java index 15a979c0d..a91086b86 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/BytestreamManager.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/BytestreamManager.java @@ -18,6 +18,7 @@ package org.jivesoftware.smackx.bytestreams; import java.io.IOException; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smack.XMPPException; import org.jivesoftware.smackx.bytestreams.ibb.InBandBytestreamManager; import org.jivesoftware.smackx.bytestreams.socks5.Socks5BytestreamManager; @@ -94,7 +95,7 @@ public interface BytestreamManager { * operation */ public BytestreamSession establishSession(String targetJID) throws XMPPException, IOException, - InterruptedException; + InterruptedException, SmackException; /** * Establishes a bytestream with the given user and returns the session to send/receive data @@ -112,6 +113,6 @@ public interface BytestreamManager { * operation */ public BytestreamSession establishSession(String targetJID, String sessionID) - throws XMPPException, IOException, InterruptedException; + throws XMPPException, IOException, InterruptedException, SmackException; } diff --git a/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/BytestreamRequest.java b/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/BytestreamRequest.java index 94f9280a3..10622e173 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/BytestreamRequest.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/BytestreamRequest.java @@ -16,7 +16,9 @@ */ package org.jivesoftware.smackx.bytestreams; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.SmackException; +import org.jivesoftware.smack.SmackException.NoResponseException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smackx.bytestreams.ibb.InBandBytestreamRequest; import org.jivesoftware.smackx.bytestreams.socks5.Socks5BytestreamRequest; @@ -48,11 +50,13 @@ public interface BytestreamRequest { * Accepts the bytestream open request and returns the session to send/receive data. * * @return the session to send/receive data - * @throws XMPPException if an error occurred while accepting the bytestream request + * @throws XMPPErrorException if an error occurred while accepting the bytestream request * @throws InterruptedException if the thread was interrupted while waiting in a blocking * operation + * @throws NoResponseException + * @throws SmackException */ - public BytestreamSession accept() throws XMPPException, InterruptedException; + public BytestreamSession accept() throws InterruptedException, NoResponseException, XMPPErrorException, SmackException; /** * Rejects the bytestream request by sending a reject error to the initiator. diff --git a/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamManager.java b/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamManager.java index d5a6ee7a7..ef79c1422 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamManager.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamManager.java @@ -25,9 +25,12 @@ import java.util.Random; import java.util.concurrent.ConcurrentHashMap; import org.jivesoftware.smack.AbstractConnectionListener; +import org.jivesoftware.smack.SmackException; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.ConnectionCreationListener; import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.packet.IQ; import org.jivesoftware.smack.packet.XMPPError; import org.jivesoftware.smackx.bytestreams.BytestreamListener; @@ -405,8 +408,9 @@ public class InBandBytestreamManager implements BytestreamManager { * @return the session to send/receive data to/from the user * @throws XMPPException if the user doesn't support or accept in-band bytestreams, or if the * user prefers smaller block sizes + * @throws SmackException if there was no response from the server. */ - public InBandBytestreamSession establishSession(String targetJID) throws XMPPException { + public InBandBytestreamSession establishSession(String targetJID) throws XMPPException, SmackException { String sessionID = getNextSessionID(); return establishSession(targetJID, sessionID); } @@ -418,11 +422,12 @@ public class InBandBytestreamManager implements BytestreamManager { * @param targetJID the JID of the user an In-Band Bytestream should be established * @param sessionID the session ID for the In-Band Bytestream request * @return the session to send/receive data to/from the user - * @throws XMPPException if the user doesn't support or accept in-band bytestreams, or if the + * @throws XMPPErrorException if the user doesn't support or accept in-band bytestreams, or if the * user prefers smaller block sizes + * @throws NoResponseException if there was no response from the server. */ public InBandBytestreamSession establishSession(String targetJID, String sessionID) - throws XMPPException { + throws NoResponseException, XMPPErrorException { Open byteStreamRequest = new Open(sessionID, this.defaultBlockSize, this.stanza); byteStreamRequest.setTo(targetJID); diff --git a/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamRequest.java b/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamRequest.java index 6e3e39ccc..e989f984b 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamRequest.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamRequest.java @@ -17,7 +17,6 @@ package org.jivesoftware.smackx.bytestreams.ibb; import org.jivesoftware.smack.XMPPConnection; -import org.jivesoftware.smack.XMPPException; import org.jivesoftware.smack.packet.IQ; import org.jivesoftware.smackx.bytestreams.BytestreamRequest; import org.jivesoftware.smackx.bytestreams.ibb.packet.Open; @@ -67,9 +66,8 @@ public class InBandBytestreamRequest implements BytestreamRequest { * send/receive data. * * @return the session to send/receive data - * @throws XMPPException if stream is invalid. */ - public InBandBytestreamSession accept() throws XMPPException { + public InBandBytestreamSession accept() { XMPPConnection connection = this.manager.getConnection(); // create In-Band Bytestream session and store it diff --git a/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamSession.java b/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamSession.java index 17f0b003c..4c033d7b7 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamSession.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamSession.java @@ -26,7 +26,6 @@ import java.util.concurrent.TimeUnit; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.PacketListener; -import org.jivesoftware.smack.XMPPException; import org.jivesoftware.smack.filter.AndFilter; import org.jivesoftware.smack.filter.PacketFilter; import org.jivesoftware.smack.filter.PacketTypeFilter; @@ -211,8 +210,10 @@ public class InBandBytestreamSession implements BytestreamSession { try { connection.createPacketCollectorAndSend(close).nextResultOrThrow(); } - catch (XMPPException e) { - throw new IOException("Error while closing stream: " + e.getMessage()); + catch (Exception e) { + // Sadly we are unable to wrap the exception within the IOException, because the + // IOException(String,Throwable) constructor is only support from Android API 9 on. + throw new IOException(); } this.inputStream.cleanup(); @@ -764,11 +765,13 @@ public class InBandBytestreamSession implements BytestreamSession { try { connection.createPacketCollectorAndSend(iq).nextResultOrThrow(); } - catch (XMPPException e) { + catch (Exception e) { // close session unless it is already closed if (!this.isClosed) { InBandBytestreamSession.this.close(); - throw new IOException("Error while sending Data: " + e.getMessage()); + // Sadly we are unable to wrap the exception within the IOException, because the + // IOException(String,Throwable) constructor is only support from Android API 9 on. + throw new IOException(); } } diff --git a/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5BytestreamManager.java b/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5BytestreamManager.java index 7b392951c..85b04c1b1 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5BytestreamManager.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5BytestreamManager.java @@ -30,9 +30,12 @@ import java.util.concurrent.ConcurrentHashMap; import java.util.concurrent.TimeoutException; import org.jivesoftware.smack.AbstractConnectionListener; +import org.jivesoftware.smack.SmackException; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.ConnectionCreationListener; import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.packet.IQ; import org.jivesoftware.smack.packet.Packet; import org.jivesoftware.smack.packet.XMPPError; @@ -406,9 +409,10 @@ public final class Socks5BytestreamManager implements BytestreamManager { * Proxy could be found, if the user couldn't connect to any of the SOCKS5 Proxies * @throws IOException if the bytestream could not be established * @throws InterruptedException if the current thread was interrupted while waiting + * @throws SmackException if there was no response from the server. */ public Socks5BytestreamSession establishSession(String targetJID) throws XMPPException, - IOException, InterruptedException { + IOException, InterruptedException, SmackException { String sessionID = getNextSessionID(); return establishSession(targetJID, sessionID); } @@ -420,25 +424,26 @@ public final class Socks5BytestreamManager implements BytestreamManager { * @param targetJID the JID of the user a SOCKS5 Bytestream should be established * @param sessionID the session ID for the SOCKS5 Bytestream request * @return the Socket to send/receive data to/from the user - * @throws XMPPException if the user doesn't support or accept SOCKS5 Bytestreams, if no Socks5 - * Proxy could be found, if the user couldn't connect to any of the SOCKS5 Proxies * @throws IOException if the bytestream could not be established * @throws InterruptedException if the current thread was interrupted while waiting + * @throws NoResponseException + * @throws SmackException if the target does not support SOCKS5. + * @throws XMPPException */ public Socks5BytestreamSession establishSession(String targetJID, String sessionID) - throws XMPPException, IOException, InterruptedException { + throws IOException, InterruptedException, NoResponseException, SmackException, XMPPException{ - XMPPException discoveryException = null; + XMPPErrorException discoveryException = null; // check if target supports SOCKS5 Bytestream if (!supportsSocks5(targetJID)) { - throw new XMPPException(targetJID + " doesn't support SOCKS5 Bytestream"); + throw new SmackException(targetJID + " doesn't support SOCKS5 Bytestream"); } List proxies = new ArrayList(); // determine SOCKS5 proxies from XMPP-server try { proxies.addAll(determineProxies()); - } catch (XMPPException e) { + } catch (XMPPErrorException e) { // don't abort here, just remember the exception thrown by determineProxies() // determineStreamHostInfos() will at least add the local Socks5 proxy (if enabled) discoveryException = e; @@ -448,7 +453,11 @@ public final class Socks5BytestreamManager implements BytestreamManager { List streamHosts = determineStreamHostInfos(proxies); if (streamHosts.isEmpty()) { - throw discoveryException != null ? discoveryException : new XMPPException("no SOCKS5 proxies available"); + if (discoveryException != null) { + throw discoveryException; + } else { + throw new SmackException("no SOCKS5 proxies available"); + } } // compute digest @@ -488,7 +497,7 @@ public final class Socks5BytestreamManager implements BytestreamManager { StreamHost usedStreamHost = initiation.getStreamHost(streamHostUsed.getJID()); if (usedStreamHost == null) { - throw new XMPPException("Remote user responded with unknown host"); + throw new SmackException("Remote user responded with unknown host"); } // build SOCKS5 client @@ -524,12 +533,11 @@ public final class Socks5BytestreamManager implements BytestreamManager { * @param targetJID the target JID * @return true if the given target JID supports feature SOCKS5 Bytestream * otherwise false - * @throws XMPPException if there was an error querying target for supported features + * @throws XMPPErrorException + * @throws NoResponseException */ - private boolean supportsSocks5(String targetJID) throws XMPPException { - ServiceDiscoveryManager serviceDiscoveryManager = ServiceDiscoveryManager.getInstanceFor(this.connection); - DiscoverInfo discoverInfo = serviceDiscoveryManager.discoverInfo(targetJID); - return discoverInfo.containsFeature(NAMESPACE); + private boolean supportsSocks5(String targetJID) throws NoResponseException, XMPPErrorException { + return ServiceDiscoveryManager.getInstanceFor(connection).supportsFeature(targetJID, NAMESPACE); } /** @@ -537,9 +545,10 @@ public final class Socks5BytestreamManager implements BytestreamManager { * in the same order as returned by the XMPP server. * * @return list of JIDs of SOCKS5 proxies - * @throws XMPPException if there was an error querying the XMPP server for SOCKS5 proxies + * @throws XMPPErrorException if there was an error querying the XMPP server for SOCKS5 proxies + * @throws NoResponseException if there was no response from the server. */ - private List determineProxies() throws XMPPException { + private List determineProxies() throws NoResponseException, XMPPErrorException { ServiceDiscoveryManager serviceDiscoveryManager = ServiceDiscoveryManager.getInstanceFor(this.connection); List proxies = new ArrayList(); @@ -615,7 +624,7 @@ public final class Socks5BytestreamManager implements BytestreamManager { streamHostRequest).nextResultOrThrow(); streamHosts.addAll(response.getStreamHosts()); } - catch (XMPPException e) { + catch (Exception e) { // blacklist errornous proxies this.proxyBlacklist.add(proxy); } diff --git a/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5BytestreamRequest.java b/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5BytestreamRequest.java index 73dce1a78..88f591450 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5BytestreamRequest.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5BytestreamRequest.java @@ -21,7 +21,9 @@ import java.net.Socket; import java.util.Collection; import java.util.concurrent.TimeoutException; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.packet.IQ; import org.jivesoftware.smack.packet.XMPPError; import org.jivesoftware.smack.util.Cache; @@ -186,10 +188,11 @@ public class Socks5BytestreamRequest implements BytestreamRequest { * {@link #setTotalConnectTimeout(int)} and {@link #setMinimumConnectTimeout(int)}. * * @return the socket to send/receive data - * @throws XMPPException if connection to all SOCKS5 proxies failed or if stream is invalid. * @throws InterruptedException if the current thread was interrupted while waiting + * @throws XMPPErrorException + * @throws SmackException */ - public Socks5BytestreamSession accept() throws XMPPException, InterruptedException { + public Socks5BytestreamSession accept() throws InterruptedException, XMPPErrorException, SmackException { Collection streamHosts = this.bytestreamRequest.getStreamHosts(); // throw exceptions if request contains no stream hosts @@ -269,15 +272,14 @@ public class Socks5BytestreamRequest implements BytestreamRequest { /** * Cancels the SOCKS5 Bytestream request by sending an error to the initiator and building a * XMPP exception. - * - * @throws XMPPException XMPP exception containing the XMPP error + * @throws XMPPErrorException */ - private void cancelRequest() throws XMPPException { + private void cancelRequest() throws XMPPErrorException { String errorMessage = "Could not establish socket with any provided host"; XMPPError error = new XMPPError(XMPPError.Condition.item_not_found, errorMessage); IQ errorIQ = IQ.createErrorResponse(this.bytestreamRequest, error); this.manager.getConnection().sendPacket(errorIQ); - throw new XMPPException(errorMessage, error); + throw new XMPPErrorException(errorMessage, error); } /** diff --git a/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5Client.java b/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5Client.java index 5e538b68a..13e74c4f2 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5Client.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5Client.java @@ -29,7 +29,9 @@ import java.util.concurrent.FutureTask; import java.util.concurrent.TimeUnit; import java.util.concurrent.TimeoutException; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smackx.bytestreams.socks5.packet.Bytestream.StreamHost; /** @@ -65,17 +67,19 @@ class Socks5Client { * @param timeout timeout to connect to SOCKS5 proxy in milliseconds * @return socket the initialized socket * @throws IOException if initializing the socket failed due to a network error - * @throws XMPPException if establishing connection to SOCKS5 proxy failed + * @throws XMPPErrorException if establishing connection to SOCKS5 proxy failed * @throws TimeoutException if connecting to SOCKS5 proxy timed out * @throws InterruptedException if the current thread was interrupted while waiting + * @throws SmackException if the connection to the SOC + * @throws XMPPException */ - public Socket getSocket(int timeout) throws IOException, XMPPException, InterruptedException, - TimeoutException { + public Socket getSocket(int timeout) throws IOException, XMPPErrorException, InterruptedException, + TimeoutException, SmackException, XMPPException { // wrap connecting in future for timeout FutureTask futureTask = new FutureTask(new Callable() { - public Socket call() throws Exception { + public Socket call() throws IOException, SmackException { // initialize socket Socket socket = new Socket(); @@ -83,16 +87,23 @@ class Socks5Client { streamHost.getPort()); socket.connect(socketAddress); + boolean res; // initialize connection to SOCKS5 proxy - if (!establish(socket)) { - - // initialization failed, close socket + try { + res = establish(socket); + } + catch (SmackException e) { socket.close(); - throw new XMPPException("establishing connection to SOCKS5 proxy failed"); - + throw e; } - return socket; + if (res) { + return socket; + } + else { + socket.close(); + throw new SmackException("SOCKS5 negotiation failed"); + } } }); @@ -110,8 +121,8 @@ class Socks5Client { if (cause instanceof IOException) { throw (IOException) cause; } - if (cause instanceof XMPPException) { - throw (XMPPException) cause; + if (cause instanceof SmackException) { + throw (SmackException) cause; } } @@ -132,49 +143,49 @@ class Socks5Client { * @param socket connected to a SOCKS5 proxy * @return true if if a stream could be established, otherwise false. * If false is returned the given Socket should be closed. - * @throws IOException if a network error occurred + * @throws SmackException */ - protected boolean establish(Socket socket) throws IOException { + protected boolean establish(Socket socket) throws SmackException { + byte[] connectionRequest; + byte[] connectionResponse; /* * use DataInputStream/DataOutpuStream to assure read and write is completed in a single * statement */ - DataInputStream in = new DataInputStream(socket.getInputStream()); - DataOutputStream out = new DataOutputStream(socket.getOutputStream()); - - // authentication negotiation - byte[] cmd = new byte[3]; - - cmd[0] = (byte) 0x05; // protocol version 5 - cmd[1] = (byte) 0x01; // number of authentication methods supported - cmd[2] = (byte) 0x00; // authentication method: no-authentication required - - out.write(cmd); - out.flush(); - - byte[] response = new byte[2]; - in.readFully(response); - - // check if server responded with correct version and no-authentication method - if (response[0] != (byte) 0x05 || response[1] != (byte) 0x00) { - return false; - } - - // request SOCKS5 connection with given address/digest - byte[] connectionRequest = createSocks5ConnectRequest(); - out.write(connectionRequest); - out.flush(); - - // receive response - byte[] connectionResponse; try { + DataInputStream in = new DataInputStream(socket.getInputStream()); + DataOutputStream out = new DataOutputStream(socket.getOutputStream()); + + // authentication negotiation + byte[] cmd = new byte[3]; + + cmd[0] = (byte) 0x05; // protocol version 5 + cmd[1] = (byte) 0x01; // number of authentication methods supported + cmd[2] = (byte) 0x00; // authentication method: no-authentication required + + out.write(cmd); + out.flush(); + + byte[] response = new byte[2]; + in.readFully(response); + + // check if server responded with correct version and no-authentication method + if (response[0] != (byte) 0x05 || response[1] != (byte) 0x00) { + return false; + } + + // request SOCKS5 connection with given address/digest + connectionRequest = createSocks5ConnectRequest(); + out.write(connectionRequest); + out.flush(); + + // receive response connectionResponse = Socks5Utils.receiveSocks5Message(in); } - catch (XMPPException e) { - return false; // server answered in an unsupported way + catch (IOException e) { + throw new SmackException(e); } - // verify response connectionRequest[1] = (byte) 0x00; // set expected return status to 0 return Arrays.equals(connectionRequest, connectionResponse); diff --git a/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5ClientForInitiator.java b/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5ClientForInitiator.java index 956722105..b2db04b4c 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5ClientForInitiator.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5ClientForInitiator.java @@ -20,8 +20,11 @@ import java.io.IOException; import java.net.Socket; import java.util.concurrent.TimeoutException; +import org.jivesoftware.smack.SmackException; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.packet.IQ; import org.jivesoftware.smackx.bytestreams.socks5.packet.Bytestream; import org.jivesoftware.smackx.bytestreams.socks5.packet.Bytestream.StreamHost; @@ -62,8 +65,8 @@ class Socks5ClientForInitiator extends Socks5Client { this.target = target; } - public Socket getSocket(int timeout) throws IOException, XMPPException, InterruptedException, - TimeoutException { + public Socket getSocket(int timeout) throws IOException, InterruptedException, + TimeoutException, XMPPException, SmackException { Socket socket = null; // check if stream host is the local SOCKS5 proxy @@ -71,7 +74,7 @@ class Socks5ClientForInitiator extends Socks5Client { Socks5Proxy socks5Server = Socks5Proxy.getSocks5Proxy(); socket = socks5Server.getSocket(this.digest); if (socket == null) { - throw new XMPPException("target is not connected to SOCKS5 proxy"); + throw new SmackException("target is not connected to SOCKS5 proxy"); } } else { @@ -80,9 +83,13 @@ class Socks5ClientForInitiator extends Socks5Client { try { activate(); } - catch (XMPPException e) { + catch (XMPPException e1) { socket.close(); - throw new XMPPException("activating SOCKS5 Bytestream failed", e); + throw e1; + } + catch (NoResponseException e2) { + socket.close(); + throw e2; } } @@ -93,8 +100,11 @@ class Socks5ClientForInitiator extends Socks5Client { /** * Activates the SOCKS5 Bytestream by sending a XMPP SOCKS5 Bytestream activation packet to the * SOCKS5 proxy. + * @throws XMPPErrorException + * @throws NoResponseException + * @throws SmackException if there was no response from the server. */ - private void activate() throws XMPPException { + private void activate() throws NoResponseException, XMPPErrorException { Bytestream activate = createStreamHostActivation(); // if activation fails #nextResultOrThrow() throws an exception connection.createPacketCollectorAndSend(activate).nextResultOrThrow(); diff --git a/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5Proxy.java b/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5Proxy.java index 77fd2d580..08a0abfff 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5Proxy.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5Proxy.java @@ -35,7 +35,7 @@ import java.util.concurrent.ConcurrentHashMap; import java.util.logging.Level; import java.util.logging.Logger; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.SmackException; /** * The Socks5Proxy class represents a local SOCKS5 proxy server. It can be enabled/disabled by @@ -392,17 +392,17 @@ public class Socks5Proxy { * Negotiates a SOCKS5 connection and stores it on success. * * @param socket connection to the client - * @throws XMPPException if client requests a connection in an unsupported way + * @throws SmackException if client requests a connection in an unsupported way * @throws IOException if a network error occurred */ - private void establishConnection(Socket socket) throws XMPPException, IOException { + private void establishConnection(Socket socket) throws SmackException, IOException { DataOutputStream out = new DataOutputStream(socket.getOutputStream()); DataInputStream in = new DataInputStream(socket.getInputStream()); // first byte is version should be 5 int b = in.read(); if (b != 5) { - throw new XMPPException("Only SOCKS5 supported"); + throw new SmackException("Only SOCKS5 supported"); } // second byte number of authentication methods supported @@ -428,7 +428,7 @@ public class Socks5Proxy { authMethodSelectionResponse[1] = (byte) 0xFF; // no acceptable methods out.write(authMethodSelectionResponse); out.flush(); - throw new XMPPException("Authentication method not supported"); + throw new SmackException("Authentication method not supported"); } authMethodSelectionResponse[1] = (byte) 0x00; // no-authentication method @@ -447,7 +447,7 @@ public class Socks5Proxy { out.write(connectionRequest); out.flush(); - throw new XMPPException("XMPPConnection is not allowed"); + throw new SmackException("Connection is not allowed"); } connectionRequest[1] = (byte) 0x00; // set return status to 0 (success) diff --git a/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5Utils.java b/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5Utils.java index 9c7cc490c..82642d9a0 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5Utils.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5Utils.java @@ -19,7 +19,7 @@ package org.jivesoftware.smackx.bytestreams.socks5; import java.io.DataInputStream; import java.io.IOException; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smack.util.StringUtils; /** @@ -53,14 +53,14 @@ class Socks5Utils { * @param in the DataInputStream to read the message from * @return the SOCKS5 message * @throws IOException if a network error occurred - * @throws XMPPException if the SOCKS5 message contains an unsupported address type + * @throws SmackException if the SOCKS5 message contains an unsupported address type */ - public static byte[] receiveSocks5Message(DataInputStream in) throws IOException, XMPPException { + public static byte[] receiveSocks5Message(DataInputStream in) throws IOException, SmackException { byte[] header = new byte[5]; in.readFully(header, 0, 5); if (header[3] != (byte) 0x03) { - throw new XMPPException("Unsupported SOCKS5 address type"); + throw new SmackException("Unsupported SOCKS5 address type"); } int addressLength = header[4]; diff --git a/extensions/src/main/java/org/jivesoftware/smackx/caps/EntityCapsManager.java b/extensions/src/main/java/org/jivesoftware/smackx/caps/EntityCapsManager.java index 42c38b42b..7f18d86ff 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/caps/EntityCapsManager.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/caps/EntityCapsManager.java @@ -17,12 +17,13 @@ package org.jivesoftware.smackx.caps; import org.jivesoftware.smack.AbstractConnectionListener; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.ConnectionCreationListener; import org.jivesoftware.smack.Manager; import org.jivesoftware.smack.PacketInterceptor; import org.jivesoftware.smack.PacketListener; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.packet.IQ; import org.jivesoftware.smack.packet.Packet; import org.jivesoftware.smack.packet.PacketExtension; @@ -391,8 +392,10 @@ public class EntityCapsManager extends Manager { * * @param jid * @return true if the entity supports Entity Capabilities. + * @throws XMPPErrorException + * @throws NoResponseException */ - public boolean areEntityCapsSupported(String jid) throws XMPPException { + public boolean areEntityCapsSupported(String jid) throws NoResponseException, XMPPErrorException { return sdm.supportsFeature(jid, NAMESPACE); } @@ -400,8 +403,10 @@ public class EntityCapsManager extends Manager { * Returns true if Entity Caps are supported by the local service/server * * @return true if the user's server supports Entity Capabilities. + * @throws XMPPErrorException + * @throws NoResponseException */ - public boolean areEntityCapsSupportedByServer() throws XMPPException { + public boolean areEntityCapsSupportedByServer() throws NoResponseException, XMPPErrorException { return areEntityCapsSupported(connection().getServiceName()); } diff --git a/extensions/src/main/java/org/jivesoftware/smackx/caps/provider/CapsExtensionProvider.java b/extensions/src/main/java/org/jivesoftware/smackx/caps/provider/CapsExtensionProvider.java index 9f27301ee..d6ec9c017 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/caps/provider/CapsExtensionProvider.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/caps/provider/CapsExtensionProvider.java @@ -1,6 +1,6 @@ /** * - * Copyright © 2009 Jonas Ådahl, 2011-2013 Florian Schmaus + * Copyright © 2009 Jonas Ådahl, 2011-2014 Florian Schmaus * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -18,7 +18,7 @@ package org.jivesoftware.smackx.caps.provider; import java.io.IOException; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smack.packet.PacketExtension; import org.jivesoftware.smack.provider.PacketExtensionProvider; import org.jivesoftware.smackx.caps.EntityCapsManager; @@ -29,7 +29,7 @@ import org.xmlpull.v1.XmlPullParserException; public class CapsExtensionProvider implements PacketExtensionProvider { public PacketExtension parseExtension(XmlPullParser parser) throws XmlPullParserException, IOException, - XMPPException { + SmackException { String hash = null; String version = null; String node = null; @@ -39,20 +39,20 @@ public class CapsExtensionProvider implements PacketExtensionProvider { version = parser.getAttributeValue(null, "ver"); node = parser.getAttributeValue(null, "node"); } else { - throw new XMPPException("Malformed Caps element"); + throw new SmackException("Malformed Caps element"); } parser.next(); if (!(parser.getEventType() == XmlPullParser.END_TAG && parser.getName().equalsIgnoreCase(EntityCapsManager.ELEMENT))) { - throw new XMPPException("Malformed nested Caps element"); + throw new SmackException("Malformed nested Caps element"); } if (hash != null && version != null && node != null) { return new CapsExtension(node, version, hash); } else { - throw new XMPPException("Caps elment with missing attributes"); + throw new SmackException("Caps elment with missing attributes"); } } } diff --git a/extensions/src/main/java/org/jivesoftware/smackx/commands/AdHocCommand.java b/extensions/src/main/java/org/jivesoftware/smackx/commands/AdHocCommand.java index 5a48c9ed4..27b7103dc 100755 --- a/extensions/src/main/java/org/jivesoftware/smackx/commands/AdHocCommand.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/commands/AdHocCommand.java @@ -16,7 +16,8 @@ */ package org.jivesoftware.smackx.commands; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.SmackException.NoResponseException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.packet.XMPPError; import org.jivesoftware.smackx.commands.packet.AdHocCommandData; import org.jivesoftware.smackx.xdata.Form; @@ -207,9 +208,9 @@ public abstract class AdHocCommand { * command. It is invoked on every command. If there is a problem executing * the command it throws an XMPPException. * - * @throws XMPPException if there is an error executing the command. + * @throws XMPPErrorException if there is an error executing the command. */ - public abstract void execute() throws XMPPException; + public abstract void execute() throws NoResponseException, XMPPErrorException; /** * Executes the next action of the command with the information provided in @@ -219,9 +220,9 @@ public abstract class AdHocCommand { * XMPPException. * * @param response the form answer of the previous stage. - * @throws XMPPException if there is a problem executing the command. + * @throws XMPPErrorException if there is a problem executing the command. */ - public abstract void next(Form response) throws XMPPException; + public abstract void next(Form response) throws NoResponseException, XMPPErrorException; /** * Completes the command execution with the information provided in the @@ -231,9 +232,9 @@ public abstract class AdHocCommand { * XMPPException. * * @param response the form answer of the previous stage. - * @throws XMPPException if there is a problem executing the command. + * @throws XMPPErrorException if there is a problem executing the command. */ - public abstract void complete(Form response) throws XMPPException; + public abstract void complete(Form response) throws NoResponseException, XMPPErrorException; /** * Goes to the previous stage. The requester is asking to re-send the @@ -241,18 +242,18 @@ public abstract class AdHocCommand { * the previous one. If there is a problem executing the command it throws * an XMPPException. * - * @throws XMPPException if there is a problem executing the command. + * @throws XMPPErrorException if there is a problem executing the command. */ - public abstract void prev() throws XMPPException; + public abstract void prev() throws NoResponseException, XMPPErrorException; /** * Cancels the execution of the command. This can be invoked on any stage of * the execution. If there is a problem executing the command it throws an * XMPPException. * - * @throws XMPPException if there is a problem executing the command. + * @throws XMPPErrorException if there is a problem executing the command. */ - public abstract void cancel() throws XMPPException; + public abstract void cancel() throws NoResponseException, XMPPErrorException; /** * Returns a collection with the allowed actions based on the current stage. diff --git a/extensions/src/main/java/org/jivesoftware/smackx/commands/AdHocCommandManager.java b/extensions/src/main/java/org/jivesoftware/smackx/commands/AdHocCommandManager.java index 0465fd272..daf9f8791 100755 --- a/extensions/src/main/java/org/jivesoftware/smackx/commands/AdHocCommandManager.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/commands/AdHocCommandManager.java @@ -18,6 +18,7 @@ package org.jivesoftware.smackx.commands; import org.jivesoftware.smack.*; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.filter.PacketFilter; import org.jivesoftware.smack.filter.PacketTypeFilter; import org.jivesoftware.smack.packet.IQ; @@ -171,7 +172,12 @@ public class AdHocCommandManager extends Manager { PacketListener listener = new PacketListener() { public void processPacket(Packet packet) { AdHocCommandData requestData = (AdHocCommandData) packet; - processAdHocCommand(requestData); + try { + processAdHocCommand(requestData); + } + catch (SmackException e) { + return; + } } }; @@ -256,8 +262,9 @@ public class AdHocCommandManager extends Manager { * @param jid the full JID to retrieve the commands for. * @return the discovered items. * @throws XMPPException if the operation failed for some reason. + * @throws SmackException if there was no response from the server. */ - public DiscoverItems discoverCommands(String jid) throws XMPPException { + public DiscoverItems discoverCommands(String jid) throws XMPPException, SmackException { return serviceDiscoveryManager.discoverItems(jid, NAMESPACE); } @@ -266,8 +273,9 @@ public class AdHocCommandManager extends Manager { * * @param jid the full JID to publish the commands to. * @throws XMPPException if the operation failed for some reason. + * @throws SmackException if there was no response from the server. */ - public void publishCommands(String jid) throws XMPPException { + public void publishCommands(String jid) throws XMPPException, SmackException { // Collects the commands to publish as items DiscoverItems discoverItems = new DiscoverItems(); Collection xCommandsList = getRegisteredCommands(); @@ -319,8 +327,9 @@ public class AdHocCommandManager extends Manager { * * @param requestData * the packet to process. + * @throws SmackException if there was no response from the server. */ - private void processAdHocCommand(AdHocCommandData requestData) { + private void processAdHocCommand(AdHocCommandData requestData) throws SmackException { // Only process requests of type SET if (requestData.getType() != IQ.Type.SET) { return; @@ -444,7 +453,7 @@ public class AdHocCommandManager extends Manager { connection().sendPacket(response); } - catch (XMPPException e) { + catch (XMPPErrorException e) { // If there is an exception caused by the next, complete, // prev or cancel method, then that error is returned to the // requester. @@ -558,7 +567,7 @@ public class AdHocCommandManager extends Manager { connection().sendPacket(response); } - catch (XMPPException e) { + catch (XMPPErrorException e) { // If there is an exception caused by the next, complete, // prev or cancel method, then that error is returned to the // requester. @@ -621,10 +630,9 @@ public class AdHocCommandManager extends Manager { * @param commandNode the command node that identifies it. * @param sessionID the session id of this execution. * @return the command instance to execute. - * @throws XMPPException if there is problem creating the new instance. + * @throws XMPPErrorException if there is problem creating the new instance. */ - private LocalCommand newInstanceOfCmd(String commandNode, String sessionID) - throws XMPPException + private LocalCommand newInstanceOfCmd(String commandNode, String sessionID) throws XMPPErrorException { AdHocCommandInfo commandInfo = commands.get(commandNode); LocalCommand command; @@ -635,11 +643,11 @@ public class AdHocCommandManager extends Manager { command.setNode(commandInfo.getNode()); } catch (InstantiationException e) { - throw new XMPPException(new XMPPError( + throw new XMPPErrorException(new XMPPError( XMPPError.Condition.internal_server_error)); } catch (IllegalAccessException e) { - throw new XMPPException(new XMPPError( + throw new XMPPErrorException(new XMPPError( XMPPError.Condition.internal_server_error)); } return command; diff --git a/extensions/src/main/java/org/jivesoftware/smackx/commands/RemoteCommand.java b/extensions/src/main/java/org/jivesoftware/smackx/commands/RemoteCommand.java index 101fb6922..b36dc2739 100755 --- a/extensions/src/main/java/org/jivesoftware/smackx/commands/RemoteCommand.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/commands/RemoteCommand.java @@ -17,8 +17,9 @@ package org.jivesoftware.smackx.commands; import org.jivesoftware.smack.SmackConfiguration; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.packet.IQ; import org.jivesoftware.smackx.commands.packet.AdHocCommandData; import org.jivesoftware.smackx.xdata.Form; @@ -79,17 +80,17 @@ public class RemoteCommand extends AdHocCommand { } @Override - public void cancel() throws XMPPException { + public void cancel() throws NoResponseException, XMPPErrorException { executeAction(Action.cancel, packetReplyTimeout); } @Override - public void complete(Form form) throws XMPPException { + public void complete(Form form) throws NoResponseException, XMPPErrorException { executeAction(Action.complete, form, packetReplyTimeout); } @Override - public void execute() throws XMPPException { + public void execute() throws NoResponseException, XMPPErrorException { executeAction(Action.execute, packetReplyTimeout); } @@ -99,23 +100,24 @@ public class RemoteCommand extends AdHocCommand { * there is a problem executing the command it throws an XMPPException. * * @param form the form anwser of the previous stage. - * @throws XMPPException if an error occurs. + * @throws XMPPErrorException if an error occurs. + * @throws NoResponseException if there was no response from the server. */ - public void execute(Form form) throws XMPPException { + public void execute(Form form) throws NoResponseException, XMPPErrorException { executeAction(Action.execute, form, packetReplyTimeout); } @Override - public void next(Form form) throws XMPPException { + public void next(Form form) throws NoResponseException, XMPPErrorException { executeAction(Action.next, form, packetReplyTimeout); } @Override - public void prev() throws XMPPException { + public void prev() throws NoResponseException, XMPPErrorException { executeAction(Action.prev, packetReplyTimeout); } - private void executeAction(Action action, long packetReplyTimeout) throws XMPPException { + private void executeAction(Action action, long packetReplyTimeout) throws NoResponseException, XMPPErrorException { executeAction(action, null, packetReplyTimeout); } @@ -127,9 +129,10 @@ public class RemoteCommand extends AdHocCommand { * @param action the action to execute. * @param form the form with the information. * @param timeout the amount of time to wait for a reply. - * @throws XMPPException if there is a problem executing the command. + * @throws XMPPErrorException if there is a problem executing the command. + * @throws NoResponseException if there was no response from the server. */ - private void executeAction(Action action, Form form, long timeout) throws XMPPException { + private void executeAction(Action action, Form form, long timeout) throws NoResponseException, XMPPErrorException { // TODO: Check that all the required fields of the form were filled, if // TODO: not throw the corresponding exeption. This will make a faster response, // TODO: since the request is stoped before it's sent. diff --git a/extensions/src/main/java/org/jivesoftware/smackx/disco/ServiceDiscoveryManager.java b/extensions/src/main/java/org/jivesoftware/smackx/disco/ServiceDiscoveryManager.java index b5cd4751b..53828d9a3 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/disco/ServiceDiscoveryManager.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/disco/ServiceDiscoveryManager.java @@ -17,11 +17,12 @@ package org.jivesoftware.smackx.disco; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.ConnectionCreationListener; import org.jivesoftware.smack.Manager; import org.jivesoftware.smack.PacketListener; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.filter.PacketFilter; import org.jivesoftware.smack.filter.PacketTypeFilter; import org.jivesoftware.smack.packet.IQ; @@ -493,9 +494,10 @@ public class ServiceDiscoveryManager extends Manager { * * @param entityID the address of the XMPP entity or null. * @return the discovered information. - * @throws XMPPException if the operation failed for some reason. + * @throws XMPPErrorException + * @throws NoResponseException */ - public DiscoverInfo discoverInfo(String entityID) throws XMPPException { + public DiscoverInfo discoverInfo(String entityID) throws NoResponseException, XMPPErrorException { if (entityID == null) return discoverInfo(null, null); @@ -536,9 +538,10 @@ public class ServiceDiscoveryManager extends Manager { * @param entityID the address of the XMPP entity. * @param node the optional attribute that supplements the 'jid' attribute. * @return the discovered information. - * @throws XMPPException if the operation failed for some reason. + * @throws XMPPErrorException if the operation failed for some reason. + * @throws NoResponseException if there was no response from the server. */ - public DiscoverInfo discoverInfo(String entityID, String node) throws XMPPException { + public DiscoverInfo discoverInfo(String entityID, String node) throws NoResponseException, XMPPErrorException { // Discover the entity's info DiscoverInfo disco = new DiscoverInfo(); disco.setType(IQ.Type.GET); @@ -555,9 +558,10 @@ public class ServiceDiscoveryManager extends Manager { * * @param entityID the address of the XMPP entity. * @return the discovered information. - * @throws XMPPException if the operation failed for some reason. + * @throws XMPPErrorException if the operation failed for some reason. + * @throws NoResponseException if there was no response from the server. */ - public DiscoverItems discoverItems(String entityID) throws XMPPException { + public DiscoverItems discoverItems(String entityID) throws NoResponseException, XMPPErrorException { return discoverItems(entityID, null); } @@ -569,9 +573,10 @@ public class ServiceDiscoveryManager extends Manager { * @param entityID the address of the XMPP entity. * @param node the optional attribute that supplements the 'jid' attribute. * @return the discovered items. - * @throws XMPPException if the operation failed for some reason. + * @throws XMPPErrorException if the operation failed for some reason. + * @throws NoResponseException if there was no response from the server. */ - public DiscoverItems discoverItems(String entityID, String node) throws XMPPException { + public DiscoverItems discoverItems(String entityID, String node) throws NoResponseException, XMPPErrorException { // Discover the entity's items DiscoverItems disco = new DiscoverItems(); disco.setType(IQ.Type.GET); @@ -590,9 +595,10 @@ public class ServiceDiscoveryManager extends Manager { * * @param entityID the address of the XMPP entity. * @return true if the server supports publishing of items. - * @throws XMPPException if the operation failed for some reason. + * @throws XMPPErrorException + * @throws NoResponseException */ - public boolean canPublishItems(String entityID) throws XMPPException { + public boolean canPublishItems(String entityID) throws NoResponseException, XMPPErrorException { DiscoverInfo info = discoverInfo(entityID); return canPublishItems(info); } @@ -618,10 +624,10 @@ public class ServiceDiscoveryManager extends Manager { * * @param entityID the address of the XMPP entity. * @param discoverItems the DiscoveryItems to publish. - * @throws XMPPException if the operation failed for some reason. + * @throws XMPPErrorException + * @throws NoResponseException */ - public void publishItems(String entityID, DiscoverItems discoverItems) - throws XMPPException { + public void publishItems(String entityID, DiscoverItems discoverItems) throws NoResponseException, XMPPErrorException { publishItems(entityID, null, discoverItems); } @@ -634,10 +640,11 @@ public class ServiceDiscoveryManager extends Manager { * @param entityID the address of the XMPP entity. * @param node the attribute that supplements the 'jid' attribute. * @param discoverItems the DiscoveryItems to publish. - * @throws XMPPException if the operation failed for some reason. + * @throws XMPPErrorException if the operation failed for some reason. + * @throws NoResponseException if there was no response from the server. */ - public void publishItems(String entityID, String node, DiscoverItems discoverItems) - throws XMPPException { + public void publishItems(String entityID, String node, DiscoverItems discoverItems) throws NoResponseException, XMPPErrorException + { discoverItems.setType(IQ.Type.SET); discoverItems.setTo(entityID); discoverItems.setNode(node); @@ -651,9 +658,10 @@ public class ServiceDiscoveryManager extends Manager { * @param jid the JID of the remote entity * @param feature * @return true if the entity supports the feature, false otherwise - * @throws XMPPException + * @throws XMPPErrorException + * @throws NoResponseException */ - public boolean supportsFeature(String jid, String feature) throws XMPPException { + public boolean supportsFeature(String jid, String feature) throws NoResponseException, XMPPErrorException { DiscoverInfo result = discoverInfo(jid); return result.containsFeature(feature); } diff --git a/extensions/src/main/java/org/jivesoftware/smackx/filetransfer/FaultTolerantNegotiator.java b/extensions/src/main/java/org/jivesoftware/smackx/filetransfer/FaultTolerantNegotiator.java index 3581e4313..1274afc57 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/filetransfer/FaultTolerantNegotiator.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/filetransfer/FaultTolerantNegotiator.java @@ -17,8 +17,11 @@ package org.jivesoftware.smackx.filetransfer; import org.jivesoftware.smack.PacketCollector; +import org.jivesoftware.smack.SmackException; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.filter.OrFilter; import org.jivesoftware.smack.filter.PacketFilter; import org.jivesoftware.smack.packet.Packet; @@ -59,7 +62,7 @@ public class FaultTolerantNegotiator extends StreamNegotiator { return new OrFilter(primaryFilter, secondaryFilter); } - InputStream negotiateIncomingStream(Packet streamInitiation) throws XMPPException { + InputStream negotiateIncomingStream(Packet streamInitiation) { throw new UnsupportedOperationException("Negotiation only handled by create incoming " + "stream method."); } @@ -69,7 +72,7 @@ public class FaultTolerantNegotiator extends StreamNegotiator { "method"); } - public InputStream createIncomingStream(StreamInitiation initiation) throws XMPPException { + public InputStream createIncomingStream(StreamInitiation initiation) throws SmackException { PacketCollector collector = connection.createPacketCollector( getInitiationPacketFilter(initiation.getFrom(), initiation.getSessionID())); @@ -80,7 +83,7 @@ public class FaultTolerantNegotiator extends StreamNegotiator { = new ExecutorCompletionService(threadPoolExecutor); List> futures = new ArrayList>(); InputStream stream = null; - XMPPException exception = null; + SmackException exception = null; try { futures.add(service.submit(new NegotiatorService(collector))); futures.add(service.submit(new NegotiatorService(collector))); @@ -107,7 +110,7 @@ public class FaultTolerantNegotiator extends StreamNegotiator { /* Do Nothing */ } catch (ExecutionException e) { - exception = new XMPPException(e.getCause()); + exception = new SmackException(e.getCause()); } } } @@ -123,7 +126,7 @@ public class FaultTolerantNegotiator extends StreamNegotiator { throw exception; } else { - throw new XMPPException("File transfer negotiation failed."); + throw new SmackException("File transfer negotiation failed."); } } @@ -135,12 +138,12 @@ public class FaultTolerantNegotiator extends StreamNegotiator { } public OutputStream createOutgoingStream(String streamID, String initiator, String target) - throws XMPPException { + throws SmackException, XMPPException { OutputStream stream; try { stream = primaryNegotiator.createOutgoingStream(streamID, initiator, target); } - catch (XMPPException ex) { + catch (Exception ex) { stream = secondaryNegotiator.createOutgoingStream(streamID, initiator, target); } @@ -169,10 +172,10 @@ public class FaultTolerantNegotiator extends StreamNegotiator { this.collector = collector; } - public InputStream call() throws Exception { + public InputStream call() throws XMPPErrorException, InterruptedException, SmackException { Packet streamInitiation = collector.nextResult(); if (streamInitiation == null) { - throw new XMPPException("No response from remote client"); + throw new NoResponseException(); } StreamNegotiator negotiator = determineNegotiator(streamInitiation); return negotiator.negotiateIncomingStream(streamInitiation); diff --git a/extensions/src/main/java/org/jivesoftware/smackx/filetransfer/FileTransfer.java b/extensions/src/main/java/org/jivesoftware/smackx/filetransfer/FileTransfer.java index b67873f70..1ad5a838e 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/filetransfer/FileTransfer.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/filetransfer/FileTransfer.java @@ -16,7 +16,7 @@ */ package org.jivesoftware.smackx.filetransfer; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.SmackException; import java.io.IOException; import java.io.InputStream; @@ -201,8 +201,8 @@ public abstract class FileTransfer { } } - protected void writeToStream(final InputStream in, final OutputStream out) - throws XMPPException + protected void writeToStream(final InputStream in, final OutputStream out) + throws SmackException { final byte[] b = new byte[BUFFER_SIZE]; int count = 0; @@ -213,7 +213,7 @@ public abstract class FileTransfer { try { out.write(b, 0, count); } catch (IOException e) { - throw new XMPPException("error writing to output stream", e); + throw new SmackException("error writing to output stream", e); } amountWritten += count; @@ -222,7 +222,7 @@ public abstract class FileTransfer { try { count = in.read(b); } catch (IOException e) { - throw new XMPPException("error reading from input stream", e); + throw new SmackException("error reading from input stream", e); } } while (count != -1 && !getStatus().equals(Status.cancelled)); diff --git a/extensions/src/main/java/org/jivesoftware/smackx/filetransfer/FileTransferNegotiator.java b/extensions/src/main/java/org/jivesoftware/smackx/filetransfer/FileTransferNegotiator.java index 8bd0005f3..561344d86 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/filetransfer/FileTransferNegotiator.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/filetransfer/FileTransferNegotiator.java @@ -30,7 +30,7 @@ import java.util.concurrent.ConcurrentHashMap; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.ConnectionListener; import org.jivesoftware.smack.PacketCollector; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.packet.IQ; import org.jivesoftware.smack.packet.Packet; import org.jivesoftware.smack.packet.XMPPError; @@ -249,11 +249,11 @@ public class FileTransferNegotiator { * * @param request The related file transfer request. * @return The file transfer object that handles the transfer - * @throws XMPPException If there are either no stream methods contained in the packet, or + * @throws XMPPErrorException If there are either no stream methods contained in the packet, or * there is not an appropriate stream method. */ public StreamNegotiator selectStreamNegotiator( - FileTransferRequest request) throws XMPPException { + FileTransferRequest request) throws XMPPErrorException { StreamInitiation si = request.getStreamInitiation(); FormField streamMethodField = getStreamMethodField(si .getFeatureNegotiationForm()); @@ -265,7 +265,7 @@ public class FileTransferNegotiator { IQ.Type.ERROR); iqPacket.setError(error); connection.sendPacket(iqPacket); - throw new XMPPException(errorMessage, error); + throw new XMPPErrorException(errorMessage, error); } // select the appropriate protocol @@ -274,7 +274,7 @@ public class FileTransferNegotiator { try { selectedStreamNegotiator = getNegotiator(streamMethodField); } - catch (XMPPException e) { + catch (XMPPErrorException e) { IQ iqPacket = createIQ(si.getPacketID(), si.getFrom(), si.getTo(), IQ.Type.ERROR); iqPacket.setError(e.getXMPPError()); @@ -300,7 +300,7 @@ public class FileTransferNegotiator { } private StreamNegotiator getNegotiator(final FormField field) - throws XMPPException { + throws XMPPErrorException { String variable; boolean isByteStream = false; boolean isIBB = false; @@ -317,7 +317,7 @@ public class FileTransferNegotiator { if (!isByteStream && !isIBB) { XMPPError error = new XMPPError(XMPPError.Condition.bad_request, "No acceptable transfer mechanism"); - throw new XMPPException(error.getMessage(), error); + throw new XMPPErrorException(error); } //if (isByteStream && isIBB && field.getType().equals(FormField.TYPE_LIST_MULTI)) { @@ -389,11 +389,11 @@ public class FileTransferNegotiator { * @param responseTimeout The amount of time, in milliseconds, to wait for the remote * user to respond. If they do not respond in time, this * @return Returns the stream negotiator selected by the peer. - * @throws XMPPException Thrown if there is an error negotiating the file transfer. + * @throws XMPPErrorException Thrown if there is an error negotiating the file transfer. */ public StreamNegotiator negotiateOutgoingTransfer(final String userID, final String streamID, final String fileName, final long size, - final String desc, int responseTimeout) throws XMPPException { + final String desc, int responseTimeout) throws XMPPErrorException { StreamInitiation si = new StreamInitiation(); si.setSessionID(streamID); si.setMimeType(URLConnection.guessContentTypeFromName(fileName)); @@ -420,11 +420,8 @@ public class FileTransferNegotiator { .getFeatureNegotiationForm())); } - else if (iqResponse.getType().equals(IQ.Type.ERROR)) { - throw new XMPPException(iqResponse.getError()); - } else { - throw new XMPPException("File transfer response unreadable"); + throw new XMPPErrorException(iqResponse.getError()); } } else { @@ -433,7 +430,7 @@ public class FileTransferNegotiator { } private StreamNegotiator getOutgoingNegotiator(final FormField field) - throws XMPPException { + throws XMPPErrorException { String variable; boolean isByteStream = false; boolean isIBB = false; @@ -450,7 +447,7 @@ public class FileTransferNegotiator { if (!isByteStream && !isIBB) { XMPPError error = new XMPPError(XMPPError.Condition.bad_request, "No acceptable transfer mechanism"); - throw new XMPPException(error.getMessage(), error); + throw new XMPPErrorException(error); } if (isByteStream && isIBB) { diff --git a/extensions/src/main/java/org/jivesoftware/smackx/filetransfer/IBBTransferNegotiator.java b/extensions/src/main/java/org/jivesoftware/smackx/filetransfer/IBBTransferNegotiator.java index fb938a2ce..d54d3f5ba 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/filetransfer/IBBTransferNegotiator.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/filetransfer/IBBTransferNegotiator.java @@ -19,8 +19,9 @@ package org.jivesoftware.smackx.filetransfer; import java.io.InputStream; import java.io.OutputStream; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.filter.AndFilter; import org.jivesoftware.smack.filter.FromMatchesFilter; import org.jivesoftware.smack.filter.PacketFilter; @@ -60,17 +61,17 @@ public class IBBTransferNegotiator extends StreamNegotiator { } public OutputStream createOutgoingStream(String streamID, String initiator, - String target) throws XMPPException { + String target) throws NoResponseException, XMPPErrorException { InBandBytestreamSession session = this.manager.establishSession(target, streamID); session.setCloseBothStreamsEnabled(true); return session.getOutputStream(); } public InputStream createIncomingStream(StreamInitiation initiation) - throws XMPPException { + throws NoResponseException, XMPPErrorException { /* - * In-Band Bytestream initiation listener must ignore next in-band - * bytestream request with given session ID + * In-Band Bytestream initiation listener must ignore next in-band bytestream request with + * given session ID */ this.manager.ignoreBytestreamRequestOnce(initiation.getSessionID()); @@ -93,7 +94,7 @@ public class IBBTransferNegotiator extends StreamNegotiator { return new String[] { InBandBytestreamManager.NAMESPACE }; } - InputStream negotiateIncomingStream(Packet streamInitiation) throws XMPPException { + InputStream negotiateIncomingStream(Packet streamInitiation) { // build In-Band Bytestream request InBandBytestreamRequest request = new ByteStreamRequest(this.manager, (Open) streamInitiation); diff --git a/extensions/src/main/java/org/jivesoftware/smackx/filetransfer/IncomingFileTransfer.java b/extensions/src/main/java/org/jivesoftware/smackx/filetransfer/IncomingFileTransfer.java index e5b269433..1752f2a94 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/filetransfer/IncomingFileTransfer.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/filetransfer/IncomingFileTransfer.java @@ -16,7 +16,8 @@ */ package org.jivesoftware.smackx.filetransfer; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.SmackException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import java.io.*; import java.util.concurrent.*; @@ -58,10 +59,11 @@ public class IncomingFileTransfer extends FileTransfer { * the negotiated stream. * * @return The negotiated InputStream from which to read the data. - * @throws XMPPException If there is an error in the negotiation process an exception + * @throws SmackException + * @throws XMPPErrorException If there is an error in the negotiation process an exception * is thrown. */ - public InputStream recieveFile() throws XMPPException { + public InputStream recieveFile() throws SmackException, XMPPErrorException { if (inputStream != null) { throw new IllegalStateException("Transfer already negotiated!"); } @@ -69,7 +71,7 @@ public class IncomingFileTransfer extends FileTransfer { try { inputStream = negotiateStream(); } - catch (XMPPException e) { + catch (XMPPErrorException e) { setException(e); throw e; } @@ -78,32 +80,31 @@ public class IncomingFileTransfer extends FileTransfer { } /** - * This method negotitates the stream and then transfer's the file over the - * negotiated stream. The transfered file will be saved at the provided - * location. + * This method negotitates the stream and then transfer's the file over the negotiated stream. + * The transfered file will be saved at the provided location. *

- * This method will return immedialtly, file transfer progress can be - * monitored through several methods: + * This method will return immedialtly, file transfer progress can be monitored through several + * methods: *

*

    *
  • {@link FileTransfer#getStatus()} *
  • {@link FileTransfer#getProgress()} *
  • {@link FileTransfer#isDone()} *
- * + * * @param file The location to save the file. - * @throws XMPPException when the file transfer fails + * @throws SmackException when the file transfer fails * @throws IllegalArgumentException This exception is thrown when the the provided file is - * either null, or cannot be written to. + * either null, or cannot be written to. */ - public void recieveFile(final File file) throws XMPPException { + public void recieveFile(final File file) throws SmackException { if (file != null) { if (!file.exists()) { try { file.createNewFile(); } catch (IOException e) { - throw new XMPPException( + throw new SmackException( "Could not create file to write too", e); } } @@ -120,8 +121,9 @@ public class IncomingFileTransfer extends FileTransfer { try { inputStream = negotiateStream(); } - catch (XMPPException e) { - handleXMPPException(e); + catch (Exception e) { + setStatus(FileTransfer.Status.error); + setException(e); return; } @@ -131,7 +133,7 @@ public class IncomingFileTransfer extends FileTransfer { setStatus(Status.in_progress); writeToStream(inputStream, outputStream); } - catch (XMPPException e) { + catch (SmackException e) { setStatus(Status.error); setError(Error.stream); setException(e); @@ -166,12 +168,7 @@ public class IncomingFileTransfer extends FileTransfer { transferThread.start(); } - private void handleXMPPException(XMPPException e) { - setStatus(FileTransfer.Status.error); - setException(e); - } - - private InputStream negotiateStream() throws XMPPException { + private InputStream negotiateStream() throws SmackException, XMPPErrorException { setStatus(Status.negotiating_transfer); final StreamNegotiator streamNegotiator = negotiator .selectStreamNegotiator(recieveRequest); @@ -190,13 +187,13 @@ public class IncomingFileTransfer extends FileTransfer { inputStream = streamNegotiatorTask.get(15, TimeUnit.SECONDS); } catch (InterruptedException e) { - throw new XMPPException("Interruption while executing", e); + throw new SmackException("Interruption while executing", e); } catch (ExecutionException e) { - throw new XMPPException("Error in execution", e); + throw new SmackException("Error in execution", e); } catch (TimeoutException e) { - throw new XMPPException("Request timed out", e); + throw new SmackException("Request timed out", e); } finally { streamNegotiatorTask.cancel(true); diff --git a/extensions/src/main/java/org/jivesoftware/smackx/filetransfer/OutgoingFileTransfer.java b/extensions/src/main/java/org/jivesoftware/smackx/filetransfer/OutgoingFileTransfer.java index 407e163f2..aeab5810a 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/filetransfer/OutgoingFileTransfer.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/filetransfer/OutgoingFileTransfer.java @@ -16,7 +16,10 @@ */ package org.jivesoftware.smackx.filetransfer; +import org.jivesoftware.smack.SmackException; +import org.jivesoftware.smack.SmackException.IllegalStateChangeException; import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.packet.XMPPError; import java.io.*; @@ -108,9 +111,10 @@ public class OutgoingFileTransfer extends FileTransfer { * @throws XMPPException * Thrown if an error occurs during the file transfer * negotiation process. + * @throws SmackException if there was no response from the server. */ public synchronized OutputStream sendFile(String fileName, long fileSize, - String description) throws XMPPException { + String description) throws XMPPException, SmackException { if (isDone() || outputStream != null) { throw new IllegalStateException( "The negotation process has already" @@ -119,7 +123,7 @@ public class OutgoingFileTransfer extends FileTransfer { try { setFileInfo(fileName, fileSize); this.outputStream = negotiateStream(fileName, fileSize, description); - } catch (XMPPException e) { + } catch (XMPPErrorException e) { handleXMPPException(e); throw e; } @@ -166,9 +170,12 @@ public class OutgoingFileTransfer extends FileTransfer { fileName, fileSize, description); progress.outputStreamEstablished(OutgoingFileTransfer.this.outputStream); } - catch (XMPPException e) { + catch (XMPPErrorException e) { handleXMPPException(e); } + catch (Exception e) { + setException(e); + } } }, "File Transfer Negotiation " + streamID); transferThread.start(); @@ -194,12 +201,12 @@ public class OutgoingFileTransfer extends FileTransfer { * * @param file the file to transfer to the remote entity. * @param description a description for the file to transfer. - * @throws XMPPException + * @throws SmackException * If there is an error during the negotiation process or the * sending of the file. */ public synchronized void sendFile(final File file, final String description) - throws XMPPException { + throws SmackException { checkTransferThread(); if (file == null || !file.exists() || !file.canRead()) { throw new IllegalArgumentException("Could not read file"); @@ -212,10 +219,13 @@ public class OutgoingFileTransfer extends FileTransfer { try { outputStream = negotiateStream(file.getName(), file .length(), description); - } catch (XMPPException e) { + } catch (XMPPErrorException e) { handleXMPPException(e); return; } + catch (Exception e) { + setException(e); + } if (outputStream == null) { return; } @@ -232,7 +242,7 @@ public class OutgoingFileTransfer extends FileTransfer { setStatus(FileTransfer.Status.error); setError(Error.bad_file); setException(e); - } catch (XMPPException e) { + } catch (SmackException e) { setStatus(FileTransfer.Status.error); setException(e); } finally { @@ -279,10 +289,13 @@ public class OutgoingFileTransfer extends FileTransfer { //Create packet filter try { outputStream = negotiateStream(fileName, fileSize, description); - } catch (XMPPException e) { + } catch (XMPPErrorException e) { handleXMPPException(e); return; } + catch (Exception e) { + setException(e); + } if (outputStream == null) { return; } @@ -292,7 +305,7 @@ public class OutgoingFileTransfer extends FileTransfer { } try { writeToStream(in, outputStream); - } catch (XMPPException e) { + } catch (SmackException e) { setStatus(FileTransfer.Status.error); setException(e); } finally { @@ -314,7 +327,7 @@ public class OutgoingFileTransfer extends FileTransfer { transferThread.start(); } - private void handleXMPPException(XMPPException e) { + private void handleXMPPException(XMPPErrorException e) { XMPPError error = e.getXMPPError(); if (error != null) { String condition = error.getCondition(); @@ -350,11 +363,11 @@ public class OutgoingFileTransfer extends FileTransfer { } private OutputStream negotiateStream(String fileName, long fileSize, - String description) throws XMPPException { + String description) throws SmackException, XMPPException { // Negotiate the file transfer profile if (!updateStatus(Status.initial, Status.negotiating_transfer)) { - throw new XMPPException("Illegal state change"); + throw new IllegalStateChangeException(); } StreamNegotiator streamNegotiator = negotiator.negotiateOutgoingTransfer( getPeer(), streamID, fileName, fileSize, description, @@ -368,13 +381,13 @@ public class OutgoingFileTransfer extends FileTransfer { // Negotiate the stream if (!updateStatus(Status.negotiating_transfer, Status.negotiating_stream)) { - throw new XMPPException("Illegal state change"); + throw new IllegalStateChangeException(); } outputStream = streamNegotiator.createOutgoingStream(streamID, initiator, getPeer()); if (!updateStatus(Status.negotiating_stream, Status.negotiated)) { - throw new XMPPException("Illegal state change"); + throw new IllegalStateChangeException(); } return outputStream; } diff --git a/extensions/src/main/java/org/jivesoftware/smackx/filetransfer/Socks5TransferNegotiator.java b/extensions/src/main/java/org/jivesoftware/smackx/filetransfer/Socks5TransferNegotiator.java index 32c80f0b9..8ce0998e2 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/filetransfer/Socks5TransferNegotiator.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/filetransfer/Socks5TransferNegotiator.java @@ -21,8 +21,11 @@ import java.io.InputStream; import java.io.OutputStream; import java.io.PushbackInputStream; +import org.jivesoftware.smack.SmackException; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.filter.AndFilter; import org.jivesoftware.smack.filter.FromMatchesFilter; import org.jivesoftware.smack.filter.PacketFilter; @@ -54,22 +57,22 @@ public class Socks5TransferNegotiator extends StreamNegotiator { } @Override - public OutputStream createOutgoingStream(String streamID, String initiator, String target) - throws XMPPException { + public OutputStream createOutgoingStream(String streamID, String initiator, String target) throws NoResponseException, SmackException, XMPPException + { try { return this.manager.establishSession(target, streamID).getOutputStream(); } catch (IOException e) { - throw new XMPPException("error establishing SOCKS5 Bytestream", e); + throw new SmackException("error establishing SOCKS5 Bytestream", e); } catch (InterruptedException e) { - throw new XMPPException("error establishing SOCKS5 Bytestream", e); + throw new SmackException("error establishing SOCKS5 Bytestream", e); } } @Override - public InputStream createIncomingStream(StreamInitiation initiation) throws XMPPException, - InterruptedException { + public InputStream createIncomingStream(StreamInitiation initiation) throws XMPPErrorException, + InterruptedException, SmackException { /* * SOCKS5 initiation listener must ignore next SOCKS5 Bytestream request with given session * ID @@ -98,8 +101,8 @@ public class Socks5TransferNegotiator extends StreamNegotiator { } @Override - InputStream negotiateIncomingStream(Packet streamInitiation) throws XMPPException, - InterruptedException { + InputStream negotiateIncomingStream(Packet streamInitiation) throws InterruptedException, + SmackException, XMPPErrorException { // build SOCKS5 Bytestream request Socks5BytestreamRequest request = new ByteStreamRequest(this.manager, (Bytestream) streamInitiation); @@ -115,7 +118,7 @@ public class Socks5TransferNegotiator extends StreamNegotiator { return stream; } catch (IOException e) { - throw new XMPPException("Error establishing input stream", e); + throw new SmackException("Error establishing input stream", e); } } diff --git a/extensions/src/main/java/org/jivesoftware/smackx/filetransfer/StreamNegotiator.java b/extensions/src/main/java/org/jivesoftware/smackx/filetransfer/StreamNegotiator.java index 72fd4c603..728bca740 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/filetransfer/StreamNegotiator.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/filetransfer/StreamNegotiator.java @@ -17,8 +17,11 @@ package org.jivesoftware.smackx.filetransfer; import org.jivesoftware.smack.PacketCollector; +import org.jivesoftware.smack.SmackException; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.filter.PacketFilter; import org.jivesoftware.smack.packet.IQ; import org.jivesoftware.smack.packet.Packet; @@ -77,7 +80,7 @@ public abstract class StreamNegotiator { return iq; } - Packet initiateIncomingStream(XMPPConnection connection, StreamInitiation initiation) throws XMPPException { + Packet initiateIncomingStream(XMPPConnection connection, StreamInitiation initiation) throws NoResponseException, XMPPErrorException { StreamInitiation response = createInitiationAccept(initiation, getNamespaces()); @@ -86,11 +89,7 @@ public abstract class StreamNegotiator { .createPacketCollector(getInitiationPacketFilter(initiation.getFrom(), initiation.getSessionID())); connection.sendPacket(response); - Packet streamMethodInitiation = collector.nextResult(); - collector.cancel(); - if (streamMethodInitiation == null) { - throw new XMPPException("No response from file transfer initiator"); - } + Packet streamMethodInitiation = collector.nextResultOrThrow(); return streamMethodInitiation; } @@ -107,8 +106,8 @@ public abstract class StreamNegotiator { public abstract PacketFilter getInitiationPacketFilter(String from, String streamID); - abstract InputStream negotiateIncomingStream(Packet streamInitiation) throws XMPPException, - InterruptedException; + abstract InputStream negotiateIncomingStream(Packet streamInitiation) throws XMPPErrorException, + InterruptedException, NoResponseException, SmackException; /** * This method handles the file stream download negotiation process. The @@ -121,12 +120,13 @@ public abstract class StreamNegotiator { * @param initiation The initiation that triggered this download. * @return After the negotiation process is complete, the InputStream to * write a file to is returned. - * @throws XMPPException If an error occurs during this process an XMPPException is + * @throws XMPPErrorException If an error occurs during this process an XMPPException is * thrown. * @throws InterruptedException If thread is interrupted. + * @throws SmackException */ public abstract InputStream createIncomingStream(StreamInitiation initiation) - throws XMPPException, InterruptedException; + throws XMPPErrorException, InterruptedException, NoResponseException, SmackException; /** * This method handles the file upload stream negotiation process. The @@ -139,11 +139,13 @@ public abstract class StreamNegotiator { * @param target The fully-qualified JID of the target or receiver of the file * transfer. * @return The negotiated stream ready for data. - * @throws XMPPException If an error occurs during the negotiation process an + * @throws XMPPErrorException If an error occurs during the negotiation process an * exception will be thrown. + * @throws SmackException + * @throws XMPPException */ public abstract OutputStream createOutgoingStream(String streamID, - String initiator, String target) throws XMPPException; + String initiator, String target) throws XMPPErrorException, NoResponseException, SmackException, XMPPException; /** * Returns the XMPP namespace reserved for this particular type of file diff --git a/extensions/src/main/java/org/jivesoftware/smackx/iqlast/LastActivityManager.java b/extensions/src/main/java/org/jivesoftware/smackx/iqlast/LastActivityManager.java index fb664793f..512a80aa9 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/iqlast/LastActivityManager.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/iqlast/LastActivityManager.java @@ -17,10 +17,13 @@ package org.jivesoftware.smackx.iqlast; +import org.jivesoftware.smack.SmackException; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.ConnectionCreationListener; import org.jivesoftware.smack.PacketListener; import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.filter.AndFilter; import org.jivesoftware.smack.filter.IQTypeFilter; import org.jivesoftware.smack.filter.PacketTypeFilter; @@ -189,10 +192,12 @@ public class LastActivityManager { * @param jid * the JID of the user. * @return the LastActivity packet of the jid. - * @throws XMPPException + * @throws XMPPErrorException * thrown if a server error has occured. + * @throws NoResponseException if there was no response from the server. */ - public static LastActivity getLastActivity(XMPPConnection con, String jid) throws XMPPException { + public static LastActivity getLastActivity(XMPPConnection con, String jid) + throws NoResponseException, XMPPErrorException { LastActivity activity = new LastActivity(); activity.setTo(jid); @@ -206,8 +211,9 @@ public class LastActivityManager { * @param connection the connection to be used * @param jid a JID to be tested for Last Activity support * @return true if Last Activity is supported, otherwise false + * @throws SmackException if there was no response from the server. */ - public static boolean isLastActivitySupported(XMPPConnection connection, String jid) { + public static boolean isLastActivitySupported(XMPPConnection connection, String jid) throws SmackException { try { DiscoverInfo result = ServiceDiscoveryManager.getInstanceFor(connection).discoverInfo(jid); diff --git a/extensions/src/main/java/org/jivesoftware/smackx/iqlast/packet/LastActivity.java b/extensions/src/main/java/org/jivesoftware/smackx/iqlast/packet/LastActivity.java index 081d044a9..c6478898f 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/iqlast/packet/LastActivity.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/iqlast/packet/LastActivity.java @@ -19,11 +19,9 @@ package org.jivesoftware.smackx.iqlast.packet; import java.io.IOException; -import org.jivesoftware.smack.XMPPConnection; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smack.packet.IQ; import org.jivesoftware.smack.provider.IQProvider; -import org.jivesoftware.smack.util.StringUtils; import org.xmlpull.v1.XmlPullParser; import org.xmlpull.v1.XmlPullParserException; @@ -98,9 +96,9 @@ public class LastActivity extends IQ { super(); } - public IQ parseIQ(XmlPullParser parser) throws XMPPException, XmlPullParserException { + public IQ parseIQ(XmlPullParser parser) throws SmackException, XmlPullParserException { if (parser.getEventType() != XmlPullParser.START_TAG) { - throw new XMPPException("Parser not in proper position, or bad XML."); + throw new SmackException("Parser not in proper position, or bad XML."); } LastActivity lastActivity = new LastActivity(); @@ -125,22 +123,4 @@ public class LastActivity extends IQ { return lastActivity; } } - - /** - * Retrieve the last activity of a particular jid. - * @param con the current XMPPConnection. - * @param jid the JID of the user. - * @return the LastActivity packet of the jid. - * @throws XMPPException thrown if a server error has occured. - * @deprecated This method only retreives the lapsed time since the last logout of a particular jid. - * Replaced by {@link org.jivesoftware.smackx.iqlast.LastActivityManager#getLastActivity(XMPPConnection, String) getLastActivity} - */ - public static LastActivity getLastActivity(XMPPConnection con, String jid) throws XMPPException { - LastActivity activity = new LastActivity(); - jid = StringUtils.parseBareAddress(jid); - activity.setTo(jid); - - LastActivity response = (LastActivity) con.createPacketCollectorAndSend(activity).nextResultOrThrow(); - return response; - } } diff --git a/extensions/src/main/java/org/jivesoftware/smackx/iqprivate/PrivateDataManager.java b/extensions/src/main/java/org/jivesoftware/smackx/iqprivate/PrivateDataManager.java index a0d79c32e..2ac51d131 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/iqprivate/PrivateDataManager.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/iqprivate/PrivateDataManager.java @@ -17,8 +17,9 @@ package org.jivesoftware.smackx.iqprivate; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.packet.IQ; import org.jivesoftware.smack.provider.IQProvider; import org.jivesoftware.smackx.iqprivate.packet.DefaultPrivateData; @@ -167,10 +168,10 @@ public class PrivateDataManager { * @param elementName the element name. * @param namespace the namespace. * @return the private data. - * @throws XMPPException if an error occurs getting the private data. + * @throws XMPPErrorException + * @throws NoResponseException */ - public PrivateData getPrivateData(final String elementName, final String namespace) - throws XMPPException + public PrivateData getPrivateData(final String elementName, final String namespace) throws NoResponseException, XMPPErrorException { // Create an IQ packet to get the private data. IQ privateDataGet = new IQ() { @@ -199,9 +200,10 @@ public class PrivateDataManager { * element name and namespace, then the new private data will overwrite the old value. * * @param privateData the private data. - * @throws XMPPException if setting the private data fails. + * @throws XMPPErrorException + * @throws NoResponseException */ - public void setPrivateData(final PrivateData privateData) throws XMPPException { + public void setPrivateData(final PrivateData privateData) throws NoResponseException, XMPPErrorException { // Create an IQ packet to set the private data. IQ privateDataSet = new IQ() { public String getChildElementXML() { diff --git a/extensions/src/main/java/org/jivesoftware/smackx/muc/MultiUserChat.java b/extensions/src/main/java/org/jivesoftware/smackx/muc/MultiUserChat.java index 564277519..1993453b0 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/muc/MultiUserChat.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/muc/MultiUserChat.java @@ -40,8 +40,11 @@ import org.jivesoftware.smack.PacketCollector; import org.jivesoftware.smack.PacketInterceptor; import org.jivesoftware.smack.PacketListener; import org.jivesoftware.smack.SmackConfiguration; +import org.jivesoftware.smack.SmackException; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.filter.AndFilter; import org.jivesoftware.smack.filter.FromMatchesFilter; import org.jivesoftware.smack.filter.MessageTypeFilter; @@ -175,17 +178,13 @@ public class MultiUserChat { * @param connection the connection to use to perform the service discovery. * @param user the user to check. A fully qualified xmpp ID, e.g. jdoe@example.com. * @return a boolean indicating whether the specified user supports the MUC protocol. + * @throws XMPPErrorException + * @throws NoResponseException */ - public static boolean isServiceEnabled(XMPPConnection connection, String user) { - try { - DiscoverInfo result = - ServiceDiscoveryManager.getInstanceFor(connection).discoverInfo(user); - return result.containsFeature(discoNamespace); - } - catch (XMPPException e) { - LOGGER.log(Level.SEVERE, "Error checking user [" + user + "] for MUC support", e); - return false; - } + public static boolean isServiceEnabled(XMPPConnection connection, String user) + throws NoResponseException, XMPPErrorException { + return ServiceDiscoveryManager.getInstanceFor(connection).supportsFeature(user, + discoNamespace); } /** @@ -212,24 +211,20 @@ public class MultiUserChat { * @param connection the connection to use to perform the service discovery. * @param user the user to check. A fully qualified xmpp ID, e.g. jdoe@example.com. * @return an Iterator on the rooms where the requested user has joined. + * @throws XMPPErrorException + * @throws NoResponseException */ - public static Iterator getJoinedRooms(XMPPConnection connection, String user) { - try { - ArrayList answer = new ArrayList(); - // Send the disco packet to the user - DiscoverItems result = - ServiceDiscoveryManager.getInstanceFor(connection).discoverItems(user, discoNode); - // Collect the entityID for each returned item - for (Iterator items=result.getItems(); items.hasNext();) { - answer.add(items.next().getEntityID()); - } - return answer.iterator(); - } - catch (XMPPException e) { - LOGGER.log(Level.SEVERE, "Error getting joined rooms for user [" + user + "]", e); - // Return an iterator on an empty collection - return new ArrayList().iterator(); + public static Iterator getJoinedRooms(XMPPConnection connection, String user) + throws NoResponseException, XMPPErrorException { + ArrayList answer = new ArrayList(); + // Send the disco packet to the user + DiscoverItems result = ServiceDiscoveryManager.getInstanceFor(connection).discoverItems( + user, discoNode); + // Collect the entityID for each returned item + for (Iterator items = result.getItems(); items.hasNext();) { + answer.add(items.next().getEntityID()); } + return answer.iterator(); } /** @@ -240,10 +235,11 @@ public class MultiUserChat { * @param room the name of the room in the form "roomName@service" of which we want to discover * its information. * @return the discovered information of a given room without actually having to join the room. - * @throws XMPPException if an error occured while trying to discover information of a room. + * @throws XMPPErrorException + * @throws NoResponseException */ public static RoomInfo getRoomInfo(XMPPConnection connection, String room) - throws XMPPException { + throws NoResponseException, XMPPErrorException { DiscoverInfo info = ServiceDiscoveryManager.getInstanceFor(connection).discoverInfo(room); return new RoomInfo(info); } @@ -253,23 +249,18 @@ public class MultiUserChat { * * @param connection the XMPP connection to use for discovering Multi-User Chat services. * @return a collection with the XMPP addresses of the Multi-User Chat services. - * @throws XMPPException if an error occured while trying to discover MUC services. + * @throws XMPPErrorException + * @throws NoResponseException */ - public static Collection getServiceNames(XMPPConnection connection) throws XMPPException { + public static Collection getServiceNames(XMPPConnection connection) throws NoResponseException, XMPPErrorException { final List answer = new ArrayList(); ServiceDiscoveryManager discoManager = ServiceDiscoveryManager.getInstanceFor(connection); DiscoverItems items = discoManager.discoverItems(connection.getServiceName()); for (Iterator it = items.getItems(); it.hasNext();) { DiscoverItems.Item item = it.next(); - try { - DiscoverInfo info = discoManager.discoverInfo(item.getEntityID()); - if (info.containsFeature("http://jabber.org/protocol/muc")) { - answer.add(item.getEntityID()); - } - } - catch (XMPPException e) { - // Trouble finding info in some cases. This is a workaround for - // discovering info on remote servers. + DiscoverInfo info = discoManager.discoverInfo(item.getEntityID()); + if (info.containsFeature(discoNamespace)) { + answer.add(item.getEntityID()); } } return answer; @@ -283,10 +274,11 @@ public class MultiUserChat { * @param connection the XMPP connection to use for discovering hosted rooms by the MUC service. * @param serviceName the service that is hosting the rooms to discover. * @return a collection of HostedRooms. - * @throws XMPPException if an error occured while trying to discover the information. + * @throws XMPPErrorException + * @throws NoResponseException */ - public static Collection getHostedRooms(XMPPConnection connection, String serviceName) - throws XMPPException { + public static Collection getHostedRooms(XMPPConnection connection, + String serviceName) throws NoResponseException, XMPPErrorException { List answer = new ArrayList(); ServiceDiscoveryManager discoManager = ServiceDiscoveryManager.getInstanceFor(connection); DiscoverItems items = discoManager.discoverItems(serviceName); @@ -321,11 +313,13 @@ public class MultiUserChat { * will unlock the room. {@link #sendConfigurationForm(Form)} * * @param nickname the nickname to use. - * @throws XMPPException if the room couldn't be created for some reason + * @throws XMPPErrorException if the room couldn't be created for some reason * (e.g. room already exists; user already joined to an existant room or * 405 error if the user is not allowed to create the room) + * @throws NoResponseException if there was no response from the server. + * @throws SmackException If the creation failed because of a missing acknowledge from the server. */ - public synchronized void create(String nickname) throws XMPPException { + public synchronized void create(String nickname) throws NoResponseException, XMPPErrorException, SmackException { if (nickname == null || nickname.equals("")) { throw new IllegalArgumentException("Nickname must not be null or blank."); } @@ -371,7 +365,7 @@ public class MultiUserChat { } // We need to leave the room since it seems that the room already existed leave(); - throw new XMPPException("Creation failed - Missing acknowledge of room creation."); + throw new SmackException("Creation failed - Missing acknowledge of room creation."); } /** @@ -382,14 +376,16 @@ public class MultiUserChat { * joining the room, the room will decide the amount of history to send. * * @param nickname the nickname to use. - * @throws XMPPException if an error occurs joining the room. In particular, a + * @throws NoResponseException + * @throws XMPPErrorException if an error occurs joining the room. In particular, a * 401 error can occur if no password was provided and one is required; or a * 403 error can occur if the user is banned; or a * 404 error can occur if the room does not exist or is locked; or a * 407 error can occur if user is not on the member list; or a * 409 error can occur if someone is already in the group chat with the same nickname. + * @throws NoResponseException if there was no response from the server. */ - public void join(String nickname) throws XMPPException { + public void join(String nickname) throws NoResponseException, XMPPErrorException { join(nickname, null, null, SmackConfiguration.getDefaultPacketReplyTimeout()); } @@ -405,14 +401,15 @@ public class MultiUserChat { * * @param nickname the nickname to use. * @param password the password to use. - * @throws XMPPException if an error occurs joining the room. In particular, a + * @throws XMPPErrorException if an error occurs joining the room. In particular, a * 401 error can occur if no password was provided and one is required; or a * 403 error can occur if the user is banned; or a * 404 error can occur if the room does not exist or is locked; or a * 407 error can occur if user is not on the member list; or a * 409 error can occur if someone is already in the group chat with the same nickname. + * @throws SmackException if there was no response from the server. */ - public void join(String nickname, String password) throws XMPPException { + public void join(String nickname, String password) throws XMPPErrorException, SmackException { join(nickname, password, null, SmackConfiguration.getDefaultPacketReplyTimeout()); } @@ -434,19 +431,20 @@ public class MultiUserChat { * @param password the password to use. * @param history the amount of discussion history to receive while joining a room. * @param timeout the amount of time to wait for a reply from the MUC service(in milleseconds). - * @throws XMPPException if an error occurs joining the room. In particular, a + * @throws XMPPErrorException if an error occurs joining the room. In particular, a * 401 error can occur if no password was provided and one is required; or a * 403 error can occur if the user is banned; or a * 404 error can occur if the room does not exist or is locked; or a * 407 error can occur if user is not on the member list; or a * 409 error can occur if someone is already in the group chat with the same nickname. + * @throws NoResponseException if there was no response from the server. */ public synchronized void join( String nickname, String password, DiscussionHistory history, long timeout) - throws XMPPException { + throws XMPPErrorException, NoResponseException { if (nickname == null || nickname.equals("")) { throw new IllegalArgumentException("Nickname must not be null or blank."); } @@ -533,9 +531,10 @@ public class MultiUserChat { * * @return the Form that contains the fields to complete together with the instrucions or * null if no configuration is possible. - * @throws XMPPException if an error occurs asking the configuration form for the room. + * @throws XMPPErrorException if an error occurs asking the configuration form for the room. + * @throws NoResponseException if there was no response from the server. */ - public Form getConfigurationForm() throws XMPPException { + public Form getConfigurationForm() throws NoResponseException, XMPPErrorException { MUCOwner iq = new MUCOwner(); iq.setTo(room); iq.setType(IQ.Type.GET); @@ -550,9 +549,10 @@ public class MultiUserChat { * will create an instant room (will use default configuration). * * @param form the form with the new settings. - * @throws XMPPException if an error occurs setting the new rooms' configuration. + * @throws XMPPErrorException if an error occurs setting the new rooms' configuration. + * @throws NoResponseException if there was no response from the server. */ - public void sendConfigurationForm(Form form) throws XMPPException { + public void sendConfigurationForm(Form form) throws NoResponseException, XMPPErrorException { MUCOwner iq = new MUCOwner(); iq.setTo(room); iq.setType(IQ.Type.SET); @@ -572,10 +572,11 @@ public class MultiUserChat { * * @return the registration Form that contains the fields to complete together with the * instrucions or null if no registration is possible. - * @throws XMPPException if an error occurs asking the registration form for the room or a + * @throws XMPPErrorException if an error occurs asking the registration form for the room or a * 405 error if the user is not allowed to register with the room. + * @throws NoResponseException if there was no response from the server. */ - public Form getRegistrationForm() throws XMPPException { + public Form getRegistrationForm() throws NoResponseException, XMPPErrorException { Registration reg = new Registration(); reg.setType(IQ.Type.GET); reg.setTo(room); @@ -594,11 +595,12 @@ public class MultiUserChat { * it will return a "Service Unavailable" error to the user (error code 503). * * @param form the completed registration form. - * @throws XMPPException if an error occurs submitting the registration form. In particular, a + * @throws XMPPErrorException if an error occurs submitting the registration form. In particular, a * 409 error can occur if the desired room nickname is already reserved for that room; * or a 503 error can occur if the room does not support registration. + * @throws NoResponseException if there was no response from the server. */ - public void sendRegistrationForm(Form form) throws XMPPException { + public void sendRegistrationForm(Form form) throws NoResponseException, XMPPErrorException { Registration reg = new Registration(); reg.setType(IQ.Type.SET); reg.setTo(room); @@ -614,12 +616,13 @@ public class MultiUserChat { * * @param reason the reason for the room destruction. * @param alternateJID the JID of an alternate location. - * @throws XMPPException if an error occurs while trying to destroy the room. + * @throws XMPPErrorException if an error occurs while trying to destroy the room. * An error can occur which will be wrapped by an XMPPException -- * XMPP error code 403. The error code can be used to present more * appropiate error messages to end-users. + * @throws NoResponseException if there was no response from the server. */ - public void destroy(String reason, String alternateJID) throws XMPPException { + public void destroy(String reason, String alternateJID) throws NoResponseException, XMPPErrorException { MUCOwner iq = new MUCOwner(); iq.setTo(room); iq.setType(IQ.Type.SET); @@ -855,8 +858,9 @@ public class MultiUserChat { * to enter the room. * * @return the reserved room nickname or null if none. + * @throws SmackException if there was no response from the server. */ - public String getReservedNickname() { + public String getReservedNickname() throws SmackException { try { DiscoverInfo result = ServiceDiscoveryManager.getInstanceFor(connection).discoverInfo( @@ -894,9 +898,10 @@ public class MultiUserChat { * status code 303 indicates that the occupant is changing his/her nickname. * * @param nickname the new nickname within the room. - * @throws XMPPException if the new nickname is already in use by another occupant. + * @throws XMPPErrorException if the new nickname is already in use by another occupant. + * @throws NoResponseException if there was no response from the server. */ - public void changeNickname(String nickname) throws XMPPException { + public void changeNickname(String nickname) throws NoResponseException, XMPPErrorException { if (nickname == null || nickname.equals("")) { throw new IllegalArgumentException("Nickname must not be null or blank."); } @@ -974,14 +979,15 @@ public class MultiUserChat { * @param nickname the nickname of the participant or visitor to kick from the room * (e.g. "john"). * @param reason the reason why the participant or visitor is being kicked from the room. - * @throws XMPPException if an error occurs kicking the occupant. In particular, a + * @throws XMPPErrorException if an error occurs kicking the occupant. In particular, a * 405 error can occur if a moderator or a user with an affiliation of "owner" or "admin" * was intended to be kicked (i.e. Not Allowed error); or a * 403 error can occur if the occupant that intended to kick another occupant does * not have kicking privileges (i.e. Forbidden error); or a * 400 error can occur if the provided nickname is not present in the room. + * @throws NoResponseException if there was no response from the server. */ - public void kickParticipant(String nickname, String reason) throws XMPPException { + public void kickParticipant(String nickname, String reason) throws XMPPErrorException, NoResponseException { changeRole(nickname, "none", reason); } @@ -991,12 +997,13 @@ public class MultiUserChat { * is able to send messages to the room occupants. * * @param nicknames the nicknames of the visitors to grant voice in the room (e.g. "john"). - * @throws XMPPException if an error occurs granting voice to a visitor. In particular, a + * @throws XMPPErrorException if an error occurs granting voice to a visitor. In particular, a * 403 error can occur if the occupant that intended to grant voice is not * a moderator in this room (i.e. Forbidden error); or a * 400 error can occur if the provided nickname is not present in the room. + * @throws NoResponseException if there was no response from the server. */ - public void grantVoice(Collection nicknames) throws XMPPException { + public void grantVoice(Collection nicknames) throws XMPPErrorException, NoResponseException { changeRole(nicknames, "participant"); } @@ -1006,12 +1013,13 @@ public class MultiUserChat { * is able to send messages to the room occupants. * * @param nickname the nickname of the visitor to grant voice in the room (e.g. "john"). - * @throws XMPPException if an error occurs granting voice to a visitor. In particular, a + * @throws XMPPErrorException if an error occurs granting voice to a visitor. In particular, a * 403 error can occur if the occupant that intended to grant voice is not * a moderator in this room (i.e. Forbidden error); or a * 400 error can occur if the provided nickname is not present in the room. + * @throws NoResponseException if there was no response from the server. */ - public void grantVoice(String nickname) throws XMPPException { + public void grantVoice(String nickname) throws XMPPErrorException, NoResponseException { changeRole(nickname, "participant", null); } @@ -1021,12 +1029,13 @@ public class MultiUserChat { * is able to send messages to the room occupants. * * @param nicknames the nicknames of the participants to revoke voice (e.g. "john"). - * @throws XMPPException if an error occurs revoking voice from a participant. In particular, a + * @throws XMPPErrorException if an error occurs revoking voice from a participant. In particular, a * 405 error can occur if a moderator or a user with an affiliation of "owner" or "admin" * was tried to revoke his voice (i.e. Not Allowed error); or a * 400 error can occur if the provided nickname is not present in the room. + * @throws NoResponseException if there was no response from the server. */ - public void revokeVoice(Collection nicknames) throws XMPPException { + public void revokeVoice(Collection nicknames) throws XMPPErrorException, NoResponseException { changeRole(nicknames, "visitor"); } @@ -1036,12 +1045,13 @@ public class MultiUserChat { * is able to send messages to the room occupants. * * @param nickname the nickname of the participant to revoke voice (e.g. "john"). - * @throws XMPPException if an error occurs revoking voice from a participant. In particular, a + * @throws XMPPErrorException if an error occurs revoking voice from a participant. In particular, a * 405 error can occur if a moderator or a user with an affiliation of "owner" or "admin" * was tried to revoke his voice (i.e. Not Allowed error); or a * 400 error can occur if the provided nickname is not present in the room. + * @throws NoResponseException if there was no response from the server. */ - public void revokeVoice(String nickname) throws XMPPException { + public void revokeVoice(String nickname) throws XMPPErrorException, NoResponseException { changeRole(nickname, "visitor", null); } @@ -1053,11 +1063,12 @@ public class MultiUserChat { * XMPP user ID of the user who initiated the ban. * * @param jids the bare XMPP user IDs of the users to ban. - * @throws XMPPException if an error occurs banning a user. In particular, a + * @throws XMPPErrorException if an error occurs banning a user. In particular, a * 405 error can occur if a moderator or a user with an affiliation of "owner" or "admin" * was tried to be banned (i.e. Not Allowed error). + * @throws NoResponseException if there was no response from the server. */ - public void banUsers(Collection jids) throws XMPPException { + public void banUsers(Collection jids) throws XMPPErrorException, NoResponseException { changeAffiliationByAdmin(jids, "outcast"); } @@ -1070,11 +1081,12 @@ public class MultiUserChat { * * @param jid the bare XMPP user ID of the user to ban (e.g. "user@host.org"). * @param reason the optional reason why the user was banned. - * @throws XMPPException if an error occurs banning a user. In particular, a + * @throws XMPPErrorException if an error occurs banning a user. In particular, a * 405 error can occur if a moderator or a user with an affiliation of "owner" or "admin" * was tried to be banned (i.e. Not Allowed error). + * @throws NoResponseException if there was no response from the server. */ - public void banUser(String jid, String reason) throws XMPPException { + public void banUser(String jid, String reason) throws XMPPErrorException, NoResponseException { changeAffiliationByAdmin(jid, "outcast", reason); } @@ -1084,9 +1096,10 @@ public class MultiUserChat { * that a user cannot enter without being on the member list). * * @param jids the XMPP user IDs of the users to grant membership. - * @throws XMPPException if an error occurs granting membership to a user. + * @throws XMPPErrorException if an error occurs granting membership to a user. + * @throws NoResponseException if there was no response from the server. */ - public void grantMembership(Collection jids) throws XMPPException { + public void grantMembership(Collection jids) throws XMPPErrorException, NoResponseException { changeAffiliationByAdmin(jids, "member"); } @@ -1096,9 +1109,10 @@ public class MultiUserChat { * that a user cannot enter without being on the member list). * * @param jid the XMPP user ID of the user to grant membership (e.g. "user@host.org"). - * @throws XMPPException if an error occurs granting membership to a user. + * @throws XMPPErrorException if an error occurs granting membership to a user. + * @throws NoResponseException if there was no response from the server. */ - public void grantMembership(String jid) throws XMPPException { + public void grantMembership(String jid) throws XMPPErrorException, NoResponseException { changeAffiliationByAdmin(jid, "member", null); } @@ -1109,9 +1123,10 @@ public class MultiUserChat { * the room is of type members-only then the user will be removed from the room. * * @param jids the bare XMPP user IDs of the users to revoke membership. - * @throws XMPPException if an error occurs revoking membership to a user. + * @throws XMPPErrorException if an error occurs revoking membership to a user. + * @throws NoResponseException if there was no response from the server. */ - public void revokeMembership(Collection jids) throws XMPPException { + public void revokeMembership(Collection jids) throws XMPPErrorException, NoResponseException { changeAffiliationByAdmin(jids, "none"); } @@ -1122,9 +1137,10 @@ public class MultiUserChat { * the room is of type members-only then the user will be removed from the room. * * @param jid the bare XMPP user ID of the user to revoke membership (e.g. "user@host.org"). - * @throws XMPPException if an error occurs revoking membership to a user. + * @throws XMPPErrorException if an error occurs revoking membership to a user. + * @throws NoResponseException if there was no response from the server. */ - public void revokeMembership(String jid) throws XMPPException { + public void revokeMembership(String jid) throws XMPPErrorException, NoResponseException { changeAffiliationByAdmin(jid, "none", null); } @@ -1134,9 +1150,10 @@ public class MultiUserChat { * other users, modify room's subject plus all the partcipants privileges. * * @param nicknames the nicknames of the occupants to grant moderator privileges. - * @throws XMPPException if an error occurs granting moderator privileges to a user. + * @throws XMPPErrorException if an error occurs granting moderator privileges to a user. + * @throws NoResponseException if there was no response from the server. */ - public void grantModerator(Collection nicknames) throws XMPPException { + public void grantModerator(Collection nicknames) throws XMPPErrorException, NoResponseException { changeRole(nicknames, "moderator"); } @@ -1146,9 +1163,10 @@ public class MultiUserChat { * other users, modify room's subject plus all the partcipants privileges. * * @param nickname the nickname of the occupant to grant moderator privileges. - * @throws XMPPException if an error occurs granting moderator privileges to a user. + * @throws XMPPErrorException if an error occurs granting moderator privileges to a user. + * @throws NoResponseException if there was no response from the server. */ - public void grantModerator(String nickname) throws XMPPException { + public void grantModerator(String nickname) throws XMPPErrorException, NoResponseException { changeRole(nickname, "moderator", null); } @@ -1159,9 +1177,10 @@ public class MultiUserChat { * not allowed to revoke moderator privileges from other room administrators or owners. * * @param nicknames the nicknames of the occupants to revoke moderator privileges. - * @throws XMPPException if an error occurs revoking moderator privileges from a user. + * @throws XMPPErrorException if an error occurs revoking moderator privileges from a user. + * @throws NoResponseException if there was no response from the server. */ - public void revokeModerator(Collection nicknames) throws XMPPException { + public void revokeModerator(Collection nicknames) throws XMPPErrorException, NoResponseException { changeRole(nicknames, "participant"); } @@ -1172,9 +1191,10 @@ public class MultiUserChat { * not allowed to revoke moderator privileges from other room administrators or owners. * * @param nickname the nickname of the occupant to revoke moderator privileges. - * @throws XMPPException if an error occurs revoking moderator privileges from a user. + * @throws XMPPErrorException if an error occurs revoking moderator privileges from a user. + * @throws NoResponseException if there was no response from the server. */ - public void revokeModerator(String nickname) throws XMPPException { + public void revokeModerator(String nickname) throws XMPPErrorException, NoResponseException { changeRole(nickname, "participant", null); } @@ -1185,9 +1205,10 @@ public class MultiUserChat { * functions. * * @param jids the collection of bare XMPP user IDs of the users to grant ownership. - * @throws XMPPException if an error occurs granting ownership privileges to a user. + * @throws XMPPErrorException if an error occurs granting ownership privileges to a user. + * @throws NoResponseException if there was no response from the server. */ - public void grantOwnership(Collection jids) throws XMPPException { + public void grantOwnership(Collection jids) throws XMPPErrorException, NoResponseException { changeAffiliationByAdmin(jids, "owner"); } @@ -1198,9 +1219,10 @@ public class MultiUserChat { * functions. * * @param jid the bare XMPP user ID of the user to grant ownership (e.g. "user@host.org"). - * @throws XMPPException if an error occurs granting ownership privileges to a user. + * @throws XMPPErrorException if an error occurs granting ownership privileges to a user. + * @throws NoResponseException if there was no response from the server. */ - public void grantOwnership(String jid) throws XMPPException { + public void grantOwnership(String jid) throws XMPPErrorException, NoResponseException { changeAffiliationByAdmin(jid, "owner", null); } @@ -1210,9 +1232,10 @@ public class MultiUserChat { * Some room implementations will not allow to grant ownership privileges to other users. * * @param jids the bare XMPP user IDs of the users to revoke ownership. - * @throws XMPPException if an error occurs revoking ownership privileges from a user. + * @throws XMPPErrorException if an error occurs revoking ownership privileges from a user. + * @throws NoResponseException if there was no response from the server. */ - public void revokeOwnership(Collection jids) throws XMPPException { + public void revokeOwnership(Collection jids) throws XMPPErrorException, NoResponseException { changeAffiliationByAdmin(jids, "admin"); } @@ -1222,9 +1245,10 @@ public class MultiUserChat { * Some room implementations will not allow to grant ownership privileges to other users. * * @param jid the bare XMPP user ID of the user to revoke ownership (e.g. "user@host.org"). - * @throws XMPPException if an error occurs revoking ownership privileges from a user. + * @throws XMPPErrorException if an error occurs revoking ownership privileges from a user. + * @throws NoResponseException if there was no response from the server. */ - public void revokeOwnership(String jid) throws XMPPException { + public void revokeOwnership(String jid) throws XMPPErrorException, NoResponseException { changeAffiliationByAdmin(jid, "admin", null); } @@ -1234,9 +1258,10 @@ public class MultiUserChat { * administrative functions such as banning users and edit moderator list. * * @param jids the bare XMPP user IDs of the users to grant administrator privileges. - * @throws XMPPException if an error occurs granting administrator privileges to a user. + * @throws XMPPErrorException if an error occurs granting administrator privileges to a user. + * @throws NoResponseException if there was no response from the server. */ - public void grantAdmin(Collection jids) throws XMPPException { + public void grantAdmin(Collection jids) throws XMPPErrorException, NoResponseException { changeAffiliationByOwner(jids, "admin"); } @@ -1247,9 +1272,10 @@ public class MultiUserChat { * * @param jid the bare XMPP user ID of the user to grant administrator privileges * (e.g. "user@host.org"). - * @throws XMPPException if an error occurs granting administrator privileges to a user. + * @throws XMPPErrorException if an error occurs granting administrator privileges to a user. + * @throws NoResponseException if there was no response from the server. */ - public void grantAdmin(String jid) throws XMPPException { + public void grantAdmin(String jid) throws XMPPErrorException, NoResponseException { changeAffiliationByOwner(jid, "admin"); } @@ -1259,9 +1285,10 @@ public class MultiUserChat { * a member or unaffiliated user. * * @param jids the bare XMPP user IDs of the user to revoke administrator privileges. - * @throws XMPPException if an error occurs revoking administrator privileges from a user. + * @throws XMPPErrorException if an error occurs revoking administrator privileges from a user. + * @throws NoResponseException if there was no response from the server. */ - public void revokeAdmin(Collection jids) throws XMPPException { + public void revokeAdmin(Collection jids) throws XMPPErrorException, NoResponseException { changeAffiliationByOwner(jids, "member"); } @@ -1272,13 +1299,15 @@ public class MultiUserChat { * * @param jid the bare XMPP user ID of the user to revoke administrator privileges * (e.g. "user@host.org"). - * @throws XMPPException if an error occurs revoking administrator privileges from a user. + * @throws XMPPErrorException if an error occurs revoking administrator privileges from a user. + * @throws NoResponseException if there was no response from the server. */ - public void revokeAdmin(String jid) throws XMPPException { + public void revokeAdmin(String jid) throws XMPPErrorException, NoResponseException { changeAffiliationByOwner(jid, "member"); } - private void changeAffiliationByOwner(String jid, String affiliation) throws XMPPException { + private void changeAffiliationByOwner(String jid, String affiliation) + throws XMPPErrorException, NoResponseException { MUCOwner iq = new MUCOwner(); iq.setTo(room); iq.setType(IQ.Type.SET); @@ -1291,7 +1320,7 @@ public class MultiUserChat { } private void changeAffiliationByOwner(Collection jids, String affiliation) - throws XMPPException { + throws NoResponseException, XMPPErrorException { MUCOwner iq = new MUCOwner(); iq.setTo(room); iq.setType(IQ.Type.SET); @@ -1311,10 +1340,11 @@ public class MultiUserChat { * @param jid * @param affiliation * @param reason the reason for the affiliation change (optional) - * @throws XMPPException + * @throws XMPPErrorException + * @throws NoResponseException */ - private void changeAffiliationByAdmin(String jid, String affiliation, String reason) - throws XMPPException { + private void changeAffiliationByAdmin(String jid, String affiliation, String reason) throws NoResponseException, XMPPErrorException + { MUCAdmin iq = new MUCAdmin(); iq.setTo(room); iq.setType(IQ.Type.SET); @@ -1328,7 +1358,7 @@ public class MultiUserChat { } private void changeAffiliationByAdmin(Collection jids, String affiliation) - throws XMPPException { + throws NoResponseException, XMPPErrorException { MUCAdmin iq = new MUCAdmin(); iq.setTo(room); iq.setType(IQ.Type.SET); @@ -1342,7 +1372,7 @@ public class MultiUserChat { connection.createPacketCollectorAndSend(iq).nextResultOrThrow(); } - private void changeRole(String nickname, String role, String reason) throws XMPPException { + private void changeRole(String nickname, String role, String reason) throws NoResponseException, XMPPErrorException { MUCAdmin iq = new MUCAdmin(); iq.setTo(room); iq.setType(IQ.Type.SET); @@ -1355,7 +1385,7 @@ public class MultiUserChat { connection.createPacketCollectorAndSend(iq).nextResultOrThrow(); } - private void changeRole(Collection nicknames, String role) throws XMPPException { + private void changeRole(Collection nicknames, String role) throws NoResponseException, XMPPErrorException { MUCAdmin iq = new MUCAdmin(); iq.setTo(room); iq.setType(IQ.Type.SET); @@ -1458,10 +1488,10 @@ public class MultiUserChat { * Returns a collection of Affiliate with the room owners. * * @return a collection of Affiliate with the room owners. - * @throws XMPPException if an error occured while performing the request to the server or you - * don't have enough privileges to get this information. + * @throws XMPPErrorException if you don't have enough privileges to get this information. + * @throws NoResponseException if there was no response from the server. */ - public Collection getOwners() throws XMPPException { + public Collection getOwners() throws NoResponseException, XMPPErrorException { return getAffiliatesByAdmin("owner"); } @@ -1469,10 +1499,10 @@ public class MultiUserChat { * Returns a collection of Affiliate with the room administrators. * * @return a collection of Affiliate with the room administrators. - * @throws XMPPException if an error occured while performing the request to the server or you - * don't have enough privileges to get this information. + * @throws XMPPErrorException if you don't have enough privileges to get this information. + * @throws NoResponseException if there was no response from the server. */ - public Collection getAdmins() throws XMPPException { + public Collection getAdmins() throws NoResponseException, XMPPErrorException { return getAffiliatesByAdmin("admin"); } @@ -1480,10 +1510,10 @@ public class MultiUserChat { * Returns a collection of Affiliate with the room members. * * @return a collection of Affiliate with the room members. - * @throws XMPPException if an error occured while performing the request to the server or you - * don't have enough privileges to get this information. + * @throws XMPPErrorException if you don't have enough privileges to get this information. + * @throws NoResponseException if there was no response from the server. */ - public Collection getMembers() throws XMPPException { + public Collection getMembers() throws NoResponseException, XMPPErrorException { return getAffiliatesByAdmin("member"); } @@ -1491,10 +1521,10 @@ public class MultiUserChat { * Returns a collection of Affiliate with the room outcasts. * * @return a collection of Affiliate with the room outcasts. - * @throws XMPPException if an error occured while performing the request to the server or you - * don't have enough privileges to get this information. + * @throws XMPPErrorException if you don't have enough privileges to get this information. + * @throws NoResponseException if there was no response from the server. */ - public Collection getOutcasts() throws XMPPException { + public Collection getOutcasts() throws NoResponseException, XMPPErrorException { return getAffiliatesByAdmin("outcast"); } @@ -1504,10 +1534,10 @@ public class MultiUserChat { * * @param affiliation the affiliation of the users in the room. * @return a collection of Affiliate that have the specified room affiliation. - * @throws XMPPException if an error occured while performing the request to the server or you - * don't have enough privileges to get this information. + * @throws XMPPErrorException if you don't have enough privileges to get this information. + * @throws NoResponseException if there was no response from the server. */ - private Collection getAffiliatesByAdmin(String affiliation) throws XMPPException { + private Collection getAffiliatesByAdmin(String affiliation) throws NoResponseException, XMPPErrorException { MUCAdmin iq = new MUCAdmin(); iq.setTo(room); iq.setType(IQ.Type.GET); @@ -1529,21 +1559,21 @@ public class MultiUserChat { * Returns a collection of Occupant with the room moderators. * * @return a collection of Occupant with the room moderators. - * @throws XMPPException if an error occured while performing the request to the server or you - * don't have enough privileges to get this information. + * @throws XMPPErrorException if you don't have enough privileges to get this information. + * @throws NoResponseException if there was no response from the server. */ - public Collection getModerators() throws XMPPException { + public Collection getModerators() throws NoResponseException, XMPPErrorException { return getOccupants("moderator"); } /** * Returns a collection of Occupant with the room participants. - * + * * @return a collection of Occupant with the room participants. - * @throws XMPPException if an error occured while performing the request to the server or you - * don't have enough privileges to get this information. + * @throws XMPPErrorException if you don't have enough privileges to get this information. + * @throws NoResponseException if there was no response from the server. */ - public Collection getParticipants() throws XMPPException { + public Collection getParticipants() throws NoResponseException, XMPPErrorException { return getOccupants("participant"); } @@ -1552,10 +1582,11 @@ public class MultiUserChat { * * @param role the role of the occupant in the room. * @return a collection of Occupant that have the specified room role. - * @throws XMPPException if an error occured while performing the request to the server or you + * @throws XMPPErrorException if an error occured while performing the request to the server or you * don't have enough privileges to get this information. + * @throws NoResponseException if there was no response from the server. */ - private Collection getOccupants(String role) throws XMPPException { + private Collection getOccupants(String role) throws NoResponseException, XMPPErrorException { MUCAdmin iq = new MUCAdmin(); iq.setTo(room); iq.setType(IQ.Type.GET); @@ -1689,10 +1720,11 @@ public class MultiUserChat { * allow a mere participant or even a visitor to change the subject. * * @param subject the new room's subject to set. - * @throws XMPPException if someone without appropriate privileges attempts to change the + * @throws XMPPErrorException if someone without appropriate privileges attempts to change the * room subject will throw an error with code 403 (i.e. Forbidden) + * @throws NoResponseException if there was no response from the server. */ - public void changeSubject(final String subject) throws XMPPException { + public void changeSubject(final String subject) throws NoResponseException, XMPPErrorException { Message message = new Message(room, Message.Type.groupchat); message.setSubject(subject); // Wait for an error or confirmation message back from the server. diff --git a/extensions/src/main/java/org/jivesoftware/smackx/offline/OfflineMessageManager.java b/extensions/src/main/java/org/jivesoftware/smackx/offline/OfflineMessageManager.java index d6aab29b3..be97e0104 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/offline/OfflineMessageManager.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/offline/OfflineMessageManager.java @@ -19,8 +19,9 @@ package org.jivesoftware.smackx.offline; import org.jivesoftware.smack.PacketCollector; import org.jivesoftware.smack.SmackConfiguration; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.filter.AndFilter; import org.jivesoftware.smack.filter.PacketExtensionFilter; import org.jivesoftware.smack.filter.PacketFilter; @@ -75,21 +76,22 @@ public class OfflineMessageManager { * messages, get specific messages, delete specific messages, etc. * * @return a boolean indicating if the server supports Flexible Offline Message Retrieval. - * @throws XMPPException If the user is not allowed to make this request. + * @throws XMPPErrorException If the user is not allowed to make this request. + * @throws NoResponseException if there was no response from the server. */ - public boolean supportsFlexibleRetrieval() throws XMPPException { - DiscoverInfo info = ServiceDiscoveryManager.getInstanceFor(connection).discoverInfo(null); - return info.containsFeature(namespace); + public boolean supportsFlexibleRetrieval() throws NoResponseException, XMPPErrorException { + return ServiceDiscoveryManager.getInstanceFor(connection).supportsFeature(connection.getServiceName(), namespace); } /** * Returns the number of offline messages for the user of the connection. * * @return the number of offline messages for the user of the connection. - * @throws XMPPException If the user is not allowed to make this request or the server does + * @throws XMPPErrorException If the user is not allowed to make this request or the server does * not support offline message retrieval. + * @throws NoResponseException if there was no response from the server. */ - public int getMessageCount() throws XMPPException { + public int getMessageCount() throws NoResponseException, XMPPErrorException { DiscoverInfo info = ServiceDiscoveryManager.getInstanceFor(connection).discoverInfo(null, namespace); Form extendedInfo = Form.getFormFrom(info); @@ -107,10 +109,11 @@ public class OfflineMessageManager { * * @return an iterator on OfflineMessageHeader that keep information about the offline * message. - * @throws XMPPException If the user is not allowed to make this request or the server does + * @throws XMPPErrorException If the user is not allowed to make this request or the server does * not support offline message retrieval. + * @throws NoResponseException if there was no response from the server. */ - public Iterator getHeaders() throws XMPPException { + public Iterator getHeaders() throws NoResponseException, XMPPErrorException { List answer = new ArrayList(); DiscoverItems items = ServiceDiscoveryManager.getInstanceFor(connection).discoverItems( null, namespace); @@ -130,10 +133,11 @@ public class OfflineMessageManager { * @param nodes the list of stamps that uniquely identifies offline message. * @return an Iterator with the offline Messages that were received as part of * this request. - * @throws XMPPException If the user is not allowed to make this request or the server does + * @throws XMPPErrorException If the user is not allowed to make this request or the server does * not support offline message retrieval. + * @throws NoResponseException if there was no response from the server. */ - public Iterator getMessages(final List nodes) throws XMPPException { + public Iterator getMessages(final List nodes) throws NoResponseException, XMPPErrorException { List messages = new ArrayList(); OfflineMessageRequest request = new OfflineMessageRequest(); for (String node : nodes) { @@ -170,10 +174,11 @@ public class OfflineMessageManager { * to delete the messages. * * @return an Iterator with all the offline Messages of the user. - * @throws XMPPException If the user is not allowed to make this request or the server does + * @throws XMPPErrorException If the user is not allowed to make this request or the server does * not support offline message retrieval. + * @throws NoResponseException if there was no response from the server. */ - public Iterator getMessages() throws XMPPException { + public Iterator getMessages() throws NoResponseException, XMPPErrorException { List messages = new ArrayList(); OfflineMessageRequest request = new OfflineMessageRequest(); request.setFetch(true); @@ -198,10 +203,11 @@ public class OfflineMessageManager { * stamps that uniquely identifies the offline messages to delete. * * @param nodes the list of stamps that uniquely identifies offline message. - * @throws XMPPException If the user is not allowed to make this request or the server does + * @throws XMPPErrorException If the user is not allowed to make this request or the server does * not support offline message retrieval. + * @throws NoResponseException if there was no response from the server. */ - public void deleteMessages(List nodes) throws XMPPException { + public void deleteMessages(List nodes) throws NoResponseException, XMPPErrorException { OfflineMessageRequest request = new OfflineMessageRequest(); for (String node : nodes) { OfflineMessageRequest.Item item = new OfflineMessageRequest.Item(node); @@ -214,10 +220,11 @@ public class OfflineMessageManager { /** * Deletes all offline messages of the user. * - * @throws XMPPException If the user is not allowed to make this request or the server does + * @throws XMPPErrorException If the user is not allowed to make this request or the server does * not support offline message retrieval. + * @throws NoResponseException if there was no response from the server. */ - public void deleteMessages() throws XMPPException { + public void deleteMessages() throws NoResponseException, XMPPErrorException { OfflineMessageRequest request = new OfflineMessageRequest(); request.setPurge(true); connection.createPacketCollectorAndSend(request).nextResultOrThrow(); diff --git a/extensions/src/main/java/org/jivesoftware/smackx/ping/PingManager.java b/extensions/src/main/java/org/jivesoftware/smackx/ping/PingManager.java index ec5944842..91e265863 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/ping/PingManager.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/ping/PingManager.java @@ -23,15 +23,18 @@ import java.util.Set; import java.util.WeakHashMap; import java.util.concurrent.ScheduledFuture; import java.util.concurrent.TimeUnit; +import java.util.logging.Level; import java.util.logging.Logger; +import org.jivesoftware.smack.SmackException; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.ConnectionCreationListener; import org.jivesoftware.smack.ConnectionListener; import org.jivesoftware.smack.Manager; import org.jivesoftware.smack.PacketListener; -import org.jivesoftware.smack.SmackError; import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.filter.AndFilter; import org.jivesoftware.smack.filter.IQTypeFilter; import org.jivesoftware.smack.filter.PacketFilter; @@ -163,14 +166,15 @@ public class PingManager extends Manager { * @param jid The id of the entity the ping is being sent to * @param pingTimeout The time to wait for a reply * @return true if a reply was received from the entity, false otherwise. + * @throws NoResponseException if there was no response from the server. */ - public boolean ping(String jid, long pingTimeout) { + public boolean ping(String jid, long pingTimeout) throws NoResponseException { Ping ping = new Ping(jid); try { connection().createPacketCollectorAndSend(ping).nextResultOrThrow(); } catch (XMPPException exc) { - return (jid.equals(connection().getServiceName()) && (exc.getSmackError() != SmackError.NO_RESPONSE_FROM_SERVER)); + return jid.equals(connection().getServiceName()); } return true; } @@ -181,8 +185,9 @@ public class PingManager extends Manager { * * @param jid The id of the entity the ping is being sent to * @return true if a reply was received from the entity, false otherwise. + * @throws SmackException if there was no response from the server. */ - public boolean ping(String jid) { + public boolean ping(String jid) throws SmackException { return ping(jid, connection().getPacketReplyTimeout()); } @@ -191,9 +196,10 @@ public class PingManager extends Manager { * * @param jid The id of the entity the query is being sent to * @return true if it supports ping, false otherwise. - * @throws XMPPException An XMPP related error occurred during the request + * @throws XMPPErrorException An XMPP related error occurred during the request + * @throws NoResponseException if there was no response from the server. */ - public boolean isPingSupported(String jid) throws XMPPException { + public boolean isPingSupported(String jid) throws NoResponseException, XMPPErrorException { return ServiceDiscoveryManager.getInstanceFor(connection()).supportsFeature(jid, PingManager.NAMESPACE); } @@ -205,8 +211,9 @@ public class PingManager extends Manager { * {@link #isPingSupported(String)} is false. * * @return true if a reply was received from the server, false otherwise. + * @throws SmackException if there was no response from the server. */ - public boolean pingMyServer() { + public boolean pingMyServer() throws SmackException { return pingMyServer(true); } @@ -219,8 +226,9 @@ public class PingManager extends Manager { * * @param notifyListeners Notify the PingFailedListener in case of error if true * @return true if the user's server could be pinged. + * @throws SmackException if there was no response from the server. */ - public boolean pingMyServer(boolean notifyListeners) { + public boolean pingMyServer(boolean notifyListeners) throws SmackException { boolean res = ping(connection().getServiceName()); if (res) { pongReceived(); @@ -327,7 +335,13 @@ public class PingManager extends Manager { return; } } - res = pingMyServer(false); + try { + res = pingMyServer(false); + } + catch (SmackException e) { + LOGGER.log(Level.WARNING, "SmackError while pinging server", e); + res = false; + } // stop when we receive a pong back if (res) { lastSuccessfulAutomaticPing = System.currentTimeMillis(); diff --git a/extensions/src/main/java/org/jivesoftware/smackx/privacy/PrivacyListManager.java b/extensions/src/main/java/org/jivesoftware/smackx/privacy/PrivacyListManager.java index b8ce18d79..033f6f439 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/privacy/PrivacyListManager.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/privacy/PrivacyListManager.java @@ -23,11 +23,12 @@ import java.util.Map; import java.util.Set; import java.util.WeakHashMap; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.ConnectionCreationListener; import org.jivesoftware.smack.Manager; import org.jivesoftware.smack.PacketListener; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.filter.AndFilter; import org.jivesoftware.smack.filter.IQTypeFilter; import org.jivesoftware.smack.filter.PacketExtensionFilter; @@ -139,9 +140,10 @@ public class PrivacyListManager extends Manager { * @param requestPrivacy is the {@link Privacy} packet configured properly whose XML * will be sent to the server. * @return a new {@link Privacy} with the data received from the server. - * @exception XMPPException if the request or the answer failed, it raises an exception. + * @throws XMPPErrorException + * @throws NoResponseException */ - private Privacy getRequest(Privacy requestPrivacy) throws XMPPException { + private Privacy getRequest(Privacy requestPrivacy) throws NoResponseException, XMPPErrorException { // The request is a get iq type requestPrivacy.setType(Privacy.Type.GET); requestPrivacy.setFrom(this.getUser()); @@ -157,9 +159,10 @@ public class PrivacyListManager extends Manager { * @param requestPrivacy is the {@link Privacy} packet configured properly whose xml will be * sent to the server. * @return a new {@link Privacy} with the data received from the server. - * @exception XMPPException if the request or the answer failed, it raises an exception. + * @throws XMPPErrorException + * @throws NoResponseException */ - private Packet setRequest(Privacy requestPrivacy) throws XMPPException { + private Packet setRequest(Privacy requestPrivacy) throws NoResponseException, XMPPErrorException { // The request is a get iq type requestPrivacy.setType(Privacy.Type.SET); requestPrivacy.setFrom(this.getUser()); @@ -171,9 +174,10 @@ public class PrivacyListManager extends Manager { * Answer a privacy containing the list structure without {@link PrivacyItem}. * * @return a Privacy with the list names. - * @throws XMPPException if an error occurs. + * @throws XMPPErrorException + * @throws NoResponseException */ - private Privacy getPrivacyWithListNames() throws XMPPException { + private Privacy getPrivacyWithListNames() throws NoResponseException, XMPPErrorException { // The request of the list is an empty privacy message Privacy request = new Privacy(); @@ -185,9 +189,10 @@ public class PrivacyListManager extends Manager { * Answer the active privacy list. * * @return the privacy list of the active list. - * @throws XMPPException if an error occurs. + * @throws XMPPErrorException + * @throws NoResponseException */ - public PrivacyList getActiveList() throws XMPPException { + public PrivacyList getActiveList() throws NoResponseException, XMPPErrorException { Privacy privacyAnswer = this.getPrivacyWithListNames(); String listName = privacyAnswer.getActiveName(); boolean isDefaultAndActive = privacyAnswer.getActiveName() != null @@ -201,9 +206,10 @@ public class PrivacyListManager extends Manager { * Answer the default privacy list. * * @return the privacy list of the default list. - * @throws XMPPException if an error occurs. + * @throws XMPPErrorException + * @throws NoResponseException */ - public PrivacyList getDefaultList() throws XMPPException { + public PrivacyList getDefaultList() throws NoResponseException, XMPPErrorException { Privacy privacyAnswer = this.getPrivacyWithListNames(); String listName = privacyAnswer.getDefaultName(); boolean isDefaultAndActive = privacyAnswer.getActiveName() != null @@ -218,9 +224,10 @@ public class PrivacyListManager extends Manager { * * @param listName the name of the list to get the allowed and blocked permissions. * @return a list of privacy items under the list listName. - * @throws XMPPException if an error occurs. + * @throws XMPPErrorException + * @throws NoResponseException */ - private List getPrivacyListItems(String listName) throws XMPPException { + private List getPrivacyListItems(String listName) throws NoResponseException, XMPPErrorException { // The request of the list is an privacy message with an empty list Privacy request = new Privacy(); request.setPrivacyList(listName, new ArrayList()); @@ -236,9 +243,10 @@ public class PrivacyListManager extends Manager { * * @param listName the name of the list to get the allowed and blocked permissions. * @return a privacy list under the list listName. - * @throws XMPPException if an error occurs. + * @throws XMPPErrorException + * @throws NoResponseException */ - public PrivacyList getPrivacyList(String listName) throws XMPPException { + public PrivacyList getPrivacyList(String listName) throws NoResponseException, XMPPErrorException { return new PrivacyList(false, false, listName, getPrivacyListItems(listName)); } @@ -246,9 +254,10 @@ public class PrivacyListManager extends Manager { * Answer every privacy list with the allowed and blocked permissions. * * @return an array of privacy lists. - * @throws XMPPException if an error occurs. + * @throws XMPPErrorException + * @throws NoResponseException */ - public PrivacyList[] getPrivacyLists() throws XMPPException { + public PrivacyList[] getPrivacyLists() throws NoResponseException, XMPPErrorException { Privacy privacyAnswer = this.getPrivacyWithListNames(); Set names = privacyAnswer.getPrivacyListNames(); PrivacyList[] lists = new PrivacyList[names.size()]; @@ -269,9 +278,10 @@ public class PrivacyListManager extends Manager { * Set or change the active list to listName. * * @param listName the list name to set as the active one. - * @exception XMPPException if the request or the answer failed, it raises an exception. + * @throws XMPPErrorException + * @throws NoResponseException */ - public void setActiveListName(String listName) throws XMPPException { + public void setActiveListName(String listName) throws NoResponseException, XMPPErrorException { // The request of the list is an privacy message with an empty list Privacy request = new Privacy(); request.setActiveName(listName); @@ -282,10 +292,10 @@ public class PrivacyListManager extends Manager { /** * Client declines the use of active lists. - * - * @throws XMPPException if an error occurs. + * @throws XMPPErrorException + * @throws NoResponseException */ - public void declineActiveList() throws XMPPException { + public void declineActiveList() throws NoResponseException, XMPPErrorException { // The request of the list is an privacy message with an empty list Privacy request = new Privacy(); request.setDeclineActiveList(true); @@ -298,9 +308,10 @@ public class PrivacyListManager extends Manager { * Set or change the default list to listName. * * @param listName the list name to set as the default one. - * @exception XMPPException if the request or the answer failed, it raises an exception. + * @throws XMPPErrorException + * @throws NoResponseException */ - public void setDefaultListName(String listName) throws XMPPException { + public void setDefaultListName(String listName) throws NoResponseException, XMPPErrorException { // The request of the list is an privacy message with an empty list Privacy request = new Privacy(); request.setDefaultName(listName); @@ -311,10 +322,10 @@ public class PrivacyListManager extends Manager { /** * Client declines the use of default lists. - * - * @throws XMPPException if an error occurs. + * @throws XMPPErrorException + * @throws NoResponseException */ - public void declineDefaultList() throws XMPPException { + public void declineDefaultList() throws NoResponseException, XMPPErrorException { // The request of the list is an privacy message with an empty list Privacy request = new Privacy(); request.setDeclineDefaultList(true); @@ -328,10 +339,11 @@ public class PrivacyListManager extends Manager { * * @param listName the list that has changed its content. * @param privacyItems a List with every privacy item in the list. - * @throws XMPPException if an error occurs. + * @throws XMPPErrorException + * @throws NoResponseException */ - public void createPrivacyList(String listName, List privacyItems) throws XMPPException { - this.updatePrivacyList(listName, privacyItems); + public void createPrivacyList(String listName, List privacyItems) throws NoResponseException, XMPPErrorException { + updatePrivacyList(listName, privacyItems); } /** @@ -341,9 +353,10 @@ public class PrivacyListManager extends Manager { * * @param listName the list that has changed its content. * @param privacyItems a List with every privacy item in the list. - * @throws XMPPException if an error occurs. + * @throws XMPPErrorException + * @throws NoResponseException */ - public void updatePrivacyList(String listName, List privacyItems) throws XMPPException { + public void updatePrivacyList(String listName, List privacyItems) throws NoResponseException, XMPPErrorException { // Build the privacy package to add or update the new list Privacy request = new Privacy(); request.setPrivacyList(listName, privacyItems); @@ -356,9 +369,10 @@ public class PrivacyListManager extends Manager { * Remove a privacy list. * * @param listName the list that has changed its content. - * @throws XMPPException if an error occurs. + * @throws XMPPErrorException + * @throws NoResponseException */ - public void deletePrivacyList(String listName) throws XMPPException { + public void deletePrivacyList(String listName) throws NoResponseException, XMPPErrorException { // The request of the list is an privacy message with an empty list Privacy request = new Privacy(); request.setPrivacyList(listName, new ArrayList()); @@ -385,9 +399,10 @@ public class PrivacyListManager extends Manager { * Check if the user's server supports privacy lists. * * @return true, if the server supports privacy lists, false otherwise. - * @throws XMPPException + * @throws XMPPErrorException + * @throws NoResponseException */ - public boolean isSupported() throws XMPPException { + public boolean isSupported() throws NoResponseException, XMPPErrorException{ return ServiceDiscoveryManager.getInstanceFor(connection()).supportsFeature( connection().getServiceName(), NAMESPACE); } diff --git a/extensions/src/main/java/org/jivesoftware/smackx/pubsub/LeafNode.java b/extensions/src/main/java/org/jivesoftware/smackx/pubsub/LeafNode.java index 601c7e0f1..701cdd462 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/pubsub/LeafNode.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/pubsub/LeafNode.java @@ -20,8 +20,9 @@ import java.util.ArrayList; import java.util.Collection; import java.util.List; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.packet.IQ.Type; import org.jivesoftware.smackx.disco.packet.DiscoverItems; import org.jivesoftware.smackx.pubsub.packet.PubSub; @@ -46,11 +47,10 @@ public class LeafNode extends Node * {@link DiscoverItems} format. * * @return The item details in {@link DiscoverItems} format - * - * @throws XMPPException + * @throws XMPPErrorException + * @throws NoResponseException if there was no response from the server. */ - public DiscoverItems discoverItems() - throws XMPPException + public DiscoverItems discoverItems() throws NoResponseException, XMPPErrorException { DiscoverItems items = new DiscoverItems(); items.setTo(to); @@ -62,12 +62,11 @@ public class LeafNode extends Node * Get the current items stored in the node. * * @return List of {@link Item} in the node - * - * @throws XMPPException + * @throws XMPPErrorException + * @throws NoResponseException if there was no response from the server. */ @SuppressWarnings("unchecked") - public List getItems() - throws XMPPException + public List getItems() throws NoResponseException, XMPPErrorException { PubSub request = createPubsubPacket(Type.GET, new GetItemsRequest(getId())); @@ -84,12 +83,11 @@ public class LeafNode extends Node * @param subscriptionId - The subscription id for the * associated subscription. * @return List of {@link Item} in the node - * - * @throws XMPPException + * @throws XMPPErrorException + * @throws NoResponseException if there was no response from the server. */ @SuppressWarnings("unchecked") - public List getItems(String subscriptionId) - throws XMPPException + public List getItems(String subscriptionId) throws NoResponseException, XMPPErrorException { PubSub request = createPubsubPacket(Type.GET, new GetItemsRequest(getId(), subscriptionId)); @@ -108,12 +106,11 @@ public class LeafNode extends Node * @param ids Item ids of the items to retrieve * * @return The list of {@link Item} with payload - * - * @throws XMPPException + * @throws XMPPErrorException + * @throws NoResponseException if there was no response from the server. */ @SuppressWarnings("unchecked") - public List getItems(Collection ids) - throws XMPPException + public List getItems(Collection ids) throws NoResponseException, XMPPErrorException { List itemList = new ArrayList(ids.size()); @@ -134,12 +131,11 @@ public class LeafNode extends Node * @param maxItems Maximum number of items to return * * @return List of {@link Item} - * - * @throws XMPPException + * @throws XMPPErrorException + * @throws NoResponseException if there was no response from the server. */ @SuppressWarnings("unchecked") - public List getItems(int maxItems) - throws XMPPException + public List getItems(int maxItems) throws NoResponseException, XMPPErrorException { PubSub request = createPubsubPacket(Type.GET, new GetItemsRequest(getId(), maxItems)); @@ -157,12 +153,11 @@ public class LeafNode extends Node * on. * * @return List of {@link Item} - * - * @throws XMPPException + * @throws XMPPErrorException + * @throws NoResponseException if there was no response from the server. */ @SuppressWarnings("unchecked") - public List getItems(int maxItems, String subscriptionId) - throws XMPPException + public List getItems(int maxItems, String subscriptionId) throws NoResponseException, XMPPErrorException { PubSub request = createPubsubPacket(Type.GET, new GetItemsRequest(getId(), subscriptionId, maxItems)); @@ -244,11 +239,11 @@ public class LeafNode extends Node * on failure. * * For asynchronous calls, use {@link #publish() publish()}. + * @throws XMPPErrorException + * @throws NoResponseException * - * @throws XMPPException */ - public void send() - throws XMPPException + public void send() throws NoResponseException, XMPPErrorException { PubSub packet = createPubsubPacket(Type.SET, new NodeExtension(PubSubElementType.PUBLISH, getId())); @@ -273,12 +268,12 @@ public class LeafNode extends Node * For asynchronous calls, use {@link #publish(Item) publish(Item)}. * * @param item - The item being sent + * @throws XMPPErrorException + * @throws NoResponseException * - * @throws XMPPException */ @SuppressWarnings("unchecked") - public void send(T item) - throws XMPPException + public void send(T item) throws NoResponseException, XMPPErrorException { Collection items = new ArrayList(1); items.add((item == null ? (T)new Item() : item)); @@ -297,11 +292,11 @@ public class LeafNode extends Node * For asynchronous calls, use {@link #publish(Collection) publish(Collection))}. * * @param items - The collection of {@link Item} objects being sent + * @throws XMPPErrorException + * @throws NoResponseException * - * @throws XMPPException */ - public void send(Collection items) - throws XMPPException + public void send(Collection items) throws NoResponseException, XMPPErrorException { PubSub packet = createPubsubPacket(Type.SET, new PublishItem(getId(), items)); @@ -313,11 +308,10 @@ public class LeafNode extends Node * *

Note: Some implementations may keep the last item * sent. - * - * @throws XMPPException + * @throws XMPPErrorException + * @throws NoResponseException if there was no response from the server. */ - public void deleteAllItems() - throws XMPPException + public void deleteAllItems() throws NoResponseException, XMPPErrorException { PubSub request = createPubsubPacket(Type.SET, new NodeExtension(PubSubElementType.PURGE_OWNER, getId()), PubSubElementType.PURGE_OWNER.getNamespace()); @@ -328,11 +322,10 @@ public class LeafNode extends Node * Delete the item with the specified id from the node. * * @param itemId The id of the item - * - * @throws XMPPException + * @throws XMPPErrorException + * @throws NoResponseException */ - public void deleteItem(String itemId) - throws XMPPException + public void deleteItem(String itemId) throws NoResponseException, XMPPErrorException { Collection items = new ArrayList(1); items.add(itemId); @@ -343,11 +336,10 @@ public class LeafNode extends Node * Delete the items with the specified id's from the node. * * @param itemIds The list of id's of items to delete - * - * @throws XMPPException + * @throws XMPPErrorException + * @throws NoResponseException if there was no response from the server. */ - public void deleteItem(Collection itemIds) - throws XMPPException + public void deleteItem(Collection itemIds) throws NoResponseException, XMPPErrorException { List items = new ArrayList(itemIds.size()); diff --git a/extensions/src/main/java/org/jivesoftware/smackx/pubsub/Node.java b/extensions/src/main/java/org/jivesoftware/smackx/pubsub/Node.java index 0092e926a..fc92be028 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/pubsub/Node.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/pubsub/Node.java @@ -23,8 +23,9 @@ import java.util.List; import java.util.concurrent.ConcurrentHashMap; import org.jivesoftware.smack.PacketListener; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.filter.OrFilter; import org.jivesoftware.smack.filter.PacketFilter; import org.jivesoftware.smack.packet.Message; @@ -91,9 +92,10 @@ abstract public class Node * via the {@link #sendConfigurationForm(Form)}. * * @return the configuration form + * @throws XMPPErrorException + * @throws NoResponseException */ - public ConfigureForm getNodeConfiguration() - throws XMPPException + public ConfigureForm getNodeConfiguration() throws NoResponseException, XMPPErrorException { Packet reply = sendPubsubPacket(Type.GET, new NodeExtension(PubSubElementType.CONFIGURE_OWNER, getId()), PubSubNamespace.OWNER); return NodeUtils.getFormFromPacket(reply, PubSubElementType.CONFIGURE_OWNER); @@ -103,9 +105,10 @@ abstract public class Node * Update the configuration with the contents of the new {@link Form} * * @param submitForm + * @throws XMPPErrorException + * @throws NoResponseException */ - public void sendConfigurationForm(Form submitForm) - throws XMPPException + public void sendConfigurationForm(Form submitForm) throws NoResponseException, XMPPErrorException { PubSub packet = createPubsubPacket(Type.SET, new FormNode(FormNodeType.CONFIGURE_OWNER, getId(), submitForm), PubSubNamespace.OWNER); con.createPacketCollectorAndSend(packet).nextResultOrThrow(); @@ -115,11 +118,10 @@ abstract public class Node * Discover node information in standard {@link DiscoverInfo} format. * * @return The discovery information about the node. - * - * @throws XMPPException + * @throws XMPPErrorException + * @throws NoResponseException if there was no response from the server. */ - public DiscoverInfo discoverInfo() - throws XMPPException + public DiscoverInfo discoverInfo() throws NoResponseException, XMPPErrorException { DiscoverInfo info = new DiscoverInfo(); info.setTo(to); @@ -131,11 +133,11 @@ abstract public class Node * Get the subscriptions currently associated with this node. * * @return List of {@link Subscription} + * @throws XMPPErrorException + * @throws NoResponseException * - * @throws XMPPException */ - public List getSubscriptions() - throws XMPPException + public List getSubscriptions() throws NoResponseException, XMPPErrorException { PubSub reply = (PubSub)sendPubsubPacket(Type.GET, new NodeExtension(PubSubElementType.SUBSCRIPTIONS, getId())); SubscriptionsExtension subElem = (SubscriptionsExtension)reply.getExtension(PubSubElementType.SUBSCRIPTIONS); @@ -155,10 +157,10 @@ abstract public class Node * the caller can configure it but is not required to do so. * @param jid The jid to subscribe as. * @return The subscription - * @exception XMPPException + * @throws XMPPErrorException + * @throws NoResponseException */ - public Subscription subscribe(String jid) - throws XMPPException + public Subscription subscribe(String jid) throws NoResponseException, XMPPErrorException { PubSub reply = (PubSub)sendPubsubPacket(Type.SET, new SubscribeExtension(jid, getId())); return (Subscription)reply.getExtension(PubSubElementType.SUBSCRIPTION); @@ -178,10 +180,10 @@ abstract public class Node * the caller can configure it but is not required to do so. * @param jid The jid to subscribe as. * @return The subscription - * @exception XMPPException + * @throws XMPPErrorException + * @throws NoResponseException */ - public Subscription subscribe(String jid, SubscribeForm subForm) - throws XMPPException + public Subscription subscribe(String jid, SubscribeForm subForm) throws NoResponseException, XMPPErrorException { PubSub request = createPubsubPacket(Type.SET, new SubscribeExtension(jid, getId())); request.addExtension(new FormNode(FormNodeType.OPTIONS, subForm)); @@ -195,11 +197,11 @@ abstract public class Node * use {@link #unsubscribe(String, String)}. * * @param jid The JID used to subscribe to the node + * @throws XMPPErrorException + * @throws NoResponseException * - * @throws XMPPException */ - public void unsubscribe(String jid) - throws XMPPException + public void unsubscribe(String jid) throws NoResponseException, XMPPErrorException { unsubscribe(jid, null); } @@ -209,11 +211,10 @@ abstract public class Node * * @param jid The JID used to subscribe to the node * @param subscriptionId The id of the subscription being removed - * - * @throws XMPPException + * @throws XMPPErrorException + * @throws NoResponseException */ - public void unsubscribe(String jid, String subscriptionId) - throws XMPPException + public void unsubscribe(String jid, String subscriptionId) throws NoResponseException, XMPPErrorException { sendPubsubPacket(Type.SET, new UnsubscribeExtension(jid, getId(), subscriptionId)); } @@ -223,11 +224,10 @@ abstract public class Node * via the {@link #sendConfigurationForm(Form)}. * * @return A subscription options form - * - * @throws XMPPException + * @throws XMPPErrorException + * @throws NoResponseException */ - public SubscribeForm getSubscriptionOptions(String jid) - throws XMPPException + public SubscribeForm getSubscriptionOptions(String jid) throws NoResponseException, XMPPErrorException { return getSubscriptionOptions(jid, null); } @@ -240,11 +240,11 @@ abstract public class Node * @param subscriptionId The subscription id * * @return The subscription option form + * @throws XMPPErrorException + * @throws NoResponseException * - * @throws XMPPException */ - public SubscribeForm getSubscriptionOptions(String jid, String subscriptionId) - throws XMPPException + public SubscribeForm getSubscriptionOptions(String jid, String subscriptionId) throws NoResponseException, XMPPErrorException { PubSub packet = (PubSub)sendPubsubPacket(Type.GET, new OptionsExtension(jid, getId(), subscriptionId)); FormNode ext = (FormNode)packet.getExtension(PubSubElementType.OPTIONS); @@ -349,14 +349,12 @@ abstract public class Node return PubSubManager.createPubsubPacket(to, type, ext, ns); } - protected Packet sendPubsubPacket(Type type, NodeExtension ext) - throws XMPPException + protected Packet sendPubsubPacket(Type type, NodeExtension ext) throws NoResponseException, XMPPErrorException { return PubSubManager.sendPubsubPacket(con, to, type, ext); } - protected Packet sendPubsubPacket(Type type, NodeExtension ext, PubSubNamespace ns) - throws XMPPException + protected Packet sendPubsubPacket(Type type, NodeExtension ext, PubSubNamespace ns) throws NoResponseException, XMPPErrorException { return PubSubManager.sendPubsubPacket(con, to, type, ext, ns); } diff --git a/extensions/src/main/java/org/jivesoftware/smackx/pubsub/PubSubManager.java b/extensions/src/main/java/org/jivesoftware/smackx/pubsub/PubSubManager.java index df6018ab3..86b34b39b 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/pubsub/PubSubManager.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/pubsub/PubSubManager.java @@ -20,8 +20,9 @@ import java.util.List; import java.util.Map; import java.util.concurrent.ConcurrentHashMap; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.packet.IQ.Type; import org.jivesoftware.smack.packet.Packet; import org.jivesoftware.smack.packet.PacketExtension; @@ -78,10 +79,10 @@ final public class PubSubManager * Creates an instant node, if supported. * * @return The node that was created - * @exception XMPPException + * @throws XMPPErrorException + * @throws NoResponseException */ - public LeafNode createNode() - throws XMPPException + public LeafNode createNode() throws NoResponseException, XMPPErrorException { PubSub reply = (PubSub)sendPubsubPacket(Type.SET, new NodeExtension(PubSubElementType.CREATE)); NodeExtension elem = (NodeExtension)reply.getExtension("create", PubSubNamespace.BASIC.getXmlns()); @@ -99,10 +100,10 @@ final public class PubSubManager * @param id The id of the node, which must be unique within the * pubsub service * @return The node that was created - * @exception XMPPException + * @throws XMPPErrorException + * @throws NoResponseException */ - public LeafNode createNode(String id) - throws XMPPException + public LeafNode createNode(String id) throws NoResponseException, XMPPErrorException { return (LeafNode)createNode(id, null); } @@ -116,10 +117,10 @@ final public class PubSubManager * pubsub service * @param config The configuration for the node * @return The node that was created - * @exception XMPPException + * @throws XMPPErrorException + * @throws NoResponseException */ - public Node createNode(String name, Form config) - throws XMPPException + public Node createNode(String name, Form config) throws NoResponseException, XMPPErrorException { PubSub request = createPubsubPacket(to, Type.SET, new NodeExtension(PubSubElementType.CREATE, name)); boolean isLeafNode = true; @@ -149,11 +150,11 @@ final public class PubSubManager * * @param id - The unique id of the node * @return the node - * @throws XMPPException The node does not exist + * @throws XMPPErrorException The node does not exist + * @throws NoResponseException if there was no response from the server. */ @SuppressWarnings("unchecked") - public T getNode(String id) - throws XMPPException + public T getNode(String id) throws NoResponseException, XMPPErrorException { Node node = nodeMap.get(id); @@ -186,11 +187,10 @@ final public class PubSubManager * @param nodeId - The id of the collection node for which the child * nodes will be returned. * @return {@link DiscoverItems} representing the existing nodes - * - * @throws XMPPException + * @throws XMPPErrorException + * @throws NoResponseException if there was no response from the server. */ - public DiscoverItems discoverNodes(String nodeId) - throws XMPPException + public DiscoverItems discoverNodes(String nodeId) throws NoResponseException, XMPPErrorException { DiscoverItems items = new DiscoverItems(); @@ -205,11 +205,10 @@ final public class PubSubManager * Gets the subscriptions on the root node. * * @return List of exceptions - * - * @throws XMPPException + * @throws XMPPErrorException + * @throws NoResponseException */ - public List getSubscriptions() - throws XMPPException + public List getSubscriptions() throws NoResponseException, XMPPErrorException { Packet reply = sendPubsubPacket(Type.GET, new NodeExtension(PubSubElementType.SUBSCRIPTIONS)); SubscriptionsExtension subElem = (SubscriptionsExtension)reply.getExtension(PubSubElementType.SUBSCRIPTIONS.getElementName(), PubSubElementType.SUBSCRIPTIONS.getNamespace().getXmlns()); @@ -220,11 +219,11 @@ final public class PubSubManager * Gets the affiliations on the root node. * * @return List of affiliations + * @throws XMPPErrorException + * @throws NoResponseException * - * @throws XMPPException */ - public List getAffiliations() - throws XMPPException + public List getAffiliations() throws NoResponseException, XMPPErrorException { PubSub reply = (PubSub)sendPubsubPacket(Type.GET, new NodeExtension(PubSubElementType.AFFILIATIONS)); AffiliationsExtension listElem = (AffiliationsExtension)reply.getExtension(PubSubElementType.AFFILIATIONS); @@ -235,10 +234,10 @@ final public class PubSubManager * Delete the specified node * * @param nodeId - * @throws XMPPException + * @throws XMPPErrorException + * @throws NoResponseException */ - public void deleteNode(String nodeId) - throws XMPPException + public void deleteNode(String nodeId) throws NoResponseException, XMPPErrorException { sendPubsubPacket(Type.SET, new NodeExtension(PubSubElementType.DELETE, nodeId), PubSubElementType.DELETE.getNamespace()); nodeMap.remove(nodeId); @@ -248,9 +247,10 @@ final public class PubSubManager * Returns the default settings for Node configuration. * * @return configuration form containing the default settings. + * @throws XMPPErrorException + * @throws NoResponseException */ - public ConfigureForm getDefaultConfiguration() - throws XMPPException + public ConfigureForm getDefaultConfiguration() throws NoResponseException, XMPPErrorException { // Errors will cause exceptions in getReply, so it only returns // on success. @@ -263,24 +263,21 @@ final public class PubSubManager * as a standard {@link DiscoverInfo} instance. * * @return The supported features - * - * @throws XMPPException + * @throws XMPPErrorException + * @throws NoResponseException */ - public DiscoverInfo getSupportedFeatures() - throws XMPPException + public DiscoverInfo getSupportedFeatures() throws NoResponseException, XMPPErrorException { ServiceDiscoveryManager mgr = ServiceDiscoveryManager.getInstanceFor(con); return mgr.discoverInfo(to); } - private Packet sendPubsubPacket(Type type, PacketExtension ext, PubSubNamespace ns) - throws XMPPException + private Packet sendPubsubPacket(Type type, PacketExtension ext, PubSubNamespace ns) throws NoResponseException, XMPPErrorException { return sendPubsubPacket(con, to, type, ext, ns); } - private Packet sendPubsubPacket(Type type, PacketExtension ext) - throws XMPPException + private Packet sendPubsubPacket(Type type, PacketExtension ext) throws NoResponseException, XMPPErrorException { return sendPubsubPacket(type, ext, null); } @@ -305,26 +302,22 @@ final public class PubSubManager return request; } - static Packet sendPubsubPacket(XMPPConnection con, String to, Type type, PacketExtension ext) - throws XMPPException + static Packet sendPubsubPacket(XMPPConnection con, String to, Type type, PacketExtension ext) throws NoResponseException, XMPPErrorException { return sendPubsubPacket(con, to, type, ext, null); } - static Packet sendPubsubPacket(XMPPConnection con, String to, Type type, PacketExtension ext, PubSubNamespace ns) - throws XMPPException + static Packet sendPubsubPacket(XMPPConnection con, String to, Type type, PacketExtension ext, PubSubNamespace ns) throws NoResponseException, XMPPErrorException { return con.createPacketCollectorAndSend(createPubsubPacket(to, type, ext, ns)).nextResultOrThrow(); } - static Packet sendPubsubPacket(XMPPConnection con, String to, Type type, PubSub packet) - throws XMPPException + static Packet sendPubsubPacket(XMPPConnection con, String to, Type type, PubSub packet) throws NoResponseException, XMPPErrorException { return sendPubsubPacket(con, to, type, packet, null); } - static Packet sendPubsubPacket(XMPPConnection con, String to, Type type, PubSub packet, PubSubNamespace ns) - throws XMPPException + static Packet sendPubsubPacket(XMPPConnection con, String to, Type type, PubSub packet, PubSubNamespace ns) throws NoResponseException, XMPPErrorException { return con.createPacketCollectorAndSend(packet).nextResultOrThrow(); } diff --git a/extensions/src/main/java/org/jivesoftware/smackx/receipts/DeliveryReceiptManager.java b/extensions/src/main/java/org/jivesoftware/smackx/receipts/DeliveryReceiptManager.java index 9e4165da0..69750aeb5 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/receipts/DeliveryReceiptManager.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/receipts/DeliveryReceiptManager.java @@ -22,6 +22,7 @@ import java.util.Map; import java.util.Set; import java.util.WeakHashMap; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.ConnectionCreationListener; import org.jivesoftware.smack.Manager; @@ -88,15 +89,12 @@ public class DeliveryReceiptManager extends Manager implements PacketListener { * * @param jid * @return true if supported + * @throws SmackException if there was no response from the server. + * @throws XMPPException */ - public boolean isSupported(String jid) { - try { - return ServiceDiscoveryManager.getInstanceFor(connection()).supportsFeature(jid, - DeliveryReceipt.NAMESPACE); - } - catch (XMPPException e) { - return false; - } + public boolean isSupported(String jid) throws SmackException, XMPPException { + return ServiceDiscoveryManager.getInstanceFor(connection()).supportsFeature(jid, + DeliveryReceipt.NAMESPACE); } // handle incoming receipts and receipt requests diff --git a/extensions/src/main/java/org/jivesoftware/smackx/search/UserSearch.java b/extensions/src/main/java/org/jivesoftware/smackx/search/UserSearch.java index 122c9e422..bee4a56fb 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/search/UserSearch.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/search/UserSearch.java @@ -16,8 +16,9 @@ */ package org.jivesoftware.smackx.search; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.packet.IQ; import org.jivesoftware.smack.provider.IQProvider; import org.jivesoftware.smack.util.PacketParserUtils; @@ -58,10 +59,10 @@ public class UserSearch extends IQ { * @param con the current XMPPConnection. * @param searchService the search service to use. (ex. search.jivesoftware.com) * @return the search form received by the server. - * @throws org.jivesoftware.smack.XMPPException - * thrown if a server error has occurred. + * @throws XMPPErrorException + * @throws NoResponseException */ - public Form getSearchForm(XMPPConnection con, String searchService) throws XMPPException { + public Form getSearchForm(XMPPConnection con, String searchService) throws NoResponseException, XMPPErrorException { UserSearch search = new UserSearch(); search.setType(IQ.Type.GET); search.setTo(searchService); @@ -77,10 +78,10 @@ public class UserSearch extends IQ { * @param searchForm the Form to send for querying. * @param searchService the search service to use. (ex. search.jivesoftware.com) * @return ReportedData the data found from the query. - * @throws org.jivesoftware.smack.XMPPException - * thrown if a server error has occurred. + * @throws XMPPErrorException + * @throws NoResponseException */ - public ReportedData sendSearchForm(XMPPConnection con, Form searchForm, String searchService) throws XMPPException { + public ReportedData sendSearchForm(XMPPConnection con, Form searchForm, String searchService) throws NoResponseException, XMPPErrorException { UserSearch search = new UserSearch(); search.setType(IQ.Type.SET); search.setTo(searchService); @@ -97,10 +98,10 @@ public class UserSearch extends IQ { * @param searchForm the Form to send for querying. * @param searchService the search service to use. (ex. search.jivesoftware.com) * @return ReportedData the data found from the query. - * @throws org.jivesoftware.smack.XMPPException - * thrown if a server error has occurred. + * @throws XMPPErrorException + * @throws NoResponseException */ - public ReportedData sendSimpleSearchForm(XMPPConnection con, Form searchForm, String searchService) throws XMPPException { + public ReportedData sendSimpleSearchForm(XMPPConnection con, Form searchForm, String searchService) throws NoResponseException, XMPPErrorException { SimpleUserSearch search = new SimpleUserSearch(); search.setForm(searchForm); search.setType(IQ.Type.SET); diff --git a/extensions/src/main/java/org/jivesoftware/smackx/search/UserSearchManager.java b/extensions/src/main/java/org/jivesoftware/smackx/search/UserSearchManager.java index 7b7e0515c..b70e155bd 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/search/UserSearchManager.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/search/UserSearchManager.java @@ -16,8 +16,10 @@ */ package org.jivesoftware.smackx.search; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smackx.disco.ServiceDiscoveryManager; import org.jivesoftware.smackx.disco.packet.DiscoverInfo; import org.jivesoftware.smackx.disco.packet.DiscoverItems; @@ -66,9 +68,10 @@ public class UserSearchManager { * * @param searchService the search service to query. * @return the form to fill out to perform a search. - * @throws XMPPException thrown if a server error has occurred. + * @throws XMPPErrorException + * @throws NoResponseException */ - public Form getSearchForm(String searchService) throws XMPPException { + public Form getSearchForm(String searchService) throws NoResponseException, XMPPErrorException { return userSearch.getSearchForm(con, searchService); } @@ -79,9 +82,10 @@ public class UserSearchManager { * @param searchForm the Form to submit for searching. * @param searchService the name of the search service to use. * @return the ReportedData returned by the server. - * @throws XMPPException thrown if a server error has occurred. + * @throws XMPPErrorException + * @throws NoResponseException */ - public ReportedData getSearchResults(Form searchForm, String searchService) throws XMPPException { + public ReportedData getSearchResults(Form searchForm, String searchService) throws NoResponseException, XMPPErrorException { return userSearch.sendSearchForm(con, searchForm, searchService); } @@ -90,9 +94,10 @@ public class UserSearchManager { * Returns a collection of search services found on the server. * * @return a Collection of search services found on the server. - * @throws XMPPException thrown if a server error has occurred. + * @throws XMPPErrorException + * @throws NoResponseException */ - public Collection getSearchServices() throws XMPPException { + public Collection getSearchServices() throws NoResponseException, XMPPErrorException { final List searchServices = new ArrayList(); ServiceDiscoveryManager discoManager = ServiceDiscoveryManager.getInstanceFor(con); DiscoverItems items = discoManager.discoverItems(con.getServiceName()); diff --git a/extensions/src/main/java/org/jivesoftware/smackx/sharedgroups/SharedGroupManager.java b/extensions/src/main/java/org/jivesoftware/smackx/sharedgroups/SharedGroupManager.java index d7ef10a80..618e7280a 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/sharedgroups/SharedGroupManager.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/sharedgroups/SharedGroupManager.java @@ -16,8 +16,9 @@ */ package org.jivesoftware.smackx.sharedgroups; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.packet.IQ; import org.jivesoftware.smackx.sharedgroups.packet.SharedGroupsInfo; @@ -39,8 +40,10 @@ public class SharedGroupManager { * * @param connection connection to use to get the user's shared groups. * @return collection with the shared groups' name of the logged user. + * @throws XMPPErrorException + * @throws NoResponseException */ - public static List getSharedGroups(XMPPConnection connection) throws XMPPException { + public static List getSharedGroups(XMPPConnection connection) throws NoResponseException, XMPPErrorException { // Discover the shared groups of the logged user SharedGroupsInfo info = new SharedGroupsInfo(); info.setType(IQ.Type.GET); diff --git a/extensions/src/main/java/org/jivesoftware/smackx/time/EntityTimeManager.java b/extensions/src/main/java/org/jivesoftware/smackx/time/EntityTimeManager.java index 20a37a81d..0aa77585d 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/time/EntityTimeManager.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/time/EntityTimeManager.java @@ -19,11 +19,12 @@ package org.jivesoftware.smackx.time; import java.util.Map; import java.util.WeakHashMap; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.ConnectionCreationListener; import org.jivesoftware.smack.Manager; import org.jivesoftware.smack.PacketListener; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.filter.AndFilter; import org.jivesoftware.smack.filter.IQTypeFilter; import org.jivesoftware.smack.filter.PacketFilter; @@ -96,11 +97,11 @@ public class EntityTimeManager extends Manager { enabled = false; } - public boolean isTimeSupported(String jid) throws XMPPException { + public boolean isTimeSupported(String jid) throws NoResponseException, XMPPErrorException { return ServiceDiscoveryManager.getInstanceFor(connection()).supportsFeature(jid, Time.NAMESPACE); } - public Time getTime(String jid) throws XMPPException { + public Time getTime(String jid) throws NoResponseException, XMPPErrorException { if (!isTimeSupported(jid)) return null; diff --git a/extensions/src/main/java/org/jivesoftware/smackx/vcardtemp/VCardManager.java b/extensions/src/main/java/org/jivesoftware/smackx/vcardtemp/VCardManager.java index 001acee57..4a58ed2a8 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/vcardtemp/VCardManager.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/vcardtemp/VCardManager.java @@ -17,8 +17,9 @@ package org.jivesoftware.smackx.vcardtemp; import org.jivesoftware.smack.ConnectionCreationListener; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smackx.disco.ServiceDiscoveryManager; public class VCardManager { @@ -40,9 +41,10 @@ public class VCardManager { * @param jid * @param connection * @return true if the given entity understands the vCard-XML format and exchange. - * @throws XMPPException If there was an exception while determining the support. + * @throws XMPPErrorException + * @throws NoResponseException */ - public static boolean isSupported(String jid, XMPPConnection connection) throws XMPPException { + public static boolean isSupported(String jid, XMPPConnection connection) throws NoResponseException, XMPPErrorException { return ServiceDiscoveryManager.getInstanceFor(connection).supportsFeature(jid, NAMESPACE); } } diff --git a/extensions/src/main/java/org/jivesoftware/smackx/vcardtemp/packet/VCard.java b/extensions/src/main/java/org/jivesoftware/smackx/vcardtemp/packet/VCard.java index 32add6568..48da1eb86 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/vcardtemp/packet/VCard.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/vcardtemp/packet/VCard.java @@ -33,8 +33,9 @@ import java.util.Map.Entry; import java.util.logging.Level; import java.util.logging.Logger; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.packet.IQ; import org.jivesoftware.smack.util.StringUtils; import org.jivesoftware.smackx.vcardtemp.VCardManager; @@ -515,9 +516,10 @@ public class VCard extends IQ { * NOTE: the method is asynchronous and does not wait for the returned value. * * @param connection the XMPPConnection to use. - * @throws XMPPException thrown if there was an issue setting the VCard in the server. + * @throws XMPPErrorException thrown if there was an issue setting the VCard in the server. + * @throws NoResponseException if there was no response from the server. */ - public void save(XMPPConnection connection) throws XMPPException { + public void save(XMPPConnection connection) throws NoResponseException, XMPPErrorException { checkAuthenticated(connection, true); setType(IQ.Type.SET); @@ -528,8 +530,10 @@ public class VCard extends IQ { /** * Load VCard information for a connected user. XMPPConnection should be authenticated * and not anonymous. + * @throws XMPPErrorException + * @throws NoResponseException */ - public void load(XMPPConnection connection) throws XMPPException { + public void load(XMPPConnection connection) throws NoResponseException, XMPPErrorException { checkAuthenticated(connection, true); setFrom(connection.getUser()); @@ -538,15 +542,17 @@ public class VCard extends IQ { /** * Load VCard information for a given user. XMPPConnection should be authenticated and not anonymous. + * @throws XMPPErrorException + * @throws NoResponseException if there was no response from the server. */ - public void load(XMPPConnection connection, String user) throws XMPPException { + public void load(XMPPConnection connection, String user) throws NoResponseException, XMPPErrorException { checkAuthenticated(connection, false); setTo(user); doLoad(connection, user); } - private void doLoad(XMPPConnection connection, String user) throws XMPPException { + private void doLoad(XMPPConnection connection, String user) throws NoResponseException, XMPPErrorException { setType(Type.GET); VCard result = (VCard) connection.createPacketCollectorAndSend(this).nextResultOrThrow(); copyFieldsFrom(result); diff --git a/extensions/src/main/java/org/jivesoftware/smackx/xhtmlim/XHTMLManager.java b/extensions/src/main/java/org/jivesoftware/smackx/xhtmlim/XHTMLManager.java index 2b21c3903..0900b36a7 100644 --- a/extensions/src/main/java/org/jivesoftware/smackx/xhtmlim/XHTMLManager.java +++ b/extensions/src/main/java/org/jivesoftware/smackx/xhtmlim/XHTMLManager.java @@ -18,16 +18,14 @@ package org.jivesoftware.smackx.xhtmlim; import org.jivesoftware.smack.ConnectionCreationListener; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.packet.Message; import org.jivesoftware.smackx.disco.ServiceDiscoveryManager; -import org.jivesoftware.smackx.disco.packet.DiscoverInfo; import org.jivesoftware.smackx.xhtmlim.packet.XHTMLExtension; import java.util.Iterator; -import java.util.logging.Level; -import java.util.logging.Logger; /** * Manages XHTML formatted texts within messages. A XHTMLManager provides a high level access to @@ -37,9 +35,6 @@ import java.util.logging.Logger; * @author Gaston Dombiak */ public class XHTMLManager { - - private static final Logger LOGGER = Logger.getLogger(XHTMLManager.class.getName()); - private final static String namespace = "http://jabber.org/protocol/xhtml-im"; // Enable the XHTML support on every established connection @@ -131,16 +126,11 @@ public class XHTMLManager { * @param connection the connection to use to perform the service discovery * @param userID the user to check. A fully qualified xmpp ID, e.g. jdoe@example.com * @return a boolean indicating whether the specified user handles XHTML messages + * @throws XMPPErrorException + * @throws NoResponseException */ - public static boolean isServiceEnabled(XMPPConnection connection, String userID) { - try { - DiscoverInfo result = - ServiceDiscoveryManager.getInstanceFor(connection).discoverInfo(userID); - return result.containsFeature(namespace); - } - catch (XMPPException e) { - LOGGER.log(Level.SEVERE, "Error checking if service is available", e); - return false; - } + public static boolean isServiceEnabled(XMPPConnection connection, String userID) + throws NoResponseException, XMPPErrorException { + return ServiceDiscoveryManager.getInstanceFor(connection).supportsFeature(userID, namespace); } } diff --git a/extensions/src/test/java/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamManagerTest.java b/extensions/src/test/java/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamManagerTest.java index 7073b9b17..207325869 100644 --- a/extensions/src/test/java/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamManagerTest.java +++ b/extensions/src/test/java/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamManagerTest.java @@ -19,8 +19,10 @@ package org.jivesoftware.smackx.bytestreams.ibb; import static org.junit.Assert.*; import static org.mockito.Mockito.*; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.packet.IQ; import org.jivesoftware.smack.packet.XMPPError; import org.jivesoftware.smackx.bytestreams.ibb.InBandBytestreamManager; @@ -55,9 +57,10 @@ public class InBandBytestreamManagerTest { /** * Initialize fields used in the tests. * @throws XMPPException + * @throws SmackException */ @Before - public void setup() throws XMPPException { + public void setup() throws XMPPException, SmackException { // build protocol verifier protocol = new Protocol(); @@ -97,9 +100,11 @@ public class InBandBytestreamManagerTest { * Invoking {@link InBandBytestreamManager#establishSession(String)} should * throw an exception if the given target does not support in-band * bytestream. + * @throws SmackException + * @throws XMPPException */ @Test - public void shouldFailIfTargetDoesNotSupportIBB() { + public void shouldFailIfTargetDoesNotSupportIBB() throws SmackException, XMPPException { InBandBytestreamManager byteStreamManager = InBandBytestreamManager.getByteStreamManager(connection); try { @@ -113,7 +118,7 @@ public class InBandBytestreamManagerTest { fail("exception should be thrown"); } - catch (XMPPException e) { + catch (XMPPErrorException e) { assertEquals(XMPPError.Condition.feature_not_implemented.toString(), e.getXMPPError().getCondition()); } @@ -147,7 +152,7 @@ public class InBandBytestreamManagerTest { } @Test - public void shouldUseConfiguredStanzaType() { + public void shouldUseConfiguredStanzaType() throws SmackException { InBandBytestreamManager byteStreamManager = InBandBytestreamManager.getByteStreamManager(connection); byteStreamManager.setStanza(StanzaType.MESSAGE); diff --git a/extensions/src/test/java/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamSessionMessageTest.java b/extensions/src/test/java/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamSessionMessageTest.java index 93078a257..e701f88c3 100644 --- a/extensions/src/test/java/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamSessionMessageTest.java +++ b/extensions/src/test/java/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamSessionMessageTest.java @@ -23,6 +23,7 @@ import java.io.InputStream; import java.io.OutputStream; import java.util.Random; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.PacketListener; import org.jivesoftware.smack.XMPPException; @@ -73,9 +74,10 @@ public class InBandBytestreamSessionMessageTest { /** * Initialize fields used in the tests. * @throws XMPPException + * @throws SmackException */ @Before - public void setup() throws XMPPException { + public void setup() throws XMPPException, SmackException { // build protocol verifier protocol = new Protocol(); diff --git a/extensions/src/test/java/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamSessionTest.java b/extensions/src/test/java/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamSessionTest.java index 32b81bc93..968af9338 100644 --- a/extensions/src/test/java/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamSessionTest.java +++ b/extensions/src/test/java/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamSessionTest.java @@ -23,6 +23,7 @@ import java.io.InputStream; import java.io.OutputStream; import java.util.Random; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.PacketListener; import org.jivesoftware.smack.XMPPException; @@ -74,9 +75,10 @@ public class InBandBytestreamSessionTest { /** * Initialize fields used in the tests. * @throws XMPPException + * @throws SmackException */ @Before - public void setup() throws XMPPException { + public void setup() throws XMPPException, SmackException { // build protocol verifier protocol = new Protocol(); diff --git a/extensions/src/test/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5ByteStreamManagerTest.java b/extensions/src/test/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5ByteStreamManagerTest.java index 7e6a1b4bc..35fe39901 100644 --- a/extensions/src/test/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5ByteStreamManagerTest.java +++ b/extensions/src/test/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5ByteStreamManagerTest.java @@ -24,8 +24,10 @@ import java.io.InputStream; import java.io.OutputStream; import java.net.ConnectException; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.packet.IQ; import org.jivesoftware.smack.packet.XMPPError; import org.jivesoftware.smack.packet.IQ.Type; @@ -71,9 +73,10 @@ public class Socks5ByteStreamManagerTest { /** * Initialize fields used in the tests. * @throws XMPPException + * @throws SmackException */ @Before - public void setup() throws XMPPException { + public void setup() throws XMPPException, SmackException { // build protocol verifier protocol = new Protocol(); @@ -133,9 +136,10 @@ public class Socks5ByteStreamManagerTest { /** * Invoking {@link Socks5BytestreamManager#establishSession(String)} should throw an exception * if the given target does not support SOCKS5 Bytestream. + * @throws XMPPException */ @Test - public void shouldFailIfTargetDoesNotSupportSocks5() { + public void shouldFailIfTargetDoesNotSupportSocks5() throws XMPPException { Socks5BytestreamManager byteStreamManager = Socks5BytestreamManager.getBytestreamManager(connection); try { @@ -148,7 +152,7 @@ public class Socks5ByteStreamManagerTest { fail("exception should be thrown"); } - catch (XMPPException e) { + catch (SmackException e) { assertTrue(e.getMessage().contains("doesn't support SOCKS5 Bytestream")); } catch (IOException e) { @@ -201,7 +205,7 @@ public class Socks5ByteStreamManagerTest { fail("exception should be thrown"); } - catch (XMPPException e) { + catch (SmackException e) { protocol.verifyAll(); assertTrue(e.getMessage().contains("no SOCKS5 proxies available")); } @@ -264,7 +268,7 @@ public class Socks5ByteStreamManagerTest { fail("exception should be thrown"); } - catch (XMPPException e) { + catch (SmackException e) { protocol.verifyAll(); assertTrue(e.getMessage().contains("no SOCKS5 proxies available")); } @@ -328,7 +332,7 @@ public class Socks5ByteStreamManagerTest { fail("exception should be thrown"); } - catch (XMPPException e) { + catch (SmackException e) { protocol.verifyAll(); assertTrue(e.getMessage().contains("no SOCKS5 proxies available")); } @@ -351,7 +355,7 @@ public class Socks5ByteStreamManagerTest { fail("exception should be thrown"); } - catch (XMPPException e) { + catch (SmackException e) { /* * #verifyAll() tests if the number of requests and responses corresponds and should * fail if the invalid proxy is queried again @@ -446,7 +450,7 @@ public class Socks5ByteStreamManagerTest { fail("exception should be thrown"); } - catch (XMPPException e) { + catch (XMPPErrorException e) { protocol.verifyAll(); assertEquals(xmppError, e.getXMPPError()); } @@ -528,7 +532,7 @@ public class Socks5ByteStreamManagerTest { fail("exception should be thrown"); } - catch (XMPPException e) { + catch (SmackException e) { protocol.verifyAll(); assertTrue(e.getMessage().contains("Remote user responded with unknown host")); } @@ -1024,7 +1028,6 @@ public class Socks5ByteStreamManagerTest { DiscoverInfo proxyInfo1 = Socks5PacketUtils.createDiscoverInfo("proxy2.xmpp-server", initiatorJID); Identity identity1 = new Identity("proxy", "proxy2.xmpp-server", "bytestreams"); - identity1.setType("bytestreams"); proxyInfo1.addIdentity(identity1); // return the SOCKS5 bytestream proxy identity if proxy is queried diff --git a/extensions/src/test/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5ByteStreamRequestTest.java b/extensions/src/test/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5ByteStreamRequestTest.java index eb107f334..3b26282d6 100644 --- a/extensions/src/test/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5ByteStreamRequestTest.java +++ b/extensions/src/test/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5ByteStreamRequestTest.java @@ -23,8 +23,10 @@ import java.io.OutputStream; import java.net.ServerSocket; import java.net.Socket; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.packet.IQ; import org.jivesoftware.smack.packet.Packet; import org.jivesoftware.smack.packet.XMPPError; @@ -60,9 +62,10 @@ public class Socks5ByteStreamRequestTest { /** * Initialize fields used in the tests. * @throws XMPPException + * @throws SmackException */ @Before - public void setup() throws XMPPException { + public void setup() throws XMPPException, SmackException { // build protocol verifier protocol = new Protocol(); @@ -99,7 +102,7 @@ public class Socks5ByteStreamRequestTest { fail("exception should be thrown"); } - catch (XMPPException e) { + catch (XMPPErrorException e) { assertTrue(e.getMessage().contains("Could not establish socket with any provided host")); } @@ -143,7 +146,7 @@ public class Socks5ByteStreamRequestTest { fail("exception should be thrown"); } - catch (XMPPException e) { + catch (XMPPErrorException e) { assertTrue(e.getMessage().contains("Could not establish socket with any provided host")); } @@ -190,7 +193,7 @@ public class Socks5ByteStreamRequestTest { fail("exception should be thrown"); } - catch (XMPPException e) { + catch (XMPPErrorException e) { assertTrue(e.getMessage().contains( "Could not establish socket with any provided host")); } diff --git a/extensions/src/test/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5ClientForInitiatorTest.java b/extensions/src/test/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5ClientForInitiatorTest.java index 4d686ce80..d0482e5a9 100644 --- a/extensions/src/test/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5ClientForInitiatorTest.java +++ b/extensions/src/test/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5ClientForInitiatorTest.java @@ -22,8 +22,10 @@ import java.io.InputStream; import java.io.OutputStream; import java.net.Socket; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.packet.IQ; import org.jivesoftware.smack.packet.XMPPError; import org.jivesoftware.smack.packet.IQ.Type; @@ -65,9 +67,10 @@ public class Socks5ClientForInitiatorTest { /** * Initialize fields used in the tests. * @throws XMPPException + * @throws SmackException */ @Before - public void setup() throws XMPPException { + public void setup() throws XMPPException, SmackException { // build protocol verifier protocol = new Protocol(); @@ -106,7 +109,7 @@ public class Socks5ClientForInitiatorTest { fail("exception should be thrown"); } - catch (XMPPException e) { + catch (SmackException e) { assertTrue(e.getMessage().contains("target is not connected to SOCKS5 proxy")); protocol.verifyAll(); // assert no XMPP messages were sent } @@ -228,8 +231,8 @@ public class Socks5ClientForInitiatorTest { fail("exception should be thrown"); } - catch (XMPPException e) { - assertTrue(e.getMessage().contains("activating SOCKS5 Bytestream failed")); + catch (XMPPErrorException e) { + assertTrue(XMPPError.Condition.internal_server_error.equals(e.getXMPPError().getCondition())); protocol.verifyAll(); } diff --git a/extensions/src/test/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5ClientTest.java b/extensions/src/test/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5ClientTest.java index f6cf65e79..fcdb189eb 100644 --- a/extensions/src/test/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5ClientTest.java +++ b/extensions/src/test/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5ClientTest.java @@ -23,7 +23,7 @@ import java.io.DataOutputStream; import java.net.ServerSocket; import java.net.Socket; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smackx.bytestreams.socks5.Socks5Client; import org.jivesoftware.smackx.bytestreams.socks5.Socks5Utils; import org.jivesoftware.smackx.bytestreams.socks5.packet.Bytestream.StreamHost; @@ -81,9 +81,9 @@ public class Socks5ClientTest { fail("exception should be thrown"); } - catch (XMPPException e) { + catch (SmackException e) { assertTrue(e.getMessage().contains( - "establishing connection to SOCKS5 proxy failed")); + "SOCKS5 negotiation failed")); } catch (Exception e) { fail(e.getMessage()); @@ -138,9 +138,9 @@ public class Socks5ClientTest { fail("exception should be thrown"); } - catch (XMPPException e) { + catch (SmackException e) { assertTrue(e.getMessage().contains( - "establishing connection to SOCKS5 proxy failed")); + "Unsupported SOCKS5 address type")); } catch (Exception e) { fail(e.getMessage()); @@ -201,9 +201,9 @@ public class Socks5ClientTest { fail("exception should be thrown"); } - catch (XMPPException e) { + catch (SmackException e) { assertTrue(e.getMessage().contains( - "establishing connection to SOCKS5 proxy failed")); + "SOCKS5 negotiation failed")); } catch (Exception e) { fail(e.getMessage()); diff --git a/extensions/src/test/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5TestProxy.java b/extensions/src/test/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5TestProxy.java index 62d59d81d..094075bd1 100644 --- a/extensions/src/test/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5TestProxy.java +++ b/extensions/src/test/java/org/jivesoftware/smackx/bytestreams/socks5/Socks5TestProxy.java @@ -27,7 +27,7 @@ import java.net.UnknownHostException; import java.util.Map; import java.util.concurrent.ConcurrentHashMap; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smackx.bytestreams.socks5.Socks5Utils; /** @@ -227,17 +227,17 @@ public class Socks5TestProxy { * Negotiates a SOCKS5 connection and stores it on success. * * @param socket connection to the client - * @throws XMPPException if client requests a connection in an unsupported way + * @throws SmackException if client requests a connection in an unsupported way * @throws IOException if a network error occurred */ - private void establishConnection(Socket socket) throws XMPPException, IOException { + private void establishConnection(Socket socket) throws IOException, SmackException { DataOutputStream out = new DataOutputStream(socket.getOutputStream()); DataInputStream in = new DataInputStream(socket.getInputStream()); // first byte is version should be 5 int b = in.read(); if (b != 5) { - throw new XMPPException("Only SOCKS5 supported"); + throw new SmackException("Only SOCKS5 supported"); } // second byte number of authentication methods supported @@ -263,7 +263,7 @@ public class Socks5TestProxy { authMethodSelectionResponse[1] = (byte) 0xFF; // no acceptable methods out.write(authMethodSelectionResponse); out.flush(); - throw new XMPPException("Authentication method not supported"); + throw new SmackException("Authentication method not supported"); } authMethodSelectionResponse[1] = (byte) 0x00; // no-authentication method diff --git a/extensions/src/test/java/org/jivesoftware/smackx/ping/PingTest.java b/extensions/src/test/java/org/jivesoftware/smackx/ping/PingTest.java index e497c31b7..d75cf92db 100644 --- a/extensions/src/test/java/org/jivesoftware/smackx/ping/PingTest.java +++ b/extensions/src/test/java/org/jivesoftware/smackx/ping/PingTest.java @@ -19,8 +19,11 @@ package org.jivesoftware.smackx.ping; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertTrue; +import static org.junit.Assert.fail; import org.jivesoftware.smack.DummyConnection; +import org.jivesoftware.smack.SmackException; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.ThreadedDummyConnection; import org.jivesoftware.smack.packet.IQ; import org.jivesoftware.smack.packet.Packet; @@ -70,15 +73,18 @@ public class PingTest extends InitExtensions { } @Test - public void checkSendingPing() throws Exception { + public void checkSendingPing() throws InterruptedException { dummyCon = new DummyConnection(); PingManager pinger = PingManager.getInstanceFor(dummyCon); - pinger.ping("test@myserver.com"); + try { + pinger.ping("test@myserver.com"); + } + catch (SmackException e) { + // Ignore the fact the server won't answer for this unit test. + } Packet sentPacket = dummyCon.getSentPacket(); - assertTrue(sentPacket instanceof Ping); - } @Test @@ -95,17 +101,20 @@ public class PingTest extends InitExtensions { /** * DummyConnection will not reply so it will timeout. - * @throws Exception + * @throws SmackException */ @Test - public void checkFailedPingOnTimeout() throws Exception { + public void checkFailedPingOnTimeout() throws SmackException { dummyCon = new DummyConnection(); PingManager pinger = PingManager.getInstanceFor(dummyCon); - boolean pingSuccess = pinger.ping("test@myserver.com"); - - assertFalse(pingSuccess); - + try { + pinger.ping("test@myserver.com"); + } + catch (NoResponseException e) { + return; + } + fail(); } /** @@ -171,13 +180,18 @@ public class PingTest extends InitExtensions { } @Test - public void checkPingToServerTimeout() throws Exception { + public void checkPingToServerTimeout() throws SmackException { DummyConnection con = new DummyConnection(); PingManager pinger = PingManager.getInstanceFor(con); - boolean pingSuccess = pinger.pingMyServer(); - - assertFalse(pingSuccess); + try { + pinger.pingMyServer(); + } + catch (NoResponseException e) { + return; + } + + fail(); } @Test diff --git a/extensions/src/test/java/org/jivesoftware/smackx/pubsub/ConfigureFormTest.java b/extensions/src/test/java/org/jivesoftware/smackx/pubsub/ConfigureFormTest.java index 939ee0a03..9ce1490fc 100644 --- a/extensions/src/test/java/org/jivesoftware/smackx/pubsub/ConfigureFormTest.java +++ b/extensions/src/test/java/org/jivesoftware/smackx/pubsub/ConfigureFormTest.java @@ -19,8 +19,10 @@ package org.jivesoftware.smackx.pubsub; import static org.junit.Assert.assertEquals; import org.jivesoftware.smack.SmackConfiguration; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smack.ThreadedDummyConnection; import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.packet.XMPPError; import org.jivesoftware.smack.packet.XMPPError.Condition; import org.jivesoftware.smackx.disco.packet.DiscoverInfo; @@ -45,7 +47,7 @@ public class ConfigureFormTest } @Test - public void getConfigFormWithInsufficientPriviliges() throws XMPPException + public void getConfigFormWithInsufficientPriviliges() throws XMPPException, SmackException { ThreadedDummyConnection con = new ThreadedDummyConnection(); PubSubManager mgr = new PubSubManager(con); @@ -65,14 +67,14 @@ public class ConfigureFormTest { node.getNodeConfiguration(); } - catch (XMPPException e) + catch (XMPPErrorException e) { Assert.assertEquals(XMPPError.Type.AUTH, e.getXMPPError().getType()); } } - @Test (expected=XMPPException.class) - public void getConfigFormWithTimeout() throws XMPPException + @Test (expected=SmackException.class) + public void getConfigFormWithTimeout() throws XMPPException, SmackException { ThreadedDummyConnection con = new ThreadedDummyConnection(); PubSubManager mgr = new PubSubManager(con); diff --git a/extensions/src/test/java/org/jivesoftware/util/ConnectionUtils.java b/extensions/src/test/java/org/jivesoftware/util/ConnectionUtils.java index d112e614c..fe80a01ae 100644 --- a/extensions/src/test/java/org/jivesoftware/util/ConnectionUtils.java +++ b/extensions/src/test/java/org/jivesoftware/util/ConnectionUtils.java @@ -20,8 +20,9 @@ import static org.mockito.Matchers.*; import static org.mockito.Mockito.*; import org.jivesoftware.smack.PacketCollector; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smack.XMPPConnection; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.filter.PacketFilter; import org.jivesoftware.smack.packet.IQ; import org.jivesoftware.smack.packet.Packet; @@ -57,10 +58,11 @@ public class ConnectionUtils { * @param initiatorJID the user associated to the XMPP connection * @param xmppServer the XMPP server associated to the XMPP connection * @return a mocked XMPP connection - * @throws XMPPException + * @throws SmackException + * @throws XMPPErrorException */ public static XMPPConnection createMockedConnection(final Protocol protocol, - String initiatorJID, String xmppServer) throws XMPPException { + String initiatorJID, String xmppServer) throws SmackException, XMPPErrorException { // mock XMPP connection XMPPConnection connection = mock(XMPPConnection.class); @@ -105,7 +107,7 @@ public class ConnectionUtils { Packet packet = protocol.getResponses().poll(); if (packet == null) return packet; XMPPError xmppError = packet.getError(); - if (xmppError != null) throw new XMPPException(xmppError); + if (xmppError != null) throw new XMPPErrorException(xmppError); return packet; } }; diff --git a/jingle/src/main/java/org/jivesoftware/smackx/jingle/ContentNegotiator.java b/jingle/src/main/java/org/jivesoftware/smackx/jingle/ContentNegotiator.java index 8cbdf4955..20d3bc872 100644 --- a/jingle/src/main/java/org/jivesoftware/smackx/jingle/ContentNegotiator.java +++ b/jingle/src/main/java/org/jivesoftware/smackx/jingle/ContentNegotiator.java @@ -19,6 +19,7 @@ package org.jivesoftware.smackx.jingle; import java.util.ArrayList; import java.util.List; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smack.XMPPException; import org.jivesoftware.smack.packet.IQ; import org.jivesoftware.smackx.jingle.listeners.JingleListener; @@ -56,7 +57,7 @@ public class ContentNegotiator extends JingleNegotiator { transportNegotiators = new ArrayList(); } - public List dispatchIncomingPacket(IQ iq, String id) throws XMPPException { + public List dispatchIncomingPacket(IQ iq, String id) throws XMPPException, SmackException { List responses = new ArrayList(); // First only process IQ packets that contain stanzas that diff --git a/jingle/src/main/java/org/jivesoftware/smackx/jingle/JingleManager.java b/jingle/src/main/java/org/jivesoftware/smackx/jingle/JingleManager.java index 86ba20257..d31cd4e7a 100644 --- a/jingle/src/main/java/org/jivesoftware/smackx/jingle/JingleManager.java +++ b/jingle/src/main/java/org/jivesoftware/smackx/jingle/JingleManager.java @@ -24,6 +24,7 @@ import java.util.logging.Logger; import org.jivesoftware.smack.ConnectionCreationListener; import org.jivesoftware.smack.PacketListener; import org.jivesoftware.smack.RosterListener; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.XMPPException; import org.jivesoftware.smack.filter.PacketFilter; @@ -44,7 +45,6 @@ import org.jivesoftware.smackx.jingle.nat.TransportCandidate; import org.jivesoftware.smackx.jingle.nat.TransportResolver; import org.jivesoftware.smackx.jingle.packet.Jingle; import org.jivesoftware.smackx.jingle.provider.JingleProvider; -import org.jivesoftware.smackx.disco.packet.DiscoverInfo; /** * Jingle is a session establishment protocol defined in (XEP-0166). @@ -205,8 +205,10 @@ public class JingleManager implements JingleSessionListener { * * @param connection XMPP XMPPConnection to be used * @param jingleMediaManagers an implemeted JingleMediaManager to be used. + * @throws SmackException + * @throws XMPPException */ - public JingleManager(XMPPConnection connection, List jingleMediaManagers) { + public JingleManager(XMPPConnection connection, List jingleMediaManagers) throws XMPPException, SmackException { this.connection = connection; this.jingleMediaManagers = jingleMediaManagers; @@ -307,15 +309,11 @@ public class JingleManager implements JingleSessionListener { * jdoe@example.com * @return a boolean indicating whether the specified user handles Jingle * messages + * @throws SmackException if there was no response from the server. + * @throws XMPPException */ - public static boolean isServiceEnabled(XMPPConnection connection, String userID) { - try { - DiscoverInfo result = ServiceDiscoveryManager.getInstanceFor(connection).discoverInfo(userID); - return result.containsFeature(Jingle.NAMESPACE); - } catch (XMPPException e) { - e.printStackTrace(); - return false; - } + public static boolean isServiceEnabled(XMPPConnection connection, String userID) throws XMPPException, SmackException { + return ServiceDiscoveryManager.getInstanceFor(connection).supportsFeature(userID, Jingle.NAMESPACE); } /** diff --git a/jingle/src/main/java/org/jivesoftware/smackx/jingle/JingleNegotiator.java b/jingle/src/main/java/org/jivesoftware/smackx/jingle/JingleNegotiator.java index 880909d59..732e167ed 100644 --- a/jingle/src/main/java/org/jivesoftware/smackx/jingle/JingleNegotiator.java +++ b/jingle/src/main/java/org/jivesoftware/smackx/jingle/JingleNegotiator.java @@ -20,6 +20,7 @@ import java.util.ArrayList; import java.util.List; import java.util.logging.Logger; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.XMPPException; import org.jivesoftware.smack.packet.IQ; @@ -232,7 +233,7 @@ public abstract class JingleNegotiator { * @return the new packet to send (either a Jingle or an IQ error). * @throws XMPPException */ - public abstract List dispatchIncomingPacket(IQ iq, String id) throws XMPPException; + public abstract List dispatchIncomingPacket(IQ iq, String id) throws XMPPException, SmackException; public void start() { diff --git a/jingle/src/main/java/org/jivesoftware/smackx/jingle/JingleSession.java b/jingle/src/main/java/org/jivesoftware/smackx/jingle/JingleSession.java index e488e65ad..eedc44a88 100644 --- a/jingle/src/main/java/org/jivesoftware/smackx/jingle/JingleSession.java +++ b/jingle/src/main/java/org/jivesoftware/smackx/jingle/JingleSession.java @@ -25,6 +25,7 @@ import java.util.logging.Logger; import org.jivesoftware.smack.ConnectionListener; import org.jivesoftware.smack.PacketListener; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.XMPPException; import org.jivesoftware.smack.filter.PacketFilter; @@ -273,8 +274,9 @@ public class JingleSession extends JingleNegotiator implements MediaReceivedList * @param iq * the packet received * @throws XMPPException + * @throws SmackException */ - public synchronized void receivePacketAndRespond(IQ iq) throws XMPPException { + public synchronized void receivePacketAndRespond(IQ iq) throws XMPPException, SmackException { List responses = new ArrayList(); String responseId = null; @@ -340,8 +342,9 @@ public class JingleSession extends JingleNegotiator implements MediaReceivedList * the packet received * @return the new Jingle packet to send. * @throws XMPPException + * @throws SmackException */ - public List dispatchIncomingPacket(IQ iq, String id) throws XMPPException { + public List dispatchIncomingPacket(IQ iq, String id) throws XMPPException, SmackException { List responses = new ArrayList(); IQ response = null; @@ -676,7 +679,7 @@ public class JingleSession extends JingleNegotiator implements MediaReceivedList public void processPacket(Packet packet) { try { receivePacketAndRespond((IQ) packet); - } catch (XMPPException e) { + } catch (Exception e) { e.printStackTrace(); } } @@ -1110,8 +1113,9 @@ public class JingleSession extends JingleNegotiator implements MediaReceivedList * This is the starting point for intitiating a new session. * * @throws IllegalStateException + * @throws SmackException */ - public void startOutgoing() throws IllegalStateException { + public void startOutgoing() throws IllegalStateException, SmackException { updatePacketListener(); setSessionState(JingleSessionStatePending.getInstance()); diff --git a/jingle/src/main/java/org/jivesoftware/smackx/jingle/JingleSessionRequest.java b/jingle/src/main/java/org/jivesoftware/smackx/jingle/JingleSessionRequest.java index 6b8e72580..e04009218 100644 --- a/jingle/src/main/java/org/jivesoftware/smackx/jingle/JingleSessionRequest.java +++ b/jingle/src/main/java/org/jivesoftware/smackx/jingle/JingleSessionRequest.java @@ -19,6 +19,7 @@ package org.jivesoftware.smackx.jingle; import java.util.logging.Level; import java.util.logging.Logger; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smack.XMPPException; import org.jivesoftware.smackx.jingle.packet.Jingle; @@ -105,8 +106,9 @@ public class JingleSessionRequest { * * @return Returns the IncomingJingleSession on which the * negotiation can be carried out. + * @throws SmackException */ - public synchronized JingleSession accept() throws XMPPException { + public synchronized JingleSession accept() throws XMPPException, SmackException { JingleSession session = null; synchronized (manager) { session = manager.createIncomingJingleSession(this); diff --git a/jingle/src/main/java/org/jivesoftware/smackx/jingle/JingleSessionState.java b/jingle/src/main/java/org/jivesoftware/smackx/jingle/JingleSessionState.java index 9adddad0e..df205ce58 100644 --- a/jingle/src/main/java/org/jivesoftware/smackx/jingle/JingleSessionState.java +++ b/jingle/src/main/java/org/jivesoftware/smackx/jingle/JingleSessionState.java @@ -16,6 +16,7 @@ */ package org.jivesoftware.smackx.jingle; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smack.packet.IQ; import org.jivesoftware.smackx.jingle.packet.Jingle; @@ -54,7 +55,7 @@ public abstract class JingleSessionState { * Process an incoming Jingle Packet. * When you look at the GoF State pattern this method roughly corresponds to example on p310: ProcessOctect(). */ - public abstract IQ processJingle(JingleSession session, Jingle jingle, JingleActionEnum action); + public abstract IQ processJingle(JingleSession session, Jingle jingle, JingleActionEnum action) throws SmackException; /** * For debugging just emit the short name of the class. diff --git a/jingle/src/main/java/org/jivesoftware/smackx/jingle/JingleSessionStateUnknown.java b/jingle/src/main/java/org/jivesoftware/smackx/jingle/JingleSessionStateUnknown.java index 3f5246603..11c425a90 100644 --- a/jingle/src/main/java/org/jivesoftware/smackx/jingle/JingleSessionStateUnknown.java +++ b/jingle/src/main/java/org/jivesoftware/smackx/jingle/JingleSessionStateUnknown.java @@ -16,6 +16,7 @@ */ package org.jivesoftware.smackx.jingle; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smack.XMPPException; import org.jivesoftware.smack.packet.IQ; import org.jivesoftware.smackx.jingle.media.JingleMediaManager; @@ -62,7 +63,7 @@ public class JingleSessionStateUnknown extends JingleSessionState { } - public IQ processJingle(JingleSession session, Jingle jingle, JingleActionEnum action) { + public IQ processJingle(JingleSession session, Jingle jingle, JingleActionEnum action) throws SmackException { IQ response = null; switch (action) { @@ -86,9 +87,10 @@ public class JingleSessionStateUnknown extends JingleSessionState { /** * In the UNKNOWN state we received a action. * This method processes that action. + * @throws SmackException */ - private IQ receiveSessionInitiateAction(JingleSession session, Jingle inJingle) { + private IQ receiveSessionInitiateAction(JingleSession session, Jingle inJingle) throws SmackException { IQ response = null; boolean shouldAck = true; diff --git a/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/BridgedResolver.java b/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/BridgedResolver.java index d0b7891de..4cc1e5e6e 100644 --- a/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/BridgedResolver.java +++ b/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/BridgedResolver.java @@ -16,8 +16,10 @@ */ package org.jivesoftware.smackx.jingle.nat; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smackx.jingle.JingleSession; import java.net.Inet6Address; @@ -94,13 +96,13 @@ public class BridgedResolver extends TransportResolver { setResolveEnd(); } - public void initialize() throws XMPPException { + public void initialize() throws SmackException, XMPPErrorException { clearCandidates(); if (!RTPBridge.serviceAvailable(connection)) { setInitialized(); - throw new XMPPException("No RTP Bridge service available"); + throw new SmackException("No RTP Bridge service available"); } setInitialized(); diff --git a/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/ICEResolver.java b/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/ICEResolver.java index f0c1e269f..5df366122 100644 --- a/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/ICEResolver.java +++ b/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/ICEResolver.java @@ -26,6 +26,7 @@ import java.util.Map; import java.util.Random; import java.util.logging.Logger; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.XMPPException; import org.jivesoftware.smackx.jingle.JingleSession; @@ -89,8 +90,9 @@ public class ICEResolver extends TransportResolver { /** * Resolve the IP and obtain a valid transport method. + * @throws SmackException */ - public synchronized void resolve(JingleSession session) throws XMPPException { + public synchronized void resolve(JingleSession session) throws XMPPException, SmackException { this.setResolveInit(); for (TransportCandidate candidate : this.getCandidatesList()) { diff --git a/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/ICETransportManager.java b/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/ICETransportManager.java index a89c490d0..56703e3c0 100644 --- a/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/ICETransportManager.java +++ b/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/ICETransportManager.java @@ -16,6 +16,7 @@ */ package org.jivesoftware.smackx.jingle.nat; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.XMPPException; import org.jivesoftware.smackx.jingle.JingleSession; @@ -32,12 +33,12 @@ public class ICETransportManager extends JingleTransportManager implements Jingl try { iceResolver.initializeAndWait(); } - catch (XMPPException e) { + catch (Exception e) { e.printStackTrace(); } } - protected TransportResolver createResolver(JingleSession session) { + protected TransportResolver createResolver(JingleSession session) throws SmackException { try { iceResolver.resolve(session); } diff --git a/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/JingleTransportManager.java b/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/JingleTransportManager.java index 1d0fbd787..75a75bc2d 100644 --- a/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/JingleTransportManager.java +++ b/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/JingleTransportManager.java @@ -16,6 +16,7 @@ */ package org.jivesoftware.smackx.jingle.nat; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smack.XMPPException; import org.jivesoftware.smackx.jingle.JingleSession; @@ -51,7 +52,7 @@ public abstract class JingleTransportManager { * * @return the TransportResolver to be used */ - public TransportResolver getResolver(JingleSession session) throws XMPPException { + public TransportResolver getResolver(JingleSession session) throws XMPPException, SmackException { TransportResolver resolver = createResolver(session); if (resolver == null) { resolver = new BasicResolver(); @@ -66,6 +67,6 @@ public abstract class JingleTransportManager { * * @return the TransportResolver */ - protected abstract TransportResolver createResolver(JingleSession session); + protected abstract TransportResolver createResolver(JingleSession session) throws SmackException; } diff --git a/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/RTPBridge.java b/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/RTPBridge.java index 53c6f39c8..45f26a2cb 100644 --- a/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/RTPBridge.java +++ b/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/RTPBridge.java @@ -24,9 +24,10 @@ import java.util.Enumeration; import java.util.Iterator; import java.util.logging.Logger; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.PacketCollector; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.packet.IQ; import org.jivesoftware.smack.provider.IQProvider; import org.jivesoftware.smack.provider.ProviderManager; @@ -407,8 +408,11 @@ public class RTPBridge extends IQ { * * @param connection * @return true if the server supports the RTPBridge service + * @throws XMPPErrorException + * @throws NoResponseException */ - public static boolean serviceAvailable(XMPPConnection connection) { + public static boolean serviceAvailable(XMPPConnection connection) throws NoResponseException, + XMPPErrorException { if (!connection.isConnected()) { return false; @@ -418,7 +422,6 @@ public class RTPBridge extends IQ { ServiceDiscoveryManager disco = ServiceDiscoveryManager .getInstanceFor(connection); - try { // DiscoverItems items = disco.discoverItems(connection.getServiceName()); // Iterator iter = items.getItems(); // while (iter.hasNext()) { @@ -428,17 +431,13 @@ public class RTPBridge extends IQ { // } // } - DiscoverInfo discoInfo = disco.discoverInfo(connection.getServiceName()); - Iterator iter = discoInfo.getIdentities(); - while (iter.hasNext()) { - DiscoverInfo.Identity identity = iter.next(); - if ((identity.getName() != null) && (identity.getName().startsWith("rtpbridge"))) { - return true; - } + DiscoverInfo discoInfo = disco.discoverInfo(connection.getServiceName()); + Iterator iter = discoInfo.getIdentities(); + while (iter.hasNext()) { + DiscoverInfo.Identity identity = iter.next(); + if ((identity.getName() != null) && (identity.getName().startsWith("rtpbridge"))) { + return true; } - } - catch (XMPPException e) { - e.printStackTrace(); } return false; diff --git a/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/STUN.java b/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/STUN.java index 823a37fa6..3825edf2a 100644 --- a/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/STUN.java +++ b/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/STUN.java @@ -19,9 +19,9 @@ package org.jivesoftware.smackx.jingle.nat; import java.util.ArrayList; import java.util.Iterator; import java.util.List; -import java.util.logging.Level; import java.util.logging.Logger; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.PacketCollector; import org.jivesoftware.smack.XMPPException; @@ -206,8 +206,10 @@ public class STUN extends IQ { * * @param connection the connection * @return true if the server support STUN + * @throws SmackException + * @throws XMPPException */ - public static boolean serviceAvailable(XMPPConnection connection) { + public static boolean serviceAvailable(XMPPConnection connection) throws XMPPException, SmackException { if (!connection.isConnected()) { return false; @@ -215,31 +217,26 @@ public class STUN extends IQ { LOGGER.fine("Service listing"); - ServiceDiscoveryManager disco = ServiceDiscoveryManager - .getInstanceFor(connection); - try { - DiscoverItems items = disco.discoverItems(connection.getServiceName()); + ServiceDiscoveryManager disco = ServiceDiscoveryManager.getInstanceFor(connection); + DiscoverItems items = disco.discoverItems(connection.getServiceName()); - Iterator iter = items.getItems(); - while (iter.hasNext()) { - DiscoverItems.Item item = iter.next(); - DiscoverInfo info = disco.discoverInfo(item.getEntityID()); - - Iterator iter2 = info.getIdentities(); - while (iter2.hasNext()) { - DiscoverInfo.Identity identity = iter2.next(); - if (identity.getCategory().equals("proxy") && identity.getType().equals("stun")) - if (info.containsFeature(NAMESPACE)) - return true; - } - - LOGGER.fine(item.getName()+"-"+info.getType()); + Iterator iter = items.getItems(); + while (iter.hasNext()) { + DiscoverItems.Item item = iter.next(); + DiscoverInfo info = disco.discoverInfo(item.getEntityID()); + Iterator iter2 = info.getIdentities(); + while (iter2.hasNext()) { + DiscoverInfo.Identity identity = iter2.next(); + if (identity.getCategory().equals("proxy") && identity.getType().equals("stun")) + if (info.containsFeature(NAMESPACE)) + return true; } + + LOGGER.fine(item.getName() + "-" + info.getType()); + } - catch (XMPPException e) { - LOGGER.log(Level.SEVERE, "serviceAvailable", e); - } + return false; } diff --git a/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/STUNTransportManager.java b/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/STUNTransportManager.java index 4b902b911..d0d1a275f 100644 --- a/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/STUNTransportManager.java +++ b/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/STUNTransportManager.java @@ -32,7 +32,7 @@ public class STUNTransportManager extends JingleTransportManager { }; try { stunResolver.initializeAndWait(); - } catch (XMPPException e) { + } catch (Exception e) { e.printStackTrace(); } } diff --git a/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/TransportNegotiator.java b/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/TransportNegotiator.java index 77c73a8bf..b6a17cfaa 100644 --- a/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/TransportNegotiator.java +++ b/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/TransportNegotiator.java @@ -23,6 +23,7 @@ import java.util.Iterator; import java.util.List; import java.util.logging.Logger; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smack.XMPPException; import org.jivesoftware.smack.packet.IQ; import org.jivesoftware.smackx.jingle.ContentNegotiator; @@ -160,7 +161,7 @@ public abstract class TransportNegotiator extends JingleNegotiator { try { sendTransportCandidatesOffer(); setNegotiatorState(JingleNegotiatorState.PENDING); - } catch (XMPPException e) { + } catch (Exception e) { // TODO Auto-generated catch block e.printStackTrace(); } @@ -528,8 +529,9 @@ public abstract class TransportNegotiator extends JingleNegotiator { * Create a Jingle packet where we announce our transport candidates. * * @throws XMPPException + * @throws SmackException */ - private void sendTransportCandidatesOffer() throws XMPPException { + private void sendTransportCandidatesOffer() throws XMPPException, SmackException { List notOffered = resolver.getCandidatesList(); notOffered.removeAll(offeredCandidates); @@ -572,8 +574,9 @@ public abstract class TransportNegotiator extends JingleNegotiator { * @param iq the packet received * @return the new Jingle packet to send. * @throws XMPPException + * @throws SmackException */ - public final List dispatchIncomingPacket(IQ iq, String id) throws XMPPException { + public final List dispatchIncomingPacket(IQ iq, String id) throws XMPPException, SmackException { List responses = new ArrayList(); IQ response = null; @@ -641,8 +644,9 @@ public abstract class TransportNegotiator extends JingleNegotiator { * * @return an IQ packet * @throws XMPPException + * @throws SmackException */ - private Jingle receiveResult(IQ iq) throws XMPPException { + private Jingle receiveResult(IQ iq) throws XMPPException, SmackException { Jingle response = null; sendTransportCandidatesOffer(); @@ -655,8 +659,9 @@ public abstract class TransportNegotiator extends JingleNegotiator { * @param jingle * @param jingleTransport * @return the iq + * @throws SmackException */ - private IQ receiveSessionInitiateAction(Jingle jingle) throws XMPPException { + private IQ receiveSessionInitiateAction(Jingle jingle) throws XMPPException, SmackException { IQ response = null; // Parse the Jingle and get any proposed transport candidates diff --git a/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/TransportResolver.java b/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/TransportResolver.java index 61c5126fc..42631614f 100644 --- a/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/TransportResolver.java +++ b/jingle/src/main/java/org/jivesoftware/smackx/jingle/nat/TransportResolver.java @@ -24,6 +24,7 @@ import java.util.Iterator; import java.util.List; import java.util.logging.Logger; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smack.XMPPException; import org.jivesoftware.smackx.jingle.JingleSession; @@ -89,12 +90,12 @@ public abstract class TransportResolver { /** * Initialize the Resolver */ - public abstract void initialize() throws XMPPException; + public abstract void initialize() throws XMPPException, SmackException; /** * Start a the resolution. */ - public abstract void resolve(JingleSession session) throws XMPPException; + public abstract void resolve(JingleSession session) throws XMPPException, SmackException; /** * Clear the list of candidates and start a new resolution process. @@ -352,8 +353,9 @@ public abstract class TransportResolver { /** * Initialize Transport Resolver and wait until it is complete unitialized. + * @throws SmackException */ - public void initializeAndWait() throws XMPPException { + public void initializeAndWait() throws XMPPException, SmackException { this.initialize(); try { LOGGER.fine("Initializing transport resolver..."); diff --git a/jingle/src/main/java/org/jivesoftware/smackx/jingle/provider/JingleProvider.java b/jingle/src/main/java/org/jivesoftware/smackx/jingle/provider/JingleProvider.java index aa48a5885..1bda6221f 100644 --- a/jingle/src/main/java/org/jivesoftware/smackx/jingle/provider/JingleProvider.java +++ b/jingle/src/main/java/org/jivesoftware/smackx/jingle/provider/JingleProvider.java @@ -17,7 +17,7 @@ package org.jivesoftware.smackx.jingle.provider; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.SmackException; import org.jivesoftware.smack.packet.IQ; import org.jivesoftware.smack.provider.IQProvider; import org.jivesoftware.smackx.jingle.JingleActionEnum; @@ -101,12 +101,12 @@ public class JingleProvider implements IQProvider { } else if (namespace.equals(JingleTransport.Ice.NAMESPACE)) { currentContent.addJingleTransport((JingleTransport) jtpIce.parseExtension(parser)); } else { - throw new XMPPException("Unknown transport namespace \"" + namespace + "\" in Jingle packet."); + throw new SmackException("Unknown transport namespace \"" + namespace + "\" in Jingle packet."); } } else if (namespace.equals(JingleContentInfo.Audio.NAMESPACE)) { jingle.setContentInfo((JingleContentInfo) jmipAudio.parseExtension(parser)); } else { - throw new XMPPException("Unknown combination of namespace \"" + namespace + "\" and element name \"" + throw new SmackException("Unknown combination of namespace \"" + namespace + "\" and element name \"" + elementName + "\" in Jingle packet."); } diff --git a/legacy/src/main/java/org/jivesoftware/smackx/workgroup/agent/Agent.java b/legacy/src/main/java/org/jivesoftware/smackx/workgroup/agent/Agent.java index 0198e66bf..4b87a91c0 100644 --- a/legacy/src/main/java/org/jivesoftware/smackx/workgroup/agent/Agent.java +++ b/legacy/src/main/java/org/jivesoftware/smackx/workgroup/agent/Agent.java @@ -19,8 +19,9 @@ package org.jivesoftware.smackx.workgroup.agent; import org.jivesoftware.smackx.workgroup.packet.AgentInfo; import org.jivesoftware.smackx.workgroup.packet.AgentWorkgroups; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.packet.IQ; import java.util.Collection; @@ -34,7 +35,7 @@ public class Agent { private XMPPConnection connection; private String workgroupJID; - public static Collection getWorkgroups(String serviceJID, String agentJID, XMPPConnection connection) throws XMPPException { + public static Collection getWorkgroups(String serviceJID, String agentJID, XMPPConnection connection) throws NoResponseException, XMPPErrorException { AgentWorkgroups request = new AgentWorkgroups(agentJID); request.setTo(serviceJID); AgentWorkgroups response = (AgentWorkgroups) connection.createPacketCollectorAndSend(request).nextResultOrThrow(); @@ -62,8 +63,10 @@ public class Agent { * Return the agents name. * * @return - the agents name. + * @throws XMPPErrorException + * @throws NoResponseException */ - public String getName() throws XMPPException { + public String getName() throws NoResponseException, XMPPErrorException { AgentInfo agentInfo = new AgentInfo(); agentInfo.setType(IQ.Type.GET); agentInfo.setTo(workgroupJID); @@ -79,10 +82,10 @@ public class Agent { * error code. * * @param newName the new name of the agent. - * @throws XMPPException if the agent is not allowed to change his name or no response was - * obtained from the server. + * @throws XMPPErrorException + * @throws NoResponseException */ - public void setName(String newName) throws XMPPException { + public void setName(String newName) throws NoResponseException, XMPPErrorException { AgentInfo agentInfo = new AgentInfo(); agentInfo.setType(IQ.Type.SET); agentInfo.setTo(workgroupJID); diff --git a/legacy/src/main/java/org/jivesoftware/smackx/workgroup/agent/AgentSession.java b/legacy/src/main/java/org/jivesoftware/smackx/workgroup/agent/AgentSession.java index 3c768f72e..2b0f7628f 100644 --- a/legacy/src/main/java/org/jivesoftware/smackx/workgroup/agent/AgentSession.java +++ b/legacy/src/main/java/org/jivesoftware/smackx/workgroup/agent/AgentSession.java @@ -17,6 +17,7 @@ package org.jivesoftware.smackx.workgroup.agent; + import org.jivesoftware.smackx.muc.packet.MUCUser; import org.jivesoftware.smackx.search.ReportedData; import org.jivesoftware.smackx.workgroup.MetaData; @@ -33,6 +34,8 @@ import org.jivesoftware.smackx.workgroup.settings.GenericSettings; import org.jivesoftware.smackx.workgroup.settings.SearchSettings; import org.jivesoftware.smackx.xdata.Form; import org.jivesoftware.smack.*; +import org.jivesoftware.smack.SmackException.NoResponseException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.filter.*; import org.jivesoftware.smack.packet.*; import org.jivesoftware.smack.util.StringUtils; @@ -198,8 +201,9 @@ public class AgentSession { * @param key the meta data key * @param val the non-null meta data value * @throws XMPPException if an exception occurs. + * @throws SmackException */ - public void setMetaData(String key, String val) throws XMPPException { + public void setMetaData(String key, String val) throws XMPPException, SmackException { synchronized (this.metaData) { List oldVals = metaData.get(key); @@ -217,8 +221,9 @@ public class AgentSession { * * @param key the meta data key. * @throws XMPPException if an exception occurs. + * @throws SmackException */ - public void removeMetaData(String key) throws XMPPException { + public void removeMetaData(String key) throws XMPPException, SmackException { synchronized (this.metaData) { List oldVal = metaData.remove(key); @@ -246,8 +251,10 @@ public class AgentSession { * * @param online true to set the agent as online with the workgroup. * @throws XMPPException if an error occurs setting the online status. + * @throws SmackException assertEquals(SmackException.Type.NO_RESPONSE_FROM_SERVER, e.getType()); + return; */ - public void setOnline(boolean online) throws XMPPException { + public void setOnline(boolean online) throws XMPPException, SmackException { // If the online status hasn't changed, do nothing. if (this.online == online) { return; @@ -305,9 +312,10 @@ public class AgentSession { * @param presenceMode the presence mode of the agent. * @param maxChats the maximum number of chats the agent is willing to accept. * @throws XMPPException if an error occurs setting the agent status. + * @throws SmackException * @throws IllegalStateException if the agent is not online with the workgroup. */ - public void setStatus(Presence.Mode presenceMode, int maxChats) throws XMPPException { + public void setStatus(Presence.Mode presenceMode, int maxChats) throws XMPPException, SmackException { setStatus(presenceMode, maxChats, null); } @@ -330,11 +338,12 @@ public class AgentSession { * @param presenceMode the presence mode of the agent. * @param maxChats the maximum number of chats the agent is willing to accept. * @param status sets the status message of the presence update. - * @throws XMPPException if an error occurs setting the agent status. + * @throws XMPPErrorException + * @throws NoResponseException * @throws IllegalStateException if the agent is not online with the workgroup. */ public void setStatus(Presence.Mode presenceMode, int maxChats, String status) - throws XMPPException { + throws NoResponseException, XMPPErrorException { if (!online) { throw new IllegalStateException("Cannot set status when the agent is not online."); } @@ -354,12 +363,14 @@ public class AgentSession { } // Send information about max chats and current chats as a packet extension. DefaultPacketExtension agentStatus = new DefaultPacketExtension(AgentStatus.ELEMENT_NAME, - AgentStatus.NAMESPACE); + AgentStatus.NAMESPACE); agentStatus.setValue("max-chats", "" + maxChats); presence.addExtension(agentStatus); presence.addExtension(new MetaData(this.metaData)); - PacketCollector collector = this.connection.createPacketCollector(new AndFilter(new PacketTypeFilter(Presence.class), FromMatchesFilter.create(workgroupJID))); + PacketCollector collector = this.connection.createPacketCollector(new AndFilter( + new PacketTypeFilter(Presence.class), + FromMatchesFilter.create(workgroupJID))); this.connection.sendPacket(presence); @@ -379,10 +390,11 @@ public class AgentSession { * * @param presenceMode the presence mode of the agent. * @param status sets the status message of the presence update. - * @throws XMPPException if an error occurs setting the agent status. + * @throws XMPPErrorException + * @throws NoResponseException * @throws IllegalStateException if the agent is not online with the workgroup. */ - public void setStatus(Presence.Mode presenceMode, String status) throws XMPPException { + public void setStatus(Presence.Mode presenceMode, String status) throws NoResponseException, XMPPErrorException { if (!online) { throw new IllegalStateException("Cannot set status when the agent is not online."); } @@ -433,8 +445,9 @@ public class AgentSession { * @param userID the id of the user to get his conversations. * @return the transcripts of a given user. * @throws XMPPException if an error occurs while getting the information. + * @throws SmackException */ - public Transcripts getTranscripts(String userID) throws XMPPException { + public Transcripts getTranscripts(String userID) throws XMPPException, SmackException { return transcriptManager.getTranscripts(workgroupJID, userID); } @@ -444,8 +457,9 @@ public class AgentSession { * @param sessionID the id of the session to get the full transcript. * @return the full conversation transcript of a given session. * @throws XMPPException if an error occurs while getting the information. + * @throws SmackException */ - public Transcript getTranscript(String sessionID) throws XMPPException { + public Transcript getTranscript(String sessionID) throws XMPPException, SmackException { return transcriptManager.getTranscript(workgroupJID, sessionID); } @@ -456,8 +470,9 @@ public class AgentSession { * * @return the Form to use for searching transcripts. * @throws XMPPException if an error occurs while sending the request to the server. + * @throws SmackException */ - public Form getTranscriptSearchForm() throws XMPPException { + public Form getTranscriptSearchForm() throws XMPPException, SmackException { return transcriptSearchManager.getSearchForm(StringUtils.parseServer(workgroupJID)); } @@ -468,9 +483,10 @@ public class AgentSession { * * @param completedForm the filled out search form. * @return the result of the transcript search. - * @throws XMPPException if an error occurs while submiting the search to the server. + * @throws SmackException + * @throws XMPPException */ - public ReportedData searchTranscripts(Form completedForm) throws XMPPException { + public ReportedData searchTranscripts(Form completedForm) throws XMPPException, SmackException { return transcriptSearchManager.submitSearch(StringUtils.parseServer(workgroupJID), completedForm); } @@ -482,9 +498,10 @@ public class AgentSession { * * @param roomID the room to get information about its occupants. * @return information about the occupants of the specified room. - * @throws XMPPException if an error occurs while getting information from the server. + * @throws XMPPErrorException + * @throws NoResponseException */ - public OccupantsInfo getOccupantsInfo(String roomID) throws XMPPException { + public OccupantsInfo getOccupantsInfo(String roomID) throws NoResponseException, XMPPErrorException { OccupantsInfo request = new OccupantsInfo(roomID); request.setType(IQ.Type.GET); request.setTo(workgroupJID); @@ -758,9 +775,10 @@ public class AgentSession { * * @param sessionID the session id of a Chat Session. * @param note the chat note to add. - * @throws XMPPException is thrown if an error occurs while adding the note. + * @throws XMPPErrorException + * @throws NoResponseException */ - public void setNote(String sessionID, String note) throws XMPPException { + public void setNote(String sessionID, String note) throws NoResponseException, XMPPErrorException { note = ChatNotes.replace(note, "\n", "\\n"); note = StringUtils.escapeForXML(note); @@ -777,9 +795,10 @@ public class AgentSession { * * @param sessionID the sessionID of the chat session. * @return the ChatNote associated with a given chat session. - * @throws XMPPException if an error occurs while retrieving the ChatNote. + * @throws XMPPErrorException if an error occurs while retrieving the ChatNote. + * @throws NoResponseException */ - public ChatNotes getNote(String sessionID) throws XMPPException { + public ChatNotes getNote(String sessionID) throws NoResponseException, XMPPErrorException { ChatNotes request = new ChatNotes(); request.setType(IQ.Type.GET); request.setTo(workgroupJID); @@ -819,9 +838,10 @@ public class AgentSession { * Asks the workgroup for it's Search Settings. * * @return SearchSettings the search settings for this workgroup. - * @throws XMPPException if an error occurs while getting information from the server. + * @throws XMPPErrorException + * @throws NoResponseException */ - public SearchSettings getSearchSettings() throws XMPPException { + public SearchSettings getSearchSettings() throws NoResponseException, XMPPErrorException { SearchSettings request = new SearchSettings(); request.setType(IQ.Type.GET); request.setTo(workgroupJID); @@ -835,9 +855,10 @@ public class AgentSession { * * @param global true to retrieve global macros, otherwise false for personal macros. * @return MacroGroup the root macro group. - * @throws XMPPException if an error occurs while getting information from the server. + * @throws XMPPErrorException if an error occurs while getting information from the server. + * @throws NoResponseException */ - public MacroGroup getMacros(boolean global) throws XMPPException { + public MacroGroup getMacros(boolean global) throws NoResponseException, XMPPErrorException { Macros request = new Macros(); request.setType(IQ.Type.GET); request.setTo(workgroupJID); @@ -851,9 +872,10 @@ public class AgentSession { * Persists the Personal Macro for an agent. * * @param group the macro group to save. - * @throws XMPPException if an error occurs while getting information from the server. + * @throws XMPPErrorException + * @throws NoResponseException */ - public void saveMacros(MacroGroup group) throws XMPPException { + public void saveMacros(MacroGroup group) throws NoResponseException, XMPPErrorException { Macros request = new Macros(); request.setType(IQ.Type.SET); request.setTo(workgroupJID); @@ -904,11 +926,12 @@ public class AgentSession { * @param invitee JID of entity that will get the invitation. * @param sessionID ID of the support session that the invitee is being invited. * @param reason the reason of the invitation. - * @throws XMPPException if the sender of the invitation is not an agent or the service failed to process + * @throws XMPPErrorException if the sender of the invitation is not an agent or the service failed to process * the request. + * @throws NoResponseException */ - public void sendRoomInvitation(RoomInvitation.Type type, String invitee, String sessionID, String reason) - throws XMPPException { + public void sendRoomInvitation(RoomInvitation.Type type, String invitee, String sessionID, String reason) throws NoResponseException, XMPPErrorException + { final RoomInvitation invitation = new RoomInvitation(type, invitee, sessionID, reason); IQ iq = new IQ() { @@ -944,11 +967,12 @@ public class AgentSession { * @param invitee JID of entity that will get the invitation. * @param sessionID ID of the support session that the invitee is being invited. * @param reason the reason of the invitation. - * @throws XMPPException if the sender of the invitation is not an agent or the service failed to process + * @throws XMPPErrorException if the sender of the invitation is not an agent or the service failed to process * the request. + * @throws NoResponseException */ - public void sendRoomTransfer(RoomTransfer.Type type, String invitee, String sessionID, String reason) - throws XMPPException { + public void sendRoomTransfer(RoomTransfer.Type type, String invitee, String sessionID, String reason) throws NoResponseException, XMPPErrorException + { final RoomTransfer transfer = new RoomTransfer(type, invitee, sessionID, reason); IQ iq = new IQ() { @@ -968,10 +992,11 @@ public class AgentSession { * * @param con the XMPPConnection to use. * @param query an optional query object used to tell the server what metadata to retrieve. This can be null. - * @throws XMPPException if an error occurs while sending the request to the server. * @return the settings for the workgroup. + * @throws XMPPErrorException if an error occurs while sending the request to the server. + * @throws NoResponseException */ - public GenericSettings getGenericSettings(XMPPConnection con, String query) throws XMPPException { + public GenericSettings getGenericSettings(XMPPConnection con, String query) throws NoResponseException, XMPPErrorException { GenericSettings setting = new GenericSettings(); setting.setType(IQ.Type.GET); setting.setTo(workgroupJID); @@ -981,7 +1006,7 @@ public class AgentSession { return response; } - public boolean hasMonitorPrivileges(XMPPConnection con) throws XMPPException { + public boolean hasMonitorPrivileges(XMPPConnection con) throws NoResponseException, XMPPErrorException { MonitorPacket request = new MonitorPacket(); request.setType(IQ.Type.GET); request.setTo(workgroupJID); @@ -990,7 +1015,7 @@ public class AgentSession { return response.isMonitor(); } - public void makeRoomOwner(XMPPConnection con, String sessionID) throws XMPPException { + public void makeRoomOwner(XMPPConnection con, String sessionID) throws NoResponseException, XMPPErrorException { MonitorPacket request = new MonitorPacket(); request.setType(IQ.Type.SET); request.setTo(workgroupJID); diff --git a/legacy/src/main/java/org/jivesoftware/smackx/workgroup/agent/TranscriptManager.java b/legacy/src/main/java/org/jivesoftware/smackx/workgroup/agent/TranscriptManager.java index f07764ca4..ed1c2f291 100644 --- a/legacy/src/main/java/org/jivesoftware/smackx/workgroup/agent/TranscriptManager.java +++ b/legacy/src/main/java/org/jivesoftware/smackx/workgroup/agent/TranscriptManager.java @@ -19,8 +19,9 @@ package org.jivesoftware.smackx.workgroup.agent; import org.jivesoftware.smackx.workgroup.packet.Transcript; import org.jivesoftware.smackx.workgroup.packet.Transcripts; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; /** * A TranscriptManager helps to retrieve the full conversation transcript of a given session @@ -42,9 +43,10 @@ public class TranscriptManager { * @param sessionID the id of the session to get the full transcript. * @param workgroupJID the JID of the workgroup that will process the request. * @return the full conversation transcript of a given session. - * @throws XMPPException if an error occurs while getting the information. + * @throws XMPPErrorException + * @throws NoResponseException */ - public Transcript getTranscript(String workgroupJID, String sessionID) throws XMPPException { + public Transcript getTranscript(String workgroupJID, String sessionID) throws NoResponseException, XMPPErrorException { Transcript request = new Transcript(sessionID); request.setTo(workgroupJID); Transcript response = (Transcript) connection.createPacketCollectorAndSend(request).nextResultOrThrow(); @@ -58,9 +60,10 @@ public class TranscriptManager { * @param userID the id of the user to get his conversations. * @param workgroupJID the JID of the workgroup that will process the request. * @return the transcripts of a given user. - * @throws XMPPException if an error occurs while getting the information. + * @throws XMPPErrorException + * @throws NoResponseException */ - public Transcripts getTranscripts(String workgroupJID, String userID) throws XMPPException { + public Transcripts getTranscripts(String workgroupJID, String userID) throws NoResponseException, XMPPErrorException { Transcripts request = new Transcripts(userID); request.setTo(workgroupJID); Transcripts response = (Transcripts) connection.createPacketCollectorAndSend(request).nextResultOrThrow(); diff --git a/legacy/src/main/java/org/jivesoftware/smackx/workgroup/agent/TranscriptSearchManager.java b/legacy/src/main/java/org/jivesoftware/smackx/workgroup/agent/TranscriptSearchManager.java index 05750f294..1c2c636d6 100644 --- a/legacy/src/main/java/org/jivesoftware/smackx/workgroup/agent/TranscriptSearchManager.java +++ b/legacy/src/main/java/org/jivesoftware/smackx/workgroup/agent/TranscriptSearchManager.java @@ -20,8 +20,9 @@ package org.jivesoftware.smackx.workgroup.agent; import org.jivesoftware.smackx.search.ReportedData; import org.jivesoftware.smackx.workgroup.packet.TranscriptSearch; import org.jivesoftware.smackx.xdata.Form; +import org.jivesoftware.smack.SmackException.NoResponseException; import org.jivesoftware.smack.XMPPConnection; -import org.jivesoftware.smack.XMPPException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.packet.IQ; /** @@ -45,9 +46,10 @@ public class TranscriptSearchManager { * * @param serviceJID the address of the workgroup service. * @return the Form to use for searching transcripts. - * @throws XMPPException if an error occurs while sending the request to the server. + * @throws XMPPErrorException + * @throws NoResponseException */ - public Form getSearchForm(String serviceJID) throws XMPPException { + public Form getSearchForm(String serviceJID) throws NoResponseException, XMPPErrorException { TranscriptSearch search = new TranscriptSearch(); search.setType(IQ.Type.GET); search.setTo(serviceJID); @@ -65,9 +67,10 @@ public class TranscriptSearchManager { * @param serviceJID the address of the workgroup service. * @param completedForm the filled out search form. * @return the result of the transcript search. - * @throws XMPPException if an error occurs while submiting the search to the server. + * @throws XMPPErrorException + * @throws NoResponseException */ - public ReportedData submitSearch(String serviceJID, Form completedForm) throws XMPPException { + public ReportedData submitSearch(String serviceJID, Form completedForm) throws NoResponseException, XMPPErrorException { TranscriptSearch search = new TranscriptSearch(); search.setType(IQ.Type.GET); search.setTo(serviceJID); diff --git a/legacy/src/main/java/org/jivesoftware/smackx/workgroup/user/Workgroup.java b/legacy/src/main/java/org/jivesoftware/smackx/workgroup/user/Workgroup.java index 869383865..8c2780e85 100644 --- a/legacy/src/main/java/org/jivesoftware/smackx/workgroup/user/Workgroup.java +++ b/legacy/src/main/java/org/jivesoftware/smackx/workgroup/user/Workgroup.java @@ -29,6 +29,8 @@ import org.jivesoftware.smackx.xdata.Form; import org.jivesoftware.smackx.xdata.FormField; import org.jivesoftware.smackx.xdata.packet.DataForm; import org.jivesoftware.smack.*; +import org.jivesoftware.smack.SmackException.NoResponseException; +import org.jivesoftware.smack.XMPPException.XMPPErrorException; import org.jivesoftware.smack.filter.*; import org.jivesoftware.smack.packet.*; import org.jivesoftware.smack.util.StringUtils; @@ -153,9 +155,10 @@ public class Workgroup { * available only when agents are available for this workgroup. * * @return true if the workgroup is available for receiving new requests. - * @throws XMPPException + * @throws XMPPErrorException + * @throws NoResponseException */ - public boolean isAvailable() throws XMPPException { + public boolean isAvailable() throws NoResponseException, XMPPErrorException { Presence directedPresence = new Presence(Presence.Type.available); directedPresence.setTo(workgroupJID); PacketFilter typeFilter = new PacketTypeFilter(Presence.class); @@ -230,8 +233,9 @@ public class Workgroup { * @throws XMPPException if an error occured joining the queue. An error may indicate * that a connection failure occured or that the server explicitly rejected the * request to join the queue. + * @throws SmackException */ - public void joinQueue() throws XMPPException { + public void joinQueue() throws XMPPException, SmackException { joinQueue(null); } @@ -267,8 +271,9 @@ public class Workgroup { * @throws XMPPException if an error occured joining the queue. An error may indicate * that a connection failure occured or that the server explicitly rejected the * request to join the queue. + * @throws SmackException */ - public void joinQueue(Form answerForm) throws XMPPException { + public void joinQueue(Form answerForm) throws XMPPException, SmackException { joinQueue(answerForm, null); } @@ -301,11 +306,12 @@ public class Workgroup { * @param answerForm the completed form associated with the join reqest. * @param userID String that represents the ID of the user when using anonymous sessions * or null if a userID should not be used. - * @throws XMPPException if an error occured joining the queue. An error may indicate + * @throws XMPPErrorException if an error occured joining the queue. An error may indicate * that a connection failure occured or that the server explicitly rejected the * request to join the queue. + * @throws NoResponseException */ - public void joinQueue(Form answerForm, String userID) throws XMPPException { + public void joinQueue(Form answerForm, String userID) throws NoResponseException, XMPPErrorException { // If already in the queue ignore the join request. if (inQueue) { throw new IllegalStateException("Already in queue " + workgroupJID); @@ -350,8 +356,9 @@ public class Workgroup { * @throws XMPPException if an error occured joining the queue. An error may indicate * that a connection failure occured or that the server explicitly rejected the * request to join the queue. + * @throws SmackException */ - public void joinQueue(Map metadata, String userID) throws XMPPException { + public void joinQueue(Map metadata, String userID) throws XMPPException, SmackException { // If already in the queue ignore the join request. if (inQueue) { throw new IllegalStateException("Already in queue " + workgroupJID); @@ -383,10 +390,11 @@ public class Workgroup { * under certain circumstances -- for example, if they no longer wish to be routed * to an agent because they've been waiting too long. * - * @throws XMPPException if an error occured trying to send the depart queue + * @throws XMPPErrorException if an error occured trying to send the depart queue * request to the server. + * @throws NoResponseException */ - public void departQueue() throws XMPPException { + public void departQueue() throws NoResponseException, XMPPErrorException { // If not in the queue ignore the depart request. if (!inQueue) { return; @@ -589,8 +597,9 @@ public class Workgroup { * @param key the key to find. * @return the ChatSetting if found, otherwise false. * @throws XMPPException if an error occurs while getting information from the server. + * @throws SmackException */ - public ChatSetting getChatSetting(String key) throws XMPPException { + public ChatSetting getChatSetting(String key) throws XMPPException, SmackException { ChatSettings chatSettings = getChatSettings(key, -1); return chatSettings.getFirstEntry(); } @@ -601,8 +610,9 @@ public class Workgroup { * @param type the type of ChatSettings to return. * @return the ChatSettings of given type, otherwise null. * @throws XMPPException if an error occurs while getting information from the server. + * @throws SmackException */ - public ChatSettings getChatSettings(int type) throws XMPPException { + public ChatSettings getChatSettings(int type) throws XMPPException, SmackException { return getChatSettings(null, type); } @@ -611,8 +621,9 @@ public class Workgroup { * * @return all ChatSettings of a given workgroup. * @throws XMPPException if an error occurs while getting information from the server. + * @throws SmackException */ - public ChatSettings getChatSettings() throws XMPPException { + public ChatSettings getChatSettings() throws XMPPException, SmackException { return getChatSettings(null, -1); } @@ -621,9 +632,10 @@ public class Workgroup { * Asks the workgroup for it's Chat Settings. * * @return key specify a key to retrieve only that settings. Otherwise for all settings, key should be null. - * @throws XMPPException if an error occurs while getting information from the server. + * @throws NoResponseException + * @throws XMPPErrorException if an error occurs while getting information from the server. */ - private ChatSettings getChatSettings(String key, int type) throws XMPPException { + private ChatSettings getChatSettings(String key, int type) throws NoResponseException, XMPPErrorException { ChatSettings request = new ChatSettings(); if (key != null) { request.setKey(key); @@ -644,8 +656,9 @@ public class Workgroup { * to see if the email service has been configured and is available. * * @return true if the email service is available, otherwise return false. + * @throws SmackException */ - public boolean isEmailAvailable() { + public boolean isEmailAvailable() throws SmackException { ServiceDiscoveryManager discoManager = ServiceDiscoveryManager.getInstanceFor(connection); try { @@ -662,9 +675,10 @@ public class Workgroup { * Asks the workgroup for it's Offline Settings. * * @return offlineSettings the offline settings for this workgroup. - * @throws XMPPException if an error occurs while getting information from the server. + * @throws XMPPErrorException + * @throws NoResponseException */ - public OfflineSettings getOfflineSettings() throws XMPPException { + public OfflineSettings getOfflineSettings() throws NoResponseException, XMPPErrorException { OfflineSettings request = new OfflineSettings(); request.setType(IQ.Type.GET); request.setTo(workgroupJID); @@ -678,9 +692,10 @@ public class Workgroup { * Asks the workgroup for it's Sound Settings. * * @return soundSettings the sound settings for the specified workgroup. - * @throws XMPPException if an error occurs while getting information from the server. + * @throws XMPPErrorException + * @throws NoResponseException */ - public SoundSettings getSoundSettings() throws XMPPException { + public SoundSettings getSoundSettings() throws NoResponseException, XMPPErrorException { SoundSettings request = new SoundSettings(); request.setType(IQ.Type.GET); request.setTo(workgroupJID); @@ -693,9 +708,10 @@ public class Workgroup { * Asks the workgroup for it's Properties * * @return the WorkgroupProperties for the specified workgroup. - * @throws XMPPException if an error occurs while getting information from the server. + * @throws XMPPErrorException + * @throws NoResponseException */ - public WorkgroupProperties getWorkgroupProperties() throws XMPPException { + public WorkgroupProperties getWorkgroupProperties() throws NoResponseException, XMPPErrorException { WorkgroupProperties request = new WorkgroupProperties(); request.setType(IQ.Type.GET); request.setTo(workgroupJID); @@ -710,9 +726,10 @@ public class Workgroup { * * @param jid the jid of the user who's information you would like the workgroup to retreive. * @return the WorkgroupProperties for the specified workgroup. - * @throws XMPPException if an error occurs while getting information from the server. + * @throws XMPPErrorException + * @throws NoResponseException */ - public WorkgroupProperties getWorkgroupProperties(String jid) throws XMPPException { + public WorkgroupProperties getWorkgroupProperties(String jid) throws NoResponseException, XMPPErrorException { WorkgroupProperties request = new WorkgroupProperties(); request.setJid(jid); request.setType(IQ.Type.GET); @@ -730,9 +747,10 @@ public class Workgroup { * for future submissions. * * @return the Form to use for searching transcripts. - * @throws XMPPException if an error occurs while sending the request to the server. + * @throws XMPPErrorException + * @throws NoResponseException */ - public Form getWorkgroupForm() throws XMPPException { + public Form getWorkgroupForm() throws NoResponseException, XMPPErrorException { WorkgroupForm workgroupForm = new WorkgroupForm(); workgroupForm.setType(IQ.Type.GET); workgroupForm.setTo(workgroupJID); diff --git a/tcp/src/main/java/org/jivesoftware/smack/PacketReader.java b/tcp/src/main/java/org/jivesoftware/smack/PacketReader.java index 76159ee06..bf5c392e7 100644 --- a/tcp/src/main/java/org/jivesoftware/smack/PacketReader.java +++ b/tcp/src/main/java/org/jivesoftware/smack/PacketReader.java @@ -20,13 +20,16 @@ package org.jivesoftware.smack; import org.jivesoftware.smack.packet.IQ; import org.jivesoftware.smack.packet.Packet; import org.jivesoftware.smack.packet.Presence; -import org.jivesoftware.smack.packet.XMPPError; import org.jivesoftware.smack.parsing.ParsingExceptionCallback; import org.jivesoftware.smack.parsing.UnparsablePacket; import org.jivesoftware.smack.sasl.SASLMechanism.Challenge; -import org.jivesoftware.smack.sasl.SASLMechanism.Failure; +import org.jivesoftware.smack.sasl.SASLMechanism.SASLFailure; import org.jivesoftware.smack.sasl.SASLMechanism.Success; import org.jivesoftware.smack.util.PacketParserUtils; + +import org.jivesoftware.smack.SmackException.NoResponseException; +import org.jivesoftware.smack.SmackException.SecurityRequiredException; +import org.jivesoftware.smack.XMPPException.StreamErrorException; import org.xmlpull.v1.XmlPullParserFactory; import org.xmlpull.v1.XmlPullParser; import org.xmlpull.v1.XmlPullParserException; @@ -82,11 +85,10 @@ class PacketReader { * Starts the packet reader thread and returns once a connection to the server * has been established. A connection will be attempted for a maximum of five * seconds. An XMPPException will be thrown if the connection fails. - * - * @throws XMPPException if the server fails to send an opening stream back - * for more than five seconds. + * @throws NoResponseException if the server fails to send an opening stream back + * within packetReplyTimeout*3. */ - synchronized public void startup() throws XMPPException { + synchronized public void startup() throws NoResponseException { readerThread.start(); // Wait for stream tag before returning. We'll wait a couple of seconds before // giving up and throwing an error. @@ -95,14 +97,14 @@ class PacketReader { // (although this is a rare thing). Therefore, we continue waiting // until either a connectionID has been set (and hence a notify was // made) or the total wait time has elapsed. - int waitTime = SmackConfiguration.getDefaultPacketReplyTimeout(); + long waitTime = connection.getPacketReplyTimeout(); wait(3 * waitTime); } catch (InterruptedException ie) { // Ignore. } if (connectionID == null) { - throw new XMPPException("XMPPConnection failed. No response from server."); + throw new NoResponseException(); } else { connection.connectionID = connectionID; @@ -225,7 +227,7 @@ class PacketReader { } } else if (parser.getName().equals("error")) { - throw new XMPPException(PacketParserUtils.parseStreamError(parser)); + throw new StreamErrorException(PacketParserUtils.parseStreamError(parser)); } else if (parser.getName().equals("features")) { parseFeatures(parser); @@ -252,9 +254,9 @@ class PacketReader { else { // SASL authentication has failed. The server may close the connection // depending on the number of retries - final Failure failure = PacketParserUtils.parseSASLFailure(parser); + final SASLFailure failure = PacketParserUtils.parseSASLFailure(parser); connection.processPacket(failure); - connection.getSASLAuthentication().authenticationFailed(failure.getCondition()); + connection.getSASLAuthentication().authenticationFailed(failure); } } else if (parser.getName().equals("challenge")) { @@ -390,9 +392,7 @@ class PacketReader { if (!startTLSReceived && connection.getConfiguration().getSecurityMode() == ConnectionConfiguration.SecurityMode.required) { - throw new XMPPException("Server does not support security (TLS), " + - "but security required by connection configuration.", - new XMPPError(XMPPError.Condition.forbidden)); + throw new SecurityRequiredException(); } } diff --git a/tcp/src/main/java/org/jivesoftware/smack/TCPConnection.java b/tcp/src/main/java/org/jivesoftware/smack/TCPConnection.java index 34434212f..b17e26bce 100644 --- a/tcp/src/main/java/org/jivesoftware/smack/TCPConnection.java +++ b/tcp/src/main/java/org/jivesoftware/smack/TCPConnection.java @@ -16,10 +16,12 @@ */ package org.jivesoftware.smack; +import org.jivesoftware.smack.SmackException.AlreadyLoggedInException; +import org.jivesoftware.smack.SmackException.NotConnectedException; +import org.jivesoftware.smack.SmackException.ConnectionException; import org.jivesoftware.smack.compression.XMPPInputOutputStream; import org.jivesoftware.smack.packet.Packet; import org.jivesoftware.smack.packet.Presence; -import org.jivesoftware.smack.packet.XMPPError; import org.jivesoftware.smack.parsing.ParsingExceptionCallback; import org.jivesoftware.smack.util.StringUtils; import org.jivesoftware.smack.util.dns.HostAddress; @@ -31,6 +33,7 @@ import javax.net.ssl.SSLSocket; import javax.security.auth.callback.Callback; import javax.security.auth.callback.CallbackHandler; import javax.security.auth.callback.PasswordCallback; +import javax.security.sasl.SaslException; import java.io.BufferedReader; import java.io.BufferedWriter; @@ -41,9 +44,9 @@ import java.io.InputStream; import java.io.InputStreamReader; import java.io.OutputStream; import java.io.OutputStreamWriter; +import java.io.UnsupportedEncodingException; import java.lang.reflect.Constructor; import java.net.Socket; -import java.net.UnknownHostException; import java.security.KeyStore; import java.security.Provider; import java.security.Security; @@ -218,12 +221,12 @@ public class TCPConnection extends XMPPConnection { } @Override - public synchronized void login(String username, String password, String resource) throws XMPPException { + public synchronized void login(String username, String password, String resource) throws XMPPException, SmackException, SaslException, IOException { if (!isConnected()) { - throw new IllegalStateException("Not connected to server."); + throw new NotConnectedException(); } if (authenticated) { - throw new IllegalStateException("Already logged in to server."); + throw new AlreadyLoggedInException(); } // Do partial version of nameprep on the username. username = username.toLowerCase().trim(); @@ -238,7 +241,7 @@ public class TCPConnection extends XMPPConnection { response = saslAuthentication.authenticate(resource, config.getCallbackHandler()); } } else { - throw new XMPPException("No non-anonymous SASL authentication mechanism available"); + throw new SaslException("No non-anonymous SASL authentication mechanism available"); } // Set the user. @@ -289,12 +292,12 @@ public class TCPConnection extends XMPPConnection { } @Override - public synchronized void loginAnonymously() throws XMPPException { + public synchronized void loginAnonymously() throws XMPPException, SmackException, SaslException, IOException { if (!isConnected()) { - throw new IllegalStateException("Not connected to server."); + throw new NotConnectedException(); } if (authenticated) { - throw new IllegalStateException("Already logged in to server."); + throw new AlreadyLoggedInException(); } String response; @@ -302,7 +305,7 @@ public class TCPConnection extends XMPPConnection { response = saslAuthentication.authenticateAnonymously(); } else { - throw new XMPPException("No anonymous SASL authentication mechanism available"); + throw new SaslException("No anonymous SASL authentication mechanism available"); } // Set the user value. @@ -331,7 +334,7 @@ public class TCPConnection extends XMPPConnection { } } - public Roster getRoster() { + public Roster getRoster() throws XMPPException, SmackException { // synchronize against login() synchronized(this) { // if connection is authenticated the roster is already set by login() @@ -475,11 +478,10 @@ public class TCPConnection extends XMPPConnection { packetWriter.sendPacket(packet); } - private void connectUsingConfiguration(ConnectionConfiguration config) throws XMPPException { - XMPPException exception = null; + private void connectUsingConfiguration(ConnectionConfiguration config) throws SmackException, IOException { + Exception exception = null; Iterator it = config.getHostAddresses().iterator(); List failedAddresses = new LinkedList(); - boolean xmppIOError = false; while (it.hasNext()) { exception = null; HostAddress hostAddress = it.next(); @@ -492,15 +494,8 @@ public class TCPConnection extends XMPPConnection { else { this.socket = config.getSocketFactory().createSocket(host, port); } - } catch (UnknownHostException uhe) { - String errorMessage = "Could not connect to " + host + ":" + port + "."; - exception = new XMPPException(errorMessage, new XMPPError(XMPPError.Condition.remote_server_timeout, - errorMessage), uhe); - } catch (IOException ioe) { - String errorMessage = "XMPPError connecting to " + host + ":" + port + "."; - exception = new XMPPException(errorMessage, new XMPPError(XMPPError.Condition.remote_server_error, - errorMessage), ioe); - xmppIOError = true; + } catch (Exception e) { + exception = e; } if (exception == null) { // We found a host to connect to, break here @@ -513,19 +508,7 @@ public class TCPConnection extends XMPPConnection { // There are no more host addresses to try // throw an exception and report all tried // HostAddresses in the exception - StringBuilder sb = new StringBuilder(); - for (HostAddress fha : failedAddresses) { - sb.append(fha.getErrorMessage()); - sb.append("; "); - } - XMPPError xmppError; - if (xmppIOError) { - xmppError = new XMPPError(XMPPError.Condition.remote_server_error); - } - else { - xmppError = new XMPPError(XMPPError.Condition.remote_server_timeout); - } - throw new XMPPException(sb.toString(), xmppError, exception); + throw new ConnectionException(failedAddresses); } } socketClosed = false; @@ -537,8 +520,10 @@ public class TCPConnection extends XMPPConnection { * XMPP stream to the server. * * @throws XMPPException if establishing a connection to the server fails. + * @throws SmackException if the server failes to respond back or if there is anther error. + * @throws IOException */ - private void initConnection() throws XMPPException { + private void initConnection() throws SmackException, IOException { boolean isFirstInitialization = packetReader == null || packetWriter == null; compressionHandler = null; serverAckdCompression = false; @@ -582,7 +567,7 @@ public class TCPConnection extends XMPPConnection { } } - catch (XMPPException ex) { + catch (Exception ex) { // An exception occurred in setting up the connection. Make sure we shut down the // readers and writers and close the socket. @@ -625,11 +610,11 @@ public class TCPConnection extends XMPPConnection { authenticated = false; connected = false; - throw ex; // Everything stoppped. Now throw the exception. + throw new SmackException(ex); // Everything stoppped. Now throw the exception. } } - private void initReaderAndWriter() throws XMPPException { + private void initReaderAndWriter() throws IOException { try { if (compressionHandler == null) { reader = @@ -655,12 +640,8 @@ public class TCPConnection extends XMPPConnection { } } } - catch (IOException ioe) { - throw new XMPPException( - "XMPPError establishing connection with server.", - new XMPPError(XMPPError.Condition.remote_server_error, - "XMPPError establishing connection with server."), - ioe); + catch (UnsupportedEncodingException ioe) { + throw new IllegalStateException(ioe); } // If debugging is enabled, we open a window and write out all network traffic. @@ -932,12 +913,10 @@ public class TCPConnection extends XMPPConnection { * occurs after an abrupt termination. * * @throws XMPPException if an error occurs while trying to establish the connection. - * Two possible errors can occur which will be wrapped by an XMPPException -- - * UnknownHostException (XMPP error code 504), and IOException (XMPP error code - * 502). The error codes and wrapped exceptions can be used to present more - * appropriate error messages to end-users. + * @throws SmackException + * @throws IOException */ - public void connect() throws XMPPException { + public void connect() throws SmackException, IOException, XMPPException { // Establishes the connection, readers and writers connectUsingConfiguration(config); // Automatically makes the login if the user was previously connected successfully diff --git a/tcp/src/test/java/org/jivesoftware/smack/RosterOfflineTest.java b/tcp/src/test/java/org/jivesoftware/smack/RosterOfflineTest.java index ccbddfa77..5f549b20d 100644 --- a/tcp/src/test/java/org/jivesoftware/smack/RosterOfflineTest.java +++ b/tcp/src/test/java/org/jivesoftware/smack/RosterOfflineTest.java @@ -18,11 +18,6 @@ package org.jivesoftware.smack; import static org.junit.Assert.*; -import java.util.Collection; -import java.util.Iterator; - -import org.jivesoftware.smack.Roster.SubscriptionMode; -import org.jivesoftware.smack.packet.Presence; import org.junit.Before; import org.junit.Test; @@ -38,7 +33,7 @@ public class RosterOfflineTest { Roster roster; @Before - public void setup() { + public void setup() throws XMPPException, SmackException { this.connection = new TCPConnection("localhost"); assertFalse(connection.isConnected()); @@ -46,61 +41,22 @@ public class RosterOfflineTest { assertNotNull(roster); } - @Test - public void shouldThrowNoExceptionOnGetterMethods() { - // all getter methods should work - assertFalse(roster.contains("test")); - - Collection entries = roster.getEntries(); - assertTrue(entries.size() == 0); - - assertNull(roster.getEntry("test")); - - assertEquals(0, roster.getEntryCount()); - - assertNull(roster.getGroup("test")); - - assertEquals(0, roster.getGroupCount()); - - Collection groups = roster.getGroups(); - assertEquals(0, groups.size()); - - Presence presence = roster.getPresence("test"); - assertEquals(Presence.Type.unavailable, presence.getType()); - - Presence presenceResource = roster.getPresenceResource("test"); - assertEquals(Presence.Type.unavailable, presenceResource.getType()); - - Iterator iterator = roster.getPresences("test"); - assertTrue(iterator.hasNext()); - assertEquals(Presence.Type.unavailable, iterator.next().getType()); - assertFalse(iterator.hasNext()); - - assertEquals(0, roster.getUnfiledEntries().size()); - - assertEquals(0, roster.getUnfiledEntryCount()); - - roster.setSubscriptionMode(SubscriptionMode.accept_all); - assertEquals(SubscriptionMode.accept_all, roster.getSubscriptionMode()); - - } - - @Test(expected = IllegalStateException.class) + @Test(expected = SmackException.class) public void shouldThrowExceptionOnCreateEntry() throws Exception { roster.createEntry("test", "test", null); } - @Test(expected = IllegalStateException.class) + @Test(expected = SmackException.class) public void shouldThrowExceptionOnCreateGroup() throws Exception { roster.createGroup("test"); } - @Test(expected = IllegalStateException.class) + @Test(expected = SmackException.class) public void shouldThrowExceptionOnReload() throws Exception { roster.reload(); } - @Test(expected = IllegalStateException.class) + @Test(expected = SmackException.class) public void shouldThrowExceptionRemoveEntry() throws Exception { roster.removeEntry(null); }