From 62001cc1a87d12dcf2d30d69ed0c1d9ae27f04cd Mon Sep 17 00:00:00 2001 From: Him188 Date: Thu, 5 Mar 2020 09:45:54 +0800 Subject: [PATCH] Review: misc improvements --- gradle.properties | 2 +- .../controller/MiraiGraphicalUIController.kt | 4 +- .../mirai/console/MiraiConsoleTerminalUI.kt | 114 ++++++-------- mirai-console/build.gradle.kts | 18 ++- .../net/mamoe/mirai/console/MiraiConsole.kt | 21 +-- .../mamoe/mirai/console/command/Command.kt | 145 ++++-------------- .../mirai/console/command/CommandManager.kt | 70 +++++++++ .../mirai/console/command/DefaultCommands.kt | 32 ++-- .../mirai/console/core/MiraiCoreLoader.kt | 50 +++--- .../mirai/console/plugins/ConfigSection.kt | 70 +++++---- .../mirai/console/plugins/PluginManager.kt | 3 +- .../mirai/console/pure/MiraiConsoleUIPure.kt | 4 +- .../mamoe/mirai/console/utils/BotHelper.kt | 19 +-- 13 files changed, 264 insertions(+), 288 deletions(-) create mode 100644 mirai-console/src/main/kotlin/net/mamoe/mirai/console/command/CommandManager.kt diff --git a/gradle.properties b/gradle.properties index 513e76952..d86a7b009 100644 --- a/gradle.properties +++ b/gradle.properties @@ -2,7 +2,7 @@ kotlin.code.style=official # config miraiVersion=0.24.1 -mirai_console_version=0.3.1 +miraiConsoleVersion=0.3.1 kotlin.incremental.multiplatform=true kotlin.parallel.tasks.in.project=true # kotlin diff --git a/mirai-console-graphical/src/main/kotlin/net/mamoe/mirai/console/graphical/controller/MiraiGraphicalUIController.kt b/mirai-console-graphical/src/main/kotlin/net/mamoe/mirai/console/graphical/controller/MiraiGraphicalUIController.kt index d39948f49..03abb928c 100644 --- a/mirai-console-graphical/src/main/kotlin/net/mamoe/mirai/console/graphical/controller/MiraiGraphicalUIController.kt +++ b/mirai-console-graphical/src/main/kotlin/net/mamoe/mirai/console/graphical/controller/MiraiGraphicalUIController.kt @@ -3,7 +3,6 @@ package net.mamoe.mirai.console.graphical.controller import javafx.application.Platform import javafx.collections.ObservableList import javafx.stage.Modality -import kotlinx.io.core.IoBuffer import net.mamoe.mirai.Bot import net.mamoe.mirai.console.MiraiConsole import net.mamoe.mirai.console.graphical.model.BotModel @@ -11,6 +10,7 @@ import net.mamoe.mirai.console.graphical.model.ConsoleInfo import net.mamoe.mirai.console.graphical.model.PluginModel import net.mamoe.mirai.console.graphical.model.VerificationCodeModel import net.mamoe.mirai.console.graphical.view.VerificationCodeFragment +import net.mamoe.mirai.console.plugins.PluginManager import net.mamoe.mirai.console.utils.MiraiConsoleUI import net.mamoe.mirai.utils.LoginSolver import tornadofx.* @@ -75,7 +75,7 @@ class MiraiGraphicalUIController : Controller(), MiraiConsoleUI { override fun createLoginSolver(): LoginSolver = loginSolver private fun getPluginsFromConsole(): ObservableList = - MiraiConsole.pluginManager.getAllPluginDescriptions().map(::PluginModel).toObservable() + PluginManager.getAllPluginDescriptions().map(::PluginModel).toObservable() } diff --git a/mirai-console-terminal/src/main/kotlin/net/mamoe/mirai/console/MiraiConsoleTerminalUI.kt b/mirai-console-terminal/src/main/kotlin/net/mamoe/mirai/console/MiraiConsoleTerminalUI.kt index 142eedee6..891e5003a 100644 --- a/mirai-console-terminal/src/main/kotlin/net/mamoe/mirai/console/MiraiConsoleTerminalUI.kt +++ b/mirai-console-terminal/src/main/kotlin/net/mamoe/mirai/console/MiraiConsoleTerminalUI.kt @@ -1,3 +1,5 @@ +@file:Suppress("MemberVisibilityCanBePrivate") + package net.mamoe.mirai.console import com.googlecode.lanterna.SGR @@ -8,7 +10,6 @@ import com.googlecode.lanterna.input.KeyStroke import com.googlecode.lanterna.input.KeyType import com.googlecode.lanterna.terminal.DefaultTerminalFactory import com.googlecode.lanterna.terminal.Terminal -import com.googlecode.lanterna.terminal.TerminalResizeListener import com.googlecode.lanterna.terminal.swing.SwingTerminal import com.googlecode.lanterna.terminal.swing.SwingTerminalFrame import kotlinx.coroutines.* @@ -16,7 +17,6 @@ import kotlinx.coroutines.io.ByteWriteChannel import kotlinx.coroutines.io.close import kotlinx.coroutines.io.jvm.nio.copyTo import kotlinx.coroutines.io.reader -import kotlinx.io.core.IoBuffer import kotlinx.io.core.use import net.mamoe.mirai.Bot import net.mamoe.mirai.console.MiraiConsoleTerminalUI.LoggerDrawer.cleanPage @@ -51,49 +51,26 @@ import kotlin.system.exitProcess * */ -fun String.actualLength(): Int { - var x = 0 - this.forEach { - if (it.isChineseChar()) { - x += 2 - } else { - x += 1 - } - } - return x -} +val String.actualLength: Int get() = this.sumBy { if (it.isChineseChar) 2 else 1 } + fun String.getSubStringIndexByActualLength(widthMax: Int): Int { - var index = 0 - var currentLength = 0 - this.forEach { - if (it.isChineseChar()) { - currentLength += 2 - } else { - currentLength += 1 - } - if (currentLength > widthMax) { - return@forEach - } - ++index - } - if (index < 2) { - index = 2 - } - return index + return this.sumBy { if (it.isChineseChar) 2 else 1 }.coerceAtMost(widthMax).coerceAtLeast(2) } -fun Char.isChineseChar(): Boolean { - return this.toString().isChineseChar() -} +val Char.isChineseChar: Boolean + get() { + return this.toString().isChineseChar + } -fun String.isChineseChar(): Boolean { - return this.matches(Regex("[\u4e00-\u9fa5]")) -} +val String.isChineseChar: Boolean + get() { + return this.matches(Regex("[\u4e00-\u9fa5]")) + } object MiraiConsoleTerminalUI : MiraiConsoleUI { - val cacheLogSize = 50 + const val cacheLogSize = 50 var mainTitle = "Mirai Console v0.01 Core v0.15" override fun pushVersion(consoleVersion: String, consoleBuild: String, coreVersion: String) { @@ -122,7 +99,7 @@ object MiraiConsoleTerminalUI : MiraiConsoleUI { @Volatile var requesting = false - var requestResult: String? = null + private var requestResult: String? = null override suspend fun requestInput(): String { requesting = true while (requesting) { @@ -132,7 +109,7 @@ object MiraiConsoleTerminalUI : MiraiConsoleUI { } - suspend fun provideInput(input: String) { + private suspend fun provideInput(input: String) { if (requesting) { requestResult = input requesting = false @@ -164,17 +141,13 @@ object MiraiConsoleTerminalUI : MiraiConsoleUI { } } - var toLog = "" + lateinit var toLog: String tempFile.inputStream().use { val img = ImageIO.read(it) - if (img == null) { - toLog += "无法创建字符图片. 请查看文件\n" - } else { - toLog += img.createCharImg((terminal.terminalSize.columns / 1.5).toInt()) - } + toLog += img?.createCharImg((terminal.terminalSize.columns / 1.5).toInt()) ?: "无法创建字符图片. 请查看文件\n" } pushLog(0, "$toLog[Login Solver]请输验证码. ${tempFile.absolutePath}") - return requestInput()!! + return requestInput() .takeUnless { it.isEmpty() || it.length != 4 } .also { pushLog(0, "[Login Solver]正在提交[$it]中...") @@ -206,11 +179,11 @@ object MiraiConsoleTerminalUI : MiraiConsoleUI { } } - val log = ConcurrentHashMap>().also { + private val log = ConcurrentHashMap>().also { it[0L] = LimitLinkedQueue(cacheLogSize) } - val botAdminCount = ConcurrentHashMap() + private val botAdminCount = ConcurrentHashMap() private val screens = mutableListOf(0L) private var currentScreenId = 0 @@ -219,7 +192,7 @@ object MiraiConsoleTerminalUI : MiraiConsoleUI { lateinit var terminal: Terminal lateinit var textGraphics: TextGraphics - var hasStart = false + private var hasStart = false private lateinit var internalPrinter: PrintStream fun start() { if (hasStart) { @@ -277,11 +250,12 @@ object MiraiConsoleTerminalUI : MiraiConsoleUI { */ var lastJob: Job? = null - terminal.addResizeListener(TerminalResizeListener { terminal1: Terminal, newSize: TerminalSize -> + terminal.addResizeListener { _: Terminal, _: TerminalSize -> lastJob = GlobalScope.launch { try { delay(300) if (lastJob == coroutineContext[Job]) { + @Suppress("BlockingMethodInNonBlockingContext") terminal.clearScreen() //inited = false update() @@ -292,7 +266,7 @@ object MiraiConsoleTerminalUI : MiraiConsoleUI { pushLog(0, "[UI ERROR] ${e.message}") } } - }) + } if (terminal !is SwingTerminalFrame) { System.setOut(PrintStream(object : OutputStream() { @@ -322,7 +296,7 @@ object MiraiConsoleTerminalUI : MiraiConsoleUI { thread { while (true) { try { - var keyStroke: KeyStroke = terminal.readInput() + val keyStroke: KeyStroke = terminal.readInput() when (keyStroke.keyType) { KeyType.ArrowLeft -> { @@ -411,7 +385,7 @@ object MiraiConsoleTerminalUI : MiraiConsoleUI { textGraphics.foregroundColor = TextColor.ANSI.WHITE textGraphics.backgroundColor = TextColor.ANSI.GREEN - textGraphics.putString((width - mainTitle.actualLength()) / 2, 1, mainTitle, SGR.BOLD) + textGraphics.putString((width - mainTitle.actualLength) / 2, 1, mainTitle, SGR.BOLD) textGraphics.foregroundColor = TextColor.ANSI.DEFAULT textGraphics.backgroundColor = TextColor.ANSI.DEFAULT textGraphics.putString(2, 3, "-".repeat(width - 4)) @@ -426,15 +400,15 @@ object MiraiConsoleTerminalUI : MiraiConsoleUI { val leftName = getScreenName(getLeftScreenId()) // clearRows(2) - textGraphics.putString((width - title.actualLength()) / 2 - "$leftName << ".length, 2, "$leftName << ") + textGraphics.putString((width - title.actualLength) / 2 - "$leftName << ".length, 2, "$leftName << ") textGraphics.foregroundColor = TextColor.ANSI.WHITE textGraphics.backgroundColor = TextColor.ANSI.YELLOW - textGraphics.putString((width - title.actualLength()) / 2, 2, title, SGR.BOLD) + textGraphics.putString((width - title.actualLength) / 2, 2, title, SGR.BOLD) textGraphics.foregroundColor = TextColor.ANSI.DEFAULT textGraphics.backgroundColor = TextColor.ANSI.DEFAULT val rightName = getScreenName(getRightScreenId()) - textGraphics.putString((width + title.actualLength()) / 2 + 1, 2, ">> $rightName") + textGraphics.putString((width + title.actualLength) / 2 + 1, 2, ">> $rightName") } fun drawMainFrame( @@ -447,7 +421,7 @@ object MiraiConsoleTerminalUI : MiraiConsoleUI { clearRows(4) textGraphics.putString(2, 4, "|Online Bots: $onlineBotCount") textGraphics.putString( - width - 2 - "Powered By Mamoe Technologies|".actualLength(), + width - 2 - "Powered By Mamoe Technologies|".actualLength, 4, "Powered By Mamoe Technologies|" ) @@ -463,7 +437,7 @@ object MiraiConsoleTerminalUI : MiraiConsoleUI { textGraphics.backgroundColor = TextColor.ANSI.DEFAULT clearRows(4) textGraphics.putString(2, 4, "|Admins: $adminCount") - textGraphics.putString(width - 2 - "Add admins via commands|".actualLength(), 4, "Add admins via commands|") + textGraphics.putString(width - 2 - "Add admins via commands|".actualLength, 4, "Add admins via commands|") } @@ -472,7 +446,7 @@ object MiraiConsoleTerminalUI : MiraiConsoleUI { fun drawLog(string: String, flush: Boolean = true) { val maxHeight = terminal.terminalSize.rows - 4 - val heightNeed = (string.actualLength() / (terminal.terminalSize.columns - 6)) + 1 + val heightNeed = (string.actualLength / (terminal.terminalSize.columns - 6)) + 1 if (heightNeed - 1 > maxHeight) { pushLog(0, "[UI ERROR]: 您的屏幕太小, 有一条超长LOG无法显示") return//拒绝打印 @@ -481,7 +455,7 @@ object MiraiConsoleTerminalUI : MiraiConsoleUI { cleanPage()//翻页 } if (string.contains("\n")) { - string.split("\n").forEach { + string.split("\n").forEach { _ -> drawLog(string, false) } } else { @@ -491,7 +465,7 @@ object MiraiConsoleTerminalUI : MiraiConsoleUI { if (x == "") { break } - val toWrite = if (x.actualLength() > width) { + val toWrite = if (x.actualLength > width) { val index = x.getSubStringIndexByActualLength(width) x.substring(0, index).also { x = if (index < x.length) { @@ -539,7 +513,7 @@ object MiraiConsoleTerminalUI : MiraiConsoleUI { var vara = 0 val toPrint = mutableListOf() toDraw.forEach { - val heightNeed = (it.actualLength() / (terminal.terminalSize.columns - 6)) + 1 + val heightNeed = (it.actualLength / (terminal.terminalSize.columns - 6)) + 1 vara += heightNeed if (currentHeight + vara < terminal.terminalSize.rows - 4) { logsToDraw++ @@ -558,8 +532,8 @@ object MiraiConsoleTerminalUI : MiraiConsoleUI { } - var commandBuilder = StringBuilder() - fun redrawCommand() { + private var commandBuilder = StringBuilder() + private fun redrawCommand() { val height = terminal.terminalSize.rows val width = terminal.terminalSize.columns clearRows(height - 3) @@ -594,7 +568,7 @@ object MiraiConsoleTerminalUI : MiraiConsoleUI { } private fun deleteCommandChar() { - if (!commandBuilder.isEmpty()) { + if (commandBuilder.isNotEmpty()) { commandBuilder = StringBuilder(commandBuilder.toString().substring(0, commandBuilder.length - 1)) } val height = terminal.terminalSize.rows @@ -606,7 +580,7 @@ object MiraiConsoleTerminalUI : MiraiConsoleUI { } - var lastEmpty: Job? = null + private var lastEmpty: Job? = null private fun emptyCommand() { commandBuilder = StringBuilder() if (terminal is SwingTerminal) { @@ -617,7 +591,9 @@ object MiraiConsoleTerminalUI : MiraiConsoleUI { try { delay(100) if (lastEmpty == coroutineContext[Job]) { - terminal.clearScreen() + withContext(Dispatchers.IO) { + terminal.clearScreen() + } //inited = false update() redrawCommand() @@ -630,7 +606,7 @@ object MiraiConsoleTerminalUI : MiraiConsoleUI { } } - fun update() { + private fun update() { when (screens[currentScreenId]) { 0L -> { drawMainFrame(screens.size - 1) @@ -658,7 +634,7 @@ object MiraiConsoleTerminalUI : MiraiConsoleUI { class LimitLinkedQueue( - val limit: Int = 50 + private val limit: Int = 50 ) : ConcurrentLinkedDeque() { override fun push(e: T) { if (size >= limit) { diff --git a/mirai-console/build.gradle.kts b/mirai-console/build.gradle.kts index f36b99db9..e9621b718 100644 --- a/mirai-console/build.gradle.kts +++ b/mirai-console/build.gradle.kts @@ -26,7 +26,7 @@ fun kotlinx(id: String, version: String) = "org.jetbrains.kotlinx:kotlinx-$id:$v fun ktor(id: String, version: String) = "io.ktor:ktor-$id:$version" -tasks.withType() { +tasks.withType { manifest { attributes["Main-Class"] = "net.mamoe.mirai.console.pure.MiraiConsolePureLoader" } @@ -35,6 +35,16 @@ tasks.withType() { val miraiVersion: String by rootProject.ext +kotlin { + sourceSets { + all { + languageSettings.enableLanguageFeature("InlineClasses") + + languageSettings.useExperimentalAnnotation("kotlin.Experimental") + languageSettings.useExperimentalAnnotation("kotlin.OptIn") + } + } +} dependencies { compileOnly("net.mamoe:mirai-core-jvm:$miraiVersion") // compileOnly("net.mamoe:mirai-core-qqandroid-jvm:$miraiVersion") @@ -65,8 +75,8 @@ dependencies { api(ktor("network", ktorVersion)) } -val mirai_console_version: String by project.ext -version = mirai_console_version +val miraiConsoleVersion: String by project.ext +version = miraiConsoleVersion description = "Console with plugin support for mirai" bintray { @@ -109,7 +119,7 @@ publishing { groupId = rootProject.group.toString() artifactId = "mirai-console" - version = mirai_console_version + version = miraiConsoleVersion pom.withXml { val root = asNode() diff --git a/mirai-console/src/main/kotlin/net/mamoe/mirai/console/MiraiConsole.kt b/mirai-console/src/main/kotlin/net/mamoe/mirai/console/MiraiConsole.kt index d18a33da2..044e74efd 100644 --- a/mirai-console/src/main/kotlin/net/mamoe/mirai/console/MiraiConsole.kt +++ b/mirai-console/src/main/kotlin/net/mamoe/mirai/console/MiraiConsole.kt @@ -12,7 +12,6 @@ package net.mamoe.mirai.console import kotlinx.coroutines.* import kotlinx.coroutines.channels.Channel import net.mamoe.mirai.Bot -import net.mamoe.mirai.BotFactory import net.mamoe.mirai.console.MiraiConsole.CommandProcessor.processNextCommandLine import net.mamoe.mirai.console.command.CommandManager import net.mamoe.mirai.console.command.CommandSender @@ -38,20 +37,10 @@ object MiraiConsole { * */ val bots get() = Bot.instances - fun getBotByUIN(uin: Long): Bot? { - bots.forEach { - if (it.get()?.uin == uin) { - return it.get() - } - } - return null + fun getBotOrNull(uin: Long): Bot? { + return bots.asSequence().mapNotNull { it.get() }.firstOrNull { it.uin == uin } } - /** - * PluginManager - */ - val pluginManager: PluginManager get() = PluginManager - /** * 与前端交互所使用的Logger */ @@ -89,9 +78,8 @@ object MiraiConsole { logger("Mirai为开源项目,请自觉遵守开源项目协议") logger("Powered by Mamoe Technologies and contributors") - MiraiCoreLoader() + MiraiCoreLoader.loadCore() - println(BotFactory::class) /* 加载ECDH */ try { ECDH() @@ -102,7 +90,7 @@ object MiraiConsole { /* 依次启用功能 */ DefaultCommands() - pluginManager.loadPlugins() + PluginManager.loadPlugins() CommandProcessor.start() /* 通知启动完成 */ @@ -150,6 +138,7 @@ object MiraiConsole { fun runConsoleCommandBlocking(command: String) = runBlocking { runConsoleCommand(command) } + @Suppress("unused") fun runCommandBlocking(sender: CommandSender, command: String) = runBlocking { runCommand(sender, command) } private suspend fun processNextCommandLine() { diff --git a/mirai-console/src/main/kotlin/net/mamoe/mirai/console/command/Command.kt b/mirai-console/src/main/kotlin/net/mamoe/mirai/console/command/Command.kt index da08ff2da..b178e1aa8 100644 --- a/mirai-console/src/main/kotlin/net/mamoe/mirai/console/command/Command.kt +++ b/mirai-console/src/main/kotlin/net/mamoe/mirai/console/command/Command.kt @@ -7,82 +7,18 @@ * https://github.com/mamoe/mirai/blob/master/LICENSE */ +@file:Suppress("NOTHING_TO_INLINE") + package net.mamoe.mirai.console.command import kotlinx.coroutines.Dispatchers import kotlinx.coroutines.runBlocking import kotlinx.coroutines.withContext import net.mamoe.mirai.console.MiraiConsole -import net.mamoe.mirai.console.plugins.PluginManager +import net.mamoe.mirai.console.plugins.PluginBase import net.mamoe.mirai.contact.Contact import net.mamoe.mirai.contact.sendMessage -import net.mamoe.mirai.message.GroupMessage import net.mamoe.mirai.message.data.MessageChain -import net.mamoe.mirai.utils.MiraiExperimentalAPI - -object CommandManager { - private val registeredCommand: MutableMap = mutableMapOf() - - fun getCommands(): Collection { - return registeredCommand.values - } - - - fun register(command: Command) { - val allNames = mutableListOf(command.name).also { it.addAll(command.alias) } - allNames.forEach { - if (registeredCommand.containsKey(it)) { - error("Command Name(or Alias) $it is already registered, consider if same functional plugin was installed") - } - } - allNames.forEach { - registeredCommand[it] = command - } - } - - fun unregister(command: Command) { - val allNames = mutableListOf(command.name).also { it.addAll(command.alias) } - allNames.forEach { - registeredCommand.remove(it) - } - } - - fun unregister(commandName: String) { - registeredCommand.remove(commandName) - } - - /* - * Index: MiraiConsole - * */ - internal suspend fun runCommand(sender: CommandSender, fullCommand: String): Boolean { - val blocks = fullCommand.split(" ") - val commandHead = blocks[0].replace("/", "") - if (!registeredCommand.containsKey(commandHead)) { - return false - } - val args = blocks.subList(1, blocks.size) - registeredCommand[commandHead]?.run { - try { - if (onCommand( - sender, - blocks.subList(1, blocks.size) - ) - ) { - PluginManager.onCommand(this, sender, args) - } else { - sender.sendMessage(this.usage) - } - } catch (e: Exception) { - sender.sendMessage("在运行指令时出现了未知错误") - e.printStackTrace() - } finally { - (sender as CommandSenderImpl).flushMessage() - } - } - return true - } - -} interface CommandSender { /** @@ -92,7 +28,7 @@ interface CommandSender { suspend fun sendMessage(message: String) /** - * 写入要发送的内容 所有内容最后会被以一条发出, 不管成功与否 + * 写入要发送的内容 所有内容最后会被以一条发出 */ fun appendMessage(message: String) @@ -139,21 +75,6 @@ open class ContactCommandSender(val contact: Contact) : CommandSenderImpl() { } } -/** - * 弃用中 - * */ -class GroupCommandSender(val toQuote: GroupMessage, contact: Contact) : ContactCommandSender(contact) { - @MiraiExperimentalAPI - override suspend fun sendMessage(message: String) { - toQuote.quoteReply(message) - } - - @MiraiExperimentalAPI - override suspend fun sendMessage(messageChain: MessageChain) { - toQuote.quoteReply(messageChain) - } -} - interface Command { val name: String val alias: List @@ -161,9 +82,18 @@ interface Command { val usage: String suspend fun onCommand(sender: CommandSender, args: List): Boolean - fun register() } +inline fun Command.register() = CommandManager.register(this) + + +fun registerCommand(builder: CommandBuilder.() -> Unit): Command { + return CommandBuilder().apply(builder).register() +} + + +// for java +@Suppress("unused") abstract class BlockingCommand( override val name: String, override val alias: List = listOf(), @@ -172,7 +102,7 @@ abstract class BlockingCommand( ) : Command { /** * 最高优先级监听器 - * 如果 return `false` 这次指令不会被 [PluginBase] 的全局 onCommand 监听器监听 + * 如果 return `false`, 这次指令不会被 [PluginBase] 的全局 onCommand 监听器监听 * */ final override suspend fun onCommand(sender: CommandSender, args: List): Boolean { return withContext(Dispatchers.IO) { @@ -181,10 +111,6 @@ abstract class BlockingCommand( } abstract fun onCommandBlocking(sender: CommandSender, args: List): Boolean - - override fun register() { - CommandManager.register(this) - } } class AnonymousCommand internal constructor( @@ -197,10 +123,6 @@ class AnonymousCommand internal constructor( override suspend fun onCommand(sender: CommandSender, args: List): Boolean { return onCommand.invoke(sender, args) } - - override fun register() { - CommandManager.register(this) - } } class CommandBuilder internal constructor() { @@ -208,30 +130,25 @@ class CommandBuilder internal constructor() { var alias: List? = null var description: String = "" var usage: String = "use /help for help" - var onCommand: (suspend CommandSender.(args: List) -> Boolean)? = null + internal var onCommand: (suspend CommandSender.(args: List) -> Boolean)? = null fun onCommand(commandProcess: suspend CommandSender.(args: List) -> Boolean) { onCommand = commandProcess } +} - fun register(): Command { - if (name == null || onCommand == null) { - error("CommandBuilder not complete") - } - if (alias == null) { - alias = listOf() - } - return AnonymousCommand( - name!!, - alias!!, - description, - usage, - onCommand!! - ).also { it.register() } +private fun CommandBuilder.register(): AnonymousCommand { + if (name == null || onCommand == null) { + error("CommandBuilder not complete") } -} - -fun registerCommand(builder: CommandBuilder.() -> Unit): Command { - return CommandBuilder().apply(builder).register() -} - + if (alias == null) { + alias = listOf() + } + return AnonymousCommand( + name!!, + alias!!, + description, + usage, + onCommand!! + ).also { it.register() } +} \ No newline at end of file diff --git a/mirai-console/src/main/kotlin/net/mamoe/mirai/console/command/CommandManager.kt b/mirai-console/src/main/kotlin/net/mamoe/mirai/console/command/CommandManager.kt new file mode 100644 index 000000000..437489ee2 --- /dev/null +++ b/mirai-console/src/main/kotlin/net/mamoe/mirai/console/command/CommandManager.kt @@ -0,0 +1,70 @@ +/* + * Copyright 2020 Mamoe Technologies and contributors. + * + * 此源代码的使用受 GNU AFFERO GENERAL PUBLIC LICENSE version 3 许可证的约束, 可以在以下链接找到该许可证. + * Use of this source code is governed by the GNU AGPLv3 license that can be found through the following link. + * + * https://github.com/mamoe/mirai/blob/master/LICENSE + */ + +@file:Suppress("unused") + +package net.mamoe.mirai.console.command + +import net.mamoe.mirai.console.plugins.PluginManager + +object CommandManager { + private val registeredCommand: MutableMap = mutableMapOf() + + val commands: Collection get() = registeredCommand.values + + fun register(command: Command) { + val allNames = mutableListOf(command.name).also { it.addAll(command.alias) } + allNames.forEach { + if (registeredCommand.containsKey(it)) { + error("Command Name(or Alias) $it is already registered, consider if same functional plugin was installed") + } + } + allNames.forEach { + registeredCommand[it] = command + } + } + + fun unregister(command: Command) { + (command.alias.asSequence() + command.name).forEach { + registeredCommand.remove(it) + } // label compilation failed + } + + fun unregister(commandName: String): Boolean { + return registeredCommand.remove(commandName) != null + } + + /* + * Index: MiraiConsole + */ + internal suspend fun runCommand(sender: CommandSender, fullCommand: String): Boolean { + val blocks = fullCommand.split(" ") + val commandHead = blocks[0].replace("/", "") + if (!registeredCommand.containsKey(commandHead)) { + return false + } + val args = blocks.drop(1) + registeredCommand[commandHead]?.run { + try { + if (onCommand(sender, blocks.drop(1))) { + PluginManager.onCommand(this, sender, args) + } else { + sender.sendMessage(this.usage) + } + } catch (e: Exception) { + sender.sendMessage("在运行指令时出现了未知错误") + e.printStackTrace() + } finally { + (sender as CommandSenderImpl).flushMessage() + } + } + return true + } + +} \ No newline at end of file diff --git a/mirai-console/src/main/kotlin/net/mamoe/mirai/console/command/DefaultCommands.kt b/mirai-console/src/main/kotlin/net/mamoe/mirai/console/command/DefaultCommands.kt index 3fcefb14e..37d5bdc55 100644 --- a/mirai-console/src/main/kotlin/net/mamoe/mirai/console/command/DefaultCommands.kt +++ b/mirai-console/src/main/kotlin/net/mamoe/mirai/console/command/DefaultCommands.kt @@ -14,7 +14,7 @@ import net.mamoe.mirai.console.MiraiConsole import net.mamoe.mirai.console.plugins.PluginManager import net.mamoe.mirai.console.utils.addManager import net.mamoe.mirai.console.utils.checkManager -import net.mamoe.mirai.console.utils.getManagers +import net.mamoe.mirai.console.utils.managers import net.mamoe.mirai.console.utils.removeManager import net.mamoe.mirai.contact.sendMessage import net.mamoe.mirai.event.subscribeMessages @@ -49,7 +49,7 @@ object DefaultCommands { MiraiConsole.logger("[Bot Manager]", 0, it[1] + " 不是一个Bot的ID") return@onCommand false } - val bot = MiraiConsole.getBotByUIN(botId) + val bot = MiraiConsole.getBotOrNull(botId) if (bot == null) { MiraiConsole.logger("[Bot Manager]", 0, "$botId 没有在Console中登陆") return@onCommand false @@ -88,7 +88,7 @@ object DefaultCommands { MiraiConsole.logger("[Bot Manager]", 0, it[2] + "移除成功") } "list" -> { - bot.getManagers().forEach { + bot.managers.forEach { MiraiConsole.logger("[Bot Manager]", 0, " -> $it") } } @@ -106,7 +106,7 @@ object DefaultCommands { return@onCommand false } if (it.size < 2) { - MiraiConsole.logger("\"/login qqnumber qqpassword \" to login a bot") + MiraiConsole.logger("\"/login qq password \" to login a bot") MiraiConsole.logger("\"/login qq号 qq密码 \" 来登录一个BOT") return@onCommand false } @@ -138,11 +138,11 @@ object DefaultCommands { } bot.login() bot.subscribeMessages { - this.startsWith("/") { + startsWith("/") { message -> if (bot.checkManager(this.sender.id)) { val sender = ContactCommandSender(this.subject) MiraiConsole.CommandProcessor.runCommand( - sender, it + sender, message ) } } @@ -159,13 +159,13 @@ object DefaultCommands { registerCommand { name = "status" description = "获取状态" - onCommand { - when (it.size) { + onCommand { args -> + when (args.size) { 0 -> { sendMessage("当前有" + MiraiConsole.bots.size + "个BOT在线") } 1 -> { - val bot = it[0] + val bot = args[0] var find = false MiraiConsole.bots.forEach { if (it.get()?.uin.toString().contains(bot)) { @@ -196,13 +196,13 @@ object DefaultCommands { return@onCommand false } val bot: Bot? = if (it.size == 2) { - if (MiraiConsole.bots.size == 0) { + if (MiraiConsole.bots.isEmpty()) { MiraiConsole.logger("还没有BOT登录") return@onCommand false } MiraiConsole.bots[0].get() } else { - MiraiConsole.getBotByUIN(it[0].toLong()) + MiraiConsole.getBotOrNull(it[0].toLong()) } if (bot == null) { MiraiConsole.logger("没有找到BOT") @@ -228,11 +228,11 @@ object DefaultCommands { alias = listOf("plugin") description = "获取插件列表" onCommand { - PluginManager.getAllPluginDescriptions().let { - it.forEach { + PluginManager.getAllPluginDescriptions().let { descriptions -> + descriptions.forEach { appendMessage("\t" + it.name + " v" + it.version + " by" + it.author + " " + it.info) } - appendMessage("加载了" + it.size + "个插件") + appendMessage("加载了" + descriptions.size + "个插件") true } } @@ -243,10 +243,10 @@ object DefaultCommands { alias = listOf("commands", "help", "helps") description = "获取指令列表" onCommand { - CommandManager.getCommands().let { + CommandManager.commands.let { commands -> var size = 0 appendMessage("")//\n - it.toSet().forEach { + commands.forEach { ++size appendMessage("-> " + it.name + " :" + it.description) } diff --git a/mirai-console/src/main/kotlin/net/mamoe/mirai/console/core/MiraiCoreLoader.kt b/mirai-console/src/main/kotlin/net/mamoe/mirai/console/core/MiraiCoreLoader.kt index 8a410c0ad..aaefb328b 100644 --- a/mirai-console/src/main/kotlin/net/mamoe/mirai/console/core/MiraiCoreLoader.kt +++ b/mirai-console/src/main/kotlin/net/mamoe/mirai/console/core/MiraiCoreLoader.kt @@ -7,15 +7,15 @@ * https://github.com/mamoe/mirai/blob/master/LICENSE */ +@file:Suppress("EXPERIMENTAL_API_USAGE") + package net.mamoe.mirai.console.core import io.ktor.client.HttpClient import io.ktor.client.engine.cio.CIO import io.ktor.client.request.get -import io.ktor.client.request.url import io.ktor.client.statement.HttpResponse import io.ktor.http.URLProtocol -import io.ktor.util.KtorExperimentalAPI import io.ktor.utils.io.ByteReadChannel import io.ktor.utils.io.jvm.javaio.copyTo import kotlinx.coroutines.Dispatchers @@ -27,12 +27,11 @@ import java.net.URLClassLoader import kotlin.math.pow import kotlin.system.exitProcess -@UseExperimental(KtorExperimentalAPI::class) val Http: HttpClient get() = HttpClient(CIO) object MiraiCoreLoader { - val coresPath by lazy { + private val coresPath by lazy { File(System.getProperty("user.dir") + "/core/").also { if (!it.exists()) { it.mkdirs() @@ -59,7 +58,7 @@ object MiraiCoreLoader { } - operator fun invoke(): String { + fun loadCore(): String { MiraiConsole.logger("Fetching Newest Core Version .. ") val newest = runBlocking { getNewestVersion() @@ -82,7 +81,7 @@ object MiraiCoreLoader { /** - * 使用Protocol Lib判断最新版本 + * 判断最新版本 * */ private suspend fun getNewestVersion(): String { try { @@ -110,9 +109,9 @@ object MiraiCoreLoader { } /** - * 使用Protocol Lib判断当前版本 - * 如果没有 会返回0.0.0 - * */ + * 判断当前版本 + * 默认返回 "0.0.0" + */ private fun getCurrentVersion(): String { val file = getProtocolLib() if (file == null || getCore() == null) return "0.0.0" @@ -133,14 +132,18 @@ object MiraiCoreLoader { } - val lib_jcenter = - "https://jcenter.bintray.com/net/mamoe/mirai-core-qqandroid-jvm/{version}/:mirai-core-qqandroid-jvm-{version}.jar" - val lib_aliyun = - "https://maven.aliyun.com/nexus/content/repositories/jcenter/net/mamoe/mirai-core-qqandroid-jvm/{version}/mirai-core-qqandroid-jvm-{version}.jar" + @Suppress("SpellCheckingInspection") + private object Links { + internal const val libJcenter = + "https://jcenter.bintray.com/net/mamoe/mirai-core-qqandroid-jvm/{version}/:mirai-core-qqandroid-jvm-{version}.jar" + internal const val libAliyun = + "https://maven.aliyun.com/nexus/content/repositories/jcenter/net/mamoe/mirai-core-qqandroid-jvm/{version}/mirai-core-qqandroid-jvm-{version}.jar" - val core_jcenter = "https://jcenter.bintray.com/net/mamoe/mirai-core-jvm/{version}/:mirai-core-jvm-{version}.jar" - val core_aliyun = - "https://maven.aliyun.com/nexus/content/repositories/jcenter/net/mamoe/mirai-core-jvm/{version}/mirai-core-jvm-{version}.jar" + internal const val coreJcenter = + "https://jcenter.bintray.com/net/mamoe/mirai-core-jvm/{version}/:mirai-core-jvm-{version}.jar" + internal const val coreAliyun = + "https://maven.aliyun.com/nexus/content/repositories/jcenter/net/mamoe/mirai-core-jvm/{version}/mirai-core-jvm-{version}.jar" + } private suspend fun downloadCoreAndLib(version: String) { var fileStream = File(coresPath.absolutePath + "/" + "mirai-core-qqandroid-jvm-$version.jar").also { @@ -150,18 +153,16 @@ object MiraiCoreLoader { }.outputStream() suspend fun downloadRequest(url: String, version: String): ByteReadChannel { - return Http.get() { - this.url(url.replace("{version}", version)) - }.content + return Http.get(url.replace("{version}", version)).content } var stream = kotlin.runCatching { MiraiConsole.logger("Downloading newest Protocol lib from Aliyun") - downloadRequest(lib_aliyun, version) + downloadRequest(Links.libAliyun, version) }.getOrElse { kotlin.runCatching { MiraiConsole.logger("Downloading newest Protocol lib from JCenter") - downloadRequest(lib_jcenter, version) + downloadRequest(Links.libJcenter, version) }.getOrElse { e -> MiraiConsole.logger("Failed to download Protocol lib, please seeking for help") e.printStackTrace() @@ -184,11 +185,11 @@ object MiraiCoreLoader { stream = try { MiraiConsole.logger("Downloading newest Mirai Core from Aliyun") - downloadRequest(core_aliyun, version) + downloadRequest(Links.coreAliyun, version) } catch (ignored: Exception) { try { MiraiConsole.logger("Downloading newest Mirai Core from JCenter") - downloadRequest(core_jcenter, version) + downloadRequest(Links.coreJcenter, version) } catch (e: Exception) { MiraiConsole.logger("Failed to download Mirai Core, please seeking for help") e.printStackTrace() @@ -240,8 +241,5 @@ object MiraiCoreLoader { } -internal class MiraiCoreClassLoader(file: File, parent: ClassLoader) : - URLClassLoader(arrayOf(file.toURI().toURL()), parent) - diff --git a/mirai-console/src/main/kotlin/net/mamoe/mirai/console/plugins/ConfigSection.kt b/mirai-console/src/main/kotlin/net/mamoe/mirai/console/plugins/ConfigSection.kt index dffc93092..995c8fd1b 100644 --- a/mirai-console/src/main/kotlin/net/mamoe/mirai/console/plugins/ConfigSection.kt +++ b/mirai-console/src/main/kotlin/net/mamoe/mirai/console/plugins/ConfigSection.kt @@ -7,6 +7,8 @@ * https://github.com/mamoe/mirai/blob/master/LICENSE */ +@file:Suppress("MemberVisibilityCanBePrivate") + package net.mamoe.mirai.console.plugins import com.alibaba.fastjson.JSON @@ -17,12 +19,14 @@ import com.moandjiezana.toml.Toml import com.moandjiezana.toml.TomlWriter import kotlinx.serialization.Serializable import kotlinx.serialization.UnstableDefault +import net.mamoe.mirai.utils.MiraiInternalAPI import net.mamoe.mirai.utils.io.encodeToString import org.yaml.snakeyaml.Yaml import java.io.File import java.io.InputStream import java.util.* import java.util.concurrent.ConcurrentHashMap +import kotlin.NoSuchElementException import kotlin.properties.ReadWriteProperty import kotlin.reflect.KClass import kotlin.reflect.KProperty @@ -134,16 +138,16 @@ inline operator fun Config.setValue(thisRef: Any?, property: K } /* 带有默认值的代理 */ +@Suppress("unused") inline fun Config.withDefault( - noinline defaultValue: () -> T + crossinline defaultValue: () -> T ): ReadWriteProperty { - val default by lazy { defaultValue.invoke() } return object : ReadWriteProperty { override fun getValue(thisRef: Any, property: KProperty<*>): T { if (this@withDefault.exist(property.name)) {//unsafe return this@withDefault.smartCast(property) } - return default + return defaultValue() } override fun setValue(thisRef: Any, property: KProperty<*>, value: T) { @@ -153,6 +157,7 @@ inline fun Config.withDefault( } /* 带有默认值且如果为空会写入的代理 */ +@Suppress("unused") inline fun Config.withDefaultWrite( noinline defaultValue: () -> T ): WithDefaultWriteLoader { @@ -191,7 +196,7 @@ class WithDefaultWriteLoader( return object : ReadWriteProperty { override fun getValue(thisRef: Any, property: KProperty<*>): T { if (config.exist(property.name)) {//unsafe - return config._smartCast(property.name, _class) + return config.smartCastInternal(property.name, _class) } return defaultValue } @@ -203,12 +208,14 @@ class WithDefaultWriteLoader( } } -inline fun Config.smartCast(property: KProperty<*>): T { - return _smartCast(property.name, T::class) +@PublishedApi +internal inline fun Config.smartCast(property: KProperty<*>): T { + return smartCastInternal(property.name, T::class) } +@PublishedApi @Suppress("IMPLICIT_CAST_TO_ANY", "UNCHECKED_CAST") -fun Config._smartCast(propertyName: String, _class: KClass): T { +internal fun Config.smartCastInternal(propertyName: String, _class: KClass): T { return when (_class) { String::class -> this.getString(propertyName) Int::class -> this.getInt(propertyName) @@ -251,70 +258,72 @@ fun Config._smartCast(propertyName: String, _class: KClass): T { interface ConfigSection : Config, MutableMap { override fun getConfigSection(key: String): ConfigSection { - val content = get(key) ?: error("ConfigSection does not contain $key ") + val content = get(key) ?: throw NoSuchElementException(key) if (content is ConfigSection) { return content } + @Suppress("UNCHECKED_CAST") return ConfigSectionDelegation( Collections.synchronizedMap( - (get(key) ?: error("ConfigSection does not contain $key ")) as LinkedHashMap + (get(key) ?: throw NoSuchElementException(key)) as LinkedHashMap ) ) } override fun getString(key: String): String { - return (get(key) ?: error("ConfigSection does not contain $key ")).toString() + return (get(key) ?: throw NoSuchElementException(key)).toString() } override fun getInt(key: String): Int { - return (get(key) ?: error("ConfigSection does not contain $key ")).toString().toInt() + return (get(key) ?: throw NoSuchElementException(key)).toString().toInt() } override fun getFloat(key: String): Float { - return (get(key) ?: error("ConfigSection does not contain $key ")).toString().toFloat() + return (get(key) ?: throw NoSuchElementException(key)).toString().toFloat() } override fun getBoolean(key: String): Boolean { - return (get(key) ?: error("ConfigSection does not contain $key ")).toString().toBoolean() + return (get(key) ?: throw NoSuchElementException(key)).toString().toBoolean() } override fun getDouble(key: String): Double { - return (get(key) ?: error("ConfigSection does not contain $key ")).toString().toDouble() + return (get(key) ?: throw NoSuchElementException(key)).toString().toDouble() } override fun getLong(key: String): Long { - return (get(key) ?: error("ConfigSection does not contain $key ")).toString().toLong() + return (get(key) ?: throw NoSuchElementException(key)).toString().toLong() } override fun getList(key: String): List<*> { - return ((get(key) ?: error("ConfigSection does not contain $key ")) as List<*>) + return ((get(key) ?: throw NoSuchElementException(key)) as List<*>) } override fun getStringList(key: String): List { - return ((get(key) ?: error("ConfigSection does not contain $key ")) as List<*>).map { it.toString() } + return ((get(key) ?: throw NoSuchElementException(key)) as List<*>).map { it.toString() } } override fun getIntList(key: String): List { - return ((get(key) ?: error("ConfigSection does not contain $key ")) as List<*>).map { it.toString().toInt() } + return ((get(key) ?: throw NoSuchElementException(key)) as List<*>).map { it.toString().toInt() } } override fun getFloatList(key: String): List { - return ((get(key) ?: error("ConfigSection does not contain $key ")) as List<*>).map { it.toString().toFloat() } + return ((get(key) ?: throw NoSuchElementException(key)) as List<*>).map { it.toString().toFloat() } } override fun getDoubleList(key: String): List { - return ((get(key) ?: error("ConfigSection does not contain $key ")) as List<*>).map { it.toString().toDouble() } + return ((get(key) ?: throw NoSuchElementException(key)) as List<*>).map { it.toString().toDouble() } } override fun getLongList(key: String): List { - return ((get(key) ?: error("ConfigSection does not contain $key ")) as List<*>).map { it.toString().toLong() } + return ((get(key) ?: throw NoSuchElementException(key)) as List<*>).map { it.toString().toLong() } } override fun getConfigSectionList(key: String): List { - return ((get(key) ?: error("ConfigSection does not contain $key ")) as List<*>).map { + return ((get(key) ?: throw NoSuchElementException(key)) as List<*>).map { if (it is ConfigSection) { it } else { + @Suppress("UNCHECKED_CAST") ConfigSectionDelegation( Collections.synchronizedMap( it as MutableMap @@ -334,7 +343,7 @@ interface ConfigSection : Config, MutableMap { } @Serializable -open class ConfigSectionImpl() : ConcurrentHashMap(), +open class ConfigSectionImpl : ConcurrentHashMap(), ConfigSection { override fun set(key: String, value: Any) { super.put(key, value) @@ -370,7 +379,7 @@ open class ConfigSectionDelegation( private val delegate: MutableMap ) : ConfigSection, MutableMap by delegate { override fun set(key: String, value: Any) { - delegate.put(key, value) + delegate[key] = value } override fun contains(key: String): Boolean { @@ -394,6 +403,7 @@ interface FileConfig : Config { } +@MiraiInternalAPI abstract class FileConfigImpl internal constructor( private val rawContent: String ) : FileConfig, @@ -402,6 +412,7 @@ abstract class FileConfigImpl internal constructor( internal var file: File? = null + @Suppress("unused") constructor(file: File) : this(file.readText()) { this.file = file } @@ -425,7 +436,7 @@ abstract class FileConfigImpl internal constructor( override fun remove(key: String): Any? = content.remove(key) override fun save() { - if (isReadOnly()) { + if (isReadOnly) { error("Config is readonly") } if (!((file?.exists())!!)) { @@ -434,7 +445,7 @@ abstract class FileConfigImpl internal constructor( file?.writeText(serialize(content)) } - fun isReadOnly() = file == null + val isReadOnly: Boolean get() = file == null override fun contains(key: String): Boolean { return content.contains(key) @@ -454,6 +465,7 @@ abstract class FileConfigImpl internal constructor( } +@UseExperimental(MiraiInternalAPI::class) class JsonConfig internal constructor( content: String ) : FileConfigImpl(content) { @@ -466,7 +478,7 @@ class JsonConfig internal constructor( if (content.isEmpty() || content.isBlank() || content == "{}") { return ConfigSectionImpl() } - return JSON.parseObject( + return JSON.parseObject( content, object : TypeReference() {}, Feature.OrderedField @@ -479,6 +491,7 @@ class JsonConfig internal constructor( } } +@UseExperimental(MiraiInternalAPI::class) class YamlConfig internal constructor(content: String) : FileConfigImpl(content) { constructor(file: File) : this(file.readText()) { this.file = file @@ -490,7 +503,7 @@ class YamlConfig internal constructor(content: String) : FileConfigImpl(content) } return ConfigSectionDelegation( Collections.synchronizedMap( - Yaml().load>(content) as LinkedHashMap + Yaml().load(content) as LinkedHashMap ) ) } @@ -501,6 +514,7 @@ class YamlConfig internal constructor(content: String) : FileConfigImpl(content) } +@UseExperimental(MiraiInternalAPI::class) class TomlConfig internal constructor(content: String) : FileConfigImpl(content) { constructor(file: File) : this(file.readText()) { this.file = file diff --git a/mirai-console/src/main/kotlin/net/mamoe/mirai/console/plugins/PluginManager.kt b/mirai-console/src/main/kotlin/net/mamoe/mirai/console/plugins/PluginManager.kt index 171364693..d8208139f 100644 --- a/mirai-console/src/main/kotlin/net/mamoe/mirai/console/plugins/PluginManager.kt +++ b/mirai-console/src/main/kotlin/net/mamoe/mirai/console/plugins/PluginManager.kt @@ -7,6 +7,8 @@ * https://github.com/mamoe/mirai/blob/master/LICENSE */ +@file:Suppress("unused", "unused") + package net.mamoe.mirai.console.plugins import kotlinx.coroutines.CancellationException @@ -22,7 +24,6 @@ import java.util.jar.JarFile object PluginManager { - @Volatile internal var lastPluginName: String = "" diff --git a/mirai-console/src/main/kotlin/net/mamoe/mirai/console/pure/MiraiConsoleUIPure.kt b/mirai-console/src/main/kotlin/net/mamoe/mirai/console/pure/MiraiConsoleUIPure.kt index ddedb1866..48ef089c5 100644 --- a/mirai-console/src/main/kotlin/net/mamoe/mirai/console/pure/MiraiConsoleUIPure.kt +++ b/mirai-console/src/main/kotlin/net/mamoe/mirai/console/pure/MiraiConsoleUIPure.kt @@ -18,8 +18,8 @@ import net.mamoe.mirai.utils.LoginSolver import kotlin.concurrent.thread class MiraiConsoleUIPure : MiraiConsoleUI { - var requesting = false - var requestStr = "" + private var requesting = false + private var requestStr = "" init { thread { diff --git a/mirai-console/src/main/kotlin/net/mamoe/mirai/console/utils/BotHelper.kt b/mirai-console/src/main/kotlin/net/mamoe/mirai/console/utils/BotHelper.kt index 2443d024e..2b383e011 100644 --- a/mirai-console/src/main/kotlin/net/mamoe/mirai/console/utils/BotHelper.kt +++ b/mirai-console/src/main/kotlin/net/mamoe/mirai/console/utils/BotHelper.kt @@ -18,32 +18,33 @@ import net.mamoe.mirai.console.plugins.withDefaultWriteSave import net.mamoe.mirai.console.utils.BotManagers.BOT_MANAGERS import java.io.File -object BotManagers { +internal object BotManagers { val config = File("${MiraiConsole.path}/bot.yml").loadAsConfig() val BOT_MANAGERS: ConfigSection by config.withDefaultWriteSave { ConfigSectionImpl() } } -fun Bot.addManager(long: Long) { +internal fun Bot.addManager(long: Long) { BOT_MANAGERS.putIfAbsent(this.uin.toString(), mutableListOf()) BOT_MANAGERS[this.uin.toString()] = (BOT_MANAGERS.getLongList(this.uin.toString()) as MutableList).apply { add(long) } BotManagers.config.save() } -fun Bot.removeManager(long: Long) { +internal fun Bot.removeManager(long: Long) { BOT_MANAGERS.putIfAbsent(this.uin.toString(), mutableListOf()) BOT_MANAGERS[this.uin.toString()] = (BOT_MANAGERS.getLongList(this.uin.toString()) as MutableList).apply { add(long) } BotManagers.config.save() } -fun Bot.getManagers(): List { - BOT_MANAGERS.putIfAbsent(this.uin.toString(), mutableListOf()) - return BOT_MANAGERS.getLongList(this.uin.toString()) -} +internal val Bot.managers: List + get() { + BOT_MANAGERS.putIfAbsent(this.uin.toString(), mutableListOf()) + return BOT_MANAGERS.getLongList(this.uin.toString()) + } -fun Bot.checkManager(long: Long): Boolean { - return this.getManagers().contains(long) +internal fun Bot.checkManager(long: Long): Boolean { + return this.managers.contains(long) }