Skip to content

Observer memory leak #15049

Closed
Closed
@jakubnavratil

Description

@jakubnavratil

What is the expected behavior?

Multiple subscriptions to same media query string should normally unsubscibe.

What is the current behavior?

Multiple subscriptions to same media query string causes memory leak, because only last of them can be GC. Component which wasn't last to subscribe isn't properly gcied and as result, whole component tree is kept in memory with all its data and detached nodes. In my application, this was causing massive memory leaks.

https://github.com/angular/material2/blob/e136fc8707ec3278ba32659e4d77ff21eed6de73/src/cdk/layout/breakpoints-observer.ts#L114
In this code, we are saving listener to closure scoped variable queryListener, which is rewritten upon next subscripion as we are trying reuse observables with _queries Map.

Solutions is not to use scoped variable but rather return queryListener inside addHandler function of fromEventPattern. Then we can this passed reference use inside removeHandler as second parametr and used it to call mql.removeListener.

(listener: Function) => {
    const queryListener = (e: any) => this.zone.run(() => listener(e));
    mql.addListener(queryListener);
    return queryListener;
},
(listener, queryListener) => mql.removeListener(queryListener))

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions