Best Python code snippet using SeleniumBase
ethan_tda_bot.py
Source:ethan_tda_bot.py
1from PyQt5.QtWidgets import QApplication, QWidget, QLabel, QTextEdit, QPushButton, QLineEdit, QListWidget2from PyQt5.QtCore import QThread, pyqtSignal3from PyQt5.QtGui import QFont, QIcon4from PyQt5.QtCore import Qt5from robin_stocks import helper as helper6from datetime import datetime, timedelta7from selenium.webdriver.support.wait import WebDriverWait8from selenium.webdriver.support import expected_conditions as EC9from selenium.webdriver.common.keys import Keys10from selenium.webdriver.common.by import By11from selenium import webdriver12from td.client import TDClient13from td.config import CONSUMER_ID, REDIRECT_URI, ACCOUNT_PASSWORD, ACCOUNT_NUMBER14from pytz import timezone15import requests16import json17import time18import os, sys19def market_order_json(symbol, quantity, direction):20 order = {21 "orderType": "MARKET",22 "session": "NORMAL",23 "duration": "DAY",24 "orderStrategyType": "SINGLE",25 "orderLegCollection": [26 {27 "instruction": direction,28 "quantity": quantity,29 "instrument": {30 "symbol": symbol,31 "assetType": "EQUITY"32 }33 }34 ]35 }36 return order37HOST_URL = 'https://ethanherokuwebhookserver.herokuapp.com'38FILE_NAME = 'C://stock_data.csv'39# os.chdir(sys._MEIPASS)40SOURCE_FOLDER = 'res/'41TIMEZONE = 'US/Eastern'42# TradingView Login43Email = "ExecutorEA.alerts@gmail.com"44Password = "Bodhieli29!"45# ChromeDriver Options46options = webdriver.ChromeOptions()47options.add_argument("--start-maximized")48options.add_argument("--disable-notifications")49options.add_experimental_option("excludeSwitches", ["enable-logging"])50driver_path = SOURCE_FOLDER + 'chromedriver.exe'51def check_exist_data(file_name, str_data):52 if os.path.isfile(file_name):53 fr = open(file_name, 'r')54 readlines = fr.readlines()55 fr.close()56 for line in readlines:57 if str_data == line[:-1]:58 return True59 return False60def save_data(file_name, str_data):61 fw = open(file_name, 'a')62 fw.write(str_data + '\n')63 fw.close()64def perform_click_chain_by_xpath(driver, click_chain):65 '''66 Safely perform click chain67 Parameters:68 driver (Selenium webdriver): Selenium webdriver69 click_chain (list): list of elements xpath to click70 '''71 for xpath in click_chain:72 if type(xpath) == str:73 try:74 WebDriverWait(driver, 2).until(EC.presence_of_element_located((By.XPATH, xpath))).click()75 time.sleep(2)76 except:77 try:78 WebDriverWait(driver, 2).until(79 EC.presence_of_element_located((By.XPATH, xpath))).location_once_scrolled_into_view80 WebDriverWait(driver, 2).until(EC.presence_of_element_located((By.XPATH, xpath))).click()81 except Exception as e:82 print(e)83 return84 else:85 continue86 elif type(xpath) == list:87 for s_xpath in xpath:88 try:89 WebDriverWait(driver, 2).until(EC.presence_of_element_located((By.XPATH, s_xpath))).click()90 time.sleep(2)91 except:92 try:93 WebDriverWait(driver, 2).until(94 EC.presence_of_element_located((By.XPATH, s_xpath))).location_once_scrolled_into_view95 WebDriverWait(driver, 2).until(EC.presence_of_element_located((By.XPATH, s_xpath))).click()96 except Exception as e:97 print(e)98 continue99 else:100 continue101def wait(func, t=2):102 def wrapper(*args, **kargs):103 time.sleep(t)104 func(*args, **kargs)105 return wrapper106def back_off(func):107 def wrapper(*args, max_tries=3, sleep_time=2, count=1):108 if count > max_tries:109 return110 try:111 func(*args)112 except Exception as e:113 print(e)114 time.sleep(sleep_time)115 count += 1116 wrapper(sleep_time=2 * count, count=count)117 else:118 return119 return wrapper120class TradeBot(QThread):121 """122 A class to represent a trading bot.123 ...124 Attributes125 ----------126 driver : Selenium webdriver127 Selenium webdriver128 Methods129 -------130 init_driver():131 Create webdriver132 set_alert(ticker, extra_text=''):133 Set alert with name = ticker + extra_text134 """135 def __init__(self, start_time, end_time, parent=None):136 QThread.__init__(self, parent)137 self.driver = None138 self.start_time = start_time139 self.end_time = end_time140 self.current_alert_list = []141 def get_top_symbols(self):142 ticker_list = []143 # Email Button144 screener_page = "https://www.tradingview.com/markets/stocks-usa/market-movers-active/"145 self.driver = webdriver.Chrome(executable_path=driver_path, options=options)146 self.driver.get("https://www.tradingview.com/")147 # Sign in button148 try:149 print(12)150 WebDriverWait(self.driver, 5).until(151 EC.presence_of_element_located(152 (By.XPATH, '/html/body/div[2]/div[3]/div/div[4]/button[1]'))).click()153 print(23)154 WebDriverWait(self.driver, 5).until(155 EC.presence_of_element_located(156 (By.XPATH, '//*[@id="overlap-manager-root"]/div/span/div[1]/div/div/div[1]'))).click()157 print(34)158 # Enter Email159 WebDriverWait(self.driver, 5).until(160 EC.presence_of_element_located(161 (By.XPATH,162 '//*[@id="overlap-manager-root"]/div/div[2]/div/div/div/div/div/div/div[1]/div[4]'))).click()163 print(45)164 # Enter Email165 WebDriverWait(self.driver, 2).until(166 EC.presence_of_element_located(167 (By.XPATH, '//*[contains(@id,"email-signin__user-name-input")]'))).send_keys(168 str(Email))169 # Enter Password170 WebDriverWait(self.driver, 2).until(171 EC.presence_of_element_located(172 (By.XPATH, '//*[contains(@id,"email-signin__password-input")]'))).send_keys(173 str(Password))174 # Sign In175 WebDriverWait(self.driver, 2).until(176 EC.presence_of_element_located((By.XPATH, '//*[contains(@id, "email-signin__submit")]'))).click()177 time.sleep(3)178 self.driver.get(screener_page)179 WebDriverWait(self.driver, 5).until(EC.presence_of_element_located(180 (By.XPATH, '//*[@id="js-screener-container"]/div[3]/table/thead/tr/th[3]/div/div/div/div'))).click()181 time.sleep(2)182 for i in range(1, 12):183 ticker_name = self.driver.find_element_by_xpath(184 f'//*[@id="js-screener-container"]/div[3]/table/tbody/tr[{i}]/td[1]/div/div[2]/a').text185 if ticker_name != 'MTL/P':186 ticker_list.append(ticker_name)187 time.sleep(1)188 self.driver.close()189 except Exception as e:190 print(e)191 return ticker_list[:10]192 def init_driver(self):193 self.driver = webdriver.Chrome(executable_path=driver_path, options=options)194 self.driver.get("https://www.tradingview.com/")195 print(12)196 WebDriverWait(self.driver, 5).until(197 EC.presence_of_element_located(198 (By.XPATH, '/html/body/div[2]/div[3]/div/div[4]/button[1]'))).click()199 print(23)200 WebDriverWait(self.driver, 5).until(201 EC.presence_of_element_located(202 (By.XPATH, '//*[@id="overlap-manager-root"]/div/span/div[1]/div/div/div[1]'))).click()203 print(34)204 # Enter Email205 WebDriverWait(self.driver, 5).until(206 EC.presence_of_element_located(207 (By.XPATH, '//*[@id="overlap-manager-root"]/div/div[2]/div/div/div/div/div/div/div[1]/div[4]'))).click()208 print(45)209 # Enter Email210 WebDriverWait(self.driver, 2).until(211 EC.presence_of_element_located((By.XPATH, '//*[contains(@id,"email-signin__user-name-input")]'))).send_keys(212 str(Email))213 # Enter Password214 WebDriverWait(self.driver, 2).until(215 EC.presence_of_element_located((By.XPATH, '//*[contains(@id,"email-signin__password-input")]'))).send_keys(216 str(Password))217 # Sign In218 WebDriverWait(self.driver, 2).until(219 EC.presence_of_element_located((By.XPATH, '//*[contains(@id, "email-signin__submit")]'))).click()220 time.sleep(3)221 self.driver.get('https://www.tradingview.com/chart/5knnvijG/')222 def change_ticker(self, ticker):223 WebDriverWait(self.driver, 2).until(224 EC.presence_of_element_located((By.ID, 'header-toolbar-symbol-search'))).click()225 WebDriverWait(self.driver, 2).until(226 EC.presence_of_element_located((By.CSS_SELECTOR, 'input[data-role="search"]'))).clear()227 WebDriverWait(self.driver, 2).until(228 EC.presence_of_element_located((By.CSS_SELECTOR, 'input[data-role="search"]'))).send_keys(ticker)229 time.sleep(3)230 WebDriverWait(self.driver, 2).until(EC.presence_of_element_located(231 (By.XPATH, '//*[@id="overlap-manager-root"]/div/div/div[2]/div/div[4]/div/div[1]/div[2]'))).click()232 @wait233 def delete_all_alerts(self):234 try:235 WebDriverWait(self.driver, 5).until(EC.presence_of_element_located(236 (By.XPATH, '/html/body/div[2]/div[5]/div/div[1]/div[1]/div[2]/div[1]/div[1]/div[2]/div[2]'))).click()237 time.sleep(1)238 WebDriverWait(self.driver, 5).until(EC.presence_of_element_located(239 (By.XPATH, '//*[@id="overlap-manager-root"]/div/span/div[1]/div/div/div[4]/div/div'))).click()240 time.sleep(1)241 WebDriverWait(self.driver, 5).until(EC.presence_of_element_located(242 (By.XPATH, '//*[@id="overlap-manager-root"]/div/div[2]/div/div/div/div[3]/div[2]/span[2]'))).click()243 time.sleep(1)244 except Exception as e:245 print(e)246 WebDriverWait(self.driver, 5).until(EC.presence_of_element_located(247 (By.XPATH, '/html/body/div[2]/div[5]/div/div[1]/div[1]/div[2]/div[1]/div[1]/div[2]/div[2]'))).click()248 time.sleep(1)249 print("close alert")250 def edit_alert_info(self, ticker, extra_text):251 # Enter alert name252 alert_input = WebDriverWait(self.driver, 2).until(253 EC.presence_of_element_located((By.CSS_SELECTOR, 'input[name="alert-name"]')))254 alert_input.location_once_scrolled_into_view255 alert_input.send_keys("{} {}".format(ticker, extra_text))256 # Enter alert description257 desc_input = WebDriverWait(self.driver, 2).until(258 EC.presence_of_element_located((By.CSS_SELECTOR, 'textarea[name="description"]')))259 desc_input.location_once_scrolled_into_view260 desc_input.clear()261 desc_input.send_keys("{} {}".format(ticker, extra_text))262 # Click submit263 WebDriverWait(self.driver, 2).until(264 EC.presence_of_element_located((By.CSS_SELECTOR, 'span.tv-button__loader'))).click()265 # Click ok in warning form266 try:267 WebDriverWait(self.driver, 10).until(268 EC.presence_of_element_located((By.CSS_SELECTOR, 'button[name="ok-button"]'))).click()269 except:270 pass271 @wait272 def set_lux_algo_alert(self, ticker, signal_type, extra_text):273 if extra_text == "Buy 1":274 click_chain = [275 '//*[@id="header-toolbar-intervals"]/div[2]', # select 1m chart276 '//*[@id="header-toolbar-alerts"]', # alert menu277 '//*[@id="overlap-manager-root"]/div/div/div[2]/div[1]/div/div/p/form/fieldset/div[1]/span/div[1]/span/span[1]/span',278 # condition dropdown279 '//*[@id="overlap-manager-root"]/div/div/div[2]/div[1]/div/div/p/form/fieldset/div[1]/span/div[1]/span/span[2]/span/span/span[6]/span',280 # select Lux Algo281 '//*[@id="overlap-manager-root"]/div/div/div[2]/div[1]/div/div/p/form/fieldset/div[2]/span/span/span[3]',282 # select type of signal283 ]284 else:285 click_chain = [286 '//*[@id="header-toolbar-intervals"]/div[2]', # select 1m chart287 '//*[@id="header-toolbar-alerts"]', # alert menu288 '//*[@id="overlap-manager-root"]/div/div/div[2]/div[1]/div/div/p/form/fieldset/div[1]/span/div[1]/span/span[1]/span',289 # condition dropdown290 '//*[@id="overlap-manager-root"]/div/div/div[2]/div[1]/div/div/p/form/fieldset/div[1]/span/div[1]/span/span[2]/span/span/span[6]/span',291 # select Lux Algo292 '//*[@id="overlap-manager-root"]/div/div/div[2]/div[1]/div/div/p/form/fieldset/div[2]/span/span/span[3]',293 # select type of signal294 ]295 if signal_type == 'Any Confirmation Sell':296 click_chain.append(297 '//*[@id="overlap-manager-root"]/div/div/div[2]/div[1]/div/div/p/form/fieldset/div[2]/span/span/span[2]/span/span/span[4]/span') # any confirmation buy click298 elif signal_type == 'Any Confirmation Buy':299 click_chain.append(300 '//*[@id="overlap-manager-root"]/div/div/div[2]/div[1]/div/div/p/form/fieldset/div[2]/span/span/span[2]/span/span/span[3]/span') # any confirmation buy click301 click_chain.append(302 '//*[@id="overlap-manager-root"]/div/div/div[2]/div[1]/div/div/p/form/fieldset/span[1]/span/span/div[2]/div[1]/div')303 # select once per bar close304 perform_click_chain_by_xpath(self.driver, click_chain)305 desc_input = WebDriverWait(self.driver, 3).until(306 EC.presence_of_element_located((By.CSS_SELECTOR, 'textarea[name="description"]')))307 desc_input.location_once_scrolled_into_view308 desc_input.clear()309 set_text = '{"symbol":"' + ticker + '","direction":"' + extra_text + '"}'310 desc_input.send_keys(set_text)311 WebDriverWait(self.driver, 2).until(312 EC.presence_of_element_located((By.XPATH, '//*[@id="overlap-manager-root"]/div/div/div[3]/div[2]'))).click()313 @wait314 def set_lux_oscillator_alert(self, ticker, moving_type, percent, extra_text):315 click_chain = [316 '//*[@id="header-toolbar-intervals"]/div[2]', # select 1m chart317 '//*[@id="header-toolbar-alerts"]', # alert menu318 '//*[@id="overlap-manager-root"]/div/div/div[2]/div[1]/div/div/p/form/fieldset/div[1]/span/div[1]/span/span[1]/span',319 # condition dropdown320 '//*[@id="overlap-manager-root"]/div/div/div[2]/div[1]/div/div/p/form/fieldset/div[1]/span/div[1]/span/span[2]/span/span/span[7]',321 # select Lux Oscillator322 '//*[@id="overlap-manager-root"]/div/div/div[2]/div[1]/div/div/p/form/fieldset/div[2]/span/span/span[3]'323 # select type of signal324 ]325 if moving_type == 'Moving Down %':326 click_chain.append(327 '//*[@id="overlap-manager-root"]/div/div/div[2]/div[1]/div/div/p/form/fieldset/div[2]/span/span/span[2]/span/span/span[20]')328 # select Moving down %329 elif moving_type == 'Moving Up %':330 click_chain.append(331 '//*[@id="overlap-manager-root"]/div/div/div[2]/div[1]/div/div/p/form/fieldset/div[2]/span/span/span[2]/span/span/span[19]')332 # select Moving up %333 click_chain.append(334 '//*[@id="overlap-manager-root"]/div/div/div[2]/div[1]/div/div/p/form/fieldset/div[1]/span/div[2]/span/span[3]')335 # select Conf dropdown336 click_chain.append(337 '//*[@id="overlap-manager-root"]/div/div/div[2]/div[1]/div/div/p/form/fieldset/div[1]/span/div[2]/span/span[2]/span/span/span[20]')338 # select Legacy Main339 click_chain.append(340 '//*[@id="overlap-manager-root"]/div/div/div[2]/div[1]/div/div/p/form/fieldset/span[1]/span/span/div[2]/div[1]/div') # select Legacy Main341 # select once per bar close342 perform_click_chain_by_xpath(self.driver, click_chain)343 # Edit moving value344 moving_val_e = WebDriverWait(self.driver, 10).until(345 EC.presence_of_element_located((By.CSS_SELECTOR, 'input[name="moving-value"]')))346 moving_val_e.send_keys(Keys.CONTROL + "a")347 moving_val_e.send_keys(Keys.DELETE)348 moving_val_e.send_keys(percent)349 # Edit moving period350 moving_period_e = WebDriverWait(self.driver, 10).until(351 EC.presence_of_element_located((By.CSS_SELECTOR, 'input[name="moving-period"]')))352 moving_period_e.send_keys(Keys.CONTROL + "a")353 moving_period_e.send_keys(Keys.DELETE)354 moving_period_e.send_keys("2")355 desc_input = WebDriverWait(self.driver, 3).until(356 EC.presence_of_element_located((By.CSS_SELECTOR, 'textarea[name="description"]')))357 desc_input.location_once_scrolled_into_view358 desc_input.clear()359 set_text = '{"symbol":"' + ticker + '","direction":"' + extra_text + '"}'360 desc_input.send_keys(set_text)361 WebDriverWait(self.driver, 2).until(362 EC.presence_of_element_located((By.XPATH, '//*[@id="overlap-manager-root"]/div/div/div[3]/div[2]'))).click()363 @wait364 def set_ppsignal_slope(self, ticker, extra_text='Buy 3'):365 click_chain = [366 '//*[@id="header-toolbar-intervals"]/div[2]', # select 1m chart367 '//*[@id="header-toolbar-alerts"]', # alert menu368 '//*[@id="overlap-manager-root"]/div/div/div[2]/div[1]/div/div/p/form/fieldset/div[1]/span/div[1]/span/span[1]/span',369 # condition dropdown370 '//*[@id="overlap-manager-root"]/div/div/div[2]/div[1]/div/div/p/form/fieldset/div[1]/span/div[1]/span/span[2]/span/span/span[1]',371 # select Heiken Ashi372 '//*[@id="overlap-manager-root"]/div/div/div[2]/div[1]/div/div/p/form/fieldset/div[2]/span/span/span[3]',373 # Select Condition Dropdown374 '//*[@id="overlap-manager-root"]/div/div/div[2]/div[1]/div/div/p/form/fieldset/div[2]/span/span/span[2]/span/span/span[4]',375 # Select Greater Than376 '//*[@id="overlap-manager-root"]/div/div/div[2]/div[1]/div/div/p/form/fieldset/div[3]/span/div[1]/span/span[3]',377 # Select Condition dropdown378 '//*[@id="overlap-manager-root"]/div/div/div[2]/div[1]/div/div/p/form/fieldset/div[3]/span/div[1]/span/span[2]/span/span/span[4]',379 # Select PpSignal Slope380 '//*[@id="overlap-manager-root"]/div/div/div[2]/div[1]/div/div/p/form/fieldset/span[1]/span/span/div[2]/div[1]',381 # select once per bar close382 ]383 perform_click_chain_by_xpath(self.driver, click_chain)384 desc_input = WebDriverWait(self.driver, 3).until(385 EC.presence_of_element_located((By.CSS_SELECTOR, 'textarea[name="description"]')))386 desc_input.location_once_scrolled_into_view387 desc_input.clear()388 set_text = '{"symbol":"' + ticker + '","direction":"' + extra_text + '"}'389 desc_input.send_keys(set_text)390 WebDriverWait(self.driver, 2).until(391 EC.presence_of_element_located((By.XPATH, '//*[@id="overlap-manager-root"]/div/div/div[3]/div[2]'))).click()392 @wait393 def set_9_ma_alert(self, ticker, extra_text='Sell 2'):394 click_chain = [395 '//*[@id="header-toolbar-intervals"]/div[2]', # select 1m chart396 '//*[@id="header-toolbar-alerts"]', # alert menu397 '//*[@id="overlap-manager-root"]/div/div/div[2]/div[1]/div/div/p/form/fieldset/div[1]/span/div[1]/span/span[1]/span',398 # condition dropdown399 '//*[@id="overlap-manager-root"]/div/div/div[2]/div[1]/div/div/p/form/fieldset/div[1]/span/div[1]/span/span[2]/span/span/span[5]/span',400 # select MA 9401 '//*[@id="overlap-manager-root"]/div/div/div[2]/div[1]/div/div/p/form/fieldset/div[2]/span/span/span[3]',402 # select type of signal403 '//*[@id="overlap-manager-root"]/div/div/div[2]/div[1]/div/div/p/form/fieldset/div[2]/span/span/span[2]/span/span/span[12]/span',404 # select Moving up %405 '//*[@id="overlap-manager-root"]/div/div/div[2]/div[1]/div/div/p/form/fieldset/span[1]/span/span/div[2]/div[1]/div',406 # select once per bar close407 ]408 perform_click_chain_by_xpath(self.driver, click_chain)409 # Edit moving value410 moving_val_e = WebDriverWait(self.driver, 10).until(411 EC.presence_of_element_located((By.CSS_SELECTOR, 'input[name="moving-value"]')))412 moving_val_e.send_keys(Keys.CONTROL + "a")413 moving_val_e.send_keys(Keys.DELETE)414 moving_val_e.send_keys("0.03")415 # Edit moving period416 moving_period_e = WebDriverWait(self.driver, 10).until(417 EC.presence_of_element_located((By.CSS_SELECTOR, 'input[name="moving-period"]')))418 moving_period_e.send_keys(Keys.CONTROL + "a")419 moving_period_e.send_keys(Keys.DELETE)420 moving_period_e.send_keys("2")421 desc_input = WebDriverWait(self.driver, 3).until(422 EC.presence_of_element_located((By.CSS_SELECTOR, 'textarea[name="description"]')))423 # desc_input.location_once_scrolled_into_view424 desc_input.clear()425 set_text = '{"symbol":"' + ticker + '","direction":"' + extra_text + '"}'426 desc_input.send_keys(set_text)427 WebDriverWait(self.driver, 2).until(428 EC.presence_of_element_located((By.XPATH, '//*[@id="overlap-manager-root"]/div/div/div[3]/div[2]'))).click()429 time.sleep(30)430 def close_alerts(self):431 try:432 WebDriverWait(self.driver, 10).until(433 EC.presence_of_element_located((By.XPATH, '//*[@id="overlap-manager-root"]/div/div/div[3]'))).click()434 except:435 pass436 def check_exit_end_of_day(self):437 now = datetime.now()438 print("date now", now)439 end_of_day = (datetime.strptime(self.start_time_date, "%Y-%m-%d") + timedelta(days=1)).strftime("%Y-%m-%d")440 if now.strftime("%Y-%m-%d %H:%M") >= end_of_day + " 09:30":441 self.init_driver()442 self.delete_all_alerts()443 self.current_alert_list = []444 self.driver.close()445 return True446 return False447 def main_part(self):448 pos_tuple = self.get_top_symbols()449 self.init_driver()450 self.delete_all_alerts()451 for s in pos_tuple:452 try:453 current_time = datetime.now(timezone(TIMEZONE)).strftime("%H:%M")454 if self.start_time > self.end_time:455 if self.end_time < current_time < self.start_time:456 return457 else:458 if self.start_time > current_time or current_time > self.end_time:459 return460 self.change_ticker(s)461 self.set_lux_algo_alert(s, signal_type='Any Confirmation Buy', extra_text='Buy 1')462 self.set_lux_oscillator_alert(s, 'Moving Up %', '0.03', 'Buy 2')463 self.set_ppsignal_slope(s, 'Buy 3')464 self.set_lux_algo_alert(s, 'Any Confirmation Sell', 'Sell 1')465 self.set_lux_oscillator_alert(s, 'Moving Down %', '0.02', 'Sell 2')466 # self.set_9_ma_alert(s, extra_text='Sell 2')467 time.sleep(1)468 except Exception as e:469 print(e)470 continue471 self.driver.close()472 def run(self):473 print("Starting TradeBot...")474 start_flag = 1475 while True:476 try:477 current_time = datetime.now(timezone(TIMEZONE))478 print(self.start_time, self.end_time, current_time.strftime("%H:%M"))479 if self.start_time > self.end_time:480 if (current_time.strftime("%H:%M") > self.start_time) or (481 current_time.strftime("%H:%M") < self.end_time):482 try:483 self.main_part()484 start_flag = 0485 except Exception as e:486 print(e)487 else:488 if start_flag == 0:489 try:490 print("finish day")491 self.init_driver()492 self.delete_all_alerts()493 self.driver.close()494 start_flag = 1495 except Exception as e:496 print(e)497 else:498 if self.start_time <= current_time.strftime("%H:%M") <= self.end_time:499 try:500 self.main_part()501 start_flag = 0502 except Exception as e:503 print(e)504 else:505 if start_flag == 0:506 try:507 print("finish day")508 self.init_driver()509 self.delete_all_alerts()510 self.driver.close()511 start_flag = 1512 except Exception as e:513 print(e)514 except Exception as e:515 print(e)516 time.sleep(30 * 60)517 def stop(self):518 self.terminate()519class MailCron(QThread):520 def __init__(self, td_session, username, password, start_time, end_time, total_assets, max_positions, parent=None):521 QThread.__init__(self, parent)522 self.td_session = td_session523 self.username = username524 self.password = password525 self.start_time = start_time526 self.end_time = end_time527 self.total_assets = total_assets528 self.max_position = max_positions529 self.current_portfolio = {}530 self.prev_alerts = {}531 def update_current_portfolio(self, ticker, quant, position):532 obj = {533 ticker: {534 'symbol': ticker,535 'quant': quant,536 'position': position,537 }538 }539 if position == 'long':540 if not self.current_portfolio:541 self.current_portfolio = obj542 else:543 self.current_portfolio.update(obj)544 elif position == 'exit':545 self.current_portfolio.pop(ticker, None)546 def order(self, ticker, action, orderType, quant):547 if action == 'BUY':548 my_order = market_order_json(ticker, quant, 'Buy')549 order_status = self.td_session.place_order(account=ACCOUNT_NUMBER, order=my_order)550 print(' \x1b[6;30;42m' + 'Buy' + '\x1b[0m' + ' Triggered on ' + ticker, "qty:", round(quant))551 if "successfully" in order_status:552 print(' \x1b[6;30;42m' + 'Buy' + '\x1b[0m' + ' Triggered on ' + ticker, "qty:", round(quant))553 return True554 elif action == 'SELL':555 my_order = market_order_json(ticker, quant, 'Sell')556 order_status = self.td_session.place_order(account=ACCOUNT_NUMBER, order=my_order)557 print(' \x1b[6;30;41m' + 'Sell' + '\x1b[0m' + ' Triggered on ' + ticker, "qty:", round(quant))558 if "successfully" in order_status:559 print(' \x1b[6;30;41m' + 'Sell' + '\x1b[0m' + ' Triggered on ' + ticker, "qty:", round(quant))560 return True561 return False562 def calculate_lot(self, ticker):563 stock_quote = self.td_session.get_quotes(instruments=[ticker])564 mark_price = float(stock_quote[ticker]['lastPrice'])565 return round(self.total_assets / mark_price)566 def exit_all_orders(self):567 try:568 orders_query = self.td_session.get_orders_query(account=ACCOUNT_NUMBER, status='FILLED')569 for ticker, value in orders_query.items():570 qty = round(float(value['quantity']))571 if qty > 0:572 my_order = market_order_json(ticker, qty, 'Sell')573 order_status = self.td_session.place_order(account=ACCOUNT_NUMBER, order=my_order)574 if "successfully" in order_status:575 print(' \x1b[6;30;41m' + 'Sell' + '\x1b[0m' + ' Triggered on ' + ticker, "qty:", qty)576 self.current_portfolio.clear()577 except Exception as e:578 print(e)579 def save_alerts(self, signal, ticker, ts):580 if ticker in self.prev_alerts:581 if 'Buy 1' in signal:582 if 'time1' in self.prev_alerts[ticker]:583 if ts >= self.prev_alerts[ticker]['time1']:584 self.prev_alerts[ticker]['time1'] = ts585 else:586 self.prev_alerts[ticker]['time1'] = ts587 if 'Buy 2' in signal:588 if 'time2' in self.prev_alerts[ticker]:589 if ts >= self.prev_alerts[ticker]['time2']:590 self.prev_alerts[ticker]['time2'] = ts591 else:592 self.prev_alerts[ticker]['time2'] = ts593 if 'Buy 3' in signal:594 if 'time3' in self.prev_alerts[ticker]:595 if ts >= self.prev_alerts[ticker]['time3']:596 self.prev_alerts[ticker]['time3'] = ts597 else:598 self.prev_alerts[ticker]['time3'] = ts599 else:600 self.prev_alerts[ticker] = {}601 if 'Buy 1' in signal:602 self.prev_alerts[ticker]['time1'] = ts603 if 'Buy 2' in signal:604 self.prev_alerts[ticker]['time2'] = ts605 if 'Buy 3' in signal:606 self.prev_alerts[ticker]['time3'] = ts607 def check_long_condition(self, total_signals):608 for ticker, content in total_signals.items():609 if 'Buy 1' in content and 'Buy 2' in content and 'Buy 3' in content:610 current_time = datetime.now(timezone(TIMEZONE)).strftime("%Y-%m-%d %H:%M:%S")611 save_data("alert_log.txt", current_time + " : " + ticker + " : " + str(content))612 if len(self.current_portfolio) < self.max_position:613 print("len position", len(self.current_portfolio), "max position", self.max_position)614 if not ticker in self.current_portfolio:615 quant = self.calculate_lot(ticker)616 print("Buying", ticker)617 # Order618 order_result = self.order(ticker, action='BUY', orderType='MKT', quant=quant)619 if order_result:620 self.update_current_portfolio(ticker, quant, position='long')621 def check_exit_long_condition(self, total_signals):622 for ticker, content in total_signals.items():623 if 'Sell 2' in content or 'Sell 1' in content:624 if len(self.current_portfolio) > 0:625 if ticker in self.current_portfolio:626 current_time = datetime.now(timezone(TIMEZONE)).strftime("%Y-%m-%d %H:%M:%S")627 save_data("alert_log.txt", current_time + " : " + ticker + " : " + str(content))628 quant = abs(float(self.current_portfolio[ticker]['quant']))629 print("Exiting long", ticker)630 order_result = self.order(ticker, action='SELL', orderType='MKT', quant=quant)631 if order_result:632 self.update_current_portfolio(ticker, quant, position='exit')633 def readmail(self):634 total_buy_signals = {}635 total_sell_signals = {}636 start_time = (datetime.now(timezone(TIMEZONE)) - timedelta(minutes=1)).strftime("%Y-%m-%d %H:%M:%S")637 end_time = datetime.now(timezone(TIMEZONE)).strftime("%Y-%m-%d %H:%M:%S")638 sell_start_time = (datetime.now(timezone(TIMEZONE)) - timedelta(seconds=5)).strftime("%Y-%m-%d %H:%M:%S")639 context = {'start_time': start_time, 'end_time': end_time}640 x = requests.post(HOST_URL + '/get_ib_signal/', data=context)641 json_data = json.loads(x.content)642 if json_data['result'] == 'ok':643 payload = json_data['payload']644 for item in payload:645 date_time = item.split(',')[0][9:]646 symbol = item.split(',')[1].split(':')[1]647 signal = item.split(',')[2].split(':')[1]648 if not symbol in total_buy_signals:649 total_buy_signals[symbol] = []650 total_buy_signals[symbol].append(signal)651 else:652 total_buy_signals[symbol].append(signal)653 if sell_start_time <= date_time <= end_time:654 if not symbol in total_sell_signals:655 total_sell_signals[symbol] = []656 total_sell_signals[symbol].append(signal)657 else:658 total_sell_signals[symbol].append(signal)659 print("Entering trades")660 self.check_long_condition(total_buy_signals)661 print("Finish checking long condition")662 self.check_exit_long_condition(total_sell_signals)663 print("Finish checking short condition")664 def run(self):665 print("Starting MailCron...")666 start_flag = 1667 while True:668 current_time = datetime.now(timezone(TIMEZONE))669 if self.start_time > self.end_time:670 if (current_time.strftime("%H:%M") > self.start_time) or (671 current_time.strftime("%H-%M") < self.end_time):672 print(start_flag)673 if start_flag == 1:674 self.td_session.login()675 self.exit_all_orders()676 self.readmail()677 start_flag = 0678 else:679 if start_flag == 0:680 print("finish day")681 self.exit_all_orders()682 start_flag = 1683 else:684 if self.start_time <= current_time.strftime("%H:%M") <= self.end_time:685 if start_flag == 1:686 self.td_session.login()687 self.exit_all_orders()688 print('Reading mail')689 self.readmail()690 start_flag = 0691 else:692 if start_flag == 0:693 print("finish day")694 self.exit_all_orders()695 start_flag = 1696 time.sleep(1)697 def stop(self):698 self.terminate()699class MessageBox(QWidget):700 countChanged = pyqtSignal(str)701 def __init__(self, message):702 self.message = message703 super(MessageBox, self).__init__()704 self.setGeometry(850, 600, 320, 222)705 self.setWindowFlags(Qt.FramelessWindowHint)706 self.setAttribute(Qt.WA_TranslucentBackground)707 self.backgroundLabel = QLabel(self)708 self.backgroundLabel.setGeometry(0, 0, 320, 222)709 self.backgroundLabel.setStyleSheet("background-image : url(messagebox.png); background-repeat: no-repeat;")710 self.messageContent = QLabel(self)711 self.messageContent.setText(self.message)712 self.messageContent.setGeometry(34, 82, 280, 40)713 self.messageContent.setStyleSheet("color:white; font-size:16px;")714 self.saveButton = QPushButton(self)715 self.saveButton.setText("Ok")716 self.saveButton.setGeometry(120, 144, 100, 40)717 self.saveButton.clicked.connect(self.OnClose)718 self.saveButton.setStyleSheet("background:#21ce99; border-radius:8px;color:white; font-size:18px; ")719 self.closeBtn = QPushButton(self)720 self.closeBtn.setGeometry(295, 5, 20, 20)721 self.closeBtn.setStyleSheet("background-image : url(close3.png);background-color: transparent; ")722 self.closeBtn.clicked.connect(self.OnClose)723 def OnClose(self):724 self.close()725 def mousePressEvent(self, event):726 if event.button() == Qt.LeftButton:727 self.offset = event.pos()728 else:729 super().mousePressEvent(event)730 def mouseMoveEvent(self, event):731 if self.offset is not None and event.buttons() == Qt.LeftButton:732 self.move(self.pos() + event.pos() - self.offset)733 else:734 super().mouseMoveEvent(event)735 def mouseReleaseEvent(self, event):736 self.offset = None737 super().mouseReleaseEvent(event)738class SecondWindow(QWidget):739 countChanged = pyqtSignal(str)740 def __init__(self, value, data):741 self.data = data742 super(SecondWindow, self).__init__()743 self.header_text = value744 self.setFixedSize(380, 200)745 self.setWindowFlags(Qt.FramelessWindowHint)746 self.setStyleSheet("background:#19181f;")747 self.titleText = QTextEdit(self)748 self.titleText.setText(self.header_text)749 self.titleText.setGeometry(20, 30, 340, 60)750 self.titleText.setStyleSheet("color:white; font-size:16px;border:none;")751 self.RequestCodeEdit = QLineEdit(self)752 self.RequestCodeEdit.setStyleSheet("background:#24202a; color:white; font-size:16px;")753 self.RequestCodeEdit.setGeometry(20, 70, 340, 30)754 self.confirmButton = QPushButton(self)755 self.confirmButton.setText("Confirm")756 self.confirmButton.setGeometry(110, 130, 160, 40)757 self.confirmButton.clicked.connect(self.OnShow)758 self.confirmButton.setStyleSheet("background:#21ce99; border-radius:8px;color:white; font-size:16px;")759 print(self.data)760 def mousePressEvent(self, event):761 if event.button() == Qt.LeftButton:762 self.offset = event.pos()763 else:764 super().mousePressEvent(event)765 def mouseMoveEvent(self, event):766 if self.offset is not None and event.buttons() == Qt.LeftButton:767 self.move(self.pos() + event.pos() - self.offset)768 else:769 super().mouseMoveEvent(event)770 def mouseReleaseEvent(self, event):771 self.offset = None772 super().mouseReleaseEvent(event)773class MainWindow(QWidget):774 start_flag = 1775 def __init__(self):776 super(MainWindow, self).__init__()777 self.setGeometry(250, 50, 716, 458)778 self.setWindowFlags(Qt.FramelessWindowHint)779 self.setAttribute(Qt.WA_TranslucentBackground)780 self.setWindowTitle("Robinhood Bot Panel")781 self.username = "e.paulson95@hotmail.com"782 self.password = "ExecutorEA2021$"783 self.backgroundLabel = QLabel(self)784 self.backgroundLabel.setGeometry(0, 0, 716, 458)785 self.backgroundLabel.setStyleSheet(786 "background-image : url(" + SOURCE_FOLDER + "Robinhood_bot2.png); background-repeat: no-repeat;")787 font = QFont()788 font.setPointSize(20)789 self.closeBtn = QPushButton(self)790 self.closeBtn.setGeometry(680, 10, 29, 29)791 self.closeBtn.setStyleSheet(792 "background-image : url(" + SOURCE_FOLDER + "close2.png);background-color: transparent;")793 self.closeBtn.clicked.connect(self.onClose)794 self.startBtn = QPushButton(self)795 self.startBtn.setGeometry(444, 18, 216, 60)796 self.startBtn.setText("Start")797 self.startBtn.setStyleSheet("background-color: #21ce99; border-radius: 18px; color:white; font-size:24px;")798 self.startBtn.clicked.connect(self.onStart)799 self.usernameEdit = QLineEdit(self)800 self.usernameEdit.setStyleSheet(801 "background-color: transparent; border-radius: 15px; color:white; font-size:16px;")802 self.usernameEdit.setGeometry(144, 117, 180, 24)803 self.usernameEdit.setText(self.username)804 self.visibleIcon = QIcon(SOURCE_FOLDER + "eye.svg")805 self.hiddenIcon = QIcon(SOURCE_FOLDER + "hidden.svg")806 self.passwordEdit = QLineEdit(self)807 self.passwordEdit.setStyleSheet(808 "background-color: transparent; border-radius: 15px; color:white; font-size:16px;")809 self.passwordEdit.setGeometry(519, 117, 159, 24)810 self.passwordEdit.setText(self.password)811 self.passwordEdit.setEchoMode(QLineEdit.Password)812 self.passwordEdit.togglepasswordAction = self.passwordEdit.addAction(813 self.visibleIcon,814 QLineEdit.TrailingPosition815 )816 # self.password.setText(robin_pass)817 self.password_shown = False818 self.passwordEdit.togglepasswordAction.triggered.connect(self.on_toggle_password_Action)819 self.totalAssetsLabel = QLabel(self)820 self.totalAssetsLabel.setStyleSheet(821 "background-color: transparent; border-radius: 6px; color:white; font-size:18px;")822 self.totalAssetsLabel.setGeometry(20, 240, 120, 30)823 self.totalAssetsLabel.setText("Total Assets:")824 self.totalAssetsLabel.setAlignment(Qt.AlignRight)825 self.totalAssetsEdit = QLineEdit(self)826 self.totalAssetsEdit.setStyleSheet(827 "background-color: #343438; border-radius: 6px; color:white; font-size:18px;")828 self.totalAssetsEdit.setGeometry(150, 240, 130, 30)829 self.totalAssetsEdit.setText("5000")830 self.totalAssetsEdit.setAlignment(Qt.AlignCenter)831 self.maxPositionLabel = QLabel(self)832 self.maxPositionLabel.setStyleSheet(833 "background-color: transparent; border-radius: 6px; color:white; font-size:18px;")834 self.maxPositionLabel.setGeometry(20, 285, 120, 30)835 self.maxPositionLabel.setText("Max Positions:")836 self.maxPositionLabel.setAlignment(Qt.AlignRight)837 self.maxPositionEdit = QLineEdit(self)838 self.maxPositionEdit.setStyleSheet(839 "background-color: #343438; border-radius: 6px; color:white; font-size:18px;")840 self.maxPositionEdit.setGeometry(150, 285, 130, 30)841 self.maxPositionEdit.setText("5")842 self.maxPositionEdit.setAlignment(Qt.AlignCenter)843 self.trailingStopPercentLabel = QLabel(self)844 self.trailingStopPercentLabel.setStyleSheet(845 "background-color: transparent; border-radius: 6px; color:white; font-size:18px;")846 self.trailingStopPercentLabel.setGeometry(20, 330, 120, 30)847 self.trailingStopPercentLabel.setText("Trail Stop(%):")848 self.trailingStopPercentLabel.setAlignment(Qt.AlignRight)849 self.trailingStopPercentEdit = QLineEdit(self)850 self.trailingStopPercentEdit.setStyleSheet(851 "background-color: #343438; border-radius: 6px; color:white; font-size:18px;")852 self.trailingStopPercentEdit.setGeometry(150, 330, 130, 30)853 self.trailingStopPercentEdit.setText("5")854 self.trailingStopPercentEdit.setAlignment(Qt.AlignCenter)855 self.startTimeLabel = QLabel(self)856 self.startTimeLabel.setStyleSheet(857 "background-color: transparent; border-radius: 6px; color:white; font-size:18px;")858 self.startTimeLabel.setGeometry(420, 240, 170, 30)859 self.startTimeLabel.setText("Start Time:")860 self.startTimeLabel.setAlignment(Qt.AlignCenter)861 self.startTimeEdit = QLineEdit(self)862 self.startTimeEdit.setStyleSheet(863 "background-color: #343438; border-radius: 6px; color:white; font-size:18px;")864 self.startTimeEdit.setGeometry(560, 240, 130, 30)865 self.startTimeEdit.setText("09:00")866 self.startTimeEdit.setAlignment(Qt.AlignCenter)867 self.endTimeLabel = QLabel(self)868 self.endTimeLabel.setStyleSheet(869 "background-color: transparent; border-radius: 6px; color:white; font-size:18px;")870 self.endTimeLabel.setGeometry(420, 285, 170, 30)871 self.endTimeLabel.setText("Edit Time:")872 self.endTimeLabel.setAlignment(Qt.AlignCenter)873 self.endTimeEdit = QLineEdit(self)874 self.endTimeEdit.setStyleSheet(875 "background-color: #343438; border-radius: 6px; color:white; font-size:18px;")876 self.endTimeEdit.setGeometry(560, 285, 130, 30)877 self.endTimeEdit.setText("15:40")878 self.endTimeEdit.setAlignment(Qt.AlignCenter)879 def on_toggle_password_Action(self):880 if not self.password_shown:881 self.passwordEdit.setEchoMode(QLineEdit.Normal)882 self.password_shown = True883 self.passwordEdit.togglepasswordAction.setIcon(self.hiddenIcon)884 else:885 self.passwordEdit.setEchoMode(QLineEdit.Password)886 self.password_shown = False887 self.passwordEdit.togglepasswordAction.setIcon(self.visibleIcon)888 def onStart(self):889 global account_type890 if self.start_flag == 1:891 self.username = self.usernameEdit.text()892 self.password = self.passwordEdit.text()893 if self.username != '' and self.password != '':894 try:895 self.td_session = TDClient(account_number=ACCOUNT_NUMBER,896 account_password=ACCOUNT_PASSWORD,897 consumer_id=CONSUMER_ID,898 redirect_uri=REDIRECT_URI)899 if self.td_session.login():900 self.startBtn.setText("Stop")901 self.bot = TradeBot(self.startTimeEdit.text(),902 self.endTimeEdit.text())903 self.mail_bot = MailCron(self.td_session,904 self.username,905 self.startTimeEdit.text(),906 self.endTimeEdit.text(),907 float(self.totalAssetsEdit.text()),908 int(self.maxPositionEdit.text()))909 self.bot.start()910 self.mail_bot.start()911 self.start_flag = 0912 else:913 self.TW = MessageBox("Login Failed Try again!")914 self.TW.show()915 except Exception as e:916 print(e)917 else:918 try:919 if self.username == '':920 self.TW = MessageBox("Please enter your email!")921 self.TW.show()922 else:923 self.TW = MessageBox("Please enter your Password!")924 self.TW.show()925 except Exception as e:926 print(e)927 else:928 self.startBtn.setText("Start")929 self.start_flag = 1930 self.bot.stop()931 # self.mail_bot.stop()932 def onClose(self):933 try:934 global app935 if self.start_flag == 0:936 self.start_flag = 1937 self.bot.stop()938 self.mail_bot.stop()939 app.quit()940 except Exception as e:941 print(e)942 def OrderUpdate(self, value):943 print(value)944 if value == 'success':945 self.startBtn.setText("Stop")946 self.bot = TradeBot(self.startTimeEdit.text(),947 self.endTimeEdit.text())948 self.mail_bot = MailCron(self.td_session,949 self.startTimeEdit.text(),950 self.endTimeEdit.text(),951 float(self.totalAssetsEdit.text()),952 int(self.maxPositionEdit.text()))953 self.bot.start()954 self.mail_bot.start()955 self.start_flag = 0956 def mousePressEvent(self, event):957 if event.button() == Qt.LeftButton:958 self.offset = event.pos()959 else:960 super().mousePressEvent(event)961 def mouseMoveEvent(self, event):962 if self.offset is not None and event.buttons() == Qt.LeftButton:963 self.move(self.pos() + event.pos() - self.offset)964 else:965 super().mouseMoveEvent(event)966 def mouseReleaseEvent(self, event):967 self.offset = None968 super().mouseReleaseEvent(event)969 def onProcess(self, perfomance):970 self.listwidget.addItem(perfomance)971if __name__ == '__main__':972 import sys973 global app974 app = QApplication(sys.argv)975 MW = MainWindow()976 MW.show()...
mag_test.py
Source:mag_test.py
...96 # - items are deleted from minicart.97 # Navigate to product98 self.get(self.base_url)99 self.hover_and_click(MainPage.women, MainPage.women_tops)100 self.click_chain([Catalog.category, Catalog.jackets], spacing=0.5)101 self.click_nth_visible_element(Catalog.product_item, 3)102 # Add product to cart103 self.click_chain([Catalog.size_option_xs,104 Catalog.color_option_first,105 Catalog.add_to_cart],106 spacing=0.5)107 # Inspect minicart108 self.scroll_to(MainPage.show_cart)109 self.wait_for_element(Cart.is_upgraded)110 self.click(MainPage.show_cart)111 price_one_piece = self.get_text(Cart.subtotal)112 # Update order in minicart113 self.find_element(Cart.quantity).send_keys(Keys.BACKSPACE)114 self.update_text(Cart.quantity, '2\n')115 self.click(Cart.update)116 self.wait_for_text('2', Cart.number_of_items)117 price_two_pieces = self.get_text(Cart.subtotal)118 # Assert order is updated119 self.assert_equal(120 float(price_two_pieces[1:-1]),121 float(price_one_piece[1:]) * 2)122 # Delete order123 self.click_chain([Cart.delete, Cart.confirm], spacing=0.5)124 self.assert_text_visible('You have no items in your shopping cart.')125 @pytest.mark.checkout_demo_user126 def test_checkout_demo_user(self):127 # This test checks that:128 # - item can be added to cart from catalog page;129 # - user can sign in into his account when he starts check-in process;130 # - order can be placed;131 # - placed order information corresponds expected;132 # - order info is retained after log out.133 # Navigate to catalog134 self.get(self.base_url)135 self.hover_and_click(MainPage.gear, MainPage.watches)136 self.click(Catalog.product_item)137 # Get item name138 item_name = self.get_text(Catalog.product_name)139 # Add to cart140 self.click(Catalog.add_to_cart)141 self.click_link_text('shopping cart')142 # Compare item_name with item_in_cart_name143 item_in_cart_name = self.get_text(Cart.product_name)144 self.assert_equal(item_name, item_in_cart_name)145 self.click(Cart.proceed_to_checkout_button)146 # Shipping page147 self.update_text(Checkout.email, 'roni_cost@example.com\n')148 self.update_text(Checkout.password, 'roni_cost3@example.com\n')149 self.wait_for_element(Checkout.shipping_address)150 self.click(Checkout.shipping_method_fixed)151 self.click(Checkout.next_button)152 # Review & Payments page153 order_total = self.get_text(Checkout.order_total)154 self.click(Checkout.place_order)155 self.wait_for_text('Thank you for your purchase!')156 # Inspect order157 order_number = self.get_text(Checkout.order_number_demo)158 self.click(Checkout.order_number_demo)159 self.assert_equal(item_in_cart_name,160 self.get_text(Checkout.product_name))161 self.assert_equal(self.get_text(Checkout.order_status), 'PENDING')162 self.assert_equal(order_total,163 self.get_text(Checkout.grand_total_price))164 self.click_link_text('Print Order')165 self.driver.switch_to.window(self.driver.window_handles[1])166 self.assert_title('Order # %s' % order_number)167 self.driver.switch_to.window(self.driver.window_handles[0])168 # Sign out169 self.click(MainPage.account_menu)170 self.click_link_text('Sign Out')171 # Sign In and View order172 self.click_partial_link_text('Sign In')173 self.update_text(SignInPage.email_field, 'roni_cost@example.com\n')174 self.update_text(SignInPage.password_field, 'roni_cost3@example.com')175 self.click(SignInPage.sign_in_button)176 self.click_link_text('My Orders')177 self.assert_text(order_number)178 # Sign out179 self.click(MainPage.account_menu)180 self.click_link_text('Sign Out')181 @pytest.mark.checkout_as_guest182 def test_checkout_as_guest(self):183 # This test check that:184 # - customer can place an order as a guest with interruptions185 # - leaving the web shop and returning again to continue;186 # - customer can sign up after order has been placed;187 # - customer can view his order in his account.188 # It is preferrable to run this test method with189 # "--settings_file=custom_settings.py>"190 # because page elements load time may vary.191 # Navigate to catalog192 self.get(self.base_url)193 self.hover_and_click(MainPage.men, MainPage.tops)194 # Go to product page195 self.click(Catalog.product_item_2nd)196 product_price = self.get_text(Catalog.product_price)197 # self._print(product_name)198 # self._print(product_price)199 self.click_chain([Catalog.size_option_xs,200 Catalog.color_option_first],201 spacing=1)202 self.click(Catalog.add_to_cart)203 self.wait_for_element(Cart.is_upgraded)204 self.click_chain([MainPage.show_cart,205 Catalog.minicart_to_checkout],206 spacing=1)207 # Checkout page208 email = random_char(7)+"@1secmail.net"209 self.update_text(Checkout.email, email+"\n")210 self.update_text(Checkout.first_name, 'Willem-Alexander Claus George')211 self.update_text(Checkout.last_name, 'Ferdinand')212 self.update_text(Checkout.street_address_1st_line, 'Noordeinde 64')213 self.update_text(Checkout.city, 'The Hague')214 self.update_text(Checkout.zip_code, '2514 GK')215 self.select_option_by_text(Checkout.country, 'Netherlands')216 self.wait_for_element_not_present(Checkout.flat_shipping_method)217 # Interruption218 self.open('about:blank')219 self.get(self.base_url)220 self.click_chain([MainPage.show_cart,221 Catalog.minicart_to_checkout],222 spacing=1)223 self.update_text(Checkout.state, 'South Holland')224 self.update_text(Checkout.phone_num, '+31976901561')225 self.click(Checkout.next_button)226 # Review & Payments page227 self.wait_for_text('Willem-Alexander Claus George Ferdinand')228 self.assert_equal(product_price, self.get_text(Checkout.price))229 self.assert_element(Checkout.order_summary)230 order_total = self.get_text(Checkout.order_total)231 self.click(Checkout.place_order)232 # After order page233 self.assert_text('Thank you for your purchase!')234 order_number = self.get_text(Checkout.order_number_guest)...
claim_third_step_page.py
Source:claim_third_step_page.py
...68 "35": self._third_step.THIRD_STEP_VOLTAGE_LEVEL_35KV_XPATH,69 "110": self._third_step.THIRD_STEP_VOLTAGE_LEVEL_110KV_XPATH}70 voltage_level = str().join([char for char in str(voltage_level) if char.isdigit()])71 if voltage_level:72 self.click_chain([self._third_step.THIRD_STEP_VOLTAGE_LIST_CSS,73 level_locators[voltage_level]])74 else:75 self.click_chain([self._third_step.THIRD_STEP_VOLTAGE_LIST_CSS,76 level_locators[model.voltage_level]])77 @allure.step78 def _select_reliability_level(self, reliability_level, model):79 required_level_value = str(reliability_level)80 dropdown_list_locator = self._third_step.THIRD_STEP_RELIABILITY_LIST_CSS81 # ÐокаÑоÑÑ Ð´Ð»Ñ ÑÐºÐ°Ð·Ð°Ð½Ð¸Ñ ÐºÐ°ÑегоÑии надежноÑÑи пÑи моÑноÑÑи до 150 кÐÑ82 reliability_level_dropdown_value_locators = {"1": self._third_step.THIRD_STEP_DROPDOWN_RELIABILITY_LEVEL_ONE_XPATH,83 "2": self._third_step.THIRD_STEP_DROPDOWN_RELIABILITY_LEVEL_TWO_XPATH,84 "3": self._third_step.THIRD_STEP_DROPDOWN_RELIABILITY_LEVEL_THREE_XPATH}85 # ÐокаÑоÑÑ Ð´Ð»Ñ ÑÐºÐ°Ð·Ð°Ð½Ð¸Ñ ÐºÐ°ÑегоÑии надежноÑÑи пÑи моÑноÑÑи более 150 кÐÑ86 reliability_level_input_value_locators = {"1": self._third_step.THIRD_STEP_INPUT_RELIABILITY_LEVEL_ONE_CSS,87 "2": self._third_step.THIRD_STEP_INPUT_RELIABILITY_LEVEL_TWO_CSS,88 "3": self._third_step.THIRD_STEP_INPUT_RELIABILITY_LEVEL_THREE_CSS}89 if reliability_level:90 if self.is_element_visible(dropdown_list_locator):91 self.click_chain([dropdown_list_locator,92 reliability_level_dropdown_value_locators[required_level_value]])93 else:94 self.click(reliability_level_input_value_locators[required_level_value])95 else:96 if self.is_element_visible(dropdown_list_locator):97 self.click_chain([dropdown_list_locator,98 reliability_level_dropdown_value_locators[model.reliability_level]])99 else:100 self.click(reliability_level_input_value_locators[model.reliability_level])101 @allure.step102 def _enter_connection_points(self, number_of_points, model):103 epu_points = self._third_step.THIRD_STEP_EPU_POINTS_CSS104 if self.is_element_visible(epu_points):105 if number_of_points:106 self.update_text(epu_points, number_of_points)107 else:108 self.update_text(epu_points, model.connection_points)109 @allure.step110 def _object_readiness_status(self, model):111 if model:...
Learn to execute automation testing from scratch with LambdaTest Learning Hub. Right from setting up the prerequisites to run your first automation test, to following best practices and diving deeper into advanced test scenarios. LambdaTest Learning Hubs compile a list of step-by-step guides to help you be proficient with different test automation frameworks i.e. Selenium, Cypress, TestNG etc.
You could also refer to video tutorials over LambdaTest YouTube channel to get step by step demonstration from industry experts.
Get 100 minutes of automation test minutes FREE!!