no message

This commit is contained in:
hellcat 2026-04-25 17:07:11 +08:00
parent c0f872f8da
commit 98ca30c3c3
9 changed files with 609 additions and 242 deletions

View File

@ -69,7 +69,11 @@
<img alt="image" class="mr-2 rounded-circle" width="50" height="50" src="/theme/cool/assets/fonts/flag-icon-css/flags/1x1/{$oNode->duck_class}.svg">
{/if}
<div class="media-body">
<div class="media-title node-status {if $oNode->online == 1 || $oNode->is_shadow == 1}node-is-online{else}node-is-offline{/if}">{$oNode->name}</div>
{if in_array($oNode->pid, $aServerLiveIds)}
<div class="media-title node-status node-is-online">{$oNode->name}</div>
{else}
<div class="media-title node-status node-is-offline">{$oNode->name}</div>
{/if}
<div class=" text-job text-muted">{$oNode->memo_front}</div>
</div>
<div class="media-items">

View File

@ -67,13 +67,20 @@ EOL;
time() - Config::obtain('last_daily_job_time') > 86399
) {
$jobs->cleanDb();
// $jobs->resetNodeBandwidth();
$jobs->reportPayUser(); // 付费用户统计
$jobs->resetDuckBandwidth(); // 重置每日的duck流量
$jobs->reportBandWidth(); // 报告流量给tg
$jobs->resetFreeUserBandwidth(); // 重置免费用户的流量
$jobs->sendDailyTrafficReport(); // 流量报告?不重要
$jobs->clearTodayWidth(); // 重置每日的用户使用流量
// $jobs->resetDuckBandwidth(); // 重置每日的duck流量 || 没有duck了
// $jobs->reportBandWidth(); // 报告流量给tg || 改写了
// $jobs->resetFreeUserBandwidth(); // 重置免费用户的流量 || 傻逼功能
// $jobs->sendDailyTrafficReport(); // 流量报告?不重要 || 不发送了,容易黑名单 * 应该跟注册邮箱分开,再说
// $jobs->clearTodayWidth(); // 重置每日的用户使用流量 || 改逻辑了,不重置
//// 节点统计组
$jobs->zhuanfa_width_merge(); // 合并转发耗流统计要在node计算之前
$jobs->day_width_report_zhuanfa(); // 汇报每天耗流 - 转发
$jobs->day_width_report(); // 汇报每天耗流
$jobs->resetZhuanfaBandwidth(); // zhuanfa流量自动重置
$jobs->resetNodeBandwidth(); // 要在最后,其他计算完再重置
//// 节点统计组 end
$jobs->smtpClearDayCount(); // 重置stmp的day_count
@ -100,7 +107,7 @@ EOL;
$jobs->sendTelegramDiary();
}
$jobs->resetTodayBandwidth();
$jobs->resetTodayBandwidth(); // 重置user的width
if (Config::obtain('telegram_daily_job')) {
$jobs->sendTelegramDailyJob();
@ -159,11 +166,14 @@ EOL;
}
if ($minute === 0) {
$jobs->mergeBandWidth();
$jobs->hour_width_report(); // 检测小时耗流
// $jobs->mergeBandWidth(); || 逻辑改变,不用了
}
// Run email queue
$jobs->processEmailQueue();
$jobs->processEmailQueue_bulk(); // 群发
$jobs->todayOk();
}
}

View File

@ -24,10 +24,12 @@ final class NodeController extends BaseController
{
$oNodeList = Node::where("type", 1)->orderBy("order_group")->orderBy("name")->get();
$aServerLiveIds = Node::where("type", 2)->where("online", 1)->pluck("id")->toArray();
return $response->write(
$this->view()
->assign('oNodeList', $oNodeList)
->assign('aServerLiveIds', $aServerLiveIds)
->fetch('user/node.tpl')
);
}

View File

@ -11,6 +11,8 @@ use function dns_get_record;
use function time;
use const DNS_A;
use const DNS_AAAA;
//use DateTime;
use Illuminate\Support\Carbon;
/**
* @property int $id 节点ID
@ -156,4 +158,37 @@ final class Node extends Model
}
}
}
// 计算距离重置日
// public function getResetDayLimitAttribute()
// {
// if (!$this->bandwidthlimit_resetday) {
// return false;
// }
//
// $iDayNow = (int) date("d");
// return (int) $this->bandwidthlimit_resetday - $iDayNow;
// }
public function getResetDayLimitAttribute()
{
if (!$this->bandwidthlimit_resetday) {
return false;
}
$iResetDay = (int) $this->bandwidthlimit_resetday;
$oNow = Carbon::now();
// 创建目标日期:设定为本月的重置日
// 如果重置日超过了当月最大天数如重置日31号当前月2月Carbon会自动处理
$oTargetDate = $oNow->copy()->day($iResetDay);
// 如果目标日期已经在今天之前,说明重置日在下个月
if ($oTargetDate->isPast()) {
$oTargetDate->addMonth();
}
// 返回相差天数
return $oNow->diffInDays($oTargetDate);
}
}

View File

@ -11,5 +11,23 @@ final class Zhuanfas extends Model
protected $connection = 'default';
protected $table = 'zhuanfas';
public function getResetDayLimitAttribute()
{
// 1. 基础防御:日期为空或无效直接返回
if (!$this->end_date || $this->end_date === '0000-00-00') {
return false;
}
// 2. 将日期转为 Unix 时间戳 (原生)
$iTargetTimestamp = strtotime($this->end_date);
$iNowTimestamp = time();
// 3. 计算差值 (秒)
$iDiffSeconds = $iTargetTimestamp - $iNowTimestamp;
// 4. 转为天数
// 如果日期已过,这里会得到负数;如果想返回 0 替代负数,请加一个判断
return (int) floor($iDiffSeconds / 86400);
}
}

View File

@ -418,19 +418,19 @@ final class Cron
// echo $e->getMessage() . PHP_EOL;
// }
//
// if (Config::obtain('telegram_node_offline')) {
// $notice_text = str_replace(
// '%node_name%',
// $node->name,
// Config::obtain('telegram_node_offline_text')
// );
//
// try {
// (new Telegram())->send(0, $notice_text);
// } catch (TelegramSDKException $e) {
// echo $e->getMessage();
// }
// }
if (Config::obtain('telegram_node_offline')) {
$notice_text = str_replace(
'%node_name%',
$node->name,
Config::obtain('telegram_node_offline_text')
);
try {
(new Telegram())->send(0, $notice_text);
} catch (TelegramSDKException $e) {
echo $e->getMessage();
}
}
$node->online = 0;
$node->save();
@ -450,19 +450,19 @@ final class Cron
// echo $e->getMessage() . PHP_EOL;
// }
// if (Config::obtain('telegram_node_online')) {
// $notice_text = str_replace(
// '%node_name%',
// $node->name,
// Config::obtain('telegram_node_online_text')
// );
//
// try {
// (new Telegram())->send(0, $notice_text);
// } catch (TelegramSDKException $e) {
// echo $e->getMessage();
// }
// }
if (Config::obtain('telegram_node_online')) {
$notice_text = str_replace(
'%node_name%',
$node->name,
Config::obtain('telegram_node_online_text')
);
try {
(new Telegram())->send(0, $notice_text);
} catch (TelegramSDKException $e) {
echo $e->getMessage();
}
}
$node->online = 1;
$node->save();
@ -1516,22 +1516,45 @@ final class Cron
echo Tools::toDateTime(time()) . ' Successfully removed inactive user\'s Link and Invite' . PHP_EOL;
}
// 废弃
// 重置nodeserver流量
public static function resetNodeBandwidth(): void
{
(new Node())->where('bandwidthlimit_resetday', date('d'))->update(['node_bandwidth' => 0]);
(new Node())->where('bandwidthlimit_resetday', date('d'))->update(['node_bandwidth' => 0, 'prev_hour_width' => 0, 'prev_day_width' => 0]);
echo Tools::toDateTime(time()) . ' 重设节点流量完成' . PHP_EOL;
}
// 机器到日期重置流量
public static function resetDuckBandwidth(): void
// 重置转发流量
// public static function resetZhuanfaBandwidth(): void
// {
// // 原子性批量更新:保持 end_date 的“日”不变,月份自动顺延
// Zhuanfas::whereDate('end_date', '<=', date("Y-m-d"))
// ->update([
// 'use_width' => 0,
// 'today_width' => 0,
// 'end_date' => DB::raw("DATE_ADD(end_date, INTERVAL 1 MONTH)"),
// ]);
// }
public static function resetZhuanfaBandwidth(): void
{
(new Ducks())->where('width_reset_day', date('d'))->update(['use_width' => 0]);
echo Tools::toDateTime(time()) . ' 重设机器流量完成' . PHP_EOL;
Zhuanfas::where('end_date', '!=', '0000-00-00')
->whereNotNull('end_date')
->whereDate('end_date', '<=', date('Y-m-d'))
->update([
'use_width' => 0,
'today_width' => 0,
'end_date' => DB::raw("DATE_ADD(NOW(), INTERVAL 1 MONTH)")
]);
}
// 机器到日期重置流量 废弃
// public static function resetDuckBandwidth(): void
// {
// (new Ducks())->where('width_reset_day', date('d'))->update(['use_width' => 0]);
//
// echo Tools::toDateTime(time()) . ' 重设机器流量完成' . PHP_EOL;
// }
// public static function resetZhuanfaBandwidth(): void
// {
// (new Ducks())->where('end_date', date('Y-m-d'))->update(['use_width' => 0]);
@ -1539,234 +1562,436 @@ final class Cron
// echo Tools::toDateTime(time()) . ' 重设机器流量完成' . PHP_EOL;
// }
// 每小时统计节点流量入库tg警报
public static function mergeBandWidth(): void
// 每小时检测server耗流
public static function hour_width_report(): void
{
$oNodeAll = Node::where('type', 1)->get();
$aZhuanfaFlowNow = [];
$aDuckFlowNow = [];
$oServers = Node::where('type', 2)->get();
$sMsg = "";
// 统计node流量
foreach ($oNodeAll as $oNodeRow) {
foreach ($oServers as $oServer) {
$iRunWidth = $oServer->node_bandwidth - $oServer->prev_hour_width;
if ($oNodeRow->node_bandwidth == 0) {
if ($oNodeRow->is_shadow != 1) {
$sMsg .= '🚨【'.$oNodeRow->name."】小时未耗流,可能异常。\n";
}
if ($iRunWidth <= 0) {
$sMsg .= '🚨【'.$oServer->duck_code."】小时未耗流,可能异常。\n";
}
@$aZhuanfaFlowNow[$oNodeRow->zhuanfa_code] += $oNodeRow->node_bandwidth;
@$aDuckFlowNow[$oNodeRow->duck_code] += $oNodeRow->node_bandwidth;
$oServer->prev_hour_width = $oServer->node_bandwidth;
$oServer->save();
}
// 入库zhunafa
foreach ($aZhuanfaFlowNow as $k => $v) {
if ($v) {
Zhuanfas::where('code', $k)->increment('today_width', $v);
Zhuanfas::where('code', $k)->increment('use_width', $v);
}
}
// 入库duck
foreach ($aDuckFlowNow as $k => $v) {
if ($v) {
Ducks::where('code', $k)->increment('today_width', $v);
Ducks::where('code', $k)->increment('use_width', $v);
}
}
// 清空node流量
Node::query()->update(['node_bandwidth' => 0]);
if ($sMsg) {
(new Telegram())->send(0, $sMsg);
}
}
// 每日报表
public static function reportBandWidth(): void
// 每天汇报server耗流
public static function day_width_report(): void
{
$oZhuanfas = new Zhuanfas();
$oDucks = new Ducks();
// 流量报告,转发
$oTgSendFormat = new TgSendFormat();
$oTgSendFormat->sTitleEmoji = "\n\n";
$oTgSendFormat->sTitle = "# 转发流量";
$today = new DateTime();
$oZhuanfasAll = $oZhuanfas->all();
foreach ($oZhuanfasAll as $oZhuanfasRow) {
$targetDate = new DateTime($oZhuanfasRow->end_date);
$interval = $today->diff($targetDate);
if ($today > $targetDate) {
$iDiffDay = -$interval->days;
} else {
$iDiffDay = $interval->days;
}
$oTgSendFormat->rowAdd(
$oZhuanfasRow->name,
$oZhuanfasRow->today_width,
$oZhuanfasRow->use_width,
$oZhuanfasRow->max_width,
$iDiffDay
);
}
$sTgReport = $oTgSendFormat->typeA();
(new Telegram())->send(0, $sTgReport);
// 流量报告,机器
$oTgSendFormat = new TgSendFormat();
$oTgSendFormat->sTitleEmoji = "\n\n";
$oTgSendFormat->sTitle = "# 机器流量";
$oDucksAll = $oDucks->orderBy('code')->get();
foreach ($oDucksAll as $oDucksRow) {
if ($oDucksRow->width_reset_day == 0) {
$iWidthResetDay = 0;
} if ($oDucksRow->width_reset_day > date('d')) {
$iWidthResetDay = $oDucksRow->width_reset_day - date('d');
} else {
$date = new DateTime();
$date->modify('first day of next month');
$date->setDate((int)$date->format('Y'), (int)$date->format('m'), $oDucksRow->width_reset_day);
$sEndDate = $date;
$currentDate = new DateTime();
$interval = $currentDate->diff($sEndDate);
$iWidthResetDay = $interval->days;
}
$oServers = Node::where('type', 2)->get();
if ($oServers->isEmpty()) {
return;
}
foreach ($oServers as $oServer) {
$iTodayWidth = $oServer->node_bandwidth - $oServer->prev_day_width;
$oTgSendFormat->rowAdd(
$oDucksRow->code,
$oDucksRow->today_width,
$oDucksRow->use_width,
$oDucksRow->max_width,
$iWidthResetDay,
$oDucksRow->memo
$oServer->duck_code,
$iTodayWidth,
$oServer->node_bandwidth,
$oServer->node_bandwidth_limit,
$oServer->reset_day_limit
);
$oServer->prev_day_width = $oServer->node_bandwidth;
$oServer->save();
}
(new Telegram())->send(0, $oTgSendFormat->typeA());
}
// 每天merge的zhuanfa耗流
public static function zhuanfa_width_merge(): void
{
$oServers = Node::where('type', 2)
->whereNotNull('zhuanfa_code')
->whereNotIn('zhuanfa_code', ['none', ''])
->get();
$aZhuanfaToday = [];
foreach ($oServers as $oServer) {
$iTodayWidth = max(0, $oServer->node_bandwidth - $oServer->prev_day_width);
$aZhuanfaToday[$oServer->zhuanfa_code] = ($aZhuanfaToday[$oServer->zhuanfa_code] ?? 0) + $iTodayWidth;
}
foreach ($aZhuanfaToday as $sZhuanfaCode => $iZhuanfaWidthToday) {
$oZhuanfa = Zhuanfas::updateOrCreate(['code' => $sZhuanfaCode]);
$oZhuanfa->today_width = $iZhuanfaWidthToday; // 这个覆盖是可以的,因为这是当前周期的总量
$oZhuanfa->save();
$oZhuanfa->increment('use_width', $iZhuanfaWidthToday); // 这里使用原子递增
}
}
public static function day_width_report_zhuanfa(): void
{
$oZhuanfas = Zhuanfas::where("status", 1)->get();
if ($oZhuanfas->isEmpty()) {
return;
}
$oTgSendFormat = new TgSendFormat();
$oTgSendFormat->sTitleEmoji = "\n\n";
$oTgSendFormat->sTitle = "# 转发流量";
foreach ($oZhuanfas as $oZhuanfa) {
$oTgSendFormat->rowAdd(
$oZhuanfa->name,
$oZhuanfa->today_width,
$oZhuanfa->use_width,
$oZhuanfa->max_width,
$oZhuanfa->reset_day_limit
);
}
$sTgReport = $oTgSendFormat->typeA();
(new Telegram())->send(0, $sTgReport);
}
// public static function mergeBandWidth__old(): void
// {
//
// $oNodeAll = Node::where('type', 1)->get();
//
// $aZhuanfaFlowNow = [];
// $aDuckFlowNow = [];
// $sMsg = "" ;
//
// // 统计node流量
// foreach ($oNodeAll as $oNodeRow) {
//
// if ($oNodeRow->node_bandwidth == 0) {
//
// if ($oNodeRow->is_shadow != 1) {
//
// $sMsg .= '🚨【'.$oNodeRow->name."】小时未耗流,可能异常。\n";
//
// }
//
// }
//
// @$aZhuanfaFlowNow[$oNodeRow->zhuanfa_code] += $oNodeRow->node_bandwidth;
// @$aDuckFlowNow[$oNodeRow->duck_code] += $oNodeRow->node_bandwidth;
//
// }
//
// // 入库zhunafa
// foreach ($aZhuanfaFlowNow as $k => $v) {
//
// if ($v) {
// Zhuanfas::where('code', $k)->increment('today_width', $v);
// Zhuanfas::where('code', $k)->increment('use_width', $v);
// }
//
// }
//
// // 入库duck
// foreach ($aDuckFlowNow as $k => $v) {
//
// if ($v) {
// Ducks::where('code', $k)->increment('today_width', $v);
// Ducks::where('code', $k)->increment('use_width', $v);
// }
//
// }
//
// // 清空node流量
// Node::query()->update(['node_bandwidth' => 0]);
//
// if ($sMsg) {
// (new Telegram())->send(0, $sMsg);
// }
//
// }
//// 每日报表
// public static function reportBandWidth(): void
// {
// //// 流量报告,转发
// $oZhuanfas = new Zhuanfas();
// $oTgSendFormat = new TgSendFormat();
// $oTgSendFormat->sTitleEmoji = "\n\n";
// $oTgSendFormat->sTitle = "# 转发流量";
// $today = new DateTime();
//
// $oZhuanfasAll = $oZhuanfas->all();
// foreach ($oZhuanfasAll as $oZhuanfasRow) {
//
// $targetDate = new DateTime($oZhuanfasRow->end_date);
// $interval = $today->diff($targetDate);
//
// if ($today > $targetDate) {
// $iDiffDay = -$interval->days;
// } else {
// $iDiffDay = $interval->days;
// }
//
// $oTgSendFormat->rowAdd(
// $oZhuanfasRow->name,
// $oZhuanfasRow->today_width,
// $oZhuanfasRow->use_width,
// $oZhuanfasRow->max_width,
// $iDiffDay
// );
//
// }
//
// $sTgReport = $oTgSendFormat->typeA();
//
// (new Telegram())->send(0, $sTgReport);
//
// //// 流量报告,直连
// $oTgSendFormat = new TgSendFormat();
// $oTgSendFormat->sTitleEmoji = "\n\n";
// $oTgSendFormat->sTitle = "# 直连流量";
//
// $oServers = Node::where('type', 2)
// ->where(function ($query) {
// $query->whereNull('zhuanfa_code')
// ->orWhereIn('zhuanfa_code', ['none', '']);
// })
// ->get();
//
// foreach ($oServers as $oServer) {
//// $oTgSendFormat->rowAdd(
//// $oServer->name,
////// $oServer->
//// );
// }
//
//
//
// // 流量报告,机器
//// $oTgSendFormat = new TgSendFormat();
//// $oTgSendFormat->sTitleEmoji = "\n\n";
//// $oTgSendFormat->sTitle = "# 机器流量";
////
//// $oDucksAll = $oDucks->orderBy('code')->get();
//// foreach ($oDucksAll as $oDucksRow) {
////
//// if ($oDucksRow->width_reset_day == 0) {
//// $iWidthResetDay = 0;
//// } if ($oDucksRow->width_reset_day > date('d')) {
//// $iWidthResetDay = $oDucksRow->width_reset_day - date('d');
//// } else {
//// $date = new DateTime();
//// $date->modify('first day of next month');
//// $date->setDate((int)$date->format('Y'), (int)$date->format('m'), $oDucksRow->width_reset_day);
//// $sEndDate = $date;
////
//// $currentDate = new DateTime();
//// $interval = $currentDate->diff($sEndDate);
//// $iWidthResetDay = $interval->days;
//// }
////
//// $oTgSendFormat->rowAdd(
//// $oDucksRow->code,
//// $oDucksRow->today_width,
//// $oDucksRow->use_width,
//// $oDucksRow->max_width,
//// $iWidthResetDay,
//// $oDucksRow->memo
//// );
////
//// }
////
//// $sTgReport = $oTgSendFormat->typeA();
////
//// (new Telegram())->send(0, $sTgReport);
//
// }
// public static function reportBandWidth_olddd(): void
// {
//
// $oZhuanfas = new Zhuanfas();
// $oDucks = new Ducks();
//
// // 流量报告,转发
// $oTgSendFormat = new TgSendFormat();
// $oTgSendFormat->sTitleEmoji = "\n\n";
// $oTgSendFormat->sTitle = "# 转发流量";
// $today = new DateTime();
//
// $oZhuanfasAll = $oZhuanfas->all();
// foreach ($oZhuanfasAll as $oZhuanfasRow) {
//
// $targetDate = new DateTime($oZhuanfasRow->end_date);
// $interval = $today->diff($targetDate);
//
// if ($today > $targetDate) {
// $iDiffDay = -$interval->days;
// } else {
// $iDiffDay = $interval->days;
// }
//
// $oTgSendFormat->rowAdd(
// $oZhuanfasRow->name,
// $oZhuanfasRow->today_width,
// $oZhuanfasRow->use_width,
// $oZhuanfasRow->max_width,
// $iDiffDay
// );
//
// }
//
// $sTgReport = $oTgSendFormat->typeA();
//
// (new Telegram())->send(0, $sTgReport);
//
// // 流量报告,机器
// $oTgSendFormat = new TgSendFormat();
// $oTgSendFormat->sTitleEmoji = "\n\n";
// $oTgSendFormat->sTitle = "# 机器流量";
//
// $oDucksAll = $oDucks->orderBy('code')->get();
// foreach ($oDucksAll as $oDucksRow) {
//
// if ($oDucksRow->width_reset_day == 0) {
// $iWidthResetDay = 0;
// } if ($oDucksRow->width_reset_day > date('d')) {
// $iWidthResetDay = $oDucksRow->width_reset_day - date('d');
// } else {
// $date = new DateTime();
// $date->modify('first day of next month');
// $date->setDate((int)$date->format('Y'), (int)$date->format('m'), $oDucksRow->width_reset_day);
// $sEndDate = $date;
//
// $currentDate = new DateTime();
// $interval = $currentDate->diff($sEndDate);
// $iWidthResetDay = $interval->days;
// }
//
// $oTgSendFormat->rowAdd(
// $oDucksRow->code,
// $oDucksRow->today_width,
// $oDucksRow->use_width,
// $oDucksRow->max_width,
// $iWidthResetDay,
// $oDucksRow->memo
// );
//
// }
//
// $sTgReport = $oTgSendFormat->typeA();
//
// (new Telegram())->send(0, $sTgReport);
//
// }
// 每日清空duck和转发的每日流量
public static function clearTodayWidth(): void
{
Ducks::query()->update(['today_width' => 0]);
Zhuanfas::query()->update(['today_width' => 0]);
}
// public static function clearTodayWidth(): void
// {
// Ducks::query()->update(['today_width' => 0]);
// Zhuanfas::query()->update(['today_width' => 0]);
// }
public static function reportBandWidth_back(): void
{
$oNode = new Node();
$oZhuanfas = new Zhuanfas();
$oDucks = new Ducks();
$oNodeAll = $oNode->all();
foreach ($oNodeAll as $oNodeRow) {
@ $iZhuanfaFlowToday[$oNodeRow->zhuanfa_code] += $oNodeRow->node_bandwidth;
@ $iDuckFlowToday[$oNodeRow->duck_code] += $oNodeRow->node_bandwidth;
$oZhuanfas->where('code', $oNodeRow->zhuanfa_code)->increment('use_width', $oNodeRow->node_bandwidth);
$oDucks->where('code', $oNodeRow->duck_code)->increment('use_width', $oNodeRow->node_bandwidth);
$oNode->where('id', $oNodeRow->id)->update(['node_bandwidth' => 0]);
}
// 流量报告,转发
$oTgSendFormat = new TgSendFormat();
$oTgSendFormat->sTitleEmoji = "⚡️⚡️⚡️⚡️⚡️⚡️";
$oTgSendFormat->sTitle = "# 转发流量";
$today = new DateTime();
$oZhuanfasAll = $oZhuanfas->all();
foreach ($oZhuanfasAll as $oZhuanfasRow) {
$targetDate = new DateTime($oZhuanfasRow->end_date);
$interval = $today->diff($targetDate);
$oTgSendFormat->rowAdd(
$oZhuanfasRow->name,
$iZhuanfaFlowToday[$oZhuanfasRow->code],
$oZhuanfasRow->use_width,
$oZhuanfasRow->max_width,
$interval->days
);
}
$sTgReport = $oTgSendFormat->typeA();
(new Telegram())->send(0, $sTgReport);
// 流量报告,机器
$oTgSendFormat = new TgSendFormat();
$oTgSendFormat->sTitleEmoji = "\n\n";
$oTgSendFormat->sTitle = "# 机器流量";
$oDucksAll = $oDucks->orderBy('code')->get();
foreach ($oDucksAll as $oDucksRow) {
if ($oDucksRow->width_reset_day == 0) {
$iWidthResetDay = 0;
} if ($oDucksRow->width_reset_day > date('d')) {
$iWidthResetDay = $oDucksRow->width_reset_day - date('d');
} else {
$date = new DateTime();
$date->modify('first day of next month');
$date->setDate((int)$date->format('Y'), (int)$date->format('m'), $oDucksRow->width_reset_day);
$sEndDate = $date;
$currentDate = new DateTime();
$interval = $currentDate->diff($sEndDate);
$iWidthResetDay = $interval->days;
}
$oTgSendFormat->rowAdd(
$oDucksRow->code,
$iDuckFlowToday[$oDucksRow->code] ?? 0,
$oDucksRow->use_width,
$oDucksRow->max_width,
$iWidthResetDay
);
}
$sTgReport = $oTgSendFormat->typeA();
(new Telegram())->send(0, $sTgReport);
}
// public static function reportBandWidth_back(): void
// {
// $oNode = new Node();
// $oZhuanfas = new Zhuanfas();
// $oDucks = new Ducks();
//
// $oNodeAll = $oNode->all();
//
// foreach ($oNodeAll as $oNodeRow) {
//
// @ $iZhuanfaFlowToday[$oNodeRow->zhuanfa_code] += $oNodeRow->node_bandwidth;
// @ $iDuckFlowToday[$oNodeRow->duck_code] += $oNodeRow->node_bandwidth;
//
// $oZhuanfas->where('code', $oNodeRow->zhuanfa_code)->increment('use_width', $oNodeRow->node_bandwidth);
// $oDucks->where('code', $oNodeRow->duck_code)->increment('use_width', $oNodeRow->node_bandwidth);
// $oNode->where('id', $oNodeRow->id)->update(['node_bandwidth' => 0]);
//
// }
//
//
// // 流量报告,转发
// $oTgSendFormat = new TgSendFormat();
// $oTgSendFormat->sTitleEmoji = "⚡️⚡️⚡️⚡️⚡️⚡️";
// $oTgSendFormat->sTitle = "# 转发流量";
// $today = new DateTime();
//
// $oZhuanfasAll = $oZhuanfas->all();
// foreach ($oZhuanfasAll as $oZhuanfasRow) {
//
// $targetDate = new DateTime($oZhuanfasRow->end_date);
// $interval = $today->diff($targetDate);
//
// $oTgSendFormat->rowAdd(
// $oZhuanfasRow->name,
// $iZhuanfaFlowToday[$oZhuanfasRow->code],
// $oZhuanfasRow->use_width,
// $oZhuanfasRow->max_width,
// $interval->days
// );
//
// }
//
// $sTgReport = $oTgSendFormat->typeA();
//
// (new Telegram())->send(0, $sTgReport);
//
// // 流量报告,机器
// $oTgSendFormat = new TgSendFormat();
// $oTgSendFormat->sTitleEmoji = "\n\n";
// $oTgSendFormat->sTitle = "# 机器流量";
//
// $oDucksAll = $oDucks->orderBy('code')->get();
// foreach ($oDucksAll as $oDucksRow) {
//
// if ($oDucksRow->width_reset_day == 0) {
// $iWidthResetDay = 0;
// } if ($oDucksRow->width_reset_day > date('d')) {
// $iWidthResetDay = $oDucksRow->width_reset_day - date('d');
// } else {
// $date = new DateTime();
// $date->modify('first day of next month');
// $date->setDate((int)$date->format('Y'), (int)$date->format('m'), $oDucksRow->width_reset_day);
// $sEndDate = $date;
//
// $currentDate = new DateTime();
// $interval = $currentDate->diff($sEndDate);
// $iWidthResetDay = $interval->days;
// }
//
// $oTgSendFormat->rowAdd(
// $oDucksRow->code,
// $iDuckFlowToday[$oDucksRow->code] ?? 0,
// $oDucksRow->use_width,
// $oDucksRow->max_width,
// $iWidthResetDay
// );
//
// }
//
// $sTgReport = $oTgSendFormat->typeA();
//
// (new Telegram())->send(0, $sTgReport);
//
// }
public static function todayOk()
{
(new Telegram())->send(0, "今日任务处理完成");
}
// 用户流量每日重置
public static function resetTodayBandwidth(): void

View File

@ -5,6 +5,8 @@ namespace App\Services\Tg\Hook\Mod;
use App\Models\Node as ModelNode;
use App\Services\Tg\Hook\Dog;
use App\Services\TomTool\Http;
use Illuminate\Support\Facades\DB;
use App\Utils\Tools;
class Node extends Base {
@ -34,7 +36,67 @@ class Node extends Base {
}
public function Clone($aParam)
public function fly()
{
$oServers = ModelNode::where("type", 2)->orderBy("order_group")->get();
//// 取出pwd
$aPwds = [];
foreach ($oServers as $oServer) {
$aChildPwds = ModelNode::where("pid", $oServer->id)->pluck("password")->toArray();
$aPwds[$oServer->id] = $aChildPwds;
}
//// 清空旧node
ModelNode::where("type", 1)->delete();
//// new分身
$aNodes = [];
foreach ($oServers as $oServer) {
for ($i=0; $i<$oServer->fly; $i++) {
$oNode = $oServer->replicate();
$oNode->pid = $oServer->id;
$aNodes[$oServer->order_group][] = $oNode;
}
}
//// 打乱、命名、落库
$aNodeNameCodeCount = [];
$iDone = 0;
$iNodeId = 1001;
foreach ($aNodes as $iOrderGroup => $aNodeOrderGroups) {
shuffle($aNodeOrderGroups);
foreach ($aNodeOrderGroups as $oNode) {
if (preg_match('/\$([^\$]+)\$/', $oNode->name, $aMatches)) {
$sNodeNameCode = $aMatches[1];
} else {
continue;
}
if (!isset($aNodeNameCodeCount[$sNodeNameCode])) {
$aNodeNameCodeCount[$sNodeNameCode] = 1;
}
$iNodeNum = $aNodeNameCodeCount[$sNodeNameCode]++;
$iNodeNum = sprintf("%02d", $iNodeNum);
$oNode->id = $iNodeId;
$oNode->name = preg_replace('/\$.*?\$/', $iNodeNum, $oNode->name);
$oNode->type = 1;
$oNode->node_bandwidth = 0;
$oNode->node_bandwidth_limit = 0;
$oNode->bandwidthlimit_resetday = 0;
$oNode->is_shadow = 0;
$oNode->password = array_pop($aPwds[$oNode->pid]) ?? Tools::genRandomChar(32);
$iDone += $oNode->save();
$iNodeId++;
}
}
return "搞定,生成".$iDone."节点";
}
public function clone($aParam)
{
// list(, $iNodeId) = explode(" ", $sText, 2);

View File

@ -168,6 +168,17 @@ final class Test extends Base
}
public function nodeReport()
{
$jobs = new Cron();
$jobs->zhuanfa_width_merge(); // 合并转发耗流统计要在node计算之前
$jobs->day_width_report_zhuanfa(); // 汇报每天耗流 - 转发
// $jobs->hour_width_report(); // 检测小时耗流
$jobs->day_width_report(); // 汇报每天耗流
$jobs->resetZhuanfaBandwidth(); // zhuanfa流量自动重置
$jobs->resetNodeBandwidth(); // 要在最后,其他计算完再重置
}
public function badian()
{
$jobs = new Cron();

View File

@ -58,7 +58,7 @@ final class TgSendFormat
$sFlowMix .= ",余".$iMaxWidth - $iUseWidth."g";
}
if ($iMaxWidth != 0) {
if ($iMaxWidth != 0 && $iLimitDay !== false) {
$sFlowMix .= ",置".$iLimitDay."d";
}