Web自動化測試(全網最給力自動化教程)

http://www.cnblogs.com/zidonghua/p/7430083.htmljavascript


python+selenium自動化軟件測試(第2章):WebDriver API

歡迎您來閱讀和練手!您將會從本章的詳細講解中,獲取很大的收穫!開始學習吧!php

 

正文html

2.1 操做元素基本方法

前言
前面已經把環境搭建好了,從這篇開始,正式學習selenium的webdriver框架。咱們日常說的 selenium自動化,其實它並非相似於QTP之類的有GUI界面的可視化工具,咱們要學的是webdriver框架的API。
本篇主要講如何用Python調用webdriver框架的API,對瀏覽器作一些常規的操做,如打開、前進、後退、刷新、設置窗口大小、截屏、退出等操做。前端

2.1.1 打開網頁

1.從selenium裏面導入webdriver模塊
2.打開Firefox瀏覽器(Ie和Chrome對應下面的)
3.打開百度網址java

2.1.2 設置休眠

1.因爲打開百度網址後,頁面加載須要幾秒鐘,因此最好等到頁面加載完成後再繼續下一步操做
2.導入time模塊,time模塊是Python自帶的,因此無需下載
3.設置等待時間,單位是秒(s),時間值能夠是小數也能夠是整數python

2.1.3 頁面刷新

1.有時候頁面操做後,數據可能沒及時同步,須要從新刷新
2.這裏能夠模擬刷新頁面操做,至關於瀏覽器輸入框後面的刷新按鈕jquery

2.1.4 頁面切換

1.當在一個瀏覽器打開兩個頁面後,想返回上一頁面,至關於瀏覽器左上角的左箭頭按鈕。android

2.返回到上一頁面後,也能夠切換到下一頁,至關於瀏覽器左上角的右箭頭按鈕。web

2.1.5 設置窗口大小

1.能夠設置瀏覽器窗口大小,如設置窗口大小爲手機分辨率540*960
2.也能夠最大化窗口

 2.1.6 截屏

1. 打開網站以後,也能夠對屏幕截屏
2.截屏後設置指定的保存路徑+文件名稱+後綴

2.1.7 退出

1.退出有兩種方式,一種是close;另一種是quit。
2.close用於關閉當前窗口,當打開的窗口較多時,就能夠用close關閉部分窗口。
3.quit用於結束進程,關閉全部的窗口。
4.最後結束測試,要用quit。quit能夠回收c盤的臨時文件。

掌握了瀏覽器的基本操做後,接下來就能夠開始學習元素定位了,元素定位須要有必定的html基礎。沒有基礎的能夠按下瀏覽器的F12快捷鍵先看下html的佈局,先了解一些就能夠了。

2.1.8 加載瀏覽器配置

啓動瀏覽器後,發現右上角安裝的插件不見了,這是由於webdriver啓動瀏覽器時候,是開的一個虛擬線程,跟手工點開是有區別的,selenium的一切操做都是模擬人工(不徹底等於人工操做)。

加載Firefox配置

   有小夥伴在用腳本啓動瀏覽器時候發現原來下載的插件不見了,沒法用firebug在打開的頁面上繼續定位頁面元素,調試起來不方便 。加載瀏覽器配置,須要用FirefoxProfile(profile_directory)這個類來加載,profile_directory既爲瀏覽器配置文件的路徑地址。

1、遇到問題
1.在使用腳本打開瀏覽器時候,發現右上角原來下載的插件firebug不見了,到底去哪了呢?
2.用腳本去打開瀏覽器時候,實際上是從新打開了一個進程,跟手動打開瀏覽器不是一個進程。
因此沒主動加載插件,不過selenium裏面其實提供了對應的方法去打開,只是不多有人用到。

 

 

2、FirefoxProfile
1.要想了解selenium裏面API的用法,最好先看下相關的幫助文檔打開cmd窗口,
輸入以下信息:

->python
->from selenium import webdriver
->help(webdriver.FirefoxProfile)

Help on class FirefoxProfile in module
selenium.webdriver.firefox.firefox_profile:
class FirefoxProfile(builtin.object)
|  Methods defined here:

|
|  init(self, profile_directory=None)
|      Initialises a new instance of a Firefox Profile
|    
|      :args:
|       - profile_directory: Directory of profile that you want to use.
|         This defaults to None and will create a new
|         directory when object is created.

2.翻譯過來大概意思是說,這裏須要profile_directory這個配置文件路徑的參數
3.profile_directory=None,若是沒有路徑,默認爲None,啓動的是一個新的,有的話就加載指定的路徑。

3、profile_directory
1.問題來了:Firefox的配置文件地址如何找到呢?
2.打開Firefox點右上角設置>?(幫助)>故障排除信息>顯示文件夾

3.打開後把路徑複製下來就能夠了:
C:\Users\xxx\AppData\Roaming\Mozilla\Firefox\Profiles\1x41j9of.default

 

4、啓動配置文件
1.因爲文件路徑存在字符:\ ,反斜槓在代碼裏是轉義字符,這個有點代碼基礎的應該都知道。
不懂什麼叫轉義字符的,本身翻書補下基礎吧!
2.遇到轉義字符,爲了避免讓轉義,有兩種處理方式:
第一種:\ (前面再加一個反斜槓)

第二種:r」\"(字符串前面加r,使用字符串原型)

 

5、參考代碼:

複製代碼
# coding=utf-8
from selenium import webdriver
# 配置文件地址
profile_directory = r'C:\Users\xxx\AppData\Roaming\Mozilla\Firefox\Profiles\1x41j9of.default'

# 加載配置配置
profile = webdriver.FirefoxProfile(profile_directory)
# 啓動瀏覽器配置
driver = webdriver.Firefox(profile)
複製代碼

 其實很簡單,在調用瀏覽器的前面,多加2行代碼而已,主要是要弄清楚原理。

 

2.2 經常使用8種元素定位(Firebug和firepath)

前言   
元素定位在firefox上能夠安裝Firebug和firepath輔助工具進行元素定位。


2.2.1 環境準備

1.瀏覽器選擇:Firefox
2.安裝插件:Firebug和FirePath(設置》附加組件》搜索:輸入插件名稱》下載安裝後重啓瀏覽器)
3.安裝完成後,頁面右上角有個小爬蟲圖標
4.快速查看xpath插件:XPath Checker這個可下載,也能夠不用下載
5.插件安裝完成後,點開附加組件》擴展,以下圖所示

 

2.2.2 查看頁面元素

以百度搜索框爲例,先打開百度網頁
1.點右上角爬蟲按鈕
2.點左下角箭頭
3.將箭頭移動到百度搜索輸入框上,輸入框高亮狀態
4.下方紅色區域就是單位到輸入框的屬性:

<input id="kw" class="s_ipt" type="text" autocomplete="off" maxlength="100" name="wd">

2.2.3 find_element_by_id()

1.從上面定位到的元素屬性中,能夠看到有個id屬性:id="kw",這裏能夠經過它的id屬性定位到這個元素。
2.定位到搜索框後,用send_keys()方法,輸入文本。

2.2.4 find_element_by_name() 

   1.從上面定位到的元素屬性中,能夠看到有個name屬性:name="wd",這裏能夠經過它的name屬性單位到這個元素。
    說明:這裏運行後會報錯,說明這個搜索框的name屬性不是惟一的,沒法經過name屬性直接定位到輸入框

2.2.5 find_element_by_class_name()

1.從上面定位到的元素屬性中,能夠看到有個class屬性:class="s_ipt",這裏能夠經過它的class屬性定位到這個元素。

2.2.6 find_element_by_tag_name()

1.從上面定位到的元素屬性中,能夠看到每一個元素都有tag(標籤)屬性,如搜索框的標籤屬性,就是最前面的input。
2.很明顯,在一個頁面中,相同的標籤有不少,因此通常不用標籤來定位。如下例子,僅供參考和理解,運行確定報錯。

 2.2.7 find_element_by_link_text()

1.定位百度頁面上"hao123"這個按鈕

 

查看頁面元素:

<a class="mnav" target="_blank" href="http://www.hao123.com">hao123</a>

2.從元素屬性能夠分析出,有個href = "http://www.hao123.com

說明它是個超連接,對於這種元素,能夠用如下方法:

 2.2.8 find_element_by_partial_link_text()

1.有時候一個超連接它的字符串可能比較長,若是輸入全稱的話,會顯示很長,這時候能夠用一模糊匹配方式,截取其中一部分字符串就能夠了

2.如「hao123」,只需輸入「ao123」也能夠定位到

2.2.9 find_element_by_xpath()

1.以上定位方式都是經過元素的某個屬性來定位的,若是一個元素它既沒有id、name、class屬性也不是超連接,這麼辦呢?或者說它的屬性不少重複的。這個時候就能夠用xpath解決。
2.xpath是一種路徑語言,跟上面的定位原理不太同樣,首先第一步要先學會用工具查看一個元素的xpath。

 

 3.按照上圖的步驟,在FirePath插件裏copy對應的xpath地址。

 2.2.10 find_element_by_css_selector()

1.css是另一種語法,比xpath更爲簡潔,可是不太好理解。這裏先學會如何用工具查看,後續的教程再深刻講解
2.打開FirePath插件選擇css
3.定位到後以下圖紅色區域顯示

 

總結:
selenium的webdriver提供了18種(注意是18種,不是8種)的元素定位方法,前面8種是經過元素的屬性來直接定位的,後面的xpath和css定位更加靈活,須要重點掌握其中一個。
前八種是你們都熟悉的,常常會用到的:

複製代碼
1.id定位:find_element_by_id(self, id_)
2.name定位:find_element_by_name(self, name)
3.class定位:find_element_by_class_name(self, name)
4.tag定位:find_element_by_tag_name(self, name)
5.link定位:find_element_by_link_text(self, link_text)
6.partial_link定位find_element_by_partial_link_text(self, link_text)
7.xpath定位:find_element_by_xpath(self, xpath)
8.css定位:find_element_by_css_selector(self, css_selector)
複製代碼

這八種是複數形式(2.8和2.27章節有介紹)

複製代碼
9.id複數定位find_elements_by_id(self, id_)
10.name複數定位find_elements_by_name(self, name)
11.class複數定位find_elements_by_class_name(self, name)
12.tag複數定位find_elements_by_tag_name(self, name)
13.link複數定位find_elements_by_link_text(self, text)
14.partial_link複數定位find_elements_by_partial_link_text(self, link_text)
15.xpath複數定位find_elements_by_xpath(self, xpath)
16.css複數定位find_elements_by_css_selector(self, css_selector
複製代碼

這兩種是參數化的方法,會在之後搭建框架的時候,會常常用到PO模式,纔會用到這個參數化的方法(將會在4.2有具體介紹)

17.find_element(self, by='id', value=None)
18.find_elements(self, by='id', value=None)

2.3 xpath定位

前言    
在上一篇簡單的介紹了用工具查看目標元素的xpath地址,工具查看比較死板,不夠靈活,有時候直接複製粘貼會定位不到。這個時候就須要本身手動的去寫xpath了,這一篇詳細講解xpath的一些語法。
什麼是xpath呢?
官方介紹:XPath即爲XML路徑語言,它是一種用來肯定XML文檔中某部分位置的語言。反正小編看這個介紹是雲裏霧裏的,通俗一點講就是經過元素的路徑來查找到這個元素的。

2.3.1 xpath:屬性定位

1.xptah也能夠經過元素的id、name、class這些屬性定位,以下圖:

2.因而能夠用如下xpath方法定位

2.3.2 xpath:其它屬性

1.若是一個元素id、name、class屬性都沒有,這時候也能夠經過其它屬性定位到

2.3.3 xpath:標籤

1.有時候同一個屬性,同名的比較多,這時候能夠經過標籤篩選下,定位更準一點
2.若是不想制定標籤名稱,能夠用*號表示任意標籤
3.若是想制定具體某個標籤,就能夠直接寫標籤名稱

2.3.4 xpath:層級

1.若是一個元素,它的屬性不是很明顯,沒法直接定位到,這時候咱們能夠先找它老爸(父元素)。
2.找到它老爸後,再找下個層級就能定位到了。

3.如上圖所示,要定位的是input這個標籤,它的老爸的id=s_kw_wrap。
4.要是它老爸的屬性也不是很明顯,就找它爺爺id=form。
5.因而就能夠經過層級關係定位到。

2.3.5 xpath:索引

1.若是一個元素它的兄弟元素跟它的標籤同樣,這時候沒法經過層級定位到。由於都是一個父親生的,多胞胎兄弟。
2.雖然雙胞胎兄弟很難識別,可是出生是有前後的,因而能夠經過它在家裏的排行老幾定位到。
3.以下圖三胞胎兄弟。

 

4.用xpath定位老大、老二和老三(這裏索引是從1開始算起的,跟Python的索引不同)。

2.3.6 xpath:邏輯運算

1.xpath還有一個比較強的功能,是能夠多個屬性邏輯運算的,能夠支持與(and)、或(or)、非(not)
2.通常用的比較多的是and運算,同時知足兩個屬性

 

2.3.7 xpath:模糊匹配

1.xpath還有一個很是強大的功能,模糊匹配。
2.掌握了模糊匹配功能,基本上沒有定位不到的。
3.好比我要定位百度頁面的超連接「hao123」,在上一篇中講過能夠經過by_link,也能夠經過by_partial_link,模糊匹配定位到。固然xpath也能夠有一樣的功能,而且更爲強大。

能夠把xpath當作是元素定位界的屠龍刀。武林至尊,寶刀xpath,css不出,誰與爭鋒?下節課將亮出倚天劍css定位。

2.4 CSS定位

前言
大部分人在使用selenium定位元素時,用的是xpath定位,由於xpath基本能解決定位的需求。css定位每每被忽略掉了,其實css定位也有它的價值,css定位更快,語法更簡潔。
這一篇css的定位方法,主要是對比上一篇的xpath來的,基本上xpath能完成的,css也能夠作到。兩篇對比學習,更容易理解。
2.4.1 css:屬性定位
1.css能夠經過元素的id、class、標籤這三個常規屬性直接定位到
2.以下是百度輸入框的的html代碼:

<input id="kw" class="s_ipt" type="text" autocomplete="off" maxlength="100" name="wd"/>

3.css用#號表示id屬性,如:#kw
4.css用.表示class屬性,如:.s_ipt
5.css直接用標籤名稱,無任何標示符,如:input

2.4.2 css:其它屬性

1.css除了能夠經過標籤、class、id這三個常規屬性定位外,也能夠經過其它屬性定位
2.如下是定位其它屬性的格式

 

2.4.3 css:標籤

1.css頁能夠經過標籤與屬性的組合來定位元素

2.4.4 css:層級關係

1.在前面一篇xpath中講到層級關係定位,這裏css也能夠達到一樣的效果
2.如xpath:

//form[@id='form']/span/input和
//form[@class='fm']/span/input也能夠用css實現

 

 

2.4.5 css:索引

1.如下圖爲例,跟上一篇同樣:

2.css也能夠經過索引option:nth-child(1)來定位子元素,這點與xpath寫法用很大差別,其實很好理解,直接翻譯過來就是第幾個小孩。

2.4.6 css:邏輯運算

1.css一樣也能夠實現邏輯運算,同時匹配兩個屬性,這裏跟xpath不同,無需寫and關鍵字

 

2.4.7 css:模糊匹配

1.css的模糊匹配contains('xxx'),網上雖然用各類資料顯示能用,可是小編親自試驗了下,一直報錯。
2.在各類百度後找到了答案:you can't do this withCSS selectors, because there is no such thing as:contains() in CSS. It was a proposal that was abandoned years ago.
很是遺憾,這個語法已經被拋棄了,因此這裏就不用管這個語法了。
css語法遠遠不止上面提到的,還有更多更強大定位策略,有興趣的能夠繼續深刻研究。官方說法,css定位更快,語法更簡潔,可是xpath更直觀,更好理解一些。

2.5 SeleniumBuilder輔助定位元素

前言
對於用火狐瀏覽器的小夥伴們,你還在爲定位元素而煩惱嘛?
上古神器Selenium Builder來啦,哪裏不會點哪裏,媽媽不再用擔憂個人定位元素問題啦!(可是也不是萬能,基本上都能覆蓋到)

2.5.1 安裝Selenium Builder

在火狐瀏覽器的附加組件中搜索添加Selenium Builder便可。安裝好後以下圖所示:

 

 2.5.2 直接運用

1.打開你要測試的URL或者打開插件後輸入你要測試的URL,以下圖

2.點擊後彈出一個彈窗,以下圖:

注:若是你是直接在你要測的網頁頁面打開這個插件時,selenium builder會直接獲取你要測的URL

3.點擊record:

而後你就能夠哪裏不會點哪裏了。這裏舉個例子:

2.5.3 實踐案例

1.百度首頁,點擊百度一下,而後點擊登陸,再一次點擊帳號和密碼輸入框,讓咱們來看看結果。

2.這裏沒有展開,點擊展開後能夠發現定位該元素的多種方法

 

直接選擇你想要的方法複製粘貼便可,不用的話直接關掉彈窗便可。

2.6 操做元素(鍵盤和鼠標事件)

前言
在前面的幾篇中重點介紹了一些元素的定位方法,定位到元素後,接下來就是須要操做元素了。本篇總結了web頁面經常使用的一些操做元素方法,能夠統稱爲行爲事件
有些web界面的選項菜單須要鼠標懸停在某個元素上才能顯示出來(如百度頁面的設置按鈕)。

2.6.1 簡單操做

    1.點擊(鼠標左鍵)頁面按鈕:click()
    2.清空輸入框:clear()
    3.輸入字符串:send_keys()
    4.send_keys()若是是發送中文的,前面需加u,如:u"中文",由於這裏是輸入到windows系統了,windows系統是GBK編碼,咱們的腳本是utf-8,須要轉碼爲Unicode國際編碼,這樣才能識別到。

 

2.6.2 submit提交表單

1.在前面百度搜索案例中,輸入關鍵字後,能夠直接按回車鍵搜索,也能夠點搜索按鈕搜索。
2.submit()通常用於模擬回車鍵。

 

2.6.3 鍵盤操做 

    1.selenium提供了一整套的模擬鍵盤操做事件,前面submit()方法若是不行的話,能夠試試模擬鍵盤事件
    2.模擬鍵盤的操做須要先導入鍵盤模塊:from selenium.webdriver.common.keysimport Keys
    3.模擬enter鍵,能夠用send_keys(Keys.ENTER)

 

    4.其它常見的鍵盤操做:
       鍵盤F1到F12:send_keys(Keys.F1)把F1改爲對應的快捷鍵:

       複製Ctrl+C:send_keys(Keys.CONTROL,'c') 

       粘貼Ctrl+V:send_keys(Keys.CONTROL,'v') 

       全選Ctrl+A:send_keys(Keys.CONTROL,'a') 

       剪切Ctrl+X:send_keys(Keys.CONTROL,'x') 

       製表鍵Tab:  send_keys(Keys.TAB) 

       這裏只是列了一些經常使用的,固然除了鍵盤事件,也有鼠標事件。

2.6.4 鼠標懸停事件

    1.鼠標不只僅能夠點擊(click),鼠標還有其它的操做,如:鼠標懸停在某個元素上,鼠標右擊,鼠標按住某個按鈕拖到
    2.鼠標事件須要先導入模塊:from selenium.webdriver.common.action_chainsimport ActionChains
        perform() 執行全部ActionChains中的行爲;
        move_to_element() 鼠標懸停。
    3.這裏以百度頁面設置按鈕爲例:

    4.除了經常使用的鼠標懸停事件外,還有
       右擊鼠標:context_click()
       雙擊鼠標:double_click()
       依葫蘆畫瓢,替換上面案例中對應的鼠標事件就能夠了
       selenium提供了一整套完整的鼠標和鍵盤行爲事件,功能仍是蠻強大滴。下一篇介紹多窗口的狀況下如何處理。

2.7 多窗口、句柄(handle)

前言   
有些頁面的連接打開後,會從新打開一個窗口,對於這種狀況,想在新頁面上操做,就得先切換窗口了。獲取窗口的惟一標識用句柄表示,因此只須要切換句柄,咱們就能在多個頁面上靈活自如的操做了。
1、認識多窗口
1.打開趕集網:http://bj.ganji.com/,點擊招聘求職按鈕會發現右邊多了一個窗口標籤

 2.咱們用代碼去執行點擊的時候,發現界面上出現兩個窗口,以下圖這種狀況就是多窗口了。

 

   3.到這裏估計有小夥伴納悶了,手工點擊是2個標籤,怎麼腳本點擊就變成2個窗口了,這個在2.1裏面講過,腳本執行是不加載配置的,手工點擊是瀏覽器默認設置了新窗口打開方式爲標籤,這裏用鼠標按住點二個標籤,拖拽出來,也就變成2個標籤了,是一回事。

 

 2、獲取當前窗口句柄

    1.元素有屬性,瀏覽器的窗口其實也有屬性的,只是你看不到,瀏覽器窗口的屬性用句柄(handle)來識別。

    2.人爲操做的話,能夠經過眼睛看,識別不一樣的窗口點擊切換。可是腳本沒長眼睛,它不知道你要操做哪一個窗口,這時候只能句柄來判斷了。

    3.獲取當前頁面的句柄:driver.current_window_handle

3、獲取全部句柄
    1.定位趕集網招聘求職按鈕,並點擊
    2.點擊後,獲取當前全部的句柄:window_handles

 

 

4、切換句柄

網上大部分教程都是些的第一種方法,小編這裏新增一個更簡單的方法,直接從獲取全部的句柄list裏面取值。

方法一(不推薦):

    1.循環判斷是否與首頁句柄相等

    2.若是不等,說明是新頁面的句柄

    3.獲取的新頁面句柄後,能夠切換到新打開的頁面上

    4.打印新頁面的title,看是否切換成功

方法二:

    1.直接獲取all_h這個list數據裏面第二個hand的值:all_h[1]

5、關閉新窗口,切回主頁
   1.close是關閉當前窗口,由於此時有兩個窗口,用close能夠關閉其中一個,quit是退出整個進程(若是當前有兩個窗口,會一塊兒關閉)。
   2.切換到首頁句柄:h
   3.打印當前頁面的title,看是否切換到首頁了

 

6、參考代碼

複製代碼
# coding:utf-8
from selenium import webdriver
driver = webdriver.Firefox()
driver.get("http://bj.ganji.com/")
h = driver.current_window_handle
print h     # 打印首頁句柄
driver.find_element_by_link_text("招聘求職").click()
all_h = driver.window_handles
print all_h        # 打印全部的句柄

# 方法一:判斷句柄,不等於首頁就切換(不推薦此方法,太繁瑣)
# for i in all_h:
#     if i != h:
#         driver.switch_to.window(i)
#         print driver.title
# 方法二:獲取list裏面第二個直接切換
driver.switch_to.window(all_h[1])
print driver.title
# 關閉新窗口
driver.close()
# 切換到首頁句柄
driver.switch_to.window(h)
# 打印當前的title
print driver.title
複製代碼

2.8 定位一組元素elements

前言    
前面的幾篇都是講如何定位一個元素,有時候一個頁面上有多個對象須要操做,若是一個個去定位的話,比較繁瑣,這時候就能夠定位一組對象。
webdriver 提供了定位一組元素的方法,跟前面八種定位方式其實同樣,只是前面是單數,這裏是複數形式:find_elements


本篇拿百度搜索做爲案例,從搜索結果中隨機選擇一條搜索結果,而後點擊查看。

 

1、定位搜索結果
    1.在百度搜索框輸入關鍵字「測試部落」後,用firebug查看頁面元素,能夠看到這些搜索結果有共同的屬性。

    2.從搜索的結果能夠看到,他們的父元素同樣:<h3 class="t">
    3.標籤都同樣,且target屬性也同樣:<a target="_blank" />
    4.因而這裏能夠用css定位(固然用xpath也是能夠的)

 

2、確認定位結果
    1.前面的定位策略只是一種猜測,並不必定真正獲取到本身想要的對象的,也行會定位到一些不想要的對象。
    2.因而能夠獲取對象的屬性,來驗證下是否是定位準確了。這裏能夠獲取href屬性,打印出url地址。

 

3、隨機函數
    1.搜索結果有10條,從這10條中隨機取一個就ok了
    2.先導入隨機函數:import random
    3.設置隨機值範圍爲0~9:a=random.randint(0~9)

 

4、隨機打開url
    1.從返回結果中隨機取一個url地址
    2.經過get方法打卡url
    3.其實這種方式是接口測試了,不屬於UI自動化,這裏只是開闊下思惟,不建議用這種方法

 

5、經過click點擊打開
    1.前面那種方法,是直接訪問url地址,算是接口測試的範疇了,真正模擬用戶點擊行爲,得用click的方法

複製代碼
# coding:utf-8
from selenium import webdriver
import random

driver = webdriver.Firefox()
driver.get("https://www.baidu.com")
driver.implicitly_wait(10)
driver.find_element_by_id("kw").send_keys(u"測試部落")
driver.find_element_by_id("kw").submit()
s = driver.find_elements_by_css_selector("h3.t>a")

# 設置隨機值
t = random.randint(0, 9)
# 隨機取一個結果點擊鼠標
s[t].click()
複製代碼

 

不知道有小夥伴有沒注意一個細節,前面在搜索框輸入關鍵字後,我並無去點擊搜索按鈕,而是用的submit的方法,submit至關於回車鍵。
具體的操做對象方法,下篇詳細介紹。本篇主要學會定位一組對象,而後隨機操做其中的一個。

2.9 iframe

1、frame和iframe區別
Frame與Iframe二者能夠實現的功能基本相同,不過Iframe比Frame具備更多的靈活性。 frame是整個頁面的框架,iframe是內嵌的網頁元素,也能夠說是內嵌的框架
Iframe標記又叫浮動幀標記,能夠用它將一個HTML文檔嵌入在一個HTML中顯示。它和Frame標記的最大區別是在網頁中嵌入 的<Iframe></Iframe>所包含的內容與整個頁面是一個總體,而<Frame>< /Frame>所包含的內容是一個獨立的個體,是能夠獨立顯示的。另外,應用Iframe還能夠在同一個頁面中屢次顯示同一內容,而沒必要重複這段內 容的代碼。

2、案例操做:163登陸界面
1.打開http://mail.163.com/登陸頁面

2.用firebug定位登陸框

3.鼠標停留在左下角(定位到iframe位置)時,右上角整個登陸框顯示灰色,說明iframe區域是整個登陸框區域

4.左下角箭頭位置顯示iframe屬性<iframe id="x-URS-iframe" frameborder="0" name="" 

 3、切換iframe
1.因爲登陸按鈕是在iframe上,因此第一步須要把定位器切換到iframe上
2.用switch_to_frame方法切換,此處有id屬性,能夠直接用id定位切換

 

 

4、若是iframe沒有id怎麼辦?
1.這裏iframe的切換是默認支持id和name的方法的,固然實際狀況中會遇到沒有id屬性和name屬性爲空的狀況,這時候就須要先定位iframe元素對象
2.定位元素仍是以前的八種方法一樣適用,這裏我能夠經過tag先定位到,也能達到一樣效果

 

5、釋放iframe
1.當iframe上的操做完後,想從新回到主頁面上操做元素,這時候,就能夠用switch_to_default_content()方法返回到主頁面

 

6、如何判斷元素是否在iframe上?
1.定位到元素後,切換到firepath界面
2.看firebug工具左上角,若是顯示Top Window說明沒有iframe
3.若是顯示iframe#xxx這樣的,說明在iframe上,#後面就是它的id

 

7、如何解決switch_to_frame上的橫線呢?    
1.先找到官放的文檔介紹

 

2.python的腳本上面劃一橫線,是說這個語法已通過時了(也能夠繼續用,只是有部分人有強迫症)。上面文檔介紹說官方已經不推薦上面的寫法了,用這個寫法就行了driver.switch_to.frame()


8、參考代碼以下:

複製代碼
# coding:utf-8
from selenium import webdriver
driver = webdriver.Firefox()
driver.get("http://mail.163.com/")
driver.implicitly_wait(30)
# 切換iframe
# iframe = driver.find_element_by_tag_name("iframe")
# driver.switch_to_frame(iframe)
# driver.switch_to_frame("x-URS-iframe")
driver.switch_to.frame("x-URS-iframe")
driver.find_element_by_name("email").send_keys("123")
driver.find_element_by_name("password").send_keys("456")
# 釋放iframe,從新回到主頁面上
driver.switch_to.default_content()
複製代碼

2.10 select下拉框

本篇以百度設置下拉選項框爲案例,詳細介紹select下拉框相關的操做方法。

1、認識select
    1.打開百度-設置-搜索設置界面,以下圖所示

 

 

    2.箭頭所指位置,就是select選項框,打開頁面元素定位,下方紅色框框區域,能夠看到select標籤屬性:                   

<select id="nr" name="NR">

    3.選項有三個。

<option selected="" value="10">每頁顯示10條</option>
<option value="20">每頁顯示20條</option>
<option value="50">每頁顯示50條</option>

2、二次定位
    1.定位select裏的選項有多種方式,這裏先介紹一種簡單的方法:二次定位
    2.基本思路,先定位select框,再定位select裏的選項            
    3.代碼以下:

 

   4.還有另一種寫法也是能夠的,把最下面兩步合併成爲一步:   

driver.find_element_by_id("nr").find_element_by_xpath("//option[@value='50']").click()

3、直接定位
    1.有不少小夥伴說firebug只能定位到select框,不能定位到裏面的選項,實際上是工具掌握的不太熟練。小編接下來教你們如何定位裏面的選項。
    2.用firebug定位到select後,下方查看元素屬性地方,點select標籤前面的+號,就能夠展開裏面的選項內容了。

 3.而後本身寫xpath定位或者css,一次性直接定位到option上的內容。(不會本身手寫的,回頭看前面的元素定位內容)

 

4、Select模塊(index)

    1.除了上面介紹的兩種簡單的方法定位到select選項,selenium還提供了更高級的玩法,導入Select模塊。直接根據屬性或索引定位。
    2.先要導入select方法:
from selenium.webdriver.support.select import Select       
    3.而後經過select選項的索引來定位選擇對應選項(從0開始計數),如選擇第三個選項:select_by_index(2)

5、Select模塊(value)

    1.Select模塊裏面除了index的方法,還有一個方法,經過選項的value值來定位。每一個選項,都有對應的value值,如

<select id="nr" name="NR">
    <option selected="" value="10">每頁顯示10條</option>
    <option value="20">每頁顯示20條</option>          
    <option value="50">每頁顯示50條</option>
</select>

   2.第二個選項對應的value值就是"20":select_by_value("20")

 

6、Select模塊(text)
    1.Select模塊裏面還有一個更加高級的功能,能夠直接經過選項的文本內容來定位。
    2.定位「每頁顯示50條」:select_by_visible_text("每頁顯示50條")

 

7、Select模塊其它方法
    1.select裏面方法除了上面介紹的三種,還有更多的功能以下:

select_by_index()  :經過索引定位
select_by_value()  :經過value值定位
select_by_visible_text() :經過文本值定位
deselect_all()          :取消全部選項
deselect_by_index()     :取消對應index選項
deselect_by_value()      :取消對應value選項
deselect_by_visible_text() :取消對應文本選項

first_selected_option()  :返回第一個選項
all_selected_options()   :返回全部的選項

 

8、整理代碼以下:

複製代碼
# coding:utf-8
from selenium import webdriver
from selenium.webdriver.common.action_chains import ActionChains
from selenium.webdriver.support.select import Select
driver = webdriver.Firefox()
url = "https://www.baidu.com"
driver.get(url)
driver.implicitly_wait(20)
# 鼠標移動到「設置」按鈕
mouse = driver.find_element_by_link_text("設置")
ActionChains(driver).move_to_element(mouse).perform()
driver.find_element_by_link_text("搜索設置").click()
# 經過text:select_by_visible_text()
s = driver.find_element_by_id("nr")
Select(s).select_by_visible_text("每頁顯示50條")

# # 分兩步:先定位下拉框,再點擊選項s = driver.find_element_by_id("nr")s.find_element_by_xpath("//option[@value='50']").click()
# # 另一種寫法                                     
driver.find_element_by_id("nr").find_element_by_xpath("//option[@value='50']").click()
# # 直接經過xpath定位
driver.find_element_by_xpath(".//*[@id='nr']/option[2]").click()
# # 經過索引:select_by_index()
s = driver.find_element_by_id("nr")
Select(s).select_by_index(2)
# # 經過value:select_by_value()
s = driver.find_element_by_id("nr")
Select(s).select_by_value("20")
複製代碼

2.11 alert\confirm\prompt

前言   
不是全部的彈出框都叫alert,在使用alert方法前,先要識別出究竟是不是alert。先認清楚alert長什麼樣子,下次碰到了,就能夠用對應方法解決。
alert\confirm\prompt彈出框操做主要方法有:
text:獲取文本值
accept() :點擊"確認"
dismiss() :點擊"取消"或者叉掉對話框
send_keys() :輸入文本值 --僅限於prompt,在alert和confirm上沒有輸入框

1、認識alert\confirm\prompt
     1.以下圖,從上到下依次爲alert\confirm\prompt,先認清楚長什麼樣子,之後遇到了就知道如何操做了。

    2.html源碼以下(有興趣的能夠copy出來,複製到txt文本里,後綴改爲html就能夠了,而後用瀏覽器打開):

複製代碼
<html>  
   <head>
     <title>Alert</title>  
    </head>  
<body>  
<input id = "alert" value = "alert" type = "button" onclick = "alert('您關注了yoyoketang嗎?');"/>  
<input id = "confirm" value = "confirm" type = "button" onclick = "confirm('肯定關注微信公衆號:yoyoketang?');"/>  
<input
id = "prompt" value = "prompt" type = "button" onclick = "var name = 
prompt('請輸入微信公衆號:','yoyoketang'); document.write(name) "/>    
</body>   
</html>  
複製代碼

2、alert操做

   1.先用switch_to_alert()方法切換到alert彈出框上
    2.能夠用text方法獲取彈出的文本 信息
    3.accept()點擊確認按鈕
    4.dismiss()至關於點右上角x,取消彈出框
   (url的路徑,直接複製瀏覽器打開的路徑)

3、confirm操做
   1.先用switch_to_alert()方法切換到alert彈出框上
    2.能夠用text方法獲取彈出的文本 信息
    3.accept()點擊確認按鈕
    4.dismiss()至關於點取消按鈕或點右上角x,取消彈出框
(url的路徑,直接複製瀏覽器打開的路徑)

4、prompt操做
   1.先用switch_to_alert()方法切換到alert彈出框上
    2.能夠用text方法獲取彈出的文本 信息
    3.accept()點擊確認按鈕
    4.dismiss()至關於點右上角x,取消彈出框
    5.send_keys()這裏多個輸入框,能夠用send_keys()方法輸入文本內容
(url的路徑,直接複製瀏覽器打開的路徑)

5、select遇到的坑
    1.在操做百度設置裏面,點擊「保存設置」按鈕時,alert彈出框沒有彈出來。(Ie瀏覽器是能夠的)
    2.分析緣由:通過慢慢調試後發現,在點擊"保存設置"按鈕時,因爲前面的select操做後,失去了焦點
    3.解決辦法:在select操做後,作個click()點擊操做

s = driver.find_element_by_id("nr")
Select(s).select_by_visible_text("每頁顯示20條")
time.sleep(3)
s.click()

 

 6、最終代碼

複製代碼
# coding:utf-8
from selenium import webdriver
from selenium.webdriver.common.action_chains import ActionChains
from selenium.webdriver.support.select import Select
import time
driver = webdriver.Firefox()
url = "https://www.baidu.com"
driver.get(url)
driver.implicitly_wait(20)
# 鼠標移動到「設置」按鈕
mouse = driver.find_element_by_link_text("設置")
ActionChains(driver).move_to_element(mouse).perform()
driver.find_element_by_link_text("搜索設置").click()
# 經過text:select_by_visible_text()
s = driver.find_element_by_id("nr")
Select(s).select_by_visible_text("每頁顯示20條")
time.sleep(3)
s.click()
driver.find_element_by_link_text("保存設置").click()
time.sleep(5)
# 獲取alert彈框
t = driver.switch_to_alert()
print t.text
t.accept()
複製代碼

這一篇應該比較簡單,alert相關的內容比較少,雖然有一些頁面也有彈窗,但不是全部的彈窗都叫alert。

alert的彈出框界面比較簡潔,調用的是Windows系統彈窗警告框,沒花裏胡哨的東西,仍是很容易區分的。

2.12 單選框和複選框(radiobox、checkbox)

本篇主要介紹單選框和複選框的操做
1、認識單選框和複選框
    1.先認清楚單選框和複選框長什麼樣

    2.各位小夥伴看清楚哦,上面的單選框是圓的;下圖複選框是方的,這個是業界的標準,要是開發小夥伴把圖標弄錯了,能夠先抽他了。
2、radio和checkbox源碼
    1.上圖的html源碼以下,把下面這段複製下來,寫到文本里,後綴改爲.html就能夠了。

複製代碼
 <html>  
    <head>  
      <meta http-equiv="content-type" content="text/html;charset=utf-8"/>  
      <title>單選和複選</title>  
    </head>  
    <body>  

    <h4>單選:性別</h4>  
    <form>  
    <label value="radio"></label>   
    <input name="sex" value="male"id="boy" type="radio"><br>  
    <label value="radio1"></label>  
    <input name="sex" value="female"id="girl" type="radio">  
    </form>  
    
    <h4>微信公衆號:從零開始學自動化測試</h4> 
    <form>  
    <!-- <labelfor="c1">checkbox1</label> --> 
    <input id="c1"type="checkbox">selenium<br>  
    <!-- <labelfor="c2">checkbox2</label> -->  
    <input id="c2"type="checkbox">python<br>  
    <!-- <labelfor="c3">checkbox3</label> -->  
    <input id="c3"type="checkbox">appium<br>  
    
    <!-- <form>  
    <input type="radio" name="sex" value="male"/> Male  
    <br />  
    <input type="radio" name="sex"value="female" /> Female  
    </form> -->  
    </body>  
    </html> 
複製代碼

3、單選:radio
  1.首先是定位選擇框的位置

 

  2.定位id,點擊圖標就能夠了,代碼以下(獲取url地址方法:把上面源碼粘貼到文本保存爲.html後綴後用瀏覽器打開,在瀏覽器url地址欄複製出地址就能夠了)
  3.先點擊boy後,等十秒再點擊girl,觀察頁面變化

 

4、複選框:checkbox
  1.勾選單個框,好比勾選selenium這個,能夠根據它的id=c1直接定位到點擊就能夠了。

  2.那麼問題來了:若是想所有勾選上呢?

5、所有勾選:
    1.所有勾選,能夠用到定位一組元素,從上面源碼能夠看出,複選框的type=checkbox,這裏能夠用xpath語法:.//*[@type='checkbox']

     2.這裏注意,敲黑板作筆記了:find_elements是不能直接點擊的,它是複數的,因此只能先獲取到全部的checkbox對象,而後經過for循環去一個個點擊操做


6、判斷是否選中:is_selected()
    1.有時候這個選項框,自己就是選中狀態,若是我再點擊一下,它就反選了,這可不是我指望的結果,那麼可不能夠當它是沒選中的時候,我去點擊下;當它已是選中狀態,我就不點擊呢?那麼問題來了:如何判斷選項框是選中狀態?
    2.判斷元素是否選中這一步纔是本文的核心內容,點擊選項框對於你們來講沒什麼難度。獲取元素是否爲選中狀態,打印結果以下圖。
    3.返回結果爲bool類型,沒點擊時候返回False,點擊後返回True,接下來就很容易判斷了,既能夠做爲操做前的判斷,也能夠做爲測試結果的判斷。

 

7、參考代碼:

複製代碼
# coding:utf-8
from selenium import webdriver
driver = webdriver.Firefox()
driver.get("file:///C:/Users/Gloria/Desktop/checkbox.html")
# 沒點擊操做前,判斷選項框狀態
s = driver.find_element_by_id("boy").is_selected()
print s
driver.find_element_by_id("boy").click()
# 點擊後,判斷元素是否爲選中狀態
r = driver.find_element_by_id("boy").is_selected()
print r
# 複選框單選
driver.find_element_by_id("c1").click()
# 複選框全選
checkboxs = driver.find_elements_by_xpath(".//*[@type='checkbox']")
for i in checkboxs:
    i.click()
複製代碼

2.13 table表格定位

前言
    在web頁面中常常會遇到table表格,特別是後臺操做頁面比較常見。本篇詳細講解table表格如何定位。
1、認識table
    1.首先看下table長什麼樣,以下圖,這種網狀表格的都是table

  2.源碼以下:(用txt文本保存,後綴改爲html)

複製代碼
<!DOCTYPE html>
<meta charset="UTF-8"> <!-- for HTML5 -->
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<html>  
        <head>  
            <title>Table測試模板</title>  
              
        </head>  
        <body>  
            <table border="1" id="myTable"> 
                <tr>  
                    <th>QQ羣</th>  
                    <th>QQ號</th>  
                    <th>羣主</th>  
                </tr>  
                <tr>  
                    <td>selenium自動化</td>  
                    <td>232607095</td>  
                    <td>YOYO</td>  
                </tr>  
                <tr>  
                    <td>appium自動化</td>  
                    <td>512200893</td>  
                    <td>YOYO</td>  
                </tr>  
            </table>  
        </body>  
</html> 
複製代碼

2、table特徵
    1.table頁面查看源碼通常有這幾個明顯的標籤:table、tr、th、td
    2.<table>標示一個表格
    3.<tr>標示這個表格中間的一個行
    4.</th> 定義表頭單元格
    5.</td> 定義單元格標籤,一組<td>標籤將將創建一個單元格,<td>標籤必須放在<tr>標籤內

3、xpath定位table
    1.舉個例子:我想定位表格裏面的「selenium自動化」元素,這裏能夠用xpath定位:.//*[@id='myTable']/tbody/tr[2]/td[1]

    2.這裏定位的格式是固定的,只需改tr和td後面的數字就能夠了.如第二行第一列tr[2]td[1].
對xpath語法不熟悉的能夠看這篇Selenium2+python自動化7-xpath定位
4、打印表格內容
    1.定位到表格內文本值,打印出來,腳本以下:

 

 5、參考代碼:

複製代碼
# coding:utf-8
from selenium import webdriver
import time
url = 'file:///C:/Users/Gloria/Desktop/table.html'
driver = webdriver.Firefox()
driver.get(url)
time.sleep(3)
t = driver.find_element_by_xpath(".//*[@id='myTable']/tbody/tr[2]/td[1]")
print t.text
複製代碼

補充說明:有些小夥伴可能會遇到table在ifame上的狀況,這時候就須要先切換iframe了。

2.14 加載Firefox配置(略,已在2.1.8講過,請查閱2.1.8節課)

2.14-1 加載Chrome配置

1、加載Chrome配置
chrome加載配置方法,只需改下面一個地方,username改爲你電腦的名字(別用中文!!!)

複製代碼
'--user-data-dir=C:\Users\username\AppData\Local\Google\Chrome\User Data'
# coding:utf-8
from selenium import webdriver
# 加載Chrome配置
option = webdriver.ChromeOptions()
option.add_argument('--user-data-dir=C:\Users\Gloria\AppData\Local\Google\Chrome\User Data')
driver = webdriver.Chrome(chrome_options=option)
driver.implicitly_wait(30)
driver.get("http://www.cnblogs.com/yoyoketang/")
複製代碼

2、Wap測試
1.作Wap測試的能夠試下,假裝成手機訪問淘寶,會出現觸屏版

 

複製代碼
# coding:utf-8
from selenium import webdriver
option = webdriver.ChromeOptions()
# 假裝iphone登陸
# option.add_argument('--user-agent=iphone')
# 假裝android
option.add_argument('--user-agent=android')
driver = webdriver.Chrome(chrome_options=option)
driver.get('http://www.taobao.com/')
複製代碼

2.15 富文本(richtext)

前言
     富文本編輯框是作web自動化最多見的場景,有不少小夥伴不知從何下手,本篇以博客園的編輯器爲例,解決如何定位富文本,輸入文本內容
1、加載配置
    1.打開博客園寫隨筆,首先須要登陸,這裏爲了不透露我的帳戶信息,我直接加載配置文件,免登陸了。
      

2、打開編輯界面
    1.博客首頁地址:bolgurl = "http://www.cnblogs.com/"
    2.個人博客園地址:yoyobolg = bolgurl + "yoyoketang"
    3.點擊「新隨筆」按鈕,id=blog_nav_newpost

3、iframe切換
    1.打開編輯界面後先不要急着輸入內容,先sleep幾秒鐘
    2.輸入標題,這裏直接經過id就能夠定位到,沒什麼難點
    3.接下來就是重點要講的富文本的編輯,這裏編輯框有個iframe,因此須要先切換

(關於iframe不懂的能夠看前面這篇:<iframe>)

 

 4、輸入正文
    1.這裏定位編輯正文是定位上圖的紅色框框位置body部分,也就是id=tinymce

    2.定位到以後,直接send_keys()方法就能夠輸入內容了

    3.有些小夥伴可能輸入不成功,能夠在輸入以前先按個table鍵,send_keys(Keys.TAB)

5、參考代碼:

複製代碼
# coding:utf-8
from selenium import webdriver
from selenium.webdriver.common.keys import Keys
import time
profileDir = r'C:\Users\Gloria\AppData\Roaming\Mozilla\Firefox\Profiles\1x41j9of.default'
profile = webdriver.FirefoxProfile(profileDir)
driver = webdriver.Firefox(profile)

bolgurl = "http://www.cnblogs.com/"
yoyobolg = bolgurl + "yoyoketang"
driver.get(yoyobolg)

driver.find_element_by_id("blog_nav_newpost").click()
time.sleep(5)
edittile = u"Selenium2+python自動化23-富文本"
editbody = u"這裏是發帖的正文"
driver.find_element_by_id("Editor_Edit_txbTitle").send_keys(edittile)

driver.switch_to.frame("Editor_Edit_EditorBody_ifr")
driver.find_element_by_id("tinymce").send_keys(Keys.TAB)
driver.find_element_by_id("tinymce").send_keys(editbody)
複製代碼

2.16-1 非input文件上傳(SendKeys)

前言
很多小夥伴問非input標籤如何上傳文檔,這個自己就是一坑,無奈不少小夥伴非要跳坑裏去,那就介紹一個非主流的上傳文件方法吧,用第三方庫SendKeys.
 
1、SendKeys安裝
1.pip安裝SendKeys
>pip install SendKeys

2.在安裝的時候若是你出現上面保存,先別急着截圖貼羣求大神,上面已經告訴解決辦法了:Get it from http://aka.ms/vcpython27
3.按上面給的地址下載文件,一路傻瓜式安裝就行
4.出現以下界面,說明安裝成功了

2、參考代碼
1.如下代碼在Chrom瀏覽器上是運行經過的,要先登陸博客園記住密碼,而後加載配置免登陸
2.chrome加載配置方法,只需改下面一個地方,username改爲你電腦的名字(別用中文!!!)

'--user-data-dir=C:\Users\username\AppData\Local\Google\Chrome\User Data'

3.後面兩次回車,是由於搜狗輸入法,第一個回車是確認輸入,第二個是肯定選中的文件

4.這裏點文件上傳按鈕也是一個坑,用工具定位的這個元素,點擊有問題,因此我改用它父元素定位了

複製代碼
# coding:utf-8
from selenium import webdriver
import SendKeys
import time
# 加載Firefox配置
# profileDir = r'C:\Users\xxxAppData\Roaming\Mozilla\Firefox\Profiles\1x41j9of.default'
# profile = webdriver.FirefoxProfile(profileDir)
# driver = webdriver.Firefox(profile)
# 加載Chrome配置
option = webdriver.ChromeOptions()
option.add_argument('--user-data-dir=C:\Users\xxxAppData\Local\Google\Chrome\User Data')
driver = webdriver.Chrome(chrome_options=option)
driver.implicitly_wait(30)
driver.get("http://www.cnblogs.com/yoyoketang/")
driver.find_element_by_link_text("新隨筆").click()
time.sleep(3)
# 點開編輯器圖片
driver.find_element_by_css_selector("img.mceIcon").click()
time.sleep(3)
# 定位全部iframe,取第二個
iframe = driver.find_elements_by_tag_name('iframe')[1]
# 切換到iframe上
driver.switch_to_frame(iframe)
# 文件路徑
time.sleep(2)
driver.find_element_by_class_name("qq-upload-button").click()
# driver.find_element_by_name("file").click()   # 這裏點文件上傳按鈕也是一個坑,我用它父元素定位了,參考上面一行
time.sleep(5)
# SendKeys方法輸入內容
SendKeys.SendKeys("D:\\test\\jie1\\blog\\12.png")  # 發送文件地址
time.sleep(1)
SendKeys.SendKeys("{ENTER}")   # 發送回車鍵
time.sleep(1)
SendKeys.SendKeys("{ENTER}")    # 由於個人電腦是搜索輸入法,因此多看一次回車
# driver.quit()
複製代碼

(備註:這裏Firefox上運行有個坑,第二次回車失效了,這個暫時沒想到好的解決辦法)
只能說到處都是坑,且用且珍惜!

2.16 文件上傳(send_keys)

前言
文件上傳是web頁面上很常見的一個功能,用腳本去實現文件上傳卻不是那麼簡單。
通常分兩個場景:一種是input標籤,這種能夠用selenium提供的send_keys()方法輕鬆解決;
另一種非input標籤實現起來比較困難,能夠藉助autoit工具或者SendKeys第三方庫。
本篇以博客園的上傳圖片爲案例,經過send_keys()方法解決文件上傳問題
1、識別上傳按鈕
1.點開博客園編輯器裏的圖片上傳按鈕,彈出」上傳本地圖片」框。
2.用firebug查看按鈕屬性,這種上傳圖片按鈕有個很明顯的標識,它是一個input標籤,而且type屬性的值爲file。只要找到這兩個標識,咱們就能夠直接用send_keys()方法上傳文件了。

 

 

2、定位iframe
1.這裏定位圖片上傳按鈕狀況有點複雜,首先它是在iframe上。
2.這個iframe的id是動態的,且沒有name屬性,其它屬性也不是很明顯。
3.經過搜索發現,這個頁面上有兩個iframe,須要定位的這個iframe是處於第二個位置。

 

4.能夠經過標籤訂位全部的iframe標籤,而後取對應的第幾個就能夠了。

 

3、文件上傳

1.先定位到文件上傳按鈕,直接調用send_keys()方法就能夠實現啦

複製代碼
# coding:utf-8
from selenium import webdriver
import time
profileDir = r'C:\Users\Gloria\AppData\Roaming\Mozilla\Firefox\Profiles\1x41j9of.default'
profile = webdriver.FirefoxProfile(profileDir)
driver = webdriver.Firefox(profile)
driver.implicitly_wait(30)
driver.get("http://www.cnblogs.com/yoyoketang/")
driver.find_element_by_link_text("新隨筆").click()
time.sleep(3)
# 點開編輯器圖片
driver.find_element_by_css_selector("img.mceIcon").click()
time.sleep(3)
# 定位全部iframe,取第二個
iframe = driver.find_elements_by_tag_name('iframe')[1]
# 切換到iframe上
driver.switch_to_frame(iframe)
# 文件路徑
driver.find_element_by_name('file').send_keys(r"D:\test\xuexi\test\14.png")
複製代碼

非input標籤的文件上傳,就不適用於此方法了,須要藉助autoit工具或者SendKeys第三方庫。

2.17 獲取元素屬性

前言
一般在作斷言以前,都要先獲取界面上元素的屬性,而後與指望結果對比。本篇介紹幾種常見的獲取元素屬性方法。
1、獲取頁面title
1.有不少小夥伴都不知道title長在哪裏,看下圖左上角。

 

2.獲取title方法很簡單,直接driver.title就能獲取到。

2、獲取元素的文本
1.以下圖這種顯示在頁面上的文本信息,能夠直接獲取到
2.查看元素屬性:<a id="setf" target="_blank" onmousedown="return ns_c({'fm':'behs','tab':'favorites','pos':0})
" href="//www.baidu.com/cache/sethelp/help.html">把百度設爲主頁</a>

3.經過driver.text獲取到文本

3、獲取元素的標籤
1.獲取百度輸入框的標籤屬性

 

4、獲取元素的其它屬性
1.獲取其它屬性方法:get_attribute("屬性"),這裏的參數能夠是class、name等任意屬性
2.如獲取百度輸入框的class屬性

5、獲取輸入框內的文本值
一、若是在百度輸入框輸入了內容,這裏輸入框的內容也是能夠獲取到的

6、獲取瀏覽器名稱
1.獲取瀏覽器名稱很簡單,用driver.name就能獲取到

# 獲取瀏覽器名稱
driver.name
7、參考代碼

複製代碼
# coding:utf-8
from selenium import webdriver
import time
driver = webdriver.Firefox()
driver.implicitly_wait(10)
driver.get("http://www.baidu.com")
time.sleep(2)

title = driver.title
print title

text = driver.find_element_by_id("setf").text
print text
# 獲取元素的標籤
tag = driver.find_element_by_id("kw").tag_name
print tag
# 獲取元素的其它屬性
name = driver.find_element_by_id("kw").get_attribute("class")
print name
# 獲取輸入框的內容
driver.find_element_by_id("kw").send_keys("yoyoketang")
value = driver.find_element_by_id("kw").get_attribute("value")
print value

# 獲取瀏覽器名稱
print driver.name
複製代碼

2.18 爬頁面源碼(page_source)

前言
有時候經過元素的屬性的查找頁面上的某個元素,可能不太好找,這時候能夠從源碼中爬出想要的信息。selenium的page_source方法能夠獲取到頁面源碼。
1、page_source
1.selenium的page_source方法能夠直接返回頁面源碼
2.從新賦值後打印出來

2、re非貪婪模式
1.這裏需導入re模塊(正則表達式模塊)
2.用re的正則匹配:非貪婪模式
3.findall方法返回的是一個list集合
4.匹配出來以後發現有一些不是url連接,能夠篩選下

3、篩選url地址出來
1.加個if語句判斷,‘http’在url裏面說明是正常的url地址了
2.把全部的url地址放到一個集合,就是咱們想要的結果啦

4、參考代碼

複製代碼
# coding:utf-8
from selenium import webdriver
import re
driver = webdriver.Firefox()
driver.get("http://www.cnblogs.com/yoyoketang/")
page = driver.page_source
# print page
# "非貪婪匹配,re.S('.'匹配字符,包括換行符)"
url_list = re.findall('href=\"(.*?)\"', page, re.S)
url_all = []
for url in url_list:
    if "http" in url:
        print url
        url_all.append(url)
# 最終的url集合
print url_all
複製代碼

2.19 cookie相關操做

前言
雖然cookie相關操做在日常ui自動化中用得少,偶爾也會用到,好比登陸有圖形驗證碼,能夠經過繞過驗證碼方式,添加cookie方法登陸。
登陸後換帳號登陸時候,也可做爲後置條件去刪除cookie而後下個帳號登陸
1、獲取cookies:get_cookies()
1.獲取cookies方法直接用:get_cookies()
2.先啓動瀏覽器,獲取cookies,打印出來發現是空:[]
3.打開博客首頁後,從新獲取cookies,打印出來,就有值了

 

2、登陸後的cookies
1.先登陸博客園(這裏登陸用本身的帳號和密碼吧)
2.從新獲取cookies,發現跟以前獲取的不同了
3.主要是找到這一個cookie,發現它的name和value發生了變化,這就是未登陸和已登陸的區別了(對比上下兩張圖)
{u'name': u'.CNBlogsCookie', u'value': u'B7813EBA142142CE88CC8C0B33B239F566xxxx'}

3、獲取指定name的cookie:driver.get_cookie(name)
1.獲取cookies發現裏面有多個cookie,有時候咱們只須要其中的一個,把重要的提出來,好比登陸的cookie
2.這裏用get_cookie(name),指定對應的cookie的name值就好了,好比博客園的:.CNBlogsCookie

4、清除指定cookie:delete_cookie()
1.爲了進一步驗證上一步獲取到的就是登陸的cookie,能夠刪除它看看頁面什麼變化
2.刪除這個cookie後刷新頁面,發現剛纔的登陸已經失效了,變成未登陸狀態了

5、清除全部cookies:delete_all_cookies()
1.清除全部cookies後登陸狀態也失效了,cookies爲空[]

6、cookie操做的幾個方法
1.get_cookies():獲取全部cookies
2.driver.get_cookie(name):獲取指定name的cookie:
3.清除指定cookie:delete_cookie()
4.delete_all_cookies():清除全部cookies
5.add_cookie(cookie_dict):添加cookie的值
(第五個方法能夠用於繞過驗證碼登陸,下篇詳細介紹)

 7、參考代碼

複製代碼
# coding:utf-8
from selenium import webdriver
import time
driver = webdriver.Firefox()
# 啓動瀏覽器後獲取cookies
print driver.get_cookies()
driver.get("http://www.cnblogs.com/yoyoketang/")
# 打開主頁後獲取cookies
print driver.get_cookies()
# 登陸後獲取cookies
url = "https://passport.cnblogs.com/user/signin"
driver.get(url)
driver.implicitly_wait(30)
driver.find_element_by_id("input1").send_keys(u"上海-悠悠")
driver.find_element_by_id("input2").send_keys(u"xxx")
driver.find_element_by_id("signin").click()
time.sleep(3)
print driver.get_cookies()
# 獲取指定name的cookie
print driver.get_cookie(name=".CNBlogsCookie")
# 清除指定name的cookie
driver.delete_cookie(name=".CNBlogsCookie")
print driver.get_cookies()
# 爲了驗證此cookie是登陸的,能夠刪除後刷新頁面
driver.refresh()
# 清除全部的cookie
driver.delete_all_cookies()
print driver.get_cookies()
複製代碼

2.20 繞過驗證碼(add_cookie)

前言
驗證碼這種問題是比較頭疼的,對於驗證碼的處理,不要去想破解方法,這個驗證碼原本就是爲了防止別人自動化登陸的。若是你能破解,說明大家公司的驗證碼嗎安全級別不高,那就須要提升級別了。
對於驗證碼,要麼是讓開發在測試環境弄個萬能的驗證碼,如:1234,要麼就是儘可能繞過去,如本篇介紹的添加cookie的方法。
1、fiddler抓包
1.前一篇講到,登陸後會生成一個已登陸狀態的cookie,那麼只須要直接把這個值添加到cookies裏面就能夠了。
2.能夠先手動登陸一次,而後抓取這個cookie,這裏就須要用抓包工具fiddler了
3.先打開博客園登陸界面,手動輸入帳號和密碼(不要點登陸按鈕)

4.打開fiddler抓包工具,此時再點博客園登陸按鈕

 

5.登陸成功後,再查看cookie變化,發現多了兩組參數,多的這兩組參數就是咱們想要的,copy出來,一會有用

2、添加cookie方法:driver.add_cookie()
1.add_cookie(cookie_dict)方法裏面參數是cookie_dict,說明裏面參數是字典類型。
2.源碼官方文檔介紹:

複製代碼
add_cookie(self, cookie_dict):
   Adds a cookie to your current session.
   
   :Args:
    - cookie_dict: A dictionary object, with required keys - "name" and "value";
       optional keys - "path", "domain", "secure", "expiry"
   
   Usage:
       driver.add_cookie({'name' : 'foo', 'value' : 'bar'})
       driver.add_cookie({'name' : 'foo', 'value' : 'bar', 'path' : '/'})
       driver.add_cookie({'name' : 'foo', 'value' : 'bar', 'path' : '/', 'secure':True})
複製代碼

3.從官方的文檔裏面能夠看出,添加cookie時候傳入字典類型就能夠了,等號左邊的是name,等號右邊的是value。
4.把前面抓到的兩組數據(參數不只僅只有name和value),寫成字典類型:
{'name':'.CNBlogsCookie','value':'2C3AE01E461B2D2F1572D02CB936D77A053089AA2xxxx...'}
{'name':'.Cnblogs.AspNetCore.Cookies','value':'CfDJ8Mmb5OBERd5FqtiQlKZZIG4HKz_Zxxx...'}

3、cookie組成結構

1.用抓包工具fidller只能看到cookie的name和value兩個參數,實際上cookie還有其它參數。
2.cookie參數組成,如下參數是我經過get_cookie(name)獲取到的。

複製代碼
cookie ={u'domain': u'.cnblogs.com',
            u'name': u'.CNBlogsCookie',
            u'value': u'xxxx',
            u'expiry': 1491887887,
            u'path': u'/',
            u'httpOnly': True,
            u'secure': False}

name:cookie的名稱
value:cookie對應的值,動態生成的
domain:服務器域名
expiry:Cookie有效終止日期
path:Path屬性定義了Web服務器上哪些路徑下的頁面可獲取服務器設置的Cookie
httpOnly:防腳本攻擊
secure:在Cookie中標記該變量,代表只有當瀏覽器和Web Server之間的通訊協議爲加密認證協議時,
瀏覽器才向服務器提交相應的Cookie。當前這種協議只有一種,即爲HTTPS。
複製代碼

4、添加cookie
1.這裏須要添加兩個cookie,一個是.CNBlogsCookie,另一個是.Cnblogs.AspNetCore.Cookies。
2.我這裏打開的網頁是博客的主頁:http://www.cnblogs.com/yoyoketang,沒進入登陸頁。
3.添加cookie後刷新頁面,接下來就是見證奇蹟的時刻了。

5、參考代碼:

複製代碼
# coding:utf-8
from selenium import webdriver
import time
driver = webdriver.Firefox()
driver.get("http://www.cnblogs.com/yoyoketang")
# # 添加cookie
c1 = {u'domain': u'.cnblogs.com',
      u'name': u'.CNBlogsCookie',
      u'value': u'xxxx',
      u'expiry': 1491887887,
      u'path': u'/',
      u'httpOnly': True,
      u'secure': False}
c2 = {u'domain': u'.cnblogs.com',
      u'name': u'.Cnblogs.AspNetCore.Cookies',
      u'value': u'xxxx',
      u'expiry': 1491887887,
      u'path': u'/',
      u'httpOnly': True,
      u'secure': False}
driver.add_cookie(c1)  # 添加2個值
driver.add_cookie(c2)
time.sleep(3)          # 交流QQ羣:232607095
# 刷新下頁面就見證奇蹟了
driver.refresh()  
複製代碼

有幾點須要注意:

1.登陸時候要勾選下次自動登陸按鈕。

2.add_cookie()只添加name和value,對於博客園的登陸是不成功。

3.本方法並不適合全部的網站,通常像博客園這種記住登陸狀態的纔會適合。

2.21 JS處理滾動條

前言
    selenium並非萬能的,有時候頁面上操做沒法實現的,這時候就須要藉助JS來完成了。
常見場景:
當頁面上的元素超過一屏後,想操做屏幕下方的元素,是不能直接定位到,會報元素不可見的。這時候須要藉助滾動條來拖動屏幕,使被操做的元素顯示在當前的屏幕上。滾動條是沒法直接用定位工具來定位的。selenium裏面也沒有直接的方法去控制滾動條,這時候只能藉助J了,還好selenium提供了一個操做js的方法:execute_script(),能夠直接執行js的腳本。

1、JavaScript簡介

1.JavaScript是世界上最流行的腳本語言,由於你在電腦、手機、平板上瀏覽的全部的網頁,以及無數基於HTML5的手機App,交互邏輯都是由JavaScript驅動的。簡單地說,JavaScript是一種運行在瀏覽器中的解釋型的編程語言。那麼問題來了,爲何咱們要學JavaScript?

2.有些特殊的操做selenium2+python沒法直接完成的,JS恰好是這方面的強項,因此算是一個很好的補充。對js不太熟悉的,能夠網上找下教程,簡單瞭解些便可。
http://www.w3school.com.cn/js/index.asp4

2、控制滾動條高度
1.滾動條回到頂部:

js="var q=document.getElementById('id').scrollTop=0"
driver.execute_script(js)

2.滾動條拉到底部

js="var q=document.documentElement.scrollTop=10000"
driver.execute_script(js)

3.這裏能夠修改scrollTop 的值,來定位右側滾動條的位置,0是最上面,10000是最底部。

3、橫向滾動條
1.有時候瀏覽器頁面須要左右滾動(通常屏幕最大化後,左右滾動的狀況已經不多見了)。

2.經過左邊控制橫向和縱向滾動條

scrollTo(x, y)js = "window.scrollTo(100,400);"
driver.execute_script(js)

3.第一個參數x是橫向距離,第二個參數y是縱向距離

4、Chrome瀏覽器
1.以上方法在Firefox上是能夠的,可是用Chrome瀏覽器,發現無論用。
谷歌瀏覽器就是這麼任性,不聽話,因而用如下方法解決谷歌瀏覽器滾動條的問題。
2.Chrome瀏覽器解決辦法:

js = "var q=document.body.scrollTop=0"
driver.execute_script(js)
 
5、元素聚焦
1.雖然用上面的方法能夠解決拖動滾動條的位置問題,可是有時候沒法肯定我須要操做的元素
在什麼位置,有可能每次打開的頁面不同,元素所在的位置也不同,怎麼辦呢?
2.這個時候咱們能夠先讓頁面直接跳到元素出現的位置,而後就能夠操做了。一樣須要藉助JS去實現。
3.元素聚焦:
target = driver.find_element_by_xxxx()
driver.execute_script("arguments[0].scrollIntoView();", target)

6、獲取瀏覽器名稱:driver.name
1.爲了解決不一樣瀏覽器操做方法不同的問題,能夠寫個函數去作兼容。
2.先用driver.name獲取瀏覽器名稱,而後用if語句作個判斷

 

 

7、兼容性
1.兼容谷歌和firefox/IE

8、scrollTo函數
樓下有個小夥伴說這個scrollTo函數不存在兼容性問題,小編借花獻佛了。
--scrollHeight 獲取對象的滾動高度。 
--scrollLeft 設置或獲取位於對象左邊界和窗口中目前可見內容的最左端之間的距離。 
--scrollTop 設置或獲取位於對象最頂端和窗口中可見內容的最頂端之間的距離。

--scrollWidth 獲取對象的滾動寬度。 

scrollTo函數不存在兼容性問題,直接用這個函數就能夠了

#滾動到底部
js = "window.scrollTo(0,document.body.scrollHeight)"
driver.execute_script(js)
#滾動到頂部
js = "window.scrollTo(0,0)"  
driver.execute_script(js)

9、參考代碼以下:

複製代碼
# coding:utf-8
from selenium import webdriver
driver = webdriver.Firefox()
driver.get("https://www.baidu.com")
print driver.name
## 回到頂部
#def scroll_top():
#        if driver.name == "chrome":
#               js = "var q=document.body.scrollTop=0"
#        else:
#                js = "var q=document.documentElement.scrollTop=0"
#        return driver.execute_script(js)
# 拉到底部
#def scroll_foot():
#       if driver.name == "chrome":
#                js = "var q=document.body.scrollTop=10000"
#        else:
#                js = "var q=document.documentElement.scrollTop=10000"
#        return driver.execute_script(js)
#滾動到底部
js = "window.scrollTo(0,document.body.scrollHeight)"
driver.execute_script(js)
#滾動到頂部
js = "window.scrollTo(0,0)"  
driver.execute_script(js)
# 聚焦元素
target = driver.find_element_by_xxxx()
driver.execute_script("arguments[0].scrollIntoView();", target)
複製代碼

JS功能仍是很強大的,它還能夠處理富文本、內嵌滾動條的問題。

2.22 JS處理富文本

前言
    <富文本>這篇解決了富文本上iframe問題,其實沒什麼特別之處,主要是iframe的切換,本篇講解經過js的方法處理富文本上iframe的問題
1、加載配置
    1.打開博客園寫隨筆,首先須要登陸,這裏爲了不透露我的帳戶信息,我直接加載配置文件,免登陸了。
      不懂如何加載配置文件的,看加載firefox配置

2、打開編輯界面
    1.博客首頁地址:bolgurl = "http://www.cnblogs.com/"
    2.個人博客園地址:yoyobolg = bolgurl + "yoyoketang"
    3.點擊「新隨筆」按鈕,id=blog_nav_newpost

3、定位iframe
    1.打開編輯界面後先不要急着輸入內容,先sleep幾秒鐘
    2.輸入標題,這裏直接經過id就能夠定位到,沒什麼難點
    3.接下來就是重點要講的富文本的編輯,這裏編輯框有個iframe,因此須要先切換

 

 4、js輸入中文
    1.這裏定位編輯正文是定位上圖的紅色框框位置body部分,也就是id=tinymce

    2.定位到以後,用js的方法直接輸入,無需切換iframe

    3.直接點保存按鈕,無需再切回來

5、參考代碼:

複製代碼
# coding:utf-8
from selenium import webdriver
from selenium.webdriver.common.keys import Keys
import time
# profileDir路徑對應直接電腦的配置路徑
profileDir = r'C:\xxx\xxx\AppData\Roaming\Mozilla\Firefox\Profiles\1x41j9of.default'
profile = webdriver.FirefoxProfile(profileDir)
driver = webdriver.Firefox(profile)
bolgurl = "http://www.cnblogs.com/"
yoyobolg = bolgurl + "yoyoketang"
driver.get(yoyobolg)
driver.find_element_by_id("blog_nav_newpost").click()
time.sleep(5)
edittile = u"Selenium2+python自動化23-富文本"
editbody = u"這裏是發帖的正文"
driver.find_element_by_id("Editor_Edit_txbTitle").send_keys(edittile)
body = "這裏是經過js發的正文內容"
# js處理iframe問題(js代碼太長了,我分紅兩行了)
js = 'document.getElementById("Editor_Edit_EditorBody_ifr")' \
     '.contentWindow.document.body.innerHTML="%s"' % body
driver.execute_script(js)
# 保存草稿
driver.find_element_by_id("Editor_Edit_lkbDraft").click()
複製代碼

2.23 js處理日曆控件(修改readonly屬性)

前言
    日曆控件是web網站上常常會遇到的一個場景,有些輸入框是能夠直接輸入日期的,有些不能,以咱們常常搶票的12306網站爲例,詳細講解如何解決日曆控件爲readonly屬性的問題。
    基本思路:先用js去掉readonly屬性,而後直接輸入日期文本內容
1、日曆控件
    1.打開12306的車票查詢界面,在出發日期輸入框沒法直接輸入時間
    2.常規思路是點開日曆控件彈出框,從日曆控件上點日期,這樣操做比較煩躁,而且咱們測試的重點不在日曆控件上,只是想輸入個時間,作下一步的操做
    3.用firebug查看輸入框的屬性:readonly="readonly",以下:

<input id="train_date" class="inp-txt" type="text" value="" name="leftTicketDTO.train_date" autocomplete="off" maxlength="10" readonly="readonly">

 

 2、去掉readonly屬性

    1.很明顯這種元素的屬性是readonly,輸入框是沒法直接輸入的,這時候須要先去掉元素的readonly屬性,而後就能夠輸入啦。

    2.點左下角firebug的「編輯按鈕」,找到對應元素,直接刪除readonly="readonly",而後回車。

    3.在頁面出發日位置輸入:yoyoketang 試試,嘿嘿,有沒有發現能夠輸入成功。固然這裏只是爲了驗證能夠輸入內容,測試時候仍是輸入測試的日期。

3、用js去掉readonly屬性
    1.用js去掉元素屬性基本思路:先定位到元素,而後用removeAttribute("readonly")方法刪除屬性。
    2.出發日元素id爲:train_date,對應js代碼爲:'document.getElementById("train_date").removeAttribute("readonly");'

4、輸入日期
    1.輸入日期前,必定要先清空文本,要否則沒法輸入成功的。
    2.這裏輸入日期後,會自動彈出日曆控件,隨便點下其它位置就行了,接下來會用js方法傳入日期,就不會彈啦!

 

5、js方法輸入日期
   1.這裏也能夠用js方法輸入日期,其實很簡單,直接改掉輸入框元素的value值就能夠啦。

6、參考代碼以下:

複製代碼
from selenium import webdriver
driver = webdriver.Firefox()
driver.get("https://kyfw.12306.cn/otn/index/init")
# 去掉元素的readonly屬性
js = 'document.getElementById("train_date").removeAttribute("readonly");'
driver.execute_script(js)
# 用js方法輸入日期
js_value = 'document.getElementById("train_date").value="2016-12-25"'
driver.execute_script(js_value)
# # 清空文本後輸入值
# driver.find_element_by_id("train_date").clear()
# driver.find_element_by_id("train_date").send_keys("2016-12-25")
複製代碼

 

2.24 js處理內嵌div滾動條

前言
    前面有篇專門用js解決了瀏覽器滾動條的問題,生活老是多姿多彩,有的滾動條就在頁面上,這時候又得仰仗js大哥來解決啦。
1、內嵌滾動條
    1.下面這張圖就是內嵌div帶有滾動條的樣子,記住它的長相。

    2.頁面源碼以下:(老規矩:copy下來,用文本保存下來,後綴改爲.html,用瀏覽器打開)

複製代碼
<!DOCTYPE html>
<meta charset="UTF-8"> <!-- for HTML5 -->
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<html>
  <head>
    <style type="text/css">
      div.scroll
      {
        background-color:#afafaf;
        width:500px;
        height:100px;
        overflow:auto;
      }
    </style>
  </head>


  <body>
    <p>我的微信公衆號:yoyoketang</p>
    <p>這是一個內嵌的div滾動條</p>
    <div id="yoyoketang" name="yoyo" class="scroll">這是一個內嵌div:民國年間,九你們族鎮守長沙,被稱爲「九門提督」。這九門勢力龐大,外八行的無人不知,無人不
曉,幾乎全部冥器,流出長沙必然通過其中一家。1933年秋,一輛神祕鬼車緩緩駛入長沙火車站,九門之首「張大佛爺」張啓山身爲佈防官,奉命調查始末。張啓山與八爺齊鐵嘴一路探訪,發現長沙城外有一座疑點重重的礦山,一直被日本人窺伺。
爲破解礦山之謎,張啓山求助同爲九門上三門的戲曲名伶二月紅,無奈二月紅雖出身考古世家,卻心繫重病的妻子丫頭,早已金盆洗手。張啓山爲了國家大義和手足之情,北上去往新月飯店爲二月紅愛妻求藥。在北平,張啓山邂逅了新月飯店的大小姐尹新月,併爲尹新月連點三盞天燈,散盡家財。尹新月幫助張啓山等人順利返回
長沙,二人暗生情愫。二月紅愛妻病入膏肓,服藥後不見好轉,最終故去。二月紅悲傷之餘卻意外發現家族祖輩與礦山亦有重大關聯,因而振做精神,決定與張啓山聯手,解開礦山之謎zhegedancihenchanghenchangchangchangchangchanchanchanchangchangchangchancg
    </div>
  </body>
</html>
複製代碼

2、縱向滾動

    1.這個是div的屬性:<div id="yoyoketang" name="yoyo" class="scroll">

    2.這裏最簡單的經過id來定位,經過控制 scrollTop的值來控制滾動條高度

    3.運行下面代碼,觀察頁面是否是先滾動到底部,過五秒再回到頂部。(get裏面地址是瀏覽器打開該頁面的地址)

 

3、橫向滾動

  1.先經過id來定位,經過控制scrollLeft的值來控制滾動條高度

4、用class屬性定位
    1.js用class屬性定位,返回的是一個list對象,這裏取第一個就能夠了。
    2.這裏要注意了,element和elements有不少小夥伴傻傻分不清楚。

有時候不少元素屬性都同樣時候,就能夠用複數定位,取對應的第幾個就能夠了。

2.25 js處理多窗口

前言
在打開頁面上連接的時候,常常會彈出另一個窗口(多窗口狀況前面這篇有講解:Selenium2+python自動化13-多窗口、句柄(handle)),這樣在多個窗口之間來回切換比較複雜,那麼有沒有辦法讓新打開的連接在一個窗口打開呢?
要解決這個問題,得從html源碼上找到緣由,而後修改元素屬性才能解決。很顯然js在這方面是萬能的,因而本篇得依靠萬能的js大哥了。
1、多窗口狀況
    1.在打baidu的網站連接時,會從新打開一個窗口
    (注意:個人百度頁面是已登陸狀態,沒登陸時候是不會從新打開窗口的)

2、查看元素屬性:target="_blank"
1.查看元素屬性,會發現這些連接有個共同屬性:target="_blank"

3、去掉target="_blank"屬性
1.由於此連接元素target="_blank",因此打開連接的時候會從新打開一個標籤頁,那麼解決這個問題,去掉該屬性就能夠了。
2.爲了驗證這個問題,能夠切換到html編輯界面,手動去掉「_blank」屬性。

 

3.刪除「_blank」屬性後,從新打開連接,這時候會發現打開的新連接會在原標籤頁打開。

4、js去掉target="_blank"屬性
1.第一步爲了先登陸,我這裏加載配置文件免登陸了(不會的看這篇:Selenium2+python自動化18-加載Firefox配置)
2.這裏用到js的定位方法,定位該元素的class屬性
3.定位到該元素後直接修改target屬性值爲空

5、參考代碼

複製代碼
# coding:utf-8
from selenium import webdriver
from selenium.webdriver.common.keys import Keys
import time
# 加載配置文件免登陸
profileDir = r'C:\Users\Gloria\AppData\Roaming\Mozilla\Firefox\Profiles\1x41j9of.default'
profile = webdriver.FirefoxProfile(profileDir)
driver = webdriver.Firefox(profile)
driver.get("https://www.baidu.com/")
# 修改元素的target屬性
js = 'document.getElementsByClassName("mnav")[0].target="";'
driver.execute_script(js)
driver.find_element_by_link_text("糯米").click()
複製代碼

注意:並非全部的連接都適用於本方法,本篇只適用於有這個target="_blank"屬性連接狀況。

本篇僅提供解決問題的辦法和思路,不要徹底照搬代碼!!!

2.26 js解決click失效問題

前言
有時候元素明明已經找到了,運行也沒報錯,點擊後頁面沒任何反應。這種問題遇到了,是比較頭疼的,由於沒任何報錯,只是click事件失效了。
本篇用2種方法解決這種詭異的點擊事件失效問題
1、遇到的問題
1.在練習百度的搜索設置按鈕時,點保存設置按鈕,alert彈出沒彈出(代碼沒報錯,只是獲取alert失敗),相信不僅是我一我的遇到過。

2、點擊父元素
1.遇到這種問題,應該是前面操做select後致使的後遺症(由於我註釋掉select那段是能夠點擊成功的)。
2.第一種解決辦法,先點擊它的父元素一次,而後再點擊這個元素。

3.實現代碼以下

3、js直接點擊

1.遇到這種詭異問題,是時候出絕招了:js大法。
2.用js直接執行點擊事件。

4、參考代碼

複製代碼
# coding:utf-8
from selenium import webdriver
from selenium.webdriver.common.action_chains import ActionChains
from selenium.webdriver.support.select import Select
import time
driver = webdriver.Firefox()
url = "https://www.baidu.com"
driver.get(url)
time.sleep(3)
mouse = driver.find_element("link text", "設置")
ActionChains(driver).move_to_element(mouse).perform()
time.sleep(3)
driver.find_element("link text", "搜索設置").click()
time.sleep(3)
s = driver.find_element("id", "nr")
Select(s).select_by_visible_text("每頁顯示50條")
# 方法一:先點父元素 交流QQ羣:232607095
# driver.find_element("id", "gxszButton").click()
# driver.find_element("class name", "prefpanelgo").click()
# 方法二:用js直接去點擊 交流QQ羣:232607095
js = 'document.getElementsByClassName("prefpanelgo")[0].click();'
driver.execute_script(js)
複製代碼

2.27 18種定位方法總結

前言
江湖傳言,武林中流傳八種定位,其中xpath是寶刀屠龍,css是倚天劍。
除了這八種,其實還有十種定位方法,眼看就快失傳了,今天小編讓失傳已久的定位方法重出江湖!

1、十八種定位方法

前八種是你們都熟悉的,常常會用到的

1.id定位:find_element_by_id(self, id_)
2.name定位:find_element_by_name(self, name)
3.class定位:find_element_by_class_name(self, name)
4.tag定位:find_element_by_tag_name(self, name)
5.link定位:find_element_by_link_text(self, link_text)
6.partial_link定位find_element_by_partial_link_text(self, link_text)
7.xpath定位:find_element_by_xpath(self, xpath)
8.css定位:find_element_by_css_selector(self, css_selector)

這八種是複數形式

9.id複數定位find_elements_by_id(self, id_)
10.name複數定位find_elements_by_name(self, name)
11.class複數定位find_elements_by_class_name(self, name)
12.tag複數定位find_elements_by_tag_name(self, name)
13.link複數定位find_elements_by_link_text(self, text)
14.partial_link複數定位find_elements_by_partial_link_text(self, link_text)
15.xpath複數定位find_elements_by_xpath(self, xpath)
16.css複數定位find_elements_by_css_selector(self, css_selector)

這兩種就是快失傳了的

17.find_element(self, by='id', value=None)
18.find_elements(self, by='id', value=None)

2、element和elements傻傻分不清
1.element方法定位到是是單數,是直接定位到元素
2.elements方法是複數,這個學過英文的都知道,定位到的是一組元素,返回的是list隊列
3.能夠用type()函數查看數據類型
4.打印這個返回的內容看看有什麼不同

3、elements定位方法
1.前面2.8章節講過定位一組元素用elements的方法,elements也能夠用於單數定位。

2.這裏重點介紹下用elements方法如何定位元素,當一個頁面上有多個屬性相同的元素時,而後父元素的屬性也比較模糊,不太好定位。這個時候不用怕,換個思惟,別老想着一次定位到,能夠先把相同屬性的元素找出來,取對應的第幾個就能夠了。

3.以下圖,百度頁面上有六個class同樣的元素,我要定位「地圖」這個元素。

4.取對應下標便可定位了。

4、參考代碼

複製代碼
# coding:utf-8
from selenium import webdriver
driver = webdriver.Firefox()
driver.get("http://www.baidu.com")
# 這裏是定位的單個id
element = driver.find_element_by_id("kw")
print type(element)
print element
# 這裏定位是多個class
elements = driver.find_elements_by_class_name("mnav")
print type(elements)
print elements
# 這裏用的css語法
s = driver.find_elements("css selector", ".mnav")
# '地圖'在第四個位置
print s[3].text
s[3].click()
# 這個寫法也是能夠的
# driver.find_elements("css selector", ".mnav")[3].click()
複製代碼

2.28 查看webdriver API(帶翻譯)

前言
    前面都是點點滴滴的介紹selenium的一些api使用方法,那麼selenium的api到底有多少呢?本篇就教你們如何去查看selenium api,不求人,無需伸手找人要,在本身電腦就有。
    pydoc是Python自帶的模塊,主要用於從python模塊中自動生成文檔,這些文檔能夠基於文本呈現的、也能夠生成WEB 頁面的,還能夠在服務器上以瀏覽器的方式呈現!
1、pydoc
    1.到底什麼是pydoc? ,這個是準確的解釋:Documentation generator and online help system. pydoc是Python自帶的模塊,主要用於從python模塊中自動生成文檔,這些文檔能夠基於文本呈現的、也能夠生成WEB
頁面的,還能夠在服務器上以瀏覽器的方式呈現!簡而言之,就是幫你從代碼和註釋自動生成文檔的工具。

    2.舉個栗子,我須要查看python裏面open函數的功能和語法,打開cmd,輸入:python -m pydoc open

    3.-m參數:python以腳本方法運行模塊
>>python -m pydoc open

 

 那麼問題來了,這個是已經知道有這個函數,去查看它的功能,selenium裏面不知道到底有多少個函數或方法,那如何查看呢?

2、啓動server
    1.打開cmd命令行,輸入:python -m pydoc -p 6666
    2.-p參數:這個表示在本機上啓動服務
    3.6666參數:這個是服務端口號,隨意設置

打開後,界面會出現一個地址:http://localhost:6666/,在瀏覽器直接打開。

3、瀏覽器查看文檔
    1.在瀏覽器輸入:http://localhost:6666/
    2.Built-in Moudles :這個是python自帶的模塊

 

4、webdriver API

    1.找到這個路徑:python2.7\lib\site-packages,點開selenium
    2.打開的selenium>webdriver>firefox>webdriver,最終路徑:http://localhost:6666/selenium.webdriver.firefox.webdriver.html
    3.最終看到的這些就是selenium的webdriver API幫助文檔啦

【附錄】webdriver API(帶翻譯)

    1.找到這個路徑:python2.7\lib\site-packages,點開selenium
    2.打開的selenium>webdriver>firefox>webdriver,最終路徑:http://localhost:6666/selenium.webdriver.firefox.webdriver.html
    3.最終看到的這些就是selenium的webdriver API幫助文檔啦

複製代碼
1.add_cookie(self,cookie_dict)
##翻譯:添加cookie,cookie參數爲字典數據類型
Adds a cookie to your current session.
:Args:
- cookie_dict: A dictionary object, with required keys - "name" and"value";
optional keys - "path", "domain", "secure","expiry"
Usage:
driver.add_cookie({'name' : 'foo', 'value' : 'bar'})
driver.add_cookie({'name' : 'foo', 'value' : 'bar', 'path' : '/'})
driver.add_cookie({'name' : 'foo', 'value' : 'bar', 'path' : '/','secure':True})
2.back(self)
##瀏覽器返回
Goes one step backward in the browser history.

:Usage:
driver.back()
3.close(self)
##關閉瀏覽器
Closes the current window.
:Usage:
driver.close()
4.create_web_element(self,element_id)
##給元素分配一個id
Creates a web element with the specified element_id.
5.delete_all_cookies(self)
##刪除全部的cookies

Delete all cookies in the scope of the session.
:Usage:
driver.delete_all_cookies()
6.delete_cookie(self,name)
##刪除指定name的cookie
Deletes a single cookie with the given name.
:Usage:
driver.delete_cookie('my_cookie')
7.execute(self,driver_command, params=None)
Sends a command to be executed by a command.CommandExecutor.
:Args:
- driver_command: The name of the command to execute as a string.

- params: A dictionary of named parameters to send with the command.
:Returns:
The command's JSON response loaded into a dictionary object.
8.execute_async_script(self,script, *args)
Asynchronously Executes JavaScript in the current window/frame.
:Args:
- script: The JavaScript to execute.
- \*args: Any applicable arguments for your JavaScript.
:Usage:
driver.execute_async_script('document.title')
9.execute_script(self,script, *args)

##執行JS
Synchronously Executes JavaScript in the current window/frame.
:Args:
- script: The JavaScript to execute.
- \*args: Any applicable arguments for your JavaScript.
:Usage:
driver.execute_script('document.title')
10.file_detector_context(*args,**kwds)
Overrides the current file detector (if necessary) in limited context.
Ensures the original file detector is set afterwards.
Example:
with webdriver.file_detector_context(UselessFileDetector):

someinput.send_keys('/etc/hosts')
:Args:
- file_detector_class - Class of the desired file detector. If the class is different
from the current file_detector, then the class is instantiated with args andkwargs
and used as a file detector during the duration of the context manager.
- args - Optional arguments that get passed to the file detector class during
instantiation.
- kwargs - Keyword arguments, passed the same way as args.
11.find_element(self,by='id', value=None)
##定位元素,參數化的方法

'Private' method used by the find_element_by_* methods.
:Usage:
Use the corresponding find_element_by_* instead of this.
:rtype: WebElement
12.find_element_by_class_name(self,name)
##經過class屬性定位元素
Finds an element by class name.
:Args:
- name: The class name of the element to find.
:Usage:
driver.find_element_by_class_name('foo')
13.find_element_by_css_selector(self,css_selector)

##經過css定位元素
Finds an element by css selector.
:Args:
- css_selector: The css selector to use when finding elements.
:Usage:
driver.find_element_by_css_selector('#foo')
14.find_element_by_id(self,id_)
##經過id定位元素
Finds an element by id.
:Args:
- id\_ - The id of the element to be found.
:Usage:

driver.find_element_by_id('foo')
15.find_element_by_link_text(self,link_text)
##經過link連接定位
Finds an element by link text.
:Args:
- link_text: The text of the element to be found.
:Usage:
driver.find_element_by_link_text('Sign In')
16.find_element_by_name(self,name)
##經過name屬性定位
Finds an element by name.
:Args:

- name: The name of the element to find.
:Usage:
driver.find_element_by_name('foo')
17.find_element_by_partial_link_text(self,link_text)
##經過部分link的模糊定位
Finds an element by a partial match of its link text.
:Args:
- link_text: The text of the element to partially match on.
:Usage:
driver.find_element_by_partial_link_text('Sign')
18.find_element_by_tag_name(self,name)
##經過標籤訂位

Finds an element by tag name.
:Args:
- name: The tag name of the element to find.
:Usage:
driver.find_element_by_tag_name('foo')
19.find_element_by_xpath(self,xpath)
##經過xpath語法定位
Finds an element by xpath.
:Args:
- xpath - The xpath locator of the element to find.
:Usage:
driver.find_element_by_xpath('//div/td[1]')

20.find_elements(self,by='id', value=None)
##定位一組元素
'Private' method used by the find_elements_by_* methods.
:Usage:
Use the corresponding find_elements_by_* instead of this.
:rtype: list of WebElement
21.find_elements_by_class_name(self,name)
Finds elements by class name.
:Args:
- name: The class name of the elements to find.
:Usage:
driver.find_elements_by_class_name('foo')

22.find_elements_by_css_selector(self,css_selector)
Finds elements by css selector.
:Args:
- css_selector: The css selector to use when finding elements.
:Usage:
driver.find_elements_by_css_selector('.foo')
23.find_elements_by_id(self,id_)
Finds multiple elements by id.
:Args:
- id\_ - The id of the elements to be found.
:Usage:
driver.find_elements_by_id('foo')

24.find_elements_by_link_text(self,text)
Finds elements by link text.
:Args:
- link_text: The text of the elements to be found.
:Usage:
driver.find_elements_by_link_text('Sign In')
25.find_elements_by_name(self,name)
Finds elements by name.
:Args:
- name: The name of the elements to find.
:Usage:
driver.find_elements_by_name('foo')

26.find_elements_by_partial_link_text(self,link_text)
Finds elements by a partial match of their link text.
:Args:
- link_text: The text of the element to partial match on.
:Usage:
driver.find_element_by_partial_link_text('Sign')
27.find_elements_by_tag_name(self,name)
Finds elements by tag name.
:Args:
- name: The tag name the use when finding elements.
:Usage:
driver.find_elements_by_tag_name('foo')

28.find_elements_by_xpath(self,xpath)
Finds multiple elements by xpath.
:Args:
- xpath - The xpath locator of the elements to be found.
:Usage:
driver.find_elements_by_xpath("//div[contains(@class, 'foo')]")
29.forward(self)
##切換到下一頁面
Goes one step forward in the browser history.
:Usage:
driver.forward()
30.get(self, url)

##打開url地址
Loads a web page in the current browser session.
31.get_cookie(self,name)
##獲取指定名稱的cookie
Get a single cookie by name. Returns the cookie if found, None if not.
:Usage:
driver.get_cookie('my_cookie')
32.get_cookies(self)
##獲取全部的cookies
Returns a set of dictionaries, corresponding to cookies visible in the currentsession.
:Usage:

driver.get_cookies()
33.get_log(self,log_type)
Gets the log for a given log type
:Args:
- log_type: type of log that which will be returned
:Usage:
driver.get_log('browser')
driver.get_log('driver')
driver.get_log('client')
driver.get_log('server')
34.get_screenshot_as_base64(self)
##截圖base64格式

Gets the screenshot of the current window as a base64 encoded string
which is useful in embedded images in HTML.
:Usage:
driver.get_screenshot_as_base64()
35.get_screenshot_as_file(self,filename)
##截圖保存爲指定文件名稱
Gets the screenshot of the current window. Returns False if there is
any IOError, else returns True. Use full paths in your filename.
:Args:
- filename: The full path you wish to save your screenshot to.
:Usage:
driver.get_screenshot_as_file('/Screenshots/foo.png')

36.get_screenshot_as_png(self)
##截圖爲png格式二進制流
Gets the screenshot of the current window as a binary data.
:Usage:
driver.get_screenshot_as_png()
37.get_window_position(self,windowHandle='current')
Gets the x,y position of the current window.
:Usage:
driver.get_window_position()
38.get_window_size(self,windowHandle='current')
##獲取窗口的寬高
Gets the width and height of the current window.

:Usage:
driver.get_window_size()
39.implicitly_wait(self,time_to_wait)
##隱式等待
Sets a sticky timeout to implicitly wait for an element to be found,
or a command to complete. This method only needs to be called one
time per session. To set the timeout for calls to
execute_async_script, see set_script_timeout.
:Args:
- time_to_wait: Amount of time to wait (in seconds)
:Usage:
driver.implicitly_wait(30)

40.maximize_window(self)
##最大化窗口
Maximizes the current window that webdriver is using
41.refresh(self)
##刷新頁面
Refreshes the current page.
:Usage:
driver.refresh()
save_screenshot = get_screenshot_as_file(self, filename)
Gets the screenshot of the current window. Returns False if there is
any IOError, else returns True. Use full paths in your filename.
:Args:

- filename: The full path you wish to save your screenshot to.
:Usage:
driver.get_screenshot_as_file('/Screenshots/foo.png')
42.set_page_load_timeout(self,time_to_wait)
##設置頁面加載超時時間
Set the amount of time to wait for a page load to complete
before throwing an error.
:Args:
- time_to_wait: The amount of time to wait
:Usage:
driver.set_page_load_timeout(30)
43.set_script_timeout(self,time_to_wait)

Set the amount of time that the script should wait during an
execute_async_script call before throwing an error.
:Args:
- time_to_wait: The amount of time to wait (in seconds)
:Usage:
driver.set_script_timeout(30)
44.set_window_position(self,x, y, windowHandle='current')
Sets the x,y position of the current window. (window.moveTo)
:Args:
- x: the x-coordinate in pixels to set the window position
- y: the y-coordinate in pixels to set the window position
:Usage:

driver.set_window_position(0,0)
45.set_window_size(self,width, height, windowHandle='current')
##設置窗口大小
Sets the width and height of the current window. (window.resizeTo)
:Args:
- width: the width in pixels to set the window to
- height: the height in pixels to set the window to
:Usage:
driver.set_window_size(800,600)
46.start_client(self)
Called before starting a new session. This method may be overridden
to define custom startup behavior.

start_session(self, desired_capabilities,browser_profile=None)
Creates a new session with the desired capabilities.
:Args:
- browser_name - The name of the browser to request.
- version - Which browser version to request.
- platform - Which platform to request the browser on.
- javascript_enabled - Whether the new session should support JavaScript.
- browser_profile - A selenium.webdriver.firefox.firefox_profile.FirefoxProfileobject. Only used if Firefox is requested.
47.stop_client(self)
Called after executing a quit command. This method may be overridden

to define custom shutdown behavior.
48.switch_to_active_element(self)
##切換到活動的元素上,通常失去焦點時候會用到
Deprecated use driver.switch_to.active_element
49.switch_to_alert(self)
##切換到alert彈出框上
Deprecated use driver.switch_to.alert
50.switch_to_default_content(self)
##切換到默認的主頁面上
Deprecated use driver.switch_to.default_content
51.switch_to_frame(self,frame_reference)
##切換iframe

Deprecated use driver.switch_to.frame
52.switch_to_window(self,window_name)
##切換窗口
Deprecated use driver.switch_to.window
Data descriptors inherited fromselenium.webdriver.remote.webdriver.WebDriver:
__dict__
dictionary for instance variables (if defined)
__weakref__
list of weak references to the object (if defined)
53.application_cache
Returns a ApplicationCache Object to interact with the browser app cache

54.current_url
##獲取當前頁面的url地址
Gets the URL of the current page.
:Usage:
driver.current_url
55.current_window_handle
##獲取當前頁面handle
Returns the handle of the current window.
:Usage:
driver.current_window_handle
56.desired_capabilities

returns the drivers current desired capabilities being used
57.file_detector
58.log_types
Gets a list of the available log types
:Usage:
driver.log_types
59.mobile
60.name
##獲取瀏覽器名稱
Returns the name of the underlying browser for this instance.
:Usage:
- driver.name

61.orientation
Gets the current orientation of the device
:Usage:
orientation = driver.orientation
62.page_source
##獲取頁面源碼
Gets the source of the current page.
:Usage:
driver.page_source
63.switch_to
##切換iframe,handle等方法
64.title

##獲取頁面title
Returns the title of the current page.
:Usage:
driver.title
65.window_handles
##獲取全部的handle
Returns the handles of all windows within the current session.
:Usage:
driver.window_handles
複製代碼

 

小編後續有空再翻譯下吧,英文水平有限。在學習過程當中有遇到疑問的,能夠加selenium(python+java) QQ羣交流:232607095

 

2.29 練習題1:去掉頁面動態窗

咱們在瀏覽網頁時常常會碰到各類花樣的彈窗,在作UI自動化測試的時候勢必要處理這些彈窗,這裏就介紹一下目前前端界兩種彈窗的處理方法。
1、alert彈窗 

 

 

這種彈窗是最簡單的一種,Selenium裏有自帶的方法來處理它,用switch_to.alert先定位到彈窗,而後使用一系列方法來操做:
accept - 點擊【確認】按鈕

dismiss - 點擊【取消】按鈕(若有按鈕)

send_keys - 輸入內容(若有輸入框)

這裏舉一個菜鳥教程上的一個例子:

http://www.runoob.com/try/try.php?filename=tryjs_alert,

在頁面左邊點擊【顯示警告框】就會彈出一個alert彈窗:

咱們用如下代碼就能實現切換至彈窗並點擊【肯定】按鈕的效果:
al = driver.switch_to_alert() al.accept()
這裏這個switch_to_alert()實際上是舊寫法,照理應該是用switch_to.alert(),可是新寫法卻會報錯,目前猜想是版本問題,可能不支持新寫法,這裏就先用舊寫法。

如下是完整代碼,爲了運行的時候看得清楚,我加了兩處等待:

複製代碼
# encoding:utf-8 
from selenium import webdriver 
import time 
driver = webdriver.Firefox() 
driver.get("http://www.runoob.com/try/try.php?filename=tryjs_alert")  
driver.switch_to.frame("iframeResult")
driver.find_element_by_xpath("html/body/input").click() 
time.sleep(1) al = driver.switch_to_alert() 
time.sleep(1) al.accept()
複製代碼

2、自定義彈窗 
因爲alert彈窗不美觀,如今大多數網站都會使用自定義彈窗,使用Selenium自帶的方法就駕馭不了了,此時就要搬出JS大法。這裏舉一個新世界教育官網首頁的例子(http://sh.xsjedu.org): 

 

你們能看到,圖中的這種彈窗就是如今主流的表現形式,處理這種彈窗能夠利用HTML DOM Style 對象,有一個display屬性,能夠設置元素如何被顯示,
詳細解釋能夠參考http://www.w3school.com.cn/jsref/prop_style_display.asp。將display的值設置成none就能夠去除這個彈窗了:
js = 'document.getElementById("doyoo_monitor").style.display="none";'

完整代碼以下:

複製代碼
# encoding:utf-8
from selenium import webdriver
import time 
driver = webdriver.Firefox() 
driver.get("http://sh.xsjedu.org/")
time.sleep(1)
js='document.getElementById("doyoo_monitor").style.display="none";'
driver.execute_script(js)
複製代碼

是否是既簡單又高效?

2.30 練習題2:定位百度-更多產品

練習題2:定位百度首頁上更多產品裏面的‘所有產品’

 

參考代碼

複製代碼
# coding:utf-8
from selenium import webdriver
from selenium.webdriver.common.action_chains import ActionChains
import time
driver = webdriver.Firefox()
url = "https://www.baidu.com"
driver.get(url)
driver.maximize_window()
time.sleep(2)
e = driver.find_element_by_link_text("更多產品")
ActionChains(driver).move_to_element(e).perform()
time.sleep(1)
# ele = driver.find_element_by_name("tj_more")
# 經確認,是能夠定位到元素的
# print ele.text
# 這一步點擊失效了
# ele.click()  
# js大法好,完美解決ckick失效問題
js = "document.getElementsByName('tj_more')[0].click()"
driver.execute_script(js)
複製代碼

2.31 練習題3:獲取百度聯繫詞

前言
最近有小夥伴問百度輸入後,輸入框下方的聯想詞如何定位到,這個其實難度不大,用前面所講的元素定位徹底能夠定位到的。
本篇以百度輸入框輸入關鍵字匹配後,打印出聯想詞彙。
1、定位輸入框聯想詞
1.首先在百度輸入框輸入關鍵詞,如:博客,而後輸入框下方會自動匹配出關鍵詞。
2.這時候能夠用firebug工具定位到聯想出來的詞,能夠看到下方匹配出來的詞都有共同的class屬性,這時候就能夠所有定位到了。

2、打印所有匹配出來的詞
1.經過get_attribute()方法獲取到文本信息

3、點擊其中一個
1.點擊其中的一個聯想詞,如:第二個
2.這裏能夠先加一個判斷,若是獲取到了就點擊,沒獲取到就不點擊了,以避免拋異常。
(若是想依次點擊,用for循環就能夠了)

3、參考代碼

複製代碼
# coding:utf-8
from selenium import webdriver
import time
driver = webdriver.Firefox()
driver.implicitly_wait(10)
driver.get("http://www.baidu.com")
time.sleep(1)
driver.find_element_by_id("kw").send_keys(u"博客")
# 獲取百度輸入框的
time.sleep(1)
bd = driver.find_elements_by_class_name("bdsug-overflow")
for i in bd:
    print i.get_attribute("data-key")
# 點擊其中的一個,如:第二個
if len(bd) > 1:
    bd[1].click()
    # 打印當前頁面url
    print driver.current_url
else:
    print "未獲取到匹配的詞"
複製代碼

2.32 js幾種定位方法總結

前言
本篇總結了幾種js經常使用的定位元素方法,並用js點擊按鈕,對input輸入框輸入文本
 
1、如下總結了5種js定位的方法
除了id是定位到的是單個element元素對象,其它的都是elements返回的是list對象
1.經過id獲取
document.getElementById(「id」)
2.經過name獲取
 document.getElementsByName(「Name」)

返回的是list

3.經過標籤名選取元素
document.getElementsByTagName(「tag」)
4.經過CLASS類選取元素
document.getElementsByClassName(「class」)
兼容性:IE8及其如下版本的瀏覽器未實現getElementsByClassName方法
5.經過CSS選擇器選取元素
document.querySelectorAll(「css selector")
兼容性:IE8及其如下版本的瀏覽器只支持CSS2標準的選擇器語法
 
2、id定位
1.定位博客首頁的管理按鈕:id="blog_nav_contact"

2.js的定位語法裏面id定位獲取的是單個元素對象,能夠直接用click()方法點擊元素

 

3、class定位
1.js裏面class定位獲取到是是一個list列表對象
2.操做元素的話經過下標取對應的第幾個值,若是隻用一個那就取下標[0]

3.定位到輸入框,能夠直接用value="xxx"方法輸入內容

4.ByName和ByTagName跟上面class同樣,都是定位的一組元素
 
4、CSS選擇器
1.css選擇器定位到的也是一組元素,語法跟前面學到的css語法是同樣的

5、參考代碼:

複製代碼
# coding: utf-8
from selenium import Webdriver
import time

driver = webdriver.Firefox()
driver.get("http://cnblogs.com/yoyoketang")

#定位首頁管理按鈕:id=blog_nav_contact
js1 = 'document.getElementById("blog_nav_contact")'.click;'
driver.execute_script(js1)

#輸入帳號
js2 = 'document.getElementsByClassName("input-text")[0].value="悠悠";'
driver.execute_script(js2)

#輸入密碼
js3 = 'document.getElementsByClassName("input-text")[1].value="xxx";'
driver.execute_script(js3)

#勾選記住密碼
js4 = 'document.getElementsByName("remember_me")[0].click();'
driver.execute_script(js4)

#點擊登陸按鈕
js5 = 'document.querySelectorAll(#signin)[0].click();'
driver.execute_script(js5)
複製代碼

 

2.33 定位的坑:class屬性有空格

前言
有些class屬性中間有空格,若是直接複製過來定位是會報錯的InvalidSelectorException: Message:
The given selector u-label f-dn is either invalid or does not result in a WebElement. The following error occurred:
InvalidSelectorError: Compound class names not permitted
這個報錯意思是說定位語法錯了。
 
1、定位帶空格的class屬性
1.以126郵箱爲例:http://mail.126.com/,定位帳號輸入框

 

2.若是直接複製過來用class屬性定位是會報錯的

 

2、class屬性科普
1.class屬性中間的空格並非空字符串,那是間隔符號,表示的是一個元素有多個class的屬性名稱,在整個HTML文檔,使用CSS中的同一個class類多是一個或多個!
(class屬性是比較特殊的一個,除了這個有多個屬性外,其它的像name,id是沒多個屬性的)

2.想補習html基礎知識的能夠參考菜鳥教程:http://www.runoob.com/html/html-attributes.html
 
3、class定位
1.既然知道class屬性有空格是多個屬性了,那定位的時候取其中的一個就行(而且要惟一),也就是說class="j-inputtext dlemail",取j-inputtext 和dlemail都是能夠的,這樣這個class屬性在頁面上惟一就行

2.那麼問題來了:如何才知道這個元素的某個屬性是否是在頁面上是惟一的呢?
 
4、判斷元素惟一性
1.F12切換到HTML界面,在搜索框輸入關鍵字搜索,如:j-inputtext,而後按回車搜索,看頁面上有幾個class屬性中有j-inputtext這個屬性的,就知道是否是惟一的了。

5、class屬性不惟一怎麼辦
1.若是這個class的多個屬性都不是惟一的咋辦呢,元素不惟一也不用怕,能夠用複數定位,把全部的相同元素定位出來,按下標取第幾個就行。

 

6、css定位
1.css來定位class屬性的元素前面加個點(.)就行,而後空格變成點(.)就能定位了
2.固然css也能夠取class屬性的其中一個屬性(頁面上惟一的)來定位,定位方法是靈活多變的

 

7、參考代碼

複製代碼
# coding:utf-8
from selenium import webdriver
driver = webdriver.Firefox()
driver.get("http://mail.126.com/")
driver.implicitly_wait(20)
driver.switch_to.frame("x-URS-iframe")
# 方法一:取單個class屬性
driver.find_element_by_class_name("dlemail").send_keys("yoyo")
driver.find_element_by_class_name("dlpwd").send_keys("12333")
# 方法二:定位一組取下標定位(乃下策)
# driver.find_elements_by_class_name("j-inputtext")[0].send_keys("yoyo")
# driver.find_elements_by_class_name("j-inputtext")[1].send_keys("12333")
# 方法三:css定位
# driver.find_element_by_css_selector(".j-inputtext.dlemail").send_keys("yoyo")
# driver.find_element_by_css_selector(".j-inputtext.dlpwd").send_keys("123")
# 方法四:取單個class屬性也是能夠的
# driver.find_element_by_css_selector(".dlemail").send_keys("yoyo")
# driver.find_element_by_css_selector(".dlpwd").send_keys("123")
複製代碼

2.34 jquery定位(簡直逆天)

前言
元素定位能夠說是學自動化的小夥伴遇到的一道門檻,學會了定位也就打通了任督二脈,前面分享過selenium的18般武藝,再加上五種js的定位大法。
這些還不夠的話,今天再分享一個定位神器jquery,簡直逆天了!
 
1、jquery搜索元素
1.按F12進控制檯
2.點所有按鈕
3.右側若是沒出現輸入框,就點下小箭頭按鈕
4.輸入框輸入jquery定位語法,如:$("#input1")

5.點運行按鈕
6.左邊會出現定位到的元素,若是有多個會以list列表的形式展現出。

 

2、jquery定位語法
1.jquery語法能夠學下w3school的教程:http://www.w3school.com.cn/jquery/jquery_syntax.asp

2.格式以下:
$(selector).action()
--selector:這裏的定位語法和css的定位語法是一致的,如:id就是#,class就是點(.),tag標籤名前面就無符號
--action:這個是定位元素以後的操做行爲事件,如click

3、jquery行爲
1.發送文本語法:$(selector).val(輸入文本的值)
2.清空文本語法:$(selector).val('')   # 空字符串,兩個單引號
3.點擊按鈕:$(selector).click()

4、參考腳本

複製代碼
# coding:utf-8
from selenium import webdriver
import time
driver = webdriver.Firefox()
driver.get("https://passport.cnblogs.com/user/signin")
driver.implicitly_wait(20)
# 輸入帳號
username = "$('#input1').val('上海-悠悠')"
driver.execute_script(username)
# 清空文本
# time.sleep(5)
# clear = "$('#input1').val('')"
# driver.execute_script(clear)
# 輸入密碼
psw = "$('#input2').val('yoyo')"
driver.execute_script(psw)
# 點擊登陸按鈕
button = "$('#signin').click()"
driver.execute_script(button)
複製代碼

 

相關文章
相關標籤/搜索