| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252 |
- <?php
- namespace pt\controllers;
- use bizHd\saas\services\StaffService;
- use common\components\jwt;
- use common\components\util;
- use Yii;
- class BaseController extends PublicController
- {
- public $staff, $staffId;
- public $isLogin = false;
- public $guestAccess = [];//不需要登陆的方法名
- public $validate = true;
- public function beforeAction($action)
- {
- // 新增:全局安全检查
- $this->securityCheck();
- //6表示总后台
- Yii::$app->params['ptStyle'] = 6;
- $staffId = jwt::getLoginId();
- if (empty($staffId)) {
- $this->validate = false;
- }
- //临时开放花材管理权限给商家
- $limitId = 4;
- if (getenv('YII_ENV') == 'production') {
- $limitId = 2;
- }
- if ($staffId == $limitId) {
- $currentRoute = $this->id . '/' . $action->id;
- $arr = [
- 'staff/login-detail',
- 'item/list',
- 'item-class/list',
- 'item-class/get-all-class',
- 'unit/get-all-unit',
- 'upload/save-img',
- 'item/add',
- ];
- if (in_array($currentRoute, $arr) == false) {
- util::fail('没有找到资源');
- }
- }
- //游客可以访问的方法
- if (in_array($action->id, $this->guestAccess)) {
- $this->validate = true;
- } else {
- $staff = StaffService::getById($staffId, true);
- if (empty($staff)) {
- util::logout();
- }
- if ($staff->status == 0) {
- util::logout("账号已冻结");
- }
- $this->staff = $staff;
- }
- if ($this->validate == false) {
- util::notLogin();
- }
- $this->staffId = $staffId;
- return parent::beforeAction($action);
- }
- /**
- * 全局安全检查
- */
- protected function securityCheck()
- {
- $request = Yii::$app->request;
- $this->checkSuspiciousParameters($request);
- $this->checkFileUploadSecurity($request);
- $this->checkSqlInjection($request);
- $this->checkXssAttack($request);
- $this->logSecurityActivity($request);
- }
- /**
- * 检查可疑参数
- */
- protected function checkSuspiciousParameters($request)
- {
- $dangerousPatterns = [
- // 代码执行相关
- '/eval\s*\(/i',
- '/exec\s*\(/i',
- '/system\s*\(/i',
- '/passthru\s*\(/i',
- '/shell_exec\s*\(/i',
- '/proc_open\s*\(/i',
- '/popen\s*\(/i',
-
- // 文件操作相关
- '/file_put_contents\s*\(/i',
- '/file_get_contents\s*\(/i',
- '/fwrite\s*\(/i',
- '/fopen\s*\(/i',
-
- // 目录遍历
- '/\.\.\//',
- '/\.\.\\\/',
-
- // 模板注入
- '/<\?php/i',
- '/<\?=/i',
- '/<\?/i',
-
- // 序列化攻击
- '/O:\d+:/',
- '/a:\d+:/',
- '/s:\d+:/',
- ];
-
- foreach (['get', 'post'] as $method) {
- $params = $request->$method();
- foreach ($params as $key => $value) {
- if (is_string($value)) {
- foreach ($dangerousPatterns as $pattern) {
- if (preg_match($pattern, $value)) {
- $this->logSecurityViolation($request, "Dangerous pattern detected: $pattern in $key");
- throw new \yii\web\HttpException(403, 'Access denied');
- }
- }
- }
- }
- }
- }
- /**
- * 检查文件上传安全
- */
- protected function checkFileUploadSecurity($request)
- {
- if (!empty($_FILES)) {
- foreach ($_FILES as $file) {
- if (isset($file['name'])) {
- $ext = strtolower(pathinfo($file['name'], PATHINFO_EXTENSION));
- $allowed = ['jpg', 'jpeg', 'png', 'gif', 'pdf', 'doc', 'docx'];
- if (!in_array($ext, $allowed)) {
- $this->logSecurityViolation($request, "Illegal file upload: " . $file['name']);
- throw new \yii\web\HttpException(403, 'Illegal file type');
- }
- }
- }
- }
- }
- /**
- * 检查SQL注入
- */
- protected function checkSqlInjection($request)
- {
- $sqlPatterns = [
- '/select\s.+\sfrom/i',
- '/union\s+select/i',
- '/insert\s+into/i',
- '/update\s.+\sset/i',
- '/delete\s+from/i',
- '/drop\s+table/i',
- '/--/',
- '/\bOR\b.+\=/i',
- ];
- foreach (['get', 'post'] as $method) {
- $params = $request->$method();
- foreach ($params as $key => $value) {
- if (is_string($value)) {
- foreach ($sqlPatterns as $pattern) {
- if (preg_match($pattern, $value)) {
- $this->logSecurityViolation($request, "SQL injection pattern: $pattern in $key");
- throw new \yii\web\HttpException(403, 'Access denied');
- }
- }
- }
- }
- }
- }
- /**
- * 检查XSS攻击
- */
- protected function checkXssAttack($request)
- {
- $xssPatterns = [
- '/<script\b[^>]*>(.*?)<\/script>/is',
- '/on\w+\s*=/i',
- '/javascript:/i',
- '/<iframe/i',
- '/<img/i',
- ];
- foreach (['get', 'post'] as $method) {
- $params = $request->$method();
- foreach ($params as $key => $value) {
- if (is_string($value)) {
- foreach ($xssPatterns as $pattern) {
- if (preg_match($pattern, $value)) {
- $this->logSecurityViolation($request, "XSS pattern: $pattern in $key");
- throw new \yii\web\HttpException(403, 'Access denied');
- }
- }
- }
- }
- }
- }
- /**
- * 记录安全日志
- */
- protected function logSecurityActivity($request)
- {
- $log = [
- 'time' => date('Y-m-d H:i:s'),
- 'ip' => $request->userIP,
- 'url' => $request->url,
- 'get' => $request->get(),
- 'post' => $request->post(),
- 'user_agent' => $request->userAgent,
- ];
- file_put_contents(
- Yii::getAlias('@runtime/logs/security_activity.log'),
- json_encode($log, JSON_UNESCAPED_UNICODE) . "\n",
- FILE_APPEND
- );
- }
- /**
- * 记录安全违规日志
- */
- protected function logSecurityViolation($request, $reason)
- {
- $log = [
- 'time' => date('Y-m-d H:i:s'),
- 'ip' => $request->userIP,
- 'url' => $request->url,
- 'get' => $request->get(),
- 'post' => $request->post(),
- 'user_agent' => $request->userAgent,
- 'reason' => $reason,
- ];
- file_put_contents(
- Yii::getAlias('@runtime/logs/security_violation.log'),
- json_encode($log, JSON_UNESCAPED_UNICODE) . "\n",
- FILE_APPEND
- );
- }
- }
|