pw-automation-framework 2.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.
- package/README.md +93 -0
- package/bin/lexxit-automation-framework.js +427 -0
- package/dist/app.d.ts +2 -0
- package/dist/app.js +26 -0
- package/dist/app.js.map +1 -0
- package/dist/controllers/controller.d.ts +57 -0
- package/dist/controllers/controller.js +263 -0
- package/dist/controllers/controller.js.map +1 -0
- package/dist/core/BrowserManager.d.ts +46 -0
- package/dist/core/BrowserManager.js +377 -0
- package/dist/core/BrowserManager.js.map +1 -0
- package/dist/core/PlaywrightEngine.d.ts +16 -0
- package/dist/core/PlaywrightEngine.js +246 -0
- package/dist/core/PlaywrightEngine.js.map +1 -0
- package/dist/core/ScreenshotManager.d.ts +10 -0
- package/dist/core/ScreenshotManager.js +28 -0
- package/dist/core/ScreenshotManager.js.map +1 -0
- package/dist/core/TestData.d.ts +12 -0
- package/dist/core/TestData.js +29 -0
- package/dist/core/TestData.js.map +1 -0
- package/dist/core/TestExecutor.d.ts +16 -0
- package/dist/core/TestExecutor.js +355 -0
- package/dist/core/TestExecutor.js.map +1 -0
- package/dist/core/handlers/AllHandlers.d.ts +116 -0
- package/dist/core/handlers/AllHandlers.js +648 -0
- package/dist/core/handlers/AllHandlers.js.map +1 -0
- package/dist/core/handlers/BaseHandler.d.ts +16 -0
- package/dist/core/handlers/BaseHandler.js +27 -0
- package/dist/core/handlers/BaseHandler.js.map +1 -0
- package/dist/core/handlers/ClickHandler.d.ts +34 -0
- package/dist/core/handlers/ClickHandler.js +359 -0
- package/dist/core/handlers/ClickHandler.js.map +1 -0
- package/dist/core/handlers/CustomCodeHandler.d.ts +35 -0
- package/dist/core/handlers/CustomCodeHandler.js +102 -0
- package/dist/core/handlers/CustomCodeHandler.js.map +1 -0
- package/dist/core/handlers/DropdownHandler.d.ts +43 -0
- package/dist/core/handlers/DropdownHandler.js +304 -0
- package/dist/core/handlers/DropdownHandler.js.map +1 -0
- package/dist/core/handlers/InputHandler.d.ts +24 -0
- package/dist/core/handlers/InputHandler.js +197 -0
- package/dist/core/handlers/InputHandler.js.map +1 -0
- package/dist/core/registry/ActionRegistry.d.ts +8 -0
- package/dist/core/registry/ActionRegistry.js +35 -0
- package/dist/core/registry/ActionRegistry.js.map +1 -0
- package/dist/installer/frameworkLauncher.d.ts +31 -0
- package/dist/installer/frameworkLauncher.js +198 -0
- package/dist/installer/frameworkLauncher.js.map +1 -0
- package/dist/queue/ExecutionQueue.d.ts +52 -0
- package/dist/queue/ExecutionQueue.js +175 -0
- package/dist/queue/ExecutionQueue.js.map +1 -0
- package/dist/routes/api.routes.d.ts +2 -0
- package/dist/routes/api.routes.js +16 -0
- package/dist/routes/api.routes.js.map +1 -0
- package/dist/server.d.ts +1 -0
- package/dist/server.js +30 -0
- package/dist/server.js.map +1 -0
- package/dist/types/types.d.ts +135 -0
- package/dist/types/types.js +4 -0
- package/dist/types/types.js.map +1 -0
- package/dist/utils/elementHighlight.d.ts +35 -0
- package/dist/utils/elementHighlight.js +136 -0
- package/dist/utils/elementHighlight.js.map +1 -0
- package/dist/utils/locatorHelper.d.ts +7 -0
- package/dist/utils/locatorHelper.js +53 -0
- package/dist/utils/locatorHelper.js.map +1 -0
- package/dist/utils/logger.d.ts +12 -0
- package/dist/utils/logger.js +35 -0
- package/dist/utils/logger.js.map +1 -0
- package/dist/utils/response.d.ts +4 -0
- package/dist/utils/response.js +25 -0
- package/dist/utils/response.js.map +1 -0
- package/dist/utils/responseFormatter.d.ts +78 -0
- package/dist/utils/responseFormatter.js +123 -0
- package/dist/utils/responseFormatter.js.map +1 -0
- package/dist/utils/sseManager.d.ts +32 -0
- package/dist/utils/sseManager.js +122 -0
- package/dist/utils/sseManager.js.map +1 -0
- package/lexxit-automation-framework-2.0.0.tgz +0 -0
- package/npmignore +5 -0
- package/package.json +36 -0
- package/scripts/postinstall.js +52 -0
- package/src/app.ts +27 -0
- package/src/controllers/controller.ts +282 -0
- package/src/core/BrowserManager.ts +398 -0
- package/src/core/PlaywrightEngine.ts +371 -0
- package/src/core/ScreenshotManager.ts +25 -0
- package/src/core/TestData.ts +25 -0
- package/src/core/TestExecutor.ts +436 -0
- package/src/core/handlers/AllHandlers.ts +626 -0
- package/src/core/handlers/BaseHandler.ts +41 -0
- package/src/core/handlers/ClickHandler.ts +482 -0
- package/src/core/handlers/CustomCodeHandler.ts +123 -0
- package/src/core/handlers/DropdownHandler.ts +438 -0
- package/src/core/handlers/InputHandler.ts +192 -0
- package/src/core/registry/ActionRegistry.ts +31 -0
- package/src/installer/frameworkLauncher.ts +242 -0
- package/src/installer/install.sh +107 -0
- package/src/public/dashboard.html +540 -0
- package/src/public/queue-monitor.html +190 -0
- package/src/queue/ExecutionQueue.ts +200 -0
- package/src/routes/api.routes.ts +16 -0
- package/src/server.ts +29 -0
- package/src/types/types.ts +169 -0
- package/src/utils/elementHighlight.ts +174 -0
- package/src/utils/locatorHelper.ts +49 -0
- package/src/utils/logger.ts +40 -0
- package/src/utils/response.ts +27 -0
- package/src/utils/responseFormatter.ts +167 -0
- package/src/utils/sseManager.ts +127 -0
- package/tsconfig.json +18 -0
- package/videos/fb1b94b6-6639-4c9a-82bb-63572606f403/page@5bd5c6c8b62baa700e9810cdd64f5c49.webm +0 -0
|
@@ -0,0 +1,282 @@
|
|
|
1
|
+
import { Request, Response } from "express";
|
|
2
|
+
import { executionQueue } from "../queue/ExecutionQueue";
|
|
3
|
+
import { sseManager } from "../utils/sseManager";
|
|
4
|
+
import { formatExecutionResult, formatScriptResult } from "../utils/responseFormatter";
|
|
5
|
+
import { Logger } from "../utils/logger";
|
|
6
|
+
|
|
7
|
+
const log = Logger.create("ApiController");
|
|
8
|
+
|
|
9
|
+
export class ApiController {
|
|
10
|
+
|
|
11
|
+
/**
|
|
12
|
+
* POST /api/run-test
|
|
13
|
+
* ------------------
|
|
14
|
+
* Enqueues execution, returns 202 + executionId immediately.
|
|
15
|
+
* The caller opens the dashboard and subscribes to SSE for live updates.
|
|
16
|
+
* Call GET /api/result/:executionId when done to get the full formatted result.
|
|
17
|
+
*/
|
|
18
|
+
static async runTest(req: Request, res: Response): Promise<void> {
|
|
19
|
+
const payload = req.body;
|
|
20
|
+
if (!payload?.scripts?.length) {
|
|
21
|
+
res.status(400).json({ error: "'scripts' array is required." });
|
|
22
|
+
return;
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
// Validate that steps have step_script
|
|
26
|
+
const missingSteps: string[] = [];
|
|
27
|
+
for (const script of payload.scripts) {
|
|
28
|
+
for (const step of (script.steps || [])) {
|
|
29
|
+
if (!step.step_script || step.step_script.trim() === "") {
|
|
30
|
+
missingSteps.push(step.step_name || "unnamed step");
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
}
|
|
34
|
+
if (missingSteps.length > 0) {
|
|
35
|
+
res.status(400).json({
|
|
36
|
+
error: "Steps are missing step_script field.",
|
|
37
|
+
detail: `Steps without step_script: ${missingSteps.slice(0, 5).join(", ")}`,
|
|
38
|
+
fix: "Call prepareSteps(uid) in your main app to resolve obj_uid → step_script before sending to the framework.",
|
|
39
|
+
});
|
|
40
|
+
return;
|
|
41
|
+
}
|
|
42
|
+
|
|
43
|
+
const executionId = executionQueue.enqueue(payload);
|
|
44
|
+
const dashboardURL = `http://localhost:${process.env.PORT || 3000}/dashboard/${executionId}`;
|
|
45
|
+
const resultURL = `http://localhost:${process.env.PORT || 3000}/api/result/${executionId}`;
|
|
46
|
+
const streamURL = `http://localhost:${process.env.PORT || 3000}/api/stream/${executionId}`;
|
|
47
|
+
// const videoURL = `http://localhost:${process.env.PORT || 3000}/api/video/${executionId}`;
|
|
48
|
+
|
|
49
|
+
log.info(`Enqueued: ${executionId} | scripts=${payload.scripts.length}`);
|
|
50
|
+
|
|
51
|
+
res.status(202).json({
|
|
52
|
+
executionId,
|
|
53
|
+
dashboardURL,
|
|
54
|
+
resultURL, // Poll this for final result
|
|
55
|
+
streamURL, // Subscribe to this for live events
|
|
56
|
+
// videoURL,
|
|
57
|
+
status: "queued",
|
|
58
|
+
message: "Execution queued. Dashboard opening. Subscribe to streamURL for live updates, or poll resultURL for final result.",
|
|
59
|
+
});
|
|
60
|
+
}
|
|
61
|
+
|
|
62
|
+
/**
|
|
63
|
+
* GET /api/stream/:executionId
|
|
64
|
+
* ----------------------------
|
|
65
|
+
* SSE endpoint — dashboard subscribes here for live step events.
|
|
66
|
+
* Replays all past events immediately for late-connecting clients.
|
|
67
|
+
*/
|
|
68
|
+
static stream(req: Request, res: Response): void {
|
|
69
|
+
const { executionId } = req.params;
|
|
70
|
+
sseManager.addClient(executionId, res);
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
/**
|
|
74
|
+
* GET /api/result/:executionId
|
|
75
|
+
* ----------------------------
|
|
76
|
+
* Returns the FULL formatted result once execution is complete.
|
|
77
|
+
* Returns 202 if still running (poll until 200).
|
|
78
|
+
*
|
|
79
|
+
* Response matches the standard format:
|
|
80
|
+
* {
|
|
81
|
+
* "status": "pass|fail",
|
|
82
|
+
* "results": [{ "test_script_uid": "...", "status": "...", "results": [...] }]
|
|
83
|
+
* }
|
|
84
|
+
*/
|
|
85
|
+
static getResult(req: Request, res: Response): void {
|
|
86
|
+
const { executionId } = req.params;
|
|
87
|
+
const job = executionQueue.getJob(executionId);
|
|
88
|
+
|
|
89
|
+
if (!job) {
|
|
90
|
+
res.status(404).json({ error: `Execution ${executionId} not found` });
|
|
91
|
+
return;
|
|
92
|
+
}
|
|
93
|
+
|
|
94
|
+
if (job.status === "queued" || job.status === "running") {
|
|
95
|
+
res.status(202).json({
|
|
96
|
+
executionId,
|
|
97
|
+
status: job.status,
|
|
98
|
+
message: "Execution still in progress",
|
|
99
|
+
progress: job.progress,
|
|
100
|
+
});
|
|
101
|
+
return;
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
if (job.status === "cancelled") {
|
|
105
|
+
res.status(200).json({
|
|
106
|
+
executionId,
|
|
107
|
+
status: "cancelled",
|
|
108
|
+
message: "Execution was cancelled",
|
|
109
|
+
});
|
|
110
|
+
return;
|
|
111
|
+
}
|
|
112
|
+
|
|
113
|
+
if (!job.result) {
|
|
114
|
+
res.status(500).json({
|
|
115
|
+
executionId,
|
|
116
|
+
status: "failed",
|
|
117
|
+
error: job.error || "Execution failed with no result",
|
|
118
|
+
});
|
|
119
|
+
return;
|
|
120
|
+
}
|
|
121
|
+
|
|
122
|
+
// Return formatted result matching the standard API format
|
|
123
|
+
res.status(200).json(formatExecutionResult(job.result));
|
|
124
|
+
// console.log(formatExecutionResult(job.result));
|
|
125
|
+
}
|
|
126
|
+
|
|
127
|
+
/**
|
|
128
|
+
* GET /api/status/:executionId
|
|
129
|
+
* ----------------------------
|
|
130
|
+
* Lightweight status check (progress only, no full results).
|
|
131
|
+
*/
|
|
132
|
+
static getStatus(req: Request, res: Response): void {
|
|
133
|
+
const { executionId } = req.params;
|
|
134
|
+
const job = executionQueue.getJob(executionId);
|
|
135
|
+
|
|
136
|
+
if (!job) {
|
|
137
|
+
res.status(404).json({ error: `Execution ${executionId} not found` });
|
|
138
|
+
return;
|
|
139
|
+
}
|
|
140
|
+
|
|
141
|
+
res.json({
|
|
142
|
+
executionId: job.executionId,
|
|
143
|
+
status: job.status,
|
|
144
|
+
queuedAt: job.queuedAt,
|
|
145
|
+
startedAt: job.startedAt,
|
|
146
|
+
completedAt: job.completedAt,
|
|
147
|
+
cancelledAt: job.cancelledAt,
|
|
148
|
+
progress: job.progress,
|
|
149
|
+
cancelRequested: job.cancelRequested,
|
|
150
|
+
error: job.error,
|
|
151
|
+
});
|
|
152
|
+
}
|
|
153
|
+
|
|
154
|
+
/**
|
|
155
|
+
* DELETE /api/cancel/:executionId
|
|
156
|
+
*/
|
|
157
|
+
static cancelExecution(req: Request, res: Response): void {
|
|
158
|
+
const { executionId } = req.params;
|
|
159
|
+
const result = executionQueue.cancel(executionId);
|
|
160
|
+
res.status(result.success ? 200 : 400).json({ executionId, ...result });
|
|
161
|
+
}
|
|
162
|
+
|
|
163
|
+
/**
|
|
164
|
+
* DELETE /api/cancel-all
|
|
165
|
+
*/
|
|
166
|
+
static cancelAll(_req: Request, res: Response): void {
|
|
167
|
+
res.json(executionQueue.cancelAll());
|
|
168
|
+
}
|
|
169
|
+
|
|
170
|
+
/**
|
|
171
|
+
* GET /api/queue
|
|
172
|
+
*/
|
|
173
|
+
static getQueue(_req: Request, res: Response): void {
|
|
174
|
+
res.json(executionQueue.getQueueStats());
|
|
175
|
+
}
|
|
176
|
+
|
|
177
|
+
/**
|
|
178
|
+
* GET /api/health
|
|
179
|
+
*/
|
|
180
|
+
static health(_req: Request, res: Response): void {
|
|
181
|
+
res.json({
|
|
182
|
+
status: "ok",
|
|
183
|
+
version: "2.0.0",
|
|
184
|
+
ts: new Date().toISOString(),
|
|
185
|
+
queue: executionQueue.getQueueStats(),
|
|
186
|
+
});
|
|
187
|
+
}
|
|
188
|
+
|
|
189
|
+
/**
|
|
190
|
+
* GET /api/actions
|
|
191
|
+
*/
|
|
192
|
+
static listActions(_req: Request, res: Response): void {
|
|
193
|
+
res.json({ total: ALL_ACTIONS.length, actions: ALL_ACTIONS });
|
|
194
|
+
}
|
|
195
|
+
}
|
|
196
|
+
|
|
197
|
+
const ALL_ACTIONS = [
|
|
198
|
+
// Browser
|
|
199
|
+
{ name: "openBrowser", category: "browser", example: "tSetup.openBrowser('chrome')" },
|
|
200
|
+
{ name: "closeBrowser", category: "browser", example: "tSetup.closeBrowser()" },
|
|
201
|
+
{ name: "navigateToURL", category: "browser", example: "tSetup.navigateToURL('https://example.com')" },
|
|
202
|
+
{ name: "navigateBack", category: "browser", example: "tSetup.navigateBack()" },
|
|
203
|
+
{ name: "navigateForward", category: "browser", example: "tSetup.navigateForward()" },
|
|
204
|
+
{ name: "refreshPage", category: "browser", example: "tSetup.refreshPage()" },
|
|
205
|
+
{ name: "maximizeWindow", category: "browser", example: "tSetup.maximizeWindow()" },
|
|
206
|
+
{ name: "setWindowSize", category: "browser", example: "tSetup.setWindowSize('1920', '1080')" },
|
|
207
|
+
{ name: "switchToTab", category: "browser", example: "tSetup.switchToTab('1')" },
|
|
208
|
+
{ name: "openNewTab", category: "browser", example: "tSetup.openNewTab('https://example.com')" },
|
|
209
|
+
{ name: "closeCurrentTab", category: "browser", example: "tSetup.closeCurrentTab()" },
|
|
210
|
+
{ name: "acceptAlert", category: "browser", example: "tSetup.acceptAlert()" },
|
|
211
|
+
{ name: "dismissAlert", category: "browser", example: "tSetup.dismissAlert()" },
|
|
212
|
+
{ name: "getAlertText", category: "browser", example: "tSetup.getAlertText('storeKey')" },
|
|
213
|
+
{ name: "switchToFrame", category: "browser", example: "tSetup.switchToFrame('frameName')" },
|
|
214
|
+
{ name: "executeScript", category: "browser", example: "tSetup.executeScript('return document.title')" },
|
|
215
|
+
{ name: "scrollToBottom", category: "browser", example: "tSetup.scrollToBottom()" },
|
|
216
|
+
{ name: "scrollToTop", category: "browser", example: "tSetup.scrollToTop()" },
|
|
217
|
+
{ name: "deleteAllCookies", category: "browser", example: "tSetup.deleteAllCookies()" },
|
|
218
|
+
{ name: "clearLocalStorage", category: "browser", example: "tSetup.clearLocalStorage()" },
|
|
219
|
+
{ name: "clearSessionStorage", category: "browser", example: "tSetup.clearSessionStorage()" },
|
|
220
|
+
{ name: "takeScreenshot", category: "browser", example: "tSetup.takeScreenshot()" },
|
|
221
|
+
{ name: "getTitle", category: "browser", example: "tSetup.getTitle('storeKey')" },
|
|
222
|
+
{ name: "verifyTitle", category: "browser", example: "tSetup.verifyTitle('Expected Title')" },
|
|
223
|
+
{ name: "verifyPartialTitle", category: "browser", example: "tSetup.verifyPartialTitle('Expected')" },
|
|
224
|
+
{ name: "getCurrentURL", category: "browser", example: "tSetup.getCurrentURL()" },
|
|
225
|
+
// Input
|
|
226
|
+
{ name: "enterText", category: "input", example: "tSetup.enterText('xpath', '//input[...]', 'value')" },
|
|
227
|
+
{ name: "typeText", category: "input", example: "tSetup.typeText('xpath', '//input[...]', 'value', '50')" },
|
|
228
|
+
{ name: "clearText", category: "input", example: "tSetup.clearText('xpath', '//input[...]')" },
|
|
229
|
+
{ name: "appendText", category: "input", example: "tSetup.appendText('xpath', '//input[...]', ' extra')" },
|
|
230
|
+
{ name: "getInputValue", category: "input", example: "tSetup.getInputValue('xpath', '//input', 'storeKey')" },
|
|
231
|
+
{ name: "setInputValue", category: "input", example: "tSetup.setInputValue('xpath', '//input', 'value')" },
|
|
232
|
+
{ name: "uploadFile", category: "input", example: "tSetup.uploadFile('xpath', '//input[@type=\"file\"]', '/path/file.pdf')" },
|
|
233
|
+
// Click
|
|
234
|
+
{ name: "clickElement", category: "click", example: "tSetup.clickElement('xpath', '//button[...]')" },
|
|
235
|
+
{ name: "doubleClick", category: "click", example: "tSetup.doubleClick('xpath', '//div[...]')" },
|
|
236
|
+
{ name: "rightClick", category: "click", example: "tSetup.rightClick('xpath', '//div[...]')" },
|
|
237
|
+
{ name: "hover", category: "click", example: "tSetup.hover('xpath', '//div[...]')" },
|
|
238
|
+
{ name: "clickByJS", category: "click", example: "tSetup.clickByJS('xpath', '//button[...]')" },
|
|
239
|
+
{ name: "clickIfPresent", category: "click", example: "tSetup.clickIfPresent('xpath', '//button[...]')" },
|
|
240
|
+
{ name: "dragAndDrop", category: "click", example: "tSetup.dragAndDrop('xpath', '//src', 'xpath', '//target')" },
|
|
241
|
+
{ name: "clickByText", category: "click", example: "tSetup.clickByText('Sign In')" },
|
|
242
|
+
{ name: "clickNthElement", category: "click", example: "tSetup.clickNthElement('xpath', '//li', '2')" },
|
|
243
|
+
{ name: "scrollAndClick", category: "click", example: "tSetup.scrollAndClick('xpath', '//button[...]')" },
|
|
244
|
+
// Dropdown
|
|
245
|
+
{ name: "selectDropdown", category: "dropdown", example: "tSetup.selectDropdown('xpath', '//select', 'Option Label')" },
|
|
246
|
+
{ name: "selectByIndex", category: "dropdown", example: "tSetup.selectByIndex('xpath', '//select', '2')" },
|
|
247
|
+
{ name: "selectByValue", category: "dropdown", example: "tSetup.selectByValue('xpath', '//select', 'optValue')" },
|
|
248
|
+
{ name: "selectCustomDropdown", category: "dropdown", example: "tSetup.selectCustomDropdown('xpath', '//div.dd', 'xpath', '//li')" },
|
|
249
|
+
{ name: "selectAutocomplete", category: "dropdown", example: "tSetup.selectAutocomplete('xpath', '//input', 'New York', 'xpath', '//li')" },
|
|
250
|
+
// Assertion
|
|
251
|
+
{ name: "verifyText", category: "assertion", example: "tSetup.verifyText('xpath', '//h1', 'Welcome')" },
|
|
252
|
+
{ name: "verifyTextContains", category: "assertion", example: "tSetup.verifyTextContains('xpath', '//p', 'success')" },
|
|
253
|
+
{ name: "verifyVisible", category: "assertion", example: "tSetup.verifyVisible('xpath', '//div[...]')" },
|
|
254
|
+
{ name: "verifyHidden", category: "assertion", example: "tSetup.verifyHidden('xpath', '//div[...]')" },
|
|
255
|
+
{ name: "verifyEnabled", category: "assertion", example: "tSetup.verifyEnabled('xpath', '//button[...]')" },
|
|
256
|
+
{ name: "verifyDisabled", category: "assertion", example: "tSetup.verifyDisabled('xpath', '//button[...]')" },
|
|
257
|
+
{ name: "verifyURL", category: "assertion", example: "tSetup.verifyURL('https://example.com/dashboard')" },
|
|
258
|
+
{ name: "verifyPartialURL", category: "assertion", example: "tSetup.verifyPartialURL('dashboard')" },
|
|
259
|
+
{ name: "verifyElementCount", category: "assertion", example: "tSetup.verifyElementCount('xpath', '//li', '5')" },
|
|
260
|
+
{ name: "verifyAttribute", category: "assertion", example: "tSetup.verifyAttribute('xpath', '//input', 'placeholder', 'Email')" },
|
|
261
|
+
{ name: "getText", category: "assertion", example: "tSetup.getText('xpath', '//h1', 'storeKey')" },
|
|
262
|
+
// Wait
|
|
263
|
+
{ name: "waitForElement", category: "wait", example: "tSetup.waitForElement('xpath', '//div', '10000')" },
|
|
264
|
+
{ name: "waitForElementHidden", category: "wait", example: "tSetup.waitForElementHidden('xpath', '//div[@id=\"loader\"]', '10000')" },
|
|
265
|
+
{ name: "waitForURL", category: "wait", example: "tSetup.waitForURL('dashboard', '10000')" },
|
|
266
|
+
{ name: "waitForPageLoad", category: "wait", example: "tSetup.waitForPageLoad('10000')" },
|
|
267
|
+
{ name: "waitForNetworkIdle", category: "wait", example: "tSetup.waitForNetworkIdle('10000')" },
|
|
268
|
+
{ name: "sleep", category: "wait", example: "tSetup.sleep('2000')" },
|
|
269
|
+
// Keyboard
|
|
270
|
+
{ name: "pressKey", category: "keyboard", example: "tSetup.pressKey('Enter')" },
|
|
271
|
+
{ name: "pressKeyOn", category: "keyboard", example: "tSetup.pressKeyOn('xpath', '//input', 'Enter')" },
|
|
272
|
+
{ name: "keyCombo", category: "keyboard", example: "tSetup.keyCombo('Control+A')" },
|
|
273
|
+
// Checkbox
|
|
274
|
+
{ name: "checkCheckbox", category: "checkbox", example: "tSetup.checkCheckbox('xpath', '//input[@type=\"checkbox\"]')" },
|
|
275
|
+
{ name: "uncheckCheckbox", category: "checkbox", example: "tSetup.uncheckCheckbox('xpath', '//input[@type=\"checkbox\"]')" },
|
|
276
|
+
{ name: "selectRadio", category: "checkbox", example: "tSetup.selectRadio('xpath', '//input[@type=\"radio\"][@value=\"opt1\"]')" },
|
|
277
|
+
// Table
|
|
278
|
+
{ name: "getTableRowCount", category: "table", example: "tSetup.getTableRowCount('xpath', '//table/tbody/tr', 'rowCount')" },
|
|
279
|
+
{ name: "verifyTableCell", category: "table", example: "tSetup.verifyTableCell('xpath', '//table/tbody/tr[1]/td[2]', 'Expected')" },
|
|
280
|
+
{ name: "clickTableRow", category: "table", example: "tSetup.clickTableRow('xpath', '//table/tbody/tr', '3')" },
|
|
281
|
+
{ name: "runCustomCode", category: "customcode", example: "tSetup.runCustomCode('const result = \"LN\" + Math.floor(Math.random()*1000);', 'result', '//input[@id=\"ref\"]')" },,
|
|
282
|
+
];
|