ff-dom 1.0.18-beta.5 → 1.0.18

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.
@@ -869,9 +869,9 @@ const getReferenceElementsXpath = (domNode, docmt, isTarget) => {
869
869
  }
870
870
  return xpaths1;
871
871
  };
872
- const parseXml = (xmlStr) => {
872
+ const parseXml = (xmlStr, type) => {
873
873
  if (window.DOMParser) {
874
- return new window.DOMParser().parseFromString(xmlStr, "text/xml");
874
+ return new window.DOMParser().parseFromString(xmlStr, type);
875
875
  }
876
876
  return null;
877
877
  };
@@ -1084,7 +1084,7 @@ const getUniqueParentXpath = (domNode, docmt, node, isTarget, nodeXpath, isIndex
1084
1084
  currentNode = currentNode.parentElement;
1085
1085
  }
1086
1086
  // Final constructed XPath
1087
- const finalXPath = xpathParts.join("");
1087
+ const finalXPath = xpathParts.join("") + nodeXpath;
1088
1088
  let count = getCountOfXPath(finalXPath, domNode, docmt);
1089
1089
  if (count === 1) {
1090
1090
  parentXpathCache.set(domNode, finalXPath); // Cache final result
@@ -1618,6 +1618,7 @@ const addAllXPathAttributes = (attributes, targetElemt, docmt, isIndex, isTarget
1618
1618
  catch (error) {
1619
1619
  console.log(error);
1620
1620
  }
1621
+ return xpathData$1;
1621
1622
  };
1622
1623
  const parseDOM = (element, doc, isIndex, isTarget) => {
1623
1624
  xpathData$1 = [];
@@ -2189,10 +2190,27 @@ const referenceXpath = {
2189
2190
  getReferenceElementXpath,
2190
2191
  };
2191
2192
 
2192
- const getElementFromShadowRoot = (element, selector) => {
2193
- const shadowRoot = element.shadowRoot;
2194
- if (shadowRoot && !selector.includes("dynamic")) {
2195
- return shadowRoot.querySelector(selector);
2193
+ const getElementFromShadowRoot = (el, selector) => {
2194
+ // const shadowRoot = (element as HTMLElement).shadowRoot;
2195
+ // if (shadowRoot && !selector.includes("dynamic")) {
2196
+ // return shadowRoot.querySelector(selector);
2197
+ // }
2198
+ const elements = Array.from(el.querySelectorAll('*'));
2199
+ try {
2200
+ for (let i = 0; i < elements.length; i++) {
2201
+ if (elements[i].shadowRoot) {
2202
+ const { shadowRoot } = elements[i];
2203
+ if (shadowRoot) {
2204
+ getElementFromShadowRoot(shadowRoot, selector);
2205
+ if (shadowRoot && !selector.includes("dynamic")) {
2206
+ return shadowRoot.querySelector(selector);
2207
+ }
2208
+ }
2209
+ }
2210
+ }
2211
+ }
2212
+ catch (error) {
2213
+ console.log(error);
2196
2214
  }
2197
2215
  return null;
2198
2216
  };
@@ -2226,30 +2244,27 @@ const relations = [
2226
2244
  "/preceding",
2227
2245
  "/following",
2228
2246
  ];
2229
- function getElementFromXPath(tempDiv, xpath) {
2230
- let currentElement = tempDiv;
2231
- const window = currentElement.ownerDocument.defaultView;
2247
+ function getElementFromXPath(docmt, xpath) {
2248
+ const window = docmt.defaultView;
2232
2249
  if (!window)
2233
2250
  return null;
2234
2251
  const xpathEvaluator = new window.XPathEvaluator();
2235
- const xpathResult = xpathEvaluator.evaluate(xpath, currentElement.ownerDocument, //here even tempDiv can be passed
2236
- null, window.XPathResult.FIRST_ORDERED_NODE_TYPE, null);
2252
+ const xpathResult = xpathEvaluator.evaluate(xpath, docmt, null, window.XPathResult.FIRST_ORDERED_NODE_TYPE, null);
2237
2253
  return xpathResult.singleNodeValue;
2238
2254
  }
2239
- function checkReferenceElementIsValid(locator, relation, tempDiv) {
2255
+ function checkReferenceElementIsValid(locator, relation, docmt) {
2240
2256
  if (locator.includes(relation)) {
2241
2257
  const locatotSplitArray = locator.split(relation);
2242
2258
  const sourceLoc = locatotSplitArray[0].trim();
2243
- let currentElement = tempDiv;
2244
- const window = currentElement.ownerDocument.defaultView;
2259
+ const window = docmt.defaultView;
2245
2260
  if (!window)
2246
2261
  return null;
2247
2262
  if (!locator.includes("dynamic")) {
2248
2263
  const xpathEvaluator = new window.XPathEvaluator();
2249
- const xpathResult = xpathEvaluator.evaluate(sourceLoc, currentElement.ownerDocument, null, window.XPathResult.FIRST_ORDERED_NODE_TYPE, null);
2264
+ const xpathResult = xpathEvaluator.evaluate(sourceLoc, docmt, null, window.XPathResult.FIRST_ORDERED_NODE_TYPE, null);
2250
2265
  const sourceElement = xpathResult.singleNodeValue;
2251
2266
  if (sourceElement) {
2252
- const xpathResultComplete = xpathEvaluator.evaluate(locator, currentElement.ownerDocument, null, window.XPathResult.FIRST_ORDERED_NODE_TYPE, null);
2267
+ const xpathResultComplete = xpathEvaluator.evaluate(locator, docmt, null, window.XPathResult.FIRST_ORDERED_NODE_TYPE, null);
2253
2268
  const completeElement = xpathResultComplete.singleNodeValue;
2254
2269
  let relativeXpath;
2255
2270
  if (completeElement) {
@@ -2270,16 +2285,12 @@ function checkReferenceElementIsValid(locator, relation, tempDiv) {
2270
2285
  return null;
2271
2286
  }
2272
2287
  const getElementsFromHTML = (record, docmt) => {
2273
- const document = docmt;
2274
- // global.SVGElement = document.defaultView?.SVGElement!;
2275
- const tempDiv = document.createElement("div");
2276
- const elementsToRemove = document.querySelectorAll("script, style, link[rel='stylesheet'], meta, noscript, embed, object, param, source, svg");
2288
+ const elementsToRemove = docmt.querySelectorAll("script, style, link[rel='stylesheet'], meta, noscript, embed, object, param, source, svg");
2277
2289
  if (elementsToRemove) {
2278
2290
  elementsToRemove.forEach((tag) => {
2279
2291
  tag.remove();
2280
2292
  });
2281
2293
  }
2282
- tempDiv.innerHTML = document.body.innerHTML;
2283
2294
  const finalLocatorsSet = new Set();
2284
2295
  let finalLocators = [];
2285
2296
  function createLocator(base, overrides = {}) {
@@ -2353,209 +2364,199 @@ const getElementsFromHTML = (record, docmt) => {
2353
2364
  if (record.isShared.includes("Y")) {
2354
2365
  break locators;
2355
2366
  }
2356
- for (const relation of relations) {
2357
- try {
2358
- let targetElement = null;
2359
- if (locator.value.startsWith("iframe")) {
2360
- const iframe = tempDiv.querySelector(locator.value);
2361
- if (iframe) {
2362
- const iframeDocument = iframe.contentDocument || iframe.contentWindow?.document;
2363
- if (iframeDocument) {
2364
- targetElement = iframeDocument.querySelector(locator.value.slice(6));
2365
- }
2367
+ try {
2368
+ let targetElement = null;
2369
+ if (locator.value.startsWith("iframe")) {
2370
+ const iframe = docmt.querySelector(locator.value);
2371
+ if (iframe) {
2372
+ const iframeDocument = iframe.contentDocument || iframe.contentWindow?.document;
2373
+ if (iframeDocument) {
2374
+ targetElement = iframeDocument.querySelector(locator.value.slice(6));
2366
2375
  }
2367
2376
  }
2368
- else {
2369
- const selectors = locator.value.split(">>>"); // Custom delimiter for shadow DOM
2370
- let currentElement = tempDiv;
2371
- for (const selector of selectors) {
2372
- if (currentElement) {
2373
- const trimmedSelector = selector.trim();
2374
- if (locator.name.includes("id") ||
2375
- trimmedSelector.startsWith("#")) {
2376
- targetElement = currentElement.querySelector("#" + trimmedSelector);
2377
- }
2378
- else if (locator.name.includes("className") ||
2379
- trimmedSelector.startsWith(".")) {
2380
- targetElement = currentElement.querySelector("." + trimmedSelector);
2381
- }
2382
- else if ((locator.name.includes("xpath") ||
2383
- trimmedSelector.startsWith("//")) &&
2384
- !locator.type.match("dynamic")) {
2385
- if (tempDiv.innerHTML) {
2386
- const normalizedXPath = normalizeXPath(trimmedSelector);
2387
- targetElement = getElementFromXPath(tempDiv, normalizedXPath);
2388
- if (targetElement) {
2389
- createLocator(locator, {
2390
- value: trimmedSelector,
2391
- isRecorded: String(locator.isRecorded).includes("N")
2392
- ? "N"
2393
- : "Y",
2394
- });
2395
- }
2396
- }
2397
- }
2398
- else {
2399
- targetElement = currentElement.querySelector(trimmedSelector);
2400
- if (!targetElement) {
2401
- targetElement = getElementFromShadowRoot(currentElement, trimmedSelector);
2402
- }
2403
- }
2404
- if (!targetElement &&
2405
- isSvg(currentElement) &&
2406
- !locator.type.match("dynamic")) {
2407
- targetElement = currentElement.querySelector(trimmedSelector);
2377
+ }
2378
+ else {
2379
+ const selectors = locator.value.split(">>>"); // Custom delimiter for shadow DOM
2380
+ for (const selector of selectors) {
2381
+ if (docmt) {
2382
+ const trimmedSelector = selector.trim();
2383
+ if (locator.name.includes("id") ||
2384
+ trimmedSelector.startsWith("#")) {
2385
+ targetElement = docmt.querySelector("#" + trimmedSelector);
2386
+ }
2387
+ else if (locator.name.includes("className") ||
2388
+ trimmedSelector.startsWith(".")) {
2389
+ targetElement = docmt.querySelector("." + trimmedSelector);
2390
+ }
2391
+ else if ((locator.name.includes("xpath") ||
2392
+ trimmedSelector.startsWith("//")) &&
2393
+ !locator.type.match("dynamic")) {
2394
+ const normalizedXPath = normalizeXPath(trimmedSelector);
2395
+ targetElement = getElementFromXPath(docmt, normalizedXPath);
2396
+ if (targetElement) {
2397
+ createLocator(locator, {
2398
+ value: trimmedSelector,
2399
+ isRecorded: String(locator.isRecorded).includes("N")
2400
+ ? "N"
2401
+ : "Y",
2402
+ });
2408
2403
  }
2409
- currentElement = targetElement;
2410
2404
  }
2411
2405
  else {
2412
- console.error("Element not found at:", selector);
2413
- break;
2406
+ targetElement = docmt.querySelector(trimmedSelector);
2407
+ if (!targetElement) {
2408
+ targetElement = getElementFromShadowRoot(docmt.body, trimmedSelector);
2409
+ }
2414
2410
  }
2415
2411
  }
2416
- }
2417
- const locatorExists = (name, value) => {
2418
- const key = `${name}:${value}`;
2419
- return finalLocatorsSet.has(key);
2420
- };
2421
- if (targetElement) {
2422
- const idValue = getId(targetElement);
2423
- if (idValue && !locatorExists("id", idValue)) {
2424
- record.locators.forEach((loc) => {
2425
- createLocator(loc, {
2426
- name: "id",
2427
- value: idValue,
2428
- isRecorded: loc.value === idValue && loc.name === "id"
2429
- ? loc.isRecorded
2430
- : "Y",
2431
- isSelfHealed: loc.value === idValue && loc.name === "id"
2432
- ? loc.isSelfHealed
2433
- : "Y",
2434
- });
2435
- });
2412
+ else {
2413
+ console.error("Element not found at:", selector);
2414
+ break;
2436
2415
  }
2437
- const textValue = getVisibleText(targetElement);
2438
- if (textValue) {
2439
- record.locators.forEach((loc) => {
2440
- createLocator(loc, {
2441
- name: "linkText",
2442
- type: "static",
2443
- value: textValue,
2444
- isRecorded: loc.value === textValue ? loc.isRecorded : "Y",
2445
- isSelfHealed: loc.value === textValue ? loc.isSelfHealed : "Y",
2446
- });
2416
+ }
2417
+ }
2418
+ const locatorExists = (name, value) => {
2419
+ const key = `${name}:${value}`;
2420
+ return finalLocatorsSet.has(key);
2421
+ };
2422
+ if (targetElement) {
2423
+ const idValue = getId(targetElement);
2424
+ if (idValue && !locatorExists("id", idValue)) {
2425
+ record.locators.forEach((loc) => {
2426
+ createLocator(loc, {
2427
+ name: "id",
2428
+ value: idValue,
2429
+ isRecorded: loc.value === idValue && loc.name === "id"
2430
+ ? loc.isRecorded
2431
+ : "Y",
2432
+ isSelfHealed: loc.value === idValue && loc.name === "id"
2433
+ ? loc.isSelfHealed
2434
+ : "Y",
2447
2435
  });
2448
- }
2449
- const nameLocator = getName(targetElement);
2450
- if (nameLocator && !locatorExists("name", nameLocator)) {
2451
- record.locators.forEach((loc) => {
2452
- createLocator(loc, {
2453
- name: "name",
2454
- type: "static",
2455
- value: nameLocator,
2456
- isRecorded: loc.value === nameLocator && loc.name === "name"
2457
- ? loc.isRecorded
2458
- : "Y",
2459
- isSelfHealed: loc.value === nameLocator && loc.name === "name"
2460
- ? loc.isSelfHealed
2461
- : "Y",
2462
- });
2436
+ });
2437
+ }
2438
+ const textValue = getVisibleText(targetElement);
2439
+ if (textValue) {
2440
+ record.locators.forEach((loc) => {
2441
+ createLocator(loc, {
2442
+ name: "linkText",
2443
+ type: "static",
2444
+ value: textValue,
2445
+ isRecorded: loc.value === textValue ? loc.isRecorded : "Y",
2446
+ isSelfHealed: loc.value === textValue ? loc.isSelfHealed : "Y",
2463
2447
  });
2464
- }
2465
- const classValue = getClassName(targetElement);
2466
- if (classValue &&
2467
- classValue.trim() !== "" &&
2468
- !locatorExists("className", classValue)) {
2469
- record.locators.forEach((loc) => {
2470
- createLocator(loc, {
2471
- name: "className",
2472
- value: classValue,
2473
- isRecorded: loc.value === classValue && loc.name === "className"
2474
- ? loc.isRecorded
2475
- : "Y",
2476
- isSelfHealed: loc.value === classValue && loc.name === "className"
2477
- ? loc.isSelfHealed
2478
- : "Y",
2479
- });
2448
+ });
2449
+ }
2450
+ const nameLocator = getName(targetElement);
2451
+ if (nameLocator && !locatorExists("name", nameLocator)) {
2452
+ record.locators.forEach((loc) => {
2453
+ createLocator(loc, {
2454
+ name: "name",
2455
+ type: "static",
2456
+ value: nameLocator,
2457
+ isRecorded: loc.value === nameLocator && loc.name === "name"
2458
+ ? loc.isRecorded
2459
+ : "Y",
2460
+ isSelfHealed: loc.value === nameLocator && loc.name === "name"
2461
+ ? loc.isSelfHealed
2462
+ : "Y",
2480
2463
  });
2481
- }
2482
- const fnValue = parseDOM(targetElement, document, false, true);
2464
+ });
2465
+ }
2466
+ const classValue = getClassName(targetElement);
2467
+ if (classValue &&
2468
+ classValue.trim() !== "" &&
2469
+ !locatorExists("className", classValue)) {
2483
2470
  record.locators.forEach((loc) => {
2484
2471
  createLocator(loc, {
2485
- name: 'xpath',
2486
- value: fnValue,
2487
- isRecorded: fnValue?.find((x) => x.value === loc.value)
2472
+ name: "className",
2473
+ value: classValue,
2474
+ isRecorded: loc.value === classValue && loc.name === "className"
2488
2475
  ? loc.isRecorded
2489
2476
  : "Y",
2490
- isSelfHealed: fnValue?.find((x) => x.value === loc.value)
2477
+ isSelfHealed: loc.value === classValue && loc.name === "className"
2491
2478
  ? loc.isSelfHealed
2492
2479
  : "Y",
2493
2480
  });
2494
2481
  });
2495
- for (const locator of record.locators) {
2496
- try {
2497
- for (const loc of record.locators) {
2498
- if (!loc.value)
2499
- continue;
2500
- for (const relation of relations) {
2501
- if (loc.value.includes(relation)) {
2502
- const relativeXpath = checkReferenceElementIsValid(loc.value, relation, tempDiv);
2503
- if (relativeXpath) {
2504
- createLocator(loc, {
2505
- name: "xpath",
2506
- value: relativeXpath,
2507
- isRecorded: locator.isRecorded !== "" &&
2508
- locator.isRecorded !== null
2509
- ? locator.isRecorded
2510
- : "Y",
2511
- });
2512
- break;
2513
- }
2482
+ }
2483
+ const xpathResults = parseDOM(targetElement, docmt, false, true);
2484
+ xpathResults.forEach((result) => {
2485
+ const fnValue = result.value;
2486
+ if (fnValue && !locatorExists(result.key.replace('xpath by', '').trim(), fnValue)) {
2487
+ record.locators.forEach((loc) => {
2488
+ createLocator(loc, {
2489
+ name: 'xpath',
2490
+ value: fnValue,
2491
+ isRecorded: loc.value === fnValue ? loc.isRecorded : 'Y',
2492
+ isSelfHealed: loc.value === fnValue ? loc.isSelfHealed : 'Y',
2493
+ });
2494
+ });
2495
+ }
2496
+ });
2497
+ for (const locator of record.locators) {
2498
+ try {
2499
+ for (const loc of record.locators) {
2500
+ if (!loc.value)
2501
+ continue;
2502
+ for (const relation of relations) {
2503
+ if (loc.value.includes(relation)) {
2504
+ const relativeXpath = checkReferenceElementIsValid(loc.value, relation, docmt);
2505
+ if (relativeXpath) {
2506
+ createLocator(loc, {
2507
+ name: "xpath",
2508
+ value: relativeXpath,
2509
+ isRecorded: locator.isRecorded !== "" &&
2510
+ locator.isRecorded !== null
2511
+ ? locator.isRecorded
2512
+ : "Y",
2513
+ });
2514
+ break;
2514
2515
  }
2515
2516
  }
2516
2517
  }
2517
2518
  }
2518
- catch (error) {
2519
- console.error("Error processing locator:", locator, error);
2520
- }
2521
2519
  }
2522
- const finalAutoHealedLocators = finalLocators.map((obj) => ({
2523
- ...obj,
2524
- value: cleanLocatorValue(obj.value, obj.name, obj.isRecorded),
2525
- }));
2526
- const finalUniqueAutoHealedLocators = finalAutoHealedLocators.reduce((unique, locator) => {
2527
- if (locator.value &&
2528
- !unique.some((l) => l.value === locator.value)) {
2529
- unique.push(locator);
2530
- }
2531
- return unique;
2532
- }, []);
2533
- const jsonResult = [
2534
- {
2535
- name: `${record.name}`,
2536
- desc: `${record.desc}`,
2537
- type: `${record.type}`,
2538
- locators: finalUniqueAutoHealedLocators.filter((locator) => locator?.value != null && locator.value !== ""),
2539
- isShared: `${record.isShared}`,
2540
- projectId: `${record.projectId}`,
2541
- projectType: `${record.projectType}`,
2542
- isRecorded: `${record.isRecorded}`,
2543
- folder: `${record.folder}`,
2544
- parentId: `${record.parentId}`,
2545
- parentName: `${record.parentName}`,
2546
- platform: `${record.platform}`,
2547
- licenseId: `${record.licenseId}`,
2548
- licenseType: `${record.licenseType}`,
2549
- userId: `${record.userId}`,
2550
- },
2551
- ];
2552
- return jsonResult;
2520
+ catch (error) {
2521
+ console.error("Error processing locator:", locator, error);
2522
+ }
2553
2523
  }
2524
+ const finalAutoHealedLocators = finalLocators.map((obj) => ({
2525
+ ...obj,
2526
+ value: cleanLocatorValue(obj.value, obj.name, obj.isRecorded),
2527
+ }));
2528
+ const finalUniqueAutoHealedLocators = finalAutoHealedLocators.reduce((unique, locator) => {
2529
+ if (locator.value &&
2530
+ !unique.some((l) => l.value === locator.value)) {
2531
+ unique.push(locator);
2532
+ }
2533
+ return unique;
2534
+ }, []);
2535
+ const jsonResult = [
2536
+ {
2537
+ name: `${record.name}`,
2538
+ desc: `${record.desc}`,
2539
+ type: `${record.type}`,
2540
+ locators: finalUniqueAutoHealedLocators.filter((locator) => locator?.value != null && locator.value !== ""),
2541
+ isShared: `${record.isShared}`,
2542
+ projectId: `${record.projectId}`,
2543
+ projectType: `${record.projectType}`,
2544
+ isRecorded: `${record.isRecorded}`,
2545
+ folder: `${record.folder}`,
2546
+ parentId: `${record.parentId}`,
2547
+ parentName: `${record.parentName}`,
2548
+ platform: `${record.platform}`,
2549
+ licenseId: `${record.licenseId}`,
2550
+ licenseType: `${record.licenseType}`,
2551
+ userId: `${record.userId}`,
2552
+ },
2553
+ ];
2554
+ return jsonResult;
2554
2555
  }
2555
- catch (error) {
2556
- console.error("Error processing locator:", locator, error);
2557
- continue;
2558
- }
2556
+ }
2557
+ catch (error) {
2558
+ console.error("Error processing locator:", locator, error);
2559
+ continue;
2559
2560
  }
2560
2561
  }
2561
2562
  catch (error) {