Compare commits

..
62 Commits
Author SHA1 Message Date
Mr Chen c4a844cadb Merge pull request #209 from midoks/dev
0.9.13
2022-10-11 12:47:26 +08:00
midoks a88a281175 0.9.13
0.9.13
2022-10-11 12:46:35 +08:00
midoks f3f3b1c6bd Update init.lua 2022-10-11 12:35:59 +08:00
midoks 4259ac51cb up 2022-10-11 11:41:32 +08:00
midoks 4db1357d3d 更新mysql版本 2022-10-11 09:03:53 +08:00
midoks 15873e0824 Update op_waf.js 2022-10-11 00:40:21 +08:00
midoks dcdb07f76d up 2022-10-11 00:35:13 +08:00
midoks 8b70637479 Update index.py 2022-10-10 23:28:36 +08:00
midoks c77085fea4 Update index.py 2022-10-10 23:27:20 +08:00
midoks a265f3d0d5 Update index.py 2022-10-10 23:24:54 +08:00
midoks 7ea486cd1d Update index.py 2022-10-10 23:22:43 +08:00
midoks 0e31e87e28 Update index.py 2022-10-10 23:22:04 +08:00
midoks 8c621c892e Update index.py 2022-10-10 23:16:59 +08:00
midoks 32bcae603c Update index.py 2022-10-10 23:16:48 +08:00
midoks 98ec21446d Update index.py 2022-10-10 22:41:36 +08:00
midoks 0ee3682502 Update redis.service.tpl 2022-10-10 22:11:51 +08:00
midoks c609d1a012 Update redis.service.tpl 2022-10-10 22:05:55 +08:00
midoks 27b1a78879 up 2022-10-10 22:03:21 +08:00
midoks 773de840a5 Update redis.js 2022-10-10 21:55:00 +08:00
midoks 91d6ff3c54 Update index.py 2022-10-10 21:52:11 +08:00
midoks 03376bd42d Update redis.conf 2022-10-10 21:50:04 +08:00
midoks 036c5114c2 Update index.py 2022-10-10 21:35:51 +08:00
midoks a772e70fde Update index.py 2022-10-10 21:33:20 +08:00
midoks 53055bbdef Update index.py 2022-10-10 21:31:43 +08:00
midoks f81d598fcf Update index.py 2022-10-10 21:13:44 +08:00
midoks 3530e83bb9 up 2022-10-10 21:09:35 +08:00
midoks 1271b2f637 Update index.py 2022-10-10 21:00:30 +08:00
midoks 2dc6bc7753 Update index.py 2022-10-10 20:58:45 +08:00
midoks e52d9e3ea3 Update index.py 2022-10-10 20:55:45 +08:00
midoks d8a570e55e Update index.html 2022-10-10 20:46:07 +08:00
midoks f4ceaf667b php-yum更新 2022-10-10 20:43:48 +08:00
midoks 958ba16b85 Update index.html 2022-10-10 20:28:44 +08:00
midoks 73039777bb Update index.py 2022-10-10 20:06:00 +08:00
midoks 864e4c910c PHP添加会话管理功能 2022-10-10 19:54:23 +08:00
midoks 4da57405af Update init.lua 2022-10-10 13:01:27 +08:00
midoks dff638571a Update init.lua 2022-10-10 12:45:31 +08:00
midoks c7d9ec51cc up 2022-10-10 12:36:42 +08:00
midoks 501c575f73 up 2022-10-10 12:13:45 +08:00
midoks 0fd966ca65 up 2022-10-10 02:14:31 +08:00
midoks 172dde2794 Update mariadb.js 2022-10-09 23:26:50 +08:00
midoks 78fdc80652 优化mysql进入phpmyadmin 2022-10-09 23:24:47 +08:00
midoks 01b8c9b8ff Update init.lua 2022-10-09 22:47:28 +08:00
midoks b840086d4d op防火墙更新1 2022-10-09 21:29:40 +08:00
midoks 4c73f13f2d up 2022-10-09 11:36:57 +08:00
midoks f31c1aae96 up 2022-10-09 10:39:46 +08:00
midoks 5c24a831db Update index.py 2022-10-09 02:04:17 +08:00
midoks 91d07eebad Update install.sh 2022-10-09 01:59:17 +08:00
midoks 3b51ef2434 up 2022-10-09 01:49:17 +08:00
midoks 31c5e42b09 Update index.html 2022-10-09 01:38:15 +08:00
midoks b8b3a237ef up 2022-10-09 01:37:14 +08:00
midoks 5cb2aefbbc up 2022-10-09 01:25:53 +08:00
midoks 19173af3e2 Update logs_backup.py 2022-10-09 00:31:15 +08:00
midoks 3dc493108b Update mw.tpl 2022-10-09 00:30:03 +08:00
midoks 55af62000b Update logs_backup.py 2022-10-09 00:26:28 +08:00
midoks a1c8c48761 Update index.js 2022-10-08 22:45:44 +08:00
midoks 8c3ec0a103 Update index.js 2022-10-08 22:40:23 +08:00
midoks 5cbde31105 Update tool_task.py 2022-10-08 18:15:57 +08:00
midoks 04dd94032e Update tool_task.py 2022-10-08 18:12:45 +08:00
midoks 8a11195b0d Update tool_task.py 2022-10-08 18:08:38 +08:00
midoks 1eb76baae7 改变弹框方式 2022-10-08 16:05:24 +08:00
midoks 2669d6f021 Update init.lua 2022-10-08 15:21:17 +08:00
midoks 6f13a03a2c Update config_api.py 2022-10-08 14:24:58 +08:00
45 changed files with 1800 additions and 345 deletions
+8 -9
View File
@@ -90,16 +90,15 @@ docker run -itd --name mw-server --privileged=true -p 7200:7200 -p 80:80 -p 443:
```
### 版本更新 0.9.12
* 日志清理插件优化。
* 计划任务显示完整。
* 加入gitea插件。
* 融合mw-cli命令。
* 加快php编译速度。
* swap加上调整功能。
* 其他细节优化。
### 版本更新 0.9.13
* 优化弹框。
* 修复计划任务[日志切割]。
* 优化mysql的与phpmyadmin的连接。
* PHP添加`会话管理`功能。
* redis优化。
* 更新mysql[5.7]的安装。
* OP防火墙部分功能优化。
### JSDelivr安装地址
+1 -1
View File
@@ -15,7 +15,7 @@ from flask import request
class config_api:
__version = '0.9.12'
__version = '0.9.13'
def __init__(self):
pass
+1
View File
@@ -98,6 +98,7 @@ def initConf():
"/var/log/secure",
"/var/log/lastlog",
"/var/log/cron",
"/www/server/cron"
]
for i in clogcom:
if os.path.exists(i):
-2
View File
@@ -23,8 +23,6 @@ Install_app()
echo '正在安装脚本文件...' > $install_tmp
mkdir -p $serverPath/clean
echo "" > $serverPath/clean/clean.conf
cd ${rootPath} && python3 ${rootPath}/plugins/clean/index.py start
echo "${VERSION}" > $serverPath/clean/version.pl
echo '安装完成' > $install_tmp
+4 -2
View File
@@ -88,16 +88,18 @@ def createBgTaskByName(name, args):
_where1 = args['minute-n']
_minute = ''
mw_dir = mw.getRunDir()
cmd = '''
mw_dir=%s
rname=%s
plugin_path=%s
script_path=%s
logs_file=$plugin_path/${rname}.log
''' % (name, getServerDir(), getPluginDir())
''' % (mw_dir, name, getServerDir(), getPluginDir())
cmd += 'echo "★【`date +"%Y-%m-%d %H:%M:%S"`】 STSRT★" >> $logs_file' + "\n"
cmd += 'echo ">>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>" >> $logs_file' + "\n"
cmd += 'echo "python3 $script_path/index.py clean >> $logs_file 2>&1"' + "\n"
cmd += 'python3 $script_path/index.py clean >> $logs_file 2>&1' + "\n"
cmd += 'cd $mw_dir && python3 $script_path/index.py clean >> $logs_file 2>&1' + "\n"
cmd += 'echo "【`date +"%Y-%m-%d %H:%M:%S"`】 END★" >> $logs_file' + "\n"
cmd += 'echo "<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<" >> $logs_file' + "\n"
+5 -1
View File
@@ -817,6 +817,7 @@ function openPhpmyadmin(name,username,password){
layer.msg('当前为['+rdata.choose+']模式,若要使用请切换模式.',{icon:2,shade: [0.3, '#000']});
return;
}
var phpmyadmin_cfg = rdata;
data = syncPost('/plugins/run',{'name':'phpmyadmin','func':'get_home_page'});
var rdata = $.parseJSON(data.data);
@@ -824,7 +825,10 @@ function openPhpmyadmin(name,username,password){
layer.msg(rdata.msg,{icon:2,shade: [0.3, '#000']});
return;
}
$("#toPHPMyAdmin").attr('action',rdata.data);
var home_page = rdata.data;
home_page = home_page.replace("http://","http://"+phpmyadmin_cfg['username']+":"+phpmyadmin_cfg['password']+"@");
$("#toPHPMyAdmin").attr('action',home_page);
if($("#toPHPMyAdmin").attr('action').indexOf('phpmyadmin') == -1){
layer.msg('请先安装phpMyAdmin',{icon:2,shade: [0.3, '#000']});
+27 -4
View File
@@ -68,6 +68,26 @@ function myAsyncPost(method,args){
return syncPost('/plugins/run', {name:'mysql', func:method, args:_args});
}
function vaildPhpmyadmin(url,username,password){
console.log("Authorization: Basic " + btoa(username + ":" + password));
$.ajax({
type: "GET",
url: url,
dataType: 'json',
async: false,
username:username,
password:password,
headers: {
"Authorization": "Basic " + btoa(username + ":" + password)
},
data: 'vaild',
success: function (){
alert('Thanks for your comment!');
}
});
}
function runInfo(){
myPost('run_info','',function(data){
@@ -818,16 +838,19 @@ function openPhpmyadmin(name,username,password){
layer.msg('当前为[mariadb]模式,若要使用请切换模式.',{icon:2,shade: [0.3, '#000']});
return;
}
// console.log(data);
var phpmyadmin_cfg = rdata;
data = syncPost('/plugins/run',{'name':'phpmyadmin','func':'get_home_page'});
var rdata = $.parseJSON(data.data);
if (!rdata.status){
layer.msg(rdata.msg,{icon:2,shade: [0.3, '#000']});
return;
}
$("#toPHPMyAdmin").attr('action',rdata.data);
var home_page = rdata.data;
home_page = home_page.replace("http://","http://"+phpmyadmin_cfg['username']+":"+phpmyadmin_cfg['password']+"@")
$("#toPHPMyAdmin").attr('action',home_page);
if($("#toPHPMyAdmin").attr('action').indexOf('phpmyadmin') == -1){
layer.msg('请先安装phpMyAdmin',{icon:2,shade: [0.3, '#000']});
setTimeout(function(){ window.location.href = '/soft'; },3000);
@@ -836,7 +859,7 @@ function openPhpmyadmin(name,username,password){
//检查版本
data = syncPost('/plugins/run',{'name':'phpmyadmin','func':'version'});
bigVer = data.data.split('.')[0]
bigVer = data.data.split('.')[0];
if (bigVer>=4.5){
setTimeout(function(){
+2 -2
View File
@@ -17,7 +17,7 @@ sysName=`uname`
install_tmp=${rootPath}/tmp/mw_install.pl
mysqlDir=${serverPath}/source/mysql
VERSION="5.7.37"
VERSION="5.7.39"
Install_mysql()
@@ -68,7 +68,7 @@ Install_mysql()
fi
#检测文件是否损坏.
md5_mysql_ok=d0489fc3880248a58759c50bfb286dbb
md5_mysql_ok=db1b672fc257bd46356c7af26dd22801
if [ -f ${mysqlDir}/mysql-boost-${VERSION}.tar.gz ];then
md5_mysql=`md5sum ${mysqlDir}/mysql-boost-${VERSION}.tar.gz | awk '{print $1}'`
if [ "${md5_mysql_ok}" == "${md5_mysql}" ]; then
+2 -2
View File
@@ -1,6 +1,6 @@
lua_shared_dict limit 30m;
lua_shared_dict drop_ip 30m;
lua_shared_dict drop_sum 30m;
lua_shared_dict drop_ip 10m;
lua_shared_dict drop_sum 10m;
lua_package_path "{$WAF_PATH}/lua/?.lua;{$ROOT_PATH}/openresty/lualib/?.lua;;";
access_by_lua_file {$WAF_PATH}/lua/init.lua;
+1 -1
View File
@@ -232,7 +232,7 @@
<p onclick="wafGloabl();">全局配置</p>
<p onclick="wafSite();">站点配置</p>
<p onclick="wafHistory();">封锁历史</p>
<!-- <p onclick="wafLogs();">操作日志</p> -->
<p onclick="wafLogs();">操作日志</p>
</div>
<!-- lib-con -->
<div class="bt-w-con pd15">
+39 -5
View File
@@ -111,7 +111,7 @@ def initSiteInfo():
tmp['log'] = True
tmp['get'] = True
tmp['post'] = True
tmp['open'] = False
tmp['open'] = True
tmp['cc'] = config_contents['cc']
tmp['retry'] = config_contents['retry']
@@ -122,7 +122,22 @@ def initSiteInfo():
tmp['scan'] = config_contents['scan']
cdn_header = ['x-forwarded-for',
'x-real-ip', 'HTTP_CF_CONNECTING_IP']
'x-real-ip',
'x-forwarded',
'forwarded-for',
'forwarded',
'true-client-ip',
'client-ip',
'ali-cdn-real-ip',
'cdn-src-ip',
'cdn-real-ip',
'cf-connecting-ip',
'cf-connecting-ip',
'x-cluster-client-ip',
'wl-proxy-client-ip',
'proxy-client-ip',
'true-client-ip',
'HTTP_CF_CONNECTING_IP']
tmp['cdn_header'] = cdn_header
disable_upload_ext = ["php", "jsp"]
@@ -163,6 +178,7 @@ def initTotalInfo():
tmp['get'] = 0
tmp['post'] = 0
tmp['total'] = 0
tmp['url_ext'] = 0
_name = {}
_name[name] = tmp
total_contents['sites'] = _name
@@ -186,10 +202,12 @@ def status():
def contentReplace(content):
service_path = mw.getServerDir()
waf_path = getServerDir() + "/waf"
waf_root = getServerDir()
waf_path = waf_root + "/waf"
content = content.replace('{$ROOT_PATH}', mw.getRootDir())
content = content.replace('{$SERVER_PATH}', service_path)
content = content.replace('{$WAF_PATH}', waf_path)
content = content.replace('{$WAF_ROOT}', waf_root)
return content
@@ -201,6 +219,14 @@ def initDreplace():
cmd = 'cp -rf ' + sdir + ' ' + path
mw.execShell(cmd)
logs_path = path + '/logs'
if not os.path.exists(logs_path):
mw.execShell('mkdir -p ' + logs_path)
debug_log = path + '/debug.log'
if not os.path.exists(debug_log):
mw.execShell('echo "" > ' + debug_log)
config = path + '/waf/config.json'
content = mw.readFile(config)
content = json.loads(content)
@@ -214,6 +240,11 @@ def initDreplace():
content = contentReplace(content)
mw.writeFile(config, content)
config_common = path + "/waf/lua/common.lua"
content = mw.readFile(config_common)
content = contentReplace(content)
mw.writeFile(config_common, content)
waf_conf = mw.getServerDir() + "/openresty/nginx/conf/luawaf.conf"
waf_tpl = getPluginDir() + "/conf/luawaf.conf"
content = mw.readFile(waf_tpl)
@@ -224,6 +255,9 @@ def initDreplace():
initSiteInfo()
initTotalInfo()
if not mw.isAppleSystem():
mw.execShell("chown -R www:www " + path)
def start():
initDreplace()
@@ -800,7 +834,7 @@ def getLogsList():
return data[1]
data = []
path = mw.getLogsDir() + '/waf'
path = getServerDir() + '/logs'
if not os.path.exists(path):
return mw.returnJson(False, '还未生成!', [])
@@ -823,7 +857,7 @@ def getSafeLogs():
if not data[0]:
return data[1]
path = mw.getLogsDir() + '/waf'
path = getServerDir() + '/logs'
file = path + '/' + args['siteName'] + '_' + args['toDate'] + '.log'
if not os.path.exists(file):
return mw.returnJson(False, "文件不存在!")
+2 -2
View File
@@ -19,12 +19,12 @@ Install_of(){
echo '0.1' > $serverPath/op_waf/version.pl
echo 'install ok' > $install_tmp
cd ${rootPath} && python3 plugins/op_waf/index.py start
cd ${rootPath} && python3 ${rootPath}/plugins/op_waf/index.py start
}
Uninstall_of(){
cd ${rootPath} && python3 plugins/op_waf/index.py stop
cd ${rootPath} && python3 ${rootPath}/plugins/op_waf/index.py stop
rm -rf $serverPath/op_waf
}
+17 -17
View File
@@ -28,7 +28,7 @@ function setRequestCode(ruleName, statusCode){
title: "设置响应代码【" + ruleName + "】",
area: '300px',
shift: 5,
closeBtn: 2,
closeBtn: 1,
shadeClose: true,
content: '<div class="bt-form pd20 pb70">\
<div class="line">\
@@ -144,7 +144,7 @@ function setCcRule(cycle, limit, endtime, siteName, increase){
type: 1,
title: "设置CC规则",
area: '540px',
closeBtn: 2,
closeBtn: 1,
shadeClose: false,
content: '<form class="bt-form pd20 pb70">\
<div class="line">\
@@ -184,7 +184,7 @@ function setRetry(retry_cycle, retry, retry_time, siteName) {
type: 1,
title: "设置恶意容忍规则",
area: '500px',
closeBtn: 2,
closeBtn: 1,
shadeClose: false,
content: '<form class="bt-form pd20 pb70">\
<div class="line">\
@@ -339,7 +339,7 @@ function setObjConf(ruleName, type) {
type: 1,
title: "编辑规则【" + ruleName + "】",
area: ['700px', '530px'],
closeBtn: 2,
closeBtn: 1,
shadeClose: false,
content: '<div class="pd15">\
<div style="border-bottom:#ccc 1px solid;margin-bottom:10px;padding-bottom:10px">\
@@ -405,7 +405,7 @@ function scanRule() {
type: 1,
title: "常用扫描器过滤规则",
area: '650px',
closeBtn: 2,
closeBtn: 1,
shadeClose: false,
content: '<form class="bt-form pd20 pb70">\
<div class="line">\
@@ -571,7 +571,7 @@ function ipWhite(type) {
type: 1,
title: "管理IP白名单",
area: ['500px', '500px'],
closeBtn: 2,
closeBtn: 1,
shadeClose: false,
content: '<div class="pd15 ipv4_list">\
<div style="border-bottom:#ccc 1px solid;margin-bottom:10px;padding-bottom:10px">\
@@ -714,7 +714,7 @@ function ipBlack(type) {
type: 1,
title: "管理IP黑名单",
area: ['500px', '500px'],
closeBtn: 2,
closeBtn: 1,
shadeClose: false,
content: '<div class="tab_list"><div class="tab_block active">IPv4黑名单</div><div class="tab_block">IPv6黑名单</div></div>\
<div class="pd15 ipv4_block">\
@@ -824,12 +824,12 @@ function wafScreen(){
<div class="line"><span class="name">CC攻击</span><span class="val">'+rdata.rules.cc+'</span></div>\
<div class="line"><span class="name">恶意User-Agent</span><span class="val">'+rdata.rules.user_agent+'</span></div>\
<div class="line"><span class="name">Cookie渗透</span><span class="val">'+rdata.rules.cookie+'</span></div>\
<div class="line"><span class="name">恶意扫描</span><span class="val">0</span></div>\
<div class="line"><span class="name">恶意扫描</span><span class="val">'+rdata.rules.scan+'</span></div>\
<div class="line"><span class="name">恶意HEAD请求</span><span class="val">0</span></div>\
<div class="line"><span class="name">URI自定义拦截</span><span class="val">0</span></div>\
<div class="line"><span class="name">URI保护</span><span class="val">0</span></div>\
<div class="line"><span class="name">URI自定义拦截</span><span class="val">'+rdata.rules.args+'</span></div>\
<div class="line"><span class="name">URI保护</span><span class="val">'+rdata.rules.args+'</span></div>\
<div class="line"><span class="name">恶意文件上传</span><span class="val">0</span></div>\
<div class="line"><span class="name">禁止的扩展名</span><span class="val">0</span></div>\
<div class="line"><span class="name">禁止的扩展名</span><span class="val">'+rdata.rules.url_ext+'</span></div>\
<div class="line"><span class="name">禁止PHP脚本</span><span class="val">0</span></div>\
</div>';
@@ -975,7 +975,7 @@ function siteWafLog(siteName) {
type: 1,
title: "日志【" + siteName + "】",
area: ['880px', '500px'],
closeBtn: 2,
closeBtn: 1,
shadeClose: false,
content: '<div class="lib-box pd15 lib-box-log">\
<div class="lib-con-title" style="height:40px"><select id="selectLogDay" class="bt-input-text" onchange="siteLogCon(\''+ siteName + '\',this.options[this.options.selectedIndex].value,1)">' + selectLogDay + '</select></div>\
@@ -1071,7 +1071,7 @@ function siteLogCon(siteName, day, page) {
type: 1,
title: time + "详情",
area: '600px',
closeBtn: 2,
closeBtn: 1,
shadeClose: false,
content: '<div class="pd15 lib-box">\
<table class="table" style="border:#ddd 1px solid; margin-bottom:10px">\
@@ -1190,7 +1190,7 @@ function siteRuleAdmin(siteName, ruleName, type) {
type: 1,
title: "管理网站过滤规则【" + title + "】",
area: ['500px', '500px'],
closeBtn: 2,
closeBtn: 1,
shadeClose: false,
content: '<div class="pd15">\
<div style="border-bottom:#ccc 1px solid;margin-bottom:10px;padding-bottom:10px">\
@@ -1237,7 +1237,7 @@ function cdnHeader(siteName, type) {
type: 1,
title: "管理网站【" + siteName + "】CDN-Headers",
area: ['500px', '500px'],
closeBtn: 2,
closeBtn: 1,
shadeClose: false,
content: '<div class="pd15">\
<div style="border-bottom:#ccc 1px solid;margin-bottom:10px;padding-bottom:10px">\
@@ -1342,7 +1342,7 @@ function setSiteObjConf(siteName, ruleName, type) {
type: 1,
title: "编辑网站【" + siteName + "】规则【" + ruleName + "】",
area: ['700px', '530px'],
closeBtn: 2,
closeBtn: 1,
shadeClose: false,
content: '<div class="pd15">\
<div class="divtable">\
@@ -1394,7 +1394,7 @@ function siteWafConfig(siteName, type) {
type: 1,
title: "网站配置【" + siteName + "】",
area: ['700px', '500px'],
closeBtn: 2,
closeBtn: 1,
shadeClose: false,
content: '<div id="s_w_c"></div>'
});
-7
View File
@@ -1,7 +0,0 @@
# coding:utf-8
import sys
import io
import os
import time
import json
+161 -7
View File
@@ -6,14 +6,168 @@ import os
import time
import json
TEST_URL = "t1.cn"
import os
import sys
import time
import string
import json
import hashlib
import shlex
import datetime
import subprocess
import re
from random import Random
def run():
print('op lua run ok')
TEST_URL = "http://t1.cn/"
# TEST_URL = "https://www.zzzvps.com/"
def httpGet(url, timeout=10):
import urllib.request
try:
req = urllib.request.urlopen(url, timeout=timeout)
result = req.read().decode('utf-8')
return result
except Exception as e:
return str(e)
def httpGet__UA(url, ua, timeout=10):
import urllib.request
headers = {'user-agent': ua}
try:
req = urllib.request.Request(url, headers=headers)
response = urllib.request.urlopen(req)
result = response.read().decode('utf-8')
return result
except Exception as e:
return str(e)
def httpPost(url, data, timeout=10):
"""
发送POST请求
@url 被请求的URL地址(必需)
@data POST参数,可以是字符串或字典(必需)
@timeout 超时时间默认60秒
return string
"""
if sys.version_info[0] == 2:
try:
import urllib
import urllib2
import ssl
ssl._create_default_https_context = ssl._create_unverified_context
data = urllib.urlencode(data)
req = urllib2.Request(url, data)
response = urllib2.urlopen(req, timeout=timeout)
return response.read()
except Exception as ex:
return str(ex)
else:
try:
import urllib.request
import ssl
try:
ssl._create_default_https_context = ssl._create_unverified_context
except:
pass
data = urllib.parse.urlencode(data).encode('utf-8')
req = urllib.request.Request(url, data)
response = urllib.request.urlopen(req, timeout=timeout)
result = response.read()
if type(result) == bytes:
result = result.decode('utf-8')
return result
except Exception as ex:
return str(ex)
def test_Dir():
'''
目录保存
'''
url = TEST_URL + '?t=../etc/passwd'
print("args test start")
url_val = httpGet(url, 10)
# print(url_val)
print("args test end")
def test_UA():
'''
user-agent 过滤
'''
url = TEST_URL
print("user-agent test start")
url_val = httpGet__UA(url, 'ApacheBench')
print(url_val)
print("user-agent test end")
def test_POST():
'''
user-agent 过滤
'''
url = TEST_URL
print("POST test start")
url_val = httpPost(url, {'data': "substr($mmsss,0,1)"})
# url_val = httpPost(url, {'data': "123123"})
print(url_val)
print("POST test end")
def test_scan():
'''
目录保存
'''
url = TEST_URL + '/acunetix_wvs_security_test?t=1'
print("scan test start")
url_val = httpGet(url, 10)
print(url_val)
print("scan test end")
def test_CC():
'''
目录保存
'''
url = TEST_URL + 'ok.txt'
print("CC test start")
for x in range(122):
url_val = httpGet(url, 10)
print(url_val)
print("CC test end")
def test_url_ext():
'''
目录保存
'''
url = TEST_URL + 't.sql'
print("url_ext start")
url_val = httpGet(url, 10)
print(url_val)
print("url_ext end")
def test_start():
# test_Dir()
# test_UA()
# test_POST()
# test_scan()
# test_CC()
test_url_ext()
if __name__ == "__main__":
if len(sys.argv) > 1:
if action == "run":
run()
os.system('cd /Users/midoks/Desktop/mwdev/server/mdserver-web/plugins/op_waf && sh install.sh uninstall 0.1 && sh install.sh install 0.1')
os.system('cd /Users/midoks/Desktop/mwdev/server/mdserver-web/ && python3 plugins/openresty/index.py stop && python3 plugins/openresty/index.py start')
test_start()
+2
View File
@@ -2,6 +2,8 @@
PATH=/bin:/sbin:/usr/bin:/usr/sbin:/usr/local/bin:/usr/local/sbin:~/bin
export PATH
# yum -y install httpd-tools
# ab -c 1000 -n 1000000 http://xx.xx.xx/
python3 index.py
+1 -1
View File
@@ -1 +1 @@
{"reqfile_path": "{$WAF_PATH}/html", "retry": {"retry_time": 180, "is_open_global": 0, "retry": 6, "retry_cycle": 60}, "log": true, "scan": {"status": 444, "ps": "\u8fc7\u6ee4\u5e38\u89c1\u626b\u63cf\u6d4b\u8bd5\u5de5\u5177\u7684\u6e17\u900f\u6d4b\u8bd5", "open": true, "reqfile": ""}, "cc": {"status": 444, "ps": "\u8fc7\u8651CC\u653b\u51fb", "limit": 120, "endtime": 300, "open": true, "reqfile": "", "cycle": 60}, "get": {"status": 403, "ps": "\u8fc7\u6ee4uri\u3001uri\u53c2\u6570\u4e2d\u5e38\u89c1sql\u6ce8\u5165\u3001xss\u7b49\u653b\u51fb", "open": true, "reqfile": "get.html"}, "log_save": 30, "user-agent": {"status": 403, "ps": "\u901a\u5e38\u7528\u4e8e\u8fc7\u6ee4\u6d4f\u89c8\u5668\u3001\u8718\u86db\u53ca\u4e00\u4e9b\u81ea\u52a8\u626b\u63cf\u5668", "open": true, "reqfile": "user_agent.html"}, "other": {"status": 403, "ps": "\u5176\u5b83\u975e\u901a\u7528\u8fc7\u6ee4", "reqfile": "other.html"}, "cookie": {"status": 403, "ps": "\u8fc7\u6ee4\u5229\u7528Cookie\u53d1\u8d77\u7684\u6e17\u900f\u653b\u51fb", "open": true, "reqfile": "cookie.html"}, "logs_path": "/www/wwwlogs/btwaf", "post": {"status": 403, "ps": "\u8fc7\u6ee4POST\u53c2\u6570\u4e2d\u5e38\u89c1sql\u6ce8\u5165\u3001xss\u7b49\u653b\u51fb", "open": true, "reqfile": "post.html"}, "open": true}
{"reqfile_path": "{$WAF_PATH}/html", "retry": {"retry_time": 180, "is_open_global": 0, "retry": 6, "retry_cycle": 60}, "log": true, "scan": {"status": 444, "ps": "\u8fc7\u6ee4\u5e38\u89c1\u626b\u63cf\u6d4b\u8bd5\u5de5\u5177\u7684\u6e17\u900f\u6d4b\u8bd5", "open": true, "reqfile": ""}, "cc": {"status": 444, "ps": "\u8fc7\u8651CC\u653b\u51fb", "limit": 120, "endtime": 300, "open": true, "reqfile": "", "cycle": 60}, "get": {"status": 403, "ps": "\u8fc7\u6ee4uri\u3001uri\u53c2\u6570\u4e2d\u5e38\u89c1sql\u6ce8\u5165\u3001xss\u7b49\u653b\u51fb", "open": true, "reqfile": "get.html"}, "log_save": 30, "user-agent": {"status": 403, "ps": "\u901a\u5e38\u7528\u4e8e\u8fc7\u6ee4\u6d4f\u89c8\u5668\u3001\u8718\u86db\u53ca\u4e00\u4e9b\u81ea\u52a8\u626b\u63cf\u5668", "open": true, "reqfile": "user_agent.html"}, "other": {"status": 403, "ps": "\u5176\u5b83\u975e\u901a\u7528\u8fc7\u6ee4", "reqfile": "other.html"}, "cookie": {"status": 403, "ps": "\u8fc7\u6ee4\u5229\u7528Cookie\u53d1\u8d77\u7684\u6e17\u900f\u653b\u51fb", "open": true, "reqfile": "cookie.html"}, "logs_path": "/www/wwwlogs/waf", "post": {"status": 403, "ps": "\u8fc7\u6ee4POST\u53c2\u6570\u4e2d\u5e38\u89c1sql\u6ce8\u5165\u3001xss\u7b49\u653b\u51fb", "open": true, "reqfile": "post.html"}, "open": true}
+168 -30
View File
@@ -1,26 +1,89 @@
local setmetatable = setmetatable
local _M = { _VERSION = '0.01' }
local _M = { _VERSION = '0.02' }
local mt = { __index = _M }
local json = require "cjson"
local ngx_match = ngx.re.find
local debug_mode = false
function _M.new(self, cpath, rpath, logdir)
-- ngx.log(ngx.ERR,"read:"..cpath..",rpath:"..rpath)
local opt = {
cpath = cpath,
rpath = rpath,
logdir = logdir,
config = '',
site_config = '',
params = nil
local waf_root = "{$WAF_ROOT}"
local cpath = waf_root.."/waf/"
local logdir = waf_root.."/logs/"
local rpath = cpath.."/rule/"
function _M.new(self)
local self = {
waf_root = waf_root,
cpath = cpath,
rpath = rpath,
logdir = logdir,
config = '',
site_config = '',
server_name = '',
params = nil
}
local p = setmetatable(opt, mt)
return p
return setmetatable(self, mt)
end
function _M.setDebug(self, mode)
debug_mode = mode
end
-- 调试方式
function _M.D(self, msg)
if not debug_mode then return true end
local _msg = ''
if type(msg) == 'table' then
for key, val in pairs(msg) do
_msg = tostring( key)..':'.."\n"
end
elseif type(msg) == 'string' then
_msg = msg
elseif type(msg) == 'nil' then
_msg = 'nil'
else
_msg = msg
end
local fp = io.open(waf_root.."/debug.log", "ab")
if fp == nil then
return nil
end
local localtime = os.date("%Y-%m-%d %H:%M:%S")
if server_name then
fp:write(tostring(_msg) .. "\n")
else
fp:write(localtime..":"..tostring(_msg) .. "\n")
end
fp:flush()
fp:close()
return true
end
local function write_file_clear(filename, body)
fp = io.open(filename,'w')
if fp == nil then
return nil
end
fp:write(body)
fp:flush()
fp:close()
return true
end
function _M.setConfData( self, config, site_config )
self.config = config
self.site_config = site_config
@@ -94,6 +157,10 @@ function _M.compare_ip(self,ips)
end
function _M.to_json(self, msg)
return json.encode(msg)
end
function _M.return_message(self, status, msg)
ngx.header.content_type = "application/json;"
ngx.status = status
@@ -136,20 +203,15 @@ function _M.write_file(self, filename, body)
return true
end
function _M.write_file_clear(self, filename, body)
fp = io.open(filename,'w')
if fp == nil then
return nil
end
fp:write(body)
fp:flush()
fp:close()
return true
return write_file_clear(filename, body)
end
function _M.write_drop_ip(self, is_drop, drop_time)
local filename = self.cpath .. 'drop_ip.log'
local filename = self.logdir .. 'drop_ip.log'
local fp = io.open(filename,'ab')
local server_name = self.params["server_name"]
local ip = self.params["server_name"]
@@ -234,11 +296,21 @@ function _M.read_file(self, name)
end
function _M.read_file_table( self, name )
return self:select_rule(self:read_file('args'))
return self:select_rule(self:read_file(name))
end
local function timer_at_inc_log(premature)
local total_path = cpath .. 'total.json'
local tbody = ngx.shared.limit:get(total_path)
if not tbody then
return false
end
return write_file_clear(total_path,tbody)
end
function _M.inc_log(self, name, rule)
local server_name = self.params['server_name']
local total_path = self.cpath .. 'total.json'
local tbody = ngx.shared.limit:get(total_path)
@@ -246,7 +318,10 @@ function _M.inc_log(self, name, rule)
tbody = self:read_file_body(total_path)
if not tbody then return false end
end
local total = json.decode(tbody)
-- 开始计算
if not total['sites'] then total['sites'] = {} end
if not total['sites'][server_name] then total['sites'][server_name] = {} end
if not total['sites'][server_name][name] then total['sites'][server_name][name] = 0 end
@@ -256,13 +331,15 @@ function _M.inc_log(self, name, rule)
total['total'] = total['total'] + 1
total['sites'][server_name][name] = total['sites'][server_name][name] + 1
total['rules'][name] = total['rules'][name] + 1
local total_log = json.encode(total)
if not total_log then return false end
ngx.shared.limit:set(total_path,total_log)
if not ngx.shared.limit:get('mw_waf_timeout') then
self:write_file_clear(total_path,total_log)
ngx.shared.limit:set('mw_waf_timeout',1,5)
end
-- 异步执行
ngx.timer.at(1, timer_at_inc_log)
end
@@ -289,9 +366,66 @@ function _M.get_server_name(self)
end
-- function _M.get_sn(self)
-- retun string.gsub(self:get_server_name(),'_','.')
-- end
function _M.is_ngx_match_orgin(self,rule,match, sign)
if ngx_match(ngx.unescape_uri(match), rule,"isjo") then
error_rule = rule .. ' >> ' .. sign .. ':' .. match
return true
end
return false
end
function _M.ngx_match_string(self, rule, content,sign)
local t = self:is_ngx_match_orgin(rule, content, sign)
if t then
return true
end
return false
end
function _M.ngx_match_list(self, rules, content)
for i,rule in ipairs(rules)
do
if rule[1] == 1 then
local t = self:is_ngx_match_orgin(rule[2], content, rule[3])
if t then
return true
end
end
end
return false
end
function _M.is_ngx_match_ua(self, rules, content)
-- ngx.header.content_type = "text/html"
for i,rule in ipairs(rules)
do
-- 开启的规则,才匹配。
if rule[1] == 1 then
local t = self:is_ngx_match_orgin(rule[2], content, rule[3])
if t then
return true
end
end
end
return false
end
function _M.is_ngx_match_post(self, rules, content)
for i,rule in ipairs(rules)
do
-- 开启的规则,才匹配。
if rule[1] == 1 then
local t = self:is_ngx_match_orgin(rule[2],content, rule[3])
if t then
return true
end
end
end
return false
end
function _M.is_ngx_match(self, rules, sbody, rule_name)
@@ -341,6 +475,7 @@ end
function _M.write_log(self, name, rule)
local ip = self.params['ip']
local retry = self.config['retry']['retry']
local retry_time = self.config['retry']['retry_time']
@@ -352,6 +487,7 @@ function _M.write_log(self, name, rule)
else
ngx.shared.drop_ip:set(ip,1,retry_cycle)
end
if self.config['log'] ~= true or self:is_site_config('log') ~= true then return false end
local method = ngx.req.get_method()
if error_rule then
@@ -384,10 +520,13 @@ end
function _M.get_client_ip(self)
local client_ip = "unknown"
local server_name = self.params['server_name']
-- self:D("fff..."..client_ip..server_name)
if self.site_config[server_name] then
if self.site_config[server_name]['cdn'] then
for _,v in ipairs(self.site_config[server_name]['cdn_header'])
do
-- C:D("vv:"..v..tostring(request_header[v]))
if request_header[v] ~= nil and request_header[v] ~= "" then
local header_tmp = request_header[v]
if type(header_tmp) == "table" then header_tmp = header_tmp[1] end
@@ -408,7 +547,6 @@ end
function _M.is_site_config(self,cname)
local server_name = self.params["server_name"]
if self.site_config[server_name] ~= nil then
if cname == 'cc' then
return self.site_config[server_name][cname]['open']
+163 -168
View File
@@ -1,65 +1,55 @@
local cpath = "{$WAF_PATH}/"
local rpath = "{$WAF_PATH}/rule/"
local logdir = "{$ROOT_PATH}/wwwlogs/waf/"
local json = require "cjson"
local ngx_match = ngx.re.find
local _C = require "common"
local C = _C:new(cpath, rpath, logdir)
local __C = require "common"
local C = __C:new()
config = C:read_file_body_decode(cpath .. 'config.json')
local site_config = C:read_file_body_decode(cpath .. 'site.json')
local waf_root = "{$WAF_ROOT}"
config = C:read_file_body_decode(waf_root.."/waf/"..'config.json')
local site_config = C:read_file_body_decode(waf_root.."/waf/"..'site.json')
C:setConfData(config, site_config)
-- D func
local function D(msg)
local _msg = ''
if type(msg) == 'table' then
for key, val in pairs(msg) do
_msg = key..':'..val.."\n"
end
elseif type(msg) == 'string' then
_msg = msg
elseif type(msg) == 'nil' then
_msg = 'nil'
else
_msg = msg
end
if not debug_mode then return true end
local fp = io.open(cpath..'debug.log', 'ab')
if fp == nil then
return nil
end
local localtime = os.date("%Y-%m-%d %H:%M:%S")
if server_name then
fp:write(tostring(_msg) .. "\n")
else
fp:write(localtime..":"..tostring(_msg) .. "\n")
end
fp:flush()
fp:close()
return true
end
local get_html = C:read_file_body(config["reqfile_path"] .. '/' .. config["get"]["reqfile"])
local post_html = C:read_file_body(config["reqfile_path"] .. '/' .. config["post"]["reqfile"])
local user_agent_html = C:read_file_body(config["reqfile_path"] .. '/' .. config["user-agent"]["reqfile"])
local args_rules = C:read_file_table('args')
local ip_white_rules = C:read_file('ip_white')
local ip_black_rules = C:read_file('ip_black')
local scan_black_rules = C:read_file('scan_black')
local user_agent_rules = C:read_file('user_agent')
local post_rules = C:read_file('post')
local cookie_rules = C:read_file('cookie')
local server_name = string.gsub(C:get_server_name(),'_','.')
-- C:D("sss:"..C:get_server_name())
function initParams()
local data = {}
data['ip'] = C:get_client_ip()
data['ipn'] = C:arrip(data['ip'])
data['server_name'] = server_name
-- data['ip'] = C:get_client_ip()
-- data['ipn'] = C:arrip(data['ip'])
data['request_header'] = ngx.req.get_headers()
data['uri'] = ngx.unescape_uri(ngx.var.uri)
data['server_name'] = string.gsub(C:get_server_name(),'_','.')
data['uri_request_args'] = ngx.req.get_uri_args()
data['method'] = ngx.req.get_method()
data['request_uri'] = ngx.var.request_uri
data['cookie'] = ngx.var.http_cookie
return data
end
local params = initParams()
C:setParams(params)
C:setDebug(true)
local server_name = params["server_name"]
params['ip'] = C:get_client_ip()
params['ipn'] = C:arrip(params['ip'])
C:D(server_name)
function get_return_state(rstate,rmsg)
result = {}
@@ -102,20 +92,20 @@ function save_ip_on(data)
end
end
function remove_btwaf_drop_ip()
function remove_waf_drop_ip()
if not uri_request_args['ip'] or not C:is_ipaddr(uri_request_args['ip']) then return get_return_state(true,'格式错误') end
if ngx.shared.btwaf:get(cpath2 .. 'stop_ip') then
ret=ngx.shared.btwaf:get(cpath2 .. 'stop_ip')
ip_data=json.decode(ret)
result=is_chekc_table(ip_data,uri_request_args['ip'])
result = is_chekc_table(ip_data,uri_request_args['ip'])
os.execute("sleep " .. 0.6)
ret2=ngx.shared.btwaf:get(cpath2 .. 'stop_ip')
ip_data2=json.decode(ret2)
ip_data2 = json.decode(ret2)
if result == 3 then
for k,v in pairs(ip_data2)
do
if uri_request_args['ip'] == v['ip'] then
v['time']=0
v['time'] = 0
end
end
end
@@ -125,7 +115,7 @@ function remove_btwaf_drop_ip()
return get_return_state(true,uri_request_args['ip'] .. '已解封')
end
function clean_btwaf_drop_ip()
function clean_waf_drop_ip()
if ngx.shared.btwaf:get(cpath2 .. 'stop_ip') then
ret2=ngx.shared.btwaf:get(cpath2 .. 'stop_ip')
ip_data2=json.decode(ret2)
@@ -155,15 +145,7 @@ function min_route()
end
end
local get_html = C:read_file_body(config["reqfile_path"] .. '/' .. config["get"]["reqfile"])
local post_html = C:read_file_body(config["reqfile_path"] .. '/' .. config["post"]["reqfile"])
local user_agent_html = C:read_file_body(config["reqfile_path"] .. '/' .. config["user-agent"]["reqfile"])
local args_rules = C:read_file_table('args')
local ip_white_rules = C:read_file('ip_white')
local ip_black_rules = C:read_file('ip_black')
local scan_black_rules = C:read_file('scan_black')
function waf_args()
function waf_get_args()
if not config['get']['open'] or not C:is_site_config('get') then return false end
if C:is_ngx_match(args_rules, params['uri_request_args'],'args') then
C:write_log('args','regular')
@@ -196,8 +178,20 @@ function waf_ip_black()
end
function waf_user_agent()
-- user_agent 过滤
if not config['user-agent']['open'] or not C:is_site_config('user-agent') then return false end
if C:is_ngx_match_ua(user_agent_rules,params['request_header']['user-agent']) then
C:write_log('user_agent','regular')
C:return_html(config['user-agent']['status'],user_agent_html)
return true
end
return false
end
function waf_drop()
local count,_ = ngx.shared.drop_ip:get(ip)
local count , _ = ngx.shared.drop_ip:get(ip)
if not count then return false end
if count > config['retry'] then
ngx.exit(config['cc']['status'])
@@ -206,28 +200,33 @@ function waf_drop()
return false
end
function waf_user_agent()
if not config['user-agent']['open'] or not C:is_site_config('user-agent') then return false end
if C:is_ngx_match(user_agent_rules,params['request_header']['user-agent'],'user_agent') then
C:write_log('user_agent','regular')
C:return_html(config['user-agent']['status'],user_agent_html)
return true
end
return false
end
function cc()
function waf_cc()
local ip = params['ip']
local ip_lock = ngx.shared.drop_ip:get(ip)
if ip_lock then
if ip_lock > 0 then
ngx.exit(config['cc']['status'])
return true
end
end
if not config['cc']['open'] or not C:is_site_config('cc') then return false end
local request_uri = params['request_uri']
local endtime = config['cc']['endtime']
if not config['cc']['open'] or not site_cc then return false end
local token = ngx.md5(ip .. '_' .. request_uri)
local count,_ = ngx.shared.limit:get(token)
local count = ngx.shared.limit:get(token)
local limit = config['cc']['limit']
local cycle = config['cc']['cycle']
if count then
if count > limit then
local safe_count,_ = ngx.shared.drop_sum:get(ip)
if count > limit then
local safe_count, _ = ngx.shared.drop_sum:get(ip)
if not safe_count then
ngx.shared.drop_sum:set(ip,1,86400)
safe_count = 1
@@ -236,23 +235,22 @@ function cc()
end
local lock_time = (endtime * safe_count)
if lock_time > 86400 then lock_time = 86400 end
ngx.shared.drop_ip:set(ip,retry+1,lock_time)
-- lock_time = 10
ngx.shared.drop_ip:set(ip,1,lock_time)
C:write_log('cc',cycle..'秒内累计超过'..limit..'次请求,封锁' .. lock_time .. '秒')
C:write_drop_ip('cc',lock_time)
if not server_name then
insert_ip_list(ip,lock_time,os.time(),'1111')
else
insert_ip_list(ip,lock_time,os.time(),server_name)
end
ngx.exit(config['cc']['status'])
return true
else
ngx.shared.limit:incr(token,1)
end
else
ngx.shared.limit:set(token,1,cycle)
ngx.shared.drop_sum:set(ip,1,86400)
ngx.shared.limit:set(token, 1, cycle)
end
return false
end
--强制验证是否使用正常浏览器访问网站
@@ -287,20 +285,25 @@ end
function waf_scan_black()
-- 扫描软件禁止
if not config['scan']['open'] or not C:is_site_config('scan') then return false end
if C:is_ngx_match(scan_black_rules['cookie'],params["request_header"]["cookie"],false) then
C:write_log('scan','regular')
ngx.exit(config['scan']['status'])
return true
end
if C:is_ngx_match(scan_black_rules['args'],params["request_uri"],false) then
if not params["cookie"] then
if C:ngx_match_string(scan_black_rules['cookie'], tostring(params["cookie"]),'scan') then
C:write_log('scan','regular')
ngx.exit(config['scan']['status'])
return true
end
end
if C:ngx_match_string(scan_black_rules['args'], params["request_uri"], 'scan') then
C:write_log('scan','regular')
ngx.exit(config['scan']['status'])
return true
end
for key,value in pairs(params["request_header"])
do
if C:is_ngx_match(scan_black_rules['header'], key, false) then
if C:ngx_match_string(scan_black_rules['header'], key, 'scan') then
C:write_log('scan','regular')
ngx.exit(config['scan']['status'])
return true
@@ -309,20 +312,9 @@ function waf_scan_black()
return false
end
function waf_post_referer()
if params['method'] ~= "POST" then return false end
if C:is_ngx_match(referer_local, params['request_header']['Referer'],'post') then
C:write_log('post_referer','regular')
C:return_html(config['post']['status'],post_html)
return true
end
return false
end
function waf_post()
if not config['post']['open'] or not C:is_site_config('post') then return false end
if params['method'] ~= "POST" then return false end
if waf_post_referer() then return true end
content_length = tonumber(params["request_header"]['content-length'])
max_len = 640 * 1020000
if content_length > max_len then return false end
@@ -333,7 +325,19 @@ function waf_post()
return false
end
if C:is_ngx_match(post_rules,request_args,'post') then
for key, val in pairs(request_args) do
if type(val) == "table" then
if type(val[1]) == "boolean" then
return false
end
data = table.concat(val, ", ")
else
data = val
end
end
if C:is_ngx_match_post(post_rules,data) then
C:write_log('post','regular')
C:return_html(config['post']['status'],post_html)
return true
@@ -366,10 +370,11 @@ function post_data_chekc()
end
if not list_list then return false end
aaa=nil
aaa = nil
for k,v in pairs(request_args)
do
aaa=v
aaa = v
end
if not aaa then return false end
@@ -381,7 +386,7 @@ function post_data_chekc()
if not data_len then return false end
if arrlen(data_len) ==0 then return false end
if C:is_ngx_match(post_rules,data_len,'post') then
if C:is_ngx_match_post(post_rules , data_len) then
C:write_log('post','regular')
C:return_html(config['post']['status'],post_html)
return true
@@ -406,7 +411,7 @@ end
function post_X_Forwarded()
if not config['post']['open'] or not C:is_site_config('post') then return false end
if params['method'] ~= "POST" then return false end
if C:is_ngx_match(post_rules,params["request_header"]['X-forwarded-For'],'post') then
if C:is_ngx_match_post(post_rules,params["request_header"]['X-forwarded-For']) then
C:write_log('post','regular')
C:return_html(config['post']['status'],post_html)
return true
@@ -415,39 +420,39 @@ function post_X_Forwarded()
end
function php_path()
if site_config[server_name] == nil then return false end
for _,rule in ipairs(site_config[server_name]['disable_php_path'])
do
if ngx_match(uri,rule .. "/?.*\\.php$","isjo") then
C:write_log('php_path','regular')
C:return_html(config['other']['status'],other_html)
return C:return_message(200,uri)
end
end
return false
end
-- function php_path()
-- if site_config[server_name] == nil then return false end
-- for _,rule in ipairs(site_config[server_name]['disable_php_path'])
-- do
-- if C:ngx_match_string(params['uri'],rule .. "/?.*\\.php$","isjo") then
-- C:write_log('php_path','regular')
-- C:return_html(config['other']['status'],other_html)
-- return C:return_message(200,uri)
-- end
-- end
-- return false
-- end
function url_path()
if site_config[server_name] == nil then return false end
for _,rule in ipairs(site_config[server_name]['disable_path'])
do
if ngx_match(uri,rule,"isjo") then
C:write_log('path','regular')
C:return_html(config['other']['status'],other_html)
return true
end
end
return false
end
-- function url_path()
-- if site_config[server_name] == nil then return false end
-- for _,rule in ipairs(site_config[server_name]['disable_path'])
-- do
-- if ngx_match(uri,rule,"isjo") then
-- C:write_log('path','regular')
-- C:return_html(config['other']['status'],other_html)
-- return true
-- end
-- end
-- return false
-- end
function url_ext()
if site_config[server_name] == nil then return false end
for _,rule in ipairs(site_config[server_name]['disable_ext'])
do
if ngx_match(uri,"\\."..rule.."$","isjo") then
if C:ngx_match_string("\\."..rule.."$", params['uri'],'url_ext') then
C:write_log('url_ext','regular')
C:return_html(config['other']['status'],other_html)
C:return_html(config['other']['status'], other_html)
return true
end
end
@@ -555,7 +560,7 @@ function waf_cookie()
if not params["request_header"]['cookie'] then return false end
if type(params["request_header"]['cookie']) ~= "string" then return false end
request_cookie = string.lower(params["request_header"]['cookie'])
if C:is_ngx_match(cookie_rules,request_cookie,'cookie') then
if C:ngx_match_list(cookie_rules,request_cookie,'cookie') then
C:write_log('cookie','regular')
C:return_html(config['cookie']['status'],cookie_html)
return true
@@ -563,55 +568,45 @@ function waf_cookie()
return false
end
function waf_referer()
if params["method"] ~= "GET" then return false end
if not config['get']['open'] or not C:is_site_config('get') then return false end
if C:is_ngx_match(referer_local,params["request_header"]['Referer'],'args') then
C:write_log('get_referer','regular')
C:return_html(config['get']['status'], get_html)
return true
end
return false
end
function waf()
min_route()
-- white ip
if waf_ip_white() then return true end
waf_ip_black()
-- black ip
if waf_ip_black() then return true end
waf_drop()
waf_user_agent()
-- cc setting
if waf_drop() then return true end
if waf_cc() then return true end
waf_url()
-- ua check
if waf_user_agent() then return true end
if waf_url() then return true end
if params["method"] == "GET" then
waf_referer()
waf_cookie()
end
-- cookie检查
if waf_cookie() then return true end
-- args参数拦截
if waf_get_args() then return true end
if params["method"] == "POST" then
waf_referer()
waf_cookie()
end
-- 扫描软件禁止
if waf_scan_black() then return true end
waf_args()
waf_scan_black()
waf_post()
post_data_chekc()
local server_name = params["server_name"]
if site_config[server_name] then
X_Forwarded()
post_X_Forwarded()
php_path()
url_path()
url_ext()
url_rule_ex()
url_tell()
post_data()
if waf_post() then return true end
if post_data_chekc() then return true end
if site_config[server_name]['open'] then
if X_Forwarded() then return true end
if post_X_Forwarded() then return true end
-- url_path()
if url_ext() then return true end
-- url_rule_ex()
-- url_tell()
-- post_data()
end
end
+1 -1
View File
@@ -1 +1 @@
[[1, "(HTTrack|Apache-HttpClient|harvest|audit|dirbuster|pangolin|nmap|sqln|hydra|Parser|libwww|BBBike|sqlmap|w3af|owasp|Nikto|fimap|havij|zmeu|BabyKrokodil|netsparker|httperf| SF/)", "\u5173\u952e\u8bcd\u8fc7\u6ee41", 0]]
[[1,"(HTTrack|Apache-HttpClient|harvest|audit|dirbuster|pangolin|nmap|sqln|hydra|Parser|libwww|BBBike|sqlmap|w3af|owasp|Nikto|fimap|havij|zmeu|BabyKrokodil|netsparker|httperf| SF/)","关键词过滤1",0],[1,"(ApacheBench)","AB测试",0]]
+1 -1
View File
@@ -1 +1 @@
{"rules":{"user_agent":0,"cookie":0,"post":0,"args":0,"url":0,"cc":0},"sites":{},"total":0}
{"rules":{"url_ext":0,"user_agent":0,"scan":0,"cookie":0,"post":0,"args":0,"url":0,"cc":0},"sites":{},"total":0}
+39
View File
@@ -1,3 +1,41 @@
<style type="text/css">
.bt-w-main{
height: 600px;
}
.session_clear_list {
border:1px solid #ececec;
margin-bottom: 15px;
width: 270px;
}
.session_clear_list .line {
padding: 0;
border-bottom: 1px solid #ececec;
width: 270px;
}
.session_clear_list .line:last-child {
border-bottom: 0px;
}
.session_clear_list .line span{
width: auto;
height: 35px;
line-height: 35px;
text-align: left;
padding: 0 5px;
}
.session_clear_list .line span:first-child {
width: 170px;
border-right: 1px solid #ececec;
background: #f7f7f7;
float: left;
}
</style>
<div class="bt-form">
<div class='plugin_version'></div>
<div class="bt-w-main">
@@ -13,6 +51,7 @@
<p onclick="disableFunc($('.plugin_version').attr('version'));">禁用函数</p>
<p onclick="getFpmConfig($('.plugin_version').attr('version'));">性能调整</p>
<p onclick="getFpmStatus($('.plugin_version').attr('version'));">负载状况</p>
<p onclick="getSessionConfig($('.plugin_version').attr('version'));" title="session管理">会话管理</p>
<p onclick="pluginLogs('php-apt',$('.plugin_version').attr('version'),'fpm_log');">FPM日志</p>
<p onclick="pluginLogs('php-apt',$('.plugin_version').attr('version'),'fpm_slow_log');">慢日志</p>
<p onclick="getPhpinfo($('.plugin_version').attr('version'));">PHPIFNO</p>
+182
View File
@@ -490,6 +490,180 @@ def getFpmStatus(version):
return mw.returnJson(True, "OK", data)
def getSessionConf(version):
filename = getConf(version)
if not os.path.exists(filename):
return mw.returnJson(False, '指定PHP版本不存在!')
phpini = mw.readFile(filename)
rep = r'session.save_handler\s*=\s*([0-9A-Za-z_& ~]+)(\s*;?|\r?\n)'
save_handler = re.search(rep, phpini)
if save_handler:
save_handler = save_handler.group(1)
else:
save_handler = "files"
reppath = r'\nsession.save_path\s*=\s*"tcp\:\/\/([\d\.]+):(\d+).*\r?\n'
passrep = r'\nsession.save_path\s*=\s*"tcp://[\w\.\?\:]+=(.*)"\r?\n'
memcached = r'\nsession.save_path\s*=\s*"([\d\.]+):(\d+)"'
save_path = re.search(reppath, phpini)
if not save_path:
save_path = re.search(memcached, phpini)
passwd = re.search(passrep, phpini)
port = ""
if passwd:
passwd = passwd.group(1)
else:
passwd = ""
if save_path:
port = save_path.group(2)
save_path = save_path.group(1)
else:
save_path = ""
data = {"save_handler": save_handler, "save_path": save_path,
"passwd": passwd, "port": port}
return mw.returnJson(True, 'ok', data)
def setSessionConf(version):
args = getArgs()
ip = args['ip']
port = args['port']
passwd = args['passwd']
save_handler = args['save_handler']
if save_handler != "file":
iprep = r"(2(5[0-5]{1}|[0-4]\d{1})|[0-1]?\d{1,2})\.(2(5[0-5]{1}|[0-4]\d{1})|[0-1]?\d{1,2})\.(2(5[0-5]{1}|[0-4]\d{1})|[0-1]?\d{1,2})\.(2(5[0-5]{1}|[0-4]\d{1})|[0-1]?\d{1,2})"
if not re.search(iprep, ip):
return mw.returnJson(False, '请输入正确的IP地址')
try:
port = int(port)
if port >= 65535 or port < 1:
return mw.returnJson(False, '请输入正确的端口号')
except:
return mw.returnJson(False, '请输入正确的端口号')
prep = r"[\~\`\/\=]"
if re.search(prep, passwd):
return mw.returnJson(False, '请不要输入以下特殊字符 " ~ ` / = "')
filename = getConf(version)
if not os.path.exists(filename):
return mw.returnJson(False, '指定PHP版本不存在!')
phpini = mw.readFile(filename)
session_tmp = getServerDir() + "/tmp/session"
rep = r'session.save_handler\s*=\s*(.+)\r?\n'
val = r'session.save_handler = ' + save_handler + '\n'
phpini = re.sub(rep, val, phpini)
content = mw.execShell(
'cat /etc/php/' + version + '/fpm/conf.d/*' + " | grep -v '^;' |tr -s '\n'")
content = content[0]
if save_handler == "memcached":
if not re.search("memcached.so", phpini):
return mw.returnJson(False, '请先安装%s扩展' % save_handler)
rep = r'\nsession.save_path\s*=\s*(.+)\r?\n'
val = r'\nsession.save_path = "%s:%s" \n' % (ip, port)
if re.search(rep, phpini):
phpini = re.sub(rep, val, phpini)
else:
phpini = re.sub('\n;session.save_path = "' + "/var/lib/php/sessions" + '"',
'\n;session.save_path = "' + "/var/lib/php/sessions" + '"' + val, phpini)
if save_handler == "memcache":
if not content.find('memcache') > -1:
return mw.returnJson(False, '请先安装%s扩展' % save_handler)
rep = r'\nsession.save_path\s*=\s*(.+)\r?\n'
val = r'\nsession.save_path = "%s:%s" \n' % (ip, port)
if re.search(rep, phpini):
phpini = re.sub(rep, val, phpini)
else:
phpini = re.sub('\n;session.save_path = "' + "/var/lib/php/sessions" + '"',
'\n;session.save_path = "' + "/var/lib/php/sessions" + '"' + val, phpini)
if save_handler == "redis":
if not content.find('redis') > -1:
return mw.returnJson(False, '请先安装%s扩展' % save_handler)
if passwd:
passwd = "?auth=" + passwd
else:
passwd = ""
rep = r'\nsession.save_path\s*=\s*(.+)\r?\n'
val = r'\nsession.save_path = "tcp://%s:%s%s"\n' % (ip, port, passwd)
res = re.search(rep, phpini)
if res:
phpini = re.sub(rep, val, phpini)
else:
phpini = re.sub('\n;session.save_path = "' + "/var/lib/php/sessions" + '"',
'\n;session.save_path = "' + "/var/lib/php/sessions" + '"' + val, phpini)
if save_handler == "file":
rep = r'\nsession.save_path\s*=\s*(.+)\r?\n'
val = r'\nsession.save_path = "' + session_tmp + '"\n'
if re.search(rep, phpini):
phpini = re.sub(rep, val, phpini)
else:
phpini = re.sub('\n;session.save_path = "' + "/var/lib/php/sessions" + '"',
'\n;session.save_path = "' + "/var/lib/php/sessions" + '"' + val, phpini)
mw.writeFile(filename, phpini)
reload(version)
return mw.returnJson(True, '设置成功!')
def getSessionCount_Origin(version):
session_tmp = getServerDir() + "/tmp/session"
d = ["/tmp", "/var/lib/php/sessions", session_tmp]
count = 0
for i in d:
if not os.path.exists(i):
mw.execShell('mkdir -p %s' % i)
list = os.listdir(i)
for l in list:
if os.path.isdir(i + "/" + l):
l1 = os.listdir(i + "/" + l)
for ll in l1:
if "sess_" in ll:
count += 1
continue
if "sess_" in l:
count += 1
s = "find /tmp -mtime +1 |grep 'sess_' | wc -l"
old_file = int(mw.execShell(s)[0].split("\n")[0])
s = "find " + session_tmp + " -mtime +1 |grep 'sess_'|wc -l"
old_file += int(mw.execShell(s)[0].split("\n")[0])
return {"total": count, "oldfile": old_file}
def getSessionCount(version):
data = getSessionCount_Origin(version)
return mw.returnJson(True, 'ok!', data)
def cleanSessionOld(version):
s = "find /tmp -mtime +1 |grep 'sess_'|xargs rm -f"
mw.execShell(s)
session_tmp = getServerDir() + "/tmp/session"
s = "find " + session_tmp + " -mtime +1 |grep 'sess_' |xargs rm -f"
mw.execShell(s)
old_file_conf = getSessionCount_Origin(version)["oldfile"]
if old_file_conf == 0:
return mw.returnJson(True, '清理成功')
else:
return mw.returnJson(True, '清理失败')
def getDisableFunc(version):
filename = getConf(version)
if not os.path.exists(filename):
@@ -688,6 +862,14 @@ if __name__ == "__main__":
print(setFpmConfig(version))
elif func == 'get_fpm_status':
print(getFpmStatus(version))
elif func == 'get_session_conf':
print(getSessionConf(version))
elif func == 'set_session_conf':
print(setSessionConf(version))
elif func == 'get_session_count':
print(getSessionCount(version))
elif func == 'clean_session_old':
print(cleanSessionOld(version))
elif func == 'get_disable_func':
print(getDisableFunc(version))
elif func == 'set_disable_func':
+145
View File
@@ -368,6 +368,151 @@ function disableFunc(version) {
$(".soft-man-con").html(con);
});
}
function getSessionConfig(version){
phpPost('get_session_conf', version, '', function(ret_data){
var rdata = $.parseJSON(ret_data.data);
if(!rdata.status){
layer.msg(rdata.msg, { icon: rdata.status ? 1 : 2 });
return;
}
var rdata = rdata.data;
var cacheList = "<option value='file' " + (rdata.save_handler == "file" ? 'selected' : '') + ">file</option>" +
"<option value='redis' " + (rdata.save_handler == "redis" ? 'selected' : '') + ">redis</option>" +
"<option value='memcache' " + (rdata.save_handler == "memcache" ? 'selected' : '') + ">memcache</option>" +
"<option value='memcached' " + (rdata.save_handler == "memcached" ? 'selected' : '') + ">memcached</option>";
var info = rdata.save_path.split(":");
var con = "<div class='conf_p'>" +
"<p class='line'><span class='span_tit'>存储模式:</span><select class='bt-input-text' name='save_handler' style='width:200px;'>" + cacheList + "</select></p>" +
"<p class='line'><span class='span_tit'>IP地址:</span><input class='bt-input-text' type='text' name='ip' style='width:200px;' value='"+ info[0] +"' /></p>" +
"<p class='line'><span class='span_tit'>端口:</span><input class='bt-input-text' type='text' name='port' style='width:200px;' value='"+rdata.port+"' /></p>" +
"<p class='line'><span class='span_tit'>密码:</span><input class='bt-input-text' type='text' name='passwd' style='width:200px;' value='"+rdata.passwd+"' /></p>" +
"<p class='line'><div class='mtb15' style='margin-left:100px;'><button class='btn btn-success btn-sm' onclick='setSessionConfig(\"" + version + "\",1)'>保存</button></div></p>" +
"</div>\
<ul class='help-info-text c7'>\
<li>若你的站点并发比较高,使用Redis,Memcache能有效提升PHP并发能力</li>\
<li>若调整Session模式后,网站访问异常,请切换回原来的模式</li>\
<li>切换Session模式会使在线的用户会话丢失,请在流量小的时候切换</li>\
</ul>\
<div id='session_clear' class='session_clear' style='border-top: #ccc 1px dashed;padding-top: 15px;margin-top: 15px;'>\
</div>\
</div>";
$(".soft-man-con").html(con);
if (rdata.save_handler == 'file'){
$('input[name="ip"]').attr('disabled','disabled');
$('input[name="port"]').attr('disabled','disabled');
$('input[name="passwd"]').attr('placeholder','如果没有密码留空');
$('input[name="passwd"]').attr('disabled','disabled');
}
// change event
$("select[name='save_handler']").change(function() {
var type = $(this).val();
var passwd = $('input[name="passwd"]').val();
if (passwd == ""){
$('input[name="passwd"]').attr('placeholder','如果没有密码留空');
}
var ip = $('input[name="ip"]').val();
if (ip == ""){
$('input[name="ip"]').val('127.0.0.1');
}
switch (type) {
case 'redis':
var port = $('input[name="port"]').val();
if (port == ""){
$('input[name="port"]').val('6379');
}
$('input[name="ip"]').removeAttr('disabled');
$('input[name="port"]').removeAttr('disabled');
$('input[name="passwd"]').removeAttr('disabled');
break;
case 'file':
$('input[name="ip"]').val("").attr('disabled','disabled');
$('input[name="port"]').val("").attr('disabled','disabled');
$('input[name="passwd"]').val("").attr('disabled','disabled');
break;
case 'memcache':
var port = $('input[name="port"]').val();
if (port == ""){
$('input[name="port"]').val('11211');
}
$('input[name="ip"]').removeAttr('disabled');
$('input[name="port"]').removeAttr('disabled');
$('input[name="passwd"]').removeAttr('disabled');
break;
case 'memcached':
var port = $('input[name="port"]').val();
if (port == ""){
$('input[name="port"]').val('11211');
}
$('input[name="ip"]').removeAttr('disabled');
$('input[name="port"]').removeAttr('disabled');
$('input[name="passwd"]').removeAttr('disabled');
break;
}
});
//load session stats
phpPost('get_session_count', version, '', function(ret_data){
var rdata = $.parseJSON(ret_data.data);
if(!rdata.status){
layer.msg(rdata.msg, { icon: rdata.status ? 1 : 2 });
return;
}
var rdata = rdata.data;
var html_var = "<div class='clear_title' style='padding-bottom:15px;'>清理Session文件</div>\
<div class='clear_conter'>\
<div class='session_clear_list'>\
<div class='line'><span>总Session文件数量</span><span>"+rdata.total+"</span></div>\
<div class='line'><span>可清理的Session文件数量</span><span>"+rdata.oldfile+"</span></div>\
</div>\
<button id='clean_func' class='btn btn-success btn-sm clear_session_file'>清理session文件</button>";
$("#session_clear").html(html_var);
$('#clean_func').click(function(){
phpPost('clean_session_old', version, '', function(ret_data){
var rdata = $.parseJSON(ret_data.data);
showMsg(rdata.msg,function(){
getSessionConfig(version);
},{ icon: rdata.status ? 1 : 2 });
});
});
});
});
}
function setSessionConfig(version){
var ip = $('input[name="ip"]').val();
var port = $('input[name="port"]').val();
var passwd = $('input[name="passwd"]').val();
var save_handler = $("select[name='save_handler']").val();
var data = {
ip:ip,
port:port,
passwd:passwd,
save_handler:save_handler,
};
phpPost('set_session_conf', version, data, function(ret_data){
var rdata = $.parseJSON(ret_data.data);
layer.msg(rdata.msg, { icon: rdata.status ? 1 : 2 });
});
}
//设置禁用函数
function setDisableFunc(version, act, fs) {
var fsArr = fs.split(',');
+38
View File
@@ -1,3 +1,40 @@
<style type="text/css">
.bt-w-main{
height: 600px;
}
.session_clear_list {
border:1px solid #ececec;
margin-bottom: 15px;
width: 270px;
}
.session_clear_list .line {
padding: 0;
border-bottom: 1px solid #ececec;
width: 270px;
}
.session_clear_list .line:last-child {
border-bottom: 0px;
}
.session_clear_list .line span{
width: auto;
height: 35px;
line-height: 35px;
text-align: left;
padding: 0 5px;
}
.session_clear_list .line span:first-child {
width: 170px;
border-right: 1px solid #ececec;
background: #f7f7f7;
float: left;
}
</style>
<div class="bt-form">
<div class='plugin_version'></div>
<div class="bt-w-main">
@@ -13,6 +50,7 @@
<p onclick="disableFunc($('.plugin_version').attr('version'));">禁用函数</p>
<p onclick="getFpmConfig($('.plugin_version').attr('version'));">性能调整</p>
<p onclick="getFpmStatus($('.plugin_version').attr('version'));">负载状况</p>
<p onclick="getSessionConfig($('.plugin_version').attr('version'));" title="session管理">会话管理</p>
<p onclick="pluginLogs('php-yum',$('.plugin_version').attr('version'),'fpm_log');">FPM日志</p>
<p onclick="pluginLogs('php-yum',$('.plugin_version').attr('version'),'fpm_slow_log');">慢日志</p>
<p onclick="getPhpinfo($('.plugin_version').attr('version'));">PHPIFNO</p>
+182
View File
@@ -492,6 +492,180 @@ def getFpmStatus(version):
return mw.returnJson(True, "OK", data)
def getSessionConf(version):
filename = getConf(version)
if not os.path.exists(filename):
return mw.returnJson(False, '指定PHP版本不存在!')
phpini = mw.readFile(filename)
rep = r'session.save_handler\s*=\s*([0-9A-Za-z_& ~]+)(\s*;?|\r?\n)'
save_handler = re.search(rep, phpini)
if save_handler:
save_handler = save_handler.group(1)
else:
save_handler = "files"
reppath = r'\nsession.save_path\s*=\s*"tcp\:\/\/([\d\.]+):(\d+).*\r?\n'
passrep = r'\nsession.save_path\s*=\s*"tcp://[\w\.\?\:]+=(.*)"\r?\n'
memcached = r'\nsession.save_path\s*=\s*"([\d\.]+):(\d+)"'
save_path = re.search(reppath, phpini)
if not save_path:
save_path = re.search(memcached, phpini)
passwd = re.search(passrep, phpini)
port = ""
if passwd:
passwd = passwd.group(1)
else:
passwd = ""
if save_path:
port = save_path.group(2)
save_path = save_path.group(1)
else:
save_path = ""
data = {"save_handler": save_handler, "save_path": save_path,
"passwd": passwd, "port": port}
return mw.returnJson(True, 'ok', data)
def setSessionConf(version):
args = getArgs()
ip = args['ip']
port = args['port']
passwd = args['passwd']
save_handler = args['save_handler']
if save_handler != "file":
iprep = r"(2(5[0-5]{1}|[0-4]\d{1})|[0-1]?\d{1,2})\.(2(5[0-5]{1}|[0-4]\d{1})|[0-1]?\d{1,2})\.(2(5[0-5]{1}|[0-4]\d{1})|[0-1]?\d{1,2})\.(2(5[0-5]{1}|[0-4]\d{1})|[0-1]?\d{1,2})"
if not re.search(iprep, ip):
return mw.returnJson(False, '请输入正确的IP地址')
try:
port = int(port)
if port >= 65535 or port < 1:
return mw.returnJson(False, '请输入正确的端口号')
except:
return mw.returnJson(False, '请输入正确的端口号')
prep = r"[\~\`\/\=]"
if re.search(prep, passwd):
return mw.returnJson(False, '请不要输入以下特殊字符 " ~ ` / = "')
filename = getConf(version)
if not os.path.exists(filename):
return mw.returnJson(False, '指定PHP版本不存在!')
phpini = mw.readFile(filename)
session_tmp = getServerDir() + "/tmp/session"
rep = r'session.save_handler\s*=\s*(.+)\r?\n'
val = r'session.save_handler = ' + save_handler + '\n'
phpini = re.sub(rep, val, phpini)
content = mw.execShell('cat /etc/opt/remi/php' +
version + "/php.d/* | grep -v '^;' |tr -s '\n'")
content = content[0]
if save_handler == "memcached":
if not content.find("memcached.so") > -1:
return mw.returnJson(False, '请先安装%s扩展' % save_handler)
rep = r'\nsession.save_path\s*=\s*(.+)\r?\n'
val = r'\nsession.save_path = "%s:%s" \n' % (ip, port)
if re.search(rep, phpini):
phpini = re.sub(rep, val, phpini)
else:
phpini = re.sub('\n;session.save_path = "/tmp"',
'\n;session.save_path = "/tmp"' + val, phpini)
if save_handler == "memcache":
if not content.find("memcache.so") > -1:
return mw.returnJson(False, '请先安装%s扩展' % save_handler)
rep = r'\nsession.save_path\s*=\s*(.+)\r?\n'
val = r'\nsession.save_path = "%s:%s" \n' % (ip, port)
if re.search(rep, phpini):
phpini = re.sub(rep, val, phpini)
else:
phpini = re.sub('\n;session.save_path = "/tmp"',
'\n;session.save_path = "/tmp"' + val, phpini)
if save_handler == "redis":
if not content.find("redis.so") > -1:
return mw.returnJson(False, '请先安装%s扩展' % save_handler)
if passwd:
passwd = "?auth=" + passwd
else:
passwd = ""
rep = r'\nsession.save_path\s*=\s*(.+)\r?\n'
val = r'\nsession.save_path = "tcp://%s:%s%s"\n' % (ip, port, passwd)
res = re.search(rep, phpini)
if res:
phpini = re.sub(rep, val, phpini)
else:
phpini = re.sub('\n;session.save_path = "/tmp"',
'\n;session.save_path = "/tmp"' + val, phpini)
if save_handler == "file":
rep = r'\nsession.save_path\s*=\s*(.+)\r?\n'
val = r'\nsession.save_path = "' + session_tmp + '"\n'
if re.search(rep, phpini):
phpini = re.sub(rep, val, phpini)
else:
phpini = re.sub('\n;session.save_path = "/tmp"',
'\n;session.save_path = "/tmp"' + val, phpini)
mw.writeFile(filename, phpini)
restart(version)
return mw.returnJson(True, '设置成功!')
def getSessionCount_Origin(version):
session_tmp = getServerDir() + "/tmp/session"
d = ["/tmp", session_tmp]
count = 0
for i in d:
if not os.path.exists(i):
mw.execShell('mkdir -p %s' % i)
list = os.listdir(i)
for l in list:
if os.path.isdir(i + "/" + l):
l1 = os.listdir(i + "/" + l)
for ll in l1:
if "sess_" in ll:
count += 1
continue
if "sess_" in l:
count += 1
s = "find /tmp -mtime +1 |grep 'sess_' | wc -l"
old_file = int(mw.execShell(s)[0].split("\n")[0])
s = "find " + session_tmp + " -mtime +1 |grep 'sess_'|wc -l"
old_file += int(mw.execShell(s)[0].split("\n")[0])
return {"total": count, "oldfile": old_file}
def getSessionCount(version):
data = getSessionCount_Origin(version)
return mw.returnJson(True, 'ok!', data)
def cleanSessionOld(version):
s = "find /tmp -mtime +1 |grep 'sess_'|xargs rm -f"
mw.execShell(s)
session_tmp = getServerDir() + "/tmp/session"
s = "find " + session_tmp + " -mtime +1 |grep 'sess_' |xargs rm -f"
mw.execShell(s)
old_file_conf = getSessionCount_Origin(version)["oldfile"]
if old_file_conf == 0:
return mw.returnJson(True, '清理成功')
else:
return mw.returnJson(True, '清理失败')
def getDisableFunc(version):
filename = getConf(version)
if not os.path.exists(filename):
@@ -689,6 +863,14 @@ if __name__ == "__main__":
print(setFpmConfig(version))
elif func == 'get_fpm_status':
print(getFpmStatus(version))
elif func == 'get_session_conf':
print(getSessionConf(version))
elif func == 'set_session_conf':
print(setSessionConf(version))
elif func == 'get_session_count':
print(getSessionCount(version))
elif func == 'clean_session_old':
print(cleanSessionOld(version))
elif func == 'get_disable_func':
print(getDisableFunc(version))
elif func == 'set_disable_func':
+141
View File
@@ -340,6 +340,147 @@ function getFpmStatus(version){
});
}
function getSessionConfig(version){
phpPost('get_session_conf', version, '', function(ret_data){
var rdata = $.parseJSON(ret_data.data);
if(!rdata.status){
layer.msg(rdata.msg, { icon: rdata.status ? 1 : 2 });
return;
}
var rdata = rdata.data;
var cacheList = "<option value='file' " + (rdata.save_handler == "file" ? 'selected' : '') + ">file</option>" +
"<option value='redis' " + (rdata.save_handler == "redis" ? 'selected' : '') + ">redis</option>" +
"<option value='memcache' " + (rdata.save_handler == "memcache" ? 'selected' : '') + ">memcache</option>" +
"<option value='memcached' " + (rdata.save_handler == "memcached" ? 'selected' : '') + ">memcached</option>";
var info = rdata.save_path.split(":");
var con = "<div class='conf_p'>" +
"<p class='line'><span class='span_tit'>存储模式:</span><select class='bt-input-text' name='save_handler' style='width:200px;'>" + cacheList + "</select></p>" +
"<p class='line'><span class='span_tit'>IP地址:</span><input class='bt-input-text' type='text' name='ip' style='width:200px;' value='"+ info[0] +"' /></p>" +
"<p class='line'><span class='span_tit'>端口:</span><input class='bt-input-text' type='text' name='port' style='width:200px;' value='"+rdata.port+"' /></p>" +
"<p class='line'><span class='span_tit'>密码:</span><input class='bt-input-text' type='text' name='passwd' style='width:200px;' value='"+rdata.passwd+"' /></p>" +
"<p class='line'><div class='mtb15' style='margin-left:100px;'><button class='btn btn-success btn-sm' onclick='setSessionConfig(\"" + version + "\",1)'>保存</button></div></p>" +
"</div>\
<ul class='help-info-text c7'>\
<li>若你的站点并发比较高,使用Redis,Memcache能有效提升PHP并发能力</li>\
<li>若调整Session模式后,网站访问异常,请切换回原来的模式</li>\
<li>切换Session模式会使在线的用户会话丢失,请在流量小的时候切换</li>\
</ul>\
<div id='session_clear' class='session_clear' style='border-top: #ccc 1px dashed;padding-top: 15px;margin-top: 15px;'>\
</div>\
</div>";
$(".soft-man-con").html(con);
if (rdata.save_handler == 'file'){
$('input[name="ip"]').attr('disabled','disabled');
$('input[name="port"]').attr('disabled','disabled');
$('input[name="passwd"]').attr('placeholder','如果没有密码留空');
$('input[name="passwd"]').attr('disabled','disabled');
}
// change event
$("select[name='save_handler']").change(function() {
var type = $(this).val();
var passwd = $('input[name="passwd"]').val();
if (passwd == ""){
$('input[name="passwd"]').attr('placeholder','如果没有密码留空');
}
var ip = $('input[name="ip"]').val();
if (ip == ""){
$('input[name="ip"]').val('127.0.0.1');
}
switch (type) {
case 'redis':
var port = $('input[name="port"]').val();
if (port == ""){
$('input[name="port"]').val('6379');
}
$('input[name="ip"]').removeAttr('disabled');
$('input[name="port"]').removeAttr('disabled');
$('input[name="passwd"]').removeAttr('disabled');
break;
case 'file':
$('input[name="ip"]').val("").attr('disabled','disabled');
$('input[name="port"]').val("").attr('disabled','disabled');
$('input[name="passwd"]').val("").attr('disabled','disabled');
break;
case 'memcache':
var port = $('input[name="port"]').val();
if (port == ""){
$('input[name="port"]').val('11211');
}
$('input[name="ip"]').removeAttr('disabled');
$('input[name="port"]').removeAttr('disabled');
$('input[name="passwd"]').removeAttr('disabled');
break;
case 'memcached':
var port = $('input[name="port"]').val();
if (port == ""){
$('input[name="port"]').val('11211');
}
$('input[name="ip"]').removeAttr('disabled');
$('input[name="port"]').removeAttr('disabled');
$('input[name="passwd"]').removeAttr('disabled');
break;
}
});
//load session stats
phpPost('get_session_count', version, '', function(ret_data){
var rdata = $.parseJSON(ret_data.data);
if(!rdata.status){
layer.msg(rdata.msg, { icon: rdata.status ? 1 : 2 });
return;
}
var rdata = rdata.data;
var html_var = "<div class='clear_title' style='padding-bottom:15px;'>清理Session文件</div>\
<div class='clear_conter'>\
<div class='session_clear_list'>\
<div class='line'><span>总Session文件数量</span><span>"+rdata.total+"</span></div>\
<div class='line'><span>可清理的Session文件数量</span><span>"+rdata.oldfile+"</span></div>\
</div>\
<button id='clean_func' class='btn btn-success btn-sm clear_session_file'>清理session文件</button>";
$("#session_clear").html(html_var);
$('#clean_func').click(function(){
phpPost('clean_session_old', version, '', function(ret_data){
var rdata = $.parseJSON(ret_data.data);
showMsg(rdata.msg,function(){
getSessionConfig(version);
},{ icon: rdata.status ? 1 : 2 });
});
});
});
});
}
function setSessionConfig(version){
var ip = $('input[name="ip"]').val();
var port = $('input[name="port"]').val();
var passwd = $('input[name="passwd"]').val();
var save_handler = $("select[name='save_handler']").val();
var data = {
ip:ip,
port:port,
passwd:passwd,
save_handler:save_handler,
};
phpPost('set_session_conf', version, data, function(ret_data){
var rdata = $.parseJSON(ret_data.data);
layer.msg(rdata.msg, { icon: rdata.status ? 1 : 2 });
});
}
//禁用函数
function disableFunc(version) {
phpPost('get_disable_func', version,'',function(data){
+40 -1
View File
@@ -1,6 +1,43 @@
<style type="text/css">
.bt-w-main{
height: 642px;
}
.session_clear_list {
border:1px solid #ececec;
margin-bottom: 15px;
width: 270px;
}
.session_clear_list .line {
padding: 0;
border-bottom: 1px solid #ececec;
width: 270px;
}
.session_clear_list .line:last-child {
border-bottom: 0px;
}
.session_clear_list .line span{
width: auto;
height: 35px;
line-height: 35px;
text-align: left;
padding: 0 5px;
}
.session_clear_list .line span:first-child {
width: 170px;
border-right: 1px solid #ececec;
background: #f7f7f7;
float: left;
}
</style>
<div class="bt-form">
<div class='plugin_version'></div>
<div class="bt-w-main">
<div class="bt-w-main" >
<div class="bt-w-menu">
<p class="bgw" onclick="pluginService('php', $('.plugin_version').attr('version'));">服务</p>
<p onclick="pluginInitD('php', $('.plugin_version').attr('version'));">自启动</p>
@@ -13,6 +50,7 @@
<p onclick="disableFunc($('.plugin_version').attr('version'));">禁用函数</p>
<p onclick="getFpmConfig($('.plugin_version').attr('version'));">性能调整</p>
<p onclick="getFpmStatus($('.plugin_version').attr('version'));">负载状况</p>
<p onclick="getSessionConfig($('.plugin_version').attr('version'));" title="session管理">会话管理</p>
<p onclick="pluginLogs('php',$('.plugin_version').attr('version'),'fpm_log');">FPM日志</p>
<p onclick="pluginLogs('php',$('.plugin_version').attr('version'),'fpm_slow_log');">慢日志</p>
<p onclick="getPhpinfo($('.plugin_version').attr('version'));">PHPIFNO</p>
@@ -24,6 +62,7 @@
</div>
</div>
<script type="text/javascript">
$.getScript( "/plugins/file?name=php&f=js/php.js", function(){
pluginService('php', $('.plugin_version').attr('version'));
+179
View File
@@ -632,6 +632,176 @@ def getFpmStatus(version):
return mw.returnJson(True, "OK", data)
def getSessionConf(version):
filename = getConf(version)
if not os.path.exists(filename):
return mw.returnJson(False, '指定PHP版本不存在!')
phpini = mw.readFile(filename)
rep = r'session.save_handler\s*=\s*([0-9A-Za-z_& ~]+)(\s*;?|\r?\n)'
save_handler = re.search(rep, phpini)
if save_handler:
save_handler = save_handler.group(1)
else:
save_handler = "files"
reppath = r'\nsession.save_path\s*=\s*"tcp\:\/\/([\d\.]+):(\d+).*\r?\n'
passrep = r'\nsession.save_path\s*=\s*"tcp://[\w\.\?\:]+=(.*)"\r?\n'
memcached = r'\nsession.save_path\s*=\s*"([\d\.]+):(\d+)"'
save_path = re.search(reppath, phpini)
if not save_path:
save_path = re.search(memcached, phpini)
passwd = re.search(passrep, phpini)
port = ""
if passwd:
passwd = passwd.group(1)
else:
passwd = ""
if save_path:
port = save_path.group(2)
save_path = save_path.group(1)
else:
save_path = ""
data = {"save_handler": save_handler, "save_path": save_path,
"passwd": passwd, "port": port}
return mw.returnJson(True, 'ok', data)
def setSessionConf(version):
args = getArgs()
ip = args['ip']
port = args['port']
passwd = args['passwd']
save_handler = args['save_handler']
if save_handler != "file":
iprep = r"(2(5[0-5]{1}|[0-4]\d{1})|[0-1]?\d{1,2})\.(2(5[0-5]{1}|[0-4]\d{1})|[0-1]?\d{1,2})\.(2(5[0-5]{1}|[0-4]\d{1})|[0-1]?\d{1,2})\.(2(5[0-5]{1}|[0-4]\d{1})|[0-1]?\d{1,2})"
if not re.search(iprep, ip):
return mw.returnJson(False, '请输入正确的IP地址')
try:
port = int(port)
if port >= 65535 or port < 1:
return mw.returnJson(False, '请输入正确的端口号')
except:
return mw.returnJson(False, '请输入正确的端口号')
prep = r"[\~\`\/\=]"
if re.search(prep, passwd):
return mw.returnJson(False, '请不要输入以下特殊字符 " ~ ` / = "')
filename = getConf(version)
if not os.path.exists(filename):
return mw.returnJson(False, '指定PHP版本不存在!')
phpini = mw.readFile(filename)
session_tmp = getServerDir() + "/tmp/session"
rep = r'session.save_handler\s*=\s*(.+)\r?\n'
val = r'session.save_handler = ' + save_handler + '\n'
phpini = re.sub(rep, val, phpini)
if save_handler == "memcached":
if not re.search("memcached.so", phpini):
return mw.returnJson(False, '请先安装%s扩展' % save_handler)
rep = r'\nsession.save_path\s*=\s*(.+)\r?\n'
val = r'\nsession.save_path = "%s:%s" \n' % (ip, port)
if re.search(rep, phpini):
phpini = re.sub(rep, val, phpini)
else:
phpini = re.sub('\n;session.save_path = "' + session_tmp + '"',
'\n;session.save_path = "' + session_tmp + '"' + val, phpini)
if save_handler == "memcache":
if not re.search("memcache.so", phpini):
return mw.returnJson(False, '请先安装%s扩展' % save_handler)
rep = r'\nsession.save_path\s*=\s*(.+)\r?\n'
val = r'\nsession.save_path = "%s:%s" \n' % (ip, port)
if re.search(rep, phpini):
phpini = re.sub(rep, val, phpini)
else:
phpini = re.sub('\n;session.save_path = "' + session_tmp + '"',
'\n;session.save_path = "' + session_tmp + '"' + val, phpini)
if save_handler == "redis":
if not re.search("redis.so", phpini):
return mw.returnJson(False, '请先安装%s扩展' % save_handler)
if passwd:
passwd = "?auth=" + passwd
else:
passwd = ""
rep = r'\nsession.save_path\s*=\s*(.+)\r?\n'
val = r'\nsession.save_path = "tcp://%s:%s%s"\n' % (ip, port, passwd)
res = re.search(rep, phpini)
if res:
phpini = re.sub(rep, val, phpini)
else:
phpini = re.sub('\n;session.save_path = "' + session_tmp + '"',
'\n;session.save_path = "' + session_tmp + '"' + val, phpini)
if save_handler == "file":
rep = r'\nsession.save_path\s*=\s*(.+)\r?\n'
val = r'\nsession.save_path = "' + session_tmp + '"\n'
if re.search(rep, phpini):
phpini = re.sub(rep, val, phpini)
else:
phpini = re.sub('\n;session.save_path = "' + session_tmp + '"',
'\n;session.save_path = "' + session_tmp + '"' + val, phpini)
mw.writeFile(filename, phpini)
reload(version)
return mw.returnJson(True, '设置成功!')
def getSessionCount_Origin(version):
session_tmp = getServerDir() + "/tmp/session"
d = [session_tmp]
count = 0
for i in d:
if not os.path.exists(i):
mw.execShell('mkdir -p %s' % i)
list = os.listdir(i)
for l in list:
if os.path.isdir(i + "/" + l):
l1 = os.listdir(i + "/" + l)
for ll in l1:
if "sess_" in ll:
count += 1
continue
if "sess_" in l:
count += 1
s = "find /tmp -mtime +1 |grep 'sess_' | wc -l"
old_file = int(mw.execShell(s)[0].split("\n")[0])
s = "find " + session_tmp + " -mtime +1 |grep 'sess_'|wc -l"
old_file += int(mw.execShell(s)[0].split("\n")[0])
return {"total": count, "oldfile": old_file}
def getSessionCount(version):
data = getSessionCount_Origin(version)
return mw.returnJson(True, 'ok!', data)
def cleanSessionOld(version):
s = "find /tmp -mtime +1 |grep 'sess_'|xargs rm -f"
mw.execShell(s)
session_tmp = getServerDir() + "/tmp/session"
s = "find " + session_tmp + " -mtime +1 |grep 'sess_' |xargs rm -f"
mw.execShell(s)
old_file_conf = getSessionCount_Origin(version)["oldfile"]
if old_file_conf == 0:
return mw.returnJson(True, '清理成功')
else:
return mw.returnJson(True, '清理失败')
def getDisableFunc(version):
filename = getConf(version)
if not os.path.exists(filename):
@@ -794,6 +964,7 @@ def installPreInspection(version):
return 'fedora[{}]不可安装'.format(sysId)
return 'ok'
if __name__ == "__main__":
if len(sys.argv) < 3:
@@ -847,6 +1018,14 @@ if __name__ == "__main__":
print(setFpmConfig(version))
elif func == 'get_fpm_status':
print(getFpmStatus(version))
elif func == 'get_session_conf':
print(getSessionConf(version))
elif func == 'set_session_conf':
print(setSessionConf(version))
elif func == 'get_session_count':
print(getSessionCount(version))
elif func == 'clean_session_old':
print(cleanSessionOld(version))
elif func == 'get_disable_func':
print(getDisableFunc(version))
elif func == 'set_disable_func':
+146 -14
View File
@@ -1,14 +1,3 @@
function str2Obj(str){
var data = {};
kv = str.split('&');
for(i in kv){
v = kv[i].split('=');
data[v[0]] = v[1];
}
return data;
}
function phpPost(method, version, args,callback){
var loadT = layer.msg('正在获取...', { icon: 16, time: 0, shade: 0.3 });
@@ -18,7 +7,7 @@ function phpPost(method, version, args,callback){
req_data['version'] = version;
if (typeof(args) == 'string'){
req_data['args'] = JSON.stringify(str2Obj(args));
req_data['args'] = JSON.stringify(toArrayObject(args));
} else {
req_data['args'] = JSON.stringify(args);
}
@@ -46,7 +35,7 @@ function phpPostCallbak(method, version, args,callback){
args['version'] = version;
if (typeof(args) == 'string'){
req_data['args'] = JSON.stringify(str2Obj(args));
req_data['args'] = JSON.stringify(toArrayObject(args));
} else {
req_data['args'] = JSON.stringify(args);
}
@@ -194,7 +183,7 @@ function getFpmConfig(version){
"<option value='3' " + (rdata.max_children == 100 ? 'selected' : '') + ">100并发</option>" +
"<option value='4' " + (rdata.max_children == 200 ? 'selected' : '') + ">200并发</option>" +
"<option value='5' " + (rdata.max_children == 300 ? 'selected' : '') + ">300并发</option>" +
"<option value='6' " + (rdata.max_children == 500 ? 'selected' : '') + ">500并发</option>"
"<option value='6' " + (rdata.max_children == 500 ? 'selected' : '') + ">500并发</option>";
var pms = [{ 'name': 'static', 'title': '静态' }, { 'name': 'dynamic', 'title': '动态' }];
var pmList = '';
for (var i = 0; i < pms.length; i++) {
@@ -340,6 +329,149 @@ function getFpmStatus(version){
});
}
function getSessionConfig(version){
phpPost('get_session_conf', version, '', function(ret_data){
var rdata = $.parseJSON(ret_data.data);
if(!rdata.status){
layer.msg(rdata.msg, { icon: rdata.status ? 1 : 2 });
return;
}
var rdata = rdata.data;
var cacheList = "<option value='file' " + (rdata.save_handler == "file" ? 'selected' : '') + ">file</option>" +
"<option value='redis' " + (rdata.save_handler == "redis" ? 'selected' : '') + ">redis</option>" +
"<option value='memcache' " + (rdata.save_handler == "memcache" ? 'selected' : '') + ">memcache</option>" +
"<option value='memcached' " + (rdata.save_handler == "memcached" ? 'selected' : '') + ">memcached</option>";
var info = rdata.save_path.split(":");
var con = "<div class='conf_p'>" +
"<p class='line'><span class='span_tit'>存储模式:</span><select class='bt-input-text' name='save_handler' style='width:200px;'>" + cacheList + "</select></p>" +
"<p class='line'><span class='span_tit'>IP地址:</span><input class='bt-input-text' type='text' name='ip' style='width:200px;' value='"+ info[0] +"' /></p>" +
"<p class='line'><span class='span_tit'>端口:</span><input class='bt-input-text' type='text' name='port' style='width:200px;' value='"+rdata.port+"' /></p>" +
"<p class='line'><span class='span_tit'>密码:</span><input class='bt-input-text' type='text' name='passwd' style='width:200px;' value='"+rdata.passwd+"' /></p>" +
"<p class='line'><div class='mtb15' style='margin-left:100px;'><button class='btn btn-success btn-sm' onclick='setSessionConfig(\"" + version + "\",1)'>保存</button></div></p>" +
"</div>\
<ul class='help-info-text c7'>\
<li>若你的站点并发比较高,使用Redis,Memcache能有效提升PHP并发能力</li>\
<li>若调整Session模式后,网站访问异常,请切换回原来的模式</li>\
<li>切换Session模式会使在线的用户会话丢失,请在流量小的时候切换</li>\
</ul>\
<div id='session_clear' class='session_clear' style='border-top: #ccc 1px dashed;padding-top: 15px;margin-top: 15px;'>\
</div>\
</div>";
$(".soft-man-con").html(con);
if (rdata.save_handler == 'file'){
$('input[name="ip"]').attr('disabled','disabled');
$('input[name="port"]').attr('disabled','disabled');
$('input[name="passwd"]').attr('placeholder','如果没有密码留空');
$('input[name="passwd"]').attr('disabled','disabled');
}
// change event
$("select[name='save_handler']").change(function() {
var type = $(this).val();
var passwd = $('input[name="passwd"]').val();
if (passwd == ""){
$('input[name="passwd"]').attr('placeholder','如果没有密码留空');
}
var ip = $('input[name="ip"]').val();
if (ip == ""){
$('input[name="ip"]').val('127.0.0.1');
}
switch (type) {
case 'redis':
var port = $('input[name="port"]').val();
if (port == ""){
$('input[name="port"]').val('6379');
}
$('input[name="ip"]').removeAttr('disabled');
$('input[name="port"]').removeAttr('disabled');
$('input[name="passwd"]').removeAttr('disabled');
break;
case 'file':
$('input[name="ip"]').val("").attr('disabled','disabled');
$('input[name="port"]').val("").attr('disabled','disabled');
$('input[name="passwd"]').val("").attr('disabled','disabled');
break;
case 'memcache':
var port = $('input[name="port"]').val();
if (port == ""){
$('input[name="port"]').val('11211');
}
$('input[name="ip"]').removeAttr('disabled');
$('input[name="port"]').removeAttr('disabled');
$('input[name="passwd"]').removeAttr('disabled');
break;
case 'memcached':
var port = $('input[name="port"]').val();
if (port == ""){
$('input[name="port"]').val('11211');
}
$('input[name="ip"]').removeAttr('disabled');
$('input[name="port"]').removeAttr('disabled');
$('input[name="passwd"]').removeAttr('disabled');
break;
}
});
//load session stats
phpPost('get_session_count', version, '', function(ret_data){
var rdata = $.parseJSON(ret_data.data);
if(!rdata.status){
layer.msg(rdata.msg, { icon: rdata.status ? 1 : 2 });
return;
}
var rdata = rdata.data;
var html_var = "<div class='clear_title' style='padding-bottom:15px;'>清理Session文件</div>\
<div class='clear_conter'>\
<div class='session_clear_list'>\
<div class='line'><span>总Session文件数量</span><span>"+rdata.total+"</span></div>\
<div class='line'><span>可清理的Session文件数量</span><span>"+rdata.oldfile+"</span></div>\
</div>\
<button id='clean_func' class='btn btn-success btn-sm clear_session_file'>清理session文件</button>";
$("#session_clear").html(html_var);
$('#clean_func').click(function(){
phpPost('clean_session_old', version, '', function(ret_data){
var rdata = $.parseJSON(ret_data.data);
showMsg(rdata.msg,function(){
getSessionConfig(version);
},{ icon: rdata.status ? 1 : 2 });
});
});
});
});
}
function setSessionConfig(version){
var ip = $('input[name="ip"]').val();
var port = $('input[name="port"]').val();
var passwd = $('input[name="passwd"]').val();
var save_handler = $("select[name='save_handler']").val();
var data = {
ip:ip,
port:port,
passwd:passwd,
save_handler:save_handler,
};
phpPost('set_session_conf', version, data, function(ret_data){
var rdata = $.parseJSON(ret_data.data);
layer.msg(rdata.msg, { icon: rdata.status ? 1 : 2 });
});
}
//禁用函数
function disableFunc(version) {
phpPost('get_disable_func', version,'',function(data){
+1 -1
View File
@@ -1,7 +1,7 @@
daemonize yes
pidfile {$SERVER_PATH}/redis/redis_6379.pid
bind 127.0.0.1
bind 0.0.0.0
port 6379
requirepass admin
+13 -3
View File
@@ -125,7 +125,7 @@ def redisOp(method):
data = mw.execShell('systemctl ' + method + ' redis')
if data[1] == '':
return 'ok'
return 'fail'
return data[1]
data = mw.execShell(file + ' start')
if data[1] == '':
@@ -154,6 +154,10 @@ def reload():
def runInfo():
s = status()
if s == 'stop':
return mw.returnJson(False, '未启动')
requirepass = ""
conf = getServerDir() + '/redis.conf'
@@ -163,9 +167,15 @@ def runInfo():
if tmp:
requirepass = tmp.groups()[1]
cmd = getServerDir() + "/bin/redis-cli info"
default_ip = '0.0.0.0'
findDebian = mw.execShell('cat /etc/issue |grep Debian')
if findDebian[0] != '':
default_ip = mw.getLocalIp()
cmd = getServerDir() + "/bin/redis-cli -h " + default_ip + " info"
if requirepass != "":
cmd = getServerDir() + '/bin/redis-cli -a "' + requirepass + '" info'
cmd = getServerDir() + '/bin/redis-cli -h ' + default_ip + \
' -a "' + requirepass + '" info'
data = mw.execShell(cmd)[0]
res = [
-1
View File
@@ -5,7 +5,6 @@ After=network.target
[Service]
Type=forking
ExecStart={$SERVER_PATH}/redis/bin/redis-server {$SERVER_PATH}/redis/redis.conf
ExecStop={$SERVER_PATH}/redis/redis-cli shutdown
ExecReload=/bin/kill -USR2 $MAINPID
Restart=on-failure
+5
View File
@@ -69,6 +69,11 @@ function redisStatus(version) {
redisPost('run_info',version, {},function(data){
var rdata = $.parseJSON(data.data);
// if (!rdata.status){
// layer.msg(data.msg,{icon:0,time:2000,shade: [0.3, '#000']});
// return;
// }
hit = (parseInt(rdata.keyspace_hits) / (parseInt(rdata.keyspace_hits) + parseInt(rdata.keyspace_misses)) * 100).toFixed(2);
var con = '<div class="divtable">\
<table class="table table-hover table-bordered" style="width: 490px;">\
+8 -7
View File
@@ -117,7 +117,7 @@ def swapOp(method):
return 'ok'
return 'fail'
data = mw.execShell(file + ' start')
data = mw.execShell(file + ' ' + method)
if data[1] == '':
return 'ok'
return 'fail'
@@ -136,7 +136,7 @@ def restart():
def reload():
return swapOp('reload')
return 'ok'
def initdStatus():
@@ -185,14 +185,15 @@ def changeSwap():
size = args['size']
swapOp('stop')
os.system('dd if=/dev/zero of=' + getServerDir() +
'/swapfile bs=1M count=' + size)
os.system('mkswap ' + getServerDir() + '/swapfile')
os.system('chmod 600 ' + getServerDir() + '/swapfile')
gsdir = getServerDir()
cmd = 'dd if=/dev/zero of=' + gsdir + '/swapfile bs=1M count=' + size
cmd += ' && mkswap ' + gsdir + '/swapfile && chmod 600 ' + gsdir + '/swapfile'
msg = mw.execShell(cmd)
swapOp('start')
return mw.returnJson(True, "修改成功!")
return mw.returnJson(True, "修改成功:\n" + msg[0])
if __name__ == "__main__":
func = sys.argv[1]
+5 -5
View File
@@ -54,7 +54,7 @@ function modifyAuthPath() {
type: 1,
area: "500px",
title: "修改安全入口",
closeBtn: 2,
closeBtn: 1,
shift: 5,
shadeClose: false,
content: '<div class="bt-form bt-form pd20 pb70">\
@@ -131,7 +131,7 @@ function setPassword(a) {
type: 1,
area: "290px",
title: '修改密码',
closeBtn: 2,
closeBtn: 1,
shift: 5,
shadeClose: false,
content: "<div class='bt-form pd20 pb70'>\
@@ -187,7 +187,7 @@ function setUserName(a) {
type: 1,
area: "290px",
title: '修改面板用户名',
closeBtn: 2,
closeBtn: 1,
shift: 5,
shadeClose: false,
content: "<div class='bt-form pd20 pb70'>\
@@ -238,7 +238,7 @@ function setPanelSSL(){
<input type="checkbox" id="checkSSL" /><label style="font-weight: 400;margin: 3px 5px 0px;" for="checkSSL">我已了经解详情,并愿意承担风险</label>\
<a target="_blank" class="btlink" href="https://www.bt.cn/bbs/thread-4689-1-1.html" style="float: right;">了解详情</a>\
</p>';
layer.confirm(msg,{title:'设置面板SSL',closeBtn:2,icon:3,area:'550px',cancel:function(){
layer.confirm(msg,{title:'设置面板SSL',closeBtn:1,icon:3,area:'550px',cancel:function(){
if(status == 0){
$("#panelSSL").prop("checked",false);
}
@@ -302,7 +302,7 @@ function getPanelSSL(){
type: 1,
area: "600px",
title: '自定义面板证书',
closeBtn: 2,
closeBtn: 1,
shift: 5,
shadeClose: false,
content:certBody
+1 -1
View File
@@ -180,7 +180,7 @@ function setControl(act, value=false){
//清理记录
function closeControl(){
layer.confirm('您真的清空所有监控记录吗?',{title:'清空记录',icon:3,closeBtn:2}, function() {
layer.confirm('您真的清空所有监控记录吗?',{title:'清空记录',icon:3,closeBtn:1}, function() {
loadT = layer.msg('正在处理,请稍候...',{icon:16,time:0})
$.post('/system/set_control','type=del',function(rdata){
layer.close(loadT);
+3 -3
View File
@@ -24,7 +24,7 @@ function getLogs(id){
title:lan.crontab.task_log_title,
area: ['60%','500px'],
shadeClose:false,
closeBtn:2,
closeBtn:1,
content:'<div class="setchmod bt-form pd20 pb70">'
+'<pre id="crontab-log" style="overflow: auto; border: 0px none; line-height:23px;padding: 15px; margin: 0px; white-space: pre-wrap; height: 405px; background-color: rgb(51,51,51);color:#f1f1f1;border-radius:0px;font-family:"></pre>'
+'<div class="bt-form-submit-btn" style="margin-top: 0px;">'
@@ -93,7 +93,7 @@ function getCronData(page){
// 设置计划任务状态
function setTaskStatus(id,status){
var confirm = layer.confirm(status == '0'?'计划任务暂停后将无法继续运行,您真的要停用这个计划任务吗?':'该计划任务已停用,是否要启用这个计划任务', {title:'提示',icon:3,closeBtn:2},function(index) {
var confirm = layer.confirm(status == '0'?'计划任务暂停后将无法继续运行,您真的要停用这个计划任务吗?':'该计划任务已停用,是否要启用这个计划任务', {title:'提示',icon:3,closeBtn:1},function(index) {
if (index > 0) {
var loadT = layer.msg('正在设置状态,请稍后...',{icon:16,time:0,shade: [0.3, '#000']});
$.post('/crontab/set_cron_status',{id:id},function(rdata){
@@ -610,7 +610,7 @@ function editTaskInfo(id){
area: ['850px','450px'],
skin:'layer-create-content',
shadeClose:false,
closeBtn:2,
closeBtn:1,
content:'<div class="setting-con ptb20">\
<div class="clearfix plan ptb10">\
<span class="typename c4 pull-left f14 text-right mr20">任务类型</span>\
+10 -10
View File
@@ -196,7 +196,7 @@ function recycleBin(type){
layer.open({
type: 1,
shift: 5,
closeBtn: 2,
closeBtn: 1,
area: ['80%','606px'],
title: lan.files.recycle_bin_title,
content: tablehtml
@@ -841,7 +841,7 @@ function createFile(type, path) {
layer.open({
type: 1,
shift: 5,
closeBtn: 2,
closeBtn: 1,
area: '320px',
title: '新建空白文件',
content: '<div class="bt-form pd20 pb70">\
@@ -881,7 +881,7 @@ function createDir(type, path) {
layer.open({
type: 1,
shift: 5,
closeBtn: 2,
closeBtn: 1,
area: '320px',
title: '新建目录',
content: '<div class="bt-form pd20 pb70">\
@@ -981,7 +981,7 @@ function downloadFile(action){
layer.open({
type: 1,
shift: 5,
closeBtn: 2,
closeBtn: 1,
area: '500px',
btn:["确定","关闭"],
title: lan.files.down_title,
@@ -1034,7 +1034,7 @@ function reName(type, fileName) {
layer.open({
type: 1,
shift: 5,
closeBtn: 2,
closeBtn: 1,
area: '320px',
title: '重命名',
btn:["确定","保存"],
@@ -1185,7 +1185,7 @@ function zip(dirName,submits) {
layer.open({
type: 1,
shift: 5,
closeBtn: 2,
closeBtn: 1,
area: '650px',
title: lan.files.zip_title,
content: '<div class="bt-form pd20 pb70">'
@@ -1241,7 +1241,7 @@ function unZip(fileName,type) {
layer.open({
type: 1,
shift: 5,
closeBtn: 2,
closeBtn: 1,
area: '490px',
title: '解压文件',
content: '<div class="bt-form pd20 pb70">'
@@ -1299,7 +1299,7 @@ function getImage(fileName){
var imgUrl = '/files/download?filename='+fileName;
layer.open({
type:1,
closeBtn: 2,
closeBtn: 1,
title:false,
area: '500px',
shadeClose: true,
@@ -1319,7 +1319,7 @@ function uploadFiles(){
var path = $("#DirPathPlace input").val()+"/";
layer.open({
type:1,
closeBtn: 2,
closeBtn: 1,
title:lan.files.up_title,
area: ['500px','300px'],
shadeClose:false,
@@ -1364,7 +1364,7 @@ function setChmod(action,fileName){
// console.log(rdata);
layer.open({
type:1,
closeBtn: 2,
closeBtn: 1,
title: '设置权限['+fileName+']',
area: '400px',
shadeClose:false,
+8 -8
View File
@@ -527,7 +527,7 @@ function checkUpdate() {
}
if (rdata.status === false) {
layer.confirm(rdata.msg, { title: lan.index.update_check, icon: 1, closeBtn: 2, btn: [lan.public.know, lan.public.close] });
layer.confirm(rdata.msg, { title: lan.index.update_check, icon: 1, closeBtn: 1, btn: [lan.public.know, lan.public.close] });
return;
}
layer.msg(rdata.msg, { icon: 1 });
@@ -610,7 +610,7 @@ function reBoot() {
type: 1,
title: '重启服务器或者面板',
area: '330px',
closeBtn: 2,
closeBtn: 1,
shadeClose: false,
content: '<div class="rebt-con"><div class="rebt-li"><a data-id="server" href="javascript:;">重启服务器</a></div><div class="rebt-li"><a data-id="panel" href="javascript:;">重启面板</a></div></div>'
});
@@ -620,7 +620,7 @@ function reBoot() {
var type = $(this).attr('data-id');
switch (type) {
case 'panel':
layer.confirm('即将重启面板服务,继续吗?', { title: '重启面板服务', closeBtn: 2, icon: 3 }, function () {
layer.confirm('即将重启面板服务,继续吗?', { title: '重启面板服务', closeBtn: 1, icon: 3 }, function () {
var loadT = layer.load();
$.post('/system/restart','',function (rdata) {
layer.close(loadT);
@@ -634,7 +634,7 @@ function reBoot() {
type: 1,
title: '安全重启服务器',
area: ['500px', '280px'],
closeBtn: 2,
closeBtn: 1,
shadeClose: false,
content: "<div class='bt-form bt-window-restart'>\
<div class='pd15'>\
@@ -692,7 +692,7 @@ function reBoot() {
//修复面板
function repPanel() {
layer.confirm(lan.index.rep_panel_msg, { title: lan.index.rep_panel_title, closeBtn: 2, icon: 3 }, function() {
layer.confirm(lan.index.rep_panel_msg, { title: lan.index.rep_panel_title, closeBtn: 1, icon: 3 }, function() {
var loadT = layer.msg(lan.index.rep_panel_the, { icon: 16, time: 0, shade: [0.3, '#000'] });
$.get('/system?action=RepPanel', function(rdata) {
layer.close(loadT);
@@ -750,7 +750,7 @@ function showDanger(num, port) {
type: 1,
area: ['720px', '410px'],
title: '安全提醒(如你想放弃任何安全提醒通知,请删除宝塔安全登录插件)',
closeBtn: 2,
closeBtn: 1,
shift: 5,
content: '<div class="pd20">\
<table class="f14 showDanger"><tbody>\
@@ -769,7 +769,7 @@ function showDanger(num, port) {
//加载关键数据总数
loadKeyDataCount();
function loadKeyDataCount(){
var plist = ['mysql', 'csvn', 'gogs'];
var plist = ['mysql', 'gogs','gitea'];
for (var i = 0; i < plist.length; i++) {
pname = plist[i];
function call(pname){
@@ -784,7 +784,7 @@ function loadKeyDataCount(){
}
var html = '<li class="sys-li-box col-xs-3 col-sm-3 col-md-3 col-lg-3">\
<p class="name f15 c9">'+pname+'</p>\
<div class="val"><a class="btlink" onclick="softMain(\''+pname+'\',\''+rdata['data']['ver']+'\')">'+rdata['data']['count']+'</a></div></li>';
<div class="val"><a class="btlink" onclick="softMain(\''+pname+'\',\''+pname+'\',\''+rdata['data']['ver']+'\')">'+rdata['data']['count']+'</a></div></li>';
$('#index_overview').append(html);
},'json');
}
+9 -9
View File
@@ -204,7 +204,7 @@ function changePath(d) {
type: 1,
area: "650px",
title: '选择目录',
closeBtn: 2,
closeBtn: 1,
shift: 5,
shadeClose: false,
content: "<div class='changepath'><div class='path-top'><button type='button' class='btn btn-default btn-sm' onclick='backFile()'><span class='glyphicon glyphicon-share-alt'></span>返回</button>\
@@ -554,7 +554,7 @@ function onlineEditFile(k, f) {
var r = layer.open({
type: 1,
shift: 5,
closeBtn: 2,
closeBtn: 1,
area: ["90%", "90%"],
title: lan.bt.edit_title+"[" + f + "]",
content: '<form class="bt-form pd20 pb70"><div class="line"><p style="color:red;margin-bottom:10px">'+lan.bt.edit_ps+' <select class="bt-input-text" name="encoding" style="width: 74px;position: absolute;top: 31px;right: 19px;height: 22px;z-index: 9999;border-radius: 0;">' + n + '</select></p><textarea class="mCustomScrollbar bt-input-text" id="textBody" style="width:100%;margin:0 auto;line-height: 1.8;position: relative;top: 10px;" value="" /> </div> <div class="bt-form-submit-btn" style="position:absolute; bottom:0; width:100%"> <button type="button" class="btn btn-danger btn-sm btn-editor-close">'+lan.public.close+'</button> <button id="OnlineEditFileBtn" type="button" class="btn btn-success btn-sm">'+lan.public.save+'</button> </div> </form>'
@@ -638,7 +638,7 @@ function safeMessage(j, h, g, f) {
type: 1,
title: j,
area: "350px",
closeBtn: 2,
closeBtn: 1,
shadeClose: true,
content: "<div class='bt-form webDelete pd20 pb70'><p>" + h + "</p>" + f + "<div class='vcode'>"+lan.bt.cal_msg+"<span class='text'>" + sumtext + "</span>=<input type='number' id='vcodeResult' value=''></div><div class='bt-form-submit-btn'><button type='button' class='btn btn-danger btn-sm bt-cancel'>"+lan.public.cancel+"</button> <button type='button' id='toSubmit' class='btn btn-success btn-sm' >"+lan.public.ok+"</button></div></div>"
});
@@ -718,7 +718,7 @@ $(function() {
});
$("#dologin").click(function() {
layer.confirm('您真的要退出面板吗?', {icon:3,closeBtn: 2}, function() {
layer.confirm('您真的要退出面板吗?', {icon:3,closeBtn: 1}, function() {
window.location.href = "/login?dologin=True"
});
return false
@@ -1030,7 +1030,7 @@ function bindPanel(a,type,ip,btid,url,user,pw){
type: 1,
area: "400px",
title: titleName,
closeBtn: 2,
closeBtn: 1,
shift: 5,
shadeClose: false,
content: "<div class='bt-form pd20 pb70'>\
@@ -1106,7 +1106,7 @@ function messageBox() {
type: 1,
title: '消息盒子',
area: "670px",
closeBtn: 2,
closeBtn: 1,
shadeClose: false,
content: '<div class="bt-form">\
<div class="bt-w-main">\
@@ -1459,7 +1459,7 @@ function webShell() {
type: 1,
title: "本地终端",
area: ['685px','435px'],
closeBtn: 2,
closeBtn: 1,
shadeClose: false,
content: '<div class="term-box"><div id="term"></div></div>\
<div class="shell-text-input">\
@@ -1661,7 +1661,7 @@ function pluginOpService(a, b, v) {
case "restart":d = '重启';break;
case "reload":d = '重载';break;
}
layer.confirm( msgTpl('您真的要{1}{2}{3}服务吗?', [d,a,v]), {icon:3,closeBtn: 2}, function() {
layer.confirm( msgTpl('您真的要{1}{2}{3}服务吗?', [d,a,v]), {icon:3,closeBtn: 1}, function() {
var e = layer.msg(msgTpl('正在{1}{2}{3}服务,请稍候...',[d,a,v]), {icon: 16,time: 0});
$.post("/plugins/run", c, function(g) {
layer.close(e);
@@ -1937,7 +1937,7 @@ function pluginOpInitD(a, _version, b) {
case "initd_install":d = '加载';break;
case "initd_uninstall":d = '卸载';break;
}
layer.confirm( msgTpl('您真的要{1}{2}{3}服务吗?', [d,a,_version]), {icon:3,closeBtn: 2}, function() {
layer.confirm( msgTpl('您真的要{1}{2}{3}服务吗?', [d,a,_version]), {icon:3,closeBtn: 1}, function() {
var e = layer.msg(msgTpl('正在{1}{2}{3}服务,请稍候...',[d,a,_version]), {icon: 16,time: 0});
$.post("/plugins/run", c, function(g) {
layer.close(e);
+14 -14
View File
@@ -233,7 +233,7 @@ function webAddPage(type) {
skin: 'demo-class',
area: '640px',
title: '添加网站',
closeBtn: 2,
closeBtn: 1,
shift: 0,
shadeClose: false,
content: "<form class='bt-form pd20 pb70' id='addweb'>\
@@ -673,7 +673,7 @@ function DomainRoot(id, name,msg) {
skin: 'demo-class',
area: '450px',
title: lan.site.domain_man,
closeBtn: 2,
closeBtn: 1,
shift: 0,
shadeClose: true,
content: "<div class='divtable padding-10'>\
@@ -869,7 +869,7 @@ function getBackup(id,name,page) {
skin: 'demo-class',
area: '700px',
title: '打包备份',
closeBtn: 2,
closeBtn: 1,
shift: 0,
shadeClose: false,
content: "<div class='bt-form ptb15 mlr15' id='webBackup'>\
@@ -918,7 +918,7 @@ function setIndex(id){
type: 1,
area: '500px',
title: lan.site.setindex,
closeBtn: 2,
closeBtn: 1,
shift: 5,
shadeClose: true,
content:"<form class='bt-form' id='SetIndex'><div class='SetIndex'>"
@@ -964,7 +964,7 @@ function getDefaultSite(){
type: 1,
area: '530px',
title: '设置默认站点',
closeBtn: 2,
closeBtn: 1,
shift: 5,
shadeClose: true,
content:'<div class="bt-form ptb15 pb70">\
@@ -1021,7 +1021,7 @@ function webEdit(id,website,endTime,addtime){
type: 1,
area: '640px',
title: '站点修改['+website+'] -- 添加时间['+addtime+']',
closeBtn: 2,
closeBtn: 1,
shift: 0,
content: "<div class='bt-form'>"
+"<div class='bt-w-menu pull-left' style='height: 565px;'>"
@@ -1363,7 +1363,7 @@ function showRewrite(rdata){
type: 1,
area: '500px',
title: '配置伪静态规则',
closeBtn: 2,
closeBtn: 1,
shift: 5,
shadeClose: true,
content:webBakHtml
@@ -1430,7 +1430,7 @@ function to301(siteName, type, obj){
skin: 'demo-class',
area: '650px',
title: type == 1 ? '创建重定向' : '修改重定向[' + obj.redirectname + ']',
closeBtn: 2,
closeBtn: 1,
shift: 5,
shadeClose: false,
content: "<form id='form_redirect' class='divtable pd20' style='padding-bottom: 60px'>" +
@@ -1632,7 +1632,7 @@ function toProxy(siteName, type, obj) {
type: 1,
area: '650px',
title: "创建反向代理",
closeBtn: 2,
closeBtn: 1,
shift: 5,
shadeClose: false,
btn: ['提交','关闭'],
@@ -2381,7 +2381,7 @@ function setRewriteTel(act){
aindex = layer.open({
type: 1,
shift: 5,
closeBtn: 2,
closeBtn: 1,
area: '320px', //宽高
title: '保存为Rewrite模板',
content: '<div class="bt-form pd20 pb70">\
@@ -2408,7 +2408,7 @@ function siteDefaultPage(){
type: 1,
area: '460px',
title: '修改默认页',
closeBtn: 2,
closeBtn: 1,
shift: 0,
content: '<div class="changeDefault pd20">\
<button class="btn btn-default btn-sm mg10" style="width:188px" onclick="changeDefault(1)">默认文档</button>\
@@ -2465,7 +2465,7 @@ function setClassType(){
type: 1,
area: '350px',
title: '网站分类管理',
closeBtn: 2,
closeBtn: 1,
shift: 0,
content: '<div class="bt-form edit_site_type">\
<div class="divtable mtb15" style="overflow:auto">\
@@ -2523,7 +2523,7 @@ function editClassType(id,name){
type: 1,
area: '350px',
title: '修改分类管理【' + name + '】',
closeBtn: 2,
closeBtn: 1,
shift: 0,
content: "<form class='bt-form bt-form pd20 pb70' id='mod_pwd'>\
<div class='line'>\
@@ -2563,7 +2563,7 @@ function moveClassTYpe(){
type: 1,
area: '350px',
title: '设置站点分类',
closeBtn: 2,
closeBtn: 1,
shift: 0,
content: '<div class="bt-form edit_site_type">\
<div class="divtable mtb15" style="overflow:auto;height:80px;">\
+3 -3
View File
@@ -205,7 +205,7 @@ function addVersion(name, ver, type, obj, title, install_pre_inspection) {
type: 1,
title: titlename + "软件安装",
area: '350px',
closeBtn: 2,
closeBtn: 1,
shadeClose: true,
btn: ['提交','关闭'],
content: "<div class='bt-form pd20 c6'>\
@@ -262,7 +262,7 @@ function uninstallPreInspection(name, ver, callback){
function runUninstallVersion(name, version){
layer.confirm(msgTpl('您真的要卸载[{1}-{2}]吗?', [name, version]), { icon: 3, closeBtn: 2 }, function() {
layer.confirm(msgTpl('您真的要卸载[{1}-{2}]吗?', [name, version]), { icon: 3, closeBtn: 1 }, function() {
var data = 'name=' + name + '&version=' + version;
var loadT = layer.msg('正在处理,请稍候...', { icon: 16, time: 0, shade: [0.3, '#000'] });
$.post('/plugins/uninstall', data, function(rdata) {
@@ -431,7 +431,7 @@ function importPlugin(file){
type: 1,
area: "500px",
title: "安装第三方插件包",
closeBtn: 2,
closeBtn: 1,
shift: 5,
shadeClose: false,
content: '<style>\
+19
View File
@@ -179,6 +179,22 @@ error_logs()
tail -n 100 $mw_path/logs/error.log
}
mw_update()
{
curl -fsSL https://raw.githubusercontent.com/midoks/mdserver-web/master/scripts/update.sh | bash
}
mw_update_dev()
{
curl -fsSL https://raw.githubusercontent.com/midoks/mdserver-web/dev/scripts/update_dev.sh | bash
}
mw_install_app()
{
bash $mw_path/scripts/quick/app.sh
}
case "$1" in
'start') mw_start;;
'stop') mw_stop;;
@@ -194,6 +210,9 @@ case "$1" in
mw_start_task;;
'status') mw_status;;
'logs') error_logs;;
'update') mw_update;;
'update_dev') mw_update_dev;;
'install_app') mw_install_app;;
'default')
cd $mw_path
port=7200
+3 -2
View File
@@ -15,8 +15,9 @@ if sys.platform != 'darwin':
chdir = os.getcwd()
sys.path.append(chdir + '/class/core')
reload(sys)
sys.setdefaultencoding('utf-8')
# importlib.reload(sys)
# sys.setdefaultencoding('utf-8')
import mw
print('==================================================================')