From 2da448d2fd6451ed055ff33da26a266fa3b1db46 Mon Sep 17 00:00:00 2001 From: Gaston Dombiak Date: Fri, 24 Oct 2008 05:17:50 +0000 Subject: [PATCH] Simplified list of #login methods in XMPPConnection. git-svn-id: http://svn.igniterealtime.org/svn/repos/smack/trunk@10846 b35dd754-fafc-0310-a699-88a17e54d16e --- .../smack/ConnectionConfiguration.java | 73 ++++- .../smack/SmackConfiguration.java | 8 +- .../jivesoftware/smack/XMPPConnection.java | 261 +++--------------- 3 files changed, 111 insertions(+), 231 deletions(-) diff --git a/source/org/jivesoftware/smack/ConnectionConfiguration.java b/source/org/jivesoftware/smack/ConnectionConfiguration.java index 0c9d0915c..1cc81424f 100644 --- a/source/org/jivesoftware/smack/ConnectionConfiguration.java +++ b/source/org/jivesoftware/smack/ConnectionConfiguration.java @@ -20,10 +20,11 @@ package org.jivesoftware.smack; -import org.jivesoftware.smack.util.DNSUtil; import org.jivesoftware.smack.proxy.ProxyInfo; +import org.jivesoftware.smack.util.DNSUtil; import javax.net.SocketFactory; +import javax.security.auth.callback.CallbackHandler; import java.io.File; /** @@ -57,6 +58,10 @@ public class ConnectionConfiguration implements Cloneable { private boolean compressionEnabled = false; private boolean saslAuthenticationEnabled = true; + /** + * Used to get information from the user + */ + private CallbackHandler callbackHandler; private boolean debuggerEnabled = XMPPConnection.DEBUG_ENABLED; @@ -70,7 +75,8 @@ public class ConnectionConfiguration implements Cloneable { private String username; private String password; private String resource; - private boolean sendPresence; + private boolean sendPresence = true; + private boolean rosterLoadedAtLogin = true; private SecurityMode securityMode = SecurityMode.enabled; // Holds the proxy information (such as proxyhost, proxyport, username, password etc) @@ -563,6 +569,66 @@ public class ConnectionConfiguration implements Cloneable { this.socketFactory = socketFactory; } + /** + * Sets if an initial available presence will be sent to the server. By default + * an available presence will be sent to the server indicating that this presence + * is not online and available to receive messages. If you want to log in without + * being 'noticed' then pass a false value. + * + * @param sendPresence true if an initial available presence will be sent while logging in. + */ + public void setSendPresence(boolean sendPresence) { + this.sendPresence = sendPresence; + } + + /** + * Returns true if the roster will be loaded from the server when logging in. This + * is the common behaviour for clients but sometimes clients may want to differ this + * or just never do it if not interested in rosters. + * + * @return true if the roster will be loaded from the server when logging in. + */ + public boolean isRosterLoadedAtLogin() { + return rosterLoadedAtLogin; + } + + /** + * Sets if the roster will be loaded from the server when logging in. This + * is the common behaviour for clients but sometimes clients may want to differ this + * or just never do it if not interested in rosters. + * + * @param rosterLoadedAtLogin if the roster will be loaded from the server when logging in. + */ + public void setRosterLoadedAtLogin(boolean rosterLoadedAtLogin) { + this.rosterLoadedAtLogin = rosterLoadedAtLogin; + } + + /** + * Returns a CallbackHandler to obtain information, such as the password or + * principal information during the SASL authentication. A CallbackHandler + * will be used ONLY if no password was specified during the login while + * using SASL authentication. + * + * @return a CallbackHandler to obtain information, such as the password or + * principal information during the SASL authentication. + */ + public CallbackHandler getCallbackHandler() { + return callbackHandler; + } + + /** + * Sets a CallbackHandler to obtain information, such as the password or + * principal information during the SASL authentication. A CallbackHandler + * will be used ONLY if no password was specified during the login while + * using SASL authentication. + * + * @param callbackHandler to obtain information, such as the password or + * principal information during the SASL authentication. + */ + public void setCallbackHandler(CallbackHandler callbackHandler) { + this.callbackHandler = callbackHandler; + } + /** * Returns the socket factory used to create new xmppConnection sockets. * This is useful when connecting through SOCKS5 proxies. @@ -636,10 +702,9 @@ public class ConnectionConfiguration implements Cloneable { return sendPresence; } - void setLoginInfo(String username, String password, String resource, boolean sendPresence) { + void setLoginInfo(String username, String password, String resource) { this.username = username; this.password = password; this.resource = resource; - this.sendPresence = sendPresence; } } diff --git a/source/org/jivesoftware/smack/SmackConfiguration.java b/source/org/jivesoftware/smack/SmackConfiguration.java index fe14d426d..faa78ff3a 100644 --- a/source/org/jivesoftware/smack/SmackConfiguration.java +++ b/source/org/jivesoftware/smack/SmackConfiguration.java @@ -25,11 +25,7 @@ import org.xmlpull.v1.XmlPullParser; import java.io.InputStream; import java.net.URL; -import java.util.ArrayList; -import java.util.Vector; -import java.util.Collection; -import java.util.Enumeration; -import java.util.List; +import java.util.*; /** * Represents the configuration of Smack. The configuration is used for: @@ -48,7 +44,7 @@ import java.util.List; */ public final class SmackConfiguration { - private static final String SMACK_VERSION = "3.0.5"; + private static final String SMACK_VERSION = "3.1.0"; private static int packetReplyTimeout = 5000; private static int keepAliveInterval = 30000; diff --git a/source/org/jivesoftware/smack/XMPPConnection.java b/source/org/jivesoftware/smack/XMPPConnection.java index 80be0f2d2..29d27c9a0 100644 --- a/source/org/jivesoftware/smack/XMPPConnection.java +++ b/source/org/jivesoftware/smack/XMPPConnection.java @@ -20,7 +20,6 @@ package org.jivesoftware.smack; -import org.jivesoftware.smack.Roster; import org.jivesoftware.smack.debugger.SmackDebugger; import org.jivesoftware.smack.filter.PacketFilter; import org.jivesoftware.smack.packet.Packet; @@ -165,11 +164,6 @@ public class XMPPConnection { Writer writer; Reader reader; - /** - * Flag that indicates if the roster has been preloaded during login - */ - boolean preloadRoster = true; - /** * Collection of available stream compression methods offered by the server. */ @@ -336,136 +330,54 @@ public class XMPPConnection { * Logs in to the server using the strongest authentication mode supported by * the server, then sets presence to available. If more than five seconds * (default timeout) elapses in each step of the authentication process without - * a response from the server, or if an error occurs, a XMPPException will be thrown. + * a response from the server, or if an error occurs, a XMPPException will be thrown.

* - * It is recommended to use the {@link #login(String, CallbackHandler)} instead. + * It is possible to log in without sending an initial available presence by using + * {@link ConnectionConfiguration#setSendPresence(boolean)}. If this connection is + * not interested in loading its roster upon login then use + * {@link ConnectionConfiguration#setRosterLoadedAtLogin(boolean)}. + * Finally, if you want to not pass a password and instead use a more advanced mechanism + * while using SASL then you may be interested in using + * {@link ConnectionConfiguration#setCallbackHandler(javax.security.auth.callback.CallbackHandler)}. + * For more advanced login settings see {@link ConnectionConfiguration}. * * @param username the username. - * @param password the password. + * @param password the password or null if using a CallbackHandler. * @throws XMPPException if an error occurs. */ public void login(String username, String password) throws XMPPException { login(username, password, "Smack"); } - /** - * Logs in to the server using the strongest authentication mode supported by - * the server, then sets presence to available. If more than five seconds - * (default timeout) elapses in each step of the authentication process without - * a response from the server, or if an error occurs, a XMPPException will be thrown. - * - * It is recommended to use the {@link #login(String, CallbackHandler)} instead. - * - * @param username the username. - * @param cbh The CallbackHandler used to determine password, or other information. - * @throws XMPPException if an error occurs. - */ - public void login(String username, CallbackHandler cbh) throws XMPPException { - login(username, "Smack", cbh); - } - - /** - * Logs in to the server using the strongest authentication mode supported by - * the server, then sets presence to available. If more than five seconds - * (default timeout) elapses in each step of the authentication process without - * a response from the server, or if an error occurs, a XMPPException will be thrown. - * - * It is recommended to use the {@link #login(String, String, CallbackHandler)} instead. - * - * @param username the username. - * @param password the password. - * @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. - */ - public synchronized void login(String username, String password, String resource) - throws XMPPException { - login(username, password, resource, true, true); - } - - /** - * Logs in to the server using the strongest authentication mode supported by - * the server, then sets presence to available. If more than five seconds - * (default timeout) elapses in each step of the authentication process without - * a response from the server, or if an error occurs, a XMPPException will be thrown. - * - * @param username the username. - * @param cbh the password. - * @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. - */ - public synchronized void login(String username, String resource, CallbackHandler cbh) - throws XMPPException { - login(username, resource, true, cbh); - } - /** * Logs in to the server using the strongest authentication mode supported by * the server. If the server supports SASL authentication then the user will be - * authenticated using SASL if not Non-SASL authentication will be tried. An available - * presence may optionally be sent. If sendPresence - * is false, a presence packet must be sent manually later. If more than five seconds - * (default timeout) elapses in each step of the authentication process without a - * response from the server, or if an error occurs, a XMPPException will be thrown.

- *

+ * authenticated using SASL if not Non-SASL authentication will be tried. If more than + * five seconds (default timeout) elapses in each step of the authentication process + * without a response from the server, or if an error occurs, a XMPPException will be + * thrown.

+ * * Before logging in (i.e. authenticate) to the server the connection must be connected. * For compatibility and easiness of use the connection will automatically connect to the - * server if not already connected. + * server if not already connected.

* - * It is recommended to use the {@link #login(String, String, boolean, CallbackHandler)} instead. + * It is possible to log in without sending an initial available presence by using + * {@link ConnectionConfiguration#setSendPresence(boolean)}. If this connection is + * not interested in loading its roster upon login then use + * {@link ConnectionConfiguration#setRosterLoadedAtLogin(boolean)}. + * Finally, if you want to not pass a password and instead use a more advanced mechanism + * while using SASL then you may be interested in using + * {@link ConnectionConfiguration#setCallbackHandler(javax.security.auth.callback.CallbackHandler)}. + * For more advanced login settings see {@link ConnectionConfiguration}. * * @param username the username. - * @param password the password. + * @param password the password or null if using a CallbackHandler. * @param resource the resource. - * @param sendPresence if true an available presence will be sent automatically - * after login is completed. * @throws XMPPException if an error occurs. * @throws IllegalStateException if not connected to the server, or already logged in * to the serrver. */ - public synchronized void login(String username, String password, String resource, - boolean sendPresence) throws XMPPException { - login(username, password, resource, sendPresence, true); - } - - /** - * Logs in to the server using the strongest authentication mode supported by - * the server. If the server supports SASL authentication then the user will be - * authenticated using SASL if not Non-SASL authentication will be tried. An available - * presence may optionally be sent. - * - * If sendPresence - * is false, a presence packet must be sent manually later. If more than five seconds - * (default timeout) elapses in each step of the authentication process without a - * response from the server, or if an error occurs, a XMPPException will be thrown.

- *

- * - * If preloadRoster - * is false, a roster request packet must be sent manually later.

- *

- * - * Before logging in (i.e. authenticate) to the server the connection must be connected. - * For compatibility and easiness of use the connection will automatically connect to the - * server if not already connected. - * - * It is recommended to use the {@link #login(String, String, boolean, CallbackHandler)} instead. - * - * @param username the username. - * @param password the password. - * @param resource the resource. - * @param sendPresence if true an available presence will be sent automatically - * after login is completed. - * @param preloadRoster if true roster request will be sent to the server, - * otherwise roster will be gotten on demand. - * @throws XMPPException if an error occurs. - * @throws IllegalStateException if not connected to the server, or already logged in - * to the serrver. - */ - public synchronized void login(String username, String password, String resource, - boolean sendPresence, boolean preloadRoster) throws XMPPException { + public synchronized void login(String username, String password, String resource) throws XMPPException { if (!isConnected()) { throw new IllegalStateException("Not connected to server."); } @@ -479,7 +391,13 @@ public class XMPPConnection { if (configuration.isSASLAuthenticationEnabled() && saslAuthentication.hasNonAnonymousAuthentication()) { // Authenticate using SASL - response = saslAuthentication.authenticate(username, password, resource); + if (password != null) { + response = saslAuthentication.authenticate(username, password, resource); + } + else { + response = saslAuthentication + .authenticate(username, resource, configuration.getCallbackHandler()); + } } else { // Authenticate using Non-SASL @@ -504,109 +422,16 @@ public class XMPPConnection { useCompression(); } - this.preloadRoster = preloadRoster; - if (preloadRoster) { - // Create the roster if it is not a reconnection. - if (this.roster == null) { - this.roster = new Roster(this); - } - roster.reload(); - } - - // Set presence to online. - if (sendPresence) { - packetWriter.sendPacket(new Presence(Presence.Type.available)); - } - - // Indicate that we're now authenticated. - authenticated = true; - anonymous = false; - - // Stores the autentication for future reconnection - this.getConfiguration().setLoginInfo(username, password, resource, sendPresence); - - // If debugging is enabled, change the the debug window title to include the - // name we are now logged-in as. - // If DEBUG_ENABLED was set to true AFTER the connection was created the debugger - // will be null - if (configuration.isDebuggerEnabled() && debugger != null) { - debugger.userHasLogged(user); - } - } - /** - * Logs in to the server using the strongest authentication mode supported by - * the server. If the server supports SASL authentication then the user will be - * authenticated using SASL if not Non-SASL authentication will be tried. An available - * presence may optionally be sent. If sendPresence - * is false, a presence packet must be sent manually later. If more than five seconds - * (default timeout) elapses in each step of the authentication process without a - * response from the server, or if an error occurs, a XMPPException will be thrown.

- *

- * Before logging in (i.e. authenticate) to the server the connection must be connected. - * For compatibility and easiness of use the connection will automatically connect to the - * server if not already connected. - * - * This version requires the use of a CallbackHandler to obtain information, such as the - * password or principal information - * - * @param username the username. - * @param cbh the callback handler. - * @param resource the resource. - * @param sendPresence if true an available presence will be sent automatically - * after login is completed. - * @throws XMPPException if an error occurs. - * @throws IllegalStateException if not connected to the server, or already logged in - * to the serrver. - */ - public synchronized void login(String username, String resource, - boolean sendPresence, CallbackHandler cbh) throws XMPPException { - - - if (!isConnected()) { - throw new IllegalStateException("Not connected to server."); - } - if (authenticated) { - throw new IllegalStateException("Already logged in to server."); - } - // Do partial version of nameprep on the username. - username = username.toLowerCase().trim(); - - String response; - if (configuration.isSASLAuthenticationEnabled() && - saslAuthentication.hasNonAnonymousAuthentication()) { - // Authenticate using SASL - response = saslAuthentication.authenticate(username, resource, cbh); - } - else { - throw new XMPPException("SASL authentication unavilable"); - } - - // Set the user. - if (response != null) { - this.user = response; - // Update the serviceName with the one returned by the server - this.serviceName = StringUtils.parseServer(response); - } - else { - this.user = username + "@" + this.serviceName; - if (resource != null) { - this.user += "/" + resource; - } - } - - // If compression is enabled then request the server to use stream compression - if (configuration.isCompressionEnabled()) { - useCompression(); - } - // Create the roster if it is not a reconnection. if (this.roster == null) { this.roster = new Roster(this); } - roster.reload(); + if (configuration.isRosterLoadedAtLogin()) { + roster.reload(); + } // Set presence to online. - if (sendPresence) { + if (configuration.isSendPresence()) { packetWriter.sendPacket(new Presence(Presence.Type.available)); } @@ -614,9 +439,8 @@ public class XMPPConnection { authenticated = true; anonymous = false; - //TODO: Handle this! // Stores the autentication for future reconnection - //this.getConfiguration().setLoginInfo(username, password, resource, sendPresence); + this.getConfiguration().setLoginInfo(username, password, resource); // If debugging is enabled, change the the debug window title to include the // name we are now logged-in as. @@ -625,7 +449,6 @@ public class XMPPConnection { if (configuration.isDebuggerEnabled() && debugger != null) { debugger.userHasLogged(user); } - } /** @@ -693,11 +516,7 @@ public class XMPPConnection { * @return the user's roster, or null if the user has not logged in yet. */ public Roster getRoster() { - if (!preloadRoster) { - preloadRoster = true; - if (this.roster == null) { - this.roster = new Roster(this); - } + if (!configuration.isRosterLoadedAtLogin()) { roster.reload(); } if (roster == null) { @@ -1605,7 +1424,7 @@ public class XMPPConnection { } else { login(getConfiguration().getUsername(), getConfiguration().getPassword(), - getConfiguration().getResource(), getConfiguration().isSendPresence(), true); + getConfiguration().getResource()); } } catch (XMPPException e) {