@ -0,0 +1,25 @@
|
||||
APP_DEBUG = true
|
||||
|
||||
[APP]
|
||||
DEFAULT_TIMEZONE = Asia/Taipei
|
||||
|
||||
[DATABASE]
|
||||
TYPE = mysql
|
||||
HOSTNAME = 127.0.0.1
|
||||
DATABASE = sso_h888_fun
|
||||
USERNAME = sso_h888_fun
|
||||
PASSWORD = EFyGDeDdnidrrsL3
|
||||
HOSTPORT = 3306
|
||||
CHARSET = utf8mb4
|
||||
DEBUG = true
|
||||
PREFIX = asc_
|
||||
|
||||
[LANG]
|
||||
default_lang = zh-tw
|
||||
|
||||
[JWT]
|
||||
SECRET=6dffd0dcd8d732d6b5e5e6c7bd7d1eff
|
||||
refresh_ttl = 360
|
||||
|
||||
[ASC]
|
||||
SMS_DISABLE = false
|
||||
@ -0,0 +1,12 @@
|
||||
{
|
||||
"name": "My Server",
|
||||
"host": "stage",
|
||||
"protocol": "sftp",
|
||||
"port": 22,
|
||||
"username": "root",
|
||||
"password": "%1WoCvN7FD.oUYhf",
|
||||
"remotePath": "/www/wwwroot/sso.h888.fun",
|
||||
"uploadOnSave": true,
|
||||
"useTempFile": false,
|
||||
"openSsh": false
|
||||
}
|
||||
@ -0,0 +1 @@
|
||||
deny from all
|
||||
@ -0,0 +1,22 @@
|
||||
<?php
|
||||
declare (strict_types = 1);
|
||||
|
||||
namespace app;
|
||||
|
||||
use think\Service;
|
||||
|
||||
/**
|
||||
* 应用服务类
|
||||
*/
|
||||
class AppService extends Service
|
||||
{
|
||||
public function register()
|
||||
{
|
||||
// 服务注册
|
||||
}
|
||||
|
||||
public function boot()
|
||||
{
|
||||
// 服务启动
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,94 @@
|
||||
<?php
|
||||
declare (strict_types = 1);
|
||||
|
||||
namespace app;
|
||||
|
||||
use think\App;
|
||||
use think\exception\ValidateException;
|
||||
use think\Validate;
|
||||
|
||||
/**
|
||||
* 控制器基础类
|
||||
*/
|
||||
abstract class BaseController
|
||||
{
|
||||
/**
|
||||
* Request实例
|
||||
* @var \think\Request
|
||||
*/
|
||||
protected $request;
|
||||
|
||||
/**
|
||||
* 应用实例
|
||||
* @var \think\App
|
||||
*/
|
||||
protected $app;
|
||||
|
||||
/**
|
||||
* 是否批量验证
|
||||
* @var bool
|
||||
*/
|
||||
protected $batchValidate = false;
|
||||
|
||||
/**
|
||||
* 控制器中间件
|
||||
* @var array
|
||||
*/
|
||||
protected $middleware = [];
|
||||
|
||||
/**
|
||||
* 构造方法
|
||||
* @access public
|
||||
* @param App $app 应用对象
|
||||
*/
|
||||
public function __construct(App $app)
|
||||
{
|
||||
$this->app = $app;
|
||||
$this->request = $this->app->request;
|
||||
|
||||
// 控制器初始化
|
||||
$this->initialize();
|
||||
}
|
||||
|
||||
// 初始化
|
||||
protected function initialize()
|
||||
{}
|
||||
|
||||
/**
|
||||
* 验证数据
|
||||
* @access protected
|
||||
* @param array $data 数据
|
||||
* @param string|array $validate 验证器名或者验证规则数组
|
||||
* @param array $message 提示信息
|
||||
* @param bool $batch 是否批量验证
|
||||
* @return array|string|true
|
||||
* @throws ValidateException
|
||||
*/
|
||||
protected function validate(array $data, $validate, array $message = [], bool $batch = false)
|
||||
{
|
||||
if (is_array($validate)) {
|
||||
$v = new Validate();
|
||||
$v->rule($validate);
|
||||
} else {
|
||||
if (strpos($validate, '.')) {
|
||||
// 支持场景
|
||||
[$validate, $scene] = explode('.', $validate);
|
||||
}
|
||||
$class = false !== strpos($validate, '\\') ? $validate : $this->app->parseClass('validate', $validate);
|
||||
$v = new $class();
|
||||
if (!empty($scene)) {
|
||||
$v->scene($scene);
|
||||
}
|
||||
}
|
||||
|
||||
$v->message($message);
|
||||
|
||||
// 是否批量验证
|
||||
if ($batch || $this->batchValidate) {
|
||||
$v->batch(true);
|
||||
}
|
||||
|
||||
return $v->failException(true)->check($data);
|
||||
}
|
||||
|
||||
}
|
||||
@ -0,0 +1,58 @@
|
||||
<?php
|
||||
namespace app;
|
||||
|
||||
use think\db\exception\DataNotFoundException;
|
||||
use think\db\exception\ModelNotFoundException;
|
||||
use think\exception\Handle;
|
||||
use think\exception\HttpException;
|
||||
use think\exception\HttpResponseException;
|
||||
use think\exception\ValidateException;
|
||||
use think\Response;
|
||||
use Throwable;
|
||||
|
||||
/**
|
||||
* 应用异常处理类
|
||||
*/
|
||||
class ExceptionHandle extends Handle
|
||||
{
|
||||
/**
|
||||
* 不需要记录信息(日志)的异常类列表
|
||||
* @var array
|
||||
*/
|
||||
protected $ignoreReport = [
|
||||
HttpException::class,
|
||||
HttpResponseException::class,
|
||||
ModelNotFoundException::class,
|
||||
DataNotFoundException::class,
|
||||
ValidateException::class,
|
||||
];
|
||||
|
||||
/**
|
||||
* 记录异常信息(包括日志或者其它方式记录)
|
||||
*
|
||||
* @access public
|
||||
* @param Throwable $exception
|
||||
* @return void
|
||||
*/
|
||||
public function report(Throwable $exception): void
|
||||
{
|
||||
// 使用内置的方式记录异常日志
|
||||
parent::report($exception);
|
||||
}
|
||||
|
||||
/**
|
||||
* Render an exception into an HTTP response.
|
||||
*
|
||||
* @access public
|
||||
* @param \think\Request $request
|
||||
* @param Throwable $e
|
||||
* @return Response
|
||||
*/
|
||||
public function render($request, Throwable $e): Response
|
||||
{
|
||||
// 添加自定义异常处理机制
|
||||
|
||||
// 其他错误交给系统处理
|
||||
return parent::render($request, $e);
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,8 @@
|
||||
<?php
|
||||
namespace app;
|
||||
|
||||
// 应用请求对象类
|
||||
class Request extends \think\Request
|
||||
{
|
||||
|
||||
}
|
||||
@ -0,0 +1,167 @@
|
||||
<?php
|
||||
namespace app\adminapi\controller\v1;
|
||||
|
||||
use app\adminapi\ApiController;
|
||||
use think\facade\Db;
|
||||
|
||||
class Admin extends ApiController
|
||||
{
|
||||
public function getAdminUsers()
|
||||
{
|
||||
if(!input('search')){
|
||||
$result=Db::name('admin')
|
||||
->page(input('current'),input('size'))
|
||||
->select();
|
||||
|
||||
$total=Db::name('admin')
|
||||
->count();
|
||||
}else{
|
||||
$result=Db::name('admin')
|
||||
->where('username','like','%'.input('search').'%')
|
||||
->page(input('current'),input('size'))
|
||||
->select();
|
||||
|
||||
$total=Db::name('admin')
|
||||
->where('username','like','%'.input('search').'%')
|
||||
->count();
|
||||
}
|
||||
|
||||
if(!$result){
|
||||
$result=[];
|
||||
}
|
||||
|
||||
$rtn=[
|
||||
'total' => $total,
|
||||
'data' => $result
|
||||
];
|
||||
|
||||
return $this->Success($rtn);
|
||||
}
|
||||
|
||||
public function getUser(){
|
||||
|
||||
$id=input('id');
|
||||
|
||||
$result=Db::name('admin')
|
||||
->field('id,username,email,status,role_id as role')
|
||||
->where('id',$id)
|
||||
->find();
|
||||
|
||||
if(!$result){
|
||||
$result=[];
|
||||
}
|
||||
|
||||
return $this->success($result);
|
||||
}
|
||||
|
||||
public function addUser(){
|
||||
|
||||
$req=input();
|
||||
|
||||
$password_hash = password_hash($req['password'], PASSWORD_DEFAULT);
|
||||
|
||||
$data=[
|
||||
'username' => $req['username'],
|
||||
'password' => $password_hash,
|
||||
'email' => $req['email'],
|
||||
'action_list' => '',
|
||||
'status' => $req['status'],
|
||||
];
|
||||
|
||||
$result=Db::name('admin')
|
||||
->insert($data);
|
||||
|
||||
if(!$result){
|
||||
$result=[];
|
||||
}
|
||||
|
||||
return $this->success($result);
|
||||
}
|
||||
|
||||
public function updateUser(){
|
||||
|
||||
$req=input();
|
||||
$data=[
|
||||
'username' => $req['username'],
|
||||
'email' => $req['email'],
|
||||
'role_id' => $req['role'],
|
||||
'action_list' => '',
|
||||
'status' => $req['status'],
|
||||
];
|
||||
|
||||
if(strlen($req['password'])>0){
|
||||
$data['password']=$req['password'];
|
||||
}
|
||||
|
||||
$result=Db::name('admin')
|
||||
->where('id',$req['id'])
|
||||
->update($data);
|
||||
|
||||
if(!$result){
|
||||
$result=[];
|
||||
}
|
||||
|
||||
return $this->success($result);
|
||||
}
|
||||
|
||||
public function deleteUser(){
|
||||
$id=input('id');
|
||||
|
||||
$result=Db::name('admin')
|
||||
->where('id',$id)
|
||||
->delete();
|
||||
|
||||
return $this->success($result);
|
||||
}
|
||||
|
||||
public function updateStatus(){
|
||||
$id=input('id');
|
||||
$status=input('status');
|
||||
|
||||
$result=Db::name('admin')
|
||||
->where('id',$id)
|
||||
->update(['status'=>$status]);
|
||||
|
||||
if(!$result){
|
||||
$result=[];
|
||||
}
|
||||
|
||||
return $this->success($result);
|
||||
}
|
||||
|
||||
|
||||
public function getAdminLogs()
|
||||
{
|
||||
if(!input('search')){
|
||||
$result=Db::name('admin_log')
|
||||
->page(input('current'),input('size'))
|
||||
->order('id','desc')
|
||||
->select();
|
||||
|
||||
$total=Db::name('admin_log')
|
||||
->count();
|
||||
}else{
|
||||
$result=Db::name('admin_log')
|
||||
->where('admin_name','like','%'.input('search').'%')
|
||||
->page(input('current'),input('size'))
|
||||
->order('id','desc')
|
||||
->select();
|
||||
|
||||
$total=Db::name('admin_log')
|
||||
->where('admin_name','like','%'.input('search').'%')
|
||||
->count();
|
||||
}
|
||||
|
||||
if(!$result){
|
||||
$result=[];
|
||||
}
|
||||
|
||||
$rtn=[
|
||||
'total' => $total,
|
||||
'data' => $result
|
||||
];
|
||||
|
||||
return $this->Success($rtn);
|
||||
}
|
||||
|
||||
}
|
||||
@ -0,0 +1,153 @@
|
||||
<?php
|
||||
namespace app\adminapi\controller\v1;
|
||||
|
||||
use app\adminapi\ApiController;
|
||||
use think\facade\Db;
|
||||
use think\facade\Session;
|
||||
use thans\jwt\facade\JWTAuth;
|
||||
use think\facade\Log;
|
||||
|
||||
class Auth extends ApiController
|
||||
{
|
||||
public function Login()
|
||||
{
|
||||
$username=input('username');
|
||||
$password=input('password');
|
||||
|
||||
// $captcha=input('captcha');
|
||||
|
||||
// Log::write(json_encode(Session::all()));
|
||||
|
||||
// if(!captcha_check($captcha)){
|
||||
// return $this->Error('驗證碼錯誤','請求失敗',301);
|
||||
// }
|
||||
$result=Db::name('admin')
|
||||
->where('username',$username)
|
||||
->find();
|
||||
|
||||
if(!$result){
|
||||
return $this->Error('帳號或密碼錯誤','請求失敗',302);
|
||||
}
|
||||
|
||||
if(!password_verify($password , $result['password'])){
|
||||
return $this->Error('帳號或密碼錯誤','請求失敗',303);
|
||||
}
|
||||
|
||||
$token = JWTAuth::builder(['uid' => $result['id']]);
|
||||
|
||||
$result=[
|
||||
'user'=>[
|
||||
'uid'=>$result['id'],
|
||||
"name" => $result['username'],
|
||||
"avatar" => "https://gw.alipayobjects.com/zos/rmsportal/ubnKSIfAJTxIgXOKlciN.png",
|
||||
"address" => "固原市",
|
||||
"position" => [
|
||||
"CN" => "產品分析師 | 螞蟻金服-計算服務事業群-IOS平臺部",
|
||||
"TW" => "產品分析師 | 螞蟻金服-計算服務事業群-IOS平臺部",
|
||||
"US" => "Product analyst | Ant Financial - Computing services business group - IOS platform division"
|
||||
]
|
||||
],
|
||||
'permissions'=>[
|
||||
[
|
||||
'id'=>'queryForm',
|
||||
'operation'=>['add','edit','delete']
|
||||
]
|
||||
],
|
||||
'roles'=>[
|
||||
[
|
||||
'id'=>'admin',
|
||||
'operation'=>['add','edit','delete']
|
||||
]
|
||||
],
|
||||
'token'=>$token,
|
||||
'expireAt'=>time()+30*60*1000
|
||||
];
|
||||
return $this->Success($result);
|
||||
|
||||
}
|
||||
|
||||
public function check(){
|
||||
print_r(JWTAuth::auth());
|
||||
}
|
||||
|
||||
public function captcha($id=''){
|
||||
return captcha($id);
|
||||
}
|
||||
|
||||
public function checkC($value){
|
||||
print_r(Session::all());
|
||||
|
||||
if(!captcha_check($value)){
|
||||
//驗證失敗
|
||||
echo 'failure';
|
||||
};
|
||||
echo 'Success';
|
||||
}
|
||||
|
||||
public function getRoute(){
|
||||
$routes=[
|
||||
[
|
||||
"router" => "root",
|
||||
"children" => [
|
||||
"DashBoard",
|
||||
[
|
||||
"router" => "system",
|
||||
"children" => [
|
||||
[
|
||||
"router" => "systemConfig",
|
||||
"name" => "站台設置",
|
||||
"authority" => [
|
||||
"permission" => "demo",
|
||||
"role" => "admin"
|
||||
]
|
||||
]
|
||||
]
|
||||
],
|
||||
[
|
||||
"router" => "admin",
|
||||
"children" => [
|
||||
"adminUser",
|
||||
"adminLog",
|
||||
"adminRole",
|
||||
]
|
||||
],
|
||||
[
|
||||
"router" => "goods",
|
||||
"children" => [
|
||||
"goodsList",
|
||||
"goodsCategory",
|
||||
"goodsType",
|
||||
]
|
||||
],
|
||||
[
|
||||
"router" => "order",
|
||||
"children" => [
|
||||
"orderList",
|
||||
]
|
||||
],
|
||||
[
|
||||
"router" => "room",
|
||||
"children" => [
|
||||
"roomList",
|
||||
]
|
||||
],
|
||||
[
|
||||
"router" => "user",
|
||||
"children" => [
|
||||
"userList"
|
||||
]
|
||||
],
|
||||
[
|
||||
"router" => "setting",
|
||||
"children" => [
|
||||
"settingBase",
|
||||
"settingConfig"
|
||||
]
|
||||
]
|
||||
]
|
||||
]
|
||||
];
|
||||
|
||||
return $this->Success($routes);
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,187 @@
|
||||
<?php
|
||||
namespace app\adminapi\controller\v1;
|
||||
|
||||
use app\adminapi\ApiController;
|
||||
use think\facade\Db;
|
||||
|
||||
use app\common\lib\Vcard;
|
||||
use app\common\lib\Aes;
|
||||
|
||||
class Card extends ApiController
|
||||
{
|
||||
public function addPrecard(){
|
||||
$req=input();
|
||||
//取得prefix
|
||||
$agent = Db::name('agent')
|
||||
->where('id',$req['agent_id'])
|
||||
->find();
|
||||
|
||||
$aes = new Aes([]);
|
||||
|
||||
for($i=0;$i<input('number');$i++){
|
||||
|
||||
// $user_id=genUniqid($agent['prefix']);
|
||||
// $verify_code = genSerialNo();
|
||||
|
||||
// $params = urlencode($aes->encrypt('user_id='.$user_id.'&verify_code='.$verify_code));
|
||||
// $nfcUrl = genQrCode(getUrl().'/card/?params='.$params,$user_id,'nfc');
|
||||
|
||||
$data[]=[
|
||||
// 'user_id'=>$user_id,
|
||||
'agent_id'=>$req['agent_id'],
|
||||
'try_days'=>7,
|
||||
'verify_code'=>'',
|
||||
'expire_time'=>$req['expire_time'],
|
||||
'status'=>0,
|
||||
];
|
||||
|
||||
}
|
||||
|
||||
try{
|
||||
Db::name('precard')
|
||||
->insertAll($data);
|
||||
}catch(\Exception $e){
|
||||
print_r($e);
|
||||
return $this->error('新增失敗');
|
||||
}
|
||||
|
||||
return $this->success('新增成功');
|
||||
}
|
||||
|
||||
// 取得預開卡資料
|
||||
public function getPrecard(){
|
||||
$do=Db::name('precard');
|
||||
|
||||
if(!input('search')){
|
||||
$result=$do
|
||||
->page(input('current'),input('size'))
|
||||
->order('id','desc')
|
||||
->select()->toArray();
|
||||
|
||||
$total=$do
|
||||
->count();
|
||||
}else{
|
||||
$result=$do
|
||||
->where('user_id','like','%'.input('search').'%')
|
||||
->page(input('current'),input('size'))
|
||||
->order('id','desc')
|
||||
->select()->toArray();
|
||||
|
||||
$total=$do
|
||||
->where('user_id','like','%'.input('search').'%')
|
||||
->count();
|
||||
}
|
||||
|
||||
if(!$result){
|
||||
$result=[];
|
||||
}
|
||||
|
||||
foreach($result as $key => $val){
|
||||
// $aes = new Aes([]);
|
||||
// $nfc_url = 'user_id='.$val['user_id'].'&verify_code='.$val['verify_code'];
|
||||
// $result[$key]['params'] = getUrl().'/card/'.urlencode($aes->encrypt($nfc_url));
|
||||
$result[$key]['agent_name'] = Db::name('agent')->where('id',$val['agent_id'])->value('name');
|
||||
$result[$key]['expire'] = date('Y-m-d',$val['expire_time']);
|
||||
switch($val['status']){
|
||||
case 0:
|
||||
$result[$key]['status_name']='未制卡';
|
||||
break;
|
||||
case 1:
|
||||
$result[$key]['status_name']='已制卡';
|
||||
break;
|
||||
case 2:
|
||||
$result[$key]['status_name']='已開通';
|
||||
break;
|
||||
case 3:
|
||||
$result[$key]['status_name']='已作癈';
|
||||
break;
|
||||
}
|
||||
|
||||
$aes = new Aes([]);
|
||||
$params = urlencode($aes->encrypt('verify_code='.$val['verify_code']));
|
||||
$result[$key]['nfcurl']= getUrl().'/card/?params='.$params;
|
||||
// $nfcUrl = genQrCode('https://'.$_SERVER['HTTP_HOST'].'/card/?params='.$params,$data['user_id'],'nfc');
|
||||
}
|
||||
|
||||
$rtn=[
|
||||
'total' => $total,
|
||||
'data' => $result
|
||||
];
|
||||
|
||||
return $this->Success($rtn);
|
||||
|
||||
}
|
||||
|
||||
public function deleteCard(){
|
||||
$id=input('id');
|
||||
|
||||
$result=Db::name('precard')
|
||||
->where('id',$id)
|
||||
->delete();
|
||||
|
||||
return $this->success($result);
|
||||
}
|
||||
|
||||
public function updateStatus(){
|
||||
$id=input('id');
|
||||
$status=input('status');
|
||||
|
||||
$result=Db::name('precard')
|
||||
->where('id',$id)
|
||||
->update(['status'=>$status]);
|
||||
|
||||
if(!$result){
|
||||
$result=[];
|
||||
}
|
||||
|
||||
return $this->success($result);
|
||||
}
|
||||
|
||||
public function updateVerifyCode(){
|
||||
$id=input('id');
|
||||
$verify_code=strtoupper(input('code'));
|
||||
|
||||
$is_user = Db::name('user')
|
||||
->where('uniqid',$verify_code)
|
||||
->count();
|
||||
|
||||
if($is_user){
|
||||
return $this->error('卡片已綁定會員');
|
||||
}
|
||||
|
||||
$is_precard = Db::name('precard')
|
||||
->where('verify_code',$verify_code)
|
||||
->count();
|
||||
|
||||
if($is_precard){
|
||||
return $this->error('已存在預製卡');
|
||||
}
|
||||
|
||||
try{
|
||||
$result=Db::name('precard')
|
||||
->where('id',$id)
|
||||
->update(['verify_code'=>$verify_code,'status'=>1]);
|
||||
|
||||
return $this->success('設定成功');
|
||||
}catch(\Exception $e){
|
||||
return $this->error('系統錯誤');
|
||||
}
|
||||
}
|
||||
|
||||
public function downloadQr(){
|
||||
$id=input('id');
|
||||
|
||||
$pc=Db::name('precard')
|
||||
->where('id',$id)
|
||||
->find();
|
||||
|
||||
if(strlen($pc['nfc_qrcode'])>0){
|
||||
$nfc_qrcode = $pc['nfc_qrcode'];
|
||||
}else{
|
||||
|
||||
}
|
||||
|
||||
return $this->success($result);
|
||||
}
|
||||
|
||||
}
|
||||
@ -0,0 +1,18 @@
|
||||
<?php
|
||||
namespace app\adminapi\controller\v1;
|
||||
|
||||
use app\BaseController;
|
||||
|
||||
use app\common\lib\Vcard;
|
||||
|
||||
class Index extends BaseController
|
||||
{
|
||||
public function index()
|
||||
{
|
||||
return 'Admin Index';
|
||||
}
|
||||
|
||||
public function test(){
|
||||
Vcard::genVcf('mc638ac4d74c7e6');
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,87 @@
|
||||
<?php
|
||||
namespace app\admin\controller\v1;
|
||||
|
||||
use app\api\ApiController;
|
||||
use think\facade\Db;
|
||||
|
||||
class Right extends ApiController
|
||||
{
|
||||
public function getTree()
|
||||
{
|
||||
|
||||
$data=[
|
||||
'title'=>'所有權限',
|
||||
'key'=>'all',
|
||||
'level'=>0,
|
||||
'index'=>0
|
||||
];
|
||||
|
||||
$data=$this->buildTree($data);
|
||||
|
||||
|
||||
if(!$data){
|
||||
$result=[];
|
||||
}
|
||||
|
||||
// $result['children']=$children;
|
||||
|
||||
|
||||
$rtn=[
|
||||
// 'total' => $total,
|
||||
$data
|
||||
];
|
||||
|
||||
return $this->Success($rtn);
|
||||
}
|
||||
|
||||
private static function buildTree($data,$level=0){
|
||||
$level=$level+1;
|
||||
$menu = Db::name('menu')
|
||||
->where('pid',$data['index'])
|
||||
->select();
|
||||
|
||||
if(!$menu){
|
||||
return $data;
|
||||
}
|
||||
|
||||
$children=[];
|
||||
|
||||
foreach($menu as $key => $val){
|
||||
$children[$key]['title']=$val['title'];
|
||||
$children[$key]['index']=$val['id'];
|
||||
$children[$key]['level']=$level;
|
||||
$children[$key]['key']=$val['node'];
|
||||
if($level < 2){
|
||||
$children[$key]=self::buildTree($children[$key],$level);
|
||||
}else{
|
||||
$children[$key]=self::appendPermission($children[$key]);
|
||||
}
|
||||
}
|
||||
if($children){
|
||||
$data['children'] = $children;
|
||||
}
|
||||
return $data;
|
||||
}
|
||||
|
||||
private static function appendPermission($data){
|
||||
$perm = Db::name('permission')
|
||||
->where('menu_id',$data['index'])
|
||||
->select();
|
||||
|
||||
if(!$perm){
|
||||
return $data;
|
||||
}
|
||||
|
||||
$children=[];
|
||||
|
||||
foreach($perm as $key => $val){
|
||||
$children[$key]['title']=lang($val['code']);
|
||||
$children[$key]['index']=$val['id'];
|
||||
$children[$key]['key']=$val['code'];
|
||||
}
|
||||
if($children){
|
||||
$data['children'] = $children;
|
||||
}
|
||||
return $data;
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,86 @@
|
||||
<?php
|
||||
namespace app\adminapi\controller\v1;
|
||||
|
||||
use app\adminapi\ApiController;
|
||||
use think\facade\Db;
|
||||
|
||||
class Role extends ApiController
|
||||
{
|
||||
public function getRoles()
|
||||
{
|
||||
$result=Db::name('role')
|
||||
->select();
|
||||
|
||||
if(!$result){
|
||||
$result=[];
|
||||
}
|
||||
// foreach($result as $key=>$val){
|
||||
// // $rtn=Db::name('goods')->where('gc_id',$val['id'])->select()->toArray();
|
||||
// // if($rtn){
|
||||
// // $result[$key]['goods']=[];
|
||||
// // }
|
||||
// $result[$key]['goods']=Db::name('goods')->where('gc_id',$val['id'])->select()->toArray();
|
||||
// }
|
||||
return $this->Success($result);
|
||||
}
|
||||
|
||||
public function getRoleById(){
|
||||
$id=input('id');
|
||||
|
||||
$result=Db::name('role')
|
||||
->where('id',$id)
|
||||
->find();
|
||||
|
||||
$rtn=[
|
||||
'id' => $result['id'],
|
||||
'name' => $result['name'],
|
||||
'desc' => $result['desc'],
|
||||
'permission'=>json_decode($result['limits'])
|
||||
];
|
||||
|
||||
return $this->Success($rtn);
|
||||
}
|
||||
|
||||
public function addRole(){
|
||||
$req=input();
|
||||
|
||||
$data = [
|
||||
'name'=>$req['name'],
|
||||
'desc'=>$req['desc'],
|
||||
'limits'=>json_encode($req['permission'])
|
||||
];
|
||||
|
||||
$result=Db::name('role')
|
||||
->insert($data);
|
||||
|
||||
return $this->Success($result);
|
||||
}
|
||||
|
||||
public function updateRole(){
|
||||
$req=input();
|
||||
|
||||
$data = [
|
||||
'name' =>$req['name'],
|
||||
'desc' =>$req['desc'],
|
||||
'limits' =>json_encode($req['permission'])
|
||||
];
|
||||
|
||||
$result=Db::name('role')
|
||||
->where('id',$req['id'])
|
||||
->update($data);
|
||||
|
||||
return $this->Success($result);
|
||||
}
|
||||
|
||||
public function deleteRole(){
|
||||
$id=input('id');
|
||||
|
||||
|
||||
$result=Db::name('role')
|
||||
->where('id',$id)
|
||||
->delete();
|
||||
|
||||
return $this->Success($result);
|
||||
}
|
||||
|
||||
}
|
||||
@ -0,0 +1,45 @@
|
||||
<?php
|
||||
namespace app\adminapi\controller\v1;
|
||||
|
||||
use app\adminapi\ApiController;
|
||||
use think\facade\Db;
|
||||
|
||||
class Site extends ApiController
|
||||
{
|
||||
public function getSiteConfig(){
|
||||
$result = Db::name('site_config')
|
||||
->where('parent_id','<>',0)
|
||||
->select();
|
||||
|
||||
foreach($result as $key => $val){
|
||||
$rtn[$val['code']]=$val['value'];
|
||||
}
|
||||
|
||||
return $this->success($rtn);
|
||||
}
|
||||
|
||||
public function setSiteConfig(){
|
||||
$data = input();
|
||||
unset($data['version']);
|
||||
unset($data['controller']);
|
||||
unset($data['action']);
|
||||
try{
|
||||
foreach($data as $key => $val){
|
||||
Db::name('site_config')
|
||||
->where('code',$key)
|
||||
->update(['value'=>$val]);
|
||||
}
|
||||
}catch(\Exception $e){
|
||||
return $this->error('更新失敗');
|
||||
}
|
||||
|
||||
return $this->success('更新成功');
|
||||
}
|
||||
|
||||
public function getAgents(){
|
||||
$result = Db::name('agent')
|
||||
->select();
|
||||
|
||||
return $this->success($result);
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,305 @@
|
||||
<?php
|
||||
namespace app\adminapi\controller\v1;
|
||||
|
||||
use app\adminapi\ApiController;
|
||||
use think\facade\Db;
|
||||
|
||||
use app\common\lib\Vcard;
|
||||
use app\common\lib\Aes;
|
||||
|
||||
class User extends ApiController
|
||||
{
|
||||
public function getInfo()
|
||||
{
|
||||
$id=$this->request->uid;
|
||||
$result=Db::name('user')
|
||||
->where('id',$id)
|
||||
->find();
|
||||
|
||||
if(!$result){
|
||||
$result=[];
|
||||
}
|
||||
// foreach($result as $key=>$val){
|
||||
// // $rtn=Db::name('goods')->where('gc_id',$val['id'])->select()->toArray();
|
||||
// // if($rtn){
|
||||
// // $result[$key]['goods']=[];
|
||||
// // }
|
||||
// $result[$key]['goods']=Db::name('goods')->where('gc_id',$val['id'])->select()->toArray();
|
||||
// }
|
||||
return $this->Success($result);
|
||||
}
|
||||
|
||||
// 取得會員資料
|
||||
public function getUsers(){
|
||||
$do=Db::name('user');
|
||||
|
||||
if(!input('search')){
|
||||
$result=$do
|
||||
->page(input('current'),input('size'))
|
||||
->order('id','desc')
|
||||
->select()->toArray();
|
||||
|
||||
$total=$do
|
||||
->count();
|
||||
}else{
|
||||
$result=$do
|
||||
->where('user_id','like','%'.input('search').'%')
|
||||
->page(input('current'),input('size'))
|
||||
->order('id','desc')
|
||||
->select()->toArray();
|
||||
|
||||
$total=$do
|
||||
->where('user_id','like','%'.input('search').'%')
|
||||
->count();
|
||||
}
|
||||
|
||||
if(!$result){
|
||||
$result=[];
|
||||
}
|
||||
|
||||
$aes = new Aes([]);
|
||||
|
||||
foreach($result as $key => $val){
|
||||
$result[$key]['level_name']= Db::name('user_level')->where('level_id',$val['level'])->where('agent_id',$val['agent_id'])->value('name');
|
||||
|
||||
if($val['parent_id']>0){
|
||||
$result[$key]['parent_name']=Db::name('user')->where('id',$val['parent_id'])->value('real_name');
|
||||
}
|
||||
if($val['overdue_time']>0){
|
||||
$result[$key]['overdue'] = date('Y-m-d',$val['overdue_time']);
|
||||
}else{
|
||||
$result[$key]['overdue'] = '無限期';
|
||||
}
|
||||
if(strlen($val['uniqid'])>0){
|
||||
$uniqid = $val['uniqid'];
|
||||
}else{
|
||||
$uniqid = '00000000';
|
||||
}
|
||||
$params = urlencode($aes->encrypt('user_id='.$val['user_id'].'&verify_code='.$uniqid));
|
||||
$result[$key]['nfcurl']= getUrl().'/card/?params='.$params;
|
||||
}
|
||||
|
||||
$rtn=[
|
||||
'total' => $total,
|
||||
'data' => $result
|
||||
];
|
||||
|
||||
return $this->Success($rtn);
|
||||
|
||||
}
|
||||
|
||||
public function getUser(){
|
||||
|
||||
$id=input('id');
|
||||
|
||||
$result=Db::name('user')
|
||||
->where('id',$id)
|
||||
->find();
|
||||
|
||||
|
||||
|
||||
if(!$result){
|
||||
$result=[];
|
||||
}
|
||||
|
||||
$levels=Db::name('user_level')
|
||||
->where('agent_id',$result['agent_id'])
|
||||
->select();
|
||||
|
||||
$result['levels']=$levels;
|
||||
|
||||
|
||||
return $this->success($result);
|
||||
}
|
||||
|
||||
public function addUser(){
|
||||
|
||||
$req=input();
|
||||
unset($req['version']);
|
||||
unset($req['controller']);
|
||||
unset($req['action']);
|
||||
$req['user_id'] = 'mc'.uniqid();
|
||||
$req['line_id'] = $req['user_id'];
|
||||
$req['create_time']=date('Y-m-d H:i:s');
|
||||
$req['update_time']=date('Y-m-d H:i:s');
|
||||
|
||||
$result=Db::name('user')
|
||||
->insert($req);
|
||||
|
||||
if(!$result){
|
||||
$result=[];
|
||||
}
|
||||
|
||||
return $this->success($result);
|
||||
}
|
||||
|
||||
public function updateUser(){
|
||||
|
||||
$req=input();
|
||||
unset($req['version']);
|
||||
unset($req['controller']);
|
||||
unset($req['action']);
|
||||
unset($req['levels']);
|
||||
unset($req['status']);
|
||||
|
||||
$level_option = Db::name('user_level')
|
||||
->where('agent_id',$req['agent_id'])
|
||||
->where('level_id',$req['level'])
|
||||
->find();
|
||||
|
||||
$req['nc_type']=$level_option['nc_type'];
|
||||
$req['nc_func']=$level_option['nc_func'];
|
||||
|
||||
$req['update_time']=date('Y-m-d H:i:s');
|
||||
|
||||
$result=Db::name('user')
|
||||
->where('id',$req['id'])
|
||||
->update($req);
|
||||
|
||||
Vcard::genVcf(input('user_id'));
|
||||
|
||||
if(!$result){
|
||||
$result=[];
|
||||
}
|
||||
|
||||
return $this->success($result);
|
||||
}
|
||||
|
||||
public function deleteUser(){
|
||||
$id=input('id');
|
||||
|
||||
$result=Db::name('user')
|
||||
->where('id',$id)
|
||||
->delete();
|
||||
|
||||
return $this->success($result);
|
||||
}
|
||||
|
||||
public function updateStatus(){
|
||||
$id=input('id');
|
||||
$status=input('status');
|
||||
|
||||
$result=Db::name('user')
|
||||
->where('id',$id)
|
||||
->update(['status'=>$status]);
|
||||
|
||||
if(!$result){
|
||||
$result=[];
|
||||
}
|
||||
|
||||
return $this->success($result);
|
||||
}
|
||||
|
||||
public function getUserCard(){
|
||||
|
||||
$id=input('id');
|
||||
|
||||
$result=Db::name('user_card')
|
||||
->field('id,type,title,content,nfc_show,sort_id')
|
||||
->where('user_id',$id)
|
||||
->order('sort_id')
|
||||
->select();
|
||||
|
||||
|
||||
if(!$result){
|
||||
$result=[];
|
||||
}
|
||||
|
||||
return $this->success($result);
|
||||
}
|
||||
|
||||
public function uploadAvatar(){
|
||||
$files = request()->file('avatar');
|
||||
$savename = \think\facade\Filesystem::disk('public')->putFile( input('id'), $files);
|
||||
|
||||
$avatar = getUrl().'/storage/'.$savename;
|
||||
|
||||
return $this->Success($avatar);
|
||||
}
|
||||
|
||||
public function updateUserCard(){
|
||||
$user_id=input('id');
|
||||
$cards=input('cards');
|
||||
|
||||
Db::name('user_card')
|
||||
->where('user_id',$user_id)
|
||||
->delete();
|
||||
|
||||
foreach($cards as $key => $val){
|
||||
$nfc_show = $val['nfc_show']?1:0;
|
||||
|
||||
Db::name('user_card')
|
||||
->insert([
|
||||
'user_id' => $user_id,
|
||||
'type' => $val['type'],
|
||||
'title' => $val['title'],
|
||||
'content' => $val['content'],
|
||||
'nfc_show' => $nfc_show,
|
||||
'sort_id' => $key,
|
||||
'create_time' => time()
|
||||
]);
|
||||
}
|
||||
|
||||
// if(!$result){
|
||||
// $result=[];
|
||||
// }
|
||||
|
||||
return $this->success(['code'=>200]);
|
||||
}
|
||||
|
||||
public function updateVerifyCode(){
|
||||
$id=input('id');
|
||||
$uniqid=strtoupper(input('code'));
|
||||
|
||||
$result=Db::name('user')
|
||||
->where('id',$id)
|
||||
->update(['uniqid'=>$uniqid]);
|
||||
|
||||
return $this->success('設定成功');
|
||||
}
|
||||
|
||||
// 取得預開卡資料
|
||||
public function getPrecard(){
|
||||
$do=Db::name('precard');
|
||||
|
||||
if(!input('search')){
|
||||
$result=$do
|
||||
->page(input('current'),input('size'))
|
||||
->order('id','desc')
|
||||
->select()->toArray();
|
||||
|
||||
$total=$do
|
||||
->count();
|
||||
}else{
|
||||
$result=$do
|
||||
->where('user_id','like','%'.input('search').'%')
|
||||
->page(input('current'),input('size'))
|
||||
->order('id','desc')
|
||||
->select()->toArray();
|
||||
|
||||
$total=$do
|
||||
->where('user_id','like','%'.input('search').'%')
|
||||
->count();
|
||||
}
|
||||
|
||||
if(!$result){
|
||||
$result=[];
|
||||
}
|
||||
|
||||
foreach($result as $key => $val){
|
||||
$aes = new Aes([]);
|
||||
$nfc_url = 'user_id='.$val['user_id'].'&verify_code='.$val['verify_code'];
|
||||
$result[$key]['params'] = getUrl().'/card/'.urlencode($aes->encrypt($nfc_url));
|
||||
}
|
||||
|
||||
$rtn=[
|
||||
'total' => $total,
|
||||
'data' => $result
|
||||
];
|
||||
|
||||
return $this->Success($rtn);
|
||||
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
@ -0,0 +1,6 @@
|
||||
<?php
|
||||
return [
|
||||
\think\middleware\SessionInit::class,
|
||||
\think\middleware\AllowCrossDomain::class,
|
||||
// app\api\middleware\CheckSiteCode::class
|
||||
];
|
||||
@ -0,0 +1,9 @@
|
||||
<?php
|
||||
use think\facade\Route;
|
||||
|
||||
|
||||
// Route::group(function () {
|
||||
// Route::rule(':version/user/:action', 'api/:version.user/:action');
|
||||
// })->middleware(\app\api\middleware\JWT::class);
|
||||
|
||||
Route::rule(':version/:controller/:action','adminapi/:version.:controller/:action');
|
||||
@ -0,0 +1,12 @@
|
||||
<?php
|
||||
// api公用函數
|
||||
use think\facade\Db;
|
||||
|
||||
|
||||
function getPrefixByAppId($appid){
|
||||
return 'tg';
|
||||
}
|
||||
|
||||
function checkParams(){
|
||||
print_r('aaaaa');
|
||||
}
|
||||
@ -0,0 +1,194 @@
|
||||
<?php
|
||||
|
||||
namespace app\api\controller\v1;
|
||||
|
||||
use app\api\ApiController;
|
||||
use think\facade\Db;
|
||||
|
||||
// use app\api\validate\User as UserValidate;
|
||||
// use think\exception\ValidateException;
|
||||
use app\common\lib\Token;
|
||||
|
||||
class User extends ApiController
|
||||
{
|
||||
public function getInfo()
|
||||
{
|
||||
try {
|
||||
$user = Db::name('user')
|
||||
->field('user_id,avatar,line_id,line_name,line_picture,phone,real_name,email, code,parent_id')
|
||||
->where('user_id', input('user_id'))
|
||||
// ->whereNotNull('delete_time')
|
||||
->find();
|
||||
|
||||
return $this->success($user);
|
||||
} catch (\Exception $e) {
|
||||
return $this->error('操作失敗');
|
||||
}
|
||||
}
|
||||
|
||||
public function getUsers()
|
||||
{
|
||||
try {
|
||||
$users = Db::name('user')
|
||||
->field('user_id,avatar,line_id,line_name,line_picture,phone,real_name,code')
|
||||
->whereNotNull('delete_time')
|
||||
->select();
|
||||
|
||||
return $this->success($users);
|
||||
} catch (\Exception $e) {
|
||||
return $this->error('操作失敗');
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public function add()
|
||||
{
|
||||
|
||||
$data = input();
|
||||
|
||||
unset($data['version']);
|
||||
unset($data['action']);
|
||||
unset($data['controller']);
|
||||
|
||||
|
||||
$user_id = genUniqid($data['appid']);
|
||||
|
||||
$data['user_id'] = $user_id;
|
||||
|
||||
$avatar = isset($data['line_picture']) ? $this->saveLineImage($data['line_picture'], $data['user_id']) : '';
|
||||
|
||||
if (!empty($avatar)) {
|
||||
$data['line_picture'] = getUrl() . '/storage/' . $data['user_id'] . '/' . $avatar;
|
||||
} else {
|
||||
$data['line_picture'] = '';
|
||||
}
|
||||
|
||||
if (!isset($data['avatar'])) {
|
||||
$data['avatar'] = $data['line_picture'];
|
||||
} else {
|
||||
$file_path = $_SERVER['DOCUMENT_ROOT'] . '/storage/' . $data['user_id'] . '/' . date('Ymd') . '/';
|
||||
if (!is_dir($file_path)) {
|
||||
mkdir($file_path, 0777, true);
|
||||
}
|
||||
$temp_file = str_replace(getUrl(), "", $data['avatar']);
|
||||
$avatar_file = $file_path . basename($temp_file);
|
||||
if (!rename($_SERVER['DOCUMENT_ROOT'] . $temp_file, $avatar_file)) {
|
||||
return $this->error('搬移檔案失敗');
|
||||
}
|
||||
$data['avatar'] = getUrl() . '/storage/' . $data['user_id'] . '/' . date('Ymd') . '/' . basename($temp_file);
|
||||
}
|
||||
|
||||
$phone_exist = Db::name('user')
|
||||
->where('phone', input('phone'))
|
||||
->find();
|
||||
|
||||
// 檢查會員電話是否存在
|
||||
if (!$phone_exist) {
|
||||
// 檢查推薦碼是否存在,存在的話取得推薦人的id
|
||||
if (input('refer_code')) {
|
||||
$refer_id = Db::name('user')
|
||||
->where('code', input('refer_code'))
|
||||
->value('user_id');
|
||||
|
||||
if ($refer_id) {
|
||||
$data['parent_id'] = $refer_id;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
unset($data['appid']);
|
||||
unset($data['timestamp']);
|
||||
unset($data['sign']);
|
||||
unset($data['refer_code']);
|
||||
|
||||
try {
|
||||
if ($phone_exist) {
|
||||
Db::name('user')
|
||||
->where('phone', input('phone'))
|
||||
->update($data);
|
||||
} else {
|
||||
$id = Db::name('user')
|
||||
->insertGetId($data);
|
||||
|
||||
$refer_code = encodeRefer($id);
|
||||
|
||||
Db::name('user')
|
||||
->where('id', $id)
|
||||
->update(['code' => $refer_code]);
|
||||
}
|
||||
|
||||
|
||||
|
||||
//使用id取得user資料庫的資料
|
||||
$result = Db::name('user')
|
||||
->where('phone', input('phone'))
|
||||
->find();
|
||||
|
||||
$payload = [
|
||||
'user_id' => $data['user_id'],
|
||||
];
|
||||
|
||||
$token = Token::genToken($payload);
|
||||
|
||||
return $this->success(['uid' => $data['user_id'], 'info' => $result, 'token' => 'Bearer ' . $token]);
|
||||
} catch (\Exception $e) {
|
||||
return $this->error($e->getMessage());
|
||||
}
|
||||
}
|
||||
|
||||
public function delete()
|
||||
{
|
||||
try {
|
||||
Db::name('user')
|
||||
->where('user_id', input('user_id'))
|
||||
->update([
|
||||
'delete_time' => time()
|
||||
]);
|
||||
return $this->success('操作成功');
|
||||
} catch (\Exception $e) {
|
||||
return $this->error('操作失敗');
|
||||
}
|
||||
}
|
||||
|
||||
public function update()
|
||||
{
|
||||
$data = input('post.');
|
||||
|
||||
unset($data['appid']);
|
||||
unset($data['timestamp']);
|
||||
unset($data['sign']);
|
||||
|
||||
try {
|
||||
Db::name('user')
|
||||
->where('user_id', $data['user_id'])
|
||||
->update($data);
|
||||
|
||||
return $this->success('操作成功');
|
||||
} catch (\Exception $e) {
|
||||
return $this->error('操作失敗');
|
||||
}
|
||||
}
|
||||
|
||||
private function saveLineImage($pictureUrl, $uid)
|
||||
{
|
||||
if ($pictureUrl) {
|
||||
$curl = curl_init($pictureUrl);
|
||||
curl_setopt($curl, CURLOPT_RETURNTRANSFER, 1);
|
||||
$imageData = curl_exec($curl);
|
||||
curl_close($curl);
|
||||
|
||||
$filename = $uid . "_line.jpg";
|
||||
$filedir = $_SERVER['DOCUMENT_ROOT'] . '/storage/' . $uid;
|
||||
if (!file_exists($filedir)) {
|
||||
mkdir($filedir, 0777, true);
|
||||
}
|
||||
$fp = fopen($filedir . '/' . $filename, 'a');
|
||||
fwrite($fp, $imageData);
|
||||
fclose($fp);
|
||||
|
||||
return $filename;
|
||||
} else {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,7 @@
|
||||
<?php
|
||||
return [
|
||||
// \think\middleware\SessionInit::class,
|
||||
// \think\middleware\AllowCrossDomain::class,
|
||||
// app\api\middleware\CheckParams::class
|
||||
// app\api\middleware\CheckSiteCode::class
|
||||
];
|
||||
@ -0,0 +1,41 @@
|
||||
<?php
|
||||
|
||||
declare (strict_types=1);
|
||||
|
||||
namespace app\api\middleware;
|
||||
|
||||
use think\exception\HttpException;
|
||||
|
||||
class CheckParams
|
||||
{
|
||||
public function handle($request, \Closure $next): object
|
||||
{
|
||||
|
||||
$params = $request->param();
|
||||
if(!isset($params['sign'])){
|
||||
return json(['code'=>401,'message'=>'API驗證失敗','data'=>'No Sign','time'=>time()]);
|
||||
}
|
||||
|
||||
$sign = $params['sign'];
|
||||
|
||||
unset($params['sign']);
|
||||
unset($params['controller']);
|
||||
unset($params['action']);
|
||||
unset($params['version']);
|
||||
ksort($params);
|
||||
|
||||
$string = md5(md5(strtolower(http_build_query($params))).'seckey');
|
||||
// print_r($string === $sign);
|
||||
// var_dump($sign);
|
||||
// var_dump($string);
|
||||
|
||||
if($string !== $sign){
|
||||
// throw new HttpException(401, 'Sign Error!!!');
|
||||
return json(['code'=>401,'message'=>'API驗證失敗','data'=>'Sign Error','time'=>time()]);
|
||||
}
|
||||
|
||||
$response = $next($request);
|
||||
|
||||
return $response;
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,14 @@
|
||||
<?php
|
||||
use think\facade\Route;
|
||||
|
||||
|
||||
Route::group(function () {
|
||||
Route::rule(':version/user/:action', 'api/:version.user/:action');
|
||||
})->middleware(\app\api\middleware\CheckParams::class);
|
||||
|
||||
Route::group(function(){
|
||||
Route::rule(':version/:controller/:action','api/:version.:controller/:action');
|
||||
})->allowCrossDomain([
|
||||
'Access-Control-Allow-Headers' => 'Origin, X-Requested-With, Content-Type, Accept, Authorization, SessionId, sessionid',
|
||||
'Access-Control-Expose-Headers' => 'Authorization, SessionId, sessionid'
|
||||
]);
|
||||
@ -0,0 +1,25 @@
|
||||
<?php
|
||||
namespace app\api\validate;
|
||||
|
||||
use think\Validate;
|
||||
|
||||
class User extends Validate
|
||||
{
|
||||
protected $rule = [
|
||||
'appid' => 'require',
|
||||
'user_id' => 'require|max:255',
|
||||
'name' => 'require|max:25',
|
||||
'level' => 'number|between:0,3',
|
||||
'overdue_time' => 'number'
|
||||
];
|
||||
|
||||
protected $message = [
|
||||
'appid.require' => 'appid 不可為空',
|
||||
'user_id.require' => 'User Id不可為空',
|
||||
'name.require' => 'Name不得為空',
|
||||
'name.max' => 'Name不得超過25個字',
|
||||
'level.number' => 'Level必需是數字',
|
||||
'level.between' => 'Level只能在0-3之間',
|
||||
'overdue_time.require' => 'overdue_time必需是數字',
|
||||
];
|
||||
}
|
||||
@ -0,0 +1,24 @@
|
||||
<?php
|
||||
namespace app\api\validate;
|
||||
|
||||
use think\Validate;
|
||||
|
||||
class UserLevel extends Validate
|
||||
{
|
||||
protected $rule = [
|
||||
'appid' => 'require',
|
||||
'user_id' => 'require|max:255',
|
||||
'level' => 'require|number|between:0,3',
|
||||
'overdue_time' => 'require|number'
|
||||
];
|
||||
|
||||
protected $message = [
|
||||
'appid.require' => 'appid 不可為空',
|
||||
'user_id.require' => 'User Id不可為空',
|
||||
'level.require' => 'Level不可為空',
|
||||
'level.number' => 'Level必需是數字',
|
||||
'level.between' => 'Level只能在0-3之間',
|
||||
'overdue_time.require' => 'overdue_time不可為空',
|
||||
'overdue_time.number' => 'overdue_time必需是數字',
|
||||
];
|
||||
}
|
||||
@ -0,0 +1,60 @@
|
||||
<?php
|
||||
declare (strict_types = 1);
|
||||
|
||||
namespace app\command;
|
||||
|
||||
use think\console\Command;
|
||||
use think\console\Input;
|
||||
use think\console\input\Argument;
|
||||
use think\console\input\Option;
|
||||
use think\console\Output;
|
||||
|
||||
use think\facade\Db;
|
||||
|
||||
class CheckExpire extends Command
|
||||
{
|
||||
protected function configure()
|
||||
{
|
||||
// 指令配置
|
||||
$this->setName('checkexpire')
|
||||
->setDescription('the checkexpire command');
|
||||
}
|
||||
|
||||
protected function execute(Input $input, Output $output)
|
||||
{
|
||||
// 取得代理資料
|
||||
$t_agents = Db::name('agent')->select();
|
||||
|
||||
foreach($t_agents as $val){
|
||||
$agents[$val['id']] = $val;
|
||||
}
|
||||
|
||||
// 取得過期用戶
|
||||
$e_users = Db::name('user')
|
||||
->where('status',1)
|
||||
->where('overdue_time','<',time())
|
||||
->select();
|
||||
|
||||
// 更新過期用戶
|
||||
foreach($e_users as $val){
|
||||
$data['level']=0;
|
||||
$data['status']=1;
|
||||
|
||||
$level_option = Db::name('user_level')
|
||||
->where('agent_id',$val['agent_id'])
|
||||
->where('level_id',$data['level'])
|
||||
->find();
|
||||
|
||||
$data['nc_type']=$level_option['nc_type'];
|
||||
$data['nc_func']=$level_option['nc_func'];
|
||||
|
||||
|
||||
Db::name('user')
|
||||
->where('id',$val['id'])
|
||||
->update($data);
|
||||
}
|
||||
|
||||
// 指令输出
|
||||
$output->writeln('checkexpire');
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,62 @@
|
||||
<?php
|
||||
declare (strict_types = 1);
|
||||
|
||||
namespace app\command;
|
||||
|
||||
use think\console\Command;
|
||||
use think\console\Input;
|
||||
use think\console\input\Argument;
|
||||
use think\console\input\Option;
|
||||
use think\console\Output;
|
||||
|
||||
use think\facade\Db;
|
||||
|
||||
class CheckTrial extends Command
|
||||
{
|
||||
protected function configure()
|
||||
{
|
||||
// 指令配置
|
||||
$this->setName('checktrial')
|
||||
->setDescription('the checktrial command');
|
||||
}
|
||||
|
||||
protected function execute(Input $input, Output $output)
|
||||
{
|
||||
// 取得代理資料
|
||||
$t_agents = Db::name('agent')
|
||||
->select();
|
||||
|
||||
foreach($t_agents as $val){
|
||||
$agents[$val['id']] = $val;
|
||||
}
|
||||
|
||||
// 取得試用過期用戶
|
||||
$e_users = Db::name('user')
|
||||
->where('status',2)
|
||||
->where('overdue_time','<',time())
|
||||
->select();
|
||||
|
||||
// 更新試用過期用戶
|
||||
foreach($e_users as $val){
|
||||
$data['overdue_time']=strtotime("+".$agents[$val['agent_id']]['base_days']." days");
|
||||
$data['level']=$agents[$val['agent_id']]['base_level'];
|
||||
|
||||
$level_option = Db::name('user_level')
|
||||
->where('agent_id',$val['agent_id'])
|
||||
->where('level_id',$data['level'])
|
||||
->find();
|
||||
|
||||
$data['nc_type']=$level_option['nc_type'];
|
||||
$data['nc_func']=$level_option['nc_func'];
|
||||
|
||||
$data['status']=1;
|
||||
print_r($data);
|
||||
Db::name('user')
|
||||
->where('id',$val['id'])
|
||||
->update($data);
|
||||
}
|
||||
|
||||
// 指令输出
|
||||
$output->writeln('檢查試用會員完成');
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,29 @@
|
||||
<?php
|
||||
namespace app\common\lib;
|
||||
|
||||
class Aes{
|
||||
|
||||
private $key = 'iloveutel';
|
||||
private $iv = '1234567890123456';
|
||||
private $method = 'AES-128-CBC';
|
||||
|
||||
/**
|
||||
* 構造方法
|
||||
*/
|
||||
public function __construct($config){
|
||||
foreach($config as $k=>$v){
|
||||
|
||||
$this->$k = $v;
|
||||
}
|
||||
}
|
||||
|
||||
// 加密
|
||||
public function encrypt($data){
|
||||
return base64_encode(openssl_encrypt($data, $this->method,$this->key, OPENSSL_RAW_DATA , $this->iv));
|
||||
}
|
||||
|
||||
//解密
|
||||
public function descrypt($data){
|
||||
return openssl_decrypt(base64_decode($data), $this->method, $this->key, OPENSSL_RAW_DATA, $this->iv);
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,38 @@
|
||||
<?php
|
||||
namespace app\common\lib;
|
||||
|
||||
use Firebase\JWT\JWT;
|
||||
use Firebase\JWT\Key;
|
||||
|
||||
class Token{
|
||||
/**
|
||||
* 構造方法
|
||||
*/
|
||||
public function __construct(){
|
||||
|
||||
}
|
||||
|
||||
public static function genToken($payload){
|
||||
$payload = array_merge($payload,[
|
||||
'aud' => '',
|
||||
'exp' => time() + (365 * 24 * 60 * 60),
|
||||
'iat' => time(),
|
||||
'iss' => '',
|
||||
'jti' => uniqid(mt_rand(), true),
|
||||
'nbf' => time(),
|
||||
'sub' => '',
|
||||
]);
|
||||
|
||||
return JWT::encode($payload, \think\facade\Config::get('jwt.secret'), 'HS256');
|
||||
}
|
||||
|
||||
public static function check($token){
|
||||
try{
|
||||
$decode = JWT::decode($token, new Key(\think\facade\Config::get('jwt.secret'), 'HS256'));
|
||||
return true;
|
||||
}catch(\Exception $e){
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@ -0,0 +1,51 @@
|
||||
<?php
|
||||
namespace app\common\lib;
|
||||
|
||||
use think\facade\Db;
|
||||
|
||||
use JeroenDesloovere\VCard\VCard as VCardApi;
|
||||
|
||||
class Vcard{
|
||||
|
||||
public static function genVcf($userid){
|
||||
$userInfo = Db::name('user')->where('user_id',$userid)->find();
|
||||
if(!$userInfo){
|
||||
return false;
|
||||
}
|
||||
$vcard = new VCardApi();
|
||||
|
||||
$lastname = $userInfo['real_name'];
|
||||
$firstname = '';
|
||||
$additional = '';
|
||||
$prefix = '';
|
||||
$suffix = '';
|
||||
|
||||
$vcard->addName($lastname, $firstname, $additional, $prefix, $suffix);
|
||||
|
||||
// add work data
|
||||
$vcard->addCompany($userInfo['company']);
|
||||
$vcard->addJobtitle($userInfo['title']);
|
||||
// $vcard->addRole('Data Protection Officer');
|
||||
$vcard->addEmail($userInfo['email']);
|
||||
$vcard->addPhoneNumber($userInfo['phone'], 'PREF;CELL');
|
||||
$vcard->addPhoneNumber($userInfo['tel'], 'WORK');
|
||||
// $vcard->addAddress(null, null, 'street', 'worktown', null, 'workpostcode', 'Belgium');
|
||||
// $vcard->addLabel('street, worktown, workpostcode Belgium');
|
||||
if($userInfo['url']){
|
||||
// $vcard->addURL(getUrl().'/card/?userid='.$userInfo['user_id']);
|
||||
$vcard->addURL($userInfo['url']);
|
||||
}
|
||||
|
||||
$vcard->addPhoto(__DIR__.'/../../../public/storage/'.$userInfo['user_id'].'/'.$userInfo['user_id'].'_line.jpg');
|
||||
|
||||
// return vcard as a string
|
||||
//return $vcard->getOutput();
|
||||
|
||||
// return vcard as a download
|
||||
// return $vcard->download();
|
||||
$vcard->setSavePath(__DIR__.'/../../../public/storage/'.$userInfo['user_id'].'/');
|
||||
$vcard->setFilename($userInfo['user_id']);
|
||||
$vcard->save();
|
||||
return true;
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,6 @@
|
||||
<?php
|
||||
namespace app\common\sms;
|
||||
|
||||
interface Isms {
|
||||
public function sendSms(array $data);
|
||||
}
|
||||
@ -0,0 +1,23 @@
|
||||
<?php
|
||||
namespace app\common\sms;
|
||||
|
||||
use think\facade\Db;
|
||||
use app\common\sms\SmsFactory;
|
||||
|
||||
class Sms
|
||||
{
|
||||
//使用靜態方法,建立物流單
|
||||
public static function createSms($smscode,$data)
|
||||
{
|
||||
|
||||
$sms = SmsFactory::createSmsService($smscode);
|
||||
|
||||
$result = $sms->sendSms($data);
|
||||
|
||||
if(!$result){
|
||||
return FALSE;
|
||||
}
|
||||
return TRUE;
|
||||
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,17 @@
|
||||
<?php
|
||||
namespace app\common\sms;
|
||||
|
||||
use app\common\sms\SmskingSms;
|
||||
use think\Exception;
|
||||
|
||||
class SmsFactory
|
||||
{
|
||||
public static function createSmsService($serviceName) {
|
||||
switch ($serviceName) {
|
||||
case 'smsking':
|
||||
return new SmskingSms('slash1000','a810309');
|
||||
default:
|
||||
throw new Exception("Unsupported sms service: $serviceName");
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,53 @@
|
||||
<?php
|
||||
|
||||
namespace app\common\sms;
|
||||
|
||||
use GuzzleHttp\Client;
|
||||
|
||||
use app\common\sms\Isms;
|
||||
|
||||
use think\facade\Db;
|
||||
|
||||
//實作物流串接介面
|
||||
class SmskingSms implements Isms
|
||||
{
|
||||
private $username;
|
||||
private $password;
|
||||
|
||||
public function __construct(string $username, string $password)
|
||||
{
|
||||
$this->username = $username;
|
||||
$this->password = $password;
|
||||
}
|
||||
|
||||
public function sendSms(array $data)
|
||||
{
|
||||
// 將$message 轉為 Big5 編碼
|
||||
$message = mb_convert_encoding($data['message'], 'BIG5', 'UTF-8');
|
||||
|
||||
$url = 'https://api.kotsms.com.tw/kotsmsapi-1.php';
|
||||
|
||||
$query = http_build_query([
|
||||
'username' => $this->username,
|
||||
'password' => $this->password,
|
||||
'dstaddr' => $data['recipient'],
|
||||
'smbody' => $message,
|
||||
]);
|
||||
|
||||
$url .= '?' . $query;
|
||||
// 使用 Guzzle 發送 API 請求
|
||||
$client = new Client();
|
||||
$response = $client->request('GET', $url);
|
||||
|
||||
// 處理 API 回應
|
||||
$body = $response->getBody()->getContents();
|
||||
$result =explode('=',$body);
|
||||
// $result = json_decode($body, true);
|
||||
if (is_numeric(intval($result[1])) && intval($result[1])>=0) {
|
||||
return true;
|
||||
} else {
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,12 @@
|
||||
<?php
|
||||
namespace app\controller;
|
||||
|
||||
use app\BaseController;
|
||||
|
||||
class Index extends BaseController
|
||||
{
|
||||
public function index()
|
||||
{
|
||||
return '';
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,19 @@
|
||||
<?php
|
||||
namespace app\controller;
|
||||
|
||||
use app\BaseController;
|
||||
|
||||
use think\facade\Db;
|
||||
|
||||
use app\common\lib\Vcard;
|
||||
|
||||
class Vcf extends BaseController
|
||||
{
|
||||
|
||||
public function index(){
|
||||
$userid=input('userid');
|
||||
$userid='mc622b0cda299c6';
|
||||
|
||||
Vcard::genVcf($userid);
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,17 @@
|
||||
<?php
|
||||
// 事件定义文件
|
||||
return [
|
||||
'bind' => [
|
||||
],
|
||||
|
||||
'listen' => [
|
||||
'AppInit' => [],
|
||||
'HttpRun' => [],
|
||||
'HttpEnd' => [],
|
||||
'LogLevel' => [],
|
||||
'LogWrite' => [],
|
||||
],
|
||||
|
||||
'subscribe' => [
|
||||
],
|
||||
];
|
||||
@ -0,0 +1,10 @@
|
||||
<?php
|
||||
// 全局中间件定义文件
|
||||
return [
|
||||
// 全局请求缓存
|
||||
// \think\middleware\CheckRequestCache::class,
|
||||
// 多语言加载
|
||||
// \think\middleware\LoadLangPack::class,
|
||||
// Session初始化
|
||||
// \think\middleware\SessionInit::class
|
||||
];
|
||||
@ -0,0 +1,9 @@
|
||||
<?php
|
||||
use app\ExceptionHandle;
|
||||
use app\Request;
|
||||
|
||||
// 容器Provider定义文件
|
||||
return [
|
||||
'think\Request' => Request::class,
|
||||
'think\exception\Handle' => ExceptionHandle::class,
|
||||
];
|
||||
@ -0,0 +1,9 @@
|
||||
<?php
|
||||
|
||||
use app\AppService;
|
||||
|
||||
// 系统服务定义文件
|
||||
// 服务在完成全局初始化之后执行
|
||||
return [
|
||||
AppService::class,
|
||||
];
|
||||
@ -0,0 +1,55 @@
|
||||
{
|
||||
"name": "topthink/think",
|
||||
"description": "the new thinkphp framework",
|
||||
"type": "project",
|
||||
"keywords": [
|
||||
"framework",
|
||||
"thinkphp",
|
||||
"ORM"
|
||||
],
|
||||
"homepage": "http://thinkphp.cn/",
|
||||
"license": "Apache-2.0",
|
||||
"authors": [
|
||||
{
|
||||
"name": "liu21st",
|
||||
"email": "liu21st@gmail.com"
|
||||
},
|
||||
{
|
||||
"name": "yunwuxin",
|
||||
"email": "448901948@qq.com"
|
||||
}
|
||||
],
|
||||
"require": {
|
||||
"php": ">=7.2.5",
|
||||
"topthink/framework": "^6.0.0",
|
||||
"topthink/think-orm": "^2.0",
|
||||
"topthink/think-multi-app": "^1.0",
|
||||
"thans/tp-jwt-auth": "^1.2",
|
||||
"guzzlehttp/guzzle": "~6.0",
|
||||
"aferrandini/phpqrcode": "^1.0",
|
||||
"jeroendesloovere/vcard": "^1.7",
|
||||
"topthink/think-filesystem": "^2.0",
|
||||
"firebase/php-jwt": "^6.4"
|
||||
},
|
||||
"require-dev": {
|
||||
"symfony/var-dumper": "^4.2",
|
||||
"topthink/think-trace":"^1.0"
|
||||
},
|
||||
"autoload": {
|
||||
"psr-4": {
|
||||
"app\\": "app"
|
||||
},
|
||||
"psr-0": {
|
||||
"": "extend/"
|
||||
}
|
||||
},
|
||||
"config": {
|
||||
"preferred-install": "dist"
|
||||
},
|
||||
"scripts": {
|
||||
"post-autoload-dump": [
|
||||
"@php think service:discover",
|
||||
"@php think vendor:publish"
|
||||
]
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,29 @@
|
||||
<?php
|
||||
|
||||
// +----------------------------------------------------------------------
|
||||
// | 缓存设置
|
||||
// +----------------------------------------------------------------------
|
||||
|
||||
return [
|
||||
// 默认缓存驱动
|
||||
'default' => env('cache.driver', 'file'),
|
||||
|
||||
// 缓存连接方式配置
|
||||
'stores' => [
|
||||
'file' => [
|
||||
// 驱动方式
|
||||
'type' => 'File',
|
||||
// 缓存保存目录
|
||||
'path' => '',
|
||||
// 缓存前缀
|
||||
'prefix' => '',
|
||||
// 缓存有效期 0表示永久缓存
|
||||
'expire' => 0,
|
||||
// 缓存标签前缀
|
||||
'tag_prefix' => 'tag:',
|
||||
// 序列化机制 例如 ['serialize', 'unserialize']
|
||||
'serialize' => [],
|
||||
],
|
||||
// 更多的缓存连接
|
||||
],
|
||||
];
|
||||
@ -0,0 +1,11 @@
|
||||
<?php
|
||||
// +----------------------------------------------------------------------
|
||||
// | 控制台配置
|
||||
// +----------------------------------------------------------------------
|
||||
return [
|
||||
// 指令定义
|
||||
'commands' => [
|
||||
'checktrial' => app\command\CheckTrial::class,
|
||||
'checkexpire' => app\command\CheckExpire::class,
|
||||
],
|
||||
];
|
||||
@ -0,0 +1,20 @@
|
||||
<?php
|
||||
// +----------------------------------------------------------------------
|
||||
// | Cookie设置
|
||||
// +----------------------------------------------------------------------
|
||||
return [
|
||||
// cookie 保存时间
|
||||
'expire' => 0,
|
||||
// cookie 保存路径
|
||||
'path' => '/',
|
||||
// cookie 有效域名
|
||||
'domain' => '',
|
||||
// cookie 启用安全传输
|
||||
'secure' => false,
|
||||
// httponly设置
|
||||
'httponly' => false,
|
||||
// 是否使用 setcookie
|
||||
'setcookie' => true,
|
||||
// samesite 设置,支持 'strict' 'lax'
|
||||
'samesite' => '',
|
||||
];
|
||||
@ -0,0 +1,24 @@
|
||||
<?php
|
||||
|
||||
return [
|
||||
// 默认磁盘
|
||||
'default' => env('filesystem.driver', 'local'),
|
||||
// 磁盘列表
|
||||
'disks' => [
|
||||
'local' => [
|
||||
'type' => 'local',
|
||||
'root' => app()->getRuntimePath() . 'storage',
|
||||
],
|
||||
'public' => [
|
||||
// 磁盘类型
|
||||
'type' => 'local',
|
||||
// 磁盘路径
|
||||
'root' => app()->getRootPath() . 'public/storage',
|
||||
// 磁盘路径对应的外部URL路径
|
||||
'url' => '/storage',
|
||||
// 可见性
|
||||
'visibility' => 'public',
|
||||
],
|
||||
// 更多的磁盘配置信息
|
||||
],
|
||||
];
|
||||
@ -0,0 +1,27 @@
|
||||
<?php
|
||||
// +----------------------------------------------------------------------
|
||||
// | 多语言设置
|
||||
// +----------------------------------------------------------------------
|
||||
|
||||
return [
|
||||
// 默认语言
|
||||
'default_lang' => env('lang.default_lang', 'zh-cn'),
|
||||
// 允许的语言列表
|
||||
'allow_lang_list' => [],
|
||||
// 多语言自动侦测变量名
|
||||
'detect_var' => 'lang',
|
||||
// 是否使用Cookie记录
|
||||
'use_cookie' => true,
|
||||
// 多语言cookie变量
|
||||
'cookie_var' => 'think_lang',
|
||||
// 多语言header变量
|
||||
'header_var' => 'think-lang',
|
||||
// 扩展语言包
|
||||
'extend_list' => [],
|
||||
// Accept-Language转义为对应语言包名称
|
||||
'accept_language' => [
|
||||
'zh-hans-cn' => 'zh-cn',
|
||||
],
|
||||
// 是否支持语言分组
|
||||
'allow_group' => false,
|
||||
];
|
||||
@ -0,0 +1,45 @@
|
||||
<?php
|
||||
|
||||
// +----------------------------------------------------------------------
|
||||
// | 日志设置
|
||||
// +----------------------------------------------------------------------
|
||||
return [
|
||||
// 默认日志记录通道
|
||||
'default' => env('log.channel', 'file'),
|
||||
// 日志记录级别
|
||||
'level' => [],
|
||||
// 日志类型记录的通道 ['error'=>'email',...]
|
||||
'type_channel' => [],
|
||||
// 关闭全局日志写入
|
||||
'close' => false,
|
||||
// 全局日志处理 支持闭包
|
||||
'processor' => null,
|
||||
|
||||
// 日志通道列表
|
||||
'channels' => [
|
||||
'file' => [
|
||||
// 日志记录方式
|
||||
'type' => 'File',
|
||||
// 日志保存目录
|
||||
'path' => '',
|
||||
// 单文件日志写入
|
||||
'single' => false,
|
||||
// 独立日志级别
|
||||
'apart_level' => [],
|
||||
// 最大日志文件数量
|
||||
'max_files' => 0,
|
||||
// 使用JSON格式记录
|
||||
'json' => false,
|
||||
// 日志处理
|
||||
'processor' => null,
|
||||
// 关闭通道日志写入
|
||||
'close' => false,
|
||||
// 日志输出格式化
|
||||
'format' => '[%s][%s] %s',
|
||||
// 是否实时写入
|
||||
'realtime_write' => false,
|
||||
],
|
||||
// 其它日志通道配置
|
||||
],
|
||||
|
||||
];
|
||||
@ -0,0 +1,8 @@
|
||||
<?php
|
||||
// 中间件配置
|
||||
return [
|
||||
// 别名或分组
|
||||
'alias' => [],
|
||||
// 优先级设置,此数组中的中间件会按照数组中的顺序优先执行
|
||||
'priority' => [],
|
||||
];
|
||||
@ -0,0 +1,45 @@
|
||||
<?php
|
||||
// +----------------------------------------------------------------------
|
||||
// | 路由设置
|
||||
// +----------------------------------------------------------------------
|
||||
|
||||
return [
|
||||
// pathinfo分隔符
|
||||
'pathinfo_depr' => '/',
|
||||
// URL伪静态后缀
|
||||
'url_html_suffix' => 'html',
|
||||
// URL普通方式参数 用于自动生成
|
||||
'url_common_param' => true,
|
||||
// 是否开启路由延迟解析
|
||||
'url_lazy_route' => false,
|
||||
// 是否强制使用路由
|
||||
'url_route_must' => false,
|
||||
// 合并路由规则
|
||||
'route_rule_merge' => false,
|
||||
// 路由是否完全匹配
|
||||
'route_complete_match' => false,
|
||||
// 访问控制器层名称
|
||||
'controller_layer' => 'controller',
|
||||
// 空控制器名
|
||||
'empty_controller' => 'Error',
|
||||
// 是否使用控制器后缀
|
||||
'controller_suffix' => false,
|
||||
// 默认的路由变量规则
|
||||
'default_route_pattern' => '[\w\.]+',
|
||||
// 是否开启请求缓存 true自动缓存 支持设置请求缓存规则
|
||||
'request_cache_key' => false,
|
||||
// 请求缓存有效期
|
||||
'request_cache_expire' => null,
|
||||
// 全局请求缓存排除规则
|
||||
'request_cache_except' => [],
|
||||
// 默认控制器名
|
||||
'default_controller' => 'Index',
|
||||
// 默认操作名
|
||||
'default_action' => 'index',
|
||||
// 操作方法后缀
|
||||
'action_suffix' => '',
|
||||
// 默认JSONP格式返回的处理方法
|
||||
'default_jsonp_handler' => 'jsonpReturn',
|
||||
// 默认JSONP处理方法
|
||||
'var_jsonp_handler' => 'callback',
|
||||
];
|
||||
@ -0,0 +1,19 @@
|
||||
<?php
|
||||
// +----------------------------------------------------------------------
|
||||
// | 会话设置
|
||||
// +----------------------------------------------------------------------
|
||||
|
||||
return [
|
||||
// session name
|
||||
'name' => 'PHPSESSID',
|
||||
// SESSION_ID的提交变量,解决flash上传跨域
|
||||
'var_session_id' => '',
|
||||
// 驱动方式 支持file cache
|
||||
'type' => 'file',
|
||||
// 存储连接标识 当type使用cache的时候有效
|
||||
'store' => null,
|
||||
// 过期时间
|
||||
'expire' => 1440,
|
||||
// 前缀
|
||||
'prefix' => '',
|
||||
];
|
||||
@ -0,0 +1,10 @@
|
||||
<?php
|
||||
// +----------------------------------------------------------------------
|
||||
// | Trace设置 开启调试模式后有效
|
||||
// +----------------------------------------------------------------------
|
||||
return [
|
||||
// 内置Html和Console两种方式 支持扩展
|
||||
'type' => 'Html',
|
||||
// 读取的日志通道名
|
||||
'channel' => '',
|
||||
];
|
||||
@ -0,0 +1,25 @@
|
||||
<?php
|
||||
// +----------------------------------------------------------------------
|
||||
// | 模板设置
|
||||
// +----------------------------------------------------------------------
|
||||
|
||||
return [
|
||||
// 模板引擎类型使用Think
|
||||
'type' => 'Think',
|
||||
// 默认模板渲染规则 1 解析为小写+下划线 2 全部转换小写 3 保持操作方法
|
||||
'auto_rule' => 1,
|
||||
// 模板目录名
|
||||
'view_dir_name' => 'view',
|
||||
// 模板后缀
|
||||
'view_suffix' => 'html',
|
||||
// 模板文件名分隔符
|
||||
'view_depr' => DIRECTORY_SEPARATOR,
|
||||
// 模板引擎普通标签开始标记
|
||||
'tpl_begin' => '{',
|
||||
// 模板引擎普通标签结束标记
|
||||
'tpl_end' => '}',
|
||||
// 标签库标签开始标记
|
||||
'taglib_begin' => '{',
|
||||
// 标签库标签结束标记
|
||||
'taglib_end' => '}',
|
||||
];
|
||||
@ -0,0 +1,2 @@
|
||||
*
|
||||
!.gitignore
|
||||
@ -0,0 +1,6 @@
|
||||
{
|
||||
"name": "ecard_api",
|
||||
"lockfileVersion": 2,
|
||||
"requires": true,
|
||||
"packages": {}
|
||||
}
|
||||
@ -0,0 +1 @@
|
||||
{}
|
||||
@ -0,0 +1 @@
|
||||
open_basedir=/www/wwwroot/sso.h888.fun/:/tmp/
|
||||
@ -0,0 +1,198 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-TW">
|
||||
<head>
|
||||
<meta charset="UTF-8" />
|
||||
<meta http-equiv="X-UA-Compatible" content="IE=edge" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<title>Error!!!</title>
|
||||
<style>
|
||||
* {
|
||||
margin:0px auto;
|
||||
padding: 0px;
|
||||
text-align:center;
|
||||
}
|
||||
body {
|
||||
background-color: #D4D9ED;
|
||||
}
|
||||
.cont_principal {
|
||||
position: absolute;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
overflow: hidden;
|
||||
}
|
||||
.cont_error {
|
||||
position: absolute;
|
||||
width: 100%;
|
||||
height: 300px;
|
||||
top: 50%;
|
||||
margin-top:-150px;
|
||||
}
|
||||
|
||||
.cont_error > h1 {
|
||||
font-family: 'Lato', sans-serif;
|
||||
font-weight: 400;
|
||||
font-size:150px;
|
||||
color:#fff;
|
||||
position: relative;
|
||||
left:-100%;
|
||||
transition: all 0.5s;
|
||||
}
|
||||
|
||||
|
||||
.cont_error > p {
|
||||
font-family: 'Lato', sans-serif;
|
||||
font-weight: 300;
|
||||
font-size:24px;
|
||||
letter-spacing: 5px;
|
||||
color:#9294AE;
|
||||
position: relative;
|
||||
left:100%;
|
||||
transition: all 0.5s;
|
||||
transition-delay: 0.5s;
|
||||
-webkit-transition: all 0.5s;
|
||||
-webkit-transition-delay: 0.5s;
|
||||
}
|
||||
|
||||
.cont_aura_1 {
|
||||
position:absolute;
|
||||
width:300px;
|
||||
height: 120%;
|
||||
top:25px;
|
||||
right: -340px;
|
||||
background-color: #8A65DF;
|
||||
box-shadow: 0px 0px 60px 20px rgba(137,100,222,0.5);
|
||||
-webkit-transition: all 0.5s;
|
||||
transition: all 0.5s;
|
||||
}
|
||||
|
||||
.cont_aura_2 {
|
||||
position:absolute;
|
||||
width:100%;
|
||||
height: 300px;
|
||||
right:-10%;
|
||||
bottom:-301px;
|
||||
background-color: #8B65E4;
|
||||
box-shadow: 0px 0px 60px 10px rgba(131, 95, 214, 0.5),0px 0px 20px 0px rgba(0,0,0,0.1);
|
||||
z-index:5;
|
||||
transition: all 0.5s;
|
||||
-webkit-transition: all 0.5s;
|
||||
}
|
||||
|
||||
.cont_error_active > .cont_error > h1 {
|
||||
left:0%;
|
||||
}
|
||||
.cont_error_active > .cont_error > p {
|
||||
left:0%;
|
||||
}
|
||||
|
||||
.cont_error_active > .cont_aura_2 {
|
||||
animation-name: animation_error_2;
|
||||
animation-duration: 4s;
|
||||
animation-timing-function: linear;
|
||||
animation-iteration-count: infinite;
|
||||
animation-direction: alternate;
|
||||
transform: rotate(-20deg);
|
||||
}
|
||||
.cont_error_active > .cont_aura_1 {
|
||||
transform: rotate(20deg);
|
||||
right:-170px;
|
||||
animation-name: animation_error_1;
|
||||
animation-duration: 4s;
|
||||
animation-timing-function: linear;
|
||||
animation-iteration-count: infinite;
|
||||
animation-direction: alternate;
|
||||
}
|
||||
|
||||
@-webkit-keyframes animation_error_1 {
|
||||
from {
|
||||
-webkit-transform: rotate(20deg);
|
||||
transform: rotate(20deg);
|
||||
}
|
||||
to { -webkit-transform: rotate(25deg);
|
||||
transform: rotate(25deg);
|
||||
}
|
||||
}
|
||||
@-o-keyframes animation_error_1 {
|
||||
from {
|
||||
-webkit-transform: rotate(20deg);
|
||||
transform: rotate(20deg);
|
||||
}
|
||||
to { -webkit-transform: rotate(25deg);
|
||||
transform: rotate(25deg);
|
||||
}
|
||||
|
||||
}
|
||||
@-moz-keyframes animation_error_1 {
|
||||
from {
|
||||
-webkit-transform: rotate(20deg);
|
||||
transform: rotate(20deg);
|
||||
}
|
||||
to { -webkit-transform: rotate(25deg);
|
||||
transform: rotate(25deg);
|
||||
}
|
||||
|
||||
}
|
||||
@keyframes animation_error_1 {
|
||||
from {
|
||||
-webkit-transform: rotate(20deg);
|
||||
transform: rotate(20deg);
|
||||
}
|
||||
to { -webkit-transform: rotate(25deg);
|
||||
transform: rotate(25deg);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
@-webkit-keyframes animation_error_2 {
|
||||
from { -webkit-transform: rotate(-15deg);
|
||||
transform: rotate(-15deg);
|
||||
}
|
||||
to { -webkit-transform: rotate(-20deg);
|
||||
transform: rotate(-20deg);
|
||||
}
|
||||
}
|
||||
@-o-keyframes animation_error_2 {
|
||||
from { -webkit-transform: rotate(-15deg);
|
||||
transform: rotate(-15deg);
|
||||
}
|
||||
to { -webkit-transform: rotate(-20deg);
|
||||
transform: rotate(-20deg);
|
||||
}
|
||||
}
|
||||
}
|
||||
@-moz-keyframes animation_error_2 {
|
||||
from { -webkit-transform: rotate(-15deg);
|
||||
transform: rotate(-15deg);
|
||||
}
|
||||
to { -webkit-transform: rotate(-20deg);
|
||||
transform: rotate(-20deg);
|
||||
}
|
||||
}
|
||||
@keyframes animation_error_2 {
|
||||
from { -webkit-transform: rotate(-15deg);
|
||||
transform: rotate(-15deg);
|
||||
}
|
||||
to { -webkit-transform: rotate(-20deg);
|
||||
transform: rotate(-20deg);
|
||||
}
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<div class="cont_principal">
|
||||
<div class="cont_error">
|
||||
<h1>Oops</h1>
|
||||
<p>The Page you're looking for isn't here.</p>
|
||||
</div>
|
||||
<div class="cont_aura_1"></div>
|
||||
<div class="cont_aura_2"></div>
|
||||
</div>
|
||||
</body>
|
||||
<script>
|
||||
window.onload = function(){
|
||||
document.querySelector('.cont_principal').className= "cont_principal cont_error_active";
|
||||
}
|
||||
</script>
|
||||
</html>
|
||||
|
After Width: | Height: | Size: 1.1 KiB |
@ -0,0 +1,25 @@
|
||||
<?php
|
||||
// +----------------------------------------------------------------------
|
||||
// | ThinkPHP [ WE CAN DO IT JUST THINK ]
|
||||
// +----------------------------------------------------------------------
|
||||
// | Copyright (c) 2006-2019 http://thinkphp.cn All rights reserved.
|
||||
// +----------------------------------------------------------------------
|
||||
// | Licensed ( http://www.apache.org/licenses/LICENSE-2.0 )
|
||||
// +----------------------------------------------------------------------
|
||||
// | Author: liu21st <liu21st@gmail.com>
|
||||
// +----------------------------------------------------------------------
|
||||
|
||||
// [ 应用入口文件 ]
|
||||
namespace think;
|
||||
|
||||
require __DIR__ . '/../vendor/autoload.php';
|
||||
|
||||
define('ROOT_PATH',$_SERVER['DOCUMENT_ROOT']);
|
||||
// 执行HTTP应用并响应
|
||||
$http = (new App())->http;
|
||||
|
||||
$response = $http->run();
|
||||
|
||||
$response->send();
|
||||
|
||||
$http->end($response);
|
||||
@ -0,0 +1,17 @@
|
||||
<?php
|
||||
// +----------------------------------------------------------------------
|
||||
// | ThinkPHP [ WE CAN DO IT JUST THINK ]
|
||||
// +----------------------------------------------------------------------
|
||||
// | Copyright (c) 2006~2018 http://thinkphp.cn All rights reserved.
|
||||
// +----------------------------------------------------------------------
|
||||
// | Licensed ( http://www.apache.org/licenses/LICENSE-2.0 )
|
||||
// +----------------------------------------------------------------------
|
||||
// | Author: liu21st <liu21st@gmail.com>
|
||||
// +----------------------------------------------------------------------
|
||||
use think\facade\Route;
|
||||
|
||||
Route::get('think', function () {
|
||||
return 'hello,ThinkPHP6!';
|
||||
});
|
||||
|
||||
Route::get('hello/:name', 'index/hello');
|
||||
@ -0,0 +1,2 @@
|
||||
*
|
||||
!.gitignore
|
||||
@ -0,0 +1,10 @@
|
||||
#!/usr/bin/env php
|
||||
<?php
|
||||
namespace think;
|
||||
|
||||
// 命令行入口文件
|
||||
// 加载基础文件
|
||||
require __DIR__ . '/vendor/autoload.php';
|
||||
|
||||
// 应用初始化
|
||||
(new App())->console->run();
|
||||
@ -0,0 +1 @@
|
||||
.idea
|
||||
@ -0,0 +1,165 @@
|
||||
GNU LESSER GENERAL PUBLIC LICENSE
|
||||
Version 3, 29 June 2007
|
||||
|
||||
Copyright (C) 2007 Free Software Foundation, Inc. <http://fsf.org/>
|
||||
Everyone is permitted to copy and distribute verbatim copies
|
||||
of this license document, but changing it is not allowed.
|
||||
|
||||
|
||||
This version of the GNU Lesser General Public License incorporates
|
||||
the terms and conditions of version 3 of the GNU General Public
|
||||
License, supplemented by the additional permissions listed below.
|
||||
|
||||
0. Additional Definitions.
|
||||
|
||||
As used herein, "this License" refers to version 3 of the GNU Lesser
|
||||
General Public License, and the "GNU GPL" refers to version 3 of the GNU
|
||||
General Public License.
|
||||
|
||||
"The Library" refers to a covered work governed by this License,
|
||||
other than an Application or a Combined Work as defined below.
|
||||
|
||||
An "Application" is any work that makes use of an interface provided
|
||||
by the Library, but which is not otherwise based on the Library.
|
||||
Defining a subclass of a class defined by the Library is deemed a mode
|
||||
of using an interface provided by the Library.
|
||||
|
||||
A "Combined Work" is a work produced by combining or linking an
|
||||
Application with the Library. The particular version of the Library
|
||||
with which the Combined Work was made is also called the "Linked
|
||||
Version".
|
||||
|
||||
The "Minimal Corresponding Source" for a Combined Work means the
|
||||
Corresponding Source for the Combined Work, excluding any source code
|
||||
for portions of the Combined Work that, considered in isolation, are
|
||||
based on the Application, and not on the Linked Version.
|
||||
|
||||
The "Corresponding Application Code" for a Combined Work means the
|
||||
object code and/or source code for the Application, including any data
|
||||
and utility programs needed for reproducing the Combined Work from the
|
||||
Application, but excluding the System Libraries of the Combined Work.
|
||||
|
||||
1. Exception to Section 3 of the GNU GPL.
|
||||
|
||||
You may convey a covered work under sections 3 and 4 of this License
|
||||
without being bound by section 3 of the GNU GPL.
|
||||
|
||||
2. Conveying Modified Versions.
|
||||
|
||||
If you modify a copy of the Library, and, in your modifications, a
|
||||
facility refers to a function or data to be supplied by an Application
|
||||
that uses the facility (other than as an argument passed when the
|
||||
facility is invoked), then you may convey a copy of the modified
|
||||
version:
|
||||
|
||||
a) under this License, provided that you make a good faith effort to
|
||||
ensure that, in the event an Application does not supply the
|
||||
function or data, the facility still operates, and performs
|
||||
whatever part of its purpose remains meaningful, or
|
||||
|
||||
b) under the GNU GPL, with none of the additional permissions of
|
||||
this License applicable to that copy.
|
||||
|
||||
3. Object Code Incorporating Material from Library Header Files.
|
||||
|
||||
The object code form of an Application may incorporate material from
|
||||
a header file that is part of the Library. You may convey such object
|
||||
code under terms of your choice, provided that, if the incorporated
|
||||
material is not limited to numerical parameters, data structure
|
||||
layouts and accessors, or small macros, inline functions and templates
|
||||
(ten or fewer lines in length), you do both of the following:
|
||||
|
||||
a) Give prominent notice with each copy of the object code that the
|
||||
Library is used in it and that the Library and its use are
|
||||
covered by this License.
|
||||
|
||||
b) Accompany the object code with a copy of the GNU GPL and this license
|
||||
document.
|
||||
|
||||
4. Combined Works.
|
||||
|
||||
You may convey a Combined Work under terms of your choice that,
|
||||
taken together, effectively do not restrict modification of the
|
||||
portions of the Library contained in the Combined Work and reverse
|
||||
engineering for debugging such modifications, if you also do each of
|
||||
the following:
|
||||
|
||||
a) Give prominent notice with each copy of the Combined Work that
|
||||
the Library is used in it and that the Library and its use are
|
||||
covered by this License.
|
||||
|
||||
b) Accompany the Combined Work with a copy of the GNU GPL and this license
|
||||
document.
|
||||
|
||||
c) For a Combined Work that displays copyright notices during
|
||||
execution, include the copyright notice for the Library among
|
||||
these notices, as well as a reference directing the user to the
|
||||
copies of the GNU GPL and this license document.
|
||||
|
||||
d) Do one of the following:
|
||||
|
||||
0) Convey the Minimal Corresponding Source under the terms of this
|
||||
License, and the Corresponding Application Code in a form
|
||||
suitable for, and under terms that permit, the user to
|
||||
recombine or relink the Application with a modified version of
|
||||
the Linked Version to produce a modified Combined Work, in the
|
||||
manner specified by section 6 of the GNU GPL for conveying
|
||||
Corresponding Source.
|
||||
|
||||
1) Use a suitable shared library mechanism for linking with the
|
||||
Library. A suitable mechanism is one that (a) uses at run time
|
||||
a copy of the Library already present on the user's computer
|
||||
system, and (b) will operate properly with a modified version
|
||||
of the Library that is interface-compatible with the Linked
|
||||
Version.
|
||||
|
||||
e) Provide Installation Information, but only if you would otherwise
|
||||
be required to provide such information under section 6 of the
|
||||
GNU GPL, and only to the extent that such information is
|
||||
necessary to install and execute a modified version of the
|
||||
Combined Work produced by recombining or relinking the
|
||||
Application with a modified version of the Linked Version. (If
|
||||
you use option 4d0, the Installation Information must accompany
|
||||
the Minimal Corresponding Source and Corresponding Application
|
||||
Code. If you use option 4d1, you must provide the Installation
|
||||
Information in the manner specified by section 6 of the GNU GPL
|
||||
for conveying Corresponding Source.)
|
||||
|
||||
5. Combined Libraries.
|
||||
|
||||
You may place library facilities that are a work based on the
|
||||
Library side by side in a single library together with other library
|
||||
facilities that are not Applications and are not covered by this
|
||||
License, and convey such a combined library under terms of your
|
||||
choice, if you do both of the following:
|
||||
|
||||
a) Accompany the combined library with a copy of the same work based
|
||||
on the Library, uncombined with any other library facilities,
|
||||
conveyed under the terms of this License.
|
||||
|
||||
b) Give prominent notice with the combined library that part of it
|
||||
is a work based on the Library, and explaining where to find the
|
||||
accompanying uncombined form of the same work.
|
||||
|
||||
6. Revised Versions of the GNU Lesser General Public License.
|
||||
|
||||
The Free Software Foundation may publish revised and/or new versions
|
||||
of the GNU Lesser General Public License from time to time. Such new
|
||||
versions will be similar in spirit to the present version, but may
|
||||
differ in detail to address new problems or concerns.
|
||||
|
||||
Each version is given a distinguishing version number. If the
|
||||
Library as you received it specifies that a certain numbered version
|
||||
of the GNU Lesser General Public License "or any later version"
|
||||
applies to it, you have the option of following the terms and
|
||||
conditions either of that published version or of any later version
|
||||
published by the Free Software Foundation. If the Library as you
|
||||
received it does not specify a version number of the GNU Lesser
|
||||
General Public License, you may choose any version of the GNU Lesser
|
||||
General Public License ever published by the Free Software Foundation.
|
||||
|
||||
If the Library as you received it specifies that a proxy can decide
|
||||
whether future versions of the GNU Lesser General Public License shall
|
||||
apply, that proxy's public statement of acceptance of any version is
|
||||
permanent authorization for you to choose that version for the
|
||||
Library.
|
||||
@ -0,0 +1,2 @@
|
||||
1.1.5
|
||||
2012021604
|
||||
|
After Width: | Height: | Size: 126 B |
|
After Width: | Height: | Size: 202 B |
|
After Width: | Height: | Size: 205 B |
|
After Width: | Height: | Size: 216 B |
|
After Width: | Height: | Size: 210 B |
|
After Width: | Height: | Size: 213 B |
|
After Width: | Height: | Size: 219 B |
|
After Width: | Height: | Size: 211 B |
|
After Width: | Height: | Size: 211 B |
|
After Width: | Height: | Size: 228 B |
|
After Width: | Height: | Size: 225 B |