gpt4 book ai didi

Python:在 pytest 中比较两个 JSON 对象

转载 作者:太空宇宙 更新时间:2023-11-04 00:27:56 28 4
gpt4 key购买 nike

我有一个返回此 JSON 响应的 API

{
"message": "Staff name and password pair not match",
"errors": {
"resource": "Login",
"field": "staff_authentication",
"code": "invalid",
"stack_trace": null
}
}

我想使用 pytest 构建 JSON 对象的副本并确保它完全相同

import pytest
import json
from collections import namedtuple
from flask import url_for
from myapp import create_app

@pytest.mark.usefixtures('client_class')
class TestAuth:

def test_login(self, client):
assert client.get(url_for('stafflogin')).status_code == 405
res = self._login(client, 'no_such_user', '123456')
assert res.status_code == 422
response_object = self._json2obj(res.data)
assert response_object.message == 'Staff name and password pair not match'
invalid_password_json = dict(message="Staff name and password pair not match",
errors=dict(
resource="Login",
code="invalid",
field="staff_authentication",
stack_trace=None,)
)
assert self._ordered(response_object) == self._ordered(invalid_password_json)

def _login(self, client, staff_name, staff_password):
return client.post('/login',
data=json.dumps(dict(staff_name=staff_name, staff_password=staff_password)),
content_type='application/json',
follow_redirects=True)

def _json_object_hook(self, d): return namedtuple('X', d.keys())(*d.values())
def _json2obj(self, data): return json.loads(data, object_hook=self._json_object_hook)

def _ordered(self, obj):
if isinstance(obj, dict):
return sorted((k, self._ordered(v)) for k, v in obj.items())
if isinstance(obj, list):
return sorted(self._ordered(x) for x in obj)
else:
return obj

pytest 显示这 2 个对象不相等。

>       assert self._ordered(response_object) == self._ordered(invalid_password_json)
E AssertionError: assert X(message='St...k_trace=None)) == [('errors', [(...r not match')]
E At index 0 diff: 'Staff name and password pair not match' != ('errors', [('code', 'invalid'), ('field', 'staff_authentication'), ('resource', 'Login'), ('stack_trace', None)])
E Full diff:
E - X(message='Staff name and password pair not match', errors=X(resource='Login', field='staff_authentication', code='invalid', stack_trace=None))
E + [('errors',
E + [('code', 'invalid'),
E + ('field', 'staff_authentication'),
E + ('resource', 'Login'),
E + ('stack_trace', None)]),
E + ('message', 'Staff name and password pair not match')]

tests/test_app.py:31: AssertionError
=========================== 1 failed in 0.22 seconds ===========================

如何使新创建的 JSON 对象与响应相同?

最佳答案

我没有将 JSON 响应转换为 Object,而是使用 json.loads() 将其转换为 Dictionary,然后比较它们.

def test_login(self, client):
res = return client.post('/login',
data=json.dumps(dict(staff_name='no_such_user', staff_password='password')),
content_type='application/json',
follow_redirects=True)
assert res.status_code == 422
invalid_password_json = dict(message="Staff name and password pair not match",
errors=dict(
resource="Login",
code="invalid",
field="staff_authentication",
stack_trace=None,),
)
assert json.loads(res.data) == invalid_password_json

这样,我就不必担心 JSON 响应中的空格差异以及 JSON 结构的排序问题。只需让 Python 的字典比较函数检查是否相等。

关于Python:在 pytest 中比较两个 JSON 对象,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/46786342/

28 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com