Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Data manager's should_retry did not get called #8

Merged
merged 1 commit into from
Feb 12, 2013
Merged

Data manager's should_retry did not get called #8

merged 1 commit into from
Feb 12, 2013

Conversation

sirn
Copy link
Contributor

@sirn sirn commented Jan 21, 2013

I'm trying to use tm.attempts to automatically retry a query in case of exception and found that zone.sqlalchemy.SessionDataManager.should_retry did not get called at all in pyramid_tm. I've tried debugging the problem and found these lines as culprit:

try:
    manager.abort()
    retryable = manager._retryable(*exc_info[:-1])

As far as I understand, this is related to how manager._retryable works:

  1. manager._retryable will get a list of data manager instances via manager.get()._resources and call that data manager's should_retry. (1):

    for dm in self.get()._resources:
        should_retry = getattr(dm, 'should_retry', None)
        if (should_retry is not None) and should_retry(error):
            return True
  2. However calling manager.abort() will empty the manager.get()._resources.

  3. Since manager._retryable is called after abort in pyramid_tm, it will try to iterate over an empty list and no data manager's should_retry gets called at all. 😢 (2):

    try:
        manager.abort()
        retryable = manager._retryable(*exc_info[:-1])
        if (number <= 0) or (not retryable):
            reraise(*exc_info)

This patch simply reversing these two lines since real Attempt in transaction.manager also has it reversed (3):

def _retry_or_raise(self, t, v, tb):
    retry = self.manager._retryable(t, v)
    self.manager.abort()
    if retry:

I'm not quite sure how to write a test for this one, so I added active to DummyTransaction to simulate data manager's presenceness to ensure _retryable is only returned if there's active data manager (tests properly failing after I swapped two lines in __init__.py back).

Thanks raydeo in #pyramid for helping me tracking this down! 👍

Since manager._retryable rely on manager.get()._resources to not be
empty, which is cleared after abort() is called. Unless these two lines
are reversed, data manager's should_retry won't get called at all.
mmerickel added a commit that referenced this pull request Feb 12, 2013
Data manager's should_retry did not get called
@mmerickel mmerickel merged commit e8fc3cf into Pylons:master Feb 12, 2013
@mmerickel
Copy link
Member

thanks for this

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.

2 participants