MobArena icon indicating copy to clipboard operation
MobArena copied to clipboard

Isolated chat feature does not work with BungeeCord networks that have connected global chat.

Open mibby opened this issue 8 years ago • 9 comments

MobArena v0.97.2-SNAPSHOT Paper dev 882

@garbagemule The isolated-chat: true feature does not work with networked servers that have a shared global chat. It isolates arena chat on the server with the plugin but not on the other. I suspect this is due to how the isolation feature works in MobArena. Using the PVPArena plugin by slipcor, chat is truly isolated to the server with the plugin only, when in / part of the arena. I have tested functionality with two global chat plugins. The message gets through to the other server in both cases.

I'd greatly appreciate an actual chat system / prefixed chat in MA to avoid spam across my network's global chat. :)

mibby avatar Oct 02 '16 08:10 mibby

Seems this API method only sees local players and the server chat hook still sends it anyways:

https://github.com/garbagemule/MobArena/blob/master/src/main/java/com/garbagemule/MobArena/listeners/MAGlobalListener.java#L241

So a way to fix this is killing the event and sending the event's message to each player individually

slipcor avatar Dec 17 '16 11:12 slipcor

@garbagemule Was wondering since MobArena is now utilizing a global messenger for prefix, if a prefix could be added to the isolated chat while part of the mobarena, so players know their chat is arena only.

mibby avatar Mar 15 '17 13:03 mibby

I have a feeling this is going to be a long journey. Let's start by establishing the facts of current state of things.

Bukkit's Chat API

When a player types a message in the chat, it fires an AsyncPlayerChatEvent. The event consists of the following relevant properties:

  • the player who typed the message,
  • the message the player typed,
  • the format string by which the message will be formatted, and
  • a list of recipients

It is possible to manipulate the format, the message, and the set of recipients.

Isolating Messages

If an arena has isolated-chat: true, MobArena will modify the event by a set operation on the recipients set - it retains all players currently in the arena of the player who typed the message. As a result, the message will only be delivered to the players in the arena.

An important detail with this approach is that MobArena doesn't "forward" the message in any way. The event is not cancelled - it just goes through, because it should. It is a chat event, and it should pass through all the other event handlers as a chat event. The only difference is that MobArena decides who the message is eventually delivered to.

The importance lies in compliance with the event-driven paradigm. Most notably in relation to chat plugins - they still treat it as a normal event and run all their fancy logic against it (including formatting, styling, channel stuff, etc.).

Enter BungeeCord

With BungeeCord in the mix, things get really icky. MobArena still does the right thing, but BungeeCord has its own event listener for chat events. If it receives an event that hasn't been cancelled, it will forward that event to all other servers in its cluster (based on some configuration values, I'm guessing).

As a result, MobArena's correct treatment of the event is now "broken". We need to keep in mind that BungeeCord is just a massive hack, and the way it handles chat events is what is actually broken here. That said, I can think of no other straightforward way to implement a cluster-wide chat system without injecting some sort of faux player instance acting like a proxy (this opens a completely different can of worms).

PvPArena's Solution

In PvPArena, the solution is to simply cancel the event. To BungeeCord, this chat message will never be displayed to anyone, because the event is cancelled. PvPArena then "forwards" the message to the players in the arena as per-player messages from the server, leaving the impression that the chat event actually went through (but it never did).

My biggest issue with this solution is that it breaks the event-driven paradigm. The event is cancelled, signaling "this was never actually sent to anyone", yet the message itself was extracted and passed on, behind the event system's back. From a purely theoretical perspective, this is completely unacceptable, because it removes from the paradigm the essence of decoupling and "fairness".

From a more pragmatic perspective, it is less dire. It's still pretty unfortunate, though, because chat plugins no longer get the "final say" that they should have, being plugins dedicated to these events. They also may not get a say in terms of formatting and styling. So now you have a broken chat plugin.

Other plugins, like event loggers, are also affected, being tricked into thinking they shouldn't log a chat message, even though it was clearly handed off to the players.

The Best Worst Solution?

We live in a world of sub-optimal solutions, and sometimes you just gotta pick one and roll with it. I still believe there solutions that don't involve breaking the event-driven paradigm.

Even if an optimal solution existed within BungeeCord, the chance of it ever being implemented is almost laughably slim, given past experiences.

I think the most important thing to figure out is whether or not the chat plugins' native isolated chats can't be used instead of pushing that responsibility on to MobArena. I mean, they are chat plugins - they are better at this than a minigame plugin would ever be. So perhaps the entire thing could be solved by using proximity-based chat channels, MobArena's class permissions, or perhaps a "run command as player"-based solution in MobArena that allows for even more flexibility than "just" chat plugin integration?

garbagemule avatar Mar 15 '17 23:03 garbagemule

For what it's worth, PvPArena's solution does work wonderfully in my driven case since it does keep the chat isolated strictly to the list of players part of the arena. Since the chat event is cancelled and then forwarded to that specific list of players only, there is no worries about that spam being sent across all servers connected in the proxy-server mesh network.

While it may be fine for most people to have a local 'isolated' server-specific chat handled by the chat plugin itself, in my case I prefer to have one unified 'global' chat across all my servers with the arenas itself isolating chat to avoid gameplay spam. Since I actually utilize a unified global chat system instead of proximity and server based, this wouldn't work well for me.

mibby avatar Mar 16 '17 05:03 mibby

If the chat plugin supports cluster-wide channels and proximity- or membership-based channels (I imagine most do), the solution I'm envisioning revolves around combining them. In bullets:

  • There is a main, global, cluster-wide chat channel. This is the main/only channel that everyone typically talks in.
  • Each arena has its own channel.
  • When a player joins an arena, they join the arena's channel and have that channel selected as their "current" channel. When they type, only people in that channel see their messages. They still see messages from the global channel (optional).
  • When an arena player leaves the arena, they leave the arena's channel as well.

I see no better solution than this. It would require changes in MobArena, but the changes would likely be beneficial to other situations. Better yet, it might be completely doable with an addon plugin. MobArena should not break compliance with the platform's paradigm just to support BungeeCord setups.

garbagemule avatar Mar 16 '17 11:03 garbagemule

Cross-referencing #395

ct-martin avatar Dec 26 '17 20:12 ct-martin

To let other plugins that process the chat event, we must have something that cancel the event on bungeecord side. Thats possible but then need more works for bungeecord

SaitDev avatar Sep 27 '18 02:09 SaitDev

Hi, try adding support for bungeecord to solve this issue but I fail it. The solution now fall back to https://github.com/garbagemule/MobArena/issues/395#issuecomment-350043365 Question: your cross server chat is being implemented by ChatControl or what plugin, and all normal chat is sent to other server? @mibby

SaitDev avatar Nov 20 '18 15:11 SaitDev

@SaitDev I use ChatControlPro for syncing chat, yep. Apologies for the late reply!

mibby avatar Dec 25 '18 05:12 mibby