调整金额

This commit is contained in:
2026-01-31 17:14:05 +08:00
parent 2060ddff83
commit 4c2fe1d2a1
7 changed files with 88 additions and 62 deletions

BIN
bocai.db

Binary file not shown.

View File

@@ -64,7 +64,27 @@ function updateChart1() {
left: 'center'
},
tooltip: {
trigger: 'axis'
trigger: 'axis',
axisPointer: {
type: 'cross',
label: {
backgroundColor: '#6a7985'
}
},
formatter: function(params) {
let result = params[0].name + '<br/>';
params.forEach(function(item) {
let value = item.value;
let color = item.color;
let status = value >= 0 ? '盈利' : '亏损';
let statusColor = value >= 0 ? '#4CAF50' : '#ff6b6b';
result += '<span style="display:inline-block;margin-right:5px;border-radius:10px;width:10px;height:10px;background-color:' + color + '"></span>';
result += item.seriesName + ': ';
result += '<span style="color:' + statusColor + ';">' + value + '</span> ';
result += '<span style="color:' + statusColor + ';">(' + status + ')</span><br/>';
});
return result;
}
},
legend: {
data: ['数据'],

View File

@@ -18,7 +18,7 @@ public class BocaiApplication {
// // 依次执行三个任务
//
// 1. 执行CrawlerSchedule方法
System.out.println("\n=== 开始执行CrawlerSchedule任务 ===");
// System.out.println("\n=== 开始执行CrawlerSchedule任务 ===");
// CrawlerSchedule crawlerSchedule = context.getBean(CrawlerSchedule.class);
// crawlerSchedule.executeLotteryDraw();
//

View File

@@ -12,7 +12,8 @@ public class TessConfig {
Tesseract instance = new Tesseract();
instance.setLanguage("oci"); // 设置语言包,这里使用英语
instance.setDatapath("tessdata"); // 设置语言包路径
instance.setDatapath("src/main/resources/tessdata"); // 设置语言包路径
// instance.setDatapath("tessdata"); // 设置语言包路径
return instance;
}
}

View File

@@ -41,7 +41,7 @@ public class BetSchedule {
private BetRecordRepository betRecordRepository;
// 从7:02分钟起每5分钟执行一次
// @Scheduled(cron = "30 2/5 * * * ?")
@Scheduled(cron = "30 2/5 * * * ?")
public void placeBet() {
LocalDateTime now = LocalDateTime.now();
int hour = now.getHour();
@@ -53,7 +53,7 @@ public class BetSchedule {
String currentTime = now.format(
DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss")
);
System.out.println(currentTime + " - 不在投注时间范围内,跳过执行");
log.info("{}", currentTime + " - 不在投注时间范围内,跳过执行");
return;
}
@@ -64,13 +64,13 @@ public class BetSchedule {
LoginInfoResult loginInfo = loginInfoRepository.findFirstByOrderByCreateTimeDesc().orElse(null);
if (loginInfo == null) {
System.out.println(currentTime + " - 未找到登录信息,跳过执行");
log.info("{}", currentTime + " - 未找到登录信息,跳过执行");
return;
}
// 检查onOff字段是否为1开启状态
if (loginInfo.getOnOff() != 1) {
System.out.println(currentTime + " - 投注功能未开启,跳过执行");
log.info("{}", currentTime + " - 投注功能未开启,跳过执行");
return;
}
@@ -84,34 +84,33 @@ public class BetSchedule {
if (startTime != null) {
Double totalResultAmount = completedTodayRepository.sumResultAmountByCreateTimeAfter(startTime);
if (totalResultAmount != null) {
System.out.println(" - 今日盈亏总和: " + totalResultAmount);
log.info(" - 今日盈亏总和: {}", totalResultAmount);
// 判断是否达到止盈点
if (totalResultAmount >= winNum) {
System.out.println(currentTime + " - 已达到止盈点 " + winNum + ",跳过执行");
log.info("{}", currentTime + " - 已达到止盈点 " + winNum + ",跳过执行");
return;
}
// 判断是否达到止亏点
if (totalResultAmount <= -loseNum) {
System.out.println(currentTime + " - 已达到止亏点 " + loseNum + ",跳过执行");
log.info("{}", currentTime + " - 已达到止亏点 " + loseNum + ",跳过执行");
return;
}
}
}
}
System.out.println(currentTime + " - 开始执行投注...");
log.info("{}", currentTime + " - 开始执行投注...");
try {
// 执行投注逻辑
executeBet(loginInfo);
System.out.println(currentTime + " - 投注执行完成");
log.info("{}", currentTime + " - 投注执行完成");
} catch (Exception e) {
System.err.println(currentTime + " - 投注执行失败:");
e.printStackTrace();
log.error("{} - 投注执行失败:", currentTime, e);
}
}
@@ -130,7 +129,7 @@ public class BetSchedule {
LocalDateTime now = LocalDateTime.now();
// 2. 从BetRecord中获取第一条记录根据betTime排序
System.out.println(" - 从BetRecord中获取第一条记录...");
log.info(" - 从BetRecord中获取第一条记录...");
Optional<BetRecord> optionalBetRecord = betRecordRepository.findFirstByOrderByBetTimeDesc();
if (optionalBetRecord.isPresent()) {
@@ -138,30 +137,29 @@ public class BetSchedule {
String betData = betRecord.getBetData();
String betTime = betRecord.getBetTime();
System.out.println(" - 投注时间: " + betTime);
System.out.println(" - 投注数据: " + betData);
log.info(" - 投注时间: {}", betTime);
log.info(" - 投注数据: {}", betData);
// 调用投注接口
System.out.println(" - 提交投注...");
log.info(" - 提交投注...");
String betResult = callBetApi(betData, null);
System.out.println(" - 投注结果: " + betResult);
log.info(" - 投注结果: {}", betResult);
// 记录投注结果
System.out.println(" - 记录投注结果...");
log.info(" - 记录投注结果...");
recordBetResult(betData, betResult);
// 投注成功后删除BetRecord记录
if (betResult == null) {
betRecordRepository.delete(betRecord);
System.out.println(" - 已删除投注记录,期数: " + betRecord.getBetNum());
log.info(" - 已删除投注记录,期数: {}", betRecord.getBetNum());
}
} else {
System.out.println(" - 未找到投注记录");
log.info(" - 未找到投注记录");
}
} catch (Exception e) {
System.err.println(" - 投注执行失败:");
e.printStackTrace();
log.error(" - 投注执行失败:", e);
}
}
@@ -207,6 +205,6 @@ public class BetSchedule {
// 这里可以实现将投注结果记录到数据库或日志文件的逻辑
// 为了简单起见,我们这里只打印日志
String currentTime = LocalDateTime.now().format(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss"));
System.out.println(" - 投注记录: [" + currentTime + "] 数据: " + betData + ", 结果: " + betResult);
log.info(" - 投注记录: [{}] 数据: {}, 结果: {}", currentTime, betData, betResult);
}
}

View File

@@ -2,6 +2,7 @@ package com.tem.bocai.schedules;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import lombok.extern.slf4j.Slf4j;
import org.json.JSONArray;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.scheduling.annotation.Scheduled;
@@ -31,6 +32,7 @@ import org.springframework.beans.factory.annotation.Autowired;
/**
* 执行预测脚本
*/
@Slf4j
@Component
public class ExBetScriptSchedule {
@@ -48,13 +50,13 @@ public class ExBetScriptSchedule {
try {
File currentDataDir = new File(pypath, "current_data");
if (!currentDataDir.exists() || !currentDataDir.isDirectory()) {
System.out.println("current_data目录不存在");
log.info("current_data目录不存在");
return false;
}
File[] files = currentDataDir.listFiles();
if (files == null || files.length == 0) {
System.out.println("current_data目录为空");
log.info("current_data目录为空");
return false;
}
@@ -75,7 +77,7 @@ public class ExBetScriptSchedule {
}
if (latestFile == null) {
System.out.println("未找到JSON文件");
log.info("未找到JSON文件");
return false;
}
@@ -88,19 +90,15 @@ public class ExBetScriptSchedule {
LocalDateTime fiveMinutesAgo = now.minusMinutes(5);
if (fileModifiedTime.isAfter(fiveMinutesAgo)) {
System.out.println("发现新数据文件: " + latestFile.getName() +
", 修改时间: " + fileModifiedTime.format(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss")));
log.info("发现新数据文件: {}, 修改时间: {}", latestFile.getName(), fileModifiedTime.format(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss")));
return true;
} else {
System.out.println("最新数据文件: " + latestFile.getName() +
", 修改时间: " + fileModifiedTime.format(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss")) +
", 超过5分钟跳过执行");
log.info("最新数据文件: {}, 修改时间: {}, 超过5分钟跳过执行", latestFile.getName(), fileModifiedTime.format(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss")));
return false;
}
} catch (Exception e) {
System.err.println("检查新数据时发生错误:");
e.printStackTrace();
log.error("检查新数据时发生错误:", e);
return false;
}
}
@@ -127,7 +125,7 @@ public class ExBetScriptSchedule {
}
// 从7:01分钟起每5分钟执行一次
// @Scheduled(cron = "30 1/5 * * * ?")
@Scheduled(cron = "30 1/5 * * * ?")
public void executePythonScript() {
LocalDateTime now = LocalDateTime.now();
int hour = now.getHour();
@@ -138,17 +136,17 @@ public class ExBetScriptSchedule {
String currentTime = now.format(
DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss")
);
System.out.println(currentTime + " - 不在投注时间范围内,跳过执行");
log.info("{}", currentTime + " - 不在投注时间范围内,跳过执行");
return;
}
// 检查PyModel/current_data目录下最新的文件是否存在新数据
if (!checkNewDataExists()) {
System.out.println("未发现新数据跳过执行Python脚本");
log.info("未发现新数据跳过执行Python脚本");
return;
}
System.out.println("开始执行Python脚本...");
log.info("开始执行Python脚本...");
// 获取当前时间格式化为yyyy-MM-dd HH:mm:ss
String currentTime = java.time.LocalDateTime.now().format(
@@ -186,12 +184,12 @@ public class ExBetScriptSchedule {
}
}
System.out.println("执行命令: " + String.join(" ", command));
log.info("执行命令: {}", String.join(" ", command));
// 创建ProcessBuilder并设置工作目录为PyModel
ProcessBuilder pb = new ProcessBuilder(command);
// 设置工作目录为PyModel
pb.directory(new java.io.File("PyModel"));
pb.directory(new java.io.File(pypath));
// 执行Python脚本
Process process = pb.start();
@@ -220,18 +218,17 @@ public class ExBetScriptSchedule {
// 等待脚本执行完成
int exitCode = process.waitFor();
System.out.println("Python脚本执行完成退出码: " + exitCode);
System.out.println("脚本输出:\n" + output.toString());
log.info("Python脚本执行完成退出码: {}", exitCode);
log.info("脚本输出:\n{}", output.toString());
if (exitCode != 0) {
System.err.println("脚本执行错误:\n" + errorOutput.toString());
log.error("脚本执行错误:\n{}", errorOutput.toString());
} else {
parseScriptOutput(output.toString());
}
} catch (IOException | InterruptedException e) {
System.err.println("执行Python脚本时发生错误:");
e.printStackTrace();
log.error("执行Python脚本时发生错误:", e);
}
}
@@ -241,16 +238,16 @@ public class ExBetScriptSchedule {
*/
private void parseScriptOutput(String output) {
try {
System.out.println("开始解析脚本输出...");
log.info("开始解析脚本输出...");
JSONObject jsonOutput = JSON.parseObject(output);
if (jsonOutput == null) {
System.out.println("输出为空或无法解析为JSON");
log.info("输出为空或无法解析为JSON");
return;
}
JSONObject result = jsonOutput.getJSONObject("result");
if (result == null) {
System.out.println("未找到result字段");
log.info("未找到result字段");
return;
}
@@ -274,20 +271,19 @@ public class ExBetScriptSchedule {
}
}
if (!validResults.isEmpty()) {
System.out.println("提取到的有效预测结果:");
log.info("提取到的有效预测结果:");
for (Map.Entry<Integer, Map<Integer, Object>> entry : validResults.entrySet()) {
System.out.println("位置 " + entry.getKey() + ": " + entry.getValue());
log.info("位置 {}: {}", entry.getKey(), entry.getValue());
}
// 生成符合test.json格式的数据
generateOutputData(validResults);
} else {
System.out.println("未找到有效的预测结果所有值均为None");
log.info("未找到有效的预测结果所有值均为None");
}
} catch (Exception e) {
System.err.println("解析脚本输出时发生错误:");
e.printStackTrace();
log.error("解析脚本输出时发生错误:", e);
}
}
@@ -367,8 +363,8 @@ public class ExBetScriptSchedule {
outputData.put("fastBets", false);
outputData.put("ignore", false);
System.out.println("生成的输出数据:");
System.out.println(outputData.toString(2));
log.info("生成的输出数据:");
log.info("{}", outputData.toString(2));
// 保存到数据库
try {
@@ -383,13 +379,12 @@ public class ExBetScriptSchedule {
// 检查betNum是否已存在避免重复保存
if (!betRecordRepository.existsByBetNum(drawNumber)) {
betRecordRepository.save(betRecord);
System.out.println("保存投注记录到数据库成功,期数: " + drawNumber);
log.info("保存投注记录到数据库成功,期数: {}", drawNumber);
} else {
System.out.println("投注记录已存在,期数: " + drawNumber);
log.info("投注记录已存在,期数: {}", drawNumber);
}
} catch (Exception e) {
System.err.println("保存投注记录到数据库失败:");
e.printStackTrace();
log.error("保存投注记录到数据库失败:", e);
}
}
}

View File

@@ -9,6 +9,7 @@ import lombok.extern.slf4j.Slf4j;
import net.sourceforge.tess4j.Tesseract;
import net.sourceforge.tess4j.TesseractException;
import org.apache.http.Header;
import org.apache.http.HttpHost;
import org.apache.http.NameValuePair;
import org.apache.http.client.CookieStore;
import org.apache.http.client.config.RequestConfig;
@@ -372,8 +373,16 @@ public class TokenCacheService {
// 等待一下再发送登录请求
Thread.sleep(1500 + (long) (Math.random() * 1000));
// 新增代码:增加代理
String proxyHost = "127.0.0.1";
int proxyPort = 7890;
HttpHost proxy = new HttpHost(proxyHost, proxyPort);
RequestConfig proxyConfig = RequestConfig.custom()
.setProxy(proxy)
.build();
HttpPost loginPost = createLoginRequest(code,loginInfoParam);
// 新增代码:将代理类放入配置中
loginPost.setConfig(proxyConfig);
try (CloseableHttpResponse loginResponse = httpClient.execute(loginPost)) {
return processLoginResponse(loginResponse, cookieStore);
}
@@ -383,13 +392,16 @@ public class TokenCacheService {
* 创建登录请求
*/
private HttpPost createLoginRequest(String code,LoginInfoParam loginInfoParam) throws UnsupportedEncodingException {
HttpPost loginPost = new HttpPost(loginInfoParam.loginUrl + "/login");
// 设置请求头
setCommonHeaders(loginPost);
loginPost.setHeader("Referer", loginInfoParam.loginUrl + "/login");
loginPost.setHeader("Origin", loginInfoParam.loginUrl);
loginPost.setHeader("Accept", "application/json, text/plain, */*");
// 构建登录参数
List<NameValuePair> params = new ArrayList<>();
params.add(new BasicNameValuePair("type", "1"));