eyal282

Action by Day Reddit Bot

Apr 5th, 2024 (edited)
156
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Python 6.20 KB | None | 0 0
  1. # I think PMs don't work, so editing settings should be done by replying to the bot in any sub it has access to.
  2.  
  3. # Import dependencies
  4. import praw
  5. import sqlite3
  6. import datetime
  7. import pytz
  8. import time
  9. import os
  10. import logging
  11.  
  12. from praw.models import Message
  13. from praw.models import Comment
  14. from praw.models import SubredditMessage
  15.  
  16. from dotenv import load_dotenv
  17.  
  18. load_dotenv()
  19.  
  20. #logger = logging.getLogger('prawcore')
  21. #logger.setLevel(logging.DEBUG)
  22.  
  23.  
  24. botUsername = "ActionByDayBOT"
  25.  
  26. try:
  27.     # Reddit initialization
  28.     reddit = praw.Reddit(
  29.         client_id="9yCd3MbHa6kSdkPqagq4TA",
  30.         client_secret=os.getenv("CLIENT_SECRET"),
  31.         user_agent="Action by Day (BOT)",
  32.         username=botUsername,
  33.         password=os.getenv("BOT_PASSWORD")
  34.     )
  35.  
  36. except Exception as e:
  37.     print("Login error:")
  38.     print(e)
  39.  
  40. # Retry loop
  41. max_retries = 10
  42. retries = 0
  43. while retries < max_retries:
  44.     try:
  45.         # Try the API call
  46.         username = reddit.user.me()
  47.  
  48.         if(username is None or username == "None"):
  49.             raise Exception("Authentication passed but without a valid user.")
  50.        
  51.         print("Logged in successfully!")
  52.         break
  53.  
  54.     except Exception as e:
  55.         # Auth failed, retry
  56.         retries += 1
  57.         print(f"Auth failed, retrying (attempt {retries}/{max_retries})")
  58.         print(e)
  59.         time.sleep(2 * retries)
  60.  
  61. # Connect to SQLite database
  62. conn = sqlite3.connect('bot.db')
  63. c = conn.cursor()
  64.  
  65. # Create table to store subreddit configs
  66. c.execute('''
  67.           CREATE TABLE IF NOT EXISTS config
  68.           (id INTEGER PRIMARY KEY AUTOINCREMENT,
  69.            subreddit_name TEXT,
  70.            flair TEXT,
  71.            day TEXT,  
  72.            timezone TEXT)
  73.           ''')
  74.  
  75. # Get config for a subreddit_name          
  76. def get_config(subreddit_name):
  77.     c.execute("SELECT * FROM config WHERE subreddit_name=?", (subreddit_name,))
  78.     return c.fetchone()
  79.  
  80. # Update config for a subreddit
  81. def update_config(subreddit_name, flair, day, timezone):
  82.     c.execute("""UPDATE config
  83.               SET flair=?, day=?, timezone=?
  84.               WHERE subreddit_name=?""",
  85.               (flair, day, timezone, subreddit_name))
  86.     conn.commit()
  87.  
  88. # Handle incoming Reddit messages
  89. def handle_message(message):
  90.  
  91.     # Split message into command and arguments
  92.     command, *args = message.body.split()
  93.  
  94.     if command == "!help":
  95.         # Return help text
  96.         reply = get_help_text()
  97.  
  98.     else:        
  99.         subreddit_name = args[0]
  100.  
  101.         if not subreddit.moderator(reddit.user.me()):
  102.             message.reply("I must be a moderator to configure this subreddit.")
  103.         return
  104.    
  105.         if not subreddit.moderator(message.author):
  106.             message.reply("You must be a moderator to configure this subreddit.")
  107.         return
  108.    
  109.         if command == "!addflair":
  110.             # Add flair config
  111.    
  112.             flair, day = args[1:]
  113.            
  114.             config = get_config(subreddit_name)
  115.             if not config:
  116.                 # Initialize config if none exists
  117.                 c.execute("INSERT INTO config (subreddit_name) VALUES (?)", (subreddit_name,))
  118.                
  119.             update_config(subreddit_name, flair, day, config['timezone'])
  120.            
  121.             # Confirmation reply
  122.             reply = "Flair added successfully"
  123.            
  124.         elif command == "!removeflair":
  125.             # Remove flair config
  126.             flair = args[1]
  127.            
  128.             config = get_config(subreddit_name)
  129.             if not config:
  130.                 reply = "Subreddit not configured"
  131.             else:
  132.                 # Remove flair text, leave other values  
  133.                 update_config(subreddit_name, "", config['day'], config['timezone'])
  134.                 reply = "Flair removed successfully"
  135.                
  136.         elif command == "!timezone":
  137.             # Update timezone
  138.             timezone = args[1]
  139.            
  140.             config = get_config(subreddit_name)
  141.             if not config:
  142.                 # Initialize if no config
  143.                 c.execute("INSERT INTO config (subreddit_name) VALUES (?)", (subreddit_name,))
  144.                
  145.             update_config(subreddit_name, config['flair'], config['day'], timezone)
  146.             reply = "Timezone updated successfully"
  147.            
  148.         else:
  149.             # Unknown command
  150.             reply = "Unknown command. use !help for list of commands."
  151.  
  152.     # Send reply    
  153.     message.reply(reply)
  154.  
  155. # Help text    
  156. def get_help_text():
  157.     return """
  158.     Commands:
  159.    
  160.     !addflair <subreddit> <flair text> <day of week>
  161.     !removeflair <subreddit> <flair text>  
  162.     !timezone <subreddit> <timezone>
  163.     """
  164.  
  165. # Check submissions in configured subreddits
  166. def on_main_sub():
  167.  
  168.     # Get all subreddit configs
  169.     c.execute("SELECT * FROM config")
  170.     configs = c.fetchall()
  171.  
  172.     # Loop through configs
  173.     for config in configs:
  174.         subreddit_name = config['subreddit_name']
  175.         flair = config['flair']
  176.         day = config['day']
  177.         timezone = config['timezone']
  178.        
  179.         # Check submissions
  180.         for submission in subreddit.stream.submissions():
  181.             if submission.link_flair_text == flair:
  182.  
  183.                 # Get current weekday
  184.                 current_day = get_weekday(timezone)
  185.  
  186.                 if current_day != day:
  187.                     # Remove post
  188.                     submission.mod.remove()
  189.  
  190.                     # Reply to author
  191.                     reply_to_author(submission, config)
  192.                    
  193. # Reply to author with reason                    
  194. def reply_to_author(submission, config):
  195.     flair = config['flair']
  196.     day = config['day']
  197.    
  198.     reply = f"The {flair} flair can only be used on {day}."
  199.     submission.reply(reply)
  200.    
  201. # Get weekday from timezone  
  202. def get_weekday(timezone):
  203.     tz = pytz.timezone(timezone)
  204.     now = datetime.datetime.now(tz)
  205.     return now.strftime("%A")
  206.  
  207.  
  208. # Main loop
  209. def main():
  210.     while True:
  211.         try:
  212.             # Check submissions
  213.             # on_main_sub()
  214.    
  215.             try:
  216.                 for message in reddit.inbox.unread(limit=None):
  217.                     print(type(message))
  218.                     if isinstance(message, Message):
  219.                         print(message.body)
  220.  
  221.                    
  222.             except Exception as e:
  223.                 print(f"Error reading private messages: {e}")
  224.            
  225.         except Exception as e:
  226.             # Print any errors
  227.             print(f"Global Error: {e}")
  228.            
  229.         time.sleep(60)
  230.  
  231. main()
  232.  
  233. subreddit = reddit.subreddit("all")
  234.  
  235. for comment in subreddit.stream.comments(pause_after=-1):  # stream will return None when there are no new objects in the stream
  236.     if comment is None:
  237.         for i in reddit.inbox.unread(limit=None):
  238.             if isinstance(i, SubredditMessage):  # make sure it's a comment, because it could also be a message
  239.                 try:
  240.                     i.author
  241.                     i.body
  242.                 except Exception as e:
  243.                     # Print any errors
  244.                     print(f"Failed to access potential mod invite message {e}")
  245.  
  246.                 finally:
  247.                     if i.author is None:
  248.                         if not subreddit.moderator(reddit.user.me()):
  249.                             print("Accepted a mod invite")
  250.                             i.subreddit.mod.accept_invite()
  251.                             i.mark_read()
Advertisement
Add Comment
Please, Sign In to add comment