Skip to content

fix: Second attempt at fixing trace propagation in Celery 4.2+#831

Merged
untitaker merged 5 commits into
masterfrom
fix/celery-trace-propagation-2
Sep 23, 2020
Merged

fix: Second attempt at fixing trace propagation in Celery 4.2+#831
untitaker merged 5 commits into
masterfrom
fix/celery-trace-propagation-2

Conversation

@untitaker

@untitaker untitaker commented Sep 22, 2020

Copy link
Copy Markdown
Member

It turns out the bug is perfectly reproducible with the Redis backend, I just messed up the test.

apply_async was basically patched at the wrong point in time, and as such the trace propagation didn't work out.

Sorry y'all for dropping this on you without so little context, we can go through this tomorrow.

Follow-up to #824 #825

# Note: kwargs can contain headers=None, so no setdefault!
# Unsure which backend though.
kwarg_headers = kwargs.get("headers") or {}
kwarg_headers.update(headers)

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This line is currently crashing all the time (in capture_internal_exceptions) because the old code could not deal with kwargs == {"headers": None}, only kwargs == {}.

# Need to setdefault the inner headers too since other
# tracing tools (dd-trace-py) also employ this exact
# workaround and we don't want to break them.
#

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Turns out it is perfectly reproducible. The bug we're working around lives in celery.app.amqp, but it seems that module is used in redis too??? tbh I no longer understand how celery separates concerns.


# this backend requires capture_events_forksafe
celery.conf.worker_max_tasks_per_child = 1
celery.conf.worker_concurrency = 1

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This speeds up tests, otherwise celery forks 20 times.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sounds good on the perspective of speeding up tests -- won't this have an effect on bugs and code paths surfaced by tests, though?

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

So we haven't had any bugs related to this so far and my gut feeling tells me no. There is no direct communication between the forked processes so I'd say it's unlikely, and the tests won't send in high event volumes ever anyway.

Comment thread tests/conftest.py
@request.addfinalizer
def _():
assert not in_process_events
capture_events()

@untitaker untitaker Sep 22, 2020

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Need to remove this assertion because we actually do have events in the same process now.

We need to call capture_events or otherwise our transport will raise an error (this fixture setup is overdue for refactor...)

@untitaker
untitaker merged commit 4bf4859 into master Sep 23, 2020
@untitaker
untitaker deleted the fix/celery-trace-propagation-2 branch September 23, 2020 14:33
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants