diff options
author | Lyubomir Marinov <lyubomir.marinov@jitsi.org> | 2008-09-20 20:36:27 +0000 |
---|---|---|
committer | Lyubomir Marinov <lyubomir.marinov@jitsi.org> | 2008-09-20 20:36:27 +0000 |
commit | 182ada36e3a288d03fd7d6d96e88d1bb409dc983 (patch) | |
tree | dc3ecf63b2dcbcccf38c8a1018041382649629d2 /src/net/java/sip/communicator | |
parent | 7447c700b0414a077aff8ec7fea337dad1f4d11e (diff) | |
download | jitsi-182ada36e3a288d03fd7d6d96e88d1bb409dc983.zip jitsi-182ada36e3a288d03fd7d6d96e88d1bb409dc983.tar.gz jitsi-182ada36e3a288d03fd7d6d96e88d1bb409dc983.tar.bz2 |
When starting the applications, loads the stored accounts in the background in order to allow the UI to appear as soon as possible.
Diffstat (limited to 'src/net/java/sip/communicator')
37 files changed, 1469 insertions, 2430 deletions
diff --git a/src/net/java/sip/communicator/impl/protocol/AccountManagerImpl.java b/src/net/java/sip/communicator/impl/protocol/AccountManagerImpl.java new file mode 100644 index 0000000..c09439f --- /dev/null +++ b/src/net/java/sip/communicator/impl/protocol/AccountManagerImpl.java @@ -0,0 +1,556 @@ +/*
+ * SIP Communicator, the OpenSource Java VoIP and Instant Messaging client.
+ *
+ * Distributable under LGPL license.
+ * See terms of license at gnu.org.
+ */
+package net.java.sip.communicator.impl.protocol;
+
+import java.util.*;
+
+import org.osgi.framework.*;
+
+import net.java.sip.communicator.service.configuration.*;
+import net.java.sip.communicator.service.protocol.*;
+import net.java.sip.communicator.service.protocol.event.*;
+import net.java.sip.communicator.util.*;
+
+public class AccountManagerImpl
+ implements AccountManager
+{
+
+ /**
+ * The delay in milliseconds the background <code>Thread</code> loading the
+ * stored accounts should wait before dying so that it doesn't get recreated
+ * for each <code>ProtocolProviderFactory</code> registration.
+ */
+ private static final long LOAD_STORED_ACCOUNTS_TIMEOUT = 30000;
+
+ /**
+ * The <code>BundleContext</code> this service is registered in.
+ */
+ private final BundleContext bundleContext;
+
+ /**
+ * The <code>ConfigurationService</code> storing the accounts managed by
+ * this instance.
+ */
+ private ConfigurationService configurationService;
+
+ /**
+ * The <code>AccountManagerListener</code>s currently interested in the
+ * events fired by this manager.
+ */
+ private final List<AccountManagerListener> listeners =
+ new LinkedList<AccountManagerListener>();
+
+ /**
+ * The queue of <code>ProtocolProviderFactory</code> services awaiting their
+ * stored accounts to be loaded.
+ */
+ private final Queue<ProtocolProviderFactory> loadStoredAccountsQueue =
+ new LinkedList<ProtocolProviderFactory>();
+
+ /**
+ * The <code>Thread</code> loading the stored accounts of the
+ * <code>ProtocolProviderFactory</code> services waiting in
+ * {@link #loadStoredAccountsQueue}.
+ */
+ private Thread loadStoredAccountsThread;
+
+ private final Logger logger = Logger.getLogger(AccountManagerImpl.class);
+
+ /**
+ * Initializes a new <code>AccountManagerImpl</code> instance loaded in a
+ * specific <code>BundleContext</code> (in which the caller will usually
+ * later register it).
+ *
+ * @param bundleContext the <code>BundleContext</code> in which the new
+ * instance is loaded (and in which the caller will usually later
+ * register it as a service)
+ */
+ public AccountManagerImpl(BundleContext bundleContext)
+ {
+ this.bundleContext = bundleContext;
+
+ this.bundleContext.addServiceListener(new ServiceListener()
+ {
+ public void serviceChanged(ServiceEvent serviceEvent)
+ {
+ AccountManagerImpl.this.serviceChanged(serviceEvent);
+ }
+ });
+ }
+
+ public void addListener(AccountManagerListener listener)
+ {
+ synchronized (listeners)
+ {
+ if (!listeners.contains(listener))
+ {
+ listeners.add(listener);
+ }
+ }
+ }
+
+ /**
+ * Loads the accounts stored for a specific
+ * <code>ProtocolProviderFactory</code>.
+ *
+ * @param factory the <code>ProtocolProviderFactory</code> to load the
+ * stored accounts of
+ */
+ private void doLoadStoredAccounts(ProtocolProviderFactory factory)
+ {
+ ConfigurationService configService = getConfigurationService();
+ String factoryPackage = getFactoryImplPackageName(factory);
+ List<String> storedAccounts =
+ configService.getPropertyNamesByPrefix(factoryPackage, true);
+
+ logger.debug("Discovered " + storedAccounts.size() + " stored "
+ + factoryPackage + " accounts");
+
+ for (Iterator<String> storedAccountIter = storedAccounts.iterator(); storedAccountIter
+ .hasNext();)
+ {
+ String storedAccount = storedAccountIter.next();
+
+ logger.debug("Loading account " + storedAccount);
+
+ List<String> storedAccountProperties =
+ configService.getPropertyNamesByPrefix(storedAccount, true);
+ Map<String, String> accountProperties =
+ new Hashtable<String, String>();
+
+ for (Iterator<String> storedAccountPropertyIter =
+ storedAccountProperties.iterator(); storedAccountPropertyIter
+ .hasNext();)
+ {
+ String property = storedAccountPropertyIter.next();
+ String value = configService.getString(property);
+
+ property = stripPackagePrefix(property);
+
+ // Decode passwords.
+ if (ProtocolProviderFactory.PASSWORD.equals(property))
+ {
+ if (value == null)
+ {
+ value = "";
+ }
+ else if (value.length() != 0)
+ {
+
+ /*
+ * TODO Converting byte[] to String using the platform's
+ * default charset may result in an invalid password.
+ */
+ value = new String(Base64.decode(value));
+ }
+ }
+
+ if (value != null)
+ {
+ accountProperties.put(property, value);
+ }
+ }
+
+ try
+ {
+ factory.loadAccount(accountProperties);
+ }
+ catch (Exception ex)
+ {
+
+ /*
+ * Swallow the exception in order to prevent a single account
+ * from halting the loading of subsequent accounts.
+ */
+ logger.error("Failed to load account " + accountProperties, ex);
+ }
+ }
+ }
+
+ /**
+ * Notifies the registered {@link #listeners} that the stored accounts of a
+ * specific <code>ProtocolProviderFactory</code> have just been loaded.
+ *
+ * @param factory the <code>ProtocolProviderFactory</code> which had its
+ * stored accounts just loaded
+ */
+ private void fireStoredAccountsLoaded(ProtocolProviderFactory factory)
+ {
+ AccountManagerListener[] listeners;
+ synchronized (this.listeners)
+ {
+ listeners =
+ this.listeners
+ .toArray(new AccountManagerListener[this.listeners.size()]);
+ }
+
+ int listenerCount = listeners.length;
+ if (listenerCount > 0)
+ {
+ AccountManagerEvent event =
+ new AccountManagerEvent(this,
+ AccountManagerEvent.STORED_ACCOUNTS_LOADED, factory);
+
+ for (int listenerIndex = 0; listenerIndex < listenerCount; listenerIndex++)
+ {
+ listeners[listenerIndex].handleAccountManagerEvent(event);
+ }
+ }
+ }
+
+ private ConfigurationService getConfigurationService()
+ {
+ if (configurationService == null)
+ {
+ configurationService =
+ (ConfigurationService) bundleContext.getService(bundleContext
+ .getServiceReference(ConfigurationService.class.getName()));
+ }
+ return configurationService;
+ }
+
+ private String getFactoryImplPackageName(ProtocolProviderFactory factory) {
+ String className = factory.getClass().getName();
+
+ return className.substring(0, className.lastIndexOf('.'));
+ }
+
+ public boolean hasStoredAccounts()
+ {
+ ServiceReference[] factoryRefs = null;
+ boolean hasStoredAccounts = false;
+
+ try
+ {
+ factoryRefs =
+ bundleContext.getServiceReferences(
+ ProtocolProviderFactory.class.getName(), null);
+ }
+ catch (InvalidSyntaxException ex)
+ {
+ logger.error(
+ "Failed to retrieve the registered ProtocolProviderFactories",
+ ex);
+ }
+
+ if ((factoryRefs != null) && (factoryRefs.length > 0))
+ {
+ ConfigurationService configService = getConfigurationService();
+
+ for (int factoryRefI = 0; factoryRefI < factoryRefs.length; factoryRefI++)
+ {
+ ProtocolProviderFactory factory =
+ (ProtocolProviderFactory) bundleContext
+ .getService(factoryRefs[factoryRefI]);
+ String factoryPackage = getFactoryImplPackageName(factory);
+ List<String> storedAccounts =
+ configService
+ .getPropertyNamesByPrefix(factoryPackage, true);
+
+ /* Ignore the hidden accounts. */
+ for (Iterator<String> storedAccountIter =
+ storedAccounts.iterator(); storedAccountIter.hasNext();)
+ {
+ String storedAccount = storedAccountIter.next();
+ List<String> storedAccountProperties =
+ configService.getPropertyNamesByPrefix(storedAccount,
+ true);
+ boolean hidden = false;
+
+ for (Iterator<String> storedAccountPropertyIter =
+ storedAccountProperties.iterator(); storedAccountPropertyIter
+ .hasNext();)
+ {
+ String property = storedAccountPropertyIter.next();
+ String value = configService.getString(property);
+
+ property = stripPackagePrefix(property);
+
+ if (ProtocolProviderFactory.IS_PROTOCOL_HIDDEN
+ .equals(property))
+ {
+ hidden = (value != null);
+ break;
+ }
+ }
+
+ if (!hidden)
+ {
+ hasStoredAccounts = true;
+ break;
+ }
+ }
+
+ if (hasStoredAccounts)
+ {
+ break;
+ }
+ }
+ }
+ return hasStoredAccounts;
+ }
+
+ /**
+ * Loads the accounts stored for a specific
+ * <code>ProtocolProviderFactory</code> and notifies the registered
+ * {@link #listeners} that the stored accounts of the specified
+ * <code>factory</code> have just been loaded
+ *
+ * @param factory the <code>ProtocolProviderFactory</code> to load the
+ * stored accounts of
+ */
+ private void loadStoredAccounts(ProtocolProviderFactory factory)
+ {
+ doLoadStoredAccounts(factory);
+
+ fireStoredAccountsLoaded(factory);
+ }
+
+ /**
+ * Notifies this manager that a specific
+ * <code>ProtocolProviderFactory</code> has been registered as a service.
+ * The current implementation queues the specified <code>factory</code> to
+ * have its stored accounts as soon as possible.
+ *
+ * @param factory the <code>ProtocolProviderFactory</code> which has been
+ * registered as a service.
+ */
+ private void protocolProviderFactoryRegistered(
+ ProtocolProviderFactory factory)
+ {
+ queueLoadStoredAccounts(factory);
+ }
+
+ /**
+ * Queues a specific <code>ProtocolProviderFactory</code> to have its stored
+ * accounts loaded as soon as possible.
+ *
+ * @param factory the <code>ProtocolProviderFactory</code> to be queued for
+ * loading its stored accounts as soon as possible
+ */
+ private void queueLoadStoredAccounts(ProtocolProviderFactory factory)
+ {
+ synchronized (loadStoredAccountsQueue)
+ {
+ loadStoredAccountsQueue.add(factory);
+ loadStoredAccountsQueue.notify();
+
+ if (loadStoredAccountsThread == null)
+ {
+ loadStoredAccountsThread = new Thread()
+ {
+ public void run()
+ {
+ runInLoadStoredAccountsThread();
+ }
+ };
+ loadStoredAccountsThread.setDaemon(true);
+ loadStoredAccountsThread
+ .setName("AccountManager.loadStoredAccounts");
+ loadStoredAccountsThread.start();
+ }
+ }
+ }
+
+ public void removeListener(AccountManagerListener listener)
+ {
+ synchronized (listeners)
+ {
+ listeners.remove(listener);
+ }
+ }
+
+ /**
+ * Running in {@link #loadStoredAccountsThread}, loads the stored accounts
+ * of the <code>ProtocolProviderFactory</code> services waiting in
+ * {@link #loadStoredAccountsQueue}
+ */
+ private void runInLoadStoredAccountsThread()
+ {
+ boolean interrupted = false;
+ while (!interrupted)
+ {
+ try
+ {
+ ProtocolProviderFactory factory;
+
+ synchronized (loadStoredAccountsQueue)
+ {
+ factory = loadStoredAccountsQueue.poll();
+ if (factory == null)
+ {
+ /*
+ * Technically, we should be handing spurious wakeups.
+ * However, we cannot check the condition in a queue.
+ * Anyway, we just want to keep this Thread alive long
+ * enough to allow it to not be re-created multiple
+ * times and not handing a spurious wakeup will just
+ * cause such an inconvenience.
+ */
+ try
+ {
+ loadStoredAccountsQueue
+ .wait(LOAD_STORED_ACCOUNTS_TIMEOUT);
+ }
+ catch (InterruptedException ex)
+ {
+ logger
+ .warn(
+ "The loading of the stored accounts has been interrupted",
+ ex);
+ interrupted = true;
+ break;
+ }
+
+ factory = loadStoredAccountsQueue.poll();
+ }
+ }
+
+ if (factory != null)
+ {
+ try
+ {
+ loadStoredAccounts(factory);
+ }
+ catch (Exception ex)
+ {
+
+ /*
+ * Swallow the exception in order to prevent a single
+ * factory from halting the loading of subsequent
+ * factories.
+ */
+ logger.error("Failed to load accounts for " + factory,
+ ex);
+ }
+ }
+ }
+ finally
+ {
+ synchronized (loadStoredAccountsQueue)
+ {
+ if (!interrupted && (loadStoredAccountsQueue.size() <= 0))
+ {
+ if (loadStoredAccountsThread == Thread.currentThread())
+ {
+ loadStoredAccountsThread = null;
+ }
+ break;
+ }
+ }
+ }
+ }
+ }
+
+ /**
+ * Notifies this manager that an OSGi service has changed. The current
+ * implementation tracks the registrations of
+ * <code>ProtocolProviderFactory</code> services in order to queue them for
+ * loading their stored accounts.
+ *
+ * @param serviceEvent the <code>ServiceEvent</code> containing the event
+ * data
+ */
+ private void serviceChanged(ServiceEvent serviceEvent)
+ {
+ Object service =
+ bundleContext.getService(serviceEvent.getServiceReference());
+
+ if (service instanceof ProtocolProviderFactory)
+ {
+ ProtocolProviderFactory factory = (ProtocolProviderFactory) service;
+
+ switch (serviceEvent.getType())
+ {
+ case ServiceEvent.REGISTERED:
+ protocolProviderFactoryRegistered(factory);
+ break;
+ default:
+ break;
+ }
+ }
+ }
+
+ public void storeAccount(ProtocolProviderFactory factory,
+ AccountID accountID)
+ {
+ ConfigurationService configurationService = getConfigurationService();
+ String factoryPackage = getFactoryImplPackageName(factory);
+
+ // First check if such accountID already exist in the configuration.
+ List<String> storedAccounts =
+ configurationService.getPropertyNamesByPrefix(factoryPackage, true);
+ String accountUID = accountID.getAccountUniqueID();
+ String accountNodeName = null;
+
+ for (Iterator<String> storedAccountIter = storedAccounts.iterator(); storedAccountIter
+ .hasNext();)
+ {
+ String storedAccount = storedAccountIter.next();
+ String storedAccountUID =
+ configurationService.getString(storedAccount + ".ACCOUNT_UID");
+
+ if (storedAccountUID.equals(accountUID))
+ {
+ accountNodeName = configurationService.getString(storedAccount);
+ }
+ }
+
+ // Create a unique node name of the properties node that will contain
+ // this account's properties.
+ if (accountNodeName == null)
+ {
+ accountNodeName = "acc" + Long.toString(System.currentTimeMillis());
+
+ // set a value for the persistent node so that we could later
+ // retrieve it as a property
+ configurationService.setProperty(factoryPackage // prefix
+ + "." + accountNodeName, accountNodeName);
+
+ // register the account in the configuration service.
+ // we register all the properties in the following hierarchy
+ //net.java.sip.communicator.impl.protocol.PROTO_NAME.ACC_ID.PROP_NAME
+ configurationService.setProperty(factoryPackage// prefix
+ + "." + accountNodeName // node name for the account id
+ + "." + ProtocolProviderFactory.ACCOUNT_UID, // propname
+ accountID.getAccountUniqueID()); // value
+ }
+
+ // store the rest of the properties
+ Map accountProperties = accountID.getAccountProperties();
+
+ for (Iterator entryIter = accountProperties.entrySet().iterator(); entryIter
+ .hasNext();)
+ {
+ Map.Entry entry = (Map.Entry) entryIter.next();
+ String property = (String) entry.getKey();
+ String value = (String) entry.getValue();
+
+ // if this is a password - encode it.
+ if (property.equals(ProtocolProviderFactory.PASSWORD))
+ value = new String(Base64.encode(value.getBytes()));
+
+ configurationService.setProperty(factoryPackage // prefix
+ + "." + accountNodeName // a uniew node name for the account id
+ + "." + property, // propname
+ value); // value
+ }
+
+ logger.debug("Stored account for id " + accountID.getAccountUniqueID()
+ + " for package " + factoryPackage);
+ }
+
+ private String stripPackagePrefix(String property)
+ {
+ int packageEndIndex = property.lastIndexOf('.');
+ if (packageEndIndex != -1)
+ {
+ property = property.substring(packageEndIndex + 1);
+ }
+ return property;
+ }
+}
diff --git a/src/net/java/sip/communicator/impl/protocol/ProtocolProviderActivator.java b/src/net/java/sip/communicator/impl/protocol/ProtocolProviderActivator.java new file mode 100644 index 0000000..c96b100 --- /dev/null +++ b/src/net/java/sip/communicator/impl/protocol/ProtocolProviderActivator.java @@ -0,0 +1,33 @@ +/*
+ * SIP Communicator, the OpenSource Java VoIP and Instant Messaging client.
+ *
+ * Distributable under LGPL license.
+ * See terms of license at gnu.org.
+ */
+package net.java.sip.communicator.impl.protocol;
+
+import org.osgi.framework.*;
+
+import net.java.sip.communicator.service.protocol.*;
+
+public class ProtocolProviderActivator
+ implements BundleActivator
+{
+ private ServiceRegistration accountManagerServiceRegistration;
+
+ public void start(BundleContext bundleContext) throws Exception
+ {
+ accountManagerServiceRegistration =
+ bundleContext.registerService(AccountManager.class.getName(),
+ new AccountManagerImpl(bundleContext), null);
+ }
+
+ public void stop(BundleContext bundleContext) throws Exception
+ {
+ if (accountManagerServiceRegistration != null)
+ {
+ accountManagerServiceRegistration.unregister();
+ accountManagerServiceRegistration = null;
+ }
+ }
+}
diff --git a/src/net/java/sip/communicator/impl/protocol/dict/DictActivator.java b/src/net/java/sip/communicator/impl/protocol/dict/DictActivator.java index 0940c98..d0bc20d 100644 --- a/src/net/java/sip/communicator/impl/protocol/dict/DictActivator.java +++ b/src/net/java/sip/communicator/impl/protocol/dict/DictActivator.java @@ -54,12 +54,9 @@ public class DictActivator Hashtable hashtable = new Hashtable(); hashtable.put(ProtocolProviderFactory.PROTOCOL, ProtocolNames.DICT); - + dictProviderFactory = new ProtocolProviderFactoryDictImpl(); - - //load all stored Dict accounts. - dictProviderFactory.loadStoredAccounts(); - + //reg the dict provider factory. dictPpFactoryServReg = context.registerService( ProtocolProviderFactory.class.getName(), diff --git a/src/net/java/sip/communicator/impl/protocol/dict/ProtocolProviderFactoryDictImpl.java b/src/net/java/sip/communicator/impl/protocol/dict/ProtocolProviderFactoryDictImpl.java index 8560aba..45eabaf 100644 --- a/src/net/java/sip/communicator/impl/protocol/dict/ProtocolProviderFactoryDictImpl.java +++ b/src/net/java/sip/communicator/impl/protocol/dict/ProtocolProviderFactoryDictImpl.java @@ -28,69 +28,19 @@ public class ProtocolProviderFactoryDictImpl = Logger.getLogger(ProtocolProviderFactoryDictImpl.class); /** - * The table that we store our accounts in. - */ - private Hashtable registeredAccounts = new Hashtable(); - - /** * Name for the auto-create group */ private String groupName = "Dictionaries"; - - private BundleContext bundleContext; /** * Creates an instance of the ProtocolProviderFactoryDictImpl. */ public ProtocolProviderFactoryDictImpl() { - super(); - bundleContext = DictActivator.getBundleContext(); - } - - /** - * Returns the ServiceReference for the protocol provider corresponding - * to the specified accountID or null if the accountID is unknown. - * - * @param accountID the accountID of the protocol provider we'd like to - * get - * @return a ServiceReference object to the protocol provider with the - * specified account id and null if the account id is unknwon to the - * provider factory. - */ - public ServiceReference getProviderForAccount(AccountID accountID) - { - ServiceRegistration registration - = (ServiceRegistration)registeredAccounts.get(accountID); - - return (registration == null ) - ? null - : registration.getReference(); - } - - /** - * Returns a copy of the list containing the <tt>AccoudID</tt>s of all - * accounts currently registered in this protocol provider. - * - * @return a copy of the list containing the <tt>AccoudID</tt>s of all - * accounts currently registered in this protocol provider. - */ - public ArrayList getRegisteredAccounts() - { - return new ArrayList(registeredAccounts.keySet()); + super(DictActivator.getBundleContext(), ProtocolNames.DICT); } /** - * Loads (and hence installs) all accounts previously stored in the - * configuration service. - */ - public void loadStoredAccounts() - { - super.loadStoredAccounts(DictActivator.getBundleContext()); - } - - - /** * Initializaed and creates an account corresponding to the specified * accountProperties and registers the resulting ProtocolProvider in the * <tt>context</tt> BundleContext parameter. @@ -132,7 +82,7 @@ public class ProtocolProviderFactoryDictImpl //an osgi event, the osgi event triggers (through the UI) a call to the //ProtocolProviderService.register() method and it needs to acces //the configuration service and check for a stored password. - this.storeAccount(DictActivator.getBundleContext(), accountID); + this.storeAccount(accountID); accountID = loadAccount(accountProperties); @@ -143,160 +93,29 @@ public class ProtocolProviderFactoryDictImpl return accountID; } - - /** - * Initializes and creates an account corresponding to the specified - * accountProperties and registers the resulting ProtocolProvider in the - * <tt>context</tt> BundleContext parameter. - * - * @param accountProperties a set of protocol (or implementation) - * specific properties defining the new account. - * @return the AccountID of the newly loaded account - */ - public AccountID loadAccount(Map accountProperties) - { - //BundleContext context = DictActivator.getBundleContext(); - - if(bundleContext == null) - { - throw new NullPointerException("The specified BundleContext was null"); - } - - String userIDStr = (String) accountProperties.get(USER_ID); - - AccountID accountID = new DictAccountID(userIDStr, accountProperties); - - //get a reference to the configuration service and register whatever - //properties we have in it. - - Hashtable properties = new Hashtable(); - properties.put(PROTOCOL, ProtocolNames.DICT); - properties.put(USER_ID, userIDStr); - - ProtocolProviderServiceDictImpl dictProtocolProvider - = new ProtocolProviderServiceDictImpl(); - - dictProtocolProvider.initialize(userIDStr, accountID); - - ServiceRegistration registration - = bundleContext.registerService( ProtocolProviderService.class.getName(), - dictProtocolProvider, - properties); - - registeredAccounts.put(accountID, registration); - return accountID; - } - - /** - * Removes the specified account from the list of accounts that this - * provider factory is handling. - * - * @param accountID the ID of the account to remove. - * @return true if an account with the specified ID existed and was - * removed and false otherwise. - */ - public boolean uninstallAccount(AccountID accountID) + protected AccountID createAccountID(String userID, Map accountProperties) { - //unregister the protocol provider - ServiceReference serRef = getProviderForAccount(accountID); - - ProtocolProviderService protocolProvider - = (ProtocolProviderService) DictActivator.getBundleContext() - .getService(serRef); - - try - { - protocolProvider.unregister(); - } - catch (OperationFailedException exc) - { - logger.error("Failed to unregister protocol provider for account : " - + accountID + " caused by : " + exc); - } - - ServiceRegistration registration - = (ServiceRegistration) registeredAccounts.remove(accountID); - - if(registration == null) - { - return false; - } - - //kill the service - registration.unregister(); - - registeredAccounts.remove(accountID); - - return removeStoredAccount(DictActivator.getBundleContext(), accountID); + return new DictAccountID(userID, accountProperties); } - /** - * Saves the password for the specified account after scrambling it a bit - * so that it is not visible from first sight (Method remains highly - * insecure). - * - * @param accountID the AccountID for the account whose password we're - * storing. - * @param passwd the password itself. - * - * @throws java.lang.IllegalArgumentException if no account corresponding - * to <tt>accountID</tt> has been previously stored. - */ - public void storePassword(AccountID accountID, String passwd) - throws IllegalArgumentException + protected ProtocolProviderService createService(String userID, + AccountID accountID) { - super.storePassword(DictActivator.getBundleContext(), - accountID, - passwd); - } + ProtocolProviderServiceDictImpl service = + new ProtocolProviderServiceDictImpl(); - /** - * Returns the password last saved for the specified account. - * - * @param accountID the AccountID for the account whose password we're - * looking for.. - * - * @return a String containing the password for the specified accountID. - * - * @throws java.lang.IllegalArgumentException if no account corresponding - * to <tt>accountID</tt> has been previously stored. - */ - public String loadPassword(AccountID accountID) - throws IllegalArgumentException - { - return super.loadPassword(DictActivator.getBundleContext(), accountID ); + service.initialize(userID, accountID); + return service; } /** - * Prepares the factory for bundle shutdown. - */ - public void stop() - { - Enumeration registrations = this.registeredAccounts.elements(); - - while(registrations.hasMoreElements()) - { - ServiceRegistration reg - = ((ServiceRegistration)registrations.nextElement()); - - reg.unregister(); - } - - Enumeration idEnum = registeredAccounts.keys(); - - while(idEnum.hasMoreElements()) - { - registeredAccounts.remove(idEnum.nextElement()); - } - } - - /** * Creates a group for the dict contacts */ private void createGroup() { // Get MetaContactListService + BundleContext bundleContext = getBundleContext(); ServiceReference mfcServiceRef = bundleContext .getServiceReference(MetaContactListService.class.getName()); @@ -325,6 +144,7 @@ public class ProtocolProviderFactoryDictImpl private void createDefaultContact(AccountID accountID) { // Gets the MetaContactListService. + BundleContext bundleContext = getBundleContext(); ServiceReference mfcServiceRef = bundleContext .getServiceReference(MetaContactListService.class.getName()); MetaContactListService mcl = (MetaContactListService) diff --git a/src/net/java/sip/communicator/impl/protocol/gibberish/GibberishActivator.java b/src/net/java/sip/communicator/impl/protocol/gibberish/GibberishActivator.java index 4d53521..9aeb337 100644 --- a/src/net/java/sip/communicator/impl/protocol/gibberish/GibberishActivator.java +++ b/src/net/java/sip/communicator/impl/protocol/gibberish/GibberishActivator.java @@ -65,9 +65,6 @@ public class GibberishActivator gibberishProviderFactory = new ProtocolProviderFactoryGibberishImpl(); - //load all stored Gibberish accounts. - gibberishProviderFactory.loadStoredAccounts(); - //reg the gibberish provider factory. gibberishPpFactoryServReg = context.registerService( ProtocolProviderFactory.class.getName(), diff --git a/src/net/java/sip/communicator/impl/protocol/gibberish/ProtocolProviderFactoryGibberishImpl.java b/src/net/java/sip/communicator/impl/protocol/gibberish/ProtocolProviderFactoryGibberishImpl.java index d6c7806..6e43fb0 100644 --- a/src/net/java/sip/communicator/impl/protocol/gibberish/ProtocolProviderFactoryGibberishImpl.java +++ b/src/net/java/sip/communicator/impl/protocol/gibberish/ProtocolProviderFactoryGibberishImpl.java @@ -26,61 +26,13 @@ public class ProtocolProviderFactoryGibberishImpl = Logger.getLogger(ProtocolProviderFactoryGibberishImpl.class); /** - * The table that we store our accounts in. - */ - private Hashtable registeredAccounts = new Hashtable(); - - - /** * Creates an instance of the ProtocolProviderFactoryGibberishImpl. */ public ProtocolProviderFactoryGibberishImpl() { - super(); - } - - /** - * Returns the ServiceReference for the protocol provider corresponding - * to the specified accountID or null if the accountID is unknown. - * - * @param accountID the accountID of the protocol provider we'd like to - * get - * @return a ServiceReference object to the protocol provider with the - * specified account id and null if the account id is unknwon to the - * provider factory. - */ - public ServiceReference getProviderForAccount(AccountID accountID) - { - ServiceRegistration registration - = (ServiceRegistration)registeredAccounts.get(accountID); - - return (registration == null ) - ? null - : registration.getReference(); - } - - /** - * Returns a copy of the list containing the <tt>AccoudID</tt>s of all - * accounts currently registered in this protocol provider. - * - * @return a copy of the list containing the <tt>AccoudID</tt>s of all - * accounts currently registered in this protocol provider. - */ - public ArrayList getRegisteredAccounts() - { - return new ArrayList(registeredAccounts.keySet()); - } - - /** - * Loads (and hence installs) all accounts previously stored in the - * configuration service. - */ - public void loadStoredAccounts() - { - super.loadStoredAccounts( GibberishActivator.getBundleContext()); + super(GibberishActivator.getBundleContext(), "Gibberish"); } - /** * Initializaed and creates an account corresponding to the specified * accountProperties and registers the resulting ProtocolProvider in the @@ -119,9 +71,7 @@ public class ProtocolProviderFactoryGibberishImpl //an osgi event, the osgi event triggers (through the UI) a call to the //ProtocolProviderService.register() method and it needs to acces //the configuration service and check for a stored password. - this.storeAccount( - GibberishActivator.getBundleContext() - , accountID); + this.storeAccount(accountID); accountID = loadAccount(accountProperties); @@ -185,7 +135,7 @@ public class ProtocolProviderFactoryGibberishImpl // an osgi event, the osgi event triggers (trhgough the UI) a call to // the register() method and it needs to acces the configuration service // and check for a password. - this.storeAccount(GibberishActivator.getBundleContext(), accountID); + this.storeAccount(accountID); Hashtable properties = new Hashtable(); properties.put(PROTOCOL, ProtocolNames.GIBBERISH); @@ -196,8 +146,7 @@ public class ProtocolProviderFactoryGibberishImpl // We store again the account in order to store all properties added // during the protocol provider initialization. - this.storeAccount( - GibberishActivator.getBundleContext(), accountID); + this.storeAccount(accountID); registration = context.registerService( @@ -209,148 +158,18 @@ public class ProtocolProviderFactoryGibberishImpl registeredAccounts.put(accountID, registration); } - /** - * Initializes and creates an account corresponding to the specified - * accountProperties and registers the resulting ProtocolProvider in the - * <tt>context</tt> BundleContext parameter. - * - * @param accountProperties a set of protocol (or implementation) - * specific properties defining the new account. - * @return the AccountID of the newly loaded account - */ - public AccountID loadAccount( Map accountProperties) + protected AccountID createAccountID(String userID, Map accountProperties) { - BundleContext context - = GibberishActivator.getBundleContext(); - if(context == null) - throw new NullPointerException("The specified BundleContext was null"); - - String userIDStr = (String)accountProperties.get(USER_ID); - - AccountID accountID = new GibberishAccountID(userIDStr, accountProperties); - - //get a reference to the configuration service and register whatever - //properties we have in it. - - Hashtable properties = new Hashtable(); - properties.put(PROTOCOL, "Gibberish"); - properties.put(USER_ID, userIDStr); - - ProtocolProviderServiceGibberishImpl gibberishProtocolProvider - = new ProtocolProviderServiceGibberishImpl(); - - gibberishProtocolProvider.initialize(userIDStr, accountID); - - ServiceRegistration registration - = context.registerService( ProtocolProviderService.class.getName(), - gibberishProtocolProvider, - properties); - - registeredAccounts.put(accountID, registration); - return accountID; + return new GibberishAccountID(userID, accountProperties); } - - /** - * Removes the specified account from the list of accounts that this - * provider factory is handling. - * - * @param accountID the ID of the account to remove. - * @return true if an account with the specified ID existed and was - * removed and false otherwise. - */ - public boolean uninstallAccount(AccountID accountID) + protected ProtocolProviderService createService(String userID, + AccountID accountID) { - //unregister the protocol provider - ServiceReference serRef = getProviderForAccount(accountID); - - ProtocolProviderService protocolProvider - = (ProtocolProviderService) GibberishActivator.getBundleContext() - .getService(serRef); - - try { - protocolProvider.unregister(); - } - catch (OperationFailedException exc) { - logger.error("Failed to unregister protocol provider for account : " - + accountID + " caused by : " + exc); - } + ProtocolProviderServiceGibberishImpl service = + new ProtocolProviderServiceGibberishImpl(); - ServiceRegistration registration - = (ServiceRegistration)registeredAccounts.remove(accountID); - - if(registration == null) - return false; - - //kill the service - registration.unregister(); - - registeredAccounts.remove(accountID ); - - return removeStoredAccount( - GibberishActivator.getBundleContext() - , accountID); + service.initialize(userID, accountID); + return service; } - - /** - * Saves the password for the specified account after scrambling it a bit - * so that it is not visible from first sight (Method remains highly - * insecure). - * - * @param accountID the AccountID for the account whose password we're - * storing. - * @param passwd the password itself. - * - * @throws java.lang.IllegalArgumentException if no account corresponding - * to <tt>accountID</tt> has been previously stored. - */ - public void storePassword(AccountID accountID, String passwd) - throws IllegalArgumentException - { - super.storePassword(GibberishActivator.getBundleContext() - , accountID - , passwd); - } - - /** - * Returns the password last saved for the specified account. - * - * @param accountID the AccountID for the account whose password we're - * looking for.. - * - * @return a String containing the password for the specified accountID. - * - * @throws java.lang.IllegalArgumentException if no account corresponding - * to <tt>accountID</tt> has been previously stored. - */ - public String loadPassword(AccountID accountID) - throws IllegalArgumentException - { - return super.loadPassword(GibberishActivator.getBundleContext() - , accountID ); - } - - /** - * Prepares the factory for bundle shutdown. - */ - public void stop() - { - Enumeration registrations = this.registeredAccounts.elements(); - - while(registrations.hasMoreElements()) - { - ServiceRegistration reg - = ((ServiceRegistration)registrations.nextElement()); - - reg.unregister(); - } - - Enumeration idEnum = registeredAccounts.keys(); - - while(idEnum.hasMoreElements()) - { - registeredAccounts.remove(idEnum.nextElement()); - } - } - } diff --git a/src/net/java/sip/communicator/impl/protocol/icq/IcqActivator.java b/src/net/java/sip/communicator/impl/protocol/icq/IcqActivator.java index 9da06a2..48f5809 100644 --- a/src/net/java/sip/communicator/impl/protocol/icq/IcqActivator.java +++ b/src/net/java/sip/communicator/impl/protocol/icq/IcqActivator.java @@ -49,12 +49,6 @@ public class IcqActivator icqProviderFactory = new ProtocolProviderFactoryIcqImpl(false); aimProviderFactory = new ProtocolProviderFactoryIcqImpl(true); - //load all icq providers - icqProviderFactory.loadStoredAccounts(); - - //load all aim providers - aimProviderFactory.loadStoredAccounts(); - //reg the icq account man. icqPpFactoryServReg = context.registerService( ProtocolProviderFactory.class.getName(), diff --git a/src/net/java/sip/communicator/impl/protocol/icq/ProtocolProviderFactoryIcqImpl.java b/src/net/java/sip/communicator/impl/protocol/icq/ProtocolProviderFactoryIcqImpl.java index 8665b4c..3ed97c2 100644 --- a/src/net/java/sip/communicator/impl/protocol/icq/ProtocolProviderFactoryIcqImpl.java +++ b/src/net/java/sip/communicator/impl/protocol/icq/ProtocolProviderFactoryIcqImpl.java @@ -24,11 +24,6 @@ public class ProtocolProviderFactoryIcqImpl ProtocolProviderFactoryIcqImpl.class); /** - * The table that we store our accounts in. - */ - private Hashtable registeredAccounts = new Hashtable(); - - /** * Is this factory is created for aim or icq accounts */ private boolean isAimFactory = false; @@ -39,37 +34,10 @@ public class ProtocolProviderFactoryIcqImpl */ protected ProtocolProviderFactoryIcqImpl(boolean isAimFactory) { - this.isAimFactory = isAimFactory; - } - - /** - * Returns a copy of the list containing all accounts currently - * registered in this protocol provider. - * - * @return a copy of the llist containing all accounts currently installed - * in the protocol provider. - */ - public ArrayList getRegisteredAccounts() - { - return new ArrayList(registeredAccounts.keySet()); - } - - /** - * Returns the ServiceReference for the protocol provider corresponding to - * the specified accountID or null if the accountID is unknown. - * @param accountID the accountID of the protocol provider we'd like to get - * @return a ServiceReference object to the protocol provider with the - * specified account id and null if the account id is unknwon to the - * provider factory. - */ - public ServiceReference getProviderForAccount(AccountID accountID) - { - ServiceRegistration registration - = (ServiceRegistration)registeredAccounts.get(accountID); + super(IcqActivator.getBundleContext(), isAimFactory ? ProtocolNames.AIM + : ProtocolNames.ICQ); - return (registration == null ) - ? null - : registration.getReference(); + this.isAimFactory = isAimFactory; } /** @@ -115,9 +83,7 @@ public class ProtocolProviderFactoryIcqImpl //an osgi event, the osgi event triggers (trhgough the UI) a call to //the register() method and it needs to acces the configuration service //and check for a password. - this.storeAccount( - IcqActivator.getBundleContext() - , accountID); + this.storeAccount(accountID); accountID = loadAccount(accountProperties); @@ -128,184 +94,39 @@ public class ProtocolProviderFactoryIcqImpl * Initializes and creates an account corresponding to the specified * accountProperties and registers the resulting ProtocolProvider in the * <tt>context</tt> BundleContext parameter. - * - * @param accountProperties a set of protocol (or implementation) - * specific properties defining the new account. + * + * @param accountProperties a set of protocol (or implementation) specific + * properties defining the new account. * @return the AccountID of the newly created account */ - public AccountID loadAccount( Map accountProperties) + public AccountID loadAccount(Map accountProperties) { - BundleContext context - = IcqActivator.getBundleContext(); - if(context == null) - throw new NullPointerException("The specified BundleContext was null"); - // there are two factories - one for icq accounts and one for aim ones. // if we are trying to load an icq account in aim factory - skip it // and the same for aim accounts in icq factory - if((IcqAccountID.isAIM(accountProperties) && !isAimFactory) || - (!IcqAccountID.isAIM(accountProperties) && isAimFactory)) - return null; - - if (!accountProperties.containsKey(PROTOCOL)) - if(IcqAccountID.isAIM(accountProperties)) - accountProperties.put(PROTOCOL, ProtocolNames.AIM); - else - accountProperties.put(PROTOCOL, ProtocolNames.ICQ); - - String userIDStr = (String)accountProperties.get(USER_ID); - - AccountID accountID = new IcqAccountID(userIDStr, accountProperties); - - //get a reference to the configuration service and register whatever - //properties we have in it. - - ProtocolProviderServiceIcqImpl icqProtocolProvider - = new ProtocolProviderServiceIcqImpl(); - - icqProtocolProvider.initialize(userIDStr, accountID); - - Hashtable properties = new Hashtable(); - properties.put(PROTOCOL, icqProtocolProvider.getProtocolName()); - properties.put(USER_ID, userIDStr); - - ServiceRegistration registration - = context.registerService( ProtocolProviderService.class.getName(), - icqProtocolProvider, - properties); - - registeredAccounts.put(accountID, registration); - return accountID; - } - - - /** - * Removes the specified account from the list of accounts that this - * provider factory is handling. If the specified accountID is unknown to - * the ProtocolProviderFactory, the call has no effect and false is returned. - * This method is persistent in nature and once called the account - * corresponding to the specified ID will not be loaded during future runs - * of the project. - * - * @param accountID the ID of the account to remove. - * @return true if an account with the specified ID existed and was removed - * and false otherwise. - */ - public boolean uninstallAccount(AccountID accountID) - { - //unregister the protocol provider - ServiceReference serRef = getProviderForAccount(accountID); - - ProtocolProviderService protocolProvider - = (ProtocolProviderService) IcqActivator.getBundleContext() - .getService(serRef); - - try { - protocolProvider.unregister(); - } - catch (OperationFailedException e) { - logger.error("Failed to unregister protocol provider for account : " - + accountID + " caused by : " + e); - } - - ServiceRegistration registration - = (ServiceRegistration)registeredAccounts.remove(accountID); - - if(registration == null) - return false; - - //kill the service - registration.unregister(); - - return removeStoredAccount( - IcqActivator.getBundleContext() - , accountID); - } - - /** - * Loads (and hence installs) all accounts previously stored in the - * configuration service. - */ - public void loadStoredAccounts() - { - super.loadStoredAccounts( IcqActivator.getBundleContext()); - } - - /** - * Prepares the factory for bundle shutdown. - */ - public void stop() - { - Enumeration registrations = this.registeredAccounts.elements(); - - while(registrations.hasMoreElements()) + boolean accountPropertiesIsAIM = IcqAccountID.isAIM(accountProperties); + if ((accountPropertiesIsAIM && !isAimFactory) + || (!accountPropertiesIsAIM && isAimFactory)) { - ServiceRegistration reg - = ((ServiceRegistration)registrations.nextElement()); - - reg.unregister(); - - + return null; } - Enumeration idEnum = registeredAccounts.keys(); - - while(idEnum.hasMoreElements()) - { - registeredAccounts.remove(idEnum.nextElement()); - } + return super.loadAccount(accountProperties); } - /** - * Returns the configuraiton service property name prefix that we use to - * store properties concerning the account with the specified id. - * @param accountID the AccountID whose property name prefix we're looking - * for. - * @return the prefix of the configuration service property name that - * we're using when storing properties for the specified account. - */ - public String findAccountPrefix(AccountID accountID) + protected AccountID createAccountID(String userID, Map accountProperties) { - return super.findAccountPrefix(IcqActivator.getBundleContext() - , accountID); + return new IcqAccountID(userID, accountProperties); } - /** - * Saves the password for the specified account after scrambling it a bit - * so that it is not visible from first sight (Method remains highly - * insecure). - * - * @param accountID the AccountID for the account whose password we're - * storing. - * @param passwd the password itself. - * - * @throws java.lang.IllegalArgumentException if no account corresponding - * to <tt>accountID</tt> has been previously stored. - */ - public void storePassword(AccountID accountID, String passwd) - throws IllegalArgumentException + protected ProtocolProviderService createService(String userID, + AccountID accountID) { - super.storePassword(IcqActivator.getBundleContext() - , accountID - , passwd); - } + ProtocolProviderServiceIcqImpl service = + new ProtocolProviderServiceIcqImpl(); - /** - * Returns the password last saved for the specified account. - * - * @param accountID the AccountID for the account whose password we're - * looking for.. - * - * @return a String containing the password for the specified accountID. - * - * @throws java.lang.IllegalArgumentException if no account corresponding - * to <tt>accountID</tt> has been previously stored. - */ - public String loadPassword(AccountID accountID) - throws IllegalArgumentException - { - return super.loadPassword(IcqActivator.getBundleContext() - , accountID ); + service.initialize(userID, accountID); + return service; } @Override @@ -353,7 +174,7 @@ public class ProtocolProviderFactoryIcqImpl // an osgi event, the osgi event triggers (trhgough the UI) a call to // the register() method and it needs to acces the configuration service // and check for a password. - this.storeAccount(IcqActivator.getBundleContext(), accountID); + this.storeAccount(accountID); Hashtable properties = new Hashtable(); properties.put(PROTOCOL, ProtocolNames.ICQ); @@ -364,8 +185,7 @@ public class ProtocolProviderFactoryIcqImpl // We store again the account in order to store all properties added // during the protocol provider initialization. - this.storeAccount( - IcqActivator.getBundleContext(), accountID); + this.storeAccount(accountID); registration = context.registerService( diff --git a/src/net/java/sip/communicator/impl/protocol/irc/IrcActivator.java b/src/net/java/sip/communicator/impl/protocol/irc/IrcActivator.java index b9e36b9..0bf2302 100644 --- a/src/net/java/sip/communicator/impl/protocol/irc/IrcActivator.java +++ b/src/net/java/sip/communicator/impl/protocol/irc/IrcActivator.java @@ -66,9 +66,6 @@ public class IrcActivator ircProviderFactory = new ProtocolProviderFactoryIrcImpl(); - //Load all stored IRC accounts. - ircProviderFactory.loadStoredAccounts(); - //Register the IRC provider factory. ircPpFactoryServReg = context.registerService( ProtocolProviderFactory.class.getName(), diff --git a/src/net/java/sip/communicator/impl/protocol/irc/ProtocolProviderFactoryIrcImpl.java b/src/net/java/sip/communicator/impl/protocol/irc/ProtocolProviderFactoryIrcImpl.java index 3527d8c..cc8395a 100644 --- a/src/net/java/sip/communicator/impl/protocol/irc/ProtocolProviderFactoryIrcImpl.java +++ b/src/net/java/sip/communicator/impl/protocol/irc/ProtocolProviderFactoryIrcImpl.java @@ -9,6 +9,7 @@ package net.java.sip.communicator.impl.protocol.irc; import java.util.*; import org.osgi.framework.*; + import net.java.sip.communicator.service.protocol.*; import net.java.sip.communicator.util.*; @@ -25,50 +26,9 @@ public class ProtocolProviderFactoryIrcImpl private static final Logger logger = Logger.getLogger(ProtocolProviderFactoryIrcImpl.class); - /** - * The table that we store our accounts in. - */ - private Hashtable registeredAccounts = new Hashtable(); - - /** - * Returns a copy of the list containing the <tt>AccoudID</tt>s of all - * accounts currently registered in this protocol provider. - * - * @return a copy of the list containing the <tt>AccoudID</tt>s of all - * accounts currently registered in this protocol provider. - */ - public ArrayList getRegisteredAccounts() - { - return new ArrayList(registeredAccounts.keySet()); - } - - /** - * Returns the ServiceReference for the protocol provider corresponding - * to the specified accountID or null if the accountID is unknown. - * - * @param accountID the accountID of the protocol provider we'd like to - * get - * @return a ServiceReference object to the protocol provider with the - * specified account id and null if the account id is unknown to the - * provider factory. - */ - public ServiceReference getProviderForAccount(AccountID accountID) - { - ServiceRegistration registration - = (ServiceRegistration)registeredAccounts.get(accountID); - - return (registration == null ) - ? null - : registration.getReference(); - } - - /** - * Loads (and hence installs) all accounts previously stored in the - * configuration service. - */ - public void loadStoredAccounts() + public ProtocolProviderFactoryIrcImpl() { - super.loadStoredAccounts( IrcActivator.bundleContext); + super(IrcActivator.bundleContext, ProtocolNames.IRC); } /** @@ -112,128 +72,26 @@ public class ProtocolProviderFactoryIrcImpl //an OSGI event, the OSGI event triggers (through the UI) a call to the //ProtocolProviderService.register() method and it needs to access //the configuration service and check for a stored password. - this.storeAccount(IrcActivator.bundleContext, accountID); + this.storeAccount(accountID); accountID = loadAccount(accountProperties); return accountID; } - - /** - * Initializes and creates an account corresponding to the specified - * accountProperties and registers the resulting ProtocolProvider in the - * <tt>context</tt> BundleContext parameter. - * - * @param accountProperties a set of protocol (or implementation) - * specific properties defining the new account. - * @return the AccountID of the newly loaded account - */ - public AccountID loadAccount( Map accountProperties) - { - - if(IrcActivator.bundleContext == null) - throw new NullPointerException( - "The specified BundleContext was null"); - String userIDStr = (String)accountProperties.get(USER_ID); - - AccountID accountID = new IrcAccountID(userIDStr, accountProperties); - - //get a reference to the configuration service and register whatever - //properties we have in it. - - Hashtable properties = new Hashtable(); - properties.put(PROTOCOL, ProtocolNames.IRC); - properties.put(USER_ID, userIDStr); - - ProtocolProviderServiceIrcImpl ircProtocolProvider - = new ProtocolProviderServiceIrcImpl(); - - ircProtocolProvider.initialize(userIDStr, accountID); - - ServiceRegistration registration - = IrcActivator.bundleContext.registerService( - ProtocolProviderService.class.getName(), - ircProtocolProvider, - properties); - - registeredAccounts.put(accountID, registration); - return accountID; - } - - - /** - * Removes the specified account from the list of accounts that this - * provider factory is handling. - * - * @param accountID the ID of the account to remove. - * @return true if an account with the specified ID existed and was - * removed and false otherwise. - */ - public boolean uninstallAccount(AccountID accountID) + protected AccountID createAccountID(String userID, Map accountProperties) { - //unregister the protocol provider - ServiceReference serRef = getProviderForAccount(accountID); - - ProtocolProviderService protocolProvider - = (ProtocolProviderService) IrcActivator.bundleContext - .getService(serRef); - - try { - protocolProvider.unregister(); - } - catch (OperationFailedException exc) { - logger.error("Failed to unregister protocol provider for account : " - + accountID + " caused by : " + exc); - } - - ServiceRegistration registration - = (ServiceRegistration)registeredAccounts.remove(accountID); - - if(registration == null) - return false; - - //kill the service - registration.unregister(); - - return removeStoredAccount(IrcActivator.bundleContext, accountID); + return new IrcAccountID(userID, accountProperties); } - /** - * Saves the password for the specified account after scrambling it a bit - * so that it is not visible from first sight (Method remains highly - * insecure). - * - * @param accountID the AccountID for the account whose password we're - * storing. - * @param passwd the password itself. - * - * @throws java.lang.IllegalArgumentException if no account corresponding - * to <tt>accountID</tt> has been previously stored. - */ - public void storePassword(AccountID accountID, String passwd) - throws IllegalArgumentException + protected ProtocolProviderService createService(String userID, + AccountID accountID) { - super.storePassword(IrcActivator.bundleContext, - accountID, - passwd); - } + ProtocolProviderServiceIrcImpl service = + new ProtocolProviderServiceIrcImpl(); - /** - * Returns the password last saved for the specified account. - * - * @param accountID the AccountID for the account whose password we're - * looking for. - * - * @return a String containing the password for the specified accountID. - * - * @throws java.lang.IllegalArgumentException if no account corresponding - * to <tt>accountID</tt> has been previously stored. - */ - public String loadPassword(AccountID accountID) - throws IllegalArgumentException - { - return super.loadPassword(IrcActivator.bundleContext, accountID ); + service.initialize(userID, accountID); + return service; } @Override @@ -244,5 +102,4 @@ public class ProtocolProviderFactoryIrcImpl // TODO Auto-generated method stub } - }
\ No newline at end of file diff --git a/src/net/java/sip/communicator/impl/protocol/jabber/JabberActivator.java b/src/net/java/sip/communicator/impl/protocol/jabber/JabberActivator.java index e72ea38..269e109 100644 --- a/src/net/java/sip/communicator/impl/protocol/jabber/JabberActivator.java +++ b/src/net/java/sip/communicator/impl/protocol/jabber/JabberActivator.java @@ -66,9 +66,6 @@ public class JabberActivator jabberProviderFactory = new ProtocolProviderFactoryJabberImpl(); - //load all jabber providers - jabberProviderFactory.loadStoredAccounts(); - //reg the jabber account man. jabberPpFactoryServReg = context.registerService( ProtocolProviderFactory.class.getName(), diff --git a/src/net/java/sip/communicator/impl/protocol/jabber/ProtocolProviderFactoryJabberImpl.java b/src/net/java/sip/communicator/impl/protocol/jabber/ProtocolProviderFactoryJabberImpl.java index 025b7ae..025dceb 100644 --- a/src/net/java/sip/communicator/impl/protocol/jabber/ProtocolProviderFactoryJabberImpl.java +++ b/src/net/java/sip/communicator/impl/protocol/jabber/ProtocolProviderFactoryJabberImpl.java @@ -25,45 +25,11 @@ public class ProtocolProviderFactoryJabberImpl ProtocolProviderFactoryJabberImpl.class); /** - * The table that we store our accounts in. - */ - private Hashtable registeredAccounts = new Hashtable(); - - /** * Creates an instance of the ProtocolProviderFactoryJabberImpl. */ protected ProtocolProviderFactoryJabberImpl() { - } - - /** - * Returns a copy of the list containing all accounts currently - * registered in this protocol provider. - * - * @return a copy of the llist containing all accounts currently installed - * in the protocol provider. - */ - public ArrayList getRegisteredAccounts() - { - return new ArrayList(registeredAccounts.keySet()); - } - - /** - * Returns the ServiceReference for the protocol provider corresponding to - * the specified accountID or null if the accountID is unknown. - * @param accountID the accountID of the protocol provider we'd like to get - * @return a ServiceReference object to the protocol provider with the - * specified account id and null if the account id is unknwon to the - * provider factory. - */ - public ServiceReference getProviderForAccount(AccountID accountID) - { - ServiceRegistration registration - = (ServiceRegistration)registeredAccounts.get(accountID); - - return (registration == null ) - ? null - : registration.getReference(); + super(JabberActivator.getBundleContext(), ProtocolNames.JABBER); } /** @@ -119,185 +85,26 @@ public class ProtocolProviderFactoryJabberImpl //an osgi event, the osgi event triggers (trhgough the UI) a call to //the register() method and it needs to acces the configuration service //and check for a password. - this.storeAccount( - JabberActivator.getBundleContext() - , accountID); + this.storeAccount(accountID); accountID = loadAccount(accountProperties); return accountID; } - /** - * Initializes and creates an account corresponding to the specified - * accountProperties and registers the resulting ProtocolProvider in the - * <tt>context</tt> BundleContext parameter. - * - * @param accountProperties a set of protocol (or implementation) - * specific properties defining the new account. - * @return the AccountID of the newly created account - */ - public AccountID loadAccount( Map accountProperties) - { - BundleContext context - = JabberActivator.getBundleContext(); - if(context == null) - throw new NullPointerException( - "The specified BundleContext was null"); - - String userIDStr = (String)accountProperties.get(USER_ID); - - AccountID accountID = new JabberAccountID(userIDStr, accountProperties); - - //get a reference to the configuration service and register whatever - //properties we have in it. - - Hashtable properties = new Hashtable(); - properties.put(PROTOCOL, ProtocolNames.JABBER); - properties.put(USER_ID, userIDStr); - - ProtocolProviderServiceJabberImpl jabberProtocolProvider - = new ProtocolProviderServiceJabberImpl(); - - jabberProtocolProvider.initialize(userIDStr, accountID); - - ServiceRegistration registration - = context.registerService( ProtocolProviderService.class.getName(), - jabberProtocolProvider, - properties); - - registeredAccounts.put(accountID, registration); - return accountID; - } - - - /** - * Removes the specified account from the list of accounts that this - * provider factory is handling. If the specified accountID is unknown to - * the ProtocolProviderFactory, the call has no effect and false is returned. - * This method is persistent in nature and once called the account - * corresponding to the specified ID will not be loaded during future runs - * of the project. - * - * @param accountID the ID of the account to remove. - * @return true if an account with the specified ID existed and was removed - * and false otherwise. - */ - public boolean uninstallAccount(AccountID accountID) - { - //unregister the protocol provider - ServiceReference serRef = getProviderForAccount(accountID); - - ProtocolProviderService protocolProvider - = (ProtocolProviderService) JabberActivator.getBundleContext() - .getService(serRef); - - try { - protocolProvider.unregister(); - } - catch (OperationFailedException exc) { - logger.error("Failed to unregister protocol provider for account : " - + accountID + " caused by : " + exc); - } - - ServiceRegistration registration - = (ServiceRegistration)registeredAccounts.remove(accountID); - - if(registration == null) - return false; - - //kill the service - registration.unregister(); - - return removeStoredAccount( - JabberActivator.getBundleContext() - , accountID); - } - - /** - * Loads (and hence installs) all accounts previously stored in the - * configuration service. - */ - public void loadStoredAccounts() + protected AccountID createAccountID(String userID, Map accountProperties) { - super.loadStoredAccounts( JabberActivator.getBundleContext()); + return new JabberAccountID(userID, accountProperties); } - /** - * Prepares the factory for bundle shutdown. - */ - public void stop() + protected ProtocolProviderService createService(String userID, + AccountID accountID) { - Enumeration registrations = this.registeredAccounts.elements(); - - while(registrations.hasMoreElements()) - { - ServiceRegistration reg - = ((ServiceRegistration)registrations.nextElement()); + ProtocolProviderServiceJabberImpl service = + new ProtocolProviderServiceJabberImpl(); - ProtocolProviderServiceJabberImpl provider - = (ProtocolProviderServiceJabberImpl) JabberActivator - .getBundleContext().getService(reg.getReference()); - - //do an attempt to kill the provider - provider.shutdown(); - reg.unregister(); - } - - registeredAccounts.clear(); - } - - - /** - * Returns the configuraiton service property name prefix that we use to - * store properties concerning the account with the specified id. - * @param accountID the AccountID whose property name prefix we're looking - * for. - * @return the prefix of the configuration service property name that - * we're using when storing properties for the specified account. - */ - public String findAccountPrefix(AccountID accountID) - { - return super.findAccountPrefix(JabberActivator.getBundleContext() - , accountID); - } - - /** - * Saves the password for the specified account after scrambling it a bit - * so that it is not visible from first sight (Method remains highly - * insecure). - * - * @param accountID the AccountID for the account whose password we're - * storing. - * @param passwd the password itself. - * - * @throws java.lang.IllegalArgumentException if no account corresponding - * to <tt>accountID</tt> has been previously stored. - */ - public void storePassword(AccountID accountID, String passwd) - throws IllegalArgumentException - { - super.storePassword(JabberActivator.getBundleContext() - , accountID - , passwd); - } - - /** - * Returns the password last saved for the specified account. - * - * @param accountID the AccountID for the account whose password we're - * looking for.. - * - * @return a String containing the password for the specified accountID. - * - * @throws java.lang.IllegalArgumentException if no account corresponding - * to <tt>accountID</tt> has been previously stored. - */ - public String loadPassword(AccountID accountID) - throws IllegalArgumentException - { - return super.loadPassword(JabberActivator.getBundleContext() - , accountID ); + service.initialize(userID, accountID); + return service; } @Override @@ -358,7 +165,7 @@ public class ProtocolProviderFactoryJabberImpl // an osgi event, the osgi event triggers (trhgough the UI) a call to // the register() method and it needs to acces the configuration service // and check for a password. - this.storeAccount(JabberActivator.getBundleContext(), accountID); + this.storeAccount(accountID); Hashtable properties = new Hashtable(); properties.put(PROTOCOL, ProtocolNames.JABBER); @@ -369,8 +176,7 @@ public class ProtocolProviderFactoryJabberImpl // We store again the account in order to store all properties added // during the protocol provider initialization. - this.storeAccount( - JabberActivator.getBundleContext(), accountID); + this.storeAccount(accountID); registration = context.registerService( diff --git a/src/net/java/sip/communicator/impl/protocol/msn/MsnActivator.java b/src/net/java/sip/communicator/impl/protocol/msn/MsnActivator.java index 7dbb079..3587034 100644 --- a/src/net/java/sip/communicator/impl/protocol/msn/MsnActivator.java +++ b/src/net/java/sip/communicator/impl/protocol/msn/MsnActivator.java @@ -48,9 +48,6 @@ public class MsnActivator msnProviderFactory = new ProtocolProviderFactoryMsnImpl(); - //load all msn providers - msnProviderFactory.loadStoredAccounts(); - //reg the msn account man. msnPpFactoryServReg = context.registerService( ProtocolProviderFactory.class.getName(), diff --git a/src/net/java/sip/communicator/impl/protocol/msn/ProtocolProviderFactoryMsnImpl.java b/src/net/java/sip/communicator/impl/protocol/msn/ProtocolProviderFactoryMsnImpl.java index 9d9c7b9..3229282 100644 --- a/src/net/java/sip/communicator/impl/protocol/msn/ProtocolProviderFactoryMsnImpl.java +++ b/src/net/java/sip/communicator/impl/protocol/msn/ProtocolProviderFactoryMsnImpl.java @@ -19,46 +19,13 @@ import net.java.sip.communicator.service.protocol.*; public class ProtocolProviderFactoryMsnImpl extends ProtocolProviderFactory { - /** - * The table that we store our accounts in. - */ - private Hashtable registeredAccounts = new Hashtable(); /** * Creates an instance of the ProtocolProviderFactoryMsnImpl. */ protected ProtocolProviderFactoryMsnImpl() { - } - - /** - * Returns a copy of the list containing all accounts currently - * registered in this protocol provider. - * - * @return a copy of the llist containing all accounts currently installed - * in the protocol provider. - */ - public ArrayList getRegisteredAccounts() - { - return new ArrayList(registeredAccounts.keySet()); - } - - /** - * Returns the ServiceReference for the protocol provider corresponding to - * the specified accountID or null if the accountID is unknown. - * @param accountID the accountID of the protocol provider we'd like to get - * @return a ServiceReference object to the protocol provider with the - * specified account id and null if the account id is unknwon to the - * provider factory. - */ - public ServiceReference getProviderForAccount(AccountID accountID) - { - ServiceRegistration registration - = (ServiceRegistration)registeredAccounts.get(accountID); - - return (registration == null ) - ? null - : registration.getReference(); + super(MsnActivator.getBundleContext(), ProtocolNames.MSN); } /** @@ -100,167 +67,26 @@ public class ProtocolProviderFactoryMsnImpl //an osgi event, the osgi event triggers (trhgough the UI) a call to //the register() method and it needs to acces the configuration service //and check for a password. - this.storeAccount( - MsnActivator.getBundleContext() - , accountID); + this.storeAccount(accountID); accountID = loadAccount(accountProperties); return accountID; } - /** - * Initializes and creates an account corresponding to the specified - * accountProperties and registers the resulting ProtocolProvider in the - * <tt>context</tt> BundleContext parameter. - * - * @param accountProperties a set of protocol (or implementation) - * specific properties defining the new account. - * @return the AccountID of the newly created account - */ - public AccountID loadAccount( Map accountProperties) + protected AccountID createAccountID(String userID, Map accountProperties) { - BundleContext context - = MsnActivator.getBundleContext(); - if(context == null) - throw new NullPointerException("The specified BundleContext was null"); - - String userIDStr = (String)accountProperties.get(USER_ID); - - AccountID accountID = new MsnAccountID(userIDStr, accountProperties); - - //get a reference to the configuration service and register whatever - //properties we have in it. - - Hashtable properties = new Hashtable(); - properties.put(PROTOCOL, ProtocolNames.MSN); - properties.put(USER_ID, userIDStr); - - ProtocolProviderServiceMsnImpl msnProtocolProvider - = new ProtocolProviderServiceMsnImpl(); - - msnProtocolProvider.initialize(userIDStr, accountID); - - ServiceRegistration registration - = context.registerService( ProtocolProviderService.class.getName(), - msnProtocolProvider, - properties); - - registeredAccounts.put(accountID, registration); - return accountID; + return new MsnAccountID(userID, accountProperties); } - - /** - * Removes the specified account from the list of accounts that this - * provider factory is handling. If the specified accountID is unknown to - * the ProtocolProviderFactory, the call has no effect and false is returned. - * This method is persistent in nature and once called the account - * corresponding to the specified ID will not be loaded during future runs - * of the project. - * - * @param accountID the ID of the account to remove. - * @return true if an account with the specified ID existed and was removed - * and false otherwise. - */ - public boolean uninstallAccount(AccountID accountID) - { - ServiceRegistration registration - = (ServiceRegistration)registeredAccounts.remove(accountID); - - if(registration == null) - return false; - - //kill the service - registration.unregister(); - - return removeStoredAccount( - MsnActivator.getBundleContext() - , accountID); - } - - /** - * Loads (and hence installs) all accounts previously stored in the - * configuration service. - */ - public void loadStoredAccounts() - { - super.loadStoredAccounts( MsnActivator.getBundleContext()); - } - - /** - * Prepares the factory for bundle shutdown. - */ - public void stop() - { - Enumeration registrations = this.registeredAccounts.elements(); - - while(registrations.hasMoreElements()) - { - ServiceRegistration reg - = ((ServiceRegistration)registrations.nextElement()); - - reg.unregister(); - } - - Enumeration idEnum = registeredAccounts.keys(); - - while(idEnum.hasMoreElements()) - { - registeredAccounts.remove(idEnum.nextElement()); - } - } - - /** - * Returns the configuraiton service property name prefix that we use to - * store properties concerning the account with the specified id. - * @param accountID the AccountID whose property name prefix we're looking - * for. - * @return the prefix of the configuration service property name that - * we're using when storing properties for the specified account. - */ - public String findAccountPrefix(AccountID accountID) - { - return super.findAccountPrefix(MsnActivator.getBundleContext() - , accountID); - } - - /** - * Saves the password for the specified account after scrambling it a bit - * so that it is not visible from first sight (Method remains highly - * insecure). - * - * @param accountID the AccountID for the account whose password we're - * storing. - * @param passwd the password itself. - * - * @throws java.lang.IllegalArgumentException if no account corresponding - * to <tt>accountID</tt> has been previously stored. - */ - public void storePassword(AccountID accountID, String passwd) - throws IllegalArgumentException + protected ProtocolProviderService createService(String userID, + AccountID accountID) { - super.storePassword(MsnActivator.getBundleContext() - , accountID - , passwd); - } + ProtocolProviderServiceMsnImpl service = + new ProtocolProviderServiceMsnImpl(); - /** - * Returns the password last saved for the specified account. - * - * @param accountID the AccountID for the account whose password we're - * looking for.. - * - * @return a String containing the password for the specified accountID. - * - * @throws java.lang.IllegalArgumentException if no account corresponding - * to <tt>accountID</tt> has been previously stored. - */ - public String loadPassword(AccountID accountID) - throws IllegalArgumentException - { - return super.loadPassword(MsnActivator.getBundleContext() - , accountID ); + service.initialize(userID, accountID); + return service; } @Override @@ -308,7 +134,7 @@ public class ProtocolProviderFactoryMsnImpl // an osgi event, the osgi event triggers (trhgough the UI) a call to // the register() method and it needs to acces the configuration service // and check for a password. - this.storeAccount(MsnActivator.getBundleContext(), accountID); + this.storeAccount(accountID); Hashtable properties = new Hashtable(); properties.put(PROTOCOL, ProtocolNames.MSN); @@ -319,8 +145,7 @@ public class ProtocolProviderFactoryMsnImpl // We store again the account in order to store all properties added // during the protocol provider initialization. - this.storeAccount( - MsnActivator.getBundleContext(), accountID); + this.storeAccount(accountID); registration = context.registerService( diff --git a/src/net/java/sip/communicator/impl/protocol/msn/ProtocolProviderServiceMsnImpl.java b/src/net/java/sip/communicator/impl/protocol/msn/ProtocolProviderServiceMsnImpl.java index e988695..91d9e58 100644 --- a/src/net/java/sip/communicator/impl/protocol/msn/ProtocolProviderServiceMsnImpl.java +++ b/src/net/java/sip/communicator/impl/protocol/msn/ProtocolProviderServiceMsnImpl.java @@ -1,4 +1,3 @@ - /* * SIP Communicator, the OpenSource Java VoIP and Instant Messaging client. * @@ -7,7 +6,6 @@ */ package net.java.sip.communicator.impl.protocol.msn; -import java.io.*; import java.net.*; import java.nio.channels.*; import java.util.*; @@ -335,8 +333,11 @@ public class ProtocolProviderServiceMsnImpl public void shutdown() { synchronized(initializationLock){ - messenger.logout(); - messenger = null; + if (messenger != null) + { + messenger.logout(); + messenger = null; + } isInitialized = false; } } diff --git a/src/net/java/sip/communicator/impl/protocol/rss/ProtocolProviderFactoryRssImpl.java b/src/net/java/sip/communicator/impl/protocol/rss/ProtocolProviderFactoryRssImpl.java index 2336022..04f34e8 100644 --- a/src/net/java/sip/communicator/impl/protocol/rss/ProtocolProviderFactoryRssImpl.java +++ b/src/net/java/sip/communicator/impl/protocol/rss/ProtocolProviderFactoryRssImpl.java @@ -9,7 +9,7 @@ package net.java.sip.communicator.impl.protocol.rss; import java.util.*; import org.osgi.framework.*; -import net.java.sip.communicator.service.contactlist.*; + import net.java.sip.communicator.service.protocol.*; import net.java.sip.communicator.util.*; @@ -26,62 +26,16 @@ public class ProtocolProviderFactoryRssImpl = Logger.getLogger(ProtocolProviderFactoryRssImpl.class); /** - * The table that we store our accounts in. - */ - private Hashtable registeredAccounts = new Hashtable(); - - /** * Creates an instance of the ProtocolProviderFactoryRssImpl. */ public ProtocolProviderFactoryRssImpl() { - super(); - } - - /** - * Returns the ServiceReference for the protocol provider corresponding - * to the specified accountID or null if the accountID is unknown. - * - * @param accountID the accountID of the protocol provider we'd like to - * get - * @return a ServiceReference object to the protocol provider with the - * specified account id and null if the account id is unknwon to the - * provider factory. - */ - public ServiceReference getProviderForAccount(AccountID accountID) - { - ServiceRegistration registration - = (ServiceRegistration)registeredAccounts.get(accountID); - - return (registration == null ) - ? null - : registration.getReference(); - } - - /** - * Returns a copy of the list containing the <tt>AccoudID</tt>s of all - * accounts currently registered in this protocol provider. - * - * @return a copy of the list containing the <tt>AccoudID</tt>s of all - * accounts currently registered in this protocol provider. - */ - public ArrayList getRegisteredAccounts() - { - return new ArrayList(registeredAccounts.keySet()); - } - - /** - * Loads (and hence installs) all accounts previously stored in the - * configuration service. - */ - public void loadStoredAccounts() - { - super.loadStoredAccounts( RssActivator.getBundleContext()); + super(RssActivator.getBundleContext(), + ProtocolProviderServiceRssImpl.RSS_PROTOCOL_NAME); } - /** - * Initializaed and creates an account corresponding to the specified + * Initialized and creates an account corresponding to the specified * accountProperties and registers the resulting ProtocolProvider in the * <tt>context</tt> BundleContext parameter. * @@ -118,156 +72,26 @@ public class ProtocolProviderFactoryRssImpl //an osgi event, the osgi event triggers (through the UI) a call to the //ProtocolProviderService.register() method and it needs to acces //the configuration service and check for a stored password. - this.storeAccount( - RssActivator.getBundleContext() - , accountID); + this.storeAccount(accountID); accountID = loadAccount(accountProperties); return accountID; } - /** - * Initializes and creates an account corresponding to the specified - * accountProperties and registers the resulting ProtocolProvider in the - * <tt>context</tt> BundleContext parameter. - * - * @param accountProperties a set of protocol (or implementation) - * specific properties defining the new account. - * @return the AccountID of the newly loaded account - */ - public AccountID loadAccount( Map accountProperties) - { - BundleContext context - = RssActivator.getBundleContext(); - if(context == null) - throw new NullPointerException("The specified BundleContext was null"); - - String userIDStr = (String)accountProperties.get(USER_ID); - - AccountID accountID = new RssAccountID(userIDStr, accountProperties); - - //get a reference to the configuration service and register whatever - //properties we have in it. - - Hashtable properties = new Hashtable(); - properties.put(PROTOCOL - , ProtocolProviderServiceRssImpl.RSS_PROTOCOL_NAME); - properties.put(USER_ID, userIDStr); - - ProtocolProviderServiceRssImpl rssProtocolProvider - = new ProtocolProviderServiceRssImpl(); - - rssProtocolProvider.initialize(userIDStr, accountID); - - ServiceRegistration registration - = context.registerService( ProtocolProviderService.class.getName(), - rssProtocolProvider, - properties); - - registeredAccounts.put(accountID, registration); - return accountID; - } - - - /** - * Removes the specified account from the list of accounts that this - * provider factory is handling. - * - * @param accountID the ID of the account to remove. - * @return true if an account with the specified ID existed and was - * removed and false otherwise. - */ - public boolean uninstallAccount(AccountID accountID) - { - //unregister the protocol provider - ServiceReference serRef = getProviderForAccount(accountID); - - ProtocolProviderService protocolProvider - = (ProtocolProviderService) RssActivator.getBundleContext() - .getService(serRef); - - try - { - protocolProvider.unregister(); - } - catch (OperationFailedException exc) - { - logger.error("Failed to unregister protocol provider for account : " - + accountID + " caused by : " + exc); - } - - ServiceRegistration registration - = (ServiceRegistration)registeredAccounts.remove(accountID); - - if(registration == null) - return false; - - //kill the service - registration.unregister(); - - registeredAccounts.remove(accountID); - - return removeStoredAccount(RssActivator.getBundleContext(), accountID); - } - /** - * Saves the password for the specified account after scrambling it a bit - * so that it is not visible from first sight (Method remains highly - * insecure). - * - * @param accountID the AccountID for the account whose password we're - * storing. - * @param passwd the password itself. - * - * @throws java.lang.IllegalArgumentException if no account corresponding - * to <tt>accountID</tt> has been previously stored. - */ - public void storePassword(AccountID accountID, String passwd) - throws IllegalArgumentException + protected AccountID createAccountID(String userID, Map accountProperties) { - super.storePassword(RssActivator.getBundleContext(), - accountID, - passwd); + return new RssAccountID(userID, accountProperties); } - /** - * Returns the password last saved for the specified account. - * - * @param accountID the AccountID for the account whose password we're - * looking for.. - * - * @return a String containing the password for the specified accountID. - * - * @throws java.lang.IllegalArgumentException if no account corresponding - * to <tt>accountID</tt> has been previously stored. - */ - public String loadPassword(AccountID accountID) - throws IllegalArgumentException + protected ProtocolProviderService createService(String userID, + AccountID accountID) { - return super.loadPassword(RssActivator.getBundleContext(), accountID ); - } - - /** - * Prepares the factory for bundle shutdown. - */ - public void stop() - { - Enumeration registrations = this.registeredAccounts.elements(); - - while(registrations.hasMoreElements()) - { - ServiceRegistration reg - = ((ServiceRegistration)registrations.nextElement()); - - reg.unregister(); - } - - Enumeration idEnum = registeredAccounts.keys(); + ProtocolProviderServiceRssImpl service = + new ProtocolProviderServiceRssImpl(); - while(idEnum.hasMoreElements()) - { - registeredAccounts.remove(idEnum.nextElement()); - } + service.initialize(userID, accountID); + return service; } @Override diff --git a/src/net/java/sip/communicator/impl/protocol/rss/RssActivator.java b/src/net/java/sip/communicator/impl/protocol/rss/RssActivator.java index cae818c..b839e74 100644 --- a/src/net/java/sip/communicator/impl/protocol/rss/RssActivator.java +++ b/src/net/java/sip/communicator/impl/protocol/rss/RssActivator.java @@ -84,9 +84,6 @@ public class RssActivator rssProviderFactory = new ProtocolProviderFactoryRssImpl(); - //load all stored Rss accounts. - rssProviderFactory.loadStoredAccounts(); - //reg the rss provider factory. rssPpFactoryServReg = context.registerService( ProtocolProviderFactory.class.getName(), diff --git a/src/net/java/sip/communicator/impl/protocol/sip/ProtocolProviderFactorySipImpl.java b/src/net/java/sip/communicator/impl/protocol/sip/ProtocolProviderFactorySipImpl.java index 8764a6e..b40ddc1 100644 --- a/src/net/java/sip/communicator/impl/protocol/sip/ProtocolProviderFactorySipImpl.java +++ b/src/net/java/sip/communicator/impl/protocol/sip/ProtocolProviderFactorySipImpl.java @@ -25,48 +25,11 @@ public class ProtocolProviderFactorySipImpl Logger.getLogger(ProtocolProviderFactorySipImpl.class); /** - * The table that we store our accounts in. - */ - private Hashtable<AccountID, ServiceRegistration> registeredAccounts - = new Hashtable<AccountID, ServiceRegistration>(); - - /** * Constructs a new instance of the ProtocolProviderFactorySipImpl. */ public ProtocolProviderFactorySipImpl() { - } - - /** - * Returns the ServiceReference for the protocol provider corresponding - * to the specified accountID or null if the accountID is unknown. - * - * @param accountID the accountID of the protocol provider we'd like to - * get - * @return a ServiceReference object to the protocol provider with the - * specified account id and null if the account id is unknwon to the - * provider factory. - */ - public ServiceReference getProviderForAccount(AccountID accountID) - { - ServiceRegistration registration - = (ServiceRegistration)registeredAccounts.get(accountID); - - return (registration == null ) - ? null - : registration.getReference(); - } - - /** - * Returns a copy of the list containing all accounts currently - * registered in this protocol provider. - * - * @return a copy of the llist containing all accounts currently installed - * in the protocol provider. - */ - public ArrayList<AccountID> getRegisteredAccounts() - { - return new ArrayList<AccountID>(registeredAccounts.keySet()); + super(SipActivator.getBundleContext(), ProtocolNames.SIP); } /** @@ -120,12 +83,10 @@ public class ProtocolProviderFactorySipImpl "An account for id " + userIDStr + " was already installed!"); //first store the account and only then load it as the load generates - //an osgi event, the osgi event triggers (trhgough the UI) a call to - //the register() method and it needs to acces the configuration service + //an osgi event, the osgi event triggers (through the UI) a call to + //the register() method and it needs to access the configuration service //and check for a password. - this.storeAccount( - SipActivator.getBundleContext(), - accountID); + this.storeAccount(accountID); try { @@ -203,7 +164,7 @@ public class ProtocolProviderFactorySipImpl // an osgi event, the osgi event triggers (trhgough the UI) a call to // the register() method and it needs to acces the configuration service // and check for a password. - this.storeAccount(SipActivator.getBundleContext(), accountID); + this.storeAccount(accountID); String userIDStr = (String) accountProperties.get(USER_ID); @@ -218,8 +179,7 @@ public class ProtocolProviderFactorySipImpl // We store again the account in order to store all properties added // during the protocol provider initialization. - this.storeAccount( - SipActivator.getBundleContext(), accountID); + this.storeAccount(accountID); registration = context.registerService( @@ -237,61 +197,29 @@ public class ProtocolProviderFactorySipImpl } } - /** - * Initializes and creates an account corresponding to the specified - * accountProperties and registers the resulting ProtocolProvider in the - * <tt>context</tt> BundleContext parameter. - * - * @param accountProperties a set of protocol (or implementation) - * specific properties defining the new account. - * @return the AccountID of the newly created account - */ - protected AccountID loadAccount(Map accountProperties) + protected AccountID createAccountID(String userID, Map accountProperties) { - BundleContext context - = SipActivator.getBundleContext(); - if(context == null) - throw new NullPointerException("The specified BundleContext was null"); - - String userIDStr = (String)accountProperties.get(USER_ID); - if(userIDStr == null) - throw new NullPointerException( - "The account properties contained no user id."); - - if(accountProperties == null) - throw new NullPointerException("The specified property map was null"); - String serverAddress = (String) accountProperties.get(SERVER_ADDRESS); - if(serverAddress == null) - throw new NullPointerException( - serverAddress - + " is not a valid ServerAddress"); - - if (!accountProperties.containsKey(PROTOCOL)) - accountProperties.put(PROTOCOL, ProtocolNames.SIP); - - SipAccountID accountID = - new SipAccountID(userIDStr, accountProperties, serverAddress); - - //get a reference to the configuration service and register whatever - //properties we have in it. - - Hashtable properties = new Hashtable(); - properties.put(PROTOCOL, ProtocolNames.SIP); - properties.put(USER_ID, userIDStr); + if (serverAddress == null) + throw new NullPointerException(serverAddress + + " is not a valid ServerAddress"); + return new SipAccountID(userID, accountProperties, serverAddress); + } - ProtocolProviderServiceSipImpl sipProtocolProvider - = new ProtocolProviderServiceSipImpl(); + protected ProtocolProviderService createService(String userID, + AccountID accountID) + { + ProtocolProviderServiceSipImpl service = + new ProtocolProviderServiceSipImpl(); try { - sipProtocolProvider.initialize(userIDStr, accountID); + service.initialize(userID, (SipAccountID) accountID); // We store again the account in order to store all properties added // during the protocol provider initialization. - this.storeAccount( - SipActivator.getBundleContext(), accountID); + storeAccount(accountID); } catch (OperationFailedException ex) { @@ -299,134 +227,6 @@ public class ProtocolProviderFactorySipImpl throw new IllegalArgumentException("Failed to initialize account" + ex.getMessage()); } - - ServiceRegistration registration - = context.registerService( ProtocolProviderService.class.getName(), - sipProtocolProvider, - properties); - - registeredAccounts.put(accountID, registration); - return accountID; + return service; } - - /** - * Loads (and hence installs) all accounts previously stored in the - * configuration service. - */ - public void loadStoredAccounts() - { - super.loadStoredAccounts( SipActivator.getBundleContext()); - } - - - /** - * Removes the specified account from the list of accounts that this - * provider factory is handling. If the specified accountID is unknown to - * the ProtocolProviderFactory, the call has no effect and false is returned. - * This method is persistent in nature and once called the account - * corresponding to the specified ID will not be loaded during future runs - * of the project. - * - * @param accountID the ID of the account to remove. - * @return true if an account with the specified ID existed and was removed - * and false otherwise. - */ - public boolean uninstallAccount(AccountID accountID) - { - //unregister the protocol provider - ServiceReference serRef = getProviderForAccount(accountID); - - if (serRef == null) - return false; - - ProtocolProviderService protocolProvider - = (ProtocolProviderService) SipActivator.getBundleContext() - .getService(serRef); - - try { - protocolProvider.unregister(); - } - catch (OperationFailedException e) { - logger.error("Failed to unregister protocol provider for account : " - + accountID + " caused by : " + e); - } - - ServiceRegistration registration - = (ServiceRegistration) registeredAccounts.remove(accountID); - - if (registration == null) - return false; - - //kill the service - registration.unregister(); - - return removeStoredAccount( - SipActivator.getBundleContext() - , accountID); - } - - /** - * Prepares the factory for bundle shutdown. - */ - public void stop() - { - logger.trace("Preparing to stop all SIP protocol providers."); - Enumeration registrations = this.registeredAccounts.elements(); - - while(registrations.hasMoreElements()) - { - ServiceRegistration reg - = ((ServiceRegistration)registrations.nextElement()); - - ProtocolProviderServiceSipImpl provider - = (ProtocolProviderServiceSipImpl) SipActivator - .getBundleContext().getService(reg.getReference()); - - //do an attempt to kill the provider - provider.shutdown(); - - reg.unregister(); - } - - registeredAccounts.clear(); - } - - /** - * Saves the password for the specified account after scrambling it a bit - * so that it is not visible from first sight (Method remains highly - * insecure). - * - * @param accountID the AccountID for the account whose password we're - * storing. - * @param passwd the password itself. - * - * @throws java.lang.IllegalArgumentException if no account corresponding - * to <tt>accountID</tt> has been previously stored. - */ - public void storePassword(AccountID accountID, String passwd) - throws IllegalArgumentException - { - super.storePassword(SipActivator.getBundleContext() - , accountID - , passwd); - } - - /** - * Returns the password last saved for the specified account. - * - * @param accountID the AccountID for the account whose password we're - * looking for.. - * - * @return a String containing the password for the specified accountID. - * - * @throws java.lang.IllegalArgumentException if no account corresponding - * to <tt>accountID</tt> has been previously stored. - */ - public String loadPassword(AccountID accountID) - throws IllegalArgumentException - { - return super.loadPassword(SipActivator.getBundleContext() - , accountID ); - } - } diff --git a/src/net/java/sip/communicator/impl/protocol/sip/SipActivator.java b/src/net/java/sip/communicator/impl/protocol/sip/SipActivator.java index b0bdf33..71828c2 100644 --- a/src/net/java/sip/communicator/impl/protocol/sip/SipActivator.java +++ b/src/net/java/sip/communicator/impl/protocol/sip/SipActivator.java @@ -52,24 +52,25 @@ public class SipActivator public void start(BundleContext context) throws Exception { logger.debug("Started."); - this.bundleContext = context; - Hashtable hashtable = new Hashtable(); - hashtable.put(ProtocolProviderFactory.PROTOCOL, ProtocolNames.SIP); + + SipActivator.bundleContext = context; sipProviderFactory = new ProtocolProviderFactorySipImpl(); - //load all sip providers - sipProviderFactory.loadStoredAccounts(); + /* + * Install the UriHandler prior to registering the factory service in + * order to allow it to detect when the stored accounts are loaded + * (because they may be asynchronously loaded). + */ + uriHandlerSipImpl = new UriHandlerSipImpl(sipProviderFactory); //reg the sip account man. + Dictionary<String, String> properties = new Hashtable<String, String>(); + properties.put(ProtocolProviderFactory.PROTOCOL, ProtocolNames.SIP); sipPpFactoryServReg = context.registerService( ProtocolProviderFactory.class.getName(), sipProviderFactory, - hashtable); - - uriHandlerSipImpl = new UriHandlerSipImpl(sipProviderFactory); - context.addServiceListener(uriHandlerSipImpl); - uriHandlerSipImpl.registerHandlerService(); + properties); logger.debug("SIP Protocol Provider Factory ... [REGISTERED]"); } @@ -211,6 +212,11 @@ public class SipActivator { sipProviderFactory.stop(); sipPpFactoryServReg.unregister(); - context.removeServiceListener(uriHandlerSipImpl); + + if (uriHandlerSipImpl != null) + { + uriHandlerSipImpl.dispose(); + uriHandlerSipImpl = null; + } } } diff --git a/src/net/java/sip/communicator/impl/protocol/sip/UriHandlerSipImpl.java b/src/net/java/sip/communicator/impl/protocol/sip/UriHandlerSipImpl.java index 9064b22..908e11c 100644 --- a/src/net/java/sip/communicator/impl/protocol/sip/UriHandlerSipImpl.java +++ b/src/net/java/sip/communicator/impl/protocol/sip/UriHandlerSipImpl.java @@ -25,8 +25,8 @@ import net.java.sip.communicator.util.*; */ public class UriHandlerSipImpl implements UriHandler, - ServiceListener - + ServiceListener, + AccountManagerListener { private static final Logger logger = Logger.getLogger(UriHandlerSipImpl.class); @@ -34,7 +34,7 @@ public class UriHandlerSipImpl /** * The protocol provider factory that created us. */ - private ProtocolProviderFactory protoFactory = null; + private final ProtocolProviderFactory protoFactory; /** * A reference to the OSGi registration we create with this handler. @@ -44,27 +44,105 @@ public class UriHandlerSipImpl /** * The object that we are using to synchronize our service registration. */ - private Object registrationLock = new Object(); + private final Object registrationLock = new Object(); + + private AccountManager accountManager; + + private final boolean[] storedAccountsAreLoaded = new boolean[1]; + + private List<String> uris; /** * Creates an instance of this uri handler, so that it would start handling - * URIs by passing them to the providers registered by <tt>protoFactory</tt>. - * + * URIs by passing them to the providers registered by <tt>protoFactory</tt> + * . + * * @param parentProvider the provider that created us. - * + * * @throws NullPointerException if <tt>protoFactory</tt> is <tt>null</tt>. */ - protected UriHandlerSipImpl(ProtocolProviderFactory protoFactory) + public UriHandlerSipImpl(ProtocolProviderFactorySipImpl protoFactory) throws NullPointerException { - if(protoFactory == null) + if (protoFactory == null) { throw new NullPointerException( - "The ProtocolProviderFactory that a UriHandler is created with " - + " cannot be null."); + "The ProtocolProviderFactory that a UriHandler is created with " + + " cannot be null."); } this.protoFactory = protoFactory; + + hookStoredAccounts(); + + this.protoFactory.getBundleContext().addServiceListener(this); + /* + * Registering the UriHandler isn't strictly necessary if the + * requirement to register the protoFactory after creating this instance + * is met. + */ + registerHandlerService(); + } + + public void dispose() + { + protoFactory.getBundleContext().removeServiceListener(this); + unregisterHandlerService(); + + unhookStoredAccounts(); + } + + private void hookStoredAccounts() + { + if (accountManager == null) + { + BundleContext bundleContext = protoFactory.getBundleContext(); + + accountManager = + (AccountManager) bundleContext.getService(bundleContext + .getServiceReference(AccountManager.class.getName())); + accountManager.addListener(this); + } + } + + private void unhookStoredAccounts() + { + if (accountManager != null) + { + accountManager.removeListener(this); + accountManager = null; + } + } + + public void handleAccountManagerEvent(AccountManagerEvent event) + { + if ((AccountManagerEvent.STORED_ACCOUNTS_LOADED == event.getType()) + && (protoFactory == event.getFactory())) + { + List<String> uris = null; + + synchronized (storedAccountsAreLoaded) + { + storedAccountsAreLoaded[0] = true; + + if (this.uris != null) + { + uris = this.uris; + this.uris = null; + } + } + + unhookStoredAccounts(); + + if (uris != null) + { + for (Iterator<String> uriIter = uris.iterator(); uriIter + .hasNext();) + { + handleUri(uriIter.next()); + } + } + } } /** @@ -102,8 +180,11 @@ public class UriHandlerSipImpl { synchronized(registrationLock) { - ourServiceRegistration.unregister(); - ourServiceRegistration = null; + if (ourServiceRegistration != null) + { + ourServiceRegistration.unregister(); + ourServiceRegistration = null; + } } } @@ -127,6 +208,23 @@ public class UriHandlerSipImpl */ public void handleUri(String uri) { + /* + * TODO If the requirement to register the factory service after + * creating this instance is broken, we'll end up not handling the URIs. + */ + synchronized (storedAccountsAreLoaded) + { + if (!storedAccountsAreLoaded[0]) + { + if (uris == null) + { + uris = new LinkedList<String>(); + } + uris.add(uri); + return; + } + } + ProtocolProviderService provider; try { @@ -143,10 +241,8 @@ public class UriHandlerSipImpl if(provider == null) { showErrorMessage( - "You need to configure at least one " - + "SIP" +" account \n" - +"to be able to call " + uri, - null); + "You need to configure at least one SIP account \n" + + "to be able to call " + uri, null); return; } @@ -213,26 +309,25 @@ public class UriHandlerSipImpl Object sourceService = SipActivator.bundleContext .getService(event.getServiceReference()); - //ignore anything but our protocol factory. - if( ! (sourceService instanceof ProtocolProviderFactorySipImpl) - || (sourceService != protoFactory)) + // ignore anything but our protocol factory. + if (sourceService != protoFactory) { return; } - if(event.getType() == ServiceEvent.REGISTERED) + switch (event.getType()) { - //our factory has just been registered as a service ... + case ServiceEvent.REGISTERED: + // our factory has just been registered as a service ... registerHandlerService(); - } - else if(event.getType() == ServiceEvent.UNREGISTERING) - { - //our factory just died - seppuku. + break; + case ServiceEvent.UNREGISTERING: + // our factory just died - seppuku. unregisterHandlerService(); - } - else if(event.getType() == ServiceEvent.MODIFIED) - { - //we don't care. + break; + default: + // we don't care. + break; } } diff --git a/src/net/java/sip/communicator/impl/protocol/ssh/ProtocolProviderFactorySSH.java b/src/net/java/sip/communicator/impl/protocol/ssh/ProtocolProviderFactorySSH.java index f59b2cf..8650518 100644 --- a/src/net/java/sip/communicator/impl/protocol/ssh/ProtocolProviderFactorySSH.java +++ b/src/net/java/sip/communicator/impl/protocol/ssh/ProtocolProviderFactorySSH.java @@ -12,6 +12,8 @@ package net.java.sip.communicator.impl.protocol.ssh; +import org.osgi.framework.*; + import net.java.sip.communicator.service.protocol.*; /** @@ -32,5 +34,10 @@ public abstract class ProtocolProviderFactorySSH * for a ProtocolProviderFactory. */ public static final String KNOWN_HOSTS_FILE = "KNOWN_HOSTS_FILE"; - + + protected ProtocolProviderFactorySSH(BundleContext bundleContext, + String protocolName) + { + super(bundleContext, protocolName); + } } diff --git a/src/net/java/sip/communicator/impl/protocol/ssh/ProtocolProviderFactorySSHImpl.java b/src/net/java/sip/communicator/impl/protocol/ssh/ProtocolProviderFactorySSHImpl.java index 529176d..9aa25e6 100644 --- a/src/net/java/sip/communicator/impl/protocol/ssh/ProtocolProviderFactorySSHImpl.java +++ b/src/net/java/sip/communicator/impl/protocol/ssh/ProtocolProviderFactorySSHImpl.java @@ -15,6 +15,7 @@ package net.java.sip.communicator.impl.protocol.ssh; import java.util.*; import org.osgi.framework.*; + import net.java.sip.communicator.service.protocol.*; import net.java.sip.communicator.util.*; @@ -30,62 +31,15 @@ public class ProtocolProviderFactorySSHImpl private static final Logger logger = Logger.getLogger(ProtocolProviderFactorySSHImpl.class); - /** - * The table that we store our accounts in. - */ - private Hashtable registeredAccounts = new Hashtable(); - /** * Creates an instance of the ProtocolProviderFactorySSHImpl. */ public ProtocolProviderFactorySSHImpl() { - super(); - } - - /** - * Returns the ServiceReference for the protocol provider corresponding - * to the specified accountID or null if the accountID is unknown. - * - * @param accountID the accountID of the protocol provider we'd like to - * get - * @return a ServiceReference object to the protocol provider with the - * specified account id and null if the account id is unknwon to the - * provider factory. - */ - public ServiceReference getProviderForAccount(AccountID accountID) - { - ServiceRegistration registration - = (ServiceRegistration)registeredAccounts.get(accountID); - - return (registration == null ) - ? null - : registration.getReference(); - } - - /** - * Returns a copy of the list containing the <tt>AccoudID</tt>s of all - * accounts currently registered in this protocol provider. - * - * @return a copy of the list containing the <tt>AccoudID</tt>s of all - * accounts currently registered in this protocol provider. - */ - public ArrayList getRegisteredAccounts() - { - return new ArrayList(registeredAccounts.keySet()); + super(SSHActivator.getBundleContext(), ProtocolNames.SSH); } - - /** - * Loads (and hence installs) all accounts previously stored in the - * configuration service. - */ - public void loadStoredAccounts() - { - super.loadStoredAccounts( SSHActivator.getBundleContext()); - } - - + /** * Initializaed and creates an account corresponding to the specified * accountProperties and registers the resulting ProtocolProvider in the @@ -127,9 +81,7 @@ public class ProtocolProviderFactorySSHImpl //an osgi event, the osgi event triggers (through the UI) a call to the //ProtocolProviderService.register() method and it needs to acces //the configuration service and check for a stored password. - this.storeAccount( - SSHActivator.getBundleContext() - , accountID); + this.storeAccount(accountID); accountID = loadAccount(accountProperties); @@ -156,91 +108,22 @@ public class ProtocolProviderFactorySSHImpl */ return accountID; } - - /** - * Initializes and creates an account corresponding to the specified - * accountProperties and registers the resulting ProtocolProvider in the - * <tt>context</tt> BundleContext parameter. - * - * @param accountProperties a set of protocol (or implementation) - * specific properties defining the new account. - * @return the AccountID of the newly loaded account - */ - public AccountID loadAccount(Map accountProperties) + + protected AccountID createAccountID(String userID, Map accountProperties) { - BundleContext context = SSHActivator.getBundleContext(); - if(context == null) - throw new NullPointerException("The specified BundleContext was" + - " null"); - - String userIDStr = (String) accountProperties.get(USER_ID); - AccountID accountID = new SSHAccountID(userIDStr, accountProperties); - - //get a reference to the configuration service and register whatever - //properties we have in it. - - Hashtable properties = new Hashtable(); - properties.put(PROTOCOL, ProtocolNames.SSH); - properties.put(USER_ID, userIDStr); - - ProtocolProviderServiceSSHImpl sshProtocolProvider - = new ProtocolProviderServiceSSHImpl(); - - sshProtocolProvider.initialize(userIDStr, accountID); - - ServiceRegistration registration = context.registerService( - ProtocolProviderService.class.getName(), - sshProtocolProvider, - properties); - - registeredAccounts.put(accountID, registration); - return accountID; + return new SSHAccountID(userID, accountProperties); } - - - /** - * Removes the specified account from the list of accounts that this - * provider factory is handling. - * - * @param accountID the ID of the account to remove. - * @return true if an account with the specified ID existed and was - * removed and false otherwise. - */ - public boolean uninstallAccount(AccountID accountID) + + protected ProtocolProviderService createService(String userID, + AccountID accountID) { - //unregister the protocol provider - ServiceReference serRef = getProviderForAccount(accountID); - - ProtocolProviderService protocolProvider - = (ProtocolProviderService) SSHActivator.getBundleContext() - .getService(serRef); - - try - { - protocolProvider.unregister(); - } - catch (OperationFailedException exc) - { - logger.error("Failed to unregister protocol provider for account : " - + accountID + " caused by : " + exc); - } - - ServiceRegistration registration - = (ServiceRegistration)registeredAccounts.remove(accountID); - - if(registration == null) - return false; - - //kill the service - registration.unregister(); - - registeredAccounts.remove(accountID); - - return removeStoredAccount( - SSHActivator.getBundleContext() - , accountID); + ProtocolProviderServiceSSHImpl service = + new ProtocolProviderServiceSSHImpl(); + + service.initialize(userID, accountID); + return service; } -// + // /** // * Saves the password for the specified account after scrambling it a bit // * so that it is not visible from first sight (Method remains highly @@ -279,29 +162,6 @@ public class ProtocolProviderFactorySSHImpl // , accountID ); // return(String.valueOf(Base64.decode(password))); // } - - /** - * Prepares the factory for bundle shutdown. - */ - public void stop() - { - Enumeration registrations = this.registeredAccounts.elements(); - - while(registrations.hasMoreElements()) - { - ServiceRegistration reg - = ((ServiceRegistration)registrations.nextElement()); - - reg.unregister(); - } - - Enumeration idEnum = registeredAccounts.keys(); - - while(idEnum.hasMoreElements()) - { - registeredAccounts.remove(idEnum.nextElement()); - } - } @Override public void modifyAccount( ProtocolProviderService protocolProvider, diff --git a/src/net/java/sip/communicator/impl/protocol/ssh/SSHActivator.java b/src/net/java/sip/communicator/impl/protocol/ssh/SSHActivator.java index 7981779..37af1ad 100644 --- a/src/net/java/sip/communicator/impl/protocol/ssh/SSHActivator.java +++ b/src/net/java/sip/communicator/impl/protocol/ssh/SSHActivator.java @@ -68,12 +68,9 @@ public class SSHActivator Hashtable hashtable = new Hashtable(); hashtable.put(ProtocolProviderFactory.PROTOCOL, "SSH"); - + sshProviderFactory = new ProtocolProviderFactorySSHImpl(); - - //load all stored SSH accounts. - sshProviderFactory.loadStoredAccounts(); - + //reg the ssh provider factory. sshPpFactoryServReg = context.registerService( ProtocolProviderFactory.class.getName(), diff --git a/src/net/java/sip/communicator/impl/protocol/yahoo/ProtocolProviderFactoryYahooImpl.java b/src/net/java/sip/communicator/impl/protocol/yahoo/ProtocolProviderFactoryYahooImpl.java index 4091435..505763e 100644 --- a/src/net/java/sip/communicator/impl/protocol/yahoo/ProtocolProviderFactoryYahooImpl.java +++ b/src/net/java/sip/communicator/impl/protocol/yahoo/ProtocolProviderFactoryYahooImpl.java @@ -19,46 +19,13 @@ import net.java.sip.communicator.service.protocol.*; public class ProtocolProviderFactoryYahooImpl extends ProtocolProviderFactory { - /** - * The table that we store our accounts in. - */ - private Hashtable registeredAccounts = new Hashtable(); /** * Creates an instance of the ProtocolProviderFactoryYahooImpl. */ protected ProtocolProviderFactoryYahooImpl() { - } - - /** - * Returns a copy of the list containing all accounts currently - * registered in this protocol provider. - * - * @return a copy of the llist containing all accounts currently installed - * in the protocol provider. - */ - public ArrayList getRegisteredAccounts() - { - return new ArrayList(registeredAccounts.keySet()); - } - - /** - * Returns the ServiceReference for the protocol provider corresponding to - * the specified accountID or null if the accountID is unknown. - * @param accountID the accountID of the protocol provider we'd like to get - * @return a ServiceReference object to the protocol provider with the - * specified account id and null if the account id is unknwon to the - * provider factory. - */ - public ServiceReference getProviderForAccount(AccountID accountID) - { - ServiceRegistration registration - = (ServiceRegistration)registeredAccounts.get(accountID); - - return (registration == null ) - ? null - : registration.getReference(); + super(YahooActivator.getBundleContext(), ProtocolNames.YAHOO); } /** @@ -100,167 +67,26 @@ public class ProtocolProviderFactoryYahooImpl //an osgi event, the osgi event triggers (trhgough the UI) a call to //the register() method and it needs to acces the configuration service //and check for a password. - this.storeAccount( - YahooActivator.getBundleContext() - , accountID); + this.storeAccount(accountID); accountID = loadAccount(accountProperties); return accountID; } - /** - * Initializes and creates an account corresponding to the specified - * accountProperties and registers the resulting ProtocolProvider in the - * <tt>context</tt> BundleContext parameter. - * - * @param accountProperties a set of protocol (or implementation) - * specific properties defining the new account. - * @return the AccountID of the newly created account - */ - public AccountID loadAccount( Map accountProperties) + protected AccountID createAccountID(String userID, Map accountProperties) { - BundleContext context - = YahooActivator.getBundleContext(); - if(context == null) - throw new NullPointerException("The specified BundleContext was null"); - - String userIDStr = (String)accountProperties.get(USER_ID); - - AccountID accountID = new YahooAccountID(userIDStr, accountProperties); - - //get a reference to the configuration service and register whatever - //properties we have in it. - - Hashtable properties = new Hashtable(); - properties.put(PROTOCOL, ProtocolNames.YAHOO); - properties.put(USER_ID, userIDStr); - - ProtocolProviderServiceYahooImpl yahooProtocolProvider - = new ProtocolProviderServiceYahooImpl(); - - yahooProtocolProvider.initialize(userIDStr, accountID); - - ServiceRegistration registration - = context.registerService( ProtocolProviderService.class.getName(), - yahooProtocolProvider, - properties); - - registeredAccounts.put(accountID, registration); - return accountID; + return new YahooAccountID(userID, accountProperties); } - - /** - * Removes the specified account from the list of accounts that this - * provider factory is handling. If the specified accountID is unknown to - * the ProtocolProviderFactory, the call has no effect and false is returned. - * This method is persistent in nature and once called the account - * corresponding to the specified ID will not be loaded during future runs - * of the project. - * - * @param accountID the ID of the account to remove. - * @return true if an account with the specified ID existed and was removed - * and false otherwise. - */ - public boolean uninstallAccount(AccountID accountID) - { - ServiceRegistration registration - = (ServiceRegistration)registeredAccounts.remove(accountID); - - if(registration == null) - return false; - - //kill the service - registration.unregister(); - - return removeStoredAccount( - YahooActivator.getBundleContext() - , accountID); - } - - /** - * Loads (and hence installs) all accounts previously stored in the - * configuration service. - */ - public void loadStoredAccounts() - { - super.loadStoredAccounts( YahooActivator.getBundleContext()); - } - - /** - * Prepares the factory for bundle shutdown. - */ - public void stop() - { - Enumeration registrations = this.registeredAccounts.elements(); - - while(registrations.hasMoreElements()) - { - ServiceRegistration reg - = ((ServiceRegistration)registrations.nextElement()); - - reg.unregister(); - } - - Enumeration idEnum = registeredAccounts.keys(); - - while(idEnum.hasMoreElements()) - { - registeredAccounts.remove(idEnum.nextElement()); - } - } - - /** - * Returns the configuraiton service property name prefix that we use to - * store properties concerning the account with the specified id. - * @param accountID the AccountID whose property name prefix we're looking - * for. - * @return the prefix of the configuration service property name that - * we're using when storing properties for the specified account. - */ - public String findAccountPrefix(AccountID accountID) - { - return super.findAccountPrefix(YahooActivator.getBundleContext() - , accountID); - } - - /** - * Saves the password for the specified account after scrambling it a bit - * so that it is not visible from first sight (Method remains highly - * insecure). - * - * @param accountID the AccountID for the account whose password we're - * storing. - * @param passwd the password itself. - * - * @throws java.lang.IllegalArgumentException if no account corresponding - * to <tt>accountID</tt> has been previously stored. - */ - public void storePassword(AccountID accountID, String passwd) - throws IllegalArgumentException + protected ProtocolProviderService createService(String userID, + AccountID accountID) { - super.storePassword(YahooActivator.getBundleContext() - , accountID - , passwd); - } + ProtocolProviderServiceYahooImpl service = + new ProtocolProviderServiceYahooImpl(); - /** - * Returns the password last saved for the specified account. - * - * @param accountID the AccountID for the account whose password we're - * looking for.. - * - * @return a String containing the password for the specified accountID. - * - * @throws java.lang.IllegalArgumentException if no account corresponding - * to <tt>accountID</tt> has been previously stored. - */ - public String loadPassword(AccountID accountID) - throws IllegalArgumentException - { - return super.loadPassword(YahooActivator.getBundleContext() - , accountID ); + service.initialize(userID, accountID); + return service; } @Override @@ -309,7 +135,7 @@ public class ProtocolProviderFactoryYahooImpl // an osgi event, the osgi event triggers (trhgough the UI) a call to // the register() method and it needs to acces the configuration service // and check for a password. - this.storeAccount(YahooActivator.getBundleContext(), accountID); + this.storeAccount(accountID); Hashtable properties = new Hashtable(); properties.put(PROTOCOL, ProtocolNames.YAHOO); @@ -320,8 +146,7 @@ public class ProtocolProviderFactoryYahooImpl // We store again the account in order to store all properties added // during the protocol provider initialization. - this.storeAccount( - YahooActivator.getBundleContext(), accountID); + this.storeAccount(accountID); registration = context.registerService( diff --git a/src/net/java/sip/communicator/impl/protocol/yahoo/YahooActivator.java b/src/net/java/sip/communicator/impl/protocol/yahoo/YahooActivator.java index 8dbe58b..b5c7c1f 100644 --- a/src/net/java/sip/communicator/impl/protocol/yahoo/YahooActivator.java +++ b/src/net/java/sip/communicator/impl/protocol/yahoo/YahooActivator.java @@ -48,9 +48,6 @@ public class YahooActivator yahooProviderFactory = new ProtocolProviderFactoryYahooImpl(); - //load all yahoo providers - yahooProviderFactory.loadStoredAccounts(); - //reg the yahoo account man. yahooPpFactoryServReg = context.registerService( ProtocolProviderFactory.class.getName(), diff --git a/src/net/java/sip/communicator/impl/protocol/zeroconf/ProtocolProviderFactoryZeroconfImpl.java b/src/net/java/sip/communicator/impl/protocol/zeroconf/ProtocolProviderFactoryZeroconfImpl.java index 008c531..88aabc3 100644 --- a/src/net/java/sip/communicator/impl/protocol/zeroconf/ProtocolProviderFactoryZeroconfImpl.java +++ b/src/net/java/sip/communicator/impl/protocol/zeroconf/ProtocolProviderFactoryZeroconfImpl.java @@ -9,6 +9,7 @@ package net.java.sip.communicator.impl.protocol.zeroconf; import java.util.*; import org.osgi.framework.*; + import net.java.sip.communicator.service.protocol.*; import net.java.sip.communicator.util.*; @@ -27,61 +28,13 @@ public class ProtocolProviderFactoryZeroconfImpl = Logger.getLogger(ProtocolProviderFactoryZeroconfImpl.class); /** - * The table that we store our accounts in. - */ - private Hashtable registeredAccounts = new Hashtable(); - - - /** * Creates an instance of the ProtocolProviderFactoryZeroconfImpl. */ public ProtocolProviderFactoryZeroconfImpl() { - super(); - } - - /** - * Returns the ServiceReference for the protocol provider corresponding - * to the specified accountID or null if the accountID is unknown. - * - * @param accountID the accountID of the protocol provider we'd like to - * get - * @return a ServiceReference object to the protocol provider with the - * specified account id and null if the account id is unknwon to the - * provider factory. - */ - public ServiceReference getProviderForAccount(AccountID accountID) - { - ServiceRegistration registration - = (ServiceRegistration)registeredAccounts.get(accountID); - - return (registration == null ) - ? null - : registration.getReference(); - } - - /** - * Returns a copy of the list containing the <tt>AccoudID</tt>s of all - * accounts currently registered in this protocol provider. - * - * @return a copy of the list containing the <tt>AccoudID</tt>s of all - * accounts currently registered in this protocol provider. - */ - public ArrayList getRegisteredAccounts() - { - return new ArrayList(registeredAccounts.keySet()); - } - - /** - * Loads (and hence installs) all accounts previously stored in the - * configuration service. - */ - public void loadStoredAccounts() - { - super.loadStoredAccounts( ZeroconfActivator.getBundleContext()); + super(ZeroconfActivator.getBundleContext(), ProtocolNames.ZEROCONF); } - /** * Initializaed and creates an account corresponding to the specified * accountProperties and registers the resulting ProtocolProvider in the @@ -124,172 +77,26 @@ public class ProtocolProviderFactoryZeroconfImpl //an osgi event, the osgi event triggers (through the UI) a call to the //ProtocolProviderService.register() method and it needs to acces //the configuration service and check for a stored password. - this.storeAccount( - ZeroconfActivator.getBundleContext() - , accountID); + this.storeAccount(accountID); accountID = loadAccount(accountProperties); return accountID; } - /** - * Initializes and creates an account corresponding to the specified - * accountProperties and registers the resulting ProtocolProvider in the - * <tt>context</tt> BundleContext parameter. - * - * @param accountProperties a set of protocol (or implementation) - * specific properties defining the new account. - * @return the AccountID of the newly loaded account - */ - public AccountID loadAccount( Map accountProperties) - { - BundleContext context - = ZeroconfActivator.getBundleContext(); - if(context == null) - throw new NullPointerException( - "The specified BundleContext was null"); - - String userIDStr = (String)accountProperties.get(USER_ID); - - AccountID accountID = - new ZeroconfAccountID(userIDStr, accountProperties); - - //get a reference to the configuration service and register whatever - //properties we have in it. - - Hashtable properties = new Hashtable(); - properties.put(PROTOCOL, ProtocolNames.ZEROCONF); - properties.put(USER_ID, userIDStr); - - ProtocolProviderServiceZeroconfImpl zeroconfProtocolProvider - = new ProtocolProviderServiceZeroconfImpl(); - - zeroconfProtocolProvider.initialize(userIDStr, accountID); - - ServiceRegistration registration - = context.registerService( ProtocolProviderService.class.getName(), - zeroconfProtocolProvider, - properties); - - registeredAccounts.put(accountID, registration); - - return accountID; - } - - - /** - * Removes the specified account from the list of accounts that this - * provider factory is handling. - * - * @param accountID the ID of the account to remove. - * @return true if an account with the specified ID existed and was - * removed and false otherwise. - */ - public boolean uninstallAccount(AccountID accountID) - { - //unregister the protocol provider - ServiceReference serRef = getProviderForAccount(accountID); - - if(serRef == null) - return false; - - ProtocolProviderService protocolProvider - = (ProtocolProviderService) ZeroconfActivator.getBundleContext() - .getService(serRef); - if (protocolProvider == null) - { - logger.error("ProtocolProviderService = null !!"); - return false; - } - - try - { - protocolProvider.unregister(); - } - catch (OperationFailedException exc) - { - logger.error("Failed to unregister protocol provider for account : " - + accountID + " caused by : " + exc); - } - - ServiceRegistration registration - = (ServiceRegistration)registeredAccounts.remove(accountID); - - if(registration == null) - return false; - - //kill the service - registration.unregister(); - - registeredAccounts.remove(accountID ); - - return removeStoredAccount( - ZeroconfActivator.getBundleContext() - , accountID); - } - /** - * Saves the password for the specified account after scrambling it a bit - * so that it is not visible from first sight (Method remains highly - * insecure). - * - * @param accountID the AccountID for the account whose password we're - * storing. - * @param passwd the password itself. - * - * @throws java.lang.IllegalArgumentException if no account corresponding - * to <tt>accountID</tt> has been previously stored. - */ - public void storePassword(AccountID accountID, String passwd) - throws IllegalArgumentException + protected AccountID createAccountID(String userID, Map accountProperties) { - super.storePassword(ZeroconfActivator.getBundleContext() - , accountID - , passwd); + return new ZeroconfAccountID(userID, accountProperties); } - /** - * Returns the password last saved for the specified account. - * - * @param accountID the AccountID for the account whose password we're - * looking for.. - * - * @return a String containing the password for the specified accountID. - * - * @throws java.lang.IllegalArgumentException if no account corresponding - * to <tt>accountID</tt> has been previously stored. - */ - public String loadPassword(AccountID accountID) - throws IllegalArgumentException + protected ProtocolProviderService createService(String userID, + AccountID accountID) { - return super.loadPassword(ZeroconfActivator.getBundleContext() - , accountID ); - } + ProtocolProviderServiceZeroconfImpl service = + new ProtocolProviderServiceZeroconfImpl(); - /** - * Prepares the factory for bundle shutdown. - */ - public void stop() - { - Enumeration registrations = this.registeredAccounts.elements(); - - while(registrations.hasMoreElements()) - { - ServiceRegistration reg - = ((ServiceRegistration)registrations.nextElement()); - - ProtocolProviderServiceZeroconfImpl provider - = (ProtocolProviderServiceZeroconfImpl) ZeroconfActivator - .getBundleContext().getService(reg.getReference()); - - //do an attempt to kill the provider - provider.shutdown(); - - - reg.unregister(); - } - - registeredAccounts.clear(); + service.initialize(userID, accountID); + return service; } @Override @@ -298,7 +105,5 @@ public class ProtocolProviderFactoryZeroconfImpl throws NullPointerException { // TODO Auto-generated method stub - } - } diff --git a/src/net/java/sip/communicator/impl/protocol/zeroconf/ZeroconfActivator.java b/src/net/java/sip/communicator/impl/protocol/zeroconf/ZeroconfActivator.java index 8de1830..fab3cc4 100644 --- a/src/net/java/sip/communicator/impl/protocol/zeroconf/ZeroconfActivator.java +++ b/src/net/java/sip/communicator/impl/protocol/zeroconf/ZeroconfActivator.java @@ -65,9 +65,6 @@ public class ZeroconfActivator zeroconfProviderFactory = new ProtocolProviderFactoryZeroconfImpl(); - //load all stored Zeroconf accounts. - zeroconfProviderFactory.loadStoredAccounts(); - //register the zeroconf provider factory. zeroconfPpFactoryServReg = context.registerService( ProtocolProviderFactory.class.getName(), diff --git a/src/net/java/sip/communicator/plugin/simpleaccreg/InitialAccountRegistrationFrame.java b/src/net/java/sip/communicator/plugin/simpleaccreg/InitialAccountRegistrationFrame.java index f02735d..49f08ec 100644 --- a/src/net/java/sip/communicator/plugin/simpleaccreg/InitialAccountRegistrationFrame.java +++ b/src/net/java/sip/communicator/plugin/simpleaccreg/InitialAccountRegistrationFrame.java @@ -33,6 +33,8 @@ public class InitialAccountRegistrationFrame extends JFrame implements ServiceListener { + private ConfigurationService configurationService; + private final Logger logger = Logger.getLogger(InitialAccountRegistrationFrame.class); @@ -115,11 +117,10 @@ public class InitialAccountRegistrationFrame contactList .createMetaContactGroup(contactList.getRoot(), groupName); - SimpleAccountRegistrationActivator.getConfigurationService(). - setProperty( - "net.java.sip.communicator.impl.gui.addcontact.lastContactParent", - groupName - ); + getConfigurationService() + .setProperty( + "net.java.sip.communicator.impl.gui.addcontact.lastContactParent", + groupName); } } @@ -517,8 +518,7 @@ public class InitialAccountRegistrationFrame { String prefix = "net.java.sip.communicator.impl.gui.accounts"; - ConfigurationService configService - = SimpleAccountRegistrationActivator.getConfigurationService(); + ConfigurationService configService = getConfigurationService(); List accounts = configService.getPropertyNamesByPrefix(prefix, true); @@ -557,4 +557,20 @@ public class InitialAccountRegistrationFrame } } + public ConfigurationService getConfigurationService() + { + if (configurationService == null) + { + BundleContext bundleContext = + SimpleAccountRegistrationActivator.bundleContext; + ServiceReference configReference = + bundleContext.getServiceReference(ConfigurationService.class + .getName()); + + configurationService = + (ConfigurationService) bundleContext + .getService(configReference); + } + return configurationService; + } } diff --git a/src/net/java/sip/communicator/plugin/simpleaccreg/Resources.java b/src/net/java/sip/communicator/plugin/simpleaccreg/Resources.java index 3a542c9..4141876 100644 --- a/src/net/java/sip/communicator/plugin/simpleaccreg/Resources.java +++ b/src/net/java/sip/communicator/plugin/simpleaccreg/Resources.java @@ -4,14 +4,9 @@ * Distributable under LGPL license. * See terms of license at gnu.org. */ - package net.java.sip.communicator.plugin.simpleaccreg; -import java.io.*; -import java.util.*; - import net.java.sip.communicator.service.resources.*; -import net.java.sip.communicator.util.*; import org.osgi.framework.*; @@ -23,9 +18,6 @@ import org.osgi.framework.*; */ public class Resources { - - private static Logger log = Logger.getLogger(Resources.class); - private static ResourceManagementService resourcesService; /** diff --git a/src/net/java/sip/communicator/plugin/simpleaccreg/SimpleAccountRegistrationActivator.java b/src/net/java/sip/communicator/plugin/simpleaccreg/SimpleAccountRegistrationActivator.java index acc161e..eed4308 100644 --- a/src/net/java/sip/communicator/plugin/simpleaccreg/SimpleAccountRegistrationActivator.java +++ b/src/net/java/sip/communicator/plugin/simpleaccreg/SimpleAccountRegistrationActivator.java @@ -9,7 +9,6 @@ package net.java.sip.communicator.plugin.simpleaccreg; import java.awt.*; import java.util.*; -import net.java.sip.communicator.service.configuration.*; import net.java.sip.communicator.service.contactlist.*; import net.java.sip.communicator.service.protocol.*; import net.java.sip.communicator.util.*; @@ -24,17 +23,20 @@ public class SimpleAccountRegistrationActivator public static BundleContext bundleContext; - private static ConfigurationService configService; - public void start(BundleContext bc) throws Exception { bundleContext = bc; - if (!hasRegisteredAccounts()) + /* + * Because the stored accounts may be asynchronously loaded, relying + * only on the registered accounts isn't possible. Instead, presume the + * stored accounts are valid and will later successfully be registered. + */ + if (!hasStoredAccounts()) { // If no preferred wizard is specified we launch the default wizard. - InitialAccountRegistrationFrame accountRegFrame - = new InitialAccountRegistrationFrame(); + InitialAccountRegistrationFrame accountRegFrame = + new InitialAccountRegistrationFrame(); accountRegFrame.pack(); @@ -54,24 +56,6 @@ public class SimpleAccountRegistrationActivator } /** - * Returns the <tt>ConfigurationService</tt> obtained from the bundle - * context. - * @return the <tt>ConfigurationService</tt> obtained from the bundle - * context - */ - public static ConfigurationService getConfigurationService() { - if(configService == null) { - ServiceReference configReference = bundleContext - .getServiceReference(ConfigurationService.class.getName()); - - configService = (ConfigurationService) bundleContext - .getService(configReference); - } - - return configService; - } - - /** * Returns all <tt>ProtocolProviderFactory</tt>s obtained from the bundle * context. * @return all <tt>ProtocolProviderFactory</tt>s obtained from the bundle @@ -93,27 +77,22 @@ public class SimpleAccountRegistrationActivator logger.error("Unable to obtain service references. " + e); } - for (int i = 0; i < serRefs.length; i++) + for (int serRefIndex = 0; serRefIndex < serRefs.length; serRefIndex++) { - ProtocolProviderFactory providerFactory - = (ProtocolProviderFactory) bundleContext - .getService(serRefs[i]); - - ArrayList accountsList = providerFactory.getRegisteredAccounts(); + ProtocolProviderFactory providerFactory = + (ProtocolProviderFactory) bundleContext + .getService(serRefs[serRefIndex]); - AccountID accountID; - ServiceReference serRef; - ProtocolProviderService protocolProvider; - - for (int j = 0; j < accountsList.size(); j++) + for (Iterator<AccountID> registeredAccountIter = + providerFactory.getRegisteredAccounts().iterator(); registeredAccountIter + .hasNext();) { - accountID = (AccountID) accountsList.get(j); - - boolean isHidden = - accountID.getAccountProperties() - .get(ProtocolProviderFactory.IS_PROTOCOL_HIDDEN) != null; + AccountID accountID = registeredAccountIter.next(); + boolean isHidden = + accountID.getAccountProperties().get( + ProtocolProviderFactory.IS_PROTOCOL_HIDDEN) != null; - if(!isHidden) + if (!isHidden) { hasRegisteredAccounts = true; break; @@ -127,6 +106,26 @@ public class SimpleAccountRegistrationActivator return hasRegisteredAccounts; } + private static boolean hasStoredAccounts() + { + ServiceReference accountManagerReference = + bundleContext.getServiceReference(AccountManager.class.getName()); + boolean hasStoredAccounts = false; + + if (accountManagerReference != null) + { + AccountManager accountManager = + (AccountManager) bundleContext + .getService(accountManagerReference); + + if (accountManager != null) + { + hasStoredAccounts = accountManager.hasStoredAccounts(); + } + } + return hasStoredAccounts; + } + /** * Returns the <tt>MetaContactListService</tt> obtained from the bundle * context. diff --git a/src/net/java/sip/communicator/service/protocol/AbstractProtocolProviderService.java b/src/net/java/sip/communicator/service/protocol/AbstractProtocolProviderService.java index 2a7334e..5d1b414 100644 --- a/src/net/java/sip/communicator/service/protocol/AbstractProtocolProviderService.java +++ b/src/net/java/sip/communicator/service/protocol/AbstractProtocolProviderService.java @@ -29,7 +29,8 @@ public abstract class AbstractProtocolProviderService * A list of all listeners registered for * <tt>RegistrationStateChangeEvent</tt>s. */ - private final List registrationListeners = new ArrayList(); + private final List<RegistrationStateChangeListener> registrationListeners = + new ArrayList<RegistrationStateChangeListener>(); /** * Registers the specified listener with this provider so that it would @@ -73,16 +74,17 @@ public abstract class AbstractProtocolProviderService logger.debug("Dispatching " + event + " to " + registrationListeners.size()+ " listeners."); - Iterator listeners = null; + Iterator<RegistrationStateChangeListener> listeners = null; synchronized (registrationListeners) { - listeners = new ArrayList(registrationListeners).iterator(); + listeners = + new ArrayList<RegistrationStateChangeListener>( + registrationListeners).iterator(); } while (listeners.hasNext()) { - RegistrationStateChangeListener listener - = (RegistrationStateChangeListener) listeners.next(); + RegistrationStateChangeListener listener = listeners.next(); listener.registrationStateChanged(event); } diff --git a/src/net/java/sip/communicator/service/protocol/AccountManager.java b/src/net/java/sip/communicator/service/protocol/AccountManager.java new file mode 100644 index 0000000..6cdb8e3 --- /dev/null +++ b/src/net/java/sip/communicator/service/protocol/AccountManager.java @@ -0,0 +1,61 @@ +/*
+ * SIP Communicator, the OpenSource Java VoIP and Instant Messaging client.
+ *
+ * Distributable under LGPL license.
+ * See terms of license at gnu.org.
+ */
+package net.java.sip.communicator.service.protocol;
+
+import net.java.sip.communicator.service.protocol.event.*;
+
+/**
+ * Represents a manager of accounts which contains the details about the format
+ * in which the accounts in question are stored (i.e. knows how to store and load
+ * them) and takes care of loading them on start-up.
+ *
+ * @author Lubomir Marinov
+ */
+public interface AccountManager
+{
+
+ /**
+ * Registers a specific listener to be notified about events fired by this
+ * <code>AccountManager</code>. If the <code>listener</code> is already
+ * registered, it will not be registered again.
+ *
+ * @param listener the listener to be registered for notification events
+ * fired by this <code>AccountManager</code>
+ */
+ void addListener(AccountManagerListener listener);
+
+ /**
+ * Determines whether the account store represented by this manager contains
+ * stored accounts.
+ *
+ * @return <tt>true</tt> if the account store represented by this manager
+ * contains stored accounts; <tt>false</tt>, otherwise
+ */
+ boolean hasStoredAccounts();
+
+ /**
+ * Unregisters a specific listener from this <code>AccountManager</code> so
+ * that it no longer received notifications about events fired by this
+ * manager.
+ *
+ * @param listener the listener to be unregistered from this
+ * <code>AccountManager</code> so that it no longer receives
+ * notifications about events fired by this manager
+ */
+ void removeListener(AccountManagerListener listener);
+
+ /**
+ * Stores an account represented in the form of an <code>AccountID</code>
+ * created by a specific <code>ProtocolProviderFactory</code>.
+ *
+ * @param factory the <code>ProtocolProviderFactory</code> which created the
+ * account to be stored
+ * @param accountID the account in the form of <code>AccountID</code> to be
+ * stored
+ */
+ void storeAccount(ProtocolProviderFactory factory, AccountID accountID);
+}
diff --git a/src/net/java/sip/communicator/service/protocol/ProtocolProviderFactory.java b/src/net/java/sip/communicator/service/protocol/ProtocolProviderFactory.java index 3501cd5..82fdb82 100644 --- a/src/net/java/sip/communicator/service/protocol/ProtocolProviderFactory.java +++ b/src/net/java/sip/communicator/service/protocol/ProtocolProviderFactory.java @@ -8,13 +8,11 @@ package net.java.sip.communicator.service.protocol; import java.util.*; +import org.osgi.framework.*; -import net.java.sip.communicator.impl.protocol.sip.*; import net.java.sip.communicator.service.configuration.*; import net.java.sip.communicator.util.*; -import org.osgi.framework.*; - /** * The ProtocolProviderFactory is what actually creates instances of a * ProtocolProviderService implementation. A provider factory would register, @@ -25,6 +23,7 @@ import org.osgi.framework.*; * would user account registered through the various services. * * @author Emil Ivov + * @author Lubomir Marinov */ public abstract class ProtocolProviderFactory { @@ -202,6 +201,48 @@ public abstract class ProtocolProviderFactory public static final String IS_PROTOCOL_HIDDEN = "IS_PROTOCOL_HIDDEN"; /** + * The <code>BundleContext</code> containing (or to contain) the service + * registration of this factory. + */ + private final BundleContext bundleContext; + + /** + * The name of the protocol this factory registers its + * <code>ProtocolProviderService</code>s with and to be placed in the + * properties of the accounts created by this factory. + */ + private final String protocolName; + + /** + * The table that we store our accounts in. + * <p> + * TODO Synchronize the access to the field which may in turn be better + * achieved by also hiding it from protected into private access. + * </p> + */ + protected final Hashtable<AccountID, ServiceRegistration> registeredAccounts = + new Hashtable<AccountID, ServiceRegistration>(); + + protected ProtocolProviderFactory(BundleContext bundleContext, + String protocolName) + { + this.bundleContext = bundleContext; + this.protocolName = protocolName; + } + + /** + * Gets the <code>BundleContext</code> containing (or to contain) the + * service registration of this factory. + * + * @return the <code>BundleContext</code> containing (or to contain) the + * service registration of this factory + */ + public BundleContext getBundleContext() + { + return bundleContext; + } + + /** * Initializes and creates an account corresponding to the specified * accountProperties and registers the resulting ProtocolProvider in the * <tt>context</tt> BundleContext parameter. Note that account @@ -254,7 +295,13 @@ public abstract class ProtocolProviderFactory * @return a copy of the list containing the <tt>AccountID</tt>s of all * accounts currently registered in this protocol provider. */ - public abstract ArrayList<AccountID> getRegisteredAccounts(); + public ArrayList<AccountID> getRegisteredAccounts() + { + synchronized (registeredAccounts) + { + return new ArrayList<AccountID>(registeredAccounts.keySet()); + } + } /** * Returns the ServiceReference for the protocol provider corresponding to @@ -264,8 +311,17 @@ public abstract class ProtocolProviderFactory * specified account id and null if the account id is unknown to the * provider factory. */ - public abstract ServiceReference getProviderForAccount( - AccountID accountID); + public ServiceReference getProviderForAccount(AccountID accountID) + { + ServiceRegistration registration; + + synchronized (registeredAccounts) + { + registration = + (ServiceRegistration) registeredAccounts.get(accountID); + } + return (registration == null) ? null : registration.getReference(); + } /** * Removes the specified account from the list of accounts that this @@ -279,121 +335,103 @@ public abstract class ProtocolProviderFactory * @return true if an account with the specified ID existed and was removed * and false otherwise. */ - public abstract boolean uninstallAccount(AccountID accountID); - - /** - * The method stores the specified account in the configuration service - * under the package name of the source factory. The restore and remove - * account methods are to be used to obtain access to and control the stored - * accounts. - * <p> - * In order to store all account properties, the method would create an - * entry in the configuration service corresponding (beginning with) the - * <tt>sourceFactory</tt>'s package name and add to it a unique identifier - * (e.g. the current miliseconds.) - * <p> - * @param bundleContext a currently valid bundle context. - * @param accountID the AccountID corresponding to the account that we would - * like to store. - */ - protected void storeAccount(BundleContext bundleContext, - AccountID accountID) + public boolean uninstallAccount(AccountID accountID) { - String sourcePackageName = getFactoryImplPackageName(); - - String accountNodeName = null; - - ServiceReference confReference - = bundleContext.getServiceReference( - ConfigurationService.class.getName()); - - ConfigurationService configurationService - = (ConfigurationService) bundleContext.getService(confReference); + // Unregister the protocol provider. + ServiceReference serRef = getProviderForAccount(accountID); - // First check if such accountID already exist in the configuration. - List accounts = configurationService - .getPropertyNamesByPrefix(sourcePackageName, true); - - Iterator accountsIter = accounts.iterator(); - - while(accountsIter.hasNext()) + if (serRef == null) { - String accountRootPropName - = (String) accountsIter.next(); + return false; + } - String accountIDString - = configurationService.getString( - accountRootPropName + ".ACCOUNT_UID"); + BundleContext bundleContext = getBundleContext(); + ProtocolProviderService protocolProvider = + (ProtocolProviderService) bundleContext.getService(serRef); - if(accountIDString.equals(accountID.getAccountUniqueID())) - { - accountNodeName - = configurationService.getString(accountRootPropName); - } + try + { + protocolProvider.unregister(); } - - //Create a unique node name of the properties node that will contain - //this account's properties. - if (accountNodeName == null) + catch (OperationFailedException ex) { - accountNodeName = "acc" + Long.toString(System.currentTimeMillis()); - - //set a value for the persistent node so that we could later - // retrieve it as a property - configurationService.setProperty( - sourcePackageName //prefix - + "." + accountNodeName, - accountNodeName); - - //register the account in the configuration service. - //we register all the properties in the following hierarchy - //net.java.sip.communicator.impl.protocol.PROTO_NAME.ACC_ID.PROP_NAME - configurationService.setProperty( - sourcePackageName//prefix - + "." + accountNodeName // node name for the account id - + "." + ACCOUNT_UID, // propname - accountID.getAccountUniqueID()); // value + logger + .error("Failed to unregister protocol provider for account : " + + accountID + " caused by: " + ex); } - //store the rest of the properties - Iterator accountPropKeys - = accountID.getAccountProperties().keySet().iterator(); + ServiceRegistration registration; - while (accountPropKeys.hasNext()) + synchronized (registeredAccounts) { - String propKey = - (String)accountPropKeys.next(); - String propValue = - (String)accountID.getAccountProperties().get(propKey); + registration = registeredAccounts.remove(accountID); + } + if (registration == null) + { + return false; + } - //if this is a password - encode it. - if(propKey.equals(PASSWORD)) - propValue = new String(Base64.encode(propValue.getBytes())); + // Kill the service. + registration.unregister(); - configurationService.setProperty( - sourcePackageName //prefix + return removeStoredAccount(bundleContext, accountID); + } - + "." + accountNodeName // a uniew node name for the account id - + "." + propKey, // propname - propValue); // value - } + /** + * The method stores the specified account in the configuration service + * under the package name of the source factory. The restore and remove + * account methods are to be used to obtain access to and control the stored + * accounts. + * <p> + * In order to store all account properties, the method would create an + * entry in the configuration service corresponding (beginning with) the + * <tt>sourceFactory</tt>'s package name and add to it a unique identifier + * (e.g. the current miliseconds.) + * </p> + * + * @param accountID the AccountID corresponding to the account that we would + * like to store. + */ + protected void storeAccount(AccountID accountID) + { + getAccountManager().storeAccount(this, accountID); + } - logger.debug("Stored account for id " + accountID.getAccountUniqueID() - + " for package " + getFactoryImplPackageName()); + /** + * Saves the password for the specified account after scrambling it a bit so + * that it is not visible from first sight. (The method remains highly + * insecure). + * + * @param accountID the AccountID for the account whose password we're + * storing + * @param password the password itself + * + * @throws IllegalArgumentException if no account corresponding to + * <code>accountID</code> has been previously stored + */ + public void storePassword(AccountID accountID, String password) + throws IllegalArgumentException + { + storePassword(getBundleContext(), accountID, password); } /** * Saves the password for the specified account after scrambling it a bit - * sot that it is not visible from first sight (Method remains highly + * so that it is not visible from first sight (Method remains highly * insecure). - * + * <p> + * TODO Delegate the implementation to {@link AccountManager} because it + * knows the format in which the password (among the other account + * properties) is to be saved. + * </p> + * * @param bundleContext a currently valid bundle context. * @param accountID the AccountID for the account whose password we're - * storing. + * storing. * @param password the password itself. - * - * @throws java.lang.IllegalArgumentException if no account corresponding - * to <tt>accountID</tt> has been previously stored. + * + * @throws IllegalArgumentException if no account corresponding to + * <tt>accountID</tt> has been previously stored. */ protected void storePassword(BundleContext bundleContext, AccountID accountID, @@ -431,11 +469,29 @@ public abstract class ProtocolProviderFactory /** * Returns the password last saved for the specified account. - * + * + * @param accountID the AccountID for the account whose password we're + * looking for + * + * @return a String containing the password for the specified accountID + */ + public String loadPassword(AccountID accountID) + { + return loadPassword(getBundleContext(), accountID); + } + + /** + * Returns the password last saved for the specified account. + * <p> + * TODO Delegate the implementation to {@link AccountManager} because it + * knows the format in which the password (among the other account + * properties) was saved. + * </p> + * * @param bundleContext a currently valid bundle context. * @param accountID the AccountID for the account whose password we're - * looking for.. - * + * looking for.. + * * @return a String containing the password for the specified accountID. */ protected String loadPassword(BundleContext bundleContext, @@ -465,103 +521,110 @@ public abstract class ProtocolProviderFactory return new String(Base64.decode(mangledPassword)); } - /** - * Restores all accounts stored for the package corresponding to - * sourceFactory and and installs everyone of them through the install - * account method. - * <p> - * @param bundleContext a currently valid bundle context. + * Initializes and creates an account corresponding to the specified + * accountProperties and registers the resulting ProtocolProvider in the + * <tt>context</tt> BundleContext parameter. This method has a persistent + * effect. Once created the resulting account will remain installed until + * removed through the uninstallAccount method. + * + * @param accountProperties a set of protocol (or implementation) specific + * properties defining the new account. + * @return the AccountID of the newly loaded account */ - protected void loadStoredAccounts(BundleContext bundleContext) + public AccountID loadAccount(Map accountProperties) { - String sourcePackageName = getFactoryImplPackageName(); + BundleContext bundleContext = getBundleContext(); + if (bundleContext == null) + throw new NullPointerException( + "The specified BundleContext was null"); - ServiceReference confReference - = bundleContext.getServiceReference( - ConfigurationService.class.getName()); - ConfigurationService configurationService - = (ConfigurationService) bundleContext.getService(confReference); + if (accountProperties == null) + throw new NullPointerException( + "The specified property map was null"); - //first retrieve all accounts that we've registered - List storedAccounts = configurationService.getPropertyNamesByPrefix( - sourcePackageName, true); - - logger.debug("Discovered " - + storedAccounts.size() - + " stored accounts"); + String userID = (String) accountProperties.get(USER_ID); + if (userID == null) + throw new NullPointerException( + "The account properties contained no user id."); - //load all accounts stored in the configuration service - Iterator storedAccountsIter = storedAccounts.iterator(); + String protocolName = getProtocolName(); + if (!accountProperties.containsKey(PROTOCOL)) + accountProperties.put(PROTOCOL, protocolName); - while (storedAccountsIter.hasNext()) - { - String accountRootPropName = (String) storedAccountsIter.next(); - logger.debug("Loading account " + accountRootPropName); + AccountID accountID = createAccountID(userID, accountProperties); - //get all properties that we've stored for this account and load - //them into the accountProperties table. + ProtocolProviderService service = createService(userID, accountID); - List storedAccPropNames = configurationService.getPropertyNamesByPrefix( - accountRootPropName, true); + Dictionary<String, String> properties = new Hashtable<String, String>(); + properties.put(PROTOCOL, protocolName); + properties.put(USER_ID, userID); - Iterator propNamesIter = storedAccPropNames.iterator(); - Map accountProperties = new Hashtable(); - while(propNamesIter.hasNext()) - { - String fullPropertyName = (String)propNamesIter.next(); - String storedPropertyValue - = configurationService.getString(fullPropertyName); + ServiceRegistration serviceRegistration = + bundleContext.registerService(ProtocolProviderService.class + .getName(), service, properties); - //strip the package prefix off the property name. - String propertyName = fullPropertyName.substring( - fullPropertyName.lastIndexOf('.')+1); + synchronized (registeredAccounts) + { + registeredAccounts.put(accountID, serviceRegistration); + } - //if this is a password - decode it first - if(propertyName.equals(PASSWORD)) - { - if(storedPropertyValue == null - || storedPropertyValue.length() == 0) - { - storedPropertyValue = ""; - } - else - { - storedPropertyValue = new String( - Base64.decode(storedPropertyValue)); - } - } + return accountID; + } - if(storedPropertyValue != null) - accountProperties.put(propertyName, storedPropertyValue); - } - try - { - loadAccount(accountProperties); - } - catch (Exception exc) - { - //catch any exception here so that one failing accoung does not - //cut the whole account reloading process - logger.error("Failed to reload account:" + accountProperties, - exc); - } - } + /** + * Creates a new <code>AccountID</code> instance with a specific user ID to + * represent a given set of account properties. + * <p> + * The method is a pure factory allowing implementers to specify the runtime + * type of the created <code>AccountID</code> and customize the instance. + * The returned <code>AccountID</code> will later be associated with a + * <code>ProtocolProviderService</code> by the caller (e.g. using + * {@link #createService(String, AccountID)}). + * </p> + * + * @param userID the user ID of the new instance + * @param accountProperties the set of properties to be represented by the + * new instance + * @return a new <code>AccountID</code> instance with the specified user ID + * representing the given set of account properties + */ + protected abstract AccountID createAccountID(String userID, + Map accountProperties); + + /** + * Gets the name of the protocol this factory registers its + * <code>ProtocolProviderService</code>s with and to be placed in the + * properties of the accounts created by this factory. + * + * @return the name of the protocol this factory registers its + * <code>ProtocolProviderService</code>s with and to be placed in + * the properties of the accounts created by this factory + */ + protected String getProtocolName() + { + return protocolName; } /** - * Initializes and creates an account corresponding to the specified - * accountProperties and registers the resulting ProtocolProvider in the - * <tt>context</tt> BundleContext parameter. This method has a persistent - * effect. Once created the resulting account will remain installed until - * removed through the uninstall account method. - * - * @param accountProperties a set of protocol (or implementation) - * specific properties defining the new account. - * - * @return the AccountID of the newly loaded account - */ - protected abstract AccountID loadAccount( Map accountProperties); + * Initializes a new <code>ProtocolProviderService</code> instance with a + * specific user ID to represent a specific <code>AccountID</code>. + * <p> + * The method is a pure factory allowing implementers to specify the runtime + * type of the created <code>ProtocolProviderService</code> and customize + * the instance. The caller will later register the returned service with + * the <code>BundleContext</code> of this factory. + * </p> + * + * @param userID the user ID to initialize the new instance with + * @param accountID the <code>AccountID</code> to be represented by the new + * instance + * @return a new <code>ProtocolProviderService</code> instance with the + * specific user ID representing the specified + * <code>AccountID</code> + */ + protected abstract ProtocolProviderService createService(String userID, + AccountID accountID); /** * Removes the account with <tt>accountID</tt> from the set of accounts @@ -691,4 +754,53 @@ public abstract class ProtocolProviderFactory return className.substring(0, className.lastIndexOf('.')); } + + /** + * Prepares the factory for bundle shutdown. + */ + public void stop() + { + logger.trace("Preparing to stop all protocol providers of" + this); + + synchronized (registeredAccounts) + { + for (Enumeration<ServiceRegistration> registrations = + registeredAccounts.elements(); registrations.hasMoreElements();) + { + ServiceRegistration reg = registrations.nextElement(); + + stop(reg); + + reg.unregister(); + } + + registeredAccounts.clear(); + } + } + + /** + * Shuts down the <code>ProtocolProviderService</code> representing an + * account registered with this factory. + * + * @param registeredAccount the <code>ServiceRegistration</code> of the + * <code>ProtocolProviderService</code> representing an account + * registered with this factory + */ + protected void stop(ServiceRegistration registeredAccount) + { + ProtocolProviderService protocolProviderService = + (ProtocolProviderService) getBundleContext().getService( + registeredAccount.getReference()); + + protocolProviderService.shutdown(); + } + + private AccountManager getAccountManager() + { + BundleContext bundleContext = getBundleContext(); + ServiceReference serviceReference = + bundleContext.getServiceReference(AccountManager.class.getName()); + + return (AccountManager) bundleContext.getService(serviceReference); + } } diff --git a/src/net/java/sip/communicator/service/protocol/event/AccountManagerEvent.java b/src/net/java/sip/communicator/service/protocol/event/AccountManagerEvent.java new file mode 100644 index 0000000..550b340 --- /dev/null +++ b/src/net/java/sip/communicator/service/protocol/event/AccountManagerEvent.java @@ -0,0 +1,84 @@ +/*
+ * SIP Communicator, the OpenSource Java VoIP and Instant Messaging client.
+ *
+ * Distributable under LGPL license.
+ * See terms of license at gnu.org.
+ */
+package net.java.sip.communicator.service.protocol.event;
+
+import java.util.*;
+
+import net.java.sip.communicator.service.protocol.*;
+
+/**
+ * Represents a notifying event fired by a specific {@link AccountManager}.
+ *
+ * @author Lubomir Marinov
+ */
+public class AccountManagerEvent
+ extends EventObject
+{
+
+ /**
+ * The type of event notifying that the loading of the stored accounts of a
+ * specific <code>ProtocolProviderFactory</code> has finished.
+ */
+ public static final int STORED_ACCOUNTS_LOADED = 1;
+
+ /**
+ * The <code>ProtocolProviderFactory</code> being worked on at the time this
+ * event has been fired.
+ */
+ private final ProtocolProviderFactory factory;
+
+ /**
+ * The (detail) type of this event which is one of
+ * {@link #STORED_ACCOUNTS_LOADED}.
+ */
+ private final int type;
+
+ /**
+ * Initializes a new <code>AccountManagerEvent</code> instance fired by a
+ * specific <code>AccountManager</code> in order to notify of an event of a
+ * specific type occurring while working on a specific
+ * <code>ProtocolProviderFactory</code>.
+ *
+ * @param accountManager the <code>AccountManager</code> issuing the
+ * notification i.e. the source of the event
+ * @param type
+ * @param factory the <code>ProtocolProviderFactory</code> being worked on
+ * at the time this event has been fired
+ */
+ public AccountManagerEvent(AccountManager accountManager, int type,
+ ProtocolProviderFactory factory)
+ {
+ super(accountManager);
+
+ this.type = type;
+ this.factory = factory;
+ }
+
+ /**
+ * Gets the <code>ProtocolProviderFactory</code> being worked on at the time
+ * this event has been fired.
+ *
+ * @return the <code>ProtocolProviderFactory</code> being worked on at the
+ * time this event has been fired
+ */
+ public ProtocolProviderFactory getFactory()
+ {
+ return factory;
+ }
+
+ /**
+ * Gets the (detail) type of this event which is one of
+ * <code>STORED_ACCOUNTS_LOADED</code>.
+ *
+ * @return the (detail) type of this event which is one of
+ * <code>STORED_ACCOUNTS_LOADED</code>
+ */
+ public int getType()
+ {
+ return type;
+ }
+}
diff --git a/src/net/java/sip/communicator/service/protocol/event/AccountManagerListener.java b/src/net/java/sip/communicator/service/protocol/event/AccountManagerListener.java new file mode 100644 index 0000000..ee03822 --- /dev/null +++ b/src/net/java/sip/communicator/service/protocol/event/AccountManagerListener.java @@ -0,0 +1,31 @@ +/*
+ * SIP Communicator, the OpenSource Java VoIP and Instant Messaging client.
+ *
+ * Distributable under LGPL license.
+ * See terms of license at gnu.org.
+ */
+package net.java.sip.communicator.service.protocol.event;
+
+import java.util.*;
+
+import net.java.sip.communicator.service.protocol.*;
+
+/**
+ * Represents a listener receiving notifications from {@link AccountManager}.
+ *
+ * @author Lubomir Marinov
+ */
+public interface AccountManagerListener
+ extends EventListener
+{
+
+ /**
+ * Notifies this listener about an event fired by a specific
+ * <code>AccountManager</code>.
+ *
+ * @param event the <code>AccountManagerEvent</code> describing the
+ * <code>AccountManager</code> firing the notification and the
+ * other details of the specific notification.
+ */
+ void handleAccountManagerEvent(AccountManagerEvent event);
+}
diff --git a/src/net/java/sip/communicator/service/protocol/protocol.provider.manifest.mf b/src/net/java/sip/communicator/service/protocol/protocol.provider.manifest.mf index 557bd2b..c2faf0c 100644 --- a/src/net/java/sip/communicator/service/protocol/protocol.provider.manifest.mf +++ b/src/net/java/sip/communicator/service/protocol/protocol.provider.manifest.mf @@ -1,3 +1,4 @@ +Bundle-Activator: net.java.sip.communicator.impl.protocol.ProtocolProviderActivator Bundle-Name: Protocol Provider Service Bundle-Description: Protocol Provider Service. Bundle-Vendor: sip-communicator.org diff --git a/src/net/java/sip/communicator/util/launchutils/LaunchArgHandler.java b/src/net/java/sip/communicator/util/launchutils/LaunchArgHandler.java index 372220b..4a4d1f2 100644 --- a/src/net/java/sip/communicator/util/launchutils/LaunchArgHandler.java +++ b/src/net/java/sip/communicator/util/launchutils/LaunchArgHandler.java @@ -128,23 +128,38 @@ public class LaunchArgHandler */ private LaunchArgHandler() { - try + InputStream versionPropertiesStream = + getClass().getResourceAsStream(VERSION_PROPERTIES); + boolean versionPropertiesAreLoaded = false; + if (versionPropertiesStream != null) { - versionProperties.load( - getClass().getResourceAsStream(VERSION_PROPERTIES)); - - // start url handler for mac os. - String osName = System.getProperty("os.name"); - if (osName.startsWith("Mac")) + try { - new AEGetURLEventHandler(this); + try + { + versionProperties.load(versionPropertiesStream); + versionPropertiesAreLoaded = true; + } + finally + { + versionPropertiesStream.close(); + } + } + catch (IOException exc) + { + // no need to worry the user, so only print if we're in FINEST } } - catch(IOException exc) + if (!versionPropertiesAreLoaded) { - //no need to worry the user, so only print if we're in FINEST logger.trace("Couldn't open version.properties"); } + + // Start url handler for Mac OS X. + if (System.getProperty("os.name").startsWith("Mac")) + { + new AEGetURLEventHandler(this); + } } /** |