diff options
author | Ingo Bauersachs <ingo@jitsi.org> | 2013-12-08 13:11:47 +0100 |
---|---|---|
committer | Ingo Bauersachs <ingo@jitsi.org> | 2013-12-08 13:11:47 +0100 |
commit | ae070f1e4f9aa6a5a307e6db60fa6bfb762cbe2d (patch) | |
tree | 7db0df8d598bf9d5927716bf3dedc80331369998 /src/net/java/sip/communicator/impl/protocol | |
parent | 9d31fa1c9cf978a3fadae338247f56c9f2739022 (diff) | |
download | jitsi-ae070f1e4f9aa6a5a307e6db60fa6bfb762cbe2d.zip jitsi-ae070f1e4f9aa6a5a307e6db60fa6bfb762cbe2d.tar.gz jitsi-ae070f1e4f9aa6a5a307e6db60fa6bfb762cbe2d.tar.bz2 |
Remove RSS protocol
Diffstat (limited to 'src/net/java/sip/communicator/impl/protocol')
18 files changed, 0 insertions, 4811 deletions
diff --git a/src/net/java/sip/communicator/impl/protocol/rss/ContactGroupRssImpl.java b/src/net/java/sip/communicator/impl/protocol/rss/ContactGroupRssImpl.java deleted file mode 100644 index 3a770a2..0000000 --- a/src/net/java/sip/communicator/impl/protocol/rss/ContactGroupRssImpl.java +++ /dev/null @@ -1,594 +0,0 @@ -/* - * Jitsi, 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.rss; - -import java.util.*; - -import net.java.sip.communicator.service.protocol.*; - -/** - * A simple, straightforward implementation of a rss ContactGroup. Since - * the Rss protocol is not a real one, we simply store all group details - * in class fields. You should know that when implementing a real protocol, - * the contact group implementation would rather encapsulate group objects from - * the protocol stack and group property values should be returned by consulting - * the encapsulated object. - * - * @author Emil Ivov - */ -public class ContactGroupRssImpl - implements ContactGroup -{ - - /** - * The name of this Rss contact group. - */ - private String groupName = null; - - /** - * The list of this group's members. - */ - private Vector<Contact> contacts = new Vector<Contact>(); - - /** - * The list of sub groups belonging to this group. - */ - private Vector<ContactGroup> subGroups = new Vector<ContactGroup>(); - - /** - * The group that this group belongs to (or null if this is the root group). - */ - private ContactGroupRssImpl parentGroup = null; - - /** - * Determines whether this group is really in the contact list or whether - * it is here only temporarily and will be gone next time we restart. - */ - private boolean isPersistent = true; - - /** - * The protocol provider that created us. - */ - private ProtocolProviderServiceRssImpl parentProvider = null; - - /** - * Determines whether this group has been resolved on the server. - * Unresolved groups are groups that were available on previous runs and - * that the meta contact list has stored. During all next runs, when - * bootstrapping, the meta contact list would create these groups as - * unresolved. Once a protocol provider implementation confirms that the - * groups are still on the server, it would issue an event indicating that - * the groups are now resolved. - */ - private boolean isResolved = true; - - /** - * An id uniquely identifying the group. For many protocols this could be - * the group name itself. - */ - private String uid = null; - private static final String UID_SUFFIX = ".uid"; - - /** - * Creates a ContactGroupRssImpl with the specified name. - * - * @param groupName the name of the group. - * @param parentProvider the protocol provider that created this group. - */ - public ContactGroupRssImpl( - String groupName, - ProtocolProviderServiceRssImpl parentProvider) - { - this.groupName = groupName; - this.uid = groupName + UID_SUFFIX; - this.parentProvider = parentProvider; - } - - /** - * Determines whether the group may contain subgroups or not. - * - * @return always true in this implementation. - */ - public boolean canContainSubgroups() - { - return true; - } - - /** - * Returns the protocol provider that this group belongs to. - * @return a regerence to the ProtocolProviderService instance that this - * ContactGroup belongs to. - */ - public ProtocolProviderService getProtocolProvider() - { - return parentProvider; - } - - /** - * Returns an Iterator over all contacts, member of this - * <tt>ContactGroup</tt>. - * - * @return a java.util.Iterator over all contacts inside this - * <tt>ContactGroup</tt> - */ - public Iterator<Contact> contacts() - { - return contacts.iterator(); - } - - /** - * Adds the specified contact to this group. - * @param contactToAdd the ContactRssImpl to add to this group. - */ - public void addContact(ContactRssImpl contactToAdd) - { - this.contacts.add(contactToAdd); - contactToAdd.setParentGroup(this); - } - - /** - * Returns the number of <tt>Contact</tt> members of this - * <tt>ContactGroup</tt> - * - * @return an int indicating the number of <tt>Contact</tt>s, members of - * this <tt>ContactGroup</tt>. - */ - public int countContacts() - { - return contacts.size(); - } - - /** - * Returns the number of subgroups contained by this - * <tt>ContactGroup</tt>. - * - * @return the number of subGroups currently added to this group. - */ - public int countSubgroups() - { - return subGroups.size(); - } - - /** - * Adds the specified contact group to the contained by this group. - * @param subgroup the ContactGroupRssImpl to add as a subgroup to this group. - */ - public void addSubgroup(ContactGroupRssImpl subgroup) - { - this.subGroups.add(subgroup); - subgroup.setParentGroup(this); - } - - /** - * Sets the group that is the new parent of this group - * @param parent ContactGroupRssImpl - */ - void setParentGroup(ContactGroupRssImpl parent) - { - this.parentGroup = parent; - } - - /** - * Returns the contact group that currently contains this group or null if - * this is the root contact group. - * @return the contact group that currently contains this group or null if - * this is the root contact group. - */ - public ContactGroup getParentContactGroup() - { - return this.parentGroup; - } - - /** - * Removes the specified contact group from the this group's subgroups. - * @param subgroup the ContactGroupRssImpl subgroup to remove. - */ - public void removeSubGroup(ContactGroupRssImpl subgroup) - { - this.subGroups.remove(subgroup); - subgroup.setParentGroup(null); - } - - /** - * Returns the group that is parent of the specified rssGroup or null - * if no parent was found. - * @param rssGroup the group whose parent we're looking for. - * @return the ContactGroupRssImpl instance that rssGroup - * belongs to or null if no parent was found. - */ - public ContactGroupRssImpl findGroupParent( - ContactGroupRssImpl rssGroup) - { - if ( subGroups.contains(rssGroup) ) - return this; - - Iterator<ContactGroup> subGroupsIter = subgroups(); - while (subGroupsIter.hasNext()) - { - ContactGroupRssImpl subgroup - = (ContactGroupRssImpl) subGroupsIter.next(); - - ContactGroupRssImpl parent - = subgroup.findGroupParent(rssGroup); - - if(parent != null) - return parent; - } - return null; - } - - /** - * Returns the group that is parent of the specified rssContact or - * null if no parent was found. - * - * @param rssContact the contact whose parent we're looking for. - * @return the ContactGroupRssImpl instance that rssContact - * belongs to or <tt>null</tt> if no parent was found. - */ - public ContactGroupRssImpl findContactParent( - ContactRssImpl rssContact) - { - if ( contacts.contains(rssContact) ) - return this; - - Iterator<ContactGroup> subGroupsIter = subgroups(); - while (subGroupsIter.hasNext()) - { - ContactGroupRssImpl subgroup - = (ContactGroupRssImpl) subGroupsIter.next(); - - ContactGroupRssImpl parent - = subgroup.findContactParent(rssContact); - - if(parent != null) - return parent; - } - return null; - } - - - - /** - * Returns the <tt>Contact</tt> with the specified address or identifier. - * - * @param id the addres or identifier of the <tt>Contact</tt> we are - * looking for. - * @return the <tt>Contact</tt> with the specified id or address. - */ - public Contact getContact(String id) - { - Iterator<Contact> contactsIter = contacts(); - while (contactsIter.hasNext()) - { - ContactRssImpl contact = (ContactRssImpl) contactsIter.next(); - if (contact.getAddress().equals(id)) - return contact; - - } - return null; - } - - /** - * Returns the subgroup with the specified index. - * - * @param index the index of the <tt>ContactGroup</tt> to retrieve. - * @return the <tt>ContactGroup</tt> with the specified index. - */ - public ContactGroup getGroup(int index) - { - return subGroups.get(index); - } - - /** - * Returns the subgroup with the specified name. - * - * @param groupName the name of the <tt>ContactGroup</tt> to retrieve. - * @return the <tt>ContactGroup</tt> with the specified index. - */ - public ContactGroup getGroup(String groupName) - { - Iterator<ContactGroup> groupsIter = subgroups(); - while (groupsIter.hasNext()) - { - ContactGroupRssImpl contactGroup - = (ContactGroupRssImpl) groupsIter.next(); - if (contactGroup.getGroupName().equals(groupName)) - return contactGroup; - - } - return null; - - } - - /** - * Returns the name of this group. - * - * @return a String containing the name of this group. - */ - public String getGroupName() - { - return this.groupName; - } - - /** - * Sets this group a new name. - * @param newGrpName a String containing the new name of this group. - */ - public void setGroupName(String newGrpName) - { - this.groupName = newGrpName; - } - - /** - * Returns an iterator over the sub groups that this - * <tt>ContactGroup</tt> contains. - * - * @return a java.util.Iterator over the <tt>ContactGroup</tt> children - * of this group (i.e. subgroups). - */ - public Iterator<ContactGroup> subgroups() - { - return subGroups.iterator(); - } - - /** - * Removes the specified contact from this group. - * @param contact the ContactRssImpl to remove from this group - */ - public void removeContact(ContactRssImpl contact) - { - this.contacts.remove(contact); - } - - /** - * Returns the contact with the specified id or null if no such contact - * exists. - * @param id the id of the contact we're looking for. - * @return ContactRssImpl - */ - public ContactRssImpl findContactByID(String id) - { - //first go through the contacts that are direct children. - Iterator<Contact> contactsIter = contacts(); - - while(contactsIter.hasNext()) - { - ContactRssImpl mContact = (ContactRssImpl)contactsIter.next(); - - if( mContact.getAddress().equals(id) ) - return mContact; - } - - //if we didn't find it here, let's try in the subougroups - Iterator<ContactGroup> groupsIter = subgroups(); - - while( groupsIter.hasNext() ) - { - ContactGroupRssImpl mGroup = (ContactGroupRssImpl)groupsIter.next(); - - ContactRssImpl mContact = mGroup.findContactByID(id); - - if (mContact != null) - return mContact; - } - - return null; - } - - - /** - * Returns a String representation of this group and the contacts it - * contains (may turn out to be a relatively long string). - * @return a String representing this group and its child contacts. - */ - @Override - public String toString() - { - - StringBuffer buff = new StringBuffer(getGroupName()); - buff.append(".subGroups=" + countSubgroups() + ":\n"); - - Iterator<ContactGroup> subGroups = subgroups(); - while (subGroups.hasNext()) - { - ContactGroupRssImpl group = (ContactGroupRssImpl)subGroups.next(); - buff.append(group.toString()); - if (subGroups.hasNext()) - buff.append("\n"); - } - - buff.append("\nChildContacts="+countContacts()+":["); - - Iterator<Contact> contacts = contacts(); - while (contacts.hasNext()) - { - ContactRssImpl contact = (ContactRssImpl) contacts.next(); - buff.append(contact.toString()); - if(contacts.hasNext()) - buff.append(", "); - } - return buff.append("]").toString(); - } - - public void getRssURLList(List<ContactRssImpl> rssURLList) - { - Iterator<ContactGroup> subGroups = subgroups(); - while (subGroups.hasNext()) - { - ContactGroupRssImpl group = (ContactGroupRssImpl)subGroups.next(); - group.getRssURLList(rssURLList); - } - - Iterator<Contact> contacts = contacts(); - while (contacts.hasNext()) - { - ContactRssImpl contact = (ContactRssImpl) contacts.next(); - rssURLList.add(contact); - } - } - - /** - * Specifies whether or not this contact group is being stored by the server. - * Non persistent contact groups are common in the case of simple, - * non-persistent presence operation sets. They could however also be seen - * in persistent presence operation sets when for example we have received - * an event from someone not on our contact list and the contact that we - * associated with that user is placed in a non persistent group. Non - * persistent contact groups are volatile even when coming from a persistent - * presence op. set. They would only exist until the application is closed - * and will not be there next time it is loaded. - * - * @param isPersistent true if the contact group is to be persistent and - * false otherwise. - */ - public void setPersistent(boolean isPersistent) - { - this.isPersistent = isPersistent; - } - - /** - * Determines whether or not this contact group is being stored by the - * server. Non persistent contact groups exist for the sole purpose of - * containing non persistent contacts. - * @return true if the contact group is persistent and false otherwise. - */ - public boolean isPersistent() - { - return isPersistent; - } - - /** - * Returns null as no persistent data is required and the contact address is - * sufficient for restoring the contact. - * <p> - * @return null as no such data is needed. - */ - public String getPersistentData() - { - return null; - } - - /** - * Determines whether or not this contact has been resolved against the - * server. Unresolved contacts are used when initially loading a contact - * list that has been stored in a local file until the presence operation - * set has managed to retrieve all the contact list from the server and has - * properly mapped contacts to their on-line buddies. - * @return true if the contact has been resolved (mapped against a buddy) - * and false otherwise. - */ - public boolean isResolved() - { - return isResolved; - } - - /** - * Makes the group resolved or unresolved. - * - * @param resolved true to make the group resolved; false to - * make it unresolved - */ - public void setResolved(boolean resolved) - { - this.isResolved = resolved; - } - - /** - * Returns a <tt>String</tt> that uniquely represnets the group inside - * the current protocol. The string MUST be persistent (it must not change - * across connections or runs of the application). In many cases (Jabber, - * ICQ) the string may match the name of the group as these protocols - * only allow a single level of contact groups and there is no danger of - * having the same name twice in the same contact list. Other protocols - * (no examples come to mind but that doesn't bother me ;) ) may be - * supporting mutilple levels of grooups so it might be possible for group - * A and group B to both contain groups named C. In such cases the - * implementation must find a way to return a unique identifier in this - * method and this UID should never change for a given group. - * - * @return a String representing this group in a unique and persistent - * way. - */ - public String getUID() - { - return uid; - } - - /** - * Ugly but tricky conversion method. - * @param uid the uid we'd like to get a name from - * @return the name of the group with the specified <tt>uid</tt>. - */ - static String createNameFromUID(String uid) - { - return uid.substring(0, uid.length() - (UID_SUFFIX.length())); - } - - /** - * Indicates whether some other object is "equal to" this one which in terms - * of contact groups translates to having the equal names and matching - * subgroups and child contacts. The resolved status of contactgroups and - * contacts is deliberately ignored so that groups and/or contacts would - * be assumed equal even if it differs. - * <p> - * @param obj the reference object with which to compare. - * @return <code>true</code> if this contact group has the equal child - * contacts and subgroups to those of the <code>obj</code> argument. - */ - @Override - public boolean equals(Object obj) - { - if(obj == null - || !(obj instanceof ContactGroupRssImpl)) - return false; - - ContactGroupRssImpl rssGroup - = (ContactGroupRssImpl)obj; - - if( ! rssGroup.getGroupName().equals(getGroupName()) - || ! rssGroup.getUID().equals(getUID()) - || rssGroup.countContacts() != countContacts() - || rssGroup.countSubgroups() != countSubgroups()) - return false; - - //traverse child contacts - Iterator<Contact> theirContacts = rssGroup.contacts(); - - while(theirContacts.hasNext()) - { - ContactRssImpl theirContact - = (ContactRssImpl)theirContacts.next(); - - ContactRssImpl ourContact - = (ContactRssImpl)getContact(theirContact.getAddress()); - - if(ourContact == null - || !ourContact.equals(theirContact)) - return false; - } - - //traverse subgroups - Iterator<ContactGroup> theirSubgroups = rssGroup.subgroups(); - - while(theirSubgroups.hasNext()) - { - ContactGroupRssImpl theirSubgroup - = (ContactGroupRssImpl)theirSubgroups.next(); - - ContactGroupRssImpl ourSubgroup - = (ContactGroupRssImpl)getGroup( - theirSubgroup.getGroupName()); - - if(ourSubgroup == null - || !ourSubgroup.equals(theirSubgroup)) - return false; - } - - return true; - } -} - diff --git a/src/net/java/sip/communicator/impl/protocol/rss/ContactRssImpl.java b/src/net/java/sip/communicator/impl/protocol/rss/ContactRssImpl.java deleted file mode 100644 index 76a773e..0000000 --- a/src/net/java/sip/communicator/impl/protocol/rss/ContactRssImpl.java +++ /dev/null @@ -1,436 +0,0 @@ -/* - * Jitsi, 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.rss; - -import java.io.*; -import java.net.*; - -import net.java.sip.communicator.service.protocol.*; - -/** - * An implementation of a rss Contact. - * - * @author Jean-Albert Vescovo - * @author Mihai Balan - */ -public class ContactRssImpl - extends AbstractContact -{ - - /** - * Item key identifying the last item retrieved and displayed. - */ - //private RssItemKey lastItem = new RssItemKey(new Date(0)); - - /** - * Contact's nickname. - */ - private String nickName = null; - - /** - * Stores the contact's display image to avoid downloading it multiple times. - */ - private byte[] icon; - - /** - * This contact's URL (URL of the RSS feed). - */ - //private URL rssURL = null; - - /** - * This contact id (http://... or feed://...) - */ - private String contactID = null; - - /** - * The provider that created us. - */ - private ProtocolProviderServiceRssImpl parentProvider = null; - - /** - * The group that the contact belongs to. - */ - private ContactGroupRssImpl parentGroup = null; - - /** - * The presence status of the contact. - */ - private PresenceStatus presenceStatus = RssStatusEnum.OFFLINE; - - /** - * Determines whether this contact is persistent, i.e. member of the contact - * list or whether it is here only temporarily. - */ - private boolean isPersistent = true; - - /** - * Determines whether the contact has been resolved (i.e. we have a - * confirmation that it is still on the server contact list). - */ - private boolean isResolved = false; - - /** - * The feed reader that we'll be using to retrieve the RSS flow associated - * with this contact. - */ - private RssFeedReader rssFeedReader = null; - - /** - * Creates an instance of a meta contact with the specified string used - * as a name and identifier. - * - * @param rssURL the URL of the rss feed that this contact will be wrapping. - * @param parentProvider the provider that created us. - */ - public ContactRssImpl(String contactID, - URL rssURL, - //RssFeedReader rssFeedReader, - String persistentData, - ProtocolProviderServiceRssImpl parentProvider) - throws OperationFailedException, FileNotFoundException - { - this.contactID = contactID; - //this.rssURL = rssURL; - this.parentProvider = parentProvider; - if(persistentData == null) - { - this.rssFeedReader = new RssFeedReader(rssURL); - } - else - { - this.rssFeedReader = RssFeedReader.deserialize(rssURL, persistentData); - this.nickName = this.rssFeedReader.getTitle(); - } - //this.rssFeedReader = rssFeedReader; - } - - /** - * This method is only called when the contact is added to a new - * <tt>ContactGroupRssImpl</tt> by the - * <tt>ContactGroupRssImpl</tt> itself. - * - * @param newParentGroup the <tt>ContactGroupRssImpl</tt> that is now - * parent of this <tt>ContactRssImpl</tt> - */ - void setParentGroup(ContactGroupRssImpl newParentGroup) - { - this.parentGroup = newParentGroup; - } - - /** - * Returns a String that can be used for identifying the contact. - * - * @return a String id representing that uniquely identifies the contact. - */ - public String getAddress() - { - return contactID; - } - - /** - * Returns the URL that this contact is representing. - * - * @return the URL of the RSS flow that this contact represents. - */ - /*public URL getRssURL() - { - return rssURL; - }*/ - - /** - * Returns a String that could be used by any user interacting modules - * for referring to this contact. - * - * @return a String that can be used for referring to this contact when - * interacting with the user. - */ - public String getDisplayName() - { - if(nickName == null) - { - return contactID; - } - else - { - return nickName; - } - } - - /*** - * Sets the contact's nickname. - * @param nickName - */ - public void setDisplayName(String nickName) - { - this.nickName = nickName; - } - - /*** - * Returns a <tt>RssItemKey</tt> object that identifies the last retrieved - * item in the feed. - * @return key identifying the last item in the feed. - */ - /*public RssItemKey getLastItemKey() - { - return this.lastItem; - }*/ - - /*** - * Sets the key identifying the last item in the feed. It's usually used in - * conjunction with a new <tt>RssItemKey</tt> object. For instance: - * <code>contact.setLastItemKey(new RssItemKey(new Date()));</code> - * - * @param key key identifying the last item in the feed or (at least) - * allowing differencing for newer items. - * - * @see RssItemKey - */ - /*public void setLastItemKey(RssItemKey key) - { - this.lastItem= key; - }*/ - - /** - * Returns an avatar if one is already present or <tt>null</tt> in case it - * is not in which case it the method also queues the contact for image - * updates. - * - * @return the avatar of this contact or <tt>null</tt> if no avatar is - * currently available. - */ - public byte[] getImage() - { - return getImage(true); - } - - /** - * Returns a reference to the image assigned to this contact. If no image - * is present and the retrieveIfNecessary flag is true, we schedule the - * image for retrieval from the server. - * - * @param retrieveIfNecessary specifies whether the method should queue - * this contact for avatar update from the server. - * - * @return a reference to the image currently stored by this contact. - */ - byte[] getImage(boolean retrieveIfNecessary) - { - if(icon == null && retrieveIfNecessary) - { - OperationSetPersistentPresenceRssImpl pres - = (OperationSetPersistentPresenceRssImpl)this.parentProvider - .getOperationSet(OperationSetPersistentPresence.class); - - pres.getImageRetriever().addContact(this); - } - - return icon; - } - - /** - * Set the image of the contact. - * - * @param imgBytes the bytes of the image that we'd like to set. - */ - void setImage(byte[] imgBytes) - { - this.icon = imgBytes; - } - - /** - * Returns the status of the contact. - * - * @return Current presence status of the contact. - */ - public PresenceStatus getPresenceStatus() - { - return this.presenceStatus; - } - - /** - * Sets <tt>rssPresenceStatus</tt> as the PresenceStatus that this - * contact is currently in. - * @param rssPresenceStatus the <tt>RssPresenceStatus</tt> - * currently valid for this contact. - */ - public void setPresenceStatus(PresenceStatus rssPresenceStatus) - { - this.presenceStatus = rssPresenceStatus; - } - - /** - * Returns a reference to the protocol provider that created the contact. - * - * @return a reference to an instance of the ProtocolProviderService - */ - public ProtocolProviderService getProtocolProvider() - { - return parentProvider; - } - - /** - * Determines whether or not this contact represents our own identity. - * - * @return true in case this is a contact that represents ourselves and - * false otherwise. - */ - public boolean isLocal() - { - return false; - } - - /** - * Returns the group that contains this contact. - * @return a reference to the <tt>ContactGroupRssImpl</tt> that - * contains this contact. - */ - public ContactGroup getParentContactGroup() - { - return this.parentGroup; - } - - /** - * Returns a string representation of this contact, containing most of its - * representative details. - * - * @return a string representation of this contact. - */ - @Override - public String toString() - { - StringBuffer buff - = new StringBuffer("ContactRssImpl[ DisplayName=") - .append(getDisplayName()).append("]"); - - return buff.toString(); - } - - /** - * Determines whether or not this contact is being stored by the server. - * Non persistent contacts are common in the case of simple, non-persistent - * presence operation sets. They could however also be seen in persistent - * presence operation sets when for example we have received an event - * from someone not on our contact list. Non persistent contacts are - * volatile even when coming from a persistent presence operation set. They - * would only exist until the application is closed and will not be there - * next time it is loaded. - * - * @return true if the contact is persistent and false otherwise. - */ - public boolean isPersistent() - { - return isPersistent; - } - - /** - * Specifies whether or not this contact is being stored by the server. - * Non persistent contacts are common in the case of simple, non-persistent - * presence operation sets. They could however also be seen in persistent - * presence operation sets when for example we have received an event - * from someone not on our contact list. Non persistent contacts are - * volatile even when coming from a persistent presence operation set. They - * would only exist until the application is closed and will not be there - * next time it is loaded. - * - * @param isPersistent true if the contact is persistent and false - * otherwise. - */ - public void setPersistent(boolean isPersistent) - { - this.isPersistent = isPersistent; - } - - /*** - * Produces a textual representation of contact data that can be used to - * restore the contact even before the network connection has been - * initialized. This data contains the key identifying the last displayed - * item, so that upon restart, items that have already been displayed in - * older sessions don't get displayed again. - */ - public String getPersistentData() - { - /*RssItemKey lastItem = rssFeedReader.getLastItemKey(); - if (lastItem != null) - return lastItem.serialize(); - else - return null;*/ - return rssFeedReader.serialize(); - } - - /*** - * Restores feed item identification data from their textual representation. - * @param persistentData textual representation of item key. - * - * #setPersistentData() - */ - /*public void setPersistentData(String persistentData) - { - lastItem = RssItemKey.deserialize(persistentData); - }*/ - - /** - * Determines whether or not this contact has been resolved against the - * server. Unresolved contacts are used when initially loading a contact - * list that has been stored in a local file until the presence operation - * set has managed to retrieve all the contact list from the server and has - * properly mapped contacts to their on-line buddies. - * - * @return true if the contact has been resolved (mapped against a buddy) - * and false otherwise. - */ - public boolean isResolved() - { - return isResolved; - } - - /** - * Makes the contact resolved or unresolved. - * - * @param resolved true to make the contact resolved; false to - * make it unresolved - */ - public void setResolved(boolean resolved) - { - this.isResolved = resolved; - } - - /** - * Returns the persistent presence operation set that this contact belongs - * to. - * - * @return the <tt>OperationSetPersistentPresenceRssImpl</tt> that - * this contact belongs to. - */ - public OperationSetPersistentPresenceRssImpl - getParentPresenceOperationSet() - { - return (OperationSetPersistentPresenceRssImpl)parentProvider - .getOperationSet(OperationSetPersistentPresence.class); - } - - /** - * Returns the RSS feed reader that we are using to retrieve flows - * associated with this contact. - * - * @return a reference to the <tt>RssFeedReader</tt> that we are using to - * retrieve the flow associated with this contact. - */ - public RssFeedReader getRssFeedReader() - { - return rssFeedReader; - } - - /** - * Return the current status message of this contact. - * - * @return null as the protocol has no support of status messages - */ - public String getStatusMessage() - { - return null; - } -} diff --git a/src/net/java/sip/communicator/impl/protocol/rss/ImageRetriever.java b/src/net/java/sip/communicator/impl/protocol/rss/ImageRetriever.java deleted file mode 100644 index fe18f71..0000000 --- a/src/net/java/sip/communicator/impl/protocol/rss/ImageRetriever.java +++ /dev/null @@ -1,355 +0,0 @@ -/* - * Jitsi, 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.rss; - -import java.awt.*; -import java.awt.image.*; -import java.io.*; -import java.net.*; -import java.util.*; - -import javax.imageio.*; - -import net.java.sip.communicator.service.protocol.event.*; -import net.java.sip.communicator.util.*; - -import com.ctreber.aclib.image.ico.*; - -/** - * A class that implements threaded retrieval for rss images. We launch from - * within the presence operation set in order to retrieve image icons without - * blocking. - * - * @author Emil Ivov - */ -public class ImageRetriever extends Thread -{ - private static final Logger logger = Logger.getLogger(ImageRetriever.class); - - /** - * list with the accounts with missing image - */ - private Vector<ContactRssImpl> contactsForUpdate = new Vector<ContactRssImpl>(); - - /** - * The operation set that created us. - */ - private OperationSetPersistentPresenceRssImpl parentOperationSet = null; - - /** - * The path within the bundle for the default RSS 64x64 icon. - */ - private String defaultIconId = "pageImageRss"; - - /** - * Creates the thread - */ - ImageRetriever(OperationSetPersistentPresenceRssImpl parentOpSet) - { - super("RssImageRetriever"); - setDaemon(true); - this.parentOperationSet = parentOpSet; - } - - /** - * Updates all contacts that we add to this retriever, and gets back to - * sleep if there aren't any. - */ - @Override - public void run() - { - try - { - Collection<ContactRssImpl> copyContactsForUpdate = null; - while (true) - { - synchronized (contactsForUpdate) - { - if (contactsForUpdate.isEmpty()) - contactsForUpdate.wait(); - - copyContactsForUpdate = new Vector<ContactRssImpl>( - contactsForUpdate); - contactsForUpdate.clear(); - } - - Iterator<ContactRssImpl> iter = copyContactsForUpdate - .iterator(); - while (iter.hasNext()) - { - ContactRssImpl contact = iter.next(); - - byte[] imgBytes = getAvatar(contact); - - if (imgBytes != null) - { - byte[] oldImage = contact.getImage(false); - contact.setImage(imgBytes); - - parentOperationSet.fireContactPropertyChangeEvent( - ContactPropertyChangeEvent.PROPERTY_IMAGE, - contact, - oldImage, - imgBytes); - } - } - } - } - catch (InterruptedException ex) - { - logger.error("NickRetriever error waiting will stop now!", ex); - } - } - - /** - * Add contact for retreiving if the provider is register notify the - * retreiver to get the nicks if we are not registered add a listener to - * wiat for registering - * - * @param contact - * the contact that we'd like to add for image retrieval. - */ - synchronized void addContact(ContactRssImpl contact) - { - synchronized (contactsForUpdate) - { - if (!contactsForUpdate.contains(contact)) - { - contactsForUpdate.add(contact); - contactsForUpdate.notifyAll(); - } - } - } - - /** - * Executes the actual image retriever. - * - * @param contact - * the contact that we'd like to retrieve an image for. - * - * @return a byte array with the image of the specified contact. - */ - private byte[] getAvatar(ContactRssImpl contact) - { - try - { - //we need to also use findFavIconFromSiteIndex but right now - //i can't find a quick way to reliably convert a URL (possibly a - //PNG an ICO or a 301 redirection) into an image byte array. - byte[] image = getFavIconFromSiteRoot(contact); - - if (image == null) - { - image = getDefaultRssIcon(); - } - - - return image; - } - catch (Exception exc) - { - if (logger.isTraceEnabled()) - logger.trace("Cannot load image for contact " + this + " : " - + exc.getMessage(), exc); - - return null; - } - } - - /** - * Returns the address of a favicon (i.e. HTML "icon" or "shortcut icon") if - * any is contained by the page on <tt>urlAddress</tt> or <tt>null</tt> if - * the page on the specified address does not contain a link to a favicon. - * - * @param urlAddress - * the address of the page that we'd like to check for a favicon. - * @return the address of the favicon for the <tt>urlAddress</tt> page or - * <tt>null</tt> if the page does not define such an icon. - */ - private String findFavIconFromSiteIndex(ContactRssImpl contact) - { - try - { - URL feedLocation = new URL(contact.getRssFeedReader().getURL()); - - URL siteIndex = new URL(feedLocation.getProtocol() + "://" - + feedLocation.getHost()); - - BufferedReader in = new BufferedReader(new InputStreamReader( - siteIndex.openStream())); - - String inputLine; - - while ((inputLine = in.readLine()) != null) - { - int index = 0; - while (index != -1) - { - int tagBeginIndex = inputLine.toLowerCase().indexOf( - "<link", index); - - if (tagBeginIndex == -1) - { - break; - } - - int tagEndIndex = inputLine.toLowerCase().indexOf(">", - tagBeginIndex); - if (tagEndIndex != -1) - { - String linkTag = inputLine.substring(tagBeginIndex, - tagEndIndex + 1); - - boolean isIconTag = linkTag.toLowerCase().matches( - ".*rel=.icon..*"); - - if (!isIconTag) - isIconTag = linkTag.toLowerCase().matches( - ".*rel=.shortcut icon..*"); - - if (isIconTag) - { - // find the value of the href tag - int hrefInd = linkTag.toLowerCase() - .indexOf("href="); - hrefInd += ("href=".length() + 1); - char startQuote = linkTag.charAt(hrefInd - 1); - int endQuoteInd = linkTag.indexOf(startQuote, - hrefInd); - - String iconLink = linkTag.substring(hrefInd, - endQuoteInd); - - return iconLink; - } - } - index = tagEndIndex + 1; - } - } - in.close(); - } - catch (Exception exc) - { - if (logger.isTraceEnabled()) - logger.trace("Failed to retrieve link image.", exc); - } - - return null; - } - - /** - * Looks for and fetches a possible favicon.ico icon from the host that - * hosts the specified URI. - * - * @return - */ - private byte[] getFavIconFromSiteRoot(ContactRssImpl contact) - { - Image selectedIcon; - URL location = null; - - // we use these to get the best possible icon in case our favicon is a - // multi-page icon. - int maxWidth = 0; - int maxColors = 0; - int crtDescriptor = -1; - - // used for ICO to PNG translation. Uses PNG as it's the "safest" - // choice. - ByteArrayOutputStream output = new ByteArrayOutputStream(); - byte[] result = null; - - try - { - URL feedLocation = new URL(contact.getRssFeedReader().getURL()); - - location = new URL(feedLocation.getProtocol() + "://" - + feedLocation.getHost() + "/favicon.ico"); - - ICOFile favicon = new ICOFile(location); - - if (logger.isTraceEnabled()) - logger.trace("Icon has " + favicon.getImageCount() + " pages"); - - for (int i = 0; i < favicon.getDescriptors().size(); i++) - { - BitmapDescriptor bmpDesc = favicon.getDescriptor(i); - if ((maxWidth < bmpDesc.getWidth())) - { - maxWidth = bmpDesc.getWidth(); - maxColors = bmpDesc.getColorCount(); - crtDescriptor = i; - } - - if ((maxColors < bmpDesc.getColorCount())) - { - maxWidth = bmpDesc.getWidth(); - maxColors = bmpDesc.getColorCount(); - crtDescriptor = i; - } - } - - // if icons is either invalid or contains no data, return the - // default - // RSS icon. - if (crtDescriptor == -1) - { - return null; - } - - selectedIcon = favicon.getDescriptor(crtDescriptor).getImageRGB(); - - // decode ICO as a PNG and return the result - ImageIO.write((BufferedImage) selectedIcon, "PNG", output); - result = output.toByteArray(); - - if (logger.isTraceEnabled()) - logger.trace("Result has " + result.length + " bytes"); - if (logger.isTraceEnabled()) - logger.trace("Icon is " + maxWidth + " px X " + maxWidth + " px @ " - + maxColors + " colors"); - - output.close(); - return result; - } - catch (MalformedURLException murlex) - { - // this shouldn't happen. Ever. - logger.error("Malformed URL " + murlex, murlex); - } - catch (IOException ioex) - { - logger.warn("I/O Error on favicon retrieval. " + ioex.getMessage()); - if (logger.isDebugEnabled()) - logger.debug("I/O Error on favicon retrieval. " + ioex, ioex); - } - catch (Exception ex) - { - logger.warn("Unknown error on favicon retrieval. " + ex + - ". Error for location: " + location, ex); - if (logger.isDebugEnabled()) - logger.debug("", ex); - } - - return null; - } - - /** - * Returns the default icon in case the feed has no favicon on the server. - * Uses the <tt>defaultIconPath</tt> constant to locate the default icon to - * be displayed. - * - * @return binary representation of the default icon. - */ - private byte[] getDefaultRssIcon() - { - if (logger.isTraceEnabled()) - logger.trace("Loading default icon at " + defaultIconId); - - return ProtocolIconRssImpl.getImageInBytes(defaultIconId); - } -} diff --git a/src/net/java/sip/communicator/impl/protocol/rss/MessageRssImpl.java b/src/net/java/sip/communicator/impl/protocol/rss/MessageRssImpl.java deleted file mode 100644 index ab86568..0000000 --- a/src/net/java/sip/communicator/impl/protocol/rss/MessageRssImpl.java +++ /dev/null @@ -1,33 +0,0 @@ -/* - * Jitsi, 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.rss; - -import net.java.sip.communicator.service.protocol.*; - -/** - * Very simple message implementation for the Rss protocol. - * - * @author Emil Ivov - * @author Lubomir Marinov - */ -public class MessageRssImpl - extends AbstractMessage -{ - - /** - * Creates a message instance according to the specified parameters. - * - * @param content the message body - * @param contentType message content type or null for text/plain - * @param contentEncoding message encoding or null for UTF8 - * @param subject the subject of the message or null for no subject. - */ - public MessageRssImpl(String content, String contentType, - String contentEncoding, String subject) - { - super(content, contentType, contentEncoding, subject); - } -} diff --git a/src/net/java/sip/communicator/impl/protocol/rss/OperationSetBasicInstantMessagingRssImpl.java b/src/net/java/sip/communicator/impl/protocol/rss/OperationSetBasicInstantMessagingRssImpl.java deleted file mode 100644 index a05bc72..0000000 --- a/src/net/java/sip/communicator/impl/protocol/rss/OperationSetBasicInstantMessagingRssImpl.java +++ /dev/null @@ -1,481 +0,0 @@ -/* - * Jitsi, 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.rss; - -import java.io.*; -import java.util.*; - -import net.java.sip.communicator.service.gui.*; -import net.java.sip.communicator.service.protocol.*; -import net.java.sip.communicator.service.protocol.event.*; -import net.java.sip.communicator.util.*; - -/** - * Instant messaging functionalities for the RSS protocol. - * - * @author Jean-Albert Vescovo - * @author Mihai Balan - */ -public class OperationSetBasicInstantMessagingRssImpl - extends AbstractOperationSetBasicInstantMessaging - implements RegistrationStateChangeListener -{ - private static final Logger logger - = Logger.getLogger(OperationSetBasicInstantMessagingRssImpl.class); - - /** - * The currently valid persistent presence operation set. - */ - private OperationSetPersistentPresenceRssImpl opSetPersPresence = null; - - /** - * The protocol provider that created us. - */ - private ProtocolProviderServiceRssImpl parentProvider = null; - - /** - * The timer used in order to refresh one or more RSS feeds - */ - private Timer timer = null; - - /** - * The value corresponding to the time in ms - * of the RSS refreshing period (here 5min) - */ - private static final int PERIOD_REFRESH_RSS = 300000; - - /** - * The value corresponding to the time in ms that we wait before the - * initial refresh RSS when starting the application. Ideally this should - * be less than <tt>PERIOD_REFRESH_RSS</tt> but more than a minute in order - * to prevent from overloading the system on startup. - */ - private static final int INITIAL_RSS_LOAD_DELAY = 150000; - - /** - * The localised message that we should show to the user before we remove - * a dead RSS contact - */ - private static final String MSG_CONFIRM_REMOVE_MISSING_CONTACT - = "plugin.rssaccregwizz.CONFIRM_ACCOUNT_REMOVAL"; - - /** - * The title of the confirmation dialog that we show to the user before we - * remove a dead contact - */ - private static final String TITLE_CONFIRM_REMOVE_MISSING_CONTACT - = "plugin.rssaccregwizz.CONFIRM_ACCOUNT_REMOVAL_TITLE"; - - /** - * Creates an instance of this operation set keeping a reference to the - * parent protocol provider and presence operation set. - * - * @param provider The provider instance that creates us. - * @param opSetPersPresence the currently valid - * <tt>OperationSetPersistentPresenceRssImpl</tt> instance. - */ - public OperationSetBasicInstantMessagingRssImpl( - ProtocolProviderServiceRssImpl provider, - OperationSetPersistentPresenceRssImpl opSetPersPresence) - { - this.opSetPersPresence = opSetPersPresence; - this.parentProvider = provider; - - parentProvider.addRegistrationStateChangeListener(this); - if(parentProvider.isRegistered()) - { - createTimer(); - } - } - - /** - * Create a Message instance for sending a simple text messages with default - * (text/html) content type and encoding. - * - * @param messageText the string content of the message. - * @return Message the newly created message - */ - @Override - public Message createMessage(String messageText) - { - return createMessage(messageText, HTML_MIME_TYPE, - DEFAULT_MIME_ENCODING, null); - } - - @Override - public Message createMessage(String content, String contentType, - String encoding, String subject) - { - return new MessageRssImpl(content, contentType, encoding, subject); - } - - /** - * Updates the RSS feed associated with rssContact. If the update has been - * requested by the user the method would fire a message received event - * even if there are no new items. - * - * @param rssContact the <tt>contact</tt> to send query to. - * @param userRequestedUpdate indicates whether the query is triggered by - * the user or by a scheduled timer task. - */ - private void submitRssQuery(ContactRssImpl rssContact, - boolean userRequestedUpdate) - { - String newDisplayName; - String oldDisplayName; - String news; - - RssFeedReader rssFeed = rssContact.getRssFeedReader(); - - try - { - //we create the message containing the new items retrieved - news = rssFeed.getNewFeeds(); - - //if the contact was offline then switch it to online since - //apparently we succeeded to retrieve its flow - if(rssContact.getPresenceStatus() == RssStatusEnum.OFFLINE) - { - getParentProvider().getOperationSetPresence() - .changePresenceStatusForContact( - rssContact, RssStatusEnum.ONLINE); - - } - } - catch (FileNotFoundException ex) - { - //RSS flow no longer exists - ask user to remove; - handleFileNotFoundException(rssContact, ex); - - logger.warn("RSS flow no longer exists. Error was: " - + ex.getMessage()); - if (logger.isDebugEnabled()) - logger.debug(ex); - return; - } - catch (OperationFailedException ex) - { - logger.error("Failed to retrieve RSS flow. Error was: " - + ex.getMessage() - , ex); - return; - } - - if(news != null) - { - //we recover the feed's old name - oldDisplayName = rssContact.getDisplayName(); - newDisplayName = rssFeed.getTitle(); - rssContact.setDisplayName(newDisplayName); - - //We have a new date or a new name on this feed/contact, we fire - //that the contact has his properties modified in order to save it - this.opSetPersPresence.fireContactPropertyChangeEvent( - ContactPropertyChangeEvent. - PROPERTY_DISPLAY_NAME, - rssContact, - oldDisplayName, - newDisplayName); - - //The feed has been updated or if the user made a request on a - //specific feed/contact, we fire a new message containing the new items - //to the user - fireMessageEvent( - new MessageReceivedEvent( - createMessage(news), - rssContact, - new Date())); - } - else if(userRequestedUpdate) - { - news = rssFeed.getNoNewFeedString(); - fireMessageEvent( - new MessageReceivedEvent( - createMessage(news), - rssContact, - new Date())); - } - } - - /** - * Refreshes all the registered feeds. - */ - public void refreshAllRssFeeds() - { - Vector<ContactRssImpl> rssContactList = new Vector<ContactRssImpl>(); - opSetPersPresence.getContactListRoot().getRssURLList(rssContactList); - - for (ContactRssImpl contact : rssContactList) - { - try - { - submitRssQuery(contact, false); - } - catch (Exception ex) - { - logger.error("Failed to refresh feed for " + contact, ex); - } - } - } - - /** - * Refreshes a specific RSS feed. - * - * @param rssURL the <tt>contact</tt> (feed) to be refreshed. - */ - public void refreshRssFeed( ContactRssImpl rssURL) - { - submitRssQuery(rssURL, true); - } - - /** - * Creates the timer for refreshing RSS feeds. - */ - public void createTimer() - { - if (timer != null ) - return; - - if (logger.isTraceEnabled()) - logger.trace("Creating rss timer and task."); - RssTimerRefreshFeed refresh = new RssTimerRefreshFeed(this); - this.timer = new Timer(); - this.timer.scheduleAtFixedRate(refresh, - INITIAL_RSS_LOAD_DELAY, - PERIOD_REFRESH_RSS); - - if (logger.isTraceEnabled()) - logger.trace("Done."); - } - - /** - * Cancels the timer if the user switched to the OFFLINE status. - */ - public void stopTimer(){ - this.timer.cancel(); - } - - /** - * Retrieves the feeds for a new RSS feed just added as persistent contact. - * - * @param contact the <tt>Contact</tt> added - */ - public void threadedContactFeedUpdate(ContactRssImpl contact) - { - RssThread rssThr = new RssThread(this, contact); - rssThr.start(); - } - - /** - * Sends the <tt>message</tt> to the destination indicated by the - * <tt>to</tt> contact. - * - * @param to the <tt>Contact</tt> to send <tt>message</tt> to - * @param message the <tt>Message</tt> to send. - * @throws IllegalStateException if the underlying ICQ stack is not - * registered and initialized. - * @throws IllegalArgumentException if <tt>to</tt> is not an instance - * belonging to the underlying implementation. - */ - public void sendInstantMessage(Contact to, Message message) - throws IllegalStateException, - IllegalArgumentException - { - if( !(to instanceof ContactRssImpl) ) - throw new IllegalArgumentException( - "The specified contact is not a Rss contact." - + to); - - if( to.isPersistent() && - to.getPresenceStatus().equals(RssStatusEnum.OFFLINE)) - { - MessageDeliveryFailedEvent evt = - new MessageDeliveryFailedEvent( - message, - to, - MessageDeliveryFailedEvent.OFFLINE_MESSAGES_NOT_SUPPORTED); - fireMessageEvent(evt); - return; - } - - //refresh the present rssFeed "to" - Message msg = new MessageRssImpl("Refreshing feed...", - DEFAULT_MIME_TYPE, DEFAULT_MIME_ENCODING, null); - - fireMessageEvent( - new MessageDeliveredEvent(msg, to, new Date())); - - threadedContactFeedUpdate((ContactRssImpl)to); - } - - /** - * Determines whether the protocol provider (or the protocol itself) supports - * sending and receiving offline messages. Most often this method would - * return true for protocols that support offline messages and false for - * those that don't. It is however possible for a protocol to support these - * messages and yet have a particular account that does not (i.e. feature - * not enabled on the protocol server). In cases like this it is possible - * for this method to return true even when offline messaging is not - * supported, and then have the sendMessage method throw an - * OperationFailedException with code - OFFLINE_MESSAGES_NOT_SUPPORTED. - * - * @return <tt>true</tt> if the protocol supports offline messages and - * <tt>false</tt> otherwise. - */ - public boolean isOfflineMessagingSupported() - { - return false; - } - - /** - * Determines whether the protocol supports the supplied content type. - * - * @param contentType the type we want to check - * @return <tt>true</tt> if the protocol supports it and - * <tt>false</tt> otherwise. - */ - public boolean isContentTypeSupported(String contentType) - { - if(contentType.equals(DEFAULT_MIME_TYPE)) - return true; - else if(contentType.equals(HTML_MIME_TYPE)) - return true; - else - return false; - } - - /** - * Returns the protocol provider that this operation set belongs to. - * - * @return a reference to the <tt>ProtocolProviderServiceRssImpl</tt> - * instance that this operation set belongs to. - */ - public ProtocolProviderServiceRssImpl getParentProvider() - { - return this.parentProvider; - } - - /** - * Returns a reference to the presence operation set instance used by our - * source provider. - * - * @return a reference to the <tt>OperationSetPersistentPresenceRssImpl</tt> - * instance used by this provider. - */ - public OperationSetPersistentPresenceRssImpl getOpSetPersPresence() - { - return this.opSetPersPresence; - } - - /** - * The method is called by the ProtocolProvider whenever a change in the - * registration state of the corresponding provider has occurred. We use - * it to start and stop the timer that periodically checks for RSS updates. - * - * @param evt ProviderStatusChangeEvent the event describing the status - * change. - */ - public void registrationStateChanged(RegistrationStateChangeEvent evt) - { - if (evt.getNewState().equals(RegistrationState.REGISTERED)) - { - if (timer == null) - { - createTimer(); - } - } - else if(timer != null) - { - timer.cancel(); - timer = null; - } - } - - /** - * Queries the user as to whether or not the specified contact should be - * removed and removes it if necessary. - * - * @param contact the contact that has caused the - * <tt>FileNotFoundException</tt> and that we should probably remove. - * @param ex the <tt>FileNotFoundException</tt> - * that is causing all the commotion. - */ - private void handleFileNotFoundException(ContactRssImpl contact, - FileNotFoundException ex) - { - new FileNotFoundExceptionHandler(contact).start(); - } - - /** - * A thread that queries the user as to whether or not the specified - * contact should be removed and removes it if necessary. - */ - private class FileNotFoundExceptionHandler extends Thread - { - private ContactRssImpl contact = null; - - /** - * Creates a FileNotFoundExceptionHandler for the specified contact. - * - * @param contact the contact that has caused the - * <tt>FileNotFoundException</tt> and that we should probably remove. - */ - public FileNotFoundExceptionHandler(ContactRssImpl contact) - { - setName(FileNotFoundExceptionHandler.class.getName()); - - this.contact = contact; - } - - /** - * Queries the user as to whether or not the specified - * contact should be removed and removes it if necessary. - */ - @Override - public void run() - { - //do not bother the user with offline contacts - if (contact.getPresenceStatus() == RssStatusEnum.OFFLINE) - { - return; - } - - UIService uiService = RssActivator.getUIService(); - String title = RssActivator.getResources() - .getI18NString(TITLE_CONFIRM_REMOVE_MISSING_CONTACT); - String message = RssActivator.getResources() - .getI18NString(MSG_CONFIRM_REMOVE_MISSING_CONTACT, - new String[]{contact.getAddress()}); - - //switch the contact to an offline state so that we don't ask - //the user what to do about it any more. - getParentProvider().getOperationSetPresence() - .changePresenceStatusForContact(contact, - RssStatusEnum.OFFLINE); - - int result = uiService.getPopupDialog() - .showConfirmPopupDialog(message, - title, - PopupDialog.YES_NO_OPTION); - - if (result == PopupDialog.YES_OPTION) - { - //remove contact - try - { - getParentProvider().getOperationSetPresence() - .unsubscribe(contact); - } - catch (OperationFailedException exc) - { - if (logger.isInfoEnabled()) - logger.info("We could not remove a dead contact", exc); - } - } - } - } -} diff --git a/src/net/java/sip/communicator/impl/protocol/rss/OperationSetPersistentPresenceRssImpl.java b/src/net/java/sip/communicator/impl/protocol/rss/OperationSetPersistentPresenceRssImpl.java deleted file mode 100644 index 559c0e8..0000000 --- a/src/net/java/sip/communicator/impl/protocol/rss/OperationSetPersistentPresenceRssImpl.java +++ /dev/null @@ -1,862 +0,0 @@ -/* - * Jitsi, 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.rss; - -import java.io.*; -import java.net.*; -import java.util.*; - -import net.java.sip.communicator.service.protocol.*; -import net.java.sip.communicator.service.protocol.event.*; -import net.java.sip.communicator.util.*; - -/** - * A RSS implementation of a persistent presence operation set. In order - * to simulate server persistence, this operation set would simply accept all - * unresolved contacts and resolve them immediately. A real world protocol - * implementation would save it on a server using methods provided by the - * protocol stack. - * - * @author Jean-Albert Vescovo - * @author Emil Ivov - */ -public class OperationSetPersistentPresenceRssImpl - extends AbstractOperationSetPersistentPresence<ProtocolProviderServiceRssImpl> -{ - private static final Logger logger = - Logger.getLogger(OperationSetPersistentPresenceRssImpl.class); - - /** - * The root of the RSS contact list. - */ - private ContactGroupRssImpl contactListRoot = null; - - /** - * The currently active status message. - */ - private String statusMessage = "Default Status Message"; - - /** - * Our default presence status. - */ - private PresenceStatus presenceStatus = RssStatusEnum.OFFLINE; - - /** - * The <tt>AuthorizationHandler</tt> instance that we'd have to transmit - * authorization requests to for approval. - */ - private AuthorizationHandler authorizationHandler = null; - - /** - * The image retriever that we use to retrieve rss contacts - */ - private ImageRetriever imageRetriever = null; - - /** - * Creates an instance of this operation set keeping a reference to the - * specified parent <tt>provider</tt>. - * @param provider the ProtocolProviderServiceRssImpl instance that - * created us. - */ - public OperationSetPersistentPresenceRssImpl( - ProtocolProviderServiceRssImpl provider) - { - super(provider); - - contactListRoot = new ContactGroupRssImpl("RootGroup", provider); - - // add our un-registration listener - parentProvider.addRegistrationStateChangeListener( - new UnregistrationListener()); - - imageRetriever = new ImageRetriever(this); - - imageRetriever.start(); - } - - /* - * Overrides - * AbstractOperationSetPersistentPresence#fireProviderStatusChangeEvent - * (PresenceStatus) to stop the firing of an event. - */ - @Override - protected void fireProviderStatusChangeEvent(PresenceStatus oldValue) - { - // Override the super implementation and stop the firing of an event. - } - - /** - * Creates a group with the specified name and parent in the server - * stored contact list. - * - * @param parent the group where the new group should be created - * @param groupName the name of the new group to create. - */ - public void createServerStoredContactGroup(ContactGroup parent, - String groupName) - { - ContactGroupRssImpl newGroup - = new ContactGroupRssImpl(groupName, parentProvider); - - ((ContactGroupRssImpl)parent).addSubgroup(newGroup); - - this.fireServerStoredGroupEvent( - newGroup, ServerStoredGroupEvent.GROUP_CREATED_EVENT); - } - - /** - * A RSS Provider method to use for fast filling of a contact list. - * - * @param contactGroup the group to add - */ - public void addRssGroup(ContactGroupRssImpl contactGroup) - { - contactListRoot.addSubgroup(contactGroup); - } - - /** - * A RSS Provider method to use for fast filling of a contact list. - * This method would add both the group and fire an event. - * - * @param parent the group where <tt>contactGroup</tt> should be added. - * @param contactGroup the group to add - */ - public void addRssGroupAndFireEvent( - ContactGroupRssImpl parent - , ContactGroupRssImpl contactGroup) - { - parent.addSubgroup(contactGroup); - - this.fireServerStoredGroupEvent( - contactGroup, ServerStoredGroupEvent.GROUP_CREATED_EVENT); - } - - - /** - * Returns a reference to the contact with the specified ID in case we - * have a subscription for it and null otherwise/ - * - * @param contactID a String identifier of the contact which we're - * seeking a reference of. - * @return a reference to the Contact with the specified - * <tt>contactID</tt> or null if we don't have a subscription for the - * that identifier. - */ - public Contact findContactByID(String contactID) - { - return contactListRoot.findContactByID(contactID); - } - - /** - * Sets the specified status message. - * @param statusMessage a String containing the new status message. - */ - public void setStatusMessage(String statusMessage) - { - this.statusMessage = statusMessage; - } - - /** - * Returns the status message that was last set through - * setCurrentStatusMessage. - * - * @return the last status message that we have requested and the aim - * server has confirmed. - */ - public String getCurrentStatusMessage() - { - return statusMessage; - } - - /** - * Returns the protocol specific contact instance representing the local - * user. - * - * @return the Contact (address, phone number, or uin) that the Provider - * implementation is communicating on behalf of. - */ - public Contact getLocalContact() - { - return null; - } - - /** - * Returns a PresenceStatus instance representing the state this provider - * is currently in. - * - * @return the PresenceStatus last published by this provider. - */ - public PresenceStatus getPresenceStatus() - { - return presenceStatus; - } - - /** - * Returns the root group of the server stored contact list. - * - * @return the root ContactGroup for the ContactList stored by this - * service. - */ - public ContactGroup getServerStoredContactListRoot() - { - return contactListRoot; - } - - /** - * Returns the set of PresenceStatus objects that a user of this service - * may request the provider to enter. - * - * @return Iterator a PresenceStatus array containing "enterable" status - * instances. - */ - public Iterator<PresenceStatus> getSupportedStatusSet() - { - return RssStatusEnum.supportedStatusSet(); - } - - /*** - * Return the <tt>ContactGroup</tt> that represents the root of the contacts - * list. - * @return ContactGroupRssImpl representing the root of the contacts list. - */ - public ContactGroupRssImpl getContactListRoot() - { - return this.contactListRoot; - } - - /** - * Removes the specified contact from its current parent and places it - * under <tt>newParent</tt>. - * - * @param contactToMove the <tt>Contact</tt> to move - * @param newParent the <tt>ContactGroup</tt> where <tt>Contact</tt> - * would be placed. - */ - public void moveContactToGroup(Contact contactToMove, - ContactGroup newParent) - { - ContactRssImpl rssContact - = (ContactRssImpl)contactToMove; - - ContactGroupRssImpl parentRssGroup - = findContactParent(rssContact); - - parentRssGroup.removeContact(rssContact); - - //if this is a volatile contact then we haven't really subscribed to - //them so we'd need to do so here - if(!rssContact.isPersistent()) - { - //first tell everyone that the volatile contact was removed - fireSubscriptionEvent(rssContact - , parentRssGroup - , SubscriptionEvent.SUBSCRIPTION_REMOVED); - - try - { - //now subscribe - this.subscribe(newParent, contactToMove.getAddress()); - - //now tell everyone that we've added the contact - fireSubscriptionEvent(rssContact - , newParent - , SubscriptionEvent.SUBSCRIPTION_CREATED); - } - catch (Exception ex) - { - logger.error("Failed to move contact " - + rssContact.getAddress() - , ex); - } - } - else - { - ( (ContactGroupRssImpl) newParent) - .addContact(rssContact); - - fireSubscriptionMovedEvent(contactToMove - , parentRssGroup - , newParent); - } - } - - /** - * Requests the provider to enter into a status corresponding to the - * specified parameters. - * - * @param status the PresenceStatus as returned by - * getRequestableStatusSet - * @param statusMessage the message that should be set as the reason to - * enter that status - * @throws IllegalArgumentException if the status requested is not a - * valid PresenceStatus supported by this provider. - * @throws IllegalStateException if the provider is not currently - * registered. - * @throws OperationFailedException with code NETWORK_FAILURE if - * publishing the status fails due to a network error. - */ - public void publishPresenceStatus(PresenceStatus status, - String statusMessage) throws - IllegalArgumentException, IllegalStateException, - OperationFailedException - { - PresenceStatus oldPresenceStatus = this.presenceStatus; - this.presenceStatus = status; - this.statusMessage = statusMessage; - - this.fireProviderStatusChangeEvent(oldPresenceStatus); - - //since we are not a real protocol, we set the contact presence status - //ourselves and make them have the same status as ours. - changePresenceStatusForAllContacts( getServerStoredContactListRoot() - , getPresenceStatus()); - } - - - - /** - * Get the PresenceStatus for a particular contact. - * - * @param contactIdentifier the identifier of the contact whose status - * we're interested in. - * @return PresenceStatus the <tt>PresenceStatus</tt> of the specified - * <tt>contact</tt> - * @throws IllegalArgumentException if <tt>contact</tt> is not a contact - * known to the underlying protocol provider - * @throws IllegalStateException if the underlying protocol provider is - * not registered/signed on a public service. - * @throws OperationFailedException with code NETWORK_FAILURE if - * retrieving the status fails due to errors experienced during - * network communication - */ - public PresenceStatus queryContactStatus(String contactIdentifier) throws - IllegalArgumentException, IllegalStateException, - OperationFailedException - { - return findContactByID(contactIdentifier).getPresenceStatus(); - } - - /** - * Sets the presence status of <tt>contact</tt> to <tt>newStatus</tt>. - * - * @param contact the <tt>ContactRssImpl</tt> whose status we'd like - * to set. - * @param newStatus the new status we'd like to set to <tt>contact</tt>. - */ - public void changePresenceStatusForContact( - ContactRssImpl contact - , PresenceStatus newStatus) - { - PresenceStatus oldStatus = contact.getPresenceStatus(); - contact.setPresenceStatus(newStatus); - - fireContactPresenceStatusChangeEvent( - contact, findContactParent(contact), oldStatus); - } - - /** - * Sets the presence status of all <tt>contact</tt>s in our contact list - * (except those that correspond to another provider registered with SC) - * to <tt>newStatus</tt>. - * - * @param newStatus the new status we'd like to set to <tt>contact</tt>. - * @param parent the group in which we'd have to update the status of all - * direct and indirect child contacts. - */ - private void changePresenceStatusForAllContacts(ContactGroup parent, - PresenceStatus newStatus) - { - //first set the status for contacts in this group - Iterator<Contact> childContacts = parent.contacts(); - - while(childContacts.hasNext()) - { - ContactRssImpl contact - = (ContactRssImpl)childContacts.next(); - - PresenceStatus oldStatus = contact.getPresenceStatus(); - contact.setPresenceStatus(newStatus); - - fireContactPresenceStatusChangeEvent( - contact, parent, oldStatus); - } - - //now call this method recursively for all subgroups - Iterator<ContactGroup> subgroups = parent.subgroups(); - - while(subgroups.hasNext()) - { - ContactGroup subgroup = subgroups.next(); - changePresenceStatusForAllContacts(subgroup, newStatus); - } - } - - /** - * Returns the group that is parent of the specified rssGroup or null - * if no parent was found. - * @param rssGroup the group whose parent we're looking for. - * @return the ContactGroupRssImpl instance that rssGroup - * belongs to or null if no parent was found. - */ - public ContactGroupRssImpl findGroupParent(ContactGroupRssImpl rssGroup) - { - return contactListRoot.findGroupParent(rssGroup); - } - - /** - * Returns the group that is parent of the specified rssContact or - * null if no parent was found. - * @param rssContact the contact whose parent we're looking for. - * @return the ContactGroupRssImpl instance that rssContact - * belongs to or null if no parent was found. - */ - public ContactGroupRssImpl findContactParent( - ContactRssImpl rssContact) - { - return (ContactGroupRssImpl)rssContact.getParentContactGroup(); - } - - /** - * Removes the specified group from the server stored contact list. - * - * @param group the group to remove. - * - * @throws IllegalArgumentException if <tt>group</tt> was not found in this - * protocol's contact list. - */ - public void removeServerStoredContactGroup(ContactGroup group) - throws IllegalArgumentException - { - ContactGroupRssImpl rssGroup = (ContactGroupRssImpl)group; - - ContactGroupRssImpl parent = findGroupParent(rssGroup); - - if(parent == null){ - throw new IllegalArgumentException( - "group " + group - + " does not seem to belong to this protocol's contact list."); - } - - parent.removeSubGroup(rssGroup); - - this.fireServerStoredGroupEvent( - rssGroup, ServerStoredGroupEvent.GROUP_REMOVED_EVENT); - } - - /** - * Renames the specified group from the server stored contact list. - * - * @param group the group to rename. - * @param newName the new name of the group. - */ - public void renameServerStoredContactGroup(ContactGroup group, - String newName) - { - ((ContactGroupRssImpl)group).setGroupName(newName); - - this.fireServerStoredGroupEvent( - group, - ServerStoredGroupEvent.GROUP_RENAMED_EVENT); - } - - /** - * Handler for incoming authorization requests. - * - * @param handler an instance of an AuthorizationHandler for - * authorization requests coming from other users requesting - * permission add us to their contact list. - */ - - public void setAuthorizationHandler(AuthorizationHandler handler) - { - this.authorizationHandler = handler; - } - - - /** - * Persistently adds a subscription for the presence status of the - * contact corresponding to the specified contactIdentifier and indicates - * that it should be added to the specified group of the server stored - * contact list. - * - * @param parent the parent group of the server stored contact list - * where the contact should be added. <p> - * @param contactIdentifier the contact whose status updates we are - * subscribing for. - * @throws IllegalArgumentException if <tt>contact</tt> or - * <tt>parent</tt> are not a contact known to the underlying protocol - * provider. - * @throws IllegalStateException if the underlying protocol provider is - * not registered/signed on a public service. - * @throws OperationFailedException with code NETWORK_FAILURE if - * subscribing fails due to errors experienced during network - * communication - */ - public void subscribe(ContactGroup parent, String contactIdentifier) - throws IllegalArgumentException, - IllegalStateException, - OperationFailedException - { - URL rssURL = null; - - String contactIdentifierURL = contactIdentifier; - // in order to allow adding of URIs like feed://a.host.com/feed.xml - // or like feed:https://a.host.com/feed.xml - if (contactIdentifierURL.startsWith("feed:https")) - { - contactIdentifierURL = contactIdentifierURL - .replaceFirst("feed:https", "https"); - } - else if (contactIdentifierURL.startsWith("feed")) - { - contactIdentifierURL = contactIdentifierURL - .replaceFirst("feed", "http"); - } - - if(findContactByID(contactIdentifier) != null) - { - if (logger.isDebugEnabled()) - logger.debug( - "contact with same id already exists - " + contactIdentifier); - return; - } - - try - { - rssURL = new URL(contactIdentifierURL); - } - catch (MalformedURLException ex) - { - throw new IllegalArgumentException( - "failed to create a URL for address " - + contactIdentifier - + ". Error was: " - + ex.getMessage()); - } - - //we instantiate a new RssFeedReader which will contain the feed - //associated with the contact. It is important to try and connect here - //in order to report failure if there is a problem with the feed. - //RssFeedReader rssFeedReader = new RssFeedReader(rssURL); - - //we parse the feed/contact here so that we could be notified of any - //failures - try - { - ContactRssImpl contact = new ContactRssImpl( - contactIdentifier, - rssURL, - null, - parentProvider); - ((ContactGroupRssImpl)parent).addContact(contact); - - - fireSubscriptionEvent(contact, - parent, - SubscriptionEvent.SUBSCRIPTION_CREATED); - - //since we are not a real protocol, we set the contact - //presence status ourselves - changePresenceStatusForContact(contact, getPresenceStatus()); - - //now update the flow for the first time. - parentProvider.getBasicInstantMessaging() - .threadedContactFeedUpdate(contact); - } - catch(FileNotFoundException ex) - { - //means the feed is no longer there. - //ignore and subscribe the contact so that the exception would - //occur while we try to refresh it. This way we would ask the - //user whether they want it removed. - if (logger.isDebugEnabled()) - logger.debug("failed to create a URL for address " - + contactIdentifier - + ". Error was: " - + ex.getMessage() - , ex); - } - } - - - /** - * Adds a subscription for the presence status of the contact - * corresponding to the specified contactIdentifier. - * - * @param contactIdentifier the identifier of the contact whose status - * updates we are subscribing for. <p> - * @throws IllegalArgumentException if <tt>contact</tt> is not a contact - * known to the underlying protocol provider - * @throws IllegalStateException if the underlying protocol provider is - * not registered/signed on a public service. - * @throws OperationFailedException with code NETWORK_FAILURE if - * subscribing fails due to errors experienced during network - * communication - */ - public void subscribe(String contactIdentifier) throws - IllegalArgumentException, IllegalStateException, - OperationFailedException - { - subscribe(contactListRoot, contactIdentifier); - } - - /** - * Removes a subscription for the presence status of the specified - * contact. - * - * @param contact the contact whose status updates we are unsubscribing - * from. - * @throws IllegalArgumentException if <tt>contact</tt> is not a contact - * known to the underlying protocol provider - * @throws IllegalStateException if the underlying protocol provider is - * not registered/signed on a public service. - * @throws OperationFailedException with code NETWORK_FAILURE if - * unsubscribing fails due to errors experienced during network - * communication - */ - public void unsubscribe(Contact contact) throws IllegalArgumentException, - IllegalStateException, OperationFailedException - { - ContactGroupRssImpl parentGroup - = (ContactGroupRssImpl)((ContactRssImpl)contact) - .getParentContactGroup(); - - parentGroup.removeContact((ContactRssImpl)contact); - - fireSubscriptionEvent(contact, - ((ContactRssImpl)contact).getParentContactGroup(), - SubscriptionEvent.SUBSCRIPTION_REMOVED); - } - - /** - * Creates and returns a unresolved contact from the specified - * <tt>address</tt> and <tt>persistentData</tt>. The method will not try - * to establish a network connection and resolve the newly created Contact - * against the server. The protocol provider may will later try and resolve - * the contact. When this happens the corresponding event would notify - * interested subscription listeners. - * - * @param address an identifier of the contact that we'll be creating. - * @param persistentData a String returned Contact's getPersistentData() - * method during a previous run and that has been persistently stored - * locally. - * @return the unresolved <tt>Contact</tt> created from the specified - * <tt>address</tt> and <tt>persistentData</tt> - */ - public Contact createUnresolvedContact(String address, - String persistentData) - { - return createUnresolvedContact( address, - persistentData, - getServerStoredContactListRoot()); - } - - /** - * Creates and returns a unresolved contact from the specified - * <tt>address</tt> and <tt>persistentData</tt>. The method will not try - * to establish a network connection and resolve the newly created Contact - * against the server. The protocol provider may will later try and resolve - * the contact. When this happens the corresponding event would notify - * interested subscription listeners. - * - * @param address an identifier of the contact that we'll be creating. - * @param persistentData a String returned Contact's getPersistentData() - * method during a previous run and that has been persistently stored - * locally. - * @param parent the group where the unresolved contact is - * supposed to belong to. - * - * @return the unresolved <tt>Contact</tt> created from the specified - * <tt>address</tt> and <tt>persistentData</tt> - * @throws IllegalArgumentException if the status requested is not a - * valid PresenceStatus supported by this provider. - */ - public Contact createUnresolvedContact(String address, - String persistentData, - ContactGroup parent) - throws IllegalArgumentException - { - URL rssURL = null; - - String contactIdentifierURL = address; - // in order to allow adding of URIs like feed://a.host.com/feed.xml - // or like feed:https://a.host.com/feed.xml - if (contactIdentifierURL.startsWith("feed:https")) - { - contactIdentifierURL = contactIdentifierURL - .replaceFirst("feed:https", "https"); - } - else if (contactIdentifierURL.startsWith("feed")) - { - contactIdentifierURL = contactIdentifierURL - .replaceFirst("feed", "http"); - } - - try - { - rssURL = new URL(contactIdentifierURL); - } - catch (MalformedURLException ex) - { - throw new IllegalArgumentException( - "failed to create a URL for address " - + address - + ". Error was: " - + ex.getMessage()); - } - - try - { - ContactRssImpl contact = new ContactRssImpl( - address, - rssURL, - persistentData, - parentProvider); - contact.setResolved(false); - - ( (ContactGroupRssImpl) parent).addContact(contact); - - fireSubscriptionEvent(contact, - parent, - SubscriptionEvent.SUBSCRIPTION_CREATED); - - //since we don't have any server, we'll simply resolve the contact - //ourselves as if we've just received an event from the server telling - //us that it has been resolved. - contact.setResolved(true); - fireSubscriptionEvent( - contact, parent, SubscriptionEvent.SUBSCRIPTION_RESOLVED); - - //since we are not a real protocol, we set the contact presence status - //ourselves - changePresenceStatusForContact( contact, getPresenceStatus()); - - //we retrieve if exists the persistent data for this contact - //which represents the date of the last item seen by the user - //contact.setPersistentData(persistentData); - - //hack: make sure we launch the image cache thread here because - //the meta cl service isn't listening for contact_resolved events yet. - contact.getImage(); - - return contact; - } - catch(FileNotFoundException ex) - { - //means the feed is no longer there. - //ignore and subscribe the contact so that the exception would - //occur while we try to refresh it. This way we would ask the - //user whether they want it removed. - if (logger.isDebugEnabled()) - logger.debug("failed to create a URL for address " - + rssURL - + ". Error was: " - + ex.getMessage() - , ex); - } - catch(OperationFailedException ex) - { - if (logger.isDebugEnabled()) - logger.debug("failed to create a URL for address " - + rssURL - + ". Error was: " - + ex.getMessage() - , ex); - } - return null; - } - - /** - * Creates and returns a unresolved contact group from the specified - * <tt>address</tt> and <tt>persistentData</tt>. The method will not try - * to establish a network connection and resolve the newly created - * <tt>ContactGroup</tt> against the server or the contact itself. The - * protocol provider will later resolve the contact group. When this happens - * the corresponding event would notify interested subscription listeners. - * - * @param groupUID an identifier, returned by ContactGroup's getGroupUID, - * that the protocol provider may use in order to create the group. - * @param persistentData a String returned ContactGroups's - * getPersistentData() method during a previous run and that has been - * persistently stored locally. - * @param parentGroup the group under which the new group is to be created - * or null if this is group directly underneath the root. - * @return the unresolved <tt>ContactGroup</tt> created from the specified - * <tt>UID</tt> and <tt>persistentData</tt> - */ - public ContactGroup createUnresolvedContactGroup(String groupUID, - String persistentData, ContactGroup parentGroup) - { - ContactGroupRssImpl newGroup - = new ContactGroupRssImpl( - ContactGroupRssImpl.createNameFromUID(groupUID) - , parentProvider); - newGroup.setResolved(true); - - //if parent is null then we're adding under root. - if(parentGroup == null) - parentGroup = getServerStoredContactListRoot(); - - ((ContactGroupRssImpl)parentGroup).addSubgroup(newGroup); - - this.fireServerStoredGroupEvent( - newGroup, ServerStoredGroupEvent.GROUP_CREATED_EVENT); - - return newGroup; - } - - private class UnregistrationListener - implements RegistrationStateChangeListener - { - /** - * The method is called by a ProtocolProvider implementation whenever - * a change in the registration state of the corresponding provider had - * occurred. The method is particularly interested in events stating - * that the RSS provider has unregistered so that it would fire - * status change events for all contacts in our buddy list. - * - * @param evt ProviderStatusChangeEvent the event describing the status - * change. - */ - public void registrationStateChanged(RegistrationStateChangeEvent evt) - { - if(evt.getNewState() == RegistrationState.REGISTERED) - { - if(presenceStatus != RssStatusEnum.ONLINE) - { - presenceStatus = RssStatusEnum.ONLINE; - changePresenceStatusForAllContacts( - contactListRoot, presenceStatus); - } - } - else if(evt.getNewState() == RegistrationState.UNREGISTERED - || evt.getNewState() == RegistrationState.AUTHENTICATION_FAILED - || evt.getNewState() == RegistrationState.CONNECTION_FAILED) - { - if(presenceStatus != RssStatusEnum.OFFLINE) - { - presenceStatus = RssStatusEnum.OFFLINE; - changePresenceStatusForAllContacts( - contactListRoot, presenceStatus); - } - } - - } - } - - /** - * Returns the image retriever that we are using in this opset to retrieve - * avatars (favicons) for our icons. - * - * @return the <tt>ImageRetriever</tt> that we use to retrieve favicons for - * our rss contacts. - */ - public ImageRetriever getImageRetriever() - { - return imageRetriever; - } -} diff --git a/src/net/java/sip/communicator/impl/protocol/rss/ProtocolIconRssImpl.java b/src/net/java/sip/communicator/impl/protocol/rss/ProtocolIconRssImpl.java deleted file mode 100644 index 0c08ce9..0000000 --- a/src/net/java/sip/communicator/impl/protocol/rss/ProtocolIconRssImpl.java +++ /dev/null @@ -1,165 +0,0 @@ -/* - * Jitsi, 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.rss; - -import java.io.*; -import java.util.*; - -import net.java.sip.communicator.service.protocol.*; -import net.java.sip.communicator.util.*; - -import org.jitsi.service.resources.*; -import org.osgi.framework.*; - -/** - * Represents the Rss protocol icon. Implements the <tt>ProtocolIcon</tt> - * interface in order to provide a Rss logo image in two different sizes. - * - * @author Yana Stamcheva - */ -public class ProtocolIconRssImpl - implements ProtocolIcon -{ - private static Logger logger - = Logger.getLogger(ProtocolIconRssImpl.class); - - private static ResourceManagementService resourcesService; - - /** - * A hash table containing the protocol icon in different sizes. - */ - private static Hashtable<String, byte[]> iconsTable - = new Hashtable<String, byte[]>(); - static - { - iconsTable.put(ProtocolIcon.ICON_SIZE_16x16, - getImageInBytes("service.protocol.rss.RSS_16x16")); - - iconsTable.put(ProtocolIcon.ICON_SIZE_32x32, - getImageInBytes("service.protocol.rss.RSS_32x32")); - - iconsTable.put(ProtocolIcon.ICON_SIZE_48x48, - getImageInBytes("service.protocol.rss.RSS_48x48")); - - iconsTable.put(ProtocolIcon.ICON_SIZE_64x64, - getImageInBytes("service.protocol.rss.RSS_64x64")); - } - - /** - * A hash table containing the path to the protocol icon in different sizes. - */ - private static Hashtable<String, String> iconPathsTable - = new Hashtable<String, String>(); - static - { - iconPathsTable.put(ProtocolIcon.ICON_SIZE_16x16, - getResources().getImagePath("service.protocol.rss.RSS_16x16")); - - iconPathsTable.put(ProtocolIcon.ICON_SIZE_32x32, - getResources().getImagePath("service.protocol.rss.RSS_32x32")); - - iconPathsTable.put(ProtocolIcon.ICON_SIZE_48x48, - getResources().getImagePath("service.protocol.rss.RSS_48x48")); - - iconPathsTable.put(ProtocolIcon.ICON_SIZE_64x64, - getResources().getImagePath("service.protocol.rss.RSS_64x64")); - } - - /** - * Implements the <tt>ProtocolIcon.getSupportedSizes()</tt> method. Returns - * an iterator to a set containing the supported icon sizes. - * @return an iterator to a set containing the supported icon sizes - */ - public Iterator<String> getSupportedSizes() - { - return iconsTable.keySet().iterator(); - } - - /** - * Returns TRUE if a icon with the given size is supported, FALSE-otherwise. - */ - public boolean isSizeSupported(String iconSize) - { - return iconsTable.containsKey(iconSize); - } - - /** - * Returns the icon image in the given size. - * @param iconSize the icon size; one of ICON_SIZE_XXX constants - */ - public byte[] getIcon(String iconSize) - { - return iconsTable.get(iconSize); - } - - /** - * Returns a path to the icon with the given size. - * @param iconSize the size of the icon we're looking for - * @return the path to the icon with the given size - */ - public String getIconPath(String iconSize) - { - return iconPathsTable.get(iconSize); - } - - /** - * Returns the icon image used to represent the protocol connecting state. - * @return the icon image used to represent the protocol connecting state - */ - public byte[] getConnectingIcon() - { - return getImageInBytes("protocolIconRss"); - } - - /** - * Returns the byte representation of the image corresponding to the given - * identifier. - * - * @param imageID the identifier of the image - * @return the byte representation of the image corresponding to the given - * identifier. - */ - public static byte[] getImageInBytes(String imageID) - { - InputStream in = getResources(). - getImageInputStream(imageID); - - if (in == null) - return null; - byte[] image = null; - try - { - image = new byte[in.available()]; - - in.read(image); - } - catch (IOException e) - { - logger.error("Failed to load image:" + imageID, e); - } - - return image; - } - - public static ResourceManagementService getResources() - { - if (resourcesService == null) - { - ServiceReference serviceReference = RssActivator.bundleContext - .getServiceReference(ResourceManagementService.class.getName()); - - if(serviceReference == null) - return null; - - resourcesService - = (ResourceManagementService)RssActivator.bundleContext - .getService(serviceReference); - } - - return resourcesService; - } -} diff --git a/src/net/java/sip/communicator/impl/protocol/rss/ProtocolProviderFactoryRssImpl.java b/src/net/java/sip/communicator/impl/protocol/rss/ProtocolProviderFactoryRssImpl.java deleted file mode 100644 index 1f74cee..0000000 --- a/src/net/java/sip/communicator/impl/protocol/rss/ProtocolProviderFactoryRssImpl.java +++ /dev/null @@ -1,233 +0,0 @@ -/* - * Jitsi, 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.rss; - -import java.security.*; -import java.security.cert.*; -import java.util.*; - -import javax.net.ssl.*; - -import net.java.sip.communicator.service.protocol.*; -import net.java.sip.communicator.util.*; - -import org.osgi.framework.*; - -/** - * The Rss protocol provider factory creates instances of the Rss - * protocol provider service. One Service instance corresponds to one account. - * - * @author Emil Ivov - * @author Lubomir Marinov - */ -public class ProtocolProviderFactoryRssImpl - extends ProtocolProviderFactory -{ - /** - * The <tt>Logger</tt> used by the <tt>ProtocolProviderFactoryRssImpl</tt> - * class and its instances for logging output. - */ - private static final Logger logger - = Logger.getLogger(ProtocolProviderFactoryRssImpl.class); - - /** - * The indicator which determines whether the delayed execution of - * {@link #installCustomSSLTrustManager()} which has to happen only once has - * been performed. - */ - private static boolean customSSLTrustManagerIsInstalled = false; - - /** - * Creates an instance of the ProtocolProviderFactoryRssImpl. - */ - public ProtocolProviderFactoryRssImpl() - { - super(RssActivator.getBundleContext(), - ProtocolProviderServiceRssImpl.RSS_PROTOCOL_NAME); - } - - /** - * Initialized and creates an account corresponding to the specified - * accountProperties and registers the resulting ProtocolProvider in the - * <tt>context</tt> BundleContext parameter. - * - * @param userIDStr tha/a user identifier uniquely representing the newly - * created account within the protocol namespace. - * @param accountProperties a set of protocol (or implementation) - * specific properties defining the new account. - * @return the AccountID of the newly created account. - */ - @Override - public AccountID installAccount( String userIDStr, - Map<String, String> accountProperties) - { - BundleContext context - = RssActivator.getBundleContext(); - if (context == null) - throw new NullPointerException("The specified BundleContext was null"); - - if (userIDStr == null) - throw new NullPointerException("The specified AccountID was null"); - - if (accountProperties == null) - throw new NullPointerException("The specified property map was null"); - - accountProperties.put(USER_ID, userIDStr); - - AccountID accountID = new RssAccountID(userIDStr, accountProperties); - - //make sure we haven't seen this account id before. - if (registeredAccounts.containsKey(accountID)) - throw new IllegalStateException( - "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 (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(accountID, false); - - accountID = loadAccount(accountProperties); - - return accountID; - } - - @Override - protected AccountID createAccountID( - String userID, - Map<String, String> accountProperties) - { - return new RssAccountID(userID, accountProperties); - } - - @Override - protected ProtocolProviderService createService(String userID, - AccountID accountID) - { - synchronized (ProtocolProviderFactoryRssImpl.class) - { - if (!customSSLTrustManagerIsInstalled) - { - System.setProperty( - "http.agent", - System.getProperty("sip-communicator.application.name") - + "/" - + System.getProperty("sip-communicator.version")); - logger - .debug( - "User-Agent set to " - + System.getProperty("http.agent")); - - try - { - installCustomSSLTrustManager(); - customSSLTrustManagerIsInstalled = true; - } - catch (java.security.GeneralSecurityException gsex) - { - logger.error(gsex); - } - } - } - - ProtocolProviderServiceRssImpl service = - new ProtocolProviderServiceRssImpl(); - - service.initialize(userID, accountID); - return service; - } - - /** - * Installs a trust manager that would accept all certificates so that - * we could install rss feeds from sites with expired/self-signed - * certificates. - */ - private static void installCustomSSLTrustManager() - throws GeneralSecurityException - { - // Let us create the factory where we can set some parameters for the - // connection - SSLContext sc = SSLContext.getInstance("SSL"); - sc.init(null, - new TrustManager[] { new TrustlessManager()}, - new SecureRandom()); - - // Create the socket connection and open it to the secure remote web server - HttpsURLConnection.setDefaultSSLSocketFactory(sc.getSocketFactory()); - } - - @Override - public void modifyAccount( ProtocolProviderService protocolProvider, - Map<String, String> accountProperties) - throws NullPointerException - { - // TODO Auto-generated method stub - } - - /** - * A trust manager that would accept all certificates so that we would be - * able to add rss feeds from sites with expired/self-signed certificates. - */ - private static class TrustlessManager - implements X509TrustManager - { - public X509Certificate[] getAcceptedIssuers() - { - return null; - } - - /** - * Given the partial or complete certificate chain provided by the peer, - * build a certificate path to a trusted root and return if it can be - * validated and is trusted for client SSL authentication based on the - * authentication type. The authentication type is determined by the - * actual certificate used. For instance, if RSAPublicKey is used, the - * authType should be "RSA". Checking is case-sensitive. - * - * @param certs the peer certificate chain - * @param authType the authentication type based on the client - * certificate - * - * @throws IllegalArgumentException - if null or zero-length chain is - * passed in for the chain parameter or if null or zero-length string - * is passed in for the authType parameter - * @throws CertificateException - if the certificate chain is not - * trusted by this TrustManager. - */ - public void checkClientTrusted(X509Certificate[] certs, String authType) - throws CertificateException - { - } - - /** - * Given the partial or complete certificate chain provided by the peer, - * build a certificate path to a trusted root and return if it can be - * validated and is trusted for server SSL authentication based on the - * authentication type. The authentication type is the key exchange - * algorithm portion of the cipher suites represented as a String, such - * as "RSA", "DHE_DSS". Note: for some exportable cipher suites, the - * key exchange algorithm is determined at run time during the - * handshake. For instance, for TLS_RSA_EXPORT_WITH_RC4_40_MD5, the - * authType should be RSA_EXPORT when an ephemeral RSA key is used for - * the key exchange, and RSA when the key from the server certificate - * is used. Checking is case-sensitive. - * - * @param certs the peer certificate chain - * @param authType the key exchange algorithm used - * - * @throws IllegalArgumentException if null or zero-length chain is - * passed in for the chain parameter or if null or zero-length string - * is passed in for the authType parameter - * @throws CertificateException if the certificate chain is not trusted - * by this TrustManager. - */ - public void checkServerTrusted(X509Certificate[] certs, String authType) - throws CertificateException - { - } - } -} diff --git a/src/net/java/sip/communicator/impl/protocol/rss/ProtocolProviderServiceRssImpl.java b/src/net/java/sip/communicator/impl/protocol/rss/ProtocolProviderServiceRssImpl.java deleted file mode 100644 index 2b3bf85..0000000 --- a/src/net/java/sip/communicator/impl/protocol/rss/ProtocolProviderServiceRssImpl.java +++ /dev/null @@ -1,297 +0,0 @@ -/* - * Jitsi, 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.rss; - -import net.java.sip.communicator.service.protocol.*; -import net.java.sip.communicator.service.protocol.event.*; -import net.java.sip.communicator.util.*; - -/** - * A Rss implementation of the ProtocolProviderService. - * - * @author Jean-Albert Vescovo - * @author Emil Ivov - */ -public class ProtocolProviderServiceRssImpl - extends AbstractProtocolProviderService -{ - private static final Logger logger - = Logger.getLogger(ProtocolProviderServiceRssImpl.class); - - /** - * The name of this protocol. - */ - public static final String RSS_PROTOCOL_NAME = "RSS"; - - /** - * The id of the account that this protocol provider represents. - */ - private AccountID accountID = null; - - /** - * We use this to lock access to initialization. - */ - private final Object initializationLock = new Object(); - - /** - * Indicates whether or not the provider is initialized and ready for use. - */ - private boolean isInitialized = false; - - /** - * The logo corresponding to the rss protocol. - */ - private final ProtocolIconRssImpl rssIcon = new ProtocolIconRssImpl(); - - /** - * A reference to the IM operation set - */ - private OperationSetBasicInstantMessagingRssImpl basicInstantMessaging; - - /** - * The registration state that we are currently in. Note that in a real - * world protocol implementation this field won't exist and the registration - * state would be retrieved from the protocol stack. - */ - private RegistrationState currentRegistrationState - = RegistrationState.UNREGISTERED; - - /** - * The default constructor for the Rss protocol provider. - */ - public ProtocolProviderServiceRssImpl() - { - if (logger.isTraceEnabled()) - logger.trace("Creating a rss provider."); - } - - /** - * Initializes the service implementation, and puts it in a state where it - * could interoperate with other services. It is strongly recomended that - * properties in this Map be mapped to property names as specified by - * <tt>AccountProperties</tt>. - * - * @param userID the user id of the rss account we're currently - * initializing - * @param accountID the identifier of the account that this protocol - * provider represents. - * - * @see net.java.sip.communicator.service.protocol.AccountID - */ - protected void initialize(String userID, - AccountID accountID) - { - synchronized(initializationLock) - { - this.accountID = accountID; - - //initialize the presence operationset - OperationSetPersistentPresenceRssImpl persistentPresence = - new OperationSetPersistentPresenceRssImpl(this); - - addSupportedOperationSet( - OperationSetPersistentPresence.class, - persistentPresence); - //register it once again for those that simply need presence and - //won't be smart enough to check for a persistent presence - //alternative - addSupportedOperationSet( - OperationSetPresence.class, - persistentPresence); - - //initialize the IM operation set - //OperationSetBasicInstantMessagingRssImpl - basicInstantMessaging - = new OperationSetBasicInstantMessagingRssImpl( - this, - persistentPresence); - addSupportedOperationSet( - OperationSetBasicInstantMessaging.class, - basicInstantMessaging); - - isInitialized = true; - } - } - - /** - * Returns the AccountID that uniquely identifies the account represented - * by this instance of the ProtocolProviderService. - * - * @return the id of the account represented by this provider. - */ - public AccountID getAccountID() - { - return accountID; - } - - /** - * Returns the short name of the protocol that the implementation of this - * provider is based upon (like SIP, Jabber, ICQ/AIM, or others for - * example). - * - * @return a String containing the short name of the protocol this - * service is implementing (most often that would be a name in - * ProtocolNames). - */ - public String getProtocolName() - { - return RSS_PROTOCOL_NAME; - } - - /** - * Returns the state of the registration of this protocol provider with - * the corresponding registration service. - * - * @return ProviderRegistrationState - */ - public RegistrationState getRegistrationState() - { - return currentRegistrationState; - } - - /** - * Starts the registration process. - * - * @param authority the security authority that will be used for - * resolving any security challenges that may be returned during the - * registration or at any moment while wer're registered. - * @throws OperationFailedException with the corresponding code it the - * registration fails for some reason (e.g. a networking error or an - * implementation problem). - */ - public void register(SecurityAuthority authority) - throws OperationFailedException - { - RegistrationState oldState = currentRegistrationState; - currentRegistrationState = RegistrationState.REGISTERED; - - fireRegistrationStateChanged( - oldState - , currentRegistrationState - , RegistrationStateChangeEvent.REASON_USER_REQUEST - , null); - } - - /** - * Makes the service implementation close all open sockets and release - * any resources that it might have taken and prepare for - * shutdown/garbage collection. - */ - public void shutdown() - { - if(!isInitialized) - { - return; - } - if (logger.isTraceEnabled()) - logger.trace("Killing the Rss Protocol Provider."); - - if(isRegistered()) - { - try - { - //do the unregistration - unregister(); - } - catch (OperationFailedException ex) - { - //we're shutting down so we need to silence the exception here - logger.error( - "Failed to properly unregister before shutting down. " - + getAccountID() - , ex); - } - } - - isInitialized = false; - } - - /** - * Ends the registration of this protocol provider with the current - * registration service. - * - * @throws OperationFailedException with the corresponding code it the - * registration fails for some reason (e.g. a networking error or an - * implementation problem). - */ - public void unregister() - throws OperationFailedException - { - RegistrationState oldState = currentRegistrationState; - currentRegistrationState = RegistrationState.UNREGISTERED; - - fireRegistrationStateChanged( - oldState - , currentRegistrationState - , RegistrationStateChangeEvent.REASON_USER_REQUEST - , null); - } - - /* - * (non-Javadoc) - * - * @see net.java.sip.communicator.service.protocol.ProtocolProviderService# - * isSignallingTransportSecure() - */ - public boolean isSignalingTransportSecure() - { - return false; - } - - /** - * Returns the "transport" protocol of this instance used to carry the - * control channel for the current protocol service. - * - * @return The "transport" protocol of this instance: TCP. - */ - public TransportProtocol getTransportProtocol() - { - return TransportProtocol.TCP; - } - - /** - * Returns the rss protocol icon. - * @return the rss protocol icon - */ - public ProtocolIcon getProtocolIcon() - { - return rssIcon; - } - - /** - * Returns the IM set - * @return the IM set - */ - public OperationSetBasicInstantMessagingRssImpl getBasicInstantMessaging() - { - return this.basicInstantMessaging; - } - - /** - * Returns a reference to the instant messaging operation set that we are - * currently using for this provider. - * @return a reference to the instant messaging operation set that we are - * currently using for this provider. - */ - public OperationSetBasicInstantMessagingRssImpl getOperationSetBasicIM() - { - return (OperationSetBasicInstantMessagingRssImpl) - getOperationSet(OperationSetBasicInstantMessaging.class); - } - - /** - * Returns a reference to the presence operation set that we are currently - * using for this provider. - * @return a reference to the presence operation set that we are currently - * using for this provider. - */ - public OperationSetPersistentPresenceRssImpl getOperationSetPresence() - { - return (OperationSetPersistentPresenceRssImpl) - getOperationSet(OperationSetPersistentPresence.class); - } -} diff --git a/src/net/java/sip/communicator/impl/protocol/rss/RssAccountID.java b/src/net/java/sip/communicator/impl/protocol/rss/RssAccountID.java deleted file mode 100644 index 3709681..0000000 --- a/src/net/java/sip/communicator/impl/protocol/rss/RssAccountID.java +++ /dev/null @@ -1,33 +0,0 @@ -/* - * Jitsi, 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.rss; - -import java.util.*; - -import net.java.sip.communicator.service.protocol.*; - -/** - * The Rss implementation of a sip-communicator account id. - * @author Emil Ivov - */ -public class RssAccountID - extends AccountID -{ - /** - * Creates an account id from the specified id and account properties. - * - * @param userID the user identifier correspnding to the account - * @param accountProperties any other properties necessary for the account. - */ - RssAccountID(String userID, Map<String, String> accountProperties) - { - super( userID, - accountProperties, - ProtocolProviderServiceRssImpl.RSS_PROTOCOL_NAME, - "rss.org"); - } -} diff --git a/src/net/java/sip/communicator/impl/protocol/rss/RssActivator.java b/src/net/java/sip/communicator/impl/protocol/rss/RssActivator.java deleted file mode 100644 index f25e531..0000000 --- a/src/net/java/sip/communicator/impl/protocol/rss/RssActivator.java +++ /dev/null @@ -1,173 +0,0 @@ -/* - * Jitsi, 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.rss; - -import java.util.*; - -import net.java.sip.communicator.service.gui.*; -import net.java.sip.communicator.service.protocol.*; -import net.java.sip.communicator.service.resources.*; -import net.java.sip.communicator.util.*; - -import org.jitsi.service.resources.*; -import org.osgi.framework.*; - -/** - * Loads the Rss provider factory and registers its services in the OSGI - * bundle context. - * - * @author Jean-Albert Vescovo - * @author Mihai Balan - * @author Emil Ivov - */ -public class RssActivator - implements BundleActivator -{ - private static final Logger logger - = Logger.getLogger(RssActivator.class); - - /** - * A reference to the registration of our Rss protocol provider - * factory. - */ - private ServiceRegistration rssPpFactoryServReg = null; - - /** - * A reference to the Rss protocol provider factory. - */ - private static ProtocolProviderFactoryRssImpl - rssProviderFactory = null; - - /** - * The currently valid bundle context. - */ - static BundleContext bundleContext = null; - - /** - * The <tt>ResourceManagementService</tt> that we use in this provider. - */ - private static ResourceManagementService resourcesService = null; - - /** - * The <tt>UIService</tt> that we use in this provider. - */ - private static UIService uiService = null; - - /** - * The uri handler that would be handling all feed:// links. - */ - private UriHandlerRssImpl uriHandler = null; - - /** - * Called when this bundle is started. In here we'll export the - * rss ProtocolProviderFactory implementation so that it could be - * possible to register accounts with it in SIP Communicator. - * - * @param context The execution context of the bundle being started. - * @throws Exception If this method throws an exception, this bundle is - * marked as stopped and the Framework will remove this bundle's - * listeners, unregister all services registered by this bundle, and - * release all services used by this bundle. - */ - public void start(BundleContext context) - throws Exception - { - RssActivator.bundleContext = context; - - Hashtable<String, String> hashtable = new Hashtable<String, String>(); - hashtable.put(ProtocolProviderFactory.PROTOCOL, "RSS"); - - rssProviderFactory = new ProtocolProviderFactoryRssImpl(); - - //reg the rss provider factory. - rssPpFactoryServReg = context.registerService( - ProtocolProviderFactory.class.getName(), - rssProviderFactory, - hashtable); - - if (logger.isInfoEnabled()) - logger.info("RSS protocol implementation [STARTED]."); - - uriHandler = new UriHandlerRssImpl(); - bundleContext.addServiceListener(uriHandler); - uriHandler.registerHandlerService(); - } - - /** - * Returns a reference to the bundle context that we were started with. - * @return a reference to the BundleContext instance that we were started - * witn. - */ - public static BundleContext getBundleContext() - { - return bundleContext; - } - - /** - * Retrurns a reference to the protocol provider factory that we have - * registered. - * @return a reference to the <tt>ProtocolProviderFactoryJabberImpl</tt> - * instance that we have registered from this package. - */ - public static ProtocolProviderFactoryRssImpl getProtocolProviderFactory() - { - return rssProviderFactory; - } - - /** - * Called when this bundle is stopped so the Framework can perform the - * bundle-specific activities necessary to stop the bundle. - * - * @param context The execution context of the bundle being stopped. - * @throws Exception If this method throws an exception, the bundle is - * still marked as stopped, and the Framework will remove the bundle's - * listeners, unregister all services registered by the bundle, and - * release all services used by the bundle. - */ - public void stop(BundleContext context) - throws Exception - { - RssActivator.rssProviderFactory.stop(); - rssPpFactoryServReg.unregister(); - - context.removeServiceListener(uriHandler); - - if (logger.isInfoEnabled()) - logger.info("RSS protocol implementation [STOPPED]."); - } - - /** - * Returns the <tt>ResourceManagementService</tt>. - * @return the <tt>ResourceManagementService</tt>. - */ - public static ResourceManagementService getResources() - { - if (resourcesService == null) - resourcesService - = ResourceManagementServiceUtils.getService(bundleContext); - return resourcesService; - } - - /** - * Returns a reference to the <tt>UIService</tt> instance that is currently - * in use. - * @return a reference to the currently valid <tt>UIService</tt>. - */ - public static UIService getUIService() - { - if (uiService == null) - { - ServiceReference serviceReference - = bundleContext.getServiceReference(UIService.class.getName()); - - if (serviceReference != null) - uiService - = (UIService) bundleContext.getService(serviceReference); - } - return uiService; - } -} diff --git a/src/net/java/sip/communicator/impl/protocol/rss/RssFeedReader.java b/src/net/java/sip/communicator/impl/protocol/rss/RssFeedReader.java deleted file mode 100644 index 11a4707..0000000 --- a/src/net/java/sip/communicator/impl/protocol/rss/RssFeedReader.java +++ /dev/null @@ -1,356 +0,0 @@ -/* - * Jitsi, 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.rss; - -import java.io.*; -import java.net.*; -import java.util.*; - -import net.java.sip.communicator.service.protocol.*; -import net.java.sip.communicator.util.*; - -import com.sun.syndication.feed.synd.*; -import com.sun.syndication.io.*; - -/** - * Wrapper class for the ROME functionality used in the RSS implementation in - * SIP Communicator. - * The class provides the means for identifying feed items, formatting and - * displaying the actual feed items. - * - * @author Jean-Albert Vescovo - * @author Mihai Balan - * @author Vincent Lucas - */ -public class RssFeedReader -{ - private static final Logger logger - = Logger.getLogger(ContactRssImpl.class); - /** - * The URL of the contact/feed, used to make a TCP query for the XML file - * containing the actual RSS feed. - */ - private URL rssURL; - - /** - * The title of the feed, which will be used as the display name - * of the contact/feed. - */ - private String title = "No feed avalaible !"; - - /** - * The object charged to retrieve the feed incoming from the relevant - * server. - */ - private SyndFeed feed = null; - - /** - * Key identifying the retrieved item in this feed. - */ - private RssItemKey lastItemKey; - - /** - * An array of <tt>SyndEntry</tt> objects which will contain all the items - * retrieved from the feed. - */ - private SyndEntry[] items = null; - - /** - * Tells us if the feeds is available or not. In other words, if the feed is - * ONLINE or OFFLINE. - */ - private boolean isFeedJoinable = false; - - /** - * Creates an instance of a RSS reader with the specified string used - * as an URL for the actual feed. - * - * @param contactRssURL the URL of this feed. - */ - public RssFeedReader(URL contactRssURL) - throws OperationFailedException, FileNotFoundException - { - this.rssURL = contactRssURL; - this.lastItemKey = null; - // Try to retrieve the feed and to complete this instantiation. - this.retrieveFlow(); - } - - /** - * Refreshes the RSS feed associated with this reader, and does not store - * the feed items (see getNewFeeds for this). - * - * @throws OperationFailedException with code ILLEGAL_ARGUMENT - * @throws FileNotFoundException if the feed does not exist any more. - */ - @SuppressWarnings("unchecked") //rome legacy code - private void retrieveFlow() - throws OperationFailedException, FileNotFoundException - { - - SyndFeedInput input = new SyndFeedInput(); - - try - { - this.feed = input.build(new XmlReader(rssURL)); - } - catch (FileNotFoundException ex) - { - this.isFeedJoinable = false; - //We are handling that in OpSetBasicInstantMessaging as it indicates - //a feed that has most likely been removed - throw ex; - } - catch (IOException ex) - { - this.isFeedJoinable = false; - throw new OperationFailedException( - "Failed to create and XmlReader for url: " + rssURL - , OperationFailedException.GENERAL_ERROR - , ex); - } - catch(FeedException fex) - { - this.isFeedJoinable = false; - throw new OperationFailedException( - "Failed to create and XmlReader for url: " + rssURL - , OperationFailedException.GENERAL_ERROR - , fex); - } - this.isFeedJoinable = true; - - this.feed.getEntries(); - - this.title = this.feed.getTitle(); - - // retrieve items - this.items = (SyndEntry[]) this.feed.getEntries().toArray(new SyndEntry[0]); - Arrays.sort(items, new SyndEntryComparator()); - } - - /** - * Returns the textual representation of the feed's items with regard to the - * key of the last item shown to the user. The items are sorted in reverse - * chronological order, if possible. - * @return textual representation of the feed items. - */ - public synchronized String getNewFeeds() - throws OperationFailedException, FileNotFoundException - { - String newsAbstract = null; - StringBuffer printedFeed = new StringBuffer(); - - int i; - boolean hasSomeNews = false; - - // Try to retrieve the feed and to complete this instanciation. - this.retrieveFlow(); - - for (i = items.length - 1; - i >= 0 && (new RssItemKey(items[i])).compareTo(lastItemKey) != 0; - --i) - { - hasSomeNews = true; - // Get the abstract of the news. - newsAbstract = getNewsAbstract(items[i]); - // Forge the news text to be displayed. - printedFeed.insert(0, - "<a href=\""+items[i].getLink()+"\">" - + "<strong>"+ items[i].getTitle() + "</strong>" - + "</a>" - + "<br>" - + newsAbstract - + "<hr>"); - } - if (!hasSomeNews) - { - return null; - } - lastItemKey = new RssItemKey(items[items.length - 1]); - printedFeed - .append ("<em>Send anything to refresh this feed...</em><br>\n"); - return printedFeed.toString(); - } - - public String getNoNewFeedString() - { - return "<strong>No new articles in your feed since" - + " last update.</strong><br>" - + "<em>Send anything to refresh this feed...</em><br>\n"; - } - - /** - * The function retrieves the abstract (textual description) of a feed item - * or an empty string otherwise. It takes care of all format specific data - * and returns a nicely formatted <tt>String</tt> - * - * @param syndEntry - Feed entry for which to retrieve the abstract (text) - * @return String representation of the news abstract or an empty string if - * no such data could be found. - */ - private String getNewsAbstract(SyndEntry syndEntry) - { - StringBuffer newsAbstract = new StringBuffer(); - List<?> contents; - - // get item contents - contents = syndEntry.getContents(); - if (!contents.isEmpty()) - { - Iterator<?> it = contents.iterator(); - while (it.hasNext()) - { - newsAbstract.append(((SyndContent)it.next()).getValue()); - } - } - - // format the contents - if (newsAbstract.toString().length() != 0) - return newsAbstract.toString(); - else - { - if (syndEntry.getDescription() != null) - { - if(syndEntry.getDescription().getValue() != null) - newsAbstract.append(syndEntry.getDescription().getValue()); - } - } - return newsAbstract.toString(); - } - - /** - * Return the key for the last item retrieved. - * - * @return key of the last item retrieved. - */ - public RssItemKey getLastItemKey() - { - return this.lastItemKey; - } - - /** - * Returns a ChannelIF that can be used to know if a feed exists indeed. - * - * @return a ChannelIF containing the result of a query on a RSS server. - */ - public SyndFeed getFeed() - { - return this.feed; - } - - /** - * Returns a Date giving the publication date of the feed on the relevant - * server. - * - * In most case, this date doesn't exist on the server. Not used at this - * time in this implementation. - * - * @return a Date representing the publication date of the feed. - */ - public Date getPubDate() - { - return this.feed.getPublishedDate(); - } - - /** - * Returns a String used as a display name. - * - * @return a String title representing the feed/contact. - */ - public String getTitle() - { - return this.title; - } - - /** - * Returns a String that can be used for identifying the contact. - * - * We'll prefer to use the title of the feed as display name. - * - * @return a String id representing and uniquely identifying the contact. - */ - public String getURL() - { - return rssURL.toString(); - } - - private static class SyndEntryComparator implements Comparator<SyndEntry> - { - /** - * Compares its two items for order. Returns a negative integer, - * zero, or a positive integer as the first argument has a date - * which precedes, is equal or is greater the second. - * <p> - * @param o1 the first item to be compared. - * @param o2 the second item to be compared. - * @return a negative integer, zero, or a positive integer as the - * first item has a date that is before is equal to or is - * after the second. - * @throws ClassCastException if one of the objects is not a - * SyndEntry instance. - */ - public int compare(SyndEntry o1, SyndEntry o2) - { - Date date1 = o1.getPublishedDate(); - Date date2 = o2.getPublishedDate(); - - if (date1 == null || date2 == null) - { - return 0; - } - return date1.compareTo(date2); - } - } - - public String serialize() - { - StringBuffer result = new StringBuffer(); - - if(this.lastItemKey != null) - { - result.append(lastItemKey.serialize()); - } - result.append("displayName="); - result.append(this.title); - result.append(";"); - - return result.toString(); - } - - public static RssFeedReader deserialize(URL contactRssURL, String settings) - throws OperationFailedException, FileNotFoundException - { - StringTokenizer reader = new StringTokenizer(settings, ";"); - String tmpTitle = null; - - while (reader.hasMoreTokens()) - { - String data[] = reader.nextToken().split("=", 2); - - if (data[0].equals("displayName")) - { - if (data.length == 2) - { - tmpTitle = data[1]; - } - else - { - logger.error("Failed to deserialize RSS settings. Parse displayName error: " + - settings, - new Exception("Parse itemUri error: " + settings)); - return null; - } - } - } - RssItemKey tmpKey = RssItemKey.deserialize(settings); - RssFeedReader rssFeedReader = new RssFeedReader(contactRssURL); - rssFeedReader.lastItemKey = tmpKey; - rssFeedReader.title = tmpTitle; - - return rssFeedReader; - } -} diff --git a/src/net/java/sip/communicator/impl/protocol/rss/RssItemKey.java b/src/net/java/sip/communicator/impl/protocol/rss/RssItemKey.java deleted file mode 100644 index a0f1d2a..0000000 --- a/src/net/java/sip/communicator/impl/protocol/rss/RssItemKey.java +++ /dev/null @@ -1,311 +0,0 @@ -/*
- * Jitsi, 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.rss;
-
-import java.text.*;
-import java.util.*;
-
-import net.java.sip.communicator.util.*;
-
-import com.sun.syndication.feed.synd.*;
-
-/**
- * The <code>RssItemKey</code> is used to encapsulate information pertaining to
- * the last item retrieved from a RSS feed. It can be used with both feeds that
- * provide and that don't provide a date for their contents.
- *
- * @author Mihai Balan
- * @author Vincent Lucas
- */
-public class RssItemKey
- //implements Comparable
-{
- private static final Logger logger =
- Logger.getLogger(OperationSetPersistentPresenceRssImpl.class);
-
- /**
- * Date of the last show post. If it cannot be used, it's null.
- */
- private Date itemDate;
-
- /**
- * URI (link) of the last shown post. If it's not used, it's null.
- */
- private String itemUri;
-
- /**
- * Flag to mark whether date is used to mark items (<code>true</code>) or
- * URI (<code>false</code>)
- */
- private boolean usesDate;
-
- /**
- * Sets the date format for serializing and deserialiazing.
- */
- private static SimpleDateFormat formatter =
- new SimpleDateFormat("yyyy.MM.dd-HH:mm:ss");
-
- /**
- * Creates a RssContactSettings object that uses date if possible or at
- * least URI to identify feed items.
- * @param entry The last Syndentry of the RSS feed.
- */
- public RssItemKey(SyndEntry entry)
- {
- this.itemUri = entry.getUri();
- this.itemDate = entry.getPublishedDate();
- this.usesDate = (this.itemDate != null);
- // Some feeds are storing the URI of the entry in the link tag. Do not
- // ask me why, but it is llike this.
- if(!usesDate && itemUri == null)
- {
- this.itemUri = entry.getLink();
- }
- }
-
- /**
- * Creates a RssContactSettings object that uses date to identify feed
- * items, with the last item date specified by the <tt>Date</tt>
- * parameter.
- * @param date date/time of the last item of the RSS feed.
- */
- private RssItemKey(Date date)
- {
- this.itemUri = null;
- this.itemDate = date;
- this.usesDate = true;
- }
-
- /**
- * Creates a RssContactSettings object that uses URI to identify feed
- * items.
- * @param uri The URI of the last RSS entry.
- */
- private RssItemKey(String uri)
- {
- this.itemUri = uri;
- this.itemDate = null;
- this.usesDate = false;
- }
-
- /**
- * Determines if the current key uses <code>Date</code> as a means of
- * identification or not. Usually if true is returned this also implies that
- * <code>getItemUri() == null</code> so this should be used with care.
- * Similarly, if <code>false</code> is returned, one should assume that
- * <code>getItemDate() == null</code>.
- *
- * @return <code>true</code> if date is used for identification,
- * <code>false</code> otherwise.
- * @see #getItemDate()
- * @see #getItemUri()
- */
- public boolean usesDate()
- {
- return this.usesDate;
- }
-
- /**
- * Returns the date that is used as a key. Note that null can also be
- * returned in case <code>usesDate() == false</code>.
- *
- * @return date field of the key.
- * @see #usesDate()
- */
- public Date getItemDate()
- {
- return this.itemDate;
- }
-
- /**
- * Returns the URI that is used as a key. Note that null can also be
- * returned in case <code>usesDate() == true</code>.
- *
- * @return URI field of the key.
- * @see #usesDate()
- */
- public String getItemUri()
- {
- return this.itemUri;
- }
-
- /***
- * Used for restoring the key information from a textual representation.
- *
- * @param settings textual representation of the stored data
- * @return the result rss item
- */
- public static RssItemKey deserialize(String settings)
- {
- StringTokenizer reader = new StringTokenizer(settings, ";");
- Date date = null;
- String uri = null;
- boolean useInitialized = false;
- boolean isDateUsed = false;
-
- while (reader.hasMoreTokens())
- {
- String data[] = reader.nextToken().split("=", 2);
-
- // Parse the date item.
- if (data[0].equals("itemDate"))
- {
- if (data.length == 2)
- {
- try
- {
- if(!data[1].equals("null"))
- {
- date = formatter.parse(data[1]);
- }
- }
- catch (ParseException e)
- {
- logger.error("Failed to deserialize RSS settings. Parse date error: " +
- settings,
- e);
- return null;
- }
- }
- else
- {
- logger.error("Failed to deserialize RSS settings. Parse itemDate error: " +
- settings,
- new Exception("Parse itemDate error: " + settings));
- return null;
- }
- }
- // Parse the uri item.
- else if (data[0].equals("itemUri"))
- {
- if (data.length == 2)
- {
- if(!data[1].equals("null"))
- {
- uri = data[1];
- }
- }
- else
- {
- logger.error("Failed to deserialize RSS settings. Parse itemUri error: " +
- settings,
- new Exception("Parse itemUri error: " + settings));
- return null;
- }
- }
- // Parse the usesDate item.
- else if (data[0].equals("usesDate"))
- {
- if (data.length == 2)
- {
- isDateUsed = Boolean.valueOf(data[1]).booleanValue();
- useInitialized = true;
- }
- else
- {
- logger.error("Failed to deserialize RSS settings. Parse usesDate error: " +
- settings,
- new Exception("Parse usesDate error: " + settings));
- return null;
- }
- }
- }
-
- // If the initialization was good, we create a new RssItemKey.
- if(useInitialized)
- {
- if(isDateUsed && date != null)
- {
- return new RssItemKey(date);
- }
- else if(!isDateUsed && uri != null)
- {
- return new RssItemKey(uri);
- }
- }
- // Else we must return null, has the persistentData is buggy.
- return null;
- }
-
- /**
- * Serializes current key to a textual representation.
- *
- * @return String containing the textual representation of the current key.
- */
- public String serialize()
- {
- StringBuffer result = new StringBuffer();
-
- // Create the date item for the persistentData.
- result.append("itemDate=");
- result.append(
- itemDate == null ?
- "null" : formatter.format(itemDate));
- result.append(";");
-
- // Create the uri item for the persistentData.
- result.append("itemUri=");
- result.append(
- itemUri == null ?
- "null" : itemUri);
- result.append(";");
-
- // Create the usesDate item for the persistentData.
- result.append("usesDate=");
- result.append(usesDate);
- result.append(";");
-
- return result.toString();
- }
-
- /**
- * Returns the textual representation of the settings object. This can
- * be easily de-serialized with a call to <code>deserialize()</code>.
- *
- * @see #deserialize(String)
- */
- @Override
- public String toString()
- {
- return this.serialize();
- }
-
- /**
- * Compare 2 RssItemKey. Compare items with date or with uri, but return
- * always 1 when we can't say anything about order (one is date, the other
- * is uri or the obj is null).
- */
- public int compareTo(RssItemKey obj)
- {
- if(obj == null)
- {
- return 1;
- }
- if (this.usesDate())
- {
- if (obj.usesDate())
- {
- return this.itemDate.compareTo(obj.itemDate);
- }
- else
- {
- return 0;
- }
- }
- else
- {
- if(obj.usesDate())
- {
- return 0;
- }
- else
- {
- return this.itemUri.compareToIgnoreCase(obj.itemUri);
- }
- }
- }
-}
diff --git a/src/net/java/sip/communicator/impl/protocol/rss/RssStatusEnum.java b/src/net/java/sip/communicator/impl/protocol/rss/RssStatusEnum.java deleted file mode 100644 index be6a9e2..0000000 --- a/src/net/java/sip/communicator/impl/protocol/rss/RssStatusEnum.java +++ /dev/null @@ -1,111 +0,0 @@ -/* - * Jitsi, 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.rss; - -import java.io.*; -import java.util.*; - -import net.java.sip.communicator.service.protocol.*; -import net.java.sip.communicator.util.*; - -/** - * An implementation of <tt>PresenceStatus</tt> that enumerates all states that - * a Rss contact can fall into. - * - * @author Jean-Albert Vescovo - */ -public class RssStatusEnum - extends PresenceStatus -{ - private static final Logger logger - = Logger.getLogger(RssStatusEnum.class); - - /** - * Indicates an Offline status or status with 0 connectivity. - */ - public static final RssStatusEnum OFFLINE - = new RssStatusEnum( - 0, - "Offline", - getImageInBytes("service.protocol.rss.OFFLINE_STATUS_ICON")); - - /** - * The Online status. Indicate that the user is able and willing to - * communicate. - */ - public static final RssStatusEnum ONLINE - = new RssStatusEnum( - 65, - "Online", - getImageInBytes("service.protocol.rss.RSS_16x16")); - - /** - * Initialize the list of supported status states. - */ - private static List<PresenceStatus> supportedStatusSet = new LinkedList<PresenceStatus>(); - static - { - supportedStatusSet.add(OFFLINE); - supportedStatusSet.add(ONLINE); - } - - /** - * Creates an instance of <tt>RssPresneceStatus</tt> with the - * specified parameters. - * @param status the connectivity level of the new presence status instance - * @param statusName the name of the presence status. - * @param statusIcon the icon associated with this status - */ - private RssStatusEnum(int status, - String statusName, - byte[] statusIcon) - { - super(status, statusName, statusIcon); - } - - /** - * Returns an iterator over all status instances supproted by the rss - * provider. - * @return an <tt>Iterator</tt> over all status instances supported by the - * rss provider. - */ - static Iterator<PresenceStatus> supportedStatusSet() - { - return supportedStatusSet.iterator(); - } - - /** - * Returns the byte representation of the image corresponding to the given - * identifier. - * - * @param imageID the identifier of the image - * @return the byte representation of the image corresponding to the given - * identifier. - */ - private static byte[] getImageInBytes(String imageID) - { - InputStream in = RssActivator.getResources(). - getImageInputStream(imageID); - - if (in == null) - return null; - byte[] image = null; - try - { - image = new byte[in.available()]; - - in.read(image); - } - catch (IOException e) - { - logger.error("Failed to load image:" + imageID, e); - } - - return image; - } - -} diff --git a/src/net/java/sip/communicator/impl/protocol/rss/RssThread.java b/src/net/java/sip/communicator/impl/protocol/rss/RssThread.java deleted file mode 100644 index 8ef5668..0000000 --- a/src/net/java/sip/communicator/impl/protocol/rss/RssThread.java +++ /dev/null @@ -1,46 +0,0 @@ -/* - * Jitsi, 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.rss; - -/** - * Instant messaging functionalites for the Rss protocol. - * - * @author Jean-Albert Vescovo - */ -public class RssThread - extends Thread -{ - private OperationSetBasicInstantMessagingRssImpl opSet; - private ContactRssImpl rssContact = null; - - /** - * Creates a new instance of RssThread - * - * @param opSet the OperationSetBasicInstantMessagingRssImpl instance that - * is managing the rss protocol. - * @param rssContact the contact that the thread is going to do a query - */ - public RssThread(OperationSetBasicInstantMessagingRssImpl opSet, - ContactRssImpl rssContact) - { - this.opSet = opSet; - this.rssContact = rssContact; - - this.setDaemon(true); - } - - /** - * The task executed by the thread. - * If no rss contact given as parameter, the query is launched for all - * contacts - */ - @Override - public void run() - { - this.opSet.refreshRssFeed(this.rssContact); - } -} diff --git a/src/net/java/sip/communicator/impl/protocol/rss/RssTimerRefreshFeed.java b/src/net/java/sip/communicator/impl/protocol/rss/RssTimerRefreshFeed.java deleted file mode 100644 index 25fc05c..0000000 --- a/src/net/java/sip/communicator/impl/protocol/rss/RssTimerRefreshFeed.java +++ /dev/null @@ -1,50 +0,0 @@ -/* - * Jitsi, 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.rss; - -import java.util.*; - -import net.java.sip.communicator.util.*; - -/** - * Instant messaging functionalites for the Rss protocol. - * - * @author Jean-Albert Vescovo - */ - -public class RssTimerRefreshFeed - extends TimerTask -{ - private static final Logger logger - = Logger.getLogger(RssTimerRefreshFeed.class); - - private OperationSetBasicInstantMessagingRssImpl opSet; - - /** - * Creates an instance of timer used to seeking periodically the rss feeds - * registered as contacts. - * @param opSet the OperationSetBasicInstantMessagingRssImpl instance that - * is managing the rss protocol. - */ - public RssTimerRefreshFeed(OperationSetBasicInstantMessagingRssImpl opSet) - { - this.opSet = opSet; - } - - /** - * What the timer is supposed to do each time the PERIOD_REFRESH_RSS expire. - * In facts, it launch a new thread responsible for starting one or more - * rss queries - */ - @Override - public void run() - { - if (logger.isTraceEnabled()) - logger.trace("Starting a periodic rss check."); - this.opSet.refreshAllRssFeeds(); - } -} diff --git a/src/net/java/sip/communicator/impl/protocol/rss/UriHandlerRssImpl.java b/src/net/java/sip/communicator/impl/protocol/rss/UriHandlerRssImpl.java deleted file mode 100644 index 7f73dd9..0000000 --- a/src/net/java/sip/communicator/impl/protocol/rss/UriHandlerRssImpl.java +++ /dev/null @@ -1,251 +0,0 @@ -/* - * Jitsi, 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.rss; - -import java.util.*; - -import net.java.sip.communicator.service.argdelegation.*; -import net.java.sip.communicator.service.gui.*; -import net.java.sip.communicator.service.protocol.*; -import net.java.sip.communicator.util.*; - -import org.osgi.framework.*; - -/** - * The RSS implementation of the URI handler. This class handles RSS feeds by - * adding them to your contact list. - * - * @author Emil Ivov - */ -public class UriHandlerRssImpl - implements UriHandler, - ServiceListener - -{ - private static final Logger logger = - Logger.getLogger(UriHandlerRssImpl.class); - - /** - * A reference to the OSGi registration we create with this handler. - */ - private ServiceRegistration ourServiceRegistration = null; - - /** - * The object that we are using to synchronize our service registration. - */ - private final Object registrationLock = new Object(); - - /** - * Creates an instance of this uri handler, so that it would start handling - * URIs by passing them to the RSS providers. - */ - protected UriHandlerRssImpl() - throws NullPointerException - { - } - - /** - * Registers this UriHandler with the bundle context so that it could - * start handling URIs - */ - public void registerHandlerService() - { - synchronized(registrationLock) - { - if (ourServiceRegistration != null) - { - // ... we are already registered (this is probably - // happening during startup) - return; - } - - Hashtable<String, String> registrationProperties - = new Hashtable<String, String>(); - - registrationProperties - .put(UriHandler.PROTOCOL_PROPERTY, getProtocol()); - - ourServiceRegistration - = RssActivator - .bundleContext - .registerService( - UriHandler.class.getName(), - this, - registrationProperties); - } - } - - /** - * Unregisters this UriHandler from the bundle context. - */ - public void unregisterHandlerService() - { - synchronized(registrationLock) - { - ourServiceRegistration.unregister(); - ourServiceRegistration = null; - } - } - - /** - * Returns the protocol that this handler is responsible for. In this case - * this would be the "feed" protocol. - * - * @return the protocol that this handler is responsible for. - */ - public String getProtocol() - { - return "feed"; - } - - /** - * Parses the specified URI and creates a call with the currently active - * telephony operation set. - * - * @param uri the feed: URI that we have to call. - */ - public void handleUri(String uri) - { - byte[] icon = RssActivator.getResources() - .getImageInBytes("pageImageRss"); - int answer = RssActivator.getUIService().getPopupDialog() - .showConfirmPopupDialog( - "Would you like to add the following feed to " - +"your list of contacts?\n" - +uri, - "Add RSS feed?", - PopupDialog.YES_NO_OPTION, - PopupDialog.QUESTION_MESSAGE, - icon); - - if (answer != PopupDialog.YES_OPTION) - { - return; - } - - ProtocolProviderService provider; - try - { - provider = getRssProvider(); - } - catch (OperationFailedException exc) - { - // The operation has been canceled by the user. Bail out. - if (logger.isTraceEnabled()) - logger.trace("User canceled handling of uri " + uri); - return; - } - - //if provider is null then we need to tell the user to create an account - if(provider == null) - { - showErrorMessage( - "You need to configure at least one " - + "RSS" +" account to be able to add the feed\n" - + uri, - null); - return; - } - - OperationSetPresence presenceOpSet - = provider.getOperationSet(OperationSetPresence.class); - - try - { - presenceOpSet.subscribe(uri); - } - catch (OperationFailedException exc) - { - showErrorMessage("Failed to subscribe to the following feed\n" - + uri, - exc); - } - } - - /** - * The point of implementing a service listener here is so that we would - * only register our own uri handling service and thus only handle URIs - * while the factory is available as an OSGi service. We remove ourselves - * when our factory unregisters its service reference. - * - * @param event the OSGi <tt>ServiceEvent</tt> - */ - public void serviceChanged(ServiceEvent event) - { - Object sourceService - = RssActivator - .bundleContext.getService(event.getServiceReference()); - - //ignore anything but our protocol factory. - if (!(sourceService instanceof ProtocolProviderFactoryRssImpl)) - return; - - switch (event.getType()) - { - case ServiceEvent.REGISTERED: - //our factory has just been registered as a service ... - registerHandlerService(); - break; - - case ServiceEvent.UNREGISTERING: - //our factory just died - seppuku. - unregisterHandlerService(); - break; - - case ServiceEvent.MODIFIED: - default: - //we don't care. - break; - } - } - - /** - * Uses the <tt>UIService</tt> to show an error <tt>message</tt> and log - * and <tt>exception</tt>. - * - * @param message the message that we'd like to show to the user. - * @param exc the exception that we'd like to log - */ - private void showErrorMessage(String message, Exception exc) - { - RssActivator.getUIService().getPopupDialog().showMessagePopupDialog( - message, - "Failed to create call!", - PopupDialog.ERROR_MESSAGE); - logger.error(message, exc); - } - - /** - * Returns the default provider that we are supposed to add feeds to. - * - * @return the provider that we should add the URIs to or null if no - * provider was found. - */ - public ProtocolProviderService getRssProvider() - throws OperationFailedException - { - //get a reference to the provider - ServiceReference[] serRefs = null; - String osgiFilter = "(" + ProtocolProviderFactory.PROTOCOL - + "=" + ProtocolNames.RSS + ")"; - - try { - serRefs = RssActivator.bundleContext.getServiceReferences( - ProtocolProviderService.class.getName(), osgiFilter); - } catch (InvalidSyntaxException ise) - { - //shouldn't happen as the filter is static (typos maybe? :D) - return null; - } - - if(serRefs == null || serRefs.length == 0) - return null; - - return (ProtocolProviderService)RssActivator.getBundleContext() - .getService(serRefs[0]); - } -} diff --git a/src/net/java/sip/communicator/impl/protocol/rss/rss.provider.manifest.mf b/src/net/java/sip/communicator/impl/protocol/rss/rss.provider.manifest.mf deleted file mode 100644 index b318209..0000000 --- a/src/net/java/sip/communicator/impl/protocol/rss/rss.provider.manifest.mf +++ /dev/null @@ -1,24 +0,0 @@ -Bundle-Activator: net.java.sip.communicator.impl.protocol.rss.RssActivator -Bundle-Name: Rss Protocol Provider -Bundle-Description: A bundle providing support for the Rss protocol. -Bundle-Vendor: jitsi.org -Bundle-Version: 0.0.1 -Bundle-SymbolicName: net.java.sip.communicator.protocol.rss -Import-Package: org.osgi.framework, - org.apache.log4j, - org.xml.sax, - org.xml.sax.helpers, - org.xml.sax.ext, - org.w3c.dom, - javax.xml.parsers, - javax.imageio, - javax.net.ssl, - org.jitsi.service.configuration, - net.java.sip.communicator.service.contactlist, - org.jitsi.service.resources, net.java.sip.communicator.service.resources, - net.java.sip.communicator.util, - net.java.sip.communicator.service.protocol, - net.java.sip.communicator.service.protocol.event, - net.java.sip.communicator.service.gui, - net.java.sip.communicator.service.argdelegation - |