TeamspeakStats/tsstats/template.py

109 lines
3.5 KiB
Python
Raw Normal View History

# -*- coding: utf-8 -*-
import logging
from collections import namedtuple
from os.path import dirname, join
import pendulum
from jinja2 import ChoiceLoader, Environment, FileSystemLoader, PackageLoader
from tsstats.log import Server
from tsstats.utils import filter_threshold, seconds_to_text, sort_clients
logger = logging.getLogger('tsstats')
SortedClients = namedtuple('SortedClients', [
'onlinetime', 'kicks', 'pkicks', 'bans', 'pbans'])
def prepare_clients(clients, onlinetime_threshold=-1):
'''
Prepare `clients` for rendering
sort them, clean their nick-history and convert onlinetime to string
:param clients: List of clients to prepare
:param onlinetime_threshold: threshold for clients onlinetime
:type clients: tsstats.client.Clients
:type onlinetime_treshold: int
:return: `clients` sorted by onlinetime, kics, pkicks, bans and pbans
:rtype: tsstats.template.SortedClients
'''
# drop current nick from nick-history
[
c.nick_history.remove(c.nick)
for c in clients
if c.nick in c.nick_history
]
# sort by onlinetime
onlinetime_ = sort_clients(
clients, lambda c: c.onlinetime.total_seconds()
)
# filter clients not matching threshold
onlinetime_ = filter_threshold(onlinetime_, onlinetime_threshold)
# convert timespans to text
onlinetime = [
(client, seconds_to_text(int(onlinetime)))
for client, onlinetime in onlinetime_
]
return SortedClients(
onlinetime=onlinetime,
kicks=sort_clients(clients, lambda c: c.kicks),
pkicks=sort_clients(clients, lambda c: c.pkicks),
bans=sort_clients(clients, lambda c: c.bans),
pbans=sort_clients(clients, lambda c: c.pbans)
)
def render_servers(servers, output, title='TeamspeakStats',
template='index.jinja2', datetime_fmt='%x %X %Z',
onlinetime_threshold=-1):
'''
Render `servers`
:param servers: list of servers to render
:param output: path to output-file
:param template_name: path to template-file
:param title: title of the resulting html-document
:param template_path: path to template-file
:param datetime_fmt: custom datetime-format
:param onlinetime_threshold: threshold for clients onlinetime
:type servers: [tsstats.log.Server]
:type output: str
:type template_name: str
:type title: str
:type template_path: str
:type datetime_fmt: str
:type onlinetime_threshold: int
'''
# preparse servers
prepared_servers = [
2016-11-23 15:23:20 -05:00
Server(sid, prepare_clients(clients, onlinetime_threshold))
for sid, clients in servers
]
# render
template_loader = ChoiceLoader([
PackageLoader(__package__, 'templates'),
FileSystemLoader(join(dirname(__file__), 'templates'))
])
template_env = Environment(loader=template_loader)
def frmttime(timestamp):
if not timestamp:
return ''
formatted = timestamp.strftime(datetime_fmt)
logger.debug('Formatting timestamp %s -> %s', timestamp, formatted)
return formatted
template_env.filters['frmttime'] = frmttime
2016-11-18 15:46:38 -05:00
template = template_env.get_template(template)
logger.debug('Rendering template %s', template)
template.stream(title=title, servers=prepared_servers,
debug=logger.level <= logging.DEBUG,
creation_time=pendulum.utcnow())\
.dump(output, encoding='utf-8')
logger.debug('Wrote rendered template to %s', output)