python_atp框架
生活随笔
收集整理的這篇文章主要介紹了
python_atp框架
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
atp接口自動化框架
程序說明:接口自動化框架,主要是通過讀Excel中的接口用例,然后自動化跑用例
實現功能:讀Excel,調用接口,結果校驗,寫報告,及發送報告
依賴軟件:程序運行需要使用request,xlrd,nnlog,yagmail,xlutils,faker,jsonpath第三方模塊,安裝命令pip3 install 模塊名稱
程序運行:Python bin/start.py
程序結構,如下圖:
?
代碼如下:
1、setting配置文件
import os import faker#郵箱信息 email_info={'user': 'xx@qq.com','host': 'smtp.qq.com','password': 'XX' }#發件人和抄送人信息 to=['XX@qq.com'] cc=['XX@qq.com']#每個目錄的路徑 base_path=os.path.dirname(os.path.dirname(os.path.abspath(__file__))) log_path=os.path.join(base_path,'logs','atp.log') report_path=os.path.join(base_path,'report') cases_path=os.path.join(base_path,'cases')#case文件前綴 case_file_start='case'#測試數據生成 f=faker.Faker(locale='zh-CN') fun_map={"<phone>":f.phone_number,"<id_card>":f.ssn,"<email>":f.email,"<name>":f.name,"<addr>":f.address,"<password>":f.ssn }#測試環境配置,可通過修改evn,進行線上,線下及準生產環境的自由切換 evn='test' host_map={"test":"http://XX","dev":"http://XX/","pre":"http://XX/", } host=host_map[evn]?2、lib下的各功能模塊
首先是讀Excel,讀用例模塊
import traceback import xlrd import nnlog from config.setting import log_path,fun_mapclass Read_Case:def __init__(self):self.log = nnlog.Logger(log_path) #聲明日志對象#用例讀取函數def read_excel(self,xls_path):case_list = [] #定義用例存放listtry:book = xlrd.open_workbook(xls_path) #讀取用例文件sheet1 = book.sheet_by_index(0) #聲明使用文本簿第0個for row in range (1,sheet1.nrows): #從第1行開始讀取用例,第0行是表頭,所以不用讀取row_case=sheet1.row_values(row)[1:7] #讀取1-6列數據,放入listrow_case[2]=self.parameter_change_dic(self.replace_parameter(row_case[2])) #對入參進行參數化替換及數據轉換為字典row_case[3]=self.parameter_change_dic(self.replace_parameter(row_case[3])) #對請求頭進行參數化替換及數據轉為字典case_list.append(row_case) #逐行用例放入list中return case_list #返回用例集except Exception as e:#如果報錯,報錯信息寫入LOGself.log.error("讀取用例文件出錯,文件名是:%s"%xls_path)self.log.error("具體錯誤信息是%s"%traceback.format_exc())#參數化函數def replace_parameter(self,str):for parameter in fun_map.keys(): #變量參數化名稱if parameter in str: #如果字符串中存在定義的參數化名進行參數化替換str=str.replace(parameter,fun_map[parameter]()) #把隨機生成的參數化值替換到STR中return str #把參數化替換后的STR返回#傳參字符串轉換字典def parameter_change_dic(self,str):parameter_dic={} #字典if str.strip(): #如果字符串非空middle_value=str.split(',') #先對字符串逗號分隔放入LISTfor value in middle_value: #對list每一項進行KEY和VALUE放入字典kname,vname=value.split('=')#等號區分,分別讀取KEY和VALUE值parameter_dic[kname]=vname #逐項加入字典return parameter_dic #返回轉換后的字典執行用例功能模塊
import traceback import requests,nnlog from config.setting import host,log_path from urllib.parse import urljoinclass Test_Request:def __init__(self,url,method,data,header,is_json='否'): #參數傳參與EXCEL順序保持一致self.method=method.lower()self.url=urljoin(host,url) #host+接口名稱拼接,urljoin可以拼接連接,無需考慮多斜杠,少斜杠的問題self.data=data #傳參self.is_json=is_json #是否是JSON格式self.header=header #請求頭self.log=nnlog.Logger(log_path) #日志對象聲明self.test_request() #類中調用方法,聲明對象后無需單獨執行方法def test_request(self):try:if self.is_json=='是': #如果是json格式,請求參數用JSONcase_result=requests.request(self.method,self.url,json=self.data,headers=self.header).json()else: #如果不是JSON格式,請求參數用datacase_result=requests.request(self.method,self.url,data=self.data,headers=self.header).json()except Exception as e: #上面的請求出錯后,就行寫日志self.log.error('請求 %s的時候出錯了,請求參數是:%s,錯誤信息是 %s' % (self.url, self.data, traceback.format_exc()))self.result = {"msg": "請求接口出錯了", "error_msg": traceback.format_exc()} #這種日志寫法,防止出錯后,后續用例無法執行self.text = ' {"msg":"請求接口出錯了","error_msg":%s} ' % traceback.format_exc() #這種日志寫法,防止出錯后,后續用例無法執行else:self.result=case_result #JSON格式的返回結果self.text=str(case_result) #返回結果轉字符串類型處理接口返回結果,實際結果與預期對比
import nnlog from config.setting import log_path import jsonpathclass Test_Response:def __init__(self,check_str,response_str):self.log = nnlog.Logger(log_path) #聲明日志對象self.check_str=check_str #預期結果self.response_str=response_str #實際返回結果self.status='通過' #執行狀態self.reason="都通過啦" #不通過的原因self.check_response() #類中調用方法,聲明對象后無需單獨執行方法def check_response(self):symbol = ['!=', '>=', '<=', '=', '>', '<'] #符號庫middle_value=self.check_str.strip().split(',') #對預期字符串去空格,逗號分隔for c_value in middle_value: #遍歷預期listfor s_mark in symbol: #遍歷符合庫if s_mark in c_value: #假如符號在本次遍歷的預期串中,比如encode=0v_key,v_value=c_value.strip().split(s_mark) #預期串按符號分隔case_result=self.get_value(self.response_str,v_key) #獲取實際結果中包含該KEY的值s_mark="==" if s_mark=='=' else s_mark #假如符號是=號,變==,為實際結果和預期結果對比code="%s %s %s"%(case_result,s_mark,v_value) #實際結果,符號,預期結果組合code_result=eval(code) #字符串執行命令if not code_result: #假如實際與預期不符,打印日志self.reason = 'key是%s,運算的代碼是%s' % (v_key, code)self.log.error(self.reason) #輸出錯誤原因self.status = '失敗' #執行狀態為失敗return Falsebreakreturn Truedef get_value(self,c_result, k_value):'這個函數是用來從返回結果里面獲取key的'result = jsonpath.jsonpath(c_result, '$..%s' % k_value) #獲取key為k_value的值if result: #假如result不為空return result[0] #返回獲取到的第一個return '' #否則返回空?寫報告
import time import xlrd import nnlog from xlutils import copy import os from config.setting import log_path, report_pathlog=nnlog.Logger(log_path) def write_excel(file_name,result_list):log.debug('現在開始寫報告了:文件名是%s 內容:%s'%(file_name,result_list)) #寫報告日志,注意如果返回結果太大,請不要打印result_listbook=xlrd.open_workbook(file_name) #打開用例文件new_book=copy.copy(book) #復制該文件sheet=new_book.get_sheet(0) #獲取第0個sheetfor row,result in enumerate(result_list,1): #遍歷返回結果列表,行從第1行開始寫for col,value in enumerate(result[1:],7): #遍歷返回結果且從下標1開始,因為第一個結果放請求參數,列從第7列開始sheet.write(row,col,value) #遍歷寫實際結果,原因,狀態sheet.write(row,3,result[0]) #最后寫請求參數,也就是更新請求參數為實際發送請求時的參數值file_name=os.path.split(file_name)[-1].replace('xlsx','xls') #獲取文件名,且把xls替換為xlsxnew_file_name=time.strftime('%Y%m%d%H%M%S')+"_"+file_name #新文件名稱有當前時間+原文件名構成abs_path=os.path.join(report_path,new_file_name) #新文件名+報告地址,構成最新的文件路徑new_book.save(abs_path) #文件保存到報告路徑下log.debug("報告生成完成,文件名是%s"%abs_path) #打印報告地址return abs_path #返回報告地址寫郵件
import traceback import yagmail import time import nnlog from config.setting import email_info,cc,to,log_pathlog=nnlog.Logger(log_path) #日志對象聲明 def send_mail(all_num,pass_num,file_name):log.debug('開始發送郵件') #發送郵件日志subject = "%s---接口測試結果" % time.strftime('%Y-%m-%d %H:%M:%S') #郵件標題content = '''各位好:"本次接口測試完成,結果如下:測試用例總共【%s】條,通過用例【%s】條,失敗用例【%s】條"詳細信息請看附件'''%(all_num,pass_num,all_num-pass_num) #郵件內容try:mail=yagmail.SMTP(**email_info) #解包方式傳入參數mail.send(to=to,cc=cc,subject=subject,contents=content,attachments=file_name) #發送郵件except Exception as e:log.error("發送郵件出錯了,錯誤信息是:\n%s"%traceback.format_exc()) #捕獲錯誤信息else:log.info("發送郵件成功") #發送成功日志啟動自動化文件
from config.setting import cases_path,case_file_start,log_path from lib.parse_response import Test_Response from lib.request import Test_Request from lib.read_case import Read_Case import os from lib.mail import send_mail from lib.write_report import write_excel import nnlog log=nnlog.Logger(log_path) #聲明日志對象class CaseRun:all_num=0 #總用例數pass_num=0 #通過用例數#獲取用例函數def get_case(self):excel_list=[] #用例文件列表for file in os.listdir(cases_path):#遍歷用例文件夾下的文件列表if file.startswith(case_file_start) and (file.endswith("xls") or file.endswith("xlsx")): #如果是規定的用例格式文件abs_path=os.path.join(cases_path,file) #文件名和路徑拼接excel_list.append(abs_path) #用例文件路徑放入用例文件listreturn excel_list #返回用例文件list#執行用例用例def run_case(self,file_name):read_case_obj=Read_Case() #聲明讀用例對象case_list=read_case_obj.read_excel(file_name) #對用例且放入用例listresponse_list=[] #聲明返回結果listfor case in case_list: #遍歷用例listself.all_num+=1 #每次循環用例總數加1req_obj=Test_Request(*case[:5]) #解包方式傳入用例的URL,data,method,is_json,headerresponse_obj=Test_Response(case[-1],req_obj.result) #預期與實際結果對比if response_obj.status=='通過': #加入預期與實際結果對比,狀態返回通過self.pass_num+=1 #通過數加1response_list.append([str(req_obj.data),req_obj.text,response_obj.reason,response_obj.status]) #通過還是失敗,需要把實際請求參數,返回結果,原因,狀態放入返回結果listreturn write_excel(file_name,response_list) #返回報告地址#主函數def main(self):report_list=[] #報告地址listexcel_list=self.get_case() #用例文件列表for excel in excel_list: #循環文件列表report_name=self.run_case(excel) #執行用例report_list.append(report_name) #每個用例的報告加入到報告listsend_mail(self.all_num,self.pass_num,report_list) #發送郵件log.debug('運行完成') #運行成功if __name__=='__main__':run=CaseRun() #實例化主程序對象run.main() #調用主方法,執行自動化測試用例?備注:當然還可以根據該框架更加豐富一下,比如測試數據通過數據讀取,或者寫方法自動生成,或外部文件讀取,另外也可加入多種接口請求,比如XML等
轉載于:https://www.cnblogs.com/xiaokuangnvhai/p/11242420.html
總結
以上是生活随笔為你收集整理的python_atp框架的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: oracle ocp笔记(1)
- 下一篇: 暑假集训考试反思+其它乱写