@simplysf/simply-utam-core 0.0.0 → 0.1.0

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 (64) hide show
  1. package/LICENSE.txt +206 -0
  2. package/README.md +98 -12
  3. package/lib/discovery/index.d.ts +1 -0
  4. package/lib/discovery/index.js +17 -0
  5. package/lib/discovery/index.js.map +1 -0
  6. package/lib/discovery/project-discovery.d.ts +55 -0
  7. package/lib/discovery/project-discovery.js +180 -0
  8. package/lib/discovery/project-discovery.js.map +1 -0
  9. package/lib/index.d.ts +8 -2
  10. package/lib/index.js +8 -2
  11. package/lib/index.js.map +1 -1
  12. package/lib/namespaces/index.d.ts +1 -0
  13. package/lib/namespaces/index.js +17 -0
  14. package/lib/namespaces/index.js.map +1 -0
  15. package/lib/namespaces/namespace-rewriter.d.ts +50 -0
  16. package/lib/namespaces/namespace-rewriter.js +223 -0
  17. package/lib/namespaces/namespace-rewriter.js.map +1 -0
  18. package/lib/navigator.d.ts +133 -5
  19. package/lib/navigator.js +224 -12
  20. package/lib/navigator.js.map +1 -1
  21. package/lib/overrides/index.d.ts +1 -0
  22. package/lib/overrides/index.js +17 -0
  23. package/lib/overrides/index.js.map +1 -0
  24. package/lib/overrides/overrides-merger.d.ts +63 -0
  25. package/lib/overrides/overrides-merger.js +280 -0
  26. package/lib/overrides/overrides-merger.js.map +1 -0
  27. package/lib/rules/index.d.ts +1 -0
  28. package/lib/rules/index.js +17 -0
  29. package/lib/rules/index.js.map +1 -0
  30. package/lib/rules/rules-generator.d.ts +49 -0
  31. package/lib/rules/rules-generator.js +199 -0
  32. package/lib/rules/rules-generator.js.map +1 -0
  33. package/lib/scaffold/index.d.ts +1 -0
  34. package/lib/scaffold/index.js +17 -0
  35. package/lib/scaffold/index.js.map +1 -0
  36. package/lib/scaffold/project-scaffolder.d.ts +148 -0
  37. package/lib/scaffold/project-scaffolder.js +313 -0
  38. package/lib/scaffold/project-scaffolder.js.map +1 -0
  39. package/lib/steps/expression-matcher.d.ts +42 -0
  40. package/lib/steps/expression-matcher.js +106 -0
  41. package/lib/steps/expression-matcher.js.map +1 -0
  42. package/lib/steps/gherkin-parser.d.ts +27 -0
  43. package/lib/steps/gherkin-parser.js +98 -0
  44. package/lib/steps/gherkin-parser.js.map +1 -0
  45. package/lib/steps/index.d.ts +4 -0
  46. package/lib/steps/index.js +20 -0
  47. package/lib/steps/index.js.map +1 -0
  48. package/lib/steps/snippet-generator.d.ts +34 -0
  49. package/lib/steps/snippet-generator.js +101 -0
  50. package/lib/steps/snippet-generator.js.map +1 -0
  51. package/lib/steps/step-scaffolder.d.ts +49 -0
  52. package/lib/steps/step-scaffolder.js +225 -0
  53. package/lib/steps/step-scaffolder.js.map +1 -0
  54. package/lib/test-environment.d.ts +99 -4
  55. package/lib/test-environment.js +302 -4
  56. package/lib/test-environment.js.map +1 -1
  57. package/package.json +34 -4
  58. package/templates/generator.config.json +13 -0
  59. package/templates/hello.feature +4 -0
  60. package/templates/hello.steps.mjs +7 -0
  61. package/templates/namespace-map.json +3 -0
  62. package/templates/utam.config.json +9 -0
  63. package/templates/wdio.conf.mjs +68 -0
  64. package/templates/wireit.json +37 -0
package/lib/index.js CHANGED
@@ -20,8 +20,14 @@
20
20
  //
21
21
  // Nothing here depends on WebdriverIO or UTAM at runtime: the browser and UTAM objects are typed
22
22
  // structurally, so consumers bring whichever versions their test project already uses.
23
- export { TestEnvironment, USERNAME_ENV } from './test-environment.js';
23
+ export { TestEnvironment, USERNAME_ENV, DEFAULT_ALLOWED_HOST_PATTERNS, isHostAllowed, validateAndParseSecureUrl, getTestEnvironment, setTestEnvironment, resetTestEnvironment, } from './test-environment.js';
24
24
  export { applicationPath, lightningAppName, newRecordPath, recordPath, relatedListPath } from './lightning-paths.js';
25
- export { LightningNavigator, } from './navigator.js';
25
+ export { LightningNavigator, goToLoginUrl, goToExperiencePage, loginAsUser, loginAsExperienceUser, goToApplication, goToCreateNewRecord, goToRecord, goToRelatedList, resolveBrowser, } from './navigator.js';
26
26
  export { formatUtamHtml, getUtamHtml, logUtamHtml } from './utam-html.js';
27
+ export { findLwcDirectories, discoverComponentsInPackageDir, discoverProject, } from './discovery/index.js';
28
+ export { ROOT_TARGETS, convertLwcNameToHtml, getTargetsFromMeta, generateLwcRules, } from './rules/index.js';
29
+ export { detectIndentation, findUtamOverridesFiles, walkElements, mergeElements, applyUtamOverrides, } from './overrides/index.js';
30
+ export { findUtamJsonFiles, updateValueWithMappings, rewriteUtamNamespaces, } from './namespaces/index.js';
31
+ export { parseGherkinDocument, extractStepsFromGherkin, normalizeExpression, extractStepExpressionsFromContent, compileStepExpressions, matchStepAgainstExpressions, formatParameterNames, generateStepSnippet, formatCode, resolveGlobs, resolveDefaultTargetOutput, generateCucumberSteps, } from './steps/index.js';
32
+ export { DEFAULT_TEMPLATES_DIR, DEFAULT_REQUIRED_DEV_DEPENDENCIES, loadTemplate, generateGeneratorConfig, generateUtamConfig, generateWdioConfig, generateNamespaceMap, generateHelloFeature, generateHelloSteps, injectWireitConfiguration, checkMissingDependencies, scaffoldProject, } from './scaffold/index.js';
27
33
  //# sourceMappingURL=index.js.map
package/lib/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;GAcG;AAEH,gGAAgG;AAChG,+EAA+E;AAC/E,gGAAgG;AAChG,2CAA2C;AAC3C,EAAE;AACF,iGAAiG;AACjG,uFAAuF;AAEvF,OAAO,EAAE,eAAe,EAAE,YAAY,EAA6C,MAAM,uBAAuB,CAAC;AACjH,OAAO,EAAE,eAAe,EAAE,gBAAgB,EAAE,aAAa,EAAE,UAAU,EAAE,eAAe,EAAE,MAAM,sBAAsB,CAAC;AACrH,OAAO,EACL,kBAAkB,GAInB,MAAM,gBAAgB,CAAC;AACxB,OAAO,EAAE,cAAc,EAAE,WAAW,EAAE,WAAW,EAAuC,MAAM,gBAAgB,CAAC"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;GAcG;AAEH,gGAAgG;AAChG,+EAA+E;AAC/E,gGAAgG;AAChG,2CAA2C;AAC3C,EAAE;AACF,iGAAiG;AACjG,uFAAuF;AAEvF,OAAO,EACL,eAAe,EACf,YAAY,EACZ,6BAA6B,EAC7B,aAAa,EACb,yBAAyB,EACzB,kBAAkB,EAClB,kBAAkB,EAClB,oBAAoB,GAGrB,MAAM,uBAAuB,CAAC;AAE/B,OAAO,EAAE,eAAe,EAAE,gBAAgB,EAAE,aAAa,EAAE,UAAU,EAAE,eAAe,EAAE,MAAM,sBAAsB,CAAC;AAErH,OAAO,EACL,kBAAkB,EAClB,YAAY,EACZ,kBAAkB,EAClB,WAAW,EACX,qBAAqB,EACrB,eAAe,EACf,mBAAmB,EACnB,UAAU,EACV,eAAe,EACf,cAAc,GAIf,MAAM,gBAAgB,CAAC;AAExB,OAAO,EAAE,cAAc,EAAE,WAAW,EAAE,WAAW,EAAuC,MAAM,gBAAgB,CAAC;AAE/G,OAAO,EACL,kBAAkB,EAClB,8BAA8B,EAC9B,eAAe,GAKhB,MAAM,sBAAsB,CAAC;AAE9B,OAAO,EACL,YAAY,EACZ,oBAAoB,EACpB,kBAAkB,EAClB,gBAAgB,GAIjB,MAAM,kBAAkB,CAAC;AAE1B,OAAO,EACL,iBAAiB,EACjB,sBAAsB,EACtB,YAAY,EACZ,aAAa,EACb,kBAAkB,GAMnB,MAAM,sBAAsB,CAAC;AAE9B,OAAO,EACL,iBAAiB,EACjB,uBAAuB,EACvB,qBAAqB,GAKtB,MAAM,uBAAuB,CAAC;AAE/B,OAAO,EACL,oBAAoB,EACpB,uBAAuB,EACvB,mBAAmB,EACnB,iCAAiC,EACjC,sBAAsB,EACtB,2BAA2B,EAC3B,oBAAoB,EACpB,mBAAmB,EACnB,UAAU,EACV,YAAY,EACZ,0BAA0B,EAC1B,qBAAqB,GAQtB,MAAM,kBAAkB,CAAC;AAE1B,OAAO,EACL,qBAAqB,EACrB,iCAAiC,EACjC,YAAY,EACZ,uBAAuB,EACvB,kBAAkB,EAClB,kBAAkB,EAClB,oBAAoB,EACpB,oBAAoB,EACpB,kBAAkB,EAClB,yBAAyB,EACzB,wBAAwB,EACxB,eAAe,GAGhB,MAAM,qBAAqB,CAAC"}
@@ -0,0 +1 @@
1
+ export * from './namespace-rewriter.js';
@@ -0,0 +1,17 @@
1
+ /*
2
+ * Copyright (c) 2026, SimplySF.
3
+ *
4
+ * Licensed under the Apache License, Version 2.0 (the "License");
5
+ * you may not use this file except in compliance with the License.
6
+ * You may obtain a copy of the License at
7
+ *
8
+ * http://www.apache.org/licenses/LICENSE-2.0
9
+ *
10
+ * Unless required by applicable law or agreed to in writing, software
11
+ * distributed under the License is distributed on an "AS IS" BASIS,
12
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13
+ * See the License for the specific language governing permissions and
14
+ * limitations under the License.
15
+ */
16
+ export * from './namespace-rewriter.js';
17
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/namespaces/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;GAcG;AAEH,cAAc,yBAAyB,CAAC"}
@@ -0,0 +1,50 @@
1
+ export interface RewriteNamespacesOptions {
2
+ rootDir?: string;
3
+ sourceDirs?: string[];
4
+ configFile?: string;
5
+ mappings?: Record<string, string>;
6
+ dryRun?: boolean;
7
+ verbose?: boolean;
8
+ }
9
+ export interface NamespaceReplacement {
10
+ original: string;
11
+ updated: string;
12
+ }
13
+ export interface FileRewriteResult {
14
+ filePath: string;
15
+ changes: NamespaceReplacement[];
16
+ applied: boolean;
17
+ error?: string;
18
+ }
19
+ export interface RewriteNamespacesResult {
20
+ filesScanned: number;
21
+ filesModified: number;
22
+ totalReplacements: number;
23
+ dryRun: boolean;
24
+ configMissingOrEmpty: boolean;
25
+ notice?: string;
26
+ results: FileRewriteResult[];
27
+ }
28
+ /**
29
+ * Recursively locates all *.utam.json files in a directory.
30
+ *
31
+ * @param dirPath - Directory to search within.
32
+ * @returns Array of absolute paths to discovered *.utam.json files.
33
+ */
34
+ export declare function findUtamJsonFiles(dirPath: string): string[];
35
+ /**
36
+ * Recursively updates string values in a JSON structure based on sorted prefix mappings.
37
+ *
38
+ * @param value - Value or AST subtree to examine.
39
+ * @param sortedMappings - Tuples of [originalPrefix, replacementPrefix] sorted descending by length.
40
+ * @param changesList - Array recording applied namespace replacements.
41
+ * @returns Transformed value with replaced prefixes.
42
+ */
43
+ export declare function updateValueWithMappings(value: unknown, sortedMappings: Array<[string, string]>, changesList: NamespaceReplacement[]): unknown;
44
+ /**
45
+ * Rewrites namespace prefixes across compiled *.utam.json page object definitions.
46
+ *
47
+ * @param options - Namespace rewriting options.
48
+ * @returns Summary of files scanned and namespace replacements made.
49
+ */
50
+ export declare function rewriteUtamNamespaces(options?: RewriteNamespacesOptions): RewriteNamespacesResult;
@@ -0,0 +1,223 @@
1
+ /*
2
+ * Copyright (c) 2026, SimplySF.
3
+ *
4
+ * Licensed under the Apache License, Version 2.0 (the "License");
5
+ * you may not use this file except in compliance with the License.
6
+ * You may obtain a copy of the License at
7
+ *
8
+ * http://www.apache.org/licenses/LICENSE-2.0
9
+ *
10
+ * Unless required by applicable law or agreed to in writing, software
11
+ * distributed under the License is distributed on an "AS IS" BASIS,
12
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13
+ * See the License for the specific language governing permissions and
14
+ * limitations under the License.
15
+ */
16
+ import fs from 'node:fs';
17
+ import path from 'node:path';
18
+ import { discoverProject } from '../discovery/index.js';
19
+ import { detectIndentation } from '../overrides/index.js';
20
+ /**
21
+ * Recursively locates all *.utam.json files in a directory.
22
+ *
23
+ * @param dirPath - Directory to search within.
24
+ * @returns Array of absolute paths to discovered *.utam.json files.
25
+ */
26
+ export function findUtamJsonFiles(dirPath) {
27
+ const filesList = [];
28
+ try {
29
+ if (!fs.existsSync(dirPath)) {
30
+ return filesList;
31
+ }
32
+ const entries = fs.readdirSync(dirPath, { withFileTypes: true });
33
+ for (const entry of entries) {
34
+ const fullPath = path.join(dirPath, entry.name);
35
+ if (entry.isDirectory()) {
36
+ const name = entry.name;
37
+ if (name !== 'node_modules' &&
38
+ name !== '.git' &&
39
+ name !== 'dist' &&
40
+ name !== 'lib' &&
41
+ name !== '.wireit' &&
42
+ name !== 'pageObjects' &&
43
+ name !== 'allure-results') {
44
+ filesList.push(...findUtamJsonFiles(fullPath));
45
+ }
46
+ }
47
+ else if (entry.isFile() && entry.name.endsWith('.utam.json')) {
48
+ filesList.push(fullPath);
49
+ }
50
+ }
51
+ }
52
+ catch {
53
+ // Gracefully ignore directory read errors
54
+ }
55
+ return filesList;
56
+ }
57
+ /**
58
+ * Recursively updates string values in a JSON structure based on sorted prefix mappings.
59
+ *
60
+ * @param value - Value or AST subtree to examine.
61
+ * @param sortedMappings - Tuples of [originalPrefix, replacementPrefix] sorted descending by length.
62
+ * @param changesList - Array recording applied namespace replacements.
63
+ * @returns Transformed value with replaced prefixes.
64
+ */
65
+ export function updateValueWithMappings(value, sortedMappings, changesList) {
66
+ if (typeof value === 'string') {
67
+ for (const [prefix, replacement] of sortedMappings) {
68
+ if (value.startsWith(prefix)) {
69
+ const updated = replacement + value.slice(prefix.length);
70
+ changesList.push({ original: value, updated });
71
+ return updated;
72
+ }
73
+ }
74
+ return value;
75
+ }
76
+ if (Array.isArray(value)) {
77
+ return value.map((item) => updateValueWithMappings(item, sortedMappings, changesList));
78
+ }
79
+ if (value !== null && typeof value === 'object') {
80
+ const updatedObj = {};
81
+ for (const [key, val] of Object.entries(value)) {
82
+ updatedObj[key] = updateValueWithMappings(val, sortedMappings, changesList);
83
+ }
84
+ return updatedObj;
85
+ }
86
+ return value;
87
+ }
88
+ function resolveMappings(rootDir, configFile, mappings) {
89
+ let rawMappings = {};
90
+ if (mappings) {
91
+ rawMappings = mappings;
92
+ }
93
+ else {
94
+ const configPath = configFile
95
+ ? path.isAbsolute(configFile)
96
+ ? configFile
97
+ : path.resolve(rootDir, configFile)
98
+ : path.join(rootDir, '.utam', 'namespace-map.json');
99
+ if (!fs.existsSync(configPath)) {
100
+ return {
101
+ sortedMappings: [],
102
+ configMissingOrEmpty: true,
103
+ notice: `Namespace configuration file not found at ${configPath}. Exiting cleanly.`,
104
+ };
105
+ }
106
+ try {
107
+ const configContent = fs.readFileSync(configPath, 'utf-8');
108
+ const parsed = JSON.parse(configContent);
109
+ if (parsed && typeof parsed === 'object' && !Array.isArray(parsed)) {
110
+ rawMappings = parsed;
111
+ }
112
+ }
113
+ catch (err) {
114
+ return {
115
+ sortedMappings: [],
116
+ configMissingOrEmpty: true,
117
+ notice: `Failed to parse namespace config file: ${err.message}`,
118
+ };
119
+ }
120
+ }
121
+ const mappingEntries = Object.entries(rawMappings).filter(([prefix, replacement]) => typeof prefix === 'string' && prefix.trim() && typeof replacement === 'string');
122
+ if (mappingEntries.length === 0) {
123
+ return {
124
+ sortedMappings: [],
125
+ configMissingOrEmpty: true,
126
+ notice: 'Namespace mapping object is empty. No rewrites required.',
127
+ };
128
+ }
129
+ return {
130
+ sortedMappings: [...mappingEntries].sort((a, b) => b[0].length - a[0].length),
131
+ configMissingOrEmpty: false,
132
+ };
133
+ }
134
+ function processSingleUtamFile(file, sortedMappings, dryRun) {
135
+ let fileContent;
136
+ let originalJson;
137
+ try {
138
+ fileContent = fs.readFileSync(file, 'utf-8');
139
+ originalJson = JSON.parse(fileContent);
140
+ }
141
+ catch (err) {
142
+ return {
143
+ filePath: file,
144
+ changes: [],
145
+ applied: false,
146
+ error: `Failed to parse UTAM JSON: ${err.message}`,
147
+ };
148
+ }
149
+ const changesList = [];
150
+ const updatedJson = updateValueWithMappings(originalJson, sortedMappings, changesList);
151
+ if (changesList.length === 0) {
152
+ return {
153
+ filePath: file,
154
+ changes: [],
155
+ applied: false,
156
+ };
157
+ }
158
+ if (!dryRun) {
159
+ const indent = detectIndentation(fileContent);
160
+ const endsWithNewline = fileContent.endsWith('\n');
161
+ let outputContent = JSON.stringify(updatedJson, null, indent);
162
+ if (endsWithNewline && !outputContent.endsWith('\n')) {
163
+ outputContent += '\n';
164
+ }
165
+ fs.writeFileSync(file, outputContent, 'utf-8');
166
+ }
167
+ return {
168
+ filePath: file,
169
+ changes: changesList,
170
+ applied: true,
171
+ };
172
+ }
173
+ /**
174
+ * Rewrites namespace prefixes across compiled *.utam.json page object definitions.
175
+ *
176
+ * @param options - Namespace rewriting options.
177
+ * @returns Summary of files scanned and namespace replacements made.
178
+ */
179
+ export function rewriteUtamNamespaces(options = {}) {
180
+ const rootDir = path.resolve(options.rootDir ?? process.cwd());
181
+ const dryRun = Boolean(options.dryRun);
182
+ const resolution = resolveMappings(rootDir, options.configFile, options.mappings);
183
+ if (resolution.configMissingOrEmpty) {
184
+ return {
185
+ filesScanned: 0,
186
+ filesModified: 0,
187
+ totalReplacements: 0,
188
+ dryRun,
189
+ configMissingOrEmpty: true,
190
+ notice: resolution.notice,
191
+ results: [],
192
+ };
193
+ }
194
+ let sourceDirs = options.sourceDirs;
195
+ if (!sourceDirs || sourceDirs.length === 0) {
196
+ const discovered = discoverProject(rootDir);
197
+ sourceDirs = discovered.packageDirectories.length > 0 ? discovered.packageDirectories : ['./sfdx-source'];
198
+ }
199
+ const allUtamFiles = [];
200
+ for (const sourceDir of sourceDirs) {
201
+ const resolvedSource = path.isAbsolute(sourceDir) ? sourceDir : path.resolve(rootDir, sourceDir);
202
+ allUtamFiles.push(...findUtamJsonFiles(resolvedSource));
203
+ }
204
+ const uniqueUtamFiles = Array.from(new Set(allUtamFiles));
205
+ const result = {
206
+ filesScanned: uniqueUtamFiles.length,
207
+ filesModified: 0,
208
+ totalReplacements: 0,
209
+ dryRun,
210
+ configMissingOrEmpty: false,
211
+ results: [],
212
+ };
213
+ for (const file of uniqueUtamFiles) {
214
+ const fileResult = processSingleUtamFile(file, resolution.sortedMappings, dryRun);
215
+ if (fileResult.applied) {
216
+ result.filesModified++;
217
+ result.totalReplacements += fileResult.changes.length;
218
+ }
219
+ result.results.push(fileResult);
220
+ }
221
+ return result;
222
+ }
223
+ //# sourceMappingURL=namespace-rewriter.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"namespace-rewriter.js","sourceRoot":"","sources":["../../src/namespaces/namespace-rewriter.ts"],"names":[],"mappings":"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"}
@@ -1,3 +1,4 @@
1
+ import { TestEnvironment } from './test-environment.js';
1
2
  /** The part of a WebdriverIO browser the navigator drives. */
2
3
  export type NavigableBrowser = {
3
4
  navigateTo(url: string): Promise<unknown>;
@@ -5,6 +6,12 @@ export type NavigableBrowser = {
5
6
  /** Anything that can mint a logged-in URL; `TestEnvironment` in practice. */
6
7
  export type FrontdoorUrlSource = {
7
8
  buildFrontdoorUrl(returnUrl?: string): Promise<string>;
9
+ buildExperienceFrontdoorUrl?(sitePrefix?: string, returnUrl?: string): Promise<string>;
10
+ getOrgId?(): Promise<string>;
11
+ getUserIdByUsername?(username: string): Promise<string>;
12
+ getInstanceUrl?(): Promise<string>;
13
+ getNetworkIdByPrefix?(sitePrefix?: string): Promise<string>;
14
+ buildExperienceUrl?(sitePrefix?: string, path?: string): Promise<string>;
8
15
  };
9
16
  export type LightningNavigatorOptions = {
10
17
  /** Where login URLs come from. Defaults to a `TestEnvironment` for `UTAM_USERNAME`. */
@@ -12,6 +19,16 @@ export type LightningNavigatorOptions = {
12
19
  /** The browser to drive. Defaults to WebdriverIO's global `browser`, looked up on each call. */
13
20
  browser?: NavigableBrowser;
14
21
  };
22
+ declare global {
23
+ var browser: NavigableBrowser | undefined;
24
+ }
25
+ /**
26
+ * Resolves an active browser instance from explicit parameters or the global runtime context.
27
+ *
28
+ * @param browserInstance - Optional explicit browser instance.
29
+ * @returns The resolved NavigableBrowser instance.
30
+ */
31
+ export declare function resolveBrowser(browserInstance?: NavigableBrowser): NavigableBrowser;
15
32
  /**
16
33
  * Logs the browser in to the test org and opens a Lightning page in one step. Every navigation
17
34
  * goes through a fresh frontdoor URL, so each one also works as the first thing a test does.
@@ -28,34 +45,145 @@ export declare class LightningNavigator {
28
45
  * Log in and open `returnUrl`, or the org's default landing page when it is omitted.
29
46
  *
30
47
  * @param returnUrl Path to open after login.
48
+ * @returns The resolved frontdoor URL navigated to.
31
49
  */
32
- goToLoginUrl(returnUrl?: string): Promise<void>;
50
+ goToLoginUrl(returnUrl?: string): Promise<string>;
33
51
  /**
34
52
  * Log in and open a Lightning app's home page.
35
53
  *
36
54
  * @param applicationName The app's developer name; see `lightningAppName` for namespacing.
55
+ * @returns The resolved application URL.
37
56
  */
38
- goToApplication(applicationName: string): Promise<void>;
57
+ goToApplication(applicationName: string): Promise<string>;
39
58
  /**
40
59
  * Log in and open the new-record form for an object.
41
60
  *
42
61
  * @param applicationName The app's developer name.
43
62
  * @param objectApiName The object's API name.
63
+ * @returns The resolved record creation URL.
44
64
  */
45
- goToCreateNewRecord(applicationName: string, objectApiName: string): Promise<void>;
65
+ goToCreateNewRecord(applicationName: string, objectApiName: string): Promise<string>;
46
66
  /**
47
67
  * Log in and open a record's detail page.
48
68
  *
49
69
  * @param applicationName The app's developer name.
50
70
  * @param recordId The record's id.
71
+ * @returns The resolved record view URL.
51
72
  */
52
- goToRecord(applicationName: string, recordId: string): Promise<void>;
73
+ goToRecord(applicationName: string, recordId: string): Promise<string>;
53
74
  /**
54
75
  * Log in and open one of a record's related lists.
55
76
  *
56
77
  * @param applicationName The app's developer name.
57
78
  * @param recordId The parent record's id.
58
79
  * @param relatedListName The relationship name.
80
+ * @returns The resolved related list URL.
81
+ */
82
+ goToRelatedList(applicationName: string, recordId: string, relatedListName: string): Promise<string>;
83
+ /**
84
+ * Navigates the browser to a specific Experience Cloud site page via UI Bridge frontdoor login.
85
+ *
86
+ * @param sitePrefix - The URL prefix of the Experience site.
87
+ * @param pageName - The Experience page name (relative to /s/).
88
+ * @returns The resolved Experience frontdoor URL navigated to.
89
+ */
90
+ goToExperiencePage(sitePrefix: string, pageName: string): Promise<string>;
91
+ /**
92
+ * Logs in as a specific user using Salesforce user impersonation.
93
+ *
94
+ * @param username - The target user's username.
95
+ * @param returnUrl - The target page to land on once logged in. Defaults to '/'.
96
+ * @returns The resolved impersonation redirect URL.
59
97
  */
60
- goToRelatedList(applicationName: string, recordId: string, relatedListName: string): Promise<void>;
98
+ loginAsUser(username: string, returnUrl?: string): Promise<string>;
99
+ /**
100
+ * Logs in as a specific user and navigates directly to an Experience Cloud site.
101
+ *
102
+ * @param username - The target user's username.
103
+ * @param sitePrefix - The URL prefix of the Experience site.
104
+ * @param pageName - The Experience page name (relative to /s/).
105
+ * @returns The resolved Experience site page URL.
106
+ */
107
+ loginAsExperienceUser(username: string, sitePrefix: string, pageName: string): Promise<string>;
108
+ resolveBrowser(): NavigableBrowser;
61
109
  }
110
+ /**
111
+ * Functional helper: Navigates the browser to the Salesforce Frontdoor login URL.
112
+ *
113
+ * @param returnUrl - Optional landing page path after login.
114
+ * @param browserInstance - Optional browser instance overriding the global runner.
115
+ * @param testEnvironment - Optional TestEnvironment instance.
116
+ * @returns The resolved frontdoor URL navigated to.
117
+ */
118
+ export declare function goToLoginUrl(returnUrl?: string, browserInstance?: NavigableBrowser, testEnvironment?: TestEnvironment): Promise<string>;
119
+ /**
120
+ * Functional helper: Navigates the browser to an Experience Cloud page.
121
+ *
122
+ * @param sitePrefix - The URL prefix of the Experience site.
123
+ * @param pageName - The Experience page name.
124
+ * @param browserInstance - Optional browser instance overriding the global runner.
125
+ * @param testEnvironment - Optional TestEnvironment instance.
126
+ * @returns The resolved Experience frontdoor URL navigated to.
127
+ */
128
+ export declare function goToExperiencePage(sitePrefix: string, pageName: string, browserInstance?: NavigableBrowser, testEnvironment?: TestEnvironment): Promise<string>;
129
+ /**
130
+ * Functional helper: Logs in as a specific user using Salesforce user impersonation.
131
+ *
132
+ * @param username - The target user's username.
133
+ * @param returnUrl - Landing path after impersonation.
134
+ * @param browserInstance - Optional browser instance overriding the global runner.
135
+ * @param testEnvironment - Optional TestEnvironment instance.
136
+ * @returns The resolved impersonation redirect URL.
137
+ */
138
+ export declare function loginAsUser(username: string, returnUrl?: string, browserInstance?: NavigableBrowser, testEnvironment?: TestEnvironment): Promise<string>;
139
+ /**
140
+ * Functional helper: Logs in as a user and navigates directly to an Experience Cloud site.
141
+ *
142
+ * @param username - The target user's username.
143
+ * @param sitePrefix - The URL prefix of the Experience site.
144
+ * @param pageName - The Experience page name.
145
+ * @param browserInstance - Optional browser instance overriding the global runner.
146
+ * @param testEnvironment - Optional TestEnvironment instance.
147
+ * @returns The resolved Experience site page URL.
148
+ */
149
+ export declare function loginAsExperienceUser(username: string, sitePrefix: string, pageName: string, browserInstance?: NavigableBrowser, testEnvironment?: TestEnvironment): Promise<string>;
150
+ /**
151
+ * Functional helper: Navigates to a standard Lightning Application home page.
152
+ *
153
+ * @param applicationName - The developer name of the Lightning application.
154
+ * @param browserInstance - Optional browser instance.
155
+ * @param testEnvironment - Optional TestEnvironment instance.
156
+ * @returns The resolved frontdoor application URL.
157
+ */
158
+ export declare function goToApplication(applicationName: string, browserInstance?: NavigableBrowser, testEnvironment?: TestEnvironment): Promise<string>;
159
+ /**
160
+ * Functional helper: Navigates to a new record creation page for a specific sObject in an application.
161
+ *
162
+ * @param applicationName - The developer name of the Lightning application.
163
+ * @param objectName - The API name of the sObject.
164
+ * @param browserInstance - Optional browser instance.
165
+ * @param testEnvironment - Optional TestEnvironment instance.
166
+ * @returns The resolved frontdoor URL.
167
+ */
168
+ export declare function goToCreateNewRecord(applicationName: string, objectName: string, browserInstance?: NavigableBrowser, testEnvironment?: TestEnvironment): Promise<string>;
169
+ /**
170
+ * Functional helper: Navigates to a record view page in a Lightning application.
171
+ *
172
+ * @param applicationName - The developer name of the Lightning application.
173
+ * @param recordId - The 15 or 18 character Salesforce record ID.
174
+ * @param browserInstance - Optional browser instance.
175
+ * @param testEnvironment - Optional TestEnvironment instance.
176
+ * @returns The resolved frontdoor URL.
177
+ */
178
+ export declare function goToRecord(applicationName: string, recordId: string, browserInstance?: NavigableBrowser, testEnvironment?: TestEnvironment): Promise<string>;
179
+ /**
180
+ * Functional helper: Navigates to a related list view for a specific record in a Lightning application.
181
+ *
182
+ * @param applicationName - The developer name of the Lightning application.
183
+ * @param recordId - The 15 or 18 character parent record ID.
184
+ * @param relatedListName - The relationship name of the related list.
185
+ * @param browserInstance - Optional browser instance.
186
+ * @param testEnvironment - Optional TestEnvironment instance.
187
+ * @returns The resolved frontdoor URL.
188
+ */
189
+ export declare function goToRelatedList(applicationName: string, recordId: string, relatedListName: string, browserInstance?: NavigableBrowser, testEnvironment?: TestEnvironment): Promise<string>;