Pavel Loginov 2021-08-15 15:02:12 +06:00
parent a50fe9a946
commit 494352ac87
35 changed files with 785 additions and 339 deletions

View File

@ -11,7 +11,7 @@ form = funct.form
serv = form.getvalue('serv') serv = form.getvalue('serv')
print('Content-type: text/html\n') print('Content-type: text/html\n')
funct.check_login() funct.check_login(service=1)
funct.page_for_admin(level=3) funct.page_for_admin(level=3)
if ( if (
@ -21,7 +21,7 @@ if (
form.getvalue('generateconfig') is None form.getvalue('generateconfig') is None
): ):
try: try:
user, user_id, role, token, servers = funct.get_users_params() user, user_id, role, token, servers, user_services = funct.get_users_params()
cookie = http.cookies.SimpleCookie(os.environ.get("HTTP_COOKIE")) cookie = http.cookies.SimpleCookie(os.environ.get("HTTP_COOKIE"))
group = cookie.get('group') group = cookie.get('group')
user_group = group.value user_group = group.value
@ -55,6 +55,7 @@ if (
saved_servers=sql.select_saved_servers(), saved_servers=sql.select_saved_servers(),
white_lists=white_lists, white_lists=white_lists,
black_lists=black_lists, black_lists=black_lists,
user_services=user_services,
token=token) token=token)
print(template) print(template)

View File

@ -19,28 +19,31 @@ error = ""
aftersave = "" aftersave = ""
try: try:
user, user_id, role, token, servers = funct.get_users_params() user, user_id, role, token, servers, user_services = funct.get_users_params()
except Exception: except Exception as e:
pass print(str(e))
if service == 'keepalived': if service == 'keepalived':
title = "Working with Keepalived configuration files" if funct.check_login(service=3):
action = "config.py?service=keepalived" title = "Working with Keepalived configuration files"
configs_dir = funct.get_config_var('configs', 'kp_save_configs_dir') action = "config.py?service=keepalived"
file_format = 'conf' configs_dir = funct.get_config_var('configs', 'kp_save_configs_dir')
servers = sql.get_dick_permit(keepalived=1) file_format = 'conf'
servers = sql.get_dick_permit(keepalived=1)
elif service == 'nginx': elif service == 'nginx':
title = "Working with Nginx configuration files" if funct.check_login(service=2):
action = "config.py?service=nginx" title = "Working with Nginx configuration files"
configs_dir = funct.get_config_var('configs', 'nginx_save_configs_dir') action = "config.py?service=nginx"
file_format = 'conf' configs_dir = funct.get_config_var('configs', 'nginx_save_configs_dir')
servers = sql.get_dick_permit(nginx=1) file_format = 'conf'
servers = sql.get_dick_permit(nginx=1)
else: else:
title = "Working with HAProxy configuration files" if funct.check_login(service=1):
action = "config.py" title = "Working with HAProxy configuration files"
configs_dir = funct.get_config_var('configs', 'haproxy_save_configs_dir') action = "config.py"
file_format = 'cfg' configs_dir = funct.get_config_var('configs', 'haproxy_save_configs_dir')
servers = sql.get_dick_permit() file_format = 'cfg'
servers = sql.get_dick_permit()
if serv is not None: if serv is not None:
cfg = configs_dir + serv + "-" + funct.get_data('config') + "."+file_format cfg = configs_dir + serv + "-" + funct.get_data('config') + "."+file_format
@ -126,5 +129,6 @@ template = template.render(h2=1, title=title,
stderr=stderr, stderr=stderr,
error=error, error=error,
service=service, service=service,
user_services=user_services,
token=token) token=token)
print(template) print(template)

View File

@ -709,8 +709,38 @@ def update_db_v_5_2_0(**kwargs):
print('Updating... DB has been updated to version 5.2.0') print('Updating... DB has been updated to version 5.2.0')
def update_db_v_5_2_4(**kwargs):
cursor = conn.cursor()
sql = """ALTER TABLE `user` ADD COLUMN user_services varchar DEFAULT '1 2 3';"""
try:
cursor.execute(sql)
except Exception as e:
if kwargs.get('silent') != 1:
if str(e) == 'duplicate column name: user_services':
print('Updating... DB has been updated to version 5.2.4')
else:
print("An error occurred:", e)
else:
print("Updating... DB has been updated to version 5.2.4")
def update_db_v_5_2_4_1(**kwargs):
cursor = conn.cursor()
sql = """ALTER TABLE `servers` ADD COLUMN nginx_metrics integer DEFAULT 0;"""
try:
cursor.execute(sql)
except Exception as e:
if kwargs.get('silent') != 1:
if str(e) == 'duplicate column name: user_services':
print('Updating... DB has been updated to version 5.2.4')
else:
print("An error occurred:", e)
else:
print("Updating... DB has been updated to version 5.2.4")
def update_ver(): def update_ver():
query = Version.update(version = '5.2.3.0') query = Version.update(version = '5.2.4.0')
try: try:
query.execute() query.execute()
except: except:
@ -737,6 +767,8 @@ def update_all():
update_db_v_5_1_2() update_db_v_5_1_2()
update_db_v_5_1_3() update_db_v_5_1_3()
update_db_v_5_2_0() update_db_v_5_2_0()
update_db_v_5_2_4()
update_db_v_5_2_4_1()
update_ver() update_ver()
@ -760,6 +792,8 @@ def update_all_silent():
update_db_v_5_1_2(silent=1) update_db_v_5_1_2(silent=1)
update_db_v_5_1_3(silent=1) update_db_v_5_1_3(silent=1)
update_db_v_5_2_0(silent=1) update_db_v_5_2_0(silent=1)
update_db_v_5_2_4(silent=1)
update_db_v_5_2_4_1(silent=1)
update_ver() update_ver()

View File

@ -30,6 +30,7 @@ class User(BaseModel):
groups = CharField() groups = CharField()
ldap_user = IntegerField(default=0) ldap_user = IntegerField(default=0)
activeuser = IntegerField(default=1) activeuser = IntegerField(default=1)
user_services = CharField(constraints=[SQL('DEFAULT "1 2 3"')])
class Meta: class Meta:
table_name = 'user' table_name = 'user'
@ -40,23 +41,24 @@ class Server(BaseModel):
hostname = CharField() hostname = CharField()
ip = CharField() ip = CharField()
groups = CharField() groups = CharField()
type_ip = IntegerField(default=0) type_ip = IntegerField(constraints=[SQL('DEFAULT 0')])
enable = IntegerField(default=1) enable = IntegerField(constraints=[SQL('DEFAULT 1')])
master = IntegerField(default=0) master = IntegerField(constraints=[SQL('DEFAULT 0')])
cred = IntegerField(default=1) cred = IntegerField(constraints=[SQL('DEFAULT 1')])
alert = IntegerField(default=0) alert = IntegerField(constraints=[SQL('DEFAULT 0')])
metrics = IntegerField(default=0) metrics = IntegerField(constraints=[SQL('DEFAULT 0')])
port = IntegerField(default=22) port = IntegerField(constraints=[SQL('DEFAULT 22')])
desc = CharField(null=True) desc = CharField(null=True)
active = IntegerField(default=0) active = IntegerField(constraints=[SQL('DEFAULT 0')])
keepalived = IntegerField(default=0) keepalived = IntegerField(constraints=[SQL('DEFAULT 0')])
nginx = IntegerField(default=0) nginx = IntegerField(constraints=[SQL('DEFAULT 0')])
haproxy = IntegerField(default=0) haproxy = IntegerField(constraints=[SQL('DEFAULT 0')])
pos = IntegerField(default=0) pos = IntegerField(constraints=[SQL('DEFAULT 0')])
nginx_active = IntegerField(default=0) nginx_active = IntegerField(constraints=[SQL('DEFAULT 0')])
firewall_enable = IntegerField(default=0) firewall_enable = IntegerField(constraints=[SQL('DEFAULT 0')])
nginx_alert = IntegerField(default=0) nginx_alert = IntegerField(constraints=[SQL('DEFAULT 0')])
protected = IntegerField(default=0) protected = IntegerField(constraints=[SQL('DEFAULT 0')])
nginx_metrics = IntegerField(constraints=[SQL('DEFAULT 1')])
class Meta: class Meta:
table_name = 'servers' table_name = 'servers'
@ -206,6 +208,16 @@ class WafMetrics(BaseModel):
primary_key = False primary_key = False
class NginxMetrics(BaseModel):
serv = CharField()
conn = IntegerField()
date = DateTimeField(default=datetime.now)
class Meta:
table_name = 'nginx_metrics'
primary_key = False
class Version(BaseModel): class Version(BaseModel):
version = CharField() version = CharField()
@ -403,4 +415,4 @@ def create_tables():
conn.create_tables([User, Server, Role, Telegram, Slack, UUID, Token, ApiToken, Groups, UserGroups, conn.create_tables([User, Server, Role, Telegram, Slack, UUID, Token, ApiToken, Groups, UserGroups,
Setting, Cred, Backup, Metrics, WafMetrics, Version, Option, SavedServer, Waf, Setting, Cred, Backup, Metrics, WafMetrics, Version, Option, SavedServer, Waf,
PortScannerSettings, PortScannerPorts, PortScannerHistory, ProvidersCreds, PortScannerSettings, PortScannerPorts, PortScannerHistory, ProvidersCreds,
ProvisionedServers, MetricsHttpStatus, SMON, WafRules, Alerts, GeoipCodes]) ProvisionedServers, MetricsHttpStatus, SMON, WafRules, Alerts, GeoipCodes, NginxMetrics])

View File

@ -219,7 +219,7 @@ def slack_send_mess(mess, **kwargs):
logging('localhost', str(e), haproxywi=1) logging('localhost', str(e), haproxywi=1)
def check_login(): def check_login(**kwargs):
import sql import sql
import http.cookies import http.cookies
cookie = http.cookies.SimpleCookie(os.environ.get("HTTP_COOKIE")) cookie = http.cookies.SimpleCookie(os.environ.get("HTTP_COOKIE"))
@ -233,6 +233,15 @@ def check_login():
if sql.get_user_name_by_uuid(user_uuid.value) is None: if sql.get_user_name_by_uuid(user_uuid.value) is None:
print('<meta http-equiv="refresh" content="0; url=login.py?ref=%s">' % ref) print('<meta http-equiv="refresh" content="0; url=login.py?ref=%s">' % ref)
return False return False
if kwargs.get('service'):
required_service = str(kwargs.get('service'))
user_id = sql.get_user_id_by_uuid(user_uuid.value)
user_services = sql.select_user_services(user_id)
if required_service in user_services:
return True
else:
print('<meta http-equiv="refresh" content="0; url=overview.py">')
return False
else: else:
print('<meta http-equiv="refresh" content="0; url=login.py?ref=%s">' % ref) print('<meta http-equiv="refresh" content="0; url=login.py?ref=%s">' % ref)
return False return False
@ -795,12 +804,13 @@ def upload_and_restart(serv, cfg, **kwargs):
else: else:
commands = ["sudo mv -f " + tmp_file + " /etc/keepalived/keepalived.conf && sudo systemctl restart keepalived"] commands = ["sudo mv -f " + tmp_file + " /etc/keepalived/keepalived.conf && sudo systemctl restart keepalived"]
elif kwargs.get("nginx"): elif kwargs.get("nginx"):
check_and_move = "sudo mv -f " + tmp_file + " " + config_path + " && sudo nginx -t -q"
if kwargs.get("just_save") == "save": if kwargs.get("just_save") == "save":
commands = ["sudo mv -f " + tmp_file + " " + config_path + " && sudo nginx -t -q"] commands = [check_and_move]
elif kwargs.get("just_save") == "reload": elif kwargs.get("just_save") == "reload":
commands = ["sudo mv -f " + tmp_file + " " + config_path + " && sudo nginx -t -q && sudo systemctl reload nginx"] commands = [check_and_move + " && sudo systemctl reload nginx"]
else: else:
commands = ["sudo mv -f " + tmp_file + " " + config_path + " && sudo nginx -t -q && sudo systemctl restart nginx"] commands = [check_and_move + " && sudo systemctl restart nginx"]
if sql.return_firewall(serv): if sql.return_firewall(serv):
commands[0] += open_port_firewalld(cfg, serv=serv, service='nginx') commands[0] += open_port_firewalld(cfg, serv=serv, service='nginx')
else: else:
@ -811,14 +821,17 @@ def upload_and_restart(serv, cfg, **kwargs):
else: else:
haproxy_service_name = "haproxy" haproxy_service_name = "haproxy"
check_config = "sudo " + haproxy_service_name + " -q -c -f " + tmp_file
move_config = " && sudo mv -f " + tmp_file + " " + config_path
if kwargs.get("just_save") == "test": if kwargs.get("just_save") == "test":
commands = ["sudo "+haproxy_service_name+" -q -c -f " + tmp_file + " && sudo rm -f " + tmp_file] commands = [check_config + " && sudo rm -f " + tmp_file]
elif kwargs.get("just_save") == "save": elif kwargs.get("just_save") == "save":
commands = ["sudo "+haproxy_service_name+" -q -c -f " + tmp_file + " && sudo mv -f " + tmp_file + " " + config_path] commands = [check_config + move_config]
elif kwargs.get("just_save") == "reload": elif kwargs.get("just_save") == "reload":
commands = ["sudo "+haproxy_service_name+" -q -c -f " + tmp_file + " && sudo mv -f " + tmp_file + " " + config_path + " && sudo systemctl reload "+haproxy_service_name+""] commands = [check_config + move_config + " && sudo systemctl reload "+haproxy_service_name+""]
else: else:
commands = ["sudo "+haproxy_service_name+" -q -c -f " + tmp_file + " && sudo mv -f " + tmp_file + " " + config_path + " && sudo systemctl restart "+haproxy_service_name+""] commands = [check_config + move_config + " && sudo systemctl restart "+haproxy_service_name+""]
if sql.return_firewall(serv): if sql.return_firewall(serv):
commands[0] += open_port_firewalld(cfg, serv=serv) commands[0] += open_port_firewalld(cfg, serv=serv)
error += str(upload(serv, tmp_file, cfg, dir='fullpath')) error += str(upload(serv, tmp_file, cfg, dir='fullpath'))
@ -1237,10 +1250,12 @@ def get_users_params(**kwargs):
import http.cookies import http.cookies
import sql import sql
cookie = http.cookies.SimpleCookie(os.environ.get("HTTP_COOKIE")) cookie = http.cookies.SimpleCookie(os.environ.get("HTTP_COOKIE"))
user_id = cookie.get('uuid') user_uuid = cookie.get('uuid')
user = sql.get_user_name_by_uuid(user_id.value) user = sql.get_user_name_by_uuid(user_uuid.value)
role = sql.get_user_role_by_uuid(user_id.value) role = sql.get_user_role_by_uuid(user_uuid.value)
token = sql.get_token(user_id.value) user_id = sql.get_user_id_by_uuid(user_uuid.value)
user_services = sql.select_user_services(user_id)
token = sql.get_token(user_uuid.value)
if kwargs.get('virt'): if kwargs.get('virt'):
servers = sql.get_dick_permit(virt=1) servers = sql.get_dick_permit(virt=1)
elif kwargs.get('disable'): elif kwargs.get('disable'):
@ -1248,7 +1263,7 @@ def get_users_params(**kwargs):
else: else:
servers = sql.get_dick_permit() servers = sql.get_dick_permit()
return user, user_id, role, token, servers return user, user_uuid, role, token, servers, user_services
def check_user_group(**kwargs): def check_user_group(**kwargs):

View File

@ -5,14 +5,14 @@ env = Environment(loader=FileSystemLoader('templates/'), autoescape=True)
template = env.get_template('ha.html') template = env.get_template('ha.html')
print('Content-type: text/html\n') print('Content-type: text/html\n')
funct.check_login() funct.check_login(service=3)
funct.page_for_admin(level=2) funct.page_for_admin(level=2)
form = funct.form form = funct.form
serv = form.getvalue('serv') serv = form.getvalue('serv')
try: try:
user, user_id, role, token, servers = funct.get_users_params() user, user_id, role, token, servers, user_services = funct.get_users_params()
except Exception: except Exception:
pass pass
@ -23,5 +23,6 @@ output_from_parsed_template = template.render(h2=1,
user=user, user=user,
serv=serv, serv=serv,
selects=servers, selects=servers,
user_services=user_services,
token=token) token=token)
print(output_from_parsed_template) print(output_from_parsed_template)

View File

@ -10,43 +10,46 @@ print('Content-type: text/html\n')
funct.check_login() funct.check_login()
try: try:
user, user_id, role, token, servers = funct.get_users_params() user, user_id, role, token, servers, user_services = funct.get_users_params()
services = [] services = []
except: except:
pass pass
form = funct.form form = funct.form
serv = form.getvalue('serv') serv = funct.is_ip_or_dns(form.getvalue('serv'))
service = form.getvalue('service') service = form.getvalue('service')
autorefresh = 0 autorefresh = 0
cmd = "ps ax |grep -e 'keep_alive.py' |grep -v grep |wc -l" cmd = "ps ax |grep -e 'keep_alive.py' |grep -v grep |wc -l"
keep_alive, stderr = funct.subprocess_execute(cmd) keep_alive, stderr = funct.subprocess_execute(cmd)
if service == 'nginx': if service == 'nginx':
title = 'Nginx servers overview' if funct.check_login(service=2):
servers = sql.get_dick_permit(virt=1, nginx=1) title = 'Nginx servers overview'
service = 'nginx' servers = sql.get_dick_permit(virt=1, nginx=1)
if serv: service = 'nginx'
if funct.check_is_server_in_group(serv): if serv:
servers = sql.select_servers(server=serv) if funct.check_is_server_in_group(serv):
autorefresh = 1 servers = sql.select_servers(server=serv)
autorefresh = 1
elif service == 'keepalived': elif service == 'keepalived':
title = 'Keepalived servers overview' if funct.check_login(service=3):
servers = sql.get_dick_permit(virt=1, keepalived=1) title = 'Keepalived servers overview'
service = 'keepalived' servers = sql.get_dick_permit(virt=1, keepalived=1)
if serv: service = 'keepalived'
if funct.check_is_server_in_group(serv): if serv:
servers = sql.select_servers(server=serv) if funct.check_is_server_in_group(serv):
autorefresh = 1 servers = sql.select_servers(server=serv)
autorefresh = 1
else: else:
title = "HAProxy servers overview" if funct.check_login(service=1):
service = 'haproxy' title = "HAProxy servers overview"
if serv: service = 'haproxy'
if funct.check_is_server_in_group(serv): if serv:
servers = sql.select_servers(server=serv) if funct.check_is_server_in_group(serv):
autorefresh = 1 servers = sql.select_servers(server=serv)
else: autorefresh = 1
servers = sql.get_dick_permit(virt=1, haproxy=1) else:
servers = sql.get_dick_permit(virt=1, haproxy=1)
services_name = {'roxy-wi-checker': 'Master backends checker service', services_name = {'roxy-wi-checker': 'Master backends checker service',
'roxy-wi-keep_alive': 'Auto start service', 'roxy-wi-keep_alive': 'Auto start service',
@ -147,5 +150,6 @@ template = template.render(h2=1,
serv=serv, serv=serv,
service=service, service=service,
services=services, services=services,
user_services=user_services,
token=token) token=token)
print(template) print(template)

View File

@ -32,14 +32,16 @@ print('Content-type: text/html\n')
funct.check_login() funct.check_login()
try: try:
user, user_id, role, token, servers = funct.get_users_params() user, user_id, role, token, servers, user_services = funct.get_users_params()
except Exception: except Exception:
pass pass
if service == 'nginx': if service == 'nginx':
title = "Nginx`s logs" if funct.check_login(service=2):
title = "Nginx`s logs"
else: else:
title = "HAProxy`s logs" if funct.check_login(service=1):
title = "HAProxy`s logs"
template = template.render(h2=1, template = template.render(h2=1,
autorefresh=1, autorefresh=1,
@ -58,5 +60,6 @@ template = template.render(h2=1,
minut1=minut1, minut1=minut1,
waf=waf, waf=waf,
service=service, service=service,
user_services=user_services,
token=token) token=token)
print(template) print(template)

View File

@ -4,12 +4,14 @@ import sql
from jinja2 import Environment, FileSystemLoader from jinja2 import Environment, FileSystemLoader
env = Environment(loader=FileSystemLoader('templates/'), autoescape=True) env = Environment(loader=FileSystemLoader('templates/'), autoescape=True)
template = env.get_template('metrics.html') template = env.get_template('metrics.html')
form = funct.form
service = form.getvalue('service')
print('Content-type: text/html\n')
funct.check_login() funct.check_login()
print('Content-type: text/html\n')
try: try:
user, user_id, role, token, servers = funct.get_users_params() user, user_id, role, token, servers, user_services = funct.get_users_params()
cmd = "rpm --query roxy-wi-metrics-* |awk -F\"metrics\" '{print $2}' |awk -F\".noa\" '{print $1}' |sed 's/-//1' |sed 's/-/./'" cmd = "rpm --query roxy-wi-metrics-* |awk -F\"metrics\" '{print $2}' |awk -F\".noa\" '{print $1}' |sed 's/-//1' |sed 's/-/./'"
service_ver, stderr = funct.subprocess_execute(cmd) service_ver, stderr = funct.subprocess_execute(cmd)
services = '0' services = '0'
@ -18,17 +20,26 @@ try:
if service_ver[0] == '* is not installed': if service_ver[0] == '* is not installed':
servers = '' servers = ''
else: else:
servers = sql.select_servers_metrics() if service == 'nginx':
if funct.check_login(service=2):
title = "Nginx`s metrics"
servers = sql.select_nginx_servers_metrics_for_master()
else:
if funct.check_login(service=1):
title = "HAProxy`s metrics"
servers = sql.select_servers_metrics()
services = '1' services = '1'
except Exception as e: except Exception as e:
pass pass
template = template.render(h2=1, title="Metrics", template = template.render(h2=1, title=title,
autorefresh=1, autorefresh=1,
role=role, role=role,
user=user, user=user,
servers=servers, servers=servers,
services=services, services=services,
user_services=user_services,
service=service,
token=token) token=token)
print(template) print(template)

View File

@ -9,7 +9,7 @@ print('Content-type: text/html\n')
funct.check_login() funct.check_login()
try: try:
user, user_id, role, token, servers = funct.get_users_params(virt=1) user, user_id, role, token, servers, user_services = funct.get_users_params(virt=1)
except Exception: except Exception:
pass pass
@ -20,5 +20,6 @@ output_from_parsed_template = template.render(h2=1, autorefresh=0,
user=user, user=user,
servers=servers, servers=servers,
versions=funct.versions(), versions=funct.versions(),
user_services=user_services,
token=token) token=token)
print(output_from_parsed_template) print(output_from_parsed_template)

View File

@ -13,6 +13,7 @@ act = form.getvalue("act")
if (form.getvalue('new_metrics') or if (form.getvalue('new_metrics') or
form.getvalue('new_http_metrics') or form.getvalue('new_http_metrics') or
form.getvalue('new_waf_metrics') or form.getvalue('new_waf_metrics') or
form.getvalue('new_nginx_metrics') or
form.getvalue('metrics_hapwi_ram') or form.getvalue('metrics_hapwi_ram') or
form.getvalue('metrics_hapwi_cpu') or form.getvalue('metrics_hapwi_cpu') or
form.getvalue('getoption') or form.getvalue('getoption') or
@ -74,7 +75,7 @@ if serv and form.getvalue('ssl_cert'):
os.makedirs(cert_local_dir) os.makedirs(cert_local_dir)
if form.getvalue('ssl_name') is None: if form.getvalue('ssl_name') is None:
print('error: Please enter desired name') print('error: Please enter a desired name')
else: else:
name = form.getvalue('ssl_name') name = form.getvalue('ssl_name')
@ -82,7 +83,7 @@ if serv and form.getvalue('ssl_cert'):
with open(name, "w") as ssl_cert: with open(name, "w") as ssl_cert:
ssl_cert.write(form.getvalue('ssl_cert')) ssl_cert.write(form.getvalue('ssl_cert'))
except IOError as e: except IOError as e:
print('error: Can\'t save ssl keys file. Check ssh keys path in config ' + e.args[0]) print('error: Cannot save the SSL key file. Check a SSH key path in config ' + e.args[0])
MASTERS = sql.is_master(serv) MASTERS = sql.is_master(serv)
for master in MASTERS: for master in MASTERS:
@ -91,7 +92,7 @@ if serv and form.getvalue('ssl_cert'):
try: try:
error = funct.upload(serv, cert_path, name) error = funct.upload(serv, cert_path, name)
if error == '': if error == '':
print('success: SSL file has been uploaded to %s into: %s%s' % (serv, cert_path, '/' + name)) print('success: the SSL file has been uploaded to %s into: %s%s' % (serv, cert_path, '/' + name))
except Exception as e: except Exception as e:
funct.logging('localhost', e.args[0], haproxywi=1) funct.logging('localhost', e.args[0], haproxywi=1)
try: try:
@ -136,7 +137,7 @@ if form.getvalue('backend_ip') is not None:
sys.exit() sys.exit()
if form.getvalue('backend_port') is None: if form.getvalue('backend_port') is None:
print('error: Backend port must be integer and not 0') print('error: The backend port must be integer and not 0')
sys.exit() sys.exit()
haproxy_sock_port = sql.get_setting('haproxy_sock_port') haproxy_sock_port = sql.get_setting('haproxy_sock_port')
@ -421,7 +422,7 @@ if form.getvalue('action_keepalived') is not None and serv is not None:
if form.getvalue('action_waf') is not None and serv is not None: if form.getvalue('action_waf') is not None and serv is not None:
serv = form.getvalue('serv') serv = form.getvalue('serv')
action = form.getvalue('action_waf') action = form.getvalue('action_waf')
funct.logging(serv, 'WAF service was ' + action + 'ed', haproxywi=1, login=1) funct.logging(serv, 'WAF service has been ' + action + 'ed', haproxywi=1, login=1)
commands = ["sudo systemctl %s waf" % action] commands = ["sudo systemctl %s waf" % action]
funct.ssh_command(serv, commands) funct.ssh_command(serv, commands)
@ -434,7 +435,7 @@ if form.getvalue('action_service') is not None:
elif action == "restart": elif action == "restart":
cmd = "sudo systemctl restart %s --now" % serv cmd = "sudo systemctl restart %s --now" % serv
output, stderr = funct.subprocess_execute(cmd) output, stderr = funct.subprocess_execute(cmd)
funct.logging('localhost', ' The service ' + serv + ' was ' + action + 'ed', haproxywi=1, login=1) funct.logging('localhost', ' The service ' + serv + ' has been ' + action + 'ed', haproxywi=1, login=1)
if act == "overviewHapserverBackends": if act == "overviewHapserverBackends":
from jinja2 import Environment, FileSystemLoader from jinja2 import Environment, FileSystemLoader
@ -461,7 +462,7 @@ if act == "overviewHapserverBackends":
try: try:
cfg = configs_dir + serv + "-" + funct.get_data('config') + '.' + format_file cfg = configs_dir + serv + "-" + funct.get_data('config') + '.' + format_file
except Exception as e: except Exception as e:
funct.logging('localhost', ' Cannot generate cfg path ' + str(e), haproxywi=1) funct.logging('localhost', ' Cannot generate a cfg path ' + str(e), haproxywi=1)
try: try:
if service == 'nginx': if service == 'nginx':
error = funct.get_config(serv, cfg, nginx=1) error = funct.get_config(serv, cfg, nginx=1)
@ -470,7 +471,7 @@ if act == "overviewHapserverBackends":
else: else:
error = funct.get_config(serv, cfg) error = funct.get_config(serv, cfg)
except Exception as e: except Exception as e:
funct.logging('localhost', ' Cannot download config ' + str(e), haproxywi=1) funct.logging('localhost', ' Cannot download a config ' + str(e), haproxywi=1)
try: try:
sections = funct.get_sections(cfg, service=service) sections = funct.get_sections(cfg, service=service)
except Exception as e: except Exception as e:
@ -491,15 +492,15 @@ if form.getvalue('show_userlists'):
try: try:
cfg = configs_dir + serv + "-" + funct.get_data('config') + '.' + format_file cfg = configs_dir + serv + "-" + funct.get_data('config') + '.' + format_file
except Exception as e: except Exception as e:
funct.logging('localhost', ' Cannot generate cfg path ' + str(e), haproxywi=1) funct.logging('localhost', ' Cannot generate a cfg path ' + str(e), haproxywi=1)
try: try:
error = funct.get_config(serv, cfg) error = funct.get_config(serv, cfg)
except Exception as e: except Exception as e:
funct.logging('localhost', ' Cannot download config ' + str(e), haproxywi=1) funct.logging('localhost', ' Cannot download a config ' + str(e), haproxywi=1)
try: try:
sections = funct.get_userlists(cfg) sections = funct.get_userlists(cfg)
except Exception as e: except Exception as e:
funct.logging('localhost', ' Cannot get Userlists from config file ' + str(e), haproxywi=1) funct.logging('localhost', ' Cannot get Userlists from the config file ' + str(e), haproxywi=1)
sections = 'error: Cannot get Userlists' sections = 'error: Cannot get Userlists'
print(sections) print(sections)
@ -522,10 +523,21 @@ if act == "overview":
import http.cookies import http.cookies
from jinja2 import Environment, FileSystemLoader from jinja2 import Environment, FileSystemLoader
async def async_get_overview(serv1, serv2): async def async_get_overview(serv1, serv2, user_uuid):
haproxy = sql.select_haproxy(serv2) user_id = sql.get_user_id_by_uuid(user_uuid)
keepalived = sql.select_keepalived(serv2) user_services = sql.select_user_services(user_id)
nginx = sql.select_nginx(serv2) if '1' in user_services:
haproxy = sql.select_haproxy(serv2)
else:
haproxy = 0
if '2' in user_services:
nginx = sql.select_nginx(serv2)
else:
nginx = 0
if '3' in user_services:
keepalived = sql.select_keepalived(serv2)
else:
keepalived = 0
waf = sql.select_waf_servers(serv2) waf = sql.select_waf_servers(serv2)
haproxy_process = '' haproxy_process = ''
keepalived_process = '' keepalived_process = ''
@ -573,13 +585,13 @@ if act == "overview":
servers = [] servers = []
template = env.get_template('overview.html') template = env.get_template('overview.html')
cookie = http.cookies.SimpleCookie(os.environ.get("HTTP_COOKIE")) cookie = http.cookies.SimpleCookie(os.environ.get("HTTP_COOKIE"))
user_id = cookie.get('uuid') user_uuid = cookie.get('uuid')
futures = [async_get_overview(server[1], server[2]) for server in sql.select_servers(server=serv)] futures = [async_get_overview(server[1], server[2], user_uuid.value) for server in sql.select_servers(server=serv)]
for i, future in enumerate(asyncio.as_completed(futures)): for i, future in enumerate(asyncio.as_completed(futures)):
result = await future result = await future
servers.append(result) servers.append(result)
servers_sorted = sorted(servers, key=funct.get_key) servers_sorted = sorted(servers, key=funct.get_key)
template = template.render(service_status=servers_sorted, role=sql.get_user_role_by_uuid(user_id.value)) template = template.render(service_status=servers_sorted, role=sql.get_user_role_by_uuid(user_uuid.value))
print(template) print(template)
@ -752,7 +764,7 @@ if serv is not None and act == "stats":
print(data.decode('utf-8')) print(data.decode('utf-8'))
if serv is not None and form.getvalue('show_log') is not None: if serv is not None and form.getvalue('show_log') is not None:
rows = form.getvalue('rows') rows = form.getvalue('show_log')
waf = form.getvalue('waf') waf = form.getvalue('waf')
grep = form.getvalue('grep') grep = form.getvalue('grep')
hour = form.getvalue('hour') hour = form.getvalue('hour')
@ -804,8 +816,6 @@ if serv is not None and act == "showMap":
print('<center>') print('<center>')
print("<h4>Map from %s</h4><br />" % serv) print("<h4>Map from %s</h4><br />" % serv)
G = nx.DiGraph()
error = funct.get_config(serv, cfg) error = funct.get_config(serv, cfg)
if error: if error:
print(error) print(error)
@ -814,37 +824,36 @@ if serv is not None and act == "showMap":
except IOError: except IOError:
print('error: Can\'t read import config file') print('error: Can\'t read import config file')
G = nx.DiGraph()
node = "" node = ""
line_new2 = [1, ""] line_new2 = [1, ""]
i, k = 800, 800 sections = {'listens': dict(), 'backends': dict()}
j = 0
for line in conf: for line in conf:
if line.startswith('listen') or line.startswith('frontend'): if line.startswith('listen') or line.startswith('frontend'):
if "stats" not in line: if "stats" not in line:
node = line node = line
i = i - 750
if line.find("backend") == 0: if line.find("backend") == 0:
node = line node = line
i = i - 700 node = node.split('\n')[0]
G.add_node(node, pos=(k, i), label_pos=(k, i + 100)) sections['backends'][node] = {'servers': dict()}
if "bind" in line or (line.startswith('listen') and ":" in line) or ( if "bind" in line or (line.startswith('listen') and ":" in line) or (
line.startswith('frontend') and ":" in line): line.startswith('frontend') and ":" in line):
try: try:
bind = line.split(":") bind = line.split(":")
if stats_port not in bind[1]: if str(stats_port) not in bind[1]:
bind[1] = bind[1].strip(' ') bind[1] = bind[1].strip(' ')
bind = bind[1].split("crt") bind = bind[1].split("crt")
node = node.strip(' \t\n\r') node = node.strip(' \t\n\r')
node = node + ":" + bind[0] node = node + ":" + bind[0]
G.add_node(node, pos=(k, i), label_pos=(k, i + 100)) node = node.split('\n')[0]
except Exception: sections['listens'][node] = {'servers': dict()}
except Exception as e:
pass pass
if "server " in line or "use_backend" in line or "default_backend" in line and "stats" not in line and "#" not in line: if "server " in line or "use_backend" in line or "default_backend" in line and "stats" not in line and "#" not in line:
if "timeout" not in line and "default-server" not in line and "#" not in line and "stats" not in line: if "timeout" not in line and "default-server" not in line and "#" not in line and "stats" not in line:
i = i - 1050
j = j + 1
if "check" in line: if "check" in line:
line_new = line.split("check") line_new = line.split("check")
else: else:
@ -863,29 +872,133 @@ if serv is not None and act == "showMap":
except Exception as e: except Exception as e:
backend_server_port = '' backend_server_port = ''
if j % 2 == 0: try:
G.add_node(line_new[0], pos=(k + 250, i - 335), label_pos=(k + 215, i - 180)) sections['listens'][node]['servers'][line_new[0]] = {line_new[0]: backend_server_port}
else: except Exception as e:
G.add_node(line_new[0], pos=(k - 250, i - 0), label_pos=(k - 245, i + 180)) pass
if line_new2[1] != "": try:
G.add_edge(node, line_new[0], port=backend_server_port) sections['backends'][node]['servers'][line_new[0]] = {line_new[0]: backend_server_port}
else: except Exception as e:
G.add_edge(node, line_new[0], port='') pass
os.system("/bin/rm -f " + cfg) os.system("/bin/rm -f " + cfg)
i, k, j = 0, 0, 0
backend_servers_len_dict = 1
backends_from_frontends = []
backends_servers = []
for key, val in sections.items():
if key == 'listens':
for k2, v2 in val.items():
i -= 750
G.add_node(k2, pos=(k, i), label_pos=(k, i + 250))
for k3, v3 in v2.items():
for k4, v4 in v3.items():
""" Add backend servers of listens or backend from frontends """
i -= 300
j += 1
server_name = k4
if 'default_backend' in k4 or 'use_backend' in k4:
backend_name = k4.split(' ')[1]
backend_name = 'backend ' + backend_name
k4 = backend_name
backends_from_frontends.append(k4)
if k4 not in backends_servers:
if j % 2 == 0:
G.add_node(k4, pos=(k + 250, i - 100), label_pos=(k + 250, i - 420))
else:
G.add_node(k4, pos=(k - 250, i - 370), label_pos=(k - 245, i - 650))
if v4[server_name] != '':
G.add_edge(k2, k4, port=v4[server_name])
else:
G.add_edge(k2, k4, port='')
for k4, v4 in v3.items():
""" Add servers from backends """
i -= 300
j -= 1
if 'default_backend' in k4 or 'use_backend' in k4:
backend_name = k4.split(' ')[1]
backend_name = 'backend ' + backend_name
k4 = backend_name
backends_from_frontends.append(k4)
if j % 2 == 0:
if len(v3) % 2 == 0:
i += (700 * backend_servers_len_dict) + 700
for k5, v5 in sections['backends'][k4]['servers'].items():
i -= 700
s = k + 400
G.add_node(k5, pos=(s + 250, i - 335), label_pos=(s + 215, i - 580))
if v5[k5] != '':
G.add_edge(k4, k5, port=v5[k5])
else:
G.add_edge(k4, k5, port='')
backends_servers.append(k5)
else:
for k5, v5 in sections['backends'][k4]['servers'].items():
i -= 700
s = k - 400
G.add_node(k5, pos=(s - 250, i - 0), label_pos=(s - 245, i - 270))
if v5[k5] != '':
G.add_edge(k4, k5, port=v5[k5])
else:
G.add_edge(k4, k5, port='')
backends_servers.append(k5)
backend_servers_len_dict = len(sections['backends'][k4]['servers'])
backends_servers.append(k4)
elif key == 'backends':
for k2, v2 in val.items():
if k2 not in backends_from_frontends:
i -= 750
G.add_node(k2, pos=(k, i), label_pos=(k, i + 250))
for k3, v3 in v2.items():
for k4, v4 in v3.items():
if k4 not in backends_servers:
i -= 300
j += 1
if j % 2 == 0:
s = k + 400
G.add_node(k4, pos=(s + 250, i - 335), label_pos=(s + 215, i - 580))
else:
s = k - 400
G.add_node(k4, pos=(s - 250, i - 0), label_pos=(s - 245, i - 270))
if v4[k4] != '':
G.add_edge(k2, k4, port=v4[k4])
else:
G.add_edge(k2, k4, port='')
backends_servers.append(k4)
pos = nx.get_node_attributes(G, 'pos') pos = nx.get_node_attributes(G, 'pos')
pos_label = nx.get_node_attributes(G, 'label_pos') pos_label = nx.get_node_attributes(G, 'label_pos')
edge_labels = nx.get_edge_attributes(G, 'port') edge_labels = nx.get_edge_attributes(G, 'port')
try: try:
plt.figure(10, figsize=(10, 15)) plt.figure(10, figsize=(10, 20))
nx.draw(G, pos, with_labels=False, font_weight='bold', width=3, alpha=0.1, linewidths=5) nx.draw(G, pos, with_labels=False, font_weight='bold', width=3, alpha=0.1, linewidths=5)
nx.draw_networkx_nodes(G, pos, node_color="skyblue", node_size=100, alpha=0.8, node_shape="p") nx.draw_networkx_nodes(G, pos, node_color="#5d9ceb", node_size=100, alpha=0.8, node_shape="h")
nx.draw_networkx_labels(G, pos=pos_label, alpha=1, font_color="green", font_size=10) nx.draw_networkx_labels(G, pos=pos_label, alpha=1, font_color="#5CB85C", font_size=10)
nx.draw_networkx_edges(G, pos, width=0.5, alpha=0.5, edge_color="#5D9CEB", arrows=False) nx.draw_networkx_edges(G, pos, width=0.3, alpha=0.7, edge_color="#5D9CEB", arrows=False)
nx.draw_networkx_edge_labels(G, pos, label_pos=0.5, font_color="blue", edge_labels=edge_labels, font_size=8) nx.draw_networkx_edge_labels(G, pos, alpha=0.4, label_pos=0.5, font_color="#5d9ceb", edge_labels=edge_labels, font_size=8)
plt.savefig("map.png") plt.savefig("map.png")
plt.show() plt.show()
@ -896,7 +1009,6 @@ if serv is not None and act == "showMap":
os.getcwd()) + "/map" + date + ".png" os.getcwd()) + "/map" + date + ".png"
output, stderr = funct.subprocess_execute(cmd) output, stderr = funct.subprocess_execute(cmd)
print(stderr) print(stderr)
print('<img src="/map%s.png" alt="map">' % date) print('<img src="/map%s.png" alt="map">' % date)
if form.getvalue('servaction') is not None: if form.getvalue('servaction') is not None:
@ -1042,7 +1154,7 @@ if form.getvalue('master'):
commands = ["chmod +x " + script + " && ./" + script + " PROXY=" + proxy_serv + " SSH_PORT=" + ssh_port + commands = ["chmod +x " + script + " && ./" + script + " PROXY=" + proxy_serv + " SSH_PORT=" + ssh_port +
" ETH=" + ETH + " IP=" + str(IP) + " MASTER=MASTER" + " SYN_FLOOD=" + syn_flood + " HOST=" + str(master) + " ETH=" + ETH + " IP=" + str(IP) + " MASTER=MASTER" + " SYN_FLOOD=" + syn_flood + " HOST=" + str(master) +
" USER=" + str(ssh_user_name) + " PASS=" + str(ssh_user_password) + " KEY=" + str(ssh_key_name)] " USER=" + str(ssh_user_name) + " PASS='" + str(ssh_user_password) + "' KEY=" + str(ssh_key_name)]
output, error = funct.subprocess_execute(commands[0]) output, error = funct.subprocess_execute(commands[0])
@ -1083,7 +1195,7 @@ if form.getvalue('master_slave'):
commands = ["chmod +x " + script + " && ./" + script + " PROXY=" + proxy_serv + " SSH_PORT=" + ssh_port + commands = ["chmod +x " + script + " && ./" + script + " PROXY=" + proxy_serv + " SSH_PORT=" + ssh_port +
" ETH=" + ETH + " IP=" + IP + " MASTER=BACKUP" + " HOST=" + str(slave) + " ETH=" + ETH + " IP=" + IP + " MASTER=BACKUP" + " HOST=" + str(slave) +
" USER=" + str(ssh_user_name) + " PASS=" + str(ssh_user_password) + " KEY=" + str(ssh_key_name)] " USER=" + str(ssh_user_name) + " PASS='" + str(ssh_user_password) + "' KEY=" + str(ssh_key_name)]
output, error = funct.subprocess_execute(commands[0]) output, error = funct.subprocess_execute(commands[0])
@ -1121,7 +1233,7 @@ if form.getvalue('masteradd'):
commands = ["chmod +x " + script + " && ./" + script + " PROXY=" + proxy_serv + commands = ["chmod +x " + script + " && ./" + script + " PROXY=" + proxy_serv +
" SSH_PORT=" + ssh_port + " ETH=" + ETH + " SSH_PORT=" + ssh_port + " ETH=" + ETH +
" IP=" + str(IP) + " MASTER=MASTER" + " RESTART=" + kp + " ADD_VRRP=1 HOST=" + str(master) + " IP=" + str(IP) + " MASTER=MASTER" + " RESTART=" + kp + " ADD_VRRP=1 HOST=" + str(master) +
" USER=" + str(ssh_user_name) + " PASS=" + str(ssh_user_password) + " KEY=" + str(ssh_key_name)] " USER=" + str(ssh_user_name) + " PASS='" + str(ssh_user_password) + "' KEY=" + str(ssh_key_name)]
output, error = funct.subprocess_execute(commands[0]) output, error = funct.subprocess_execute(commands[0])
@ -1155,7 +1267,7 @@ if form.getvalue('masteradd_slave'):
commands = ["chmod +x " + script + " && ./" + script + " PROXY=" + proxy_serv + commands = ["chmod +x " + script + " && ./" + script + " PROXY=" + proxy_serv +
" SSH_PORT=" + ssh_port + " ETH=" + ETH + " SSH_PORT=" + ssh_port + " ETH=" + ETH +
" IP=" + str(IP) + " MASTER=BACKUP" + " RESTART=" + kp + " ADD_VRRP=1 HOST=" + str(slave) + " IP=" + str(IP) + " MASTER=BACKUP" + " RESTART=" + kp + " ADD_VRRP=1 HOST=" + str(slave) +
" USER=" + str(ssh_user_name) + " PASS=" + str(ssh_user_password) + " KEY=" + str(ssh_key_name)] " USER=" + str(ssh_user_name) + " PASS='" + str(ssh_user_password) + "' KEY=" + str(ssh_key_name)]
output, error = funct.subprocess_execute(commands[0]) output, error = funct.subprocess_execute(commands[0])
@ -1250,8 +1362,8 @@ if form.getvalue('haproxy_exp_install'):
commands = ["chmod +x " + script + " && ./" + script + " PROXY=" + proxy_serv + commands = ["chmod +x " + script + " && ./" + script + " PROXY=" + proxy_serv +
" STAT_PORT=" + stats_port + " STAT_FILE=" + server_state_file + " STAT_PORT=" + stats_port + " STAT_FILE=" + server_state_file +
" SSH_PORT=" + ssh_port + " STAT_PAGE=" + stat_page + " SSH_PORT=" + ssh_port + " STAT_PAGE=" + stat_page +
" STATS_USER=" + stats_user + " STATS_PASS=" + stats_password + " HOST=" + serv + " STATS_USER=" + stats_user + " STATS_PASS='" + stats_password + "' HOST=" + serv +
" USER=" + ssh_user_name + " PASS=" + ssh_user_password + " KEY=" + ssh_key_name] " USER=" + ssh_user_name + " PASS='" + ssh_user_password + "' KEY=" + ssh_key_name]
output, error = funct.subprocess_execute(commands[0]) output, error = funct.subprocess_execute(commands[0])
@ -1286,8 +1398,8 @@ if form.getvalue('nginx_exp_install'):
commands = ["chmod +x " + script + " && ./" + script + " PROXY=" + proxy_serv + commands = ["chmod +x " + script + " && ./" + script + " PROXY=" + proxy_serv +
" STAT_PORT=" + stats_port + " SSH_PORT=" + ssh_port + " STAT_PAGE=" + stats_page + " STAT_PORT=" + stats_port + " SSH_PORT=" + ssh_port + " STAT_PAGE=" + stats_page +
" STATS_USER=" + stats_user + " STATS_PASS=" + stats_password + " HOST=" + serv + " STATS_USER=" + stats_user + " STATS_PASS='" + stats_password + "' HOST=" + serv +
" USER=" + ssh_user_name + " PASS=" + ssh_user_password + " KEY=" + ssh_key_name] " USER=" + ssh_user_name + " PASS='" + ssh_user_password + "' KEY=" + ssh_key_name]
output, error = funct.subprocess_execute(commands[0]) output, error = funct.subprocess_execute(commands[0])
@ -1317,7 +1429,7 @@ if form.getvalue('node_exp_install'):
proxy_serv = '' proxy_serv = ''
commands = ["chmod +x " + script + " && ./" + script + " PROXY=" + proxy_serv + " SSH_PORT=" + ssh_port + commands = ["chmod +x " + script + " && ./" + script + " PROXY=" + proxy_serv + " SSH_PORT=" + ssh_port +
" HOST=" + serv + " USER=" + ssh_user_name + " PASS=" + ssh_user_password + " KEY=" + ssh_key_name] " HOST=" + serv + " USER=" + ssh_user_name + " PASS='" + ssh_user_password + "' KEY=" + ssh_key_name]
output, error = funct.subprocess_execute(commands[0]) output, error = funct.subprocess_execute(commands[0])
@ -1384,7 +1496,7 @@ if form.getvalue('backup') or form.getvalue('deljob') or form.getvalue('backupup
print('success: Backup job has been created') print('success: Backup job has been created')
funct.logging('backup ', ' a new backup job for server ' + serv + ' has been created', haproxywi=1, login=1) funct.logging('backup ', ' a new backup job for server ' + serv + ' has been created', haproxywi=1, login=1)
else: else:
print('error: Cannot add job into DB') print('error: Cannot add the job into DB')
elif deljob: elif deljob:
sql.delete_backups(deljob) sql.delete_backups(deljob)
print('Ok') print('Ok')
@ -1560,6 +1672,29 @@ if form.getvalue('new_waf_metrics'):
print(json.dumps(metrics)) print(json.dumps(metrics))
if form.getvalue('new_nginx_metrics'):
serv = form.getvalue('server')
time_range = form.getvalue('time_range')
metric = sql.select_nginx_metrics(serv, time_range=time_range)
metrics = {'chartData': {}}
metrics['chartData']['labels'] = {}
labels = ''
curr_con = ''
for i in metric:
label = str(i[2])
label = label.split(' ')[1]
labels += label + ','
curr_con += str(i[1]) + ','
metrics['chartData']['labels'] = labels
metrics['chartData']['curr_con'] = curr_con
metrics['chartData']['server'] = serv
import json
print(json.dumps(metrics))
if form.getvalue('get_hap_v'): if form.getvalue('get_hap_v'):
output = funct.check_haproxy_version(serv) output = funct.check_haproxy_version(serv)
print(output) print(output)
@ -1590,7 +1725,7 @@ if form.getvalue('bwlists_create'):
open(list_path, 'a').close() open(list_path, 'a').close()
print('success: ') print('success: ')
try: try:
funct.logging(serv, 'has created ' + color + ' list ' + list_name, haproxywi=1, login=1) funct.logging(serv, 'has been created ' + color + ' list ' + list_name, haproxywi=1, login=1)
except Exception: except Exception:
pass pass
except IOError as e: except IOError as e:
@ -1631,7 +1766,7 @@ if form.getvalue('bwlists_save'):
else: else:
print('success: Edited ' + color + ' list was uploaded to ' + serv + ' , ') print('success: Edited ' + color + ' list was uploaded to ' + serv + ' , ')
try: try:
funct.logging(serv, 'has edited ' + color + ' list ' + bwlists_save, haproxywi=1, login=1) funct.logging(serv, 'has been edited the ' + color + ' list ' + bwlists_save, haproxywi=1, login=1)
except Exception: except Exception:
pass pass
@ -1676,9 +1811,9 @@ if form.getvalue('bwlists_delete'):
if error: if error:
print('error: Deleting fail: %s , ' % error) print('error: Deleting fail: %s , ' % error)
else: else:
print('success: ' + color + ' list was delete on ' + serv + ' , ') print('success: the ' + color + ' list has been deleted on ' + serv + ' , ')
try: try:
funct.logging(serv, 'has deleted ' + color + ' list ' + bwlists_delete, haproxywi=1, login=1) funct.logging(serv, 'has been deleted the ' + color + ' list ' + bwlists_delete, haproxywi=1, login=1)
except Exception: except Exception:
pass pass
@ -1732,7 +1867,7 @@ if form.getvalue('change_waf_mode'):
serv = sql.select_server_by_name(server_hostname) serv = sql.select_server_by_name(server_hostname)
commands = ["sudo sed -i 's/^SecRuleEngine.*/SecRuleEngine %s/' %s/waf/modsecurity.conf " % (waf_mode, haproxy_dir)] commands = ["sudo sed -i 's/^SecRuleEngine.*/SecRuleEngine %s/' %s/waf/modsecurity.conf " % (waf_mode, haproxy_dir)]
funct.ssh_command(serv, commands) funct.ssh_command(serv, commands)
funct.logging(serv, 'Was changed WAF mod to ' + waf_mode, haproxywi=1, login=1) funct.logging(serv, 'Has been changed WAF mod to ' + waf_mode, haproxywi=1, login=1)
error_mess = 'error: All fields must be completed' error_mess = 'error: All fields must be completed'
@ -1761,12 +1896,10 @@ if form.getvalue('newuser') is not None:
roles=sql.select_roles(), roles=sql.select_roles(),
adding=1) adding=1)
print(template) print(template)
funct.logging('a new user ' + new_user, ' has created ', haproxywi=1, login=1) funct.logging('a new user ' + new_user, ' has been created ', haproxywi=1, login=1)
else: else:
print('error: dalsdm') print('error: dalsdm')
funct.logging(new_user, ' tried to privilege escalation', haproxywi=1, login=1) funct.logging(new_user, ' tried to privilege escalation', haproxywi=1, login=1)
else:
print('error: dalsdm123')
if form.getvalue('userdel') is not None: if form.getvalue('userdel') is not None:
userdel = form.getvalue('userdel') userdel = form.getvalue('userdel')
@ -1776,7 +1909,7 @@ if form.getvalue('userdel') is not None:
username = u.username username = u.username
if sql.delete_user(userdel): if sql.delete_user(userdel):
sql.delete_user_groups(userdel) sql.delete_user_groups(userdel)
funct.logging(username, ' has deleted user ', haproxywi=1, login=1) funct.logging(username, ' has been deleted user ', haproxywi=1, login=1)
print("Ok") print("Ok")
if form.getvalue('updateuser') is not None: if form.getvalue('updateuser') is not None:
@ -1791,7 +1924,7 @@ if form.getvalue('updateuser') is not None:
if funct.check_user_group(): if funct.check_user_group():
if funct.is_admin(level=role_id): if funct.is_admin(level=role_id):
sql.update_user(new_user, email, role, user_id, activeuser) sql.update_user(new_user, email, role, user_id, activeuser)
funct.logging(new_user, ' has updated user ', haproxywi=1, login=1) funct.logging(new_user, ' has been updated user ', haproxywi=1, login=1)
else: else:
funct.logging(new_user, ' tried to privilege escalation', haproxywi=1, login=1) funct.logging(new_user, ' tried to privilege escalation', haproxywi=1, login=1)
@ -2148,6 +2281,19 @@ if form.getvalue('updatesettings') is not None:
funct.logging('value ' + val, ' changed settings ' + settings, haproxywi=1, login=1) funct.logging('value ' + val, ' changed settings ' + settings, haproxywi=1, login=1)
print("Ok") print("Ok")
if form.getvalue('getuserservices'):
user_id = form.getvalue('getuserservices')
groups = []
u_g = sql.select_user_groups(user_id)
for g in u_g:
groups.append(g.user_group_id)
from jinja2 import Environment, FileSystemLoader
env = Environment(loader=FileSystemLoader('templates/ajax'), autoescape=True)
template = env.get_template('/show_user_services.html')
template = template.render(user_services=sql.select_user_services(user_id), id=user_id)
print(template)
if form.getvalue('getusergroups'): if form.getvalue('getusergroups'):
user_id = form.getvalue('getusergroups') user_id = form.getvalue('getusergroups')
groups = [] groups = []
@ -2171,7 +2317,15 @@ if form.getvalue('changeUserGroupId') is not None:
continue continue
sql.update_user_groups(groups=group[0], user_group_id=group_id) sql.update_user_groups(groups=group[0], user_group_id=group_id)
funct.logging('localhost', ' has upgraded groups for user: ' + user, haproxywi=1, login=1) funct.logging('localhost', ' has been updated groups for user: ' + user, haproxywi=1, login=1)
if form.getvalue('changeUserServicesId') is not None:
user_id = form.getvalue('changeUserServicesId')
services = form.getvalue('changeUserServices')
user = form.getvalue('changeUserServicesUser')
if sql.update_user_services(services=services, user_id=user_id):
funct.logging('localhost', ' has been updated services for user: ' + user, haproxywi=1, login=1)
if form.getvalue('changeUserCurrentGroupId') is not None: if form.getvalue('changeUserCurrentGroupId') is not None:
group_id = form.getvalue('changeUserCurrentGroupId') group_id = form.getvalue('changeUserCurrentGroupId')
@ -2318,8 +2472,9 @@ if form.getvalue('nginxConnections'):
user = sql.get_setting('nginx_stats_user') user = sql.get_setting('nginx_stats_user')
password = sql.get_setting('nginx_stats_password') password = sql.get_setting('nginx_stats_password')
page = sql.get_setting('nginx_stats_page') page = sql.get_setting('nginx_stats_page')
url = 'http://{}:{}/{}'.format(serv, port, page)
r = requests.get('http://' + serv + ':' + port + '/' + page, auth=(user, password)) r = requests.get(url, auth=(user, password))
if r.status_code == 200: if r.status_code == 200:
bin_bout = [0, 0] bin_bout = [0, 0]
@ -2398,7 +2553,7 @@ if form.getvalue('lets_domain'):
commands = ["chmod +x " + script + " && ./" + script + " PROXY=" + proxy_serv + " haproxy_dir=" + haproxy_dir + commands = ["chmod +x " + script + " && ./" + script + " PROXY=" + proxy_serv + " haproxy_dir=" + haproxy_dir +
" DOMAIN=" + lets_domain + " EMAIL=" + lets_email + " SSH_PORT=" + ssh_port + " SSL_PATH=" + ssl_path + " DOMAIN=" + lets_domain + " EMAIL=" + lets_email + " SSH_PORT=" + ssh_port + " SSL_PATH=" + ssl_path +
" HOST=" + serv + " USER=" + ssh_user_name + " PASS=" + ssh_user_password + " KEY=" + ssh_key_name] " HOST=" + serv + " USER=" + ssh_user_name + " PASS='" + ssh_user_password + "' KEY=" + ssh_key_name]
output, error = funct.subprocess_execute(commands[0]) output, error = funct.subprocess_execute(commands[0])

View File

@ -14,7 +14,7 @@ print('Content-type: text/html\n')
funct.check_login() funct.check_login()
try: try:
user, user_id, role, token, servers = funct.get_users_params() user, user_id, role, token, servers, user_services = funct.get_users_params()
groups = sql.select_groups() groups = sql.select_groups()
user_group = funct.get_user_group(id=1) user_group = funct.get_user_group(id=1)
@ -80,7 +80,7 @@ try:
cmd = "systemctl is-active roxy-wi-portscanner" cmd = "systemctl is-active roxy-wi-portscanner"
port_scanner, stderr = funct.subprocess_execute(cmd) port_scanner, stderr = funct.subprocess_execute(cmd)
except Exception as e: except:
role = '' role = ''
user = '' user = ''
users = '' users = ''
@ -101,7 +101,6 @@ except Exception as e:
is_checker_worker = '' is_checker_worker = ''
is_metrics_worker = '' is_metrics_worker = ''
token = '' token = ''
print(str(e))
template = template.render(h2=1, template = template.render(h2=1,
@ -134,5 +133,6 @@ template = template.render(h2=1,
is_checker_worker=is_checker_worker, is_checker_worker=is_checker_worker,
is_metrics_worker=is_metrics_worker, is_metrics_worker=is_metrics_worker,
host=host, host=host,
user_services=user_services,
token=token) token=token)
print(template) print(template)

View File

@ -12,7 +12,7 @@ print('Content-type: text/html\n')
funct.check_login() funct.check_login()
try: try:
user, user_id, role, token, servers = funct.get_users_params(virt=1) user, user_id, role, token, servers, user_services = funct.get_users_params(virt=1)
except Exception as e: except Exception as e:
print(str(e)) print(str(e))
@ -52,5 +52,6 @@ output_from_parsed_template = template.render(h2=1, autorefresh=0,
history=history, history=history,
port_scanner=''.join(port_scanner), port_scanner=''.join(port_scanner),
port_scanner_stderr=port_scanner_stderr, port_scanner_stderr=port_scanner_stderr,
user_services=user_services,
token=token) token=token)
print(output_from_parsed_template) print(output_from_parsed_template)

View File

@ -10,7 +10,7 @@ print('Content-type: text/html\n')
funct.check_login() funct.check_login()
funct.page_for_admin(level=2) funct.page_for_admin(level=2)
try: try:
user, user_id, role, token, servers = funct.get_users_params() user, user_id, role, token, servers, user_services = funct.get_users_params()
if role == 1: if role == 1:
groups=sql.select_groups() groups=sql.select_groups()
else: else:
@ -37,5 +37,6 @@ output_from_parsed_template = template.render(title="Servers provisioning",
servers=sql.select_provisioned_servers(), servers=sql.select_provisioned_servers(),
providers=sql.select_providers(user_group), providers=sql.select_providers(user_group),
is_terraform=is_terraform, is_terraform=is_terraform,
user_services=user_services,
token=token) token=token)
print(output_from_parsed_template) print(output_from_parsed_template)

View File

@ -1,16 +1,18 @@
#!/usr/bin/env python3 #!/usr/bin/env python3
import os import os
import sql
import funct import funct
from jinja2 import Environment, FileSystemLoader from jinja2 import Environment, FileSystemLoader
env = Environment(loader=FileSystemLoader('templates/'), autoescape=True, extensions=['jinja2.ext.loopcontrols']) env = Environment(loader=FileSystemLoader('templates/'), autoescape=True, extensions=['jinja2.ext.loopcontrols'])
template = env.get_template('sections.html') template = env.get_template('sections.html')
print('Content-type: text/html\n') print('Content-type: text/html\n')
funct.check_login() funct.check_login(service=1)
form = funct.form form = funct.form
serv = form.getvalue('serv') serv = form.getvalue('serv')
section = form.getvalue('section') section = form.getvalue('section')
is_serv_protected = sql.is_serv_protected(serv)
sections = "" sections = ""
config_read = "" config_read = ""
cfg = "" cfg = ""
@ -21,7 +23,7 @@ start_line = ""
end_line = "" end_line = ""
try: try:
user, user_id, role, token, servers = funct.get_users_params() user, user_id, role, token, servers, user_services = funct.get_users_params()
except Exception: except Exception:
pass pass
@ -90,5 +92,7 @@ template = template.render(h2=1, title="Working with HAProxy configs",
end_line=end_line, end_line=end_line,
section=section, section=section,
sections=sections, sections=sections,
is_serv_protected=is_serv_protected,
user_services=user_services,
token=token) token=token)
print(template) print(template)

View File

@ -10,7 +10,7 @@ print('Content-type: text/html\n')
funct.check_login() funct.check_login()
funct.page_for_admin(level=2) funct.page_for_admin(level=2)
try: try:
user, user_id, role, token, servers = funct.get_users_params() user, user_id, role, token, servers, user_services = funct.get_users_params()
ldap_enable = sql.get_setting('ldap_enable') ldap_enable = sql.get_setting('ldap_enable')
user_group = funct.get_user_group(id=1) user_group = funct.get_user_group(id=1)
settings = sql.get_setting('', all=1) settings = sql.get_setting('', all=1)
@ -35,5 +35,6 @@ output_from_parsed_template = template.render(title="Servers: ",
backups=sql.select_backups(), backups=sql.select_backups(),
page="servers.py", page="servers.py",
geoip_country_codes=geoip_country_codes, geoip_country_codes=geoip_country_codes,
user_services=user_services,
ldap_enable=ldap_enable) ldap_enable=ldap_enable)
print(output_from_parsed_template) print(output_from_parsed_template)

View File

@ -14,7 +14,7 @@ print('Content-type: text/html\n')
funct.check_login() funct.check_login()
try: try:
user, user_id, role, token, servers = funct.get_users_params() user, user_id, role, token, servers, user_services = funct.get_users_params()
user_group = funct.get_user_group(id=1) user_group = funct.get_user_group(id=1)
cmd = "systemctl is-active roxy-wi-smon" cmd = "systemctl is-active roxy-wi-smon"
smon_status, stderr = funct.subprocess_execute(cmd) smon_status, stderr = funct.subprocess_execute(cmd)
@ -54,5 +54,6 @@ template = template.render(h2=1, title=title,
smon_error=stderr, smon_error=stderr,
action=action, action=action,
sort=sort, sort=sort,
user_services=user_services,
token=token) token=token)
print(template) print(template)

View File

@ -257,7 +257,8 @@ def delete_server(server_id):
def update_hapwi_server(server_id, alert, metrics, active, service_name): def update_hapwi_server(server_id, alert, metrics, active, service_name):
try: try:
if service_name == 'nginx': if service_name == 'nginx':
update_hapwi = Server.update(nginx_alert=alert, metrics=metrics, nginx_active=active).where( update_hapwi = Server.update(nginx_alert=alert, metrics=metrics, nginx_active=active,
nginx_metrics=metrics).where(
Server.server_id == server_id) Server.server_id == server_id)
else: else:
update_hapwi = Server.update(alert=alert, metrics=metrics, active=active).where( update_hapwi = Server.update(alert=alert, metrics=metrics, active=active).where(
@ -523,6 +524,18 @@ def get_api_token(token):
return True if token == user_token.token else False return True if token == user_token.token else False
def get_user_id_by_api_token(token):
query = (User
.select(User.user_id)
.join(ApiToken, on=(ApiToken.user_name == User.username))
.where(ApiToken.token == token))
try:
query_res = query.execute()
except Exception as e:
return str(e)
for i in query_res:
return i.user_id
def get_username_groupid_from_api_token(token): def get_username_groupid_from_api_token(token):
try: try:
user_name = ApiToken.get(ApiToken.token == token) user_name = ApiToken.get(ApiToken.token == token)
@ -1069,6 +1082,13 @@ def insert_metrics_http(serv, http_2xx, http_3xx, http_4xx, http_5xx):
out_error(e) out_error(e)
def insert_nginx_metrics(serv, conn):
try:
NginxMetrics.insert(serv=serv, conn=conn, date=funct.get_data('regular')).execute()
except Exception as e:
out_error(e)
def select_waf_metrics_enable_server(ip): def select_waf_metrics_enable_server(ip):
query = Waf.select(Waf.metrics).join(Server, on=(Waf.server_id == Server.server_id)).where(Server.ip == ip) query = Waf.select(Waf.metrics).join(Server, on=(Waf.server_id == Server.server_id)).where(Server.ip == ip)
try: try:
@ -1092,14 +1112,14 @@ def select_waf_servers(serv):
def select_waf_servers_metrics_for_master(): def select_waf_servers_metrics_for_master():
cursor = conn.cursor() query = Server.select(Server.ip).join(Waf, on=(Waf.server_id == Server.server_id)).where((Server.enable == 1) &
sql = """ select servers.ip from servers left join waf as waf on waf.server_id = servers.id where servers.enable = 1 and waf.metrics = '1' """ Waf.metrics == 1)
try: try:
cursor.execute(sql) query_res = query.execute()
except Exception as e: except Exception as e:
out_error(e) out_error(e)
else: else:
return cursor.fetchall() return query_res
def select_waf_servers_metrics(uuid): def select_waf_servers_metrics(uuid):
@ -1163,6 +1183,42 @@ def select_waf_metrics(serv, **kwargs):
return cursor.fetchall() return cursor.fetchall()
def select_nginx_metrics(serv, **kwargs):
cursor = conn.cursor()
if mysql_enable == '1':
if kwargs.get('time_range') == '60':
date_from = "and date > now() - INTERVAL 60 minute and rowid % 2 = 0"
elif kwargs.get('time_range') == '180':
date_from = "and date > now() - INTERVAL 180 minute and rowid % 5 = 0"
elif kwargs.get('time_range') == '360':
date_from = "and date > now() - INTERVAL 360 minute and rowid % 7 = 0"
elif kwargs.get('time_range') == '720':
date_from = "and date > now() - INTERVAL 720 minute and rowid % 9 = 0"
else:
date_from = "and date > now() - INTERVAL 30 minute"
sql = """ select * from nginx_metrics where serv = '{serv}' {date_from} order by `date` desc limit 60 """.format(serv=serv, date_from=date_from)
else:
if kwargs.get('time_range') == '60':
date_from = "and date > datetime('now', '-60 minutes', 'localtime') and rowid % 2 = 0"
elif kwargs.get('time_range') == '180':
date_from = "and date > datetime('now', '-180 minutes', 'localtime') and rowid % 5 = 0"
elif kwargs.get('time_range') == '360':
date_from = "and date > datetime('now', '-360 minutes', 'localtime') and rowid % 7 = 0"
elif kwargs.get('time_range') == '720':
date_from = "and date > datetime('now', '-720 minutes', 'localtime') and rowid % 9 = 0"
else:
date_from = "and date > datetime('now', '-30 minutes', 'localtime')"
sql = """ select * from (select * from nginx_metrics where serv = '{serv}' {date_from} order by `date`) order by `date` """.format(serv=serv, date_from=date_from)
try:
cursor.execute(sql)
except Exception as e:
out_error(e)
else:
return cursor.fetchall()
def insert_waf_metrics_enable(serv, enable): def insert_waf_metrics_enable(serv, enable):
try: try:
server_id = Server.get(Server.ip == serv).server_id server_id = Server.get(Server.ip == serv).server_id
@ -1309,6 +1365,14 @@ def delete_http_metrics():
out_error(e) out_error(e)
def delete_nginx_metrics():
query = NginxMetrics.delete().where(NginxMetrics.date < funct.get_data('regular', timedelta_minus=3))
try:
query.execute()
except Exception as e:
out_error(e)
def select_metrics(serv, **kwargs): def select_metrics(serv, **kwargs):
cursor = conn.cursor() cursor = conn.cursor()
@ -1384,16 +1448,26 @@ def select_metrics_http(serv, **kwargs):
def select_servers_metrics_for_master(**kwargs): def select_servers_metrics_for_master(**kwargs):
cursor = conn.cursor()
sql = """select ip from servers where metrics = 1 """
if kwargs.get('group') is not None: if kwargs.get('group') is not None:
sql = """select ip from servers where metrics = 1 and groups = '%s' """ % kwargs.get('group') query = Server.select(Server.ip).where((Server.metrics == 1) & (Server.groups == kwargs.get(group)))
else:
query = Server.select(Server.ip).where(Server.metrics == 1)
try: try:
cursor.execute(sql) query_res = query.execute()
except Exception as e: except Exception as e:
out_error(e) out_error(e)
else: else:
return cursor.fetchall() return query_res
def select_nginx_servers_metrics_for_master():
query = Server.select(Server.ip).where(Server.nginx_metrics == 1)
try:
query_res = query.execute()
except Exception as e:
out_error(e)
else:
return query_res
def select_servers_metrics(): def select_servers_metrics():
@ -2630,3 +2704,23 @@ def is_serv_protected(serv):
return "" return ""
else: else:
return True if query_res.protected else False return True if query_res.protected else False
def select_user_services(user_id):
try:
query_res = User.get(User.user_id == user_id).user_services
except Exception as e:
out_error(e)
return ""
else:
return query_res
def update_user_services(services, user_id):
try:
User.update(user_services=services).where(User.user_id == user_id).execute()
return True
except Exception as e:
out_error(e)
return False

View File

@ -64,7 +64,8 @@
<br /><span class="add-button" title="Add group" id="add-group-button">+ Add</span> <br /><span class="add-button" title="Add group" id="add-group-button">+ Add</span>
<br /><br /> <br /><br />
<div class="add-note alert addName alert-info" style="width: inherit; margin-right: 15px;"> <div class="add-note alert addName alert-info" style="width: inherit; margin-right: 15px;">
How to setup groups you can read in this <a href="https://roxy-wi.org/howto.py?howto=setup" title="How to setup servers, group and SSH credentials" target="_blank">article</a> How to setup groups you can read in this <a href="https://roxy-wi.org/howto.py?howto=server_groups" title="How to use groups and roles" target="_blank">article</a>
and this <a href="https://roxy-wi.org/howto.py?howto=setup" title="How to setup servers, group and SSH credentials" target="_blank">article</a>
</div> </div>
</div> </div>
<div id="servers"> <div id="servers">

View File

@ -57,13 +57,14 @@
<ul class="menu"> <ul class="menu">
{% if user %} {% if user %}
<li><a href="/app/overview.py" title="Server and service status" class="overview-link">Overview</a></li> <li><a href="/app/overview.py" title="Server and service status" class="overview-link">Overview</a></li>
{% if '1' in user_services %}
<li class="p_menu"><a title="Actions with Haproxy" class="config-show">Haproxy</a> <li class="p_menu"><a title="Actions with Haproxy" class="config-show">Haproxy</a>
<ul class="v_menu"> <ul class="v_menu">
<li><a href="/app/hapservers.py" title="HAProxy servers overview" class="overview-link head-submenu">Overview</a> </li> <li><a href="/app/hapservers.py" title="HAProxy servers overview" class="overview-link head-submenu">Overview</a> </li>
<li><a href="/app/config.py" title="Working with HAProxy configs" class="edit head-submenu">Configs</a></li> <li><a href="/app/config.py" title="Working with HAProxy configs" class="edit head-submenu">Configs</a></li>
<li><a href="/app/viewsttats.py" title="HAProxy statistics " class="stats head-submenu">Stats</a></li> <li><a href="/app/viewsttats.py" title="HAProxy statistics " class="stats head-submenu">Stats</a></li>
<li><a href="/app/runtimeapi.py" title="Runtime API - Roxy-WI" class="runtime head-submenu">Runtime API</a></li> <li><a href="/app/runtimeapi.py" title="Runtime API - Roxy-WI" class="runtime head-submenu">Runtime API</a></li>
<li><a href="/app/metrics.py" title="Metrics" class="metrics head-submenu">Metrics</a></li> <li><a href="/app/metrics.py" title="HAProxy's metrics" class="metrics head-submenu">Metrics</a></li>
{% if role <= 3 %} {% if role <= 3 %}
<li><a href="/app/add.py#proxy" title="Add proxy: Create proxy - Roxy-WI" class="add-proxy head-submenu" id="add1">Add proxy</a></li> <li><a href="/app/add.py#proxy" title="Add proxy: Create proxy - Roxy-WI" class="add-proxy head-submenu" id="add1">Add proxy</a></li>
<li><a href="/app/versions.py" title="Working with versions HAProxy configs" class="version head-submenu">Versions</a></li> <li><a href="/app/versions.py" title="Working with versions HAProxy configs" class="version head-submenu">Versions</a></li>
@ -73,19 +74,23 @@
{% endif %} {% endif %}
</ul> </ul>
</li> </li>
{% endif %}
{% if '2' in user_services %}
<li class="p_menu"> <li class="p_menu">
<a title="Actions with Nginx" class="nginx-menu">Nginx</a> <a title="Actions with Nginx" class="nginx-menu">Nginx</a>
<ul class="v_menu"> <ul class="v_menu">
<li><a href="/app/hapservers.py?service=nginx" title="Overview Nginx servers" class="overview-link head-submenu">Overview</a></li> <li><a href="/app/hapservers.py?service=nginx" title="Overview Nginx servers" class="overview-link head-submenu">Overview</a></li>
<li><a href="/app/config.py?service=nginx" title="Working with Nginx configs" class="edit head-submenu">Configs</a></li> <li><a href="/app/config.py?service=nginx" title="Working with Nginx configs" class="edit head-submenu">Configs</a></li>
<li><a href="/app/viewsttats.py?service=nginx" title="Nginx statistics" class="stats head-submenu">Stats</a></li> <li><a href="/app/viewsttats.py?service=nginx" title="Nginx statistics" class="stats head-submenu">Stats</a></li>
<li><a href="/app/metrics.py?service=nginx" title="Nginx's metrics" class="metrics head-submenu">Metrics</a></li>
{% if role <= 3 %} {% if role <= 3 %}
<li><a href="/app/versions.py?service=nginx" title="Working with versions Nginx configs" class="version head-submenu">Versions</a></li> <li><a href="/app/versions.py?service=nginx" title="Working with versions Nginx configs" class="version head-submenu">Versions</a></li>
<li><a href="/app/add.py?service=nginx#ssl" title="Add proxy: Upload SSL certificates - Roxy-WI" class="cert head-submenu" id="add3">SSL</a></li> <li><a href="/app/add.py?service=nginx#ssl" title="Add proxy: Upload SSL certificates - Roxy-WI" class="cert head-submenu" id="add3">SSL</a></li>
{% endif %} {% endif %}
</ul> </ul>
</li> </li>
{% endif %}
{% if '3' in user_services %}
{% if role <= 2 %} {% if role <= 2 %}
<li class="p_menu"> <li class="p_menu">
<a title="Keepalived" class="ha">Keepalived</a> <a title="Keepalived" class="ha">Keepalived</a>
@ -96,6 +101,7 @@
<li><a href="/app/versions.py?service=keepalived" title="Working with versions Keepalived configs" class="version head-submenu keepalived_versions">Versions</a></li> <li><a href="/app/versions.py?service=keepalived" title="Working with versions Keepalived configs" class="version head-submenu keepalived_versions">Versions</a></li>
</ul> </ul>
</li> </li>
{% endif %}
{% endif %} {% endif %}
<li class="p_menu"> <li class="p_menu">
<a title="Monitoring tools" class="stats">Monitoring</a> <a title="Monitoring tools" class="stats">Monitoring</a>

View File

@ -42,7 +42,7 @@
<td class="checkbox help_cursor">{{ checkbox('hap', title='Roxy-WI will try to install HAProxy') }}</td> <td class="checkbox help_cursor">{{ checkbox('hap', title='Roxy-WI will try to install HAProxy') }}</td>
<td class="checkbox help_cursor">{{ checkbox('nginx', title='Roxy-WI will try to install Nginx') }}</td> <td class="checkbox help_cursor">{{ checkbox('nginx', title='Roxy-WI will try to install Nginx') }}</td>
<td class="checkbox help_cursor">{{ checkbox('virt_server', title='Roxy-WI will add VRRP address as a separated server', checked='checked') }}</td> <td class="checkbox help_cursor">{{ checkbox('virt_server', title='Roxy-WI will add VRRP address as a separated server', checked='checked') }}</td>
<td class="checkbox">{{ checkbox('syn_flood') }}</td> <td class="syn-flood-protection-field">{{ checkbox('syn_flood') }}</td>
<td> <td>
<button id="create" title="Create HA configuration">Create</button> <button id="create" title="Create HA configuration">Create</button>
</td> </td>

View File

@ -90,6 +90,7 @@
showOverviewServer('{{s.1}}', server_ip, '{{s.0}}', '{{service}}'); showOverviewServer('{{s.1}}', server_ip, '{{s.0}}', '{{service}}');
{% if service == 'nginx' %} {% if service == 'nginx' %}
showNginxConnections(server_ip) showNginxConnections(server_ip)
getNginxChartData(server_ip)
{% elif service == 'haproxy' %} {% elif service == 'haproxy' %}
showBytes(server_ip) showBytes(server_ip)
{% endif %} {% endif %}
@ -115,6 +116,7 @@
{% set checker_desc = 'Checker monitors Nginx services. If Nginx service is down, Checker will alert via Telegram' %} {% set checker_desc = 'Checker monitors Nginx services. If Nginx service is down, Checker will alert via Telegram' %}
{% set is_auto_start_enabled = s.8.0.17 %} {% set is_auto_start_enabled = s.8.0.17 %}
{% set is_checker_enabled = s.8.0.19 %} {% set is_checker_enabled = s.8.0.19 %}
{% set is_metrics_enabled = s.8.0.21 %}
{% if s.5.0.1 == 'active' %} {% if s.5.0.1 == 'active' %}
{% set additional_status_class = 'div-server-head-up' %} {% set additional_status_class = 'div-server-head-up' %}
{% else %} {% else %}
@ -130,6 +132,7 @@
{% set checker_desc = 'Checker monitors HAProxy services and its backends. If some backend or HAProxy service is down, Checker will alert via Telegram' %} {% set checker_desc = 'Checker monitors HAProxy services and its backends. If some backend or HAProxy service is down, Checker will alert via Telegram' %}
{% set is_auto_start_enabled = s.8.0.12 %} {% set is_auto_start_enabled = s.8.0.12 %}
{% set is_checker_enabled = s.8.0.8 %} {% set is_checker_enabled = s.8.0.8 %}
{% set is_metrics_enabled = s.8.0.9 %}
{% if s.5 != False %} {% if s.5 != False %}
{% set additional_status_class = 'div-server-head-up' %} {% set additional_status_class = 'div-server-head-up' %}
{% else %} {% else %}
@ -195,7 +198,11 @@
{% endif %} {% endif %}
</div> </div>
<div class="server-desc"> <div class="server-desc">
{% if s.3 is none %}
No description
{% else %}
{{s.3}} {{s.3}}
{% endif %}
<br /> <br />
{% if service == 'nginx' or service == 'keepalived' %} {% if service == 'nginx' or service == 'keepalived' %}
Version: {{s.5.0.0}} Process_num: {{s.5.0.3}} Version: {{s.5.0.0}} Process_num: {{s.5.0.3}}
@ -242,14 +249,12 @@
{% else %} {% else %}
{{ checkbox(id, title=checker_desc, value='1', desc='Checker') }} {{ checkbox(id, title=checker_desc, value='1', desc='Checker') }}
{% endif %} {% endif %}
{% if service == 'haproxy' %}
{% set id = 'metrics-' + s.8.0.0|string() %} {% set id = 'metrics-' + s.8.0.0|string() %}
{% if s.8.0.9 == 1 %} {% if is_metrics_enabled == 1 %}
{{ checkbox(id, title='Collecting metrics is enabled', value='1', desc='Metrics', checked='checked') }} {{ checkbox(id, title='Collecting metrics is enabled', value='1', desc='Metrics', checked='checked') }}
{% else %} {% else %}
{{ checkbox(id, title='Enable collecting metrics', value='1', desc='Metrics') }} {{ checkbox(id, title='Enable collecting metrics', value='1', desc='Metrics') }}
{% endif %} {% endif %}
{% endif %}
{% set id = 'active-' + s.8.0.0|string() %} {% set id = 'active-' + s.8.0.0|string() %}
{% if is_auto_start_enabled == 1 %} {% if is_auto_start_enabled == 1 %}
{{ checkbox(id, title='Auto Start is enabled', value='1', desc='Auto Start', checked='checked') }} {{ checkbox(id, title='Auto Start is enabled', value='1', desc='Auto Start', checked='checked') }}
@ -259,12 +264,8 @@
{% endif %} {% endif %}
</div> </div>
<div class="server-act-links"> <div class="server-act-links">
{% if service != 'keepalived' %}
<a href="/app/config.py?service={{service}}&serv={{s.2}}&showConfig" class="ui-button ui-widget ui-corner-all" title="Open running config">Config</a> <a href="/app/config.py?service={{service}}&serv={{s.2}}&showConfig" class="ui-button ui-widget ui-corner-all" title="Open running config">Config</a>
{% else %} <a href="/app/config.py?service={{service}}&serv={{s.2}}&showCompare" class="ui-button ui-widget ui-corner-all" title="Compare configs">Compare</a>
<a href="/app/config.py?service={{service}}" class="ui-button ui-widget ui-corner-all" title="Edit running config">Config</a>
{% endif %}
<a href="/app/config.py?service={{service}}&serv={{s.2}}&showCompare" class="ui-button ui-widget ui-corner-all" title="Compare configs">Compare</a>
{% if service != 'nginx' and service != 'keepalived' %} {% if service != 'nginx' and service != 'keepalived' %}
<a href="/app/config.py?serv={{s.2}}&showMap" class="ui-button ui-widget ui-corner-all" title="Show map">Map</a> <a href="/app/config.py?serv={{s.2}}&showMap" class="ui-button ui-widget ui-corner-all" title="Show map">Map</a>
{% endif %} {% endif %}
@ -295,7 +296,7 @@
{% endif %} {% endif %}
{% endfor %} {% endfor %}
</div> </div>
{% if serv and service == 'haproxy' %} {% if serv %}
<div style="clear: both; width: 95%;"> <div style="clear: both; width: 95%;">
<div style="padding-left: 25px;float: left;margin-top: -15px;"> <div style="padding-left: 25px;float: left;margin-top: -15px;">
<b>Time range:</b> <b>Time range:</b>
@ -312,6 +313,7 @@
</div> </div>
</div> </div>
{% for s in servers %} {% for s in servers %}
{% if service == 'haproxy' %}
<div id="server_metrics_div" class="chart-container" style="display: block; width: 91.3%; height: 300px;"> <div id="server_metrics_div" class="chart-container" style="display: block; width: 91.3%; height: 300px;">
<canvas id="{{s.2}}" role="img"></canvas> <canvas id="{{s.2}}" role="img"></canvas>
</div> </div>
@ -321,6 +323,10 @@
<div id="waf_metrics_div" class="chart-container" style="display: block; width: 90%; height: 300px;"> <div id="waf_metrics_div" class="chart-container" style="display: block; width: 90%; height: 300px;">
<canvas id="s_{{s.2}}" role="img"></canvas> <canvas id="s_{{s.2}}" role="img"></canvas>
</div> </div>
{% endif %}
<div id="nginx_metrics_div" class="chart-container" style="display: block; width: 90%; height: 300px;">
<canvas id="nginx_{{s.2}}" role="img"></canvas>
</div>
{% endfor %} {% endfor %}
{% endif %} {% endif %}
<div id="dialog-confirm" style="display: none;"> <div id="dialog-confirm" style="display: none;">

View File

@ -9,16 +9,16 @@
{% if page != "servers.py" %} {% if page != "servers.py" %}
<th style="width: 10%">Group</th> <th style="width: 10%">Group</th>
{% endif %} {% endif %}
<th class="checkbox-head" style="width: 5%">Enabled</th> <th class="checkbox-head" style="min-width: 70px;">Enabled</th>
<th style="width: 5%; padding-left: 5px;" class="help_cursor"> <th style="min-width: 50px; padding-left: 5px;" class="help_cursor">
<span title="Virtual IP, something like VRRP">Virt</span> <span title="Virtual IP, something like VRRP">Virt</span>
</th> </th>
<th class="checkbox-head" style="width: 5%">HAProxy</th> <th class="checkbox-head" style="min-width: 75px">HAProxy</th>
<th class="checkbox-head" style="min-width: 50px;">Nginx</th> <th class="checkbox-head" style="min-width: 65px;">Nginx</th>
<th style="min-width: 100px;" class="help_cursor"> <th style="min-width: 100px;" class="help_cursor">
<span title="If the server has a firewall enabled, enable this option">Firewalld</span> <span title="If the server has a firewall enabled, enable this option">Firewalld</span>
</th> </th>
<th class="checkbox-head" style="width: 5%" class="help_cursor"> <th class="checkbox-head" style="min-width: 80px;" class="help_cursor">
<span title="If protection is enabled, then the server is inaccessible for editing by everyone except the admin role">Protected</span> <span title="If protection is enabled, then the server is inaccessible for editing by everyone except the admin role">Protected</span>
</th> </th>
<th style="width: 10%" class="help_cursor"> <th style="width: 10%" class="help_cursor">

View File

@ -7,10 +7,11 @@
<th style="width: 10%">Password</th> <th style="width: 10%">Password</th>
<th style="width: 10%">Active</th> <th style="width: 10%">Active</th>
<th style="width: 20%">Email</th> <th style="width: 20%">Email</th>
<th style="width: {% if page == 'servers.py' %}100{% else %}10{% endif %}%">Role</th> <th style="width: 10%">Role</th>
{% if page != "servers.py" %} {% if page != "servers.py" %}
<th style="width: 100%">Group</th> <th style="width: 10%">Group</th>
{% endif %} {% endif %}
<th style="width: 100%">Services</th>
<th></th> <th></th>
<th></th> <th></th>
</tr> </tr>
@ -76,6 +77,9 @@
<span title="Change user groups" style="cursor: pointer; margin-left: 15px;" class="div-pic" onclick="openChangeUserGroupDialog('{{user.user_id}}')"> <span title="Change user groups" style="cursor: pointer; margin-left: 15px;" class="div-pic" onclick="openChangeUserGroupDialog('{{user.user_id}}')">
</td> </td>
{% endif %} {% endif %}
<td>
<span title="Change user groups" style="cursor: pointer; margin-left: 15px;" class="div-pic" onclick="openChangeUserServiceDialog('{{user.user_id}}')">
</td>
<td> <td>
<a class="add" onclick="cloneUser({{user.user_id}})" id="clone-{{user.user_id}}" title="Clone {{user.1}}" style="cursor: pointer;"></a> <a class="add" onclick="cloneUser({{user.user_id}})" id="clone-{{user.user_id}}" title="Clone {{user.1}}" style="cursor: pointer;"></a>
</td> </td>

View File

@ -27,6 +27,7 @@
{% if servers|length == 0 %} {% if servers|length == 0 %}
{% include 'include/getstarted.html' %} {% include 'include/getstarted.html' %}
{% else %} {% else %}
{% if service != 'nginx' %}
<table style="min-width: 40%;"> <table style="min-width: 40%;">
<tr class="overviewHead"> <tr class="overviewHead">
<th colspan=13 style="background-color: #d1ecf1"> <th colspan=13 style="background-color: #d1ecf1">
@ -37,6 +38,7 @@
</tr> </tr>
</table> </table>
<div id="table_metrics"></div> <div id="table_metrics"></div>
{% endif %}
<div style="padding-left: 25px;float: left;margin-top: 6px;"> <div style="padding-left: 25px;float: left;margin-top: 6px;">
<b>Time range:</b> <b>Time range:</b>
<select title="Choose time range" id="time-range"> <select title="Choose time range" id="time-range">
@ -47,19 +49,27 @@
<option value="720">12 hours</option> <option value="720">12 hours</option>
</select> </select>
</div> </div>
{% if service != 'nginx' %}
<div style="margin-top: 6px;"> <div style="margin-top: 6px;">
{{ checkbox('hide_http_metrics', desc='Hide HTTP metrics', title='Hide HTTP metrics') }} {{ checkbox('hide_http_metrics', desc='Hide HTTP metrics', title='Hide HTTP metrics') }}
</div> </div>
{% endif %}
<div id="refresh" style="text-align: right;margin-top: 20px;margin-right: 10px;" title="Refresh metrics" onclick="showMetrics()"> <div id="refresh" style="text-align: right;margin-top: 20px;margin-right: 10px;" title="Refresh metrics" onclick="showMetrics()">
<span class="service-reload"></span> <span class="service-reload"></span>
</div> </div>
{% for s in servers %} {% for s in servers %}
{% if service != 'nginx' %}
<div class="chart-container"> <div class="chart-container">
<canvas id="{{s.ip}}" role="img"></canvas> <canvas id="{{s.ip}}" role="img"></canvas>
</div> </div>
<div class="chart-container http_metrics_div" style="display: none"> <div class="chart-container http_metrics_div" style="display: none">
<canvas id="http_{{s.ip}}" role="img"></canvas> <canvas id="http_{{s.ip}}" role="img"></canvas>
</div> </div>
{% else %}
<div class="chart-container nginx_metrics_div" style="display: none">
<canvas id="nginx_{{s.ip}}" role="img"></canvas>
</div>
{% endif %}
{% endfor %} {% endfor %}
<script> <script>
function showMetrics() { function showMetrics() {
@ -67,15 +77,21 @@
(resolve, reject) => { (resolve, reject) => {
removeData(); removeData();
{% for s in servers %} {% for s in servers %}
{% if service != 'nginx' %}
getChartData('{{s.ip}}') getChartData('{{s.ip}}')
getHttpChartData('{{s.ip}}') getHttpChartData('{{s.ip}}')
{% else %}
getNginxChartData('{{s.ip}}')
{% endif %}
{% endfor %} {% endfor %}
{% if service != 'nginx' %}
if (localStorage.getItem('table_metrics') == 0 || localStorage.getItem('table_metrics') === null) { if (localStorage.getItem('table_metrics') == 0 || localStorage.getItem('table_metrics') === null) {
$('#dis_table_metric').css('display', 'none'); $('#dis_table_metric').css('display', 'none');
} else { } else {
$('#en_table_metric').css('display', 'none'); $('#en_table_metric').css('display', 'none');
loadMetrics(); loadMetrics();
} }
{% endif %}
}); });
metrics.then(); metrics.then();
} }
@ -86,8 +102,12 @@
let metrics = new Promise( let metrics = new Promise(
(resolve, reject) => { (resolve, reject) => {
{% for s in servers %} {% for s in servers %}
{% if service != 'nginx' %}
getChartData('{{s.ip}}') getChartData('{{s.ip}}')
getHttpChartData('{{s.ip}}') getHttpChartData('{{s.ip}}')
{% else %}
getNginxChartData('{{s.ip}}')
{% endif %}
{% endfor %} {% endfor %}
}); });
metrics.then(); metrics.then();

View File

@ -47,7 +47,7 @@
<td class="padding10 first-collumn">Current version</td> <td class="padding10 first-collumn">Current version</td>
<td class="padding10 first-collumn" style="width: 30%;">Available Versions</td> <td class="padding10 first-collumn" style="width: 30%;">Available Versions</td>
<td class="padding10 first-collumn" style="width: 30%;">Server</td> <td class="padding10 first-collumn" style="width: 30%;">Server</td>
<td>SYN flood protect</td> <td>SYN-flood protection</td>
<td></td> <td></td>
</tr> </tr>
<tr> <tr>
@ -69,8 +69,8 @@
{% endfor %} {% endfor %}
</select> </select>
</td> </td>
<td> <td class="syn-flood-protection-field">
{{ checkbox('syn_flood', title="Enable SYN flood protect", checked='checked') }} {{ checkbox('syn_flood', title="Enable SYN-flood protection", checked='checked') }}
</td> </td>
<td> <td>
<span class="ui-button ui-widget ui-corner-all" id="install" title="Install HAProxy">Install</span> <span class="ui-button ui-widget ui-corner-all" id="install" title="Install HAProxy">Install</span>
@ -83,7 +83,7 @@
<td class="padding10 first-collumn">Current version</td> <td class="padding10 first-collumn">Current version</td>
<td class="padding10 first-collumn" style="width: 30%;">Available Versions</td> <td class="padding10 first-collumn" style="width: 30%;">Available Versions</td>
<td class="padding10 first-collumn" style="width: 30%;">Server</td> <td class="padding10 first-collumn" style="width: 30%;">Server</td>
<td>SYN flood protect</td> <td>SYN-flood protection</td>
<td></td> <td></td>
</tr> </tr>
<tr> <tr>
@ -100,8 +100,8 @@
{% endfor %} {% endfor %}
</select> </select>
</td> </td>
<td> <td class="syn-flood-protection-field">
{{ checkbox('nginx_syn_flood', title="Enable SYN flood protect", checked='checked') }} {{ checkbox('nginx_syn_flood', title="Enable SYN-flood protection", checked='checked') }}
</td> </td>
<td> <td>
<span class="ui-button ui-widget ui-corner-all" id="nginx_install" title="Install Nginx">Install</span> <span class="ui-button ui-widget ui-corner-all" id="nginx_install" title="Install Nginx">Install</span>

View File

@ -14,11 +14,11 @@ funct.check_login()
funct.page_for_admin() funct.page_for_admin()
try: try:
user, user_id, role, token, servers = funct.get_users_params() user, user_id, role, token, servers, user_services = funct.get_users_params()
users = sql.select_users() users = sql.select_users()
settings = sql.get_setting('', all=1) settings = sql.get_setting('', all=1)
ldap_enable = sql.get_setting('ldap_enable') ldap_enable = sql.get_setting('ldap_enable')
grafana, stderr = funct.subprocess_execute("service grafana-server status |grep Active |awk '{print $1}'") grafana, stderr = funct.subprocess_execute("systemctl is-active grafana-server")
except Exception: except Exception:
pass pass
@ -38,5 +38,6 @@ template = template.render(title="Admin area: Manage users",
backups=sql.select_backups(), backups=sql.select_backups(),
grafana=''.join(grafana), grafana=''.join(grafana),
page="users.py", page="users.py",
user_services=user_services,
ldap_enable=ldap_enable) ldap_enable=ldap_enable)
print(template) print(template)

View File

@ -22,31 +22,34 @@ if form.getvalue('configver'):
template = env.get_template('configver.html') template = env.get_template('configver.html')
try: try:
user, user_id, role, token, servers = funct.get_users_params(disable=1) user, user_id, role, token, servers, user_services = funct.get_users_params(disable=1)
except: except:
pass pass
if service == 'keepalived': if service == 'keepalived':
configs_dir = funct.get_config_var('configs', 'kp_save_configs_dir') if funct.check_login(service=3):
title = "Working with versions Keepalived configs" configs_dir = funct.get_config_var('configs', 'kp_save_configs_dir')
files = funct.get_files(dir=configs_dir, format='conf') title = "Working with versions Keepalived configs"
action = 'versions.py?service=keepalived' files = funct.get_files(dir=configs_dir, format='conf')
format = 'conf' action = 'versions.py?service=keepalived'
servers = sql.get_dick_permit(keepalived=1) format = 'conf'
servers = sql.get_dick_permit(keepalived=1)
elif service == 'nginx': elif service == 'nginx':
configs_dir = funct.get_config_var('configs', 'nginx_save_configs_dir') if funct.check_login(service=2):
title = "Working with versions Nginx configs" configs_dir = funct.get_config_var('configs', 'nginx_save_configs_dir')
files = funct.get_files(dir=configs_dir, format='conf') title = "Working with versions Nginx configs"
action = 'versions.py?service=nginx' files = funct.get_files(dir=configs_dir, format='conf')
format = 'conf' action = 'versions.py?service=nginx'
servers = sql.get_dick_permit(nginx=1) format = 'conf'
servers = sql.get_dick_permit(nginx=1)
else: else:
title = "Working with versions HAProxy configs" if funct.check_login(service=1):
files = funct.get_files() title = "Working with versions HAProxy configs"
action = "versions.py" files = funct.get_files()
configs_dir = funct.get_config_var('configs', 'haproxy_save_configs_dir') action = "versions.py"
format = 'cfg' configs_dir = funct.get_config_var('configs', 'haproxy_save_configs_dir')
format = 'cfg'
if serv is not None and form.getvalue('del') is not None: if serv is not None and form.getvalue('del') is not None:
@ -69,10 +72,12 @@ if serv is not None and form.getvalue('config') is not None:
configver = configs_dir + configver configver = configs_dir + configver
save = form.getvalue('save') save = form.getvalue('save')
aftersave = 1 aftersave = 1
try: try:
funct.logging(serv, "configver.py upload old config %s" % configver) funct.logging(serv, "versions.py upload old config %s" % configver)
except Exception: except Exception:
pass pass
if service == 'keepalived': if service == 'keepalived':
stderr = funct.upload_and_restart(serv, configver, just_save=save, keepalived=1) stderr = funct.upload_and_restart(serv, configver, just_save=save, keepalived=1)
elif service == 'nginx': elif service == 'nginx':
@ -96,5 +101,6 @@ template = template.render(h2=1, title=title,
file=file, file=file,
configver=configver, configver=configver,
service=service, service=service,
user_services=user_services,
token=token) token=token)
print(template) print(template)

View File

@ -42,7 +42,6 @@ else:
log_path = funct.get_config_var('main', 'log_path') log_path = funct.get_config_var('main', 'log_path')
time_storage = sql.get_setting('log_time_storage') time_storage = sql.get_setting('log_time_storage')
time_storage = int(time_storage)
try: try:
time_storage_hours = time_storage * 24 time_storage_hours = time_storage * 24
@ -60,7 +59,7 @@ except Exception:
pass pass
try: try:
user, user_id, role, token, servers = funct.get_users_params() user, user_id, role, token, servers, user_services = funct.get_users_params()
except Exception: except Exception:
pass pass
@ -85,6 +84,7 @@ output_from_parsed_template = template.render(h2=1,
hour1=hour1, hour1=hour1,
minut=minut, minut=minut,
minut1=minut1, minut1=minut1,
page = page, page=page,
user_services=user_services,
token=token) token=token)
print(output_from_parsed_template) print(output_from_parsed_template)

View File

@ -11,12 +11,14 @@ print('Content-type: text/html\n')
funct.check_login() funct.check_login()
if service == 'nginx': if service == 'nginx':
title = 'Nginx stats page' if funct.check_login(service=2):
title = 'Nginx stats page'
else: else:
title = 'HAProxy stats page' if funct.check_login(service=1):
title = 'HAProxy stats page'
try: try:
user, user_id, role, token, servers = funct.get_users_params(virt=1) user, user_id, role, token, servers, user_services = funct.get_users_params(virt=1)
if serv is None: if serv is None:
first_serv = servers first_serv = servers
@ -37,6 +39,7 @@ output_from_parsed_template = template.render(h2=1,
selects=servers, selects=servers,
serv=serv, serv=serv,
service=service, service=service,
user_services=user_services,
token=token) token=token)
print(output_from_parsed_template) print(output_from_parsed_template)

View File

@ -9,11 +9,11 @@ form = funct.form
manage_rules = form.getvalue('manage_rules') manage_rules = form.getvalue('manage_rules')
print('Content-type: text/html\n') print('Content-type: text/html\n')
funct.check_login() funct.check_login(service=1)
funct.page_for_admin(level=2) funct.page_for_admin(level=2)
try: try:
user, user_id, role, token, servers = funct.get_users_params() user, user_id, role, token, servers, user_services = funct.get_users_params()
except Exception: except Exception:
pass pass
@ -40,5 +40,6 @@ template = template.render(h2=1, title=title,
servers_all=servers, servers_all=servers,
manage_rules=manage_rules, manage_rules=manage_rules,
rules=rules, rules=rules,
user_services=user_services,
token=token) token=token)
print(template) print(template)

View File

@ -279,6 +279,82 @@ function renderWafChart(data, labels, server) {
}); });
charts.push(myChart); charts.push(myChart);
} }
function getNginxChartData(server) {
$.ajax({
url: "options.py",
data: {
new_nginx_metrics: '1',
server: server,
time_range: $( "#time-range option:selected" ).val(),
token: $('#token').val()
},
type: "POST",
success: function (result) {
var data = [];
data.push(result.chartData.curr_con);
data.push(result.chartData.server);
var labels = result.chartData.labels;
renderNginxChart(data, labels, server);
}
});
}
function renderNginxChart(data, labels, server) {
var ctx = 'nginx_'+server
var myChart = new Chart(ctx, {
type: 'line',
data: {
labels: labels.split(','),
datasets: [
{
parsing: false,
normalized: true,
label: 'Connections',
data: data[0].split(','),
borderColor: 'rgba(75, 192, 192, 1)',
backgroundColor: 'rgba(75, 192, 192, 0.2)',
}
]
},
options: {
animation: false,
maintainAspectRatio: false,
title: {
display: true,
text: "Nginx "+data[1],
fontSize: 20,
padding: 0,
},
scales: {
yAxes: [{
ticks: {
beginAtZero: true,
}
}],
xAxes: [{
ticks: {
major: {
enabled: true,
fontStyle: 'bold'
},
source: 'data',
autoSkip: true,
autoSkipPadding: 45,
maxRotation: 0
}
}]
},
legend: {
display: true,
labels: {
fontColor: 'rgb(255, 99, 132)',
defaultFontSize: '10',
defaultFontFamily: 'BlinkMacSystemFont'
},
}
}
});
charts.push(myChart);
}
$("#secIntervals").css("display", "none"); $("#secIntervals").css("display", "none");
function loadMetrics() { function loadMetrics() {

View File

@ -15,6 +15,16 @@ function escapeHtml(unsafe) {
.replace(/'/g, "&#039;"); .replace(/'/g, "&#039;");
} }
var wait_mess = '<div class="alert alert-warning">Please do not close or refresh the page. Wait until the job is completed. This may take some time</div>' var wait_mess = '<div class="alert alert-warning">Please do not close or refresh the page. Wait until the job is completed. This may take some time</div>'
function show_current_page(id) {
id.parent().css('display', 'contents');
id.parent().css('font-size', '13px');
id.parent().css('top', '0');
id.parent().css('left', '0');
id.parent().children().css('margin-left', '-20px');
id.parent().find('a').css('padding-left', '20px');
id.find('a').css('padding-left', '30px');
id.find('a').css('border-left', '4px solid #5D9CEB');
}
$( function() { $( function() {
$('.menu li ul li').each(function () { $('.menu li ul li').each(function () {
var link = $(this).find('a').attr('href'); var link = $(this).find('a').attr('href');
@ -23,131 +33,35 @@ $( function() {
cur_url[1] = 'haproxy'; cur_url[1] = 'haproxy';
} }
if (cur_url[0] == link2 && cur_url[1].split('&')[0] != 'service=keepalived' && cur_url[1].split('&')[0] != 'service=nginx') { if (cur_url[0] == link2 && cur_url[1].split('&')[0] != 'service=keepalived' && cur_url[1].split('&')[0] != 'service=nginx') {
$(this).parent().css('display', 'contents'); show_current_page($(this))
$(this).parent().css('font-size', '13px');
$(this).parent().css('top', '0');
$(this).parent().css('left', '0');
$(this).parent().children().css('margin-left', '-20px');
$(this).parent().find('a').css('padding-left', '20px');
$(this).find('a').css('padding-left', '30px');
$(this).find('a').css('border-left', '4px solid #5D9CEB');
} else if(cur_url[0] == 'versions.py' && cur_url[1].split('&')[0] == 'service=keepalived' && link2 == 'versions.py?service=keepalived'){ } else if(cur_url[0] == 'versions.py' && cur_url[1].split('&')[0] == 'service=keepalived' && link2 == 'versions.py?service=keepalived'){
$(this).parent().css('display', 'contents'); show_current_page($(this))
$(this).parent().css('font-size', '13px');
$(this).parent().css('top', '0');
$(this).parent().css('left', '0');
$(this).parent().children().css('margin-left', '-20px');
$(this).parent().find('a').css('padding-left', '20px');
$(this).find('a').css('padding-left', '30px');
$(this).find('a').css('border-left', '4px solid #5D9CEB');
} else if(cur_url[0] == 'config.py' && cur_url[1].split('&')[0] == 'service=keepalived' && link2 == 'config.py?service=keepalived'){ } else if(cur_url[0] == 'config.py' && cur_url[1].split('&')[0] == 'service=keepalived' && link2 == 'config.py?service=keepalived'){
$(this).parent().css('display', 'contents'); show_current_page($(this))
$(this).parent().css('font-size', '13px');
$(this).parent().css('top', '0');
$(this).parent().css('left', '0');
$(this).parent().children().css('margin-left', '-20px');
$(this).parent().find('a').css('padding-left', '20px');
$(this).find('a').css('padding-left', '30px');
$(this).find('a').css('border-left', '4px solid #5D9CEB');
} else if(cur_url[0] == 'versions.py' && cur_url[1].split('&')[0] == 'service=nginx' && link2 == 'versions.py?service=nginx'){ } else if(cur_url[0] == 'versions.py' && cur_url[1].split('&')[0] == 'service=nginx' && link2 == 'versions.py?service=nginx'){
$(this).parent().css('display', 'contents'); show_current_page($(this))
$(this).parent().css('font-size', '13px');
$(this).parent().css('top', '0');
$(this).parent().css('left', '0');
$(this).parent().children().css('margin-left', '-20px');
$(this).parent().find('a').css('padding-left', '20px');
$(this).find('a').css('padding-left', '30px');
$(this).find('a').css('border-left', '4px solid #5D9CEB');
} else if(cur_url[0] == 'config.py' && cur_url[1].split('&')[0] == 'service=nginx' && link2 == 'config.py?service=nginx'){ } else if(cur_url[0] == 'config.py' && cur_url[1].split('&')[0] == 'service=nginx' && link2 == 'config.py?service=nginx'){
$(this).parent().css('display', 'contents'); show_current_page($(this))
$(this).parent().css('font-size', '13px');
$(this).parent().css('top', '0');
$(this).parent().css('left', '0');
$(this).parent().children().css('margin-left', '-20px');
$(this).parent().find('a').css('padding-left', '20px');
$(this).find('a').css('padding-left', '30px');
$(this).find('a').css('border-left', '4px solid #5D9CEB');
} else if(cur_url[0] == 'hapservers.py' && cur_url[1].split('&')[0] == 'service=nginx' && link2 == 'hapservers.py?service=nginx'){ } else if(cur_url[0] == 'hapservers.py' && cur_url[1].split('&')[0] == 'service=nginx' && link2 == 'hapservers.py?service=nginx'){
$(this).parent().css('display', 'contents'); show_current_page($(this))
$(this).parent().css('font-size', '13px');
$(this).parent().css('top', '0');
$(this).parent().css('left', '0');
$(this).parent().children().css('margin-left', '-20px');
$(this).parent().find('a').css('padding-left', '20px');
$(this).find('a').css('padding-left', '30px');
$(this).find('a').css('border-left', '4px solid #5D9CEB');
} else if(cur_url[0] == 'hapservers.py' && cur_url[1].split('&')[0] == 'service=keepalived' && link2 == 'hapservers.py?service=keepalived'){ } else if(cur_url[0] == 'hapservers.py' && cur_url[1].split('&')[0] == 'service=keepalived' && link2 == 'hapservers.py?service=keepalived'){
$(this).parent().css('display', 'contents'); show_current_page($(this))
$(this).parent().css('font-size', '13px');
$(this).parent().css('top', '0');
$(this).parent().css('left', '0');
$(this).parent().children().css('margin-left', '-20px');
$(this).parent().find('a').css('padding-left', '20px');
$(this).find('a').css('padding-left', '30px');
$(this).find('a').css('border-left', '4px solid #5D9CEB');
} else if(cur_url[0] == 'viewsttats.py' && cur_url[1].split('&')[0] == 'service=nginx' && link2 == 'viewsttats.py?service=nginx'){ } else if(cur_url[0] == 'viewsttats.py' && cur_url[1].split('&')[0] == 'service=nginx' && link2 == 'viewsttats.py?service=nginx'){
$(this).parent().css('display', 'contents'); show_current_page($(this))
$(this).parent().css('font-size', '13px');
$(this).parent().css('top', '0');
$(this).parent().css('left', '0');
$(this).parent().children().css('margin-left', '-20px');
$(this).parent().find('a').css('padding-left', '20px');
$(this).find('a').css('padding-left', '30px');
$(this).find('a').css('border-left', '4px solid #5D9CEB');
} else if(cur_url[0] == 'smon.py' && cur_url[1].split('&')[0] == 'action=view' && link2 == 'smon.py?action=view'){ } else if(cur_url[0] == 'smon.py' && cur_url[1].split('&')[0] == 'action=view' && link2 == 'smon.py?action=view'){
$(this).parent().css('display', 'contents'); show_current_page($(this))
$(this).parent().css('font-size', '13px');
$(this).parent().css('top', '0');
$(this).parent().css('left', '0');
$(this).parent().children().css('margin-left', '-20px');
$(this).parent().find('a').css('padding-left', '20px');
$(this).find('a').css('padding-left', '30px');
$(this).find('a').css('border-left', '4px solid #5D9CEB');
} else if(cur_url[0] == 'smon.py' && cur_url[1].split('&')[0] == 'action=add' && link2 == 'smon.py?action=add'){ } else if(cur_url[0] == 'smon.py' && cur_url[1].split('&')[0] == 'action=add' && link2 == 'smon.py?action=add'){
$(this).parent().css('display', 'contents'); show_current_page($(this))
$(this).parent().css('font-size', '13px');
$(this).parent().css('top', '0');
$(this).parent().css('left', '0');
$(this).parent().children().css('margin-left', '-20px');
$(this).parent().find('a').css('padding-left', '20px');
$(this).find('a').css('padding-left', '30px');
$(this).find('a').css('border-left', '4px solid #5D9CEB');
} else if(cur_url[0] == 'smon.py' && cur_url[1].split('&')[0] == 'action=history' && link2 == 'smon.py?action=history'){ } else if(cur_url[0] == 'smon.py' && cur_url[1].split('&')[0] == 'action=history' && link2 == 'smon.py?action=history'){
$(this).parent().css('display', 'contents'); show_current_page($(this))
$(this).parent().css('font-size', '13px');
$(this).parent().css('top', '0');
$(this).parent().css('left', '0');
$(this).parent().children().css('margin-left', '-20px');
$(this).parent().find('a').css('padding-left', '20px');
$(this).find('a').css('padding-left', '30px');
$(this).find('a').css('border-left', '4px solid #5D9CEB');
} else if(cur_url[0] == 'smon.py' && cur_url[1].split('&')[0] == 'action=checker_history' && link2 == 'smon.py?action=checker_history'){ } else if(cur_url[0] == 'smon.py' && cur_url[1].split('&')[0] == 'action=checker_history' && link2 == 'smon.py?action=checker_history'){
$(this).parent().css('display', 'contents'); show_current_page($(this))
$(this).parent().css('font-size', '13px');
$(this).parent().css('top', '0');
$(this).parent().css('left', '0');
$(this).parent().children().css('margin-left', '-20px');
$(this).parent().find('a').css('padding-left', '20px');
$(this).find('a').css('padding-left', '30px');
$(this).find('a').css('border-left', '4px solid #5D9CEB');
} else if(cur_url[0] == 'add.py' && cur_url[1].split('&')[0] == 'service=nginx#ssl' && link2 == 'add.py?service=nginx#ssl'){ } else if(cur_url[0] == 'add.py' && cur_url[1].split('&')[0] == 'service=nginx#ssl' && link2 == 'add.py?service=nginx#ssl'){
$(this).parent().css('display', 'contents'); show_current_page($(this))
$(this).parent().css('font-size', '13px');
$(this).parent().css('top', '0');
$(this).parent().css('left', '0');
$(this).parent().children().css('margin-left', '-20px');
$(this).parent().find('a').css('padding-left', '20px');
$(this).find('a').css('padding-left', '30px');
$(this).find('a').css('border-left', '4px solid #5D9CEB');
} else if(cur_url[0] == 'viewlogs.py' && cur_url[1].split('&')[0] == 'type=2' && link2 == 'viewlogs.py?type=2'){ } else if(cur_url[0] == 'viewlogs.py' && cur_url[1].split('&')[0] == 'type=2' && link2 == 'viewlogs.py?type=2'){
$(this).parent().css('display', 'contents'); show_current_page($(this))
$(this).parent().css('font-size', '13px'); } else if(cur_url[0] == 'metrics.py' && cur_url[1].split('&')[0] == 'service=nginx' && link2 == 'metrics?service=nginx'){
$(this).parent().css('top', '0'); show_current_page($(this))
$(this).parent().css('left', '0');
$(this).parent().children().css('margin-left', '-20px');
$(this).parent().find('a').css('padding-left', '20px');
$(this).find('a').css('padding-left', '30px');
$(this).find('a').css('border-left', '4px solid #5D9CEB');
} }
}); });
}); });

View File

@ -385,6 +385,9 @@ pre {
.cred-field { .cred-field {
min-width: 225px; min-width: 225px;
} }
.syn-flood-protection-field {
padding-left: 60px;
}
.overviewTr { .overviewTr {
margin: 0; margin: 0;
background-color: #f6f8fa; background-color: #f6f8fa;

View File

@ -1846,6 +1846,8 @@ function checkSshConnect(ip) {
toastr.error(data) toastr.error(data)
} else if(data.indexOf('failed') != '-1') { } else if(data.indexOf('failed') != '-1') {
toastr.error(data) toastr.error(data)
} else if(data.indexOf('Errno') != '-1') {
toastr.error(data)
} else { } else {
toastr.clear(); toastr.clear();
toastr.success('Connect is accepted'); toastr.success('Connect is accepted');
@ -1859,6 +1861,9 @@ function openChangeUserPasswordDialog(id) {
function openChangeUserGroupDialog(id) { function openChangeUserGroupDialog(id) {
changeUserGroupDialog(id); changeUserGroupDialog(id);
} }
function openChangeUserServiceDialog(id) {
changeUserServiceDialog(id);
}
function changeUserPasswordDialog(id) { function changeUserPasswordDialog(id) {
$( "#user-change-password-table" ).dialog({ $( "#user-change-password-table" ).dialog({
autoOpen: true, autoOpen: true,
@ -1952,6 +1957,40 @@ function changeUserGroupDialog(id) {
} }
} ); } );
} }
function changeUserServiceDialog(id) {
$.ajax( {
url: "options.py",
data: {
getuserservices: id,
token: $('#token').val()
},
type: "POST",
success: function( data ) {
if (data.indexOf('danger') != '-1') {
toastr.error(data);
} else {
toastr.clear();
$('#change-user-service-form').html(data);
$( "#change-user-service-dialog" ).dialog({
resizable: false,
height: "auto",
width: 450,
modal: true,
title: "Manage "+$('#login-'+id).val()+" services",
buttons: {
"Save": function() {
$( this ).dialog( "close" );
changeUserServices(id);
},
Cancel: function() {
$( this ).dialog( "close" );
}
}
});
}
}
} );
}
function changeUserGroup(id) { function changeUserGroup(id) {
var groups = $('#usergroup-'+id).val().toString(); var groups = $('#usergroup-'+id).val().toString();
$.ajax( { $.ajax( {
@ -1975,6 +2014,29 @@ function changeUserGroup(id) {
} }
} ); } );
} }
function changeUserServices(id) {
var services = $('#userservice-'+id).val().toString();
$.ajax( {
url: "options.py",
data: {
changeUserServicesId: id,
changeUserServices: services,
changeUserServicesUser: $('#login-'+id).val(),
token: $('#token').val()
},
type: "POST",
success: function( data ) {
if (data.indexOf('error:') != '-1' || data.indexOf('Failed') != '-1') {
toastr.error(data);
} else {
$("#user-" + id).addClass("update", 1000);
setTimeout(function () {
$("#user-" + id).removeClass("update");
}, 2500);
}
}
} );
}
function addUserGroup(id) { function addUserGroup(id) {
$.ajax( { $.ajax( {
url: "options.py", url: "options.py",