1package im.conversations.android.xmpp.model.stanza;
2
3import com.google.common.base.Strings;
4import com.google.common.collect.ImmutableMap;
5import eu.siacs.conversations.xml.Element;
6import eu.siacs.conversations.xml.LocalizedContent;
7import im.conversations.android.annotation.XmlElement;
8import im.conversations.android.xmpp.model.Extension;
9import im.conversations.android.xmpp.model.jabber.Body;
10import im.conversations.android.xmpp.model.jabber.Subject;
11import java.util.Locale;
12
13@XmlElement
14public class Message extends Stanza {
15
16 public Message() {
17 super(Message.class);
18 }
19
20 public Message(Type type) {
21 this();
22 this.setType(type);
23 }
24
25 public LocalizedContent getBody() {
26 return getLocalizedContent(Body.class);
27 }
28
29 public LocalizedContent getSubject() {
30 return getLocalizedContent(Subject.class);
31 }
32
33 private LocalizedContent getLocalizedContent(final Class<? extends Extension> clazz) {
34 final var builder = new ImmutableMap.Builder<String, String>();
35 final var messageLanguage = this.getAttribute("xml:lang");
36 final var parentLanguage =
37 Strings.isNullOrEmpty(messageLanguage)
38 ? LocalizedContent.STREAM_LANGUAGE
39 : messageLanguage;
40 for (final var element : this.getExtensions(clazz)) {
41 final var elementLanguage = element.getAttribute("xml:lang");
42 final var language =
43 Strings.isNullOrEmpty(elementLanguage) ? parentLanguage : elementLanguage;
44 final var content = element.getContent();
45 if (content == null) {
46 continue;
47 }
48 builder.put(language, content);
49 }
50 try {
51 return LocalizedContent.get(builder.buildOrThrow());
52 } catch (final IllegalArgumentException e) {
53 return null;
54 }
55 }
56
57 public Type getType() {
58 final var value = this.getAttribute("type");
59 if (value == null) {
60 return Type.NORMAL;
61 } else {
62 try {
63 return Type.valueOf(value.toUpperCase(Locale.ROOT));
64 } catch (final IllegalArgumentException e) {
65 return null;
66 }
67 }
68 }
69
70 public void setType(final Type type) {
71 if (type == null || type == Type.NORMAL) {
72 this.removeAttribute("type");
73 } else {
74 this.setAttribute("type", type.toString().toLowerCase(Locale.ROOT));
75 }
76 }
77
78 public void setBody(final String text) {
79 this.addExtension(new Body(text));
80 }
81
82 public void setAxolotlMessage(Element axolotlMessage) {
83 this.children.remove(findChild("body"));
84 this.children.add(0, axolotlMessage);
85 }
86
87 public enum Type {
88 ERROR,
89 NORMAL,
90 GROUPCHAT,
91 HEADLINE,
92 CHAT
93 }
94}