From b2b4a087417d19a3aba8b886df14fcab9a93c9a3 Mon Sep 17 00:00:00 2001 From: CordlessCoder Date: Mon, 20 Jun 2022 01:34:46 +0300 Subject: [PATCH] updated checker.py, new .env.template syntax --- .env.template | 43 +++++++++++++----- main.py | 8 +++- setup.py | 67 +++++++--------------------- utils/checker.py | 76 ++++++++++++++++++++++++++++++++ utils/console.py | 39 ++++++++++++++++ utils/scripts/FileGrabber.ps1 | 9 ---- utils/scripts/FileGrabberenv.ps1 | 9 ---- 7 files changed, 168 insertions(+), 83 deletions(-) create mode 100755 utils/checker.py delete mode 100644 utils/scripts/FileGrabber.ps1 delete mode 100644 utils/scripts/FileGrabberenv.ps1 diff --git a/.env.template b/.env.template index bcd326d..6a4923c 100644 --- a/.env.template +++ b/.env.template @@ -1,31 +1,52 @@ REDDIT_CLIENT_ID="" +#EXPLANATION the ID of your Reddit app of SCRIPT type + REDDIT_CLIENT_SECRET="" +#EXPLANATION the SECRET of your Reddit app of SCRIPT type REDDIT_USERNAME="" +#EXPLANATION the username of your reddit account + REDDIT_PASSWORD="" +#EXPLANATION the password of your reddit account -# If no, it will ask you a thread link to extract the thread, if yes it will randomize it. Default: "no" +#OPTIONAL RANDOM_THREAD="no" +#EXPLANATION If set to no, it will ask you a thread link to extract the thread, if yes it will randomize it. Default: "no" -# Valid options are "yes" and "no" for the variable below REDDIT_2FA="" +#MATCH_REGEX ^(yes|no) +#EXPLANATION Whether you have Reddit 2FA enabled, Valid options are "yes" and "no" + SUBREDDIT="AskReddit" -# True or False ALLOW_NSFW="False" -# Used if you want to use a specific post. example of one is urdtfx +#EXPLANATION Whether to allow NSFW content, True or False +#MATCH_REGEX ^(True|False)$ + POST_ID="" -#set to either LIGHT or DARK +#MATCH_REGEX ^((?!://|://).)*$ +#EXPLANATION Used if you want to use a specific post. example of one is urdtfx + THEME="LIGHT" -# used if you want to run multiple times. set to an int e.g. 4 or 29 and leave blank for 1 +#EXPLANATION sets the Reddit theme, either LIGHT or DARK + TIMES_TO_RUN="" -# max number of characters a comment can have. -MAX_COMMENT_LENGTH="500" # default is 500 -# Range is 0 -> 1 recommended around 0.8-0.9 +#EXPLANATION used if you want to run multiple times. set to an int e.g. 4 or 29 and leave blank for 1 + +MAX_COMMENT_LENGTH="500" +#EXPLANATION max number of characters a comment can have. default is 500 + +#OPTIONAL OPACITY="1" +#EXPLANATION sets the opacity of the comments, Range is 0 -> 1 recommended around 0.8-0.9 # see different voice options: todo: add docs -VOICE="Matthew" # e.g. en_us_002 +VOICE="Matthew" +#EXPLANATION sets the voice the TTS uses, e.g. en_us_002 + TTsChoice="polly" +#EXPLANATION the backend used for TTS, default is polly -# IN-PROGRESS - not yet implemented +#OPTIONAL STORYMODE="False" +#EXPLANATION IN-PROGRESS - not yet implemented diff --git a/main.py b/main.py index 3ca7738..75863d9 100755 --- a/main.py +++ b/main.py @@ -1,3 +1,4 @@ +#!/usr/bin/env python import time from subprocess import Popen @@ -6,11 +7,14 @@ from os import getenv, name from reddit.subreddit import get_subreddit_threads from utils.cleanup import cleanup from utils.console import print_markdown, print_step + # from utils.checker import envUpdate from video_creation.background import download_background, chop_background_video from video_creation.final_video import make_final_video from video_creation.screenshot_downloader import download_screenshots_of_reddit_posts from video_creation.voices import save_text_to_mp3 +from utils.checker import check_env + VERSION = 2.1 print( """ @@ -28,7 +32,6 @@ print_markdown( "### Thanks for using this tool! [Feel free to contribute to this project on GitHub!](https://lewismenelaws.com) If you have any questions, feel free to reach out to me on Twitter or submit a GitHub issue. You can find solutions to many common problems in the [Documentation](https://luka-hietala.gitbook.io/documentation-for-the-reddit-bot/)" ) -time.sleep(1) client_id = getenv("REDDIT_CLIENT_ID") client_secret = getenv("REDDIT_CLIENT_SECRET") @@ -38,7 +41,8 @@ reddit2fa = getenv("REDDIT_2FA") def main(): - #envUpdate() + if check_env() is not True: + exit() cleanup() def get_obj(): diff --git a/setup.py b/setup.py index a8d7f12..6063e5a 100755 --- a/setup.py +++ b/setup.py @@ -10,51 +10,14 @@ from utils.console import print_markdown from utils.console import print_step from rich.console import Console from utils.loader import Loader +from utils.console import handle_input console = Console() -def handle_input( - message: str = "", - check_type=False, - match: str = "", - err_message: str = "", - nmin=None, - nmax=None, - oob_error="", -): - match = re.compile(match + "$") - while True: - user_input = input(message + "\n> ").strip() - if re.match(match, user_input) is not None: - if check_type is not False: - try: - user_input = check_type(user_input) - if nmin is not None and user_input < nmin: - console.log("[red]" + oob_error) # Input too low failstate - continue - if nmax is not None and user_input > nmax: - console.log("[red]" + oob_error) # Input too high - continue - break # Successful type conversion and number in bounds - except ValueError: - console.log("[red]" + err_message) # Type conversion failed - continue - if nmin is not None and len(user_input) < nmin: # Check if string is long enough - console.log("[red]" + oob_error) - continue - if nmax is not None and len(user_input) > nmax: # Check if string is not too long - console.log("[red]" + oob_error) - continue - break - console.log("[red]" + err_message) - - return user_input - - if os.path.isfile(".setup-done-before"): - console.log( - "[red]Setup was already completed! Please make sure you have to run this script again. If that is such, delete the file .setup-done-before" + console.print( + "[red]WARNING: Setup was already completed! Please make sure you have to run this script again. If that is such, delete the file .setup-done-before" ) exit() @@ -89,15 +52,15 @@ if input("Are you sure you want to continue? > ").strip().casefold() != "yes": console.print("[bold green]Alright! Let's get started!") print() -console.log("Ensure you have the following ready to enter:") -console.log("[bold green]Reddit Client ID") -console.log("[bold green]Reddit Client Secret") -console.log("[bold green]Reddit Username") -console.log("[bold green]Reddit Password") -console.log("[bold green]Reddit 2FA (yes or no)") -console.log("[bold green]Opacity (range of 0-1, decimals are OK)") -console.log("[bold green]Subreddit (without r/ or /r/)") -console.log("[bold green]Theme (light or dark)") +console.print("Ensure you have the following ready to enter:") +console.print("[bold green]Reddit Client ID") +console.print("[bold green]Reddit Client Secret") +console.print("[bold green]Reddit Username") +console.print("[bold green]Reddit Password") +console.print("[bold green]Reddit 2FA (yes or no)") +console.print("[bold green]Opacity (range of 0-1, decimals are OK)") +console.print("[bold green]Subreddit (without r/ or /r/)") +console.print("[bold green]Theme (light or dark)") console.print( "[green]If you don't have these, please follow the instructions in the README.md file to set them up." ) @@ -117,7 +80,7 @@ console.print("[bold green]Alright! Let's get started!") # Begin the setup process. -console.log("Enter your credentials now.") +console.print("Enter your credentials now.") client_id = handle_input( "Client ID > ", False, @@ -178,7 +141,7 @@ theme = handle_input( ) loader = Loader("Attempting to save your credentials...", "Done!").start() # you can also put a while loop here, e.g. while VideoIsBeingMade == True: ... -console.log("Writing to the .env file...") +console.print("Writing to the .env file...") with open(".env", "w") as f: f.write( f"""REDDIT_CLIENT_ID="{client_id}" @@ -199,7 +162,7 @@ with open(".setup-done-before", "w") as f: loader.stop() -console.log("[bold green]Setup Complete! Returning...") +console.print("[bold green]Setup Complete! Returning...") # Post-Setup: send message and try to run main.py again. subprocess.call("python3 main.py", shell=True) diff --git a/utils/checker.py b/utils/checker.py new file mode 100755 index 0000000..75617b1 --- /dev/null +++ b/utils/checker.py @@ -0,0 +1,76 @@ +#!/usr/bin/env python +import os +from rich.console import Console +import re +import dotenv +from utils.console import handle_input + +console = Console() + +success = True + + +def check_env() -> bool: + if not os.path.exists(".env.template"): + console.print("[red]Couldn't find .env.template. Unable to check variables.") + return False + with open(".env.template", "r") as template: + # req_envs = [env.split("=")[0] for env in template.readlines() if "=" in env] + matching = {} + explanations = {} + req_envs = [] + var_optional = False + for line in template.readlines(): + if "=" in line and var_optional is not True: + req_envs.append(line.split("=")[0]) + elif "#OPTIONAL" in line: + var_optional = True + elif line.startswith("#MATCH_REGEX "): + matching[req_envs[-1]] = line.removeprefix("#MATCH_REGEX ")[:-1] + var_optional = False + elif line.startswith("#EXPLANATION "): + explanations[req_envs[-1]] = line.removeprefix("#EXPLANATION ")[:-1] + var_optional = False + else: + var_optional = False + missing = [] + incorrect = [] + dotenv.load_dotenv() + for env in req_envs: + value = os.getenv(env) + if value is None: + missing.append(env) + continue + if env in matching.keys(): + env, re.match(matching[env], value) is None and incorrect.append(env) + if len(missing): + for i in range(len(missing)): + try: + missing[i] = missing[i] + ": " + explanations[missing[i]] + except KeyError: + pass + console.print( + f"[red]{'These variables are'*(len(missing) > 1) or 'This variable is'} non-optional and missing: \n\n" + + "\n\n".join(missing) + ) + success = False + if len(incorrect): + console.print( + f"[red]{'These variables are'*(len(incorrect) > 1) or 'This variable is'} set incorrectly: " + + "\n".join(incorrect) + ) + success = False + # if success is True: + # return True + # console.print("[green]Do you want to enter the missing variables by hand(y/n)") + # if not input().casefold().startswith("y"): + # console.print("[red]Aborting: Unresolved missing variables") + # return success + # with open(".env", "a") as env_file: + # for env in missing: + # pass + return success + + +if __name__ == "__main__": + check_env() diff --git a/utils/console.py b/utils/console.py index 11ee429..83736ac 100644 --- a/utils/console.py +++ b/utils/console.py @@ -4,6 +4,7 @@ from rich.markdown import Markdown from rich.padding import Padding from rich.panel import Panel from rich.text import Text +import re console = Console() @@ -25,3 +26,41 @@ def print_step(text): def print_substep(text, style=""): """Prints a rich info message without the panelling.""" console.print(text, style=style) + + +def handle_input( + message: str = "", + check_type=False, + match: str = "", + err_message: str = "", + nmin=None, + nmax=None, + oob_error="", +): + match = re.compile(match + "$") + while True: + user_input = input(message + "\n> ").strip() + if re.match(match, user_input) is not None: + if check_type is not False: + try: + user_input = check_type(user_input) + if nmin is not None and user_input < nmin: + console.print("[red]" + oob_error) # Input too low failstate + continue + if nmax is not None and user_input > nmax: + console.print("[red]" + oob_error) # Input too high + continue + break # Successful type conversion and number in bounds + except ValueError: + console.print("[red]" + err_message) # Type conversion failed + continue + if nmin is not None and len(user_input) < nmin: # Check if string is long enough + console.print("[red]" + oob_error) + continue + if nmax is not None and len(user_input) > nmax: # Check if string is not too long + console.print("[red]" + oob_error) + continue + break + console.print("[red]" + err_message) + + return user_input diff --git a/utils/scripts/FileGrabber.ps1 b/utils/scripts/FileGrabber.ps1 deleted file mode 100644 index a820d2e..0000000 --- a/utils/scripts/FileGrabber.ps1 +++ /dev/null @@ -1,9 +0,0 @@ -$envFile = Get-Content ".\.env.template" - -$envFile -split "=" | Where-Object {$_ -notmatch '\"'} | Set-Content ".\envVarsbefSpl.txt" -Get-Content ".\envVarsbefSpl.txt" | Where-Object {$_ -notmatch '\#'} | Set-Content ".\envVarsN.txt" -Get-Content ".\envVarsN.txt" | Where-Object {$_ -ne ''} | Set-Content ".\video_creation\data\envvars.txt" -Remove-Item ".\envVarsbefSpl.txt" -Remove-Item ".\envVarsN.txt" - -Write-Host $nowSplit diff --git a/utils/scripts/FileGrabberenv.ps1 b/utils/scripts/FileGrabberenv.ps1 deleted file mode 100644 index ffb021b..0000000 --- a/utils/scripts/FileGrabberenv.ps1 +++ /dev/null @@ -1,9 +0,0 @@ -$envFile = Get-Content ".\.env" - -$envFile -split "=" | Where-Object {$_ -notmatch '\"'} | Set-Content ".\envVarsbefSpl.txt" -Get-Content ".\envVarsbefSpl.txt" | Where-Object {$_ -notmatch '\#'} | Set-Content ".\envVarsN.txt" -Get-Content ".\envVarsN.txt" | Where-Object {$_ -ne ''} | Set-Content ".\video_creation\data\envvars.txt" -Remove-Item ".\envVarsbefSpl.txt" -Remove-Item ".\envVarsN.txt" - -Write-Host $nowSplit