@dev-blinq/cucumber_client 1.0.1265-dev → 1.0.1266-dev

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.
@@ -316,6 +316,27 @@ var DOM_Parent = class {
316
316
  }
317
317
  return ancestors;
318
318
  }
319
+ getFullAncestorChainToRoot(element, root) {
320
+ if (!element || !(element instanceof Element)) {
321
+ throw new Error("Invalid element provided");
322
+ }
323
+ if (!root || !(root instanceof Element)) {
324
+ throw new Error("Invalid root provided");
325
+ }
326
+ if (!this.containsElementCrossShadow(root, element)) {
327
+ throw new Error("Root does not contain the element");
328
+ }
329
+ const ancestors = [];
330
+ let currentElement = element;
331
+ while (currentElement && currentElement !== root && this.containsElementCrossShadow(root, currentElement)) {
332
+ ancestors.push(currentElement);
333
+ currentElement = this.getActualParent(currentElement);
334
+ }
335
+ if (currentElement === root) {
336
+ ancestors.push(currentElement);
337
+ }
338
+ return ancestors;
339
+ }
319
340
  getClimbCountToParent(element, targetParent) {
320
341
  if (!element || !(element instanceof Element)) {
321
342
  throw new Error("Invalid element provided");
@@ -8230,6 +8251,7 @@ var LocatorGenerator = class {
8230
8251
  this.dom_Parent = new dom_parent_default();
8231
8252
  this.PW = __PW;
8232
8253
  this.injectedScript = injectedScript;
8254
+ this.cache = /* @__PURE__ */ new Map();
8233
8255
  }
8234
8256
  getMatchingElements(selector, options = {}) {
8235
8257
  const { root = window.document, prefix, visible = true } = options;
@@ -8375,12 +8397,16 @@ var LocatorGenerator = class {
8375
8397
  const text = this.injectedScript.utils.elementText(/* @__PURE__ */ new Map(), textElement).full;
8376
8398
  if (!textSet.has(text)) {
8377
8399
  textSet.add(text);
8378
- result.push({
8400
+ const loc = {
8379
8401
  css: restOfSelector,
8380
8402
  climb: climbCount,
8381
8403
  text,
8382
8404
  priority: 1
8383
- });
8405
+ };
8406
+ if (locator.index !== void 0) {
8407
+ loc.index = locator.index;
8408
+ }
8409
+ result.push(loc);
8384
8410
  }
8385
8411
  }
8386
8412
  } catch (error) {
@@ -8481,7 +8507,10 @@ var LocatorGenerator = class {
8481
8507
  const nonUnique = [];
8482
8508
  for (const locator of locators) {
8483
8509
  const elements = this.getMatchingElements(locator.css, options);
8484
- if (elements.length === 1) {
8510
+ if (elements.length === 0) {
8511
+ console.warn(`No elements found for locator: ${locator.css}`);
8512
+ continue;
8513
+ } else if (elements.length === 1) {
8485
8514
  if (element === elements[0]) {
8486
8515
  locator.priority = 1;
8487
8516
  unique.push(locator);
@@ -8501,9 +8530,18 @@ var LocatorGenerator = class {
8501
8530
  }
8502
8531
  return { unique, nonUnique };
8503
8532
  }
8533
+ getCategorizedLocators(element, options = {}) {
8534
+ if (this.cache.has(element)) {
8535
+ return this.cache.get(element);
8536
+ }
8537
+ const locators = this.getElementLocators(element, options);
8538
+ }
8504
8539
  getUniqueLocators(element, locatorGenerator = this.getNoTextLocators, options = {}) {
8540
+ return this.getUniqueLocators2(element, locatorGenerator, options);
8541
+ }
8542
+ getUniqueLocators1(element, locatorGenerator = this.getNoTextLocators, options = {}) {
8505
8543
  try {
8506
- const { maxLocators = 5, root = window.document.body, next = "LCA" } = options;
8544
+ const { maxLocators = 5, root = window.document.body, next = "LCA", minLocators = 3 } = options;
8507
8545
  if (!element) {
8508
8546
  return [];
8509
8547
  }
@@ -8584,7 +8622,7 @@ var LocatorGenerator = class {
8584
8622
  result.push(_locator);
8585
8623
  } else {
8586
8624
  const index = _elements.indexOf(element);
8587
- if (index !== -1) {
8625
+ if (index !== -1 && index < 5) {
8588
8626
  _locator.css = fullSelector;
8589
8627
  _locator.index = index;
8590
8628
  _locator.priority = 2;
@@ -8595,7 +8633,7 @@ var LocatorGenerator = class {
8595
8633
  }
8596
8634
  } else {
8597
8635
  const index = elements.indexOf(element);
8598
- if (index !== -1) {
8636
+ if (index !== -1 && index < 5) {
8599
8637
  locator.index = index;
8600
8638
  locator.priority = 2;
8601
8639
  result.push(locator);
@@ -8603,7 +8641,7 @@ var LocatorGenerator = class {
8603
8641
  }
8604
8642
  } else {
8605
8643
  const index = elements.indexOf(element);
8606
- if (index !== -1) {
8644
+ if (index !== -1 && index < 5) {
8607
8645
  locator.index = index;
8608
8646
  locator.priority = 2;
8609
8647
  result.push(locator);
@@ -8614,7 +8652,7 @@ var LocatorGenerator = class {
8614
8652
  delete locator.engine;
8615
8653
  delete locator.selector;
8616
8654
  }
8617
- if (result.length === 0) {
8655
+ if (result.length < minLocators && root && root.contains(element)) {
8618
8656
  const parent = this.dom_Parent.getActualParent(element);
8619
8657
  const locs = this.getUniqueLocators(parent, locatorGenerator, {
8620
8658
  ...options,
@@ -8631,6 +8669,124 @@ var LocatorGenerator = class {
8631
8669
  return [];
8632
8670
  }
8633
8671
  }
8672
+ getUniqueLocators2(element, locatorGenerator = this.getNoTextLocators, options = {}) {
8673
+ try {
8674
+ const { maxLocators = 5, root = window.document.body } = options;
8675
+ if (!element) {
8676
+ return [];
8677
+ }
8678
+ if (element === root) {
8679
+ if (element === window.document.documentElement) {
8680
+ return [
8681
+ {
8682
+ css: "html",
8683
+ score: 1,
8684
+ priority: 1
8685
+ },
8686
+ {
8687
+ css: ":root",
8688
+ score: 1,
8689
+ priority: 1
8690
+ }
8691
+ ];
8692
+ } else {
8693
+ return [
8694
+ {
8695
+ css: ":root",
8696
+ score: 1,
8697
+ priority: 1
8698
+ // }, {
8699
+ // css: ":root",
8700
+ // score: 1,
8701
+ // priority: 1,
8702
+ }
8703
+ ];
8704
+ }
8705
+ }
8706
+ console.log("Generating locators for element:", element);
8707
+ const locators = locatorGenerator(element, options);
8708
+ console.log("Generated locators:", locators);
8709
+ if (!locators || !Array.isArray(locators)) {
8710
+ console.error("Locator generator did not return an array of locators");
8711
+ return [];
8712
+ }
8713
+ console.log("Categorizing locators for element:", element);
8714
+ const categorizedLocators = this.categorizeLocators(element, locators, options);
8715
+ console.log("Categorized locators:", categorizedLocators);
8716
+ const { unique, nonUnique } = categorizedLocators;
8717
+ const result = [];
8718
+ if (unique.length > 0) {
8719
+ result.push(...unique);
8720
+ }
8721
+ if (result.length >= maxLocators) {
8722
+ return result.slice(0, maxLocators);
8723
+ }
8724
+ const elementsCache = /* @__PURE__ */ new Map();
8725
+ const allAncestors = this.dom_Parent.getFullAncestorChainToRoot(element, root);
8726
+ allAncestors.shift();
8727
+ const ancestorLocators = [];
8728
+ for (const ancestor of allAncestors) {
8729
+ const _locators = locatorGenerator(ancestor, options);
8730
+ if (!_locators || !Array.isArray(_locators) || _locators.length === 0) {
8731
+ continue;
8732
+ }
8733
+ const _categorized = this.categorizeLocators(ancestor, _locators, options);
8734
+ ancestorLocators.push({
8735
+ element: ancestor,
8736
+ locators: _categorized
8737
+ });
8738
+ elementsCache.set(ancestor, _categorized);
8739
+ if (_categorized.unique.length > 0) {
8740
+ break;
8741
+ }
8742
+ }
8743
+ const uniqueAncestor = ancestorLocators[ancestorLocators.length - 1];
8744
+ for (const locator of nonUnique) {
8745
+ const selector = locator.css ?? locator.selector;
8746
+ const elements = locator.elements || this.getMatchingElements(selector, options);
8747
+ if (elements.length === 0) {
8748
+ console.warn(`No elements found for locator: ${selector}`);
8749
+ continue;
8750
+ }
8751
+ for (const unique_locator of uniqueAncestor.locators.unique) {
8752
+ const fullSelector = `${unique_locator.css} >> ${selector}`;
8753
+ const elements2 = this.getMatchingElements(fullSelector, options);
8754
+ if (elements2.length === 1 && elements2[0] === element) {
8755
+ const effectiveScore = (unique_locator.score + locator.score) / 2 + 100;
8756
+ const newLocator = {
8757
+ ...unique_locator,
8758
+ css: fullSelector,
8759
+ score: effectiveScore,
8760
+ priority: 1
8761
+ // unique locators have higher priority
8762
+ };
8763
+ result.push(newLocator);
8764
+ } else {
8765
+ const index = elements2.indexOf(element);
8766
+ if (index !== -1 && index < 5) {
8767
+ const effectiveScore = (unique_locator.score + locator.score) / 2;
8768
+ const newLocator = {
8769
+ ...unique_locator,
8770
+ css: fullSelector,
8771
+ index,
8772
+ score: effectiveScore + 200,
8773
+ priority: 2
8774
+ // non-unique locators have lower priority
8775
+ };
8776
+ result.push(newLocator);
8777
+ }
8778
+ }
8779
+ }
8780
+ }
8781
+ result.sort((a, b) => a.score - b.score);
8782
+ console.log("Final locators:", result, element);
8783
+ console.groupEnd();
8784
+ return result.slice(0, maxLocators);
8785
+ } catch (error) {
8786
+ console.error("Error in getUniqueLocators:", error);
8787
+ return [];
8788
+ }
8789
+ }
8634
8790
  getElementLocators(element, options = {}) {
8635
8791
  var _a;
8636
8792
  const { excludeText = false } = options;
@@ -35,6 +35,28 @@ class DOM_Parent {
35
35
 
36
36
  return ancestors;
37
37
  }
38
+ getFullAncestorChainToRoot(element, root) {
39
+ if (!element || !(element instanceof Element)) {
40
+ throw new Error('Invalid element provided');
41
+ }
42
+ if (!root || !(root instanceof Element)) {
43
+ throw new Error('Invalid root provided');
44
+ }
45
+ if (!this.containsElementCrossShadow(root, element)) {
46
+ throw new Error('Root does not contain the element');
47
+ }
48
+ const ancestors = [];
49
+ let currentElement = element;
50
+ while (currentElement && currentElement !== root && this.containsElementCrossShadow(root, currentElement)) {
51
+ ancestors.push(currentElement);
52
+ currentElement = this.getActualParent(currentElement);
53
+
54
+ }
55
+ if (currentElement === root) {
56
+ ancestors.push(currentElement);
57
+ }
58
+ return ancestors;
59
+ }
38
60
  getClimbCountToParent(element, targetParent) {
39
61
  if (!element || !(element instanceof Element)) {
40
62
  throw new Error('Invalid element provided');
@@ -19,6 +19,7 @@ class LocatorGenerator {
19
19
  this.dom_Parent = new DOM_Parent();
20
20
  this.PW = __PW;
21
21
  this.injectedScript = injectedScript;
22
+ this.cache = new Map();
22
23
  }
23
24
 
24
25
  getMatchingElements(selector, options = {}) {
@@ -176,13 +177,16 @@ class LocatorGenerator {
176
177
  const text = this.injectedScript.utils.elementText(new Map(), textElement).full;
177
178
  if (!textSet.has(text)) {
178
179
  textSet.add(text);
179
- result.push({
180
+ const loc = {
180
181
  css: restOfSelector,
181
182
  climb: climbCount,
182
183
  text,
183
184
  priority: 1,
184
- });
185
-
185
+ }
186
+ if (locator.index !== undefined) {
187
+ loc.index = locator.index;
188
+ }
189
+ result.push(loc);
186
190
  }
187
191
 
188
192
 
@@ -297,7 +301,10 @@ class LocatorGenerator {
297
301
  const nonUnique = [];
298
302
  for (const locator of locators) {
299
303
  const elements = this.getMatchingElements(locator.css, options);
300
- if (elements.length === 1) {
304
+ if (elements.length === 0) {
305
+ console.warn(`No elements found for locator: ${locator.css}`);
306
+ continue;
307
+ } else if (elements.length === 1) {
301
308
  if (element === elements[0]) {
302
309
  locator.priority = 1;
303
310
  unique.push(locator);
@@ -318,13 +325,21 @@ class LocatorGenerator {
318
325
  return { unique, nonUnique };
319
326
  }
320
327
 
321
-
328
+ getCategorizedLocators(element, options = {}) {
329
+ if (this.cache.has(element)) {
330
+ return this.cache.get(element);
331
+ }
332
+ const locators = this.getElementLocators(element, options);
333
+ }
322
334
 
323
335
 
324
336
  getUniqueLocators(element, locatorGenerator = this.getNoTextLocators, options = {}) {
337
+ return this.getUniqueLocators2(element, locatorGenerator, options);
338
+ }
339
+ getUniqueLocators1(element, locatorGenerator = this.getNoTextLocators, options = {}) {
325
340
  try {
326
341
 
327
- const { maxLocators = 5, root = window.document.body, next = "LCA" } = options;
342
+ const { maxLocators = 5, root = window.document.body, next = "LCA", minLocators = 3 } = options;
328
343
 
329
344
  if (!element) {
330
345
  return [];
@@ -414,7 +429,7 @@ class LocatorGenerator {
414
429
  result.push(_locator);
415
430
  } else {
416
431
  const index = _elements.indexOf(element);
417
- if (index !== -1) {
432
+ if (index !== -1 && index < 5) {
418
433
  // _locator.selector = fullSelector;
419
434
  _locator.css = fullSelector;
420
435
  _locator.index = index;
@@ -428,7 +443,7 @@ class LocatorGenerator {
428
443
 
429
444
  } else {
430
445
  const index = elements.indexOf(element);
431
- if (index !== -1) {
446
+ if (index !== -1 && index < 5) {
432
447
  locator.index = index
433
448
  locator.priority = 2; // non-unique locators have lower priority
434
449
  result.push(locator);
@@ -437,7 +452,7 @@ class LocatorGenerator {
437
452
 
438
453
  } else {
439
454
  const index = elements.indexOf(element);
440
- if (index !== -1) {
455
+ if (index !== -1 && index < 5) {
441
456
  locator.index = index
442
457
  locator.priority = 2; // non-unique locators have lower priority
443
458
  result.push(locator);
@@ -450,7 +465,7 @@ class LocatorGenerator {
450
465
  delete locator.selector;
451
466
  }
452
467
 
453
- if (result.length === 0) {
468
+ if (result.length < minLocators && root && root.contains(element)) {
454
469
  const parent = this.dom_Parent.getActualParent(element);
455
470
  const locs = this.getUniqueLocators(parent, locatorGenerator, {
456
471
  ...options,
@@ -470,6 +485,137 @@ class LocatorGenerator {
470
485
  return [];
471
486
  }
472
487
  }
488
+
489
+ getUniqueLocators2(element, locatorGenerator = this.getNoTextLocators, options = {}) {
490
+ try {
491
+
492
+ const { maxLocators = 5, root = window.document.body } = options;
493
+
494
+ if (!element) {
495
+ return [];
496
+ }
497
+ if (element === root) {
498
+ if (element === window.document.documentElement) {
499
+ return [{
500
+ css: "html",
501
+ score: 1,
502
+ priority: 1,
503
+ }, {
504
+ css: ":root",
505
+ score: 1,
506
+ priority: 1,
507
+ }
508
+ ]
509
+ } else {
510
+ return [{
511
+ css: ":root",
512
+ score: 1,
513
+ priority: 1,
514
+ // }, {
515
+ // css: ":root",
516
+ // score: 1,
517
+ // priority: 1,
518
+ }
519
+ ]
520
+ }
521
+ }
522
+
523
+ console.log("Generating locators for element:", element);
524
+ const locators = locatorGenerator(element, options);
525
+ console.log("Generated locators:", locators);
526
+ if (!locators || !Array.isArray(locators)) {
527
+ // throw new Error("Locator generator did not return an array of locators");
528
+ console.error("Locator generator did not return an array of locators");
529
+ return [];
530
+ }
531
+
532
+ console.log("Categorizing locators for element:", element);
533
+ const categorizedLocators = this.categorizeLocators(element, locators, options);
534
+ console.log("Categorized locators:", categorizedLocators);
535
+ // categorizedLocators.unique = limitLocators(categorizedLocators.unique, options);
536
+ // categorizedLocators.nonUnique = limitLocators(categorizedLocators.nonUnique, options);
537
+
538
+ const { unique, nonUnique } = categorizedLocators;
539
+ const result = [];
540
+ if (unique.length > 0) {
541
+ result.push(...unique);
542
+ }
543
+ if (result.length >= maxLocators) {
544
+ return result.slice(0, maxLocators);
545
+ }
546
+
547
+ const elementsCache = new Map();
548
+
549
+ const allAncestors = this.dom_Parent.getFullAncestorChainToRoot(element, root);
550
+ allAncestors.shift(); // remove the element itself from the ancestors
551
+
552
+ const ancestorLocators = [];
553
+ for (const ancestor of allAncestors) {
554
+ const _locators = locatorGenerator(ancestor, options);
555
+ if (!_locators || !Array.isArray(_locators) || _locators.length
556
+ === 0) {
557
+ continue;
558
+ }
559
+ const _categorized = this.categorizeLocators(ancestor, _locators, options);
560
+ ancestorLocators.push({
561
+ element: ancestor,
562
+ locators: _categorized,
563
+ });
564
+ elementsCache.set(ancestor, _categorized);
565
+ if (_categorized.unique.length > 0) {
566
+ break;
567
+ }
568
+ }
569
+
570
+ const uniqueAncestor = ancestorLocators[ancestorLocators.length - 1];
571
+
572
+ for (const locator of nonUnique) {
573
+ const selector = locator.css ?? locator.selector;
574
+ const elements = locator.elements || this.getMatchingElements(selector, options);
575
+ if (elements.length === 0) {
576
+ console.warn(`No elements found for locator: ${selector}`);
577
+ continue;
578
+ }
579
+
580
+ for (const unique_locator of uniqueAncestor.locators.unique) {
581
+ const fullSelector = `${unique_locator.css} >> ${selector}`;
582
+ const elements = this.getMatchingElements(fullSelector, options);
583
+ if (elements.length === 1 && elements[0] === element) {
584
+ const effectiveScore = (unique_locator.score + locator.score) / 2 + 100;
585
+ const newLocator = {
586
+ ...unique_locator,
587
+ css: fullSelector,
588
+ score: effectiveScore,
589
+ priority: 1, // unique locators have higher priority
590
+ };
591
+ result.push(newLocator);
592
+ } else {
593
+ const index = elements.indexOf(element);
594
+ if (index !== -1 && index < 5) {
595
+ const effectiveScore = (unique_locator.score + locator.score) / 2;
596
+ const newLocator = {
597
+ ...unique_locator,
598
+ css: fullSelector,
599
+ index,
600
+ score: effectiveScore + 200,
601
+ priority: 2, // non-unique locators have lower priority
602
+ };
603
+ result.push(newLocator);
604
+ }
605
+ }
606
+ }
607
+
608
+ }
609
+ result.sort((a, b) => a.score - b.score);
610
+ console.log("Final locators:", result, element);
611
+ console.groupEnd();
612
+ return result.slice(0, maxLocators);
613
+ }
614
+ catch (error) {
615
+ console.error("Error in getUniqueLocators:", error);
616
+ return [];
617
+ }
618
+ }
473
619
  getElementLocators(element, options = {}) {
474
620
 
475
621
  const { excludeText = false } = options;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@dev-blinq/cucumber_client",
3
- "version": "1.0.1265-dev",
3
+ "version": "1.0.1266-dev",
4
4
  "description": "",
5
5
  "main": "bin/index.js",
6
6
  "types": "bin/index.d.ts",