Skip to content

Commit c11504f

Browse files
timblakelyMikeRyanDev
authored andcommitted
fix(StoreDevtools): Do not send full liftedState for application actions (#790)
1 parent c8560e4 commit c11504f

File tree

1 file changed

+31
-4
lines changed

1 file changed

+31
-4
lines changed

modules/store-devtools/src/extension.ts

Lines changed: 31 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ import { takeUntil } from 'rxjs/operator/takeUntil';
1010

1111
import { STORE_DEVTOOLS_CONFIG, StoreDevtoolsConfig } from './config';
1212
import { LiftedState } from './reducer';
13+
import { PerformAction } from './actions';
1314
import { applyOperators } from './utils';
1415

1516
export const ExtensionActionTypes = {
@@ -28,11 +29,13 @@ export interface ReduxDevtoolsExtensionConnection {
2829
unsubscribe(): void;
2930
send(action: any, state: any): void;
3031
init(state?: any): void;
32+
error(any: any): void;
3133
}
3234
export interface ReduxDevtoolsExtensionConfig {
3335
features?: object | boolean;
3436
name: string | undefined;
3537
instanceId: string;
38+
maxAge?: number;
3639
}
3740

3841
export interface ReduxDevtoolsExtension {
@@ -51,6 +54,7 @@ export interface ReduxDevtoolsExtension {
5154
export class DevtoolsExtension {
5255
private instanceId = `ngrx-store-${Date.now()}`;
5356
private devtoolsExtension: ReduxDevtoolsExtension;
57+
private extensionConnection: ReduxDevtoolsExtensionConnection;
5458

5559
liftedActions$: Observable<any>;
5660
actions$: Observable<any>;
@@ -68,7 +72,26 @@ export class DevtoolsExtension {
6872
return;
6973
}
7074

71-
this.devtoolsExtension.send(null, state, this.config, this.instanceId);
75+
// Check to see if the action requires a full update of the liftedState.
76+
// If it is a simple action generated by the user's app, only send the
77+
// action and the current state (fast).
78+
//
79+
// A full liftedState update (slow: serializes the entire liftedState) is
80+
// only required when:
81+
// a) redux-devtools-extension fires the @@Init action (ignored by
82+
// @ngrx/store-devtools)
83+
// b) an action is generated by an @ngrx module (e.g. @ngrx/effects/init
84+
// or @ngrx/store/update-reducers)
85+
// c) the state has been recomputed due to time-traveling
86+
// d) any action that is not a PerformAction to err on the side of
87+
// caution.
88+
if (action instanceof PerformAction) {
89+
const currentState = state.computedStates[state.currentStateIndex].state;
90+
this.extensionConnection.send(action.action, currentState);
91+
} else {
92+
// Requires full state update;
93+
this.devtoolsExtension.send(null, state, this.config, this.instanceId);
94+
}
7295
}
7396

7497
private createChangesObservable(): Observable<any> {
@@ -77,15 +100,19 @@ export class DevtoolsExtension {
77100
}
78101

79102
return new Observable(subscriber => {
80-
const connection = this.devtoolsExtension.connect({
103+
let extensionOptions: ReduxDevtoolsExtensionConfig = {
81104
instanceId: this.instanceId,
82105
name: this.config.name,
83106
features: this.config.features,
84-
});
107+
};
108+
if (this.config.maxAge !== false /* support === 0 */) {
109+
extensionOptions.maxAge = this.config.maxAge;
110+
}
111+
const connection = this.devtoolsExtension.connect(extensionOptions);
112+
this.extensionConnection = connection;
85113
connection.init();
86114

87115
connection.subscribe((change: any) => subscriber.next(change));
88-
89116
return connection.unsubscribe;
90117
});
91118
}

0 commit comments

Comments
 (0)