Last active
August 24, 2016 21:32
-
-
Save tdeck/9fa7ed6ecc62c826732c to your computer and use it in GitHub Desktop.
LifePreserver - Script to limit players' time on a minecraft server
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#! /usr/bin/env python | |
# LifePreserver - Time limiting script for Minecraft servers | |
import sys | |
from subprocess import Popen, PIPE | |
from collections import Counter | |
from datetime import datetime | |
from pytz import timezone | |
from time import sleep | |
START_HOUR = 9 | |
DAILY_CAP = 240 | |
TIMEZONE = timezone('US/Central') | |
accounted_day = None | |
minutes_used = Counter() | |
proc = Popen(sys.argv[1:], stdin=PIPE, stdout=PIPE) | |
def readline(): | |
rv = proc.stdout.readline().strip() | |
print rv | |
return rv | |
def writeline(val): | |
print ">", val | |
proc.stdin.write(val + "\n") | |
def list_players(): | |
writeline('/list') | |
while 'There are' not in readline(): | |
pass | |
names = readline().partition(': ')[2] | |
if not names: return [] | |
return names.split(', ') | |
def tell(player, message): | |
writeline('/tell ' + player + ' ' + message) | |
def kick(player, message): | |
writeline('/kick ' + player + ' ' + message) | |
def check_and_kick(): | |
global accounted_day | |
global minutes_used | |
# Check that the accounting is for today, else reset the count | |
today = datetime.now(TIMEZONE).toordinal() | |
if today != accounted_day: | |
accounted_day = today | |
minutes_used = Counter() | |
players = list_players() | |
for player in players: | |
minutes_used[player] += 1 | |
mins = minutes_used[player] | |
if datetime.now(TIMEZONE).hour < START_HOUR: | |
kick(player, "It's too early to play Minecraft. The server opens again at {}:00".format(START_HOUR)) | |
if mins >= DAILY_CAP: | |
kick(player, "Time's up for today") | |
elif (mins % 30 == 0) or (mins >= DAILY_CAP - 5): # Will be kicked soon | |
tell(player, 'You have {} minutes of play time left.'.format(DAILY_CAP - mins)) | |
elif mins == 1: # First login of the day | |
tell(player, 'You will be able to play on this server for {} minutes today'.format(DAILY_CAP)) | |
tell(player, 'After your time runs out, you will be kicked automatically.') | |
try: | |
while True: | |
sleep(60) | |
check_and_kick() | |
except: | |
proc.terminate() |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment