测试平台系列(7) 改造注册接口

简介: 改造注册接口

引入jwt改造注册接口


回顾

还记得我们之前编写了一个register接口吗?可那只是个空壳,直接返回了注册成功的响应体。


这不禁让我想起以前在某快递网站上,点击催单按钮,对方直接弹出催单成功的alert提示。但我打开了他的html代码,发现只要点击这个按钮就会弹出提示,没有任何后端的交互,这里我就不点名这个韵达快递了哈。只能说真的很秀~

知识准备


  • cookie和session
    传统的web软件,需要存储用户的登录信息。cookie和session是比较常见的模式,当然也是比较古老的模式。其中cookie主要依赖于客户端,可以简单的说是浏览器。可以说用户的登录信息,存储在浏览器的localstorage中。而session,顾名思义,它是将用户存储于服务器中。更好的解释请自行百度。。
  • token
    token从广义说的话,是令牌的意思。我这里是json web token(JWT)的简写。简单的说,就是一种通过存储用户信息(以base64编码存储)然后需要的时候将之解析的方法。这样就达到你这个用户所有信息都被存储为一个字符串而且也看不到具体内容的目的。感兴趣的同学可以去看看~~

Python中的JWT

Python自带了jwt,现在咱们来熟悉一下相关的方法。

先给出我在pity/middleware/Jwt.py中的实现


import hashlib
from datetime import timedelta, datetime
import jwt
from jwt.exceptions import ExpiredSignatureError
EXPIRED_HOUR = 3
class UserToken(object):
    key = 'pityToken'
    salt = 'pity'
    @staticmethod
    def get_token(data):
        new_data = dict({"exp": datetime.utcnow() + timedelta(hours=EXPIRED_HOUR)}, **data)
        return jwt.encode(new_data, key=UserToken.key).decode()
    @staticmethod
    def parse_token(token):
        try:
            return jwt.decode(token, key=UserToken.key)
        except ExpiredSignatureError:
            raise Exception("token已过期, 请重新登录")
    @staticmethod
    def add_salt(password):
        m = hashlib.md5()
        m.update(password + UserToken.salt)
        return m.hexdigest()

UserToken类有3个方法,第一个方法呢,就是把用户信息压缩成一串字符串,并附带3小时的过期时间。


第二个就是解析token为之前的用户信息。


第二个方法add_salt是为了能够用md5码去存储用户密码,一旦有邪恶势力拿到数据库密码的话,不至于会暴露用户的密码,add_salt就是加盐的意思,如果你要反破解md5码,嘿嘿,我这里给你加了一层你想象不到的东西,所以相对来说还是比较安全的呢。

编写核心方法


仔细想一下,我们的用户如果需要注册的话,第一步是先判断这个账号是否已经注册过了。好,那我们来编写第一个方法: register_user

我们新建dao/auth/UserDao.py


from sqlalchemy import or_
from app.middleware.Jwt import UserToken
from app.models import db
from app.models.user import User
from app.utils.logger import Log
class UserDao(object):
    log = Log("UserDao")
    @staticmethod
    def register_user(username, name, password, email):
        """
        :param username: 用户名
        :param name: 姓名
        :param password: 密码
        :param email: 邮箱
        :return:
        """
        try:
            users = User.query.filter(or_(User.username == username, User.email == email)).all()
            if users is not None:
                raise Exception("用户名或邮箱已存在")
            # 注册的时候给密码加盐
            pwd = UserToken.add_salt(password)
            user = User(username, name, pwd, email)
            db.session.add(user)
            db.session.commit()
        except Exception as e:
            UserDao.log.error(f"用户注册失败: {str(e)}")
            return str(e)
        return None


注意,User.query.filter这行代码的意思是,找出所有username或email已经存在的用户,如果有,则抛出异常,没有则直接通过orm插入这行数据。

在orm的世界里,我们实例化的user对象就是数据表中的一行数据,这样理解会否更清晰一点呢?

改造注册接口


1.jpg

image

可以看到这个方法很空洞,我们需要做什么呢。

首先我们是不是得接收传入的用户名/密码/邮箱等注册信息,对参数进行一些关键校验,然后调用刚才的核心方法。如果不出错的话,咱们的登录方法就写好了~

校验参数

2.jpg

image

Flask通过 request.get_json() 可以直接获取到传入的json数据,并返回一个dict对象。

PS: 这么写比较丑陋,暂时先忍忍,后续我们再进行改造。

引入核心方法

3.jpg

image

只是导入了UserDao模块并调用了register方法,如果err不为空,就返回code=110, 意思是报警了(报错了)


说明一下,code=101是参数错误,110是异常错误, 0是正常返回。


注意,这不是什么官方的规定,是我一时兴起哈哈,以后都会按照这个约定来。

完整代码:

简单地测试一下


启动服务

4.jpg

image

可以看到,出现了循环引用的问题,原来我们在app/init.py里面引入了controller,在controller里面又引入了model,在model里面又引入了app/init.py里面的pity对象,所以出现了循环引用。


解决的方法很简单:我们把注册蓝图这种脏活累活都放到run.py,他是最外层,没有人引入run.py的东西。

改动后的app/init.py:


from flask import Flask
from config import Config
pity = Flask(__name__)
pity.config.from_object(Config)

run.py:


from datetime import datetime
from app import pity
from app.utils.logger import Log
from app.controllers.auth.user import auth
# 注册蓝图
pity.register_blueprint(auth)
@pity.route('/')
def hello_world():
    log = Log("hello world")
    log.info("有人访问了你的网站了")
    now = datetime.now().strftime("%Y-%M-%d %H:%M:%S")
    print(now)
    return now
if __name__ == "__main__":
    pity.run("0.0.0.0", threaded=True, port="7777")

打开postman测试一下:

5.jpg

image

不对劲的事情又发生了,好气呀!但是咱们不慌,仔细看一下这个报错,说的是405http方法不允许,找到我们写的接口:

6.jpg

image

原来是这里出了问题,我们稍稍改动一下,将请求方式改成post即可。

7.jpg

image

重启服务try again

8.jpg

image

奇怪了,明明没有注册过这个用户,却提示了这个,首先我们检查一下数据库:

9.jpg

image

发现数据库也没问题,那么我们使出大招,断点疗法:

10.jpg

image

此处点一下会出现一个红色小圆形,再次请求:

11.jpg

image

原来如此,我们的判断除了问题,返回的是个空数组,当然不是None了,所以咱们需要修改下校验方式:

12.jpg

image

重启后继续尝试:

13.jpg

image

这个我看出来了,这一定是md5那块出了问题,仔细找下原因吧。

(太特么自信了,导致前面的图懒得改,只能边写边修改了,以后就不会这样直播写了,写好了直接上代码即可。)

看报错的意思是,unicode必须hash成bytes,多大点事: 直接利用api:

14.jpg

image

重启后继续尝试:

15.jpg

image

真不容易,咱们检查下数据库:

16.jpg

有了,注意密码也不是明文哦

检查下重复注册问题(再次请求一次)


17.jpg

image


时间不早了,今天的内容就到这了,打烊了打烊了,疯狂写bug!!!




相关文章
|
2月前
|
JSON 搜索推荐 网络协议
玩转curl指令—测试简单的HTTP接口
玩转curl指令—测试简单的HTTP接口
59 0
|
2月前
|
资源调度 测试技术 Linux
一款接口自动化神器—开源接口测试平台Lim(Less is More)
一款接口自动化神器—开源接口测试平台Lim(Less is More)
130 2
|
2月前
|
安全 测试技术 持续交付
接口自动化测试的基本流程
接口自动化测试的基本流程
|
2月前
|
监控 安全 测试技术
《Eolink 征文活动- -RESTful接口全解测试-全方位了解Eolink-三神技超亮点》
《Eolink 征文活动- -RESTful接口全解测试-全方位了解Eolink-三神技超亮点》
66 0
|
3天前
|
人工智能 监控 数据处理
【AI大模型应用开发】【LangSmith: 生产级AI应用维护平台】1. 快速上手数据集与测试评估过程
【AI大模型应用开发】【LangSmith: 生产级AI应用维护平台】1. 快速上手数据集与测试评估过程
18 0
|
1月前
|
缓存 运维 Serverless
应用研发平台EMAS产品常见问题之测试检查更新没有反应如何解决
应用研发平台EMAS(Enterprise Mobile Application Service)是阿里云提供的一个全栈移动应用开发平台,集成了应用开发、测试、部署、监控和运营服务;本合集旨在总结EMAS产品在应用开发和运维过程中的常见问题及解决方案,助力开发者和企业高效解决技术难题,加速移动应用的上线和稳定运行。
|
1月前
|
机器学习/深度学习 人工智能 监控
视觉智能平台常见问题之体验产品的美颜测试关掉如何解决
视觉智能平台是利用机器学习和图像处理技术,提供图像识别、视频分析等智能视觉服务的平台;本合集针对该平台在使用中遇到的常见问题进行了收集和解答,以帮助开发者和企业用户在整合和部署视觉智能解决方案时,能够更快地定位问题并找到有效的解决策略。
24 1
|
2月前
|
开发框架 JSON .NET
初学者不会写接口怎么办?微软Visual Studio 2022无脑式API接口创建——Swagger一键导入APIKit快速测试
初学者不会写接口怎么办?微软Visual Studio 2022无脑式API接口创建——Swagger一键导入APIKit快速测试
78 0
|
2月前
|
测试技术
Lim测试平台测试报告说明
Lim测试平台测试报告说明
32 2

热门文章

最新文章