powered by Jive Software

Black List filtering

Hi,

I am facing a new challenge in my XMPP quest! Indeed, I am trying to filter Chat’‘s packets from contacts listed in a Black List (group of the user’'s roster). To comply with my Interface structure, filters must be added to XMPPConnection. As a matter of fact, I created a method that executes nearly that:

  • public void filterBlackList() {

XMPPConnection connection = (XMPPConnection)sessionInfos.getConnection();

//Packet Filter definition (blocks black list contacts)

Iterator iti = null;

RosterEntry ent;

AndFilter opposedFilter = new AndFilter();

RosterGroup group = contactList.getGroup(“BlackList”); // contactList is the user’'s Roster

if(group != null) {

iti = group.getEntries();

}

if(iti != null) {

AndFilter contactFilter = new AndFilter();

while(iti.hasNext()) {

contactFilter = new AndFilter(new MessageTypeFilter(Message.Type.CHAT),

new FromContainsFilter(((RosterEntry)iti.next()).getUser()));

opposedFilter.addFilter(contactFilter);

}

}

opposedFilter.addFilter(new MessageTypeFilter(Message.Type.GROUP_CHAT));

//adds Listener and PacketFilter to connection

connection.removePacketListener(pl); //pl is a PacketFilter

connection.addPacketListener(pl,new NotFilter(opposedFilter));

}+

I call this method when user logins and each times user adds or removes entry from BlackList group. I thought this could works but it seems that it do not… In fact, I cannot understand why but packet are not filtered or all packets are refused, and sometimes I get an error on PacketListener#processPacket() method that I did not have before.

So, is there anything I coded badly? Or is there a cooler way to sort out this “black list” use case problem?

Thanks,

Seb

Ooooops, I am really tired not to have found it before! I solved it easily! I should have used OrFilter instead of AndFilter…

+public void filterBlackList() {

XMPPConnection connection = (XMPPConnection)sessionInfos.getConnection();

//Packet Filter definition (blocks black list contacts)

Iterator iti = null;

RosterEntry ent;

OrFilter opposedFilter = new OrFilter();

opposedFilter.addFilter(new MessageTypeFilter(Message.Type.GROUP_CHAT));

opposedFilter.addFilter(new MessageTypeFilter(Message.Type.ERROR));

opposedFilter.addFilter(new MessageTypeFilter(Message.Type.HEADLINE));

opposedFilter.addFilter(new MessageTypeFilter(Message.Type.NORMAL));

RosterGroup group = contactList.getGroup(sessionInfos.getBlackList());

if(group != null) {

iti = group.getEntries();

}

if(iti != null) {

while(iti.hasNext()) {

opposedFilter.addFilter(new FromContainsFilter(((RosterEntry)iti.next()).getUser()));

}

}

//adds Listener and Filter to connection

connection.removePacketListener(sessionInfos.getPacketListener());

PacketFilter filter = new AndFilter(new NotFilter(opposedFilter),

new MessageTypeFilter(Message.Type.CHAT));

connection.addPacketListener(sessionInfos.getPacketListener(),filter);

}+

It works properly now, but I am curious to know if there is a smarter code that could do the same job… Any idea?

Hey Seb,

We have the issue SMACK-31 in our roadmap which I think solves what you are trying to achieve manually. Blocking Communication is required by the XMPP spec and it involves both client and server support. Until we don’'t have official support for that you can use your workaround.

Regards,

– Gato

Thanks Gato,

Indeed, it remembers me something I read in XMPP specs… So, while waiting this issue, I am going to use my do-it-yourself method (that works fine!)

Regards,

Seb

Am working on Black List support at the moment.

Like everything else seems to be with Jabber, it’'s 10 times more complicated than necessary and the spec seems to be written by someone who hates programmers

There’'s a slight snag:

As far as I can understand the spec, a user should be able to set the active blacklist after logging in, but before sending an availble presence and retrieving the roster.

This would mean altering or adding new login methods to the XMPPConnection class, and maybe having to explitily call roster.reload and manually send the first presence packet.

(To be honest, I’'ve never been too keen on becoming imediately available after logging in - starting off as invisible could be useful )

It would prob. be best to add new login methods and depreciate the current for backwards compatibility.