fix:修改SqlResponseObject继承关系;添加thriftpy2依赖

This commit is contained in:
duanchao.bill
2022-04-27 17:37:14 +08:00
parent 0db832ca22
commit 42e56f7cc8
14 changed files with 150 additions and 64 deletions

View File

@@ -43,7 +43,8 @@ class TestCompat(unittest.TestCase):
"body.data.buildings[0].building_id",
)
self.assertEqual(
compat._convert_jmespath("body.users[-1]"), "body.users[-1]",
compat._convert_jmespath("body.users[-1]"),
"body.users[-1]",
)
self.assertEqual(
compat._convert_jmespath("body.result.WorkNode_-1"),

View File

@@ -97,7 +97,11 @@ class TestLoader(unittest.TestCase):
)
def test_load_env_path_not_exist(self):
dot_env_path = os.path.join(os.getcwd(), "tests", "data",)
dot_env_path = os.path.join(
os.getcwd(),
"tests",
"data",
)
env_variables_mapping = loader.load_dot_env_file(dot_env_path)
self.assertEqual(env_variables_mapping, {})

View File

@@ -534,7 +534,8 @@ def main_make(tests_paths: List[Text]) -> List[Text]:
def init_make_parser(subparsers):
"""make testcases: parse command line options and run commands."""
parser = subparsers.add_parser(
"make", help="Convert YAML/JSON testcases to pytest cases.",
"make",
help="Convert YAML/JSON testcases to pytest cases.",
)
parser.add_argument(
"testcase_path", nargs="*", help="Specify YAML/JSON testcase file/folder path"

View File

@@ -73,7 +73,8 @@ from request_methods.request_with_functions_test import (
content,
)
self.assertIn(
".call(RequestWithFunctions)", content,
".call(RequestWithFunctions)",
content,
)
def test_make_testcase_folder(self):
@@ -111,7 +112,8 @@ from request_methods.request_with_functions_test import (
)
loader.project_meta = None
self.assertEqual(
ensure_file_abs_path_valid(os.getcwd()), os.getcwd(),
ensure_file_abs_path_valid(os.getcwd()),
os.getcwd(),
)
loader.project_meta = None
self.assertEqual(
@@ -122,11 +124,17 @@ from request_methods.request_with_functions_test import (
def test_convert_testcase_path(self):
self.assertEqual(
convert_testcase_path(os.path.join(self.data_dir, "a-b.c", "2 3.yml")),
(os.path.join(self.data_dir, "a_b_c", "T2_3_test.py"), "T23",),
(
os.path.join(self.data_dir, "a_b_c", "T2_3_test.py"),
"T23",
),
)
self.assertEqual(
convert_testcase_path(os.path.join(self.data_dir, "a-b.c", "中文case.yml")),
(os.path.join(self.data_dir, "a_b_c", "中文case_test.py"), "中文Case",),
(
os.path.join(self.data_dir, "a_b_c", "中文case_test.py"),
"中文Case",
),
)
def test_make_config_chain_style(self):
@@ -145,7 +153,11 @@ from request_methods.request_with_functions_test import (
def test_make_teststep_chain_style(self):
step = {
"name": "get with params",
"variables": {"foo1": "bar1", "foo2": 123, "sum_v": "${sum_two(1, 2)}",},
"variables": {
"foo1": "bar1",
"foo2": 123,
"sum_v": "${sum_two(1, 2)}",
},
"request": {
"method": "GET",
"url": "/get",

View File

@@ -76,7 +76,7 @@ class TransportEnum(Text, Enum):
class TThriftRequest(BaseModel):
""" rpc request model"""
"""rpc request model"""
method: Text = ""
params: Dict = {}
@@ -106,7 +106,7 @@ class SqlMethodEnum(Text, Enum):
class TSqlRequest(BaseModel):
""" sql request model"""
"""sql request model"""
db_config: TConfigDB = TConfigDB()
method: SqlMethodEnum = None

View File

@@ -476,7 +476,9 @@ def parse_variables_mapping(
return parsed_variables
def parse_parameters(parameters: Dict,) -> List[Dict]:
def parse_parameters(
parameters: Dict,
) -> List[Dict]:
"""parse parameters and generate cartesian product.
Args:

View File

@@ -11,7 +11,7 @@ from httprunner.parser import parse_string_value, Parser
def get_uniform_comparator(comparator: Text):
""" convert comparator alias to uniform name"""
"""convert comparator alias to uniform name"""
if comparator in ["eq", "equals", "equal"]:
return "equal"
elif comparator in ["lt", "less_than"]:
@@ -114,7 +114,7 @@ def uniform_validator(validator):
class ResponseObjectBase(object):
def __init__(self, resp_obj, parser: Parser):
""" initialize with a response object
"""initialize with a response object
Args:
resp_obj (instance): requests.Response instance
@@ -125,7 +125,9 @@ class ResponseObjectBase(object):
self.validation_results: Dict = {}
def extract(
self, extractors: Dict[Text, Text], variables_mapping: VariablesMapping = None,
self,
extractors: Dict[Text, Text],
variables_mapping: VariablesMapping = None,
) -> Dict[Text, Any]:
if not extractors:
return {}
@@ -142,10 +144,22 @@ class ResponseObjectBase(object):
return extract_mapping
def _search_jmespath(self, expr: Text) -> Any:
raise NotImplementedError("_search_jmespath not override")
try:
check_value = jmespath.search(expr, self.resp_obj)
except JMESPathError as ex:
logger.error(
f"failed to search with jmespath\n"
f"expression: {expr}\n"
f"data: {self.resp_obj}\n"
f"exception: {ex}"
)
raise
return check_value
def validate(
self, validators: Validators, variables_mapping: VariablesMapping = None,
self,
validators: Validators,
variables_mapping: VariablesMapping = None,
):
variables_mapping = variables_mapping or {}
@@ -277,19 +291,8 @@ class ResponseObject(ResponseObjectBase):
class ThriftResponseObject(ResponseObjectBase):
def _search_jmespath(self, expr: Text) -> Any:
try:
check_value = jmespath.search(expr, self.resp_obj)
except JMESPathError as ex:
logger.error(
f"failed to search with jmespath\n"
f"expression: {expr}\n"
f"data: {self.resp_obj}\n"
f"exception: {ex}"
)
raise
return check_value
class SqlResponseObject(ThriftResponseObject):
pass
class SqlResponseObject(ResponseObjectBase):
pass

View File

@@ -61,6 +61,9 @@ class TestResponse(unittest.TestCase):
def test_validate_functions(self):
variables_mapping = {"index": 1}
self.resp_obj.validate(
[{"eq": ["${get_num(0)}", 0]}, {"eq": ["${get_num($index)}", 1]},],
[
{"eq": ["${get_num(0)}", 0]},
{"eq": ["${get_num($index)}", 1]},
],
variables_mapping=variables_mapping,
)

View File

@@ -67,7 +67,10 @@ def call_hooks(
def run_step_request(runner: HttpRunner, step: TStep) -> StepResult:
"""run teststep: request"""
step_result = StepResult(name=step.name, success=False,)
step_result = StepResult(
name=step.name,
success=False,
)
start_time = time.time()
step.variables = runner.merge_step_variables(step.variables)
@@ -79,7 +82,8 @@ def run_step_request(runner: HttpRunner, step: TStep) -> StepResult:
request_dict.pop("upload", None)
parsed_request_dict = runner.parser.parse_data(request_dict, step.variables)
parsed_request_dict["headers"].setdefault(
"HRUN-Request-ID", f"HRUN-{runner.case_id}-{str(int(time.time() * 1000))[-6:]}",
"HRUN-Request-ID",
f"HRUN-{runner.case_id}-{str(int(time.time() * 1000))[-6:]}",
)
step.variables["request"] = parsed_request_dict

View File

@@ -23,7 +23,10 @@ def run_step_sql_request(runner: HttpRunner, step: TStep) -> StepResult:
"""run teststep:sql request"""
start_time = time.time()
step_result = StepResult(name=step.name, success=False,)
step_result = StepResult(
name=step.name,
success=False,
)
step.variables = runner.merge_step_variables(step.variables)
# parse
request_dict = step.sql_request.dict()
@@ -48,11 +51,7 @@ def run_step_sql_request(runner: HttpRunner, step: TStep) -> StepResult:
parsed_request_dict["db_config"]["database"] or config.db.database
)
if parsed_request_dict["db_config"]["psm"]:
runner.db_engine = DBEngine(
f'mysql+pymysql://:@/?charset=utf8mb4&db_psm={parsed_request_dict["psm"]}'
)
else:
if not runner.db_engine:
runner.db_engine = DBEngine(
f'mysql+pymysql://{parsed_request_dict["db_config"]["user"]}:'
f'{parsed_request_dict["db_config"]["password"]}@{parsed_request_dict["db_config"]["ip"]}:'
@@ -171,10 +170,8 @@ class RunSqlRequest(IStep):
return self
def with_db_config(
self, psm=None, user=None, password=None, ip=None, port=None, database=None
self, user=None, password=None, ip=None, port=None, database=None, psm=None
):
if psm:
self.__step.sql_request.db_config.psm = psm
if user:
self.__step.sql_request.db_config.user = user
if password:
@@ -185,6 +182,8 @@ class RunSqlRequest(IStep):
self.__step.sql_request.db_config.port = port
if database:
self.__step.sql_request.db_config.database = database
if psm:
self.__step.sql_request.db_config.psm = psm
return self
def fetchone(self, sql) -> "RunSqlRequest":

View File

@@ -22,7 +22,10 @@ def run_step_thrift_request(runner: HttpRunner, step: TStep) -> StepResult:
"""run teststep:thrift request"""
start_time = time.time()
step_result = StepResult(name=step.name, success=False,)
step_result = StepResult(
name=step.name,
success=False,
)
step.variables = runner.merge_step_variables(step.variables)
# parse
request_dict = step.thrift_request.dict()
@@ -65,17 +68,18 @@ def run_step_thrift_request(runner: HttpRunner, step: TStep) -> StepResult:
step.variables["thrift_request"] = parsed_request_dict
psm = parsed_request_dict["psm"]
runner.thrift_client = parsed_request_dict["thrift_client"]
if not runner.thrift_client:
runner.thrift_client = parsed_request_dict["thrift_client"]
if not runner.thrift_client:
runner.thrift_client = ThriftClient(
parsed_request_dict["idl_path"],
parsed_request_dict["service_name"],
parsed_request_dict["ip"],
parsed_request_dict["port"],
parsed_request_dict["timeout"],
parsed_request_dict["proto_type"],
parsed_request_dict["trans_port"],
thrift_file=parsed_request_dict["idl_path"],
service_name=parsed_request_dict["service_name"],
ip=parsed_request_dict["ip"],
port=parsed_request_dict["port"],
include_dirs=parsed_request_dict["include_dirs"],
timeout=parsed_request_dict["timeout"],
proto_type=parsed_request_dict["proto_type"],
trans_type=parsed_request_dict["trans_port"],
)
# setup hooks

View File

@@ -78,9 +78,7 @@ def unicode_2_utf8_keep_native(para):
def encode_basestring(s):
"""Return a JSON representation of a Python string
"""
"""Return a JSON representation of a Python string"""
def replace(match):
return ESCAPE_DCT[match.group(0)]
@@ -89,9 +87,7 @@ def encode_basestring(s):
def py_encode_basestring_ascii(s):
"""Return an ASCII-only JSON representation of a Python string
"""
"""Return an ASCII-only JSON representation of a Python string"""
if isinstance(s, str) and HAS_UTF8.search(s) is not None:
s = s.decode("utf-8")
@@ -289,10 +285,10 @@ class MyJSONEncoder(json.JSONEncoder):
def encode(self, o):
"""Return a JSON string representation of a Python data structure.
JSONEncoder().encode({"foo": ["bar", "baz"]})
'{"foo": ["bar", "baz"]}'
JSONEncoder().encode({"foo": ["bar", "baz"]})
'{"foo": ["bar", "baz"]}'
"""
"""
# This is for extremely simple cases and benchmarks.
if isinstance(o, str):
@@ -363,7 +359,7 @@ class ThriftJSONEncoder(json.JSONEncoder):
JSONEncoder().encode({"foo": ["bar", "baz"]})
'{"foo": ["bar", "baz"]}'
"""
"""
# This is for extremely simple cases and benchmarks.
if isinstance(o, str):