609 lines
19 KiB
Python
609 lines
19 KiB
Python
from settings import config
|
|
from flask import g, url_for, request, session, make_response
|
|
from paramecio2.libraries.generate_admin_class import GenerateAdminClass
|
|
from paramecio2.libraries.i18n import I18n
|
|
from paramecio2.modules.admin import admin_app, t as admin_t
|
|
from paramecio2.libraries.db.coreforms import SelectForm, SelectModelForm
|
|
from paramecio2.libraries.mtemplates import PTemplate, env_theme
|
|
from paramecio2.libraries import datetime
|
|
from paramecio2.libraries.urls import make_media_url
|
|
from modules.monit.models.monit import Server, ServerData, Alerts
|
|
from paramecio2.libraries.db.webmodel import WebModel
|
|
from paramecio2.libraries.lists import AjaxList
|
|
from paramecio2.libraries.db.extraforms.fileform import FileForm
|
|
from paramecio2.libraries.formsutils import show_form
|
|
from modules.pastafari2.libraries.task import Task as SSHTask
|
|
from modules.pastafari2.models.tasks import Task, LogTask
|
|
from modules.pastafari2.libraries.configtask import config_task
|
|
from modules.pastafari2.models.pastafari2 import ServerGroup, ServerDbTask
|
|
from pathlib import Path
|
|
import paramiko
|
|
import socket
|
|
import os
|
|
try:
|
|
import ujson as json
|
|
except:
|
|
import json
|
|
|
|
env=env_theme(__file__)
|
|
|
|
t=PTemplate(env)
|
|
|
|
t.env.directories=admin_t.env.directories
|
|
|
|
t.env.directories.insert(1, os.path.dirname(__file__).replace('/admin', '')+'/templates/admin')
|
|
|
|
system_path='./ssh/'
|
|
|
|
@admin_app.route('/pastafari2/dashboard/')
|
|
def pastafari2_dashboard():
|
|
|
|
return t.load_template('dash_pastafari.phtml', title=I18n.lang('pastafari2', 'servers_dashboard', 'Servers Dashboard'), path_module='admin_app.pastafari2_dashboard')
|
|
|
|
@admin_app.route('/pastafari2/settings/')
|
|
def pastafari2_settings():
|
|
"""
|
|
forms={}
|
|
|
|
forms['ssh_key_priv']=FileForm('ssh_key_priv', '', '')
|
|
forms['ssh_key_pub']=FileForm('ssh_key_pub', '', '')
|
|
|
|
forms['ssh_key_priv'].help=I18n.lang('pastafari2', 'ssh_key_priv_file_help', 'Global private SSH key used for enter in servers')
|
|
forms['ssh_key_pub'].help=I18n.lang('pastafari2', 'ssh_key_pub_file_help', 'Global public SSH key used for enter in servers')
|
|
|
|
forms['ssh_key_priv'].label=I18n.lang('pastafari2', 'ssh_key_priv_file', 'Global private SSH')
|
|
forms['ssh_key_pub'].label=I18n.lang('pastafari2', 'ssh_key_pub_file', 'Global public SSH')
|
|
|
|
forms['ssh_key_priv'].required=True
|
|
forms['ssh_key_pub'].required=True
|
|
|
|
html_forms=show_form({}, forms, t, yes_error=False, pass_values=True, modelform_tpl='forms/modelform.phtml')
|
|
"""
|
|
|
|
txt_error=''
|
|
txt_generate_key='<p>You have created your ssh keys</p>'
|
|
txt_generate_key_button='Regenerate SSH keys'
|
|
regenerate=True
|
|
|
|
if not os.path.isdir(system_path):
|
|
|
|
try:
|
|
Path(system_path).mkdir(mode=511)
|
|
|
|
except:
|
|
|
|
txt_error='<p><strong>You need create ssh directory for save ssh keys</strong></p>'
|
|
|
|
#Get ssh key
|
|
|
|
if not os.path.isfile(system_path+'id_rsa'):
|
|
|
|
txt_generate_key='<p>You need generate a global private ssh key, because doesn\'t exists</p>'
|
|
txt_generate_key_button='Generate SSH keys'
|
|
regenerate=False
|
|
pass
|
|
|
|
return t.load_template('settings.phtml', title=I18n.lang('pastafari2', 'settings', 'Settings'), path_module='admin_app.pastafari2_settings', txt_error=txt_error, txt_generate_key=txt_generate_key, txt_generate_key_button=txt_generate_key_button, regenerate=regenerate)
|
|
|
|
@admin_app.route('/pastafari2/edit_global_ssh_keys/', methods=['POST'])
|
|
def pastafari2_edit_global_ssh_keys():
|
|
|
|
form={}
|
|
|
|
error=0
|
|
|
|
if not os.path.isfile(system_path+'id_rsa'):
|
|
|
|
try:
|
|
|
|
key=paramiko.RSAKey.generate(2048)
|
|
key.write_private_key_file(system_path+'id_rsa')
|
|
|
|
with open(system_path+'id_rsa.pub',"w") as pub_key:
|
|
pub_key.write("%s %s" % (key.get_name(), key.get_base64()))
|
|
|
|
except:
|
|
|
|
error=1
|
|
|
|
"""
|
|
if not 'ssh_key_priv_file' in request.files:
|
|
error=1
|
|
form['ssh_key_priv']='ssh private key file required'
|
|
|
|
if not 'ssh_key_pub_file' in request.files:
|
|
error=1
|
|
form['ssh_key_pub']='ssh public key file required'
|
|
|
|
if not error:
|
|
ssh_key_priv=request.files['ssh_key_priv_file']
|
|
ssh_key_pub=request.files['ssh_key_pub_file']
|
|
|
|
if ssh_key_priv.filename=='':
|
|
error=1
|
|
form['ssh_key_priv']='ssh private key file required'
|
|
|
|
if ssh_key_pub.filename=='':
|
|
error=1
|
|
form['ssh_key_pub']='ssh private key file required'
|
|
|
|
if not os.path.isdir(system_path):
|
|
|
|
try:
|
|
Path(system_path).mkdir(mode=511)
|
|
|
|
except:
|
|
|
|
error=1
|
|
form['ssh_key_priv']='You need create ssh directory for save ssh keys'
|
|
|
|
if not error:
|
|
|
|
#Load keys
|
|
|
|
#Check keys
|
|
|
|
|
|
|
|
pass
|
|
"""
|
|
|
|
#return {'form': form, 'error': error}
|
|
return {'error': error}
|
|
|
|
@admin_app.route('/pastafari2/add_server/')
|
|
def pastafari2_add_server():
|
|
|
|
db=g.connection
|
|
|
|
group_form=SelectModelForm('group_id', '', ServerGroup(db), 'group', 'id', field_parent=None)
|
|
|
|
return t.load_template('add_server.phtml', title=I18n.lang('pastafari2', 'add_server', 'Add server'), path_module='admin_app.pastafari2_dashboard', group_form=group_form)
|
|
|
|
|
|
@admin_app.route('/pastafari2/add_server_task/', methods=['POST'])
|
|
def pastafari2_add_server_task():
|
|
|
|
db=g.connection
|
|
|
|
#task=Task(db)
|
|
|
|
#task.safe_query()
|
|
|
|
#logtask=LogTask(db)
|
|
|
|
#server=ServerTask(db)
|
|
#(self, server, conn, remote_user='root', remote_password='', private_key='./ssh/id_rsa', password_key='', remote_path='leviathan', task_id=0, data={}):
|
|
error_form={}
|
|
|
|
server_host=request.form.get('server_host', '')
|
|
server_username=request.form.get('server_username', '')
|
|
server_password=request.form.get('server_password', '')
|
|
repeat_server_password=request.form.get('repeat_server_password', '')
|
|
group_id=request.form.get('group_id', '')
|
|
private_key='./ssh/id_rsa'
|
|
public_key='./ssh/id_rsa.pub'
|
|
remote_path='pastafari2'
|
|
task_id=0
|
|
ip=''
|
|
error=0
|
|
data={}
|
|
ssh_user=config_task.remote_user
|
|
|
|
#make ping to server
|
|
|
|
if server_host=='':
|
|
error=1
|
|
error_form['#server_host_error']=I18n.lang('pastafari2', 'error_hostname', 'Error: you need enter a valid hostname')
|
|
|
|
txt_error=''
|
|
|
|
try:
|
|
#print("IP address of %s: %s" %(remote_host, socket.gethostbyname(remote_host)))
|
|
ip=socket.gethostbyname(server_host)
|
|
pass
|
|
except socket.error as err_msg:
|
|
error=1
|
|
error_form['#server_host_error']=I18n.lang('pastafari2', 'error_getting_ip_host', 'Error: '+err_msg.__str__())
|
|
|
|
if not error:
|
|
|
|
group_name=''
|
|
|
|
if group_id!='':
|
|
server_group=ServerGroup(db)
|
|
arr_group=server_group.set_conditions('WHERE id=%s', [group_id]).select_a_row_where()
|
|
group_name=arr_group['group']
|
|
|
|
data={'ssh_user': ssh_user, 'pub_key': public_key, 'url_stats': config.domain_url+url_for('monit_app.monit_get_data', api_key=config.monit_api_key), 'hostname': server_host, 'ip': ip, 'group_id': group_id, 'group_name': group_name}
|
|
|
|
with SSHTask(server_host, db, remote_user=server_username, remote_password=server_password, private_key=private_key, remote_path=remote_path, task_id=task_id, data=data) as ssh_task:
|
|
if not ssh_task.prepare_connection():
|
|
error=1
|
|
txt_error=I18n.lang('pastafari2', 'error_connection', 'Error: cannot connect to server')
|
|
error_form['#server_host_error']=I18n.lang('pastafari2', 'error_connection', 'Error: cannot connect to server')
|
|
else:
|
|
# Prepare task for install monit
|
|
pass
|
|
|
|
task=Task(db)
|
|
|
|
task_id=0
|
|
|
|
path_task='modules.pastafari2.tasks.system.task'
|
|
|
|
if not task.run_task(server_host, path_task, 'Add new server', 'add_new_server', 'Task for add a new server', user=server_username, password=server_password, where_sql_server='', url='', data=data, send_task=True):
|
|
|
|
error=1
|
|
error_form['#server_host_error']=I18n.lang('pastafari2', 'error_exec_task', 'Error: cannot execute the task')
|
|
|
|
task_id=task.task_id
|
|
|
|
return {'error': error, 'txt_error': txt_error, 'error_form': error_form, 'task_id': task_id}
|
|
|
|
# Maybe translate to api
|
|
|
|
@admin_app.route('/pastafari2/progress/')
|
|
def pastafari2_progress():
|
|
|
|
db=g.connection
|
|
|
|
task_id=request.args.get('task_id', '0')
|
|
|
|
position=request.args.get('position', '0')
|
|
|
|
task=Task(db)
|
|
|
|
arr_task=task.set_conditions('WHERE id=%s', [task_id]).select_a_row_where()
|
|
|
|
#print(arr_task)
|
|
|
|
return t.load_template('progress.phtml', title=I18n.lang('pastafari2', 'task_progress', 'Task progress'), path_module='admin_app.pastafari2_dashboard', name_task=arr_task['name_task'], description_task=arr_task['description_task'], position=position, task_id=task_id, server=arr_task['server'])
|
|
|
|
|
|
|
|
@admin_app.route('/pastafari2/getprogress/', methods=['POST'])
|
|
def pastafari2_getprogress():
|
|
|
|
s=session
|
|
|
|
db=g.connection
|
|
|
|
if request.args.get('task_id', '0')=='0':
|
|
|
|
s['get_progress']=s.get('get_progress', 0)
|
|
|
|
try:
|
|
|
|
task_id=int(request.args.get('task_id', '0'))
|
|
except:
|
|
task_id=0
|
|
|
|
try:
|
|
position=int(request.args.get('position', '0'))
|
|
except:
|
|
position=0
|
|
|
|
task=Task(db)
|
|
logtask=LogTask(db)
|
|
|
|
arr_task=task.select_a_row(task_id)
|
|
|
|
arr_rows={'wait': 1}
|
|
|
|
if arr_task:
|
|
|
|
logtask.set_limit([position, 5])
|
|
|
|
logtask.set_order({'id': 0})
|
|
|
|
logtask.conditions=['WHERE task_id=%s', [task_id]]
|
|
|
|
server=request.args.get('server', '')
|
|
|
|
if server!='':
|
|
logtask.conditions=['WHERE task_id=%s and logtask.server=%s', [task_id, server]]
|
|
|
|
logtask.yes_reset_conditions=False
|
|
|
|
c=0
|
|
|
|
arr_rows=[]
|
|
|
|
with logtask.select([], True) as cursor:
|
|
for arr_row in cursor:
|
|
arr_rows.append(arr_row)
|
|
c+=1
|
|
|
|
if c==0:
|
|
arr_rows=[]
|
|
|
|
c_error=logtask.set_conditions('WHERE task_id=%s and logtask.error=%s and logtask.status=%s', [task_id, 1, 1]).select_count()
|
|
|
|
if c_error==0:
|
|
|
|
arr_rows={'wait': 1}
|
|
else:
|
|
logtask.limit=''
|
|
|
|
with logtask.set_conditions('WHERE task_id=%s and logtask.error=%s and logtask.status=%s', [task_id, 1, 1]).select([], True) as cursor:
|
|
for arr_row in cursor:
|
|
arr_rows.append(arr_row)
|
|
|
|
else:
|
|
|
|
arr_rows=[{'task_id': task_id, 'progress': 100, 'message': 'Error: no exists task', 'error': 1, 'status': 1}]
|
|
|
|
db.close()
|
|
|
|
#header=response.headers
|
|
|
|
resp=make_response(json.dumps(arr_rows))
|
|
|
|
resp.headers['Content-Type']='application/json'
|
|
|
|
return resp
|
|
|
|
@admin_app.route('/pastafari2/get_servers/', methods=['POST'])
|
|
def get_servers_task():
|
|
|
|
db=g.connection
|
|
|
|
group_sql=''
|
|
|
|
count_data=[]
|
|
sql_data=[]
|
|
|
|
group_id=request.form.get('group_id', '')
|
|
|
|
group_sql_count=''
|
|
group_sql=''
|
|
|
|
if group_id!='':
|
|
group_sql_count=' WHERE `group_id`=%s'
|
|
count_data=[group_id]
|
|
sql_data=[group_id]
|
|
group_sql=' WHERE `group_id`=%s'
|
|
|
|
|
|
|
|
fields=[[I18n.lang('pastafari2', 'hostname', 'Hostname'), True], ['IP', True], [I18n.lang('pastafari2', 'selected', 'Selected'), False], [I18n.lang('pastafari2', 'options', 'Options'), False]]
|
|
arr_order_fields=['hostname', 'ip']
|
|
|
|
count_query=['select count(serverdbtask.id) as num_elements from serverdbtask'+group_sql_count, count_data]
|
|
|
|
# server.id as select_id,
|
|
|
|
# select hostname, ip, date, num_updates, id from serverofuser where user_id=%s;
|
|
|
|
str_query=['select serverdbtask.hostname, serverdbtask.ip, serverdbtask.id as select_id, serverdbtask.id from serverdbtask'+group_sql, sql_data]
|
|
|
|
ajax=AjaxList(db, fields, arr_order_fields, count_query, str_query)
|
|
|
|
#ajax.func_fields['id']=options_server
|
|
#ajax.func_fields['ip']=options_ip
|
|
ajax.func_fields['select_id']=options_selected
|
|
ajax.func_fields['id']=options_options
|
|
ajax.limit=0
|
|
|
|
#{'fields': [['Hostname', True], ['IP', True], ['Status', True], ['Options', False]], 'rows': [{'hostname': 'debian-pc.localdomain', 'ip': '<span id="ip_192.168.122.125">192.168.122.125</span>', 'date': '<img src="/mediafrom/pastafari2/images/status_green.png" />', 'id': '<a href="#">View stats</a>'}, {'hostname': 'DESKTOP-HLHPSSO', 'ip': '<span id="ip_192.168.122.81">192.168.122.81</span>', 'date': '<img src="/mediafrom/pastafari2/images/status_green.png" />', 'id': '<a href="#">View stats</a>'}], 'html_pages': ''}
|
|
|
|
return ajax.show()
|
|
|
|
"""
|
|
def options_server(row_id, row):
|
|
|
|
#'<a href="{}">{}</a>'.format(url_for('.services', server_id=row_id), I18n.lang('monit', 'services', 'Services'))
|
|
|
|
arr_options=['<a href="{}">{}</a>'.format("", I18n.lang('pastafari2', 'edit', 'Edit'))]
|
|
arr_options.append('<a href="{}">{}</a>'.format("", I18n.lang('pastafari2', 'make_task', 'Make task')))
|
|
arr_options.append('<a href="{}">{}</a>'.format("", I18n.lang('pastafari2', 'delete', 'Delete')))
|
|
"""
|
|
|
|
def options_selected(row_id, row):
|
|
|
|
return '<input type="checkbox" name="server_id_{}" class="server_id" value="{}"/>'.format(row_id, row_id)
|
|
|
|
def options_options(row_id, row):
|
|
|
|
arr_options=['<a href="{}">{}</a>'.format(url_for('admin_app.pastafari2_edit_server', id=row_id, op_admin=1), I18n.lang('pastafari2', 'edit', 'Edit'))]
|
|
#arr_options.append('<a href="{}">{}</a>'.format("", I18n.lang('pastafari2', 'make_task', 'Make task')))
|
|
arr_options.append('<a href="{}">{}</a>'.format(url_for('admin_app.pastafari2_delete_server', server_id=row_id), I18n.lang('pastafari2', 'delete', 'Delete')))
|
|
|
|
return '<br />'.join(arr_options)
|
|
|
|
|
|
@admin_app.route('/pastafari2/get_groups/', methods=['GET'])
|
|
def get_groups_task():
|
|
|
|
db=g.connection
|
|
|
|
arr_groups=[]
|
|
|
|
with db.query('select * from servergroup', []) as cursor:
|
|
for data in cursor:
|
|
arr_groups.append(data)
|
|
|
|
return json.dumps(arr_groups)
|
|
|
|
|
|
@admin_app.route('/pastafari2/update_task/', methods=['POST'])
|
|
def pastafari2_update_task():
|
|
|
|
db=g.connection
|
|
|
|
ids=json.loads(request.form.get('ids', '[]'))
|
|
arr_ids=[]
|
|
|
|
error=0
|
|
txt_error=''
|
|
error_form={}
|
|
|
|
#print(ids)
|
|
for v in ids:
|
|
arr_ids.append(str(int(v)))
|
|
|
|
where_sql='WHERE id IN ('+",".join(arr_ids)+') order by hostname ASC'
|
|
|
|
#print(where_sql)
|
|
|
|
task=Task(db)
|
|
|
|
task_id=0
|
|
|
|
path_task='modules.pastafari2.tasks.system.updates'
|
|
|
|
data={}
|
|
|
|
server_host=''
|
|
|
|
user=config_task.remote_user
|
|
|
|
ssh_key_priv='./ssh/id_rsa'
|
|
|
|
if not task.run_task(server_host, path_task, 'Update server', 'update_server', 'Task for update servers', user=user, password='', where_sql_server=where_sql, ssh_key_priv=ssh_key_priv, url='', data=data, send_task=True):
|
|
|
|
error=1
|
|
error_form['#server_host_error']=I18n.lang('pastafari2', 'error_exec_task', 'Error: cannot execute the task')
|
|
|
|
task_id=task.task_id
|
|
|
|
return {'error': error, 'txt_error': txt_error, 'error_form': error_form, 'task_id': task_id}
|
|
|
|
return {}
|
|
|
|
@admin_app.route('/pastafari2/multiprogress/')
|
|
def pastafari2_multiprogress():
|
|
|
|
db=g.connection
|
|
|
|
task_id=request.args.get('task_id', '')
|
|
|
|
task=Task(db)
|
|
|
|
arr_task=task.select_a_row(task_id)
|
|
|
|
num_servers=task.set_conditions('WHERE parent_id=%s', [task_id]).select_count()
|
|
|
|
if arr_task:
|
|
|
|
return t.load_template('multiprogress.phtml', title=I18n.lang('pastafari2', 'task_progress', 'Task progress'), path_module='admin_app.pastafari2_dashboard', name_task=arr_task['name_task'], description_task=arr_task['description_task'], task_id=task_id, server=arr_task['server'], num_servers=num_servers)
|
|
|
|
else:
|
|
|
|
return ""
|
|
|
|
@admin_app.route('/pastafari2/get_servers_task/')
|
|
def pastafari2_get_servers_task():
|
|
|
|
db=g.connection
|
|
|
|
task_id=request.args.get('task_id', '')
|
|
|
|
task=Task(db)
|
|
|
|
arr_ids=task.set_conditions('WHERE parent_id=%s', [task_id]).select_to_array(['id', 'hostname', 'server'])
|
|
|
|
resp=make_response(json.dumps(arr_ids))
|
|
|
|
resp.headers['Content-Type']='application/json'
|
|
|
|
return resp
|
|
|
|
@admin_app.route('/pastafari2/get_multiprogress/')
|
|
def pastafari2_get_multiprogress():
|
|
|
|
s=session
|
|
|
|
db=g.connection
|
|
|
|
ids=request.args.get('ids', '[]')
|
|
|
|
#position=0
|
|
|
|
try:
|
|
position=int(request.args.get('position', '0'))
|
|
except:
|
|
position=0
|
|
|
|
final_ids=[str(i) for i in json.loads(ids)]
|
|
|
|
final_str=",".join(['%s']*len(final_ids))
|
|
|
|
task=Task(db)
|
|
|
|
logtask=LogTask(db)
|
|
|
|
arr_log=logtask.set_limit([position, 20]).set_conditions('WHERE task_id IN ({})'.format(final_str), final_ids).select_to_array([], True)
|
|
|
|
resp=make_response(json.dumps(arr_log))
|
|
|
|
resp.headers['Content-Type']='application/json'
|
|
|
|
return resp
|
|
|
|
@admin_app.route('/pastafari2/delete_server/')
|
|
def pastafari2_delete_server():
|
|
|
|
db=g.connection
|
|
|
|
server=ServerDbTask(db)
|
|
|
|
server_id=request.args.get('server_id', '0')
|
|
|
|
arr_server=server.select_a_row(server_id)
|
|
|
|
if arr_server:
|
|
|
|
return t.load_template('delete_server.phtml', title=I18n.lang('pastafari2', 'delete_server', 'Delete server'), path_module='admin_app.pastafari2_dashboard', server_id=server_id, server=arr_server)
|
|
|
|
else:
|
|
|
|
return ""
|
|
|
|
@admin_app.route('/pastafari2/delete_server_db/', methods=['POST'])
|
|
def pastafari2_delete_server_db():
|
|
|
|
db=g.connection
|
|
|
|
error=0
|
|
|
|
server=ServerDbTask(db)
|
|
|
|
server_id=request.form.get('server_id', '0')
|
|
|
|
server.set_conditions('WHERE id=%s', [server_id]).delete()
|
|
|
|
return {'error': error}
|
|
|
|
|
|
@admin_app.route('/pastafari2/edit_server/', methods=['POST', 'GET'])
|
|
def pastafari2_edit_server():
|
|
|
|
db=g.connection
|
|
|
|
error=0
|
|
|
|
server=ServerDbTask(db)
|
|
|
|
#server_id=request.form.get('server_id', '0')
|
|
|
|
url=url_for('.pastafari2_edit_server')
|
|
|
|
admin=GenerateAdminClass(server, url, t)
|
|
|
|
admin.arr_fields_edit=['hostname', 'ip']
|
|
|
|
admin.url_redirect=url_for('.pastafari2_dashboard')
|
|
|
|
form_admin=admin.show()
|
|
|
|
if type(form_admin).__name__=='str':
|
|
|
|
return t.load_template('edit_server.phtml', title=I18n.lang('pastafari2', 'edit_server', 'Edit server'), path_module='admin_app.pastafari2_dashboard', edit_server=form_admin)
|
|
|
|
else:
|
|
return form_admin
|
|
|
|
|
|
|