Browse Source

Initial commit

Kirk Trombley 6 years ago
commit
39ac497712
5 changed files with 99 additions and 0 deletions
  1. 3 0
      .gitignore
  2. 11 0
      README.md
  3. 79 0
      app.py
  4. 2 0
      requirements.txt
  5. 4 0
      secret.toml.template

+ 3 - 0
.gitignore

@@ -0,0 +1,3 @@
+__pycache__/
+*.pyc
+secret.toml

+ 11 - 0
README.md

@@ -0,0 +1,11 @@
+# Teamspeak Server Status Service
+
+Simple Flask app, exposes 2 endpoints
+
+`/` - Return the user list of the server as JSON of the form `{users: ["foo", "bar"]}`
+
+`/page` - A human-readable HTML page with the user list
+
+Config goes in `secret.toml` file, following the `secret.toml.template` given
+
+No guarantees for speed or safety are made

+ 79 - 0
app.py

@@ -0,0 +1,79 @@
+#!/usr/bin/env python3
+
+from telnetlib import Telnet
+
+import toml
+from flask import Flask, jsonify, render_template_string
+
+app = Flask(__name__)
+
+
+def get_users():
+    with open("secret.toml") as infile:
+        cfg = toml.load(infile)
+
+    login = ("login %s %s\n" % (cfg["user"], cfg["pass"])).encode("utf-8")
+
+    with Telnet(cfg["host"], cfg["port"], 5) as tn:
+        tn.write(login)
+        tn.write(b"use 1 -virtual\n")
+        tn.write(b"clientlist\n")
+        tn.write(b"whoami\n")
+        tn.write(b"quit\n")
+        response = tn.read_until(b"virtualserver_status").decode("ascii")
+
+    return [x.split("=", 1)[1] for x in response.split()
+            if x.startswith("client_nickname") and "serveradmin" not in x]
+
+
+@app.route("/")
+def get_status():
+    return jsonify({"users": get_users()})
+
+
+@app.route("/page")
+def get_status_page():
+    users = get_users()
+    if len(users) == 0:
+        text = "No one in teamspeak!"
+    elif len(users) == 1:
+        text = f"Only {users[0]}"
+    else:
+        text = "I see the following people: " + ", ".join(users)
+
+    return render_template_string("""
+        <!doctype html>
+        <title>Teamspeak Server Status</title>
+        <style>
+        body {
+            margin: 0px 0px 0px 0px;
+            padding: 0px 0px 0px 0px;
+            font-family: verdana, arial, helvetica, sans-serif;
+            color: #ccc;
+            background-color: #333;
+        }
+        h1 {
+            font-size: 24px;
+            line-height: 44px;
+            font-weight: bold;
+            margin-top: 0;
+            margin-bottom: 0;
+        }
+        </style>
+        {% if scrolling %}
+        <marquee direction="up" style="height 600px" behavior="alternate">
+        <marquee direction="right" style="width 600px" behavior="alternate">
+        {% endif %}
+        <div class="page">
+            <h1>TeamSpeak Server Status</h1>
+            {{ r }}
+        </div>
+        {% if scrolling %}
+        </marquee>
+        </marquee>
+        {% endif %}
+    """, scrolling=True, r=text)
+
+
+if __name__ == "__main__":
+    app.run("0.0.0.0", 5000, debug=True, threaded=True)

+ 2 - 0
requirements.txt

@@ -0,0 +1,2 @@
+toml
+Flask

+ 4 - 0
secret.toml.template

@@ -0,0 +1,4 @@
+host = "ADDRESS"
+port = 10011
+user = "USER"
+pass = "PASS"