1- <!-- TestPilot-Template-Version: 7 -->
2- # Windows 桌面应用平台蓝本规则(platform = "desktop")
1+ <!-- TestPilot-Template-Version: 8 -->
2+ # Windows 獢摨撟喳�閫�嚗latform = "desktop"嚗?
33
4- > 本文件定义 Windows 桌面应用(WPF /WinForms/Electron/Qt 等)蓝本的完整规则。
5- > 桌面测试通过 pywinauto / UI Automation 驱动。
6- > 生成蓝本前 ** 必须 ** 通读本文件,不得跳过任何章节。
4+ > �祆�隞嗅�銋? Windows 獢摨嚗PF /WinForms/Electron/Qt 蝑�����渲��?
5+ > 獢瘚��� pywinauto / UI Automation 撽勗�?
6+ > ����? * 敹◆ ** �粉�祆�隞塚�銝�頝唾�隞颱�蝡��?
77
88---
99
10- ## 零、生成蓝本前必须先通读源代码(强制执行)
10+ ## �嗚����砍�敹◆�粉皞誨��撘箏�扯�嚗?
1111
12- ** 蓝本的唯一依据是代码,不是猜测,不是常识,不是用户描述。 * *
12+ ** ��銝靘�臭誨��銝��嚗��臬虜霂�銝�冽�膩�? *
1313
14- 在写任何 JSON 之前,必须按顺序完成:
14+ �典�隞颱� JSON 銋�嚗�憿餅�憿箏�摰�嚗?
1515
16- 0 . ** 先读 ` testpilot/CHANGELOG.md ` (如果存在) ** — 了解当前已覆盖的功能和尚未测试的模块,避免重复写或漏写;如果不存在则跳过
17- 1 . ** 读主窗口/入口文件 ** — 了解应用结构(如 ` MainWindow.xaml ` 、 ` main.py ` 、 ` app.py ` )
18- 2 . ** 读每个窗口的 UI 文件 ** — 找出所有控件,记录真实的 ` Name ` 、 ` AutomationId ` 、 ` Content ` 属性
19- 3 . ** 记录元素的真实标识 ** — ` automationid:xxx ` 或 ` name:控件显示文字 ` (选择器的唯一来源)
20- 4 . ** 读事件处理逻辑 ** — 确认每个按钮点击的真实结果(弹出什么窗口、显示什么文字)
21- 5 . ** 确认提示方式 ** — 成功/失败提示是 ` MessageBox ` (阻塞弹窗,需 click 关闭)还是标签文字(可断言)
22- 6 . ** 列出已实现功能 ** — 代码里有什么就测什么,未实现的功能不写蓝本
16+ 0 . ** �粉 ` testpilot/CHANGELOG.md ` 嚗����剁� ** �?鈭圾敶�撌脰�������芣�霂�璅∪�嚗��憭�����憒�銝��典�頝唾�
17+ 1 . ** 霂颱蜓蝒/�亙�辣 ** �?鈭圾摨蝏�嚗� ` MainWindow.xaml ` � main.py` � app.py` 嚗?
18+ 2 . ** 霂餅�銝芰���� UI �辣 ** �?�曉��隞塚�霈啣����? ` Name ` � AutomationId` � Content` 撅?
19+ 3 . ** 霈啣�����摰�霂? * �? ` automationid:xxx ` �? ` name:�找辣�曄內�� ` 嚗�函��臭��交�嚗?
20+ 4 . ** 霂颱�隞嗅��餉� ** �?蝖株恕瘥葵��孵��摰���撘孵隞銋���蝷箔�銋�摮�
21+ 5 . ** 蝖株恕�內�孵� ** �?��/憭梯揖�內�? ` MessageBox ` 嚗憛撕蝒�� click �喲嚗��舀�蝑暹�摮��舀閮嚗?
22+ 6 . ** �撌脣��啣��? * �?隞����隞銋停瘚�銋��芸��啁��銝��
2323
24- ** 禁止跳过代码阅读直接生成蓝本。凭想象写的选择器和断言几乎必然失败。 * *
24+ ** 蝳迫頝唾�隞���粉�湔�����唾情����典��剛���敹憭梯揖�? *
2525
2626---
2727
28- ## 一、必填字段
28+ ## 銝��憛怠�畾?
2929
3030| 摮挾 | 霂湔� | 蝷箔� |
3131| ------| ------| ------|
3232| ` platform ` | �箏� ` "desktop" ` | ` "desktop" ` |
33- | ` window_title ` | 主窗口标题(精确匹配) | ` "财务管理系统 " ` |
33+ | ` window_title ` | 銝餌����憸�蝎曄&�寥�嚗? | ` "韐W蝞∠�蝟餌� " ` |
3434| ` base_url ` | ** �征** ` "" ` | ` "" ` |
3535| ` app_name ` | 摨�妍 | ` "韐W蝞∠�蝟餌�" ` |
36- | ` description ` | 50-200字功能描述 | |
36+ | ` description ` | 50-200摮��賣�餈? | |
3737| ` start_command ` | �臬�賭誘嚗�� | ` "MyApp.exe" ` |
3838| ` start_cwd ` | �臬�桀�嚗�� | ` "./dist" ` |
3939
4040### �蝳迫
4141
42- - ❌ ` base_url ` 填了 HTTP URL → 桌面应用不是 Web,留空
43- - ❌ 填了 ` app_package ` / ` bundle_id ` (移动端字段)
44- - ❌ ` window_title ` 填错(必须与应用标题栏完全一致)
42+ - �? ` base_url ` 憛思� HTTP URL �?獢摨銝 Web嚗�蝛?
43+ - �?憛思� ` app_package ` / ` bundle_id ` 嚗宏�函垢摮挾嚗?
44+ - �? ` window_title ` 憛恍�嚗�憿颱�摨�����其��湛�
4545
4646---
4747
4848## 鈭��剖��其�銵剁��芸�霈訾誑銝雿�
4949
5050| �其� | 敹‵� | 霂湔� |
5151| ------| ---------| ------|
52- | ` navigate ` | ` value ` (窗口标题或命令) , ` description ` | 启动/重启应用 |
52+ | ` navigate ` | ` value ` (蝒���隞? , ` description ` | �臬/�摨 |
5353| ` click ` | ` target ` , ` description ` | �孵�� |
5454| ` fill ` | ` target ` , ` value ` , ` description ` | 颲� |
55- | ` wait ` | ` description ` | 等待( ` value ` 指定毫秒) |
56- | ` assert_text ` | ` expected ` , ` description ` | 断言窗口内包含文本 |
55+ | ` wait ` | ` description ` | 蝑�嚗 value` ��瘥怎�嚗? |
56+ | ` assert_text ` | ` expected ` , ` description ` | �剛�蝒���急��? |
5757| ` screenshot ` | ` description ` | �芸�� |
5858
59- ### 绝对禁止的动作
59+ ### 蝏笆蝳迫�雿?
6060
61- - ❌ ` select ` 、 ` navigate_to ` 、 ` evaluate ` 、 ` call_method ` (非桌面动作)
62- - ❌ ` reset_state ` 、 ` page_query ` 、 ` scroll ` (非桌面动作)
61+ - �? ` select ` � navigate_to` � evaluate` � call_method`嚗�獢�其�嚗?
62+ - �? ` reset_state ` � page_query` � scroll` 嚗�獢�其�嚗?
6363
6464---
6565
66- ## 三、选择器规则
66+ ## 銝�刻��?
6767
68- ### 桌面应用选择器格式
68+ ### 獢摨��冽撘?
6969
70- 桌面应用元素通过 ** 屏幕上可见的原文 ** 定位:
70+ 獢摨���� ** 撅�銝閫��� ** 摰�嚗?
7171
7272```
7373name:撅�銝閫���
7474```
7575
76- | 界面元素 | 蓝本选择器 |
76+ ### � ��其�甇仿�霂�撘箏�扯�嚗�銝?target �賢�憿餃�嚗?
77+
78+ �遙雿�銝?` target ` ��其���敹◆摰�隞乩�銝郊嚗?* 蝻箔�銝** 嚗?
79+
80+ 1 . ** 摰�皞�** 嚗�啗砲�找辣��函� ` .xaml ` / ` .py ` / ` .js ` �辣嚗�雿�瑚�銵?
81+ 2 . ** 憭��** 嚗�隞��銝剖��嗆隞嗥� ` Content ` �Header` �Text ` 蝑��批潘�** 蝳迫�剛扇敹���** 嚗�憒�隞��銝剜� ` AutomationId ` 嚗�� ` automationid:xxx `
82+ 3 . ** 撖寧�** 嚗&霈文��嗥���銝��函��V�摰��曄內��摮��其��湛��蝛箸���嫘之撠�嚗?
83+
84+ ** 銝�銝郊撉�撠勗���?= 敹�粹����舫�典仃韐亦�蝚砌�憭批��?*
85+
86+ | ��� | ���?|
7787| ---------| -----------|
7888| ��� "Login" | ` name:Login ` |
7989| ��� "蝖桀�" | ` name:蝖桀� ` |
80- | 输入框旁标签 "用户名" | ` name:用户名 ` |
81- | 菜单项 "文件 " | ` name:文件 ` |
82- | 标签页 "设置 " | ` name:设置 ` |
90+ | 颲獢��倌 "�冽�? | `name:�冽� |
91+ | ��憿?"�辣 " | ` name:�辣 ` |
92+ | �倌憿?"霈曄蔭 " | ` name:霈曄蔭 ` |
8393
84- ### ⚠️ 绝对禁止的写法
94+ ### �� 蝏笆蝳迫��瘜?
8595
86- - ❌ ` name:Login按钮 ` (禁止在原文后加中文后缀)
87- - ❌ ` name:确定按钮 ` (屏幕上只显示"确定",不是"确定按钮")
88- - ❌ ` name:用户名输入框 ` (屏幕上只显示"用户名",不是"用户名输入框")
89- - ❌ ` #id ` 、 ` .class ` (Web CSS 选择器,桌面不支持)
90- - ❌ ` accessibility_id:xxx ` (移动端选择器,桌面不支持)
96+ - �? ` name:Login� ` 嚗�甇W����銝剜���嚗?
97+ - �? ` name:蝖桀�� ` 嚗�撟��芣蝷?蝖桀�"嚗��?蝖桀��"嚗?
98+ - �? ` name:�冽���交� ` 嚗�撟��芣蝷?�冽�?嚗��?�冽���交�"嚗?
99+ - �? ` #id ` � .class`嚗eb CSS ��剁�獢銝��
100+ - �? ` accessibility_id:xxx ` 嚗宏�函垢��剁�獢銝��
91101
92- ** 核心原则: ` name: ` 后面跟的必须是屏幕上肉眼可见的原文,不多不少。 * *
102+ ** �詨���嚗 name:` �頝�敹◆�臬�撟���航�����銝�銝��? *
93103
94104---
95105
96- ## 四、瞬态 UI 不可断言清单
106+ ## ��? UI 銝�剛�皜�
97107
98108| 蝏辣 | 霂湔� |
99109| ------| ------|
100- | 系统托盘通知 | 气泡提示,短暂显示 |
110+ | 蝟餌���� | 瘞部�內嚗�蝷? |
101111| Splash Screen | �臬�駁嚗�蝘�瘨仃 |
102- | 状态栏瞬态提示 | 短暂显示后恢复原文 |
112+ | �嗆��祆�蝷? | �剜��曄內�憭��? |
103113| ToolTip | 曌��砍��內嚗宏撘瘨仃 |
104114
105- ### 代码稽核—持久性验证
115+ ### 隞��蝔賣��銋折�霂?
106116
107117```
108- ✅ 可以断言:
109- - 窗口标题栏文字
110- - 按钮/标签持久显示的文字
118+ �?�臭誑�剛�嚗?
119+ - 蝒����摮?
120+ - �/�倌���曄內��摮?
111121 - �”憿嫘”�澆����
112- - 状态栏持久化文字
122+ - �嗆�����摮?
113123
114- ❌ 不能断言:
124+ �?銝�剛�嚗?
115125 - 瘞部�
116126 - �臬�駁
117- - 工具提示(ToolTip)
127+ - 撌亙�內嚗oolTip嚗?
118128```
119129
120130---
121131
122- ## 五、等待时间计算公式
132+ ## 鈭�敺�渲恣蝞撘?
123133
124134```
125- wait 时间 = 操作耗时 + 1500ms(预留窗口刷新 + UI Automation 响应)
135+ wait �園 = ��� + 1500ms嚗������? + UI Automation ��嚗?
126136```
127137
128138| �箸 | wait �園 |
129139| ------| ----------|
130- | 应用冷启动 | wait 3000-5000(视应用大小) |
131- | 弹出子窗口/对话框 | wait 1500 |
140+ | 摨�瑕�? | wait 3000-5000嚗�摨憭批�嚗? |
141+ | 撘孵摮��?撖寡�獢? | wait 1500 |
132142| �辣霂餃��� | wait 2000 |
133143| 蝵�霂瑟� | API�園 + 1500 |
134- | 纯 UI 控件操作 | wait 1000 |
144+ | 蝥? UI �找辣�� | wait 1000 |
135145
136146---
137147
138- ## 六、场景自包含原则与连续流模式(flow 强制决策)
148+ ## �准�航���銝�蝏剜�璅∪�嚗low 撘箏�喟�嚗?
139149
140- ### ⚠️ 生成蓝本时必须对每个 page 做 flow 决策
150+ ### �� ����嗅�憿餃笆瘥葵 page �? flow �喟�
141151
142- ** 判断规则(按顺序检查): * *
143- 1 . 该 page 下有 ≥2 个场景,且都需要先登录才能操作?→ ** 必须 ` "flow": true ` **
144- 2 . 该 page 下有 ≥2 个场景是连续菜单操作或多标签页切换?→ ** 必须 ` "flow": true ` **
145- 3 . 该 page 下场景需要互相独立的干净状态(如正确登录 vs 错误登录)?→ 不写 flow(默认 false)
152+ ** �斗閫�嚗�憿箏�璉�伐�嚗? *
153+ 1 . 霂? page 銝� �? 銝芸�荔�銝�閬��餃����嚗� ** 敹◆ ` "flow": true ` **
154+ 2 . 霂? page 銝� �? 銝芸�舀餈賒�������倌憿萄��g��? ** 敹◆ ` "flow": true ` **
155+ 3 . 霂? page 銝�舫�閬��貊蝡�撟脣��嗆�憒迤蝖桃敶? vs �秤�餃�嚗��?銝� flow嚗�霈?false嚗?
146156
147- ** 简单总结:如果多个场景都要先登录再操作同一个窗口,那这个 page 必须设 ` "flow": true ` 。不加 flow 导致每个场景都重启应用+重复登录 = 严重浪费。 * *
157+ ** 蝞�餌�嚗���銝芸�舫閬��餃���雿�銝銝芰�������銝? page 敹◆霈? ` "flow": true ` ���? flow 撖潸瘥葵�箸�賡��臬��?���餃� = 銝仿�瘚芾晶�? *
148158
149- ### 默认模式( ` flow: false ` )
159+ ### 暺恕璅∪�嚗 flow: false`嚗?
150160
151161- 撘��冽�銝芸�舫�航�摨
152- - 每个场景的第一步应是 ` navigate ` (启动应用) + ` wait ` (等启动完成)
153- - ** 禁止 ** 场景间传递状态
154- - 如果场景需要特定前置状态(如已登录),必须在该场景内重新执行操作
162+ - 瘥葵�箸�洵銝甇亙��? ` navigate ` 嚗�典��剁� + ` wait ` 嚗��臬摰�嚗?
163+ - ** 蝳迫 ** �箸�港���?
164+ - 憒��箸�閬摰�蝵桃��憒歇�餃�嚗�敹◆�刻砲�箸���唳銵�雿?
155165
156- ### 连续流模式( ` flow: true ` )
166+ ### 餈賒瘚芋撘� ` flow: true ` 嚗?
157167
158- 在 ` page ` 级别设置 ` "flow": true ` ,同一页面内的场景将连续执行:
159- - 仅第1个场景执行 navigate 启动应用,后续场景的 navigate ** 自动跳过 **
160- - 场景间保持窗口状态
161- - 连续3个场景失败 → 尝试重启恢复后继续
162- - 每个场景仍需写 navigate(方便单独运行)
168+ �? ` page ` 蝥批霈曄蔭 ` "flow": true ` 嚗�銝憿菟���箸撠�蝏剜銵�
169+ - 隞洵1銝芸�舀銵? navigate �臬摨嚗�蝏剖�舐� navigate ** �芸頝唾� **
170+ - �箸�港������?
171+ - 餈賒3銝芸�臬仃韐?�?撠���W��誧蝏?
172+ - 瘥葵�箸隞��?navigate嚗靘踹��祈�銵�
163173
164- ** 重要: ** flow 场景仍需写 navigate(方便单独运行),引擎在 flow 模式下自动跳过。
174+ ** ��嚗? * flow �箸隞��?navigate嚗靘踹��祈�銵�嚗�� flow 璅∪�銝�刻歲餈?
165175
166176### � flow ���箸��嚗��園�閬�敹◆�萄�嚗�
167177
168- ** flow 模式下,第2个及之后的场景只写 navigate + 该场景自己的操作步骤,绝对禁止重复写登录步骤! * *
178+ ** flow 璅∪�銝�蝚?銝芸�銋���臬�? navigate + 霂亙�航撌梁���甇仿炊嚗�撖寧�甇a�憭��餃�甇仿炊嚗? *
169179
170- 引擎会跳过非首场景的 navigate,直接从第2步开始执行。如果第2步是 ` fill 用户名 ` ,但页面此时已经登录在主界面上 → 找不到输入框 → 超时失败 → 连续3步失败 → 整个场景被熔断跳过 → 后续场景全部同样失败。
180+ 撘�隡歲餈�擐�舐� navigate嚗�乩�蝚?甇亙�憪銵��洵2甇交 `fill �冽�嚗�憿菟甇斗撌脩��餃��其蜓�銝?�?�曆��啗��交� �?頞憭梯揖 �?餈賒3甇亙仃韐?�?�港葵�箸鋡怎��剛歲餈?�?�賒�箸�券�憭梯揖�?
171181
172- | ❌ 错误写法(非首场景重复登录) | ✅ 正确写法(非首场景直接操作) |
182+ | �?�秤��嚗�擐�舫�憭敶� | �?甇�&��嚗�擐�舐�交�雿� |
173183| ---| ---|
174- | 场景2 : navigate → wait → fill用户名 → fill密码 → click登录 → wait → 实际操作 | 场景2 : navigate → 实际操作 → assert_text |
175- | 场景3 : navigate → wait → fill用户名 → fill密码 → click登录 → wait → 实际操作 | 场景3 : navigate → 实际操作 → assert_text |
184+ | �箸2 : navigate �? wait �?fill�冽�?�?fill撖� �?click�餃� �? wait �?摰��� | �箸2 : navigate �?摰��� �? assert_text |
185+ | �箸3 : navigate �? wait �?fill�冽�?�?fill撖� �?click�餃� �? wait �?摰��� | �箸3 : navigate �?摰��� �? assert_text |
176186
177- ** 核心原则:flow 模式下,只有第1个场景做完整的启动+登录流程,后续场景的 navigate 后面直接写该场景自己的操作。 * *
187+ ** �詨���嚗low 璅∪�銝��芣�蝚?銝芸�臬�摰��?�餃�瘚�嚗�蝏剖�舐� navigate ��湔�砲�箸�芸楛��雿? *
178188
179189---
180190
181- ## 七、完整 JSON 模板
191+ ## 銝��? JSON 璅⊥
182192
183193``` json
184194{
185- "app_name" : " 你的应用名 " ,
186- "description" : " 50-200字功能描述 " ,
195+ "app_name" : "雿�摨�? ,
196+ "description" : "50-200摮��賣�餈? ,
187197 "base_url" : " " ,
188198 "platform" : " desktop" ,
189199 "window_title" : " 摨蝒��" ,
@@ -192,19 +202,19 @@ wait 时间 = 操作耗时 + 1500ms(预留窗口刷新 + UI Automation 响应
192202 "pages" : [
193203 {
194204 "url" : " " ,
195- "name" : " 主窗口 " ,
205+ "name" : "銝餌��? ,
196206 "scenarios" : [
197207 {
198208 "name" : " 甇�&�餃�" ,
199209 "steps" : [
200210 {"action" : " navigate" , "value" : " 摨蝒��" , "description" : " �臬摨" },
201211 {"action" : " wait" , "value" : " 3000" , "description" : " 蝑�摨蝒摰�蝸" },
202- {"action" : " fill" , "target" : " name:用户名 " , "value" : " admin" , "description" : " 在用户名输入框输入admin " },
212+ {"action" : " fill" , "target" : " name:�冽�? , " value": "admin", "description": "�函�瑕�颲獢��仟dmin " },
203213 {"action" : " fill" , "target" : " name:撖�" , "value" : " admin123" , "description" : " �典����交�颲admin123" },
204- {"action" : " click" , "target" : " name:登录 " , "description" : " 点击登录按钮,验证账号后进入主界面 " },
205- {"action" : " wait" , "value" : " 2000" , "description" : " 等待登录验证和界面切换 " },
206- {"action" : " assert_text" , "expected" : " 欢迎 " , "description" : " 验证主界面显示欢迎信息 " },
207- {"action" : " screenshot" , "description" : " 登录成功后的主界面 " }
214+ {"action" : " click" , "target" : " name:�餃� " , "description" : "�孵�餃��嚗�霂揭�瑕�餈銝餌��? },
215+ {"action" : " wait" , "value" : " 2000" , "description" : "蝑��餃�撉����W��? },
216+ {"action" : " assert_text" , "expected" : " 甈Z� " , "description" : "撉�銝餌��X蝷箸洽餈縑�? },
217+ {"action" : " screenshot" , "description" : "�餃�����銝餌��? }
208218 ]
209219 }
210220 ]
@@ -215,24 +225,24 @@ wait 时间 = 操作耗时 + 1500ms(预留窗口刷新 + UI Automation 响应
215225
216226---
217227
218- ## 八、代码稽核清单
228+ ## �怒誨�里�豢��?
219229
220- - [ ] 查看应用界面,确认 ` name: ` 后的文字与屏幕显示完全一致
221- - [ ] ` name: ` 后没有添加"按钮"/"输入框"等中文后缀
230+ - [ ] �亦�摨�嚗&霈? ` name: ` ����銝�撟蝷箏��其��?
231+ - [ ] ` name: ` �瓷�溶�?�"/"颲獢?蝑葉��蝻
222232- [ ] ` window_title ` 銝��冽�憸�摰�寥�
223- - [ ] ` base_url ` 为空字符串 ` "" `
233+ - [ ] ` base_url ` 銝箇征摮泵銝? ` "" `
224234- [ ] ` expected ` ���函��V����曄內
225- - [ ] 启动后有足够的 wait 时间
235+ - [ ] �臬��頞喳��? wait �園
226236
227237---
228238
229- ## 九、踩坑清单
239+ ## 銋萱���?
230240
231241| �秤 | �� | 甇�&�� |
232242| ------| ------| ---------|
233- | ` name:登录按钮 ` | 找不到(屏幕只显示"登录") | ` name:登录 ` |
234- | ` name:用户名输入框 ` | 找不到 | ` name:用户名 ` |
235- | 用 CSS 选择器 ` #id ` | 桌面不支持 | 用 ` name:原文 ` |
236- | 用 ` accessibility_id: ` | 桌面不支持 | 用 ` name:原文 ` |
237- | 应用启动后没 wait | 窗口未就绪 | wait 3000-5000 |
238- | ` window_title ` 拼错 | 引擎找不到窗口 | 与标题栏完全一致 |
243+ | ` name:�餃�� ` | �曆��堆�撅��芣蝷?�餃�"嚗? | ` name:�餃� ` |
244+ | ` name:�冽���交� ` | �曆��? | `name:�冽� |
245+ | �? CSS ��? ` #id ` | 獢銝�? | �? ` name:�� ` |
246+ | �? ` accessibility_id: ` | 獢銝�? | �? ` name:�� ` |
247+ | 摨�臬�瓷 wait | 蝒�芸停蝏? | wait 3000-5000 |
248+ | ` window_title ` �潮� | 撘��曆��啁��? | 銝�憸�摰銝�? |
0 commit comments