mirror of
https://github.com/vanitasvitae/Smack.git
synced 2024-12-24 03:27:59 +01:00
Improve PubSub API
Use Manager pattern for PubSubManager. Also improve the API of ServiceDiscoverManager.
This commit is contained in:
parent
9e351f0535
commit
001e824fb9
16 changed files with 368 additions and 140 deletions
|
@ -53,7 +53,7 @@ Create a node with default configuration and then configure it:
|
|||
|
||||
```
|
||||
// Create a pubsub manager using an existing XMPPConnection
|
||||
PubSubManager mgr = new PubSubManager(con);
|
||||
PubSubManager mgr = PubSubManager.getInstanceFor(con);
|
||||
|
||||
// Create the node
|
||||
LeafNode leaf = mgr.createNode("testNode");
|
||||
|
@ -71,7 +71,7 @@ Create and configure a node:
|
|||
|
||||
```
|
||||
// Create a pubsub manager using an existing XMPPConnection
|
||||
PubSubManager mgr = new PubSubManager(con);
|
||||
PubSubManager mgr = PubSubManager.getInstanceFor(con);
|
||||
|
||||
// Create the node
|
||||
ConfigureForm form = new ConfigureForm(FormType.submit);
|
||||
|
@ -108,7 +108,7 @@ In this example we publish an item to a node that does not take payload:
|
|||
|
||||
```
|
||||
// Create a pubsub manager using an existing XMPPConnection
|
||||
PubSubManager mgr = new PubSubManager(con);
|
||||
PubSubManager mgr = PubSubManager.getInstanceFor(con);
|
||||
|
||||
// Get the node
|
||||
LeafNode node = mgr.getNode("testNode");
|
||||
|
@ -124,7 +124,7 @@ In this example we publish an item to a node that does take payload:
|
|||
|
||||
```
|
||||
// Create a pubsub manager using an existing XMPPConnection
|
||||
PubSubManager mgr = new PubSubManager(con);
|
||||
PubSubManager mgr = PubSubManager.getInstanceFor(con);
|
||||
|
||||
// Get the node
|
||||
LeafNode node = mgr.getNode("testNode");
|
||||
|
@ -167,7 +167,7 @@ subscribe for messages.
|
|||
|
||||
```
|
||||
// Create a pubsub manager using an existing XMPPConnection
|
||||
PubSubManager mgr = new PubSubManager(con);
|
||||
PubSubManager mgr = PubSubManager.getInstanceFor(con);
|
||||
|
||||
// Get the node
|
||||
LeafNode node = mgr.getNode("testNode");
|
||||
|
@ -198,7 +198,7 @@ subscribe for item deletion messages.
|
|||
|
||||
```
|
||||
// Create a pubsub manager using an existing XMPPConnection
|
||||
PubSubManager mgr = new PubSubManager(con);
|
||||
PubSubManager mgr = PubSubManager.getInstanceFor(con);
|
||||
|
||||
// Get the node
|
||||
LeafNode node = mgr.getNode("testNode");
|
||||
|
@ -230,7 +230,7 @@ subscribe for node configuration messages.
|
|||
|
||||
```
|
||||
// Create a pubsub manager using an existing XMPPConnection
|
||||
PubSubManager mgr = new PubSubManager(con);
|
||||
PubSubManager mgr = PubSubManager.getInstanceFor(con);
|
||||
|
||||
// Get the node
|
||||
Node node = mgr.getNode("testNode");
|
||||
|
@ -286,7 +286,7 @@ In this example we can see how to retrieve the existing items from a node:
|
|||
|
||||
```
|
||||
// Create a pubsub manager using an existing XMPPConnection
|
||||
PubSubManager mgr = new PubSubManager(con);
|
||||
PubSubManager mgr = PubSubManager.getInstanceFor(con);
|
||||
|
||||
// Get the node
|
||||
LeafNode node = mgr.getNode("testNode");
|
||||
|
@ -298,7 +298,7 @@ In this example we can see how to retrieve the last N existing items:
|
|||
|
||||
```
|
||||
// Create a pubsub manager using an existing XMPPConnection
|
||||
PubSubManager mgr = new PubSubManager(con);
|
||||
PubSubManager mgr = PubSubManager.getInstanceFor(con);
|
||||
|
||||
// Get the node
|
||||
LeafNode node = mgr.getNode("testNode");
|
||||
|
@ -310,7 +310,7 @@ In this example we can see how to retrieve the specified existing items:
|
|||
|
||||
```
|
||||
// Create a pubsub manager using an existing XMPPConnection
|
||||
PubSubManager mgr = new PubSubManager(con);
|
||||
PubSubManager mgr = PubSubManager.getInstanceFor(con);
|
||||
|
||||
// Get the node
|
||||
LeafNode node = mgr.getNode("testNode");
|
||||
|
@ -341,7 +341,7 @@ In this example we can see how to get pubsub capabilities:
|
|||
|
||||
```
|
||||
// Create a pubsub manager using an existing XMPPConnection
|
||||
PubSubManager mgr = new PubSubManager(con);
|
||||
PubSubManager mgr = PubSubManager.getInstanceFor(con);
|
||||
|
||||
// Get the pubsub features that are supported
|
||||
DiscoverInfo supportedFeatures = mgr.getSupportedFeatures();
|
||||
|
@ -351,7 +351,7 @@ In this example we can see how to get pubsub subscriptions for all nodes:
|
|||
|
||||
```
|
||||
// Create a pubsub manager using an existing XMPPConnection
|
||||
PubSubManager mgr = new PubSubManager(con);
|
||||
PubSubManager mgr = PubSubManager.getInstanceFor(con);
|
||||
|
||||
// Get all the subscriptions in the pubsub service
|
||||
List<Subscription;> subscriptions = mgr.getSubscriptions();
|
||||
|
@ -362,7 +362,7 @@ on the pubsub service:
|
|||
|
||||
```
|
||||
// Create a pubsub manager using an existing XMPPConnection
|
||||
PubSubManager mgr = new PubSubManager(con);
|
||||
PubSubManager mgr = PubSubManager.getInstanceFor(con);
|
||||
|
||||
// Get the affiliations for the users bare JID
|
||||
List<Affiliation;> affiliations = mgr.getAffiliations();
|
||||
|
@ -372,7 +372,7 @@ In this example we can see how to get information about the node:
|
|||
|
||||
```
|
||||
// Create a pubsub manager using an existing XMPPConnection
|
||||
PubSubManager mgr = new PubSubManager(con);
|
||||
PubSubManager mgr = PubSubManager.getInstanceFor(con);
|
||||
Node node = mgr.getNode("testNode");
|
||||
|
||||
// Get the node information
|
||||
|
@ -383,7 +383,7 @@ In this example we can see how to discover the node items:
|
|||
|
||||
```
|
||||
// Create a pubsub manager using an existing XMPPConnection
|
||||
PubSubManager mgr = new PubSubManager(con);
|
||||
PubSubManager mgr = PubSubManager.getInstanceFor(con);
|
||||
Node node = mgr.getNode("testNode");
|
||||
|
||||
// Discover the node items
|
||||
|
@ -394,7 +394,7 @@ In this example we can see how to get node subscriptions:
|
|||
|
||||
```
|
||||
// Create a pubsub manager using an existing XMPPConnection
|
||||
PubSubManager mgr = new PubSubManager(con);
|
||||
PubSubManager mgr = PubSubManager.getInstanceFor(con);
|
||||
Node node = mgr.getNode("testNode");
|
||||
|
||||
// Discover the node subscriptions
|
||||
|
|
|
@ -283,11 +283,7 @@ public class MultipleRecipientManager {
|
|||
*/
|
||||
private static DomainBareJid getMultipleRecipienServiceAddress(XMPPConnection connection) throws NoResponseException, XMPPErrorException, NotConnectedException, InterruptedException {
|
||||
ServiceDiscoveryManager sdm = ServiceDiscoveryManager.getInstanceFor(connection);
|
||||
List<DomainBareJid> services = sdm.findServices(MultipleAddresses.NAMESPACE, true, true);
|
||||
if (services.size() > 0) {
|
||||
return services.get(0);
|
||||
}
|
||||
return null;
|
||||
return sdm.findService(MultipleAddresses.NAMESPACE, true);
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -684,7 +684,7 @@ public final class ServiceDiscoveryManager extends Manager {
|
|||
* Create a cache to hold the 25 most recently lookup services for a given feature for a period
|
||||
* of 24 hours.
|
||||
*/
|
||||
private Cache<String, List<DomainBareJid>> services = new ExpirationCache<>(25,
|
||||
private Cache<String, List<DiscoverInfo>> services = new ExpirationCache<>(25,
|
||||
24 * 60 * 60 * 1000);
|
||||
|
||||
/**
|
||||
|
@ -699,17 +699,17 @@ public final class ServiceDiscoveryManager extends Manager {
|
|||
* @throws NotConnectedException
|
||||
* @throws InterruptedException
|
||||
*/
|
||||
public List<DomainBareJid> findServices(String feature, boolean stopOnFirst, boolean useCache)
|
||||
public List<DiscoverInfo> findServicesDiscoverInfo(String feature, boolean stopOnFirst, boolean useCache)
|
||||
throws NoResponseException, XMPPErrorException, NotConnectedException, InterruptedException {
|
||||
List<DomainBareJid> serviceAddresses = null;
|
||||
List<DiscoverInfo> serviceDiscoInfo = null;
|
||||
DomainBareJid serviceName = connection().getServiceName();
|
||||
if (useCache) {
|
||||
serviceAddresses = services.get(feature);
|
||||
if (serviceAddresses != null) {
|
||||
return serviceAddresses;
|
||||
serviceDiscoInfo = services.get(feature);
|
||||
if (serviceDiscoInfo != null) {
|
||||
return serviceDiscoInfo;
|
||||
}
|
||||
}
|
||||
serviceAddresses = new LinkedList<>();
|
||||
serviceDiscoInfo = new LinkedList<>();
|
||||
// Send the disco packet to the server itself
|
||||
DiscoverInfo info;
|
||||
try {
|
||||
|
@ -717,17 +717,17 @@ public final class ServiceDiscoveryManager extends Manager {
|
|||
} catch (XMPPErrorException e) {
|
||||
// Be extra robust here: Return the empty linked list and log this situation
|
||||
LOGGER.log(Level.WARNING, "Could not discover information about service", e);
|
||||
return serviceAddresses;
|
||||
return serviceDiscoInfo;
|
||||
}
|
||||
// Check if the server supports XEP-33
|
||||
// Check if the server supports the feature
|
||||
if (info.containsFeature(feature)) {
|
||||
serviceAddresses.add(serviceName);
|
||||
serviceDiscoInfo.add(info);
|
||||
if (stopOnFirst) {
|
||||
if (useCache) {
|
||||
// Cache the discovered information
|
||||
services.put(feature, serviceAddresses);
|
||||
services.put(feature, serviceDiscoInfo);
|
||||
}
|
||||
return serviceAddresses;
|
||||
return serviceDiscoInfo;
|
||||
}
|
||||
}
|
||||
DiscoverItems items;
|
||||
|
@ -736,7 +736,7 @@ public final class ServiceDiscoveryManager extends Manager {
|
|||
items = discoverItems(serviceName);
|
||||
} catch(XMPPErrorException e) {
|
||||
LOGGER.log(Level.WARNING, "Could not discover items about service", e);
|
||||
return serviceAddresses;
|
||||
return serviceDiscoInfo;
|
||||
}
|
||||
for (DiscoverItems.Item item : items.getItems()) {
|
||||
try {
|
||||
|
@ -752,7 +752,8 @@ public final class ServiceDiscoveryManager extends Manager {
|
|||
continue;
|
||||
}
|
||||
if (info.containsFeature(feature)) {
|
||||
serviceAddresses.add(item.getEntityID().asDomainBareJid());
|
||||
serviceDiscoInfo.add(info);
|
||||
//serviceAddresses.add(item.getEntityID().asDomainBareJid());
|
||||
if (stopOnFirst) {
|
||||
break;
|
||||
}
|
||||
|
@ -760,9 +761,54 @@ public final class ServiceDiscoveryManager extends Manager {
|
|||
}
|
||||
if (useCache) {
|
||||
// Cache the discovered information
|
||||
services.put(feature, serviceAddresses);
|
||||
services.put(feature, serviceDiscoInfo);
|
||||
}
|
||||
return serviceAddresses;
|
||||
return serviceDiscoInfo;
|
||||
}
|
||||
|
||||
/**
|
||||
* Find all services under the users service that provide a given feature.
|
||||
*
|
||||
* @param feature the feature to search for
|
||||
* @param stopOnFirst if true, stop searching after the first service was found
|
||||
* @param useCache if true, query a cache first to avoid network I/O
|
||||
* @return a possible empty list of services providing the given feature
|
||||
* @throws NoResponseException
|
||||
* @throws XMPPErrorException
|
||||
* @throws NotConnectedException
|
||||
* @throws InterruptedException
|
||||
*/
|
||||
public List<DomainBareJid> findServices(String feature, boolean stopOnFirst, boolean useCache) throws NoResponseException, XMPPErrorException, NotConnectedException, InterruptedException {
|
||||
List<DiscoverInfo> services = findServicesDiscoverInfo(feature, stopOnFirst, useCache);
|
||||
List<DomainBareJid> res = new ArrayList<>(services.size());
|
||||
for (DiscoverInfo info : services) {
|
||||
res.add(info.getFrom().asDomainBareJid());
|
||||
}
|
||||
return res;
|
||||
}
|
||||
|
||||
public DomainBareJid findService(String feature, boolean useCache, String category, String type)
|
||||
throws NoResponseException, XMPPErrorException, NotConnectedException,
|
||||
InterruptedException {
|
||||
List<DiscoverInfo> services = findServicesDiscoverInfo(feature, true, useCache);
|
||||
if (services.isEmpty()) {
|
||||
return null;
|
||||
}
|
||||
DiscoverInfo info = services.get(0);
|
||||
if (category != null && type != null) {
|
||||
if (!info.hasIdentity(category, type)) {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
else if (category != null || type != null) {
|
||||
throw new IllegalArgumentException("Must specify either both, category and type, or none");
|
||||
}
|
||||
return info.getFrom().asDomainBareJid();
|
||||
}
|
||||
|
||||
public DomainBareJid findService(String feature, boolean useCache) throws NoResponseException,
|
||||
XMPPErrorException, NotConnectedException, InterruptedException {
|
||||
return findService(feature, useCache, null, null);
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -16,13 +16,11 @@
|
|||
*/
|
||||
package org.jivesoftware.smackx.pubsub;
|
||||
|
||||
import org.jivesoftware.smack.XMPPConnection;
|
||||
|
||||
public class CollectionNode extends Node
|
||||
{
|
||||
CollectionNode(XMPPConnection connection, String nodeId)
|
||||
CollectionNode(PubSubManager pubSubManager, String nodeId)
|
||||
{
|
||||
super(connection, nodeId);
|
||||
super(pubSubManager, nodeId);
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -22,7 +22,6 @@ import java.util.List;
|
|||
|
||||
import org.jivesoftware.smack.SmackException.NoResponseException;
|
||||
import org.jivesoftware.smack.SmackException.NotConnectedException;
|
||||
import org.jivesoftware.smack.XMPPConnection;
|
||||
import org.jivesoftware.smack.XMPPException.XMPPErrorException;
|
||||
import org.jivesoftware.smack.packet.IQ.Type;
|
||||
import org.jivesoftware.smack.packet.ExtensionElement;
|
||||
|
@ -39,9 +38,9 @@ import org.jivesoftware.smackx.pubsub.packet.PubSub;
|
|||
*/
|
||||
public class LeafNode extends Node
|
||||
{
|
||||
LeafNode(XMPPConnection connection, String nodeName)
|
||||
LeafNode(PubSubManager pubSubManager, String nodeId)
|
||||
{
|
||||
super(connection, nodeName);
|
||||
super(pubSubManager, nodeId);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -57,9 +56,9 @@ public class LeafNode extends Node
|
|||
public DiscoverItems discoverItems() throws NoResponseException, XMPPErrorException, NotConnectedException, InterruptedException
|
||||
{
|
||||
DiscoverItems items = new DiscoverItems();
|
||||
items.setTo(to);
|
||||
items.setTo(pubSubManager.getServiceJid());
|
||||
items.setNode(getId());
|
||||
return (DiscoverItems) con.createPacketCollectorAndSend(items).nextResultOrThrow();
|
||||
return pubSubManager.getConnection().createPacketCollectorAndSend(items).nextResultOrThrow();
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -193,7 +192,7 @@ public class LeafNode extends Node
|
|||
private <T extends Item> List<T> getItems(PubSub request,
|
||||
List<ExtensionElement> returnedExtensions) throws NoResponseException,
|
||||
XMPPErrorException, NotConnectedException, InterruptedException {
|
||||
PubSub result = con.createPacketCollectorAndSend(request).nextResultOrThrow();
|
||||
PubSub result = pubSubManager.getConnection().createPacketCollectorAndSend(request).nextResultOrThrow();
|
||||
ItemsExtension itemsElem = result.getExtension(PubSubElementType.ITEMS);
|
||||
if (returnedExtensions != null) {
|
||||
returnedExtensions.addAll(result.getExtensions());
|
||||
|
@ -219,7 +218,7 @@ public class LeafNode extends Node
|
|||
{
|
||||
PubSub packet = createPubsubPacket(Type.set, new NodeExtension(PubSubElementType.PUBLISH, getId()));
|
||||
|
||||
con.sendStanza(packet);
|
||||
pubSubManager.getConnection().sendStanza(packet);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -266,7 +265,7 @@ public class LeafNode extends Node
|
|||
{
|
||||
PubSub packet = createPubsubPacket(Type.set, new PublishItem<T>(getId(), items));
|
||||
|
||||
con.sendStanza(packet);
|
||||
pubSubManager.getConnection().sendStanza(packet);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -290,7 +289,7 @@ public class LeafNode extends Node
|
|||
{
|
||||
PubSub packet = createPubsubPacket(Type.set, new NodeExtension(PubSubElementType.PUBLISH, getId()));
|
||||
|
||||
con.createPacketCollectorAndSend(packet).nextResultOrThrow();
|
||||
pubSubManager.getConnection().createPacketCollectorAndSend(packet).nextResultOrThrow();
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -347,7 +346,7 @@ public class LeafNode extends Node
|
|||
{
|
||||
PubSub packet = createPubsubPacket(Type.set, new PublishItem<T>(getId(), items));
|
||||
|
||||
con.createPacketCollectorAndSend(packet).nextResultOrThrow();
|
||||
pubSubManager.getConnection().createPacketCollectorAndSend(packet).nextResultOrThrow();
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -364,7 +363,7 @@ public class LeafNode extends Node
|
|||
{
|
||||
PubSub request = createPubsubPacket(Type.set, new NodeExtension(PubSubElementType.PURGE_OWNER, getId()), PubSubElementType.PURGE_OWNER.getNamespace());
|
||||
|
||||
con.createPacketCollectorAndSend(request).nextResultOrThrow();
|
||||
pubSubManager.getConnection().createPacketCollectorAndSend(request).nextResultOrThrow();
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -401,6 +400,6 @@ public class LeafNode extends Node
|
|||
items.add(new Item(id));
|
||||
}
|
||||
PubSub request = createPubsubPacket(Type.set, new ItemsExtension(ItemsExtension.ItemsElementType.retract, getId(), items));
|
||||
con.createPacketCollectorAndSend(request).nextResultOrThrow();
|
||||
pubSubManager.getConnection().createPacketCollectorAndSend(request).nextResultOrThrow();
|
||||
}
|
||||
}
|
||||
|
|
|
@ -24,7 +24,6 @@ import java.util.concurrent.ConcurrentHashMap;
|
|||
import org.jivesoftware.smack.StanzaListener;
|
||||
import org.jivesoftware.smack.SmackException.NoResponseException;
|
||||
import org.jivesoftware.smack.SmackException.NotConnectedException;
|
||||
import org.jivesoftware.smack.XMPPConnection;
|
||||
import org.jivesoftware.smack.XMPPException.XMPPErrorException;
|
||||
import org.jivesoftware.smack.filter.OrFilter;
|
||||
import org.jivesoftware.smack.filter.StanzaFilter;
|
||||
|
@ -43,13 +42,11 @@ import org.jivesoftware.smackx.pubsub.util.NodeUtils;
|
|||
import org.jivesoftware.smackx.shim.packet.Header;
|
||||
import org.jivesoftware.smackx.shim.packet.HeadersExtension;
|
||||
import org.jivesoftware.smackx.xdata.Form;
|
||||
import org.jxmpp.jid.Jid;
|
||||
|
||||
abstract public class Node
|
||||
{
|
||||
protected XMPPConnection con;
|
||||
protected String id;
|
||||
protected Jid to;
|
||||
protected final PubSubManager pubSubManager;
|
||||
protected final String id;
|
||||
|
||||
protected ConcurrentHashMap<ItemEventListener<Item>, StanzaListener> itemEventToListenerMap = new ConcurrentHashMap<ItemEventListener<Item>, StanzaListener>();
|
||||
protected ConcurrentHashMap<ItemDeleteListener, StanzaListener> itemDeleteToListenerMap = new ConcurrentHashMap<ItemDeleteListener, StanzaListener>();
|
||||
|
@ -62,21 +59,10 @@ abstract public class Node
|
|||
* @param connection The connection the node is associated with
|
||||
* @param nodeName The node id
|
||||
*/
|
||||
Node(XMPPConnection connection, String nodeName)
|
||||
Node(PubSubManager pubSubManager, String nodeId)
|
||||
{
|
||||
con = connection;
|
||||
id = nodeName;
|
||||
}
|
||||
|
||||
/**
|
||||
* Some XMPP servers may require a specific service to be addressed on the
|
||||
* server.
|
||||
*
|
||||
* For example, OpenFire requires the server to be prefixed by <b>pubsub</b>
|
||||
*/
|
||||
void setTo(Jid toAddress)
|
||||
{
|
||||
to = toAddress;
|
||||
this.pubSubManager = pubSubManager;
|
||||
id = nodeId;
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -119,7 +105,7 @@ abstract public class Node
|
|||
{
|
||||
PubSub packet = createPubsubPacket(Type.set, new FormNode(FormNodeType.CONFIGURE_OWNER,
|
||||
getId(), submitForm), PubSubNamespace.OWNER);
|
||||
con.createPacketCollectorAndSend(packet).nextResultOrThrow();
|
||||
pubSubManager.getConnection().createPacketCollectorAndSend(packet).nextResultOrThrow();
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -134,9 +120,9 @@ abstract public class Node
|
|||
public DiscoverInfo discoverInfo() throws NoResponseException, XMPPErrorException, NotConnectedException, InterruptedException
|
||||
{
|
||||
DiscoverInfo info = new DiscoverInfo();
|
||||
info.setTo(to);
|
||||
info.setTo(pubSubManager.getServiceJid());
|
||||
info.setNode(getId());
|
||||
return (DiscoverInfo) con.createPacketCollectorAndSend(info).nextResultOrThrow();
|
||||
return pubSubManager.getConnection().createPacketCollectorAndSend(info).nextResultOrThrow();
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -336,7 +322,7 @@ abstract public class Node
|
|||
PubSub request = createPubsubPacket(Type.set, new SubscribeExtension(jid, getId()));
|
||||
// CHECKSTYLE:ON
|
||||
request.addExtension(new FormNode(FormNodeType.OPTIONS, subForm));
|
||||
PubSub reply = PubSubManager.sendPubsubPacket(con, request);
|
||||
PubSub reply = sendPubsubPacket(request);
|
||||
return reply.getExtension(PubSubElementType.SUBSCRIPTION);
|
||||
}
|
||||
|
||||
|
@ -420,7 +406,7 @@ abstract public class Node
|
|||
{
|
||||
StanzaListener conListener = new ItemEventTranslator(listener);
|
||||
itemEventToListenerMap.put(listener, conListener);
|
||||
con.addSyncStanzaListener(conListener, new EventContentFilter(EventElementType.items.toString(), "item"));
|
||||
pubSubManager.getConnection().addSyncStanzaListener(conListener, new EventContentFilter(EventElementType.items.toString(), "item"));
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -433,7 +419,7 @@ abstract public class Node
|
|||
StanzaListener conListener = itemEventToListenerMap.remove(listener);
|
||||
|
||||
if (conListener != null)
|
||||
con.removeSyncStanzaListener(conListener);
|
||||
pubSubManager.getConnection().removeSyncStanzaListener(conListener);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -446,7 +432,7 @@ abstract public class Node
|
|||
{
|
||||
StanzaListener conListener = new NodeConfigTranslator(listener);
|
||||
configEventToListenerMap.put(listener, conListener);
|
||||
con.addSyncStanzaListener(conListener, new EventContentFilter(EventElementType.configuration.toString()));
|
||||
pubSubManager.getConnection().addSyncStanzaListener(conListener, new EventContentFilter(EventElementType.configuration.toString()));
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -459,7 +445,7 @@ abstract public class Node
|
|||
StanzaListener conListener = configEventToListenerMap .remove(listener);
|
||||
|
||||
if (conListener != null)
|
||||
con.removeSyncStanzaListener(conListener);
|
||||
pubSubManager.getConnection().removeSyncStanzaListener(conListener);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -475,7 +461,7 @@ abstract public class Node
|
|||
EventContentFilter deleteItem = new EventContentFilter(EventElementType.items.toString(), "retract");
|
||||
EventContentFilter purge = new EventContentFilter(EventElementType.purge.toString());
|
||||
|
||||
con.addSyncStanzaListener(delListener, new OrFilter(deleteItem, purge));
|
||||
pubSubManager.getConnection().addSyncStanzaListener(delListener, new OrFilter(deleteItem, purge));
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -488,7 +474,7 @@ abstract public class Node
|
|||
StanzaListener conListener = itemDeleteToListenerMap .remove(listener);
|
||||
|
||||
if (conListener != null)
|
||||
con.removeSyncStanzaListener(conListener);
|
||||
pubSubManager.getConnection().removeSyncStanzaListener(conListener);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -504,12 +490,12 @@ abstract public class Node
|
|||
|
||||
protected PubSub createPubsubPacket(Type type, ExtensionElement ext, PubSubNamespace ns)
|
||||
{
|
||||
return PubSub.createPubsubPacket(to, type, ext, ns);
|
||||
return PubSub.createPubsubPacket(pubSubManager.getServiceJid(), type, ext, ns);
|
||||
}
|
||||
|
||||
protected PubSub sendPubsubPacket(PubSub packet) throws NoResponseException, XMPPErrorException, NotConnectedException, InterruptedException
|
||||
{
|
||||
return PubSubManager.sendPubsubPacket(con, packet);
|
||||
return pubSubManager.sendPubsubPacket(packet);
|
||||
}
|
||||
|
||||
|
||||
|
|
|
@ -17,16 +17,22 @@
|
|||
package org.jivesoftware.smackx.pubsub;
|
||||
|
||||
import java.util.Collections;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.WeakHashMap;
|
||||
import java.util.concurrent.ConcurrentHashMap;
|
||||
import java.util.logging.Level;
|
||||
import java.util.logging.Logger;
|
||||
|
||||
import org.jivesoftware.smack.Manager;
|
||||
import org.jivesoftware.smack.SmackException.NoResponseException;
|
||||
import org.jivesoftware.smack.SmackException.NotConnectedException;
|
||||
import org.jivesoftware.smack.XMPPConnection;
|
||||
import org.jivesoftware.smack.XMPPException.XMPPErrorException;
|
||||
import org.jivesoftware.smack.packet.EmptyResultIQ;
|
||||
import org.jivesoftware.smack.packet.IQ;
|
||||
import org.jivesoftware.smack.packet.XMPPError;
|
||||
import org.jivesoftware.smack.packet.IQ.Type;
|
||||
import org.jivesoftware.smack.packet.Stanza;
|
||||
import org.jivesoftware.smack.packet.ExtensionElement;
|
||||
|
@ -52,24 +58,73 @@ import org.jxmpp.stringprep.XmppStringprepException;
|
|||
*
|
||||
* @author Robin Collier
|
||||
*/
|
||||
final public class PubSubManager
|
||||
{
|
||||
private XMPPConnection con;
|
||||
private DomainBareJid to;
|
||||
private Map<String, Node> nodeMap = new ConcurrentHashMap<String, Node>();
|
||||
public final class PubSubManager extends Manager {
|
||||
|
||||
/**
|
||||
* Create a pubsub manager associated to the specified connection. Defaults the service
|
||||
* name to <i>pubsub</i>
|
||||
*
|
||||
* @param connection The XMPP connection
|
||||
* @throws XmppStringprepException
|
||||
*/
|
||||
public PubSubManager(XMPPConnection connection) throws XmppStringprepException
|
||||
{
|
||||
con = connection;
|
||||
to = JidCreate.domainBareFrom("pubsub." + connection.getServiceName());
|
||||
}
|
||||
private static final Logger LOGGER = Logger.getLogger(PubSubManager.class.getName());
|
||||
private static final Map<XMPPConnection, Map<DomainBareJid, PubSubManager>> INSTANCES = new WeakHashMap<>();
|
||||
|
||||
/**
|
||||
* The JID of the PubSub service this manager manages.
|
||||
*/
|
||||
private final DomainBareJid pubSubService;
|
||||
|
||||
/**
|
||||
* A map of node IDs to Nodes, used to cache those Nodes. This does only cache the type of Node,
|
||||
* i.e. {@link CollectionNode} or {@link LeafNode}.
|
||||
*/
|
||||
private final Map<String, Node> nodeMap = new ConcurrentHashMap<String, Node>();
|
||||
|
||||
/**
|
||||
* Get a PubSub manager for the default PubSub service of the connection.
|
||||
*
|
||||
* @param connection
|
||||
* @return the default PubSub manager.
|
||||
*/
|
||||
public static PubSubManager getInstance(XMPPConnection connection) {
|
||||
DomainBareJid pubSubService = null;
|
||||
if (connection.isAuthenticated()) {
|
||||
try {
|
||||
pubSubService = getPubSubService(connection);
|
||||
}
|
||||
catch (NoResponseException | XMPPErrorException | NotConnectedException e) {
|
||||
LOGGER.log(Level.WARNING, "Could not determine PubSub service", e);
|
||||
}
|
||||
catch (InterruptedException e) {
|
||||
LOGGER.log(Level.FINE, "Interupted while trying to determine PubSub service", e);
|
||||
}
|
||||
}
|
||||
if (pubSubService == null) {
|
||||
try {
|
||||
// Perform an educated guess about what the PubSub service's domain bare JID may be
|
||||
pubSubService = JidCreate.domainBareFrom("pubsub." + connection.getServiceName());
|
||||
}
|
||||
catch (XmppStringprepException e) {
|
||||
throw new RuntimeException(e);
|
||||
}
|
||||
}
|
||||
return getInstance(connection, pubSubService);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the PubSub manager for the given connection and PubSub service.
|
||||
*
|
||||
* @param connection the XMPP connection.
|
||||
* @param pubSubService the PubSub service.
|
||||
* @return a PubSub manager for the connection and service.
|
||||
*/
|
||||
public static synchronized PubSubManager getInstance(XMPPConnection connection, DomainBareJid pubSubService) {
|
||||
Map<DomainBareJid, PubSubManager> managers = INSTANCES.get(connection);
|
||||
if (managers == null) {
|
||||
managers = new HashMap<>();
|
||||
INSTANCES.put(connection, managers);
|
||||
}
|
||||
PubSubManager pubSubManager = managers.get(pubSubService);
|
||||
if (pubSubManager == null) {
|
||||
pubSubManager = new PubSubManager(connection, pubSubService);
|
||||
managers.put(pubSubService, pubSubManager);
|
||||
}
|
||||
return pubSubManager;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a pubsub manager associated to the specified connection where
|
||||
|
@ -78,10 +133,10 @@ final public class PubSubManager
|
|||
* @param connection The XMPP connection
|
||||
* @param toAddress The pubsub specific to address (required for some servers)
|
||||
*/
|
||||
public PubSubManager(XMPPConnection connection, DomainBareJid toAddress)
|
||||
PubSubManager(XMPPConnection connection, DomainBareJid toAddress)
|
||||
{
|
||||
con = connection;
|
||||
to = toAddress;
|
||||
super(connection);
|
||||
pubSubService = toAddress;
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -98,8 +153,7 @@ final public class PubSubManager
|
|||
PubSub reply = sendPubsubPacket(Type.set, new NodeExtension(PubSubElementType.CREATE), null);
|
||||
NodeExtension elem = reply.getExtension("create", PubSubNamespace.BASIC.getXmlns());
|
||||
|
||||
LeafNode newNode = new LeafNode(con, elem.getNode());
|
||||
newNode.setTo(to);
|
||||
LeafNode newNode = new LeafNode(this, elem.getNode());
|
||||
nodeMap.put(newNode.getId(), newNode);
|
||||
|
||||
return newNode;
|
||||
|
@ -108,7 +162,7 @@ final public class PubSubManager
|
|||
/**
|
||||
* Creates a node with default configuration.
|
||||
*
|
||||
* @param id The id of the node, which must be unique within the
|
||||
* @param nodeId The id of the node, which must be unique within the
|
||||
* pubsub service
|
||||
* @return The node that was created
|
||||
* @throws XMPPErrorException
|
||||
|
@ -116,9 +170,9 @@ final public class PubSubManager
|
|||
* @throws NotConnectedException
|
||||
* @throws InterruptedException
|
||||
*/
|
||||
public LeafNode createNode(String id) throws NoResponseException, XMPPErrorException, NotConnectedException, InterruptedException
|
||||
public LeafNode createNode(String nodeId) throws NoResponseException, XMPPErrorException, NotConnectedException, InterruptedException
|
||||
{
|
||||
return (LeafNode)createNode(id, null);
|
||||
return (LeafNode) createNode(nodeId, null);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -126,7 +180,7 @@ final public class PubSubManager
|
|||
*
|
||||
* Note: This is the only way to create a collection node.
|
||||
*
|
||||
* @param name The name of the node, which must be unique within the
|
||||
* @param nodeId The name of the node, which must be unique within the
|
||||
* pubsub service
|
||||
* @param config The configuration for the node
|
||||
* @return The node that was created
|
||||
|
@ -135,9 +189,9 @@ final public class PubSubManager
|
|||
* @throws NotConnectedException
|
||||
* @throws InterruptedException
|
||||
*/
|
||||
public Node createNode(String name, Form config) throws NoResponseException, XMPPErrorException, NotConnectedException, InterruptedException
|
||||
public Node createNode(String nodeId, Form config) throws NoResponseException, XMPPErrorException, NotConnectedException, InterruptedException
|
||||
{
|
||||
PubSub request = PubSub.createPubsubPacket(to, Type.set, new NodeExtension(PubSubElementType.CREATE, name), null);
|
||||
PubSub request = PubSub.createPubsubPacket(pubSubService, Type.set, new NodeExtension(PubSubElementType.CREATE, nodeId), null);
|
||||
boolean isLeafNode = true;
|
||||
|
||||
if (config != null)
|
||||
|
@ -151,9 +205,8 @@ final public class PubSubManager
|
|||
|
||||
// Errors will cause exceptions in getReply, so it only returns
|
||||
// on success.
|
||||
sendPubsubPacket(con, request);
|
||||
Node newNode = isLeafNode ? new LeafNode(con, name) : new CollectionNode(con, name);
|
||||
newNode.setTo(to);
|
||||
sendPubsubPacket(request);
|
||||
Node newNode = isLeafNode ? new LeafNode(this, nodeId) : new CollectionNode(this, nodeId);
|
||||
nodeMap.put(newNode.getId(), newNode);
|
||||
|
||||
return newNode;
|
||||
|
@ -177,16 +230,16 @@ final public class PubSubManager
|
|||
if (node == null)
|
||||
{
|
||||
DiscoverInfo info = new DiscoverInfo();
|
||||
info.setTo(to);
|
||||
info.setTo(pubSubService);
|
||||
info.setNode(id);
|
||||
|
||||
DiscoverInfo infoReply = (DiscoverInfo) con.createPacketCollectorAndSend(info).nextResultOrThrow();
|
||||
DiscoverInfo infoReply = connection().createPacketCollectorAndSend(info).nextResultOrThrow();
|
||||
|
||||
if (infoReply.hasIdentity(PubSub.ELEMENT, "leaf")) {
|
||||
node = new LeafNode(con, id);
|
||||
node = new LeafNode(this, id);
|
||||
}
|
||||
else if (infoReply.hasIdentity(PubSub.ELEMENT, "collection")) {
|
||||
node = new CollectionNode(con, id);
|
||||
node = new CollectionNode(this, id);
|
||||
}
|
||||
else {
|
||||
// XEP-60 5.3 states that
|
||||
|
@ -194,12 +247,11 @@ final public class PubSubManager
|
|||
// If this is not the case, then we are dealing with an PubSub implementation that doesn't follow the specification.
|
||||
throw new AssertionError(
|
||||
"PubSub service '"
|
||||
+ to
|
||||
+ pubSubService
|
||||
+ "' returned disco info result for node '"
|
||||
+ id
|
||||
+ "', but it did not contain an Identity of type 'leaf' or 'collection' (and category 'pubsub'), which is not allowed according to XEP-60 5.3.");
|
||||
}
|
||||
node.setTo(to);
|
||||
nodeMap.put(id, node);
|
||||
}
|
||||
@SuppressWarnings("unchecked")
|
||||
|
@ -229,8 +281,8 @@ final public class PubSubManager
|
|||
|
||||
if (nodeId != null)
|
||||
items.setNode(nodeId);
|
||||
items.setTo(to);
|
||||
DiscoverItems nodeItems = (DiscoverItems) con.createPacketCollectorAndSend(items).nextResultOrThrow();
|
||||
items.setTo(pubSubService);
|
||||
DiscoverItems nodeItems = connection().createPacketCollectorAndSend(items).nextResultOrThrow();
|
||||
return nodeItems;
|
||||
}
|
||||
|
||||
|
@ -299,6 +351,15 @@ final public class PubSubManager
|
|||
return NodeUtils.getFormFromPacket(reply, PubSubElementType.DEFAULT);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the JID of the PubSub service managed by this manager.
|
||||
*
|
||||
* @return the JID of the PubSub service.
|
||||
*/
|
||||
public DomainBareJid getServiceJid() {
|
||||
return pubSubService;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the supported features of the servers pubsub implementation
|
||||
* as a standard {@link DiscoverInfo} instance.
|
||||
|
@ -311,33 +372,92 @@ final public class PubSubManager
|
|||
*/
|
||||
public DiscoverInfo getSupportedFeatures() throws NoResponseException, XMPPErrorException, NotConnectedException, InterruptedException
|
||||
{
|
||||
ServiceDiscoveryManager mgr = ServiceDiscoveryManager.getInstanceFor(con);
|
||||
return mgr.discoverInfo(to);
|
||||
ServiceDiscoveryManager mgr = ServiceDiscoveryManager.getInstanceFor(connection());
|
||||
return mgr.discoverInfo(pubSubService);
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if it is possible to create PubSub nodes on this service. It could be possible that the
|
||||
* PubSub service allows only certain XMPP entities (clients) to create nodes and publish items
|
||||
* to them.
|
||||
* <p>
|
||||
* Note that since XEP-60 does not provide an API to determine if an XMPP entity is allowed to
|
||||
* create nodes, therefore this method creates an instant node calling {@link #createNode()} to
|
||||
* determine if it is possible to create nodes.
|
||||
* </p>
|
||||
*
|
||||
* @return <code>true</code> if it is possible to create nodes, <code>false</code> otherwise.
|
||||
* @throws NoResponseException
|
||||
* @throws NotConnectedException
|
||||
* @throws InterruptedException
|
||||
* @throws XMPPErrorException
|
||||
*/
|
||||
public boolean canCreateNodesAndPublishItems() throws NoResponseException, NotConnectedException, InterruptedException, XMPPErrorException {
|
||||
LeafNode leafNode = null;
|
||||
try {
|
||||
leafNode = createNode();
|
||||
}
|
||||
catch (XMPPErrorException e) {
|
||||
if (e.getXMPPError().getCondition() == XMPPError.Condition.forbidden) {
|
||||
return false;
|
||||
}
|
||||
throw e;
|
||||
} finally {
|
||||
if (leafNode != null) {
|
||||
deleteNode(leafNode.getId());
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
private PubSub sendPubsubPacket(Type type, ExtensionElement ext, PubSubNamespace ns)
|
||||
throws NoResponseException, XMPPErrorException, NotConnectedException, InterruptedException {
|
||||
return sendPubsubPacket(con, to, type, Collections.singletonList(ext), ns);
|
||||
return sendPubsubPacket(pubSubService, type, Collections.singletonList(ext), ns);
|
||||
}
|
||||
|
||||
static PubSub sendPubsubPacket(XMPPConnection con, Jid to, Type type, List<ExtensionElement> extList, PubSubNamespace ns) throws NoResponseException, XMPPErrorException, NotConnectedException, InterruptedException
|
||||
{
|
||||
XMPPConnection getConnection() {
|
||||
return connection();
|
||||
}
|
||||
|
||||
PubSub sendPubsubPacket(Jid to, Type type, List<ExtensionElement> extList, PubSubNamespace ns)
|
||||
throws NoResponseException, XMPPErrorException, NotConnectedException,
|
||||
InterruptedException {
|
||||
// CHECKSTYLE:OFF
|
||||
PubSub pubSub = new PubSub(to, type, ns);
|
||||
for (ExtensionElement pe : extList) {
|
||||
pubSub.addExtension(pe);
|
||||
}
|
||||
// CHECKSTYLE:ON
|
||||
return sendPubsubPacket(con ,pubSub);
|
||||
return sendPubsubPacket(pubSub);
|
||||
}
|
||||
|
||||
static PubSub sendPubsubPacket(XMPPConnection con, PubSub packet) throws NoResponseException, XMPPErrorException, NotConnectedException, InterruptedException
|
||||
{
|
||||
IQ resultIQ = con.createPacketCollectorAndSend(packet).nextResultOrThrow();
|
||||
PubSub sendPubsubPacket(PubSub packet) throws NoResponseException, XMPPErrorException,
|
||||
NotConnectedException, InterruptedException {
|
||||
IQ resultIQ = connection().createPacketCollectorAndSend(packet).nextResultOrThrow();
|
||||
if (resultIQ instanceof EmptyResultIQ) {
|
||||
return null;
|
||||
}
|
||||
return (PubSub) resultIQ;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the "default" PubSub service for a given XMPP connection. The default PubSub service is
|
||||
* simply an arbitrary XMPP service with the PubSub feature and an identity of category "pubsub"
|
||||
* and type "service".
|
||||
*
|
||||
* @param connection
|
||||
* @return the default PubSub service or <code>null</code>.
|
||||
* @throws NoResponseException
|
||||
* @throws XMPPErrorException
|
||||
* @throws NotConnectedException
|
||||
* @throws InterruptedException
|
||||
* @see <a href="http://xmpp.org/extensions/xep-0060.html#entity-features">XEP-60 § 5.1 Discover
|
||||
* Features</a>
|
||||
*/
|
||||
public static DomainBareJid getPubSubService(XMPPConnection connection)
|
||||
throws NoResponseException, XMPPErrorException, NotConnectedException,
|
||||
InterruptedException {
|
||||
return ServiceDiscoveryManager.getInstanceFor(connection).findService(PubSub.NAMESPACE,
|
||||
true, "pubsub", "service");
|
||||
}
|
||||
}
|
||||
|
|
|
@ -16,6 +16,6 @@
|
|||
*/
|
||||
|
||||
/**
|
||||
* TODO describe me.
|
||||
* Listeners for Publish-Subscribe (XEP-60) events.
|
||||
*/
|
||||
package org.jivesoftware.smackx.pubsub.listener;
|
||||
|
|
|
@ -16,6 +16,6 @@
|
|||
*/
|
||||
|
||||
/**
|
||||
* TODO describe me.
|
||||
* Smack's API for XEP-60: Publish-Subscribe.
|
||||
*/
|
||||
package org.jivesoftware.smackx.pubsub;
|
||||
|
|
|
@ -16,6 +16,6 @@
|
|||
*/
|
||||
|
||||
/**
|
||||
* TODO describe me.
|
||||
* Stanzas and extension elements for Publish-Subscribe (XEP-60).
|
||||
*/
|
||||
package org.jivesoftware.smackx.pubsub.packet;
|
||||
|
|
|
@ -16,6 +16,6 @@
|
|||
*/
|
||||
|
||||
/**
|
||||
* TODO describe me.
|
||||
* Providers for Publish-Subscribe (XEP-60).
|
||||
*/
|
||||
package org.jivesoftware.smackx.pubsub.provider;
|
||||
|
|
|
@ -16,6 +16,6 @@
|
|||
*/
|
||||
|
||||
/**
|
||||
* TODO describe me.
|
||||
* Utilities for Publish-Subscribe (XEP-60).
|
||||
*/
|
||||
package org.jivesoftware.smackx.pubsub.util;
|
||||
|
|
|
@ -54,7 +54,7 @@ public class ConfigureFormTest
|
|||
public void getConfigFormWithInsufficientPriviliges() throws XMPPException, SmackException, IOException, InterruptedException
|
||||
{
|
||||
ThreadedDummyConnection con = ThreadedDummyConnection.newInstance();
|
||||
PubSubManager mgr = new PubSubManager(con);
|
||||
PubSubManager mgr = new PubSubManager(con, PubSubManagerTest.DUMMY_PUBSUB_SERVICE);
|
||||
DiscoverInfo info = new DiscoverInfo();
|
||||
Identity ident = new Identity("pubsub", null, "leaf");
|
||||
info.addIdentity(ident);
|
||||
|
@ -81,7 +81,7 @@ public class ConfigureFormTest
|
|||
public void getConfigFormWithTimeout() throws XMPPException, SmackException, InterruptedException, XmppStringprepException
|
||||
{
|
||||
ThreadedDummyConnection con = new ThreadedDummyConnection();
|
||||
PubSubManager mgr = new PubSubManager(con);
|
||||
PubSubManager mgr = new PubSubManager(con, PubSubManagerTest.DUMMY_PUBSUB_SERVICE);
|
||||
DiscoverInfo info = new DiscoverInfo();
|
||||
Identity ident = new Identity("pubsub", null, "leaf");
|
||||
info.addIdentity(ident);
|
||||
|
|
|
@ -25,13 +25,29 @@ import org.jivesoftware.smack.ThreadedDummyConnection;
|
|||
import org.jivesoftware.smack.XMPPException;
|
||||
import org.jivesoftware.smackx.pubsub.packet.PubSub;
|
||||
import org.junit.Test;
|
||||
import org.jxmpp.jid.DomainBareJid;
|
||||
import org.jxmpp.jid.impl.JidCreate;
|
||||
import org.jxmpp.stringprep.XmppStringprepException;
|
||||
|
||||
public class PubSubManagerTest {
|
||||
|
||||
public static final DomainBareJid DUMMY_PUBSUB_SERVICE;
|
||||
|
||||
static {
|
||||
DomainBareJid pubSubService;
|
||||
try {
|
||||
pubSubService = JidCreate.domainBareFrom("pubsub.dummy.org");
|
||||
}
|
||||
catch (XmppStringprepException e) {
|
||||
throw new AssertionError(e);
|
||||
}
|
||||
DUMMY_PUBSUB_SERVICE = pubSubService;
|
||||
}
|
||||
|
||||
@Test
|
||||
public void deleteNodeTest() throws InterruptedException, SmackException, IOException, XMPPException {
|
||||
ThreadedDummyConnection con = ThreadedDummyConnection.newInstance();
|
||||
PubSubManager mgr = new PubSubManager(con);
|
||||
PubSubManager mgr = new PubSubManager(con, DUMMY_PUBSUB_SERVICE);
|
||||
|
||||
mgr.deleteNode("foo@bar.org");
|
||||
|
||||
|
|
|
@ -0,0 +1,66 @@
|
|||
/**
|
||||
*
|
||||
* Copyright 2015 Florian Schmaus
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package org.jivesoftware.smackx.pubsub;
|
||||
|
||||
import static org.junit.Assert.assertEquals;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import org.igniterealtime.smack.inttest.AbstractSmackIntegrationTest;
|
||||
import org.igniterealtime.smack.inttest.SmackIntegrationTest;
|
||||
import org.igniterealtime.smack.inttest.SmackIntegrationTestEnvironment;
|
||||
import org.igniterealtime.smack.inttest.TestNotPossibleException;
|
||||
import org.jivesoftware.smack.SmackException.NoResponseException;
|
||||
import org.jivesoftware.smack.SmackException.NotConnectedException;
|
||||
import org.jivesoftware.smack.XMPPException.XMPPErrorException;
|
||||
import org.jxmpp.jid.DomainBareJid;
|
||||
|
||||
public class PubSubIntegrationTest extends AbstractSmackIntegrationTest {
|
||||
|
||||
private final PubSubManager pubSubManagerOne;
|
||||
|
||||
public PubSubIntegrationTest(SmackIntegrationTestEnvironment environment)
|
||||
throws TestNotPossibleException, NoResponseException, XMPPErrorException,
|
||||
NotConnectedException, InterruptedException {
|
||||
super(environment);
|
||||
DomainBareJid pubSubService = PubSubManager.getPubSubService(conOne);
|
||||
if (pubSubService == null) {
|
||||
throw new TestNotPossibleException("No PubSub service found");
|
||||
}
|
||||
pubSubManagerOne = PubSubManager.getInstance(conOne, pubSubService);
|
||||
if (!pubSubManagerOne.canCreateNodesAndPublishItems()) {
|
||||
throw new TestNotPossibleException("PubSub service does not allow node creation");
|
||||
}
|
||||
}
|
||||
|
||||
@SmackIntegrationTest
|
||||
public void simplePubSubNodeTest() throws NoResponseException, XMPPErrorException, NotConnectedException, InterruptedException {
|
||||
final String nodename = "sinttest-simple-nodename-" + testRunId;
|
||||
final String itemId = "sintest-simple-itemid-" + testRunId;
|
||||
LeafNode leafNode = pubSubManagerOne.createNode(nodename);
|
||||
try {
|
||||
leafNode.publish(new Item(itemId));
|
||||
List<Item> items = leafNode.getItems();
|
||||
assertEquals(1, items.size());
|
||||
Item item = items.get(0);
|
||||
assertEquals(itemId, item.getId());
|
||||
}
|
||||
finally {
|
||||
pubSubManagerOne.deleteNode(nodename);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -0,0 +1 @@
|
|||
../../../../../../../../smack-extensions/src/main/java/org/jivesoftware/smackx/pubsub/package-info.java
|
Loading…
Reference in a new issue