mirror of
https://codeberg.org/Mercury-IM/Smack
synced 2024-11-26 08:12:05 +01:00
Rework smackx.address (XEP-0033: Extended Stanza Addressing)
- Make MultipleAddress.Type a enum - Change the signature of the methods to use Collection instead of List - Use for-each loops instead of iterators - Switch Provider to new provider pattern (using switch-case) - Use XmlStringBuilder (extend the API by two new methods)
This commit is contained in:
parent
36da216b4a
commit
fe74fc23dc
5 changed files with 108 additions and 109 deletions
|
@ -98,6 +98,10 @@ public class XmlStringBuilder implements Appendable, CharSequence {
|
|||
return this;
|
||||
}
|
||||
|
||||
public XmlStringBuilder halfOpenElement(NamedElement namedElement) {
|
||||
return halfOpenElement(namedElement.getElementName());
|
||||
}
|
||||
|
||||
public XmlStringBuilder openElement(String name) {
|
||||
halfOpenElement(name).rightAngleBracket();
|
||||
return this;
|
||||
|
@ -207,6 +211,13 @@ public class XmlStringBuilder implements Appendable, CharSequence {
|
|||
return this;
|
||||
}
|
||||
|
||||
public XmlStringBuilder optBooleanAttribute(String name, boolean bool) {
|
||||
if (bool) {
|
||||
sb.append(' ').append(name).append("='true'");
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
public XmlStringBuilder xmlnsAttribute(String value) {
|
||||
optAttribute("xmlns", value);
|
||||
return this;
|
||||
|
|
|
@ -42,7 +42,7 @@ public class MultipleRecipientInfo {
|
|||
* @return list of primary recipients of the packet.
|
||||
*/
|
||||
public List<MultipleAddresses.Address> getTOAddresses() {
|
||||
return extension.getAddressesOfType(MultipleAddresses.TO);
|
||||
return extension.getAddressesOfType(MultipleAddresses.Type.to);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -52,7 +52,7 @@ public class MultipleRecipientInfo {
|
|||
* @return list of secondary recipients of the packet.
|
||||
*/
|
||||
public List<MultipleAddresses.Address> getCCAddresses() {
|
||||
return extension.getAddressesOfType(MultipleAddresses.CC);
|
||||
return extension.getAddressesOfType(MultipleAddresses.Type.cc);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -65,7 +65,7 @@ public class MultipleRecipientInfo {
|
|||
* no specific address was provided.
|
||||
*/
|
||||
public String getReplyRoom() {
|
||||
List<MultipleAddresses.Address> replyRoom = extension.getAddressesOfType(MultipleAddresses.REPLY_ROOM);
|
||||
List<MultipleAddresses.Address> replyRoom = extension.getAddressesOfType(MultipleAddresses.Type.replyroom);
|
||||
return replyRoom.isEmpty() ? null : ((MultipleAddresses.Address) replyRoom.get(0)).getJid();
|
||||
}
|
||||
|
||||
|
@ -77,7 +77,7 @@ public class MultipleRecipientInfo {
|
|||
* @return true if the received packet should not be replied.
|
||||
*/
|
||||
public boolean shouldNotReply() {
|
||||
return !extension.getAddressesOfType(MultipleAddresses.NO_REPLY).isEmpty();
|
||||
return !extension.getAddressesOfType(MultipleAddresses.Type.noreply).isEmpty();
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -89,7 +89,7 @@ public class MultipleRecipientInfo {
|
|||
* no specific address was provided.
|
||||
*/
|
||||
public MultipleAddresses.Address getReplyAddress() {
|
||||
List<MultipleAddresses.Address> replyTo = extension.getAddressesOfType(MultipleAddresses.REPLY_TO);
|
||||
List<MultipleAddresses.Address> replyTo = extension.getAddressesOfType(MultipleAddresses.Type.replyto);
|
||||
return replyTo.isEmpty() ? null : (MultipleAddresses.Address) replyTo.get(0);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -30,7 +30,7 @@ import org.jivesoftware.smackx.disco.ServiceDiscoveryManager;
|
|||
import org.jxmpp.util.XmppStringUtils;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Iterator;
|
||||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
|
@ -43,7 +43,7 @@ import java.util.List;
|
|||
public class MultipleRecipientManager {
|
||||
|
||||
/**
|
||||
* Sends the specified packet to the list of specified recipients using the
|
||||
* Sends the specified packet to the collection of specified recipients using the
|
||||
* specified connection. If the server has support for XEP-33 then only one
|
||||
* packet is going to be sent to the server with the multiple recipient instructions.
|
||||
* However, if XEP-33 is not supported by the server then the client is going to send
|
||||
|
@ -51,11 +51,11 @@ public class MultipleRecipientManager {
|
|||
*
|
||||
* @param connection the connection to use to send the packet.
|
||||
* @param packet the packet to send to the list of recipients.
|
||||
* @param to the list of JIDs to include in the TO list or <tt>null</tt> if no TO
|
||||
* @param to the collection of JIDs to include in the TO list or <tt>null</tt> if no TO
|
||||
* list exists.
|
||||
* @param cc the list of JIDs to include in the CC list or <tt>null</tt> if no CC
|
||||
* @param cc the collection of JIDs to include in the CC list or <tt>null</tt> if no CC
|
||||
* list exists.
|
||||
* @param bcc the list of JIDs to include in the BCC list or <tt>null</tt> if no BCC
|
||||
* @param bcc the collection of JIDs to include in the BCC list or <tt>null</tt> if no BCC
|
||||
* list exists.
|
||||
* @throws FeatureNotSupportedException if special XEP-33 features where requested, but the
|
||||
* server does not support them.
|
||||
|
@ -64,22 +64,22 @@ public class MultipleRecipientManager {
|
|||
* @throws NoResponseException if there was no response from the server.
|
||||
* @throws NotConnectedException
|
||||
*/
|
||||
public static void send(XMPPConnection connection, Packet packet, List<String> to, List<String> cc, List<String> bcc) throws NoResponseException, XMPPErrorException, FeatureNotSupportedException, NotConnectedException
|
||||
public static void send(XMPPConnection connection, Packet packet, Collection<String> to, Collection<String> cc, Collection<String> bcc) throws NoResponseException, XMPPErrorException, FeatureNotSupportedException, NotConnectedException
|
||||
{
|
||||
send(connection, packet, to, cc, bcc, null, null, false);
|
||||
}
|
||||
|
||||
/**
|
||||
* Sends the specified packet to the list of specified recipients using the specified
|
||||
* Sends the specified packet to the collection of specified recipients using the specified
|
||||
* connection. If the server has support for XEP-33 then only one packet is going to be sent to
|
||||
* the server with the multiple recipient instructions. However, if XEP-33 is not supported by
|
||||
* the server then the client is going to send the packet to each recipient.
|
||||
*
|
||||
* @param connection the connection to use to send the packet.
|
||||
* @param packet the packet to send to the list of recipients.
|
||||
* @param to the list of JIDs to include in the TO list or <tt>null</tt> if no TO list exists.
|
||||
* @param cc the list of JIDs to include in the CC list or <tt>null</tt> if no CC list exists.
|
||||
* @param bcc the list of JIDs to include in the BCC list or <tt>null</tt> if no BCC list
|
||||
* @param to the collection of JIDs to include in the TO list or <tt>null</tt> if no TO list exists.
|
||||
* @param cc the collection of JIDs to include in the CC list or <tt>null</tt> if no CC list exists.
|
||||
* @param bcc the collection of JIDs to include in the BCC list or <tt>null</tt> if no BCC list
|
||||
* exists.
|
||||
* @param replyTo address to which all replies are requested to be sent or <tt>null</tt>
|
||||
* indicating that they can reply to any address.
|
||||
|
@ -93,7 +93,7 @@ public class MultipleRecipientManager {
|
|||
* server does not support them.
|
||||
* @throws NotConnectedException
|
||||
*/
|
||||
public static void send(XMPPConnection connection, Packet packet, List<String> to, List<String> cc, List<String> bcc,
|
||||
public static void send(XMPPConnection connection, Packet packet, Collection<String> to, Collection<String> cc, Collection<String> bcc,
|
||||
String replyTo, String replyRoom, boolean noReply) throws NoResponseException, XMPPErrorException, FeatureNotSupportedException, NotConnectedException {
|
||||
String serviceAddress = getMultipleRecipienServiceAddress(connection);
|
||||
if (serviceAddress != null) {
|
||||
|
@ -149,15 +149,13 @@ public class MultipleRecipientManager {
|
|||
}
|
||||
else {
|
||||
// Send reply to multiple recipients
|
||||
List<String> to = new ArrayList<String>();
|
||||
List<String> cc = new ArrayList<String>();
|
||||
for (Iterator<MultipleAddresses.Address> it = info.getTOAddresses().iterator(); it.hasNext();) {
|
||||
String jid = it.next().getJid();
|
||||
to.add(jid);
|
||||
List<String> to = new ArrayList<String>(info.getTOAddresses().size());
|
||||
List<String> cc = new ArrayList<String>(info.getCCAddresses().size());
|
||||
for (MultipleAddresses.Address jid : info.getTOAddresses()) {
|
||||
to.add(jid.getJid());
|
||||
}
|
||||
for (Iterator<MultipleAddresses.Address> it = info.getCCAddresses().iterator(); it.hasNext();) {
|
||||
String jid = it.next().getJid();
|
||||
cc.add(jid);
|
||||
for (MultipleAddresses.Address jid : info.getCCAddresses()) {
|
||||
cc.add(jid.getJid());
|
||||
}
|
||||
// Add original sender as a 'to' address (if not already present)
|
||||
if (!to.contains(original.getFrom()) && !cc.contains(original.getFrom())) {
|
||||
|
@ -171,16 +169,7 @@ public class MultipleRecipientManager {
|
|||
cc.remove(bareJID);
|
||||
}
|
||||
|
||||
String serviceAddress = getMultipleRecipienServiceAddress(connection);
|
||||
if (serviceAddress != null) {
|
||||
// Send packet to target users using multiple recipient service provided by the server
|
||||
sendThroughService(connection, reply, to, cc, null, null, null, false,
|
||||
serviceAddress);
|
||||
}
|
||||
else {
|
||||
// Server does not support XEP-33 so try to send the packet to each recipient
|
||||
sendToIndividualRecipients(connection, reply, to, cc, null);
|
||||
}
|
||||
send(connection, reply, to, cc, null, null, null, false);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -200,51 +189,45 @@ public class MultipleRecipientManager {
|
|||
}
|
||||
|
||||
private static void sendToIndividualRecipients(XMPPConnection connection, Packet packet,
|
||||
List<String> to, List<String> cc, List<String> bcc) throws NotConnectedException {
|
||||
Collection<String> to, Collection<String> cc, Collection<String> bcc) throws NotConnectedException {
|
||||
if (to != null) {
|
||||
for (Iterator<String> it = to.iterator(); it.hasNext();) {
|
||||
String jid = it.next();
|
||||
for (String jid : to) {
|
||||
packet.setTo(jid);
|
||||
connection.sendPacket(new PacketCopy(packet.toXML()));
|
||||
}
|
||||
}
|
||||
if (cc != null) {
|
||||
for (Iterator<String> it = cc.iterator(); it.hasNext();) {
|
||||
String jid = it.next();
|
||||
for (String jid : cc) {
|
||||
packet.setTo(jid);
|
||||
connection.sendPacket(new PacketCopy(packet.toXML()));
|
||||
}
|
||||
}
|
||||
if (bcc != null) {
|
||||
for (Iterator<String> it = bcc.iterator(); it.hasNext();) {
|
||||
String jid = it.next();
|
||||
for (String jid : bcc) {
|
||||
packet.setTo(jid);
|
||||
connection.sendPacket(new PacketCopy(packet.toXML()));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private static void sendThroughService(XMPPConnection connection, Packet packet, List<String> to,
|
||||
List<String> cc, List<String> bcc, String replyTo, String replyRoom, boolean noReply,
|
||||
private static void sendThroughService(XMPPConnection connection, Packet packet, Collection<String> to,
|
||||
Collection<String> cc, Collection<String> bcc, String replyTo, String replyRoom, boolean noReply,
|
||||
String serviceAddress) throws NotConnectedException {
|
||||
// Create multiple recipient extension
|
||||
MultipleAddresses multipleAddresses = new MultipleAddresses();
|
||||
if (to != null) {
|
||||
for (Iterator<String> it = to.iterator(); it.hasNext();) {
|
||||
String jid = it.next();
|
||||
multipleAddresses.addAddress(MultipleAddresses.TO, jid, null, null, false, null);
|
||||
for (String jid : to) {
|
||||
multipleAddresses.addAddress(MultipleAddresses.Type.to, jid, null, null, false, null);
|
||||
}
|
||||
}
|
||||
if (cc != null) {
|
||||
for (Iterator<String> it = cc.iterator(); it.hasNext();) {
|
||||
String jid = it.next();
|
||||
multipleAddresses.addAddress(MultipleAddresses.CC, jid, null, null, false, null);
|
||||
for (String jid : cc) {
|
||||
multipleAddresses.addAddress(MultipleAddresses.Type.to, jid, null, null, false, null);
|
||||
}
|
||||
}
|
||||
if (bcc != null) {
|
||||
for (Iterator<String> it = bcc.iterator(); it.hasNext();) {
|
||||
String jid = it.next();
|
||||
multipleAddresses.addAddress(MultipleAddresses.BCC, jid, null, null, false, null);
|
||||
for (String jid : bcc) {
|
||||
multipleAddresses.addAddress(MultipleAddresses.Type.bcc, jid, null, null, false, null);
|
||||
}
|
||||
}
|
||||
if (noReply) {
|
||||
|
@ -253,10 +236,10 @@ public class MultipleRecipientManager {
|
|||
else {
|
||||
if (replyTo != null && replyTo.trim().length() > 0) {
|
||||
multipleAddresses
|
||||
.addAddress(MultipleAddresses.REPLY_TO, replyTo, null, null, false, null);
|
||||
.addAddress(MultipleAddresses.Type.replyto, replyTo, null, null, false, null);
|
||||
}
|
||||
if (replyRoom != null && replyRoom.trim().length() > 0) {
|
||||
multipleAddresses.addAddress(MultipleAddresses.REPLY_ROOM, replyRoom, null, null,
|
||||
multipleAddresses.addAddress(MultipleAddresses.Type.replyroom, replyRoom, null, null,
|
||||
false, null);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -17,10 +17,11 @@
|
|||
|
||||
package org.jivesoftware.smackx.address.packet;
|
||||
|
||||
import org.jivesoftware.smack.packet.NamedElement;
|
||||
import org.jivesoftware.smack.packet.PacketExtension;
|
||||
import org.jivesoftware.smack.util.XmlStringBuilder;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
|
@ -33,13 +34,14 @@ public class MultipleAddresses implements PacketExtension {
|
|||
public static final String NAMESPACE = "http://jabber.org/protocol/address";
|
||||
public static final String ELEMENT = "addresses";
|
||||
|
||||
public static final String BCC = "bcc";
|
||||
public static final String CC = "cc";
|
||||
public static final String NO_REPLY = "noreply";
|
||||
public static final String REPLY_ROOM = "replyroom";
|
||||
public static final String REPLY_TO = "replyto";
|
||||
public static final String TO = "to";
|
||||
|
||||
public enum Type {
|
||||
bcc,
|
||||
cc,
|
||||
noreply,
|
||||
replyroom,
|
||||
replyto,
|
||||
to,
|
||||
}
|
||||
|
||||
private List<Address> addresses = new ArrayList<Address>();
|
||||
|
||||
|
@ -54,7 +56,7 @@ public class MultipleAddresses implements PacketExtension {
|
|||
* @param delivered true when the packet was already delivered to this address.
|
||||
* @param uri used to specify an external system address, such as a sip:, sips:, or im: URI.
|
||||
*/
|
||||
public void addAddress(String type, String jid, String node, String desc, boolean delivered,
|
||||
public void addAddress(Type type, String jid, String node, String desc, boolean delivered,
|
||||
String uri) {
|
||||
// Create a new address with the specificed configuration
|
||||
Address address = new Address(type);
|
||||
|
@ -72,7 +74,7 @@ public class MultipleAddresses implements PacketExtension {
|
|||
*/
|
||||
public void setNoReply() {
|
||||
// Create a new address with the specificed configuration
|
||||
Address address = new Address(NO_REPLY);
|
||||
Address address = new Address(Type.noreply);
|
||||
// Add the new address to the list of multiple recipients
|
||||
addresses.add(address);
|
||||
}
|
||||
|
@ -84,10 +86,9 @@ public class MultipleAddresses implements PacketExtension {
|
|||
* @param type Examples of address type are: TO, CC, BCC, etc.
|
||||
* @return the list of addresses that matches the specified type.
|
||||
*/
|
||||
public List<Address> getAddressesOfType(String type) {
|
||||
public List<Address> getAddressesOfType(Type type) {
|
||||
List<Address> answer = new ArrayList<Address>(addresses.size());
|
||||
for (Iterator<Address> it = addresses.iterator(); it.hasNext();) {
|
||||
Address address = (Address) it.next();
|
||||
for (Address address : addresses) {
|
||||
if (address.getType().equals(type)) {
|
||||
answer.add(address);
|
||||
}
|
||||
|
@ -96,41 +97,44 @@ public class MultipleAddresses implements PacketExtension {
|
|||
return answer;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getElementName() {
|
||||
return ELEMENT;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getNamespace() {
|
||||
return NAMESPACE;
|
||||
}
|
||||
|
||||
public String toXML() {
|
||||
StringBuilder buf = new StringBuilder();
|
||||
buf.append("<").append(getElementName());
|
||||
buf.append(" xmlns=\"").append(NAMESPACE).append("\">");
|
||||
@Override
|
||||
public XmlStringBuilder toXML() {
|
||||
XmlStringBuilder buf = new XmlStringBuilder(this);
|
||||
buf.rightAngleBracket();
|
||||
// Loop through all the addresses and append them to the string buffer
|
||||
for (Iterator<Address> i = addresses.iterator(); i.hasNext();) {
|
||||
Address address = (Address) i.next();
|
||||
for (Address address : addresses) {
|
||||
buf.append(address.toXML());
|
||||
}
|
||||
buf.append("</").append(getElementName()).append(">");
|
||||
return buf.toString();
|
||||
buf.closeElement(this);
|
||||
return buf;
|
||||
}
|
||||
|
||||
public static class Address {
|
||||
public static class Address implements NamedElement {
|
||||
|
||||
private String type;
|
||||
public static final String ELEMENT = "address";
|
||||
|
||||
private final Type type;
|
||||
private String jid;
|
||||
private String node;
|
||||
private String description;
|
||||
private boolean delivered;
|
||||
private String uri;
|
||||
|
||||
private Address(String type) {
|
||||
private Address(Type type) {
|
||||
this.type = type;
|
||||
}
|
||||
|
||||
public String getType() {
|
||||
public Type getType() {
|
||||
return type;
|
||||
}
|
||||
|
||||
|
@ -174,32 +178,26 @@ public class MultipleAddresses implements PacketExtension {
|
|||
this.uri = uri;
|
||||
}
|
||||
|
||||
private String toXML() {
|
||||
StringBuilder buf = new StringBuilder();
|
||||
buf.append("<address type=\"");
|
||||
// Append the address type (e.g. TO/CC/BCC)
|
||||
buf.append(type).append("\"");
|
||||
if (jid != null) {
|
||||
buf.append(" jid=\"");
|
||||
buf.append(jid).append("\"");
|
||||
}
|
||||
if (node != null) {
|
||||
buf.append(" node=\"");
|
||||
buf.append(node).append("\"");
|
||||
@Override
|
||||
public String getElementName() {
|
||||
return ELEMENT;
|
||||
}
|
||||
|
||||
@Override
|
||||
public XmlStringBuilder toXML() {
|
||||
XmlStringBuilder buf = new XmlStringBuilder();
|
||||
buf.halfOpenElement(this).attribute("type", type);
|
||||
buf.optAttribute("jid", jid);
|
||||
buf.optAttribute("node", node);
|
||||
buf.optAttribute("desc", description);
|
||||
if (description != null && description.trim().length() > 0) {
|
||||
buf.append(" desc=\"");
|
||||
buf.append(description).append("\"");
|
||||
}
|
||||
if (delivered) {
|
||||
buf.append(" delivered=\"true\"");
|
||||
}
|
||||
if (uri != null) {
|
||||
buf.append(" uri=\"");
|
||||
buf.append(uri).append("\"");
|
||||
}
|
||||
buf.append("/>");
|
||||
return buf.toString();
|
||||
buf.optBooleanAttribute("delivered", delivered);
|
||||
buf.optAttribute("uri", uri);
|
||||
buf.closeEmptyElement();
|
||||
return buf;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -21,6 +21,7 @@ import java.io.IOException;
|
|||
|
||||
import org.jivesoftware.smack.provider.PacketExtensionProvider;
|
||||
import org.jivesoftware.smackx.address.packet.MultipleAddresses;
|
||||
import org.jivesoftware.smackx.address.packet.MultipleAddresses.Type;
|
||||
import org.xmlpull.v1.XmlPullParser;
|
||||
import org.xmlpull.v1.XmlPullParserException;
|
||||
|
||||
|
@ -35,13 +36,16 @@ public class MultipleAddressesProvider extends PacketExtensionProvider<MultipleA
|
|||
public MultipleAddresses parse(XmlPullParser parser,
|
||||
int initialDepth) throws XmlPullParserException,
|
||||
IOException {
|
||||
boolean done = false;
|
||||
MultipleAddresses multipleAddresses = new MultipleAddresses();
|
||||
while (!done) {
|
||||
outerloop: while (true) {
|
||||
int eventType = parser.next();
|
||||
if (eventType == XmlPullParser.START_TAG) {
|
||||
if (parser.getName().equals("address")) {
|
||||
String type = parser.getAttributeValue("", "type");
|
||||
switch (eventType) {
|
||||
case XmlPullParser.START_TAG:
|
||||
String name = parser.getName();
|
||||
switch (name) {
|
||||
case MultipleAddresses.Address.ELEMENT:
|
||||
String typeString = parser.getAttributeValue("", "type");
|
||||
Type type = Type.valueOf(typeString);
|
||||
String jid = parser.getAttributeValue("", "jid");
|
||||
String node = parser.getAttributeValue("", "node");
|
||||
String desc = parser.getAttributeValue("", "desc");
|
||||
|
@ -49,11 +53,14 @@ public class MultipleAddressesProvider extends PacketExtensionProvider<MultipleA
|
|||
String uri = parser.getAttributeValue("", "uri");
|
||||
// Add the parsed address
|
||||
multipleAddresses.addAddress(type, jid, node, desc, delivered, uri);
|
||||
break;
|
||||
}
|
||||
} else if (eventType == XmlPullParser.END_TAG) {
|
||||
if (parser.getName().equals(multipleAddresses.getElementName())) {
|
||||
done = true;
|
||||
break;
|
||||
case XmlPullParser.END_TAG:
|
||||
if (parser.getDepth() == initialDepth) {
|
||||
break outerloop;
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
return multipleAddresses;
|
||||
|
|
Loading…
Reference in a new issue