金融项目实战 06|Python实现接口自动化——日志、实名认证和开户接口

目录

一、日志封装及应用(理解)

二、认证开户接口脚本编写

1、代码编写

1️⃣api目录

2️⃣script目录

2、BeautifulSoup库

1️⃣简介及例子 

2️⃣提取html数据工具封装

3、认证开户参数化


一、日志封装及应用(理解)

🔴日志的作用:

  • 记录程序运行的步骤和错误。

🔴日志的场景:

  • 1、调试bug
  • 2、查看程序运行轨迹

🔴日志基本应用:

# 1、导包
import logging
# 2、调用日志⼊口
logging.error("出错啦,错误原因:{}".format(e))
import logging
# 设置日志级别 及保存⽂件名
logging.basicConfig(level=logging.DEBUG, filename="../log/p2p.log")
# 调用日志
logging.debug("调试信息")
logging.info("信息级别")
logging.warning("警告")
logging.error("断⾔错误!")
logging.critical("严重错误")

🔴测试人员使用的日志的入口:

  • info:记录运行步骤
  • error:记录运行错误

🔴日志底层组成介绍:了解底层是为了修改log打印出的信息进行美化封装

  • 说明:logging库底层有4大组件(日志器、处理器、格式器、过滤器)
    • 1、日志器:接受日志信息,设置日志显示级别
    • 2、处理器:控制日志显示位置或文件
    • 3、格式器:控制日志输出的显示样式
  • 关系:
    • 格式器必须关联处理器
    • 处理器必须关联日志器

🔴日志封装应用:

重组封装的目的:解决日志显示的样式、存储方式

①日志工具的封装

在util.py中添加日志工具的封装:

下面这个日志工具类可以当模板用,最多改一下保存日志的.log文件名称


import logging.handlers# 日志工具
class GetLog:@classmethoddef get_log(cls):cls.log = Noneif cls.log is None:# 1、获取日志器cls.log = logging.getLogger()# 设置日志级别 infocls.log.setLevel(logging.INFO)filepath = DIR_PATH + os.sep + "log" + os.sep + "p2p.log"# 2、获取处理器 TimedRotatingFileHandler:日志保存到文件且根据时间去分割tf = logging.handlers.TimedRotatingFileHandler(filename=filepath,when="midnight",interval=1,backupCount=3,encoding="utf-8")# 3、获取格式器fmt = "%(asctime)s %(levelname)s [%(filename)s(%(funcName)s:%(lineno)d)] - %(message)s"fm = logging.Formatter(fmt)# 4、将格式器添加到处理器中tf.setFormatter(fm)# 5、将处理器添加到日志器中cls.log.addHandler(tf)# 返回日志器return cls.log# 下面只是测试上面的工具能不能用的,如果运行成功,则会在log目录下产生p2p.log
# p2p.log文件内容类似为:2025-01-14 22:30:41,013 INFO [util.py(<module>:50)] - 信息级别测试
if __name__ == '__main__':GetLog.get_log().info("信息级别测试")

②工具使用

这做的目的只是让log=GetLog.get_log()在只要用到导api包就自动执行,实现自动调用方法;
(为什么这样用: Python中的`__init__.py`文件 -CSDN博客)

应用的级别:info、error

  • info:i记录程序运行的步骤
  • error:记录程序错误

标注地方:api和script

api层:记录程序步骤

script:记录程序执行结果、断言结果、错误原因

可以在api和script中每个方法中标注log,下面仅为示例:

# script目录中文件标注的示例
#2、获取短信验证码接口 测试@parameterized.expand(read_json("register_login.json", "phone_code"))def test02_phone_code(self,phone,imgVerifyCode,expec_text):try:# 1、调用获取图片验证码接口 -- 目的:让session对象记录cookie# 调用接口后session会自动记录cookieself.reg.api_img_code(234)# 2、调用短信验证码接口r = self.reg.api_phone_code(phone=phone,imgVerifyCode=imgVerifyCode)# 3、查看响应结果log.info("执行接口结果为:{}".format(r.text))self.assertIn(expec_text,r.text) # 使用text提取结果是更方便,json还要根据键找值log.info("执行断言通过!")except Exception as err:# 日志# print(err)log.error("断言失败,原因:{}".format(err))# 抛异常raise
# api目录中的示例
# 2、获取短信验证码接⼝ 封装def api_phone_code(self,phone,imgVerifyCode):data = {"phone": phone,"imgVerifyCode": imgVerifyCode,"type": "reg"}log.info("正在调用获取短信验证码接口,请求方法:{}, 请求url:{} 请求参数:{}".format("post", self.__url_phone_code,data))return self.session.post(url=self.__url_phone_code,data=data)

二、认证开户接口脚本编写

1、代码编写

1️⃣api目录

①结构

from config import HOSTclass ApiApproveTrust:# 初始化def __init__(self, session):# 获取session对象self.session = session# 认证urlself.__url_approve = HOST + "/member/realname/approverealname"# 查询认证状态urlself.__url_approve_status = HOST + "/member/member/getapprove"# 开户urlself.__url_trust = HOST + "/trust/trust/register"# 图片验证码urlself.__url_img_code = HOST + "/common/public/verifycode/{}"# 充值urlself.__url_recharge = HOST + "/trust/trust/recharge"# 1、认证接口 封装def api_approve(self):pass# 2、查询认证状态接口 封装def api_approve_status(self):pass# 3、开户接口 封装def api_trust(self):pass# 4、获取图片验证码接口 封装def api_img_code(self, random):pass# 5、充值接口封装def api_recharge(self,valicode):pass

②实现

from config import HOSTclass ApiApproveTrust:# 初始化def __init__(self, session):# 获取session对象self.session = session# 认证urlself.__url_approve = HOST + "/member/realname/approverealname"# 查询认证状态urlself.__url_approve_status = HOST + "/member/member/getapprove"# 开户urlself.__url_trust = HOST + "/trust/trust/register"# 图片验证码urlself.__url_img_code = HOST + "/common/public/verifycode/{}"# 充值urlself.__url_recharge = HOST + "/trust/trust/recharge"# 1、认证接口 封装def api_approve(self):# 1、请求参数data = {"realname":"华仔","card_id":"350102199003072237"}# 2、调用请求方法 难题:multipart/form-data使用:data+files来实现多消息体类型return self.session.post(url=self.__url_approve, data=data, files={"x": "y"})# 2、查询认证状态接口 封装def api_approve_status(self):return self.session.post(url=self.__url_approve_status)# 3、开户接口 封装def api_trust(self):return self.session.post(url=self.__url_trust)# 4、获取图片验证码接口 封装def api_img_code(self, random):return self.session.get(url=self.__url_img_code.format(random))# 5、充值接口封装def api_recharge(self,valicode):# 1、请求参数data = {"paymentType": "chinapnrTrust","amount": "1000","formStr":"reForm","valicode":valicode}# 2、调用请求方法return self.session.post(url=self.__url_recharge, data=data)

难点:认证接口请求参数类型为:multipart/form-data多消息类型,如何实现?

  • 解决:请求使用data+files两种参数格式,消息头会自动切换到multipart即可。
  • 示例:self.session.post(url=self.__url_approve, data=data, files={"x": "y"})
  • files={"x": "y"}只是起到占位作用,表明有文件而已。
2️⃣script目录

 

①结构

import unittestimport requestsfrom api.api_register_login import ApiRegisterLoginclass TestApproveTrust(unittest.TestCase):# 初始化def setUp(self) -> None:#1、获取session对象self.session = requests.Session()#2、实例化ApiRegisterLogin类方法self.approve = ApiRegisterLogin(self.session)#3、调用登录接口ApiRegisterLogin(self.session).api_login()# 结束def tearDown(self) -> None:self.session.close()#1、认证接口 测试def test01_approve(self):pass#2、查询认证状态接口 测试def test02_approve_status(self):pass#3、开户接口 测试def test03_trust(self):pass#4、获取图片验证码接口 测试def test04_img_code(self):pass#5、充值接口 测试def test05_recharge(self):pass

②实现

请求第三方开户接口 和 请求第三方充值接口 的代码需要后文的BeautifulSoup库知识。

此处是加了参数化的代码,参数化的其他内容看后文参数化小节。

import unittestimport requests
from parameterized import parameterizedfrom api import log
from api.api_approve_trust import ApiApproveTrust
from api.api_register_login import ApiRegisterLogin
from util import parser_html, read_jsonclass TestApproveTrust(unittest.TestCase):# 初始化def setUp(self) -> None:#1、获取session对象self.session = requests.Session()#2、实例化ApiRegisterLogin类方法self.approve = ApiApproveTrust(self.session)#3、调用登录接口ApiRegisterLogin(self.session).api_login()# 结束def tearDown(self) -> None:r = self.session.close()# 1、认证接口 测试# 认证接口不需要参数化的原因是:只有一个可测的用例,其他两个测试用例是bug,不适合拿来做实战def test01_approve(self,expect_test="提交成功"):try:r = self.approve.api_approve()# print(r.json())log.info("正在执行认证接口响应结果为:{}".format(r.text))self.assertIn(expect_test,r.text)log.info("认证接口断言成功!")except Exception as err:# 日志log.error("断言失败,原因:{}".format(err))# 抛异常raise#2、查询认证状态接口 测试# 不需要参数化的原因是:只有一个可测的用例,def test02_approve_status(self,expect_test="华"):try:r = self.approve.api_approve_status()# print(r.json())log.info("正在执行查询认证状态接口响应结果为:{}".format(r.text))self.assertIn(expect_test, r.text)log.info("查询认证状态接口断言成功!")except Exception as err:# 日志log.error("断言失败,原因:{}".format(err))# 抛异常raise#3、开户接口 测试def test03_trust(self,expect_test="form"):try:# 1、请求后台开户接口r = self.approve.api_trust()# print(r.json())log.info("正在执行开户接口响应结果为:{}".format(r.json()))self.assertIn(expect_test, r.text)log.info("认证开户断言成功!")# 2、请求第三方开户接口result = parser_html(r) # 结果为:(’http://xxxx‘,‘{'xxx':'xxx'},……’)r = self.session.post(url=result[0],data=result[1])# print(r.text) # 结果为:UserRegister OKself.assertIn("OK",r.text)log.info("请求第三方开户断言成功!")except Exception as err:# 日志log.error("断言失败,原因:{}".format(err))# 抛异常raise#4、获取图片验证码接口 测试@parameterized.expand(read_json("approve_trust.json","img_code"))def test04_img_code(self,random,expect_code):try:r = self.approve.api_img_code(random)# print(r.status_code)log.info("正在执行获取图片验证码接口响应结果为:{}".format(r.status_code))self.assertEqual(expect_code, r.status_code)log.info("断言获取图片验证码接口成功!")except Exception as err:# 日志log.error("断言失败,原因:{}".format(err))# 抛异常raise#5、充值接口 测试@parameterized.expand(read_json("approve_trust.json","recharge"))def test05_recharge(self,valicode,expect_text):try:# 1、调用图片验证码接口self.approve.api_img_code(123)# 2、充值接口r = self.approve.api_recharge(valicode)# print("充值接口响应结果:",r.text)log.info("正在执行充值接口响应结果为:{}".format(r.json()))if valicode == 8888:# # 断言self.assertIn("form", r.text)log.info("断言充值接口成功!")# 3、三方充值result = parser_html(r)  # 结果为:(’http://xxxx‘,‘{'xxx':'xxx'},……’)r = self.session.post(url=result[0], data=result[1])self.assertIn(expect_text, r.text)log.info("请求第三方充值断言成功!")else:# print("验证码错误的响应结果:",r.text)self.assertIn(expect_text,r.text)except Exception as err:# 日志log.error("断言失败,原因:{}".format(err))# 抛异常raise

2、BeautifulSoup库

1️⃣简介及例子 

说明:⼀个python解析html/xml的三方库

安装: pip install beautifulsoup4 -i https://mirrors.tuna.tsinghua.edu.cn/ 

基本用法

应用步骤:

  • 1、导包
  • 2、实例化
  • 3、调用方法

例子:

重点:

1、查找所有标签 bs.find_all("标签名") == 元素的集合 == ["元素1","元素2"]

2、查找属性 元素.get("属性名")

其他方法:

2️⃣提取html数据工具封装

 ①思路:

②实现

在工具类py文件末尾添加下面的封装方法

from bs4 import BeautifulSoup
def parser_html(result):# 1、提取htmlhtml = result.json().get("description").get("form")# 2、获取bs对象bs = BeautifulSoup(html,"html.parser")# 3、提取urlurl = bs.form.get("action")data = {}# 4、查找所有的input标签for input in bs.find_all("input"):data[input.get("name")]=input.get("value")return url, data

使用BeautifulSoup库后就可以实现三方开户和三方充值了,代码已经在前文2️⃣script目录展示过。

3、认证开户参数化

实现难点:

 

{"img_code": [{"desc": "获取图片验证码成功(随机小数)","random": 0.123,"expect_code": 200},{"desc": "获取图片验证码成功(随机整数)","random": 123,"expect_code": 200},{"desc": "获取图片验证码失败(随机数为空)","random": "","expect_code": 404},{"desc": "获取图片验证码失败(随机数为字符串)","random": "123hello","expect_code": 400}],"recharge": [{"desc": "后台充值响应成功","valicode": 8888,"expect_text": "OK"},{"desc": "后台充值响应成功","valicode": 8889,"expect_text": "验证码错误"}]
}

添加了参数化的完整认证开户script文件已在前文展示:2️⃣script目录

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/bicheng/68254.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

浅谈云计算15 | 存储可靠性技术(RAID)

存储可靠性技术 一、存储可靠性需求1.1 数据完整性1.2 数据可用性1.3 故障容错性 二、传统RAID技术剖析2.1 RAID 02.2 RAID 12.3 RAID 52.4 RAID 62.5 RAID 10 三、RAID 2.0技术3.1 RAID 2.0技术原理3.1.1 两层虚拟化管理模式3.1.2 数据分布与重构 3.2 RAID 2.0技术优势3.2.1 自…

Spring官网构建Springboot工程

注意&#xff1a;基于Idea的 Spring Initializr 快速构建 SpringBoot 工程时需要联网。 1.进入SpringBoot官网 Spring | Home 点击QUICKSTART 点击start.spring.io进入spring initializr 2.选择依赖 3.生成工程 下载好后解压用IDEAD导入即可。

C++基础之: 迭代器

简介 迭代器是 C 的一个重要组成部分, 它在数据结构和算法之间架起了桥梁. 迭代器作为通用指针, 可以遍历和操作容器中的元素, 同时隐藏底层的复杂性. 让我们一起探索现代 C 中迭代器的概念, 类别和使用场景. 什么是迭代器? 迭代器是一种抽象工具, 它允许顺序访问集合中的元…

C++并发编程之std::partial_sum的并行版本

在C中&#xff0c;std::partial_sum 是一个用于计算前缀和的算法&#xff0c;它将输入范围中的每个元素替换为其前缀和。为了提高性能&#xff0c;我们可以设计并实现一个并行版本的 std::partial_sum&#xff0c;以便在多核处理器上并行执行前缀和计算。基本思想是将输入范围划…

计算机的错误计算(二百一十二)

摘要 利用两个大模型计算 实验表明&#xff0c;两个大模型均进行了中肯的分析。另外&#xff0c;其中一个大模型给出了 Python代码&#xff0c;运行后&#xff0c;结果中有7位错误数字&#xff1b;而一个大模型进行加减运算时出错。 例1. 计算 下面是与一个大模型的对话…

常见的php框架有哪几个?

一直以来&#xff0c;PHP作为一种广泛使用的编程语言&#xff0c;拥有着许多优秀的框架来帮助开发人员快速构建稳定的Web应用程序。本文降为大家介绍几种常见的PHP的主流框架&#xff0c;以及它们相关的特点和使用场景。如有问题&#xff0c;欢迎指正&#xff01; 1.Laravel&a…

zerotier已配置但ip连不上?

利用zerotier内网渗透&#xff0c;在公网上远程连接使用局域网内的服务器&#xff0c;经常遇到连接不上的问题 zerotier配置过程 解决方法 声明&#xff1a;个人使用过程中&#xff0c;发现的有效解决方法&#xff0c;不一定能解决所有人的问题 总结&#xff1a; 重启Zerotier…

GORM(Go语言数据交互库)

GORM&#xff08;Go ORM&#xff0c;即对象关系映射&#xff09;是Go语言中非常流行且功能强大的数据库交互库。它简化了与关系型数据库的交互过程&#xff0c;提供了丰富的API来处理各种数据库操作。下面将详细介绍GORM的功能、使用方法和一些高级特性。 1. 安装 首先&#…

Vue+Echarts+百度地图 实现 路径规划

实现功能: 通过选择 相关调拨&#xff0c;系统自动规划 路径&#xff0c;并且以地图的形式呈现最佳路径 技术难点: 1. vue 结合使用 echarts 2.echarts 在 vue嵌入百度地图&#xff0c;并且做出路径 曲线 最终结果:

【算法】图解两个链表相交的一系列问题

问&#xff1a; 给定两个可能有环也可能无环的单链表&#xff0c;头节点head1和head2。请实现一个函数&#xff0c;如果两个链表相交&#xff0c;请返回相交的第一个节点&#xff1b;如果不相交&#xff0c;返回null。如果两个链表长度之和为N&#xff0c;时间复杂度请达到O(N…

Elasticsearch实战指南:从入门到高效使用

Elasticsearch实战指南&#xff1a;从入门到高效使用 1. 引言&#xff1a;Elasticsearch是什么&#xff1f; Elasticsearch是一个分布式、RESTful风格的搜索和分析引擎&#xff0c;广泛应用于全文搜索、日志分析、实时数据分析等场景。它的核心特点包括&#xff1a; 高性能&…

Go-Zero整合Goose实现MySQL数据库版本管理

推荐阅读 【系列好文】go-zero从入门到精通&#xff08;看了就会&#xff09; 教程地址&#xff1a;https://blog.csdn.net/u011019141/article/details/139619172 Go-Zero整合Goose实现MySQL数据库版本管理的教程 在开发中&#xff0c;数据库迁移和版本管理是必不可少的工作。…

JAVA:Spring Boot 集成 JWT 实现身份验证的技术指南

1、简述 在现代Web开发中&#xff0c;安全性尤为重要。为了确保用户的身份&#xff0c;JSON Web Token&#xff08;JWT&#xff09;作为一种轻量级且无状态的身份验证方案&#xff0c;广泛应用于微服务和分布式系统中。本篇博客将讲解如何在Spring Boot 中集成JWT实现身份验证…

【AI学习】地平线首席架构师苏箐关于自动驾驶的演讲

在地平线智驾科技畅想日上&#xff0c;地平线副总裁兼首席架构师苏箐&#xff08;前华为智驾负责人&#xff09;做了即兴演讲&#xff0c;以下是其演讲的主要内容&#xff1a; 对自动驾驶行业的看法 自动驾驶的难度与挑战&#xff1a;苏箐表示自动驾驶非常难&#xff0c;他做自…

说一说mongodb组合索引的匹配规则

一、背景 有一张1000多万条记录的大表&#xff0c;需要做归档至历史表&#xff0c;出现了大量慢查询。 查询条件是 "classroomId": {$in: ["xxx", "xxx", ..... "xxx","xxx", "xxx" ] }耗时近5秒&#xff0c;且…

更新java

下载 Java 下载 |神谕 (oracle.com)

CSS3的aria-hidden学习

前言 aria-hidden 属性可用于隐藏非交互内容&#xff0c;使其在无障碍 API 中不可见。即当aria-hidden"true" 添加到一个元素会将该元素及其所有子元素从无障碍树中移除&#xff0c;这可以通过隐藏来改善辅助技术用户的体验&#xff1a; 纯装饰性内容&#xff0c;如…

LeetCode 3066.超过阈值的最少操作数 II:模拟 - 原地建堆O(1)空间 / 优先队列O(n)空间

【LetMeFly】3066.超过阈值的最少操作数 II&#xff1a;模拟 - 原地建堆O(1)空间 / 优先队列O(n)空间 力扣题目链接&#xff1a;https://leetcode.cn/problems/minimum-operations-to-exceed-threshold-value-ii/ 给你一个下标从 0 开始的整数数组 nums 和一个整数 k 。 一次…

C# 下 SQLite 并发操作与锁库问题的 5 种解决方案

开篇&#xff1a;你是否被 SQLite 并发锁库困扰&#xff1f; 在当今数字化的时代浪潮中&#xff0c;数据已然成为了企业与开发者们手中最为宝贵的资产之一。C# 作为一门广泛应用于各类软件开发的强大编程语言&#xff0c;常常需要与数据库进行紧密交互&#xff0c;以实现数据的…

如何安装cnpm

今天尝试用npm install安装一个项目的依赖&#xff0c;但是无论如何都不能完成&#xff0c;等待时间非常久&#xff0c;所以同事推荐了cnpm&#xff0c;确实非常好用&#xff0c;所以推荐了出来&#xff0c;希望能给大家带来帮助。 cnpm 是中国淘宝团队提供的一个 npm 镜像工具…