From 5ddc3458c4df54d1bb63a0e0eebb11fc5c044895 Mon Sep 17 00:00:00 2001 From: David Slusser Date: Fri, 21 Aug 2026 09:08:46 -0700 Subject: [PATCH] truncate vendor provided strings to model limit --- .../tests/unit/web/test_tasks.py | 32 +++++++++++++++++++ src/django_project/web/tasks.py | 23 ++++++++++--- 2 files changed, 50 insertions(+), 5 deletions(-) diff --git a/src/django_project/tests/unit/web/test_tasks.py b/src/django_project/tests/unit/web/test_tasks.py index d31eaf0..3b98804 100644 --- a/src/django_project/tests/unit/web/test_tasks.py +++ b/src/django_project/tests/unit/web/test_tasks.py @@ -76,6 +76,38 @@ def test_ingests_event_with_null_primary_venue_address(self, mock_get_events_for self.assertEqual(event.location_address, "") self.assertEqual(event.map_link, "") + @patch("web.tasks.get_event_details") + @patch("web.tasks.get_events_for_organization") + def test_truncates_eventbrite_fields_to_model_limits(self, mock_get_events_for_organization, mock_get_event_details): + long_location_name = "LaunchPad INW Eventbrite Venue Name That Is Much Longer Than Sixty Four Characters" + long_location_address = "123 Long Address Lane, Spokane, WA 99201, United States, Building 7, Floor 12, Suite 1200" + + mock_get_events_for_organization.return_value = [ + { + "id": "evt_789", + "name": {"text": "A" * 300}, + "description": {"text": "Oversized venue metadata."}, + "url": "https://example.com/events/evt_789", + "start": {"utc": "2026-09-16T18:00:00Z"}, + "end": {"utc": "2026-09-16T19:00:00Z"}, + } + ] + mock_get_event_details.return_value = { + "primary_venue": { + "name": long_location_name, + "address": {"localized_address_display": long_location_address}, + }, + "tags": [], + } + + result = ingest_future_eventbrite_events(self.group.pk) + + self.assertEqual(result, f"added 1 new events for {self.group.name}") + event = Event.objects.get(social_platform_id="evt_789") + self.assertEqual(event.name, "A" * 255) + self.assertEqual(event.location_name, long_location_name[:64]) + self.assertEqual(event.location_address, long_location_address[:256]) + class TestPostEventToLinkedIn(TestCase): def test_skips_when_post_to_linkedin_setting_is_false(self): diff --git a/src/django_project/web/tasks.py b/src/django_project/web/tasks.py index d5a5bc1..333730e 100644 --- a/src/django_project/web/tasks.py +++ b/src/django_project/web/tasks.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import logging import random import re @@ -31,6 +33,15 @@ logger = logging.getLogger(__name__) +def _truncate_for_model(model: type[Event], field_name: str, value: str | None) -> str: + if not value: + return "" + max_length = model._meta.get_field(field_name).max_length + if max_length is None: + return value + return value[:max_length] + + @shared_task(time_limit=30, max_retries=0, name="web.test_task") def test_task() -> str: logger.info("test task starting") @@ -140,19 +151,21 @@ def ingest_future_eventbrite_events(group_pk) -> str: event_data: dict[str, Any] = { "group": group, - "name": item["name"].get("text", "") if item.get("name") else "", + "name": _truncate_for_model(Event, "name", item["name"].get("text", "") if item.get("name") else ""), "description": item["description"].get("text", "") if item.get("description") else "", "url": item.get("url", ""), - "social_platform_id": item.get("id", ""), + "social_platform_id": _truncate_for_model(Event, "social_platform_id", item.get("id", "")), "start_datetime": item["start"].get("utc", "") if item.get("start") else "", "end_datetime": item["end"].get("utc", "") if item.get("end") else "", - "location_name": location_data.get("name", ""), - "location_address": location_address, + "location_name": _truncate_for_model(Event, "location_name", location_data.get("name", "")), + "location_address": _truncate_for_model(Event, "location_address", location_address), "map_link": create_google_map_link(location_address) if location_address else "", } event, is_new = Event.objects.update_or_create( - group=group, social_platform_id=item["id"], defaults=event_data + group=group, + social_platform_id=_truncate_for_model(Event, "social_platform_id", item.get("id", "")), + defaults=event_data, ) if is_new: event_count += 1