mirror of
https://github.com/vanitasvitae/Smack.git
synced 2024-11-23 20:42:06 +01:00
Improve elements and providers and create tests
This commit is contained in:
parent
dd9c693c3a
commit
0900d0a27d
27 changed files with 1126 additions and 44 deletions
|
@ -29,3 +29,4 @@ include 'smack-core',
|
||||||
'smack-repl',
|
'smack-repl',
|
||||||
'smack-openpgp',
|
'smack-openpgp',
|
||||||
'smack-openpgp-bouncycastle'
|
'smack-openpgp-bouncycastle'
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,27 @@
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* Copyright 2018 Paul Schaub.
|
||||||
|
*
|
||||||
|
* 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.ox;
|
||||||
|
|
||||||
|
import org.jivesoftware.smack.initializer.UrlInitializer;
|
||||||
|
|
||||||
|
public class OpenPgpInitializer extends UrlInitializer {
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected String getProvidersUri() {
|
||||||
|
return "classpath:org.jivesoftware.smackx.ox/openpgp.providers";
|
||||||
|
}
|
||||||
|
}
|
|
@ -1,6 +1,6 @@
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
* Copyright 2017 Florian Schmaus.
|
* Copyright 2017 Florian Schmaus, 2018 Paul Schaub.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
* you may not use this file except in compliance with the License.
|
* you may not use this file except in compliance with the License.
|
||||||
|
@ -17,10 +17,48 @@
|
||||||
package org.jivesoftware.smackx.ox;
|
package org.jivesoftware.smackx.ox;
|
||||||
|
|
||||||
import java.io.InputStream;
|
import java.io.InputStream;
|
||||||
|
import java.util.Map;
|
||||||
|
import java.util.WeakHashMap;
|
||||||
|
|
||||||
public class OpenPgpManager {
|
import org.jivesoftware.smack.Manager;
|
||||||
|
import org.jivesoftware.smack.XMPPConnection;
|
||||||
|
|
||||||
|
import org.jxmpp.jid.BareJid;
|
||||||
|
|
||||||
|
public final class OpenPgpManager extends Manager {
|
||||||
|
|
||||||
|
public static final String PEP_NODE_PUBLIC_KEYS = "urn:xmpp:openpgp:0:public-keys";
|
||||||
|
|
||||||
|
public static String PEP_NODE_PUBLIC_KEY(String id) {
|
||||||
|
return PEP_NODE_PUBLIC_KEYS + ":" + id;
|
||||||
|
}
|
||||||
|
|
||||||
|
private static final Map<XMPPConnection, OpenPgpManager> INSTANCES = new WeakHashMap<>();
|
||||||
|
|
||||||
|
private OpenPgpManager(XMPPConnection connection) {
|
||||||
|
super(connection);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static OpenPgpManager getInstanceFor(XMPPConnection connection) {
|
||||||
|
OpenPgpManager manager = INSTANCES.get(connection);
|
||||||
|
if (manager == null) {
|
||||||
|
manager = new OpenPgpManager(connection);
|
||||||
|
INSTANCES.put(connection, manager);
|
||||||
|
}
|
||||||
|
return manager;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static String bareJidToIdentity(BareJid jid) {
|
||||||
|
return "xmpp:" + jid.toString();
|
||||||
|
}
|
||||||
|
|
||||||
public static OpenPgpMessage toOpenPgpMessage(InputStream is) {
|
public static OpenPgpMessage toOpenPgpMessage(InputStream is) {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void publishPublicKey() {
|
||||||
|
// Check if key available at data node
|
||||||
|
// If not, publish key to data node
|
||||||
|
// Publish ID to metadata node
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -23,6 +23,7 @@ import org.jivesoftware.smackx.ox.element.OpenPgpContentElement;
|
||||||
import org.jivesoftware.smackx.ox.element.SignElement;
|
import org.jivesoftware.smackx.ox.element.SignElement;
|
||||||
import org.jivesoftware.smackx.ox.element.SigncryptElement;
|
import org.jivesoftware.smackx.ox.element.SigncryptElement;
|
||||||
import org.jivesoftware.smackx.ox.provider.OpenPgpContentElementProvider;
|
import org.jivesoftware.smackx.ox.provider.OpenPgpContentElementProvider;
|
||||||
|
|
||||||
import org.xmlpull.v1.XmlPullParserException;
|
import org.xmlpull.v1.XmlPullParserException;
|
||||||
|
|
||||||
public class OpenPgpMessage {
|
public class OpenPgpMessage {
|
||||||
|
|
|
@ -20,6 +20,6 @@ import java.io.InputStream;
|
||||||
|
|
||||||
public interface OpenPgpProvider {
|
public interface OpenPgpProvider {
|
||||||
|
|
||||||
public OpenPgpMessage toOpenPgpMessage(InputStream is);
|
OpenPgpMessage toOpenPgpMessage(InputStream is);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
* Copyright 2017 Florian Schmaus.
|
* Copyright 2017 Florian Schmaus, 2018 Paul Schaub.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
* you may not use this file except in compliance with the License.
|
* you may not use this file except in compliance with the License.
|
||||||
|
@ -18,27 +18,39 @@ package org.jivesoftware.smackx.ox.element;
|
||||||
|
|
||||||
import java.util.Date;
|
import java.util.Date;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
import java.util.Set;
|
||||||
|
|
||||||
import org.jivesoftware.smack.packet.ExtensionElement;
|
import org.jivesoftware.smack.packet.ExtensionElement;
|
||||||
|
import org.jivesoftware.smack.util.XmlStringBuilder;
|
||||||
|
|
||||||
import org.jxmpp.jid.Jid;
|
import org.jxmpp.jid.Jid;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This class describes an OpenPGP content element which is encrypted, but not signed.
|
||||||
|
*/
|
||||||
public class CryptElement extends EncryptedOpenPgpContentElement {
|
public class CryptElement extends EncryptedOpenPgpContentElement {
|
||||||
|
|
||||||
public static final String ELEMENT = "crypt";
|
public static final String ELEMENT = "crypt";
|
||||||
|
|
||||||
public CryptElement(List<Jid> to, String rpad, Date timestamp, List<ExtensionElement> payload) {
|
public CryptElement(Set<Jid> to, String rpad, Date timestamp, List<ExtensionElement> payload) {
|
||||||
super(to, rpad, timestamp, payload);
|
super(to, rpad, timestamp, payload);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public CryptElement(Set<Jid> to, List<ExtensionElement> payload) {
|
||||||
|
super(to, payload);
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String getElementName() {
|
public String getElementName() {
|
||||||
return ELEMENT;
|
return ELEMENT;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public CharSequence toXML() {
|
public XmlStringBuilder toXML(String enclosingNamespace) {
|
||||||
// TODO Auto-generated method stub
|
XmlStringBuilder xml = new XmlStringBuilder(this).rightAngleBracket();
|
||||||
return null;
|
addCommonXml(xml);
|
||||||
|
xml.closeElement(this);
|
||||||
|
return xml;
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
* Copyright 2017 Florian Schmaus.
|
* Copyright 2017 Florian Schmaus, 2018 Paul Schaub.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
* you may not use this file except in compliance with the License.
|
* you may not use this file except in compliance with the License.
|
||||||
|
@ -16,22 +16,43 @@
|
||||||
*/
|
*/
|
||||||
package org.jivesoftware.smackx.ox.element;
|
package org.jivesoftware.smackx.ox.element;
|
||||||
|
|
||||||
|
import java.security.SecureRandom;
|
||||||
import java.util.Date;
|
import java.util.Date;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
import java.util.Set;
|
||||||
|
|
||||||
import org.jivesoftware.smack.packet.ExtensionElement;
|
import org.jivesoftware.smack.packet.ExtensionElement;
|
||||||
|
import org.jivesoftware.smack.util.StringUtils;
|
||||||
import org.jivesoftware.smack.util.XmlStringBuilder;
|
import org.jivesoftware.smack.util.XmlStringBuilder;
|
||||||
|
|
||||||
import org.jxmpp.jid.Jid;
|
import org.jxmpp.jid.Jid;
|
||||||
|
|
||||||
public abstract class EncryptedOpenPgpContentElement extends OpenPgpContentElement {
|
public abstract class EncryptedOpenPgpContentElement extends OpenPgpContentElement {
|
||||||
|
|
||||||
|
public static final String ELEM_RPAD = "rpad";
|
||||||
|
|
||||||
private final String rpad;
|
private final String rpad;
|
||||||
|
|
||||||
protected EncryptedOpenPgpContentElement(List<Jid> to, String rpad, Date timestamp, List<ExtensionElement> payload) {
|
protected EncryptedOpenPgpContentElement(Set<Jid> to, String rpad, Date timestamp, List<ExtensionElement> payload) {
|
||||||
super(to, timestamp, payload);
|
super(to, timestamp, payload);
|
||||||
this.rpad = rpad;
|
this.rpad = rpad;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
protected EncryptedOpenPgpContentElement(Set<Jid> to, List<ExtensionElement> payload) {
|
||||||
|
super(to, new Date(), payload);
|
||||||
|
this.rpad = createRandomPadding();
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getRandomPadding() {
|
||||||
|
return rpad;
|
||||||
|
}
|
||||||
|
|
||||||
|
private static String createRandomPadding() {
|
||||||
|
SecureRandom secRan = new SecureRandom();
|
||||||
|
int len = secRan.nextInt(256); // TODO: Find suitable value.
|
||||||
|
return StringUtils.randomString(len);
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected void addCommonXml(XmlStringBuilder xml) {
|
protected void addCommonXml(XmlStringBuilder xml) {
|
||||||
super.addCommonXml(xml);
|
super.addCommonXml(xml);
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
* Copyright 2017 Florian Schmaus.
|
* Copyright 2017 Florian Schmaus, 2018 Paul Schaub.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
* you may not use this file except in compliance with the License.
|
* you may not use this file except in compliance with the License.
|
||||||
|
@ -18,27 +18,39 @@ package org.jivesoftware.smackx.ox.element;
|
||||||
|
|
||||||
import java.util.Date;
|
import java.util.Date;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
import java.util.Set;
|
||||||
|
|
||||||
import org.jivesoftware.smack.packet.ExtensionElement;
|
import org.jivesoftware.smack.packet.ExtensionElement;
|
||||||
import org.jivesoftware.smack.util.XmlStringBuilder;
|
import org.jivesoftware.smack.util.XmlStringBuilder;
|
||||||
|
|
||||||
import org.jxmpp.jid.Jid;
|
import org.jxmpp.jid.Jid;
|
||||||
import org.jxmpp.util.XmppDateTime;
|
import org.jxmpp.util.XmppDateTime;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This class describes an OpenPGP content element. It defines the elements and fields that OpenPGP content elements
|
||||||
|
* do have in common.
|
||||||
|
*/
|
||||||
public abstract class OpenPgpContentElement implements ExtensionElement {
|
public abstract class OpenPgpContentElement implements ExtensionElement {
|
||||||
|
|
||||||
private final List<Jid> to;
|
public static final String ELEM_TO = "to";
|
||||||
|
public static final String ATTR_JID = "jid";
|
||||||
|
public static final String ELEM_TIME = "time";
|
||||||
|
public static final String ATTR_STAMP = "stamp";
|
||||||
|
public static final String ELEM_PAYLOAD = "payload";
|
||||||
|
|
||||||
|
private final Set<Jid> to;
|
||||||
private final Date timestamp;
|
private final Date timestamp;
|
||||||
private final List<ExtensionElement> payload;
|
private final List<ExtensionElement> payload;
|
||||||
|
|
||||||
private String timestampString;
|
private String timestampString;
|
||||||
|
|
||||||
protected OpenPgpContentElement(List<Jid> to, Date timestamp, List<ExtensionElement> payload) {
|
protected OpenPgpContentElement(Set<Jid> to, Date timestamp, List<ExtensionElement> payload) {
|
||||||
this.to = to;
|
this.to = to;
|
||||||
this.timestamp = timestamp;
|
this.timestamp = timestamp;
|
||||||
this.payload = payload;
|
this.payload = payload;
|
||||||
}
|
}
|
||||||
|
|
||||||
public final List<Jid> getTo() {
|
public final Set<Jid> getTo() {
|
||||||
return to;
|
return to;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -63,16 +75,16 @@ public abstract class OpenPgpContentElement implements ExtensionElement {
|
||||||
|
|
||||||
protected void addCommonXml(XmlStringBuilder xml) {
|
protected void addCommonXml(XmlStringBuilder xml) {
|
||||||
for (Jid toJid : to) {
|
for (Jid toJid : to) {
|
||||||
xml.halfOpenElement("to").attribute("jid", toJid).closeEmptyElement();
|
xml.halfOpenElement(ELEM_TO).attribute(ATTR_JID, toJid).closeEmptyElement();
|
||||||
}
|
}
|
||||||
|
|
||||||
ensureTimestampStringSet();
|
ensureTimestampStringSet();
|
||||||
xml.halfOpenElement("time").attribute("stamp", timestampString).closeEmptyElement();
|
xml.halfOpenElement(ELEM_TIME).attribute(ATTR_STAMP, timestampString).closeEmptyElement();
|
||||||
|
|
||||||
xml.openElement("payload");
|
xml.openElement(ELEM_PAYLOAD);
|
||||||
for (ExtensionElement element : payload) {
|
for (ExtensionElement element : payload) {
|
||||||
xml.append(element.toXML());
|
xml.append(element.toXML(getNamespace()));
|
||||||
}
|
}
|
||||||
xml.closeElement("payload");
|
xml.closeElement(ELEM_PAYLOAD);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
* Copyright 2017 Florian Schmaus.
|
* Copyright 2017 Florian Schmaus, 2018 Paul Schaub.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
* you may not use this file except in compliance with the License.
|
* you may not use this file except in compliance with the License.
|
||||||
|
@ -21,15 +21,17 @@ import java.io.IOException;
|
||||||
import java.io.InputStream;
|
import java.io.InputStream;
|
||||||
|
|
||||||
import org.jivesoftware.smack.packet.ExtensionElement;
|
import org.jivesoftware.smack.packet.ExtensionElement;
|
||||||
|
import org.jivesoftware.smack.util.XmlStringBuilder;
|
||||||
import org.jivesoftware.smack.util.stringencoder.Base64;
|
import org.jivesoftware.smack.util.stringencoder.Base64;
|
||||||
import org.jivesoftware.smackx.ox.OpenPgpManager;
|
import org.jivesoftware.smackx.ox.OpenPgpManager;
|
||||||
import org.jivesoftware.smackx.ox.OpenPgpMessage;
|
import org.jivesoftware.smackx.ox.OpenPgpMessage;
|
||||||
|
|
||||||
import org.xmlpull.v1.XmlPullParserException;
|
import org.xmlpull.v1.XmlPullParserException;
|
||||||
|
|
||||||
public class OpenPgpElement implements ExtensionElement {
|
public class OpenPgpElement implements ExtensionElement {
|
||||||
|
|
||||||
public static final String ELEMENT = "openpgp";
|
public static final String ELEMENT = "openpgp";
|
||||||
public static final String NAMESPACE = "urn:xmpp:openpg:0";
|
public static final String NAMESPACE = "urn:xmpp:openpgp:0";
|
||||||
|
|
||||||
private final String base64EncodedOpenPgpMessage;
|
private final String base64EncodedOpenPgpMessage;
|
||||||
|
|
||||||
|
@ -72,12 +74,13 @@ public class OpenPgpElement implements ExtensionElement {
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public CharSequence toXML() {
|
public XmlStringBuilder toXML(String enclosingNamespace) {
|
||||||
// TODO Auto-generated method stub
|
XmlStringBuilder xml = new XmlStringBuilder(this);
|
||||||
return null;
|
xml.rightAngleBracket().append(base64EncodedOpenPgpMessage).closeElement(this);
|
||||||
|
return xml;
|
||||||
}
|
}
|
||||||
|
|
||||||
private final void ensureOpenPgpMessageBytesSet() {
|
private void ensureOpenPgpMessageBytesSet() {
|
||||||
if (openPgpMessageBytes != null) return;
|
if (openPgpMessageBytes != null) return;
|
||||||
|
|
||||||
openPgpMessageBytes = Base64.decode(base64EncodedOpenPgpMessage);
|
openPgpMessageBytes = Base64.decode(base64EncodedOpenPgpMessage);
|
||||||
|
|
|
@ -0,0 +1,97 @@
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* Copyright 2018 Paul Schaub.
|
||||||
|
*
|
||||||
|
* 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.ox.element;
|
||||||
|
|
||||||
|
import java.nio.charset.Charset;
|
||||||
|
import java.util.Date;
|
||||||
|
|
||||||
|
import org.jivesoftware.smack.packet.ExtensionElement;
|
||||||
|
import org.jivesoftware.smack.packet.NamedElement;
|
||||||
|
import org.jivesoftware.smack.util.Objects;
|
||||||
|
import org.jivesoftware.smack.util.XmlStringBuilder;
|
||||||
|
|
||||||
|
public class PubkeyElement implements ExtensionElement {
|
||||||
|
|
||||||
|
public static final String NAMESPACE = OpenPgpElement.NAMESPACE;
|
||||||
|
public static final String ELEMENT = "pubkey";
|
||||||
|
public static final String ATTR_DATE = "date";
|
||||||
|
|
||||||
|
private final PubkeyDataElement dataElement;
|
||||||
|
private final Date date;
|
||||||
|
|
||||||
|
public PubkeyElement(PubkeyDataElement dataElement, Date date) {
|
||||||
|
this.dataElement = Objects.requireNonNull(dataElement);
|
||||||
|
this.date = date;
|
||||||
|
}
|
||||||
|
|
||||||
|
public PubkeyDataElement getDataElement() {
|
||||||
|
return dataElement;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Date getDate() {
|
||||||
|
return date;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getNamespace() {
|
||||||
|
return NAMESPACE;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getElementName() {
|
||||||
|
return ELEMENT;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public XmlStringBuilder toXML(String enclosingNamespace) {
|
||||||
|
XmlStringBuilder xml = new XmlStringBuilder(this)
|
||||||
|
.optAttribute(ATTR_DATE, date)
|
||||||
|
.rightAngleBracket()
|
||||||
|
.element(getDataElement())
|
||||||
|
.closeElement(this);
|
||||||
|
return xml;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class PubkeyDataElement implements NamedElement {
|
||||||
|
|
||||||
|
public static final String ELEMENT = "data";
|
||||||
|
|
||||||
|
private final byte[] b64Data;
|
||||||
|
|
||||||
|
public PubkeyDataElement(byte[] b64Data) {
|
||||||
|
this.b64Data = b64Data;
|
||||||
|
}
|
||||||
|
|
||||||
|
public byte[] getB64Data() {
|
||||||
|
return b64Data;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getElementName() {
|
||||||
|
return ELEMENT;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public XmlStringBuilder toXML(String enclosingNamespace) {
|
||||||
|
XmlStringBuilder xml = new XmlStringBuilder(this)
|
||||||
|
.rightAngleBracket()
|
||||||
|
.append(new String(b64Data, Charset.forName("UTF-8")))
|
||||||
|
.closeElement(this);
|
||||||
|
return xml;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,147 @@
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* Copyright 2018 Paul Schaub.
|
||||||
|
*
|
||||||
|
* 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.ox.element;
|
||||||
|
|
||||||
|
import java.util.Collections;
|
||||||
|
import java.util.Date;
|
||||||
|
import java.util.Map;
|
||||||
|
import java.util.TreeMap;
|
||||||
|
|
||||||
|
import org.jivesoftware.smack.packet.ExtensionElement;
|
||||||
|
import org.jivesoftware.smack.packet.NamedElement;
|
||||||
|
import org.jivesoftware.smack.util.Objects;
|
||||||
|
import org.jivesoftware.smack.util.XmlStringBuilder;
|
||||||
|
|
||||||
|
public final class PublicKeysListElement implements ExtensionElement {
|
||||||
|
|
||||||
|
public static final String NAMESPACE = OpenPgpElement.NAMESPACE;
|
||||||
|
public static final String ELEMENT = "public-keys-list";
|
||||||
|
|
||||||
|
private final Map<String, PubkeyMetadataElement> metadata;
|
||||||
|
|
||||||
|
private PublicKeysListElement(TreeMap<String, PubkeyMetadataElement> metadata) {
|
||||||
|
this.metadata = Collections.unmodifiableMap(metadata);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Builder builder() {
|
||||||
|
return new Builder();
|
||||||
|
}
|
||||||
|
|
||||||
|
public TreeMap<String, PubkeyMetadataElement> getMetadata() {
|
||||||
|
return new TreeMap<>(metadata);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getNamespace() {
|
||||||
|
return NAMESPACE;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getElementName() {
|
||||||
|
return ELEMENT;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public XmlStringBuilder toXML(String enclosingNamespace) {
|
||||||
|
XmlStringBuilder xml = new XmlStringBuilder(this).rightAngleBracket();
|
||||||
|
for (PubkeyMetadataElement metadataElement : metadata.values()) {
|
||||||
|
xml.element(metadataElement);
|
||||||
|
}
|
||||||
|
xml.closeElement(this);
|
||||||
|
return xml;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static final class Builder {
|
||||||
|
|
||||||
|
private final TreeMap<String, PubkeyMetadataElement> metadata = new TreeMap<>();
|
||||||
|
|
||||||
|
private Builder() {
|
||||||
|
// Empty
|
||||||
|
}
|
||||||
|
|
||||||
|
public Builder addMetadata(PubkeyMetadataElement key) {
|
||||||
|
metadata.put(key.getV4Fingerprint(), key);
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
public PublicKeysListElement build() {
|
||||||
|
return new PublicKeysListElement(metadata);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class PubkeyMetadataElement implements NamedElement {
|
||||||
|
|
||||||
|
public static final String ELEMENT = "pubkey-metadata";
|
||||||
|
public static final String ATTR_V4_FINGERPRINT = "v4-fingerprint";
|
||||||
|
public static final String ATTR_DATE = "date";
|
||||||
|
|
||||||
|
private final String v4_fingerprint;
|
||||||
|
private final Date date;
|
||||||
|
|
||||||
|
public PubkeyMetadataElement(String v4_fingerprint, Date date) {
|
||||||
|
this.v4_fingerprint = Objects.requireNonNull(v4_fingerprint);
|
||||||
|
this.date = Objects.requireNonNull(date);
|
||||||
|
|
||||||
|
if (v4_fingerprint.length() != 40) {
|
||||||
|
throw new IllegalArgumentException("OpenPGP v4 fingerprint must be 40 characters long.");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getV4Fingerprint() {
|
||||||
|
return v4_fingerprint;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Date getDate() {
|
||||||
|
return date;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getElementName() {
|
||||||
|
return ELEMENT;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public XmlStringBuilder toXML(String enclosingNamespace) {
|
||||||
|
XmlStringBuilder xml = new XmlStringBuilder(this)
|
||||||
|
.attribute(ATTR_V4_FINGERPRINT, getV4Fingerprint())
|
||||||
|
.attribute(ATTR_DATE, date).closeEmptyElement();
|
||||||
|
return xml;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int hashCode() {
|
||||||
|
return getV4Fingerprint().hashCode() + 3 * getDate().hashCode();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean equals(Object o) {
|
||||||
|
if (o == null) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!(o instanceof PubkeyMetadataElement)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (o == this) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
return hashCode() == o.hashCode();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,57 @@
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* Copyright 2018 Paul Schaub.
|
||||||
|
*
|
||||||
|
* 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.ox.element;
|
||||||
|
|
||||||
|
import java.nio.charset.Charset;
|
||||||
|
|
||||||
|
import org.jivesoftware.smack.packet.ExtensionElement;
|
||||||
|
import org.jivesoftware.smack.util.XmlStringBuilder;
|
||||||
|
|
||||||
|
public class SecretkeyElement implements ExtensionElement {
|
||||||
|
|
||||||
|
public static final String NAMESPACE = OpenPgpElement.NAMESPACE;
|
||||||
|
public static final String ELEMENT = "secretkey";
|
||||||
|
|
||||||
|
private final byte[] b64Data;
|
||||||
|
|
||||||
|
public SecretkeyElement(byte[] b64Data) {
|
||||||
|
this.b64Data = b64Data;
|
||||||
|
}
|
||||||
|
|
||||||
|
public byte[] getB64Data() {
|
||||||
|
return b64Data;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getNamespace() {
|
||||||
|
return NAMESPACE;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getElementName() {
|
||||||
|
return ELEMENT;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public XmlStringBuilder toXML(String enclosingNamespace) {
|
||||||
|
XmlStringBuilder xml = new XmlStringBuilder(this)
|
||||||
|
.rightAngleBracket()
|
||||||
|
.append(new String(b64Data, Charset.forName("UTF-8")))
|
||||||
|
.closeElement(this);
|
||||||
|
return xml;
|
||||||
|
}
|
||||||
|
}
|
|
@ -1,6 +1,6 @@
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
* Copyright 2017 Florian Schmaus.
|
* Copyright 2017 Florian Schmaus, 2018 Paul Schaub.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
* you may not use this file except in compliance with the License.
|
* you may not use this file except in compliance with the License.
|
||||||
|
@ -18,13 +18,16 @@ package org.jivesoftware.smackx.ox.element;
|
||||||
|
|
||||||
import java.util.Date;
|
import java.util.Date;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
import java.util.Set;
|
||||||
|
|
||||||
import org.jivesoftware.smack.packet.ExtensionElement;
|
import org.jivesoftware.smack.packet.ExtensionElement;
|
||||||
|
import org.jivesoftware.smack.util.XmlStringBuilder;
|
||||||
|
|
||||||
import org.jxmpp.jid.Jid;
|
import org.jxmpp.jid.Jid;
|
||||||
|
|
||||||
public class SignElement extends OpenPgpContentElement {
|
public class SignElement extends OpenPgpContentElement {
|
||||||
|
|
||||||
public SignElement(List<Jid> to, Date timestamp, List<ExtensionElement> payload) {
|
public SignElement(Set<Jid> to, Date timestamp, List<ExtensionElement> payload) {
|
||||||
super(to, timestamp, payload);
|
super(to, timestamp, payload);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -36,9 +39,11 @@ public class SignElement extends OpenPgpContentElement {
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public CharSequence toXML() {
|
public XmlStringBuilder toXML(String enclosingNamespace) {
|
||||||
// TODO Auto-generated method stub
|
XmlStringBuilder xml = new XmlStringBuilder(this).rightAngleBracket();
|
||||||
return null;
|
addCommonXml(xml);
|
||||||
|
xml.closeElement(this);
|
||||||
|
return xml;
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
* Copyright 2017 Florian Schmaus.
|
* Copyright 2017 Florian Schmaus, 2018 Paul Schaub.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
* you may not use this file except in compliance with the License.
|
* you may not use this file except in compliance with the License.
|
||||||
|
@ -18,27 +18,36 @@ package org.jivesoftware.smackx.ox.element;
|
||||||
|
|
||||||
import java.util.Date;
|
import java.util.Date;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
import java.util.Set;
|
||||||
|
|
||||||
import org.jivesoftware.smack.packet.ExtensionElement;
|
import org.jivesoftware.smack.packet.ExtensionElement;
|
||||||
|
import org.jivesoftware.smack.util.XmlStringBuilder;
|
||||||
|
|
||||||
import org.jxmpp.jid.Jid;
|
import org.jxmpp.jid.Jid;
|
||||||
|
|
||||||
public class SigncryptElement extends EncryptedOpenPgpContentElement {
|
public class SigncryptElement extends EncryptedOpenPgpContentElement {
|
||||||
|
|
||||||
public static final String ELEMENT = "signcrypt";
|
public static final String ELEMENT = "signcrypt";
|
||||||
|
|
||||||
public SigncryptElement(List<Jid> to, String rpad, Date timestamp, List<ExtensionElement> payload) {
|
public SigncryptElement(Set<Jid> to, String rpad, Date timestamp, List<ExtensionElement> payload) {
|
||||||
super(to, rpad, timestamp, payload);
|
super(to, rpad, timestamp, payload);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public SigncryptElement(Set<Jid> to, List<ExtensionElement> payload) {
|
||||||
|
super(to, payload);
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String getElementName() {
|
public String getElementName() {
|
||||||
return ELEMENT;
|
return ELEMENT;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public CharSequence toXML() {
|
public XmlStringBuilder toXML(String enclosingNamespace) {
|
||||||
// TODO Auto-generated method stub
|
XmlStringBuilder xml = new XmlStringBuilder(this).rightAngleBracket();
|
||||||
return null;
|
addCommonXml(xml);
|
||||||
|
xml.closeElement(this);
|
||||||
|
return xml;
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -17,12 +17,16 @@
|
||||||
package org.jivesoftware.smackx.ox.provider;
|
package org.jivesoftware.smackx.ox.provider;
|
||||||
|
|
||||||
import org.jivesoftware.smackx.ox.element.CryptElement;
|
import org.jivesoftware.smackx.ox.element.CryptElement;
|
||||||
|
|
||||||
import org.xmlpull.v1.XmlPullParser;
|
import org.xmlpull.v1.XmlPullParser;
|
||||||
|
|
||||||
public class CryptElementProvider extends OpenPgpContentElementProvider<CryptElement> {
|
public class CryptElementProvider extends OpenPgpContentElementProvider<CryptElement> {
|
||||||
|
|
||||||
|
public static final CryptElementProvider TEST_INSTANCE = new CryptElementProvider();
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public CryptElement parse(XmlPullParser parser, int initialDepth) throws Exception {
|
public CryptElement parse(XmlPullParser parser, int initialDepth)
|
||||||
|
throws Exception {
|
||||||
OpenPgpContentElementData data = parseOpenPgpContentElementData(parser, initialDepth);
|
OpenPgpContentElementData data = parseOpenPgpContentElementData(parser, initialDepth);
|
||||||
|
|
||||||
return new CryptElement(data.to, data.rpad, data.timestamp, data.payload);
|
return new CryptElement(data.to, data.rpad, data.timestamp, data.payload);
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
* Copyright 2017 Florian Schmaus.
|
* Copyright 2017 Florian Schmaus, 2018 Paul Schaub.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
* you may not use this file except in compliance with the License.
|
* you may not use this file except in compliance with the License.
|
||||||
|
@ -16,50 +16,127 @@
|
||||||
*/
|
*/
|
||||||
package org.jivesoftware.smackx.ox.provider;
|
package org.jivesoftware.smackx.ox.provider;
|
||||||
|
|
||||||
|
import static org.xmlpull.v1.XmlPullParser.END_TAG;
|
||||||
|
import static org.xmlpull.v1.XmlPullParser.START_TAG;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.util.Date;
|
import java.util.Date;
|
||||||
|
import java.util.HashSet;
|
||||||
import java.util.LinkedList;
|
import java.util.LinkedList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
import java.util.Set;
|
||||||
|
import java.util.logging.Level;
|
||||||
|
import java.util.logging.Logger;
|
||||||
|
|
||||||
import org.jivesoftware.smack.packet.ExtensionElement;
|
import org.jivesoftware.smack.packet.ExtensionElement;
|
||||||
import org.jivesoftware.smack.provider.ExtensionElementProvider;
|
import org.jivesoftware.smack.provider.ExtensionElementProvider;
|
||||||
|
import org.jivesoftware.smack.provider.ProviderManager;
|
||||||
import org.jivesoftware.smack.util.PacketParserUtils;
|
import org.jivesoftware.smack.util.PacketParserUtils;
|
||||||
|
import org.jivesoftware.smackx.ox.element.CryptElement;
|
||||||
|
import org.jivesoftware.smackx.ox.element.EncryptedOpenPgpContentElement;
|
||||||
import org.jivesoftware.smackx.ox.element.OpenPgpContentElement;
|
import org.jivesoftware.smackx.ox.element.OpenPgpContentElement;
|
||||||
|
import org.jivesoftware.smackx.ox.element.SignElement;
|
||||||
|
import org.jivesoftware.smackx.ox.element.SigncryptElement;
|
||||||
|
|
||||||
import org.jxmpp.jid.Jid;
|
import org.jxmpp.jid.Jid;
|
||||||
|
import org.jxmpp.jid.impl.JidCreate;
|
||||||
|
import org.jxmpp.util.XmppDateTime;
|
||||||
import org.xmlpull.v1.XmlPullParser;
|
import org.xmlpull.v1.XmlPullParser;
|
||||||
import org.xmlpull.v1.XmlPullParserException;
|
import org.xmlpull.v1.XmlPullParserException;
|
||||||
|
|
||||||
public abstract class OpenPgpContentElementProvider<O extends OpenPgpContentElement> extends ExtensionElementProvider<O> {
|
public abstract class OpenPgpContentElementProvider<O extends OpenPgpContentElement> extends ExtensionElementProvider<O> {
|
||||||
|
|
||||||
|
private static final Logger LOGGER = Logger.getLogger(OpenPgpContentElementProvider.class.getName());
|
||||||
|
|
||||||
public static OpenPgpContentElement parseOpenPgpContentElement(String element)
|
public static OpenPgpContentElement parseOpenPgpContentElement(String element)
|
||||||
throws XmlPullParserException, IOException {
|
throws XmlPullParserException, IOException {
|
||||||
XmlPullParser parser = PacketParserUtils.getParserFor(element);
|
XmlPullParser parser = PacketParserUtils.getParserFor(element);
|
||||||
return parseOpenPgpContentElement(parser);
|
return parseOpenPgpContentElement(parser);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static OpenPgpContentElement parseOpenPgpContentElement(XmlPullParser parser) {
|
public static OpenPgpContentElement parseOpenPgpContentElement(XmlPullParser parser)
|
||||||
|
throws IOException, XmlPullParserException {
|
||||||
|
// TODO
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public abstract O parse(XmlPullParser parser, int initialDepth) throws Exception;
|
public abstract O parse(XmlPullParser parser, int initialDepth) throws Exception;
|
||||||
|
|
||||||
protected static OpenPgpContentElementData parseOpenPgpContentElementData(XmlPullParser parser, int initialDepth) {
|
protected static OpenPgpContentElementData parseOpenPgpContentElementData(XmlPullParser parser, int initialDepth)
|
||||||
List<Jid> to = new LinkedList<>();
|
throws Exception {
|
||||||
|
Set<Jid> to = new HashSet<>();
|
||||||
Date timestamp = null;
|
Date timestamp = null;
|
||||||
String rpad = null;
|
String rpad = null;
|
||||||
List<ExtensionElement> payload = new LinkedList<>();
|
List<ExtensionElement> payload = new LinkedList<>();
|
||||||
|
|
||||||
|
outerloop: while (true) {
|
||||||
|
int tag = parser.next();
|
||||||
|
String name = parser.getName();
|
||||||
|
switch (tag) {
|
||||||
|
case START_TAG:
|
||||||
|
switch (name) {
|
||||||
|
|
||||||
|
case OpenPgpContentElement.ELEM_TIME:
|
||||||
|
String stamp = parser.getAttributeValue("", OpenPgpContentElement.ATTR_STAMP);
|
||||||
|
timestamp = XmppDateTime.parseDate(stamp);
|
||||||
|
break;
|
||||||
|
|
||||||
|
case OpenPgpContentElement.ELEM_TO:
|
||||||
|
String jid = parser.getAttributeValue("", OpenPgpContentElement.ATTR_JID);
|
||||||
|
to.add(JidCreate.bareFrom(jid));
|
||||||
|
break;
|
||||||
|
|
||||||
|
case EncryptedOpenPgpContentElement.ELEM_RPAD:
|
||||||
|
rpad = parser.nextText();
|
||||||
|
break;
|
||||||
|
|
||||||
|
case OpenPgpContentElement.ELEM_PAYLOAD:
|
||||||
|
innerloop: while (true) {
|
||||||
|
int ptag = parser.next();
|
||||||
|
String pname = parser.getName();
|
||||||
|
String pns = parser.getNamespace();
|
||||||
|
switch (ptag) {
|
||||||
|
|
||||||
|
case START_TAG:
|
||||||
|
ExtensionElementProvider<ExtensionElement> provider =
|
||||||
|
ProviderManager.getExtensionProvider(pname, pns);
|
||||||
|
if (provider == null) {
|
||||||
|
LOGGER.log(Level.INFO, "No provider found for " + pname + " " + pns);
|
||||||
|
continue innerloop;
|
||||||
|
}
|
||||||
|
payload.add(provider.parse(parser));
|
||||||
|
break;
|
||||||
|
|
||||||
|
case END_TAG:
|
||||||
|
break innerloop;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
case END_TAG:
|
||||||
|
switch (name) {
|
||||||
|
case CryptElement.ELEMENT:
|
||||||
|
case SigncryptElement.ELEMENT:
|
||||||
|
case SignElement.ELEMENT:
|
||||||
|
break outerloop;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return new OpenPgpContentElementData(to, timestamp, rpad, payload);
|
return new OpenPgpContentElementData(to, timestamp, rpad, payload);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected final static class OpenPgpContentElementData {
|
protected static final class OpenPgpContentElementData {
|
||||||
protected final List<Jid> to;
|
protected final Set<Jid> to;
|
||||||
protected final Date timestamp;
|
protected final Date timestamp;
|
||||||
protected final String rpad;
|
protected final String rpad;
|
||||||
protected final List<ExtensionElement> payload;
|
protected final List<ExtensionElement> payload;
|
||||||
|
|
||||||
private OpenPgpContentElementData(List<Jid> to, Date timestamp, String rpad, List<ExtensionElement> payload) {
|
private OpenPgpContentElementData(Set<Jid> to, Date timestamp, String rpad, List<ExtensionElement> payload) {
|
||||||
this.to = to;
|
this.to = to;
|
||||||
this.timestamp = timestamp;
|
this.timestamp = timestamp;
|
||||||
this.rpad = rpad;
|
this.rpad = rpad;
|
||||||
|
|
|
@ -18,10 +18,13 @@ package org.jivesoftware.smackx.ox.provider;
|
||||||
|
|
||||||
import org.jivesoftware.smack.provider.ExtensionElementProvider;
|
import org.jivesoftware.smack.provider.ExtensionElementProvider;
|
||||||
import org.jivesoftware.smackx.ox.element.OpenPgpElement;
|
import org.jivesoftware.smackx.ox.element.OpenPgpElement;
|
||||||
|
|
||||||
import org.xmlpull.v1.XmlPullParser;
|
import org.xmlpull.v1.XmlPullParser;
|
||||||
|
|
||||||
public class OpenPgpElementProvider extends ExtensionElementProvider<OpenPgpElement> {
|
public class OpenPgpElementProvider extends ExtensionElementProvider<OpenPgpElement> {
|
||||||
|
|
||||||
|
public static final OpenPgpElementProvider TEST_INSTANCE = new OpenPgpElementProvider();
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public OpenPgpElement parse(XmlPullParser parser, int initialDepth) throws Exception {
|
public OpenPgpElement parse(XmlPullParser parser, int initialDepth) throws Exception {
|
||||||
String base64EncodedOpenPgpMessage = parser.nextText();
|
String base64EncodedOpenPgpMessage = parser.nextText();
|
||||||
|
|
|
@ -0,0 +1,53 @@
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* Copyright 2018 Paul Schaub.
|
||||||
|
*
|
||||||
|
* 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.ox.provider;
|
||||||
|
|
||||||
|
import static org.xmlpull.v1.XmlPullParser.START_TAG;
|
||||||
|
|
||||||
|
import java.nio.charset.Charset;
|
||||||
|
import java.util.Date;
|
||||||
|
|
||||||
|
import org.jivesoftware.smack.provider.ExtensionElementProvider;
|
||||||
|
import org.jivesoftware.smackx.ox.element.PubkeyElement;
|
||||||
|
|
||||||
|
import org.jxmpp.util.XmppDateTime;
|
||||||
|
import org.xmlpull.v1.XmlPullParser;
|
||||||
|
|
||||||
|
public class PubkeyElementProvider extends ExtensionElementProvider<PubkeyElement> {
|
||||||
|
|
||||||
|
public static final PubkeyElementProvider TEST_INSTANCE = new PubkeyElementProvider();
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public PubkeyElement parse(XmlPullParser parser, int initialDepth) throws Exception {
|
||||||
|
String dateString = parser.getAttributeValue(null, PubkeyElement.ATTR_DATE);
|
||||||
|
Date date = dateString != null ? XmppDateTime.parseXEP0082Date(dateString) : null;
|
||||||
|
while (true) {
|
||||||
|
int tag = parser.next();
|
||||||
|
String name = parser.getName();
|
||||||
|
if (tag == START_TAG) {
|
||||||
|
switch (name) {
|
||||||
|
case PubkeyElement.PubkeyDataElement.ELEMENT:
|
||||||
|
String data = parser.nextText();
|
||||||
|
if (data != null) {
|
||||||
|
byte[] bytes = data.getBytes(Charset.forName("UTF-8"));
|
||||||
|
return new PubkeyElement(new PubkeyElement.PubkeyDataElement(bytes), date);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,65 @@
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* Copyright 2018 Paul Schaub.
|
||||||
|
*
|
||||||
|
* 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.ox.provider;
|
||||||
|
|
||||||
|
import static org.xmlpull.v1.XmlPullParser.END_TAG;
|
||||||
|
import static org.xmlpull.v1.XmlPullParser.START_TAG;
|
||||||
|
|
||||||
|
import java.util.Date;
|
||||||
|
|
||||||
|
import org.jivesoftware.smack.provider.ExtensionElementProvider;
|
||||||
|
import org.jivesoftware.smackx.ox.element.PublicKeysListElement;
|
||||||
|
|
||||||
|
import org.jxmpp.util.XmppDateTime;
|
||||||
|
import org.xmlpull.v1.XmlPullParser;
|
||||||
|
|
||||||
|
public final class PublicKeysListElementProvider extends ExtensionElementProvider<PublicKeysListElement> {
|
||||||
|
|
||||||
|
public static final PublicKeysListElementProvider TEST_INSTANCE = new PublicKeysListElementProvider();
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public PublicKeysListElement parse(XmlPullParser parser, int initialDepth) throws Exception {
|
||||||
|
|
||||||
|
PublicKeysListElement.Builder builder = PublicKeysListElement.builder();
|
||||||
|
|
||||||
|
while (true) {
|
||||||
|
|
||||||
|
int tag = parser.nextTag();
|
||||||
|
String name = parser.getName();
|
||||||
|
|
||||||
|
switch (tag) {
|
||||||
|
case START_TAG:
|
||||||
|
|
||||||
|
if (PublicKeysListElement.PubkeyMetadataElement.ELEMENT.equals(name)) {
|
||||||
|
String finger = parser.getAttributeValue(null,
|
||||||
|
PublicKeysListElement.PubkeyMetadataElement.ATTR_V4_FINGERPRINT);
|
||||||
|
String dt = parser.getAttributeValue(null,
|
||||||
|
PublicKeysListElement.PubkeyMetadataElement.ATTR_DATE);
|
||||||
|
Date date = XmppDateTime.parseXEP0082Date(dt);
|
||||||
|
builder.addMetadata(new PublicKeysListElement.PubkeyMetadataElement(finger, date));
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
case END_TAG:
|
||||||
|
|
||||||
|
if (name.equals(PublicKeysListElement.ELEMENT)) {
|
||||||
|
return builder.build();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,35 @@
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* Copyright 2018 Paul Schaub.
|
||||||
|
*
|
||||||
|
* 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.ox.provider;
|
||||||
|
|
||||||
|
import java.nio.charset.Charset;
|
||||||
|
|
||||||
|
import org.jivesoftware.smack.provider.ExtensionElementProvider;
|
||||||
|
import org.jivesoftware.smackx.ox.element.SecretkeyElement;
|
||||||
|
|
||||||
|
import org.xmlpull.v1.XmlPullParser;
|
||||||
|
|
||||||
|
public class SecretkeyElementProvider extends ExtensionElementProvider<SecretkeyElement> {
|
||||||
|
|
||||||
|
public static final SecretkeyElementProvider TEST_INSTANCE = new SecretkeyElementProvider();
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public SecretkeyElement parse(XmlPullParser parser, int initialDepth) throws Exception {
|
||||||
|
String data = parser.nextText();
|
||||||
|
return new SecretkeyElement(data.getBytes(Charset.forName("UTF-8")));
|
||||||
|
}
|
||||||
|
}
|
|
@ -20,11 +20,13 @@ import java.util.logging.Logger;
|
||||||
|
|
||||||
import org.jivesoftware.smack.util.StringUtils;
|
import org.jivesoftware.smack.util.StringUtils;
|
||||||
import org.jivesoftware.smackx.ox.element.SignElement;
|
import org.jivesoftware.smackx.ox.element.SignElement;
|
||||||
|
|
||||||
import org.xmlpull.v1.XmlPullParser;
|
import org.xmlpull.v1.XmlPullParser;
|
||||||
|
|
||||||
public class SignElementProvider extends OpenPgpContentElementProvider<SignElement> {
|
public class SignElementProvider extends OpenPgpContentElementProvider<SignElement> {
|
||||||
|
|
||||||
private static final Logger LOGGER = Logger.getLogger(SigncryptElementProvider.class.getName());
|
private static final Logger LOGGER = Logger.getLogger(SigncryptElementProvider.class.getName());
|
||||||
|
public static final SignElementProvider TEST_INSTANCE = new SignElementProvider();
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public SignElement parse(XmlPullParser parser, int initialDepth) throws Exception {
|
public SignElement parse(XmlPullParser parser, int initialDepth) throws Exception {
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
* Copyright 2017 Florian Schmaus.
|
* Copyright 2017 Florian Schmaus, 2018 Paul Schaub.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
* you may not use this file except in compliance with the License.
|
* you may not use this file except in compliance with the License.
|
||||||
|
@ -17,10 +17,13 @@
|
||||||
package org.jivesoftware.smackx.ox.provider;
|
package org.jivesoftware.smackx.ox.provider;
|
||||||
|
|
||||||
import org.jivesoftware.smackx.ox.element.SigncryptElement;
|
import org.jivesoftware.smackx.ox.element.SigncryptElement;
|
||||||
|
|
||||||
import org.xmlpull.v1.XmlPullParser;
|
import org.xmlpull.v1.XmlPullParser;
|
||||||
|
|
||||||
public class SigncryptElementProvider extends OpenPgpContentElementProvider<SigncryptElement> {
|
public class SigncryptElementProvider extends OpenPgpContentElementProvider<SigncryptElement> {
|
||||||
|
|
||||||
|
public static final SigncryptElementProvider TEST_INSTANCE = new SigncryptElementProvider();
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public SigncryptElement parse(XmlPullParser parser, int initialDepth) throws Exception {
|
public SigncryptElement parse(XmlPullParser parser, int initialDepth) throws Exception {
|
||||||
OpenPgpContentElementData data = parseOpenPgpContentElementData(parser, initialDepth);
|
OpenPgpContentElementData data = parseOpenPgpContentElementData(parser, initialDepth);
|
||||||
|
|
|
@ -0,0 +1,28 @@
|
||||||
|
<?xml version="1.0"?>
|
||||||
|
<!-- Providers for OpenPGP for XMPP -->
|
||||||
|
<smackProviders>
|
||||||
|
|
||||||
|
<!-- Stanza extensions -->
|
||||||
|
<extensionProvider>
|
||||||
|
<elementName>openpgp</elementName>
|
||||||
|
<namespace>urn:xmpp:openpgp:0</namespace>
|
||||||
|
<className>org.jivesoftware.smackx.ox.provider.OpenPgpElementProvider</className>
|
||||||
|
</extensionProvider>
|
||||||
|
|
||||||
|
<!-- PubSub extensions -->
|
||||||
|
<extensionProvider>
|
||||||
|
<elementName>pubkey</elementName>
|
||||||
|
<namespace>urn:xmpp:openpgp:0</namespace>
|
||||||
|
<className>org.jivesoftware.smackx.ox.provider.PubkeyElementProvider</className>
|
||||||
|
</extensionProvider>
|
||||||
|
<extensionProvider>
|
||||||
|
<elementName>secretkey</elementName>
|
||||||
|
<namespace>urn:xmpp:openpgp:0</namespace>
|
||||||
|
<className>org.jivesoftware.smackx.ox.provider.SecretkeyElementProvider</className>
|
||||||
|
</extensionProvider>
|
||||||
|
<extensionProvider>
|
||||||
|
<elementName>public-keys-list</elementName>
|
||||||
|
<namespace>urn:xmpp:openpgp:0</namespace>
|
||||||
|
<className>org.jivesoftware.smackx.ox.provider.PublicKeysListElementProvider</className>
|
||||||
|
</extensionProvider>
|
||||||
|
</smackProviders>
|
|
@ -0,0 +1,178 @@
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* Copyright 2018 Paul Schaub.
|
||||||
|
*
|
||||||
|
* 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.ox;
|
||||||
|
|
||||||
|
import static junit.framework.TestCase.assertEquals;
|
||||||
|
import static junit.framework.TestCase.assertNotNull;
|
||||||
|
import static org.custommonkey.xmlunit.XMLAssert.assertXMLEqual;
|
||||||
|
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.Collections;
|
||||||
|
import java.util.Date;
|
||||||
|
import java.util.HashSet;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Set;
|
||||||
|
|
||||||
|
import org.jivesoftware.smack.packet.ExtensionElement;
|
||||||
|
import org.jivesoftware.smack.packet.Message;
|
||||||
|
import org.jivesoftware.smack.test.util.SmackTestSuite;
|
||||||
|
import org.jivesoftware.smack.test.util.TestUtils;
|
||||||
|
import org.jivesoftware.smackx.ox.element.CryptElement;
|
||||||
|
import org.jivesoftware.smackx.ox.element.OpenPgpElement;
|
||||||
|
import org.jivesoftware.smackx.ox.element.SignElement;
|
||||||
|
import org.jivesoftware.smackx.ox.element.SigncryptElement;
|
||||||
|
import org.jivesoftware.smackx.ox.provider.CryptElementProvider;
|
||||||
|
import org.jivesoftware.smackx.ox.provider.OpenPgpElementProvider;
|
||||||
|
import org.jivesoftware.smackx.ox.provider.SignElementProvider;
|
||||||
|
import org.jivesoftware.smackx.ox.provider.SigncryptElementProvider;
|
||||||
|
|
||||||
|
import org.junit.Test;
|
||||||
|
import org.jxmpp.jid.Jid;
|
||||||
|
import org.jxmpp.jid.impl.JidCreate;
|
||||||
|
import org.jxmpp.stringprep.XmppStringprepException;
|
||||||
|
import org.xmlpull.v1.XmlPullParser;
|
||||||
|
|
||||||
|
public class OpenPgpElementTest extends SmackTestSuite {
|
||||||
|
|
||||||
|
private final Set<Jid> recipients;
|
||||||
|
|
||||||
|
// 2014-07-10T15:06:00.000+00:00
|
||||||
|
private static final Date testDate = new Date(1405004760000L);
|
||||||
|
|
||||||
|
public OpenPgpElementTest() throws XmppStringprepException {
|
||||||
|
super();
|
||||||
|
Set<Jid> jids = new HashSet<>();
|
||||||
|
jids.add(JidCreate.bareFrom("alice@wonderland.lit"));
|
||||||
|
jids.add(JidCreate.bareFrom("bob@builder.lit"));
|
||||||
|
this.recipients = Collections.unmodifiableSet(jids);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void providerTest() throws Exception {
|
||||||
|
String expected =
|
||||||
|
"<openpgp xmlns='urn:xmpp:openpgp:0'>" +
|
||||||
|
"BASE64_OPENPGP_MESSAGE" +
|
||||||
|
"</openpgp>";
|
||||||
|
|
||||||
|
OpenPgpElement element = new OpenPgpElement("BASE64_OPENPGP_MESSAGE");
|
||||||
|
|
||||||
|
assertXMLEqual(expected, element.toXML(null).toString());
|
||||||
|
|
||||||
|
XmlPullParser parser = TestUtils.getParser(expected);
|
||||||
|
OpenPgpElement parsed = OpenPgpElementProvider.TEST_INSTANCE.parse(parser);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void simplifiedConstructorTest() {
|
||||||
|
ArrayList<ExtensionElement> payload = new ArrayList<>();
|
||||||
|
payload.add(new Message.Body("de", "Hallo Welt!"));
|
||||||
|
CryptElement element = new CryptElement(recipients, payload);
|
||||||
|
|
||||||
|
assertNotNull(element.getRandomPadding());
|
||||||
|
assertNotNull(element.getTimestamp());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void signElementProviderTest() throws Exception {
|
||||||
|
String expected =
|
||||||
|
"<sign xmlns='urn:xmpp:openpgp:0'>" +
|
||||||
|
"<to jid='alice@wonderland.lit'/>" +
|
||||||
|
"<to jid='bob@builder.lit'/>" +
|
||||||
|
"<time stamp='2014-07-10T15:06:00.000+00:00'/>" +
|
||||||
|
"<payload>" +
|
||||||
|
"<body xmlns='jabber:client' xml:lang='en'>Hello World!</body>" +
|
||||||
|
"</payload>" +
|
||||||
|
"</sign>";
|
||||||
|
|
||||||
|
List<ExtensionElement> payload = new ArrayList<>();
|
||||||
|
payload.add(new Message.Body("en", "Hello World!"));
|
||||||
|
SignElement element = new SignElement(recipients, testDate, payload);
|
||||||
|
|
||||||
|
assertXMLEqual(expected, element.toXML(null).toString());
|
||||||
|
|
||||||
|
XmlPullParser parser = TestUtils.getParser(expected);
|
||||||
|
SignElement parsed = SignElementProvider.TEST_INSTANCE.parse(parser);
|
||||||
|
|
||||||
|
assertEquals(element.getTimestamp(), parsed.getTimestamp());
|
||||||
|
assertEquals(element.getTo(), parsed.getTo());
|
||||||
|
assertEquals(element.getPayload(), parsed.getPayload());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void cryptElementProviderTest() throws Exception {
|
||||||
|
String expected =
|
||||||
|
"<crypt xmlns='urn:xmpp:openpgp:0'>" +
|
||||||
|
"<to jid='alice@wonderland.lit'/>" +
|
||||||
|
"<time stamp='2014-07-10T15:06:00.000+00:00'/>" +
|
||||||
|
"<payload>" +
|
||||||
|
"<body xmlns='jabber:client' xml:lang='en'>The cake is a lie.</body>" +
|
||||||
|
"</payload>" +
|
||||||
|
"<rpad>f0rm1l4n4-mT8y33j!Y%fRSrcd^ZE4Q7VDt1L%WEgR!kv</rpad>" +
|
||||||
|
"</crypt>";
|
||||||
|
List<ExtensionElement> payload = new ArrayList<>();
|
||||||
|
payload.add(new Message.Body("en", "The cake is a lie."));
|
||||||
|
Set<Jid> to = new HashSet<>();
|
||||||
|
to.add(JidCreate.bareFrom("alice@wonderland.lit"));
|
||||||
|
CryptElement element = new CryptElement(to,
|
||||||
|
"f0rm1l4n4-mT8y33j!Y%fRSrcd^ZE4Q7VDt1L%WEgR!kv",
|
||||||
|
testDate,
|
||||||
|
payload);
|
||||||
|
|
||||||
|
assertXMLEqual(expected, element.toXML(null).toString());
|
||||||
|
|
||||||
|
XmlPullParser parser = TestUtils.getParser(expected);
|
||||||
|
CryptElement parsed = CryptElementProvider.TEST_INSTANCE.parse(parser);
|
||||||
|
|
||||||
|
assertEquals(element.getTimestamp(), parsed.getTimestamp());
|
||||||
|
assertEquals(element.getTo(), parsed.getTo());
|
||||||
|
assertEquals(element.getPayload(), parsed.getPayload());
|
||||||
|
assertEquals(element.getRandomPadding(), parsed.getRandomPadding());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void signcryptElementProviderTest() throws Exception {
|
||||||
|
String expected =
|
||||||
|
"<signcrypt xmlns='urn:xmpp:openpgp:0'>" +
|
||||||
|
"<to jid='juliet@example.org'/>" +
|
||||||
|
"<time stamp='2014-07-10T15:06:00.000+00:00'/>" +
|
||||||
|
"<payload>" +
|
||||||
|
"<body xmlns='jabber:client' xml:lang='en'>This is a secret message.</body>" +
|
||||||
|
"</payload>" +
|
||||||
|
"<rpad>f0rm1l4n4-mT8y33j!Y%fRSrcd^ZE4Q7VDt1L%WEgR!kv</rpad>" +
|
||||||
|
"</signcrypt>";
|
||||||
|
|
||||||
|
List<ExtensionElement> payload = new ArrayList<>();
|
||||||
|
payload.add(new Message.Body("en", "This is a secret message."));
|
||||||
|
Set<Jid> jids = new HashSet<>();
|
||||||
|
jids.add(JidCreate.bareFrom("juliet@example.org"));
|
||||||
|
SigncryptElement element = new SigncryptElement(jids,
|
||||||
|
"f0rm1l4n4-mT8y33j!Y%fRSrcd^ZE4Q7VDt1L%WEgR!kv",
|
||||||
|
testDate, payload);
|
||||||
|
|
||||||
|
assertXMLEqual(expected, element.toXML(null).toString());
|
||||||
|
|
||||||
|
XmlPullParser parser = TestUtils.getParser(expected);
|
||||||
|
SigncryptElement parsed = SigncryptElementProvider.TEST_INSTANCE.parse(parser);
|
||||||
|
|
||||||
|
assertEquals(element.getTimestamp(), parsed.getTimestamp());
|
||||||
|
assertEquals(element.getTo(), parsed.getTo());
|
||||||
|
assertEquals(element.getPayload(), parsed.getPayload());
|
||||||
|
assertEquals(element.getRandomPadding(), parsed.getRandomPadding());
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
}
|
|
@ -0,0 +1,59 @@
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* Copyright 2018 Paul Schaub.
|
||||||
|
*
|
||||||
|
* 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.ox;
|
||||||
|
|
||||||
|
import static junit.framework.TestCase.assertEquals;
|
||||||
|
import static junit.framework.TestCase.assertTrue;
|
||||||
|
import static org.custommonkey.xmlunit.XMLAssert.assertXMLEqual;
|
||||||
|
|
||||||
|
import java.nio.charset.Charset;
|
||||||
|
import java.util.Arrays;
|
||||||
|
import java.util.Date;
|
||||||
|
|
||||||
|
import org.jivesoftware.smack.test.util.SmackTestSuite;
|
||||||
|
import org.jivesoftware.smack.test.util.TestUtils;
|
||||||
|
import org.jivesoftware.smackx.ox.element.PubkeyElement;
|
||||||
|
import org.jivesoftware.smackx.ox.provider.PubkeyElementProvider;
|
||||||
|
|
||||||
|
import org.junit.Test;
|
||||||
|
import org.jxmpp.util.XmppDateTime;
|
||||||
|
import org.xmlpull.v1.XmlPullParser;
|
||||||
|
|
||||||
|
public class PubkeyElementTest extends SmackTestSuite {
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void providerTest() throws Exception {
|
||||||
|
String expected =
|
||||||
|
"<pubkey xmlns='urn:xmpp:openpgp:0' date='2018-01-21T10:46:21.000+00:00'>" +
|
||||||
|
"<data>" +
|
||||||
|
"BASE64_OPENPGP_PUBLIC_KEY" +
|
||||||
|
"</data>" +
|
||||||
|
"</pubkey>";
|
||||||
|
|
||||||
|
Date date = XmppDateTime.parseXEP0082Date("2018-01-21T10:46:21.000+00:00");
|
||||||
|
byte[] key = "BASE64_OPENPGP_PUBLIC_KEY".getBytes(Charset.forName("UTF-8"));
|
||||||
|
PubkeyElement element = new PubkeyElement(new PubkeyElement.PubkeyDataElement(key), date);
|
||||||
|
|
||||||
|
assertXMLEqual(expected, element.toXML(null).toString());
|
||||||
|
|
||||||
|
XmlPullParser parser = TestUtils.getParser(expected);
|
||||||
|
PubkeyElement parsed = PubkeyElementProvider.TEST_INSTANCE.parse(parser);
|
||||||
|
|
||||||
|
assertEquals(element.getDate(), parsed.getDate());
|
||||||
|
assertTrue(Arrays.equals(element.getDataElement().getB64Data(), parsed.getDataElement().getB64Data()));
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,93 @@
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* Copyright 2018 Paul Schaub.
|
||||||
|
*
|
||||||
|
* 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.ox;
|
||||||
|
|
||||||
|
import static junit.framework.TestCase.assertEquals;
|
||||||
|
|
||||||
|
import static org.custommonkey.xmlunit.XMLAssert.assertXMLEqual;
|
||||||
|
|
||||||
|
import java.util.Date;
|
||||||
|
|
||||||
|
import org.jivesoftware.smack.test.util.SmackTestSuite;
|
||||||
|
import org.jivesoftware.smack.test.util.TestUtils;
|
||||||
|
import org.jivesoftware.smackx.ox.element.PublicKeysListElement;
|
||||||
|
import org.jivesoftware.smackx.ox.provider.PublicKeysListElementProvider;
|
||||||
|
|
||||||
|
import org.junit.Test;
|
||||||
|
import org.jxmpp.util.XmppDateTime;
|
||||||
|
import org.xmlpull.v1.XmlPullParser;
|
||||||
|
|
||||||
|
public class PublicKeysListElementTest extends SmackTestSuite {
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void providerTest() throws Exception {
|
||||||
|
String expected =
|
||||||
|
"<public-keys-list xmlns='urn:xmpp:openpgp:0'>" +
|
||||||
|
"<pubkey-metadata " +
|
||||||
|
"v4-fingerprint='1357B01865B2503C18453D208CAC2A9678548E35' " +
|
||||||
|
"date='2018-03-01T15:26:12.000+00:00'" +
|
||||||
|
"/>" +
|
||||||
|
"<pubkey-metadata " +
|
||||||
|
"v4-fingerprint='67819B343B2AB70DED9320872C6464AF2A8E4C02' " +
|
||||||
|
"date='1953-05-16T12:00:00.000+00:00'" +
|
||||||
|
"/>" +
|
||||||
|
"</public-keys-list>";
|
||||||
|
|
||||||
|
Date date1 = XmppDateTime.parseDate("2018-03-01T15:26:12.000+00:00");
|
||||||
|
Date date2 = XmppDateTime.parseDate("1953-05-16T12:00:00.000+00:00");
|
||||||
|
PublicKeysListElement.PubkeyMetadataElement child1 =
|
||||||
|
new PublicKeysListElement.PubkeyMetadataElement(
|
||||||
|
"1357B01865B2503C18453D208CAC2A9678548E35", date1);
|
||||||
|
PublicKeysListElement.PubkeyMetadataElement child2 =
|
||||||
|
new PublicKeysListElement.PubkeyMetadataElement(
|
||||||
|
"67819B343B2AB70DED9320872C6464AF2A8E4C02", date2);
|
||||||
|
|
||||||
|
PublicKeysListElement element = PublicKeysListElement.builder()
|
||||||
|
.addMetadata(child1)
|
||||||
|
.addMetadata(child2)
|
||||||
|
.build();
|
||||||
|
|
||||||
|
assertXMLEqual(expected, element.toXML(null).toString());
|
||||||
|
|
||||||
|
XmlPullParser parser = TestUtils.getParser(expected);
|
||||||
|
PublicKeysListElement parsed = PublicKeysListElementProvider.TEST_INSTANCE.parse(parser);
|
||||||
|
|
||||||
|
assertEquals(element.getMetadata(), parsed.getMetadata());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void listBuilderRefusesDuplicatesTest() {
|
||||||
|
PublicKeysListElement.Builder builder = PublicKeysListElement.builder();
|
||||||
|
String fp40 = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMN";
|
||||||
|
Date oneDate = new Date(12337883234L);
|
||||||
|
Date otherDate = new Date(8888348384L);
|
||||||
|
|
||||||
|
// Check if size of metadata is one after insert.
|
||||||
|
builder.addMetadata(new PublicKeysListElement.PubkeyMetadataElement(fp40, oneDate));
|
||||||
|
assertEquals(builder.build().getMetadata().size(), 1);
|
||||||
|
|
||||||
|
// Check if size is still one after inserting element with same fp.
|
||||||
|
builder.addMetadata(new PublicKeysListElement.PubkeyMetadataElement(fp40, otherDate));
|
||||||
|
assertEquals(builder.build().getMetadata().size(), 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = IllegalArgumentException.class)
|
||||||
|
public void metadataFingerprintLengthTest() {
|
||||||
|
PublicKeysListElement.PubkeyMetadataElement element =
|
||||||
|
new PublicKeysListElement.PubkeyMetadataElement("thisIsNotTheCorrectLength", new Date());
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,52 @@
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* Copyright 2018 Paul Schaub.
|
||||||
|
*
|
||||||
|
* 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.ox;
|
||||||
|
|
||||||
|
import static junit.framework.TestCase.assertTrue;
|
||||||
|
import static org.custommonkey.xmlunit.XMLAssert.assertXMLEqual;
|
||||||
|
|
||||||
|
import java.nio.charset.Charset;
|
||||||
|
import java.util.Arrays;
|
||||||
|
|
||||||
|
import org.jivesoftware.smack.test.util.SmackTestSuite;
|
||||||
|
import org.jivesoftware.smack.test.util.TestUtils;
|
||||||
|
import org.jivesoftware.smackx.ox.element.SecretkeyElement;
|
||||||
|
import org.jivesoftware.smackx.ox.provider.SecretkeyElementProvider;
|
||||||
|
|
||||||
|
import org.junit.Test;
|
||||||
|
import org.xmlpull.v1.XmlPullParser;
|
||||||
|
|
||||||
|
public class SecretkeyElementTest extends SmackTestSuite {
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void providerTest() throws Exception {
|
||||||
|
String expected =
|
||||||
|
"<secretkey xmlns='urn:xmpp:openpgp:0'>" +
|
||||||
|
"BASE64_OPENPGP_ENCRYPTED_SECRET_KEY" +
|
||||||
|
"</secretkey>";
|
||||||
|
byte[] key = "BASE64_OPENPGP_ENCRYPTED_SECRET_KEY".getBytes(Charset.forName("UTF-8"));
|
||||||
|
|
||||||
|
SecretkeyElement element = new SecretkeyElement(key);
|
||||||
|
|
||||||
|
assertXMLEqual(expected, element.toXML(null).toString());
|
||||||
|
|
||||||
|
XmlPullParser parser = TestUtils.getParser(expected);
|
||||||
|
SecretkeyElement parsed = SecretkeyElementProvider.TEST_INSTANCE.parse(parser);
|
||||||
|
|
||||||
|
assertTrue(Arrays.equals(element.getB64Data(), parsed.getB64Data()));
|
||||||
|
}
|
||||||
|
}
|
Loading…
Reference in a new issue