登陆3次错误锁定,后台移动端侧边栏优化,layui2.6.7

This commit is contained in:
taoser 2021-05-19 16:04:05 +08:00
parent b53ad8ce08
commit 8c70a21d43
17 changed files with 94 additions and 214 deletions

View File

@ -7,6 +7,7 @@ use think\facade\Session;
use think\facade\Cookie; use think\facade\Cookie;
use think\facade\Config; use think\facade\Config;
use think\facade\Lang; use think\facade\Lang;
use app\event\UserLogin;
class User extends Model class User extends Model
{ {
@ -44,12 +45,18 @@ class User extends Model
{ {
//查询使用邮箱或者用户名登陆 //查询使用邮箱或者用户名登陆
$user = $this::whereOr('email',$data['name'])->whereOr('name',$data['name'])->findOrEmpty(); $user = $this::whereOr('email',$data['name'])->whereOr('name',$data['name'])->findOrEmpty();
if(!$user->isEmpty()){
//对输入的密码字段进行MD5加密再进行数据库的查询 if(!($user->isEmpty())){
//错误登陆连续3次且小于10分钟
if((time() - $user->login_error_time < 60) && is_int($user->login_error_num/3)){
return Lang::get('Please log in 10 minutes later');
}
//对输入的密码字段进行MD5加密再进行数据库的查询
$salt = substr(md5($user['create_time']),-6); $salt = substr(md5($user['create_time']),-6);
$pwd = substr_replace(md5($data['password']),$salt,0,6); $pwd = substr_replace(md5($data['password']),$salt,0,6);
$data['password'] = md5($pwd); $data['password'] = md5($pwd);
if($user['password'] == $data['password']){ if($user['password'] == $data['password']){
//将用户数据写入Session //将用户数据写入Session
Session::set('user_id',$user['id']); Session::set('user_id',$user['id']);
@ -62,12 +69,24 @@ class User extends Model
//Cookie::set('user_id', $user['id'], 604800); //Cookie::set('user_id', $user['id'], 604800);
//Cookie::set('user_name', $user['name'], 604800); //Cookie::set('user_name', $user['name'], 604800);
} }
$userInfo = ['type'=>'log','id'=>$user->id];
event(new UserLogin($userInfo));
//查询结果1表示有用户用户名密码正确 //查询结果1表示有用户用户名密码正确
return 1; return 1;
} } else {//密码错误登陆错误次数加1
$userInfo = ['type'=>'logError','id'=>$user->id];
event(new UserLogin($userInfo));
//echo $user->login_error_num;
//连续3次错误
if(is_int(($user->login_error_num+1)/3) && $user->login_error_num >0 ){
return Lang::get('Login error 3, Please log in 10 minutes later');
}
}
} }
return Lang::get('username or password error'); return Lang::get('username or password error');
} }
//更新数据 //更新数据

View File

@ -6,11 +6,9 @@ namespace app\event;
class UserLogin class UserLogin
{ {
public $name; public $user;
public $ip; public function __construct($user)
public function __construct($name,$ip)
{ {
$this->name = $name; $this->user = $user;
$this->ip = $ip;
} }
} }

View File

@ -12,7 +12,7 @@ use think\facade\Cookie;
use think\facade\Cache; use think\facade\Cache;
use think\facade\View; use think\facade\View;
use app\common\model\User; use app\common\model\User;
use app\event\UserLogin;
class Login extends BaseController class Login extends BaseController
{ {
@ -69,13 +69,7 @@ class Login extends BaseController
//登陆请求 //登陆请求
$user = new User(); $user = new User();
$res = $user->login($data); $res = $user->login($data);
if ($res == 1) { if ($res == 1) { //登陆成功
//登陆成功
$ip = request()->ip();
$name = $data['name'];
//时间更新ip和日志
event(new UserLogin($name,$ip));
return Msgres::success('login_success',Cookie::get('url')); return Msgres::success('login_success',Cookie::get('url'));
} else { } else {
return Msgres::error($res); return Msgres::error($res);

View File

@ -123,6 +123,8 @@ return [
'in' => '在', 'in' => '在',
'accumulate points' => '积分', 'accumulate points' => '积分',
'my post' => '我的帖子', 'my post' => '我的帖子',
'my auth' => '我的授权',
'Please log in 10 minutes later' => '请10分钟后再登陆',
'Login error 3, Please log in 10 minutes later' => '连续登陆错误3次,请10分钟后登录',
]; ];

View File

@ -5,6 +5,8 @@ namespace app\listener;
use think\facade\Db; use think\facade\Db;
use think\facade\Log; use think\facade\Log;
use app\common\model\User;
use think\facade\Lang;
class UserLogin class UserLogin
{ {
@ -15,28 +17,40 @@ class UserLogin
*/ */
public function handle($user) public function handle($user)
{ {
$name = $user->name; $type = $user->user['type'];
$ip = $user->ip; $id = $user->user['id'];
/* $u = User::find($id);
$url = 'http://ip-api.com/json/'.$ip.'?lang=zh-CN'; //日志
//$url = 'http://ip-api.com/json/?lang=zh-CN'; if($type == 'log'){
$add = Api::urlGet($url); //$name = $user->user['name'];
if($add->status == 'success'){ $ip = request()->ip();
$city = $add->city;
} else { /*
$city ='未知'; $url = 'http://ip-api.com/json/'.$ip.'?lang=zh-CN';
} //$url = 'http://ip-api.com/json/?lang=zh-CN';
*/ $add = Api::urlGet($url);
if($add->status == 'success'){
$city = $add->city;
} else {
$city ='未知';
}
*/
Db::name('user')->where('name',$name)->update( $u->allowField(['last_login_ip','last_login_time','login_error_num'])->save(
[ [
//'city' => $city, //'city' => $city,
'last_login_ip' => $user->ip, 'last_login_ip' => $ip,
'last_login_time' => time() 'last_login_time' => time(),
] 'login_error_num' => 0
); ]
Log::channel('login')->info('login:{user} {ip}',['user'=>$name,'ip'=>$ip]); );
Log::channel('login')->info('login:{user} {ip}',['user'=>$u->name,'ip'=>$ip]);
}
if($type == 'logError'){
$res = $u->allowField(['login_error_num','login_error_time'])->save(['login_error_num'=>$u->login_error_num+1,'login_error_time'=>time()]);
}
} }
} }

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View File

@ -718,7 +718,7 @@ body .fly-user-main{position: relative; min-height: 600px;}
.fly-case-banner{width: 300px; margin-left: -150px;} .fly-case-banner{width: 300px; margin-left: -150px;}
body .fly-user-main{width: auto;} body .fly-user-main{width: auto;}
.fly-user-main>.layui-nav{left: -300px; transition: all .3s; -webkit-transition: all .3s;} .fly-user-main>.layui-nav{position: fixed;left: -300px; transition: all .3s; -webkit-transition: all .3s;}
.fly-user-main>.fly-panel-user{width: auto; margin-left: 0; transition: all .3s; -webkit-transition: all .3s;} .fly-user-main>.fly-panel-user{width: auto; margin-left: 0; transition: all .3s; -webkit-transition: all .3s;}
.site-tree-mobile-user{display: block!important; position: fixed; z-index: 100000; bottom: 20px; left: 10px; width: 50px; height: 50px; line-height: 50px; border-radius: 2px; text-align: center; background-color: rgba(0,0,0,.7); color: #fff;} .site-tree-mobile-user{display: block!important; position: fixed; z-index: 100000; bottom: 20px; left: 10px; width: 50px; height: 50px; line-height: 50px; border-radius: 2px; text-align: center; background-color: rgba(0,0,0,.7); color: #fff;}
.site-mobile .site-tree-mobile-user{display: none !important;} .site-mobile .site-tree-mobile-user{display: none !important;}

View File

@ -135,14 +135,14 @@ layui.define(['laypage', 'fly', 'element', 'flow'], function(exports){
page(); page();
} }
}; };
*/
if(elemUC[0]){ if(elemUC[0]){
layui.each(dom.mine.children(), function(index, item){ layui.each(dom.mine.children(), function(index, item){
var othis = $(item) var othis = $(item)
gather.mine(index, othis.data('type'), othis.data('url')); gather.mine(index, othis.data('type'), othis.data('url'));
}); });
} }
*/
//显示当前tab //显示当前tab
if(location.hash){ if(location.hash){
element.tabChange('user', location.hash.replace(/^#/, '')); element.tabChange('user', location.hash.replace(/^#/, ''));

View File

@ -1,4 +1,4 @@
<div class=" layui-hide-md"> <div class="layui-hide-md">
<div class="layui-panel site-menu" style="width: auto;"> <div class="layui-panel site-menu" style="width: auto;">
<ul class="layui-menu layui-menu-lg"> <ul class="layui-menu layui-menu-lg">
<li class="layui-menu-item-group" lay-options="{type: 'group', isAllowSpread: true}"> <li class="layui-menu-item-group" lay-options="{type: 'group', isAllowSpread: true}">
@ -7,18 +7,16 @@
</div> </div>
<hr> <hr>
<ul> <ul>
{volist name="cateList" id="cate"} {volist name="cateList" id="cate"}
<li {if condition="$cate.ename eq $Request.param.ename"} class="layui-this" {/if}> <li {if condition="$cate.ename eq $Request.param.ename"} class="layui-this" {/if}>
<div class="layui-menu-body-title"> <div class="layui-menu-body-title">
<a href="{:url('article/cate',['ename' => $cate.ename])}">{:cookie('think_lang') == 'en-us' ? $cate.ename : $cate.catename} <a href="{:url('article/cate',['ename' => $cate.ename])}">{:cookie('think_lang') == 'en-us' ? $cate.ename : $cate.catename}
<span class="layui-font-12 layui-font-gray"> >></span> <span class="layui-font-12 layui-font-gray"> >> {$cate.ename}</span>
{if condition="$cate.is_hot eq 1"}<span class="layui-badge-dot"></span>{/if} {if condition="$cate.is_hot eq 1"}<span class="layui-badge-dot"></span>{/if}
</a> </a>
</div> </div>
</li> </li>
{/volist} {/volist}
</ul> </ul>
</li> </li>
@ -50,14 +48,12 @@
<span>回首页 </span> <span>回首页 </span>
<span class="layui-font-12 layui-font-gray">index</span> <span class="layui-font-12 layui-font-gray">index</span>
</a> </a>
</div> </div>
</li> </li>
</ul> </ul>
</li> </li>
</ul> </ul>
</div> </div>
</div> </div>
<div class="site-tree-mobile layui-hide"> <div class="site-tree-mobile layui-hide">

View File

@ -20,8 +20,24 @@
{block name="content"} {block name="content"}
{/block} {/block}
</div> </div>
{include file="public/footer" /}
</div> </div>
{include file="public/footer" /} <script>
layui.cache.page = 'user';
layui.cache.user = {
username: '{$user.name??'游客'}'
,uid: '{$user.id ?? -1}'
,avatar: '{$user['user_img'] ?? '/static/res/images/avatar/00.jpg'}'
,experience: '{$user.point ?? ''}'
,sex: '{$user.sex ? '女':'男'}'
};
layui.config({
version: "3.0.0"
,base: '/static/res/mods/'
}).extend({
fly: 'index'
}).use('fly');
</script>
{block name="script"} {block name="script"}
js脚本 js脚本
{/block} {/block}

View File

@ -77,22 +77,8 @@
{block name="script"} {block name="script"}
<script> <script>
layui.cache.page = 'jie'; layui.use('face', function(){
layui.cache.user = { var $ = layui.$;
username: '{$user.name??'游客'}'
,uid: '{$user.id ?? -1}'
,avatar: '{$user['user_img'] ?? '/static/res/images/avatar/00.jpg'}'
,experience: '{$user.point ?? ''}'
,sex: '{$user.sex ? '女':'男'}'
};
layui.config({
version: "3.0.0"
,base: '/static/res/mods/'
}).extend({
fly: 'index'
}).use(['fly', 'face'], function(){
var $ = layui.$
,fly = layui.fly;
//如果你是采用模版自带的编辑器,你需要开启以下语句来解析。 //如果你是采用模版自带的编辑器,你需要开启以下语句来解析。
$('.detail-body').each(function(){ $('.detail-body').each(function(){

View File

@ -160,20 +160,4 @@
}); });
</script> </script>
<script>
layui.cache.page = 'user';
layui.cache.user = {
username: '{$user.name??'游客'}'
,uid: '{$user.id ?? -1}'
,avatar: '{$user['user_img'] ?? '/static/res/images/avatar/00.jpg'}'
,experience: '{$user.point ?? ''}'
,sex: '{$user.sex ? '女':'男'}'
};
layui.config({
version: "3.0.0"
,base: '/static/res/mods/'
}).extend({
fly: 'index'
}).use('fly');
</script>
{/block} {/block}

View File

@ -11,20 +11,6 @@
var messageFind = "{:url('index/Message/find')}", var messageFind = "{:url('index/Message/find')}",
messageRemove = "{:url('index/Message/remove')}", messageRemove = "{:url('index/Message/remove')}",
userNameJump = "{:url('index/Index/jump')}"; userNameJump = "{:url('index/Index/jump')}";
layui.cache.page = 'user';
layui.cache.user = {
username: '{$user.name??'游客'}'
,uid: '{$user.id ?? -1}'
,avatar: '{$user['user_img'] ?? '/static/res/images/avatar/00.jpg'}'
,experience: '{$user.point ?? ''}'
,sex: '{$user.sex ? '女':'男'}'
};
layui.config({
version: "3.0.0"
,base: '/static/res/mods/'
}).extend({
fly: 'index'
}).use('fly');
//点开标题改变帖子已读状态 //点开标题改变帖子已读状态
$('#LAY_minemsg').on('click','.art-title', function(){ $('#LAY_minemsg').on('click','.art-title', function(){

View File

@ -108,33 +108,6 @@
{/block} {/block}
{block name="script"} {block name="script"}
<script>
//layui.cache.page = 'user';
layui.cache.user = {
username: '{$user.name??'游客'}'
,uid: '{$user.id ?? -1}'
,avatar: '{$user['user_img'] ?? '/static/res/images/avatar/00.jpg'}'
,experience: '{$user.point ?? ''}'
,sex: '{$user.sex ? '女':'男'}'
};
layui.config({
version: "3.0.0"
,base: '/static/res/mods/'
}).extend({
fly: 'index'
}).use('fly');
</script>
<!--
onclick="dele();
<script>
function dele(){
if(confirm('确定删除吗') == true){
window.location.href = "{:url('article/delete')}"
}
}
</script>
-->
<script> <script>
layui.use('laypage', function(){ layui.use('laypage', function(){

View File

@ -189,21 +189,4 @@ $(function(){
}); });
</script> </script>
<script>
layui.cache.page = 'user';
layui.cache.user = {
username: '{$user.name??'游客'}'
,uid: '{$user.id ?? -1}'
,avatar: '{$user['user_img'] ?? '/static/res/images/avatar/00.jpg'}'
,experience: '{$user.point ?? ''}'
,sex: '{$user.sex ? '女':'男'}'
};
layui.config({
version: "3.0.0"
,base: '/static/res/mods/'
}).extend({
fly: 'index'
}).use('fly');
</script>
{/block} {/block}

View File

@ -1,70 +0,0 @@
{extend name="public/user" /}
{block name="content"}
<div class="fly-msg" style="margin-bottom: 20px;">
Hi{$Think.session.user_name},你已是我们的正式社员。
</div>
<div class="layui-row layui-col-space20">
<div class="layui-col-md6">
<div class="fly-panel fly-signin fly-panel-border">
<div class="fly-panel-title"> 签到
<i class="fly-mid"></i>
<a href="javascript:;" class="fly-link" id="LAY_signinHelp">说明</a>
<i class="fly-mid"></i>
<a href="javascript:;" class="fly-link" id="LAY_signinTop">活跃榜<span class="layui-badge-dot"></span></a>
<span class="fly-signin-days">已连续签到<cite>0</cite></span> </div>
<div class="fly-panel-main fly-signin-main">
<button class="layui-btn layui-btn-danger" id="LAY_signin">今日签到</button>
<span>可获得<cite>5</cite>飞吻</span>
</div>
</div>
</div>
<div class="layui-col-md6">
<div class="fly-panel fly-panel-border"> <div class="fly-panel-title"> 我的会员信息 </div>
<div class="fly-panel-main layui-text" style="padding: 18px 15px; height: 50px; line-height: 26px;">
<p>您的财富经验值0</p> <p>您当前为:非 VIP</p> </div> </div> </div>
<div class="layui-col-md12" style="margin-top: -20px;">
<div class="fly-panel fly-panel-border"> <div class="fly-panel-title"> 快捷方式 </div>
<div class="fly-panel-main">
<ul class="layui-row layui-col-space10 fly-shortcut">
<li class="layui-col-sm3 layui-col-xs4"> <a href="{:url('index/user/set')}"><i class="layui-icon"></i><cite>修改信息</cite></a> </li>
<li class="layui-col-sm3 layui-col-xs4"> <a href="{:url('index/user/set#avatar')}"><i class="layui-icon"></i><cite>修改头像</cite></a> </li>
<li class="layui-col-sm3 layui-col-xs4"> <a href="{:url('index/user/set#pass')}"><i class="layui-icon"></i><cite>修改密码</cite></a> </li>
<li class="layui-col-sm3 layui-col-xs4"> <a href="/user/set/#bind"><i class="layui-icon"></i><cite>帐号绑定</cite></a> </li>
<li class="layui-col-sm3 layui-col-xs4"> <a href="/jie/add/"><i class="layui-icon"></i><cite>发表新帖</cite></a> </li>
<li class="layui-col-sm3 layui-col-xs4"> <a href="/column/share/"><i class="layui-icon"></i><cite>查看分享</cite></a> </li>
<li class="layui-col-sm3 layui-col-xs4 LAY_search"> <a href="javascript:;"><i class="layui-icon"></i><cite>搜索资源</cite></a> </li>
<li class="layui-col-sm3 layui-col-xs4"> <a href="/user/post/#collection"><i class="layui-icon"></i><cite>我的收藏</cite></a> </li>
<li class="layui-col-sm3 layui-col-xs4"> <a href="/jie/15697/"><i class="layui-icon"></i><cite>成为赞助商</cite></a> </li>
<li class="layui-col-sm3 layui-col-xs4"> <a href="/jie/2461/"><i class="layui-icon"></i><cite>关注公众号</cite></a> </li>
<li class="layui-col-sm3 layui-col-xs4"> <a href="http://www.test.com/doc/"><i class="layui-icon"></i><cite>文档</cite></a> </li>
<li class="layui-col-sm3 layui-col-xs4"> <a href="http://www.test.com/demo/"><i class="layui-icon"></i><cite>示例</cite></a> </li>
</ul>
</div>
</div>
</div>
</div>
{/block}
{block name="script"}
<script>
layui.cache.page = 'user';
layui.cache.user = {
username: '{$user.name??'游客'}'
,uid: '{$user.id ?? -1}'
,avatar: '{$user['user_img'] ?? '/static/res/images/avatar/00.jpg'}'
,experience: '{$user.point ?? ''}'
,sex: '{$user.sex ? '女':'男'}'
};
layui.config({
version: "3.0.0"
,base: '/static/res/mods/'
}).extend({
fly: 'index'
}).use('fly');
</script>
{/block}