-
-
Save srsinvasionbot/e796b65bf9d657cc6f3d to your computer and use it in GitHub Desktop.
SRS Banning Bot
This file contains 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 | |
######################################################################################## | |
# SRS Banning Bot v0.2 # | |
# ==================== # | |
# # | |
# See banbot.py -h for usage. # | |
# # | |
# The Reddit API python wrapper is required for this script. # | |
# See https://github.com/mellort/reddit_api # | |
# # | |
# This program is free software: you can redistribute it and/or modify # | |
# it under the terms of the GNU General Public License as published by # | |
# the Free Software Foundation, either version 3 of the License, or # | |
# (at your option) any later version. # | |
# # | |
# This program is distributed in the hope that it will be useful, # | |
# but WITHOUT ANY WARRANTY; without even the implied warranty of # | |
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # | |
# GNU General Public License for more details. # | |
# # | |
# You should have received a copy of the GNU General Public License # | |
# along with this program. If not, see <http://www.gnu.org/licenses/>. # | |
# # | |
######################################################################################## | |
try: | |
import reddit | |
except ImportError: | |
raise ImportError('Reddit API python wrapper is required. See https://github.com/mellort/reddit_api for more details.') | |
import sys, time, argparse, string | |
######################################################################################## | |
# Initialisation & Global Variables #################################################### | |
######################################################################################## | |
parser = argparse.ArgumentParser(description='SRS Banning Bot v0.2. A thermonuclear Banning Bot for reddit.',epilog='Associated files to be located in the run directory:\n\t \'white\': Whitelisting text file. The bot will not ban users on this list from any sub.\n\t \'banlog\': Banning log for the bot.\n\nUse wisely.') | |
parser.add_argument('--launch', nargs='+', help='Subreddits doing the banning. Moderator privileges required.',required=True) | |
parser.add_argument('--username', help='Reddit Username',required=True) | |
parser.add_argument('--password', help='Reddit Password',required=True) | |
parser.add_argument('--target', nargs='+', help='Subreddits targeted for banning. Defaults to the fempire.',default=['ShitRedditSays','SRSDiscussion','SRSMeta','SRSAnime','SRSArt','SRSAustralia','SRSAuthors','SRSBooks','SRSBusiness','SRSCanada','SRSCinema','SRSComics','SRSDisabilities','SRSFartsAndCrafts','SRSFoodies','SRSFunny','SRSGaming','SRSGSM','SRSHappy','SRSImages','SRSIvoryTower','SRSMailbag','SRSMusic','SRSMusicals','SRSNews','SRSPets','SRSPolitics','SRSPonies','SRSPUA','SRSQuestions','SRSSex','SRSSkeptic','SRSTechnology','SRSTelevision','SRSTrees','SRSWorldProblems','AntiSRSCirclejerk','Daww','FitnessPlus','GoldRedditSays','SciFiAndFantasy']) | |
parser.add_argument('--depth', type=int, help='Scrape Depth. Specify to reduce depth, omit for maximum depth. ',default=None) | |
parser.add_argument('--maxpost', type=int, help='Maximum allowable karma from any single post. Default=20',default=20) | |
parser.add_argument('--maxkarma', type=int, help='Maximum allowable karma from total posts. Default=200',default=200) | |
args = parser.parse_args() | |
username = args.username | |
passwd = args.password | |
launchsubs = args.launch | |
targetsubs = args.target | |
maxpost = args.maxpost | |
maxkarma = args.maxkarma | |
depth = args.depth | |
######################################################################################## | |
# Sub Routines ######################################################################### | |
######################################################################################## | |
# 1. Function for flattening multi-tier comments from a subreddit get into a single list. | |
def flatten_comments(mlcomments): | |
comm_list = [] | |
for line in mlcomments: | |
if type(line) is reddit.objects.Comment: | |
comm_list.append(line) | |
elif type(line) is list: | |
for item in line: | |
mlcomments.append(item) # Append 2nd tier list items to 1st tier | |
elif type(line) is reddit.objects.MoreComments: | |
pass | |
else: | |
raise TypeError('List must contain only reddit.objects.Comment or lists. Type passed: '+str(type(line))) | |
return comm_list | |
# 2. Function that creates the banlist. | |
def extract_banlist(comm_list,maxpost,maxkarma): | |
banlist = [] | |
for k in comm_list: | |
if (k.author_flair_text != None): | |
banlist.append({'banee':k.author.name,'targetsub':k.subreddit.display_name}) | |
elif (k.ups-k.downs) > maxpost: | |
banlist.append({'banee':k.author.name,'targetsub':k.subreddit.display_name}) | |
elif type(k.author) is reddit.objects.Redditor: | |
srsup,commenthistory = 0,[] | |
try: | |
history = list(k.author.get_comments()) | |
for comment in history: | |
for sub in targetsubs: | |
if (comment.subreddit.display_name == sub): | |
srsup = srsup + comment.ups | |
if srsup > maxkarma: | |
banlist.append({'banee':k.author.name,'targetsub':k.subreddit.display_name}) | |
except: | |
print 'Warning: Error reviewing history of: '+str(k.author.name)+'\n' | |
else: | |
sys.stdout.write('Warning: TypeError: k.author\n'+ str(type(k.author))) | |
return banlist | |
# 3. Function to scrape targeted subs for comments. | |
def scrape_comments(r, targetsubs, depth): | |
targets = [] | |
for sub in targetsubs: | |
for t in list(r.get_subreddit(sub).get_comments(limit=depth)): | |
targets.append(t) | |
return targets | |
# 4. Banning function | |
def mass_ban(r,banlist,launchsubs): | |
try: | |
banfile = open('banlog','a') | |
except IOError as e: | |
raise IOError('Unable to open banlog for writing: '+str(e)) | |
for banee in banlist: | |
for sub in launchsubs: | |
try: | |
banfile.write(str(banee['targetsub'])+' '+str(r.get_subreddit(sub).display_name)+' '+str(banee['banee'])+'\n') | |
r.get_subreddit(sub).ban(r.get_redditor(banee['banee'])) | |
except: | |
e = sys.exc_info()[1] | |
print "fail: ",str(e) | |
banfile.close() | |
# 5. Duplicate removal function. Credit Tim Peters (http://code.activestate.com/recipes/52560/) | |
def remove_dupes(q): | |
n = len(q) | |
q.sort() | |
assert n > 0 | |
last = q[0] | |
lasti = i = 1 | |
while i < n: | |
if q[i] != last: | |
q[lasti] = last = q[i] | |
lasti += 1 | |
i += 1 | |
return q[:lasti] | |
# 6. Whitelisting removal. | |
def white(q): | |
white = open('white','r').read().splitlines() | |
for h in range(len(q)-1,-1,-1): | |
for k in white: | |
if k == q[h]: | |
q.pop(h) | |
return q | |
######################################################################################## | |
# Main Routine ######################################################################### | |
######################################################################################## | |
print "=======================================\n\t SRS Banning Bot v0.2\n=======================================" | |
print str(time.asctime(time.localtime()))+" - Logging into Reddit" | |
r = reddit.Reddit(user_agent='/u/'+username+' - SRS Banning Bot v0.2') | |
r.login(username,passwd) | |
print str(time.asctime(time.localtime()))+" - Scraping Comments" | |
targets = scrape_comments(r,targetsubs,depth) | |
print str(time.asctime(time.localtime()))+" - Preparing Comments" | |
comm_list = flatten_comments(targets) | |
print str(time.asctime(time.localtime()))+" - Creating Banlist" | |
banlist = extract_banlist(comm_list, maxpost, maxkarma) | |
print str(time.asctime(time.localtime()))+" - Preparing List" | |
banlist = white(remove_dupes(banlist)) | |
print str(time.asctime(time.localtime()))+" - Banning users" | |
mass_ban(r,banlist,launchsubs) | |
print str(time.asctime(time.localtime()))+" - Fin" | |
######################################################################################## | |
# Fin ################################################################################## | |
######################################################################################## |
This file contains 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 | |
######################################################################################## | |
# SRS Unbanning Bot v0.2 # | |
# ====================== # | |
# # | |
# See ubanbot.py -h for usage. # | |
# # | |
# To be used in conjunction with SRS Banning Bot v0.2 # | |
# # | |
# The Reddit API python wrapper is required for this script. # | |
# See https://github.com/mellort/reddit_api # | |
# # | |
# This program is free software: you can redistribute it and/or modify # | |
# it under the terms of the GNU General Public License as published by # | |
# the Free Software Foundation, either version 3 of the License, or # | |
# (at your option) any later version. # | |
# # | |
# This program is distributed in the hope that it will be useful, # | |
# but WITHOUT ANY WARRANTY; without even the implied warranty of # | |
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # | |
# GNU General Public License for more details. # | |
# # | |
# You should have received a copy of the GNU General Public License # | |
# along with this program. If not, see <http://www.gnu.org/licenses/>. # | |
# # | |
######################################################################################## | |
try: | |
import reddit | |
except ImportError: | |
raise ImportError('Reddit API python wrapper is required. See https://github.com/mellort/reddit_api for more details.') | |
import sys, time, argparse, string | |
######################################################################################## | |
# Initialisation & Global Variables #################################################### | |
######################################################################################## | |
parser = argparse.ArgumentParser(description='SRS Unbanning Bot v0.2. The French military banning strategy for reddit.',epilog='Associated files to be located in the run directory:\n\t \'white\': Whitelisting text file. The unbanning bot appends to this list. Users on the whitelist will not be banned from any sub.\n\t \'banlog\': Banning log for the bot.\n\nUse wisely.') | |
parser.add_argument('--launch', nargs='+', help='Subreddits doing the unbanning. Moderator privileges required.',required=True) | |
parser.add_argument('--username', help='Reddit Username',required=True) | |
parser.add_argument('--password', help='Reddit Password',required=True) | |
parser.add_argument('--target', nargs='+', help='Subreddits targeted for unbanning. If this argument is omitted, the bot will unban all users in the banlog.') | |
args = parser.parse_args() | |
username = args.username | |
passwd = args.password | |
launchsubs = args.launch | |
targetsubs = args.target | |
######################################################################################## | |
# Sub Routines ######################################################################### | |
######################################################################################## | |
# 1. Extract a trimmed banlist | |
def extract_ubanlist(targetsubs): | |
trimmed_ubanlist = [] | |
try: | |
banlog = [line.strip().split() for line in open('banlog')] | |
except: | |
raise IOError('File \'banlog\' is required in the run directory.') | |
else: | |
if len(targetsubs) == 0: | |
trimmed_ubanlist = [line[2] for line in banlog] # Unban everyone if no target. | |
else: | |
for sub in targetsubs: | |
for line in banlog: | |
if line[0] == sub: | |
trimmed_ubanlist.append(line[2]) | |
return trimmed_ubanlist | |
# 2. Unbanning function | |
def mass_uban(r,banlist,launchsubs): | |
for banee in banlist: | |
for sub in launchsubs: | |
try: | |
print banee+' '+str(r.get_subreddit(sub).display_name) | |
r.get_subreddit(sub).unban(r.get_redditor(banee['banee'])) | |
except: | |
e = sys.exc_info()[1] | |
print "fail: ",str(e) | |
# 3. Whitelisting append. | |
def white(q): | |
try: | |
white = open('white','a') | |
for k in q: | |
white.write(k+"\n") | |
white.close | |
except: | |
raise IOError('Cannot open file \'white\' for writing.') | |
return None | |
######################################################################################## | |
# Main Routine ######################################################################### | |
######################################################################################## | |
print "=======================================\n\t SRS Banning Bot v0.2\n=======================================" | |
print str(time.asctime(time.localtime()))+" - Logging into Reddit" | |
r = reddit.Reddit(user_agent='/u/'+username+' - SRS Unbanning Bot v0.2 - Testing only') | |
r.login(username,passwd) | |
print str(time.asctime(time.localtime()))+" - Creating unbanlist" | |
ubanlist = list(set(extract_ubanlist(targetsubs))) | |
print str(time.asctime(time.localtime()))+" - Whitelisting users" | |
white(ubanlist) | |
print str(time.asctime(time.localtime()))+" - Unbanning users" | |
mass_uban(r,ubanlist,launchsubs) | |
print str(time.asctime(time.localtime()))+" - Fin" | |
######################################################################################## | |
# Fin ################################################################################## | |
######################################################################################## |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
banbot.py is designed to run as an daily cron job. Redirect the output for a log of errors:
cd 'dir containing bot'; ./banbot.py --user 'username' --password 'password' --launch [Banning Subs] --target [subs to scrape]
ubanbot.py is designed for a one-off run to undo the banbot's work.
./ubanbot.py --user 'username' --password 'password' --launch [Unbanning Subs] --target [Only unban this sub's posters]