diff --git a/src/main/kotlin/top/r3944realms/ltdmanager/module/GroupRequestHandlerModule.kt b/src/main/kotlin/top/r3944realms/ltdmanager/module/GroupRequestHandlerModule.kt index b65ae7f..729b770 100644 --- a/src/main/kotlin/top/r3944realms/ltdmanager/module/GroupRequestHandlerModule.kt +++ b/src/main/kotlin/top/r3944realms/ltdmanager/module/GroupRequestHandlerModule.kt @@ -9,6 +9,7 @@ import top.r3944realms.ltdmanager.napcat.request.group.GetGroupIgnoredNotifiesRe import top.r3944realms.ltdmanager.napcat.request.group.GetGroupSystemMsgRequest import top.r3944realms.ltdmanager.napcat.request.group.SetGroupAddRequestRequest import top.r3944realms.ltdmanager.utils.LoggerUtil +import top.r3944realms.ltdmanager.utils.SqlTemplate class GroupRequestHandlerModule( moduleName: String, @@ -132,13 +133,14 @@ class GroupRequestHandlerModule( LoggerUtil.logger.debug("[$name] 事件处理完成") } + private val queryWhitelistRecord = SqlTemplate.fromFile("whitlist/query_whitlist_record.sql") + private fun queryPlayerStatus(actor: Long): Int { LoggerUtil.logger.debug("[$name] 查询玩家状态: qq=$actor") try { getConnection().use { conn -> - val stmt = conn.prepareStatement( - "SELECT status FROM minecraft_manager_ltd_9.players WHERE qq=?" - ) + val sql = queryWhitelistRecord.bind("placeholder" to "?") + val stmt = conn.prepareStatement(sql) stmt.setLong(1, actor) val rs = stmt.executeQuery() val status = if (rs.next()) rs.getInt("status") else 0 diff --git a/src/main/kotlin/top/r3944realms/ltdmanager/module/InvitationCodesModule.kt b/src/main/kotlin/top/r3944realms/ltdmanager/module/InvitationCodesModule.kt index b5b6d3b..16673ab 100644 --- a/src/main/kotlin/top/r3944realms/ltdmanager/module/InvitationCodesModule.kt +++ b/src/main/kotlin/top/r3944realms/ltdmanager/module/InvitationCodesModule.kt @@ -25,6 +25,7 @@ import top.r3944realms.ltdmanager.napcat.data.msghistory.MsgHistorySpecificMsg import top.r3944realms.ltdmanager.napcat.request.other.SendGroupMsgRequest import top.r3944realms.ltdmanager.utils.HtmlTemplateUtil import top.r3944realms.ltdmanager.utils.LoggerUtil +import top.r3944realms.ltdmanager.utils.SqlTemplate import java.io.File import java.sql.Timestamp import java.util.* @@ -128,6 +129,11 @@ class InvitationCodesModule( ) + private val qualificationSql = SqlTemplate.fromFile("invitation/query_qualification.sql") + private val tokenInfoSql = SqlTemplate.fromFile("invitation/query_token_info.sql") + private val codeIdsSql = SqlTemplate.fromFile("invitation/query_code_ids.sql") + private val upsertAscriptionSql = SqlTemplate.fromFile("invitation/upsert_ascription.sql") + private val fileLock = ReentrantLock() private var lastTriggerMapState = loadState() @@ -205,13 +211,8 @@ class InvitationCodesModule( if (msgs.isEmpty()) return val qqIds = msgs.map { it.userId } - val placeholders = java.lang.String.join(",", Collections.nCopies(qqIds.size, "?")) - // 修正SQL语句的表名引用 - val sql = """ - SELECT q.player_id, q.effective, q.is_used, q.qq, q.status - FROM ltd_manager_bot.qualified_user_info q - WHERE q.qq IN ($placeholders) - """.trimIndent() + val placeholders = qqIds.joinToString(",") { "?" } + val sql = qualificationSql.bind("placeholders" to placeholders) try { getConnection().use { conn -> conn.prepareStatement(sql).use { pstmt -> @@ -291,13 +292,8 @@ class InvitationCodesModule( if (list.isEmpty()) return val whiteListIds = list.map { it.first } - val placeholders = java.lang.String.join(",", Collections.nCopies(whiteListIds.size, "?")) - - val sql = """ - SELECT q.player_id, q.player_name, q.token, q.expires_at - FROM ltd_manager_bot.qualified_user_info q - WHERE q.player_id IN ($placeholders) - """.trimIndent() + val placeholders = whiteListIds.joinToString(",") { "?" } + val sql = tokenInfoSql.bind("placeholders" to placeholders) try { getConnection().use { conn -> @@ -507,11 +503,7 @@ class InvitationCodesModule( if (invitationCodes.isEmpty()) return emptyMap() val placeholders = invitationCodes.joinToString(",") { "?" } - val sql = """ - SELECT i.id, i.code - FROM blessingskin.invitation_codes i - WHERE i.code IN ($placeholders) - """.trimIndent() + val sql = codeIdsSql.bind("placeholders" to placeholders) return getConnection().use { conn -> conn.prepareStatement(sql).use { pstmt -> @@ -543,12 +535,8 @@ class InvitationCodesModule( if (playerIds.isEmpty()) return - val placeholders = playerIds.joinToString(",") { "(?, ?)" } - val sql = """ - INSERT INTO ltd_manager_bot.invitation_code_ascription (id, token_id) - VALUES $placeholders - ON DUPLICATE KEY UPDATE token_id = VALUES(token_id) - """.trimIndent() + val values = playerIds.joinToString(",") { "(?, ?)" } + val sql = upsertAscriptionSql.bind("values" to values) getConnection().use { conn -> conn.prepareStatement(sql).use { pstmt -> diff --git a/src/main/kotlin/top/r3944realms/ltdmanager/module/gitea/GiteaWebhookModule.kt b/src/main/kotlin/top/r3944realms/ltdmanager/module/gitea/GiteaWebhookModule.kt index a3b835c..2f99fb3 100644 --- a/src/main/kotlin/top/r3944realms/ltdmanager/module/gitea/GiteaWebhookModule.kt +++ b/src/main/kotlin/top/r3944realms/ltdmanager/module/gitea/GiteaWebhookModule.kt @@ -56,11 +56,12 @@ class GiteaWebhookModule( } private fun startServer() { - var executor = Executors.newFixedThreadPool(2) + val threadPool = Executors.newFixedThreadPool(2) server = HttpServer.create(InetSocketAddress(port), 0).apply { createContext(webhookPath) { exchange -> scope?.launch { handleRequest(exchange) } } + executor = threadPool start() } LoggerUtil.logger.info("[$name] Webhook服务器已启动在端口 $port$webhookPath") @@ -155,7 +156,8 @@ class GiteaWebhookModule( private fun formatPush(p: PushPayload): String { val repo = p.repository.fullName val branch = p.ref.removePrefix("refs/heads/").removePrefix("refs/tags/") - val pusher = p.pusher?.login?.ifEmpty { p.pusher?.fullName } ?: p.sender.login.ifEmpty { p.sender.fullName } + val pusherUser = p.pusher + val pusher = pusherUser?.login?.ifEmpty { pusherUser.fullName } ?: p.sender.login.ifEmpty { p.sender.fullName } val count = p.totalCommits val sb = StringBuilder() diff --git a/src/main/kotlin/top/r3944realms/ltdmanager/utils/SqlTemplate.kt b/src/main/kotlin/top/r3944realms/ltdmanager/utils/SqlTemplate.kt new file mode 100644 index 0000000..22c2ea9 --- /dev/null +++ b/src/main/kotlin/top/r3944realms/ltdmanager/utils/SqlTemplate.kt @@ -0,0 +1,36 @@ +package top.r3944realms.ltdmanager.utils + +import java.io.File + +class SqlTemplate private constructor(private val template: String) { + + fun bind(vararg pairs: Pair): String { + var result = template + for ((key, value) in pairs) { + result = result.replace("\${$key}", value) + } + return result + } + + companion object { + private val cache = mutableMapOf() + + private val baseDir: String by lazy { + val configDir = File("config/sql") + if (!configDir.exists()) configDir.mkdirs() + configDir.absolutePath + } + + fun fromFile(path: String): SqlTemplate { + return cache.getOrPut(path) { + val file = File(baseDir, path) + require(file.exists()) { + "SQL template not found: ${file.absolutePath}" + } + SqlTemplate(file.readText().trimIndent()) + } + } + + fun clearCache() = cache.clear() + } +} diff --git a/src/test/kotlin/top/r394realms/ltdmanagertest/util/SqlTemplateTest.kt b/src/test/kotlin/top/r394realms/ltdmanagertest/util/SqlTemplateTest.kt new file mode 100644 index 0000000..87275af --- /dev/null +++ b/src/test/kotlin/top/r394realms/ltdmanagertest/util/SqlTemplateTest.kt @@ -0,0 +1,18 @@ +package top.r394realms.ltdmanagertest.util + +import top.r3944realms.ltdmanager.utils.SqlTemplate + +fun main() { + val sqlTemplateTest = SqlTemplateTest() + sqlTemplateTest.main() +} + +class SqlTemplateTest { + val testSql = SqlTemplate.fromFile("test/test.sql") + private fun test01(): String { + return testSql.bind("placeholder" to "?") + } + fun main() { + println(test01()) + } +} \ No newline at end of file