@equinor/fusion-framework-module-widget 16.0.6 → 16.0.8

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,33 +0,0 @@
1
- import { FlowSubject } from '@equinor/fusion-observable';
2
-
3
- import { createReducer } from './create-reducer';
4
-
5
- import { handleFetchManifest, handleImportWidget, handleFetchConfig } from './flows';
6
-
7
- import type { Actions } from './actions';
8
- import type { WidgetState, WidgetStateInitial } from '../types';
9
- import type WidgetModuleProvider from '../WidgetModuleProvider';
10
-
11
- /**
12
- * Creates and wires the RxJS-based `FlowSubject` state machine for a single
13
- * widget.
14
- *
15
- * Attaches the manifest-fetch, script-import, and config-fetch flows to the
16
- * subject so that dispatched actions trigger the corresponding side effects.
17
- *
18
- * @param value - Initial widget state (name and optional pre-loaded data).
19
- * @param provider - The {@link WidgetModuleProvider} used by flows to query
20
- * the backend API.
21
- * @returns A `FlowSubject` managing {@link WidgetState} via {@link Actions}.
22
- */
23
- export const createState = (
24
- value: WidgetStateInitial,
25
- provider: WidgetModuleProvider,
26
- ): FlowSubject<WidgetState, Actions> => {
27
- const reducer = createReducer(value);
28
- const state = new FlowSubject<WidgetState, Actions>(reducer);
29
- state.addFlow(handleFetchManifest(provider));
30
- state.addFlow(handleImportWidget());
31
- state.addFlow(handleFetchConfig(provider));
32
- return state;
33
- };
@@ -1,123 +0,0 @@
1
- import { from, of, concat } from 'rxjs';
2
- import { catchError, filter, last, map, share, switchMap } from 'rxjs/operators';
3
-
4
- import { actions } from './actions';
5
-
6
- import type { Flow } from '@equinor/fusion-observable';
7
-
8
- import type { Actions } from './actions';
9
- import type { WidgetState } from '../types';
10
- import type WidgetModuleProvider from '../WidgetModuleProvider';
11
-
12
- /**
13
- * RxJS flow that reacts to `fetchManifest` actions by querying the
14
- * {@link WidgetModuleProvider} for the manifest, emitting intermediate
15
- * `setManifest` actions, and completing with a success or failure action.
16
- *
17
- * @param provider - The widget module provider used for API queries.
18
- * @returns A `Flow` function for the widget state machine.
19
- */
20
- export const handleFetchManifest =
21
- (provider: WidgetModuleProvider): Flow<Actions, WidgetState> =>
22
- (action$) =>
23
- // React only to `fetchManifest` actions
24
- action$.pipe(
25
- filter(actions.fetchManifest.match),
26
- switchMap((action) => {
27
- const {
28
- payload: { key, args },
29
- meta: { update },
30
- } = action;
31
-
32
- // Query the provider for the manifest, dropping falsy emissions, and share it
33
- const subject = from(provider.getWidgetManifest(key, args)).pipe(
34
- filter((x) => !!x),
35
- share(),
36
- );
37
- return (
38
- concat(
39
- subject
40
- // Emit an intermediate `setManifest` for every value the query produces
41
- .pipe(map((manifest) => actions.setManifest(manifest, update))),
42
- subject
43
- // Wait for the final emission and report it as the successful result
44
- .pipe(
45
- last(),
46
- map((manifest) => actions.fetchManifest.success(manifest)),
47
- ),
48
- )
49
- // Convert any error from the query/emission chain into a failure action
50
- .pipe(
51
- catchError((err) => {
52
- console.error(err, action.payload);
53
- return of(actions.fetchManifest.failure(err));
54
- }),
55
- )
56
- );
57
- }),
58
- );
59
-
60
- /**
61
- * RxJS flow that reacts to `fetchConfig` actions by querying the
62
- * {@link WidgetModuleProvider} for the widget config, emitting intermediate
63
- * `setConfig` actions, and completing with a success or failure action.
64
- *
65
- * @param provider - The widget module provider used for API queries.
66
- * @returns A `Flow` function for the widget state machine.
67
- */
68
- // Deliberately co-located with `handleFetchManifest` above
69
- // fusion-lint-disable-next-line single-export-per-file
70
- export const handleFetchConfig =
71
- (provider: WidgetModuleProvider): Flow<Actions, WidgetState> =>
72
- (action$) =>
73
- // React only to `fetchConfig` actions
74
- action$.pipe(
75
- filter(actions.fetchConfig.match),
76
- switchMap(({ payload: { key, args } }) => {
77
- // Query the provider for the config, dropping falsy emissions, and share it
78
- const subject = from(provider.getWidgetConfig(key, args)).pipe(
79
- filter((x) => !!x),
80
- share(),
81
- );
82
- return (
83
- concat(
84
- subject
85
- // Emit an intermediate `setConfig` for every value the query produces
86
- .pipe(map((manifest) => actions.setConfig(manifest))),
87
- subject
88
- // Wait for the final emission and report it as the successful result
89
- .pipe(
90
- last(),
91
- map((manifest) => actions.fetchConfig.success(manifest)),
92
- ),
93
- )
94
- // Convert any error from the query/emission chain into a failure action
95
- .pipe(
96
- catchError((err) => {
97
- return of(actions.fetchConfig.failure(err));
98
- }),
99
- )
100
- );
101
- }),
102
- );
103
-
104
- /**
105
- * RxJS flow that reacts to `importWidget` actions by dynamically importing
106
- * the widget’s JavaScript entry point URL and emitting success or failure.
107
- *
108
- * @returns A `Flow` function for the widget state machine.
109
- */
110
- // Deliberately co-located with the other flow handlers above
111
- // fusion-lint-disable-next-line single-export-per-file
112
- export const handleImportWidget = (): Flow<Actions, WidgetState> => (action$) =>
113
- // React only to `importWidget` actions
114
- action$.pipe(
115
- filter(actions.importWidget.match),
116
- switchMap(({ payload }) => {
117
- // Dynamically import the widget's script entry point and report success/failure
118
- return from(import(/* @vite-ignore */ payload)).pipe(
119
- map(actions.importWidget.success),
120
- catchError((err) => of(actions.importWidget.failure(err))),
121
- );
122
- }),
123
- );
package/src/types.ts DELETED
@@ -1,203 +0,0 @@
1
- import type { AnyModule, CombinedModules, ModulesInstance } from '@equinor/fusion-framework-module';
2
- import type { EventModule } from '@equinor/fusion-framework-module-event';
3
- import type { HttpModule } from '@equinor/fusion-framework-module-http';
4
- import type { ServiceDiscoveryModule } from '@equinor/fusion-framework-module-service-discovery';
5
- import type { QueryCtorOptions } from '@equinor/fusion-query';
6
-
7
- // biome-ignore lint/suspicious/noExplicitAny: `Fusion` is a placeholder widening type for the framework instance shape used across widget script modules
8
- type Fusion = any;
9
-
10
- /**
11
- * Environment descriptor passed to widget render functions.
12
- *
13
- * @template TProps - Custom props type forwarded to the widget.
14
- */
15
- export type WidgetEnv<TProps = unknown> = {
16
- /** Base URL path the widget should use for routing (if applicable). */
17
- basename?: string;
18
- /** The resolved widget manifest. */
19
- manifest?: WidgetManifest;
20
- /** Arbitrary props forwarded from the host application. */
21
- props?: TProps;
22
- };
23
-
24
- /**
25
- * HTTP client abstraction used by the widget module to fetch manifests
26
- * and configurations from the backend API.
27
- */
28
- export type IClient = {
29
- /** API version string appended as a query parameter to widget endpoints. */
30
- apiVersion: string;
31
- /** Base URL used to construct full import URLs for widget scripts. */
32
- baseImportUrl: string;
33
- /** Query constructor options for fetching a {@link WidgetManifest}. */
34
- getWidgetManifest: QueryCtorOptions<WidgetManifest, GetWidgetParameters>;
35
- /** Query constructor options for fetching a {@link WidgetConfig}. */
36
- getWidgetConfig: QueryCtorOptions<WidgetConfig, GetWidgetParameters>;
37
- };
38
-
39
- /**
40
- * Peer-dependency module tuple required by the widget module.
41
- *
42
- * Includes {@link HttpModule}, {@link ServiceDiscoveryModule}, and
43
- * {@link EventModule} (the latter two are optional at runtime).
44
- */
45
- export type ModuleDeps = [HttpModule, ServiceDiscoveryModule, EventModule];
46
-
47
- /**
48
- * Parameters for fetching a widget manifest or configuration.
49
- */
50
- export type GetWidgetParameters = {
51
- /** Unique key (name) identifying the widget. */
52
- widgetKey: string;
53
- /** Optional version or tag selector for the widget. */
54
- args?: { type: 'version' | 'tag'; value: string };
55
- };
56
-
57
- /**
58
- * Function that builds a widget API endpoint URL from {@link GetWidgetParameters}.
59
- */
60
- export type WidgetEndpointBuilder = (args: GetWidgetParameters) => string;
61
-
62
- /**
63
- * Metadata manifest describing a widget’s identity, version, and entry point.
64
- *
65
- * Fetched from the backend API during widget initialization.
66
- */
67
- export type WidgetManifest = {
68
- /** Unique backend identifier for the widget. */
69
- id: string;
70
- /** Human-readable widget name (also used as lookup key). */
71
- name: string;
72
- /** Semantic version of the widget. */
73
- version: string;
74
- /** Brief description of the widget’s purpose. */
75
- description: string;
76
- /** Optional list of maintainer identifiers. */
77
- maintainers?: string[];
78
- /** Relative path to the JavaScript entry point (e.g., `index.js`). */
79
- entryPoint: string;
80
- /** Base path for widget assets (combined with `entryPoint` to build the import URL). */
81
- assetPath: string;
82
- };
83
-
84
- /**
85
- * Describes a named endpoint with a URI and optional OAuth scopes.
86
- */
87
- export type Endpoint = {
88
- /** Endpoint name. */
89
- name: string;
90
- /** Endpoint URI. */
91
- uri: string;
92
- /** Optional OAuth scopes required for the endpoint. */
93
- scopes?: string[];
94
- };
95
-
96
- /**
97
- * Runtime configuration for a widget, including environment variables and
98
- * backend endpoint mappings.
99
- *
100
- * @template TEnvironment - Custom environment shape.
101
- */
102
- export type WidgetConfig<TEnvironment = unknown> = {
103
- /** Widget-specific environment variables. */
104
- environment: TEnvironment;
105
- /** Map of endpoint names to URIs or structured {@link Endpoint} objects. */
106
- endpoints: Record<string, string | Endpoint>;
107
- };
108
-
109
- /**
110
- * Combined module set available inside a widget, merging custom modules with
111
- * the standard {@link EventModule} and {@link ServiceDiscoveryModule}.
112
- *
113
- * @template TModules - Additional modules to combine.
114
- */
115
- export type WidgetModules<TModules extends Array<AnyModule> | unknown = unknown> = CombinedModules<
116
- TModules,
117
- [EventModule, ServiceDiscoveryModule]
118
- >;
119
-
120
- /**
121
- * Generic property bag passed from the host application to a widget render
122
- * function.
123
- */
124
- export type WidgetProps = Record<PropertyKey, unknown>;
125
-
126
- /**
127
- * Arguments passed to a widget’s render functions (`renderWidget`, `render`,
128
- * `renderIcon`, and the default export).
129
- *
130
- * @template TFusion - Fusion instance type.
131
- * @template TEnv - Environment descriptor type.
132
- * @template TProps - Custom props type.
133
- */
134
-
135
- export type WidgetRenderArgs<
136
- TFusion extends Fusion = Fusion,
137
- TEnv = WidgetEnv,
138
- TProps extends WidgetProps = WidgetProps,
139
- > = {
140
- fusion: TFusion;
141
- env: TEnv;
142
- props?: TProps;
143
- };
144
-
145
- /**
146
- * Describes the interface a widget script module must export.
147
- *
148
- * A dynamically imported widget entry point is expected to expose render
149
- * functions that mount the widget into a given DOM element and return a
150
- * cleanup function.
151
- *
152
- * @template TProps - Custom props type.
153
- */
154
- export type WidgetScriptModule<TProps extends WidgetProps = WidgetProps> = {
155
- /** Default render function (fallback entry point). */
156
- default: (el: HTMLElement, args: WidgetRenderArgs, props?: TProps) => VoidFunction;
157
- /** Primary render function for the widget body. */
158
- renderWidget: (el: HTMLElement, args: WidgetRenderArgs, props?: TProps) => VoidFunction;
159
- /** Render function for the widget’s icon representation. */
160
- renderIcon: (el: HTMLElement, args: WidgetRenderArgs, props?: TProps) => VoidFunction;
161
- /** Generic render function. */
162
- render: (el: HTMLElement, args: WidgetRenderArgs, props?: TProps) => VoidFunction;
163
- };
164
-
165
- /**
166
- * Resolved module instances available inside a running widget.
167
- *
168
- * @template TModules - Additional custom modules.
169
- */
170
- export type WidgetModulesInstance<TModules extends Array<AnyModule> | unknown = unknown> =
171
- ModulesInstance<WidgetModules<TModules>>;
172
-
173
- /**
174
- * Internal state managed by a {@link Widget}’s `FlowSubject` state machine.
175
- *
176
- * Tracks manifest, config, imported script, framework module instances, and
177
- * a set of in-flight status markers.
178
- *
179
- * @template TModules - Custom module types.
180
- */
181
- // biome-ignore lint/suspicious/noExplicitAny: default must be bivariant `any`, not `unknown` — `unknown` breaks assignability when a concrete `WidgetState<TModules>` is used where the default-typed generic is expected
182
- export type WidgetState<TModules = any> = {
183
- /** Widget name (lookup key). */
184
- name: string;
185
- /** Set of in-flight action base types (e.g., `'fetch_manifest'`). */
186
- status: Set<string>;
187
- /** Resolved widget configuration (when loaded). */
188
- config?: WidgetConfig;
189
- /** Resolved widget manifest (when loaded). */
190
- manifest?: WidgetManifest;
191
- /** Imported widget script module (when loaded). */
192
- modules?: WidgetScriptModule;
193
- /** Framework module instances created for the widget. */
194
- instance?: WidgetModulesInstance<TModules>;
195
- };
196
-
197
- /**
198
- * Initial widget state shape passed to the `Widget` constructor.
199
- *
200
- * Same as {@link WidgetState} but without the `status` set, which is
201
- * initialized internally by the reducer.
202
- */
203
- export type WidgetStateInitial = Omit<WidgetState, 'status'>;
package/src/utils.ts DELETED
@@ -1,85 +0,0 @@
1
- import type { GetWidgetParameters, IClient, WidgetEndpointBuilder } from './types';
2
- import type { IHttpClient } from '@equinor/fusion-framework-module-http';
3
-
4
- /**
5
- * Creates a {@link WidgetEndpointBuilder} that produces manifest endpoint URLs.
6
- *
7
- * Routes versioned or tagged lookups to `/widgets/{key}/versions/{value}` and
8
- * unversioned lookups to `/widgets/{key}`.
9
- *
10
- * @param apiVersion - API version string appended as a query parameter.
11
- * @returns A function that maps {@link GetWidgetParameters} to a URL path.
12
- */
13
- export const defaultManifestEndpointBuilder =
14
- (apiVersion: string): WidgetEndpointBuilder =>
15
- (params: GetWidgetParameters) => {
16
- const { widgetKey, args } = params;
17
- const { type, value } = args ?? {};
18
- // Route versioned/tagged lookups differently from the unversioned default
19
- switch (type) {
20
- case 'tag':
21
- case 'version':
22
- return `/widgets/${widgetKey}/versions/${value}?api-version=${apiVersion}`;
23
- default:
24
- return `/widgets/${widgetKey}?api-version=${apiVersion}`;
25
- }
26
- };
27
-
28
- /**
29
- * Creates a {@link WidgetEndpointBuilder} that produces config endpoint URLs.
30
- *
31
- * Routes versioned or tagged lookups to `/widgets/{key}/versions/{value}/config`
32
- * and unversioned lookups to `/widgets/{key}/config`.
33
- *
34
- * @param apiVersion - API version string appended as a query parameter.
35
- * @returns A function that maps {@link GetWidgetParameters} to a URL path.
36
- */
37
- // Deliberately co-located with `defaultManifestEndpointBuilder` above
38
- // fusion-lint-disable-next-line single-export-per-file
39
- export const defaultConfigEndpointBuilder =
40
- (apiVersion: string): WidgetEndpointBuilder =>
41
- (params: GetWidgetParameters) => {
42
- const { widgetKey, args } = params;
43
- const { type, value } = args ?? {};
44
- // TODO(#5099): Align endpoints with backend when its done!
45
- switch (type) {
46
- case 'tag':
47
- case 'version':
48
- return `/widgets/${widgetKey}/versions/${value}/config?api-version=${apiVersion}`;
49
- default:
50
- return `/widgets/${widgetKey}/config?api-version=${apiVersion}`;
51
- }
52
- };
53
-
54
- /**
55
- * Creates the default {@link IClient} that uses the given HTTP client to
56
- * fetch widget manifests and configurations.
57
- *
58
- * Uses `api-version=1.0-preview` and the default manifest/config endpoint
59
- * builders.
60
- *
61
- * @param httpClient - An `IHttpClient` instance (typically resolved from the
62
- * `apps` service-discovery key).
63
- * @returns A fully configured `IClient`.
64
- */
65
- // Deliberately co-located with the endpoint builders it composes
66
- // fusion-lint-disable-next-line single-export-per-file
67
- export const createDefaultClient = (httpClient: IHttpClient): IClient => {
68
- const apiVersion = '1.0-preview';
69
- return {
70
- apiVersion,
71
- baseImportUrl: httpClient.uri,
72
- getWidgetManifest: {
73
- client: {
74
- fn: (args) => httpClient.json$(defaultManifestEndpointBuilder(apiVersion)(args)),
75
- },
76
- key: (args) => JSON.stringify(args),
77
- },
78
- getWidgetConfig: {
79
- client: {
80
- fn: (args) => httpClient.json$(defaultConfigEndpointBuilder(apiVersion)(args)),
81
- },
82
- key: (args) => JSON.stringify(args),
83
- },
84
- };
85
- };
package/src/version.ts DELETED
@@ -1,2 +0,0 @@
1
- // Generated by genversion.
2
- export const version = '16.0.6';
package/tsconfig.json DELETED
@@ -1,25 +0,0 @@
1
- {
2
- "extends": "../../../tsconfig.base.json",
3
- "compilerOptions": {
4
- "outDir": "dist/esm",
5
- "rootDir": "src",
6
- "declarationDir": "./dist/types",
7
- "removeComments": false
8
- },
9
- "references": [
10
- {
11
- "path": "../../utils/query"
12
- },
13
- {
14
- "path": "../module"
15
- },
16
- {
17
- "path": "../event"
18
- },
19
- {
20
- "path": "../service-discovery"
21
- }
22
- ],
23
- "include": ["src/**/*"],
24
- "exclude": ["node_modules", "lib"]
25
- }