@genesislcap/blank-app-seed 5.7.0-prerelease.40 → 5.7.0-prerelease.41

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@genesislcap/blank-app-seed-config",
3
3
  "description": "Genesis Blank App Seed Configuration",
4
- "version": "5.7.0-prerelease.40",
4
+ "version": "5.7.0-prerelease.41",
5
5
  "license": "Apache-2.0",
6
6
  "scripts": {
7
7
  "lint": "eslint .",
@@ -1,5 +1,5 @@
1
1
  {
2
- "UI": "14.393.3",
3
- "GSF": "8.15.0-beta3",
4
- "Auth": "8.15.0-beta3"
2
+ "UI": "14.393.4",
3
+ "GSF": "8.14.20",
4
+ "Auth": "8.14.3"
5
5
  }
package/CHANGELOG.md CHANGED
@@ -1,5 +1,14 @@
1
1
  # Changelog
2
2
 
3
+ ## [5.7.0-prerelease.41](https://github.com/genesiscommunitysuccess/blank-app-seed/compare/v5.7.0-prerelease.40...v5.7.0-prerelease.41) (2026-02-12)
4
+
5
+
6
+ ### Bug Fixes
7
+
8
+ * correct cleanup for foundation-store [FUI-0](https://github.com/genesiscommunitysuccess/blank-app-seed/issues/0) 89bd39b
9
+ * simple store configuration for notify [FUI-0](https://github.com/genesiscommunitysuccess/blank-app-seed/issues/0) f0c8786
10
+ * simple store configuration for notify [FUI-0](https://github.com/genesiscommunitysuccess/blank-app-seed/issues/0) (#548) bbdeff9
11
+
3
12
  ## [5.7.0-prerelease.40](https://github.com/genesiscommunitysuccess/blank-app-seed/compare/v5.7.0-prerelease.39...v5.7.0-prerelease.40) (2026-02-11)
4
13
 
5
14
 
@@ -5,7 +5,8 @@ import getLayoutNameByRoute from './utils/getLayoutNameByRoute';
5
5
  import type { LayoutComponentName } from './types/layout';
6
6
  import { configureFoundationAuth } from './share/foundation-auth';
7
7
  import { registerComponents } from './share/genesis-components';
8
- import { registerStylesTarget } from '../pbc/utils';
8
+ import { getStore } from './store/foundation-store';
9
+ import { customEventFactory, registerStylesTarget } from '../pbc/utils';
9
10
  {{#if FDC3.channels.length}}
10
11
  import { listenToChannel, onFDC3Ready } from './utils';
11
12
  {{/if}}
@@ -15,9 +16,10 @@ import { listenToChannel, onFDC3Ready } from './utils';
15
16
  templateUrl: './app.component.html',
16
17
  styleUrl: './app.component.css',
17
18
  })
18
- export class AppComponent implements OnInit, AfterViewInit {
19
+ export class AppComponent implements OnInit, OnDestroy, AfterViewInit {
19
20
  layoutName?: LayoutComponentName;
20
21
  title = '{{capitalCase appName}}';
22
+ store = getStore();
21
23
 
22
24
  // @ts-ignore
23
25
  @Connect connect: Connect;
@@ -38,15 +40,43 @@ export class AppComponent implements OnInit, AfterViewInit {
38
40
  }
39
41
 
40
42
  ngOnInit() {
43
+ this.addEventListeners();
44
+ this.readyStore();
41
45
  registerStylesTarget(this.el.nativeElement, 'main');
42
46
  this.loadRemotes();
43
47
  }
44
48
 
49
+ ngOnDestroy() {
50
+ this.removeEventListeners();
51
+ this.disconnectStore();
52
+ }
45
53
 
46
54
  async loadRemotes() {
47
55
  await registerComponents();
48
56
  }
49
57
 
58
+ addEventListeners() {
59
+ this.el.nativeElement.addEventListener('store-connected', this.store.onConnected);
60
+ }
61
+
62
+ removeEventListeners() {
63
+ this.el.nativeElement.removeEventListener('store-connected', this.store.onConnected);
64
+ }
65
+
66
+ readyStore() {
67
+ this.dispatchCustomEvent('store-connected', this.el.nativeElement);
68
+ this.dispatchCustomEvent('store-ready', true);
69
+ }
70
+
71
+ disconnectStore() {
72
+ this.dispatchCustomEvent('store-disconnected');
73
+ }
74
+
75
+ dispatchCustomEvent(type: string, detail?: any) {
76
+ this.el.nativeElement.dispatchEvent(customEventFactory(type, detail));
77
+ }
78
+
79
+
50
80
  ngAfterViewInit() {
51
81
  {{#if FDC3.channels.length}}
52
82
  onFDC3Ready(this.FDC3ReadyHandler);
@@ -0,0 +1,34 @@
1
+ import { CustomEventMap } from '@genesislcap/foundation-events';
2
+ import { getApp } from '@genesislcap/foundation-shell/app';
3
+ import {
4
+ AbstractStoreRoot,
5
+ registerStore,
6
+ StoreRoot,
7
+ StoreRootEventDetailMap,
8
+ } from '@genesislcap/foundation-store';
9
+ import { DI } from '@genesislcap/web-core';
10
+
11
+ export interface Store extends StoreRoot {}
12
+
13
+ export type StoreEventDetailMap = StoreRootEventDetailMap & {};
14
+
15
+ declare global {
16
+ interface HTMLElementEventMap extends CustomEventMap<StoreEventDetailMap> {}
17
+ }
18
+
19
+ class DefaultStore extends AbstractStoreRoot<Store, StoreEventDetailMap> implements Store {
20
+ constructor() {
21
+ super();
22
+
23
+ /**
24
+ * Register the store root
25
+ */
26
+ getApp().registerStoreRoot(this);
27
+ }
28
+ }
29
+
30
+ export const Store = registerStore(DefaultStore, 'Store');
31
+
32
+ export function getStore(): Store {
33
+ return DI.getOrCreateDOMContainer().get(Store) as Store;
34
+ }
@@ -1,4 +1,4 @@
1
- import { useEffect, useState } from 'react';
1
+ import { useCallback, useEffect, useState } from 'react';
2
2
  import { BrowserRouter as Router } from 'react-router-dom';
3
3
  import {
4
4
  setApiHost,
@@ -12,7 +12,6 @@ import { RoutesProvider } from './store/RoutesContext';
12
12
  import { registerComponents as genesisRegisterComponents } from './share/genesis-components';
13
13
  import { storeService } from './services/store.service';
14
14
  import AppRoutes from './components/routes/AppRoutes';
15
- import NotFoundPage from "@/pages/NotFoundPage/NotFoundPage.tsx";
16
15
  import { reduxStore } from './store/store';
17
16
  import { Provider } from 'react-redux';
18
17
 
@@ -32,15 +31,14 @@ const App: React.FC<AppProps> = ({ rootElement }) => {
32
31
  {{/each}}
33
32
  };
34
33
  {{/if}}
35
- const [isStoreConnected, setIsStoreConnected] = useState(false);
36
34
  const [componentsReady, setComponentsReady] = useState(false);
37
- const dispatchCustomEvent = (type: string, detail?: any) => {
35
+ const dispatchCustomEvent = useCallback((type: string, detail?: unknown) => {
38
36
  rootElement.dispatchEvent(customEventFactory(type, detail));
39
- };
37
+ }, [rootElement]);
40
38
 
41
- const handleStoreConnected = (event: CustomEvent) => {
39
+ const handleStoreConnected = useCallback((event: CustomEvent) => {
42
40
  storeService.onConnected(event);
43
- };
41
+ }, []);
44
42
  useEffect(() => {
45
43
  let mounted = true;
46
44
  setApiHost();
@@ -57,24 +55,21 @@ const App: React.FC<AppProps> = ({ rootElement }) => {
57
55
 
58
56
  useEffect(() => {
59
57
  registerStylesTarget(document.body, 'main');
60
- if (!isStoreConnected) {
61
- rootElement.addEventListener('store-connected', handleStoreConnected);
62
- dispatchCustomEvent('store-connected', rootElement);
63
- dispatchCustomEvent('store-ready', true);
64
- setIsStoreConnected(true);
65
- }
58
+ rootElement.addEventListener('store-connected', handleStoreConnected as EventListener);
59
+ dispatchCustomEvent('store-connected', rootElement);
60
+ dispatchCustomEvent('store-ready', true);
66
61
 
67
62
  return () => {
68
- if (isStoreConnected) {
69
- rootElement.removeEventListener('store-connected', handleStoreConnected);
70
- dispatchCustomEvent('store-disconnected');
71
- }
63
+ rootElement.removeEventListener(
64
+ 'store-connected',
65
+ handleStoreConnected as EventListener,
66
+ );
72
67
  };
73
68
  {{#if FDC3.channels.length~}}
74
69
  onFDC3Ready(FDC3ReadyHandler);
75
70
  {{/if}}
76
71
 
77
- }, [isStoreConnected]);
72
+ }, [rootElement, handleStoreConnected, dispatchCustomEvent]);
78
73
 
79
74
  const baseElement = document.querySelector('base');
80
75
  const basePath = baseElement?.getAttribute('href') || '';
@@ -1,8 +1,9 @@
1
1
  import { getApp } from '@genesislcap/foundation-shell/app';
2
2
  import type { FoundationRouter } from '@genesislcap/foundation-ui';
3
3
  import { css, GenesisElementLayout, html } from '@genesislcap/web-core';
4
+ import type { Store } from '../store/foundation-store';
4
5
 
5
- type ClientAppRouter = FoundationRouter;
6
+ type ClientAppRouter = FoundationRouter & { store: Store };
6
7
 
7
8
  const app = getApp();
8
9
 
@@ -18,5 +18,6 @@ export const MainTemplate: ViewTemplate<MainApplication> = html`
18
18
  <foundation-router
19
19
  @luminance-icon-clicked=${(x) => x.onDarkModeToggle()}
20
20
  :config=${(x) => x.config}
21
+ :store=${(x) => x.store}
21
22
  ></foundation-router>
22
23
  `;
@@ -1,4 +1,5 @@
1
1
  import { Connect, ConnectConfig, defaultConnectConfig } from '@genesislcap/foundation-comms';
2
+ import { EventEmitter } from '@genesislcap/foundation-events';
2
3
  import { App } from '@genesislcap/foundation-shell/app';
3
4
  import { importPBCAssets } from '@genesislcap/foundation-shell/pbc';
4
5
  import { configureDesignSystem } from '@genesislcap/foundation-ui';
@@ -16,6 +17,7 @@ import {
16
17
  } from '@genesislcap/web-core';
17
18
  import * as Components from '../components';
18
19
  import { MainRouterConfig } from '../routes';
20
+ import { Store, StoreEventDetailMap } from '../store/foundation-store';
19
21
  import designTokens from '../styles/design-tokens.json';
20
22
  {{#if FDC3.channels.length}}
21
23
  import { listenToChannel, onFDC3Ready } from '../utils';
@@ -25,15 +27,20 @@ import { DynamicTemplate as template, LoadingTemplate, MainTemplate } from './ma
25
27
 
26
28
  const name = '{{rootElement}}';
27
29
 
30
+ /**
31
+ * @fires store-connected - Fired when the store is connected.
32
+ * @fires store-ready - Fired when the store is ready.
33
+ */
28
34
  @customElement({
29
35
  name,
30
36
  template,
31
37
  styles,
32
38
  })
33
- export class MainApplication extends GenesisElement {
39
+ export class MainApplication extends EventEmitter<StoreEventDetailMap>(GenesisElement) {
34
40
  @App app: App;
35
41
  @Connect connect!: Connect;
36
42
  @Container container!: Container;
43
+ @Store store: Store;
37
44
 
38
45
  @inject(MainRouterConfig) config!: MainRouterConfig;
39
46
 
@@ -44,6 +51,8 @@ export class MainApplication extends GenesisElement {
44
51
  async connectedCallback() {
45
52
  this.registerDIDependencies();
46
53
  super.connectedCallback();
54
+ this.addEventListeners();
55
+ this.readyStore();
47
56
  await this.loadPBCs();
48
57
  await this.loadRemotes();
49
58
  {{#if FDC3.channels.length}}
@@ -54,6 +63,12 @@ export class MainApplication extends GenesisElement {
54
63
  });
55
64
  }
56
65
 
66
+ disconnectedCallback() {
67
+ super.disconnectedCallback();
68
+ this.removeEventListeners();
69
+ this.disconnectStore();
70
+ }
71
+
57
72
  onDarkModeToggle() {
58
73
  baseLayerLuminance.setValueFor(
59
74
  this.provider,
@@ -130,4 +145,22 @@ export class MainApplication extends GenesisElement {
130
145
  */
131
146
  );
132
147
  }
148
+
149
+ protected addEventListeners() {
150
+ this.addEventListener('store-connected', this.store.onConnected);
151
+ }
152
+
153
+ protected removeEventListeners() {
154
+ this.removeEventListener('store-connected', this.store.onConnected);
155
+ }
156
+
157
+ protected readyStore() {
158
+ // @ts-ignore
159
+ this.$emit('store-connected', this);
160
+ this.$emit('store-ready', true);
161
+ }
162
+
163
+ protected disconnectStore() {
164
+ this.$emit('store-disconnected');
165
+ }
133
166
  }
@@ -0,0 +1,29 @@
1
+ import { CustomEventMap } from '@genesislcap/foundation-events';
2
+ import { getApp } from '@genesislcap/foundation-shell/app';
3
+ import {
4
+ AbstractStoreRoot,
5
+ registerStore,
6
+ StoreRoot,
7
+ StoreRootEventDetailMap,
8
+ } from '@genesislcap/foundation-store';
9
+
10
+ export interface Store extends StoreRoot {}
11
+
12
+ export type StoreEventDetailMap = StoreRootEventDetailMap & {};
13
+
14
+ declare global {
15
+ interface HTMLElementEventMap extends CustomEventMap<StoreEventDetailMap> {}
16
+ }
17
+
18
+ class DefaultStore extends AbstractStoreRoot<Store, StoreEventDetailMap> implements Store {
19
+ constructor() {
20
+ super();
21
+
22
+ /**
23
+ * Register the store root
24
+ */
25
+ getApp().registerStoreRoot(this);
26
+ }
27
+ }
28
+
29
+ export const Store = registerStore(DefaultStore, 'Store');
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@genesislcap/blank-app-seed",
3
3
  "description": "Genesis Blank App Seed",
4
- "version": "5.7.0-prerelease.40",
4
+ "version": "5.7.0-prerelease.41",
5
5
  "license": "Apache-2.0",
6
6
  "scripts": {
7
7
  "release": "semantic-release"