Skip to content

Commit

Permalink
feat(bluemap/chat): general improvements (#7)
Browse files Browse the repository at this point in the history
Click on login text to start login process
Custom web chat prefix
Max amount of stored messages for web app
`/say` support
Collapsible chat
Message popups that disappear

Additionally `ip_lock` setting for Authentication
  • Loading branch information
Eatham532 authored Aug 20, 2024
1 parent cdd7d0e commit fa2a6a8
Show file tree
Hide file tree
Showing 7 changed files with 238 additions and 34 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -16,11 +16,13 @@ public final class AuthenticationPlugin extends JavaPlugin implements CommandExe
AuthenticationWebServer server;
AuthenticationDatabase db;
private int userMaxSessions;
boolean ipLock;

@Override
public void onEnable() {
this.saveDefaultConfig();
this.userMaxSessions = this.getConfig().getInt("user_max_sessions", 3);
this.ipLock = this.getConfig().getBoolean("ip_lock", true);
File webRoot = getDataFolder().toPath().resolve("web").toFile();
if (!webRoot.exists()) {
boolean _ignored = webRoot.mkdirs();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -50,7 +50,7 @@ public AuthenticationWebServer(@NotNull AuthenticationPlugin plugin) throws IOEx
else request.respond(401);
return;
}
if (!request.getProxyIp().equals(session.ip)) {
if (!request.getProxyIp().equals(session.ip) && plugin.ipLock) {
plugin.db.deleteSession(sessionId);
if (optionalAuth) {
request.setHeader(X_LOGGEDIN_HEADER, "false");
Expand Down
1 change: 1 addition & 0 deletions Authentication/src/main/resources/config.yml
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
ip: "127.0.0.1"
port: 8200

ip_lock: true
optional_authentication: false
session_length_days: 31
auth_token_length: 7
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,17 +11,17 @@
import org.bukkit.event.EventPriority;
import org.bukkit.event.Listener;
import org.bukkit.event.entity.PlayerDeathEvent;
import org.bukkit.event.player.AsyncPlayerChatEvent;
import org.bukkit.event.player.PlayerJoinEvent;
import org.bukkit.event.player.PlayerQuitEvent;
import org.bukkit.event.player.*;
import org.bukkit.event.server.ServerCommandEvent;
import org.bukkit.plugin.java.JavaPlugin;

import java.io.IOException;
import java.io.OutputStream;
import java.nio.charset.StandardCharsets;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.StandardOpenOption;
import java.util.Objects;
import java.util.Optional;
import java.util.UUID;
import java.util.concurrent.*;

Expand All @@ -46,12 +46,31 @@ public void forEachSession(SessionOperator op) {
@Override
public void onLoad() {
BlueMapAPI.onEnable(api -> {
this.config = getConfig();

try {
api.getWebApp().registerScript("assets/bluemap-chat.js");
api.getWebApp().registerStyle("assets/bluemap-chat.css");
copyResource("bluemap-chat.js");

copyResource("bluemap-chat.css");
copyResource("minecraft.otf");

String integration = new String(Objects.requireNonNull(getResource("bluemap-chat.js")).readAllBytes(), StandardCharsets.UTF_8)
.replaceAll("\\{\\{web-chat-prefix}}", Objects.requireNonNull(this.config.getString("web-chat-prefix", "[web]")))
.replaceAll("\\{\\{max-message-count}}", Objects.requireNonNull(this.config.getString("max-message-count", "100")));

Optional<String> authPath = Optional.ofNullable(getServer().getPluginManager().getPlugin("BlueMap-Auth"))
.map(plugin -> plugin.getConfig().getString("auth-path", "/authentication-outpost/"));

if (authPath.isPresent()) {
integration = integration.replaceAll("\\{\\{auth-path}}", authPath.get());
}

Path chatPath = api.getWebApp().getWebRoot().resolve("assets/bluemap-chat.js");
Files.createDirectories(chatPath.getParent());
OutputStream out = Files.newOutputStream(chatPath, StandardOpenOption.CREATE, StandardOpenOption.TRUNCATE_EXISTING);
out.write(integration.getBytes(StandardCharsets.UTF_8));
out.close();
} catch (IOException ex) {
getLogger().severe("Couldn't move chat resources to BlueMap!");
ex.printStackTrace();
Expand All @@ -61,18 +80,13 @@ public void onLoad() {

@Override
public void onEnable() {
pingSchedule = scheduler.scheduleAtFixedRate(new Runnable() {
public void run() {
forEachSession(SSERequest::ping);
}
}, 0, 30, TimeUnit.SECONDS);
pingSchedule = scheduler.scheduleAtFixedRate(() -> forEachSession(SSERequest::ping), 0, 30, TimeUnit.SECONDS);

getServer().getPluginManager().registerEvents(this, this);

BlueMapAPI.onEnable(api -> {
reloadConfig();
saveDefaultConfig();
this.config = getConfig();

try {
this.http = new WebServer(Objects.requireNonNull(config.getString("ip", "0.0.0.0")), config.getInt("port", 8800));
Expand All @@ -91,9 +105,7 @@ public void run() {
}
}
UUID uuid = UUID.randomUUID();
SSERequest sse = request.sse(() -> {
this.sessions.remove(uuid);
});
SSERequest sse = request.sse(() -> this.sessions.remove(uuid));
sse.ping();
JsonObject settingsObject = new JsonObject();
settingsObject.addProperty("type", "settings");
Expand Down Expand Up @@ -134,7 +146,7 @@ public void run() {
request.respond(400);
return;
}
getServer().broadcastMessage(String.format("[web] <%s> %s", username, messageString));
getServer().broadcastMessage(String.format("%s <%s> %s", config.getString("web-chat-prefix", "[web]"), username, messageString));
JsonObject messageObject = new JsonObject();
messageObject.addProperty("type", "webchat");
messageObject.addProperty("uuid", uuid);
Expand Down Expand Up @@ -179,6 +191,32 @@ public void onChatMessage(AsyncPlayerChatEvent event) {
forEachSession(sse -> sse.send(message));
}

@EventHandler(priority = EventPriority.MONITOR)
public void onServerCommand(ServerCommandEvent event) {
if (event.getCommand().startsWith("say ")) {
String msg = event.getCommand().substring(4).trim();
JsonObject message = new JsonObject();
message.addProperty("type", "chat");
message.addProperty("uuid", "0");
message.addProperty("username", "[Server]");
message.addProperty("message", msg);
forEachSession(sse -> sse.send(message));
}
}

@EventHandler(priority = EventPriority.MONITOR)
public void onPlayerCommandSend(PlayerCommandPreprocessEvent event) {
if (event.getMessage().startsWith("/say ")) {
String msg = event.getMessage().substring(4).trim();
JsonObject message = new JsonObject();
message.addProperty("type", "chat");
message.addProperty("uuid", event.getPlayer().getUniqueId().toString());
message.addProperty("username", event.getPlayer().getName());
message.addProperty("message", msg);
forEachSession(sse -> sse.send(message));
}
}

@EventHandler(priority = EventPriority.MONITOR)
public void onPlayerDeath(PlayerDeathEvent event) {
if (event.getEntityType() != EntityType.PLAYER) return;
Expand Down
86 changes: 78 additions & 8 deletions BlueMap/Chat/src/main/resources/bluemap-chat.css
Original file line number Diff line number Diff line change
Expand Up @@ -4,11 +4,15 @@
}

#chat-root {
grid-auto-rows: 1fr auto;
display: grid;
grid-auto-columns: 1fr auto;
grid-gap: 10px;
position: absolute;
bottom: 0;
left: 0;
width: min(calc(100vw - 4em), 600px);
height: 300px;
max-height: min(calc(100vh - 4em), 800px);
margin: 0;
padding: 0;
background-color: rgba(0,0,0, 0.25);
Expand All @@ -20,35 +24,81 @@
text-shadow: -2px 2px 0px black;
}

#chat-messages {


#chat-root.no-messages {
grid-gap: 0;
}

#chat-root.no-messages > #chat-messages-popup {
padding: 0;
}

#chat-root > .messages-div-hidden {
display: none;
visibility: hidden;
height: 0;
width: 0;
padding: 0;
margin: 0;
}

#chat-messages, #chat-messages-popup {
width: 100%;
height: calc(100% - 36px);
height: 100%;
padding: 6px;
margin: 0;
display: flex;
flex-direction: column-reverse;
overflow-x: hidden;
overflow-y: scroll;
overflow-y: auto;
gap: 4px;
box-sizing: border-box;
grid-row: 1;
grid-column: 1/ span 2;
}

#chat-messages > div {
#chat-messages > div, #chat-messages-popup > div {
word-wrap: break-word;
}

#chat-messages > .death {
#chat-messages > .death, #chat-messages-popup > .death {
color: #ea3e3e;
}

#chat-messages > .joinquit {
#chat-messages > .joinquit, #chat-messages-popup > .joinquit {
color: #fbd726;
}

#chat-input-wrapper {
grid-row: 2;
width: 100%;
height: 36px;
box-sizing: border-box;
}
#chat-input-wrapper.chat-logged-out > #chat-input {
pointer-events: none;
user-select: none;
cursor: pointer;
}
#chat-input-wrapper.read-only > #chat-input {
pointer-events: none;
user-select: none;
visibility: hidden;
}

#chat-input-wrapper.chat-logged-out:hover > #chat-input,
#chat-input-wrapper.chat-logged-out:active > #chat-input {
color: white;
cursor: pointer;
text-decoration: underline;
text-decoration-thickness: 2px;
}

#chat-input {
background-color: transparent;
width: 100%;
height: 36px;
height: 100%;
padding: 6px;
margin: 0;
box-sizing: border-box;
Expand All @@ -70,3 +120,23 @@
display: none;
}
}

#toggle-chat-view-control {
aspect-ratio: 1;
background-color: transparent;
color: white;
}

#toggle-chat-view-control:hover {
background-color: hsla(0, 20%, 10%, 0.2);
}

#toggle-chat-view-control:active {
background-color: hsla(0, 20%, 90%, 0.2);
color: #181818
}

.fade-out {
opacity: 0;
transition: opacity 0.5s ease-in-out;
}
Loading

0 comments on commit fa2a6a8

Please sign in to comment.