Skip to content

Commit ec406b3

Browse files
authored
Reduce the number of history events coming from tag updates that don't change anything (#1604)
1 parent 9a62fda commit ec406b3

File tree

2 files changed

+81
-21
lines changed

2 files changed

+81
-21
lines changed

datajunction-server/datajunction_server/api/nodes.py

Lines changed: 22 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -941,29 +941,30 @@ async def tags_node(
941941
Add a tag to a node
942942
"""
943943
node = await Node.get_by_name(session=session, name=name)
944+
existing_tags = {tag.name for tag in node.tags} # type: ignore
944945
if not tag_names:
945946
tag_names = [] # pragma: no cover
946-
tags = await get_tags_by_name(session, names=tag_names)
947-
node.tags = tags # type: ignore
948-
949-
session.add(node)
950-
await save_history(
951-
event=History(
952-
entity_type=EntityType.NODE,
953-
entity_name=node.name, # type: ignore
954-
node=node.name, # type: ignore
955-
activity_type=ActivityType.TAG,
956-
details={
957-
"tags": tag_names,
958-
},
959-
user=current_user.username,
960-
),
961-
session=session,
962-
)
963-
await session.commit()
964-
await session.refresh(node)
965-
for tag in tags:
966-
await session.refresh(tag)
947+
if existing_tags != set(tag_names):
948+
tags = await get_tags_by_name(session, names=tag_names)
949+
node.tags = tags # type: ignore
950+
session.add(node)
951+
await save_history(
952+
event=History(
953+
entity_type=EntityType.NODE,
954+
entity_name=node.name, # type: ignore
955+
node=node.name, # type: ignore
956+
activity_type=ActivityType.TAG,
957+
details={
958+
"tags": tag_names,
959+
},
960+
user=current_user.username,
961+
),
962+
session=session,
963+
)
964+
await session.commit()
965+
await session.refresh(node)
966+
for tag in tags:
967+
await session.refresh(tag)
967968

968969
return JSONResponse(
969970
status_code=200,

datajunction-server/tests/api/tags_test.py

Lines changed: 59 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -396,3 +396,62 @@ async def test_add_tag_to_node(self, client_with_dbt: AsyncClient) -> None:
396396
assert response.status_code == 200
397397
response_data = response.json()
398398
assert response_data == []
399+
400+
@pytest.mark.asyncio
401+
async def test_tagging_node_with_same_tags_does_not_create_history(
402+
self,
403+
client_with_dbt: AsyncClient,
404+
) -> None:
405+
"""
406+
Test that tagging a node with the same tags doesn't create a new history event.
407+
"""
408+
# Create tags
409+
await self.create_tag(client_with_dbt)
410+
await self.create_another_tag(client_with_dbt)
411+
412+
# Tag a node with two tags
413+
response = await client_with_dbt.post(
414+
"/nodes/default.items_sold_count/tags/?tag_names=sales_report&tag_names=reports",
415+
)
416+
assert response.status_code == 200
417+
418+
# Check history - should have one tag event
419+
response = await client_with_dbt.get(
420+
"/history?node=default.items_sold_count",
421+
)
422+
history = response.json()
423+
tag_events = [h for h in history if h["activity_type"] == "tag"]
424+
assert len(tag_events) == 1
425+
assert tag_events[0]["details"] == {"tags": ["sales_report", "reports"]}
426+
427+
# Tag the same node with the same tags again (order may differ)
428+
response = await client_with_dbt.post(
429+
"/nodes/default.items_sold_count/tags/?tag_names=reports&tag_names=sales_report",
430+
)
431+
assert response.status_code == 200
432+
433+
# Check history again - should still have only one tag event (no new history)
434+
response = await client_with_dbt.get(
435+
"/history?node=default.items_sold_count",
436+
)
437+
history = response.json()
438+
tag_events = [h for h in history if h["activity_type"] == "tag"]
439+
assert len(tag_events) == 1, (
440+
"No new history event should be created when tags haven't changed"
441+
)
442+
443+
# Now actually change the tags - remove one
444+
response = await client_with_dbt.post(
445+
"/nodes/default.items_sold_count/tags/?tag_names=sales_report",
446+
)
447+
assert response.status_code == 200
448+
449+
# Check history - should now have two tag events
450+
response = await client_with_dbt.get(
451+
"/history?node=default.items_sold_count",
452+
)
453+
history = response.json()
454+
tag_events = [h for h in history if h["activity_type"] == "tag"]
455+
assert len(tag_events) == 2, (
456+
"A new history event should be created when tags are changed"
457+
)

0 commit comments

Comments
 (0)