handle blocking and unblocking of full jids
This commit is contained in:
parent
c9bf1474e3
commit
7e93c1021b
|
@ -0,0 +1,87 @@
|
||||||
|
package eu.siacs.conversations.entities;
|
||||||
|
|
||||||
|
import android.content.Context;
|
||||||
|
import android.text.TextUtils;
|
||||||
|
|
||||||
|
import java.util.Collections;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Locale;
|
||||||
|
|
||||||
|
import eu.siacs.conversations.utils.UIHelper;
|
||||||
|
import rocks.xmpp.addr.Jid;
|
||||||
|
|
||||||
|
public class RawBlockable implements ListItem, Blockable {
|
||||||
|
|
||||||
|
private final Account account;
|
||||||
|
private final Jid jid;
|
||||||
|
|
||||||
|
public RawBlockable(Account account, Jid jid) {
|
||||||
|
this.account = account;
|
||||||
|
this.jid = jid;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean isBlocked() {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean isDomainBlocked() {
|
||||||
|
throw new AssertionError("not implemented");
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Jid getBlockedJid() {
|
||||||
|
return this.jid;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getDisplayName() {
|
||||||
|
if (jid.isFullJid()) {
|
||||||
|
return jid.getResource();
|
||||||
|
} else {
|
||||||
|
return jid.toEscapedString();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Jid getJid() {
|
||||||
|
return this.jid;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public List<Tag> getTags(Context context) {
|
||||||
|
return Collections.emptyList();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean match(Context context, String needle) {
|
||||||
|
if (TextUtils.isEmpty(needle)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
needle = needle.toLowerCase(Locale.US).trim();
|
||||||
|
String[] parts = needle.split("\\s+");
|
||||||
|
for (String part : parts) {
|
||||||
|
if (!jid.toEscapedString().contains(part)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Account getAccount() {
|
||||||
|
return account;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int getAvatarBackgroundColor() {
|
||||||
|
return UIHelper.getColorForName(jid.toEscapedString());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int compareTo(ListItem o) {
|
||||||
|
return this.getDisplayName().compareToIgnoreCase(
|
||||||
|
o.getDisplayName());
|
||||||
|
}
|
||||||
|
}
|
|
@ -305,7 +305,7 @@ public class IqGenerator extends AbstractGenerator {
|
||||||
public IqPacket generateSetBlockRequest(final Jid jid, boolean reportSpam) {
|
public IqPacket generateSetBlockRequest(final Jid jid, boolean reportSpam) {
|
||||||
final IqPacket iq = new IqPacket(IqPacket.TYPE.SET);
|
final IqPacket iq = new IqPacket(IqPacket.TYPE.SET);
|
||||||
final Element block = iq.addChild("block", Namespace.BLOCKING);
|
final Element block = iq.addChild("block", Namespace.BLOCKING);
|
||||||
final Element item = block.addChild("item").setAttribute("jid", jid.asBareJid().toString());
|
final Element item = block.addChild("item").setAttribute("jid", jid.toEscapedString());
|
||||||
if (reportSpam) {
|
if (reportSpam) {
|
||||||
item.addChild("report", "urn:xmpp:reporting:0").addChild("spam");
|
item.addChild("report", "urn:xmpp:reporting:0").addChild("spam");
|
||||||
}
|
}
|
||||||
|
@ -316,7 +316,7 @@ public class IqGenerator extends AbstractGenerator {
|
||||||
public IqPacket generateSetUnblockRequest(final Jid jid) {
|
public IqPacket generateSetUnblockRequest(final Jid jid) {
|
||||||
final IqPacket iq = new IqPacket(IqPacket.TYPE.SET);
|
final IqPacket iq = new IqPacket(IqPacket.TYPE.SET);
|
||||||
final Element block = iq.addChild("unblock", Namespace.BLOCKING);
|
final Element block = iq.addChild("unblock", Namespace.BLOCKING);
|
||||||
block.addChild("item").setAttribute("jid", jid.asBareJid().toString());
|
block.addChild("item").setAttribute("jid", jid.toEscapedString());
|
||||||
return iq;
|
return iq;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -127,7 +127,8 @@ public class MessageParser extends AbstractParser implements OnMessagePacketRece
|
||||||
service.reportBrokenSessionException(e, postpone);
|
service.reportBrokenSessionException(e, postpone);
|
||||||
return new Message(conversation, "", Message.ENCRYPTION_AXOLOTL_FAILED, status);
|
return new Message(conversation, "", Message.ENCRYPTION_AXOLOTL_FAILED, status);
|
||||||
} else {
|
} else {
|
||||||
Log.d(Config.LOGTAG,"ignoring broken session exception because checkForDuplicase failed");
|
Log.d(Config.LOGTAG,"ignoring broken session exception because checkForDuplicates failed");
|
||||||
|
//TODO should be still emit a failed message?
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
} catch (NotEncryptedForThisDeviceException e) {
|
} catch (NotEncryptedForThisDeviceException e) {
|
||||||
|
@ -449,6 +450,7 @@ public class MessageParser extends AbstractParser implements OnMessagePacketRece
|
||||||
origin = from;
|
origin = from;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//TODO either or is probably fine?
|
||||||
final boolean checkedForDuplicates = serverMsgId != null && remoteMsgId != null && !conversation.possibleDuplicate(serverMsgId, remoteMsgId);
|
final boolean checkedForDuplicates = serverMsgId != null && remoteMsgId != null && !conversation.possibleDuplicate(serverMsgId, remoteMsgId);
|
||||||
|
|
||||||
if (origin != null) {
|
if (origin != null) {
|
||||||
|
|
|
@ -37,6 +37,7 @@ import eu.siacs.conversations.entities.Conversational;
|
||||||
import eu.siacs.conversations.entities.ListItem;
|
import eu.siacs.conversations.entities.ListItem;
|
||||||
import eu.siacs.conversations.entities.Message;
|
import eu.siacs.conversations.entities.Message;
|
||||||
import eu.siacs.conversations.entities.MucOptions;
|
import eu.siacs.conversations.entities.MucOptions;
|
||||||
|
import eu.siacs.conversations.entities.RawBlockable;
|
||||||
import eu.siacs.conversations.http.services.MuclumbusService;
|
import eu.siacs.conversations.http.services.MuclumbusService;
|
||||||
import eu.siacs.conversations.utils.UIHelper;
|
import eu.siacs.conversations.utils.UIHelper;
|
||||||
import eu.siacs.conversations.xmpp.OnAdvancedStreamFeaturesLoaded;
|
import eu.siacs.conversations.xmpp.OnAdvancedStreamFeaturesLoaded;
|
||||||
|
@ -272,7 +273,9 @@ public class AvatarService implements OnAdvancedStreamFeaturesLoaded {
|
||||||
}
|
}
|
||||||
|
|
||||||
public Bitmap get(ListItem item, int size, boolean cachedOnly) {
|
public Bitmap get(ListItem item, int size, boolean cachedOnly) {
|
||||||
if (item instanceof Contact) {
|
if (item instanceof RawBlockable) {
|
||||||
|
return get(item.getDisplayName(), item.getJid().toEscapedString(), size, cachedOnly);
|
||||||
|
} else if (item instanceof Contact) {
|
||||||
return get((Contact) item, size, cachedOnly);
|
return get((Contact) item, size, cachedOnly);
|
||||||
} else if (item instanceof Bookmark) {
|
} else if (item instanceof Bookmark) {
|
||||||
Bookmark bookmark = (Bookmark) item;
|
Bookmark bookmark = (Bookmark) item;
|
||||||
|
|
|
@ -4251,17 +4251,15 @@ public class XmppConnectionService extends Service {
|
||||||
public boolean sendBlockRequest(final Blockable blockable, boolean reportSpam) {
|
public boolean sendBlockRequest(final Blockable blockable, boolean reportSpam) {
|
||||||
if (blockable != null && blockable.getBlockedJid() != null) {
|
if (blockable != null && blockable.getBlockedJid() != null) {
|
||||||
final Jid jid = blockable.getBlockedJid();
|
final Jid jid = blockable.getBlockedJid();
|
||||||
this.sendIqPacket(blockable.getAccount(), getIqGenerator().generateSetBlockRequest(jid, reportSpam), new OnIqPacketReceived() {
|
this.sendIqPacket(blockable.getAccount(), getIqGenerator().generateSetBlockRequest(jid, reportSpam), (a, response) -> {
|
||||||
|
if (response.getType() == IqPacket.TYPE.RESULT) {
|
||||||
@Override
|
a.getBlocklist().add(jid);
|
||||||
public void onIqPacketReceived(final Account account, final IqPacket packet) {
|
|
||||||
if (packet.getType() == IqPacket.TYPE.RESULT) {
|
|
||||||
account.getBlocklist().add(jid);
|
|
||||||
updateBlocklistUi(OnUpdateBlocklist.Status.BLOCKED);
|
updateBlocklistUi(OnUpdateBlocklist.Status.BLOCKED);
|
||||||
}
|
}
|
||||||
}
|
|
||||||
});
|
});
|
||||||
if (removeBlockedConversations(blockable.getAccount(), jid)) {
|
if (blockable.getBlockedJid().isFullJid()) {
|
||||||
|
return false;
|
||||||
|
} else if (removeBlockedConversations(blockable.getAccount(), jid)) {
|
||||||
updateConversationUi();
|
updateConversationUi();
|
||||||
return true;
|
return true;
|
||||||
} else {
|
} else {
|
||||||
|
|
|
@ -28,14 +28,18 @@ public final class BlockContactDialog {
|
||||||
|
|
||||||
final String value;
|
final String value;
|
||||||
@StringRes int res;
|
@StringRes int res;
|
||||||
if (blockable.getJid().getLocal() == null || blockable.getAccount().isBlocked(Jid.ofDomain(blockable.getJid().getDomain()))) {
|
if (blockable.getJid().isFullJid()) {
|
||||||
|
builder.setTitle(isBlocked ? R.string.action_unblock_participant : R.string.action_block_participant);
|
||||||
|
value = blockable.getJid().toEscapedString();
|
||||||
|
res = isBlocked ? R.string.unblock_contact_text : R.string.block_contact_text;
|
||||||
|
} else if (blockable.getJid().getLocal() == null || blockable.getAccount().isBlocked(Jid.ofDomain(blockable.getJid().getDomain()))) {
|
||||||
builder.setTitle(isBlocked ? R.string.action_unblock_domain : R.string.action_block_domain);
|
builder.setTitle(isBlocked ? R.string.action_unblock_domain : R.string.action_block_domain);
|
||||||
value = Jid.ofDomain(blockable.getJid().getDomain()).toString();
|
value = Jid.ofDomain(blockable.getJid().getDomain()).toString();
|
||||||
res = isBlocked ? R.string.unblock_domain_text : R.string.block_domain_text;
|
res = isBlocked ? R.string.unblock_domain_text : R.string.block_domain_text;
|
||||||
} else {
|
} else {
|
||||||
int resBlockAction = blockable instanceof Conversation && ((Conversation) blockable).isWithStranger() ? R.string.block_stranger : R.string.action_block_contact;
|
int resBlockAction = blockable instanceof Conversation && ((Conversation) blockable).isWithStranger() ? R.string.block_stranger : R.string.action_block_contact;
|
||||||
builder.setTitle(isBlocked ? R.string.action_unblock_contact : resBlockAction);
|
builder.setTitle(isBlocked ? R.string.action_unblock_contact : resBlockAction);
|
||||||
value = blockable.getJid().asBareJid().toString();
|
value = blockable.getJid().asBareJid().toEscapedString();
|
||||||
res = isBlocked ? R.string.unblock_contact_text : R.string.block_contact_text;
|
res = isBlocked ? R.string.unblock_contact_text : R.string.block_contact_text;
|
||||||
}
|
}
|
||||||
binding.text.setText(JidDialog.style(xmppActivity, res, value));
|
binding.text.setText(JidDialog.style(xmppActivity, res, value));
|
||||||
|
|
|
@ -10,7 +10,10 @@ import java.util.Collections;
|
||||||
|
|
||||||
import eu.siacs.conversations.R;
|
import eu.siacs.conversations.R;
|
||||||
import eu.siacs.conversations.entities.Account;
|
import eu.siacs.conversations.entities.Account;
|
||||||
|
import eu.siacs.conversations.entities.Blockable;
|
||||||
import eu.siacs.conversations.entities.Contact;
|
import eu.siacs.conversations.entities.Contact;
|
||||||
|
import eu.siacs.conversations.entities.ListItem;
|
||||||
|
import eu.siacs.conversations.entities.RawBlockable;
|
||||||
import eu.siacs.conversations.ui.interfaces.OnBackendConnected;
|
import eu.siacs.conversations.ui.interfaces.OnBackendConnected;
|
||||||
import eu.siacs.conversations.xmpp.OnUpdateBlocklist;
|
import eu.siacs.conversations.xmpp.OnUpdateBlocklist;
|
||||||
import rocks.xmpp.addr.Jid;
|
import rocks.xmpp.addr.Jid;
|
||||||
|
@ -23,7 +26,7 @@ public class BlocklistActivity extends AbstractSearchableListItemActivity implem
|
||||||
public void onCreate(final Bundle savedInstanceState) {
|
public void onCreate(final Bundle savedInstanceState) {
|
||||||
super.onCreate(savedInstanceState);
|
super.onCreate(savedInstanceState);
|
||||||
getListView().setOnItemLongClickListener((parent, view, position, id) -> {
|
getListView().setOnItemLongClickListener((parent, view, position, id) -> {
|
||||||
BlockContactDialog.show(BlocklistActivity.this, (Contact) getListItems().get(position));
|
BlockContactDialog.show(BlocklistActivity.this, (Blockable) getListItems().get(position));
|
||||||
return true;
|
return true;
|
||||||
});
|
});
|
||||||
this.binding.fab.show();
|
this.binding.fab.show();
|
||||||
|
@ -50,9 +53,14 @@ public class BlocklistActivity extends AbstractSearchableListItemActivity implem
|
||||||
getListItems().clear();
|
getListItems().clear();
|
||||||
if (account != null) {
|
if (account != null) {
|
||||||
for (final Jid jid : account.getBlocklist()) {
|
for (final Jid jid : account.getBlocklist()) {
|
||||||
final Contact contact = account.getRoster().getContact(jid);
|
ListItem item;
|
||||||
if (contact.match(this, needle) && contact.isBlocked()) {
|
if (jid.isFullJid()) {
|
||||||
getListItems().add(contact);
|
item = new RawBlockable(account, jid);
|
||||||
|
} else {
|
||||||
|
item = account.getRoster().getContact(jid);
|
||||||
|
}
|
||||||
|
if (item.match(this, needle)) {
|
||||||
|
getListItems().add(item);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Collections.sort(getListItems());
|
Collections.sort(getListItems());
|
||||||
|
@ -78,8 +86,8 @@ public class BlocklistActivity extends AbstractSearchableListItemActivity implem
|
||||||
);
|
);
|
||||||
|
|
||||||
dialog.setOnEnterJidDialogPositiveListener((accountJid, contactJid) -> {
|
dialog.setOnEnterJidDialogPositiveListener((accountJid, contactJid) -> {
|
||||||
Contact contact = account.getRoster().getContact(contactJid);
|
Blockable blockable = new RawBlockable(account, contactJid);
|
||||||
if (xmppConnectionService.sendBlockRequest(contact, false)) {
|
if (xmppConnectionService.sendBlockRequest(blockable, false)) {
|
||||||
Toast.makeText(BlocklistActivity.this, R.string.corresponding_conversations_closed, Toast.LENGTH_SHORT).show();
|
Toast.makeText(BlocklistActivity.this, R.string.corresponding_conversations_closed, Toast.LENGTH_SHORT).show();
|
||||||
}
|
}
|
||||||
return true;
|
return true;
|
||||||
|
@ -101,4 +109,5 @@ public class BlocklistActivity extends AbstractSearchableListItemActivity implem
|
||||||
public void OnUpdateBlocklist(final OnUpdateBlocklist.Status status) {
|
public void OnUpdateBlocklist(final OnUpdateBlocklist.Status status) {
|
||||||
refreshUi();
|
refreshUi();
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -17,6 +17,8 @@
|
||||||
<string name="action_unblock_contact">Unblock contact</string>
|
<string name="action_unblock_contact">Unblock contact</string>
|
||||||
<string name="action_block_domain">Block domain</string>
|
<string name="action_block_domain">Block domain</string>
|
||||||
<string name="action_unblock_domain">Unblock domain</string>
|
<string name="action_unblock_domain">Unblock domain</string>
|
||||||
|
<string name="action_block_participant">Block participant</string>
|
||||||
|
<string name="action_unblock_participant">Unblock participant</string>
|
||||||
<string name="title_activity_manage_accounts">Manage Accounts</string>
|
<string name="title_activity_manage_accounts">Manage Accounts</string>
|
||||||
<string name="title_activity_settings">Settings</string>
|
<string name="title_activity_settings">Settings</string>
|
||||||
<string name="title_activity_sharewith">Share with Conversation</string>
|
<string name="title_activity_sharewith">Share with Conversation</string>
|
||||||
|
|
Loading…
Reference in New Issue