Compare commits

...

2 Commits

  1. 2
      .gitignore
  2. 46
      app/admin/controller/Admin.php
  3. 22
      app/admin/controller/Index.php
  4. 8
      app/admin/route/app.php
  5. 338
      app/admin/service/AdminService.php
  6. 80
      app/admin/service/ExportService.php
  7. 11
      app/admin/service/FlowService.php
  8. 1
      app/admin/service/RechargeService.php
  9. 5
      app/admin/service/VideoService.php
  10. 6
      app/admin/service/setting/BlockStockService.php
  11. 43
      app/admin/service/setting/IPOService.php
  12. 57
      app/command/ApiLogCommand.php
  13. 14
      app/home/controller/User.php
  14. 3
      app/home/lang/zh-cn.php
  15. 3
      app/home/lang/zh-jp.php
  16. 3
      app/home/lang/zh-us.php
  17. 76
      app/home/middleware/ApiLogMiddleware.php
  18. 47
      app/home/middleware/CheckUserMiddleware.php
  19. 16
      app/home/route/app.php
  20. 13
      app/home/service/BaseHomeService.php
  21. 25
      app/home/service/LoginService.php
  22. 142
      app/home/service/UserService.php
  23. 9
      app/model/ApiLogModel.php
  24. 79
      app/model/ForexListMode.php
  25. 7
      app/model/UserAccessLogModel.php
  26. 7
      app/model/VipCodeModel.php
  27. 8
      app/model/WatchVideoLogModel.php
  28. 18
      app/utility/UnqId.php
  29. 9
      composer.json
  30. 1
      config/console.php

2
.gitignore

@ -1,6 +1,6 @@
/.idea /.idea
/.vscode /.vscode
#/vendor/ /vendor/
/runtime/ /runtime/
*.log *.log
.env .env

46
app/admin/controller/Admin.php

@ -1,4 +1,5 @@
<?php <?php
namespace app\admin\controller; namespace app\admin\controller;
use app\admin\service\AdminService; use app\admin\service\AdminService;
@ -49,24 +50,28 @@ class Admin extends AdminBaseController
return json($returnData); return json($returnData);
} }
//编辑账号 //编辑账号
public function updateAccount(){ public function updateAccount()
{
$returnData = (new AdminService())->updateAccount($this->request->param('id'), $this->request->param()); $returnData = (new AdminService())->updateAccount($this->request->param('id'), $this->request->param());
return json($returnData); return json($returnData);
} }
//更新账号状态 //更新账号状态
public function updateAccountStauts(){ public function updateAccountStauts()
{
$returnData = (new AdminService())->updateAccountStauts($this->request->param('id'), $this->request->param()); $returnData = (new AdminService())->updateAccountStauts($this->request->param('id'), $this->request->param());
return json($returnData); return json($returnData);
} }
//删除指定用户 //删除指定用户
public function del(){ public function del()
{
$returnData = (new AdminService())->del($this->request->param('id')); $returnData = (new AdminService())->del($this->request->param('id'));
return json($returnData); return json($returnData);
} }
//获取用户权限代码 //获取用户权限代码
public function getPermCode(){ public function getPermCode()
{
$returnData = (new AdminService())->getPermCode($this->request->user_id); $returnData = (new AdminService())->getPermCode($this->request->user_id);
return json($returnData); return json($returnData);
} }
@ -85,7 +90,8 @@ class Admin extends AdminBaseController
return json($returnData); return json($returnData);
} }
public function inviteCode(){ public function inviteCode()
{
$returnData = (new AdminService())->inviteCode(); $returnData = (new AdminService())->inviteCode();
return json($returnData); return json($returnData);
} }
@ -133,7 +139,21 @@ class Admin extends AdminBaseController
$returnData = (new AdminService())->getUserAccessLog($this->request->user_id, $this->request->param()); $returnData = (new AdminService())->getUserAccessLog($this->request->user_id, $this->request->param());
return json($returnData); return json($returnData);
} }
public function getUserAccessLogSummary()
{
$returnData = (new AdminService())->getUserAccessLogSummary($this->request->user_id, $this->request->param());
return json($returnData);
}
public function getVisitorAccessLog()
{
$returnData = (new AdminService())->getVisitorAccessLog($this->request->user_id, $this->request->param());
return json($returnData);
}
public function getVisitorAccessLogSummary()
{
$returnData = (new AdminService())->getVisitorAccessLogSummary($this->request->user_id, $this->request->param());
return json($returnData);
}
// 获取admin的操作记录 // 获取admin的操作记录
public function getAdminOperationLog() public function getAdminOperationLog()
{ {
@ -155,6 +175,20 @@ class Admin extends AdminBaseController
return json($returnData); return json($returnData);
} }
// 生成vip兑换码
public function generateVipCode()
{
$returnData = (new AdminService())->generateVipCode($this->request->param());
return json($returnData);
}
// 获取vip兑换码列表
public function getVipCode()
{
$returnData = (new AdminService())->getVipCode($this->request->param());
return json($returnData);
}
// 单次发送邮件或短信消息 // 单次发送邮件或短信消息
public function sendEmailOrSms() public function sendEmailOrSms()
{ {

22
app/admin/controller/Index.php

@ -35,6 +35,7 @@ use app\model\StockSgdListModel;
use app\model\StockThaListModel; use app\model\StockThaListModel;
use app\model\StockThaTradeModel; use app\model\StockThaTradeModel;
use app\model\StockTradeModel; use app\model\StockTradeModel;
use app\model\UserAccessLogModel;
use app\model\UserModel; use app\model\UserModel;
use app\model\UserVerifyLogModel; use app\model\UserVerifyLogModel;
use app\model\UserWithdrawalModel; use app\model\UserWithdrawalModel;
@ -198,8 +199,6 @@ class Index extends AdminBaseController
$todayRechargeAmount = Db::table($rechargeApplyTableName) $todayRechargeAmount = Db::table($rechargeApplyTableName)
->whereTime('create_time', 'between', [$today, $tomorrow])->where($whereInUser) ->whereTime('create_time', 'between', [$today, $tomorrow])->where($whereInUser)
->where('status', 1)->sum('recharge_num'); ->where('status', 1)->sum('recharge_num');
$todayRechargeAmountGroup = Db::table($rechargeApplyTableName)->whereTime('create_time', 'between', [$today, $tomorrow])->where($whereInUser)
->where('status', 1)->field('account_type, SUM(recharge_num) AS recharge_num')->group('recharge_num')->select();
// 今日提款金额 完成状态 // 今日提款金额 完成状态
$todayWithdrawAmount = Db::table($userWithdrawTableName) $todayWithdrawAmount = Db::table($userWithdrawTableName)
@ -215,6 +214,14 @@ class Index extends AdminBaseController
$approvedRealName = UserVerifyLogModel::where('status', 2)->where($whereInUser)->count(); // 审核通过实名认证用户数 $approvedRealName = UserVerifyLogModel::where('status', 2)->where($whereInUser)->count(); // 审核通过实名认证用户数
$failedRealName = UserVerifyLogModel::where('status', 3)->where($whereInUser)->count(); // 审核失败实名认证用户数 $failedRealName = UserVerifyLogModel::where('status', 3)->where($whereInUser)->count(); // 审核失败实名认证用户数
$todayIpVisit = UserAccessLogModel::where('user_id', null)
->whereTime('created_at', 'today')
->group('ip')
->count(); // 今日IP访问统计
$totalIpVisit = UserAccessLogModel::where('user_id', null)
->group('ip')
->count(); // 总IP访问统计
$data = [ $data = [
'todayRegisterNum' => $todayRegisterNum, // 今日注册用户 'todayRegisterNum' => $todayRegisterNum, // 今日注册用户
'totalRegisterNum' => $totalRegisterNum, // 总注册人数 'totalRegisterNum' => $totalRegisterNum, // 总注册人数
@ -229,7 +236,6 @@ class Index extends AdminBaseController
'totalWithdrawalNum' => $totalWithdrawalNum, // 总提现用户 'totalWithdrawalNum' => $totalWithdrawalNum, // 总提现用户
'todayRechargeAmount' => $todayRechargeAmount, // 今日充值金额 'todayRechargeAmount' => $todayRechargeAmount, // 今日充值金额
'todayRechargeAmountGroup' => $todayRechargeAmountGroup, // 今日充值金额 - 按充值类型分组统计
'totalRechargeAmount' => $totalRechargeAmount, // 总充值金额 'totalRechargeAmount' => $totalRechargeAmount, // 总充值金额
'todayWithdrawAmount' => $todayWithdrawAmount, // 今日提款金额 'todayWithdrawAmount' => $todayWithdrawAmount, // 今日提款金额
@ -241,6 +247,10 @@ class Index extends AdminBaseController
'awaiting_real_name' => $awaitingRealName, // 等待实名审核用户数 'awaiting_real_name' => $awaitingRealName, // 等待实名审核用户数
'approved_real_name' => $approvedRealName, // 实名审核通过用户数 'approved_real_name' => $approvedRealName, // 实名审核通过用户数
'failed_real_name' => $failedRealName, // 实名审核失败用户数 'failed_real_name' => $failedRealName, // 实名审核失败用户数
//ip游客访问统计
'todayIpVisit' => $todayIpVisit, // 今日IP访问统计
'totalIpVisit' => $totalIpVisit, // 总IP访问统计
]; ];
return json(['code' => '0', 'message' => 'SUCCESS', 'data' => $data]); return json(['code' => '0', 'message' => 'SUCCESS', 'data' => $data]);
@ -1084,7 +1094,8 @@ class Index extends AdminBaseController
return json(['msg' => $exception->getMessage()]); return json(['msg' => $exception->getMessage()]);
} }
} }
public function cacheForex(){ public function cacheForex()
{
$redis = (new AdminBaseService())->getRedis(); $redis = (new AdminBaseService())->getRedis();
// 缓存外汇 // 缓存外汇
$contractList = ForexListModel::where('status', '=', '1')->select(); $contractList = ForexListModel::where('status', '=', '1')->select();
@ -1261,8 +1272,6 @@ class Index extends AdminBaseController
// 提交事务 // 提交事务
Db::commit(); Db::commit();
} }
return json($result); return json($result);
} }
@ -1298,5 +1307,4 @@ class Index extends AdminBaseController
return json([$exception->getMessage()]); return json([$exception->getMessage()]);
} }
} }
} }

8
app/admin/route/app.php

@ -247,6 +247,8 @@ Route::group('/', function () {
// 送会员 // 送会员
Route::post('admin/give_vip', 'Admin/giveVip')->middleware('admin_log'); //赠送用户vip Route::post('admin/give_vip', 'Admin/giveVip')->middleware('admin_log'); //赠送用户vip
Route::post('admin/buy_vip_log', 'Admin/buyVipLog')->middleware('admin_log'); //用户购买VIP记录 Route::post('admin/buy_vip_log', 'Admin/buyVipLog')->middleware('admin_log'); //用户购买VIP记录
Route::post('admin/generate_vip_code', 'Admin/generateVipCode')->middleware('admin_log'); //生成vip兑换码
Route::post('admin/get_vip_code', 'Admin/getVipCode')->middleware('admin_log'); //获取vip兑换码列表
// 配置管理 // 配置管理
// 外汇插针行情 // 外汇插针行情
@ -655,7 +657,10 @@ Route::group('/', function () {
Route::post('account/translator_bind_customer_list', 'Admin/translatorBindCustomerList')->middleware('admin_log'); // 翻译员绑定的客服列表 Route::post('account/translator_bind_customer_list', 'Admin/translatorBindCustomerList')->middleware('admin_log'); // 翻译员绑定的客服列表
Route::post('account/group_leader_with_user', 'Admin/groupLeaderWithUser'); // 组长与用户添加chat好友 Route::post('account/group_leader_with_user', 'Admin/groupLeaderWithUser'); // 组长与用户添加chat好友
Route::post('account/seller_with_user', 'Admin/sellerWithUser'); // 电销与用户添加chat好友 Route::post('account/seller_with_user', 'Admin/sellerWithUser'); // 电销与用户添加chat好友
Route::post('admin/get_user_access_log', 'Admin/getUserAccessLog'); //获取用户访问页面的记录 Route::any('admin/get_user_access_log', 'Admin/getUserAccessLog'); //获取用户访问页面的记录
Route::post('admin/get_user_access_log_summary', 'Admin/getUserAccessLogSummary'); //获取用户访问页面的记录
Route::any('admin/get_visitor_access_log', 'Admin/getVisitorAccessLog'); //获取游客访问页面的记录
Route::post('admin/get_visitor_access_log_summary', 'Admin/getVisitorAccessLogSummary'); //获取用户访问页面的记录
Route::post('admin/get_admin_operation_log', 'Admin/getAdminOperationLog'); //获取管理员admin的操作记录 Route::post('admin/get_admin_operation_log', 'Admin/getAdminOperationLog'); //获取管理员admin的操作记录
//权限菜单 //权限菜单
@ -738,4 +743,3 @@ Route::get('/setting/in_option_refresh', 'setting.Option/refresh');
// 修改 印度股-source // 修改 印度股-source
Route::post('/update_source', 'Index/updateSource'); Route::post('/update_source', 'Index/updateSource');

338
app/admin/service/AdminService.php

@ -17,6 +17,8 @@ use app\model\UserAccessLogModel;
use app\model\UserChatGroupModel; use app\model\UserChatGroupModel;
use app\model\UserChatLinkModel; use app\model\UserChatLinkModel;
use app\model\UserModel; use app\model\UserModel;
use app\model\VipCodeModel;
use itinysun\model\helper\Service;
use think\facade\Cache; use think\facade\Cache;
use think\exception\ValidateException; use think\exception\ValidateException;
use app\utility\UnqId; use app\utility\UnqId;
@ -113,7 +115,6 @@ class AdminService extends AdminBaseService
} catch (\Exception $exception) { } catch (\Exception $exception) {
return $this->toData('100500', '系统繁忙.', [$exception->getMessage()]); return $this->toData('100500', '系统繁忙.', [$exception->getMessage()]);
} }
} }
/** /**
@ -232,7 +233,6 @@ class AdminService extends AdminBaseService
} catch (\Exception $exception) { } catch (\Exception $exception) {
return $this->toData('200500', 'The system is busy.', [$exception->getMessage()]); return $this->toData('200500', 'The system is busy.', [$exception->getMessage()]);
} }
} }
/** /**
@ -273,7 +273,6 @@ class AdminService extends AdminBaseService
} catch (\Exception $exception) { } catch (\Exception $exception) {
return $this->toData('200500', 'The system is busy.', [$exception->getMessage()]); return $this->toData('200500', 'The system is busy.', [$exception->getMessage()]);
} }
} }
public function updateAccountStauts($accountId, $param): array public function updateAccountStauts($accountId, $param): array
@ -300,7 +299,6 @@ class AdminService extends AdminBaseService
} catch (\Exception $exception) { } catch (\Exception $exception) {
return $this->toData('200500', 'The system is busy.', [$exception->getMessage()]); return $this->toData('200500', 'The system is busy.', [$exception->getMessage()]);
} }
} }
@ -336,7 +334,6 @@ class AdminService extends AdminBaseService
} catch (\Exception $exception) { } catch (\Exception $exception) {
return $this->toData('200500', 'The system is busy.', [$exception->getMessage()]); return $this->toData('200500', 'The system is busy.', [$exception->getMessage()]);
} }
} }
public function del($id): array public function del($id): array
@ -352,7 +349,6 @@ class AdminService extends AdminBaseService
} catch (\Exception $exception) { } catch (\Exception $exception) {
return $this->toData('200500', 'The system is busy.', [$exception->getMessage()]); return $this->toData('200500', 'The system is busy.', [$exception->getMessage()]);
} }
} }
/** /**
@ -404,7 +400,6 @@ class AdminService extends AdminBaseService
} catch (\Exception $exception) { } catch (\Exception $exception) {
return $this->toData('200500', 'The system is busy.', [$exception->getMessage()]); return $this->toData('200500', 'The system is busy.', [$exception->getMessage()]);
} }
} }
public function logList($param) public function logList($param)
@ -442,7 +437,6 @@ class AdminService extends AdminBaseService
$inviteCode = (new BaseHomeService())->getUniqInviteCode(); $inviteCode = (new BaseHomeService())->getUniqInviteCode();
AdminModel::where('id', $v->id)->update(['invite_code' => $inviteCode]); AdminModel::where('id', $v->id)->update(['invite_code' => $inviteCode]);
} }
} catch (\Exception $exception) { } catch (\Exception $exception) {
return $this->toData('500', 'The system is busy.', [$exception->getMessage(), $exception->getTrace()]); return $this->toData('500', 'The system is busy.', [$exception->getMessage(), $exception->getTrace()]);
} }
@ -665,6 +659,118 @@ class AdminService extends AdminBaseService
} }
} }
// 用户访问页面的记录汇总
public function getUserAccessLogSummary($adminId, $param)
{
try {
if (empty($param['page']) || empty($param['limit'])) {
return $this->toData('400', '缺少分页参数');
}
// 获取账号信息
$account = AdminModel::where('id', $adminId)->find();
if (empty($account)) {
return $this->toData('400', '当前账号数据为空');
}
// 获取账号角色信息
$role = AuthRoleModel::where(['id' => $account->role_id])->find();
if (empty($role)) {
return $this->toData('400', '当前账号分配的角色数据为空');
}
// 构建可查看的用户ID筛选条件
$whereUser = [
['ual.user_id', '>', 0]
];
switch ($role->name) {
case AuthRoleModel::NAME_ADMIN:
if (!empty($param['user_id'])) {
$whereUser[] = ['user_id', '=', $param['user_id']];
}
break;
case AuthRoleModel::NAME_AGENT:
$userIds = UserModel::where('agent_id', $adminId)->column('user_id');
if (!empty($param['user_id']) && in_array($param['user_id'], $userIds)) {
$whereUser[] = ['ual.user_id', '=', $param['user_id']];
} else {
$whereUser[] = ['ual.user_id', 'in', $userIds];
}
break;
case AuthRoleModel::NAME_DIRECTOR:
$teamHeaders = AdminModel::where('parent_id', $adminId)->column('id');
$userIds = [];
if (!empty($teamHeaders)) {
$customer = AdminModel::whereIn('parent_id', $teamHeaders)->column('id');
if (!empty($customer)) {
$userIds = UserModel::whereIn('customer_id', $customer)->column('user_id');
}
}
if (!empty($param['user_id']) && in_array($param['user_id'], $userIds)) {
$whereUser[] = ['ual.user_id', '=', $param['user_id']];
} else {
$whereUser[] = ['ual.user_id', 'in', $userIds];
}
break;
case AuthRoleModel::NAME_TEAM_HEADER:
$customer = AdminModel::where('parent_id', $adminId)->column('id');
$userIds = [];
if (!empty($customer)) {
$userIds = UserModel::whereIn('customer_id', $customer)->column('user_id');
}
if (!empty($param['user_id']) && in_array($param['user_id'], $userIds)) {
$whereUser[] = ['ual.user_id', '=', $param['user_id']];
} else {
$whereUser[] = ['ual.user_id', 'in', $userIds];
}
break;
case AuthRoleModel::NAME_CUSTOMER:
$userIds = UserModel::where(['customer_id' => $adminId])->column('user_id');
if (!empty($param['user_id']) && in_array($param['user_id'], $userIds)) {
$whereUser[] = ['ual.user_id', '=', $param['user_id']];
} else {
$whereUser[] = ['ual.user_id', 'in', $userIds];
}
break;
default:
return $this->toData('500', '普通角色没有关联用户账号,不能查看用户数');
}
// 组装主查询条件
$where = [];
if (!empty($param['module'])) {
$where[] = ['module', '=', $param['module']];
}
if (!empty($param['ip'])) {
$where['ip'] = $param['ip'];
}
// 构建查询(按 user_id 分组统计访问次数)
$query = Db::name('user_access_log')
->alias('ual')
->field('ual.user_id, u.user_no, COUNT(*) as access_count, MAX(ual.created_at) as created_at')
->join('users u', 'ual.user_id = u.user_id', 'LEFT')
->where($where)
->where($whereUser)
->group('ual.user_id')
->order('access_count', 'desc');
$list = $query->paginate([
'list_rows' => $param['limit'],
'page' => $param['page'],
]);
return $this->toData('0', 'SUCCESS', [
'list' => $list->items(),
'page' => $list->currentPage(),
'total' => $list->total(),
'last_page' => $list->lastPage(),
]);
} catch (\Exception $exception) {
return $this->toData('500', 'The system is busy.', [$exception->getMessage(), $exception->getTrace()]);
}
}
// 用户访问页面的记录 // 用户访问页面的记录
public function getUserAccessLog($adminId, $param) public function getUserAccessLog($adminId, $param)
{ {
@ -683,7 +789,9 @@ class AdminService extends AdminBaseService
return $this->toData('400', '当前账号分配的角色数据为空'); return $this->toData('400', '当前账号分配的角色数据为空');
} }
// 根据账号角色限制数据查看范围, 超级管理员可以查看所有用户数据,代理可以查看自己所属用户的数据,总监、组长以此类推 // 根据账号角色限制数据查看范围, 超级管理员可以查看所有用户数据,代理可以查看自己所属用户的数据,总监、组长以此类推
$whereUser = []; $whereUser = [
['user_id', '>', 0]
];
switch ($role->name) { switch ($role->name) {
case AuthRoleModel::NAME_ADMIN: // 超级管理员可以查看所有数据 case AuthRoleModel::NAME_ADMIN: // 超级管理员可以查看所有数据
if (!empty($param['user_id'])) { if (!empty($param['user_id'])) {
@ -741,6 +849,98 @@ class AdminService extends AdminBaseService
if (!empty($param['module'])) { if (!empty($param['module'])) {
$where['module'] = $param['module']; $where['module'] = $param['module'];
} }
if (!empty($param['ip'])) {
$where['ip'] = $param['ip'];
}
if (!empty($param['start_time']) && !empty($param['end_time'])) {
$whereUser[] = ['created_at', 'between time', [$param['start_time'], $param['end_time']]];
}
if ($param['export'] ?? false) {
//太多了 只取10000条
$list = UserAccessLogModel::with(['user'])->where($where)->where($whereUser)->order('id', 'desc')->limit(10000)->select();
$exportData = [['ID', '用户id', '用户编号', '访问时间', 'IP地址', '访问页面', '模块', '备注']];
foreach ($list as $item) {
$exportData[] = [$item->id, $item->user_id, $item->user->user_no ?? '', $item->created_at, $item->ip, $item->page_url, $item->module, $item->remark];
}
return ExportService::exportCsv($exportData, '用户浏览信息导出.csv');
} else {
$list = UserAccessLogModel::with(['user'])->where($where)->where($whereUser)->order('id', 'desc')->paginate([
'list_rows' => $param['limit'],
'page' => $param['page'],
]);
foreach ($list->items() as $item) {
$data[] = [
'id' => $item->id,
'user_id' => $item->user_id,
'created_at' => $item->created_at,
'ip' => $item->ip,
'page_url' => $item->page_url,
'module' => $item->module,
'remark' => $item->remark,
'updated_at' => $item->updated_at,
// 关联字段
'user_no' => $item->user->user_no ?? '',
];
}
return $this->toData('0', 'SUCCESS', [
'list' => $data,
'page' => $list->currentPage(),
'total' => $list->total(),
'last_page' => $list->lastPage(),
]);
}
} catch (\Exception $exception) {
return $this->toData('500', 'The system is busy.', [$exception->getMessage(), $exception->getTrace()]);
}
}
// 游客访问页面的记录
public function getVisitorAccessLog($adminId, $param)
{
try {
if (empty($param['page']) || empty($param['limit'])) {
return $this->toData('400', '缺少分页参数');
}
// 获取账号信息
$account = AdminModel::where('id', $adminId)->find();
if (empty($account)) {
return $this->toData('400', '当前账号数据为空');
}
// 获取账号角色信息
$role = AuthRoleModel::where(['id' => $account->role_id])->find();
if (empty($role)) {
return $this->toData('400', '当前账号分配的角色数据为空');
}
// 根据账号角色限制数据查看范围, 超级管理员可以查看所有用户数据,代理可以查看自己所属用户的数据,总监、组长以此类推
$whereUser = [
['user_id', '=', null]
];
$where = [];
if (!empty($param['module'])) {
$where['module'] = $param['module'];
}
if (!empty($param['ip'])) {
$where['ip'] = $param['ip'];
}
if (!empty($param['start_time']) && !empty($param['end_time'])) {
$whereUser[] = ['created_at', 'between time', [$param['start_time'], $param['end_time']]];
}
if ($param['export'] ?? false) {
//太多了 只取10000条
$list = UserAccessLogModel::where($where)->where($whereUser)->order('id', 'desc')->limit(10000)->select();
$exportData = [['ID', '访问时间', 'IP地址', '访问页面', '模块', '备注']];
foreach ($list as $item) {
$exportData[] = [$item->id, $item->created_at, $item->ip, $item->page_url, $item->module, $item->remark];
}
return ExportService::exportCsv($exportData, '访客浏览信息导出.csv');
} else {
$list = UserAccessLogModel::where($where)->where($whereUser)->order('id', 'desc')->paginate([ $list = UserAccessLogModel::where($where)->where($whereUser)->order('id', 'desc')->paginate([
'list_rows' => $param['limit'], 'list_rows' => $param['limit'],
'page' => $param['page'], 'page' => $param['page'],
@ -751,11 +951,71 @@ class AdminService extends AdminBaseService
'total' => $list->total(), 'total' => $list->total(),
'last_page' => $list->lastPage(), 'last_page' => $list->lastPage(),
]); ]);
}
} catch (\Exception $exception) { } catch (\Exception $exception) {
return $this->toData('500', 'The system is busy.', [$exception->getMessage(), $exception->getTrace()]); return $this->toData('500', 'The system is busy.', [$exception->getMessage(), $exception->getTrace()]);
} }
} }
// 访问页面的记录汇总
public function getVisitorAccessLogSummary($adminId, $param)
{
try {
if (empty($param['page']) || empty($param['limit'])) {
return $this->toData('400', '缺少分页参数');
}
// 获取账号信息
$account = AdminModel::where('id', $adminId)->find();
if (empty($account)) {
return $this->toData('400', '当前账号数据为空');
}
// 获取账号角色信息
$role = AuthRoleModel::where(['id' => $account->role_id])->find();
if (empty($role)) {
return $this->toData('400', '当前账号分配的角色数据为空');
}
// 构建可查看的用户ID筛选条件
$whereUser = [
['ual.user_id', '=', null],
];
// 组装主查询条件
$where = [];
if (!empty($param['module'])) {
$where[] = ['module', '=', $param['module']];
}
if (!empty($param['ip'])) {
$where[] = ['ip', '=', $param['ip']];
}
// 构建查询(按 user_id 分组统计访问次数)
$query = Db::name('user_access_log')
->alias('ual')
// ->field('user_id, COUNT(*) as access_count, MAX(create_time) as last_visit_time')
->field('ip,COUNT(*) as access_count, MAX(ual.created_at) as created_at')
->where($where)
->where($whereUser)
->group('ip')
->order('access_count', 'desc');
$list = $query->paginate([
'list_rows' => $param['limit'],
'page' => $param['page'],
]);
return $this->toData('0', 'SUCCESS', [
'list' => $list->items(),
'page' => $list->currentPage(),
'total' => $list->total(),
'last_page' => $list->lastPage(),
]);
} catch (\Exception $exception) {
return $this->toData('500', 'The system is busy.', [$exception->getMessage(), $exception->getTrace()]);
}
}
public function getAdminOperationLog($adminId, $param) public function getAdminOperationLog($adminId, $param)
{ {
try { try {
@ -926,6 +1186,65 @@ class AdminService extends AdminBaseService
} }
} }
// 生成vip兑换码
public function generateVipCode($param)
{
try {
if (!isset($param['day']) || $param['day'] <= 0) {
return $this->toData('400', lang('parameter_error'));
}
// 一次性生成10个兑换码
$resArr = [];
for ($i = 1; $i <= 10; $i++) {
$code = (new UnqId())->generateRandomCode(15);
$exists = VipCodeModel::where(['vip_code' => $code])->find();
if (!empty($exists) && $exists->vip_code == $code) {
for ($j = 1; $j <= 5; $j++) { // 如果存在相同code,本轮再试5次
$code = (new UnqId())->generateRandomCode(15);
$exists = VipCodeModel::where(['vip_code' => $code])->find();
if (empty($exists)) {
VipCodeModel::create(['vip_code' => $code, 'day' => $param['day'], 'status' => 0, 'uid' => 0]);
$resArr[] = $code;
break;
}
}
} else {
VipCodeModel::create(['vip_code' => $code, 'day' => $param['day'], 'status' => 0, 'uid' => 0]);
$resArr[] = $code;
}
}
return $this->toData('0', 'successful', [$resArr]);
} catch (\Exception $e) {
return $this->toData('500', 'The system is busy.', [$e->getMessage(), $e->getTrace()]);
}
}
public function getVipCode($param)
{
try {
if (!isset($param['page']) || !isset($param['limit'])) {
return $this->toData('400', lang('parameter_error'));
}
$where = [];
if (isset($param['status'])) {
$where['status'] = $param['status'];
}
$list = VipCodeModel::where($where)->order('id', 'desc')->paginate([
'list_rows' => $param['limit'],
'page' => $param['page'],
]);
return $this->toData('0', 'SUCCESS', [
'list' => $list->items(),
'page' => $list->currentPage(),
'total' => $list->total(),
'last_page' => $list->lastPage(),
]);
} catch (\Exception $e) {
return $this->toData('500', 'The system is busy.', [$e->getMessage(), $e->getTrace()]);
}
}
// 单次发送邮件或短信 // 单次发送邮件或短信
public function sendEmailOrSms($param) public function sendEmailOrSms($param)
{ {
@ -1050,5 +1369,4 @@ class AdminService extends AdminBaseService
return $this->toData('500', 'The system is busy', [$e->getMessage(), $e->getTrace()]); return $this->toData('500', 'The system is busy', [$e->getMessage(), $e->getTrace()]);
} }
} }
} }

80
app/admin/service/ExportService.php

@ -0,0 +1,80 @@
<?php
namespace app\admin\service;
use PhpOffice\PhpSpreadsheet\Spreadsheet;
use PhpOffice\PhpSpreadsheet\Writer\Xlsx;
class ExportService extends AdminBaseService
{
/**
* 导出 Excel
* @param array $data 二维数组(含表头)
* @param string $filename 导出文件名
*/
public static function exportExcel(array $data, string $filename = '')
{
if (empty($data)) {
throw new \Exception('导出数据不能为空');
}
$filename = $filename ?: '导出_' . date('Ymd_His') . '.xlsx';
$spreadsheet = new Spreadsheet();
$sheet = $spreadsheet->getActiveSheet();
// 列号转字母函数
$colIndexToLetter = function ($index) {
$letters = '';
while ($index >= 0) {
$letters = chr($index % 26 + 65) . $letters;
$index = intval($index / 26) - 1;
}
return $letters;
};
// 写入数据
foreach ($data as $rowIndex => $row) {
foreach ($row as $colIndex => $value) {
$cell = $colIndexToLetter($colIndex) . ($rowIndex + 1); // 例如 A1, B1...
$sheet->setCellValue($cell, $value);
}
}
// 输出到浏览器
header('Content-Type: application/vnd.openxmlformats-officedocument.spreadsheetml.sheet');
header("Content-Disposition: attachment; filename=\"{$filename}\"");
header('Cache-Control: max-age=0');
$writer = new Xlsx($spreadsheet);
$writer->save('php://output');
exit;
}
/**
* 导出 CSV
* @param array $data 二维数组(含表头)
* @param string $filename 导出文件名
*/
public static function exportCsv(array $data, string $filename = '')
{
if (empty($data)) {
throw new \Exception('导出数据不能为空');
}
$filename = $filename ?: '导出_' . date('Ymd_His') . '.csv';
header('Content-Type: text/csv');
header("Content-Disposition: attachment; filename={$filename}");
$fp = fopen('php://output', 'w');
fwrite($fp, chr(0xEF) . chr(0xBB) . chr(0xBF)); // 防止中文乱码
foreach ($data as $row) {
fputcsv($fp, $row);
}
fclose($fp);
exit;
}
}

11
app/admin/service/FlowService.php

@ -89,7 +89,6 @@ class FlowService extends AdminBaseService
} }
return $this->toData('0', 'SUCCESS', ['total' => $total, 'list' => $rows, 'extend' => (new BaseHomeService())->getCapitalTypeList($changeTypeArr)]); return $this->toData('0', 'SUCCESS', ['total' => $total, 'list' => $rows, 'extend' => (new BaseHomeService())->getCapitalTypeList($changeTypeArr)]);
} catch (ValidateException $validateException) { } catch (ValidateException $validateException) {
// 参数校验失败 // 参数校验失败
$message = $validateException->getError(); $message = $validateException->getError();
@ -157,7 +156,6 @@ class FlowService extends AdminBaseService
} }
return $this->toData('0', 'SUCCESS', ['total' => $total, 'list' => $rows, 'extend' => (new BaseHomeService())->getCapitalTypeList($changeTypeArr)]); return $this->toData('0', 'SUCCESS', ['total' => $total, 'list' => $rows, 'extend' => (new BaseHomeService())->getCapitalTypeList($changeTypeArr)]);
} catch (ValidateException $validateException) { } catch (ValidateException $validateException) {
// 参数校验失败 // 参数校验失败
$message = $validateException->getError(); $message = $validateException->getError();
@ -224,9 +222,7 @@ class FlowService extends AdminBaseService
$rows[$key]['user_no'] = $userNoArr[$item['user_id']] ?? '-'; // 用户号 $rows[$key]['user_no'] = $userNoArr[$item['user_id']] ?? '-'; // 用户号
} }
} }
return $this->toData('0', 'SUCCESS', ['total' => $total, 'list' => $rows, 'extend' => (new BaseHomeService())->getCapitalTypeList($changeTypeArr)]); return $this->toData('0', 'SUCCESS', ['total' => $total, 'list' => $rows, 'extend' => (new BaseHomeService())->getCapitalTypeList($changeTypeArr)]);
} catch (ValidateException $validateException) { } catch (ValidateException $validateException) {
// 参数校验失败 // 参数校验失败
$message = $validateException->getError(); $message = $validateException->getError();
@ -295,7 +291,6 @@ class FlowService extends AdminBaseService
} }
return $this->toData('0', 'SUCCESS', ['total' => $total, 'list' => $rows, 'extend' => (new BaseHomeService())->getCapitalTypeList($changeTypeArr)]); return $this->toData('0', 'SUCCESS', ['total' => $total, 'list' => $rows, 'extend' => (new BaseHomeService())->getCapitalTypeList($changeTypeArr)]);
} catch (ValidateException $validateException) { } catch (ValidateException $validateException) {
// 参数校验失败 // 参数校验失败
$message = $validateException->getError(); $message = $validateException->getError();
@ -424,7 +419,6 @@ class FlowService extends AdminBaseService
} }
return $this->toData('0', 'SUCCESS', ['total' => $total, 'list' => $rows, 'extend' => (new BaseHomeService())->getCapitalTypeList($changeTypeArr)]); return $this->toData('0', 'SUCCESS', ['total' => $total, 'list' => $rows, 'extend' => (new BaseHomeService())->getCapitalTypeList($changeTypeArr)]);
} catch (ValidateException $validateException) { } catch (ValidateException $validateException) {
// 参数校验失败 // 参数校验失败
$message = $validateException->getError(); $message = $validateException->getError();
@ -492,7 +486,6 @@ class FlowService extends AdminBaseService
} }
return $this->toData('0', 'SUCCESS', ['total' => $total, 'list' => $rows, 'extend' => (new BaseHomeService())->getCapitalTypeList($changeTypeArr)]); return $this->toData('0', 'SUCCESS', ['total' => $total, 'list' => $rows, 'extend' => (new BaseHomeService())->getCapitalTypeList($changeTypeArr)]);
} catch (ValidateException $validateException) { } catch (ValidateException $validateException) {
// 参数校验失败 // 参数校验失败
$message = $validateException->getError(); $message = $validateException->getError();
@ -560,7 +553,6 @@ class FlowService extends AdminBaseService
} }
return $this->toData('0', 'SUCCESS', ['total' => $total, 'list' => $rows, 'extend' => (new BaseHomeService())->getCapitalTypeList($changeTypeArr)]); return $this->toData('0', 'SUCCESS', ['total' => $total, 'list' => $rows, 'extend' => (new BaseHomeService())->getCapitalTypeList($changeTypeArr)]);
} catch (ValidateException $validateException) { } catch (ValidateException $validateException) {
// 参数校验失败 // 参数校验失败
$message = $validateException->getError(); $message = $validateException->getError();
@ -631,7 +623,6 @@ class FlowService extends AdminBaseService
} }
return $this->toData('0', 'SUCCESS', ['total' => $total, 'list' => $rows]); return $this->toData('0', 'SUCCESS', ['total' => $total, 'list' => $rows]);
} catch (ValidateException $validateException) { } catch (ValidateException $validateException) {
// 参数校验失败 // 参数校验失败
$message = $validateException->getError(); $message = $validateException->getError();
@ -708,7 +699,6 @@ class FlowService extends AdminBaseService
} }
return $this->toData('0', 'SUCCESS', ['total' => $total, 'list' => $rows]); return $this->toData('0', 'SUCCESS', ['total' => $total, 'list' => $rows]);
} catch (ValidateException $validateException) { } catch (ValidateException $validateException) {
// 参数校验失败 // 参数校验失败
$message = $validateException->getError(); $message = $validateException->getError();
@ -781,7 +771,6 @@ class FlowService extends AdminBaseService
} }
return $this->toData('0', 'SUCCESS', ['total' => $total, 'list' => $rows]); return $this->toData('0', 'SUCCESS', ['total' => $total, 'list' => $rows]);
} catch (ValidateException $validateException) { } catch (ValidateException $validateException) {
// 参数校验失败 // 参数校验失败
$message = $validateException->getError(); $message = $validateException->getError();

1
app/admin/service/RechargeService.php

@ -59,7 +59,6 @@ class RechargeService extends AdminBaseService
$total = RechargeApplyModel::where($where)->where($whereU)->count(); $total = RechargeApplyModel::where($where)->where($whereU)->count();
// 统计 充值成功 // 统计 充值成功
$sum = RechargeApplyModel::where($where)->where($whereU)->where('status', 1)->sum('recharge_num'); $sum = RechargeApplyModel::where($where)->where($whereU)->where('status', 1)->sum('recharge_num');
$groupSum = RechargeApplyModel::where($where)->where($whereU)->where('status', 1)->field('account_type, SUM(recharge_num) AS recharge_num')->group('recharge_num')->select(); $groupSum = RechargeApplyModel::where($where)->where($whereU)->where('status', 1)->field('account_type, SUM(recharge_num) AS recharge_num')->group('recharge_num')->select();
$rows = []; $rows = [];

5
app/admin/service/VideoService.php

@ -1,5 +1,7 @@
<?php <?php
namespace app\admin\service; namespace app\admin\service;
use app\model\BlockedWordModel; use app\model\BlockedWordModel;
use app\model\VideoOnDemandModel; use app\model\VideoOnDemandModel;
@ -65,7 +67,7 @@ class VideoService extends AdminBaseService
if (empty($param['id'])) { if (empty($param['id'])) {
return $this->toData('400', 'Missing param id'); return $this->toData('400', 'Missing param id');
} }
if (empty($param['title']) || empty($param['cover_url']) || empty($param['state']) || empty($param['video_collection']) || empty($param['video_type'])) { if (empty($param['title']) || empty($param['cover_url']) || !in_array($param['state'], [0, 1]) || empty($param['video_collection']) || empty($param['video_type'])) {
return $this->toData('400', '参错错误'); return $this->toData('400', '参错错误');
} }
$ckInfo = VideoOnDemandModel::where('id', $param['id'])->find(); $ckInfo = VideoOnDemandModel::where('id', $param['id'])->find();
@ -173,5 +175,4 @@ class VideoService extends AdminBaseService
return $this->toData('500', 'The system is busy.', [$exception->getMessage(), $exception->getTrace()]); return $this->toData('500', 'The system is busy.', [$exception->getMessage(), $exception->getTrace()]);
} }
} }
} }

6
app/admin/service/setting/BlockStockService.php

@ -51,7 +51,6 @@ class BlockStockService extends AdminBaseService
$list = $query->order('id', 'desc')->page($param['page'], $param['limit'])->select(); $list = $query->order('id', 'desc')->page($param['page'], $param['limit'])->select();
$total = $totalQuery->order('id', 'desc')->count(); $total = $totalQuery->order('id', 'desc')->count();
return $this->toData('0', 'SUCCESS', ['list' => $list, 'total' => $total, 'extend' => [ return $this->toData('0', 'SUCCESS', ['list' => $list, 'total' => $total, 'extend' => [
// 'tape_list' => StockBlockListModel::$tapeList, // 'tape_list' => StockBlockListModel::$tapeList,
// 'stock_type_list' => StockBlockListModel::$typeList, // 'stock_type_list' => StockBlockListModel::$typeList,
@ -302,7 +301,8 @@ class BlockStockService extends AdminBaseService
} }
// 可出售时间时间 // 可出售时间时间
if (empty($param['today_add']) || !is_numeric($param['today_add'])) { // if (empty($param['today_add']) || !is_numeric($param['today_add'])) {
if (!is_numeric($param['today_add'])) {
return $this->toData('1', 'T+n 无效'); return $this->toData('1', 'T+n 无效');
} }
@ -350,7 +350,7 @@ class BlockStockService extends AdminBaseService
return $this->toData('0', 'SUCCESS'); return $this->toData('0', 'SUCCESS');
} catch (\Exception $exception) { } catch (\Exception $exception) {
return $this->toData('0', '系统繁忙', [$exception->getMessage()]); return $this->toData('0', '系统繁忙', [$exception->getMessage(), $exception->getTrace()]);
} }
} }

43
app/admin/service/setting/IPOService.php

@ -32,12 +32,10 @@ use app\model\StockSgdListModel;
use app\model\StockThaListModel; use app\model\StockThaListModel;
use app\model\UserArrearsModel; use app\model\UserArrearsModel;
use app\model\UserModel; use app\model\UserModel;
use app\model\UserUsPreStockOrderModel;
use think\exception\ValidateException; use think\exception\ValidateException;
use think\facade\Db; use think\facade\Db;
use think\facade\Log; use think\facade\Log;
use think\facade\Queue; use think\facade\Queue;
use function app\admin\service\getTreeMenu;
class IPOService extends AdminBaseService class IPOService extends AdminBaseService
{ {
@ -65,7 +63,8 @@ class IPOService extends AdminBaseService
return $this->toData('0', 'SUCCESS', ['total' => 0, 'list' => [], 'extent' => [ return $this->toData('0', 'SUCCESS', ['total' => 0, 'list' => [], 'extent' => [
'tape_list' => $stockTypeList['tape'], 'tape_list' => $stockTypeList['tape'],
'stock_type_list' => $stockTypeList['type'], 'stock_type_list' => $stockTypeList['type'],
'symbol' => $table_obj['stock_id']]]); 'symbol' => $table_obj['stock_id']
]]);
} }
$userId = $user['user_id']; $userId = $user['user_id'];
} }
@ -76,24 +75,31 @@ class IPOService extends AdminBaseService
return $this->toData('0', 'SUCCESS', ['total' => 0, 'list' => [], 'extent' => [ return $this->toData('0', 'SUCCESS', ['total' => 0, 'list' => [], 'extent' => [
'tape_list' => $stockTypeList['tape'], 'tape_list' => $stockTypeList['tape'],
'stock_type_list' => $stockTypeList['type'], 'stock_type_list' => $stockTypeList['type'],
'symbol' => $table_obj['stock_id']]]); 'symbol' => $table_obj['stock_id']
]]);
} }
// 未删除 // 未删除
$where[] = [ $where[] = [
'is_delete', '=', 1 'is_delete',
'=',
1
]; ];
// 股票号 // 股票号
if (!empty($param['stock_code']) && is_string($param['stock_code'])) { if (!empty($param['stock_code']) && is_string($param['stock_code'])) {
$where[] = [ $where[] = [
'stock_code', 'like', '%' . $param['stock_code'] 'stock_code',
'like',
'%' . $param['stock_code']
]; ];
} }
// 状态 // 状态
if (!empty($param['status']) && in_array($param['status'], [1, 2])) { if (!empty($param['status']) && in_array($param['status'], [1, 2])) {
$where[] = [ $where[] = [
'status', '=', $param['status'] 'status',
'=',
$param['status']
]; ];
} }
@ -563,7 +569,6 @@ class IPOService extends AdminBaseService
} catch (\Exception $exception) { } catch (\Exception $exception) {
return $this->toData('0', '系统繁忙', [$exception->getMessage()]); return $this->toData('0', '系统繁忙', [$exception->getMessage()]);
} }
} }
/** /**
@ -600,7 +605,6 @@ class IPOService extends AdminBaseService
} else { } else {
return $this->toData('1', 'FAIL'); return $this->toData('1', 'FAIL');
} }
} catch (\Exception $exception) { } catch (\Exception $exception) {
return $this->toData('1', '系统繁忙', [$exception->getMessage()]); return $this->toData('1', '系统繁忙', [$exception->getMessage()]);
} }
@ -624,7 +628,6 @@ class IPOService extends AdminBaseService
if (isset($param['is_real']) && is_numeric($param['is_real']) && $param['is_real'] == '2') { if (isset($param['is_real']) && is_numeric($param['is_real']) && $param['is_real'] == '2') {
$isReal = 2; $isReal = 2;
} }
$preInStock = Db::table($table_obj['stock_table'])->where('id', $param['id'])->where('is_delete', 1)->find(); $preInStock = Db::table($table_obj['stock_table'])->where('id', $param['id'])->where('is_delete', 1)->find();
if (empty($preInStock)) { if (empty($preInStock)) {
return $this->toData('1', '主键 无效'); return $this->toData('1', '主键 无效');
@ -647,9 +650,11 @@ class IPOService extends AdminBaseService
Db::startTrans(); Db::startTrans();
// 修改股票状态 // 修改股票状态
$num = Db::table($table_obj['stock_table'])->where('id', $preInStock['id'])->update(['open_status' => 2, $num = Db::table($table_obj['stock_table'])->where('id', $preInStock['id'])->update([
'open_status' => 2,
'open_time' => date('Y-m-d H:i:s'), 'open_time' => date('Y-m-d H:i:s'),
'update_time' => date('Y-m-d H:i:s')]); 'update_time' => date('Y-m-d H:i:s')
]);
if ($num <= 0) { if ($num <= 0) {
Db::rollback(); Db::rollback();
return $this->toData('1', '股票状态修改失败'); return $this->toData('1', '股票状态修改失败');
@ -720,10 +725,10 @@ class IPOService extends AdminBaseService
// 查询bot_user_us_pre_stock_order表,即所有申购了该股票的订单记录,修改其status状态为3 // 查询bot_user_us_pre_stock_order表,即所有申购了该股票的订单记录,修改其status状态为3
Log::info("新股上市 - 修改股票申购状态:pre_stock_id = " . $preInStock['id']); Log::info("新股上市 - 修改股票申购状态:pre_stock_id = " . $preInStock['id']);
$stockOrderList = UserUsPreStockOrderModel::where(['pre_stock_id'=>$preInStock['id']])->select()->toArray(); $stockOrderList = Db::table($table_obj['order_table'])->where(['pre_stock_id' => $preInStock['id']])->select()->toArray();
if (!empty($stockOrderList)) { if (!empty($stockOrderList)) {
foreach ($stockOrderList as $itm) { foreach ($stockOrderList as $itm) {
UserUsPreStockOrderModel::update(['status'=>3], ['id'=>$itm['id']]); Db::table($table_obj['order_table'])->where('id', $itm['id'])->update(['status' => 3]);
} }
} }
@ -817,7 +822,6 @@ class IPOService extends AdminBaseService
], 'sendGo'); ], 'sendGo');
} }
return $this->toData('0', 'SUCCESS'); return $this->toData('0', 'SUCCESS');
} }
@ -874,7 +878,8 @@ class IPOService extends AdminBaseService
'get_amount' => $get_amount, 'get_amount' => $get_amount,
'get_fee' => $get_fee, 'get_fee' => $get_fee,
'get_time' => $now, 'get_time' => $now,
'update_time' => $now]); 'update_time' => $now
]);
if ($num <= 0) { if ($num <= 0) {
Db::rollback(); Db::rollback();
@ -950,7 +955,6 @@ class IPOService extends AdminBaseService
} }
} }
} }
} }
// 更新股票数据 // 更新股票数据
$bool = Db::table($table_obj['stock_table'])->where('id', $preStock['id'])->update(['sign_status' => 1, 'update_time' => $now]); $bool = Db::table($table_obj['stock_table'])->where('id', $preStock['id'])->update(['sign_status' => 1, 'update_time' => $now]);
@ -961,7 +965,6 @@ class IPOService extends AdminBaseService
} }
// 提交事务 // 提交事务
Db::commit(); Db::commit();
} catch (\Exception $exception) { } catch (\Exception $exception) {
Db::rollback(); Db::rollback();
trace("股票签名失败-exception 股票市场:" . $market_type . $exception->getMessage(), 'error'); trace("股票签名失败-exception 股票市场:" . $market_type . $exception->getMessage(), 'error');
@ -1331,7 +1334,8 @@ class IPOService extends AdminBaseService
/** /**
* 取消上市 * 取消上市
*/ */
public function cancelIPO($market_type,$param){ public function cancelIPO($market_type, $param)
{
$table_obj = $this->getStockModel($market_type); $table_obj = $this->getStockModel($market_type);
$redis = $this->getRedis(); $redis = $this->getRedis();
if (empty($table_obj)) { if (empty($table_obj)) {
@ -1778,5 +1782,4 @@ class IPOService extends AdminBaseService
} }
return $result; return $result;
} }
} }

57
app/command/ApiLogCommand.php

@ -0,0 +1,57 @@
<?php
declare(strict_types=1);
namespace app\command;
use app\model\ApiLogModel;
use think\console\Command;
use think\console\Input;
use think\console\Output;
use think\facade\Cache;
use think\facade\Log;
class ApiLogCommand extends Command
{
protected function configure()
{
// 指令配置
$this->setName('api_log')
->setDescription('the api_log command');
}
/**
* Execute the console command.
*
* @param Input $input
* @param Output $output
* @return void
*/
protected function execute(Input $input, Output $output)
{
while (true) {
try {
$redis = Cache::store('redis')->handler();
$result = $redis->blpop(['api_log'], 5);
if ($result) {
$logData = json_decode($result[1], true);
if (!is_array($logData) || empty($logData)) {
continue;
}
if ($logData) {
$logData['params'] = json_encode($logData['params'] ?? [], JSON_UNESCAPED_UNICODE);
$logData['response'] = json_encode($logData['response'] ?? [], JSON_UNESCAPED_UNICODE);
ApiLogModel::create($logData);
}
} else {
// 如果没有数据,休眠一段时间再继续
sleep(10);
}
} catch (\Throwable $e) {
Log::error('ApiLogCommand error: ' . $e->getMessage());
sleep(3);
}
}
}
}

14
app/home/controller/User.php

@ -32,6 +32,20 @@ class User extends HomeBaseController
return json($returnData); return json($returnData);
} }
// 使用vip兑换码兑换vip
public function redeemVip(): Json
{
$returnData = (new UserService())->redeemVip($this->request->userId, $this->request->post());
return json($returnData);
}
// 观看视频记录
public function watchVideo(): Json
{
$returnData = (new UserService())->watchVideo($this->request->userId, $this->request->post());
return json($returnData);
}
public function getAnchorForAgent(): Json public function getAnchorForAgent(): Json
{ {
$returnData = (new UserService())->getAnchorForAgent($this->request->userId); $returnData = (new UserService())->getAnchorForAgent($this->request->userId);

3
app/home/lang/zh-cn.php

@ -40,7 +40,8 @@ return [
'chat_group_is_empty' => '聊天群组为空', 'chat_group_is_empty' => '聊天群组为空',
'missing_user_id' => '缺少用户ID', 'missing_user_id' => '缺少用户ID',
'data_configuration_error' => '数据配置错误', 'data_configuration_error' => '数据配置错误',
'user_usd_balance_is_insufficient' => '用户余额不足', 'user_usd_balance_is_insufficient' => '用户美元余额不足',
'user_balance_is_insufficient' => '用户余额不足',
'vip_expiration_time_error' => 'VIP过期时间错误', 'vip_expiration_time_error' => 'VIP过期时间错误',
'anchor_information_is_empty' => '主播信息为空', 'anchor_information_is_empty' => '主播信息为空',
'avatar_information_error' => '头像信息错误', 'avatar_information_error' => '头像信息错误',

3
app/home/lang/zh-jp.php

@ -41,7 +41,8 @@ return [
'chat_group_is_empty' => 'チャットグループは空です', 'chat_group_is_empty' => 'チャットグループは空です',
'missing_user_id' => 'ユーザーIDがありません', 'missing_user_id' => 'ユーザーIDがありません',
'data_configuration_error' => 'データ構成エラー', 'data_configuration_error' => 'データ構成エラー',
'user_usd_balance_is_insufficient' => 'ユーザー残高が不足しています', 'user_usd_balance_is_insufficient' => 'USDでのユーザー残高が不足しています',
'user_balance_is_insufficient' => 'ユーザー残高が不足しています',
'vip_expiration_time_error' => 'VIP有効期限エラー', 'vip_expiration_time_error' => 'VIP有効期限エラー',
'anchor_information_is_empty' => 'アンカー情報が空です', 'anchor_information_is_empty' => 'アンカー情報が空です',
'avatar_information_error' => 'アバター情報エラー', 'avatar_information_error' => 'アバター情報エラー',

3
app/home/lang/zh-us.php

@ -41,7 +41,8 @@ return [
'chat_group_is_empty' => 'Chat group is empty', 'chat_group_is_empty' => 'Chat group is empty',
'missing_user_id' => 'Missing User ID', 'missing_user_id' => 'Missing User ID',
'data_configuration_error' => 'Data configuration error', 'data_configuration_error' => 'Data configuration error',
'user_usd_balance_is_insufficient' => 'The user balance is insufficient', 'user_usd_balance_is_insufficient' => 'The user USD balance is insufficient',
'user_balance_is_insufficient' => 'The user balance is insufficient',
'vip_expiration_time_error' => 'VIP expiration time error', 'vip_expiration_time_error' => 'VIP expiration time error',
'anchor_information_is_empty' => 'The anchor information is empty', 'anchor_information_is_empty' => 'The anchor information is empty',
'avatar_information_error' => 'Avatar information error', 'avatar_information_error' => 'Avatar information error',

76
app/home/middleware/ApiLogMiddleware.php

@ -0,0 +1,76 @@
<?php
namespace app\home\middleware;
use app\home\service\BaseHomeService;
use app\model\UserModel;
use think\Response;
use think\facade\Log;
use think\Request;
/**
* @desc 记录接口日志
*/
class ApiLogMiddleware
{
// 配置需要记录日志的接口(路径部分)
protected $logRoutes = [
'phone_login',
'email_login',
'email',
'email_reg',
'sms',
'sms_reg',
'forget_email',
'forget_sms',
'user_recharge',
'transfer',
'user_drawal',
'pre_stock/order',
'fund/order',
];
public function handle(Request $request, \Closure $next)
{
// OPTIONS 请求直接返回空响应
if ($request->method(true) === 'OPTIONS') {
return response()->send();
}
$path = $request->pathinfo();
$shouldLog = in_array($path, $this->logRoutes);
$logData = [];
if ($shouldLog) {
$ip = (new BaseHomeService())->getClientRealIp();
$params = $request->param();
$logData = [
'url' => $request->url(),
'method' => $request->method(),
'params' => $params,
'ip' => $ip,
];
// 如果登录了,记录 user_id
if (!empty($request->user_id)) {
$logData['user_id'] = $request->user_id;
}
}
$response = $next($request);
if ($shouldLog && $response instanceof Response) {
$logData['response'] = $response->getData();
}
//写入redis
if (!empty($logData)) {
$logData['user_agent'] = $request->header('user-agent');
$logData['created_at'] = date('Y-m-d H:i:s');
// 记录日志到 Redis
\think\facade\Cache::store('redis')->lpush('api_log', json_encode($logData));
}
return $response;
}
}

47
app/home/middleware/CheckUserMiddleware.php

@ -0,0 +1,47 @@
<?php
namespace app\home\middleware;
use app\model\UserModel;
use think\facade\Cache;
use think\facade\Config;
use think\facade\Lang;
use think\facade\Log;
use think\Request;
/**
* @desc 必须要登陆的接口 校验是否登陆
*/
class CheckUserMiddleware
{
public function handle(Request $request, \Closure $next)
{
// OPTIONS 请求直接返回空响应
if ($request->method(true) === 'OPTIONS') {
return response()->send();
}
// 设置多语言
Config::set(['default_lang' => 'zh-jp'], 'lang'); // P2 默认设置日语
$request->lang = Config::get('lang.default_lang');
$header = $request->header();
if (isset($header['language'])) {
$lang_list = Config::get('lang.allow_lang_list');
$lang = strtolower($header['language']);
if (in_array($lang, $lang_list)) {
Lang::setLangSet($lang);
$request->lang = $lang;
}
}
if (!empty($header['token']) && is_string($header['token'])) {
$tokenUserKey = 'TOKEN:USER:' . $header['token'];
$userId = Cache::store('redis')->get($tokenUserKey);
if ($userId && $userId >= 0) {
$request->userId = $userId;
}
}
return $next($request);
}
}

16
app/home/route/app.php

@ -140,6 +140,7 @@ Route::group('/',function (){
//基金 //基金
Route::post('fund/index', 'Fund/index'); Route::post('fund/index', 'Fund/index');
Route::post('auto_login', 'Login/autoLogin'); Route::post('auto_login', 'Login/autoLogin');
Route::post('user/user_access_log', 'User/userAccessLog')->middleware(\app\home\middleware\CheckUserMiddleware::class); //记录用户访问每个页面日志
// 需要登陆的操作 // 需要登陆的操作
Route::group('/', function () { Route::group('/', function () {
@ -202,6 +203,9 @@ Route::group('/',function (){
Route::post('user/info', 'User/getUserInfo'); Route::post('user/info', 'User/getUserInfo');
Route::post('user/purchase_vip', 'User/purchaseVip'); //用户购买VIP Route::post('user/purchase_vip', 'User/purchaseVip'); //用户购买VIP
Route::post('user/purchase_vip_log', 'User/purchaseVipLog'); //用户购买VIP记录列表 Route::post('user/purchase_vip_log', 'User/purchaseVipLog'); //用户购买VIP记录列表
Route::post('user/redeem_vip', 'User/redeemVip'); //使用vip兑换码兑换vip
// 观看点播视频记录
Route::post('user/watch_video', 'User/watchVideo');
// 获取用户的代理创建的群聊信息 // 获取用户的代理创建的群聊信息
Route::post('user/get_anchor_for_agent', 'User/getAnchorForAgent'); Route::post('user/get_anchor_for_agent', 'User/getAnchorForAgent');
// 获取登陆记录 // 获取登陆记录
@ -212,7 +216,7 @@ Route::group('/',function (){
Route::post('user/apply_test', 'User/applyTest'); Route::post('user/apply_test', 'User/applyTest');
Route::post('user/test_login', 'User/testLogin'); Route::post('user/test_login', 'User/testLogin');
Route::post('user/formal_login', 'User/formalLogin'); Route::post('user/formal_login', 'User/formalLogin');
Route::post('user/user_access_log', 'User/userAccessLog'); //记录用户访问每个页面日志
Route::post('payment_list', 'Pay/payChannel'); //获取充值渠道 Route::post('payment_list', 'Pay/payChannel'); //获取充值渠道
Route::post('user_recharge', 'Pay/rechargeApply')->middleware(\app\home\middleware\RepeatOperateMiddleware::class); // 用户提交充值订单 Route::post('user_recharge', 'Pay/rechargeApply')->middleware(\app\home\middleware\RepeatOperateMiddleware::class); // 用户提交充值订单
@ -298,11 +302,5 @@ Route::group('/',function (){
Route::post('stock/stock_analysis', 'Stock/stockAnalysis'); // 股票分析 Route::post('stock/stock_analysis', 'Stock/stockAnalysis'); // 股票分析
})->middleware(\app\home\middleware\AuthMiddleware::class); })->middleware(\app\home\middleware\AuthMiddleware::class);
})->allowCrossDomain($header)
})->allowCrossDomain($header); ->middleware(\app\home\middleware\ApiLogMiddleware::class);

13
app/home/service/BaseHomeService.php

@ -76,6 +76,7 @@ class BaseHomeService
{ {
$code = random_int(1000, 9999); $code = random_int(1000, 9999);
$subject = "【Acm】あなたの認証コード[$code],有効10分以内"; $subject = "【Acm】あなたの認証コード[$code],有効10分以内";
// $subject = "your code is [$code], valid for 5 minutes";
return ['subject' => $subject, 'code' => $code]; return ['subject' => $subject, 'code' => $code];
} }
@ -999,7 +1000,17 @@ class BaseHomeService
} else { } else {
$result = []; $result = [];
foreach ($type_arr as $v) { foreach ($type_arr as $v) {
$result[$v] = $type_list[$v]; $result[$v] = $type_list[$v] ?? [
'zh-cn' => '未知类型',
'zh-zh' => '未知类型',
'zh-us' => 'Unknown Type',
'zh-cs' => 'Neznámý typ',
'zh-sp' => 'Tipo desconocido',
'zh-eu' => 'Tipo Desconocido',
'zh-th' => 'ประเภทที่ไม่รู้จัก',
'zh-in' => 'अज्ञात प्रकार',
'zh-jp' => '不明なタイプ'
];
} }
return $result; return $result;
} }

25
app/home/service/LoginService.php

@ -193,7 +193,7 @@ class LoginService extends BaseHomeService
$userId = $regUser->user_id; $userId = $regUser->user_id;
// 生成钱包地址 // 生成钱包地址
(new UserService())->doRegInitUserInfo($userId, $parentUserId); // (new UserService())->doRegInitUserInfo($userId, $parentUserId);
// 请求聊天服务,注册聊天账号 // 请求聊天服务,注册聊天账号
$chatData = [ $chatData = [
'Username' => $userNo, 'Username' => $userNo,
@ -372,7 +372,10 @@ class LoginService extends BaseHomeService
if ($this->checkForbidNation($param['nation'])) { if ($this->checkForbidNation($param['nation'])) {
return $this->toData('500', lang('unsupported_country_or_region')); return $this->toData('500', lang('unsupported_country_or_region'));
} }
//日本手机号 不加国家码是10位
if (strlen($param['phone']) != 10) {
return $this->toData('500', lang('unsupported_country_or_region'));
}
// 判断国家码是否有效 // 判断国家码是否有效
$nationExists = CountryModel::checkCodeExists($param['nation']); $nationExists = CountryModel::checkCodeExists($param['nation']);
if (!$nationExists) { if (!$nationExists) {
@ -452,17 +455,15 @@ class LoginService extends BaseHomeService
// 校验验证码 // 校验验证码
$mobile = $param['nation'] . $param['phone']; $mobile = $param['nation'] . $param['phone'];
$smsKey = 'DB:USER:UNLOGIN:SMS_CODE:' . $mobile; $smsKey = 'DB:USER:UNLOGIN:SMS_CODE:' . $mobile;
if ($param['sms_code'] != 8888) { // 方便测试,8888为万能验证码
if (!$this->checkCode($smsKey, $param['sms_code'])) { if (!$this->checkCode($smsKey, $param['sms_code'])) {
return $this->toData('500', lang('incorrect_verification_code'));
//注册验证码 //注册验证码
// $reg_key = "USER:REG:CODE"; $reg_key = "USER:REG:CODE";
// if (!$this->checkCode($reg_key, $param['sms_code'])) { if (!$this->checkCode($reg_key, $param['sms_code'])) {
// return $this->toData('100300', 'The verification code is incorrect.', []); return $this->toData('500', lang('incorrect_verification_code'));
// }
} }
} }
// 手机号是否已经存在 // 手机号是否已经存在
$phoneExists = UserModel::checkPhoneExists($param['phone']); $phoneExists = UserModel::checkPhoneExists($param['phone']);
if ($phoneExists) { if ($phoneExists) {
@ -656,11 +657,15 @@ class LoginService extends BaseHomeService
// 验证短信验证码 // 验证短信验证码
$mobile = $param['nation'] . $param['phone']; $mobile = $param['nation'] . $param['phone'];
$smsKey = 'DB:USER:UNLOGIN:SMS_CODE:' . $mobile; $smsKey = 'DB:USER:UNLOGIN:SMS_CODE:' . $mobile;
if ($param['sms_code'] != 8888) {
if (!$this->checkCode($smsKey, $param['sms_code'])) { if (!$this->checkCode($smsKey, $param['sms_code'])) {
//注册验证码
$reg_key = "USER:REG:CODE";
if (!$this->checkCode($reg_key, $param['sms_code'])) {
return $this->toData('500', lang('incorrect_verification_code')); return $this->toData('500', lang('incorrect_verification_code'));
};
} }
};
// 查找手机号 // 查找手机号
$userId = UserModel::getUserIdByNationAndPhone($param['nation'], $param['phone']); $userId = UserModel::getUserIdByNationAndPhone($param['nation'], $param['phone']);

142
app/home/service/UserService.php

@ -28,7 +28,8 @@ use app\model\UserStockJpLogModel;
use app\model\UserStockJpModel; use app\model\UserStockJpModel;
use app\model\UserStockLogModel; use app\model\UserStockLogModel;
use app\model\UserStockModel; use app\model\UserStockModel;
use app\model\UserVerifyLogModel; use app\model\VipCodeModel;
use app\model\WatchVideoLogModel;
use app\utility\Jwt; use app\utility\Jwt;
use app\utility\UnqId; use app\utility\UnqId;
use think\exception\ValidateException; use think\exception\ValidateException;
@ -127,8 +128,6 @@ class UserService extends BaseHomeService
]); ]);
} }
} }
} }
/** /**
@ -219,7 +218,7 @@ class UserService extends BaseHomeService
} }
} }
// 检测用户是否为有效VIP // 检测用户是否为有效VIP [判断规则 - 用户购买过VIP, 每个VIP有效期30天]
$isVip = false; $isVip = false;
$vipExpire = ""; //vip到期时间 $vipExpire = ""; //vip到期时间
$vipType = ""; // vip类型:青铜、白金、钻石; (管理端赠送的vip,以及vip兑换码兑换的都是显示免费标签) $vipType = ""; // vip类型:青铜、白金、钻石; (管理端赠送的vip,以及vip兑换码兑换的都是显示免费标签)
@ -240,16 +239,13 @@ class UserService extends BaseHomeService
} }
} }
// 用户是实名信息 // 获取用户观看video的最后一个记录ID
$verifyName = ""; $watchVideoLogId = 0;
$verifySurname = ""; $watchVideoLog = WatchVideoLogModel::where(['user_id' => $userId])->find();
$verifyInfo = UserVerifyLogModel::where(['user_id'=>$userId])->find(); if (!empty($watchVideoLog)) {
if (!empty($verifyInfo)){ $watchVideoLogId = $watchVideoLog->video_id;
$verifyName = $verifyInfo->name;
$verifySurname = $verifyInfo->surname;
} }
// 返回数据 // 返回数据
return $this->toData('0', 'Modification successful.', [ return $this->toData('0', 'Modification successful.', [
'logo' => $headPath, 'logo' => $headPath,
@ -286,8 +282,7 @@ class UserService extends BaseHomeService
'customer_remark' => $info['customer_remark'], 'customer_remark' => $info['customer_remark'],
'label' => $info['label'], 'label' => $info['label'],
'adjust_channel' => $info['adjust_channel'], 'adjust_channel' => $info['adjust_channel'],
'verify_name' => $verifyName, 'watch_video_id' => $watchVideoLogId, // 没看过就是0, 看过就返回的最后一次看的video_id
'verify_surname' => $verifySurname,
]); ]);
} catch (\Exception $exception) { } catch (\Exception $exception) {
return $this->toData('500', lang('system_busy'), [$exception->getMessage(), $exception->getTrace()]); return $this->toData('500', lang('system_busy'), [$exception->getMessage(), $exception->getTrace()]);
@ -312,26 +307,27 @@ class UserService extends BaseHomeService
} }
// 购买vip所需的货币类型检测 [产品确定使用美股支付 USD] // 购买vip所需的货币类型检测 [产品确定使用美股支付 USD]
if (empty($vipPurchaseCfg['stock_id'])) { if (empty($vipPurchaseCfg['stock_id'])) {
return $this->toData('501', lang('data_configuration_error')); return $this->toData('500', lang('data_configuration_error'));
} }
$stockId = $vipPurchaseCfg['stock_id']; $stockId = $vipPurchaseCfg['stock_id'];
// vip类型配置检测 // vip类型配置检测
if (!isset($vipPurchaseCfg[$param['vip_type']])) { if (!isset($vipPurchaseCfg[$param['vip_type']])) {
return $this->toData('502', lang('data_configuration_error')); return $this->toData('500', lang('data_configuration_error'));
} }
$tagVipConfig = $vipPurchaseCfg[$param['vip_type']]; $tagVipConfig = $vipPurchaseCfg[$param['vip_type']];
// vip价格检测 // vip价格检测
if (!isset($tagVipConfig['vip_price']) || $tagVipConfig['vip_price'] <= 0) { if (!isset($tagVipConfig['vip_price']) || $tagVipConfig['vip_price'] <= 0) {
return $this->toData('503', lang('data_configuration_error')); return $this->toData('500', lang('data_configuration_error'));
} }
// vip有效天数检测 // vip有效天数检测
if (!isset($tagVipConfig['vip_day']) || $tagVipConfig['vip_day'] <= 0) { if (!isset($tagVipConfig['vip_day']) || $tagVipConfig['vip_day'] <= 0) {
return $this->toData('504', lang('data_configuration_error')); return $this->toData('500', lang('data_configuration_error'));
} }
// 查询用户余额是否足够 // 查询用户余额是否足够
// $userMoney = UserStockModel::where(['user_id'=>$userId,'stock_id'=> $stockId])->find();
$userMoney = UserStockJpModel::where(['user_id' => $userId, 'stock_id' => $stockId])->find(); $userMoney = UserStockJpModel::where(['user_id' => $userId, 'stock_id' => $stockId])->find();
if (empty($userMoney)) { if (empty($userMoney)) {
return $this->toData('500', lang('user_usd_balance_is_insufficient')); return $this->toData('500', lang('user_balance_is_insufficient'));
} }
$userMoneyNum = (int)$userMoney->usable_num; $userMoneyNum = (int)$userMoney->usable_num;
if ($userMoneyNum < $tagVipConfig['vip_price']) { if ($userMoneyNum < $tagVipConfig['vip_price']) {
@ -345,6 +341,7 @@ class UserService extends BaseHomeService
// 扣除用户金额 // 扣除用户金额
UserStockJpModel::where(['user_id' => $userId, 'stock_id' => $stockId])->where('usable_num', ">=", $vipPrice)->dec('usable_num', $vipPrice)->update(); UserStockJpModel::where(['user_id' => $userId, 'stock_id' => $stockId])->where('usable_num', ">=", $vipPrice)->dec('usable_num', $vipPrice)->update();
// 添加用户USD变更日志 // 添加用户USD变更日志
// UserStockLogModel::create([
UserStockJpLogModel::create([ UserStockJpLogModel::create([
'user_id' => $userId, 'user_id' => $userId,
'change_type' => 100, 'change_type' => 100,
@ -388,7 +385,7 @@ class UserService extends BaseHomeService
'vip_type' => $vipType, 'vip_type' => $vipType,
]); ]);
}); });
return $this->toData('0', 'successful'); return $this->toData('0', 'successful', []);
} catch (\Exception $exception) { } catch (\Exception $exception) {
return $this->toData('500', lang('system_busy'), [$exception->getMessage(), $exception->getTrace()]); return $this->toData('500', lang('system_busy'), [$exception->getMessage(), $exception->getTrace()]);
} }
@ -411,12 +408,84 @@ class UserService extends BaseHomeService
'total' => $list->total(), // 总记录数 'total' => $list->total(), // 总记录数
'last_page' => $list->lastPage(), // 最后一页页码 'last_page' => $list->lastPage(), // 最后一页页码
]); ]);
} catch (\Exception $exception) { } catch (\Exception $exception) {
return $this->toData('500', lang('system_busy'), [$exception->getLine(), $exception->getMessage(), $exception->getTrace()]); return $this->toData('500', lang('system_busy'), [$exception->getLine(), $exception->getMessage(), $exception->getTrace()]);
} }
} }
// 使用vip兑换码兑换vip
public function redeemVip($userId, $param)
{
try {
if (empty($param['vip_code'])) {
return $this->toData('500', lang('missing param vip_code'));
}
$info = UserModel::where(['user_id' => $userId])->find();
if (empty($info)) {
return $this->toData('500', lang('user_does_not_exist'));
}
// 获取vip_code信息
$vipCodeInfo = VipCodeModel::where(['vip_code' => $param['vip_code']])->find();
if (empty($vipCodeInfo) || $vipCodeInfo->status != 0) {
return $this->toData('500', lang('VIP引き換えコードが無効です'));
}
$expireTimestamp = strtotime('+' . $vipCodeInfo->day . ' day');
$expireTime = date("Y-m-d H:i:s", $expireTimestamp);
// 查询用户是否开通过vip,更新用户vip到期时间
$vipLog = PurchaseVipModel::where(['user_id' => $userId])->find();
if (!empty($vipLog)) {
if (empty($vipLog->expire)) {
return $this->toData('500', lang('vip_expiration_time_error'));
}
if ($vipLog->expire >= date("Y-m-d H:i:s")) {
$expireTimestamp = strtotime('+' . $vipCodeInfo->day . ' day', strtotime($vipLog->expire));
$expireTime = date("Y-m-d H:i:s", $expireTimestamp);
}
$vipLog->expire = $expireTime;
$vipLog->save();
} else {
PurchaseVipModel::create([
'user_id' => $userId,
'expire' => $expireTime
]);
}
// 修改vip兑换码使用状态
$vipCodeInfo->status = 1;
$vipCodeInfo->uid = $userId;
$vipCodeInfo->used_time = date("Y-m-d H:i:s");
$vipCodeInfo->save();
return $this->toData('0', 'successful');
} catch (\Exception $exception) {
return $this->toData('500', lang('system_busy'), [$exception->getMessage(), $exception->getTrace()]);
}
}
// 观看视频记录
public function watchVideo($userId, $param)
{
try {
if (empty($param['video_id'])) {
return $this->toData('500', lang('missing param'));
}
$info = UserModel::where(['user_id' => $userId])->find();
if (empty($info)) {
return $this->toData('500', lang('user_does_not_exist'));
}
$exists = WatchVideoLogModel::where(['user_id' => $userId, 'video_id' => $param['video_id']])->find();
if (empty($exists)) {
WatchVideoLogModel::create([
'user_id' => $userId,
'video_id' => $param['video_id'],
'created_at' => date("Y-m-d H:i:s")
]);
}
return $this->toData('0', 'successful');
} catch (\Exception $exception) {
return $this->toData('500', lang('system_busy'), [$exception->getMessage(), $exception->getTrace()]);
}
}
// 查询代理下的一个主播信息 // 查询代理下的一个主播信息
public function getAnchorForAgent($userId) public function getAnchorForAgent($userId)
{ {
@ -589,14 +658,12 @@ class UserService extends BaseHomeService
$chatFriendsUrl = env('CHAT_SERVER.BASE_URL') . '/api/user'; $chatFriendsUrl = env('CHAT_SERVER.BASE_URL') . '/api/user';
$chatFriendsRes = (new \app\utility\RequestChatServer())->ReqChatServer($chatFriendsUrl, $upChaData, 'PUT'); $chatFriendsRes = (new \app\utility\RequestChatServer())->ReqChatServer($chatFriendsUrl, $upChaData, 'PUT');
return $this->toData($chatFriendsRes['code'], $chatFriendsRes['msg'], [$chatFriendsRes['data']]); return $this->toData($chatFriendsRes['code'], $chatFriendsRes['msg'], [$chatFriendsRes['data']]);
} catch (ValidateException $validateException) { } catch (ValidateException $validateException) {
$message = $validateException->getError(); $message = $validateException->getError();
return $this->toData('500', $message); return $this->toData('500', $message);
} catch (\Exception $exception) { } catch (\Exception $exception) {
return $this->toData('500', lang('system_busy'), [$exception->getMessage(), $exception->getTrace()]); return $this->toData('500', lang('system_busy'), [$exception->getMessage(), $exception->getTrace()]);
} }
} }
/** /**
@ -840,7 +907,6 @@ class UserService extends BaseHomeService
} catch (\Exception $exception) { } catch (\Exception $exception) {
return $this->toData('500', lang('system_busy'), [$exception->getMessage(), $exception->getTrace()]); return $this->toData('500', lang('system_busy'), [$exception->getMessage(), $exception->getTrace()]);
} }
} }
/** /**
@ -894,7 +960,6 @@ class UserService extends BaseHomeService
// 返回结果 // 返回结果
return $this->toData('0', 'successful'); return $this->toData('0', 'successful');
} catch (ValidateException $validateException) { } catch (ValidateException $validateException) {
// 参数校验失败 异常类 // 参数校验失败 异常类
$message = $validateException->getError(); $message = $validateException->getError();
@ -902,7 +967,6 @@ class UserService extends BaseHomeService
} catch (\Exception $exception) { } catch (\Exception $exception) {
return $this->toData('500', lang('system_busy'), [$exception->getMessage(), $exception->getTrace()]); return $this->toData('500', lang('system_busy'), [$exception->getMessage(), $exception->getTrace()]);
} }
} }
/** /**
@ -955,7 +1019,6 @@ class UserService extends BaseHomeService
// 返回结果 // 返回结果
return $this->toData('0', 'successful'); return $this->toData('0', 'successful');
} catch (ValidateException $validateException) { } catch (ValidateException $validateException) {
// 参数校验失败 异常类 // 参数校验失败 异常类
$message = $validateException->getError(); $message = $validateException->getError();
@ -963,7 +1026,6 @@ class UserService extends BaseHomeService
} catch (\Exception $exception) { } catch (\Exception $exception) {
return $this->toData('500', lang('system_busy'), [$exception->getMessage(), $exception->getTrace()]); return $this->toData('500', lang('system_busy'), [$exception->getMessage(), $exception->getTrace()]);
} }
} }
/** /**
@ -1010,7 +1072,6 @@ class UserService extends BaseHomeService
// 返回结果 // 返回结果
return $this->toData('0', 'successful'); return $this->toData('0', 'successful');
} catch (ValidateException $validateException) { } catch (ValidateException $validateException) {
// 参数校验失败 异常类 // 参数校验失败 异常类
$message = $validateException->getError(); $message = $validateException->getError();
@ -1018,7 +1079,6 @@ class UserService extends BaseHomeService
} catch (\Exception $exception) { } catch (\Exception $exception) {
return $this->toData('500', lang('system_busy'), [$exception->getMessage(), $exception->getTrace()]); return $this->toData('500', lang('system_busy'), [$exception->getMessage(), $exception->getTrace()]);
} }
} }
/** /**
@ -1064,7 +1124,6 @@ class UserService extends BaseHomeService
// 返回结果 // 返回结果
return $this->toData('0', 'successful'); return $this->toData('0', 'successful');
} catch (ValidateException $validateException) { } catch (ValidateException $validateException) {
// 参数校验失败 异常类 // 参数校验失败 异常类
$message = $validateException->getError(); $message = $validateException->getError();
@ -1117,7 +1176,6 @@ class UserService extends BaseHomeService
// 返回结果 // 返回结果
return $this->toData('0', 'successful'); return $this->toData('0', 'successful');
} catch (ValidateException $validateException) { } catch (ValidateException $validateException) {
// 参数校验失败 异常类 // 参数校验失败 异常类
$message = $validateException->getError(); $message = $validateException->getError();
@ -1125,7 +1183,6 @@ class UserService extends BaseHomeService
} catch (\Exception $exception) { } catch (\Exception $exception) {
return $this->toData('500', lang('system_busy'), [$exception->getMessage(), $exception->getTrace()]); return $this->toData('500', lang('system_busy'), [$exception->getMessage(), $exception->getTrace()]);
} }
} }
/** /**
@ -1177,7 +1234,6 @@ class UserService extends BaseHomeService
// 返回结果 // 返回结果
return $this->toData('0', 'successful'); return $this->toData('0', 'successful');
} catch (ValidateException $validateException) { } catch (ValidateException $validateException) {
// 参数校验失败 异常类 // 参数校验失败 异常类
$message = $validateException->getError(); $message = $validateException->getError();
@ -1185,7 +1241,6 @@ class UserService extends BaseHomeService
} catch (\Exception $exception) { } catch (\Exception $exception) {
return $this->toData('500', lang('system_busy'), [$exception->getMessage(), $exception->getTrace()]); return $this->toData('500', lang('system_busy'), [$exception->getMessage(), $exception->getTrace()]);
} }
} }
/** /**
@ -1231,7 +1286,6 @@ class UserService extends BaseHomeService
// 返回结果 // 返回结果
return $this->toData('0', 'successful'); return $this->toData('0', 'successful');
} catch (ValidateException $validateException) { } catch (ValidateException $validateException) {
// 参数校验失败 异常类 // 参数校验失败 异常类
$message = $validateException->getError(); $message = $validateException->getError();
@ -1239,7 +1293,6 @@ class UserService extends BaseHomeService
} catch (\Exception $exception) { } catch (\Exception $exception) {
return $this->toData('500', lang('system_busy'), [$exception->getMessage(), $exception->getTrace()]); return $this->toData('500', lang('system_busy'), [$exception->getMessage(), $exception->getTrace()]);
} }
} }
/** /**
@ -1284,7 +1337,6 @@ class UserService extends BaseHomeService
// 返回结果 // 返回结果
return $this->toData('0', 'successful'); return $this->toData('0', 'successful');
} catch (ValidateException $validateException) { } catch (ValidateException $validateException) {
// 参数校验失败 异常类 // 参数校验失败 异常类
$message = $validateException->getError(); $message = $validateException->getError();
@ -1336,7 +1388,6 @@ class UserService extends BaseHomeService
// 返回结果 // 返回结果
return $this->toData('0', 'successful'); return $this->toData('0', 'successful');
} catch (ValidateException $validateException) { } catch (ValidateException $validateException) {
// 参数校验失败 异常类 // 参数校验失败 异常类
$message = $validateException->getError(); $message = $validateException->getError();
@ -1453,7 +1504,6 @@ class UserService extends BaseHomeService
// 返回结果 // 返回结果
return $this->toData('0', 'successful'); return $this->toData('0', 'successful');
} catch (ValidateException $validateException) { } catch (ValidateException $validateException) {
// 参数校验失败 异常类 // 参数校验失败 异常类
$message = $validateException->getError(); $message = $validateException->getError();
@ -1553,7 +1603,6 @@ class UserService extends BaseHomeService
// 返回结果 // 返回结果
return $this->toData('0', 'successful'); return $this->toData('0', 'successful');
} catch (ValidateException $validateException) { } catch (ValidateException $validateException) {
// 参数校验失败 异常类 // 参数校验失败 异常类
$message = $validateException->getError(); $message = $validateException->getError();
@ -1575,7 +1624,6 @@ class UserService extends BaseHomeService
$list = UserLoanModel::getUserLoanList($data); $list = UserLoanModel::getUserLoanList($data);
// 返回结果 // 返回结果
return $this->toData('0', 'successful', $list); return $this->toData('0', 'successful', $list);
} catch (ValidateException $validateException) { } catch (ValidateException $validateException) {
// 参数校验失败 异常类 // 参数校验失败 异常类
$message = $validateException->getError(); $message = $validateException->getError();
@ -1600,7 +1648,6 @@ class UserService extends BaseHomeService
} catch (\Exception $exception) { } catch (\Exception $exception) {
return $this->toData('500', lang('system_busy'), [$exception->getMessage(), $exception->getTrace()]); return $this->toData('500', lang('system_busy'), [$exception->getMessage(), $exception->getTrace()]);
} }
} }
/** /**
@ -1680,7 +1727,6 @@ class UserService extends BaseHomeService
} }
return $this->toData('0', 'Already submitted'); return $this->toData('0', 'Already submitted');
} catch (\Exception $exception) { } catch (\Exception $exception) {
return $this->toData('500', lang('system_busy'), [$exception->getMessage(), $exception->getTrace()]); return $this->toData('500', lang('system_busy'), [$exception->getMessage(), $exception->getTrace()]);
} }
@ -1751,11 +1797,11 @@ class UserService extends BaseHomeService
'frozen_num' => 0, 'frozen_num' => 0,
]); ]);
} }
} }
return $this->toData('0', 'success.', []); return $this->toData('0', 'success.', []);
} }
public function applyTestMoney($userId,$param){ public function applyTestMoney($userId, $param)
{
if (empty($userId) || $userId <= 0) { if (empty($userId) || $userId <= 0) {
return $this->toData('500', lang('please_log_in_first')); return $this->toData('500', lang('please_log_in_first'));
} }
@ -1869,6 +1915,7 @@ class UserService extends BaseHomeService
'page_url' => $param['page_url'], 'page_url' => $param['page_url'],
'module' => $param['module'], 'module' => $param['module'],
'remark' => $param['remark'], 'remark' => $param['remark'],
'ip' => $param['ip'] ?? '',
]); ]);
if (empty($userAccessLog)) { if (empty($userAccessLog)) {
return $this->toData('500', lang('system_busy')); return $this->toData('500', lang('system_busy'));
@ -1880,7 +1927,8 @@ class UserService extends BaseHomeService
} }
// 用户调用接口次数记录 // 用户调用接口次数记录
public function apiCalledRecord($userId, $param){ public function apiCalledRecord($userId, $param)
{
try { try {
if (empty($param['api_name'])) { if (empty($param['api_name'])) {
return $this->toData('400', lang('parameter_error')); return $this->toData('400', lang('parameter_error'));

9
app/model/ApiLogModel.php

@ -0,0 +1,9 @@
<?php
namespace app\model;
class ApiLogModel extends BaseModel
{
protected $name = 'api_log';
}

79
app/model/ForexListMode.php

@ -0,0 +1,79 @@
<?php
namespace app\model;
/**
* @property int id
* @property string trade_name
* @property string status
* @property string is_owner
* @property string logo_link
* @property string face_value
* @property string info
* @property string sort
* @property string min_pry
* @property string max_pry
* @property string compel_num
* @property string keep_decimal
* @property string create_time
* @property string update_time
*/
class ForexListMode extends BaseModel
{
protected $name = 'forex_list';
protected $pk = 'id';
public static function getMarketList($data): array
{
$where=[
['status','=',1]
];
if(!empty($data['trade_name'])){
$where[]=[
'trade_name','like',strtoupper($data['trade_name']).'%'
];
}
if($data['page']<1){
$data['page']=1;
}
if($data['page_size']<1){
$data['page_size']=10;
}
$count=self::where($where)->count();
$list = self::where($where)->field('trade_name as name,trade_name as code')->page($data['page'],$data['page_size'])->select();
if(empty($list)){
return [];
}
return [
'total'=>$count,
'list'=>$list->toArray(),
];
}
public static function existMarket($trade_name):bool
{
$id=self::where('trade_name',$trade_name)->value('id');
return $id >0;
}
public static function getMarketFaceList($type=0)
{
$list=self::where('status',1)->field('face_value,trade_name as name,trade_name as code,sort,max_pry,min_pry')->select();
if(empty($list)){
return [];
}
$list=$list->toArray();
if($type==1){
foreach ($list as $val){
$face_list[$val['name']]=$val['face_value'];
}
}else{
$face_list=$list;
}
return $face_list;
}
}

7
app/model/UserAccessLogModel.php

@ -1,7 +1,14 @@
<?php <?php
namespace app\model; namespace app\model;
class UserAccessLogModel extends BaseModel class UserAccessLogModel extends BaseModel
{ {
protected $name = 'user_access_log'; protected $name = 'user_access_log';
// 关联 User 模型
public function user()
{
return $this->belongsTo(UserModel::class, 'user_id', 'user_id');
}
} }

7
app/model/VipCodeModel.php

@ -0,0 +1,7 @@
<?php
namespace app\model;
class VipCodeModel extends BaseModel
{
protected $name = 'vip_code';
}

8
app/model/WatchVideoLogModel.php

@ -0,0 +1,8 @@
<?php
namespace app\model;
class WatchVideoLogModel extends BaseModel
{
protected $name = 'watch_video_log';
}

18
app/utility/UnqId.php

@ -35,4 +35,22 @@ class UnqId
$encryptPassword = $this->encryptPassword($string, $salt); $encryptPassword = $this->encryptPassword($string, $salt);
return $encryptPassword == $password; return $encryptPassword == $password;
} }
// 生成随机字符
public function generateRandomCode($length = 15): string
{
$chars = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz';
$charLength = strlen($chars);
$code = '';
// 生成足够长度的安全随机数
$randomBytes = random_bytes($length);
for ($i = 0; $i < $length; $i++) {
$code .= $chars[random_int(0, $charLength - 1)];
}
return $code;
}
} }

9
composer.json

@ -33,13 +33,8 @@
"geoip2/geoip2": "2.13", "geoip2/geoip2": "2.13",
"guzzlehttp/guzzle": "^7.7", "guzzlehttp/guzzle": "^7.7",
"lcobucci/jwt": "^4.0", "lcobucci/jwt": "^4.0",
"phpoffice/phpspreadsheet": "^1.29", "phpoffice/phpspreadsheet": "^4.3",
"ext-json": "*", "ext-json": "*"
"aws/aws-sdk-php": "^3.337",
"workerman/gatewayclient": "^3.1",
"pusher/pusher-push-notifications": "^2.0",
"mongodb/mongodb": "^1.21",
"ext-mongodb": "*"
}, },
"require-dev": { "require-dev": {
"symfony/var-dumper": "^4.2", "symfony/var-dumper": "^4.2",

1
config/console.php

@ -5,5 +5,6 @@
return [ return [
// 指令定义 // 指令定义
'commands' => [ 'commands' => [
\app\command\ApiLogCommand::class,
], ],
]; ];

Loading…
Cancel
Save