appium-session-recorder 0.0.1

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 (73) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +362 -0
  3. package/bun.lock +731 -0
  4. package/package.json +62 -0
  5. package/skills/appium-cli-selector-navigator/SKILL.md +349 -0
  6. package/src/cli/arg-parser.ts +311 -0
  7. package/src/cli/commands/drive.ts +147 -0
  8. package/src/cli/commands/index.ts +54 -0
  9. package/src/cli/commands/proxy.ts +41 -0
  10. package/src/cli/commands/screen.ts +73 -0
  11. package/src/cli/commands/selectors.ts +42 -0
  12. package/src/cli/commands/session.ts +64 -0
  13. package/src/cli/commands/types.ts +11 -0
  14. package/src/cli/index.ts +158 -0
  15. package/src/cli/prompts.ts +64 -0
  16. package/src/cli/response.ts +44 -0
  17. package/src/core/appium/client.ts +248 -0
  18. package/src/core/index.ts +5 -0
  19. package/src/core/selectors/generate-candidates.ts +155 -0
  20. package/src/core/selectors/score-candidates.ts +184 -0
  21. package/src/core/types.ts +79 -0
  22. package/src/core/xml/parse-source.ts +197 -0
  23. package/src/index.ts +7 -0
  24. package/src/server/appium-client.ts +24 -0
  25. package/src/server/index.ts +6 -0
  26. package/src/server/interaction-recorder.ts +74 -0
  27. package/src/server/proxy-middleware.ts +68 -0
  28. package/src/server/routes.ts +53 -0
  29. package/src/server/server.ts +43 -0
  30. package/src/server/types.ts +34 -0
  31. package/src/ui/bun.lock +311 -0
  32. package/src/ui/index.html +16 -0
  33. package/src/ui/package.json +20 -0
  34. package/src/ui/src/App.css +12 -0
  35. package/src/ui/src/App.tsx +41 -0
  36. package/src/ui/src/components/ActionCarousel.css +128 -0
  37. package/src/ui/src/components/ActionCarousel.tsx +92 -0
  38. package/src/ui/src/components/Inspector.css +314 -0
  39. package/src/ui/src/components/Inspector.tsx +265 -0
  40. package/src/ui/src/components/InteractionCard.css +159 -0
  41. package/src/ui/src/components/InteractionCard.tsx +60 -0
  42. package/src/ui/src/components/MainInspector.css +304 -0
  43. package/src/ui/src/components/MainInspector.tsx +304 -0
  44. package/src/ui/src/components/Stats.css +27 -0
  45. package/src/ui/src/components/Timeline.css +31 -0
  46. package/src/ui/src/components/Timeline.tsx +37 -0
  47. package/src/ui/src/hooks/useInteractions.ts +73 -0
  48. package/src/ui/src/index.tsx +11 -0
  49. package/src/ui/src/services/api.ts +41 -0
  50. package/src/ui/src/styles/tokens.css +126 -0
  51. package/src/ui/src/types.ts +34 -0
  52. package/src/ui/src/utils/__tests__/locators.test.ts +304 -0
  53. package/src/ui/src/utils/__tests__/xml-parser.test.ts +326 -0
  54. package/src/ui/src/utils/locators.ts +14 -0
  55. package/src/ui/src/utils/xml-parser.ts +45 -0
  56. package/src/ui/tsconfig.json +34 -0
  57. package/src/ui/tsconfig.node.json +11 -0
  58. package/src/ui/vite.config.ts +22 -0
  59. package/tests/cli/arg-parser.test.ts +397 -0
  60. package/tests/cli/drive-commands.test.ts +151 -0
  61. package/tests/cli/selectors-best.test.ts +42 -0
  62. package/tests/cli/session-commands.test.ts +53 -0
  63. package/tests/core/selector-candidates.test.ts +83 -0
  64. package/tests/core/selector-scoring.test.ts +75 -0
  65. package/tests/core/xml-parser.test.ts +56 -0
  66. package/tests/server/appium-client.test.ts +229 -0
  67. package/tests/server/interaction-recorder.test.ts +377 -0
  68. package/tests/server/proxy-middleware.test.ts +343 -0
  69. package/tests/server/routes.test.ts +305 -0
  70. package/tsconfig.json +26 -0
  71. package/vitest.config.ts +16 -0
  72. package/vitest.ui.config.ts +15 -0
  73. package/workflow.gif +0 -0
package/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 JustasM
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/README.md ADDED
@@ -0,0 +1,362 @@
1
+ # Appium Session Recorder
2
+
3
+ A modern Appium recorder and automation CLI with real-time UI visualization, session navigation commands, and selector ranking. Built with Bun, Solid.js, and Kobalte.
4
+
5
+ ![Workflow Demo](workflow.gif)
6
+
7
+ ## ✨ Features
8
+
9
+ - 🎬 **Session Recording**: Intercepts and logs Appium commands (currently focused on `POST /session/:sessionId/*`)
10
+ - 📸 **Screenshot Capture**: Automatically captures screenshots after actions
11
+ - 🤖 **JSON-First Command Mode**: Scriptable subcommands for agent workflows (`session`, `screen`, `selectors`, `drive`)
12
+ - 🧭 **CLI App Navigation**: Drive taps, typing, back navigation, and swipe gestures via Appium
13
+ - 🏆 **Best Selector Ranking**: Heuristic ranking with strategy scoring + match counts + reason codes
14
+ - 🔍 **Element Inspector**: Interactive element inspection with multiple locator strategies
15
+ - 🎯 **Query Tester**: Test locators in real-time on captured screenshots
16
+ - 📊 **Real-time Updates**: Live dashboard with Server-Sent Events
17
+ - 🎨 **Modern UI**: Beautiful dark theme with vibrant accents using Solid.js + Kobalte
18
+ - ⚡ **Fast**: Built with Bun for optimal performance
19
+ - 🛠️ **Interactive CLI**: Beautiful prompts for easy configuration
20
+
21
+ ## 🚀 Quick Start
22
+
23
+ ### Prerequisites
24
+
25
+ - [Bun](https://bun.sh/) runtime installed
26
+ - [Appium](https://appium.io/) server installed
27
+
28
+ ### Start Appium Server
29
+
30
+ Start the Appium server (CORS is only needed if you plan to call Appium directly from a browser):
31
+
32
+ ```bash
33
+ appium --port 4723 --allow-cors
34
+ ```
35
+
36
+ The recorder proxy itself does not require `--allow-cors` for normal usage.
37
+
38
+ ### Installation
39
+
40
+ ```bash
41
+ cd appium-session-recorder # (or your cloned folder name)
42
+ bun install
43
+ ```
44
+
45
+ ### Run the CLI
46
+
47
+ ```bash
48
+ bun run cli
49
+ ```
50
+
51
+ The CLI will interactively prompt you for:
52
+ - **Proxy port** (default: 4724)
53
+ - **Proxy host** (default: 127.0.0.1)
54
+ - **Appium server URL** (default: http://127.0.0.1:4723)
55
+
56
+ Alternatively, use command-line arguments:
57
+
58
+ ```bash
59
+ bun run cli --port 8080 --appium-url http://192.168.1.100:4723
60
+ ```
61
+
62
+ Or run command mode (JSON output by default):
63
+
64
+ ```bash
65
+ bun run cli session create --appium-url http://127.0.0.1:4723 --caps-file ./caps.json --pretty
66
+ ```
67
+
68
+ ### Configure Appium Inspector
69
+
70
+ Point Appium Inspector to the recorder proxy:
71
+
72
+ | Setting | Value |
73
+ |---------|-------|
74
+ | Remote Host | `127.0.0.1` |
75
+ | Remote Port | `4724` (or your configured port) |
76
+ | Remote Path | `/` |
77
+
78
+ ### Access the UI
79
+
80
+ Open your browser to:
81
+ ```
82
+ http://localhost:4724/_recorder
83
+ ```
84
+
85
+ ## 📖 Usage
86
+
87
+ ## Security (Local-Only Tool)
88
+
89
+ This project is intended for **local testing and development**. It runs an unauthenticated proxy/UI that can forward commands to Appium. For normal usage, keep it bound to localhost and do not expose it to untrusted networks.
90
+
91
+ **Current known gaps (will be addressed in future updates):**
92
+ - Missing validation for `sessionId`
93
+ - Missing validation for `appiumUrl`
94
+ - Rate limiting for API endpoints
95
+ - Authentication/authorization (likely optional, since local-by-default is intentional)
96
+
97
+ **Practical guidance:**
98
+ - Run the recorder on `127.0.0.1` only (default) and avoid port-forwarding/sharing the port.
99
+ - Be cautious with `appium --allow-cors`; treat the recorder + Appium as a local dev surface while running.
100
+ - Page source is untrusted input; XML is rendered as text (not HTML) to mitigate XSS.
101
+
102
+ ### Command Mode (JSON)
103
+
104
+ ```bash
105
+ bun run cli <group> <command> [flags]
106
+ ```
107
+
108
+ Available command groups:
109
+
110
+ - `proxy start`
111
+ - `session create|delete`
112
+ - `screen snapshot|elements`
113
+ - `selectors best`
114
+ - `drive tap|type|back|swipe`
115
+
116
+ Global command flags:
117
+
118
+ - `--pretty` pretty-print JSON
119
+ - `--output <path>` persist JSON output to a file
120
+ - Legacy mode (`bun run cli [legacy-options]`) does not accept `--pretty` or `--output`
121
+
122
+ ### Agent Skill
123
+
124
+ This repo includes a reusable Codex skill at:
125
+
126
+ - `skills/appium-cli-selector-navigator/SKILL.md`
127
+
128
+ The skill is designed for CLI-only navigation + selector discovery loops.
129
+
130
+ ### Skill Runbook (What To Run)
131
+
132
+ Use this when you want to drive the app and find selectors with `$appium-cli-selector-navigator`.
133
+
134
+ 1. Start Appium:
135
+
136
+ ```bash
137
+ appium --port 4723 --allow-cors
138
+ ```
139
+
140
+ 2. (Optional) Install skill globally for Codex:
141
+
142
+ ```bash
143
+ mkdir -p ~/.codex/skills
144
+ cp -R ./skills/appium-cli-selector-navigator ~/.codex/skills/appium-cli-selector-navigator
145
+ ```
146
+
147
+ ```bash
148
+ mkdir -p ~/.claude/skills
149
+ cp -R ./skills/appium-cli-selector-navigator ~/.claude/skills/appium-cli-selector-navigator
150
+ ```
151
+
152
+ Restart Codex after installing the global skill.
153
+
154
+ 3. Create a capabilities file (example iOS Safari):
155
+
156
+ ```bash
157
+ cat > /tmp/caps.json <<'JSON'
158
+ {
159
+ "platformName": "iOS",
160
+ "appium:deviceName": "iPhone 17",
161
+ "appium:platformVersion": "26.2",
162
+ "appium:automationName": "XCUITest",
163
+ "appium:bundleId": "com.apple.mobilesafari",
164
+ "appium:newCommandTimeout": 3600,
165
+ "appium:connectHardwareKeyboard": true,
166
+ "appium:includeSafariInWebviews": true
167
+ }
168
+ JSON
169
+ ```
170
+
171
+ 4. Create session and capture `SESSION_ID`:
172
+
173
+ ```bash
174
+ appium-recorder session create \
175
+ --appium-url http://127.0.0.1:4723 \
176
+ --caps-file /tmp/caps.json \
177
+ --output /tmp/session.json \
178
+ --pretty \
179
+ && SESSION_ID="$(jq -r '.result.sessionId' /tmp/session.json)" \
180
+ && echo "$SESSION_ID"
181
+ ```
182
+
183
+ 5. Fetch current elements and save JSON:
184
+
185
+ ```bash
186
+ appium-recorder screen elements \
187
+ --appium-url http://127.0.0.1:4723 \
188
+ --session-id "$SESSION_ID" \
189
+ --only-actionable \
190
+ --limit 80 \
191
+ --output /tmp/elements.json \
192
+ --pretty \
193
+ && jq -r '.result.elements[] | [.elementRef, .type, .name, .label, .resourceId] | @tsv' /tmp/elements.json
194
+ ```
195
+
196
+ 6. Pick element and get best selectors:
197
+
198
+ ```bash
199
+ appium-recorder selectors best \
200
+ --appium-url http://127.0.0.1:4723 \
201
+ --session-id "$SESSION_ID" \
202
+ --element-ref "<ELEMENT_REF>" \
203
+ --pretty
204
+ ```
205
+
206
+ 7. Drive actions (examples):
207
+
208
+ ```bash
209
+ # Tap an element
210
+ appium-recorder drive tap \
211
+ --appium-url http://127.0.0.1:4723 \
212
+ --session-id "$SESSION_ID" \
213
+ --using "accessibility id" --value "Accept all" --pretty
214
+
215
+ # Type into a field
216
+ appium-recorder drive type \
217
+ --appium-url http://127.0.0.1:4723 \
218
+ --session-id "$SESSION_ID" \
219
+ --using "accessibility id" --value "Address" \
220
+ --text "example.com\n" --clear-first --pretty
221
+
222
+ # Navigate back
223
+ appium-recorder drive back \
224
+ --appium-url http://127.0.0.1:4723 \
225
+ --session-id "$SESSION_ID" --pretty
226
+
227
+ # Swipe gesture
228
+ appium-recorder drive swipe \
229
+ --appium-url http://127.0.0.1:4723 \
230
+ --session-id "$SESSION_ID" \
231
+ --from 900,1800 --to 900,400 --duration-ms 350 --pretty
232
+ ```
233
+
234
+ 8. Cleanup session:
235
+
236
+ ```bash
237
+ appium-recorder session delete \
238
+ --appium-url http://127.0.0.1:4723 \
239
+ --session-id "$SESSION_ID" --pretty
240
+ ```
241
+
242
+ ### Legacy CLI Options (Backwards Compatible)
243
+
244
+ ```bash
245
+ bun run cli [options]
246
+
247
+ OPTIONS:
248
+ -p, --port <number> Proxy server port (default: 4724)
249
+ -u, --appium-url <url> Appium server URL (default: http://127.0.0.1:4723)
250
+ --host <host> Proxy server host (default: 127.0.0.1)
251
+ -h, --help Show help message
252
+ -v, --version Show version
253
+ ```
254
+
255
+ Configuration priority (highest to lowest):
256
+ 1. Command-line arguments
257
+ 2. Interactive prompts
258
+ 3. Environment variables
259
+ 4. Default values
260
+
261
+ ### Environment Variables
262
+
263
+ ```bash
264
+ APPIUM_URL=http://192.168.1.100:4723
265
+ PROXY_PORT=8080
266
+ PROXY_HOST=127.0.0.1
267
+
268
+ bun run cli
269
+ ```
270
+
271
+ ## 🎨 UI Features
272
+
273
+ ### Dashboard
274
+
275
+ - **Total Requests**: Count of all intercepted requests
276
+ - **Actions**: Requests with screenshots (clicks, inputs, etc.)
277
+ - **Real-time Updates**: Automatically refreshes as you interact
278
+
279
+ ### Timeline
280
+
281
+ - View all interactions in chronological order
282
+ - Color-coded by HTTP method (mostly `POST`)
283
+ - **Action markers** for requests with screenshots
284
+ - Click screenshots to open inspector
285
+
286
+ ### Element Inspector
287
+
288
+ - **Query Tester**: Test different locator strategies
289
+ - accessibility id
290
+ - xpath
291
+ - class name
292
+ - iOS predicate string
293
+ - iOS class chain
294
+ - **Element Details**: View element properties (name, label, value, bounds)
295
+ - **Locators**: Auto-generated locators ready to copy
296
+ - **Click to copy**: One-click locator copying
297
+
298
+ ## 🔧 Development
299
+
300
+ ### Build the UI
301
+
302
+ ```bash
303
+ cd src/ui
304
+ bun run build
305
+ ```
306
+
307
+ ### Run in Development Mode
308
+
309
+ ```bash
310
+ # Terminal 1: Build UI in watch mode
311
+ cd src/ui
312
+ bun run dev
313
+
314
+ # Terminal 2: Run CLI
315
+ bun run cli
316
+ ```
317
+
318
+ ### Build for Production
319
+
320
+ ```bash
321
+ bun run build
322
+ ```
323
+
324
+ This builds both the UI and the CLI executable.
325
+
326
+ ## 📦 What's Recorded
327
+
328
+ The recorder captures:
329
+ - Element clicks
330
+ - Text input (value)
331
+ - Element clear
332
+ - Find element/elements
333
+ - Touch actions
334
+ - Navigation (back, forward, refresh)
335
+
336
+ For each action:
337
+ - ✅ Request details (method, path, body)
338
+ - ✅ Screenshot (base64)
339
+ - ✅ Page source (XML)
340
+ - ✅ Timestamp
341
+
342
+ ## 🎯 Use Cases
343
+
344
+ - **Test Debugging**: Review session history to debug failing tests
345
+ - **Element Discovery**: Find reliable locators for automation
346
+ - **Training**: Show team members how to interact with the app
347
+ - **Test Recording**: Generate test scripts from recorded interactions
348
+
349
+ ## 🤝 Architecture
350
+
351
+ ```
352
+ ┌─────────────────────┐ ┌─────────────────────┐ ┌─────────────────────┐
353
+ │ Appium Inspector │ ──── │ Session Recorder │ ──── │ Appium Server │
354
+ │ (localhost:4724) │ │ (Bun + Express) │ │ (localhost:4723) │
355
+ └─────────────────────┘ └─────────────────────┘ └─────────────────────┘
356
+
357
+
358
+ ┌─────────────────────┐
359
+ │ Web UI (Solid.js) │
360
+ │ Real-time Updates │
361
+ └─────────────────────┘
362
+ ```