Implement button events
This commit is contained in:
@@ -1,4 +1,4 @@
|
||||
from typing import Any, Dict
|
||||
from typing import Any, Dict, List
|
||||
|
||||
|
||||
def deep_merge(a: Dict[str, Any], b: Dict[str, Any]) -> Dict[str, Any]:
|
||||
@@ -8,13 +8,84 @@ def deep_merge(a: Dict[str, Any], b: Dict[str, Any]) -> Dict[str, Any]:
|
||||
"""
|
||||
result = dict(a)
|
||||
for k, v in b.items():
|
||||
# Key from b also in a
|
||||
if k in result:
|
||||
# a[k] and b[k] are both a dictionary: recursive deep_merge
|
||||
if isinstance(result[k], dict) and isinstance(v, dict):
|
||||
result[k] = deep_merge(result[k], v)
|
||||
# a[k] and b[k] are both a list: list_merge
|
||||
elif isinstance(result[k], list) and isinstance(v, list):
|
||||
result[k] = result[k] + v
|
||||
result[k] = list_merge(result[k], v)
|
||||
else:
|
||||
result[k] = v
|
||||
else:
|
||||
result[k] = v
|
||||
return result
|
||||
return result
|
||||
|
||||
def list_merge(a: List[Any], b: List[Any]) -> List[Any]:
|
||||
"""
|
||||
Merge two list together based on id's. This is similar to !extend in YAML.
|
||||
|
||||
Steps:
|
||||
1. Check if both lists contain Dicts with an `id` key in them
|
||||
1a. Otherwise just return a + b (extend)
|
||||
2. For every entry in a:
|
||||
3. Store id in a list for later
|
||||
4. Find the same id in b, if not found add to result without merge
|
||||
5. Perform a deep_merge on the dictionary, add to result list
|
||||
6. Ensure there are no id's missing from b, by checking every entry agains the list from step 3
|
||||
7. Return result
|
||||
"""
|
||||
|
||||
# If either list is empty just concatenate
|
||||
if not a or not b:
|
||||
return list(a) + list(b)
|
||||
|
||||
# Detect whether both lists contain dicts with an 'id' key
|
||||
a_has_id = any(isinstance(x, dict) and "id" in x for x in a)
|
||||
b_has_id = any(isinstance(x, dict) and "id" in x for x in b)
|
||||
|
||||
# If there are no id-based dicts in either list, just extend
|
||||
if not (a_has_id and b_has_id):
|
||||
return list(a) + list(b)
|
||||
|
||||
result: List[Any] = []
|
||||
seen_ids = set()
|
||||
|
||||
# Merge entries from `a`, matching by `id` in `b` when present
|
||||
for item in a:
|
||||
if isinstance(item, dict) and "id" in item:
|
||||
id_val = item.get("id")
|
||||
# find matching entry in b
|
||||
match = None
|
||||
for bi in b:
|
||||
if isinstance(bi, dict) and bi.get("id") == id_val:
|
||||
match = bi
|
||||
break
|
||||
|
||||
if match is not None:
|
||||
# deep_merge returns a new dict
|
||||
merged = deep_merge(item, match)
|
||||
result.append(merged)
|
||||
else:
|
||||
result.append(item)
|
||||
|
||||
if id_val is not None:
|
||||
seen_ids.add(id_val)
|
||||
else:
|
||||
# Not an id'd dict, keep as-is
|
||||
result.append(item)
|
||||
|
||||
# Add remaining entries from b that were not merged or that don't have ids
|
||||
for item in b:
|
||||
if isinstance(item, dict) and "id" in item:
|
||||
id_val = item.get("id")
|
||||
if id_val is None:
|
||||
result.append(item)
|
||||
elif id_val not in seen_ids:
|
||||
result.append(item)
|
||||
else:
|
||||
result.append(item)
|
||||
|
||||
return result
|
||||
|
||||
Reference in New Issue
Block a user