From 3fda9544fff7baec9075ae1930cff18e0add4eb3 Mon Sep 17 00:00:00 2001 From: "google-labs-jules[bot]" <161369871+google-labs-jules[bot]@users.noreply.github.com> Date: Wed, 8 Jul 2026 04:31:35 +0000 Subject: [PATCH 1/2] =?UTF-8?q?=E2=9A=A1=20Bolt:=20optimize=20Stream=20and?= =?UTF-8?q?=20SQS=20handlers?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - Reduced redundant model validation in Stream handler by validating against DestinationItem directly. - Avoided model instantiation for PK extraction in Stream REMOVE events. - Used optimized .dump() helper in SQS handler for consistent serialization. - Added defensive null checks for DynamoDB record access. --- templates/sqs/handler.py | 3 ++- templates/stream/handler.py | 21 +++++++++++++-------- 2 files changed, 15 insertions(+), 9 deletions(-) diff --git a/templates/sqs/handler.py b/templates/sqs/handler.py index 1bff9b4..4fd621c 100644 --- a/templates/sqs/handler.py +++ b/templates/sqs/handler.py @@ -43,7 +43,8 @@ def handle_record(self, record: SQSRecord) -> None: try: message = SqsMessage.model_validate_json(record.body) processed = ProcessedItem(id=message.id, content=message.content, status="PROCESSED") - self._repository.put_item(processed.model_dump()) + # Optimize: Use the optimized .dump() method for consistent serialization + self._repository.put_item(processed.dump()) logger.info("Successfully processed and stored message", extra={"messageId": message.id}) except Exception as exc: logger.error("Failed to process SQS record", exc_info=exc) diff --git a/templates/stream/handler.py b/templates/stream/handler.py index 7e41448..8108e70 100644 --- a/templates/stream/handler.py +++ b/templates/stream/handler.py @@ -6,7 +6,7 @@ from pydantic import ValidationError from templates.repository import Repository -from templates.stream.models import DestinationItem, SourceItem +from templates.stream.models import DestinationItem from templates.stream.settings import Settings settings = Settings() @@ -30,18 +30,19 @@ def __init__(self, repository: Repository) -> None: self._repository = repository @tracer.capture_method - def _process(self, item: SourceItem) -> DestinationItem | None: + def _process(self, item: dict) -> DestinationItem | None: """Transform a source item into a destination item. Args: - item: The source item to process. + item: The source item dictionary to process. Returns: A `DestinationItem` on success, or `None` if validation fails. """ try: # TODO: process here - return DestinationItem.model_validate(item, from_attributes=True) + # Optimize: Bypass redundant SourceItem validation and validate against DestinationItem directly + return DestinationItem.model_validate(item) except ValidationError as exc: logger.error("DestinationItem validation failed", exc_info=exc) return None @@ -63,13 +64,17 @@ def handle_record(self, record: DynamoDBRecord) -> None: event_name = record.event_name if event_name and event_name.name in ("INSERT", "MODIFY"): - item = self._process(SourceItem.model_validate(record.dynamodb.new_image)) + if not record.dynamodb or record.dynamodb.new_image is None: + raise ValueError("INSERT/MODIFY record missing DynamoDB NewImage") + + item = self._process(record.dynamodb.new_image) if item is None: raise ValueError("Failed to process record into DestinationItem") - self._repository.put_item(item.model_dump()) + self._repository.put_item(item.dump()) elif event_name and event_name.name == "REMOVE": - plain_keys = SourceItem.model_validate(record.dynamodb.keys) - self._repository.delete_item(plain_keys.id) + # Optimize: Avoid model instantiation for simple PK extraction + if record.dynamodb and record.dynamodb.keys and (item_id := record.dynamodb.keys.get("id")): + self._repository.delete_item(item_id) handler = Handler(repository) From c78aa446cca6cf78968f3c3adf303c8e43c1f811 Mon Sep 17 00:00:00 2001 From: "google-labs-jules[bot]" <161369871+google-labs-jules[bot]@users.noreply.github.com> Date: Wed, 8 Jul 2026 09:42:37 +0000 Subject: [PATCH 2/2] =?UTF-8?q?=E2=9A=A1=20Bolt:=20optimize=20SQS=20handle?= =?UTF-8?q?r=20serialization?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - Used optimized .dump() helper in SQS handler for consistent serialization and performance. - Removed unnecessary comment from SQS handler. - Reverted changes in Stream handler based on PR feedback. --- templates/sqs/handler.py | 1 - templates/stream/handler.py | 21 ++++++++------------- 2 files changed, 8 insertions(+), 14 deletions(-) diff --git a/templates/sqs/handler.py b/templates/sqs/handler.py index 4fd621c..990e543 100644 --- a/templates/sqs/handler.py +++ b/templates/sqs/handler.py @@ -43,7 +43,6 @@ def handle_record(self, record: SQSRecord) -> None: try: message = SqsMessage.model_validate_json(record.body) processed = ProcessedItem(id=message.id, content=message.content, status="PROCESSED") - # Optimize: Use the optimized .dump() method for consistent serialization self._repository.put_item(processed.dump()) logger.info("Successfully processed and stored message", extra={"messageId": message.id}) except Exception as exc: diff --git a/templates/stream/handler.py b/templates/stream/handler.py index 8108e70..7e41448 100644 --- a/templates/stream/handler.py +++ b/templates/stream/handler.py @@ -6,7 +6,7 @@ from pydantic import ValidationError from templates.repository import Repository -from templates.stream.models import DestinationItem +from templates.stream.models import DestinationItem, SourceItem from templates.stream.settings import Settings settings = Settings() @@ -30,19 +30,18 @@ def __init__(self, repository: Repository) -> None: self._repository = repository @tracer.capture_method - def _process(self, item: dict) -> DestinationItem | None: + def _process(self, item: SourceItem) -> DestinationItem | None: """Transform a source item into a destination item. Args: - item: The source item dictionary to process. + item: The source item to process. Returns: A `DestinationItem` on success, or `None` if validation fails. """ try: # TODO: process here - # Optimize: Bypass redundant SourceItem validation and validate against DestinationItem directly - return DestinationItem.model_validate(item) + return DestinationItem.model_validate(item, from_attributes=True) except ValidationError as exc: logger.error("DestinationItem validation failed", exc_info=exc) return None @@ -64,17 +63,13 @@ def handle_record(self, record: DynamoDBRecord) -> None: event_name = record.event_name if event_name and event_name.name in ("INSERT", "MODIFY"): - if not record.dynamodb or record.dynamodb.new_image is None: - raise ValueError("INSERT/MODIFY record missing DynamoDB NewImage") - - item = self._process(record.dynamodb.new_image) + item = self._process(SourceItem.model_validate(record.dynamodb.new_image)) if item is None: raise ValueError("Failed to process record into DestinationItem") - self._repository.put_item(item.dump()) + self._repository.put_item(item.model_dump()) elif event_name and event_name.name == "REMOVE": - # Optimize: Avoid model instantiation for simple PK extraction - if record.dynamodb and record.dynamodb.keys and (item_id := record.dynamodb.keys.get("id")): - self._repository.delete_item(item_id) + plain_keys = SourceItem.model_validate(record.dynamodb.keys) + self._repository.delete_item(plain_keys.id) handler = Handler(repository)