Maybe
(Maybe)
1
如图在初始化时,我们需要添加一个显示等待直到
导出
这个元素能够被定位到。这样我们才能够在add_element函数里面找到
self.find_ele((By.LINK_TEXT,'添加成员')).click()
。
我的疑惑:按照我的逻辑,我封装好了一个find_ele函数。这会使我在接下来10秒的时间一直寻找 添加成员
,所以init函数里面的显示等待就可以不要了。但是实际操作却不能这样。这也是为什么呀?
代码部分
ContactPage代码
class ContactPage(BasePage):
def __init__(self, driver: WebDriver):
# 接受外部传入的driver,用于当前的自动化测试
super().__init__(driver)
WebDriverWait(self.driver, 10).until(expected_conditions.visibility_of_element_located((By.LINK_TEXT, '导出')))
def add_member(self, member: Member):
self.find_ele((By.LINK_TEXT,'添加成员')).click()
self.find_ele((By.NAME, 'username')).send_keys(member.name)
self.find_ele((By.NAME, 'acctid')).send_keys(member.account)
email_ele = self.find_ele((By.ID, 'memberAdd_biz_mail'))
email_ele.clear()
email_ele.send_keys(member.mail)
self.find_ele((By.NAME, 'mobile')).send_keys(member.phone)
self.find_ele((By.LINK_TEXT, '保存')).click()
WebDriverWait(self.driver, 10) \
.until(expected_conditions.visibility_of_element_located(
(By.LINK_TEXT, '立即邀请')
)
)
# self.find_ele((By.LINK_TEXT, '立即邀请'))
return self
BasePage代码
from selenium import webdriver
from selenium.webdriver.chrome.options import Options
from selenium.webdriver.chrome.webdriver import WebDriver
from selenium.webdriver.support import expected_conditions
from selenium.webdriver.support.wait import WebDriverWait
class BasePage:
def __init__(self,driver:WebDriver):
if driver is not None:
self.driver=driver
else:
options = Options()
options.debugger_address = '127.0.0.1:9222'
self.driver = webdriver.Chrome(options=options)
def find_ele(self,element):
WebDriverWait(self.driver,10).until(expected_conditions.visibility_of_element_located(element))
return self.driver.find_element(*element)
def click_ele(self,element):
# WebDriverWait(self.driver, 10).until(expected_conditions.visibility_of_element_located(element))
return self.find_ele(element).click()
def send_ele(self,element,keyword):
return self.find_ele(element).send_keys(keyword)
test代码
class TestMemberAdd:
def setup_class(self):
self.wework = WeWorkPage()
self.contact_page = self.wework.contack()
def setup(self):
self.contact_page = self.wework.portal().contack()
@pytest.mark.parametrize('memeber_data', [
{'name': 'zzz'},
{'name': 'xxx'},
{'name': 'ccc'},
])
def test_add_member(self, memeber_data):
random = str(datetime.now().timestamp()).split('.')[0]
member = Member(**memeber_data)
member.name = member.name
member.account = member.name + random
member.mail = member.name + random
member.phone = random + '0'
self.contact_page.add_member(member) # 添加
self.member_edit_page = self.contact_page.search_member(member.account) # 搜索
get_member = self.member_edit_page.get_member() # 获取
assert get_member.account == member.account # 断言
Maybe
(Maybe)
3
实际操作就是,我如果把如图init里面的等待语句删除了就会报错。
我如果不删除就可以跑成功整个用例。但如果删除了就会报错,告诉我这句话超时;我想知道为什么,因为老师教过我们封装过BasePage,他的功能不就是让我们在规定的时间找到指定元素吗,我认为既然继承了BasePage的功能就可以去掉init里的显示等待。但实际是不能够去掉的
Maybe
(Maybe)
5
画线的部分注释掉了会报错,我也知道他不能注释,但是想不通为什么
test setup failed
self = <class 'wework.tests.test_contact_page.TestMemberAdd'>
def setup_class(self):
self.wework = WeWorkPage()
> self.contact_page = self.wework.contack()
test_contact_page.py:13:
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
..\page\wework_page.py:24: in contack
WebDriverWait(self.driver, 10).until(loop_click) # 循环调用,可以使浏览器点击一次不生效的时候在以后的10秒内多次点击直到生效
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
self = <selenium.webdriver.support.wait.WebDriverWait (session="033b8e50c06fe16032d0a0eb8e6499fc")>
method = <function WeWorkPage.contack.<locals>.loop_click at 0x000002ACFA0B7640>
message = ''
def until(self, method, message: str = ""):
"""Calls the method provided with the driver as an argument until the \
return value does not evaluate to ``False``.
:param method: callable(WebDriver)
:param message: optional message for :exc:`TimeoutException`
:returns: the result of the last call to `method`
:raises: :exc:`selenium.common.exceptions.TimeoutException` if timeout occurs
"""
screen = None
stacktrace = None
end_time = time.monotonic() + self._timeout
while True:
try:
value = method(self._driver)
if value:
return value
except self._ignored_exceptions as exc:
screen = getattr(exc, 'screen', None)
stacktrace = getattr(exc, 'stacktrace', None)
time.sleep(self._poll)
if time.monotonic() > end_time:
break
> raise TimeoutException(message, screen, stacktrace)
E selenium.common.exceptions.TimeoutException: Message:
..\..\venv\lib\site-packages\selenium\webdriver\support\wait.py:90: TimeoutException
报错来自于这里,感觉跟你的封装是没关系的。这个代码在你执行的时候被执行了,他本身的逻辑没满足导致超时了。你得看看这块的代码
Maybe
(Maybe)
7
报错内容
test_contact_page.py::TestMemberAdd::test_add_member[memeber_data0]
test_contact_page.py::TestMemberAdd::test_add_member[memeber_data1] PASSED [ 33%]FAILED [ 66%]
test_contact_page.py:17 (TestMemberAdd.test_add_member[memeber_data1])
self = <wework.tests.test_contact_page.TestMemberAdd object at 0x000001E8ACFAC610>
memeber_data = {'name': 'xxx'}
@pytest.mark.parametrize('memeber_data', [
{'name': 'zzz'},
{'name': 'xxx'},
{'name': 'ccc'},
])
def test_add_member(self, memeber_data):
random = str(datetime.now().timestamp()).split('.')[0]
member = Member(**memeber_data)
member.name = member.name
member.account = member.name + random
member.mail = member.name + random
member.phone = random + '0'
> self.contact_page.add_member(member) # 添加
test_contact_page.py:31:
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
..\page\contact_page.py:25: in add_member
self.find_ele((By.NAME, 'username')).send_keys(member.name)
..\framework\base_page.py:18: in find_ele
WebDriverWait(self.driver,10).until(expected_conditions.visibility_of_element_located(element))
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
self = <selenium.webdriver.support.wait.WebDriverWait (session="ac120d4f7f8fd10adabf303dc69eabc7")>
method = <function visibility_of_element_located.<locals>._predicate at 0x000001E8ACFAAEF0>
message = ''
def until(self, method, message: str = ""):
"""Calls the method provided with the driver as an argument until the \
return value does not evaluate to ``False``.
:param method: callable(WebDriver)
:param message: optional message for :exc:`TimeoutException`
:returns: the result of the last call to `method`
:raises: :exc:`selenium.common.exceptions.TimeoutException` if timeout occurs
"""
screen = None
stacktrace = None
end_time = time.monotonic() + self._timeout
while True:
try:
value = method(self._driver)
if value:
return value
except self._ignored_exceptions as exc:
screen = getattr(exc, 'screen', None)
stacktrace = getattr(exc, 'stacktrace', None)
time.sleep(self._poll)
if time.monotonic() > end_time:
break
> raise TimeoutException(message, screen, stacktrace)
E selenium.common.exceptions.TimeoutException: Message:
E Stacktrace:
E Backtrace:
E Ordinal0 [0x008278B3+2193587]
E Ordinal0 [0x007C0681+1771137]
E Ordinal0 [0x006D41A8+803240]
E Ordinal0 [0x007024A0+992416]
E Ordinal0 [0x0070273B+993083]
E Ordinal0 [0x0072F7C2+1177538]
E Ordinal0 [0x0071D7F4+1103860]
E Ordinal0 [0x0072DAE2+1170146]
E Ordinal0 [0x0071D5C6+1103302]
E Ordinal0 [0x006F77E0+948192]
E Ordinal0 [0x006F86E6+952038]
E GetHandleVerifier [0x00AD0CB2+2738370]
E GetHandleVerifier [0x00AC21B8+2678216]
E GetHandleVerifier [0x008B17AA+512954]
E GetHandleVerifier [0x008B0856+509030]
E Ordinal0 [0x007C743B+1799227]
E Ordinal0 [0x007CBB68+1817448]
E Ordinal0 [0x007CBC55+1817685]
E Ordinal0 [0x007D5230+1856048]
E BaseThreadInitThunk [0x7711FA29+25]
E RtlGetAppContainerNamedObjectPath [0x77947A9E+286]
E RtlGetAppContainerNamedObjectPath [0x77947A6E+238]
..\..\venv\lib\site-packages\selenium\webdriver\support\wait.py:90: TimeoutException
FAILED [100%]
test_contact_page.py:17 (TestMemberAdd.test_add_member[memeber_data2])
self = <wework.tests.test_contact_page.TestMemberAdd object at 0x000001E8ACFAC520>
memeber_data = {'name': 'ccc'}
@pytest.mark.parametrize('memeber_data', [
{'name': 'zzz'},
{'name': 'xxx'},
{'name': 'ccc'},
])
def test_add_member(self, memeber_data):
random = str(datetime.now().timestamp()).split('.')[0]
member = Member(**memeber_data)
member.name = member.name
member.account = member.name + random
member.mail = member.name + random
member.phone = random + '0'
> self.contact_page.add_member(member) # 添加
test_contact_page.py:31:
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
..\page\contact_page.py:25: in add_member
self.find_ele((By.NAME, 'username')).send_keys(member.name)
..\framework\base_page.py:18: in find_ele
WebDriverWait(self.driver,10).until(expected_conditions.visibility_of_element_located(element))
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
self = <selenium.webdriver.support.wait.WebDriverWait (session="ac120d4f7f8fd10adabf303dc69eabc7")>
method = <function visibility_of_element_located.<locals>._predicate at 0x000001E8ACFAB5B0>
message = ''
def until(self, method, message: str = ""):
"""Calls the method provided with the driver as an argument until the \
return value does not evaluate to ``False``.
:param method: callable(WebDriver)
:param message: optional message for :exc:`TimeoutException`
:returns: the result of the last call to `method`
:raises: :exc:`selenium.common.exceptions.TimeoutException` if timeout occurs
"""
screen = None
stacktrace = None
end_time = time.monotonic() + self._timeout
while True:
try:
value = method(self._driver)
if value:
return value
except self._ignored_exceptions as exc:
screen = getattr(exc, 'screen', None)
stacktrace = getattr(exc, 'stacktrace', None)
time.sleep(self._poll)
if time.monotonic() > end_time:
break
> raise TimeoutException(message, screen, stacktrace)
E selenium.common.exceptions.TimeoutException: Message:
E Stacktrace:
E Backtrace:
E Ordinal0 [0x008278B3+2193587]
E Ordinal0 [0x007C0681+1771137]
E Ordinal0 [0x006D41A8+803240]
E Ordinal0 [0x007024A0+992416]
E Ordinal0 [0x0070273B+993083]
E Ordinal0 [0x0072F7C2+1177538]
E Ordinal0 [0x0071D7F4+1103860]
E Ordinal0 [0x0072DAE2+1170146]
E Ordinal0 [0x0071D5C6+1103302]
E Ordinal0 [0x006F77E0+948192]
E Ordinal0 [0x006F86E6+952038]
E GetHandleVerifier [0x00AD0CB2+2738370]
E GetHandleVerifier [0x00AC21B8+2678216]
E GetHandleVerifier [0x008B17AA+512954]
E GetHandleVerifier [0x008B0856+509030]
E Ordinal0 [0x007C743B+1799227]
E Ordinal0 [0x007CBB68+1817448]
E Ordinal0 [0x007CBC55+1817685]
E Ordinal0 [0x007D5230+1856048]
E BaseThreadInitThunk [0x7711FA29+25]
E RtlGetAppContainerNamedObjectPath [0x77947A9E+286]
E RtlGetAppContainerNamedObjectPath [0x77947A6E+238]
..\..\venv\lib\site-packages\selenium\webdriver\support\wait.py:90: TimeoutException
**提问:**都是等待同一个界面的元素,为什么一个会报错,一个就能通过这个case
因为“添加成员“在没进入通讯录页面之前就存在了。是个巧合,在企业微信后台的默认首页里,也存在一个”添加成员“按钮,我上课的时候讲过这个,你可能没注意。