• 30行左右代码实现一个类似httprunner的接口框架


    框架的最终归宿往往是领域语言+模板解析。
    首先先约定一种所要执行操作的表述格式。然后通过模板解析将描述语言转化为代码进行执行。例如,我们可以使用以下yaml文件描述多个步骤并且需要关联的接口:
    apis.yaml:

    - name: 获取百度token接口 # 接口名称
      request:  # 请求报文
        url: https://aip.baidubce.com/oauth/2.0/token
        method: get
        params:
          grant_type: client_credentials
          client_id: kPoFYw85FXsnojsy5bB9hu6x
          client_secret: l7SuGBkDQHkjiTPU3m6NaNddD6SCvDMC
      extract:  # 提取变量, 字典格式
        token:  RESPONSE.json()['access_token']  # RESPONSE系统变量,代表响应对象
    
    - name: 百度ORC接口  # 第二个接口
      request:
        url: https://aip.baidubce.com/rest/2.0/ocr/v1/general_basic?access_token=${token}  # 使用变量
        method: post
        data:  # 请求体(表单格式)
          url: //upload-images.jianshu.io/upload_images/7575721-40c847532432e852.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240
      verify:  # 断言, 列表格式
        - RESPONSE.json()['words_result_num'] == 6
    

    其中,name为该接口或步骤的名称描述,request段是接口的信息,对应requests.request()的每一个参数,urlmethod是必要参数,params,headers,cookies,data, json,files,timeout 等,并使用对应格式。extract用于提取值, token: RESPONSE.json()['access_token'] ,表示提取该接口响应字典中的access_token字段的值保存为名为token的变量。
    在第二个接口的url中通过使用${token},引用该变量。
    verify段类似与extract, 计算表达式的值,通过结果的True/False判断该条断言是否通过。

    上面我们定义了一套接口关联的描述及规则,下面我们要对我们的规则进行解析,并加载运行,主要分为以下几步:

    1. 读取yaml文件并使用yaml.safe_load(f)转为列表/字典
    2. 遍历列表,每个列表项是一个接口
    3. 读取当前列表项(接口)的request段信息,处理${变量}
      1. 将request段(字典格式)重新转会yaml字符串
      2. 如果包含$使用string.Template('字符串').safe_subtitute(locals()),从locals()当前所有局部变量中找到$表示的同名变量,如token,并替换。
      3. 重新将替换后变量的字符串转化为字典
    4. 字典拆包,发送request请求
    5. 如果请求中有extract字段,使用eval()计算表达式的值并保存到局部变量locals()中。
    6. 如果请求中有verify字段,使用eval()计算表达式的值,并判断真假。

    实现代码:

    需要安装pyyaml: pip install pyyaml

    apis_parser.py

    import yaml
    import requests
    from string import Template
    
    with open('apis.yaml', encoding='utf-8') as f:
        apis = yaml.safe_load(f)
    
    for api in apis:
        print("处理请求:", api.get('name'))
        request = api.get('request', {})  # 请求报文,默认值为{}
        # 处理参数化请求中的${变量}
        request_str = yaml.dump(request)  # 先转为字符串
        if '$' in request_str:
            request_str = Template(request_str).safe_substitute(locals())  # 替换${变量}为局部变量中的同名变量
            request = yaml.safe_load(request_str)  # 重新转为字典
        # 发送请求
        res = requests.request(**request)  # 字典解包,发送接口
        # 提取变量
        extract = api.get('extract')
        if extract is not None:  # 如果存在extract
            for key, value in extract.items():
                # 计算value表达式,可使用的全局变量为空,可使用的局部变量为RESPONSE(响应对象)
                # 保存变量结果到局部变量中
                print("提取变量:", key, value)
                locals()[key] = eval(value, {}, {'RESPONSE': res})  
        # 处理断言
        verify = api.get('verify')
        if verify is not None:
            for line in verify:
                result = eval(line, {}, {'RESPONSE': res}) # 计算断言表达式,True代表成功,False代表失败
                print("断言:", line, "结果:", "PASS" if result else "FAIL") 
    
    

    执行结果:

    处理请求: 获取百度token接口
    提取变量: token RESPONSE.json()['access_token']
    处理请求: 百度ORC接口
    断言: RESPONSE.json()['words_result_num'] == 6 结果: PASS
    
  • 相关阅读:
    JsCV Core v0.2发布 & Javascript图像处理系列目录
    Javascript图像处理
    SOE开发之IMapServerSourceDescription
    SOE之JSONObject
    SOE开发之adddynamiclayertomapserver
    JavaScript 的 async/await
    ArcGIS Engine开发系列:将地图导出为图片的两种方法(ZZ)
    原型链
    更优美的javaScript(2)
    CSS选择器
  • 原文地址:https://www.cnblogs.com/superhin/p/11454977.html
Copyright © 2020-2023  润新知