@@ -1,15 +1,93 @@
// fakeLog 函数,使用方法:将本函数放在主函数前,调用时请务必使用await, 否则可能出现v8白框报错
//在js开头处伪造该js结束运行的日志信息, 如 await fakeLog("js脚本", true, true, 0);
//在js结尾处伪造该js开始运行的日志信息, 如 await fakeLog("js脚本", true, false, 2333);
//duration项目仅在伪造结束信息时有效, 且无实际作用, 可以任意填写, 当你需要在日志中输出特定值时才需要, 单位为毫秒
//在调用地图追踪前伪造该地图追踪开始运行的日志信息,如 await fakeLog(`地图追踪.json`, false, true, 0);
//在调用地图追踪后伪造该地图追踪结束运行的日志信息,如 await fakeLog(`地图追踪.json`, false, false, 0);
//如此便可以在js运行过程中伪造地图追踪的日志信息, 可以在日志分析等中查看
async function fakeLog ( name , isJs , isStart , duration ) {
await sleep ( 10 ) ;
const currentTime = Date . now ( ) ;
// 参数检查
if ( typeof name !== 'string' ) {
log . error ( "参数 'name' 必须是字符串类型!" ) ;
return ;
}
if ( typeof isJs !== 'boolean' ) {
log . error ( "参数 'isJs' 必须是布尔型!" ) ;
return ;
}
if ( typeof isStart !== 'boolean' ) {
log . error ( "参数 'isStart' 必须是布尔型!" ) ;
return ;
}
if ( typeof currentTime !== 'number' || ! Number . isInteger ( currentTime ) ) {
log . error ( "参数 'currentTime' 必须是整数!" ) ;
return ;
}
if ( typeof duration !== 'number' || ! Number . isInteger ( duration ) ) {
log . error ( "参数 'duration' 必须是整数!" ) ;
return ;
}
// 将 currentTime 转换为 Date 对象并格式化为 HH:mm:ss.sss
const date = new Date ( currentTime ) ;
const hours = String ( date . getHours ( ) ) . padStart ( 2 , '0' ) ;
const minutes = String ( date . getMinutes ( ) ) . padStart ( 2 , '0' ) ;
const seconds = String ( date . getSeconds ( ) ) . padStart ( 2 , '0' ) ;
const milliseconds = String ( date . getMilliseconds ( ) ) . padStart ( 3 , '0' ) ;
const formattedTime = ` ${ hours } : ${ minutes } : ${ seconds } . ${ milliseconds } ` ;
// 将 duration 转换为分钟和秒,并保留三位小数
const durationInSeconds = duration / 1000 ; // 转换为秒
const durationMinutes = Math . floor ( durationInSeconds / 60 ) ;
const durationSeconds = ( durationInSeconds % 60 ) . toFixed ( 3 ) ; // 保留三位小数
// 使用四个独立的 if 语句处理四种情况
if ( isJs && isStart ) {
// 处理 isJs = true 且 isStart = true 的情况
const logMessage = ` 正在伪造js开始的日志记录 \n \n ` +
` [ ${ formattedTime } ] [INF] BetterGenshinImpact.Service.ScriptService \n ` +
` ------------------------------ \n \n ` +
` [ ${ formattedTime } ] [INF] BetterGenshinImpact.Service.ScriptService \n ` +
` → 开始执行JS脚本: " ${ name } " ` ;
log . info ( logMessage ) ;
}
if ( isJs && ! isStart ) {
// 处理 isJs = true 且 isStart = false 的情况
const logMessage = ` 正在伪造js结束的日志记录 \n \n ` +
` [ ${ formattedTime } ] [INF] BetterGenshinImpact.Service.ScriptService \n ` +
` → 脚本执行结束: " ${ name } ", 耗时: ${ durationMinutes } 分 ${ durationSeconds } 秒 \n \n ` +
` [ ${ formattedTime } ] [INF] BetterGenshinImpact.Service.ScriptService \n ` +
` ------------------------------ ` ;
log . info ( logMessage ) ;
}
if ( ! isJs && isStart ) {
// 处理 isJs = false 且 isStart = true 的情况
const logMessage = ` 正在伪造地图追踪开始的日志记录 \n \n ` +
` [ ${ formattedTime } ] [INF] BetterGenshinImpact.Service.ScriptService \n ` +
` ------------------------------ \n \n ` +
` [ ${ formattedTime } ] [INF] BetterGenshinImpact.Service.ScriptService \n ` +
` → 开始执行地图追踪任务: " ${ name } " ` ;
log . info ( logMessage ) ;
}
if ( ! isJs && ! isStart ) {
// 处理 isJs = false 且 isStart = false 的情况
const logMessage = ` 正在伪造地图追踪结束的日志记录 \n \n ` +
` [ ${ formattedTime } ] [INF] BetterGenshinImpact.Service.ScriptService \n ` +
` → 脚本执行结束: " ${ name } ", 耗时: ${ durationMinutes } 分 ${ durationSeconds } 秒 \n \n ` +
` [ ${ formattedTime } ] [INF] BetterGenshinImpact.Service.ScriptService \n ` +
` ------------------------------ ` ;
log . info ( logMessage ) ;
}
}
// 定义目标文件夹路径和记录文件路径
const recordFolder = "record" ; // 存储记录文件的文件夹路径
const timestamp = "::2000-01-01T00:00:00.000Z" ; // 固定的时间戳
// 定义六个运行时变量,初始值分别为 2000、1000、0、0、0、0
let runtime1 = 2000 ;
let runtime2 = 1000 ;
let runtime3 = 0 ;
let runtime4 = 0 ;
let runtime5 = 0 ;
let runtime6 = 0 ;
// 从 settings 中读取用户配置,并设置默认值
const userSettings = {
operationMode : settings . operationMode || "执行任务(若不存在索引文件则自动创建)" ,
@@ -146,9 +224,10 @@ function removeJsonSuffix(fileName) {
}
// 新增逻辑:当选择“执行任务(若不存在索引文件则自动创建)”时,执行类似路径执行的逻辑
if ( userSettings . operationMode === "执行任务(若不存在索引文件则自动创建)" ) {
if ( userSettings . operationMode === "执行任务(若不存在索引文件则自动创建)" ) {
log . info ( "启用自动拾取的实时任务" ) ;
dispatcher . addTimer ( new RealtimeTimer ( "AutoPick" ) ) ;
await fakeLog ( "采集cd管理" , true , false , 1000 ) ;
// 获取子文件夹内的所有文件路径
const recordFiles = file . ReadPathSync ( subFolderPath ) ;
// 直接获取文件数量作为路径组数量
@@ -158,16 +237,16 @@ if (userSettings.operationMode === "执行任务(若不存在索引文件则
for ( let groupNumber = 1 ; groupNumber <= totalPathGroups ; groupNumber ++ ) {
const pathGroupFilePath = ` ${ subFolderPath } /路径组 ${ groupNumber } .txt ` ; // 动态生成路径组文件路径
genshin . returnMainUi ( ) ;
genshin . returnMainUi ( ) ;
//切换到指定配队
//切换到指定配队
if ( partyNamesArray [ groupNumber - 1 ] !== "" ) {
await genshin . switchParty ( partyNamesArray [ groupNumber - 1 ] )
}
await genshin . switchParty ( partyNamesArray [ groupNumber - 1 ] )
}
genshin . returnMainUi ( ) ;
genshin . returnMainUi ( ) ;
try {
try {
let pathGroupContent = await file . readText ( pathGroupFilePath ) ;
let pathGroupEntries = pathGroupContent . trim ( ) . split ( '\n' ) ;
for ( let i = 0 ; i < pathGroupEntries . length ; i ++ ) {
@@ -180,29 +259,11 @@ try {
// 获取开始时间
const startTime = new Date ( ) ;
// 更新 runtime 变量
runtime6 = runtime5 ;
runtime5 = runtime4 ;
runtime4 = runtime3 ;
runtime3 = runtime2 ;
runtime2 = runtime1 ;
runtime1 = startTime . getTime ( ) ;
// 检查时间差条件
if ( ( runtime1 - runtime2 ) < 500 &&
( runtime2 - runtime3 ) < 500 &&
( runtime3 - runtime4 ) < 500 &&
( runtime4 - runtime5 ) < 500 &&
( runtime5 - runtime6 ) < 500 ) {
log . info ( ` 连续五次时间差小于 500 毫秒,循环终止。 ` ) ;
break ; // 如果连续五次时间差小于 500 毫秒,退出循环
}
// 比较当前时间戳与任务的时间戳
const entryDate = new Date ( entryTimestamp ) ;
if ( startTime <= entryDate ) {
log . info ( ` 当前任务 ${ entryName } 未刷新,跳过任务 ${ i + 1 } / ${ pathGroupEntries . length } 个 ` ) ;
await sleep ( 50 0) ;
await sleep ( 1 0) ;
continue ; // 跳过当前任务
}
@@ -214,6 +275,10 @@ try {
continue ; // 跳过当前任务
}
//伪造地图追踪开始的日志
await fakeLog ( entryName , false , true , 0 ) ;
// 日志输出当前任务信息
log . info ( ` 当前任务 ${ entryName } 为第 ${ i + 1 } / ${ pathGroupEntries . length } 个 ` ) ;
@@ -226,21 +291,35 @@ try {
continue ; // 跳过当前任务
}
//捕获任务取消的信息并跳出循环
try {
await sleep ( 10 ) ; // 假设 sleep 是一个异步函数,休眠 10 毫秒
} catch ( error ) {
log . error ( ` 发生错误: ${ error } ` ) ;
break ; // 终止循环
}
// 获取结束时间
const endTime = new Date ( ) ;
// 比较开始时间与结束时间
const timeDiff = endTime . getTime ( ) - startTime . getTime ( ) ; // 时间差(毫秒)
//伪造地图追踪结束的日志
await fakeLog ( entryName , false , false , timeDiff ) ;
if ( timeDiff > 3000 ) { // 时间差大于3秒
// 获取当前路径组的 cdtype
const currentCdType = pathGroupCdType [ groupNumber - 1 ] || "未知类型" ;
const currentCdType = pathGroupCdType [ groupNumber - 1 ] || "未知类型" ;
// 初始化 newTimestamp 和 nextAvailableTime
let newTimestamp ;
let nextAvailableTime ;
// 初始化 newTimestamp 和 nextAvailableTime
let newTimestamp ;
let nextAvailableTime ;
// 根据 cdtype 执行不同的操作
switch ( currentCdType ) {
// 根据 cdtype 执行不同的操作
switch ( currentCdType ) {
case "1次0点刷新" :
// 将任务文件中对应的时间戳改为下一个0点
const tomorrow = new Date ( startTime . getTime ( ) + 24 * 60 * 60 * 1000 ) ;
@@ -307,24 +386,24 @@ switch (currentCdType) {
newTimestamp = startTime . toISOString ( ) ;
nextAvailableTime = startTime . toLocaleString ( ) ; // 转换为本地时间格式
break ;
}
}
// 更新任务文件中的时间戳
// 首先根据newTimestamp修改pathGroupEntries中对应项
pathGroupEntries = pathGroupEntries . map ( entry => {
// 更新任务文件中的时间戳
// 首先根据newTimestamp修改pathGroupEntries中对应项
pathGroupEntries = pathGroupEntries . map ( entry => {
const [ name , timestamp ] = entry . split ( '::' ) ;
if ( name === entryName ) {
return ` ${ name } :: ${ newTimestamp } ` ;
}
return entry ;
} ) ;
} ) ;
// 然后根据pathGroupEntries修改pathGroupContent
pathGroupContent = pathGroupEntries . join ( '\n' ) ;
// 然后根据pathGroupEntries修改pathGroupContent
pathGroupContent = pathGroupEntries . join ( '\n' ) ;
// 最后将pathGroupContent写回原文件
await file . writeText ( pathGroupFilePath , pathGroupContent ) ;
log . info ( ` 本任务执行大于10 秒, cd信息已更新, 下一次可用时间为 ${ nextAvailableTime } ` ) ;
// 最后将pathGroupContent写回原文件
await file . writeText ( pathGroupFilePath , pathGroupContent ) ;
log . info ( ` 本任务执行大于3 秒, cd信息已更新, 下一次可用时间为 ${ nextAvailableTime } ` ) ;
}
}
log . info ( ` 路径组 ${ groupNumber } 的所有任务运行完成 ` ) ;
@@ -333,7 +412,10 @@ log.info(`本任务执行大于10秒, cd信息已更新, 下一次可用时间
}
}
log . info ( '所有路径组的任务运行完成' ) ;
}
//伪造js开始的日志
await fakeLog ( "采集cd管理" , true , true , 0 ) ;
}
} catch ( error ) {
log . error ( ` 操作失败: ${ error } ` ) ;
}