import json
import os
from base import loginfo
from base.setting import setting


class TestCase:
    """
    测试基类
    """

    def __init__(self, **kwargs):
        """
        :param name: 用例名称
        :param priority: 优先级 1,2,3
        :param api_address: 请求地址
        :param save_field: 需要保存的字段
        :param method: 请求方法 post,get
        :param data: 请求参数
        :param expected: 期望结果
        :param actual: 实际结果
        :param case_pass: 是否通过 成功,失败
        """
        self.name = kwargs.get('name')
        self.priority = kwargs.get('priority')
        self.api_address = kwargs.get('api_address')
        self.method = kwargs.get('method')
        # 请求参数--需要转换成json,支持以F=开头的路径方式传入
        self.request_data = kwargs.get('request_data')
        if str(self.request_data).startswith('F='):
            path = self.request_data.split('F=')[-1]
            if setting.json_data['json_data_path']:
                base_path = setting.json_data['json_data_path']
                self.request_data = self.read_json_case(os.path.join(base_path, path))
            else:
                self.request_data = self.read_json_case(path)
        else:
            if isinstance(self.request_data, str):
                self.request_data = json.loads(self.request_data)
        self.expected = kwargs.get('expected')
        self.actual = kwargs.get('actual')
        self.case_pass = kwargs.get('case_pass')
        self.assert_method = kwargs.get('assert_method')
        self.save_field = kwargs.get('save_field')
        self.logs = None

    def read_json_case(self, path):
        with open(path, 'r', encoding='utf-8') as fp:
            data = fp.read()
            try:
                data = json.loads(data)
            except Exception as e:
                print('json数据转换失败{}'.format(e))
            finally:
                return data

    def api_assert(self):
        """
        根据传入参数调用断言方法
        :return: bool
        """
        loginfo.debug('期望结果: {}, 断言方式: {}'.format(self.expected, self.assert_method))
        if self.assert_method == 'include_text':
            self.include_text()
        elif self.assert_method == 'include_json':
            self.include_json()
        elif self.assert_method == 'equal_text':
            self.equal_text()
        elif self.assert_method == '':
            self.assert_json()
        else:
            self.equal_json()

    # 文本包含
    def include_text(self):
        if self.expected in str(self.actual):
            self.case_pass = True

    # json包含
    def include_json(self):
        self.expected = json.loads(self.expected)
        self.actual = json.loads(self.actual)
        if self.assert_json(self.expected, self.actual):
            self.case_pass = True

    def assert_json(self, exp, act):
        if isinstance(exp, str) and isinstance(act, str) and exp == act:
            return True
        elif isinstance(exp, dict):
            for j in exp.keys():
                if j in act:
                    return self.assert_json(exp[j], act[j])
                else:
                    return False
        elif isinstance(exp, list) and isinstance(act, list):
            for i in exp:
                if i in act:
                    return self.assert_json(i, act[act.index(i)])
                else:
                    return False
        else:
            return False

    # 文本相等
    def equal_text(self):
        if self.expected == self.actual:
            self.case_pass = True

    # json相等
    def equal_json(self):
        if self.expected == self.actual:
            self.case_pass = True


if __name__ == '__main__':
    a = {'c': 'ww'}
    b = {'a': 'aaa', 'b': 'bbb', 'c': {'ggg': '111'}, 'd': [{'xsd': 'tttt'}, {'rr': 'aaa'}]}
    print(a)
    print(b)
    a = TestCase().assert_json(a, b)
    print(a)