Initial commit

This commit is contained in:
Robert Miles 2018-06-26 00:12:53 +00:00
commit ee76802e74
69 changed files with 27834 additions and 0 deletions

39
NormalBot.py Normal file
View File

@ -0,0 +1,39 @@
import socket;
class NotRunningException (Exception):
pass;
class IRCBot:
# The IRC bot class. This can be reused, and will be the superclass of the actual minerbot.
def __init__(self, name, user, realname, owner):
self.name = name;
self.owner = owner;
self.user = user;
self.realname = realname;
self.running = False;
def begin(self, server, port, channels):
self.irc = socket.socket();
self.running = True;
self.irc.connect((server, port));
self.irc.send("NICK " + self.name + "\r\n");
self.irc.send("USER " + self.user + " 8 * " + self.realname + "\r\n");
for chan in channels:
self.irc.send("JOIN " + chan + "\r\n");
while True:
data = self.irc.recv(4096);
#print data;
if data.find("PING") != -1:
self.irc.send("PONG " + data.split()[1] + "\r\n");
elif data.find("PRIVMSG") != -1:
self.spokento(data)
def spokento(self, data):
if not self.running:
raise Exception("spokento was prematurely called.");
data_parts = data.split(" ",3);
id = data_parts[0];
nick = id.split("!")[0][1:];
message = data_parts[3][1:];
print(nick + ": " + message);
self.irc.send("PRIVMSG " + data_parts[2] + " :" + nick + ": " + message + "\r\n");

BIN
NormalBot.pyc Normal file

Binary file not shown.

12
bfc.py Executable file
View File

@ -0,0 +1,12 @@
#!/usr/bin/python
#programlines = sys.stdin.readlines()
symbols = ["<",">","+","-","[","]",",","."]
def clean(i):
cleanedChars = []
for char in i:
if char in symbols:
cleanedChars.append(char);
return "".join(cleanedChars)

BIN
bfc.pyc Normal file

Binary file not shown.

16
bot_runner.py Normal file
View File

@ -0,0 +1,16 @@
import minerbot
while(True):
bot = minerbot.minerbot("minerbot","minerbot","minerobber")
f = open("/home/minerobber/misc/mbchan.txt")
channels = f.read().split("\n")
f.close()
# try:
val = bot.begin("localhost",6667,channels)
if val == 0:
break
# except Exception as e:
# raise e
# bot.addNote("minerobber","Minerbot Crash","Crashed with {}: {}".format(type(e).__name__,str(e)))
# finally:
# reload(minerbot)

42
chaninfo.py Normal file
View File

@ -0,0 +1,42 @@
import requests
class ChanInfoError(Exception):
pass;
class ChannelInfo:
"""A class for obtaining info for a Twitch Channel"""
def __init__(self,channel,client_id):
self.channel = channel;
self.client_id = client_id;
self.resp = requests.get("https://api.twitch.tv/kraken/streams/{!s}?client_id={!s}".format(channel,client_id));
if self.resp.json().get("error") != None:
raise ChanInfoError("{status} {error} - \"{message}\"".format(**self.resp.json()))
"""If the channel is online, returns true. Else, returns false."""
def isOnline(self):
return self.resp.json().get('stream') != None;
"""Get the status of the stream."""
def getStatus(self):
return self.resp.json()['stream']['channel']['status']
"""Get the game."""
def getGame(self):
return self.resp.json()['stream']['game']
"""Get whether to display "playing" or "being"."""
def getDisplay(self):
return self.getGame() == "Creative"
"""Get viewer count."""
def getViewers(self):
return self.resp.json()['stream']['viewers']
"""Get embed frame (for HTML)"""
def getEmbed(self, width=950, height=700, autoplay=False):
return "<iframe src='http://player.twitch.tv/?channel={}&autoplay={}' width='{!s}' height='{!s}' frameborder='0' scrolling='no' allowfullscreen='true'></iframe>".format(self.channel,str(autoplay).lower(),width,height)
"""Update data, just runs the init again."""
def update(self):
self.__init__(self.channel,self.client_id)

BIN
chaninfo.pyc Normal file

Binary file not shown.

27
choose_parser.py Normal file
View File

@ -0,0 +1,27 @@
testString = 'say "Jasper Oxide" "Are you really that stupid?"'
def parse(text,debug=False):
lines = [text.rstrip()]
result = []
for line in lines:
linetable = []
words = line.split(" ")
i=0
while i < len(words):
if words[i].startswith('"'):
if words[i].endswith('"'):
linetable.append(words[i][1:-1])
i = i + 1
continue
part = words[i][1:]
i=i+1
while not words[i].endswith('"'):
part = part + " " + words[i]
i = i + 1
part = part + " " + words[i][:-1]
linetable.append(part)
else:
part = words[i]
linetable.append(part)
i = i + 1
result.append(linetable)
return result[0][1:]

BIN
choose_parser.pyc Normal file

Binary file not shown.

40
colorbot.py Normal file
View File

@ -0,0 +1,40 @@
import socket;
class NotRunningException (Exception):
pass;
class IRCBot:
# The IRC bot class. This can be reused, and will be the superclass of the actual minerbot.
def __init__(self, name, user, realname, owner):
self.name = name;
self.owner = owner;
self.user = user;
self.realname = realname;
self.running = False;
def begin(self, server, port, channels):
self.irc = socket.socket();
self.running = True;
self.irc.connect((server, port));
self.irc.send("NICK " + self.name + "\r\n");
self.irc.send("USER " + self.user + " 8 * " + self.realname + "\r\n");
for chan in channels:
self.irc.send("JOIN " + chan + "\r\n");
while True:
data = self.irc.recv(4096);
#print data;
if data.find("PING") != -1:
self.irc.send("PONG " + data.split()[1] + "\r\n");
elif data.find("PRIVMSG") != -1:
self.spokento(data)
def spokento(self, data):
if not self.running:
raise Exception("spokento was prematurely called.");
data_parts = data.split(" ",3);
id = data_parts[0];
nick = id.split("!")[0][1:];
message = data_parts[3][1:-2];
print(nick + ": " + message);
if nick == self.owner and message.find("!colortest") == 0:
self.irc.send("PRIVMSG "+data_parts[2]+" :\x034,1yo\x0f")

BIN
colorbot.pyc Normal file

Binary file not shown.

2
corpus Normal file
View File

@ -0,0 +1,2 @@
hi, how are you?
you seem nice.

10531
data/a-words.txt Normal file

File diff suppressed because it is too large Load Diff

2111
data/k-words.txt Normal file

File diff suppressed because it is too large Load Diff

9584
data/m-words.txt Normal file

File diff suppressed because it is too large Load Diff

1
data/synopses.json Normal file

File diff suppressed because one or more lines are too long

1
data/titles.json Normal file

File diff suppressed because one or more lines are too long

3927
data/w-words.txt Normal file

File diff suppressed because it is too large Load Diff

1
key.ps Normal file
View File

@ -0,0 +1 @@
h7lvoe263k42haljbhlbv2ag1nzt5nd

20
kwam.py Normal file
View File

@ -0,0 +1,20 @@
import random
class KWAMPlugin:
def __init__(self,bot):
for i in "kwam":
with open("data/"+i+"-words.txt") as f:
setattr(self,i,[line.replace("\n","") for line in f.readlines()])
self.bot=bot
self.answerRequests = True
def answer(self,channel,nick,msg):
if not msg.startswith("!kwam"):
return
if nick==self.bot.owner:
if msg.startswith("!kwam "):
self.answerRequests = msg.endswith("on")
return
if self.answerRequests:
words = [random.choice(self.k),random.choice(self.w),random.choice(self.a),random.choice(self.m)]
self.bot.mention(channel,nick," ".join(words))

BIN
kwam.pyc Normal file

Binary file not shown.

35
lua.py Normal file
View File

@ -0,0 +1,35 @@
from subapi import SubAPI
class LuaPlugin:
"""Handles lua execution"""
def __init__(self,bot):
self.bot = bot
self.channels = dict()
def addChannel(self,chan):
self.channels[chan]=SubAPI()
self.channels[chan].addListener(self.outWithIt(chan))
self.channels[chan].start(["/usr/bin/lua"])
def outWithIt(self,chan):
def handler(msg):
if msg.strip()=="Lua 5.2.4 Copyright (C) 1994-2015 Lua.org, PUC-Rio":
return
self.bot.say(chan,msg)
return handler
def handleCommand(self,chan,sender,cmd):
if cmd.strip()=="!lua":
self.bot.mention(chan,sender,"Use !lua <lua command> to execute lua.")
elif not cmd.startswith("!lua "):
return
elif cmd.strip()=="!lua start" and not self.channels[chan]:
self.addChannel(chan)
self.bot.say(chan,"Lua session started")
elif cmd.strip()=="!lua reset" and self.channels[chan]:
self.channels[chan].stop()
del self.channels[chan]
self.addChannel(chan)
self.bot.say(chan,"Lua session reset")
else:
self.channels[chan].sendInput(cmd.strip.split(" ",2)[1])

BIN
lua.pyc Normal file

Binary file not shown.

42
markov.py Normal file
View File

@ -0,0 +1,42 @@
import random,json
class Chain:
def __init__(self):
self.map = {}
def addWord(self,lastWord,word):
if lastWord in self.map and not word in self.map[lastWord]:
self.map[lastWord].append(word)
elif not lastWord in self.map:
self.map[lastWord] = [word]
def train(self,sentance):
words = sentance.split(" ")
lastWord = words.pop(0)
self.addWord("",lastWord)
for word in words:
self.addWord(lastWord,word)
lastWord = word
self.addWord(lastWord,"")
def generate(self):
lastWord = random.choice(self.map[""])
sentence = lastWord
while lastWord != "":
word = random.choice(self.map[lastWord])
sentence += " " + word
lastWord = word
return sentence[:-1]
def to_json(self):
return json.dumps(self.map)
@classmethod
def from_json(cls,jsonstr):
ret = cls()
ret.map = json.loads(jsonstr)
return ret
def addLinesFromFile(chain,filename):
with open(filename) as f:
for line in f.readlines():
chain.train(line.rstrip())

BIN
markov.pyc Normal file

Binary file not shown.

17
markovuniverse.py Normal file
View File

@ -0,0 +1,17 @@
import markov
def chainFromFile(filename):
with open(filename) as f:
return markov.Chain.from_json(f.read())
titles = chainFromFile("data/titles.json")
synopses = chainFromFile("data/synopses.json")
def new_episode():
title = titles.generate().encode("utf-8")
synopsis = synopses.generate().encode("utf-8")
return (title,synopsis)
if __name__=="__main__":
details = new_episode()
print "New episode:\n{} - {}".format(*details)

BIN
markovuniverse.pyc Normal file

Binary file not shown.

86
mbtilde.py Normal file
View File

@ -0,0 +1,86 @@
import sieve,plugin
class Solver(plugin.Plugin):
def __init__(self,bot):
plugin.Plugin.__init__(self,bot,"!mbtilde ([a-z]+) ([A-Za-z0-9]+)(?: (.+))?")
def answer(self,c,n,m):
if not self.cmd.search(m):
return
if n!=self.bot.owner:
self.bot.say(c,"Don't tell me what to do!")
return
if c!="#bots":
self.bot.say(c,"Remember: tildebot only awards tildes in \#bots.")
plugin.Plugin.answer(self,c,n,m) # call super method
def run(self,cmd):
if not cmd.startswith("!mbtilde"):
return False
else:
parts = cmd.split()
parts.pop(0)
parts = [part.strip() for part in parts]
try:
return getattr(self,parts[0])(*parts[1:])
except:
return False
def request(self,c,n,m):
self.bot.say(c,self._request())
def _request(self):
return "!tilde"
def add(self,c,n,m):
self.bot.say(c,self._add(m.group(2),m.group(3)))
def _add(self,num1,num2):
return int(num1)+int(num2)
def sub(self,c,n,m):
self.bot.say(c,self._sub(m.group(2),m.group(3)))
def _sub(self,num1,num2):
return int(num1)-int(num2)
def mult(self,c,n,m):
self.bot.say(c,self._mult(m.group(2),m.group(3)))
def _mult(self,num1,num2):
return int(num1)*int(num2)
def div(self,c,n,m):
self.bot.say(c,self._div(m.group(2),m.group(3)))
def _div(self,num1,num2):
return int(num1)/int(num2)
def pow(self,c,n,m):
self.bot.say(c,self._pow(m.group(2),m.group(3)))
def _pow(self,num1,num2):
return int(num1)**int(num2)
def mod(self,c,n,m):
self.bot.say(c,self._mod(m.group(2),m.group(3)))
def _mod(self,num1,num2):
return int(num1)%int(num2)
def primefac(self,c,n,m):
self.bot.say(c,self._primefac(m.group(2)))
def _primefac(self,num):
return sieve.primefactors(int(num))
def score(self,c,n,m):
self.bot.say(c,self._score())
def _score(self,d):
return "!tildescore"
def say(self,c,n,m):
self.bot.say(c,self._say(m.group(2)))
def _say(self,msg):
return msg

BIN
mbtilde.pyc Normal file

Binary file not shown.

27
minerbot.commands Normal file
View File

@ -0,0 +1,27 @@
if message.find("!steven-universe") == 0:
elif message.find("!log") == 0:
if message.find("!quit") == 0 and nick == self.owner:
elif message.find("!rollcall") == 0:
elif message.find("!twitch ") == 0:
elif message.find("!choose ") == 0:
elif message.strip == "!last5said":
elif message.find("!dicegame") == 0:
elif message.find("!online") == 0:
elif message.find("!reload\r\n") == 0 and self.owner == nick:
# elif message.find("!shop") == 0:
elif message.find("!tbadmin") == 0 and self.owner == nick:
elif message.find("!announce ") == 0:
# elif message.find("!guessing_game") == 0 and self.gg_state == "not-active":
# elif message.find("!join_guessing_game") == 0 and self.gg_state == "player-wait":
elif message.find("!reloadchannels") == 0 and nick == self.owner:
elif message.find("!save") == 0 and nick == self.owner:
elif message.find("!load") == 0 and nick == self.owner:
#elif message.find("!money") == 0:
elif message.find("!update-qdb-commits") == 0 and self.owner == nick:
elif message.find("!run ") == 0 and self.owner == nick:
#elif message.find("!tell") == 0:
elif message.find("!note ") == 0:
# elif message.find("!get-gg-state") == 0 and self.owner == nick:
elif message.find("!getStock") == 0:
elif message.find("!mbtilde ") == 0:
# elif message.find("!helpme") == 0:

414
minerbot.py Normal file
View File

@ -0,0 +1,414 @@
import socket,random,subprocess,threading,time,cPickle,string,time,prss,randwords,pstocks,chaninfo,primefac,choose_parser,notes,mbtilde,kwam,lua,urn,scplugin,json,math;
import os.path as fs;
from email.mime.text import MIMEText;
import markovuniverse as mu;
zws = ""
class NotRunningException (Exception):
pass;
log_format = "{} [{}] {}: {}"
def loadLNR():
with open("/home/minerobber/lnr.txt") as f:
return [l.rstrip() for l in f if l.rstrip()]
def saveLNR(lnr):
with open("/home/minerobber/lnr.txt","w") as f:
f.write("\n".join(lnr))
def filterNick(nick):
if len(nick) == 1:
print "Either "+nick+" is not a nick, or the person who has that nick needs a longer nick."
return nick
s = nick[0]+zws+nick[1:]
return s.encode('utf-8')
def log(channel, nick, message):
with open("/home/minerobber/log.txt","ab") as fh:
fh.write(log_format.format(time.strftime("%Y-%m-%d %H:%M:%S"),channel,nick,message))
with open("/home/minerobber/logs/"+time.strftime("%Y-%m-%d")+".txt","ab") as fh:
fh.write(log_format.format(time.strftime("%Y-%m-%d %H:%M:%S"),channel,nick,message))
def announce(channel, nick, ann, prssfeed):
prssfeed.addItem("Announcement by {} in {}".format(channel, nick),"https://tilde.town/~{}".format(nick),ann)
with open(fs.expanduser("~/public_html/announcements/rss.xml"),"wb") as rss:
rss.write(prssfeed.make())
with open(fs.expanduser("~/public_html/announcements/index.text"),"ab") as html:
html.write('{}, while in {}, announced: "{}" \n'.format(nick, channel, ann));
subprocess.check_output(["make -C ~/public_html/announcements -B"],shell=True)
cPickle.dump(prssfeed,open("/home/minerobber/misc/annrss","wb"))
def logJoin(channel,nick):
with open("/home/minerobber/log.txt","ab") as fh:
fh.write(time.strftime("%Y-%m-%d %H:%M:%S",time.localtime())+" "+nick+" joined "+channel)
def logPart(channel,nick):
with open("/home/minerobber/log.txt","ab") as fh:
fh.write(time.strftime("%Y-%m-%d %H:%M:%S",time.localtime())+" "+nick+" left "+channel)
def getBotanyPlantPath(user,file="{0}_plant_data.json"):
return "/home/{{0}}/.botany/{}".format(file).format(user)
def hasBotanyPlant(user):
return fs.exists(getBotanyPlantPath(user))
def hasVisitors(user):
return fs.exists(getBotanyPlantPath(user,"visitors.json"))
def getBotanyPlant(user):
if not hasBotanyPlant(user):
return False, {}
else:
with open(getBotanyPlantPath(user)) as f:
data = json.load(f)
# if not hasVisitors(user): # TODO: fix this
return True, data
# else:
# with open(getBotanyPlantPath(user,"visitors.json")):
# return True, data, json.load(f)
#def getBotanyLastWatered(dlw,vt):
# rvt = []
# for t in vt:
# if t < time.time():
# rvt.append(t)
# if not rvt:
# return dlw
# allts = [dlw]+rvt
# allts.sort()
# diffs = [(j-i)/86400.0 for i, j in zip(allts[:-1], allts[1:])]
# lve = next((x for x in diffs if x > 5), None)
# if not lve:
# return allts[-1]
# return allts[:diffs.index(lve)+1][-1] #this should actually work, believe it or not
class minerbot:
def __init__(self, name, user, owner):
self.name = name;
self.owner = owner;
self.user = user;
self.running = False;
self.reload = 0;
def begin(self, server, port, channels):
# declare variables here
self.irc = socket.socket();
self.randWordsList = randwords.corpus;
self.userList = [];
self.running = True;
self.channels = channels;
self.kwam = kwam.KWAMPlugin(self)
self.lua = lua.LuaPlugin(self)
self.rss = prss.PageRSS("Announcements","https://tilde.town/~minerobber/announcements","Announcements made by tilde.town members in IRC.",time.localtime())
if fs.isfile("/home/minerobber/misc/annrss"):
self.rss = cPickle.load(open("/home/minerobber/misc/annrss"))
self.notebook = notes.DatedNotebook()
self.solver = mbtilde.Solver(self)
self.urn = urn.UrnPlugin(self)
if fs.isfile("/home/minerobber/lnr.txt"):
self.lnr = loadLNR()
else:
self.lnr = []
saveLNR([])
# self.xkcd = xkcdpl.XKCDPlugin(self)
# self.g7sc = scplugin.G7SCPlugin(self,"!shinycalc")
#self.quiz = quiz.QuizGame("/home/minerobber/quiz.txt")
# connecting, as well as main loop
self.irc.connect((server, port));
self.irc.send("NICK " + self.name + "\r\n");
self.irc.send("USER " + self.user + " 8 * Making an IRC bot is fun!\r\n");
self.irc.recv(4096)
for chan in channels:
self.irc.send("JOIN " + chan + "\r\n");
while self.running:
data = self.irc.recv(4096);
if data.find("PING") != -1:
self.irc.send("PONG " + data.split()[1] + "\r\n");
elif data.find("NAMES") != -1 and not fs.isfile("/home/minerobber/userList"):
users = data[5:-3]
for name in users.split(" "):
table = []
table.append(name)
table.append(0)
self.userList.append(table);
elif data.find("PART") != -1:
logPart(data.split(" ")[2],data.split(" ")[0].split("!")[0][1:])
elif data.find("PRIVMSG") != -1:
self.spokento(data)
self.save()
return self.reload;
def runCMD(self, cmd):
i = subprocess.check_output([cmd],shell=True)
if "\n" in i:
i.replace("\n","; ")
return i;
def addNote(self,touser,fromuser,msg):
# print "ADDNOTE: {} {} {}".format(touser,fromuser,msg)
self.notebook.addNote(touser,fromuser,msg)
def readNotes(self,user):
# print "READNOTES: {}".format(user)
for msg in self.notebook.readNotes(user):
self.say(user,msg)
def haveNotesFor(self,user):
# print "CHECK: {}".format(user)
return self.notebook.checkNotes(user)
def spokento(self, data):
if not self.running:
raise Exception("spokento was prematurely called.");
data_parts = data.split(" ",3);
id = data_parts[0];
nick = id.split("!")[0][1:];
message = data_parts[3][1:];
channel = data_parts[2];
if nick=="tilde.town":
return
print "[" + channel + "] " + nick + ": " + message;
log(channel, nick, message)
self.rss.pubDate = time.localtime()
if self.haveNotesFor(nick):
self.readNotes(nick)
if message.strip()=="!water minerbot":
self.mention(channel, nick, "BZZ-ZAP! Please don't water me! I'm not waterproofed yet!!!!! BZZ-BZZ-ZZZ-ZAP!")
# elif message.find("!urlme "):
# parts = message.split()
# if len(parts)>1:
# self.mention(channel,nick,"https://tilde.town/~{}/{}".format(nick,parts[1]))
# elif message.find("!talklikeme"):
# self.say(channel,"!talklike "+nick)
# elif message.strip()=="!lnrdebug":
# self.say(channel,"lnr = {!s}".format(self.lnr))
# return
elif message.find("!plant ")==0:
ok, data = getBotanyPlant(message.split(" ",1)[1].rstrip())
if not ok:
self.mention(channel,nick,"{} doesn't have a plant".format(message.split(" ",1)[1].rstrip()))
else:
# user requested does indeed have a plant, and data is the loaded JSON representation of said plant
msg = "{d[owner]}'s ".format(d=data)
status = data["description"]
if data["is_dead"]:
status = "dead "+status
status+=" was watered"
lastwatered = data["last_watered"] #,[x['timestamp'] for x in visitors])
if (lastwatered-time.time())<=(24*60*60):
status+=" today"
hours = str(int(math.floor((time.time()-lastwatered)/3600)))
if hours=='0':
seconds = str(int(math.floor((time.time()-lastwatered)/60)))
if seconds=='1':
status+=" (about a second ago)"
else:
status+=" (about {} seconds ago)".format(seconds)
elif hours=='1':
status+=" (about an hour ago)"
else:
status+=" (about {} hours ago)".format(hours)
self.mention(channel,nick,msg+status)
elif message.find("!steven-universe") == 0:
self.mention(channel, nick, "\"{}\" - {}".format(*mu.new_episode()))
elif message.find("!quit") == 0 and nick == self.owner:
self.irc.send("QUIT :beep boop I'm a bot.\r\n");
self.running = False;
elif message.find("!rollcall") == 0:
self.say(channel,"Hey! I'm " + self.name + "! I'm a mess of code. Ask my developer (my nick, but replace bot with \"obber\") about commands of mine!")
elif message.find("!twitch ") == 0:
mparts = message.split(" ")
if len(mparts) == 2:
c = chaninfo.ChannelInfo(mparts[1][:-2],"h7lvoe263k42haljbhlbv2ag1nzt5nd")
if not c.isOnline():
self.say(channel,"{} is not streaming.".format(c.channel))
verb = "playing"
if c.getDisplay():
verb = "being"
self.say(channel, '{} is {} {}. Status: "{}"; Viewers: {!s}'.format(c.channel,verb,c.getGame(),c.getStatus(),c.getViewers()))
elif message.find("!choose ") == 0:
self.say(channel,nick+": "+random.choice(choose_parser.parse(message)))
elif message.strip == "!last5said":
with open("/home/minerobber/log.txt") as f:
lines = []
for line in f:
lines.append(line.strip())
for line in lines[:-5]:
self.say(nick,line)
elif message.find("!dicegame") == 0:
message_parts = message.split(" ",2)
sides = 6
choice = int(random.uniform(1,sides))
b_choice = int(random.uniform(1,sides))
if b_choice > choice:
winMSG = "I win!"
else:
if b_choice == choice:
winMSG = "It's a tie!"
else:
winMSG = "You win!"
self.say(channel,"You rolled a " + str(choice) + ", and I rolled a " + str(b_choice) + ". " + winMSG)
elif channel == self.name and nick == self.owner:
# d = False
# if message.startwith("s "):
# d=True
# message=message.split(" ",2)[1]
print(self.owner + " used the global to say: \"" + message + "\"")
# if d:
self.globalmsg(message)
# else:
# self.globalmsg("[GLOBAL] "+message)
# self.globalmsg(("[GLOBAL] " if not d else "") + message)
elif message.find("!lnr") == 0:
if nick==self.owner and len(message.split(" "))>1:
self.lnr.append(message.split(" ",1)[1].rstrip())
saveLNR(self.lnr)
self.mention(channel,nick,"I'll remember that...")
return
for i in self.lnr:
self.mention(nick,nick,"Late night rambling: {}".format(i))
self.mention(channel,nick,"All late night ramblings have been PM'd to you.")
elif message.find("!online") == 0:
results = self.runCMD("onlinepeople4irc")
leet = string.maketrans("aelosiuUc","43105|Uu(")
self.say(channel, results.translate(leet))
elif message.find("!reload\r\n") == 0 and self.owner == nick:
self.irc.send("QUIT :Reloading bot code...\r\n");
self.reload = 1;
self.running = False;
elif message.find("!announce ") == 0:
announce(channel, nick, " ".join(message.split(" ")[1:]), self.rss)
elif message.find("!reloadchannels") == 0 and nick == self.owner:
channels = []
with open("/home/minerobber/misc/mbchan.txt") as f:
channels = f.readlines()
self.channels_2 = channels
for channel in self.channels_2:
if channel not in self.channels:
self.irc.send("JOIN {}\r\n".format(channel))
self.channels = self.channels_2
elif message.find("!save") == 0 and nick == self.owner:
self.save()
elif message.find("!load") == 0 and nick == self.owner:
self.load()
elif message.find("!update-qdb-commits") == 0 and self.owner == nick:
self.say(channel, self.runCMD("/home/minerobber/qdb-commits-gen.sh"))
elif message.find("!run ") == 0 and self.owner == nick:
prog = message.split(" ",1)[1]
nprog = which(prog.split(" ",1)[0])
if nprog is None:
self.say(channel,"Error: program does not exist!")
else:
self.say(channel,self.runCMD(prog.replace(prog.split(" ",1)[0],nprog)))
elif message.find("!tell") == 0:
self.say(nick,"DEPRECATED: Use new \"!note\" command (same syntax)")
elif message.find("!note ") == 0:
parts = message.split(" ",2)
if not len(parts) == 3:
self.mention(channel,nick,"usage: !note <user> <message>")
else:
self.addNote(parts[1],nick,parts[2])
self.mention(channel,nick,"Message sent for {}.".format(parts[1]))
elif message.find("!getStock") == 0:
self.mention(channel,nick,"This command is out-of-service while my developer figures out what's wrong with me.")
return
ticker = pstocks.StockTicker(format="{0} ({1}) is currently priced at {2}. (a change of {3})")
parts = message.split(" ")
if len(parts) < 2:
self.say(channel, "Usage: '!getStock <ticker>'")
return
for symbol in parts[1:]:
ticker.addSymbol(symbol)
for message in ticker.getTickerValues():
self.say(channel,message)
elif message.find("!mbtilde ") == 0:
if nick != self.owner:
self.say(channel,"Don't tell me what to do!")
return
if channel != "#bots":
self.say(channel,"Remember: tildebot only awards tildes in \#bots.")
result = self.solver.run(message)
if result:
if type(result)==str:
self.say(channel,result)
else:
self.say(channel,str(result))
elif message.strip()=="!discord":
self.mention(channel,nick,"The discord invite link is: https://discord.gg/RS8gJAV")
self.solver.answer(channel,nick,message)
#self.xkcd.answer(channel,nick,message)
#self.xkcd.check_for_new_xkcd(channel)
self.kwam.answer(channel,nick,message)
# self.g7sc.handleCommand(channel,nick,message)
# self.urn.onMessage(self,channel,nick,message)
# self.lua.handleCommand(channel,nick,message)
def globalmsg(self,message):
for chan in self.channels:
self.say(chan,message)
def say(self, chan, message):
try:
if type(message)!=str:
message = str(message)
message = message.replace("\n","")
self.irc.send("PRIVMSG " + chan + " :" + message + "\r\n")
if chan.find("#") == 0:
log(chan, self.name, message)
print("[{}] {}: {}".format(chan,self.name,message))
except:
self.say(chan,"Failed to send message, try again!")
def mention(self,chan,nick,message):
self.say(chan,nick+": "+message)
# def playQuizGame(self,channel,nick,message):
# if self.quiz.notPlaying(nick):
# self.quiz.addPlayer(nick)
# self.mention(channel,nick,self.quiz.getQuestion(nick)+" Use !a, !b, !c, or !d to answer.")
# else:
# if message.rstrip() not in ("!a","!b","!c","!d"):
# return
# if not self.quiz.answer(nick,message[1]):
# self.mention(channel,nick,"Close, but no dice! Try again!")
# else:
# self.mention(channel,nick,"Correct!")
# self.quiz.addPoint(nick)
# self.quiz.save()
def save(self):
# self.quiz.save()
saveLNR(self.lnr)
return
def load(self):
# self.quiz.load()
return
def num(s):
try:
int(s)
except ValueError:
float(s)
def wait(s, minutes):
if minutes:
time.sleep(s * 60)
else:
time.sleep(s)
def which(s):
import os
def is_exe(fpath):
return fs.isfile(fpath) and os.access(fpath, os.X_OK)
fpath, fname = fs.split(s)
if fpath:
if is_exe(program):
return program
else:
for path in os.environ["PATH"].split(os.pathsep):
path = path.strip('"')
exe_file = os.path.join(path, s)
if is_exe(exe_file):
return exe_file
return None;

380
minerbot.py.save Normal file
View File

@ -0,0 +1,380 @@
import socket,random,subprocess,threading,time,cPickle,string,time,prss,randwords,pstocks,chaninfo,primefac,re;
import os.path as fs;
from email.mime.text import MIMEText;
#with open("zws.txt","rb") as f:
# zws = f.readAll()
zws = ""
class NotRunningException (Exception):
pass;
log_format = "{} [{}] {}: {}"
def filterNick(nick):
if len(nick) == 1:
print "Either "+nick+" is not a nick, or the person who has that nick needs a longer nick."
return nick
s = nick[0]+zws+nick[1:]
return s.encode('utf-8')
def log(channel, nick, message):
with open("/home/minerobber/log.txt","ab") as fh:
fh.write(log_format.format(time.strftime("%Y-%m-%d %H:%M:%S"),channel,nick,message))
with open("/home/minerobber/logs/"+time.strftime("%Y-%m-%d")+".txt","ab") as fh:
fh.write(log_format.format(time.strftime("%Y-%m-%d %H:%M:%S"),channel,nick,message))
def logPublic(channel, nick, message):
with open("/home/minerobber/public_html/public_msgs.txt","ab") as fh:
fh.write(time.strftime("%Y-%m-%d %H:%M:%S",time.localtime())+" ["+channel+"] "+nick+": "+message)
def announce(channel, nick, ann, prssfeed):
prssfeed.addItem("Announcement by {} in {}".format(channel, nick),"https://tilde.town/~{}".format(nick),ann)
with open(fs.expanduser("~/public_html/announcements/rss.xml"),"wb") as rss:
rss.write(prssfeed.make())
with open(fs.expanduser("~/public_html/announcements/index.text"),"ab") as html:
html.write('{}, while in {}, announced: "{}" \n'.format(nick, channel, ann));
subprocess.check_output(["make -C ~/public_html/announcements -B"],shell=True)
cPickle.dump(prssfeed,open("/home/minerobber/misc/annrss","wb"))
def logJoin(channel,nick):
with open("/home/minerobber/log.txt","ab") as fh:
fh.write(time.strftime("%Y-%m-%d %H:%M:%S",time.localtime())+" "+nick+" joined "+channel)
def logPart(channel,nick):
with open("/home/minerobber/log.txt","ab") as fh:
fh.write(time.strftime("%Y-%m-%d %H:%M:%S",time.localtime())+" "+nick+" left "+channel)
class minerbot:
def __init__(self, name, user, owner):
self.name = name;
self.owner = owner;
self.user = user;
self.running = False;
self.reload = 0;
def begin(self, server, port, channels):
# declare variables here
self.irc = socket.socket();
self.randWordsList = randwords.corpus;
self.userList = [];
if fs.isfile("/home/minerobber/userList"):
self.load();
self.running = True;
self.channels = channels;
self.emailTemplate = ["~{0} wanted me to tell you:\n"]
self.rss = prss.PageRSS("Announcements","https://tilde.town/~minerobber/announcements","Announcements made by tilde.town members in IRC.",time.localtime())
if fs.isfile("/home/minerobber/misc/annrss"):
self.rss = cPickle.load(open("/home/minerobber/misc/annrss"))
# self.guessgameplaying = False;
# self.gg_players = {};
# self.gg_state = "not-active";
# self.gg_votes = {}
# connecting, as well as main loop
self.irc.connect((server, port));
self.irc.send("NICK " + self.name + "\r\n");
self.irc.send("USER " + self.user + " 8 * Making an IRC bot is fun!\r\n");
for chan in channels:
self.irc.send("JOIN " + chan + "\r\n");
while self.running:
data = self.irc.recv(4096);
#print data;
if data.find("PING") != -1:
self.irc.send("PONG " + data.split()[1] + "\r\n");
elif data.find("NAMES") != -1 and not fs.isfile("/home/minerobber/userList"):
users = data[5:-3]
for name in users.split(" "):
table = []
table.append(name)
table.append(0)
self.userList.append(table);
elif data.find("JOIN") != -1:
logJoin(data.split(" ")[2],data.split(" ")[0].split("!")[0][1:])
if data.split(" ")[2] == "#music" and data.split(" ")[0].split("!")[0][1:] != self.nick:
self.say(data.split(" ")[2],"Hello, "+data.split(" ")[0].split("!")[0][1:]+"! If you want to listen along, the URL is: https://tilde.town/~kc/jukebot/listen")
elif data.find("PART") != -1:
logPart(data.split(" ")[2],data.split(" ")[0].split("!")[0][1:])
elif data.find("PRIVMSG") != -1:
self.spokento(data)
self.save()
return self.reload;
def runCMD(self, cmd):
i = subprocess.check_output([cmd],shell=True)
if "\n" in i:
i.replace("\n","; ")
return i;
def sendEmail(self, channel, sender, recipient, text):
msg = MIMEText("~{0} wanted me to tell you:\n> {1}".format(sender,text))
msg["From"] = "minerbot-messages@tilde.town"
msg["To"] = "{0}@tilde.town".format(recipient)
msg["Subject"] = "Message from ~{0}".format(sender)
msg["Cc"] = "{0}@tilde.town".format(sender)
mail = subprocess.Popen("{0} -t -oi".format(which("sendmail")).split(" "),stdin=subprocess.PIPE)
mail.communicate(msg.as_string())
self.say(channel,"Mail sent!")
# mail.close()
def spokento(self, data):
if not self.running:
raise Exception("spokento was prematurely called.");
data_parts = data.split(" ",3);
id = data_parts[0];
nick = id.split("!")[0][1:];
message = data_parts[3][1:];
channel = data_parts[2];
print "[" + channel + "] " + nick + ": " + message;
log(channel, nick, message)
self.rss.pubDate = time.localtime()
if message.find(self.owner) != -1:
logPublic(channel,nick,message)
elif message.find("!log") == 0:
logPublic(channel,nick,message.split(" ",2)[1])
if message.find("!quit") == 0 and nick == self.owner:
self.irc.send("QUIT :beep boop I'm a bot.\r\n");
self.running = False;
elif message.find("!rollcall") == 0:
self.say(channel,"Hey! I'm " + self.name + "! Use '!help' to see a list of my commands.")
elif message.find("!twitch ") == 0:
mparts = message.split(" ")
if len(mparts) == 2:
c = chaninfo.ChannelInfo(mparts[1][:-2],"h7lvoe263k42haljbhlbv2ag1nzt5nd")
if not c.isOnline():
return
verb = "playing"
if c.getDisplay():
verb = "being"
self.say(channel, '{} is {} {}. Status: "{}"; Viewers: {!s}'.format(c.channel,verb,c.getGame(),c.getStatus(),c.getViewers()))
elif message.strip == "!last5said":
with open("/home/minerobber/log.txt") as f:
lines = []
for line in f:
lines.append(line.strip())
for line in lines[:-5]:
self.say(nick,line)
elif message.find("!dicegame") == 0:
message_parts = message.split(" ",2)
sides = 6
choice = int(random.uniform(1,sides))
b_choice = int(random.uniform(1,sides))
if b_choice > choice:
winMSG = "I win!"
else:
if b_choice == choice:
winMSG = "It's a tie!"
else:
winMSG = "You win!"
self.say(channel,"You rolled a " + str(choice) + ", and I rolled a " + str(b_choice) + ". " + winMSG)
elif channel == self.name and nick == self.owner:
print(self.owner + " used the global to say: \"" + message + "\"")
for chan in self.channels:
self.say(chan,"[GLOBAL] " + message)
elif message.find("!online") == 0:
results = self.runCMD("onlinepeople4irc")
leet = string.maketrans("aelosiuUc","43105|Uu(")
self.say(channel, results.translate(leet))
elif message.find("!reload") == 0 and self.owner == nick:
self.irc.send("QUIT :Reloading bot code...\r\n");
self.reload = 1;
self.running = False;
# elif message.find("!shop") == 0:
#nyi
elif message.find("!tbadmin") == 0 and self.owner == nick:
message_parts = message.split(" ")
if message_parts[1] == "add":
for i in self.userList:
if message_parts[2] == i[0]:
i[1] += int(message_parts[3])
self.save()
elif message_parts[1] == "rm":
for i in self.userList:
if message_parts[2] == i[0]:
i[1] += int(message_parts[3])
self.save()
elif message_parts[1] == "view":
for i in self.userList:
if message_parts[2] == i[0]:
self.say(channel,i[0] + " has " + str(i[1]) + " tildebucks.")
elif message.find("!announce ") == 0:
announce(channel, nick, " ".join(message.split(" ")[1:]), self.rss)
# elif message.find("!guessing_game") == 0 and self.gg_state == "not-active":
# thread = threading.Thread(target=self.playGuessingGame, args=(channel));
# elif message.find("!join_guessing_game") == 0 and self.gg_state == "player-wait":
# self.gg_players.append(nick);
elif message.find("!save") == 0 and nick == self.owner:
self.save()
elif message.find("!load") == 0 and nick == self.owner:
self.load()
#elif message.find("!money") == 0:
# for i in self.userList:
# if i[0] == nick:
# self.say(channel,(nick + " has " + str(i[1]) + " tildebucks."))
elif message.find("!update-qdb-commits") == 0 and self.owner == nick:
self.say(channel, self.runCMD("/home/minerobber/qdb-commits-gen.sh"))
elif message.find("!run ") == 0 and self.owner == nick:
prog = message.split(" ",1)[1]
nprog = which(prog.split(" ",1)[0])
if nprog is None:
self.say(channel,"Error: program does not exist!")
else:
self.say(channel,self.runCMD(prog.replace(prog.split(" ",1)[0],nprog)))
elif message.find("!tell") == 0:
parts = message.split(" ",2)
if not len(parts) == 3:
self.say(channel,"Usage: !tell <user> <message>")
else:
self.sendEmail(channel,nick,parts[1],parts[2][:-2])
# elif message.find("!get-gg-state") == 0 and self.owner == nick:
# self.say(channel, "GG-State: " + self.gg_state)
elif message.find("!getStock") == 0:
ticker = pstocks.StockTicker(format="{0} ({1}) is currently priced at {2}. (a change of {3})")
parts = message.split(" ")
if len(parts) < 2:
self.say(channel, "Usage: '!getStock <ticker>'")
return
for symbol in parts[1:]:
ticker.addSymbol(symbol)
for message in ticker.getTickerValues():
self.say(channel,message)
elif message.find("!mbtilde ") == 0:
if nick != self.owner:
self.say(channel,"Don't tell me what to do!")
return
if channel != "#bots":
self.say(channel,"Remember: tildebot only awards tildes in \#bots.")
parts = message.split(" ",2)
parts = [s.rstrip() for s in parts]
if parts[1] == "request":
self.say("#bots","!tilde")
if parts[1] == "add":
nums = [int(s) for s in parts[2].split(" ")]
self.say(channel,"{!s}".format(sum(nums)))
if parts[1] == "sub":
nums = [int(s) for s in parts[2].split(" ",1)]
self.say(channel,"{!s}".format(nums[1]-nums[0]))
if parts[1] == "mult":
nums = [int(s) for s in parts[2].split(" ",1)]
self.say(channel,"{!s}".format(nums[1]*nums[0]))
if parts[1] == "divide":
nums = [int(s) for s in parts[2].split(" ",1)]
try:
self.say(channel,"{!s}".format(nums[0]/nums[1]))
except ZeroDivisionError:
self.say(channel,"Bugger off!")
if parts[1] == "mod":
nums = [int(s) for s in parts[2].split(" ",1)]
self.say(channel,"{!s}".format(nums[0]%nums[1]))
if parts[1] == "factor":
self.say(channel,"{!s},{!s}".format(*list(primefac.primefac(int(parts[2]))))
elif message.find("!rpg") and channel=="#rpg":
parts = message.split(" ")
if len(parts) < 2:
self.say(channel,"Usage: !rpg <action> [parameters]")
if parts[1]=="roll" and len(parts)==3:
descriptor = parts[2].rstrip()
t = re.match(descriptor,r"^(\d+)d(\d+)$")
if not t:
self.say(channel,"Usage: !rpg roll <amount of dice>d<number of sides on each>")
self.say(channel,"Example: !rpg roll 1d100")
number = t.match(0)
sides =
# elif message.find("!helpme") == 0:
# help_parts = message.split(" ",2)
# if len(help_parts) < 2:
# self.say(channel,"Commands: 'dicegame', 'online', 'tell';")
# else:
# if help_parts[1] == "dicegame":
# self.say(channel,"Play a dice game against " + self.name + ". Usage: '!dicegame'")
# elif help_parts[1] == "online":
# self.say(channel,"Returns a list of online users, as well as a user count. Usage: '!online'")
# elif help_parts[1] == "tell":
# self.say(channel,"Sends a user an email to let them know of something. Usage: '!tell <user> <thing to tell them>'")
# elif help_parts[1] == "words":
# self.say(channel,"Generates a random string of words. Usage: '!words'")
# elif help_parts[1] == "getStock":
# self.say(channel,"Gets stock info for a specific ticker. Usage: '!getStock <ticker>'")
# elif self.gg_state == "player-wait-vote" and message.find("!guess"):
# if nick in self.gg_players:
# for i in self.gg_votes:
# if i[0] == nick:
# return;
# self.gg_votes.append({nick,int(message.split(" ")[1])})
# if self.gg_state == "player-wait-vote":
# playerDouble = {};
# for i in self.gg_votes:
# if i[0] in self.gg_players:
# playerDouble.append(i[0])
# if self.gg_players == playerDouble:
# self.gg_state = "all-voted"
# self.randWordsList.append(message)
def say(self, chan, message):
self.irc.send("PRIVMSG " + chan + " :" + message + "\r\n")
if chan.find("#") == 0:
log(chan, self.name, message)
def playGuessingGame(self,chan):
self.gg_players = []
self.say(chan, "Generating number to guess...")
gg_number = random.uniform(1,100)
self.gg_state = "player-wait"
self.say(chan, "Game will start soon! To join, type \"!join_guessing_game\"")
wait(15, True)
self.gg_state = "started"
self.say(chan, "The game has started!")
playerString = "Players: "
for player in self.gg_players:
playerString += player + " "
self.say(chan, playerString)
self.say(chan,"How to play: guess a number between 1 and 100.")
self.gg_state = "player-wait-vote"
while not self.gg_state == "all-voted":
wait(5,False)
correct_players = [];
for i in self.gg_votes:
if gg_number == i[1]:
correct_players.append(i[0])
correctVoteString = "Winners: "
for player in correct_players:
correctVoteString += player + " "
self.say(chan, correctVoteString)
self.say(chan, "All of the winners get 3 tildebucks!")
for user in self.userList:
if user[0] in correct_players:
user[1] += 3;
self.save()
self.gg_state = "not-active"
def save(self):
cPickle.dump(self.userList, open("/home/minerobber/userList","wb"))
def load(self):
cPickle.load(open("/home/minerobber/userList","rb"))
def num(s):
try:
int(s)
except ValueError:
float(s)
def wait(s, minutes):
if minutes:
time.sleep(s * 60)
else:
time.sleep(s)
def which(s):
import os
def is_exe(fpath):
return fs.isfile(fpath) and os.access(fpath, os.X_OK)
fpath, fname = fs.split(s)
if fpath:
if is_exe(program):
return program
else:
for path in os.environ["PATH"].split(os.pathsep):
path = path.strip('"')
exe_file = os.path.join(path, s)
if is_exe(exe_file):
return exe_file
return None;

BIN
minerbot.pyc Normal file

Binary file not shown.

35
notes.py Normal file
View File

@ -0,0 +1,35 @@
import time
class BasicNotebook:
def __init__(self):
self.messages = {}
def _addToNotes(self,touser,msgformat):
if touser in self.messages:
self.messages[touser].append(msgformat)
else:
self.messages[touser]=[msgformat]
def addNote(self,touser,fromuser,msg):
self._addToNotes(touser,[fromuser,msg])
def _readNotes(self,user,fmtstr):
if not self.checkNotes(user):
return []
ret = []
for messageI in self.messages[user]:
ret.append(fmtstr.format(*messageI))
del self.messages[user]
return ret
def readNotes(self,user):
return self._readNotes(user,"{0} left a message: {1}")
def checkNotes(self,user):
return user in self.messages.keys()
class DatedNotebook(BasicNotebook):
def addNote(self,touser,fromuser,msg):
self._addToNotes(touser,[fromuser,msg,time.strftime("%H:%M:%S"),time.strftime("%A, %B %d, %Y")])
def readNotes(self,user):
return self._readNotes(user,"{0} left a message at {2} on {3}: {1}")

BIN
notes.pyc Normal file

Binary file not shown.

8
out.lua Normal file
View File

@ -0,0 +1,8 @@
if not table.pack then table.pack = function(...) return { n = select("#", ...), ... } end end
if not table.unpack then table.unpack = unpack end
local load = load if _VERSION:find("5.1") then load = function(x, n, _, env) local f, e = loadstring(x, n) if not f then return f, e end if env then setfenv(f, env) end return f end end
local _select, _unpack, _pack, _error = select, table.unpack, table.pack, error
local _libs = {}
local print1
print1 = print
return print1("lua")

25
plugin.py Normal file
View File

@ -0,0 +1,25 @@
import re
class Plugin:
def __init__(self,bot,command_format):
self.bot = bot
self.cmd = re.compile(command_format)
def answer(self,channel,nick,message):
m = self.cmd.search(message)
if m and hasattr(self,m.group(1).replace(" ","_")):
getattr(self,m.group(1).replace(" ","_"))(channel,nick,message)
class TestPlugin(Plugin):
def __init__(self,bot):
Plugin.__init__(self,bot,"!test ([A-Za-z]+)(?: (.+))?")
self.is_bot=True
# def is_not_a_bot(self):
# self.is_bot=False
def say(self,c,n,m):
if self.is_bot:
self.bot.mention(c,n,m)
else:
print(m)

BIN
plugin.pyc Normal file

Binary file not shown.

54
pokemon.py Normal file
View File

@ -0,0 +1,54 @@
import json,os.path,copy
class Pokemon:
def __init__(self):
self.pkmns = dict()
def __getitem__(self,k):
return self.pkmns[k]
def add(self,**kwargs):
self.pkmns[kwargs["name"]] = kwargs
class PCBox:
"""Pokemon box"""
def __init__(self):
self.pokemon = []
def move(self,pkmn):
self.pokemon.append(pkmn)
def get(self):
return self.pokemon
@classmethod
def fromList(cls,l):
ret = cls()
ret.pokemon = l
return ret
class PokemonGame:
"""A game of Pokemon. Up to 6 mons, 300000 pokeyen, and 4 moves per Pokemon."""
def __init__(self,owner,prompt):
self.setupPKMNList()
try:
with open(os.path.join("/home/minerobber/.pkmn/",owner+".json"),"r") as f:
self.data = json.load(f)
self.name = self.data["name"]
self.pokeyen = self.data["pokeyen"]
self.pkmn = self.data["pkmn"]
self.pc = []
for item in self.data["boxes"]:
self.pc.append(PCBox.fromList(item))
except IOError as e:
self.name = prompt()
self.pokeyen = 3000
self.pkmn = []
self.pc = [PCBox()]*20
def addPKMN(self,type):
if len(self.pkmn)==6:
return False
self.pkmn.append(copy.copy(self.pkmnl[type]))
def setupPKMNList(self):
self.pkmnl = Pokemon()
self.pkmnl.add(name="Charmander",maxhp=39,atk=52,dfn=43,spa=60,sde=50,speed=65,evolves=dict(at=16,to="Charmeleon"))
self.pkmnl.add(name="Charmeleon")

3
prod.py Normal file
View File

@ -0,0 +1,3 @@
from minerbot import minerbot;
bot = minerbot("minerbot", "minerbot","minerobber");
bot.begin("localhost",6667,["#bots","#minerobber","#tildetown"]);

26
prss.py Normal file
View File

@ -0,0 +1,26 @@
"""A python module for writing RSS."""
import time
class PageRSS:
"""A helper class for creating a page's RSS."""
def __init__(self, title, description, link, date):
self.items = []
self.title = title
self.description = description
self.link = link
self.pubDate = date
"""Add items to RSS feed."""
def addItem(self, title, link, desc):
item = {}
item['title'] = title
item['link'] = link
item['desc'] = desc
self.items.append(item)
"""Generates RSS feed."""
def make(self):
contents = "<?xml version='1.0' ?><rss version='2.0'><channel><title>{}</title><link>{}</link><description>{}</description><pubDate>{}</pubDate>".format(self.title,self.link,self.description,time.strftime("%a, %d %b %Y %H:%M:%S %z",self.pubDate))
for i in self.items:
contents += "<item><title>{}</title><link>{}</link><description>{}</description></item>".format(i['title'],i['link'],i['desc'])
contents += "</channel></rss>"
return contents

BIN
prss.pyc Normal file

Binary file not shown.

20
pstocks/__init__.py Normal file
View File

@ -0,0 +1,20 @@
import getters
class StockTicker:
"""A stock ticker to track certain stocks with."""
def __init__(self, data=["s","n","l1","c1"], format="{1} ({0}) {2} ({3})"):
self.symbols = []
self.data = data
self.format = format
def addSymbol(self,symbol):
self.symbols.append(symbol)
def removeSymbol(self,symbol):
self.symbols = [x for x in self.symbols if x != symbol]
def getTickerValues(self):
reader = getters.getStocks(self.symbols,"".join(self.data))
ret = []
for row in reader:
ret.append(self.format.format(*row))
return ret

BIN
pstocks/__init__.pyc Normal file

Binary file not shown.

19
pstocks/getters.py Normal file
View File

@ -0,0 +1,19 @@
import csv,requests;
from urllib import quote_plus as urlencode;
def generatorFromText(text):
for line in text.splitlines():
yield line
def getCSVFile(url):
r = requests.get(url)
reader = csv.reader(generatorFromText(r.text))
return reader
def getStocks(symbols,data):
symbol_string = ""
if type(symbols) is str:
symbol_string = symbols
else:
symbol_string = "+".join(symbols)
return getCSVFile("http://finance.yahoo.com/d/quotes.csv?s="+urlencode(symbol_string)+"&f="+data)

BIN
pstocks/getters.pyc Normal file

Binary file not shown.

32
randwords.py Normal file
View File

@ -0,0 +1,32 @@
import wordfreq,string,random
corpus = open("corpus").read().split("\n")
strs = corpus
filter = ""
for c in string.punctuation:
if c != "'":
filter += c
def getListFreqDict(list):
nl = []
for s in list:
ls = s.split(" ")
filter(ls,None)
lsc = ls[:]
for word in ls:
if word.find("http://") != -1 or word.find("https://") != -1:
lsc.remove(word);
s = " ".join(lsc)
nl.add(s)
ret = wordfreq.getFreqDict(" ".join(nl),filterchars=filter)
return ret
def getRandomWords(freqDict):
t = ""
for s in freqDict:
t += "{} ".format(s) * freqDict[s]
listW = [x for x in t.split(" ") if x != ""]
len = random.randint(1,20)
ret = ""
while len != 0:
ret += random.choice(listW)
ret += " "
len -= 1
return ret[:-1]+random.choice(".!?;")

BIN
randwords.pyc Normal file

Binary file not shown.

45
scplugin.py Normal file
View File

@ -0,0 +1,45 @@
import shinycalc
class G7SCPlugin:
help = "Generates shiny chances for pokemon generation 7 shiny hunting! Subcommands: shiny, hidden_ability, perfect_ivs"
"""Handles lua execution"""
def __init__(self,bot,prefix):
self.bot = bot
self.prefix = prefix
def handleCommand(self,chan,sender,cmd):
if cmd.strip()==prefix:
self.bot.mention(chan,sender,G7SCPlugin.help)
elif not cmd.startswith(prefix+" "):
return
else:
try:
parts = cmd.strip().split()
if not hasattr(self,parts[1]):
self.bot.mention(chan,sender,G7SCPlugin.help)
raise Exception()
args = parts[2:]
# args.insert(0,self)
self.bot.mention(chan,sender,getattr(self,parts[1])(*args))
except:
pass
def shiny(self,*args):
shinycalc.setChain(int(args[0]))
shiny = shinycalc.generateShiny()
ret = "1/{!s} chance of the pokemon being shiny.".format(shiny[0])
if shiny[1]:
ret += " (Or not. Shiny values from 1-69 aren't known yet.)"
return ret
def hidden_ability(self,*args):
shinycalc.setChain(int(args[0]))
ha = shinycalc.generateHA()
return "{!s}% chance of a hidden ability.".format(ha)
def perfect_ivs(self,*args):
shinycalc.setChain(int(args[0]))
ivs = shinycalc.generateIVs()
return "{!s} guaranteed perfect IV(s).".format(ivs)

BIN
scplugin.pyc Normal file

Binary file not shown.

53
shinycalc.py Executable file
View File

@ -0,0 +1,53 @@
#!/usr/bin/python
import argparse
chain = 0
def setChain(c):
global chain
chain = (c%256)
def generateShiny():
if chain<70:
return (4096,chain!=0)
else:
return (1024,False)
def generateIVs():
if chain<=4:
return 0
elif chain<=9:
return 1
elif chain<=19:
return 2
elif chain<=29:
return 3
else:
return 4
def generateHA():
if chain<10:
return 0
elif chain<20:
return 5
elif chain<30:
return 10
else:
return 15
if __name__=="__main__":
parser = argparse.ArgumentParser(description="Calculates shiny chance and IVs for SOS battles in generation 7.")
parser.add_argument("chain",type=int,help="Chain value. Due to overflow bug, will not be calculated hgher than 255 (handled automatically)")
args = parser.parse_args()
setChain(args.chain)
shiny = generateShiny()
iv = generateIVs()
ha = generateHA()
print "Shiny chance: 1/"+str(shiny[0])+("*" if shiny[1] else "")
print str(iv)+" guaranteed perfect IV(s)"
print "Hidden Ability chance: "+str(ha)+"%"
if shiny[1]:
print "* Shiny chances for chain values below 70 are not known."

BIN
shinycalc.pyc Normal file

Binary file not shown.

3
show.py Normal file
View File

@ -0,0 +1,3 @@
from minerbot import minerbot;
bot = minerbot("minerbot", "minerbot","minerobber");
bot.begin("irc.badnik.net",6667,["#ImANoob"]);

19
sieve.py Normal file
View File

@ -0,0 +1,19 @@
def primes(n):
if n<=2:
return []
sieve=[True]*(n+1)
for x in range(3,int(n**0.5)+1,2):
for y in range(3,(n//x)+1,2):
sieve[(x*y)]=False
return [2]+[i for i in range(3,n,2) if sieve[i]]
def primefactors(n):
primelist = primes(100)
lpf = 2
for prime in primelist:
print "Checking prime: "+str(prime)
if n%prime == 0 and prime > lpf:
print "Better prime found: "+str(prime)
lpf = prime
return "{!s},{!s}".format(lpf,n/lpf)

BIN
sieve.pyc Normal file

Binary file not shown.

35
subapi.py Normal file
View File

@ -0,0 +1,35 @@
import subprocess as sp
from threading import Thread
class SubAPI:
def __init__(self):
self.outputListeners = set()
def start(self, args, listenDaemon=True):
self.program = sp.Popen(args, stdin=sp.PIPE, stdout=sp.PIPE, stderr=sp.STDOUT, universal_newlines=True)
self.t = Thread(target=self.listen, daemon=listenDaemon)
self.t.start()
def listen(self):
while self.program.stdout.readable():
outputLine = self.program.stdout.readline()[:-1]
for listener in self.outputListeners:
listener(outputLine)
def sendInput(self, command):
self.program.stdin.write(command+"\n")
self.program.stdin.flush()
def stop(self):
self.program.terminate()
self.program.stdout.close()

BIN
subapi.pyc Normal file

Binary file not shown.

7
sugrocks.py Normal file
View File

@ -0,0 +1,7 @@
import requests
def doMethod(m):
return requests.get("https://api.sug.rocks/{}.json".format(m)).json()
def schedule():
return doMethod("schedule")

BIN
sugrocks.pyc Normal file

Binary file not shown.

2
t.tt Normal file
View File

@ -0,0 +1,2 @@
def BLANK(self,c,n,m):
self.bot.say(c,self._BLANK(m.group(2),m.group(3)))

1
te.urn Normal file
View File

@ -0,0 +1 @@
(print! "lua")

3
test.py Normal file
View File

@ -0,0 +1,3 @@
from minerbot import minerbot;
bot = minerbot("minerbot", "testuser","minerobber");
bot.begin("localhost",6667,["#minerobber"]);

5
testurn.py Normal file
View File

@ -0,0 +1,5 @@
import urn
bot = urn.TestBot()
urnp = urn.UrnPlugin(bot)
urnp.onMessage("#tildetown","minerobber","!urn (print! \"lua\")")

32
urn.py Normal file
View File

@ -0,0 +1,32 @@
import subprocess
class TestBot:
def __init__(self):
pass
def say(self,chan,message):
print(message)
class NFile:
def __init__(self,bot,chan):
self.bot = bot
self.chan = chan
def write(self,c):
self.bot.say(self.chan,c)
class UrnPlugin:
def __init__(self,bot):
self.bot = bot
def onMessage(self,chan,nick,message):
parts = message.strip().split()
if parts[0]!="!urn":
return
with open("te.urn","w") as f:
f.write(" ".join(parts[1:]))
subprocess.call("urn te.urn",shell=True)
t = subprocess.Popen("lua out.lua",shell=True,stdout=subprocess.PIPE)
out = t.communicate()[0]
lines = [l.strip() for l in out.strip().split("\n")]
for line in lines:
if line:
self.bot.say(chan,line)

BIN
urn.pyc Normal file

Binary file not shown.

14
wordfreq.py Normal file
View File

@ -0,0 +1,14 @@
import string
def getFreqDict(corpus, filterchars=string.punctuation):
corpus = corpus.lower()
for c in filterchars:
corpus = corpus.replace(c,"")
words = corpus.split()
words = filter(None,words)
freq = {}
for word in words:
if word in freq:
freq[word] += 1
else:
freq.update({word: 1})
return freq

BIN
wordfreq.pyc Normal file

Binary file not shown.

37
xkcd.py Normal file
View File

@ -0,0 +1,37 @@
import requests
class InvalidComic(Exception):
pass
class Comic(object):
def __init__(self,num=None,donterror=False):
if num:
r = requests.get("https://xkcd.com/{!s}/info.0.json".format(num))
if r.status_code!=200:
if donterror:
self.num = num
self.fakeit = True
else:
raise InvalidComic("Invalid XKCD comic \""+str(num)+"\"")
else:
self.__dict__.update(r.json())
self.fakeit = False
else:
r = requests.get("https://xkcd.com/info.0.json")
if r.status_code!=200:
if donterror:
self.num = 0
self.fakeit = True
else:
raise InvalidComic("Cannot locate latest comic.")
else:
self.__dict__.update(r.json())
self.fakeit = False
def __getattr__(self,k):
if k=="fakeit" or k=="num":
return object.__getattr__(self,k)
if self.fakeit:
return ""
else:
return object.__getattr__(self,k)

1
zws.txt Normal file
View File

@ -0,0 +1 @@