目錄
Python接口測試課程(第一天)-Python基礎
Python接口測試課程(第二天)-接口測試快速實踐
Python接口測試課程(第三天)-接口安全驗證,參數化及斷言
Python接口測試課程(第四天)-接口測試框架實現
PDF下載:鏈接:https://pan.baidu.com/s/1x3_LYq23F_1LviGVbRNFXw 密碼:xrcj
更多學習資料請加添加作者微信:superz-han 獲取
第一天: Python基礎
Python簡介、環境搭建及包管理
Python簡介
- 特點:Python是一門動態、解釋型、強類型語言
- 動態:在運行期間才做數據檢查(不用提前聲明變量)- 靜態語音(C/Java):編譯時檢查數據類型(編碼時需要聲明變量類型)
- 解釋型:在執行程序時,才一條條解釋成機器語言給計算機執行(無需編譯,速度較慢)- 編譯型語言(C/Java):先要將代碼編譯成二進制可執行文件,再執行
- 強類型:類型安全,變量一旦被指定了數據類型,如果不強制轉換,那么永遠是這種類型(嚴謹,避免類型錯誤,速度較慢)- 弱類型(VBScript/JavaScript): 類型在運行期間會轉化,如 js中的 1+"2"="12", 1會由數字轉化為string
- 編碼原則:優雅、明確、簡單
- 優點
- 簡單易學
- 開發效率高
- 高級語言
- 可移植、可擴展、可嵌入
- 龐大的三方庫
- 缺點
- 速度慢
- 代碼不能加密
- 多線程不能充分利用多核cpu(GIL全局解釋性鎖,同一時刻只能運行一個線程)
- 應用領域
- 自動化測試(UI/接口)
- 自動化運維
- 爬蟲
- Web開發(Django/Flask/..)
- 圖形GUI開發
- 游戲腳本
- 金融、量化交易
- 數據分析,大數據
- 人工智能、機器學習、NLP、計算機視覺
- 雲計算
環境搭建
Windows Python3環境搭建
- 下載Python3.6.5*.exe安裝包
- 雙擊安裝,第一個節目選中Add Python3.6.5 to PATH,點擊Install Now(默認安裝pip),一路下一步
- 驗證:打開cmd命令行,輸入python,應能進入python shell 並顯示為Python 3.6.5版本
包管理
- pip安裝
- pip install 包名 - 卸載: pip uninstall 包名
- pip install 下載的whl包.whl
- pip install -r requiements.txt(安裝requirements.txt中的所有依賴包)
- pip list 查看已安裝的三方包,pip freeze 已文件格式顯示已安裝的三方包(用於導出requiremnts.txt文件)
- 源碼安裝
- 下載源碼包,解壓,進入解壓目錄
- 打開命令行,執行
python setup.py install
- 驗證:進入python shell,輸入import 包名,不報錯表示安裝成功
- 三方包默認安裝路徑:Python3.6.5/Lib/site-packages/ 下
Python基本語法
- 縮進
if x > 0:
print("正數")
elif x = 0:
print("0")
else:
print("負數")
def add(x,y):
return x+y
- 一行多條語句
x=1; y=2; print(x+y)
- 斷行
print("this line is too long, \
so I break it to two lines")
- 注釋
# 單行注釋
a = 1
'''這是一段
多行注釋'''
def add(x, y):
"""加法函數:這是docstring(函數說明)"""
pass
- 變量
- 變量類型(局部變量、全局變量、系統變量)
- 變量賦值
- 多重賦值
x=y=z=1
- 多元賦值
x,y = y,x
- 多重賦值
- 變量自增
x+=1
x-=1
(不支持x++
,x--
)
Python3中沒有常量
基本數據類型(6種)
1. 數字Number
- 種類
- 整型int(Python3中沒有長整型,int長度幾乎沒有限制)
- 浮點型float
- 布爾型bool
- False: 0,0.0,'',[],(),{}
- True: 除False以外,['']或[[],[]]不是False
- 復數型complex
- 操作符: +,-,*,/,//(地板除),**(乘方) - Python3中的/是真實除,1/2=0.5
- 類型轉
- str(): 其他類型轉為字符串, 如
str(12)
- int(): 字符串數字轉為整型(字符串不是純整數會報錯), 如
int("12")
- float(): 字符串轉換為浮點數,如
float("1.23")
- str(): 其他類型轉為字符串, 如
2. 字符串String
-
字符串系統方法
- len(): 計算字符串長度,如
len("abcdefg")
- find()/index(): 查找字符串中某個字符第一次出現的索引(index()方法查找不到會報錯), 如
"abcdefg".find("b"); "abcedfgg".index("g")
- lower()/upper(): 將字符串轉換為全小寫/大寫,如
"AbcdeF".lower();"abcedF".upper()
- isdigit()/isalpha()/isalnum(): 判斷字符串是否純數字/純字母/純數字字母組合, 如
isdigit("123")
,結果為 True - count(): 查詢字符串中某個元素的數量,如
"aabcabc".count("a")
- join(): 將列表元素按字符串連接,如
"".join(["a","b","c"])
會按空字符連接列表元素,得到"abc" - replace(): 替換字符串中的某已部分,如
"hello,java".replace("java", "python")
,將java 替換為 python - split(): 和join相反,將字符串按分隔符分割成列表, 如
"a,b,c,d".split(",")
得到["a", "b", "c", "d"] - strip()/lstrip()/rstrip(): 去掉字符串左右/左邊/右邊的無意字符(包括空格,換行等非顯示字符),如
" this has blanks \n".strip()
得到"this has balnks"
- len(): 計算字符串長度,如
-
字符串格式化
- %: 如
"Name: %s, Age: %d" % ("Lily", 12)
或"Name: %(name)s, Age: %(age)d" % {"name": "Lily", "age": 12}
- format: 如
"Name: {}, Age: {}".format("Lily", 12)
或"Name: {name}, Age: {age}".format(name="Lily",age=12)
- substitude(不完全替換會報錯)/safe_substitude: 如
"Name: ${name}, Age: ${age}".safe_substitude(name="Lily",age=12)
- %: 如
-
案例: 利用format生成自定義html報告
tpl='''
{title} {title}
{trs}序號 用例 結果 tr='''{sn}
{case_name} {result} '''title="自動化測試報告"
case_results = [("1", "test_add_normal", "PASS"),("2", "test_add_negative", "PASS"), ("3", "test_add_float", "FAIL")]trs=''
for case_result in case_results:
tr_format = tr.format(sn=case_result[0], case_name=case_result[1], result=case_result[2])
trs += tr_formathtml = tpl.format(title=title, trs=trs)
f = open("report.html", "w")
f.write(html)
f.close()
結果預覽
自動化測試報告
序號 | 用例 | 結果 |
---|---|---|
1 | test_add_normal | PASS |
2 | test_add_negative | PASS |
3 | test_add_float | FAIL |
3. 列表List
列表元素支持各種對象的混合,支持嵌套各種對象,如
["a", 1, {"b": 3}, [1,2,3]]
- 列表操作
- 賦值:
l = [1, "hello", ("a", "b")]
- 獲取:
a = l[0] # 通過索引獲取
- 增:
l.append("c");l.extend(["d","e"]);l+["f"]
- 刪:
l.pop() # 按索引刪除,無參數默認刪除最后一個;l.remove("c") # 按元素刪除
- 改:
l[1]="HELLO" # 通過索引修改
- 查: 遍歷
for i in l: print(i)
- 賦值:
- 列表系統方法
- append()/insert()/extend(): 添加/插入/擴展(連接)
- index(): 獲取元素索引
- count(): 統計元素個數
- pop()/remove(): 按索引/元素刪除
- sort()/reverse(): 排序/反轉
- 案例: 字符串反轉
s="abcdefg"; r=''.join(reversed(a))
4. 元組Tuple
- 不可改變,常用作函數參數(安全性好)
- 同樣支持混合元素以及嵌套
- 只有一個元素時,必須加","號,如
a=("hello",)
- 因為Python中()還有分組的含義,不加","會識別為字符串
字符串/列表/元組統稱為序列, 有相似的結構和操作方法
序列相關操作方法
1. 索引 - 正反索引: ```l[3];l[-1]``` - 索引溢出(IndexError): 當索引大於序列的最大索引時會報錯,如[1,2,3,4]最大索引是3,引用l[4]會報IndexError 2. 切片 - l[1:3] # 從列表索引1到索引3(不包含索引3)進行截取, 如 l = [1, 2, 3, 4, 5], l[1:3]為[2, 3] - l[:5:2] # 第一個表示開始索引(留空0), 第二個表示結束索引(留空為最后一個,即-1), 第三個是步長, 即從開頭到第5個(不包含第5個),跳一個取一個 - *案例*: 字符串反轉 ```s="abcdefg";r=s[::-1]``` 3. 遍歷 - 按元素遍歷: ```for item in l: print(item)``` - 按索引遍歷: ```for index in range(len(l)): print(l[index])``` - 按枚舉遍歷: ```for i,v in enumerate(l): print((i,v))``` 4. 擴展/連接(添加多個元素): extend()/+ ```"abc"+"123";[1,2,3]+[4,5];[1,2,3].extend([4,5,6,7])``` 5. 類型互轉: str()/list()/tuple() >list轉str一般用join(), str轉list一般用split()- 系統函數
- len(): 計算長度
- max()/min(): 求最大/最小元素
- sorted()/reversed(): 排序/反轉並生成新序列(sort()/reverse()直接操作原序列)
l_new=sorted(l);l_new2=reversed(l)
5. 集合Set
- 集合可以通過序列生成
a = set([1,2,3])
- 集合無序,元素不重復(所有元素為可哈希元素)
- 集合分為可變集合set和不可變集合frozenset
- 操作方法: 聯合|,交集&,差集-,對稱差分^
- 系統函數: add()/update()/remove()/discard()/pop()/clear()
- 案例1: 列表去重:
l=[1,2,3,1,4,3,2,5,6,2];l=list(set(l))
(由於集合無序,無法保持原有順序) - 案例2: 100w條數據,用列表和集合哪個性能更好? - 集合性能要遠遠優於列表, 集合是基於哈希的, 無論有多少元素,查找元素永遠只需要一步操作, 而列表長度多次就可能需要操作多少次(比如元素在列表最后一個位置)
6. 字典Dict
- 字典是由若干key-value對組成, 字典是無序的, 字典的key不能重復,而且必須是可哈希的,通常是字符串
- 字典操作
- 賦值:
d = {"a":1, "b":2}
- 獲取:
a = d['a']
或a = d.get("a") # d中不存在"a"元素時不會報錯
- 增:
d["c"] = 3; d.update({"d":5, "e": 6}
- 刪:
d.pop("d");d.clear() # 清空
- 查:
d.has_key("c")
- 遍歷:
- 遍歷key:
for key in d:
或for key in d.keys():
- 遍歷value:
for value in d.values():
- 遍歷key-value對:
for item in d.items():
- 遍歷key:
- 賦值:
- 案例: 更新接口參數 api = {"url": "/api/user/login": data: {"username": "張三", "password": "123456"}},將username修改為"李四"
api['data']['username'] = "李四"
或api['data'].update({"username": "李四"})
哈希與可哈希元素
- 哈希是通過計算得到元素的存儲地址(映射), 這就要求不同長度的元素都能計算出地址,相同元素每次計算出的地址都一樣, 不同元素計算的地址必須唯一, 基於哈希的查找永遠只需要一步操作, 計算一下得到元素相應的地址, 不需要向序列那樣遍歷, 所以性能較好
- 可哈希元素: 為了保證每次計算出的地址相同, 要求元素長度是固定的, 如數字/字符串/只包含數字,字符串的元組, 這些都是可哈希元素
6種類型簡單的特點總結
- 數字/字符串/元祖: 長度固定
- 序列(字符串/列表/元祖): 有序
- 集合/字典: 無序, 不重復/鍵值不重復
條件/循環
條件判斷
- 示例:
if x>0:
print("正數")
elif x=0:
print("0")
else:
print("負數")
-
三元表達式:
max = a if a > b else b
-
案例: 判斷一個字符串是不ip地址
ip_str = '192.168.100.3'
ip_list = ip_str.split(".") # 將字符串按點分割成列表
is_ip = True # 先假設ip合法
if len(ip_list) != 4:
is_ip= False
else:
for num in ip_list:
if num.lstrip('0')!=num or not isdigit(num) or not 0 <= int(num) <= 255:
is_ip = False
if is_ip:
print("是ip")
else:
print("不是ip")
使用map函數的實現方法(參考):
def check_ipv4(ip_str):
ip = ip_str.strip().split(".")
return len(ip)4 and all(map(lambda x: x.lstrip('0')x and x.isdigit() and 0<=int(x)<= 255, ip))
循環
- for in 循環
- while 循環
文件讀寫(文本文件)
html/xml/config/csv也可以按文本文件處理
文件操作方法
- open(): 打開
f =open("test.txt")
或f =open("test.txt","r", encoding="utf-8")
或with open("test.txt) as f: # 上下文模式,出結構體自動關閉文件
- read()/readline()/readlines(): 讀取所有內容/讀取一行/讀取所有行(返回列表) - 注意: 內容中包含\n換行符,可以通過strip()去掉
- f.write()/f.save(): 寫文件/保存文件
- f.seek(): 移動文件指針,如f.seek(0), 移動到文件開頭
- f.close(): 關閉文件(打開文件要記得關閉)
文件打開模式
- r/w/a: 只讀/只寫/追加模式
- rb/wb/ab: 二進制只讀/只寫/追加模式(支持圖片等二進制文件)
- r+/rb+, w+/wb+, a+/ab+: 讀寫,區別在於, r+/w+會清空文件再寫內容, r+文件不存在會報錯, a+不清空原文件,進行追加, w+/a+文件不存在時會新建文件
文件是可迭代的,可以直接用 for line in f: 遍歷
函數/類
函數定義和調用
def add(x, y): # 定義函數
return x+y
print(add(1,3)) # 調用函數
案例: 用戶注冊/登錄函數
users = {"張三": "123456"}
def reg(username, password):
if users.get(username): # 如果用戶中存在username這個key
print("用戶已存在")
else:
users[username] = password # 向users字典中添加元素
print("添加成功")
def login(username, password)
if not users.get(username):
print("用戶不存在")
elif users['username'] == password:
print("登錄成功")
else:
print("密碼錯誤")
參數和返回值
- 函數沒有return默認返回None
- 參數支持各種對象,包含數字,支付串,列表,元組,也可以是函數和類
- 參數默認值: 有默認值的參數必須放在最后面, 如```def add(x, y=1, z=2):
- 不定參數: *args和**kwargs, 如
def func(*args, **kwargs):
可以接受任意長度和格式的參數 - 參數及返回值類型注釋(Python3)
def(x:int, y:int) -> int: # x,y為int型,函數返回為int型,只是注釋,參數格式非法不會報錯
return x+y
函數作為參數(如: 裝飾器)
def a():
print("I'm a")
def deco(func):
print("call from deco")
func()
deco(a) # 輸出"call from deco"並調用a(),輸出"I'm a"
函數嵌套(支持閉包)
def a():
a_var = 1
def b:() # 嵌套函數
a_var += 1
函數遞歸(自己調用自己,直到滿足需求)
案例: 求N!
def factorial(n):
return 1 if n == 0 or n == 1 else n * factorial(n-1)
模塊/包
模塊
- 一個py文件為一個模塊
- 模塊導入
- import os # 需要通過os調用相關方法, 如os.mkdir(),
- form configparser import ConfigParser: 可以直接使用CinfigParser()
- 支持一次導入多個
包
- 一個文件夾為一個包(Python3,文件夾中不需要建立__init__.py文件)
常用系統模塊
- os: 與操作系統交互
- os.name/os.sep/os.linesep: 系統名稱/系統路徑分隔符/系統換行符
- os.makedir()/os.makedirs(): 建立目錄/建立多級目錄
- os.getenv("PATH"): 獲取系統PATH環境變量的設置
- os.curdir/os.prdir: 獲取當前路徑/上級路徑
- os.walk(): 遍歷文件夾及子文件
- os.path.basename()/os.path.abspath()/os.path.dirname(): 文件名/文件絕對路徑/文件上級文件夾名
- os.path.join()/os.path.split(): 按當前系統分隔符(os.sep)組裝路徑/分割路徑
- os.path.exists()/os.path.isfile()/os.path.isdir(): 判斷文件(文件夾)是否存在/是否文件/是否文件夾
- 案例: 用例發現, 列出文件夾及子文件夾中所有test開頭的.py文件,並輸出文件路徑
for root,dirs,files in os.walk("./case/"):
for file in files:
if file.startswith("test") and file.endswith(".py"):
print(os.path.join(root, file)
- sys: 與Python系統交互
- sys.path: 系統路徑(搜索路徑)
- sys.platform: 系統平台,可以用來判斷是python2還是3
- sys.argv: py腳本接受的命令行參數
- sys.stdin/sys.stdout/sys.stderr: 標准輸入/輸出/錯誤
常見算法
冒泡排序
def buddle_sort(under_sort_list):
l = under_sort_list
for j in range(len(l)):
for i in range(len(l)-j-1):
if l[i] > l[i+1]:
l[i], l[i+1] = l[i+1], l[i]
快速排序
def quick_sort(l):
if len(l) < 2:
return l # 如果列表只有一個元素, 返回列表(用於結束迭代)
else:
pivot = l[0] # 取列表第一個元素為基准數
low = [i for i in l[1:] if i < pivot] # 遍歷l, 將小於基准數pivot的全放入low這個列表
high = [i for i in l[1:] if i >= pivot ]
return quick_sort(low) + [pivot] + quick_sort(high) # 對左右兩部分分別進行迭代
二分查找
def bin_search(l, n): # l為有序列表
low, high = 0, len(l) - 1 # low,high分別初始化為第一個/最后一個元素索引(最小/最大數索引)
while low < high:
mid = (high-low) // 2 # 地板除,保證索引為整數
if l[mid] == n:
return mid
elif l[mid] > n: # 中間數大於n則查找前半部分, 重置查找的最大數
high = mid -1
else: # 查找后半部分, 重置查找的最小數
low = mid + 1
return None # 循環結束沒有return mid 則說明沒找到
作業
- 查找文件中最長的行
- 統計文件中字符個數
- 判斷字符串"abacdbdde"中第一個不重復的字符
- 判斷字符串"{{({()[({})])}}"是否括號全部閉合