mirror of
https://gitea.augustin64.fr/piair/MsRewards-Reborn.git
synced 2025-07-01 20:53:57 +02:00
Compare commits
46 Commits
9bd96ad876
...
master
Author | SHA1 | Date | |
---|---|---|---|
5e5f7f7407 | |||
0cc42823ff | |||
56c858fa90 | |||
adf91ac8f0 | |||
2721c76686 | |||
45ea72a354 | |||
18b35f6f68 | |||
c53125479e | |||
df256f2405 | |||
31b4d5d7da | |||
574fa45813 | |||
3bb49d1618 | |||
e25334f1bd | |||
41312b53b9 | |||
1ac98f14c4 | |||
a197d44768 | |||
f9a21f5b98 | |||
82161973a9 | |||
c7e110787b | |||
1db1de9606 | |||
10d75f9d78 | |||
87fb791436 | |||
6995bde8a6 | |||
92069a013e | |||
906d3e7822 | |||
778adc67d2 | |||
402b8cd3ef | |||
3c74aa025e | |||
3123a1dbd0 | |||
27d45e88dd | |||
0685a42922 | |||
6729703827 | |||
304a222de1 | |||
04d33f4ecd | |||
ac22814605 | |||
b7a89b56d0 | |||
127d16afea | |||
9bcbc81c2f | |||
12eba5cde7 | |||
22ea727c47 | |||
05a1fd8557 | |||
39e226b564 | |||
cd00c8ca88 | |||
43793d2c2c | |||
ee6ec458fc | |||
e6e8bdaa06 |
1
.gitignore
vendored
1
.gitignore
vendored
@ -16,3 +16,4 @@ file.png
|
||||
*.ts
|
||||
LICENSE
|
||||
README.md
|
||||
venv
|
||||
|
@ -1,5 +1,5 @@
|
||||
FROM python:3.10
|
||||
ENV DEBIAN_FRONTEND noninteractive
|
||||
ENV DEBIAN_FRONTEND=noninteractive
|
||||
WORKDIR /app/
|
||||
|
||||
# Initial apt install
|
||||
|
226
V6.py
226
V6.py
@ -1,16 +1,17 @@
|
||||
#!/usr/bin/python3
|
||||
import random
|
||||
import subprocess
|
||||
|
||||
from modules.Classes.Config import Config
|
||||
from modules.Classes.DiscordLogger import DiscordLogger
|
||||
from modules.Classes.UserCredentials import UserCredentials
|
||||
from modules.Tools.logger import warning, critical
|
||||
from modules.Tools.logger import critical, warning
|
||||
from modules.cards import *
|
||||
from modules.config import *
|
||||
from modules.db import add_to_database
|
||||
from modules.driver_tools import *
|
||||
from modules.error import *
|
||||
|
||||
import random
|
||||
|
||||
|
||||
# create a webdriver
|
||||
def create_driver(mobile=False):
|
||||
@ -199,6 +200,10 @@ def do_poll():
|
||||
def all_cards():
|
||||
driver = config.WebDriver.driver
|
||||
|
||||
def check_popups() -> bool:
|
||||
"""
|
||||
Check various annoying popups
|
||||
"""
|
||||
def check_welcome_tour() -> bool:
|
||||
if "rewards.bing.com/welcometour" not in driver.current_url:
|
||||
return False
|
||||
@ -219,6 +224,43 @@ def all_cards():
|
||||
custom_sleep(1.5)
|
||||
return True
|
||||
|
||||
def check_streak_protection() -> bool:
|
||||
"""
|
||||
Ne perdez plus jamais votre série !
|
||||
"""
|
||||
try:
|
||||
streak_protection_close = driver.find_element(By.ID, "streak-protection-popup-close-cross")
|
||||
streak_protection_activate = driver.find_elements(By.CLASS_NAME, "earningPagePopUpPopUpSelectButton")
|
||||
streak_protection_activate[0].click()
|
||||
info("Popup 'Streak Protection' reçue")
|
||||
custom_sleep(1.5)
|
||||
|
||||
return True
|
||||
except (exceptions.NoSuchElementException, exceptions.ElementNotInteractableException, IndexError):
|
||||
# les éléments sont présents dans le DOM même quand la popup n'est pas visible apparemment
|
||||
return False
|
||||
|
||||
def check_streak_protection_expired() -> bool:
|
||||
"""
|
||||
Non, vous avez utilisé tous vos jours de protection contre les séries !
|
||||
"""
|
||||
try:
|
||||
streak_protection_close = driver.find_element(By.ID, "streak-protection-popup-close-cross")
|
||||
ok_sad_button = driver.find_elements(By.CLASS_NAME, "dashboardPopUpPopUpSelectButton")
|
||||
ok_sad_button[0].click()
|
||||
info("Popup 'Streak Protection fully used' reçue")
|
||||
custom_sleep(1.5)
|
||||
|
||||
return True
|
||||
except (exceptions.NoSuchElementException, exceptions.ElementNotInteractableException, IndexError):
|
||||
return False
|
||||
|
||||
return (
|
||||
check_welcome_tour()
|
||||
or check_streak_protection()
|
||||
or check_streak_protection_expired()
|
||||
)
|
||||
|
||||
driver.get("https://rewards.bing.com")
|
||||
wait_until_visible(By.CLASS_NAME, "c-card-content", 10, driver)
|
||||
|
||||
@ -265,15 +307,21 @@ def all_cards():
|
||||
if not checked:
|
||||
continue
|
||||
|
||||
try:
|
||||
activity = findall("data-bi-id=\"([^\"]+)\"", card_list[i].get_attribute("innerHTML"))[0]
|
||||
except Exception as e:
|
||||
warning("Can't find activity." + str(e))
|
||||
activity = ""
|
||||
|
||||
custom_sleep(1.5)
|
||||
check_welcome_tour()
|
||||
check_popups()
|
||||
driver.execute_script("arguments[0].scrollIntoView();", card_list[i])
|
||||
custom_sleep(1.5)
|
||||
card_list[i].click()
|
||||
|
||||
if len(driver.window_handles) > 1:
|
||||
driver.switch_to.window(driver.window_handles[1])
|
||||
try_play(driver.title)
|
||||
try_play(driver.title, activity)
|
||||
close_tab(driver.window_handles[1])
|
||||
|
||||
try:
|
||||
@ -283,7 +331,7 @@ def all_cards():
|
||||
if "mee-icon-AddMedium" not in card_list[i].get_attribute("innerHTML"):
|
||||
continue
|
||||
|
||||
check_welcome_tour()
|
||||
check_popups()
|
||||
driver.execute_script("arguments[0].scrollIntoView();", card_list[i])
|
||||
card_list[i].click()
|
||||
|
||||
@ -340,8 +388,124 @@ def promo():
|
||||
custom_sleep(3)
|
||||
|
||||
|
||||
def explore_on_bing(activity: str, config: Config):
|
||||
driver = config.WebDriver.driver
|
||||
|
||||
def search_bing(txt):
|
||||
search_elm = driver.find_element(By.ID, "sb_form_q")
|
||||
send_keys_wait(search_elm, txt)
|
||||
send_keys_wait(search_elm, Keys.ENTER)
|
||||
|
||||
if "lyrics" in activity:
|
||||
search_bing(
|
||||
f"paroles de {['Gata', 'Pyramide', 'Dolce Camara', 'Position', 'Mami Wata'][randint(0, 4)]}") # merci bing copilot pour les titres
|
||||
elif "flight" in activity:
|
||||
search_bing(
|
||||
f"vol {['Paris - New York', 'Londres Amsterdam', 'Bora-Bora Miami', 'Los Angeles Toulouse', 'Rome Dubai'][randint(0, 4)]}")
|
||||
elif "shopping" in activity:
|
||||
search_bing(f"idée cadeau {['Noel', 'Anniversaire'][randint(0, 1)]}")
|
||||
elif "movie" in activity:
|
||||
search_bing(
|
||||
f"Distribution {['Code 8 part 2', 'The Hunger Games: The ballad of Songbirds & Snakes', 'Rebel Moon: Part Two', 'Dune II', 'Wonka'][randint(0, 4)]}")
|
||||
elif "translator" in activity:
|
||||
search_bing(f"traduction {config.wordlist.get_word()} en anglais")
|
||||
elif "map" in activity:
|
||||
search_bing(f"{['Paris', 'Nice', 'Marseille', 'Bordeaux', 'Lyon'][randint(0, 4)]} carte")
|
||||
elif "restaurant" in activity:
|
||||
search_bing(random.choice([
|
||||
"restaurant à proximité",
|
||||
"restaurant pas loin",
|
||||
"manger dans le coin"
|
||||
]))
|
||||
elif "recipe" in activity:
|
||||
search_bing("recette de " + random.choice([
|
||||
"cake aux olives",
|
||||
"tarte tatin",
|
||||
"Kouign Amann",
|
||||
"poulet au Curry",
|
||||
"lasagnes aux épinards et ricotta",
|
||||
"Boeuf Bourguignon",
|
||||
"dessert",
|
||||
"gateau au chocolat",
|
||||
"crêpe sucrée"
|
||||
])) # Merci llama pour les idées
|
||||
elif "currency" in activity:
|
||||
currencies = [
|
||||
"euros",
|
||||
"dollars canadiens",
|
||||
"dollars",
|
||||
"livres",
|
||||
"francs suisses",
|
||||
"roubles",
|
||||
"pesos",
|
||||
"bitcoin",
|
||||
"anciens francs"
|
||||
]
|
||||
chosen = random.sample(currencies, k=2)
|
||||
search_bing(f"convertir {random.randint(2, 120)} {chosen[0]} en {chosen[1]}")
|
||||
elif "weather" in activity:
|
||||
search_bing(f"météo {['Paris', 'Nice', 'Marseille', 'Bordeaux', 'Lyon'][randint(0, 4)]}")
|
||||
elif "packagetracking" in activity:
|
||||
driver.get("https://www.bing.com/?setmkt=en-US&setlang=en-US")
|
||||
search_bing(f"{['fedex', 'UPS'][randint(0, 1)]} package tracking")
|
||||
elif "hotel" in activity:
|
||||
search_bing(f" {['Paris', 'Nice', 'Marseille', 'Bordeaux', 'Lyon'][randint(0, 4)]}")
|
||||
elif "health" in activity:
|
||||
search_bing(f"{['toux', 'douleur dos', 'nez qui coule', 'mal au genoux', 'otite'][randint(0, 4)]}")
|
||||
elif "news" in activity:
|
||||
search_bing(["actualités", "news"][randint(0, 1)])
|
||||
elif "jobs" in activity:
|
||||
search_bing("jobs")
|
||||
elif "realestate" in activity:
|
||||
search_bing(f"appartement à louer {['Paris', 'Nice', 'Marseille', 'Bordeaux', 'Lyon'][randint(0, 4)]}")
|
||||
elif "financemarket" in activity:
|
||||
search_bing(
|
||||
f"cours action {['AIR LIQUIDE', 'Airbus', 'BNP Paribas', 'Michelin', 'Stellantis', 'Vinci'][randint(0, 5)]}")
|
||||
elif "sports" in activity:
|
||||
equipes = random.sample([
|
||||
"Toulon", "toulouse",
|
||||
"stade Rochelais", "castres",
|
||||
"clermont", "perpignan",
|
||||
"aviron bayonnais", "vannes"
|
||||
], k=2)
|
||||
search_bing(f"{['score', 'résultats'][randint(0, 1)]} rugby {equipes[0]} {equipes[1]}")
|
||||
elif "videogames" in activity:
|
||||
search_bing(random.choice([
|
||||
"Minecraft", "GTA V",
|
||||
"Tetris", "PUBG",
|
||||
"Mario Kart 8",
|
||||
"Red Dead Redemption II",
|
||||
"Terraria",
|
||||
"The Witcher",
|
||||
"Animal Crossing",
|
||||
"Pokémon rouge & bleu",
|
||||
"Super Mario Bros",
|
||||
"The legend of Zelda BOTW",
|
||||
"Call of Duty Modern Warfare",
|
||||
"The Witcher III"
|
||||
]))
|
||||
elif "dictionary" in activity:
|
||||
search_bing(f"définition {config.wordlist.get_word()}")
|
||||
elif "election" in activity or "timezonedates" in activity:
|
||||
#! I don't understand the name of "timezonedates" but this seems to be the same activity
|
||||
state = random.choice([
|
||||
"Alaska", "Alabama", "Arkansas", "American Samoa", "Arizona", "California", "Colorado",
|
||||
"Connecticut", "District ", "of Columbia", "Delaware", "Florida", "Georgia", "Guam",
|
||||
"Hawaii", "Iowa", "Idaho", "Illinois", "Indiana", "Kansas", "Kentucky", "Louisiana",
|
||||
"Massachusetts", "Maryland", "Maine", "Michigan", "Minnesota", "Missouri", "Mississippi",
|
||||
"Montana", "North Carolina", "North Dakota", "Nebraska", "New Hampshire", "New Jersey",
|
||||
"New Mexico", "Nevada", "New York", "Ohio", "Oklahoma", "Oregon", "Pennsylvania",
|
||||
"Puerto Rico", "Rhode Island", "South Carolina", "South Dakota", "Tennessee", "Texas",
|
||||
"Utah", "Virginia", "Virgin Islands", "Vermont", "Washington", "Wisconsin",
|
||||
"West Virginia", "Wyoming"
|
||||
])
|
||||
search_bing(f"governor candidates {state} 2024")
|
||||
else:
|
||||
log_error(f"Explore on bing: {activity} not found.")
|
||||
|
||||
|
||||
# Find out which type of action to do
|
||||
def try_play(nom="unknown"):
|
||||
def try_play(nom="unknown", activity=""):
|
||||
driver = config.WebDriver.driver
|
||||
rgpd_popup(config)
|
||||
|
||||
@ -387,7 +551,7 @@ def try_play(nom="unknown"):
|
||||
info("On fidelity page.")
|
||||
fidelity()
|
||||
|
||||
elif wait_until_visible(By.ID, "rqStartQuiz", 5, driver):
|
||||
elif wait_until_visible(By.ID, "rqStartQuiz", 5, driver, raise_error=False):
|
||||
custom_sleep(3)
|
||||
driver.find_element(By.ID, "rqStartQuiz").click() # start the quiz
|
||||
answer_number = driver.page_source.count("rqAnswerOption")
|
||||
@ -397,9 +561,14 @@ def try_play(nom="unknown"):
|
||||
number = driver.page_source.count("rqAnswerOption")
|
||||
warning(f"recovery detected. quiz : {number}")
|
||||
play(number - 1)
|
||||
|
||||
elif "exploreonbing" in activity:
|
||||
info(f"Explore on bing: {activity}")
|
||||
explore_on_bing(activity, config)
|
||||
custom_sleep(uniform(3, 5))
|
||||
elif "Optimisez votre sécurité avec Microsoft" in driver.page_source:
|
||||
info("Still not paying Office 365 ?")
|
||||
else:
|
||||
info(f"Nothing to do on page `{nom}`")
|
||||
info(f"Nothing obvious to do on page `{nom}`.")
|
||||
custom_sleep(uniform(3, 5))
|
||||
|
||||
|
||||
@ -409,11 +578,15 @@ def login_part_1():
|
||||
info("Starting part 1 of login")
|
||||
driver = config.WebDriver.driver
|
||||
driver.get("https://login.live.com")
|
||||
try:
|
||||
wait_until_visible(By.ID, "i0116", browser=driver)
|
||||
send_wait_and_confirm(
|
||||
driver.find_element(By.ID, "i0116"),
|
||||
config.UserCredentials.get_mail()
|
||||
)
|
||||
except exceptions.NoSuchElementException:
|
||||
info("Unable to find mail input for login, might be semi-logged-in")
|
||||
|
||||
wait_until_visible(By.ID, "i0118", browser=driver)
|
||||
send_wait_and_confirm(
|
||||
driver.find_element(By.ID, "i0118"),
|
||||
@ -476,10 +649,12 @@ def login():
|
||||
def logged_in():
|
||||
driver.get("https://login.live.com")
|
||||
custom_sleep(10)
|
||||
debug(get_domain(driver))
|
||||
if get_domain(driver) == "account.microsoft.com":
|
||||
return True
|
||||
return False
|
||||
|
||||
info("Logging in...")
|
||||
driver = config.WebDriver.driver
|
||||
try:
|
||||
if not logged_in():
|
||||
@ -608,19 +783,23 @@ def fidelity():
|
||||
pause = driver.find_element(By.CSS_SELECTOR, f'[class="c-action-toggle c-glyph f-toggle glyph-pause"]')
|
||||
pause.click()
|
||||
except Exception as e:
|
||||
error(f"Error while clicking pause. Probably no cards. {e}")
|
||||
return "no cards"
|
||||
debug("No pause button.")
|
||||
|
||||
cartes = driver.find_elements(By.CSS_SELECTOR, f'[ng-repeat="item in $ctrl.transcludedItems"]')
|
||||
nb_cartes = len(cartes)
|
||||
if nb_cartes == 0:
|
||||
warning("No fidelity cards detected")
|
||||
return "No cards."
|
||||
checked_list_all = driver.find_elements(By.CSS_SELECTOR, f'[ng-if="$ctrl.complete"]')
|
||||
for i in range(nb_cartes):
|
||||
cartes[i].click()
|
||||
checked_txt = checked_list_all[i].get_attribute("innerHTML")
|
||||
ok = checked_txt.count("StatusCircleOuter checkmark")
|
||||
total = checked_txt.count("StatusCircleOuter")
|
||||
if (ok != total):
|
||||
if ok != total:
|
||||
elm = driver.find_elements(By.CLASS_NAME, 'clickable-link')[i]
|
||||
if not "moviesandtv" in elm.get_attribute("innerHTML"): # not the film card
|
||||
# legacy code. Should be removed
|
||||
if "moviesandtv" not in elm.get_attribute("innerHTML"): # not the film card
|
||||
elm.click()
|
||||
driver.switch_to.window(driver.window_handles[len(driver.window_handles) - 1])
|
||||
sub_fidelity()
|
||||
@ -738,9 +917,8 @@ def json_start(json_entry, cred: UserCredentials):
|
||||
config.WebDriver.set_pc_driver(create_driver())
|
||||
config.WebDriver.switch_to_driver("PC")
|
||||
driver = config.WebDriver.driver
|
||||
try:
|
||||
if "unban" in json_entry and str(account_id) in json_entry["unban"]:
|
||||
login_part_1()
|
||||
login()
|
||||
info("\nGO TO example.com TO PROCEED or wait 1200 secs.")
|
||||
for _ in range(1200):
|
||||
sleep(1)
|
||||
@ -749,13 +927,10 @@ def json_start(json_entry, cred: UserCredentials):
|
||||
break
|
||||
else:
|
||||
login()
|
||||
except KeyError:
|
||||
login()
|
||||
try:
|
||||
if str(account_id) in json_entry["tout"]:
|
||||
daily_routine(cred, True)
|
||||
except KeyError:
|
||||
pass
|
||||
|
||||
else:
|
||||
try:
|
||||
if str(account_id) in json_entry["daily"]:
|
||||
@ -781,10 +956,14 @@ def json_start(json_entry, cred: UserCredentials):
|
||||
log_error(e)
|
||||
except KeyError:
|
||||
pass
|
||||
|
||||
except KeyError:
|
||||
pass
|
||||
try:
|
||||
log_points()
|
||||
except Exception as e:
|
||||
error(f"CustomStart {e}")
|
||||
|
||||
driver.close()
|
||||
cred.next_account()
|
||||
account_id += 1
|
||||
@ -801,13 +980,17 @@ def default_start():
|
||||
while config.UserCredentials.is_valid():
|
||||
custom_sleep(1)
|
||||
info("Starting and configuring driver.")
|
||||
try:
|
||||
config.WebDriver.set_pc_driver(create_driver())
|
||||
except:
|
||||
info("Could not configure driver. Trying to update it.")
|
||||
subprocess.Popen(["python3", "/app/MsRewards-Reborn/modules/Tools/update_chrome.py"])
|
||||
config.WebDriver.set_pc_driver(create_driver())
|
||||
config.WebDriver.switch_to_driver("PC")
|
||||
info("Driver started.")
|
||||
config.WebDriver.pc_driver.implicitly_wait(3)
|
||||
try:
|
||||
wait_time = uniform(1200, 3600)
|
||||
wait_time = 10 # the display closes when I ctrl + c
|
||||
info(f"Waiting for {round(wait_time / 60)}min before starting")
|
||||
custom_sleep(wait_time)
|
||||
daily_routine(config.UserCredentials)
|
||||
@ -835,7 +1018,6 @@ def log_error(msg):
|
||||
|
||||
|
||||
def check_updated():
|
||||
debug(f"updated: {config.has_been_updated()}")
|
||||
if config.has_been_updated():
|
||||
config.discord.wh.send(f"Updated to {config.version}", username="update",
|
||||
avatar_url="https://cdn-icons-png.flaticon.com/512/1688/1688988.png")
|
||||
|
12
hooks/bump.sh
Executable file
12
hooks/bump.sh
Executable file
@ -0,0 +1,12 @@
|
||||
file=version
|
||||
|
||||
if [ "$(git diff HEAD version | wc -w)" -eq 0 ]
|
||||
then
|
||||
echo 'updating minor version'
|
||||
new_path=$(cat $file | awk -F . '{print $1"."$2"."$3+1 }')
|
||||
echo $new_path > $file
|
||||
git add version
|
||||
else
|
||||
echo 'Version have been updated manually'
|
||||
fi
|
||||
echo Version: $(cat $file)
|
1
hooks/pre-commit
Executable file
1
hooks/pre-commit
Executable file
@ -0,0 +1 @@
|
||||
sh hooks/bump.sh
|
@ -22,7 +22,8 @@ class Config:
|
||||
proxy = json.load(inFile)
|
||||
with open("/app/MsRewards-Reborn/user_data/configs.json", "r") as inFile:
|
||||
config = json.load(inFile)
|
||||
|
||||
with open("/app/MsRewards-Reborn/user_data/version", "r") as inFile:
|
||||
version = inFile.readline()
|
||||
"""
|
||||
setup standalone stuff
|
||||
"""
|
||||
@ -31,10 +32,9 @@ class Config:
|
||||
self.json_entry = args.json.replace("'", "\"")
|
||||
self.wordlist = WordList("/usr/share/dict/french")
|
||||
self.vnc = args.vnc
|
||||
self.version = args.update_version
|
||||
self.WebDriver = Driver()
|
||||
self.display = None
|
||||
|
||||
self.version = version
|
||||
"""
|
||||
setup UserCredential
|
||||
"""
|
||||
@ -81,4 +81,11 @@ class Config:
|
||||
self.display = display
|
||||
|
||||
def has_been_updated(self):
|
||||
return self.version != "None"
|
||||
with open('/app/MsRewards-Reborn/version', "r") as inFile:
|
||||
in_file_content = inFile.readlines()
|
||||
if self.version != in_file_content[0]:
|
||||
self.version = in_file_content[0]
|
||||
with open('/app/MsRewards-Reborn/user_data/version', "w") as outFile:
|
||||
outFile.write(self.version)
|
||||
return True
|
||||
return False
|
||||
|
@ -5,7 +5,7 @@ import subprocess
|
||||
|
||||
from logger import critical, info, error
|
||||
|
||||
errorMessage = subprocess.run(['python3', 'generate_error.py'], check=False, stdout=subprocess.PIPE,
|
||||
errorMessage = subprocess.run(['python3', '/app/MsRewards-Reborn/modules/Tools/generate_error.py'], check=False, stdout=subprocess.PIPE,
|
||||
stderr=subprocess.PIPE).stderr.decode("utf-8")
|
||||
|
||||
versionPattern = "This version of ChromeDriver only supports Chrome version ([0-9]+)"
|
||||
@ -15,6 +15,8 @@ try:
|
||||
except Exception as e:
|
||||
critical("Can't get version number from error")
|
||||
error(e)
|
||||
info("error message")
|
||||
info(errorMessage)
|
||||
exit(0)
|
||||
|
||||
info(f"Needed version : '{versionN}'")
|
||||
|
@ -1,9 +1,9 @@
|
||||
import os
|
||||
import json
|
||||
import os
|
||||
from random import uniform
|
||||
|
||||
from selenium.common import TimeoutException
|
||||
from selenium.webdriver import ActionChains, Keys
|
||||
from selenium.webdriver import Keys
|
||||
from selenium.webdriver.common.by import By
|
||||
from selenium.webdriver.support import expected_conditions
|
||||
from selenium.webdriver.support.wait import WebDriverWait
|
||||
@ -69,6 +69,7 @@ def send_keys_wait(element, keys: str) -> None:
|
||||
element.send_keys(i)
|
||||
sleep(uniform(0.1, 0.3))
|
||||
|
||||
|
||||
def send_wait_and_confirm(element, keys: str) -> None:
|
||||
send_keys_wait(element, keys)
|
||||
element.send_keys(Keys.ENTER)
|
||||
@ -81,6 +82,6 @@ def wait_until_visible(search_by: str, identifier: str, timeout: int = 20, brows
|
||||
expected_conditions.visibility_of_element_located((search_by, identifier)), "element not found")
|
||||
return True
|
||||
except TimeoutException as e:
|
||||
if raise_error:
|
||||
error(f"element {identifier} not found after {timeout}s")
|
||||
f = error if raise_error else debug
|
||||
f(f"element {identifier} not found after {timeout}s")
|
||||
return False
|
||||
|
1
user_data/version
Normal file
1
user_data/version
Normal file
@ -0,0 +1 @@
|
||||
0.0.0
|
Reference in New Issue
Block a user