Browse Source

Strategická: Dokončení logovátka

master
Jiří Kalvoda 2 years ago
parent
commit
c68d624620
  1. 2
      server/hra/web/__init__.py
  2. 104
      server/hra/web/pages.py
  3. 19
      server/static/ksp-mhd.css

2
server/hra/web/__init__.py

@ -83,7 +83,7 @@ def init_request():
g.menu += [ g.menu += [
MenuItem(app.url_for(pages.web_org_games.__name__), "Hry"), MenuItem(app.url_for(pages.web_org_games.__name__), "Hry"),
MenuItem(app.url_for(pages.web_org_users.__name__), "Uživatelé"), MenuItem(app.url_for(pages.web_org_users.__name__), "Uživatelé"),
MenuItem(app.url_for(pages.web_org_logs.__name__), "Logy"), MenuItem(app.url_for(pages.web_org_logs.__name__)+"#main_table" , "Logy"),
] ]
else: else:
g.menu += [ g.menu += [

104
server/hra/web/pages.py

@ -1,5 +1,5 @@
from flask import Flask, redirect, flash, session, g, request, get_flashed_messages from flask import Flask, redirect, flash, session, g, request, get_flashed_messages
from wtforms import Form, BooleanField, StringField, PasswordField, validators, SubmitField, IntegerField, DateTimeField from wtforms import Form, BooleanField, StringField, PasswordField, validators, SubmitField, IntegerField, DateTimeField, SelectMultipleField
from wtforms.validators import ValidationError from wtforms.validators import ValidationError
from flask_wtf import FlaskForm from flask_wtf import FlaskForm
from flask_bootstrap import Bootstrap from flask_bootstrap import Bootstrap
@ -84,6 +84,12 @@ def user_link(user):
return b.root_tag return b.root_tag
def ip_link(ip):
b = html.Builder()
with b.line():
b.a(href=app.url_for(web_org_logs.__name__, ip=ip)+"#main_table")(ip)
return b.root_tag
def right_for_game(game): def right_for_game(game):
if g.org: if g.org:
return True return True
@ -261,14 +267,16 @@ def web_game(game_id):
with b.div(_class="btn-group", role="group"): with b.div(_class="btn-group", role="group"):
if right_for_team(team): if right_for_team(team):
b.a(_class="btn btn-xs btn-primary", href=app.url_for(web_game_view.__name__, game_id=game.game_id, team_id=team.team_id))("Zobrazit hru") b.a(_class="btn btn-xs btn-primary", href=app.url_for(web_game_view.__name__, game_id=game.game_id, team_id=team.team_id))("Zobrazit hru")
b.a(_class="btn btn-xs btn-default", href=app.url_for(web_org_logs.__name__, game_id=game_id, team_id=team.team_id)+"#main_table")("Log")
if g.org: if g.org:
b.a(_class="btn btn-xs btn-default", href=app.url_for(web_org_game_userchange.__name__, game_id=game.game_id, team_id=team.team_id))("Změnit uživatele") b.a(_class="btn btn-xs btn-default", href=app.url_for(web_org_game_userchange.__name__, game_id=game.game_id, team_id=team.team_id))("Změnit uživatele")
with b.div(_class="btn-gruser_idoup", role="group"): with b.div(_class="btn-group", role="group"):
if right_for_step(game): if right_for_step(game):
with b.form(method="POST", _class="btn-group", action=app.url_for(web_game_step.__name__, game_id=game_id)): with b.form(method="POST", _class="btn-group", action=app.url_for(web_game_step.__name__, game_id=game_id)):
b.button(_class="btn btn-primary", type="submit", name="su", value="yes")("Krok") b.button(_class="btn btn-primary", type="submit", name="su", value="yes")("Krok")
if g.org: if g.org:
b.a(_class="btn btn-primary", href=app.url_for(web_org_logs.__name__, game_id=game_id)+"#main_table")("Log")
b.a(_class="btn btn-default", href=app.url_for(web_org_game_round_inspect.__name__, game_id=game_id))("Inspekce kola") b.a(_class="btn btn-default", href=app.url_for(web_org_game_round_inspect.__name__, game_id=game_id))("Inspekce kola")
if g.org: if g.org:
@ -379,13 +387,18 @@ def web_org_game_round_inspect(game_id, round_id=None):
b.line().th()("Bodů") b.line().th()("Bodů")
b.line().th()("Stažení") b.line().th()("Stažení")
b.line().th()("Nahrání") b.line().th()("Nahrání")
b.line().th()("Akce")
for team, move in zip(teams, moves): for team, move in zip(teams, moves):
with b.tr(): with b.tr():
b.line().td()(team.team_id) b.line().td()(team.team_id)
b.line().td()(user_link(team.user),": ", team.name) b.line().td()(user_link(team.user),": ", team.name)
b.line().td()(move.points) b.line().td()(move.points)
b.line().td()(move.reads_count) b.line().td()(move.reads_count)
b.line().td()(f"{move.ok_pushs_count} {move.warnings_pushs_count} {move.err_pushs_count}") b.line().td()(f"ok: {move.ok_pushs_count} w: {move.warnings_pushs_count} e: {move.err_pushs_count}")
with b.td():
with b.div(_class="btn-group", role="group"):
if right_for_team(team):
b.a(_class="btn btn-xs btn-primary", href=app.url_for(web_org_logs.__name__, game_id=game_id, team_id=team.team_id, round_id=round_id)+"#main_table")("Log")
return b.print_file() return b.print_file()
@ -482,6 +495,7 @@ def web_org_user(user_id):
b.line().h2("Uživatel ", user.print()) b.line().h2("Uživatel ", user.print())
with b.div(_class="btn-group", role="group"): with b.div(_class="btn-group", role="group"):
with b.form(method="POST", _class="btn-group", action=app.url_for(web_org_user_su.__name__, user_id=user.id)): with b.form(method="POST", _class="btn-group", action=app.url_for(web_org_user_su.__name__, user_id=user.id)):
b.a(_class="btn btn-primary", href=app.url_for(web_org_logs.__name__, user_id=user.id)+"#main_table")("Log")
b.button(_class="btn btn-default", type="submit", name="su", value="yes")("Převtělit") b.button(_class="btn btn-default", type="submit", name="su", value="yes")("Převtělit")
b.h3("Týmy") b.h3("Týmy")
with b.p().table(_class="data full"): with b.p().table(_class="data full"):
@ -503,8 +517,8 @@ def web_org_user_su(user_id):
flash("Uživatel vtělen!") flash("Uživatel vtělen!")
return redirect('/') return redirect('/')
@app.route("/org/log/<int:log_id>", methods=['GET']) @app.route("/org/log/<int:log_id>/data", methods=['GET'])
def web_org_log(log_id): def web_org_log_data(log_id):
l = db.get_session().query(db.Log).filter_by(log_id=log_id).one_or_none() l = db.get_session().query(db.Log).filter_by(log_id=log_id).one_or_none()
if l is None: if l is None:
raise werkzeug.exceptions.NotFound() raise werkzeug.exceptions.NotFound()
@ -513,31 +527,74 @@ def web_org_log(log_id):
b.p().pre(pprint.pformat(l.get_data())) b.p().pre(pprint.pformat(l.get_data()))
return b.print_file() return b.print_file()
class LogsFindForm(FlaskForm):
username = StringField('Jméno uživatele')
user_id = OptionalIntField('ID uživatele')
game_id = OptionalIntField('ID hry')
team_id = OptionalIntField('Tým')
round_id = OptionalIntField('Kolo')
limit = OptionalIntField('Limit')
ip = StringField('IP')
status = SelectMultipleField('Status', choices=[("", "*")]+[(x,x) for x in ["ok", "warning", "too_early", "too_late", "error", "http-error"]], render_kw={"size":7})
endpoint = SelectMultipleField('Stránky', choices=db.Endpoint.choices())
submit = SubmitField("Najít")
def validate_captcha(form, field):
if field.data != config.CAPTCHA:
raise ValidationError("Chyba!")
@app.route("/org/logs", methods=['GET']) @app.route("/org/logs", methods=['GET'])
def web_org_logs(): def web_org_logs():
logs = db.get_session().query(db.Log).order_by(db.Log.log_id.desc()).all() f = LogsFindForm(formdata=request.args, csrf_enabled=False)
q = db.get_session().query(db.Log).order_by(db.Log.log_id.desc())
if request.args:
f.validate()
if f.username.data:
q = q.filter(db.User.username.ilike(f"%{f.username.data}%"))
if f.user_id.data is not None:
q = q.filter_by(user_id=f.user_id.data or None)
if f.game_id.data is not None:
q = q.filter_by(game_id=f.game_id.data or None)
if f.team_id.data is not None:
q = q.filter_by(team_id=f.team_id.data or None)
if f.round_id.data is not None:
q = q.filter_by(round=f.round_id.data)
if f.ip.data:
q = q.filter(db.Log.source_ip.ilike(f"%{f.ip.data}%"))
if f.status.data and "" not in f.status.data:
q = q.filter(db.Log.status.in_(f.status.data))
if f.endpoint.data:
q = q.filter(db.Log.endpoint.in_(f.endpoint.data))
limit = f.limit.data or 20
logs = q.limit(limit).all()
count = q.count()
b = BasePage() b = BasePage()
del f.csrf_token
b.line().h2("Logy") b.line().h2("Logy")
b(jinja_mac.quick_form(f, form_type='horizontal', method="GET"))
with b.p().table(_class="data full"): with b.p().table(_class="data full"):
with b.thead(): with b.thead(id="main_table"):
b.line().th()("Čas") b.line().th("Čas")
b.line().th()("Uživatel") b.line().th("Uživatel")
b.line().th()("URL") b.line().th("URL")
b.line().th()("Hra") b.line().th("Hra")
b.line().th()("Tým") b.line().th("Status")
b.line().th()("Status") b.line().th("Popis")
b.line().th()("Popis") b.line().th("GET")
b.line().th()("GET") b.line().th("Akce")
b.line().th()("Akce")
for l in logs: for l in logs:
with b.tr(): with b.tr(_class="log_"+l.status):
b.line().td(l.time.strftime("%H:%M:%S")) b.line().td(l.time.strftime("%H:%M:%S"))
b.line().td(l.user.print() if l.user else None, b._br(), l.source_ip) b.line().td(user_link(l.user) if l.user else None, b._br(), ip_link(l.source_ip))
b.line().td(l.endpoint._name_, b._br(), l.url) b.line().td(l.endpoint._name_, b._br(), l.url)
b.line().td(l.game.print() if l.game else None) b.line().td(l.game.print() if l.game else None, b._br(), "tým: ", l.team_id, " kolo: ", l.round)
b.line().td(l.team_id)
b.line().td(l.status) b.line().td(l.status)
b.line().td(l.text) b.line().td(l.text)
with b.line().td(): with b.line().td():
@ -545,7 +602,12 @@ def web_org_logs():
b(f"{k}: {v}").br() b(f"{k}: {v}").br()
with b.line().td(): with b.line().td():
with b.div(_class="btn-group", role="group"): with b.div(_class="btn-group", role="group"):
b.a(href=app.url_for(web_org_log.__name__, log_id=l.log_id), _class="btn btn-xs btn-primary")("Podrobnosti") if l.data is not None:
b.a(href=app.url_for(web_org_log_data.__name__, log_id=l.log_id), _class="btn btn-xs btn-primary")("Data")
if count <= limit:
b.line().p(f"Toť vše ({count})")
else:
b.line().p().b(f"Zobrazeno prvních {limit} logů z {count}")
return b.print_file() return b.print_file()
from hra.web.game import get_wlogic, wlogic_by_mode from hra.web.game import get_wlogic, wlogic_by_mode

19
server/static/ksp-mhd.css

@ -300,3 +300,22 @@ nav#main-menu a.active {
.collapsible input[type="checkbox"].toggle:checked ~ .collapsible-inner { .collapsible input[type="checkbox"].toggle:checked ~ .collapsible-inner {
max-height: 100vh; max-height: 100vh;
} }
.log_ok {
background-color: #BBFFBB;
}
.log_warning {
background-color: #FFFFBB;
}
.log_error {
background-color: #FFBBBB;
}
.log_http-error {
background-color: #FF0000;
}
.log_too_late {
background-color: #BBFFFF;
}
.log_too_early {
background-color: #BBBBFF;
}

Loading…
Cancel
Save