mirror of
https://github.com/ColdeZhang/Dominion.git
synced 2024-10-19 02:46:49 +08:00
优化成员权限缓存更新加载策略,提高效率
This commit is contained in:
parent
2f9c4cd73a
commit
278ce8a686
2
pom.xml
2
pom.xml
@ -6,7 +6,7 @@
|
|||||||
|
|
||||||
<groupId>cn.lunadeer</groupId>
|
<groupId>cn.lunadeer</groupId>
|
||||||
<artifactId>Dominion</artifactId>
|
<artifactId>Dominion</artifactId>
|
||||||
<version>1.33.2-mysql-beta</version>
|
<version>1.33.3-mysql-beta</version>
|
||||||
<packaging>jar</packaging>
|
<packaging>jar</packaging>
|
||||||
|
|
||||||
<name>Dominion</name>
|
<name>Dominion</name>
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
package cn.lunadeer.dominion;
|
package cn.lunadeer.dominion;
|
||||||
|
|
||||||
import cn.lunadeer.dominion.dtos.DominionDTO;
|
import cn.lunadeer.dominion.dtos.DominionDTO;
|
||||||
|
import cn.lunadeer.minecraftpluginutils.Scheduler;
|
||||||
import cn.lunadeer.minecraftpluginutils.XLogger;
|
import cn.lunadeer.minecraftpluginutils.XLogger;
|
||||||
import com.flowpowered.math.vector.Vector2d;
|
import com.flowpowered.math.vector.Vector2d;
|
||||||
import de.bluecolored.bluemap.api.BlueMapAPI;
|
import de.bluecolored.bluemap.api.BlueMapAPI;
|
||||||
@ -17,6 +18,7 @@ public class BlueMapConnect {
|
|||||||
if (!Dominion.config.getBlueMap()) {
|
if (!Dominion.config.getBlueMap()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
Scheduler.runTaskAsync(() -> {
|
||||||
try {
|
try {
|
||||||
BlueMapAPI.getInstance().ifPresent(api -> {
|
BlueMapAPI.getInstance().ifPresent(api -> {
|
||||||
Map<String, List<DominionDTO>> world_dominions = new HashMap<>();
|
Map<String, List<DominionDTO>> world_dominions = new HashMap<>();
|
||||||
@ -70,12 +72,14 @@ public class BlueMapConnect {
|
|||||||
XLogger.warn("无法连接 BlueMap 插件,如果你不打算使用卫星地图渲染建议前往配置文件关闭此功能以避免下方的报错。");
|
XLogger.warn("无法连接 BlueMap 插件,如果你不打算使用卫星地图渲染建议前往配置文件关闭此功能以避免下方的报错。");
|
||||||
XLogger.err(e.getMessage());
|
XLogger.err(e.getMessage());
|
||||||
}
|
}
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void renderMCA(Map<String, List<String>> mca_files) {
|
public static void renderMCA(Map<String, List<String>> mca_files) {
|
||||||
if (!Dominion.config.getBlueMap()) {
|
if (!Dominion.config.getBlueMap()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
Scheduler.runTaskAsync(() -> {
|
||||||
try {
|
try {
|
||||||
BlueMapAPI.getInstance().ifPresent(api -> {
|
BlueMapAPI.getInstance().ifPresent(api -> {
|
||||||
for (String world : mca_files.keySet()) {
|
for (String world : mca_files.keySet()) {
|
||||||
@ -124,5 +128,6 @@ public class BlueMapConnect {
|
|||||||
XLogger.warn("无法连接 BlueMap 插件,如果你不打算使用卫星地图渲染建议前往配置文件关闭此功能以避免下方的报错。");
|
XLogger.warn("无法连接 BlueMap 插件,如果你不打算使用卫星地图渲染建议前往配置文件关闭此功能以避免下方的报错。");
|
||||||
XLogger.err(e.getMessage());
|
XLogger.err(e.getMessage());
|
||||||
}
|
}
|
||||||
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -51,6 +51,7 @@ public class Cache {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private void loadDominionsExecution() {
|
private void loadDominionsExecution() {
|
||||||
|
Scheduler.runTaskAsync(() -> {
|
||||||
long start = System.currentTimeMillis();
|
long start = System.currentTimeMillis();
|
||||||
id_dominions = new ConcurrentHashMap<>();
|
id_dominions = new ConcurrentHashMap<>();
|
||||||
world_dominion_tree = new ConcurrentHashMap<>();
|
world_dominion_tree = new ConcurrentHashMap<>();
|
||||||
@ -74,35 +75,49 @@ public class Cache {
|
|||||||
BlueMapConnect.render();
|
BlueMapConnect.render();
|
||||||
recheckPlayerState = true;
|
recheckPlayerState = true;
|
||||||
_last_update_dominion.set(System.currentTimeMillis());
|
_last_update_dominion.set(System.currentTimeMillis());
|
||||||
XLogger.debug("loadDominionsExecution cost: %d ms", System.currentTimeMillis() - start);
|
XLogger.debug("loadDominionsExecution cost: %d ms for %d dominions"
|
||||||
|
, System.currentTimeMillis() - start, dominions.size());
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 从数据库加载所有玩家特权
|
* 从数据库加载所有玩家特权
|
||||||
|
* 如果player_uuid为null,则加载所有玩家的特权
|
||||||
|
*
|
||||||
|
* @param player_uuid 玩家UUID
|
||||||
*/
|
*/
|
||||||
public void loadPlayerPrivileges() {
|
public void loadPlayerPrivileges(UUID player_uuid) {
|
||||||
if (_last_update_privilege.get() + UPDATE_INTERVAL < System.currentTimeMillis()) {
|
if (_last_update_privilege.get() + UPDATE_INTERVAL < System.currentTimeMillis()) {
|
||||||
loadPlayerPrivilegesExecution();
|
XLogger.debug("run loadPlayerPrivilegesExecution directly");
|
||||||
|
loadPlayerPrivilegesExecution(player_uuid);
|
||||||
} else {
|
} else {
|
||||||
if (_update_privilege_is_scheduled.get()) return;
|
if (_update_privilege_is_scheduled.get()) return;
|
||||||
|
XLogger.debug("schedule loadPlayerPrivilegesExecution");
|
||||||
_update_privilege_is_scheduled.set(true);
|
_update_privilege_is_scheduled.set(true);
|
||||||
long delay_tick = (UPDATE_INTERVAL - (System.currentTimeMillis() - _last_update_dominion.get())) / 1000 * 20L;
|
long delay_tick = (UPDATE_INTERVAL - (System.currentTimeMillis() - _last_update_privilege.get())) / 1000 * 20L;
|
||||||
Scheduler.runTaskLaterAsync(() -> {
|
Scheduler.runTaskLaterAsync(() -> {
|
||||||
loadPlayerPrivilegesExecution();
|
XLogger.debug("run loadPlayerPrivilegesExecution scheduled");
|
||||||
|
loadPlayerPrivilegesExecution(player_uuid);
|
||||||
_update_privilege_is_scheduled.set(false);
|
_update_privilege_is_scheduled.set(false);
|
||||||
},
|
},
|
||||||
delay_tick);
|
delay_tick);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void loadPlayerPrivilegesExecution() {
|
public void loadPlayerPrivileges() {
|
||||||
long start = System.currentTimeMillis();
|
loadPlayerPrivileges(null);
|
||||||
List<PlayerPrivilegeDTO> all_privileges = PlayerPrivilegeDTO.selectAll();
|
|
||||||
if (all_privileges == null) {
|
|
||||||
XLogger.err("加载玩家特权失败");
|
|
||||||
return;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private void loadPlayerPrivilegesExecution(UUID player_to_update) {
|
||||||
|
Scheduler.runTaskAsync(() -> {
|
||||||
|
long start = System.currentTimeMillis();
|
||||||
|
List<PlayerPrivilegeDTO> all_privileges = new ArrayList<>();
|
||||||
|
if (player_to_update == null) {
|
||||||
|
all_privileges = PlayerPrivilegeDTO.selectAll();
|
||||||
player_uuid_to_privilege = new ConcurrentHashMap<>();
|
player_uuid_to_privilege = new ConcurrentHashMap<>();
|
||||||
|
} else {
|
||||||
|
all_privileges = PlayerPrivilegeDTO.selectAll(player_to_update);
|
||||||
|
}
|
||||||
for (PlayerPrivilegeDTO privilege : all_privileges) {
|
for (PlayerPrivilegeDTO privilege : all_privileges) {
|
||||||
UUID player_uuid = privilege.getPlayerUUID();
|
UUID player_uuid = privilege.getPlayerUUID();
|
||||||
if (!player_uuid_to_privilege.containsKey(player_uuid)) {
|
if (!player_uuid_to_privilege.containsKey(player_uuid)) {
|
||||||
@ -112,7 +127,9 @@ public class Cache {
|
|||||||
}
|
}
|
||||||
recheckPlayerState = true;
|
recheckPlayerState = true;
|
||||||
_last_update_privilege.set(System.currentTimeMillis());
|
_last_update_privilege.set(System.currentTimeMillis());
|
||||||
XLogger.debug("loadPlayerPrivilegesExecution cost: %d ms", System.currentTimeMillis() - start);
|
XLogger.debug("loadPlayerPrivilegesExecution cost: %d ms for %d privileges"
|
||||||
|
, System.currentTimeMillis() - start, all_privileges.size());
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -318,7 +335,7 @@ public class Cache {
|
|||||||
private final AtomicBoolean _update_dominion_is_scheduled = new AtomicBoolean(false);
|
private final AtomicBoolean _update_dominion_is_scheduled = new AtomicBoolean(false);
|
||||||
private final AtomicLong _last_update_privilege = new AtomicLong(0);
|
private final AtomicLong _last_update_privilege = new AtomicLong(0);
|
||||||
private final AtomicBoolean _update_privilege_is_scheduled = new AtomicBoolean(false);
|
private final AtomicBoolean _update_privilege_is_scheduled = new AtomicBoolean(false);
|
||||||
private static final long UPDATE_INTERVAL = 1000 * 5;
|
private static final long UPDATE_INTERVAL = 1000 * 4;
|
||||||
private boolean recheckPlayerState = false; // 是否需要重新检查玩家状态(发光、飞行)
|
private boolean recheckPlayerState = false; // 是否需要重新检查玩家状态(发光、飞行)
|
||||||
public final Map<UUID, LocalDateTime> NextTimeAllowTeleport = new java.util.HashMap<>();
|
public final Map<UUID, LocalDateTime> NextTimeAllowTeleport = new java.util.HashMap<>();
|
||||||
}
|
}
|
||||||
|
@ -5,24 +5,38 @@ import org.bukkit.Location;
|
|||||||
import org.jetbrains.annotations.NotNull;
|
import org.jetbrains.annotations.NotNull;
|
||||||
|
|
||||||
import javax.annotation.Nullable;
|
import javax.annotation.Nullable;
|
||||||
import java.util.ArrayList;
|
import java.util.*;
|
||||||
import java.util.List;
|
|
||||||
import java.util.Objects;
|
|
||||||
|
|
||||||
public class DominionNode {
|
public class DominionNode {
|
||||||
public DominionDTO dominion;
|
public DominionDTO dominion;
|
||||||
public List<DominionNode> children = new ArrayList<>();
|
public List<DominionNode> children = new ArrayList<>();
|
||||||
|
|
||||||
public static List<DominionNode> BuildNodeTree(Integer rootId, List<DominionDTO> dominions) {
|
public static List<DominionNode> BuildNodeTree(Integer rootId, List<DominionDTO> dominions) {
|
||||||
List<DominionNode> dominionTree = new ArrayList<>();
|
// 映射父节点ID到其子节点列表
|
||||||
|
Map<Integer, List<DominionDTO>> parentToChildrenMap = new HashMap<>();
|
||||||
for (DominionDTO dominion : dominions) {
|
for (DominionDTO dominion : dominions) {
|
||||||
if (Objects.equals(dominion.getParentDomId(), rootId)) {
|
parentToChildrenMap
|
||||||
|
.computeIfAbsent(dominion.getParentDomId(), k -> new ArrayList<>())
|
||||||
|
.add(dominion);
|
||||||
|
}
|
||||||
|
|
||||||
|
// 递归构建节点树
|
||||||
|
return buildTree(rootId, parentToChildrenMap);
|
||||||
|
}
|
||||||
|
|
||||||
|
private static List<DominionNode> buildTree(Integer rootId, Map<Integer, List<DominionDTO>> parentToChildrenMap) {
|
||||||
|
List<DominionNode> dominionTree = new ArrayList<>();
|
||||||
|
List<DominionDTO> children = parentToChildrenMap.get(rootId);
|
||||||
|
|
||||||
|
if (children != null) {
|
||||||
|
for (DominionDTO dominion : children) {
|
||||||
DominionNode node = new DominionNode();
|
DominionNode node = new DominionNode();
|
||||||
node.dominion = dominion;
|
node.dominion = dominion;
|
||||||
node.children = BuildNodeTree(dominion.getId(), dominions);
|
node.children = buildTree(dominion.getId(), parentToChildrenMap);
|
||||||
dominionTree.add(node);
|
dominionTree.add(node);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return dominionTree;
|
return dominionTree;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -103,18 +103,17 @@ public class PrivilegeController {
|
|||||||
privilege = createPlayerPrivilege(operator, player.getUuid(), dominion);
|
privilege = createPlayerPrivilege(operator, player.getUuid(), dominion);
|
||||||
if (privilege == null) return;
|
if (privilege == null) return;
|
||||||
}
|
}
|
||||||
if (privilege.getAdmin()) {
|
if ((flag.equals("admin") || privilege.getAdmin()) && notOwner(operator, dominion)) {
|
||||||
if (notOwner(operator, dominion)) {
|
operator.setResponse(FAIL.addMessage("你不是领地 %s 的拥有者,无法修改其他玩家管理员的权限", dominionName));
|
||||||
operator.setResponse(FAIL.addMessage("你不是领地 %s 的拥有者,无法修改其他管理员的权限", dominionName));
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (flag.equals("admin")) {
|
if (flag.equals("admin")) {
|
||||||
privilege.setAdmin(value);
|
privilege.setAdmin(value);
|
||||||
} else {
|
} else {
|
||||||
|
if (privilege.getAdmin()) {
|
||||||
operator.setResponse(FAIL.addMessage("管理员拥有所有权限,无需单独设置权限"));
|
operator.setResponse(FAIL.addMessage("管理员拥有所有权限,无需单独设置权限"));
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
} else {
|
|
||||||
Flag f = Flag.getFlag(flag);
|
Flag f = Flag.getFlag(flag);
|
||||||
if (f == null) {
|
if (f == null) {
|
||||||
operator.setResponse(FAIL.addMessage("未知的领地权限 %s", flag));
|
operator.setResponse(FAIL.addMessage("未知的领地权限 %s", flag));
|
||||||
|
@ -44,7 +44,7 @@ public class PlayerPrivilegeDTO {
|
|||||||
try (ResultSet rs = updateRow.execute()) {
|
try (ResultSet rs = updateRow.execute()) {
|
||||||
List<PlayerPrivilegeDTO> players = getDTOFromRS(rs);
|
List<PlayerPrivilegeDTO> players = getDTOFromRS(rs);
|
||||||
if (players.size() == 0) return null;
|
if (players.size() == 0) return null;
|
||||||
Cache.instance.loadPlayerPrivileges();
|
Cache.instance.loadPlayerPrivileges(playerUUID);
|
||||||
return players.get(0);
|
return players.get(0);
|
||||||
} catch (Exception e) {
|
} catch (Exception e) {
|
||||||
DatabaseManager.handleDatabaseError("更新玩家权限失败: ", e, "");
|
DatabaseManager.handleDatabaseError("更新玩家权限失败: ", e, "");
|
||||||
@ -65,7 +65,7 @@ public class PlayerPrivilegeDTO {
|
|||||||
insertRow.field(new Field(f.getFlagName(), player.getFlagValue(f)));
|
insertRow.field(new Field(f.getFlagName(), player.getFlagValue(f)));
|
||||||
}
|
}
|
||||||
try (ResultSet rs = insertRow.execute()) {
|
try (ResultSet rs = insertRow.execute()) {
|
||||||
Cache.instance.loadPlayerPrivileges();
|
Cache.instance.loadPlayerPrivileges(player.getPlayerUUID());
|
||||||
List<PlayerPrivilegeDTO> players = getDTOFromRS(rs);
|
List<PlayerPrivilegeDTO> players = getDTOFromRS(rs);
|
||||||
if (players.size() == 0) return null;
|
if (players.size() == 0) return null;
|
||||||
return players.get(0);
|
return players.get(0);
|
||||||
@ -134,7 +134,6 @@ public class PlayerPrivilegeDTO {
|
|||||||
flags.put(flag, value);
|
flags.put(flag, value);
|
||||||
Field f = new Field(flag.getFlagName(), value);
|
Field f = new Field(flag.getFlagName(), value);
|
||||||
UpdateRow updateRow = new UpdateRow().field(f);
|
UpdateRow updateRow = new UpdateRow().field(f);
|
||||||
XLogger.debug("setFlagValue: " + updateRow.toString());
|
|
||||||
return doUpdate(updateRow);
|
return doUpdate(updateRow);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user