Skip to content

Commit

Permalink
fix: improve deinit logic and flow
Browse files Browse the repository at this point in the history
  • Loading branch information
moughxyz committed Feb 9, 2022
1 parent 1dd7036 commit e43c8a6
Show file tree
Hide file tree
Showing 6 changed files with 81 additions and 50 deletions.
61 changes: 37 additions & 24 deletions app/assets/javascripts/components/ApplicationView.tsx
Expand Up @@ -196,10 +196,17 @@ export class ApplicationView extends PureComponent<Props, State> {
};

render() {
if (this.application['dealloced'] === true) {
console.error('Attempting to render dealloced application');
return <div></div>;
}

const renderAppContents = !this.state.needsUnlock && this.state.launched;

return (
<PremiumModalProvider state={this.appState.features}>
<PremiumModalProvider state={this.appState?.features}>
<div className={this.platformString + ' main-ui-view sn-component'}>
{!this.state.needsUnlock && this.state.launched && (
{renderAppContents && (
<div
id="app"
className={this.state.appClass + ' app app-column-container'}
Expand All @@ -215,22 +222,24 @@ export class ApplicationView extends PureComponent<Props, State> {
</div>
)}

{!this.state.needsUnlock && this.state.launched && (
<Footer
application={this.application}
applicationGroup={this.props.mainApplicationGroup}
/>
)}
{renderAppContents && (
<>
<Footer
application={this.application}
applicationGroup={this.props.mainApplicationGroup}
/>

<SessionsModal
application={this.application}
appState={this.appState}
/>
<SessionsModal
application={this.application}
appState={this.appState}
/>

<PreferencesViewWrapper
appState={this.appState}
application={this.application}
/>
<PreferencesViewWrapper
appState={this.appState}
application={this.application}
/>
</>
)}

{this.state.challenges.map((challenge) => {
return (
Expand All @@ -245,15 +254,19 @@ export class ApplicationView extends PureComponent<Props, State> {
);
})}

<NotesContextMenu
application={this.application}
appState={this.appState}
/>
{renderAppContents && (
<>
<NotesContextMenu
application={this.application}
appState={this.appState}
/>

<PurchaseFlowWrapper
application={this.application}
appState={this.appState}
/>
<PurchaseFlowWrapper
application={this.application}
appState={this.appState}
/>
</>
)}
</div>
</PremiumModalProvider>
);
Expand Down
@@ -1,7 +1,7 @@
import { FeaturesState } from '@/ui_models/app_state/features_state';
import { observer } from 'mobx-react-lite';
import { FunctionalComponent } from 'preact';
import { useCallback, useContext, useState } from 'preact/hooks';
import { useContext } from 'preact/hooks';
import { createContext } from 'react';
import { PremiumFeaturesModal } from '../PremiumFeaturesModal';

Expand Down
24 changes: 22 additions & 2 deletions app/assets/javascripts/ui_models/app_state/app_state.ts
Expand Up @@ -93,7 +93,6 @@ export class AppState {

private readonly tagChangedDisposer: IReactionDisposer;

/* @ngInject */
constructor(application: WebApplication, private bridge: Bridge) {
this.application = application;
this.notes = new NotesState(
Expand Down Expand Up @@ -171,18 +170,39 @@ export class AppState {
storage.remove(StorageKey.ShowBetaWarning);
this.noAccountWarning.reset();
}
(this.application as unknown) = undefined;
this.actionsMenu.reset();
this.unsubApp?.();
this.unsubApp = undefined;
this.observers.length = 0;

this.appEventObserverRemovers.forEach((remover) => remover());
this.features.deinit();
this.appEventObserverRemovers.length = 0;

this.features.deinit();
(this.features as unknown) = undefined;

this.webAppEventDisposer?.();
this.webAppEventDisposer = undefined;

(this.quickSettingsMenu as unknown) = undefined;
(this.accountMenu as unknown) = undefined;
(this.actionsMenu as unknown) = undefined;
(this.preferences as unknown) = undefined;
(this.purchaseFlow as unknown) = undefined;
(this.noteTags as unknown) = undefined;
(this.sync as unknown) = undefined;
(this.searchOptions as unknown) = undefined;
(this.notes as unknown) = undefined;
(this.features as unknown) = undefined;
(this.tags as unknown) = undefined;
(this.notesView as unknown) = undefined;

document.removeEventListener('visibilitychange', this.onVisibilityChange);
this.onVisibilityChange = undefined;

this.tagChangedDisposer();
(this.tagChangedDisposer as unknown) = undefined;
}

openSessionsModal(): void {
Expand Down
34 changes: 16 additions & 18 deletions app/assets/javascripts/ui_models/application.ts
Expand Up @@ -39,8 +39,8 @@ export type WebEventObserver = (event: WebAppEvent) => void;

export class WebApplication extends SNApplication {
private webServices!: WebServices;
public noteControllerGroup: NoteGroupController;
private webEventObservers: WebEventObserver[] = [];
public noteControllerGroup: NoteGroupController;
public iconsController: IconsController;

constructor(
Expand Down Expand Up @@ -70,28 +70,26 @@ export class WebApplication extends SNApplication {
this.iconsController = new IconsController();
}

/** @override */
deinit(source: DeinitSource): void {
for (const service of Object.values(this.webServices)) {
if ('deinit' in service) {
service.deinit?.(source);
super.deinit(source);
try {
for (const service of Object.values(this.webServices)) {
if ('deinit' in service) {
service.deinit?.(source);
}
(service as any).application = undefined;
}
(service as any).application = undefined;
}
this.webServices = {} as WebServices;
this.noteControllerGroup.deinit();
this.iconsController.deinit();
this.webEventObservers.length = 0;
/**
* Allow any pending renders to complete before destroying the global
* application instance and all its services
*/
setTimeout(() => {
super.deinit(source);
this.webServices = {} as WebServices;
this.noteControllerGroup.deinit();
this.iconsController.deinit();
this.webEventObservers.length = 0;

if (source === DeinitSource.SignOut) {
this.bridge.onSignOut();
}
}, 0);
} catch (error) {
console.error('Error while deiniting application', error);
}
}

setWebServices(services: WebServices): void {
Expand Down
2 changes: 1 addition & 1 deletion package.json
Expand Up @@ -84,7 +84,7 @@
"@reach/tooltip": "^0.16.2",
"@standardnotes/components": "1.7.0",
"@standardnotes/features": "1.29.0",
"@standardnotes/snjs": "2.52.1",
"@standardnotes/snjs": "2.52.2",
"@standardnotes/settings": "^1.11.3",
"@standardnotes/sncrypto-web": "1.6.2",
"mobx": "^6.3.5",
Expand Down
8 changes: 4 additions & 4 deletions yarn.lock
Expand Up @@ -2650,10 +2650,10 @@
buffer "^6.0.3"
libsodium-wrappers "^0.7.9"

"@standardnotes/snjs@2.52.1":
version "2.52.1"
resolved "https://registry.yarnpkg.com/@standardnotes/snjs/-/snjs-2.52.1.tgz#00e2e1f7eaeef2c95b6830470031496e48ff4b83"
integrity sha512-U35dangXmhl1uEnPcDmWrRlqHyT/N5KIE5izT8w0xkhrWpc5a62j+m0u2uJNYU7C00d6ERqVWXeHCDsdSXTx8A==
"@standardnotes/snjs@2.52.2":
version "2.52.2"
resolved "https://registry.yarnpkg.com/@standardnotes/snjs/-/snjs-2.52.2.tgz#34d1edd3028aa860648548292291d6ecf8666a5f"
integrity sha512-5w2RXSquTmyYNSyKgEYqmLLqbHyYCsyrqfWlL0nuQ//hBFcf8OUbsY+Ys132TodpGZn637Al+kygoZxGBVcSyA==
dependencies:
"@standardnotes/auth" "^3.15.4"
"@standardnotes/common" "^1.9.0"
Expand Down

0 comments on commit e43c8a6

Please sign in to comment.