Why find_element_by_xpath() taking 3 positional argument? - python

*args unpacks the locators in tuple form.but is my case i have given only two arguments,but it is taking three arguments.Need help to understand.
I am newbie to selenium with python and played around some code from github,
but getting error.
TypeError: find_element_by_xpath() takes 2 positional arguments but 3 were given
locator.py
from selenium.webdriver.common.by import By
class elements(object):
Customer = (By.XPATH, "//button[contains(text(),'Customer')]")
base.py
from selenium import webdriver
from selenium.webdriver.common.by import By
class Page(object):
def __init__(self,driver,url=None):
self.url = url
self.driver = driver
def find_element_with_click(self,*locator):
self.driver.find_element_by_xpath(*locator).click()
pages.py
from selenium import webdriver
from base import Page
from locator import *
class CustomerCreation(Page):
def __init__(self, driver):
self.locator = elements
super().__init__(driver)
def create_customer(self):
self.driver.find_element_with_click(*self.locator.Customer)
testPages.py
import unittest
from selenium import webdriver
from pages import *
from locators import *
from selenium.webdriver.common.by import By
class TestPages(unittest.TestCase):
#classmethod
def setUpClass(cls):
cls.driver = webdriver.Chrome('C:\ChromeDriver\chromedriver')
cls.driver.get("#server")
def test_tes_cust(self):
page = CustomerCreation(self.driver)
res_page = page.create_customer() #Getting issue at this stage
#classmethod
def tearDownClass(cls):
cls.driver.close()
if __name__ == "__main__":
suite = unittest.TestLoader().loadTestsFromTestCase(TestPages)
unittest.TextTestRunner(verbosity=2).run(suite)
The error log:
test_tes_cust (main.TestPages) ... ERROR
======================================================================
ERROR: test_tes_cust (main.TestPages)
----------------------------------------------------------------------
Traceback (most recent call last):
File "testPages.py", line 28, in test_tes_cust
res_page = page.create_customer()
File "C:\Users###\PycharmProjects\basics\pages.py", line 35, in create_customer
self.find_element_with_click(*self.locator.Customer)
File "C:\Users###\PycharmProjects\basics\base.py", line 21, in find_element_with_click
self.driver.find_element_by_xpath(*locator).click()
TypeError: find_element_by_xpath() takes 2 positional arguments but 3 were given

You're passing one extra argument. Your arguments are:
self
By.XPATH
"//button[contains(text(),'Customer')]"
That's what you need to pass to find_element method. While find_element_by_xpath should take two arguments only:
self
"//button[contains(text(),'Customer')]"
So try to update your code as
def find_element_with_click(self,*locator):
self.driver.find_element(*locator).click()
or you need to modify your Customer as:
Customer = "//button[contains(text(),'Customer')]"
and
def find_element_with_click(self, xpath):
self.driver.find_element_by_xpath(xpath).click()

Related

how to use select class and action class in selenium with python in POM framework?

Sorry in advance if this question has been asked before. But I am trying to understand if my select class implementation is accurate?
I am using POM for my testing and I have a class called HomePage() and below is the code
class HomePage():
def __init__(self, driver)
self.driver = driver
self.id_that_i_am_using = 'navDropDown1' #this id for dropdown
self.link_text_path = 'Link Text'
# created function for clicking on DropdoWn and it does
def click_on_drop_down(self):
self.driver.find_element(value=self.id_that_i_am_using).click()
# trying to create function for select class
def select_class(self, select, driver):
select = Select()
self.driver.find_element(value=self.id_that_i_am_using).click()
select.select_by_index(1)
The Error I am getting is below:
TypeError: selec_class() missing 2 required positional arguments: 'select' and 'driver'
here is where I am trying to call my select class:
def test_login_valid(self):
driver = self.driver
driver.get("https:www.google.com")
home_page = HomePage(driver)
home_page.click_on_drop_down()
home_page.select_class()

How to execute methods in a class using Selenium and Python

I recently found the SeleniumIDE extension for Google Chrome, but there is something I don't understand...
from selenium import webdriver
from selenium.webdriver.common.by import By
class TestStealth():
def setup_method(self, method):
print("setup_method")
self.driver = webdriver.Chrome()
self.vars = {}
def teardown_method(self, method):
self.driver.quit()
def test_stealth(self):
print("Testing")
self.driver.get("https://stealthxio.myshopify.com/products/stealthxio-practice")
self.driver.set_window_size(968, 1039)
this is the code I get from selenium, when I try to run with:
run = TestStealth()
run.setup_method()
run.test_stealth()
I get an error in run.setup_method() as:
Missing 1 required positional argument: 'method'
Does anyone know what I am doing wrong?
This error message...
Missing 1 required positional argument: 'method'
...implies that the setup_method() is missing a required positional argument, i.e. 'method'
Analysis
You were pretty close. As per the defination of setup_method(self, method) it expects an argument as method.
def setup_method(self, method):
But when you invoked setup_method() as in:
run.setup_method()
You haven't passed any argument. Hence there was a argument mismatch and you see the error.
Solution
To execute your tests with in the Class using Selenium you can use the following solution:
Code Block:
class TestStealth():
def setup_method(self):
print("setup_method")
self.driver = webdriver.Chrome(executable_path=r'C:\WebDrivers\chromedriver.exe')
self.vars = {}
def teardown_method(self):
self.driver.quit()
def test_stealth(self):
print("Testing")
self.driver.get("https://stealthxio.myshopify.com/products/stealthxio-practice")
self.driver.set_window_size(968, 1039)
run = TestStealth()
run.setup_method()
run.test_stealth()
Console Output:
setup_method
DevTools listening on ws://127.0.0.1:51558/devtools/browser/88bf2c58-10da-4b03-9697-eec415197e66
Testing
Browser Snapshot:

fixture 'self' not found

I'm new with Pytest-bdd. I'm trying to run a BDD test but I find always the same problem with the fixture. This is my code.I've tried without the #pytest.fixture and with only the step of #given gherkin step I get same result. fixture 'self'not found
import os
from appium import webdriver
from time import sleep
import pytest
from pytest_bdd import scenario, given, when, then, parsers
#pytest.fixture(autouse=True, scope='module')
def Setup (self):
"Setup for the test"
desired_caps = {}
self.driver = webdriver.Remote('http://0.0.0.0:4723/wd/hub', desired_caps)
def Teardown():
self.driver.quit()
#scenario('features.feature','Prueba1')
#given('step 1')
def test_single_player_mode(self):
element1=self.driver.find_element_by_id("com.nestle.bagzielicious.beta:id/on_button_vegan")
element1.click()
sleep(1)
Usually those methods are all inside a class and then self refers to the class.
For example:
from unittest import TestCase
class DriverTestCase(TestCase):
Give the following code a try using Pytest:
import os
from appium import webdriver
from time import sleep
import pytest
from pytest_bdd import scenario, given, when, then, parsers
#pytest.fixture(autouse=True, scope='module')
def driver():
"Setup for the test"
desired_caps = {}
driver = webdriver.Remote('http://0.0.0.0:4723/wd/hub', desired_caps)
yield driver
driver.quit()
#scenario('features.feature','Prueba1')
#given('step 1')
def test_single_player_mode(driver):
element1=driver.find_element_by_id("com.nestle.bagzielicious.beta:id/on_button_vegan")
element1.click()
sleep(1)

Redirect unknown attributes

I'm building a custom class to add feautures to selenium.webdriver.Chrome on Python 3.6.2.
from selenium import webdriver
class MyChrome:
def __init__(self):
self.mydriver = webdriver.Chrome()
So far, beside some custom methods I made myself, I used to overridden some selenium.webdriver.Chrome very standard methods like this:
def get(self, url):
self.mydriver.get(url)
Since I don't want to waste time rewriting like that methods like get, find_element_by_xpath, etc... that already works fine for me I tried the following, as suggested here and here
def __getattr__(self, name, *args, **kwargs):
return getattr(self.mydriver, name)(*args, **kwargs)
But when I run the following code
from selenium import webdriver
class MyChrome:
def __init__(self):
self.mydriver = webdriver.Chrome()
def __getattr__(self, name, *args, **kwargs):
return getattr(self.mydriver, name)(*args, **kwargs)
chrome = MyChrome()
chrome.get('https://stackoverflow.com/')
I encounter the error
Traceback (most recent call last):
File "MyChrome.py", line 11, in <module>
chrome.get('https://stackoverflow.com/')
File "MyChrome.py", line 8, in __getattr__
return getattr(self.mydriver, name)(*args, **kwargs)
TypeError: get() missing 1 required positional argument: 'url'
How do I redirect calls to unknown methods called on my object chrome to it's instance variable self.driver?
I created a custom Webdriver once to add features to selenium Chrome Webdriver and I did that by subclassing selenium Chrome Webdriver. This way you inherit all the webdriver methods without a getattr
from selenium.webdriver import Chrome
class MyChrome(Chrome):
def __init__(self, *args, **kwargs):
super().__init__(*args, **kwargs)
# add all your custom features
It doesn't provide answer to your question but something you can leverage

Pytest TypeError: __init__() got an unexpected keyword argument 'browser'

I try to add pytest_addoption(parser) in my confest.py. Here are the official Pytest docs
But if I try to start test I see
TypeError: __init__() got an unexpected keyword argument 'browser'
Confest.py
import pytest
from fixture.application import Application
__author__ = 'Max'
fixture = None
#pytest.fixture
def app(request):
global fixture
browser = request.config.getoption("--browser")
if fixture is None:
fixture = Application(browser=browser)
else:
if not fixture.is_valid:
fixture = Application(browser=browser)
fixture.session.ensure_login(username="somename", password="somepassword")
return fixture
def pytest_addoption(parser):
# hooks for browsers
parser.addoption("--browser", action="store", default="chrome")
fixture/application.py
from selenium import webdriver
class Application:
def __init__(self,browser):
if browser == "chrome":
self.wd = webdriver.Chrome()
elif browser == "firefox":
self.wd = webdriver.Firefox()
else:
raise ValueError("Unrecognized browser %s" % browser)
Solution
You should use Application(browser) (at Confest.py).
Another similar problem: __init__() got an unexpected keyword argument 'user'
Explanation
When you make Application(browser=browser), you are trying to use keyword parameters.
Example with keyword parameter
from selenium import webdriver
class Application:
def __init__(self, *args, **kwargs):
if kwargs['browser'] == "chrome":
self.wd = webdriver.Chrome()
elif kwargs['browser'] == "firefox":
self.wd = webdriver.Firefox()
else:
raise ValueError("Unrecognized browser %s" % kwargs['browser'])

Categories