pytest-dsl 0.1.0__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (63) hide show
  1. pytest_dsl/__init__.py +10 -0
  2. pytest_dsl/cli.py +44 -0
  3. pytest_dsl/conftest_adapter.py +4 -0
  4. pytest_dsl/core/__init__.py +0 -0
  5. pytest_dsl/core/auth_provider.py +409 -0
  6. pytest_dsl/core/auto_decorator.py +181 -0
  7. pytest_dsl/core/auto_directory.py +81 -0
  8. pytest_dsl/core/context.py +23 -0
  9. pytest_dsl/core/custom_auth_example.py +425 -0
  10. pytest_dsl/core/dsl_executor.py +329 -0
  11. pytest_dsl/core/dsl_executor_utils.py +84 -0
  12. pytest_dsl/core/global_context.py +103 -0
  13. pytest_dsl/core/http_client.py +411 -0
  14. pytest_dsl/core/http_request.py +810 -0
  15. pytest_dsl/core/keyword_manager.py +109 -0
  16. pytest_dsl/core/lexer.py +139 -0
  17. pytest_dsl/core/parser.py +197 -0
  18. pytest_dsl/core/parsetab.py +76 -0
  19. pytest_dsl/core/plugin_discovery.py +187 -0
  20. pytest_dsl/core/utils.py +146 -0
  21. pytest_dsl/core/variable_utils.py +267 -0
  22. pytest_dsl/core/yaml_loader.py +62 -0
  23. pytest_dsl/core/yaml_vars.py +75 -0
  24. pytest_dsl/docs/custom_keywords.md +140 -0
  25. pytest_dsl/examples/__init__.py +5 -0
  26. pytest_dsl/examples/assert/assertion_example.auto +44 -0
  27. pytest_dsl/examples/assert/boolean_test.auto +34 -0
  28. pytest_dsl/examples/assert/expression_test.auto +49 -0
  29. pytest_dsl/examples/http/__init__.py +3 -0
  30. pytest_dsl/examples/http/builtin_auth_test.auto +79 -0
  31. pytest_dsl/examples/http/csrf_auth_test.auto +64 -0
  32. pytest_dsl/examples/http/custom_auth_test.auto +76 -0
  33. pytest_dsl/examples/http/file_reference_test.auto +111 -0
  34. pytest_dsl/examples/http/http_advanced.auto +91 -0
  35. pytest_dsl/examples/http/http_example.auto +147 -0
  36. pytest_dsl/examples/http/http_length_test.auto +55 -0
  37. pytest_dsl/examples/http/http_retry_assertions.auto +91 -0
  38. pytest_dsl/examples/http/http_retry_assertions_enhanced.auto +94 -0
  39. pytest_dsl/examples/http/http_with_yaml.auto +58 -0
  40. pytest_dsl/examples/http/new_retry_test.auto +22 -0
  41. pytest_dsl/examples/http/retry_assertions_only.auto +52 -0
  42. pytest_dsl/examples/http/retry_config_only.auto +49 -0
  43. pytest_dsl/examples/http/retry_debug.auto +22 -0
  44. pytest_dsl/examples/http/retry_with_fix.auto +21 -0
  45. pytest_dsl/examples/http/simple_retry.auto +20 -0
  46. pytest_dsl/examples/http/vars.yaml +55 -0
  47. pytest_dsl/examples/http_clients.yaml +48 -0
  48. pytest_dsl/examples/keyword_example.py +70 -0
  49. pytest_dsl/examples/test_assert.py +16 -0
  50. pytest_dsl/examples/test_http.py +168 -0
  51. pytest_dsl/keywords/__init__.py +10 -0
  52. pytest_dsl/keywords/assertion_keywords.py +610 -0
  53. pytest_dsl/keywords/global_keywords.py +51 -0
  54. pytest_dsl/keywords/http_keywords.py +430 -0
  55. pytest_dsl/keywords/system_keywords.py +17 -0
  56. pytest_dsl/main_adapter.py +7 -0
  57. pytest_dsl/plugin.py +44 -0
  58. pytest_dsl-0.1.0.dist-info/METADATA +537 -0
  59. pytest_dsl-0.1.0.dist-info/RECORD +63 -0
  60. pytest_dsl-0.1.0.dist-info/WHEEL +5 -0
  61. pytest_dsl-0.1.0.dist-info/entry_points.txt +5 -0
  62. pytest_dsl-0.1.0.dist-info/licenses/LICENSE +21 -0
  63. pytest_dsl-0.1.0.dist-info/top_level.txt +1 -0
@@ -0,0 +1,75 @@
1
+ import os
2
+ import yaml
3
+ from typing import Dict, Any, List, Optional
4
+ from pathlib import Path
5
+
6
+
7
+ class YAMLVariableManager:
8
+ """管理YAML格式的变量文件"""
9
+
10
+ def __init__(self):
11
+ self._loaded_files: List[str] = []
12
+ self._variables: Dict[str, Any] = {}
13
+
14
+ def has_variable(self, name: str) -> bool:
15
+ """检查变量是否存在
16
+
17
+ Args:
18
+ name: 变量名
19
+
20
+ Returns:
21
+ bool: 变量是否存在
22
+ """
23
+ return name in self._variables
24
+
25
+ def load_yaml_file(self, file_path: str) -> None:
26
+ """加载单个YAML文件中的变量"""
27
+ if not os.path.exists(file_path):
28
+ raise FileNotFoundError(f"变量文件不存在: {file_path}")
29
+
30
+ with open(file_path, 'r', encoding='utf-8') as f:
31
+ try:
32
+ variables = yaml.safe_load(f)
33
+ if variables and isinstance(variables, dict):
34
+ # 记录已加载的文件
35
+ self._loaded_files.append(file_path)
36
+ # 更新变量字典,新文件中的变量会覆盖旧的
37
+ self._variables.update(variables)
38
+ except yaml.YAMLError as e:
39
+ raise ValueError(f"YAML文件格式错误 {file_path}: {str(e)}")
40
+
41
+ def load_yaml_files(self, file_paths: List[str]) -> None:
42
+ """批量加载多个YAML文件中的变量"""
43
+ for file_path in file_paths:
44
+ self.load_yaml_file(file_path)
45
+
46
+ def load_from_directory(self, directory: str, pattern: str = "*.yaml") -> None:
47
+ """从指定目录加载所有匹配的YAML文件"""
48
+ dir_path = Path(directory)
49
+ if not dir_path.exists() or not dir_path.is_dir():
50
+ raise NotADirectoryError(f"目录不存在: {directory}")
51
+
52
+ yaml_files = list(dir_path.glob(pattern))
53
+ for yaml_file in yaml_files:
54
+ self.load_yaml_file(str(yaml_file))
55
+
56
+ def get_variable(self, name: str) -> Optional[Any]:
57
+ """获取变量值"""
58
+ return self._variables.get(name)
59
+
60
+ def get_all_variables(self) -> Dict[str, Any]:
61
+ """获取所有已加载的变量"""
62
+ return self._variables.copy()
63
+
64
+ def get_loaded_files(self) -> List[str]:
65
+ """获取已加载的文件列表"""
66
+ return self._loaded_files.copy()
67
+
68
+ def clear(self) -> None:
69
+ """清除所有已加载的变量"""
70
+ self._variables.clear()
71
+ self._loaded_files.clear()
72
+
73
+
74
+ # 创建全局YAML变量管理器实例
75
+ yaml_vars = YAMLVariableManager()
@@ -0,0 +1,140 @@
1
+ # 创建自定义关键字
2
+
3
+ ## 概述
4
+
5
+ pytest-dsl 允许用户在自己的项目中创建自定义关键字,无需修改插件本身的代码。这使得您可以针对自己的项目需求,扩展 DSL 的功能。
6
+
7
+ ## 自动扫描机制
8
+
9
+ pytest-dsl 会自动扫描并导入以下位置的关键字:
10
+
11
+ 1. 内置关键字(插件自带的)
12
+ 2. 通过 `entry_points` 机制注册的第三方插件关键字
13
+ 3. **用户项目中的 `keywords` 目录下的关键字模块**
14
+
15
+ ## 目录结构
16
+
17
+ 要创建自定义关键字,只需在您的项目根目录下创建一个 `keywords` 目录,并在其中添加 Python 模块:
18
+
19
+ ```
20
+ 项目根目录/
21
+ ├── keywords/ # 关键字根目录
22
+ │ ├── __init__.py # 可选,如果要作为包导入
23
+ │ ├── my_keywords.py # 顶层关键字模块
24
+ │ ├── another_module.py # 顶层关键字模块
25
+ │ └── web/ # 子目录(可选作为子包)
26
+ │ ├── __init__.py # 可选,如果要作为子包导入
27
+ │ └── selenium_keywords.py # 子目录中的关键字模块
28
+ ├── tests/ # 测试目录
29
+ │ └── test_dsl.py # 使用 pytest-dsl 运行的测试
30
+ └── pytest.ini # pytest 配置文件
31
+ ```
32
+
33
+ ## 创建自定义关键字
34
+
35
+ 在 `keywords` 目录下的任何 Python 文件中,您都可以使用 `keyword_manager.register` 装饰器来注册自定义关键字。
36
+
37
+ ### 基本示例
38
+
39
+ ```python
40
+ from pytest_dsl.core.keyword_manager import keyword_manager
41
+
42
+ @keyword_manager.register('打印消息', [
43
+ {'name': '消息', 'mapping': 'message', 'description': '要打印的消息内容'},
44
+ ])
45
+ def print_message(**kwargs):
46
+ """打印一条消息到控制台
47
+
48
+ Args:
49
+ message: 要打印的消息
50
+ context: 测试上下文 (自动传入)
51
+ """
52
+ message = kwargs.get('message', '')
53
+ print(f"自定义关键字消息: {message}")
54
+ return True
55
+ ```
56
+
57
+ ### 带返回值的关键字
58
+
59
+ ```python
60
+ @keyword_manager.register('生成随机数', [
61
+ {'name': '最小值', 'mapping': 'min_value', 'description': '随机数范围最小值'},
62
+ {'name': '最大值', 'mapping': 'max_value', 'description': '随机数范围最大值'},
63
+ ])
64
+ def generate_random(**kwargs):
65
+ """生成指定范围内的随机整数
66
+
67
+ Args:
68
+ min_value: 最小值
69
+ max_value: 最大值
70
+ context: 测试上下文 (自动传入)
71
+
72
+ Returns:
73
+ 随机整数
74
+ """
75
+ import random
76
+ min_value = int(kwargs.get('min_value', 1))
77
+ max_value = int(kwargs.get('max_value', 100))
78
+
79
+ result = random.randint(min_value, max_value)
80
+ return result
81
+ ```
82
+
83
+ ## 参数说明
84
+
85
+ 在注册关键字时,您需要提供参数的定义列表:
86
+
87
+ ```python
88
+ @keyword_manager.register('关键字名称', [
89
+ {'name': '中文参数名', 'mapping': '英文参数名', 'description': '参数描述'},
90
+ # 更多参数...
91
+ ])
92
+ ```
93
+
94
+ - `name`: 中文参数名,用在 DSL 文件中调用该关键字时使用
95
+ - `mapping`: 英文参数名,映射到函数参数名
96
+ - `description`: 参数描述,用于生成文档
97
+
98
+ ## 使用上下文
99
+
100
+ 每个关键字函数都会自动接收一个 `context` 参数,这是测试运行时的上下文对象:
101
+
102
+ ```python
103
+ @keyword_manager.register('保存到上下文', [
104
+ {'name': '键名', 'mapping': 'key', 'description': '保存在上下文中的键名'},
105
+ {'name': '值', 'mapping': 'value', 'description': '要保存的值'},
106
+ ])
107
+ def save_to_context(**kwargs):
108
+ """将值保存到测试上下文中"""
109
+ key = kwargs.get('key')
110
+ value = kwargs.get('value')
111
+ context = kwargs.get('context')
112
+
113
+ if key and context:
114
+ context.set(key, value)
115
+ return True
116
+ return False
117
+ ```
118
+
119
+ ## 在 DSL 中使用自定义关键字
120
+
121
+ 一旦您注册了自定义关键字,就可以在 DSL 文件中使用它们:
122
+
123
+ ```
124
+ # 测试: 自定义关键字演示
125
+ @name 自定义关键字测试
126
+ @description 演示如何使用自定义关键字
127
+
128
+ # 使用自定义关键字
129
+ 打印消息 消息="这是一条自定义消息"
130
+
131
+ # 带返回值的关键字
132
+ 随机数 = 生成随机数 最小值=1 最大值=100
133
+
134
+ # 打印结果
135
+ 打印消息 消息="生成的随机数是: ${随机数}"
136
+ ```
137
+
138
+ ## 更多示例
139
+
140
+ 查看 `pytest_dsl/examples/keyword_example.py` 文件获取更多示例。
@@ -0,0 +1,5 @@
1
+ """
2
+ pytest-dsl示例模块
3
+
4
+ 包含框架使用的示例代码和资源文件。
5
+ """
@@ -0,0 +1,44 @@
1
+ @name: 断言关键字示例
2
+ @description: 演示不同断言关键字的使用方法
3
+ @tags: [断言, JSON, 示例]
4
+ @author: Felix
5
+ @date: 2024-01-01
6
+
7
+ # 基本断言示例
8
+ [断言],条件:'1 + 1 == 2',消息:'基本算术断言失败'
9
+
10
+ # 字符串断言
11
+ str_value = "Hello, World!"
12
+ [断言],条件:'${str_value} contains "Hello"',消息:'字符串包含断言失败'
13
+
14
+ # 数字比较
15
+ num1 = 10
16
+ num2 = 5
17
+ [数据比较],实际值:${num1},预期值:${num2},操作符:'>',消息:'数字比较断言失败'
18
+
19
+ # 类型断言
20
+ [类型断言],值:${str_value},类型:'string',消息:'类型断言失败'
21
+ [类型断言],值:${num1},类型:'number',消息:'类型断言失败'
22
+
23
+ # JSON数据处理
24
+ json_data = '{"user": {"name": "张三", "age": 30, "roles": ["admin", "user"], "address": {"city": "北京", "country": "中国"}}}'
25
+
26
+ # JSON提取示例
27
+ username = [JSON提取],JSON数据:${json_data},JSONPath:'$.user.name',变量名:'username'
28
+ [断言],条件:'${username} == "张三"',消息:'JSON提取断言失败'
29
+
30
+ # JSON断言示例
31
+ [JSON断言],JSON数据:${json_data},JSONPath:'$.user.age',预期值:30,操作符:'==',消息:'JSON断言失败:年龄不匹配'
32
+
33
+ [JSON断言],JSON数据:${json_data},JSONPath:'$.user.roles[0]',预期值:'admin',消息:'JSON断言失败:角色不匹配'
34
+
35
+ # 复杂JSON断言
36
+ [JSON断言],JSON数据:${json_data},JSONPath:'$.user.address.city',预期值:'北京',消息:'JSON断言失败:城市不匹配'
37
+
38
+ # 布尔值断言
39
+ bool_value = True
40
+ [断言],条件:'${bool_value} == True',消息:'布尔值断言失败'
41
+
42
+ @teardown do
43
+ [打印],内容:'所有断言测试通过!'
44
+ end
@@ -0,0 +1,34 @@
1
+ @name: 布尔值断言测试
2
+ @description: 测试断言关键字中的布尔值处理功能
3
+ @tags: [断言, 布尔值, 示例]
4
+ @author: Felix
5
+ @date: 2024-01-01
6
+
7
+ # 基本布尔值测试
8
+ [断言],条件:'True == True',消息:'布尔值相等断言失败'
9
+ [断言],条件:'False == False',消息:'布尔值相等断言失败'
10
+ [断言],条件:'True != False',消息:'布尔值不等断言失败'
11
+
12
+ # 字符串形式的布尔值测试
13
+ true_string = 'True'
14
+ false_string = 'False'
15
+ [断言],条件:'${true_string} == True',消息:'字符串布尔值与布尔值相等断言失败'
16
+ [断言],条件:'${false_string} == False',消息:'字符串布尔值与布尔值相等断言失败'
17
+
18
+ # 使用数据比较关键字
19
+ [数据比较],实际值:'True',预期值:True,消息:'布尔值数据比较失败'
20
+ [数据比较],实际值:'false',预期值:False,消息:'小写布尔值数据比较失败'
21
+
22
+ # 使用布尔值表达式
23
+ [断言],条件:'True and True',消息:'布尔值AND表达式断言失败'
24
+ [断言],条件:'True or False',消息:'布尔值OR表达式断言失败'
25
+ [断言],条件:'not False',消息:'布尔值NOT表达式断言失败'
26
+
27
+ # 变量布尔值表达式
28
+ bool_true = True
29
+ bool_false = False
30
+ [断言],条件:'${bool_true} and not ${bool_false}',消息:'变量布尔值表达式断言失败'
31
+
32
+ @teardown do
33
+ [打印],内容:'所有布尔值断言测试通过!'
34
+ end
@@ -0,0 +1,49 @@
1
+ @name: 表达式断言测试
2
+ @description: 测试断言关键字中的表达式支持功能
3
+ @tags: [断言, 表达式, 示例]
4
+ @author: Felix
5
+ @date: 2024-01-01
6
+
7
+ # 基本算术表达式
8
+ [断言],条件:'1 + 1 == 2',消息:'基本加法断言失败'
9
+ [断言],条件:'10 - 5 == 5',消息:'基本减法断言失败'
10
+ [断言],条件:'3 * 4 == 12',消息:'基本乘法断言失败'
11
+ [断言],条件:'20 / 4 == 5',消息:'基本除法断言失败'
12
+ [断言],条件:'10 % 3 == 1',消息:'基本取模断言失败'
13
+
14
+ # 复杂算术表达式
15
+ [断言],条件:'(10 + 5) * 2 == 30',消息:'复合算术断言失败'
16
+ [断言],条件:'10 + 5 * 2 == 20',消息:'优先级算术断言失败'
17
+
18
+ # 表达式与变量结合
19
+ base_value = 10
20
+ multiplier = 2
21
+ [断言],条件:'${base_value} * ${multiplier} == 20',消息:'变量表达式断言失败'
22
+
23
+ # 字符串长度表达式
24
+ text = "Hello, World!"
25
+ [断言],条件:'len("${text}") == 13',消息:'字符串长度断言失败'
26
+
27
+ # 复杂字符串操作
28
+ [断言],条件:'"${text}".upper() contains "HELLO"',消息:'字符串方法断言失败'
29
+ [断言],条件:'"${text}".split(",")[0] == "Hello"',消息:'字符串分割断言失败'
30
+
31
+ # 直接算术表达式在左值
32
+ [断言],条件:'5 + 5 > 8',消息:'左值表达式断言失败'
33
+ [断言],条件:'5 + 5 < 20',消息:'左值表达式断言失败'
34
+
35
+ # 直接函数调用
36
+ [断言],条件:'len("test") == 4',消息:'函数调用断言失败'
37
+
38
+ # 列表和字典操作
39
+ [断言],条件:'len([1, 2, 3, 4]) == 4',消息:'列表长度断言失败'
40
+ [断言],条件:'3 in [1, 2, 3, 4]',消息:'列表包含断言失败'
41
+ [断言],条件:'"key" in {"key": "value"}',消息:'字典键断言失败'
42
+
43
+ # 数据比较关键字与表达式结合
44
+ [数据比较],实际值:'10 + 10',预期值:20,消息:'数据比较表达式失败'
45
+ [数据比较],实际值:'len("Hello")',预期值:5,消息:'函数表达式比较失败'
46
+
47
+ @teardown do
48
+ [打印],内容:'所有表达式断言测试通过!'
49
+ end
@@ -0,0 +1,3 @@
1
+ """
2
+ HTTP请求关键字示例模块
3
+ """
@@ -0,0 +1,79 @@
1
+ @name: 内置认证测试
2
+ @description: 演示内置认证提供者的使用
3
+ @tags: [HTTP, API, 授权, 示例]
4
+ @author: Felix
5
+ @date: 2024-05-01
6
+
7
+ # 内置认证测试示例
8
+ # 演示内置认证提供者的使用
9
+
10
+ # 测试Basic认证
11
+ [HTTP请求],客户端:'basic_auth',配置:'''
12
+ method: GET
13
+ url: /headers
14
+ captures:
15
+ auth_header: ["jsonpath", "$.headers.Authorization"]
16
+ asserts:
17
+ - ["status", "eq", 200]
18
+ - ["jsonpath", "$.headers.Authorization", "startswith", "Basic "]
19
+ '''
20
+
21
+ [打印],内容:'Basic认证头: ${auth_header}'
22
+
23
+ # 测试Token认证
24
+ [HTTP请求],客户端:'token_auth',配置:'''
25
+ method: GET
26
+ url: /headers
27
+ captures:
28
+ auth_header: ["jsonpath", "$.headers.Authorization"]
29
+ asserts:
30
+ - ["status", "eq", 200]
31
+ - ["jsonpath", "$.headers.Authorization", "eq", "Bearer test_token"]
32
+ '''
33
+
34
+ [打印],内容:'Token认证头: ${auth_header}'
35
+
36
+ # 测试API Key认证 (Header)
37
+ [HTTP请求],客户端:'api_key_auth',配置:'''
38
+ method: GET
39
+ url: /headers
40
+ captures:
41
+ api_key: ["jsonpath", "$.headers.X-Api-Key"]
42
+ all_headers: ["jsonpath", "$.headers"]
43
+ asserts:
44
+ - ["status", "eq", 200]
45
+ - ["jsonpath", "$.headers.X-Api-Key", "eq", "test_api_key"]
46
+ '''
47
+
48
+ [打印],内容:'API Key认证头: ${api_key}'
49
+ [打印],内容:'所有响应头: ${all_headers}'
50
+
51
+ # 测试API Key认证 (Query)
52
+ [HTTP请求],客户端:'api_key_query_auth',配置:'''
53
+ method: GET
54
+ url: /anything
55
+ captures:
56
+ api_key: ["jsonpath", "$.args.api_key"]
57
+ all_args: ["jsonpath", "$.args"]
58
+ asserts:
59
+ - ["status", "eq", 200]
60
+ - ["jsonpath", "$.args.api_key", "eq", "test_api_key"]
61
+ '''
62
+
63
+ [打印],内容:'API Key查询参数: ${api_key}'
64
+ [打印],内容:'所有查询参数: ${all_args}'
65
+
66
+ # 测试禁用认证
67
+ [HTTP请求],客户端:'basic_auth',配置:'''
68
+ method: GET
69
+ url: /headers
70
+ disable_auth: true
71
+ captures:
72
+ all_headers: ["jsonpath", "$.headers"]
73
+ asserts:
74
+ - ["status", "eq", 200]
75
+ - ["jsonpath", "$.headers.Authorization", "not_exists"]
76
+ '''
77
+
78
+ [打印],内容:'禁用认证后的响应头: ${all_headers}'
79
+ [打印],内容:'内置认证测试完成'
@@ -0,0 +1,64 @@
1
+ @name: CSRF登录授权测试
2
+ @description: 演示CSRF登录授权提供者的使用
3
+ @tags: [HTTP, API, 授权, CSRF, 示例]
4
+ @author: Felix
5
+ @date: 2024-05-20
6
+
7
+ # CSRF登录授权测试示例
8
+ # 演示CSRF登录授权提供者的使用
9
+
10
+ # 测试CSRF登录认证
11
+ [HTTP请求],客户端:'csrf_auth',配置:'''
12
+ method: GET
13
+ url: /headers
14
+ captures:
15
+ csrf_token: ["jsonpath", "$.headers.X-Csrf-Token"]
16
+ asserts:
17
+ - ["status", "eq", 200]
18
+ - ["jsonpath", "$.headers.X-Csrf-Token", "exists"]
19
+ '''
20
+
21
+ [打印],内容:'CSRF令牌: ${csrf_token}'
22
+
23
+ # 测试CSRF令牌过期后自动重新登录
24
+ [HTTP请求],客户端:'csrf_auth',配置:'''
25
+ method: GET
26
+ url: /headers
27
+ headers:
28
+ X-Csrf-Token: expired_token # 模拟过期令牌
29
+ captures:
30
+ csrf_token: ["jsonpath", "$.headers.X-Csrf-Token"]
31
+ asserts:
32
+ - ["status", "eq", 200]
33
+ - ["jsonpath", "$.headers.X-Csrf-Token", "exists"]
34
+ '''
35
+
36
+ [打印],内容:'新的CSRF令牌: ${csrf_token}'
37
+
38
+ # 测试需要CSRF令牌的POST请求
39
+ [HTTP请求],客户端:'csrf_auth',配置:'''
40
+ method: POST
41
+ url: /anything
42
+ json:
43
+ test: "data"
44
+ captures:
45
+ headers: ["jsonpath", "$.headers"]
46
+ json: ["jsonpath", "$.json"]
47
+ asserts:
48
+ - ["status", "eq", 200]
49
+ - ["jsonpath", "$.headers.X-Csrf-Token", "exists"]
50
+ '''
51
+
52
+ [打印],内容:'请求头: ${headers}'
53
+ [打印],内容:'请求体: ${json}'
54
+
55
+ # 测试禁用CSRF认证
56
+ [HTTP请求],客户端:'csrf_auth',配置:'''
57
+ method: GET
58
+ url: /headers
59
+ disable_auth: true
60
+ asserts:
61
+ - ["status", "eq", 200]
62
+ '''
63
+
64
+ [打印],内容:'CSRF登录授权测试完成'
@@ -0,0 +1,76 @@
1
+ @name: 自定义授权测试
2
+ @description: 演示自定义授权提供者的使用
3
+ @tags: [HTTP, API, 授权, 示例]
4
+ @author: Felix
5
+ @date: 2024-05-01
6
+
7
+ # 自定义授权测试示例
8
+ # 演示自定义授权提供者的使用
9
+
10
+ # 测试HMAC签名授权
11
+ [HTTP请求],客户端:'hmac_auth',配置:'''
12
+ method: GET
13
+ url: /headers
14
+ captures:
15
+ auth_header: ["jsonpath", "$.headers.Authorization"]
16
+ asserts:
17
+ - ["status", "eq", 200]
18
+ - ["jsonpath", "$.headers.Authorization", "exists"]
19
+ - ["jsonpath", "$.headers.X-Amz-Date", "exists"]
20
+ '''
21
+
22
+ [打印],内容:'HMAC授权头: ${auth_header}'
23
+
24
+ # 测试JWT刷新令牌授权
25
+ [HTTP请求],客户端:'jwt_auth',配置:'''
26
+ method: GET
27
+ url: /headers
28
+ captures:
29
+ auth_header: ["jsonpath", "$.headers.Authorization"]
30
+ asserts:
31
+ - ["status", "eq", 200]
32
+ - ["jsonpath", "$.headers.Authorization", "startswith", "Bearer "]
33
+ '''
34
+
35
+ [打印],内容:'JWT授权头: ${auth_header}'
36
+
37
+ # 测试微信小程序授权
38
+ [HTTP请求],客户端:'wechat_auth',配置:'''
39
+ method: GET
40
+ url: /headers
41
+ captures:
42
+ openid: ["jsonpath", "$.headers.X-Wx-Openid"]
43
+ session_key: ["jsonpath", "$.headers.X-Wx-Session-Key"]
44
+ asserts:
45
+ - ["status", "eq", 200]
46
+ - ["jsonpath", "$.headers.X-Wx-Openid", "exists"]
47
+ - ["jsonpath", "$.headers.X-Wx-Session-Key", "exists"]
48
+ '''
49
+
50
+ [打印],内容:'微信OpenID: ${openid}'
51
+ [打印],内容:'微信Session Key: ${session_key}'
52
+
53
+ # 测试多步骤授权
54
+ [HTTP请求],客户端:'multi_step_auth',配置:'''
55
+ method: GET
56
+ url: /headers
57
+ captures:
58
+ auth_header: ["jsonpath", "$.headers.Authorization"]
59
+ asserts:
60
+ - ["status", "eq", 200]
61
+ - ["jsonpath", "$.headers.Authorization", "startswith", "Bearer "]
62
+ '''
63
+
64
+ [打印],内容:'多步骤授权头: ${auth_header}'
65
+
66
+ # 测试禁用授权
67
+ [HTTP请求],客户端:'multi_step_auth',配置:'''
68
+ method: GET
69
+ url: /headers
70
+ disable_auth: true
71
+ asserts:
72
+ - ["status", "eq", 200]
73
+ - ["jsonpath", "$.headers.Authorization", "not_exists"]
74
+ '''
75
+
76
+ [打印],内容:'自定义授权测试完成'