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

Make pushing a new scope atomic. #364

Closed
kodhi-tech-lead opened this issue May 5, 2024 · 21 comments
Closed

Make pushing a new scope atomic. #364

kodhi-tech-lead opened this issue May 5, 2024 · 21 comments
Labels
enhancement New feature or request

Comments

@kodhi-tech-lead
Copy link

kodhi-tech-lead commented May 5, 2024

When pushNewScope is called with the init function provided, throw an exception if there is an attempt to push another scope during the execution of init. This is useful when delegating to individual sub-modules the registration of objects to a scope defined/controlled by the parent.

Thank you.

@escamoteur escamoteur added the enhancement New feature or request label May 7, 2024
@escamoteur
Copy link
Collaborator

sounds like an absolute reasonable request. will implement in the next release

@kodhi-tech-lead
Copy link
Author

Thank you.

@escamoteur
Copy link
Collaborator

done in upcoming V8

@kuhnroyal
Copy link
Contributor

I added a comment to the commit here: afa6dd3#r147433011

But adding here as well for easier tracking:

If there is an error thrown during scope push, the _pushScopeInProgress variable needs to be reset to false. Right now it is possible to lock the whole instance if there is an error thrown and never get it working again.
Maybe additionally reset the flag in reset()?

@escamoteur
Copy link
Collaborator

I didn't know that is is possible to add a comment to any commit. Interesting.
That opens another question, what would be the correct behavior in case the the init call throws?
Remove the scope again? Can the app get into any stable state in that case at all?

@kuhnroyal
Copy link
Contributor

I didn't know that is is possible to add a comment to any commit. Interesting. That opens another question, what would be the correct behavior in case the the init call throws? Remove the scope again? Can the app get into any stable state in that case at all?

That is a great question and I am not sure that there is an easy answer.
The only thing that is clear to me, is that a reset should clear the flag.

@escamoteur
Copy link
Collaborator

Where would you call the reset then? Or is it just to make sure not all tests fail after a failed pushScope?

@kuhnroyal
Copy link
Contributor

Yes, I noticed this in a failing test case, so this is a use case.
But I can also imagine showing some kind of error page and a "Try again" button that resets everything.

@escamoteur
Copy link
Collaborator

If we see the pushing of a new scope as something that consists of creating the new scope but also the successful finish of the init function, the correct behavior is probably to remove the scope and throw an error

@kuhnroyal
Copy link
Contributor

Remove the scope again?

After thinking about this for a couple minutes, I think this is the best approach. Removing the scope and all its registrations.
For my usage, I push new scopes for different navigator routes. If the scope push fails, I can deny the navigation and allow the user to try again or do whatever. At least the app is in some semi-predictable state.

If it is left as is, it is not predictable at all.

@escamoteur
Copy link
Collaborator

does this look good?

    _pushScopeInProgress = true;
    _scopes.add(_Scope(name: scopeName, disposeFunc: dispose));
    try {
      init?.call(this);
      if (isFinal) {
        _scopes.last.isFinal = true;
      }
      onScopeChanged?.call(true);
    } catch (e) {
      final failedScope = _scopes.last;

      /// prevend any new registrations in this scope
      failedScope.isFinal = true;
      failedScope.reset(dispose: true);
      _scopes.removeLast();
      rethrow;
    }
    finally {
      _pushScopeInProgress = false;
    }

@kuhnroyal
Copy link
Contributor

I think so!

@kuhnroyal
Copy link
Contributor

If you want, I can create a PR and add a test

@escamoteur
Copy link
Collaborator

let me push my change and please, add a test, that would be awesome

@escamoteur
Copy link
Collaborator

pushed

@kuhnroyal
Copy link
Contributor

@escamoteur I create a PR with the tests and also 2 other PRs with small improvements.

@kuhnroyal
Copy link
Contributor

@escamoteur Is there anything missing to get my PRs merged and this fix possibly released?

@escamoteur
Copy link
Collaborator

escamoteur commented Oct 21, 2024 via email

@escamoteur
Copy link
Collaborator

merged and published V8.0.1 thanks a lot

@kuhnroyal
Copy link
Contributor

Thanks!

@escamoteur
Copy link
Collaborator

escamoteur commented Oct 22, 2024 via email

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
enhancement New feature or request
Projects
None yet
Development

No branches or pull requests

3 participants