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

Deprecate SubscriptionDisposable #2788

Open
wants to merge 1 commit into
base: master
Choose a base branch
from

Conversation

Nateowami
Copy link
Collaborator

@Nateowami Nateowami commented Oct 9, 2024

This change is Reviewable

Copy link

codecov bot commented Oct 9, 2024

Codecov Report

All modified and coverable lines are covered by tests ✅

Project coverage is 79.08%. Comparing base (4b12097) to head (3f46d27).
Report is 20 commits behind head on master.

Additional details and impacted files
@@            Coverage Diff             @@
##           master    #2788      +/-   ##
==========================================
- Coverage   79.08%   79.08%   -0.01%     
==========================================
  Files         526      526              
  Lines       30622    30622              
  Branches     5005     5000       -5     
==========================================
- Hits        24218    24217       -1     
+ Misses       5633     5621      -12     
- Partials      771      784      +13     

☔ View full report in Codecov by Sentry.
📢 Have feedback on the report? Share it here.

Copy link
Collaborator

@RaymondLuong3 RaymondLuong3 left a comment

Choose a reason for hiding this comment

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

Could we not update the subscription disposable class? Using the DestroyRef makes sense, but having the subscription handling logic in one superclass also makes sense. In SubscriptionDisposible, instead of listening to ngOnDestroy, we can listen to destroyRef.onDestroy. What did you have in mind?

Reviewed 1 of 1 files at r1, all commit messages.
Reviewable status: :shipit: complete! all files reviewed, all discussions resolved (waiting on @Nateowami)

Copy link
Collaborator

@marksvc marksvc left a comment

Choose a reason for hiding this comment

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

@Nateowami , I don't see examples in our codebase of how we might go about this.

It looks like we might do this by (1) injecting DestroyRef in a constructor:

constructor(
    ...
    private readonly destroyRef: DestroyRef,

And then (2) registering a Subscription's unsubscribe() method with DestroyRef.onDestroy() like so:

const subscription = this.questionDoc.remoteChanges$.subscribe(() => {});
this.destroyRef.onDestroy(() \=> {
    subscription.unsubscribe();
});

Is this what you are thinking regarding using DestroyRef.onDestroy to unsubscribe?

Reviewable status: :shipit: complete! all files reviewed, all discussions resolved (waiting on @Nateowami)

@Nateowami
Copy link
Collaborator Author

@marksvc Search for takeUntilDestroyed(this.destroyRef)

Copy link
Collaborator

@marksvc marksvc left a comment

Choose a reason for hiding this comment

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

@Nateowami Thank you. Okay, that doesn't look too bad. So in my code above, it looks like my second part would instead be written as

this.questionDoc.remoteChanges$
    .pipe(takeUntilDestroyed(this.destroyRef))
    .subscribe(() => {});

Reviewable status: :shipit: complete! all files reviewed, all discussions resolved (waiting on @Nateowami)

@kylebuss kylebuss assigned kylebuss and unassigned kylebuss Oct 16, 2024
Copy link
Collaborator

@marksvc marksvc left a comment

Choose a reason for hiding this comment

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

Hey guys. Thanks for your consideration of what is going to be a good design for the system. @Nateowami , when you have a moment, I think the conversation looks to be waiting for you to respond to a question from @RaymondLuong3 .

I haven't researched enough on the topic to be sure, but if Angular+RxJS is moving to using .pipe(takeUntilDestroyed(this.destroyRef)) as a normal way of causing an unsubscribe when a component/etc is destroyed, I would be interested in using that normal practice in our codebase as well (at least for newly written code).

Reviewable status: :shipit: complete! all files reviewed, all discussions resolved (waiting on @Nateowami)

@Nateowami
Copy link
Collaborator Author

Actually, I just looked at the documentation for takeUntilDestroyed, and the DestroyRef is optional, as it can automatically inject it in most contexts:

/**
 * Operator which completes the Observable when the calling context (component, directive, service,
 * etc) is destroyed.
 *
 * @param destroyRef optionally, the `DestroyRef` representing the current context. This can be
 *     passed explicitly to use `takeUntilDestroyed` outside of an [injection
 * context](guide/dependency-injection-context). Otherwise, the current `DestroyRef` is injected.
 *
 * @developerPreview
 */
export declare function takeUntilDestroyed<T>(destroyRef?: DestroyRef): MonoTypeOperatorFunction<T>;

I also think that there are serious disadvantages to the current approach. Inheritance is often ugly and can cause issues. See #566 and #2754, two separate instances where I've had to fix it not being implemented correctly.

@Nateowami
Copy link
Collaborator Author

Actually, I think I somewhat misunderstood the documentation. If you try to remove it, you end up with this error:

NG0203: takeUntilDestroyed() can only be used within an injection context such as a constructor, a factory function, a field initializer, or a function used with runInInjectionContext. Find more at https://angular.io/errors/NG0203

So in most cases you really do need to pass a DestroyRef.

Copy link
Collaborator

@marksvc marksvc left a comment

Choose a reason for hiding this comment

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

I tried removing it from a couple places yesterday and got an error as well. I was hoping we could simplify it that much further, as well :)

Reviewable status: :shipit: complete! all files reviewed, all discussions resolved (waiting on @Nateowami)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants