1. <?php
  2. /**
  3. * Diffs two datasets of DOM elements, highlighting differences.
  4. *
  5. * @param array $dataset1 The first dataset of DOM elements.
  6. * @param array $dataset2 The second dataset of DOM elements.
  7. * @param array $defaultValues An associative array of default values for attributes.
  8. * @return array An array of differences, where each element is an array
  9. * containing the element, the attribute with the difference,
  10. * and the old and new values. Returns an empty array if no differences.
  11. */
  12. function diffDOMDatasets(array $dataset1, array $dataset2, array $defaultValues): array
  13. {
  14. $diffs = [];
  15. if (empty($dataset1) && empty($dataset2)) {
  16. return $diffs; // Both datasets are empty, no differences
  17. }
  18. if (empty($dataset1)) {
  19. // Dataset 1 is empty, all elements in dataset 2 are added
  20. foreach ($dataset2 as $element) {
  21. $diffs[] = array(
  22. 'element' => $element,
  23. 'attribute' => null, // No specific attribute difference, just addition.
  24. 'old_value' => null,
  25. 'new_value' => null
  26. );
  27. }
  28. return $diffs;
  29. }
  30. if (empty($dataset2)) {
  31. // Dataset 2 is empty, all elements in dataset 1 are removed
  32. foreach ($dataset1 as $element) {
  33. $diffs[] = array(
  34. 'element' => $element,
  35. 'attribute' => null, // No specific attribute difference, just removal.
  36. 'old_value' => null,
  37. 'new_value' => null
  38. );
  39. }
  40. return $diffs;
  41. }
  42. // Create a map of element IDs to elements for faster lookup
  43. $dataset1Map = [];
  44. foreach ($dataset1 as $element) {
  45. $dataset1Map[$element->id] = $element;
  46. }
  47. $dataset2Map = [];
  48. foreach ($dataset2 as $element) {
  49. $dataset2Map[$element->id] = $element;
  50. }
  51. // Find elements present in both datasets
  52. $commonElements = array_intersect_key($dataset1Map, $dataset2Map);
  53. foreach ($commonElements as $elementId => $element1) {
  54. $element2 = $dataset2Map[$elementId];
  55. // Iterate through attributes and check for differences
  56. foreach ($defaultValues as $attribute => $defaultValue) {
  57. $value1 = $element1->getAttribute($attribute);
  58. $value2 = $element2->getAttribute($attribute);
  59. if ($value1 !== $value2) {
  60. $diffs[] = array(
  61. 'element' => $element1,
  62. 'attribute' => $attribute,
  63. 'old_value' => $value1,
  64. 'new_value' => $value2
  65. );
  66. }
  67. // Handle attributes that don't exist in the default values.
  68. // This ensures that attributes present in the DOM but not
  69. // specified in defaultValues are also flagged.
  70. if ($element1->hasAttribute($attribute) && !$element2->hasAttribute($attribute)) {
  71. $diffs[] = array(
  72. 'element' => $element1,
  73. 'attribute' => $attribute,
  74. 'old_value' => $element1->getAttribute($attribute),
  75. 'new_value' => null
  76. );
  77. }
  78. if (!$element1->hasAttribute($attribute) && $element2->hasAttribute($attribute)) {
  79. $diffs[] = array(
  80. 'element' => $element1,
  81. 'attribute' => $attribute,
  82. 'old_value' => null,
  83. 'new_value' => $element2->getAttribute($attribute)
  84. );
  85. }
  86. }
  87. }
  88. return $diffs;
  89. }
  90. ?>

Add your comment