20
This commit is contained in:
@@ -9,3 +9,4 @@ app/command/Test.php
|
|||||||
runtime
|
runtime
|
||||||
vendor
|
vendor
|
||||||
public/shunliao.apk
|
public/shunliao.apk
|
||||||
|
.user.ini
|
||||||
|
|||||||
@@ -1 +1 @@
|
|||||||
open_basedir=/www/wwwroot/admin/:/tmp/
|
open_basedir=/www/wwwroot/im/admin/:/tmp/
|
||||||
@@ -0,0 +1,96 @@
|
|||||||
|
<?php
|
||||||
|
|
||||||
|
namespace app\api\controller;
|
||||||
|
|
||||||
|
use support\Request;
|
||||||
|
use support\Response;
|
||||||
|
use hg\apidoc\annotation as Apidoc;
|
||||||
|
use app\model\User;
|
||||||
|
use app\model\Album as AlbumModel;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 群相册
|
||||||
|
*/
|
||||||
|
class AlbumController extends BaseController
|
||||||
|
{
|
||||||
|
public $noNeedAuth = ['*'];
|
||||||
|
public $noNeedLogin = [];
|
||||||
|
/**
|
||||||
|
* @Apidoc\Title("群相册列表")
|
||||||
|
* @Apidoc\Method("POST")
|
||||||
|
* @Apidoc\Param("group_id", type="string", require=true, desc="群ID")
|
||||||
|
* @Apidoc\Param("offset", type="int", require=false, desc="偏移量,和页码二选一",default=0)
|
||||||
|
* @Apidoc\Param("page", type="int", require=false, desc="页码",default=1)
|
||||||
|
* @Apidoc\Param("limit", type="int", require=true, desc="分页大小",default=10)
|
||||||
|
*/
|
||||||
|
function list(Request $request): Response
|
||||||
|
{
|
||||||
|
$user = \support\Jwt::getUser();
|
||||||
|
$limit = $request->post('limit',10);
|
||||||
|
$offset = $request->post('offset',0);
|
||||||
|
$group_id = $request->post('groupID') ?:$request->post('group_id');
|
||||||
|
//$ls = $this->get_user_in_group($group_id);
|
||||||
|
$query = AlbumModel::where('group_id',$group_id)
|
||||||
|
->order('id','desc');
|
||||||
|
if($offset){
|
||||||
|
$list = $query->where('id','<',$offset)->limit($offset,$limit);
|
||||||
|
}else{
|
||||||
|
$list = $query->paginate($limit);
|
||||||
|
}
|
||||||
|
return $this->success('ok',$list);
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* @Apidoc\Title("创建相册")
|
||||||
|
* @Apidoc\Method("POST")
|
||||||
|
* @Apidoc\Param("groupID", type="string", require=true, desc="群ID")
|
||||||
|
* @Apidoc\Param("title", type="string", require=true, desc="标题")
|
||||||
|
* @Apidoc\Param("image", type="int", require=false, desc="封面ID")
|
||||||
|
*/
|
||||||
|
function create(Request $request): Response
|
||||||
|
{
|
||||||
|
$user_id = \support\Jwt\JwtToken::getCurrentId();
|
||||||
|
$data = [
|
||||||
|
'user_id' => $user_id,
|
||||||
|
'group_id' => $request->post('groupID'),
|
||||||
|
'title' => input('title'),
|
||||||
|
'image' => input('image'),
|
||||||
|
];
|
||||||
|
$result = AlbumModel::create($data);
|
||||||
|
return $this->success('ok',$result);
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* @Apidoc\Title("更新")
|
||||||
|
* @Apidoc\Method("POST")
|
||||||
|
* @Apidoc\Param("id", type="string", require=true, desc="ID")
|
||||||
|
* @Apidoc\Param("title", type="string", require=true, desc="标题")
|
||||||
|
* @Apidoc\Param("image", type="int", require=false, desc="封面ID")
|
||||||
|
*/
|
||||||
|
function update(Request $request): Response
|
||||||
|
{
|
||||||
|
$id = $request->input('id');
|
||||||
|
$image = $request->input('image');
|
||||||
|
$title = $request->input('title');
|
||||||
|
$album = AlbumModel::find($id);
|
||||||
|
if($title){
|
||||||
|
$album->title = $title;
|
||||||
|
}
|
||||||
|
if($image){
|
||||||
|
$album->image = $image;
|
||||||
|
}
|
||||||
|
$album->save();
|
||||||
|
return $this->success('ok',$album);
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* @Apidoc\Title("删除")
|
||||||
|
* @Apidoc\Method("POST")
|
||||||
|
* @Apidoc\Param("id", type="string", require=true, desc="ID")
|
||||||
|
*/
|
||||||
|
function delete(Request $request): Response
|
||||||
|
{
|
||||||
|
$id = Input('id');
|
||||||
|
$album = AlbumModel::whereIn('id',condition: $id)->find();
|
||||||
|
$album->delete();
|
||||||
|
|
||||||
|
return $this->success('ok');
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -90,4 +90,17 @@ class CollectionController extends BaseController{
|
|||||||
|
|
||||||
return $this->success('发布成功', ['collection' => $collection]);
|
return $this->success('发布成功', ['collection' => $collection]);
|
||||||
}
|
}
|
||||||
|
/**
|
||||||
|
* 删除收藏
|
||||||
|
* @Apidoc\Param("id", type="int",require=true, desc="收藏id")
|
||||||
|
* @param Request $request
|
||||||
|
* @return Response
|
||||||
|
*/
|
||||||
|
function delete(Request $request): Response
|
||||||
|
{
|
||||||
|
$user = \support\Jwt::getUser();
|
||||||
|
$id = $request->post('id');
|
||||||
|
CollectionModel::where('id',$id)->where('user_id',$user->id)->delete();
|
||||||
|
return $this->success('删除成功');
|
||||||
|
}
|
||||||
}
|
}
|
||||||
@@ -56,6 +56,33 @@ class CommonController extends BaseController{
|
|||||||
$config['recharge_status_list'] = \app\enum\RechargeStatus::toArray();
|
$config['recharge_status_list'] = \app\enum\RechargeStatus::toArray();
|
||||||
$config['withdrawl_status_list'] = \app\enum\WithdrawlStatus::toArray();
|
$config['withdrawl_status_list'] = \app\enum\WithdrawlStatus::toArray();
|
||||||
$config['server_status_list'] = \app\enum\ServerStatus::toArray();
|
$config['server_status_list'] = \app\enum\ServerStatus::toArray();
|
||||||
|
$config['see_point_awards'] = [
|
||||||
|
[
|
||||||
|
'name'=>'S1',
|
||||||
|
'award'=>0.05,
|
||||||
|
'total'=>50,
|
||||||
|
],
|
||||||
|
[
|
||||||
|
'name'=>'S2',
|
||||||
|
'award'=>0.1,
|
||||||
|
'total'=>100,
|
||||||
|
],
|
||||||
|
[
|
||||||
|
'name'=>'S3',
|
||||||
|
'award'=>0.15,
|
||||||
|
'total'=>1000,
|
||||||
|
],
|
||||||
|
[
|
||||||
|
'name'=>'S4',
|
||||||
|
'award'=>0.2,
|
||||||
|
'total'=>5000,
|
||||||
|
],
|
||||||
|
[
|
||||||
|
'name'=>'S5',
|
||||||
|
'award'=>0.25,
|
||||||
|
'total'=>20000,
|
||||||
|
]
|
||||||
|
];
|
||||||
//$config['getFriendList'] = $request->IM->friend->getFriendList('100006');
|
//$config['getFriendList'] = $request->IM->friend->getFriendList('100006');
|
||||||
return $this->success(__('successful'), $config);
|
return $this->success(__('successful'), $config);
|
||||||
}
|
}
|
||||||
@@ -97,7 +124,9 @@ class CommonController extends BaseController{
|
|||||||
* 注册会员
|
* 注册会员
|
||||||
*
|
*
|
||||||
* @Apidoc\Method ("POST")
|
* @Apidoc\Method ("POST")
|
||||||
|
* @Apidoc\Param("type", type="string",require=true, desc="注册方式:email,mobile")
|
||||||
* @Apidoc\Param("email", type="string",require=true, desc="邮箱")
|
* @Apidoc\Param("email", type="string",require=true, desc="邮箱")
|
||||||
|
* @Apidoc\Param("mobile", type="string",require=true, desc="手机号码")
|
||||||
* @Apidoc\Param("password", type="string",require=true, desc="密码")
|
* @Apidoc\Param("password", type="string",require=true, desc="密码")
|
||||||
* @Apidoc\Param("trade_password", type="string",require=true, desc="交易密码")
|
* @Apidoc\Param("trade_password", type="string",require=true, desc="交易密码")
|
||||||
* @Apidoc\Param("invite_code", type="string",require=true, desc="推荐码")
|
* @Apidoc\Param("invite_code", type="string",require=true, desc="推荐码")
|
||||||
@@ -121,7 +150,7 @@ class CommonController extends BaseController{
|
|||||||
}
|
}
|
||||||
$username = $email;
|
$username = $email;
|
||||||
unset($mobile);
|
unset($mobile);
|
||||||
//captcha_verfiy('email','register',$email,false);
|
captcha_verfiy('email','register',$email,false);
|
||||||
}
|
}
|
||||||
if ($type == 'mobile') {
|
if ($type == 'mobile') {
|
||||||
if(!$mobile || !Validate::regex($mobile, "^1\d{10}$")){
|
if(!$mobile || !Validate::regex($mobile, "^1\d{10}$")){
|
||||||
@@ -129,10 +158,10 @@ class CommonController extends BaseController{
|
|||||||
}
|
}
|
||||||
$username = $mobile;
|
$username = $mobile;
|
||||||
unset($email);
|
unset($email);
|
||||||
//captcha_verfiy('mobile','register',$mobile,false);
|
captcha_verfiy('mobile','register',$mobile,false);
|
||||||
}
|
}
|
||||||
if ($type == 'username') {
|
if ($type == 'username') {
|
||||||
if(!$email || !Validate::is($email, "email")){
|
if(!$username){
|
||||||
return $this->error(__('Username is incorrect'));
|
return $this->error(__('Username is incorrect'));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -151,9 +180,18 @@ class CommonController extends BaseController{
|
|||||||
'role_id' => 1,
|
'role_id' => 1,
|
||||||
'group_id' => 0,
|
'group_id' => 0,
|
||||||
'region' => '86',
|
'region' => '86',
|
||||||
'nickname' => input('nickname','用户_'.substr($username,7)),
|
'nickname' => input('nickname'),
|
||||||
'avatar' => '/static/avatar/'.rand(0,17).'.png',
|
'avatar' => '/static/avatar/'.rand(0,17).'.png',
|
||||||
];
|
];
|
||||||
|
if(empty($extends['nickname'])){
|
||||||
|
if($type == 'mobile'){
|
||||||
|
$extends['nickname'] = '用户_'.substr($username,7);
|
||||||
|
}else if($type == 'email'){
|
||||||
|
$extends['nickname'] = '用户_'.substr(explode('@',$username)[0],7);
|
||||||
|
}else{
|
||||||
|
$extends['nickname'] = $username;
|
||||||
|
}
|
||||||
|
}
|
||||||
if ($invite_code) {
|
if ($invite_code) {
|
||||||
if(strlen($invite_code) == 12){
|
if(strlen($invite_code) == 12){
|
||||||
//系统生产的一次性推荐吗
|
//系统生产的一次性推荐吗
|
||||||
@@ -203,10 +241,12 @@ class CommonController extends BaseController{
|
|||||||
* 登录
|
* 登录
|
||||||
* @Apidoc\Method("POST")
|
* @Apidoc\Method("POST")
|
||||||
* @Apidoc\Param("username", type="string",require=false, desc="用户名登录必填")
|
* @Apidoc\Param("username", type="string",require=false, desc="用户名登录必填")
|
||||||
|
* @Apidoc\Param("email", type="string",require=false, desc="邮箱登录必填")
|
||||||
* @Apidoc\Param("mobile", type="string",require=false, desc="手机号登录必填")
|
* @Apidoc\Param("mobile", type="string",require=false, desc="手机号登录必填")
|
||||||
* @Apidoc\Param("type", type="string",require=true,default="mobile",desc="登录方式,username,mobile,email")
|
* @Apidoc\Param("type", type="string",require=true,default="mobile",desc="登录方式,username,mobile,email")
|
||||||
* @Apidoc\Param("password", type="string",require=false, desc="密码的登录必填")
|
* @Apidoc\Param("password", type="string",require=false, desc="密码的登录必填")
|
||||||
* @Apidoc\Param("code", type="string",require=false, desc="验证码登录必填")
|
* @Apidoc\Param("code", type="string",require=false, desc="验证码登录必填")
|
||||||
|
* @Apidoc\Param("platform", type="string",require=false, desc="平台",default="web")
|
||||||
* @Apidoc\Param("region", type="string",require=false,default="86", desc="区域,手机号登录必填")
|
* @Apidoc\Param("region", type="string",require=false,default="86", desc="区域,手机号登录必填")
|
||||||
*/
|
*/
|
||||||
public function login(Request $request){
|
public function login(Request $request){
|
||||||
@@ -321,11 +361,13 @@ class CommonController extends BaseController{
|
|||||||
* @Apidoc\Param("email", type="string",require=true, desc="邮箱")
|
* @Apidoc\Param("email", type="string",require=true, desc="邮箱")
|
||||||
* @Apidoc\Param("newpassword", type="string",require=true, desc="新密码")
|
* @Apidoc\Param("newpassword", type="string",require=true, desc="新密码")
|
||||||
* @Apidoc\Param("code", type="string",require=true, desc="邮箱验证码,event=reset_trade_pwd")
|
* @Apidoc\Param("code", type="string",require=true, desc="邮箱验证码,event=reset_trade_pwd")
|
||||||
|
* @Apidoc\Param("verify_type", type="string",require=true, desc="验证方式,email,mobile")
|
||||||
*/
|
*/
|
||||||
public function reset_trade_pwd()
|
public function reset_trade_pwd()
|
||||||
{
|
{
|
||||||
$email = input("email");
|
$email = input("email");
|
||||||
$mobile = input("mobile");
|
$mobile = input("mobile");
|
||||||
|
$verify_type = input("verify_type");
|
||||||
$newpassword = input("newpassword");
|
$newpassword = input("newpassword");
|
||||||
if (!$newpassword) {
|
if (!$newpassword) {
|
||||||
return $this->error(__('Invalid parameters'));
|
return $this->error(__('Invalid parameters'));
|
||||||
@@ -334,7 +376,6 @@ class CommonController extends BaseController{
|
|||||||
if (!Validate::check(['newpassword' => $newpassword], ['newpassword' => 'require|regex:\S{6,32}'])) {
|
if (!Validate::check(['newpassword' => $newpassword], ['newpassword' => 'require|regex:\S{6,32}'])) {
|
||||||
return $this->error(__('Trade password must be 6-32 characters'));
|
return $this->error(__('Trade password must be 6-32 characters'));
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!$mobile && !$email){
|
if (!$mobile && !$email){
|
||||||
try{
|
try{
|
||||||
$user = \support\Jwt::getUser();
|
$user = \support\Jwt::getUser();
|
||||||
@@ -342,7 +383,14 @@ class CommonController extends BaseController{
|
|||||||
$user = false;
|
$user = false;
|
||||||
}
|
}
|
||||||
if($user){
|
if($user){
|
||||||
captcha_verfiy('mobile','reset_trade_pwd',$user->mobile);
|
|
||||||
|
if($verify_type == 'email'){
|
||||||
|
captcha_verfiy('email','reset_trade_pwd',$user->email);
|
||||||
|
}else if($verify_type == 'mobile'){
|
||||||
|
captcha_verfiy('mobile','reset_trade_pwd',$user->mobile);
|
||||||
|
}else{
|
||||||
|
return $this->error(__('Unknown verify type'));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}else{
|
}else{
|
||||||
if ($mobile && Validate::regex($mobile, "^1\d{10}$")) {
|
if ($mobile && Validate::regex($mobile, "^1\d{10}$")) {
|
||||||
@@ -402,12 +450,13 @@ class CommonController extends BaseController{
|
|||||||
$list[$code] = time();
|
$list[$code] = time();
|
||||||
cache($key,$list);
|
cache($key,$list);
|
||||||
cache('exp_'.$key,time());
|
cache('exp_'.$key,time());
|
||||||
// addJob([
|
addJob([
|
||||||
// 'email' => $email,
|
'email' => $email,
|
||||||
// 'title' => __("Mt email code"),
|
'title' => __(Config('site.name').' 验证码'),
|
||||||
// 'event' => $event,
|
'event' => $event,
|
||||||
// 'code' => $code
|
'code' => $code
|
||||||
// ],'Email');
|
],'Email');
|
||||||
|
\support\Log::channel('mail')->alert("邮件验证码:".$code.',邮箱:'.$email);
|
||||||
return $this->success(__('Email sent successfully'),[
|
return $this->success(__('Email sent successfully'),[
|
||||||
'code'=> $debug ? $code : ''
|
'code'=> $debug ? $code : ''
|
||||||
]);
|
]);
|
||||||
@@ -443,6 +492,7 @@ class CommonController extends BaseController{
|
|||||||
'event' => $event,
|
'event' => $event,
|
||||||
'code' => $code
|
'code' => $code
|
||||||
],'Sms');
|
],'Sms');
|
||||||
|
\support\Log::channel('mail')->alert("短信验证码:".$code.',手机号:'.$mobile);
|
||||||
return $this->success(__('SMS sent successfully'),[
|
return $this->success(__('SMS sent successfully'),[
|
||||||
'code'=> $debug ? $code : ''
|
'code'=> $debug ? $code : ''
|
||||||
]);
|
]);
|
||||||
|
|||||||
@@ -0,0 +1,120 @@
|
|||||||
|
<?php
|
||||||
|
|
||||||
|
namespace app\api\controller;
|
||||||
|
|
||||||
|
use support\Request;
|
||||||
|
use support\Response;
|
||||||
|
use hg\apidoc\annotation as Apidoc;
|
||||||
|
use app\model\User;
|
||||||
|
use app\model\Gallery as GalleryModel;
|
||||||
|
use app\model\Album as AlbumModel;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 相册的相片
|
||||||
|
*/
|
||||||
|
class GalleryController extends BaseController
|
||||||
|
{
|
||||||
|
public $noNeedAuth = ['*'];
|
||||||
|
public $noNeedLogin = [];
|
||||||
|
/**
|
||||||
|
* @Apidoc\Title("列表")
|
||||||
|
* @Apidoc\Method("POST")
|
||||||
|
* @Apidoc\Param("album_id", type="string", require=true, desc="相册ID")
|
||||||
|
* @Apidoc\Param("offset", type="int", require=false, desc="偏移量,和页码二选一",default=0)
|
||||||
|
* @Apidoc\Param("page", type="int", require=false, desc="页码",default=1)
|
||||||
|
* @Apidoc\Param("limit", type="int", require=true, desc="分页大小",default=10)
|
||||||
|
*/
|
||||||
|
function list(Request $request): Response
|
||||||
|
{
|
||||||
|
$user = \support\Jwt::getUser();
|
||||||
|
$limit = $request->post('limit',10);
|
||||||
|
$offset = $request->post('offset',0);
|
||||||
|
$album_id = $request->post('album_id') ?: 0;
|
||||||
|
//$ls = $this->get_user_in_group($group_id);
|
||||||
|
$query = GalleryModel::where('album_id',$album_id)->order('id','desc');
|
||||||
|
if($offset){
|
||||||
|
$list = $query->where('id','<',$offset)->limit(0,$limit);
|
||||||
|
}else{
|
||||||
|
$list = $query->paginate($limit);
|
||||||
|
}
|
||||||
|
return $this->success('ok',$list);
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* @Apidoc\Title("上传")
|
||||||
|
* @Apidoc\Method("POST")
|
||||||
|
* @Apidoc\Param("album_id", type="string", require=true, desc="相册ID",default=0)
|
||||||
|
* @Apidoc\Param("title", type="string", require=true, desc="标题")
|
||||||
|
* @Apidoc\Param("url", type="string", require=true, desc="图片")
|
||||||
|
* @Apidoc\Param("file", type="file", require=true, desc="图片,没有url得时候必传")
|
||||||
|
*/
|
||||||
|
function create(Request $request): Response
|
||||||
|
{
|
||||||
|
$user_id = \support\Jwt\JwtToken::getCurrentId();
|
||||||
|
$res = $this->_upload($request);
|
||||||
|
if(is_string($res)){
|
||||||
|
return $this->fail( $res);
|
||||||
|
}
|
||||||
|
$album_id = $request->post('album_id') ?: 0;
|
||||||
|
$album = AlbumModel::find($album_id);
|
||||||
|
if(!$album){
|
||||||
|
return $this->fail('相册不存在');
|
||||||
|
}
|
||||||
|
$insert_data = [];
|
||||||
|
foreach($res as $item){
|
||||||
|
$insert_data[] = [
|
||||||
|
'user_id' => $user_id,
|
||||||
|
'group_id' => $album->group_id,
|
||||||
|
'album_id' => $album_id,
|
||||||
|
'title' => $item['origin_name'],
|
||||||
|
'url' => $item['file_name'],
|
||||||
|
];
|
||||||
|
}
|
||||||
|
$result = GalleryModel::saveAll($insert_data);
|
||||||
|
return $this->success('ok',$result[0]);
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* @Apidoc\Title("更新")
|
||||||
|
* @Apidoc\Method("POST")
|
||||||
|
* @Apidoc\Param("id", type="string", require=true, desc="ID")
|
||||||
|
* @Apidoc\Param("title", type="string", require=true, desc="标题")
|
||||||
|
* @Apidoc\Param("url", type="string", require=true, desc="图片")
|
||||||
|
*/
|
||||||
|
function update(Request $request): Response
|
||||||
|
{
|
||||||
|
$id = $request->input('id');
|
||||||
|
$title = $request->input('title');
|
||||||
|
$url = $request->input('url');
|
||||||
|
$album = GalleryModel::find($id);
|
||||||
|
if($album){
|
||||||
|
if($title){
|
||||||
|
$album->title = $title;
|
||||||
|
}
|
||||||
|
if($url){
|
||||||
|
$album->url = $url;
|
||||||
|
}
|
||||||
|
$album->save();
|
||||||
|
}
|
||||||
|
return $this->success('ok',$album);
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* @Apidoc\Title("删除")
|
||||||
|
* @Apidoc\Method("POST")
|
||||||
|
* @Apidoc\Param("id", type="string", require=true, desc="ID")
|
||||||
|
*/
|
||||||
|
function delete(Request $request): Response
|
||||||
|
{
|
||||||
|
$ids = Input('ids');
|
||||||
|
GalleryModel::whereIn('id',condition: $ids)->delete();
|
||||||
|
return $this->success('ok');
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* 获取在群里的角色
|
||||||
|
* @Apidoc\NotParse()
|
||||||
|
* @Apidoc\NotDebug()
|
||||||
|
*/
|
||||||
|
private function get_user_in_group($group_id='',$user_id='')
|
||||||
|
{
|
||||||
|
$list = request()->IM->group->getGroupMemberList($group_id,$user_id);
|
||||||
|
return $list;
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -6,7 +6,7 @@ use support\Request;
|
|||||||
use support\Response;
|
use support\Response;
|
||||||
use hg\apidoc\annotation as Apidoc;
|
use hg\apidoc\annotation as Apidoc;
|
||||||
use app\model\User;
|
use app\model\User;
|
||||||
use app\model\Album as AlbumModel;
|
use app\model\Gallery as AlbumModel;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 群组管理
|
* 群组管理
|
||||||
@@ -19,7 +19,7 @@ class GroupController extends BaseController
|
|||||||
* @Apidoc\Title("群相片列表")
|
* @Apidoc\Title("群相片列表")
|
||||||
* @Apidoc\Method("POST")
|
* @Apidoc\Method("POST")
|
||||||
* @Apidoc\Param("group_id", type="string", require=true, desc="群ID")
|
* @Apidoc\Param("group_id", type="string", require=true, desc="群ID")
|
||||||
* @Apidoc\Param("page", type="int", require=true, desc="页码",default=1)
|
* @Apidoc\Param("offset", type="int", require=true, desc="偏移量",default=99999999999999)
|
||||||
* @Apidoc\Param("limit", type="int", require=true, desc="分页大小",default=10)
|
* @Apidoc\Param("limit", type="int", require=true, desc="分页大小",default=10)
|
||||||
*/
|
*/
|
||||||
function album_list(Request $request): Response
|
function album_list(Request $request): Response
|
||||||
|
|||||||
@@ -401,6 +401,12 @@ class MomentsController extends BaseController{
|
|||||||
$result[] = \support\Encrypt::userIDDecode($userID);
|
$result[] = \support\Encrypt::userIDDecode($userID);
|
||||||
return $result;
|
return $result;
|
||||||
}
|
}
|
||||||
|
/**
|
||||||
|
* 删除朋友圈
|
||||||
|
* @Apidoc\Method("POST")
|
||||||
|
* @Apidoc\Param("id", type="int",require=true, desc="朋友圈动态ID")
|
||||||
|
* @return Response
|
||||||
|
*/
|
||||||
function delete(Request $request): Response{
|
function delete(Request $request): Response{
|
||||||
$id = $request->post('id');
|
$id = $request->post('id');
|
||||||
$user = \support\Jwt::getUser();
|
$user = \support\Jwt::getUser();
|
||||||
@@ -422,7 +428,8 @@ class MomentsController extends BaseController{
|
|||||||
}
|
}
|
||||||
/**
|
/**
|
||||||
* 设置朋友圈背景
|
* 设置朋友圈背景
|
||||||
* @param Request $request
|
* @Apidoc\Method("POST")
|
||||||
|
* @Apidoc\Param("file", type="File",require=true, desc="文件")
|
||||||
* @return Response
|
* @return Response
|
||||||
*/
|
*/
|
||||||
function setBanner(Request $request){
|
function setBanner(Request $request){
|
||||||
|
|||||||
@@ -0,0 +1,189 @@
|
|||||||
|
<?php
|
||||||
|
namespace app\api\controller;
|
||||||
|
|
||||||
|
use app\model\User as UserModel;
|
||||||
|
use app\model\Card;
|
||||||
|
use app\model\Cdkey;
|
||||||
|
use support\think\Db;
|
||||||
|
use hg\apidoc\annotation as Apidoc;
|
||||||
|
use Tinywan\Validate\Facade\Validate;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 通行证
|
||||||
|
*/
|
||||||
|
class PassportController extends BaseController{
|
||||||
|
/**
|
||||||
|
* 不需要鉴权的方法
|
||||||
|
* @var array
|
||||||
|
*/
|
||||||
|
public $noNeedAuth = ['*'];
|
||||||
|
public $noNeedLogin = [];
|
||||||
|
/**
|
||||||
|
* 安全验证
|
||||||
|
* @Apidoc\Method("POST")
|
||||||
|
* @Apidoc\Param("verify_type", type="string", require=true, desc="验证类型,email或mobile")
|
||||||
|
* @Apidoc\Param("code", type="string", require=true, desc="验证码,event=verify")
|
||||||
|
*/
|
||||||
|
public function security_verify()
|
||||||
|
{
|
||||||
|
$user = \support\Jwt::getUser();
|
||||||
|
$verify_type = input('verify_type');
|
||||||
|
if($verify_type=='mobile'){
|
||||||
|
captcha_verfiy('mobile', 'verify', $user->mobile);
|
||||||
|
}else if($verify_type == 'email'){
|
||||||
|
captcha_verfiy('email', 'verify', $user->email);
|
||||||
|
}else{
|
||||||
|
return $this->error(__('Invalid verify type'));
|
||||||
|
}
|
||||||
|
return $this->success(__('Security verify successfully'));
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* 绑定手机号
|
||||||
|
* @Apidoc\Method("POST")
|
||||||
|
* @Apidoc\Param("region", type="string", require=true, desc="区域代码")
|
||||||
|
* @Apidoc\Param("mobile", type="string", require=true, desc="手机号")
|
||||||
|
* @Apidoc\Param("code", type="string", require=true, desc="验证码,event=bind_mobile")
|
||||||
|
*/
|
||||||
|
public function bind_mobile()
|
||||||
|
{
|
||||||
|
$user = \support\Jwt::getUser();
|
||||||
|
$mobile = input('mobile');
|
||||||
|
$region = input('region');
|
||||||
|
|
||||||
|
// 验证手机号格式
|
||||||
|
if (!$mobile || !Validate::regex($mobile, "^1\d{10}$")) {
|
||||||
|
return $this->error(__('Incorrect mobile number format'));
|
||||||
|
}
|
||||||
|
|
||||||
|
// 验证手机号唯一性
|
||||||
|
if (UserModel::where('mobile', $mobile)->where('region',$region)->where('id', '<>', $user->id)->find()) {
|
||||||
|
return $this->error(__('Mobile number already exists'));
|
||||||
|
}
|
||||||
|
|
||||||
|
// 验证验证码
|
||||||
|
captcha_verfiy('mobile', 'bind_mobile', $mobile);
|
||||||
|
|
||||||
|
// 更新用户信息
|
||||||
|
$user->mobile = $mobile;
|
||||||
|
$user->region = $region;
|
||||||
|
//$user->mobile_verify = 1;
|
||||||
|
$user->save();
|
||||||
|
|
||||||
|
return $this->success(__('Mobile number bound successfully'));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 绑定邮箱
|
||||||
|
* @Apidoc\Method("POST")
|
||||||
|
* @Apidoc\Param("email", type="string", require=true, desc="邮箱")
|
||||||
|
* @Apidoc\Param("code", type="string", require=true, desc="验证码,event=bind_email")
|
||||||
|
*/
|
||||||
|
public function bind_email()
|
||||||
|
{
|
||||||
|
$user = \support\Jwt::getUser();
|
||||||
|
$email = input('email');
|
||||||
|
// 验证邮箱格式
|
||||||
|
if (!$email || !Validate::email($email)) {
|
||||||
|
return $this->error(__('Incorrect email format'));
|
||||||
|
}
|
||||||
|
|
||||||
|
// 验证邮箱唯一性
|
||||||
|
if (UserModel::where('email', $email)->where('id', '<>', $user->id)->find()) {
|
||||||
|
return $this->error(__('Email already exists'));
|
||||||
|
}
|
||||||
|
captcha_verfiy('email', 'bind_email', $email);
|
||||||
|
|
||||||
|
|
||||||
|
// 更新用户信息
|
||||||
|
$user->email = $email;
|
||||||
|
//$user->email_verify = 1;
|
||||||
|
$user->save();
|
||||||
|
|
||||||
|
return $this->success(__('Email bound successfully'));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 绑定用户名
|
||||||
|
* @Apidoc\Method("POST")
|
||||||
|
* @Apidoc\Param("username", type="string", require=true, desc="用户名")
|
||||||
|
* @Apidoc\Param("verify_type", type="string", require=true, desc="验证类型,email或mobile")
|
||||||
|
* @Apidoc\Param("code", type="string", require=true, desc="验证码,event=bind_username")
|
||||||
|
*/
|
||||||
|
public function bind_username()
|
||||||
|
{
|
||||||
|
$user = \support\Jwt::getUser();
|
||||||
|
$username = input('username');
|
||||||
|
$verify_type = input('verify_type');
|
||||||
|
|
||||||
|
// 验证用户名格式
|
||||||
|
if (!$username || strlen($username) < 3 || strlen($username) > 20) {
|
||||||
|
return $this->error(__('Username length must be between 3 and 20 characters'));
|
||||||
|
}
|
||||||
|
|
||||||
|
// 验证用户名唯一性
|
||||||
|
if (UserModel::where('username', $username)->where('id', '<>', $user->id)->find()) {
|
||||||
|
return $this->error(__('Username already exists'));
|
||||||
|
}
|
||||||
|
|
||||||
|
if($verify_type == 'mobile'){
|
||||||
|
captcha_verfiy('mobile', 'bind_username', $user->mobile);
|
||||||
|
}else if($verify_type == 'email'){
|
||||||
|
captcha_verfiy('email', 'bind_username', $user->email);
|
||||||
|
}
|
||||||
|
|
||||||
|
// 更新用户信息
|
||||||
|
$user->username = $username;
|
||||||
|
$user->save();
|
||||||
|
|
||||||
|
return $this->success(__('Username bound successfully'));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 解绑手机号
|
||||||
|
* @Apidoc\Method("POST")
|
||||||
|
* @Apidoc\Param("code", type="string", require=true, desc="验证码,event=unbind_mobile")
|
||||||
|
*/
|
||||||
|
public function unbind_mobile()
|
||||||
|
{
|
||||||
|
$user = \support\Jwt::getUser();
|
||||||
|
|
||||||
|
if (!$user->mobile) {
|
||||||
|
return $this->error(__('Mobile number not bound'));
|
||||||
|
}
|
||||||
|
|
||||||
|
// 验证验证码
|
||||||
|
captcha_verfiy('mobile', 'unbind_mobile', $user->mobile);
|
||||||
|
|
||||||
|
// 更新用户信息
|
||||||
|
$user->mobile = '';
|
||||||
|
$user->mobile_verify = 0;
|
||||||
|
$user->save();
|
||||||
|
|
||||||
|
return $this->success(__('Mobile number unbound successfully'));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 解绑邮箱
|
||||||
|
* @Apidoc\Method("POST")
|
||||||
|
* @Apidoc\Param("code", type="string", require=true, desc="验证码,event=unbind_email")
|
||||||
|
*/
|
||||||
|
public function unbind_email()
|
||||||
|
{
|
||||||
|
$user = \support\Jwt::getUser();
|
||||||
|
|
||||||
|
if (!$user->email) {
|
||||||
|
return $this->error(__('Email not bound'));
|
||||||
|
}
|
||||||
|
|
||||||
|
// 验证验证码
|
||||||
|
captcha_verfiy('email', 'unbind_email', $user->email);
|
||||||
|
|
||||||
|
// 更新用户信息
|
||||||
|
$user->email = '';
|
||||||
|
$user->email_verify = 0;
|
||||||
|
$user->save();
|
||||||
|
|
||||||
|
return $this->success(__('Email unbound successfully'));
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
@@ -47,8 +47,7 @@ class TeamController extends BaseController{
|
|||||||
// 'user_sales_reward' => cache('user_sales_reward_'.$user_id)??0,//销售奖
|
// 'user_sales_reward' => cache('user_sales_reward_'.$user_id)??0,//销售奖
|
||||||
// 'user_output_reward' => cache('user_output_reward_'.$user_id)??0,//产值奖
|
// 'user_output_reward' => cache('user_output_reward_'.$user_id)??0,//产值奖
|
||||||
// 'user_withdrawl_reward' => cache('user_withdrawl_reward'.$user_id)??0,//提现奖
|
// 'user_withdrawl_reward' => cache('user_withdrawl_reward'.$user_id)??0,//提现奖
|
||||||
'user' => $user[0],
|
'user' => $user[0]
|
||||||
|
|
||||||
];
|
];
|
||||||
return $this->success(__('successful'),$result);
|
return $this->success(__('successful'),$result);
|
||||||
|
|
||||||
|
|||||||
@@ -95,20 +95,46 @@ class UserController extends BaseController{
|
|||||||
* @Apidoc\Param("password", type="string",require=true, desc="旧密码(新设时可用为空)")
|
* @Apidoc\Param("password", type="string",require=true, desc="旧密码(新设时可用为空)")
|
||||||
* @Apidoc\Param("newpassword", type="string",require=true, desc="新密码")
|
* @Apidoc\Param("newpassword", type="string",require=true, desc="新密码")
|
||||||
* @Apidoc\Param("renewpassword", type="string",require=true, desc="新密码")
|
* @Apidoc\Param("renewpassword", type="string",require=true, desc="新密码")
|
||||||
|
* @Apidoc\Param("code", type="string",require=true, desc="验证码")
|
||||||
|
* @Apidoc\Param("verify_type", type="string",require=true, desc="验证方式,email,mobile,password")
|
||||||
*/
|
*/
|
||||||
public function change_trade_password(){
|
public function change_trade_password(){
|
||||||
|
$user = \support\Jwt::getUser();
|
||||||
$password = input('password');
|
$password = input('password');
|
||||||
$newpassword = input('newpassword');
|
$newpassword = input('newpassword');
|
||||||
$renewpassword = input('renewpassword');
|
$renewpassword = input('renewpassword');
|
||||||
|
$verify_type = input('verify_type');
|
||||||
if (!$newpassword || !$renewpassword || $newpassword !== $renewpassword) {
|
if (!$newpassword || !$renewpassword || $newpassword !== $renewpassword) {
|
||||||
return $this->error(__('Invalid parameters'));
|
return $this->error(__('Invalid parameters'));
|
||||||
}
|
}
|
||||||
try{
|
if($verify_type == 'email'){
|
||||||
\support\Jwt::change_trade_pwd($newpassword,$password);
|
captcha_verfiy('email','reset_trade_pwd',$user->email);
|
||||||
return $this->success(__('Reset trade password successful'));
|
try{
|
||||||
} catch (\Throwable $e) {
|
\support\Jwt::change_trade_pwd($newpassword,'',true);
|
||||||
return $this->error($e->getMessage());
|
return $this->success(__('Reset trade password successful'));
|
||||||
|
} catch (\Throwable $e) {
|
||||||
|
return $this->error($e->getMessage());
|
||||||
|
}
|
||||||
|
}else if($verify_type == 'mobile'){
|
||||||
|
captcha_verfiy('mobile','reset_trade_pwd',$user->mobile);
|
||||||
|
try{
|
||||||
|
\support\Jwt::change_trade_pwd($newpassword,'',true);
|
||||||
|
return $this->success(__('Reset trade password successful'));
|
||||||
|
} catch (\Throwable $e) {
|
||||||
|
return $this->error($e->getMessage());
|
||||||
|
}
|
||||||
|
}else if($verify_type == 'password'){
|
||||||
|
if (!$password) {
|
||||||
|
return $this->error(__('Invalid parameters'));
|
||||||
|
}
|
||||||
|
try{
|
||||||
|
\support\Jwt::change_trade_pwd($newpassword,$password);
|
||||||
|
return $this->success(__('Reset trade password successful'));
|
||||||
|
} catch (\Throwable $e) {
|
||||||
|
return $this->error($e->getMessage());
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
/**
|
/**
|
||||||
* 根据关键字查询用户列表
|
* 根据关键字查询用户列表
|
||||||
|
|||||||
+30
-7
@@ -21,8 +21,8 @@ class User extends Command
|
|||||||
*/
|
*/
|
||||||
protected function configure()
|
protected function configure()
|
||||||
{
|
{
|
||||||
$this->addOption('user_id','u', InputArgument::OPTIONAL, 'user_id');
|
$this->addOption('user_id','u', InputOption::VALUE_OPTIONAL, 'user_id');
|
||||||
$this->addOption('action','a', InputArgument::OPTIONAL, '操作类型');
|
$this->addOption('action','a', InputOption::VALUE_OPTIONAL, '操作类型','test');
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -38,7 +38,28 @@ class User extends Command
|
|||||||
}
|
}
|
||||||
cp('操作不存在:'.$action);
|
cp('操作不存在:'.$action);
|
||||||
return 0;
|
return 0;
|
||||||
|
}
|
||||||
|
function test(InputInterface $input, OutputInterface $output)
|
||||||
|
{
|
||||||
|
$user_id = 104864;
|
||||||
|
$_user = Db::name('user')->where('id',$user_id)->find();
|
||||||
|
Db::query('delete FROM `wa_user_team` WHERE descendant_id='.$user_id.' or ancestor_id='.$user_id.';');
|
||||||
|
Hook('user.register_successed',$_user);
|
||||||
|
//管理团队人数
|
||||||
|
// $team_user_ids = Db::name('user_team')->where('descendant_id',$_user['id'])
|
||||||
|
// ->where('depth','>',0)
|
||||||
|
// ->order('depth','ASC')
|
||||||
|
// ->column('ancestor_id');
|
||||||
|
|
||||||
|
// Db::name('user_extend')->whereIn('user_id',$team_user_ids)->data([
|
||||||
|
// 'team_total'=> Db::raw('team_total+1')
|
||||||
|
// ])->save();
|
||||||
|
// $list = Db::name('user_extend')->whereIn('user_id',$team_user_ids)->field('user_id,team_total')->select();
|
||||||
|
// foreach($list as $v){
|
||||||
|
// cache('team_user_count_'.$v['user_id'],$v['team_total']);
|
||||||
|
// }
|
||||||
|
// cp($team_user_ids);
|
||||||
|
return 0;
|
||||||
}
|
}
|
||||||
function login(InputInterface $input, OutputInterface $output){
|
function login(InputInterface $input, OutputInterface $output){
|
||||||
// $IM = new \support\OpenImSdk\Client([
|
// $IM = new \support\OpenImSdk\Client([
|
||||||
@@ -59,19 +80,20 @@ class User extends Command
|
|||||||
}
|
}
|
||||||
function build_team(InputInterface $input, OutputInterface $output){
|
function build_team(InputInterface $input, OutputInterface $output){
|
||||||
$list = Db::name('user')->field('id')->order('id','asc')->select();
|
$list = Db::name('user')->field('id')->order('id','asc')->select();
|
||||||
|
//$list = [['id'=>100006]];
|
||||||
foreach($list as $k=>$user){
|
foreach($list as $k=>$user){
|
||||||
//team_total
|
//team_total
|
||||||
$team_user_ids = Db::name('user_team')->where('descendant_id',$user['id'])
|
$team_user_ids = Db::name('user_team')->where('ancestor_id',$user['id'])
|
||||||
->where('depth','>',0)
|
->where('depth','>',0)
|
||||||
->order('depth','ASC')
|
->order('depth','ASC')
|
||||||
->column('ancestor_id');
|
->column('descendant_id');
|
||||||
Db::name('user_extend')->where('user_id',$user['id'])->data([
|
Db::name('user_extend')->where('user_id',$user['id'])->data([
|
||||||
'team_total'=> count($team_user_ids)
|
'team_total'=> count($team_user_ids)
|
||||||
])->save();
|
])->save();
|
||||||
cache('team_user_count_'.$user['id'],count($team_user_ids));
|
cache('team_user_count_'.$user['id'],count($team_user_ids));
|
||||||
|
|
||||||
$direct_use_count = Db::name('user')->where('parent_id',$user['id'])->count('id');
|
$direct_use_count = Db::name('user')->where('parent_id',$user['id'])->count('id');
|
||||||
$vip_user_count = Db::name('user')->whereIn('id',$team_user_ids)->where('role_id','>',0)->count('id');
|
$vip_user_count = Db::name('user')->whereIn('id',$team_user_ids)->where('role_id','>',1)->count('id');
|
||||||
|
|
||||||
Db::name('user_extend')->where('user_id',$user['id'])->data([
|
Db::name('user_extend')->where('user_id',$user['id'])->data([
|
||||||
'direct_total'=> $direct_use_count,
|
'direct_total'=> $direct_use_count,
|
||||||
@@ -80,6 +102,7 @@ class User extends Command
|
|||||||
cache('team_direct_total_'.$user['id'],$direct_use_count);
|
cache('team_direct_total_'.$user['id'],$direct_use_count);
|
||||||
cache('team_vip_total_'.$user['id'],$vip_user_count);
|
cache('team_vip_total_'.$user['id'],$vip_user_count);
|
||||||
$this->level_up($user['id'],$vip_user_count);
|
$this->level_up($user['id'],$vip_user_count);
|
||||||
|
cp($user['id'].'完成');
|
||||||
}
|
}
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
@@ -87,10 +110,10 @@ class User extends Command
|
|||||||
protected function level_up($user_id,$count=0){
|
protected function level_up($user_id,$count=0){
|
||||||
$levels = [
|
$levels = [
|
||||||
0,
|
0,
|
||||||
500,
|
50,
|
||||||
|
100,
|
||||||
1000,
|
1000,
|
||||||
5000,
|
5000,
|
||||||
10000,
|
|
||||||
20000,
|
20000,
|
||||||
];
|
];
|
||||||
$level = 0;
|
$level = 0;
|
||||||
|
|||||||
+23
-25
@@ -17,12 +17,23 @@ class User{
|
|||||||
'invite_code' => \support\Encrypt::userIDencode($_user['id']),
|
'invite_code' => \support\Encrypt::userIDencode($_user['id']),
|
||||||
'userID' => \support\Encrypt::userIDencode($_user['id'])
|
'userID' => \support\Encrypt::userIDencode($_user['id'])
|
||||||
];
|
];
|
||||||
|
|
||||||
|
\app\model\User::where('id',$_user['id'])->update($saveData);
|
||||||
|
//创建扩展数据
|
||||||
|
Db::name('user_extend')->replace()->insert([
|
||||||
|
'user_id' => $_user['id'],
|
||||||
|
'consume' => 0,
|
||||||
|
// 'profile_banner' => '',
|
||||||
|
// 'moments_banner' => '',
|
||||||
|
// 'moments_allow_view_days'=>0,
|
||||||
|
]);
|
||||||
//管理直推人数和团队人数
|
//管理直推人数和团队人数
|
||||||
if($_user['parent_id']){
|
if($_user['parent_id']){
|
||||||
parent_info( $_user['id'],[
|
parent_info( $_user['id'],[
|
||||||
'id' => $_user['parent_id'],
|
'id' => $_user['parent_id'],
|
||||||
'username' => Db::name('user')->where('id',$_user['parent_id'])->value('username')
|
'username' => Db::name('user')->where('id',$_user['parent_id'])->value('username')
|
||||||
]);
|
]);
|
||||||
|
$this->buildTeam($_user);
|
||||||
//直属团队人数
|
//直属团队人数
|
||||||
Db::name('user_extend')->where('user_id',$_user['parent_id'])
|
Db::name('user_extend')->where('user_id',$_user['parent_id'])
|
||||||
->data([
|
->data([
|
||||||
@@ -31,7 +42,7 @@ class User{
|
|||||||
cache_add('team_direct_total_'.$_user['parent_id'],1);
|
cache_add('team_direct_total_'.$_user['parent_id'],1);
|
||||||
|
|
||||||
//管理团队人数
|
//管理团队人数
|
||||||
$team_user_ids = Db::name('user_team')->where('descendant_id',$user['id'])
|
$team_user_ids = Db::name('user_team')->where('descendant_id',$_user['id'])
|
||||||
->where('depth','>',0)
|
->where('depth','>',0)
|
||||||
->order('depth','ASC')
|
->order('depth','ASC')
|
||||||
->column('ancestor_id');
|
->column('ancestor_id');
|
||||||
@@ -44,19 +55,6 @@ class User{
|
|||||||
cache('team_user_count_'.$v['user_id'],$v['team_total']);
|
cache('team_user_count_'.$v['user_id'],$v['team_total']);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
\app\model\User::where('id',$_user['id'])->update($saveData);
|
|
||||||
//创建扩展数据
|
|
||||||
Db::name('user_extend')->replace()->insert([
|
|
||||||
'user_id' => $_user['id'],
|
|
||||||
'consume' => 0,
|
|
||||||
// 'profile_banner' => '',
|
|
||||||
// 'moments_banner' => '',
|
|
||||||
// 'moments_allow_view_days'=>0,
|
|
||||||
]);
|
|
||||||
|
|
||||||
|
|
||||||
$this->buildTeam($user);
|
|
||||||
}
|
}
|
||||||
function login_successed($data=[]){
|
function login_successed($data=[]){
|
||||||
$data = $this->profile($data);
|
$data = $this->profile($data);
|
||||||
@@ -71,10 +69,10 @@ class User{
|
|||||||
protected function level_up($user_id,$count=0){
|
protected function level_up($user_id,$count=0){
|
||||||
$levels = [
|
$levels = [
|
||||||
0,
|
0,
|
||||||
500,
|
50,
|
||||||
|
100,
|
||||||
1000,
|
1000,
|
||||||
5000,
|
5000,
|
||||||
10000,
|
|
||||||
20000,
|
20000,
|
||||||
];
|
];
|
||||||
$level = 0;
|
$level = 0;
|
||||||
@@ -100,7 +98,7 @@ class User{
|
|||||||
'userHeadImg' => null,
|
'userHeadImg' => null,
|
||||||
];
|
];
|
||||||
try {
|
try {
|
||||||
$ff = Db::name('user_extend')->where('user_id',$user->id)->field('moments_allow_view_days,profile_banner,moments_banner')->find();
|
$ff = Db::name('user_extend')->where('user_id',$user['id'])->field('moments_allow_view_days,profile_banner,moments_banner')->find();
|
||||||
$data['moments_allow_view_days'] = $ff['moments_allow_view_days'];
|
$data['moments_allow_view_days'] = $ff['moments_allow_view_days'];
|
||||||
$data['moments_banner'] = $ff['moments_banner'];
|
$data['moments_banner'] = $ff['moments_banner'];
|
||||||
$data['profile_banner'] = $ff['profile_banner'];
|
$data['profile_banner'] = $ff['profile_banner'];
|
||||||
@@ -170,29 +168,29 @@ class User{
|
|||||||
// 插入自己的团队关系 (自己是自己的后代)
|
// 插入自己的团队关系 (自己是自己的后代)
|
||||||
$teamData = [
|
$teamData = [
|
||||||
[
|
[
|
||||||
'ancestor_id' => $user->id,
|
'ancestor_id' => $user['id'],
|
||||||
'descendant_id' => $user->id,
|
'descendant_id' => $user['id'],
|
||||||
'depth' => 0,
|
'depth' => 0,
|
||||||
'status' => 0,
|
'status' => 0,
|
||||||
]
|
]
|
||||||
];
|
];
|
||||||
// 2. 处理团队关系(如果有推荐人)
|
// 2. 处理团队关系(如果有推荐人)
|
||||||
if ($user->parent_id) {
|
if ($user['parent_id']) {
|
||||||
|
|
||||||
parent_info( $user->id,[
|
parent_info( $user['id'],[
|
||||||
'id' => $user->parent_id,
|
'id' => $user['parent_id'],
|
||||||
'username' => Db::name('user')->where('id',$user->parent_id)->value('username')
|
'username' => Db::name('user')->where('id',$user['parent_id'])->value('username')
|
||||||
]);
|
]);
|
||||||
// 获取推荐人所有的上级关系,生成新用户的团队关系
|
// 获取推荐人所有的上级关系,生成新用户的团队关系
|
||||||
$ancestors = Db::name('user_team')
|
$ancestors = Db::name('user_team')
|
||||||
->where('descendant_id', $user->parent_id)
|
->where('descendant_id', $user['parent_id'])
|
||||||
->select();
|
->select();
|
||||||
/** @var \app\model\UserTeam $ancestor */
|
/** @var \app\model\UserTeam $ancestor */
|
||||||
// 插入新用户与祖先的关系
|
// 插入新用户与祖先的关系
|
||||||
foreach ($ancestors as $ancestor) {
|
foreach ($ancestors as $ancestor) {
|
||||||
$teamData[] = [
|
$teamData[] = [
|
||||||
'ancestor_id' => $ancestor['ancestor_id'],
|
'ancestor_id' => $ancestor['ancestor_id'],
|
||||||
'descendant_id' => $user->id,
|
'descendant_id' => $user['id'],
|
||||||
'depth' => $ancestor['depth'] + 1,
|
'depth' => $ancestor['depth'] + 1,
|
||||||
'status' => 1, // 默认状态为 0,表示无效
|
'status' => 1, // 默认状态为 0,表示无效
|
||||||
];
|
];
|
||||||
|
|||||||
+3
-3
@@ -499,13 +499,13 @@ if(!function_exists('cache_get')){
|
|||||||
if(!$ret || $force){
|
if(!$ret || $force){
|
||||||
if (str_starts_with($key, 'team_user_total_')) {
|
if (str_starts_with($key, 'team_user_total_')) {
|
||||||
$user_id = substr($key,strlen('team_user_total_'));
|
$user_id = substr($key,strlen('team_user_total_'));
|
||||||
$ret = \support\think\Db::name('user_extend')->where('user_id',$user_id)->column('team_total');
|
$ret = \support\think\Db::name('user_extend')->where('user_id',$user_id)->value('team_total');
|
||||||
}else if (str_starts_with($key, 'team_direct_total_')) {
|
}else if (str_starts_with($key, 'team_direct_total_')) {
|
||||||
$user_id = substr($key,strlen('team_direct_total_'));
|
$user_id = substr($key,strlen('team_direct_total_'));
|
||||||
$ret = \support\think\Db::name('user_extend')->where('user_id',$user_id)->column('direct_total');
|
$ret = \support\think\Db::name('user_extend')->where('user_id',$user_id)->value('direct_total');
|
||||||
}else if (str_starts_with($key, 'team_vip_total_')) {
|
}else if (str_starts_with($key, 'team_vip_total_')) {
|
||||||
$user_id = substr($key,strlen('team_vip_total_'));
|
$user_id = substr($key,strlen('team_vip_total_'));
|
||||||
$ret = \support\think\Db::name('user_extend')->where('user_id',$user_id)->column('vip_total');
|
$ret = \support\think\Db::name('user_extend')->where('user_id',$user_id)->value('vip_total');
|
||||||
}
|
}
|
||||||
cache($key,$ret);
|
cache($key,$ret);
|
||||||
}
|
}
|
||||||
|
|||||||
+27
-9
@@ -5,9 +5,12 @@ namespace app\model;
|
|||||||
* 相册模型
|
* 相册模型
|
||||||
* @property integer $id 主键(ID)
|
* @property integer $id 主键(ID)
|
||||||
* @property integer $user_id 用户ID
|
* @property integer $user_id 用户ID
|
||||||
* @property integer $group_id 内容
|
* @property integer $group_id 群组ID
|
||||||
* @property string $url 图片
|
* @property integer $userID 用户ID
|
||||||
|
* @property integer $groupID 群组ID
|
||||||
* @property string $title 标题
|
* @property string $title 标题
|
||||||
|
* @property int $image 封面图片ID
|
||||||
|
* @property int $weigh 排序权重,越小越靠前
|
||||||
* @property integer $created_at 创建时间
|
* @property integer $created_at 创建时间
|
||||||
* @property integer $updated_at 更新时间
|
* @property integer $updated_at 更新时间
|
||||||
* @property integer $status 状态(0:隐藏 1:正常)
|
* @property integer $status 状态(0:隐藏 1:正常)
|
||||||
@@ -22,30 +25,45 @@ class Album extends Base
|
|||||||
'insert' => [
|
'insert' => [
|
||||||
'status' => 1,
|
'status' => 1,
|
||||||
],
|
],
|
||||||
|
'append'=>[
|
||||||
|
'userID',
|
||||||
|
'groupID'
|
||||||
|
]
|
||||||
]);
|
]);
|
||||||
}
|
}
|
||||||
public static function onAfterInsert($row){
|
public static function onAfterInsert($row){
|
||||||
$changeData = $row->getChangedData();
|
$changeData = $row->getChangedData();
|
||||||
if(isset($changeData['url'])) {
|
if(isset($changeData['image'])) {
|
||||||
Files::where('path',$changeData['url'])->inc('use_count');
|
Files::where('path',$changeData['image'])->inc('use_count');
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
public static function onAfterUpdate($row){
|
public static function onAfterUpdate($row){
|
||||||
$OrgData = $row->getOrigin();
|
$OrgData = $row->getOrigin();
|
||||||
$changeData = $row->getChangedData();
|
$changeData = $row->getChangedData();
|
||||||
if(isset($OrgData['url']) && $OrgData['url']) {
|
if(isset($OrgData['image']) && $OrgData['image']) {
|
||||||
\support\Log::info('OrgData string');
|
\support\Log::info('OrgData string');
|
||||||
Files::where('path',$OrgData['url'])->dec('use_count');
|
Files::where('path',$OrgData['image'])->dec('use_count');
|
||||||
};
|
};
|
||||||
if(isset($changeData['url']) && $changeData['url']) {
|
if(isset($changeData['image']) && $changeData['image']) {
|
||||||
\support\Log::info('changeData string');
|
\support\Log::info('changeData string');
|
||||||
Files::where('path',$changeData['url'])->inc('use_count');
|
Files::where('path',$changeData['image'])->inc('use_count');
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static function onBeforeDelete($row){
|
||||||
|
if($row->total>0){
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
public static function onAfterDelete($row){
|
public static function onAfterDelete($row){
|
||||||
Files::where('path',$row->url)->dec('use_count');
|
Files::where('path',$row->image)->dec('use_count');
|
||||||
|
}
|
||||||
|
function getGroupIDAttr($v,$row){
|
||||||
|
return $v?:$row['group_id'];
|
||||||
|
}
|
||||||
|
function getUserIDAttr($v,$row){
|
||||||
|
return $v?:$row['user_id'];
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -33,7 +33,7 @@ class BalanceLog extends Base
|
|||||||
// ],
|
// ],
|
||||||
]);
|
]);
|
||||||
}
|
}
|
||||||
public static function create(array|object $data, array $allowField = [], bool $replace = false):\think\model\contract\Modelable
|
public static function create(array|object $data, array $allowField = [], bool $replace = false, string $suffix = ''):\think\model\contract\Modelable
|
||||||
{
|
{
|
||||||
$model = new static();
|
$model = new static();
|
||||||
if(isset($data['currency'])){
|
if(isset($data['currency'])){
|
||||||
|
|||||||
@@ -0,0 +1,63 @@
|
|||||||
|
<?php
|
||||||
|
namespace app\model;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 相册模型
|
||||||
|
* @property integer $id 主键(ID)
|
||||||
|
* @property integer $album_id 用户ID
|
||||||
|
* @property integer $user_id 用户ID
|
||||||
|
* @property integer $group_id 内容
|
||||||
|
* @property string $url 图片
|
||||||
|
* @property string $title 标题
|
||||||
|
* @property integer $created_at 创建时间
|
||||||
|
* @property integer $updated_at 更新时间
|
||||||
|
* @property integer $status 状态(0:隐藏 1:正常)
|
||||||
|
*/
|
||||||
|
class Gallery extends Base
|
||||||
|
{
|
||||||
|
protected $name = 'gallery';
|
||||||
|
|
||||||
|
protected function getOptions(): array
|
||||||
|
{
|
||||||
|
return array_merge(parent::getOptions(), [
|
||||||
|
'insert' => [
|
||||||
|
'status' => 1,
|
||||||
|
],
|
||||||
|
'append'=>[
|
||||||
|
'userID',
|
||||||
|
'groupID'
|
||||||
|
]
|
||||||
|
]);
|
||||||
|
}
|
||||||
|
function getGroupIDAttr($v,$row){
|
||||||
|
return $v?:$row['group_id'];
|
||||||
|
}
|
||||||
|
function getUserIDAttr($v,$row){
|
||||||
|
return $v?:$row['user_id'];
|
||||||
|
}
|
||||||
|
public static function onAfterInsert($row){
|
||||||
|
$changeData = $row->getChangedData();
|
||||||
|
if(isset($changeData['url'])) {
|
||||||
|
Files::where('path',$changeData['url'])->inc('use_count');
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
public static function onAfterUpdate($row){
|
||||||
|
$OrgData = $row->getOrigin();
|
||||||
|
$changeData = $row->getChangedData();
|
||||||
|
if(isset($OrgData['url']) && $OrgData['url']) {
|
||||||
|
\support\Log::info('OrgData string');
|
||||||
|
Files::where('path',$OrgData['url'])->dec('use_count');
|
||||||
|
};
|
||||||
|
if(isset($changeData['url']) && $changeData['url']) {
|
||||||
|
\support\Log::info('changeData string');
|
||||||
|
Files::where('path',$changeData['url'])->inc('use_count');
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
public static function onAfterDelete($row){
|
||||||
|
Files::where('path',$row->url)->dec('use_count');
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
+569
-55
@@ -39,7 +39,7 @@
|
|||||||
min-height: 100vh;
|
min-height: 100vh;
|
||||||
line-height: 1.6;
|
line-height: 1.6;
|
||||||
padding: 20px;
|
padding: 20px;
|
||||||
_background-image: radial-gradient(at 0 0,rgba(var(--primary-rgb),0.05) 0,transparent 50%),radial-gradient(at 100% 100%,rgba(var(--secondary-rgb),0.05) 0,transparent 50%)
|
background-image: radial-gradient(at 0 0,rgba(39, 186, 87, 0.05) 0,transparent 50%),radial-gradient(at 100% 100%,rgba(39, 186, 87, 0.05) 0,transparent 50%)
|
||||||
}
|
}
|
||||||
|
|
||||||
.container {
|
.container {
|
||||||
@@ -50,13 +50,17 @@
|
|||||||
box-shadow: var(--shadow);
|
box-shadow: var(--shadow);
|
||||||
overflow: hidden;
|
overflow: hidden;
|
||||||
position: relative;
|
position: relative;
|
||||||
z-index: 1
|
z-index: 1;
|
||||||
|
transition: var(--transition);
|
||||||
|
}
|
||||||
|
|
||||||
|
.container:hover {
|
||||||
|
box-shadow: 0 8px 32px rgba(0,0,0,0.12);
|
||||||
}
|
}
|
||||||
|
|
||||||
.container::before {
|
.container::before {
|
||||||
content: '';
|
content: '';
|
||||||
position: absolute;
|
position: absolute;
|
||||||
display: none;
|
|
||||||
top: 0;
|
top: 0;
|
||||||
left: 0;
|
left: 0;
|
||||||
width: 100%;
|
width: 100%;
|
||||||
@@ -68,7 +72,9 @@
|
|||||||
|
|
||||||
.header {
|
.header {
|
||||||
padding: 40px 40px 30px;
|
padding: 40px 40px 30px;
|
||||||
text-align: center
|
text-align: center;
|
||||||
|
position: relative;
|
||||||
|
z-index: 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
.logo {
|
.logo {
|
||||||
@@ -80,7 +86,13 @@
|
|||||||
align-items: center;
|
align-items: center;
|
||||||
justify-content: center;
|
justify-content: center;
|
||||||
box-shadow: var(--shadow);
|
box-shadow: var(--shadow);
|
||||||
margin-bottom: 20px
|
margin-bottom: 20px;
|
||||||
|
transition: var(--transition);
|
||||||
|
}
|
||||||
|
|
||||||
|
.logo:hover {
|
||||||
|
transform: scale(1.05);
|
||||||
|
box-shadow: 0 6px 20px rgba(0,0,0,0.12);
|
||||||
}
|
}
|
||||||
|
|
||||||
.logo svg {
|
.logo svg {
|
||||||
@@ -99,7 +111,8 @@
|
|||||||
}
|
}
|
||||||
|
|
||||||
.header p {
|
.header p {
|
||||||
font-size: 14pt
|
font-size: 14pt;
|
||||||
|
color: var(--text-light);
|
||||||
}
|
}
|
||||||
|
|
||||||
.card {
|
.card {
|
||||||
@@ -161,10 +174,29 @@
|
|||||||
|
|
||||||
.form-control:focus {
|
.form-control:focus {
|
||||||
border-color: var(--primary);
|
border-color: var(--primary);
|
||||||
box-shadow: 0 0 0 3px rgba(67,97,238,0.15);
|
box-shadow: 0 0 0 3px rgba(39, 186, 87, 0.15);
|
||||||
outline: 0
|
outline: 0
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.form-control.error {
|
||||||
|
border-color: #f56c6c;
|
||||||
|
}
|
||||||
|
|
||||||
|
.form-control.success {
|
||||||
|
border-color: var(--primary);
|
||||||
|
}
|
||||||
|
|
||||||
|
.error-message {
|
||||||
|
color: #f56c6c;
|
||||||
|
font-size: 12px;
|
||||||
|
margin-top: 4px;
|
||||||
|
display: none;
|
||||||
|
}
|
||||||
|
|
||||||
|
.error-message.show {
|
||||||
|
display: block;
|
||||||
|
}
|
||||||
|
|
||||||
.captcha-group {
|
.captcha-group {
|
||||||
display: flex;
|
display: flex;
|
||||||
gap: 12px
|
gap: 12px
|
||||||
@@ -184,11 +216,15 @@
|
|||||||
font-weight: 600;
|
font-weight: 600;
|
||||||
cursor: pointer;
|
cursor: pointer;
|
||||||
transition: var(--transition);
|
transition: var(--transition);
|
||||||
padding: 0 16px
|
padding: 0 16px;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
}
|
}
|
||||||
|
|
||||||
.captcha-btn:hover {
|
.captcha-btn:hover:not(:disabled) {
|
||||||
background-color: rgba(67,97,238,0.1)
|
background-color: rgba(39, 186, 87, 0.1);
|
||||||
|
transform: translateY(-1px);
|
||||||
}
|
}
|
||||||
|
|
||||||
.captcha-btn:disabled {
|
.captcha-btn:disabled {
|
||||||
@@ -209,18 +245,26 @@
|
|||||||
cursor: pointer;
|
cursor: pointer;
|
||||||
transition: var(--transition);
|
transition: var(--transition);
|
||||||
margin-top: 10px;
|
margin-top: 10px;
|
||||||
box-shadow: 0 4px 12px rgba(67,97,238,0.2)
|
box-shadow: 0 4px 12px rgba(39, 186, 87, 0.2);
|
||||||
|
position: relative;
|
||||||
|
overflow: hidden;
|
||||||
}
|
}
|
||||||
|
|
||||||
.btn:hover {
|
.btn:hover {
|
||||||
transform: translateY(-2px);
|
transform: translateY(-2px);
|
||||||
box-shadow: 0 6px 16px rgba(67,97,238,0.3)
|
box-shadow: 0 6px 16px rgba(39, 186, 87, 0.3)
|
||||||
}
|
}
|
||||||
|
|
||||||
.btn:active {
|
.btn:active {
|
||||||
transform: translateY(0)
|
transform: translateY(0)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.btn:disabled {
|
||||||
|
opacity: 0.7;
|
||||||
|
cursor: not-allowed;
|
||||||
|
transform: none;
|
||||||
|
}
|
||||||
|
|
||||||
.footer {
|
.footer {
|
||||||
margin-top: 30px;
|
margin-top: 30px;
|
||||||
text-align: center;
|
text-align: center;
|
||||||
@@ -239,7 +283,6 @@
|
|||||||
text-decoration: underline
|
text-decoration: underline
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
.other-options {
|
.other-options {
|
||||||
margin-top: 20px;
|
margin-top: 20px;
|
||||||
text-align: center;
|
text-align: center;
|
||||||
@@ -282,6 +325,14 @@
|
|||||||
height: 60px;
|
height: 60px;
|
||||||
border-radius: 15px;
|
border-radius: 15px;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.header h1 {
|
||||||
|
font-size: 20px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.header p {
|
||||||
|
font-size: 12pt;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
/*成功卡片*/
|
/*成功卡片*/
|
||||||
.success-card {
|
.success-card {
|
||||||
@@ -447,6 +498,184 @@
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.region .layui-select-title .layui-input{
|
||||||
|
height: 51px;
|
||||||
|
border-top-left-radius: 12px;
|
||||||
|
border-bottom-left-radius: 12px;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 密码强度指示器 */
|
||||||
|
.password-strength {
|
||||||
|
display: flex;
|
||||||
|
gap: 4px;
|
||||||
|
margin-top: 8px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.strength-bar {
|
||||||
|
flex: 1;
|
||||||
|
height: 4px;
|
||||||
|
border-radius: 2px;
|
||||||
|
background-color: var(--border);
|
||||||
|
transition: var(--transition);
|
||||||
|
}
|
||||||
|
|
||||||
|
.strength-bar.weak {
|
||||||
|
background-color: #f56c6c;
|
||||||
|
}
|
||||||
|
|
||||||
|
.strength-bar.medium {
|
||||||
|
background-color: #e6a23c;
|
||||||
|
}
|
||||||
|
|
||||||
|
.strength-bar.strong {
|
||||||
|
background-color: var(--primary);
|
||||||
|
}
|
||||||
|
|
||||||
|
.strength-text {
|
||||||
|
font-size: 12px;
|
||||||
|
color: var(--text-light);
|
||||||
|
margin-top: 4px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.strength-text.weak {
|
||||||
|
color: #f56c6c;
|
||||||
|
}
|
||||||
|
|
||||||
|
.strength-text.medium {
|
||||||
|
color: #e6a23c;
|
||||||
|
}
|
||||||
|
|
||||||
|
.strength-text.strong {
|
||||||
|
color: var(--primary);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 加载动画 */
|
||||||
|
.loading {
|
||||||
|
display: inline-block;
|
||||||
|
width: 20px;
|
||||||
|
height: 20px;
|
||||||
|
border: 2px solid rgba(255,255,255,0.3);
|
||||||
|
border-radius: 50%;
|
||||||
|
border-top-color: #fff;
|
||||||
|
animation: spin 1s ease-in-out infinite;
|
||||||
|
}
|
||||||
|
|
||||||
|
@keyframes spin {
|
||||||
|
to { transform: rotate(360deg); }
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 输入框图标 */
|
||||||
|
.input-icon {
|
||||||
|
position: absolute;
|
||||||
|
left: 16px;
|
||||||
|
top: 50%;
|
||||||
|
transform: translateY(-50%);
|
||||||
|
color: var(--text-light);
|
||||||
|
}
|
||||||
|
|
||||||
|
.form-control.has-icon {
|
||||||
|
padding-left: 40px;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 验证码按钮加载状态 */
|
||||||
|
.captcha-btn.loading {
|
||||||
|
position: relative;
|
||||||
|
pointer-events: none;
|
||||||
|
}
|
||||||
|
|
||||||
|
.captcha-btn.loading::after {
|
||||||
|
content: '';
|
||||||
|
position: absolute;
|
||||||
|
width: 16px;
|
||||||
|
height: 16px;
|
||||||
|
border: 2px solid rgba(39, 186, 87, 0.3);
|
||||||
|
border-radius: 50%;
|
||||||
|
border-top-color: var(--primary);
|
||||||
|
animation: spin 1s ease-in-out infinite;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 响应式优化 */
|
||||||
|
@media (max-width: 768px) {
|
||||||
|
.container {
|
||||||
|
padding: 16px;
|
||||||
|
max-width: 95%;
|
||||||
|
}
|
||||||
|
|
||||||
|
.card {
|
||||||
|
padding: 0 24px 32px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.form-group {
|
||||||
|
margin-bottom: 16px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.btn {
|
||||||
|
height: 48px;
|
||||||
|
font-size: 16px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.captcha-btn {
|
||||||
|
min-width: 100px;
|
||||||
|
font-size: 13px;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 动画效果 */
|
||||||
|
@keyframes fadeInUp {
|
||||||
|
from {
|
||||||
|
opacity: 0;
|
||||||
|
transform: translateY(20px);
|
||||||
|
}
|
||||||
|
to {
|
||||||
|
opacity: 1;
|
||||||
|
transform: translateY(0);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.form-container {
|
||||||
|
animation: fadeInUp 0.3s ease-out;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 错误消息优化 */
|
||||||
|
.error-message {
|
||||||
|
font-size: 12px;
|
||||||
|
color: #f56c6c;
|
||||||
|
margin-top: 4px;
|
||||||
|
opacity: 0;
|
||||||
|
height: 0;
|
||||||
|
overflow: hidden;
|
||||||
|
transition: var(--transition);
|
||||||
|
}
|
||||||
|
|
||||||
|
.error-message.show {
|
||||||
|
opacity: 1;
|
||||||
|
height: auto;
|
||||||
|
min-height: 16px;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 星星装饰优化 */
|
||||||
|
.star {
|
||||||
|
position: absolute;
|
||||||
|
background-color: #fff;
|
||||||
|
border-radius: 50%;
|
||||||
|
animation: twinkle 3s infinite;
|
||||||
|
}
|
||||||
|
|
||||||
|
@keyframes twinkle {
|
||||||
|
0%, 100% {
|
||||||
|
opacity: 0.3;
|
||||||
|
}
|
||||||
|
50% {
|
||||||
|
opacity: 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 庆祝效果 */
|
||||||
|
.confetti {
|
||||||
|
position: absolute;
|
||||||
|
border-radius: 2px;
|
||||||
|
}
|
||||||
|
|
||||||
</style>
|
</style>
|
||||||
{/literal}
|
{/literal}
|
||||||
</head>
|
</head>
|
||||||
@@ -819,52 +1048,77 @@
|
|||||||
</svg>
|
</svg>
|
||||||
</div>
|
</div>
|
||||||
<h1>欢迎回来</h1>
|
<h1>欢迎回来</h1>
|
||||||
<p>使用手机号码注册您的账户</p>
|
<p>使用手机号或邮箱注册您的账户</p>
|
||||||
</div>
|
</div>
|
||||||
<div class="card" data-type="register">
|
<div class="card" data-type="register">
|
||||||
<!-- 注册表单 -->
|
<!-- 注册表单 -->
|
||||||
<div class="form-container active" id="register-form">
|
<div class="form-container active" id="register-form">
|
||||||
<form id="registerForm" class="layui-form" method="post" action="/api/common/register">
|
<form id="registerForm" class="layui-form" method="post" action="/api/common/register">
|
||||||
<div class="form-group">
|
<input type="hidden" name="type" id="register_type" value="mobile" />
|
||||||
<label for="register-phone">手机号码</label>
|
<div class="layui-tab-item layui-show">
|
||||||
<div class="input-wrapper">
|
<div class="form-group">
|
||||||
<input type="tel" name="mobile" lay-reqtext="请输入您的手机号码" id="register-phone" class="form-control" placeholder="请输入您的手机号码" required lay-verify="required|phone">
|
<label for="register-phone">手机号/邮箱</label>
|
||||||
|
<div class="input-wrapper">
|
||||||
|
<i class="layui-icon layui-icon-cellphone input-icon"></i>
|
||||||
|
<input type="text" name="mobile"
|
||||||
|
lay-reqtext="请输入您的手机号或邮箱"
|
||||||
|
id="register-phone"
|
||||||
|
class="form-control has-icon"
|
||||||
|
placeholder="请输入您的手机号或邮箱"
|
||||||
|
required
|
||||||
|
lay-verify="require|username" />
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
<div class="error-message" id="phone-error"></div>
|
||||||
<div class="form-group" style="display: none;">
|
<div class="form-group" style="display: none;">
|
||||||
<label for="register-password">我的昵称</label>
|
<label for="register-password">我的昵称</label>
|
||||||
<div class="input-wrapper">
|
<div class="input-wrapper">
|
||||||
<input type="text" name="nickname" lay-reqtext="请设置您的昵称" id="register-nickname" class="form-control" placeholder="给自己取一个好听的昵称吧" required lay-verify="required">
|
<i class="layui-icon layui-icon-username input-icon"></i>
|
||||||
|
<input type="text" name="nickname" lay-reqtext="请设置您的昵称" id="register-nickname" class="form-control has-icon" placeholder="给自己取一个好听的昵称吧" lay-verify="">
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div class="form-group">
|
<div class="form-group">
|
||||||
<label for="register-captcha">验证码</label>
|
<label for="register-captcha">验证码</label>
|
||||||
<div class="captcha-group">
|
<div class="captcha-group">
|
||||||
<div class="input-wrapper" style="flex: 1;">
|
<div class="input-wrapper" style="flex: 1;">
|
||||||
<input type="text" lay-reqtext="请输入验证码" name="code" id="register-captcha" class="form-control captcha-input"
|
<i class="layui-icon layui-icon-vercode input-icon"></i>
|
||||||
|
<input type="text" lay-reqtext="请输入验证码" name="code" id="register-captcha" class="form-control captcha-input has-icon"
|
||||||
placeholder="请输入验证码" required lay-verify="required|number">
|
placeholder="请输入验证码" required lay-verify="required|number">
|
||||||
</div>
|
</div>
|
||||||
<button type="button" class="captcha-btn" id="register-get-captcha">获取验证码</button>
|
<button type="button" class="captcha-btn" id="register-get-captcha">获取验证码</button>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
<div class="error-message" id="captcha-error"></div>
|
||||||
<div class="form-group">
|
<div class="form-group">
|
||||||
<label for="register-password">设置密码</label>
|
<label for="register-password">设置密码</label>
|
||||||
<div class="input-wrapper">
|
<div class="input-wrapper">
|
||||||
<input type="password" lay-reqtext="请设置您的登录密码" name="password" id="register-password" class="form-control" placeholder="请输入6-20位密码"
|
<i class="layui-icon layui-icon-password input-icon"></i>
|
||||||
|
<input type="password" lay-reqtext="请设置您的登录密码" name="password" id="register-password" class="form-control has-icon" placeholder="请输入6-20位密码"
|
||||||
required lay-verify="required|password">
|
required lay-verify="required|password">
|
||||||
</div>
|
</div>
|
||||||
|
<div class="password-strength">
|
||||||
|
<div class="strength-bar" id="strength-bar-1"></div>
|
||||||
|
<div class="strength-bar" id="strength-bar-2"></div>
|
||||||
|
<div class="strength-bar" id="strength-bar-3"></div>
|
||||||
|
</div>
|
||||||
|
<div class="strength-text" id="strength-text">密码强度:弱</div>
|
||||||
</div>
|
</div>
|
||||||
|
<div class="error-message" id="password-error"></div>
|
||||||
<div class="form-group">
|
<div class="form-group">
|
||||||
<label for="register-password">确认密码</label>
|
<label for="register-password">确认密码</label>
|
||||||
<div class="input-wrapper">
|
<div class="input-wrapper">
|
||||||
<input type="password" lay-reqtext="请再次输入密码" name="repassword" id="register-repassword" class="form-control" placeholder="请输入6-20位密码"
|
<i class="layui-icon layui-icon-password input-icon"></i>
|
||||||
|
<input type="password" lay-reqtext="请再次输入密码" name="repassword" id="register-repassword" class="form-control has-icon" placeholder="请输入6-20位密码"
|
||||||
required lay-verify="required|repassword">
|
required lay-verify="required|repassword">
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
<div class="error-message" id="repassword-error"></div>
|
||||||
<div class="form-group">
|
<div class="form-group">
|
||||||
<label for="register-password">邀请码</label>
|
<label for="register-password">邀请码</label>
|
||||||
<div class="input-wrapper">
|
<div class="input-wrapper">
|
||||||
<input type="text" readonly class="form-control" lay-reqtext="参数错误" value="{$invite_code}" name="invite_code" required lay-verify="required">
|
<i class="layui-icon layui-icon-code input-icon"></i>
|
||||||
|
<input type="text" readonly class="form-control has-icon" lay-reqtext="参数错误" value="{$invite_code}" name="invite_code" required lay-verify="required">
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div class="form-group">
|
<div class="form-group">
|
||||||
@@ -904,15 +1158,162 @@
|
|||||||
{literal}
|
{literal}
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
layui.use(function(){
|
layui.use(function(){
|
||||||
|
var element = layui.element;
|
||||||
var layer = layui.layer;
|
var layer = layui.layer;
|
||||||
var form = layui.form;
|
var form = layui.form;
|
||||||
var $ = layui.jquery;
|
var $ = layui.jquery;
|
||||||
$('[data-type="register"]').show();
|
|
||||||
$('[data-type="success"]').hide();
|
// 初始化页面
|
||||||
|
function initPage() {
|
||||||
|
$('[data-type="register"]').show();
|
||||||
|
$('[data-type="success"]').hide();
|
||||||
|
generateStars();
|
||||||
|
}
|
||||||
|
|
||||||
|
// 生成星星装饰
|
||||||
|
function generateStars() {
|
||||||
|
const stars = document.getElementById('stars');
|
||||||
|
if (stars) {
|
||||||
|
for (let i = 0; i < 50; i++) {
|
||||||
|
const star = document.createElement('div');
|
||||||
|
star.className = 'star';
|
||||||
|
star.style.left = Math.random() * 100 + '%';
|
||||||
|
star.style.top = Math.random() * 100 + '%';
|
||||||
|
star.style.width = Math.random() * 3 + 1 + 'px';
|
||||||
|
star.style.height = star.style.width;
|
||||||
|
star.style.animationDelay = Math.random() * 3 + 's';
|
||||||
|
stars.appendChild(star);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// 密码强度检测
|
||||||
|
function checkPasswordStrength(password) {
|
||||||
|
let strength = 0;
|
||||||
|
if (password.length >= 6) strength++;
|
||||||
|
if (password.length >= 10) strength++;
|
||||||
|
if (/[A-Z]/.test(password)) strength++;
|
||||||
|
if (/[0-9]/.test(password)) strength++;
|
||||||
|
if (/[^A-Za-z0-9]/.test(password)) strength++;
|
||||||
|
|
||||||
|
// 更新密码强度指示器
|
||||||
|
const strengthBars = document.querySelectorAll('.strength-bar');
|
||||||
|
const strengthText = document.getElementById('strength-text');
|
||||||
|
|
||||||
|
strengthBars.forEach((bar, index) => {
|
||||||
|
bar.className = 'strength-bar';
|
||||||
|
if (index < Math.floor(strength / 2)) {
|
||||||
|
if (strength <= 2) {
|
||||||
|
bar.classList.add('weak');
|
||||||
|
} else if (strength <= 4) {
|
||||||
|
bar.classList.add('medium');
|
||||||
|
} else {
|
||||||
|
bar.classList.add('strong');
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
if (strength <= 2) {
|
||||||
|
strengthText.textContent = '密码强度:弱';
|
||||||
|
strengthText.className = 'strength-text weak';
|
||||||
|
} else if (strength <= 4) {
|
||||||
|
strengthText.textContent = '密码强度:中';
|
||||||
|
strengthText.className = 'strength-text medium';
|
||||||
|
} else {
|
||||||
|
strengthText.textContent = '密码强度:强';
|
||||||
|
strengthText.className = 'strength-text strong';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// 输入框验证
|
||||||
|
function validateInput(input, errorId, message) {
|
||||||
|
const errorElement = document.getElementById(errorId);
|
||||||
|
if (input.value.trim() === '') {
|
||||||
|
input.classList.add('error');
|
||||||
|
errorElement.textContent = message;
|
||||||
|
errorElement.classList.add('show');
|
||||||
|
return false;
|
||||||
|
} else {
|
||||||
|
input.classList.remove('error');
|
||||||
|
errorElement.classList.remove('show');
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// 实时验证
|
||||||
|
$('#register-phone').on('blur', function() {
|
||||||
|
validateInput(this, 'phone-error', '请输入手机号或邮箱');
|
||||||
|
});
|
||||||
|
|
||||||
|
$('#register-captcha').on('blur', function() {
|
||||||
|
validateInput(this, 'captcha-error', '请输入验证码');
|
||||||
|
});
|
||||||
|
|
||||||
|
$('#register-password').on('input', function() {
|
||||||
|
checkPasswordStrength(this.value);
|
||||||
|
validateInput(this, 'password-error', '请设置密码');
|
||||||
|
});
|
||||||
|
|
||||||
|
$('#register-password').on('blur', function() {
|
||||||
|
validateInput(this, 'password-error', '请设置密码');
|
||||||
|
});
|
||||||
|
|
||||||
|
$('#register-repassword').on('blur', function() {
|
||||||
|
if (this.value !== $('#register-password').val()) {
|
||||||
|
this.classList.add('error');
|
||||||
|
document.getElementById('repassword-error').textContent = '两次密码输入不一致';
|
||||||
|
document.getElementById('repassword-error').classList.add('show');
|
||||||
|
return false;
|
||||||
|
} else {
|
||||||
|
this.classList.remove('error');
|
||||||
|
document.getElementById('repassword-error').classList.remove('show');
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
// hash 地址定位
|
||||||
|
var hashName = 'register_type'; // hash 名称
|
||||||
|
var layid = location.hash.replace(new RegExp('^#'+ hashName + '='), ''); // 获取 lay-id 值
|
||||||
|
layid = layid || 'mobile';
|
||||||
|
// 初始切换
|
||||||
|
element.tabChange('registe-type', layid);
|
||||||
|
// 切换事件
|
||||||
|
element.on('tab(registe-type)', function(obj){
|
||||||
|
location.hash = hashName +'='+ this.getAttribute('lay-id');
|
||||||
|
$('#register_type').val(this.getAttribute('lay-id'));
|
||||||
|
});
|
||||||
|
|
||||||
form.verify({
|
form.verify({
|
||||||
|
username:function(v,elem){
|
||||||
|
if(v.indexOf('@') == -1){
|
||||||
|
if(!v){return '手机号不能为空';}
|
||||||
|
const reg = /^1[3-9]\d{9}$/;
|
||||||
|
if(!reg.test(v)){
|
||||||
|
return '手机号码格式错误';
|
||||||
|
}
|
||||||
|
$('#register_type').val('mobile');
|
||||||
|
}else{
|
||||||
|
if(!v){return '手机号或邮箱不能为空';}
|
||||||
|
const reg = /^[a-zA-Z0-9._%+-]+@(?:[a-zA-Z0-9-]+\.)+[a-zA-Z]{2,}$/;
|
||||||
|
if(!reg.test(v) || /[<>(){}[\]\\]/.test(v)){
|
||||||
|
return '邮箱格式错误';
|
||||||
|
}
|
||||||
|
$('#register_type').val('email');
|
||||||
|
}
|
||||||
|
},
|
||||||
|
phonerequire: function(value, elem) {
|
||||||
|
if($('#register_type').val() == 'mobile'){
|
||||||
|
if(!value){return '手机号不能为空';}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
emailrequire: function(value, elem) {
|
||||||
|
if($('#register_type').val() == 'email'){
|
||||||
|
if(!value){return '邮箱不能为空';}
|
||||||
|
}
|
||||||
|
},
|
||||||
password: function(value, elem) {
|
password: function(value, elem) {
|
||||||
if (value.length < 6) {
|
if (value.length < 6) {
|
||||||
return '密码太过简单';
|
return '密码长度不能少于6位';
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
repassword: function(value, elem) {
|
repassword: function(value, elem) {
|
||||||
@@ -921,68 +1322,181 @@
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
function check_exist(callback){
|
||||||
|
var elem = $('#register-phone');
|
||||||
|
var v = elem.val();
|
||||||
|
var msg='';
|
||||||
|
var data={};
|
||||||
|
var api_url='';
|
||||||
|
if($('#register_type').val() == 'email'){
|
||||||
|
api_url = '/api/Validate/check_email_exist';
|
||||||
|
data={'email':v};
|
||||||
|
msg='邮箱已经存在';
|
||||||
|
}else{
|
||||||
|
api_url = '/api/Validate/check_mobile_exist';
|
||||||
|
data={'mobile':v};
|
||||||
|
msg='手机号码已经存在';
|
||||||
|
}
|
||||||
|
$.post(api_url,data,function(res){
|
||||||
|
if(res.code === 0){
|
||||||
|
elem.removeClass('layui-form-danger').addClass('layui-form-danger');
|
||||||
|
layer.msg(msg,{icon:2});
|
||||||
|
return ;
|
||||||
|
}
|
||||||
|
callback && callback();
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
$('#register-get-captcha').on('click',function(){
|
$('#register-get-captcha').on('click',function(){
|
||||||
var isValid = form.validate('#register-phone');
|
var isValid = form.validate('#register-phone');
|
||||||
|
var msg = '请输入正确的手机号或邮箱';
|
||||||
|
var val = $('#register-phone').val();
|
||||||
|
var senddata = {
|
||||||
|
type:$('#register_type').val(),
|
||||||
|
mobile:val,
|
||||||
|
'event':'register'
|
||||||
|
};
|
||||||
|
if($('#register_type').val() == 'email'){
|
||||||
|
delete senddata['mobile'];
|
||||||
|
senddata['email'] = val;
|
||||||
|
}
|
||||||
// 验证通过
|
// 验证通过
|
||||||
if(!isValid){
|
if(!isValid){
|
||||||
layer.msg('请输入正确的手机号',{icon:2});
|
layer.msg(msg,{icon:2});
|
||||||
return ;
|
return ;
|
||||||
}
|
}
|
||||||
|
|
||||||
var btn = $('#register-get-captcha').get(0);
|
var btn = $('#register-get-captcha').get(0);
|
||||||
var phone = $('#register-phone').val();
|
|
||||||
// 禁用按钮并开始倒计时
|
// 禁用按钮并开始倒计时
|
||||||
btn.disabled = true;
|
btn.disabled = true;
|
||||||
let countdown = 60;
|
btn.classList.add('loading');
|
||||||
btn.innerHTML = `${countdown}秒后重新获取`;
|
|
||||||
|
check_exist(function(){
|
||||||
|
$.post('/api/common/captcha',senddata,function(res){
|
||||||
|
btn.classList.remove('loading');
|
||||||
|
if(res.code === 0){
|
||||||
|
layer.msg(`验证码已发送`,{icon:1});
|
||||||
|
let countdown = 60;
|
||||||
|
btn.innerHTML = `${countdown}秒后重新获取`;
|
||||||
|
|
||||||
const timer = setInterval(() => {
|
const timer = setInterval(() => {
|
||||||
countdown--;
|
countdown--;
|
||||||
btn.innerHTML = `${countdown}秒后重新获取`;
|
btn.innerHTML = `${countdown}秒后重新获取`;
|
||||||
|
|
||||||
if (countdown <= 0) {
|
if (countdown <= 0) {
|
||||||
clearInterval(timer);
|
clearInterval(timer);
|
||||||
|
btn.disabled = false;
|
||||||
|
btn.innerHTML = '获取验证码';
|
||||||
|
}
|
||||||
|
}, 1000);
|
||||||
|
}else{
|
||||||
|
btn.disabled = false;
|
||||||
|
btn.innerHTML = '获取验证码';
|
||||||
|
layer.msg(res.msg,{icon:2});
|
||||||
|
}
|
||||||
|
}).fail(function() {
|
||||||
|
btn.classList.remove('loading');
|
||||||
btn.disabled = false;
|
btn.disabled = false;
|
||||||
btn.innerHTML = '获取验证码';
|
btn.innerHTML = '获取验证码';
|
||||||
}
|
layer.msg('网络错误,请稍后重试',{icon:2});
|
||||||
}, 1000);
|
});
|
||||||
|
})
|
||||||
// 这里应该是发送验证码的AJAX请求
|
|
||||||
console.log(`发送验证码到手机: ${phone}`);
|
|
||||||
$.post('/api/common/captcha',{type:'mobile',mobile:phone,'event':'register'},function(res){
|
|
||||||
if(res.code === 0){
|
|
||||||
console.log(res);
|
|
||||||
layer.msg(`验证码已发送到手机 ${phone} (模拟)`,{icon:1});
|
|
||||||
}else{
|
|
||||||
clearInterval(timer);
|
|
||||||
btn.disabled = false;
|
|
||||||
btn.innerHTML = '获取验证码';
|
|
||||||
}
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
|
||||||
// 提交事件
|
// 提交事件
|
||||||
form.on('submit(register-form)', function(data){
|
form.on('submit(register-form)', function(data){
|
||||||
var field = data.field; // 获取表单字段值
|
var field = data.field; // 获取表单字段值
|
||||||
// 显示填写结果,仅作演示用
|
|
||||||
field['type'] = 'mobile';
|
// 验证所有输入框
|
||||||
console.log(field);
|
const phoneValid = validateInput($('#register-phone')[0], 'phone-error', '请输入手机号或邮箱');
|
||||||
// 此处可执行 Ajax 等操作
|
const captchaValid = validateInput($('#register-captcha')[0], 'captcha-error', '请输入验证码');
|
||||||
|
const passwordValid = validateInput($('#register-password')[0], 'password-error', '请设置密码');
|
||||||
|
const repasswordValid = validateInput($('#register-repassword')[0], 'repassword-error', '请确认密码');
|
||||||
|
|
||||||
|
if (!phoneValid || !captchaValid || !passwordValid || !repasswordValid) {
|
||||||
|
layer.msg('请完善表单信息',{icon:2});
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
if ($('#register-password').val() !== $('#register-repassword').val()) {
|
||||||
|
$('#register-repassword')[0].classList.add('error');
|
||||||
|
document.getElementById('repassword-error').textContent = '两次密码输入不一致';
|
||||||
|
document.getElementById('repassword-error').classList.add('show');
|
||||||
|
layer.msg('两次密码输入不一致',{icon:2});
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
const btn = this;
|
const btn = this;
|
||||||
const originalText = btn.innerHTML;
|
const originalText = btn.innerHTML;
|
||||||
btn.innerHTML = `<span class="layui-icon layui-icon-loading-1 layui-anim layui-anim-rotate layui-anim-loop"></span> 注册中...`;
|
btn.innerHTML = `<span class="layui-icon layui-icon-loading-1 layui-anim layui-anim-rotate layui-anim-loop"></span> 注册中...`;
|
||||||
btn.disabled = true;
|
btn.disabled = true;
|
||||||
$.post('/api/common/register',field,function(res){
|
if(field['type'] == 'email'){
|
||||||
|
field['email'] = field['mobile'];
|
||||||
|
delete field['mobile'];
|
||||||
|
}
|
||||||
|
$.post('/api/common/register', field, function(res){
|
||||||
btn.innerHTML = originalText;
|
btn.innerHTML = originalText;
|
||||||
btn.disabled = false;
|
btn.disabled = false;
|
||||||
if(res.code === 0 ){
|
if(res.code === 0 ){
|
||||||
|
// 更新成功页面的用户名
|
||||||
|
if (res.data && res.data.username) {
|
||||||
|
$('#username').text(res.data.username);
|
||||||
|
}
|
||||||
|
// 显示成功页面
|
||||||
$('[data-type="register"]').hide();
|
$('[data-type="register"]').hide();
|
||||||
$('[data-type="success"]').show();
|
$('[data-type="success"]').show();
|
||||||
|
// 生成庆祝效果
|
||||||
|
createConfetti();
|
||||||
}else{
|
}else{
|
||||||
layer.msg(res.msg,{icon:2});
|
layer.msg(res.msg,{icon:2});
|
||||||
}
|
}
|
||||||
|
}).fail(function() {
|
||||||
|
btn.innerHTML = originalText;
|
||||||
|
btn.disabled = false;
|
||||||
|
layer.msg('网络错误,请稍后重试',{icon:2});
|
||||||
});
|
});
|
||||||
|
|
||||||
return false; // 阻止默认 form 跳转
|
return false; // 阻止默认 form 跳转
|
||||||
});
|
});
|
||||||
|
|
||||||
|
// 创建庆祝效果
|
||||||
|
function createConfetti() {
|
||||||
|
const successCard = document.querySelector('.success-card');
|
||||||
|
if (!successCard) return;
|
||||||
|
|
||||||
|
for (let i = 0; i < 100; i++) {
|
||||||
|
const confetti = document.createElement('div');
|
||||||
|
confetti.className = 'confetti';
|
||||||
|
confetti.style.left = Math.random() * 100 + '%';
|
||||||
|
confetti.style.top = Math.random() * 100 + '%';
|
||||||
|
confetti.style.backgroundColor = getRandomColor();
|
||||||
|
confetti.style.width = Math.random() * 10 + 5 + 'px';
|
||||||
|
confetti.style.height = Math.random() * 10 + 5 + 'px';
|
||||||
|
confetti.style.opacity = 1;
|
||||||
|
confetti.style.transform = 'translateY(0) rotate(0deg)';
|
||||||
|
confetti.style.transition = 'all ' + (Math.random() * 3 + 2) + 's ease-out';
|
||||||
|
|
||||||
|
successCard.appendChild(confetti);
|
||||||
|
|
||||||
|
setTimeout(() => {
|
||||||
|
confetti.style.opacity = 0;
|
||||||
|
confetti.style.transform = 'translateY(100px) rotate(720deg)';
|
||||||
|
setTimeout(() => {
|
||||||
|
confetti.remove();
|
||||||
|
}, 5000);
|
||||||
|
}, 100);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// 获取随机颜色
|
||||||
|
function getRandomColor() {
|
||||||
|
const colors = ['#f00', '#0f0', '#00f', '#ff0', '#f0f', '#0ff', '#333', '#666', '#999'];
|
||||||
|
return colors[Math.floor(Math.random() * colors.length)];
|
||||||
|
}
|
||||||
|
|
||||||
|
// 初始化页面
|
||||||
|
initPage();
|
||||||
});
|
});
|
||||||
|
|
||||||
</script>
|
</script>
|
||||||
|
|||||||
File diff suppressed because it is too large
Load Diff
@@ -86,6 +86,7 @@ class AccountController extends Crud
|
|||||||
$username = $request->post('username', '');
|
$username = $request->post('username', '');
|
||||||
$this->removeLoginLimit($username);
|
$this->removeLoginLimit($username);
|
||||||
$password = $request->post('password', '');
|
$password = $request->post('password', '');
|
||||||
|
$code = $request->post('code', '');
|
||||||
if (!$username) {
|
if (!$username) {
|
||||||
return $this->fail('用户名不能为空');
|
return $this->fail('用户名不能为空');
|
||||||
}
|
}
|
||||||
@@ -94,26 +95,33 @@ class AccountController extends Crud
|
|||||||
* @var Admin $admin
|
* @var Admin $admin
|
||||||
*/
|
*/
|
||||||
$admin = Admin::where('username', $username)->find();
|
$admin = Admin::where('username', $username)->find();
|
||||||
// if (!$admin || !Util::passwordVerify($password, $admin->password)) {
|
|
||||||
// return $this->fail('账户不存在或密码错误');
|
|
||||||
// }
|
|
||||||
//$secret = $admin['totp_secret'] ?:'EJGYB7OZR2W46XRX7VB3PXHSOY4LUAWCA5GTDAVTWKHXNDAAAIIP7AQ3JSO3XZJNX5J5OTIDEQVKLYFYIYNAXSCYF4GNZ2EMA4ORA3Y';
|
|
||||||
//\support\Log::alert($admin['totp_secret']);
|
|
||||||
$totp = \OTPHP\TOTP::create($admin->totp_secret);
|
|
||||||
//$secret = $totp->getSecret();
|
|
||||||
//$totp->setLabel('cansnow');
|
|
||||||
//$totp->setIssuer('DVPN');
|
|
||||||
//$qrCodeUri =$totp->getProvisioningUri();
|
|
||||||
//cp($secret);
|
|
||||||
//cp($qrCodeUri);
|
|
||||||
//cp('https://api.qrtool.cn/?text='.urlencode($qrCodeUri));
|
|
||||||
//cp($totp->at(time()));
|
|
||||||
if (!$totp->verify($request->post('code', ''))) {
|
|
||||||
return $this->fail('当前账户暂时无法登录1');
|
|
||||||
}
|
|
||||||
if ($admin->status != 1) {
|
if ($admin->status != 1) {
|
||||||
return $this->fail('当前账户暂时无法登录');
|
return $this->fail('当前账户暂时无法登录');
|
||||||
}
|
}
|
||||||
|
if(!$code && !$password){
|
||||||
|
return $this->fail('请输入验证码或密码');
|
||||||
|
}
|
||||||
|
if($code){
|
||||||
|
//$secret = $admin['totp_secret'] ?:'EJGYB7OZR2W46XRX7VB3PXHSOY4LUAWCA5GTDAVTWKHXNDAAAIIP7AQ3JSO3XZJNX5J5OTIDEQVKLYFYIYNAXSCYF4GNZ2EMA4ORA3Y';
|
||||||
|
//\support\Log::alert($admin['totp_secret']);
|
||||||
|
$totp = \OTPHP\TOTP::create($admin->totp_secret);
|
||||||
|
//$secret = $totp->getSecret();
|
||||||
|
//$totp->setLabel('cansnow');
|
||||||
|
//$totp->setIssuer('DVPN');
|
||||||
|
//$qrCodeUri =$totp->getProvisioningUri();
|
||||||
|
//cp($secret);
|
||||||
|
//cp($qrCodeUri);
|
||||||
|
//cp('https://api.qrtool.cn/?text='.urlencode($qrCodeUri));
|
||||||
|
//cp($totp->at(time()));
|
||||||
|
if (!$totp->verify($code)) {
|
||||||
|
return $this->fail('动态密码错误');
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if($password){
|
||||||
|
if (!$admin || !Util::passwordVerify($password, $admin->password)) {
|
||||||
|
return $this->fail('账户不存在或密码错误');
|
||||||
|
}
|
||||||
|
}
|
||||||
$admin->login_at = time();
|
$admin->login_at = time();
|
||||||
$admin->save();
|
$admin->save();
|
||||||
$this->removeLoginLimit($username);
|
$this->removeLoginLimit($username);
|
||||||
|
|||||||
@@ -374,22 +374,15 @@ class Crud extends Base
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
$password_filed = 'password';
|
$password_fileds = ['password','trade_password','empty_password'];
|
||||||
if (isset($data[$password_filed])) {
|
foreach($password_fileds as $password_filed){
|
||||||
// 密码为空,则不更新密码
|
if (isset($data[$password_filed])) {
|
||||||
if ($data[$password_filed] === '') {
|
// 密码为空,则不更新密码
|
||||||
unset($data[$password_filed]);
|
if ($data[$password_filed] === '') {
|
||||||
} else {
|
unset($data[$password_filed]);
|
||||||
$data[$password_filed] = Util::passwordHash(md5($data[$password_filed]));
|
} else {
|
||||||
}
|
$data[$password_filed] = Util::passwordHash(md5($data[$password_filed]));
|
||||||
}
|
}
|
||||||
$password_filed = 'trade_password';
|
|
||||||
if (isset($data[$password_filed])) {
|
|
||||||
// 密码为空,则不更新密码
|
|
||||||
if ($data[$password_filed] === '') {
|
|
||||||
unset($data[$password_filed]);
|
|
||||||
} else {
|
|
||||||
$data[$password_filed] = Util::passwordHash($data[$password_filed]);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
unset($data[$primary_key]);
|
unset($data[$primary_key]);
|
||||||
|
|||||||
@@ -69,7 +69,6 @@ class IndexController extends Base
|
|||||||
}
|
}
|
||||||
//$day7_user_recharge_sum = Recharge::where('status',2)->whereTime('created_at', '-7 days')->sum('amount');
|
//$day7_user_recharge_sum = Recharge::where('status',2)->whereTime('created_at', '-7 days')->sum('amount');
|
||||||
// 总用户数
|
// 总用户数
|
||||||
$user_count = \app\model\User::where('status',1)->count('id');
|
|
||||||
$recharge_total = 0;//\app\model\Recharge::where('status',\app\enum\RechargeStatus::COMPLETE->value)->sum('amount');
|
$recharge_total = 0;//\app\model\Recharge::where('status',\app\enum\RechargeStatus::COMPLETE->value)->sum('amount');
|
||||||
// mysql版本
|
// mysql版本
|
||||||
$withdrawl_total = \app\model\Withdrawl::where('status',\app\enum\WithdrawlStatus::COMPLETE->value)->sum('recive_amount');
|
$withdrawl_total = \app\model\Withdrawl::where('status',\app\enum\WithdrawlStatus::COMPLETE->value)->sum('recive_amount');
|
||||||
@@ -90,7 +89,6 @@ class IndexController extends Base
|
|||||||
return view('index/dashboard', [
|
return view('index/dashboard', [
|
||||||
'today_user_recharge_sum' => formatAmount(cache('statistics_recharge_amount_'.date('Y-m-d')),0),
|
'today_user_recharge_sum' => formatAmount(cache('statistics_recharge_amount_'.date('Y-m-d')),0),
|
||||||
'day7_user_recharge_sum' => formatAmount($day7_user_recharge_sum,0),
|
'day7_user_recharge_sum' => formatAmount($day7_user_recharge_sum,0),
|
||||||
'user_count' => $user_count,
|
|
||||||
//'recharge' => $recharge,
|
//'recharge' => $recharge,
|
||||||
//'withdrawl' => $withdrawl,
|
//'withdrawl' => $withdrawl,
|
||||||
'recharge_total' => formatAmount($recharge_total,0),
|
'recharge_total' => formatAmount($recharge_total,0),
|
||||||
@@ -122,39 +120,28 @@ class IndexController extends Base
|
|||||||
}
|
}
|
||||||
return $this->success('ok',$res);
|
return $this->success('ok',$res);
|
||||||
}
|
}
|
||||||
function recharge_lines()
|
function lines_data(){
|
||||||
{
|
$days = Input('days',7);
|
||||||
|
$items = Input('items','');
|
||||||
|
$items = explode(',',$items);
|
||||||
$res = [];
|
$res = [];
|
||||||
for ($i=7; $i >= 0; $i--) {
|
for ($i=$days; $i >= 0; $i--) {
|
||||||
$date = date('Y-m-d',strtotime('-'.$i.' days'));
|
$date = date('Y-m-d',strtotime('-'.$i.' days'));
|
||||||
$res[$date] = [
|
$item= [];
|
||||||
'amount' => cache('statistics_recharge_amount_'.$date)?:0,
|
foreach($items as $k=>$v){
|
||||||
];
|
if($v == 'withdrawl'){
|
||||||
|
$item[$v] = cache('statistics_withdrawl_amount_'.$date)?:0;
|
||||||
|
}
|
||||||
|
if($v == 'recharge'){
|
||||||
|
$item[$v] = cache('statistics_recharge_amount_'.$date)?:0;
|
||||||
|
}
|
||||||
|
if($v == 'register'){
|
||||||
|
$item[$v] = cache('statistics_register_'.$date)?:0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
$res[$date] = $item;
|
||||||
}
|
}
|
||||||
return $this->success('ok',$res);
|
return $this->success('ok'.$items,$res);
|
||||||
}
|
|
||||||
function withdrawl_lines()
|
|
||||||
{
|
|
||||||
$res = [];
|
|
||||||
for ($i=7; $i >= 0; $i--) {
|
|
||||||
$date = date('Y-m-d',strtotime('-'.$i.' days'));
|
|
||||||
$res[$date] = [
|
|
||||||
'amount' => cache('statistics_withdrawl_amount_'.$date)?:0,
|
|
||||||
];
|
|
||||||
}
|
|
||||||
return $this->success('ok',$res);
|
|
||||||
}
|
|
||||||
function money_lines()
|
|
||||||
{
|
|
||||||
$res = [];
|
|
||||||
for ($i=7; $i >= 0; $i--) {
|
|
||||||
$date = date('Y-m-d',strtotime('-'.$i.' days'));
|
|
||||||
$res[$date] = [
|
|
||||||
'withdrawl' => cache('statistics_withdrawl_amount_'.$date)?:0,
|
|
||||||
'recharge' => cache('statistics_recharge_amount_'.$date)?:0,
|
|
||||||
];
|
|
||||||
}
|
|
||||||
return $this->success('ok',$res);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -28,6 +28,7 @@ class Config implements MiddlewareInterface
|
|||||||
$config['action'] = $request->action_name;
|
$config['action'] = $request->action_name;
|
||||||
$config['moduleurl'] = admin_path();
|
$config['moduleurl'] = admin_path();
|
||||||
$config['admin_path'] = admin_path();
|
$config['admin_path'] = admin_path();
|
||||||
|
$config['development'] = config('site.name') == '瞬聊Test';
|
||||||
$config['domain'] = env_get('server.domain','');
|
$config['domain'] = env_get('server.domain','');
|
||||||
$request->_view_vars = array_merge((array) $request->_view_vars,[
|
$request->_view_vars = array_merge((array) $request->_view_vars,[
|
||||||
'user' => session('admin'),
|
'user' => session('admin'),
|
||||||
|
|||||||
@@ -54,18 +54,28 @@
|
|||||||
<div class="login-header text-center">
|
<div class="login-header text-center">
|
||||||
<a href="javascript:;" style="font-size: 22px;display: flex;align-items: center;justify-content: center;"> <img alt="{$title}" src="{$logo}" width="32" class="m-r-5" />{$title}</a>
|
<a href="javascript:;" style="font-size: 22px;display: flex;align-items: center;justify-content: center;"> <img alt="{$title}" src="{$logo}" width="32" class="m-r-5" />{$title}</a>
|
||||||
</div>
|
</div>
|
||||||
|
<ul class="nav nav-tabs nav-justified">
|
||||||
|
<li class="active"><a data-toggle="tab" href="#otop_login">OTOP登录</a></li>
|
||||||
|
<li class="nav-item"><a data-toggle="tab" href="#passowrd_login">密码登录</a></li>
|
||||||
|
</ul>
|
||||||
<form action="{:url('account/login')}" method="post" id="loginform" valid>
|
<form action="{:url('account/login')}" method="post" id="loginform" valid>
|
||||||
<div class="form-group has-feedback feedback-left">
|
<div class="form-group has-feedback feedback-left">
|
||||||
<span class="mdi mdi-account form-control-feedback" aria-hidden="true"></span>
|
<span class="mdi mdi-account form-control-feedback" aria-hidden="true"></span>
|
||||||
<input type="text" placeholder="请输入您的用户名" class="form-control" name="username" id="username" data-rule="required" data-msg="请输入您的用户名"/>
|
<input type="text" placeholder="请输入您的用户名" class="form-control" name="username" id="username" data-rule="required" data-msg="请输入您的用户名"/>
|
||||||
</div>
|
</div>
|
||||||
<!-- <div class="form-group has-feedback feedback-left">
|
<div class="tab-content">
|
||||||
<span class="mdi mdi-lock form-control-feedback" aria-hidden="true"></span>
|
<div class="tab-pane fade active in" id="otop_login">
|
||||||
<input type="password" placeholder="请输入密码" class="form-control" id="password" name="password" data-rule="required;password" />
|
<div class="form-group has-feedback feedback-left">
|
||||||
</div> -->
|
<span class="mdi mdi-lock form-control-feedback" aria-hidden="true"></span>
|
||||||
<div class="form-group has-feedback feedback-left">
|
<input type="code" placeholder="请输入OTOP验证码" class="form-control" id="code" name="code" data-rule="required(#otop_login.active);length(4)" data-msg="请输入OTOP验证码" />
|
||||||
<span class="mdi mdi-lock form-control-feedback" aria-hidden="true"></span>
|
</div>
|
||||||
<input type="code" placeholder="请输入OTOP验证码" class="form-control" id="code" name="code" data-rule="required;length(4)" data-msg="请输入OTOP验证码" />
|
</div>
|
||||||
|
<div class="tab-pane fade" id="passowrd_login">
|
||||||
|
<div class="form-group has-feedback feedback-left">
|
||||||
|
<span class="mdi mdi-lock form-control-feedback" aria-hidden="true"></span>
|
||||||
|
<input type="password" placeholder="请输入密码" class="form-control" id="password" name="password" data-rule="required(#passowrd_login.active);password" />
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
{if Config('site.admin_login_captcha')}
|
{if Config('site.admin_login_captcha')}
|
||||||
<div class="form-group has-feedback feedback-left row">
|
<div class="form-group has-feedback feedback-left row">
|
||||||
|
|||||||
@@ -19,8 +19,7 @@
|
|||||||
<p class="h6 text-white m-t-0">7日内充值</p>
|
<p class="h6 text-white m-t-0">7日内充值</p>
|
||||||
<p class="h3 text-white m-b-0 fa-1-5x"><?=$day7_user_recharge_sum?></p>
|
<p class="h3 text-white m-b-0 fa-1-5x"><?=$day7_user_recharge_sum?></p>
|
||||||
</div>
|
</div>
|
||||||
<div class="pull-left"> <span class="img-avatar img-avatar-48 bg-translucent"><i
|
<div class="pull-left"> <span class="img-avatar img-avatar-48 bg-translucent"><i class="mdi mdi-account fa-1-5x"></i></span> </div>
|
||||||
class="mdi mdi-account fa-1-5x"></i></span> </div>
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
@@ -32,8 +31,7 @@
|
|||||||
<p class="h6 text-white m-t-0">总充值</p>
|
<p class="h6 text-white m-t-0">总充值</p>
|
||||||
<p class="h3 text-white m-b-0 fa-1-5x"><?=$recharge_total?></p>
|
<p class="h3 text-white m-b-0 fa-1-5x"><?=$recharge_total?></p>
|
||||||
</div>
|
</div>
|
||||||
<div class="pull-left"> <span class="img-avatar img-avatar-48 bg-translucent"><i
|
<div class="pull-left"> <span class="img-avatar img-avatar-48 bg-translucent"><i class="mdi mdi-arrow-down-bold fa-1-5x"></i></span> </div>
|
||||||
class="mdi mdi-arrow-down-bold fa-1-5x"></i></span> </div>
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
@@ -45,8 +43,7 @@
|
|||||||
<p class="h6 text-white m-t-0">总提现</p>
|
<p class="h6 text-white m-t-0">总提现</p>
|
||||||
<p class="h3 text-white m-b-0 fa-1-5x"><?=$withdrawl_total?></p>
|
<p class="h3 text-white m-b-0 fa-1-5x"><?=$withdrawl_total?></p>
|
||||||
</div>
|
</div>
|
||||||
<div class="pull-left"> <span class="img-avatar img-avatar-48 bg-translucent"><i
|
<div class="pull-left"> <span class="img-avatar img-avatar-48 bg-translucent"><i class="mdi mdi-arrow-up-bold fa-1-5x"></i></span> </div>
|
||||||
class="mdi mdi-arrow-up-bold fa-1-5x"></i></span> </div>
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
@@ -90,28 +87,24 @@
|
|||||||
</colgroup>
|
</colgroup>
|
||||||
<tbody>
|
<tbody>
|
||||||
<tr>
|
<tr>
|
||||||
<td>渠道商数</td>
|
<td>用户总数</td>
|
||||||
<td>
|
<td><?php echo \app\model\User::count('id');?></td>
|
||||||
<?php
|
|
||||||
echo \app\model\User::where('group_id',1)->count('id');
|
|
||||||
?>
|
|
||||||
</td>
|
|
||||||
</tr>
|
</tr>
|
||||||
<tr>
|
<tr>
|
||||||
<td>用户余额总和</td>
|
<td>VIP用户数</td>
|
||||||
<td>{$user_money_total}</td>
|
<td><?php echo \app\model\User::where('role_id',2)->count('id');?></td>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<td>SVIP1用户数</td>
|
||||||
|
<td><?php echo \app\model\User::where('role_id',3)->count('id');?></td>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<td>SVIP2用户数</td>
|
||||||
|
<td><?php echo \app\model\User::where('role_id',4)->count('id');?></td>
|
||||||
</tr>
|
</tr>
|
||||||
<tr>
|
<tr>
|
||||||
<td>用户积分总和</td>
|
<td>用户积分总和</td>
|
||||||
<td>{$user_score_total}</td>
|
<td><?php echo \app\model\User::sum('score');?></td>
|
||||||
</tr>
|
|
||||||
<tr>
|
|
||||||
<td>调研币总和</td>
|
|
||||||
<td><?php echo \app\model\User::sum('currency1');?></td>
|
|
||||||
</tr>
|
|
||||||
<tr>
|
|
||||||
<td>待分配总和</td>
|
|
||||||
<td><?php echo \app\model\User::sum('currency7');?></td>
|
|
||||||
</tr>
|
</tr>
|
||||||
</tbody>
|
</tbody>
|
||||||
</table>
|
</table>
|
||||||
@@ -132,49 +125,24 @@
|
|||||||
</colgroup>
|
</colgroup>
|
||||||
<tbody>
|
<tbody>
|
||||||
<tr>
|
<tr>
|
||||||
<td>问卷成交个数</td>
|
<td>操作系统</td>
|
||||||
<td>
|
<td>{$os}</td>
|
||||||
<?php $system_question_total = cache('system_question_total');echo $system_question_total;?>
|
|
||||||
</td>
|
|
||||||
</tr>
|
</tr>
|
||||||
<tr>
|
<tr>
|
||||||
<td>预计支出泡沫</td>
|
<td>workerman</td>
|
||||||
<td>
|
<td>{$workerman_version}</td>
|
||||||
<?php $system_question_cha_total = 0;echo $system_question_cha_total;?>
|
|
||||||
</td>
|
|
||||||
</tr>
|
</tr>
|
||||||
<tr>
|
<tr>
|
||||||
<td>总沉淀金额</td>
|
<td>webman</td>
|
||||||
<td>
|
<td>{$webman_version}</td>
|
||||||
<?php
|
|
||||||
$system_role_buy_amount_total = cache('system_role_buy_amount_total');
|
|
||||||
$system_role_buy_reward_total = cache('system_role_buy_reward_total');
|
|
||||||
$system_role_buy_residual_total = $system_role_buy_amount_total - $system_role_buy_reward_total;
|
|
||||||
echo $system_role_buy_residual_total;
|
|
||||||
?>
|
|
||||||
|
|
||||||
</td>
|
|
||||||
</tr>
|
</tr>
|
||||||
<tr>
|
<tr>
|
||||||
<td>实际泡沫</td>
|
<td>php</td>
|
||||||
<td>
|
<td>{$php_version}</td>
|
||||||
<?php
|
|
||||||
$cha = $system_question_cha_total - $system_role_buy_residual_total;
|
|
||||||
if($cha>0){
|
|
||||||
echo '<span class="text-danger">'.$cha.'</span>';
|
|
||||||
}else{
|
|
||||||
echo '<span class="text-success">'.$cha.'</span>';
|
|
||||||
}
|
|
||||||
?>
|
|
||||||
</td>
|
|
||||||
</tr>
|
</tr>
|
||||||
<tr>
|
<tr>
|
||||||
<td> </td>
|
<td>MySQL</td>
|
||||||
<td></td>
|
<td>{$mysql_version}</td>
|
||||||
</tr>
|
|
||||||
<tr>
|
|
||||||
<td> </td>
|
|
||||||
<td></td>
|
|
||||||
</tr>
|
</tr>
|
||||||
</tbody>
|
</tbody>
|
||||||
</table>
|
</table>
|
||||||
|
|||||||
@@ -83,7 +83,11 @@ define(['lightyear','multitabs', '../libs/Chart','form','bootstrap'], function (
|
|||||||
setTheme = function (input_name, data_name) {
|
setTheme = function (input_name, data_name) {
|
||||||
$("input[name='" + input_name + "']").click(function () {
|
$("input[name='" + input_name + "']").click(function () {
|
||||||
$('body').attr(data_name, $(this).val());
|
$('body').attr(data_name, $(this).val());
|
||||||
|
localStorage.setItem(data_name,$(this).val());
|
||||||
});
|
});
|
||||||
|
if(Config.development){
|
||||||
|
$('body').attr(data_name, localStorage.getItem(data_name) || 'color_8');
|
||||||
|
}
|
||||||
}
|
}
|
||||||
setTheme('logo_bg', 'data-logobg');
|
setTheme('logo_bg', 'data-logobg');
|
||||||
setTheme('header_bg', 'data-headerbg');
|
setTheme('header_bg', 'data-headerbg');
|
||||||
@@ -167,47 +171,7 @@ define(['lightyear','multitabs', '../libs/Chart','form','bootstrap'], function (
|
|||||||
});
|
});
|
||||||
},
|
},
|
||||||
dashboard: function () {
|
dashboard: function () {
|
||||||
// new Chart(
|
$.getJSON('index/lines_data?items=withdrawl,recharge&days=7',function(res){
|
||||||
// document.getElementsByClassName('js-chartjs-bars'),
|
|
||||||
// {
|
|
||||||
// type: 'bar',
|
|
||||||
// data: {
|
|
||||||
// labels: recharge_labels,
|
|
||||||
// datasets: [
|
|
||||||
// {
|
|
||||||
// label: '充值统计',
|
|
||||||
// data: recharge_values,
|
|
||||||
// borderColor: '#358ed7',
|
|
||||||
// backgroundColor: 'rgba(53, 142, 215, 0.175)',
|
|
||||||
// borderWidth: 1,
|
|
||||||
// fill: false,
|
|
||||||
// lineTension: 0.5
|
|
||||||
// },
|
|
||||||
// ]
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
// );
|
|
||||||
// new Chart(
|
|
||||||
// document.getElementsByClassName('js-chartjs-lines'),
|
|
||||||
// {
|
|
||||||
// type: 'bar',//line
|
|
||||||
// data: {
|
|
||||||
// labels: withdrawl_labels,
|
|
||||||
// datasets: [
|
|
||||||
// {
|
|
||||||
// label: '提现统计',
|
|
||||||
// data: withdrawl_values,
|
|
||||||
// borderColor: '#358ed7',
|
|
||||||
// backgroundColor: 'rgba(53, 142, 215, 0.175)',
|
|
||||||
// borderWidth: 1,
|
|
||||||
// fill: false,
|
|
||||||
// lineTension: 0.5
|
|
||||||
// }
|
|
||||||
// ]
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
// );
|
|
||||||
$.getJSON('index/money_lines',function(res){
|
|
||||||
res = res.data;
|
res = res.data;
|
||||||
var labels=[];
|
var labels=[];
|
||||||
var withdrawl_values=[];
|
var withdrawl_values=[];
|
||||||
@@ -248,17 +212,13 @@ define(['lightyear','multitabs', '../libs/Chart','form','bootstrap'], function (
|
|||||||
}
|
}
|
||||||
);
|
);
|
||||||
});
|
});
|
||||||
$.getJSON('index/role_buy_lines',function(res){
|
$.getJSON('index/lines_data?items=register&days=7',function(res){
|
||||||
res = res.data;
|
res = res.data;
|
||||||
var amount=[];
|
var register=[];
|
||||||
var reward=[];
|
|
||||||
var residual=[];
|
|
||||||
var labels=[];
|
var labels=[];
|
||||||
for (let date in res) {
|
for (let date in res) {
|
||||||
labels.push(date);
|
labels.push(date);
|
||||||
amount.push(res[date].amount);
|
register.push(res[date].register);
|
||||||
reward.push(res[date].reward);
|
|
||||||
residual.push(res[date].residual);
|
|
||||||
}
|
}
|
||||||
new Chart(document.getElementsByClassName('js-role_buy_lines'),{
|
new Chart(document.getElementsByClassName('js-role_buy_lines'),{
|
||||||
type: 'line',
|
type: 'line',
|
||||||
@@ -266,32 +226,32 @@ define(['lightyear','multitabs', '../libs/Chart','form','bootstrap'], function (
|
|||||||
labels: labels,
|
labels: labels,
|
||||||
datasets: [
|
datasets: [
|
||||||
{
|
{
|
||||||
label: '总购买金额',
|
label: '注册统计',
|
||||||
data: amount,
|
data: register,
|
||||||
borderColor: 'rgba(43, 191, 232, 0.7)',
|
borderColor: 'rgba(43, 191, 232, 0.7)',
|
||||||
backgroundColor: 'rgba(43, 191, 232, 0.7)',
|
backgroundColor: 'rgba(43, 191, 232, 0.7)',
|
||||||
borderWidth: 2,
|
borderWidth: 2,
|
||||||
fill: false,
|
fill: false,
|
||||||
lineTension: 0.5
|
lineTension: 0.5
|
||||||
},
|
},
|
||||||
{
|
// {
|
||||||
label: '奖励统计',
|
// label: '奖励统计',
|
||||||
data: reward,
|
// data: reward,
|
||||||
borderColor: 'rgba(166, 53, 215, 0.7)',
|
// borderColor: 'rgba(166, 53, 215, 0.7)',
|
||||||
backgroundColor: 'rgba(166, 53, 215, 0.7)',
|
// backgroundColor: 'rgba(166, 53, 215, 0.7)',
|
||||||
borderWidth: 2,
|
// borderWidth: 2,
|
||||||
fill: false,
|
// fill: false,
|
||||||
lineTension: 0.5
|
// lineTension: 0.5
|
||||||
},
|
// },
|
||||||
{
|
// {
|
||||||
label: '沉淀统计',
|
// label: '沉淀统计',
|
||||||
data: residual,
|
// data: residual,
|
||||||
borderColor: 'rgba(59, 199, 8, 0.7)',
|
// borderColor: 'rgba(59, 199, 8, 0.7)',
|
||||||
backgroundColor: 'rgba(59, 199, 8, 0.7)',
|
// backgroundColor: 'rgba(59, 199, 8, 0.7)',
|
||||||
borderWidth: 2,
|
// borderWidth: 2,
|
||||||
fill: false,
|
// fill: false,
|
||||||
lineTension: 0.5
|
// lineTension: 0.5
|
||||||
}
|
// }
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -50,11 +50,13 @@ define(['table', 'upload','form','qrcode'], function (Table,Upload,Form) {
|
|||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: "用户名",
|
title: "用户名",
|
||||||
field: "username"
|
field: "username",
|
||||||
|
filter: "string"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: "昵称",
|
title: "昵称",
|
||||||
field: "nickname"
|
field: "nickname",
|
||||||
|
filter: "string"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: "头像",
|
title: "头像",
|
||||||
|
|||||||
@@ -79,3 +79,11 @@ bash bootstrap.sh
|
|||||||
mage
|
mage
|
||||||
mage start
|
mage start
|
||||||
docker exec -it mongo mongorestore --uri="mongodb://openIM:n1e5a6s6m7@172.18.0.1:37017/openim_v3" /data/backup/3/openim_v3
|
docker exec -it mongo mongorestore --uri="mongodb://openIM:n1e5a6s6m7@172.18.0.1:37017/openim_v3" /data/backup/3/openim_v3
|
||||||
|
docker exec -it mongo mongorestore --uri="mongodb://openIM:n1e5a6s6m7@localhost:27017/openim_v3" /data/backup/0/openim_v3
|
||||||
|
|
||||||
|
修复未读<0的问题
|
||||||
|
cd /www/wwwroot/im/server
|
||||||
|
go run tools/fix-conversation-maxseq/main.go --config config --dry-run
|
||||||
|
清理15天以前的消息
|
||||||
|
cd /www/wwwroot/im/server
|
||||||
|
go run tools/clean-old-messages/main.go --config config --days 15
|
||||||
|
|||||||
+1
-1
@@ -68,7 +68,7 @@ class Jwt
|
|||||||
'password' => $password,
|
'password' => $password,
|
||||||
'email' => $email,
|
'email' => $email,
|
||||||
'mobile' => $mobile,
|
'mobile' => $mobile,
|
||||||
'level' => 1,
|
'level' => 0,
|
||||||
'score' => 0,
|
'score' => 0,
|
||||||
'avatar' => '',
|
'avatar' => '',
|
||||||
];
|
];
|
||||||
|
|||||||
@@ -33,9 +33,8 @@ class Auth
|
|||||||
public function getUserToken(string $userID, string $platformID = 'android'): array
|
public function getUserToken(string $userID, string $platformID = 'android'): array
|
||||||
{
|
{
|
||||||
// 获取管理员token
|
// 获取管理员token
|
||||||
$adminToken = Utils::getAdminToken();
|
|
||||||
$platformID = Utils::getPlatformId( $platformID );
|
$platformID = Utils::getPlatformId( $platformID );
|
||||||
return Utils::send(Url::$getUserToken, ['userID' => $userID, 'platformID' => $platformID], '获取用户token错误', $adminToken);
|
return Utils::send(Url::$getUserToken, ['userID' => $userID, 'platformID' => $platformID], '获取用户token错误');
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
@@ -63,7 +63,7 @@ class Friend
|
|||||||
* @param string $friendUserID 好友ID
|
* @param string $friendUserID 好友ID
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function deleteFriend(string $ownerUserID, string $friendUserID): array
|
public function deleteFriend(string $ownerUserID, string $friendUserID): array|bool
|
||||||
{
|
{
|
||||||
// 获取管理员token
|
// 获取管理员token
|
||||||
$adminToken = Utils::getAdminToken();
|
$adminToken = Utils::getAdminToken();
|
||||||
|
|||||||
@@ -192,6 +192,9 @@ class Utils
|
|||||||
return self::getTokenManager()->clearToken($userID, $isAdmin);
|
return self::getTokenManager()->clearToken($userID, $isAdmin);
|
||||||
}
|
}
|
||||||
public static function getPlatformId($name=''): int{
|
public static function getPlatformId($name=''): int{
|
||||||
|
if(ctype_digit($name)){
|
||||||
|
return (int)$name;
|
||||||
|
}
|
||||||
$arr = [
|
$arr = [
|
||||||
'ios' => 1,
|
'ios' => 1,
|
||||||
'android' => 2,
|
'android' => 2,
|
||||||
|
|||||||
Reference in New Issue
Block a user