168 lines
4.4 KiB
Python
168 lines
4.4 KiB
Python
#!/usr/bin/env python3
|
|
|
|
import logging
|
|
from influxdb import InfluxDBClient
|
|
import requests
|
|
import os
|
|
from random import randint
|
|
from time import sleep
|
|
import sys
|
|
import csv
|
|
import traceback
|
|
from collections import namedtuple
|
|
|
|
|
|
timeout = int(os.environ.get("RSSCRAPE_TIMEOUT", 60))
|
|
|
|
|
|
def get_influx():
|
|
influx_host = os.environ.get("INFLUX_HOST")
|
|
influx_port = os.environ.get("INFLUX_PORT")
|
|
influx_db = os.environ.get("INFLUX_DB")
|
|
|
|
if not all([influx_host, influx_port, influx_db]):
|
|
logging.critical("must set INFLUX_HOST, INFLUX_PORT and INFLUX_DB")
|
|
sys.exit(1)
|
|
|
|
influx = InfluxDBClient(influx_host, influx_port) # user, password
|
|
influx.create_database(influx_db)
|
|
influx.switch_database(influx_db)
|
|
|
|
return influx
|
|
|
|
|
|
# order of the skills in the stats data
|
|
STATS = ["Overall",
|
|
"Attack",
|
|
"Defence",
|
|
"Strength",
|
|
"Hitpoints",
|
|
"Ranged",
|
|
"Prayer",
|
|
"Magic",
|
|
"Cooking",
|
|
"Woodcutting",
|
|
"Fletching",
|
|
"Fishing",
|
|
"Firemaking",
|
|
"Crafting",
|
|
"Smithing",
|
|
"Mining",
|
|
"Herblore",
|
|
"Agility",
|
|
"Thieving",
|
|
"Slayer",
|
|
"Farming",
|
|
"Runecraft",
|
|
"Hunter",
|
|
"Construction"]
|
|
|
|
LEVELS = [0, 83, 174, 276, 388, 512, 650, 801, 969, 1154,
|
|
1358, 1584, 1833, 2107, 2411, 2746, 3115, 3523, 3973, 4470,
|
|
5018, 5624, 6291, 7028, 7842, 8740, 9730, 10824, 12031, 13363,
|
|
14833, 16456, 18247, 20224, 22406, 24815, 27473, 30408, 33648, 37224,
|
|
41171, 45529, 50339, 55649, 61512, 67983, 75127, 83014, 91721, 101333,
|
|
111945, 123660, 136594, 150872, 166636, 184040, 203254, 224466, 247886, 273742,
|
|
302288, 333804, 368599, 407015, 449428, 496254, 547953, 605032, 668051, 737627,
|
|
814445, 899257, 992895, 1096278, 1210421, 1336443, 1475581, 1629200, 1798808, 1986068,
|
|
2192818, 2421087, 2673114, 2951373, 3258594, 3597792, 3972294, 4385776, 4842295, 5346332,
|
|
5902831, 6517253, 7195629, 7944614, 8771558, 9684577, 10692629, 11805606, 13034431]
|
|
|
|
|
|
StatData = namedtuple("StatData", "skill rank level xp xp_next")
|
|
|
|
|
|
def get_player(name):
|
|
|
|
data = None
|
|
|
|
for trynum in range(0, 5):
|
|
sleep(randint(5, 30) * trynum)
|
|
print(f"try #{trynum}")
|
|
|
|
try:
|
|
r = requests.get("https://secure.runescape.com/m=hiscore_oldschool/a=13/index_lite.ws",
|
|
params={"player": name},
|
|
timeout=timeout)
|
|
if r.status_code != 200:
|
|
print(f"retrying, status code = {r.status_code}")
|
|
continue
|
|
except:
|
|
print(traceback.format_exc())
|
|
continue
|
|
|
|
_data = r.text
|
|
print(_data)
|
|
|
|
if len(_data) == 0 or _data[0] not in "-1234567890":
|
|
print(f"retrying, body must start with a number")
|
|
continue
|
|
|
|
data = _data
|
|
break
|
|
|
|
if data is None:
|
|
return None
|
|
|
|
# with open("sample.txt") as f:
|
|
# data = f.read()
|
|
reader = csv.reader(data.splitlines(), delimiter=',')
|
|
rows = list(reader)
|
|
ret = []
|
|
for i, row in enumerate(rows): # rank, level, xp
|
|
if i >= len(STATS):
|
|
break
|
|
level = int(row[1])
|
|
xp = int(row[2])
|
|
xp_next = -1
|
|
if level < len(LEVELS):
|
|
xp_next = LEVELS[level] - xp
|
|
ret.append(StatData(STATS[i].lower(), int(row[0]), level, xp, xp_next))
|
|
return ret
|
|
|
|
|
|
def main():
|
|
logging.basicConfig(level=logging.WARNING,
|
|
format="%(asctime)-15s %(levelname)-8s %(filename)s:%(lineno)d %(message)s")
|
|
|
|
influx = get_influx()
|
|
|
|
player_name = os.environ["PLAYER_NAME"]
|
|
|
|
if not player_name:
|
|
logging.critical("must set PLAYER_NAME")
|
|
sys.exit(1)
|
|
|
|
player_name = player_name.lower()
|
|
|
|
stats = get_player(player_name)
|
|
|
|
if stats is None:
|
|
print("failed to fetch player!")
|
|
sys.exit(1)
|
|
|
|
body = []
|
|
|
|
for measurement in ("rank", "level", "xp", "xp_next"):
|
|
fields = {}
|
|
for stat in stats:
|
|
fields[stat.skill] = getattr(stat, measurement)
|
|
|
|
blob = {"measurement": measurement,
|
|
"tags": {"username": player_name},
|
|
"fields": fields}
|
|
|
|
body.append(blob)
|
|
|
|
# import json
|
|
# print(json.dumps(body, indent=4))
|
|
# return
|
|
|
|
influx.write_points(body)
|
|
|
|
print("done!")
|
|
|
|
|
|
if __name__ == '__main__':
|
|
main()
|