From bd529d9041a5bec621124a5fd1a41223b72026ca Mon Sep 17 00:00:00 2001 From: WrBug Date: Sat, 14 Feb 2026 21:00:01 +0800 Subject: [PATCH] =?UTF-8?q?feat(cryptotail):=20=E5=B0=BE=E7=9B=98=E7=AD=96?= =?UTF-8?q?=E7=95=A5=E6=89=93=E5=8D=B0=E5=88=9D=E5=A7=8B=E4=BB=B7=E5=B7=AE?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - 周期开始预计算 AUTO 价差后打印 baseSpreadUp/baseSpreadDown - 触发价差校验时打印初始价差、系数、有效最小价差、当前K线价差及是否通过 Co-authored-by: Cursor --- .../CryptoTailOrderbookWsService.kt | 8 ++++- .../CryptoTailStrategyExecutionService.kt | 35 ++++++++++++++----- 2 files changed, 34 insertions(+), 9 deletions(-) diff --git a/backend/src/main/kotlin/com/wrbug/polymarketbot/service/cryptotail/CryptoTailOrderbookWsService.kt b/backend/src/main/kotlin/com/wrbug/polymarketbot/service/cryptotail/CryptoTailOrderbookWsService.kt index ae696d9..8ee7315 100644 --- a/backend/src/main/kotlin/com/wrbug/polymarketbot/service/cryptotail/CryptoTailOrderbookWsService.kt +++ b/backend/src/main/kotlin/com/wrbug/polymarketbot/service/cryptotail/CryptoTailOrderbookWsService.kt @@ -236,7 +236,13 @@ class CryptoTailOrderbookWsService( scope.launch { for ((intervalSeconds, periodStartUnix) in autoPeriods) { try { - binanceKlineAutoSpreadService.computeAndCache(intervalSeconds, periodStartUnix) + val pair = binanceKlineAutoSpreadService.computeAndCache(intervalSeconds, periodStartUnix) + if (pair != null) { + logger.info( + "周期开始初始价差: interval=${intervalSeconds}s periodStartUnix=$periodStartUnix " + + "baseSpreadUp=${pair.first.toPlainString()} baseSpreadDown=${pair.second.toPlainString()}" + ) + } } catch (e: Exception) { logger.warn("周期开始预计算 AUTO 价差失败: interval=$intervalSeconds periodStartUnix=$periodStartUnix ${e.message}") } diff --git a/backend/src/main/kotlin/com/wrbug/polymarketbot/service/cryptotail/CryptoTailStrategyExecutionService.kt b/backend/src/main/kotlin/com/wrbug/polymarketbot/service/cryptotail/CryptoTailStrategyExecutionService.kt index ad4b8e9..4f5a90e 100644 --- a/backend/src/main/kotlin/com/wrbug/polymarketbot/service/cryptotail/CryptoTailStrategyExecutionService.kt +++ b/backend/src/main/kotlin/com/wrbug/polymarketbot/service/cryptotail/CryptoTailStrategyExecutionService.kt @@ -188,19 +188,37 @@ class CryptoTailStrategyExecutionService( ?: return false val (openP, closeP) = oc val spreadAbs = closeP.subtract(openP).abs() - val effectiveMinSpread = when (mode) { - "FIXED" -> strategy.minSpreadValue?.takeIf { it > BigDecimal.ZERO } - "AUTO" -> computeAutoEffectiveMinSpread(strategy, periodStartUnix, outcomeIndex) - else -> null + when (mode) { + "FIXED" -> { + val effectiveMinSpread = strategy.minSpreadValue?.takeIf { it > BigDecimal.ZERO } + if (effectiveMinSpread == null || effectiveMinSpread <= BigDecimal.ZERO) return true + return spreadAbs >= effectiveMinSpread + } + "AUTO" -> { + val result = computeAutoEffectiveMinSpread(strategy, periodStartUnix, outcomeIndex) ?: return true + val effectiveMinSpread = result.effectiveMinSpread + if (effectiveMinSpread <= BigDecimal.ZERO) return true + val passed = spreadAbs >= effectiveMinSpread + logger.info( + "尾盘价差校验: 初始价差(100%基准)=${result.baseSpread.toPlainString()} 系数=${result.coefficient.toPlainString()} " + + "有效最小价差=${effectiveMinSpread.toPlainString()} 当前K线价差=${spreadAbs.toPlainString()} 通过=$passed" + ) + return passed + } + else -> return true } - if (effectiveMinSpread == null || effectiveMinSpread <= BigDecimal.ZERO) return true - return spreadAbs >= effectiveMinSpread } /** * AUTO 模式:取 100% 基准价差,按窗口内毫秒进度计算动态系数(100%→50%)得到有效最小价差。 */ - private fun computeAutoEffectiveMinSpread(strategy: CryptoTailStrategy, periodStartUnix: Long, outcomeIndex: Int): BigDecimal? { + private data class AutoSpreadResult( + val baseSpread: BigDecimal, + val coefficient: BigDecimal, + val effectiveMinSpread: BigDecimal + ) + + private fun computeAutoEffectiveMinSpread(strategy: CryptoTailStrategy, periodStartUnix: Long, outcomeIndex: Int): AutoSpreadResult? { val baseSpread = binanceKlineAutoSpreadService.getAutoMinSpreadBase(strategy.intervalSeconds, periodStartUnix, outcomeIndex) ?: binanceKlineAutoSpreadService.computeAndCache(strategy.intervalSeconds, periodStartUnix)?.let { if (outcomeIndex == 0) it.first else it.second } ?: return null @@ -217,7 +235,8 @@ class CryptoTailStrategyExecutionService( .let { p -> maxOf(BigDecimal.ZERO, minOf(BigDecimal.ONE, p)) } BigDecimal.ONE.subtract(progress.multi("0.5")) } - return baseSpread.multi(coefficient).setScale(8, RoundingMode.HALF_UP) + val effectiveMinSpread = baseSpread.multi(coefficient).setScale(8, RoundingMode.HALF_UP) + return AutoSpreadResult(baseSpread, coefficient, effectiveMinSpread) } private suspend fun placeOrderForTrigger(