1package im.conversations.android.xmpp;
 2
 3
 4import com.google.common.base.MoreObjects;
 5import com.google.common.base.Objects;
 6
 7import eu.siacs.conversations.xml.Element;
 8
 9import im.conversations.android.xmpp.model.Extension;
10
11import java.lang.reflect.Constructor;
12import java.lang.reflect.InvocationTargetException;
13
14public final class ExtensionFactory {
15
16    public static Element create(final String name, final String namespace) {
17        final Class<? extends Extension> clazz = of(name, namespace);
18        if (clazz == null) {
19            return new Element(name, namespace);
20        }
21        final Constructor<? extends Element> constructor;
22        try {
23            constructor = clazz.getDeclaredConstructor();
24        } catch (final NoSuchMethodException e) {
25            throw new IllegalStateException(
26                    String.format("%s has no default constructor", clazz.getName()),e);
27        }
28        try {
29            return constructor.newInstance();
30        } catch (final IllegalAccessException
31                | InstantiationException
32                | InvocationTargetException e) {
33            throw new IllegalStateException(
34                    String.format("%s has inaccessible default constructor", clazz.getName()),e);
35        }
36    }
37
38    private static Class<? extends Extension> of(final String name, final String namespace) {
39        return Extensions.EXTENSION_CLASS_MAP.get(new Id(name, namespace));
40    }
41
42    public static Id id(final Class<? extends Extension> clazz) {
43        return Extensions.EXTENSION_CLASS_MAP.inverse().get(clazz);
44    }
45
46    private ExtensionFactory() {}
47
48    public static class Id {
49        public final String name;
50        public final String namespace;
51
52        public Id(String name, String namespace) {
53            this.name = name;
54            this.namespace = namespace;
55        }
56
57        @Override
58        public boolean equals(Object o) {
59            if (this == o) return true;
60            if (o == null || getClass() != o.getClass()) return false;
61            Id id = (Id) o;
62            return Objects.equal(name, id.name) && Objects.equal(namespace, id.namespace);
63        }
64
65        @Override
66        public int hashCode() {
67            return Objects.hashCode(name, namespace);
68        }
69
70        @Override
71        public String toString() {
72            return MoreObjects.toStringHelper(this)
73                    .add("name", name)
74                    .add("namespace", namespace)
75                    .toString();
76        }
77    }
78}