1package eu.siacs.conversations.entities;
2
3import java.util.ArrayList;
4import java.util.List;
5
6import eu.siacs.conversations.crypto.PgpEngine;
7import eu.siacs.conversations.xml.Element;
8import eu.siacs.conversations.xmpp.stanzas.PresencePacket;
9import android.annotation.SuppressLint;
10
11@SuppressLint("DefaultLocale")
12public class MucOptions {
13 public static final int ERROR_NICK_IN_USE = 1;
14
15 public interface OnRenameListener {
16 public void onRename(boolean success);
17 }
18
19 public class User {
20 public static final int ROLE_MODERATOR = 3;
21 public static final int ROLE_NONE = 0;
22 public static final int ROLE_PARTICIPANT = 2;
23 public static final int ROLE_VISITOR = 1;
24 public static final int AFFILIATION_ADMIN = 4;
25 public static final int AFFILIATION_OWNER = 3;
26 public static final int AFFILIATION_MEMBER = 2;
27 public static final int AFFILIATION_OUTCAST = 1;
28 public static final int AFFILIATION_NONE = 0;
29
30 private int role;
31 private int affiliation;
32 private String name;
33 private long pgpKeyId = 0;
34
35 public String getName() {
36 return name;
37 }
38 public void setName(String user) {
39 this.name = user;
40 }
41
42 public int getRole() {
43 return this.role;
44 }
45 public void setRole(String role) {
46 role = role.toLowerCase();
47 if (role.equals("moderator")) {
48 this.role = ROLE_MODERATOR;
49 } else if (role.equals("participant")) {
50 this.role = ROLE_PARTICIPANT;
51 } else if (role.equals("visitor")) {
52 this.role = ROLE_VISITOR;
53 } else {
54 this.role = ROLE_NONE;
55 }
56 }
57 public int getAffiliation() {
58 return this.affiliation;
59 }
60 public void setAffiliation(String affiliation) {
61 if (affiliation.equalsIgnoreCase("admin")) {
62 this.affiliation = AFFILIATION_ADMIN;
63 } else if (affiliation.equalsIgnoreCase("owner")) {
64 this.affiliation = AFFILIATION_OWNER;
65 } else if (affiliation.equalsIgnoreCase("member")) {
66 this.affiliation = AFFILIATION_MEMBER;
67 } else if (affiliation.equalsIgnoreCase("outcast")) {
68 this.affiliation = AFFILIATION_OUTCAST;
69 } else {
70 this.affiliation = AFFILIATION_NONE;
71 }
72 }
73 public void setPgpKeyId(long id) {
74 this.pgpKeyId = id;
75 }
76
77 public long getPgpKeyId() {
78 return this.pgpKeyId;
79 }
80 }
81 private Account account;
82 private ArrayList<User> users = new ArrayList<User>();
83 private Conversation conversation;
84 private boolean isOnline = false;
85 private int error = 0;
86 private OnRenameListener renameListener = null;
87 private boolean aboutToRename = false;
88 private User self = new User();
89 private String subject = null;
90 private String nick;
91
92 public MucOptions(Account account) {
93 this.account = account;
94 }
95
96 public void deleteUser(String name) {
97 for(int i = 0; i < users.size(); ++i) {
98 if (users.get(i).getName().equals(name)) {
99 users.remove(i);
100 return;
101 }
102 }
103 }
104
105 public void addUser(User user) {
106 for(int i = 0; i < users.size(); ++i) {
107 if (users.get(i).getName().equals(user.getName())) {
108 users.set(i, user);
109 return;
110 }
111 }
112 users.add(user);
113 }
114
115 public void processPacket(PresencePacket packet, PgpEngine pgp) {
116 String[] fromParts = packet.getFrom().split("/");
117 if (fromParts.length>=2) {
118 String name = fromParts[1];
119 String type = packet.getAttribute("type");
120 if (type==null) {
121 User user = new User();
122 Element item = packet.findChild("x","http://jabber.org/protocol/muc#user").findChild("item");
123 user.setName(name);
124 user.setAffiliation(item.getAttribute("affiliation"));
125 user.setRole(item.getAttribute("role"));
126 user.setName(name);
127 if (name.equals(getJoinNick())) {
128 this.isOnline = true;
129 this.error = 0;
130 self = user;
131 } else {
132 addUser(user);
133 }
134 if (pgp != null) {
135 Element x = packet.findChild("x",
136 "jabber:x:signed");
137 if (x != null) {
138 Element status = packet.findChild("status");
139 String msg;
140 if (status != null) {
141 msg = status.getContent();
142 } else {
143 msg = "";
144 }
145 user.setPgpKeyId(pgp.fetchKeyId(account,msg, x.getContent()));
146 }
147 }
148 } else if (type.equals("unavailable")) {
149 if (name.equals(self.getName())) {
150 Element item = packet.findChild("x","http://jabber.org/protocol/muc#user").findChild("item");
151 String nick = item.getAttribute("nick");
152 if (nick!=null) {
153 aboutToRename = false;
154 if (renameListener!=null) {
155 renameListener.onRename(true);
156 }
157 }
158 }
159 deleteUser(packet.getAttribute("from").split("/")[1]);
160 } else if (type.equals("error")) {
161 Element error = packet.findChild("error");
162 if (error.hasChild("conflict")) {
163 if (aboutToRename) {
164 if (renameListener!=null) {
165 renameListener.onRename(false);
166 }
167 aboutToRename = false;
168 this.setJoinNick(getActualNick());
169 } else {
170 this.error = ERROR_NICK_IN_USE;
171 }
172 }
173 }
174 }
175 }
176
177 public List<User> getUsers() {
178 return this.users;
179 }
180
181 public String getProposedNick() {
182 String[] mucParts = conversation.getContactJid().split("/");
183 if (conversation.getBookmark() != null && conversation.getBookmark().getNick() != null) {
184 return conversation.getBookmark().getNick();
185 } else {
186 if (mucParts.length == 2) {
187 return mucParts[1];
188 } else {
189 return account.getUsername();
190 }
191 }
192 }
193
194 public String getJoinNick() {
195 return this.nick;
196 }
197
198 public String getActualNick() {
199 if (this.self.getName()!=null) {
200 return this.self.getName();
201 } else {
202 return this.getProposedNick();
203 }
204 }
205
206 public void setJoinNick(String nick) {
207 this.nick = nick;
208 }
209
210 public void setConversation(Conversation conversation) {
211 this.conversation = conversation;
212 }
213
214 public boolean online() {
215 return this.isOnline;
216 }
217
218 public int getError() {
219 return this.error;
220 }
221
222 public void setOnRenameListener(OnRenameListener listener) {
223 this.renameListener = listener;
224 }
225
226 public OnRenameListener getOnRenameListener() {
227 return this.renameListener;
228 }
229
230 public void setOffline() {
231 this.users.clear();
232 this.error = 0;
233 this.isOnline = false;
234 }
235
236 public User getSelf() {
237 return self;
238 }
239
240 public void setSubject(String content) {
241 this.subject = content;
242 }
243
244 public String getSubject() {
245 return this.subject;
246 }
247
248 public void flagAboutToRename() {
249 this.aboutToRename = true;
250 }
251
252 public long[] getPgpKeyIds() {
253 List<Long> ids = new ArrayList<Long>();
254 for(User user : getUsers()) {
255 if(user.getPgpKeyId()!=0) {
256 ids.add(user.getPgpKeyId());
257 }
258 }
259 long[] primitivLongArray = new long[ids.size()];
260 for(int i = 0; i < ids.size(); ++i) {
261 primitivLongArray[i] = ids.get(i);
262 }
263 return primitivLongArray;
264 }
265
266 public boolean pgpKeysInUse() {
267 for(User user : getUsers()) {
268 if (user.getPgpKeyId()!=0) {
269 return true;
270 }
271 }
272 return false;
273 }
274
275 public boolean everybodyHasKeys() {
276 for(User user : getUsers()) {
277 if (user.getPgpKeyId()==0) {
278 return false;
279 }
280 }
281 return true;
282 }
283
284 public String getJoinJid() {
285 return this.conversation.getContactJid().split("/")[0]+"/"+this.getJoinNick();
286 }
287}