Repository navigation
Guard StackdriverRemoteLogIO's transport.send() against errors - #71337
roshanprabu wants to merge 1 commit into
Conversation
The log processor's transport.send() call ran unguarded. This processor is installed for every supervised component (scheduler, dag-processor, triggerer, workers) whenever REMOTE_TASK_LOG routes through Stackdriver, so any IAM permission error, gRPC connectivity failure, or quota exception from Cloud Logging propagated straight out of the structlog processor and crashed the entire process -- observed as a dag-processor stuck in CrashLoopBackOff from a missing logging.logEntries.create IAM binding. The read path already has this exact guard one function down (see the try/except around read_logs() a few lines below, with the same rationale in its comment); the write path was simply missing the equivalent. Log delivery is best-effort, so this logs a warning via the handler's own logger instead of raising.
|
Hi @roshanprabu Please look into failing check |
shahar1
left a comment
There was a problem hiding this comment.
Thanks for your contribution! Two requests:
- Resolve conflicts and make the appropriate adjustments as classes have been renamed.
- Add AI attribution checkboxes to the PR's body.
|
Thanks for working on this. With the default Drafted-by: Claude Code (Opus 5.5); reviewed by @shahar1 before posting |
Summary
Fixes one of three bugs reported in #68240 (the one I could verify is still present and fix with high confidence -- see scope note below).
StackdriverRemoteLogIO.processors'procclosure calls_transport.send(...)with no error handling:This processor is installed for every supervised component (scheduler, dag-processor, triggerer, workers) whenever
REMOTE_TASK_LOGroutes through Stackdriver. Any IAM permission error, gRPC connectivity failure, or quota exception from Cloud Logging propagates straight out of the structlog processor and takes down the whole process -- reported as a dag-processor pod stuck inCrashLoopBackOffon every log emit when its Kubernetes Service Account lacked thelogging.logEntries.createIAM binding.The read path already has exactly this guard, a few lines down in the same file, with a comment explaining the rationale:
The write path was simply missing the equivalent. This PR adds it, reusing the same
_logger(already defined in this file specifically for handler-internal failures) and logging a warning instead of raising, since log delivery here is best-effort.Scope note: the linked issue reports three bugs. I traced the other two (empty labels when
record.task_instanceis unset in supervisor context, andread()filtering onlogical_date) against currentmainand found the code has moved on since the report -- there's now a fallback inproc()that reads labels from the event dict when notask_instanceis present (seetest_processors_fallback_to_event_labels), andread()'sti: RuntimeTIalready exposeslogical_datelocally without a DB round-trip. I wasn't confident those two are still bugs as described, so this PR only covers the third (transport.send()unguarded), which I could verify precisely.Test plan
test_processors_survives_transport_send_failure: mockstransport.send()to raise, asserts the processor doesn't propagate the exception.Exception: IAM permission deniedpropagating out ofproc(); re-applied the fix and confirmed it passes.pytest tests/unit/google/cloud/log/test_stackdriver_task_handler.py-- 33 passed.ruff checkandruff format --checkpass on both changed files.