teraprox-core-sdk 0.2.0 → 0.3.2
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.
- package/dist/chunk-PATJPPYP.mjs +318 -0
- package/dist/dev.d.mts +39 -0
- package/dist/dev.d.ts +39 -0
- package/dist/dev.js +470 -0
- package/dist/dev.mjs +442 -0
- package/dist/federation-B4ShfmDd.d.mts +259 -0
- package/dist/federation-B4ShfmDd.d.ts +259 -0
- package/dist/federation.d.mts +3 -0
- package/dist/federation.d.ts +3 -0
- package/dist/federation.js +358 -0
- package/dist/federation.mjs +12 -0
- package/dist/index.d.mts +115 -56
- package/dist/index.d.ts +115 -56
- package/dist/index.js +670 -38
- package/dist/index.mjs +341 -40
- package/package.json +18 -3
|
@@ -0,0 +1,259 @@
|
|
|
1
|
+
import * as react_jsx_runtime from 'react/jsx-runtime';
|
|
2
|
+
import React__default, { Dispatch } from 'react';
|
|
3
|
+
|
|
4
|
+
interface HttpController {
|
|
5
|
+
get(path?: string, query?: string): Promise<any>;
|
|
6
|
+
post(path?: string, data?: any, extraHeaders?: Record<string, string>, query?: string): Promise<any>;
|
|
7
|
+
put(path?: string, data?: any, extraHeaders?: Record<string, string>, query?: string): Promise<any>;
|
|
8
|
+
patch(path?: string, data?: any, extraHeaders?: Record<string, string>, query?: string): Promise<any>;
|
|
9
|
+
delete(path?: string, id?: string | number, extraHeaders?: Record<string, string>, query?: string): Promise<any>;
|
|
10
|
+
deleteSimple(path?: string, extraHeaders?: Record<string, string>, query?: string): Promise<any>;
|
|
11
|
+
save(path?: string, data?: any, extraHeaders?: Record<string, string>, query?: string): Promise<any>;
|
|
12
|
+
read(path?: string, id?: string | number, extraHeaders?: Record<string, string>, query?: string): Promise<any>;
|
|
13
|
+
readAll(path?: string, extraHeaders?: Record<string, string>, query?: string): Promise<any>;
|
|
14
|
+
readAllwithPage(path?: string, page?: number, size?: number): Promise<any>;
|
|
15
|
+
bulkDelete(path?: string, ids?: (string | number)[], extraHeaders?: Record<string, string>, query?: string): Promise<any>;
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
interface ToastOptions {
|
|
19
|
+
autoDismiss?: boolean;
|
|
20
|
+
autoDismissTimeout?: number;
|
|
21
|
+
}
|
|
22
|
+
interface ToastService {
|
|
23
|
+
success(message: string, options?: ToastOptions): void;
|
|
24
|
+
warning(message: string, options?: ToastOptions): void;
|
|
25
|
+
error(message: string, options?: ToastOptions): void;
|
|
26
|
+
info(message: string, options?: ToastOptions): void;
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
interface MatchingObjectSubscription {
|
|
30
|
+
context: string;
|
|
31
|
+
location: string;
|
|
32
|
+
refresher?: (payload: any, dispatch: Dispatch<any>) => void;
|
|
33
|
+
persist?: boolean;
|
|
34
|
+
userId?: string;
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
interface CoreService {
|
|
38
|
+
/** Cria um HttpController configurado para um contexto/endpoint */
|
|
39
|
+
createController(context: string, baseEndPoint?: string): HttpController;
|
|
40
|
+
/** Serviço de toast/notificações */
|
|
41
|
+
toast: ToastService;
|
|
42
|
+
/** Subscreve a um MatchingObject (real-time via Firebase RTDB) */
|
|
43
|
+
subscribe(mo: MatchingObjectSubscription): void;
|
|
44
|
+
/** Remove subscrição de um MatchingObject */
|
|
45
|
+
unsubscribe(mo: MatchingObjectSubscription): void;
|
|
46
|
+
/** Subscreve a eventos de MatchingObject via EventTarget */
|
|
47
|
+
subscribeEvent(context: string, location: string, handler: EventListenerOrEventListenerObject): void;
|
|
48
|
+
/** Remove subscrição de evento de MatchingObject */
|
|
49
|
+
unsubscribeEvent(context: string, location: string, handler: EventListenerOrEventListenerObject): void;
|
|
50
|
+
/** Encerra a sessão do usuário */
|
|
51
|
+
handleLogout(): void;
|
|
52
|
+
/** Indica se o componente está hospedado pelo Core */
|
|
53
|
+
hostedByCore: boolean;
|
|
54
|
+
}
|
|
55
|
+
|
|
56
|
+
interface FederatedBridgeProps {
|
|
57
|
+
/**
|
|
58
|
+
* CoreService completo injetado pelo host.
|
|
59
|
+
* O host monta este valor a partir do seu WebProvider interno.
|
|
60
|
+
*/
|
|
61
|
+
coreService: CoreService;
|
|
62
|
+
children: React__default.ReactNode;
|
|
63
|
+
}
|
|
64
|
+
/**
|
|
65
|
+
* Bridge padronizado para módulos federados.
|
|
66
|
+
*
|
|
67
|
+
* Responsibilities:
|
|
68
|
+
* 1. Marks window.__TERAPROX_HOSTED_BY_CORE__ = true
|
|
69
|
+
* 2. Provides CoreServiceContext with host value
|
|
70
|
+
*
|
|
71
|
+
* USAGE IN REMOTES:
|
|
72
|
+
* ```
|
|
73
|
+
* // remote/src/federation/FederatedBridge.js
|
|
74
|
+
* export { FederatedBridge as default } from 'teraprox-core-sdk/federation'
|
|
75
|
+
* ```
|
|
76
|
+
*/
|
|
77
|
+
declare function FederatedBridge({ coreService, children }: FederatedBridgeProps): react_jsx_runtime.JSX.Element;
|
|
78
|
+
|
|
79
|
+
/**
|
|
80
|
+
* Factory for creating a standardized ReducersBundle.
|
|
81
|
+
*
|
|
82
|
+
* Each remote only needs to declare ITS reducers and context map.
|
|
83
|
+
* Resolution, deduplication, and loading logic lives here in the SDK.
|
|
84
|
+
*
|
|
85
|
+
* USAGE IN REMOTES:
|
|
86
|
+
* ```
|
|
87
|
+
* import { createReducersBundle } from 'teraprox-core-sdk/federation'
|
|
88
|
+
*
|
|
89
|
+
* export default createReducersBundle({
|
|
90
|
+
* reducers: {
|
|
91
|
+
* ordemDeServico: () => import('../Reducers/osReducer'),
|
|
92
|
+
* ordemDeManutencao: () => import('../Reducers/omReducer'),
|
|
93
|
+
* },
|
|
94
|
+
* contextMap: {
|
|
95
|
+
* visaoGeral: ['ordemDeServico', 'ordemDeManutencao'],
|
|
96
|
+
* ordemDeServico: ['ordemDeServico'],
|
|
97
|
+
* },
|
|
98
|
+
* defaults: ['picker', 'globalError'],
|
|
99
|
+
* })
|
|
100
|
+
* ```
|
|
101
|
+
*/
|
|
102
|
+
interface ReducersBundleConfig {
|
|
103
|
+
/** Map de nome → importador lazy do reducer */
|
|
104
|
+
reducers: Record<string, () => Promise<any>>;
|
|
105
|
+
/** Map de contexto → lista de reducer keys necessárias */
|
|
106
|
+
contextMap: Record<string, string[]>;
|
|
107
|
+
/** Keys carregadas em TODOS os contextos */
|
|
108
|
+
defaults?: string[];
|
|
109
|
+
}
|
|
110
|
+
interface ReducersBundle {
|
|
111
|
+
getReducerKeysByContext(context: string): string[];
|
|
112
|
+
getReducersForKeys(keys: string[]): Promise<Record<string, any>>;
|
|
113
|
+
getReducersForModule(opts: {
|
|
114
|
+
context?: string;
|
|
115
|
+
modulePath?: string;
|
|
116
|
+
}): Promise<Record<string, any>>;
|
|
117
|
+
loadAllReducers(): Promise<Record<string, any>>;
|
|
118
|
+
baseReducers: Record<string, never>;
|
|
119
|
+
}
|
|
120
|
+
declare function createReducersBundle(config: ReducersBundleConfig): ReducersBundle;
|
|
121
|
+
|
|
122
|
+
interface StandaloneConfig {
|
|
123
|
+
/**
|
|
124
|
+
* Factory for creating an HttpController. The remote provides its
|
|
125
|
+
* local implementation (using basicController + axios).
|
|
126
|
+
*/
|
|
127
|
+
createController: (context: string, baseEndPoint?: string) => HttpController;
|
|
128
|
+
/** Toast function from react-toast-notifications */
|
|
129
|
+
addToast: (message: string, options?: any) => void;
|
|
130
|
+
/**
|
|
131
|
+
* Firebase client config object (from REACT_APP_FIREBASE_CONFIG).
|
|
132
|
+
* When provided together with `tenant`, enables real-time matching
|
|
133
|
+
* object listening via Firebase RTDB — same path the Core uses.
|
|
134
|
+
*
|
|
135
|
+
* If omitted, the provider auto-detects the RTDB emulator:
|
|
136
|
+
* 1. Reads `REACT_APP_RTDB_EMULATOR_HOST` (e.g. `localhost:9000`)
|
|
137
|
+
* 2. Falls back to probing `localhost:9000`
|
|
138
|
+
* 3. If neither works, shows a configuration popup (dev only)
|
|
139
|
+
*/
|
|
140
|
+
firebaseConfig?: Record<string, unknown>;
|
|
141
|
+
/**
|
|
142
|
+
* Tenant / company ID used to build the RTDB path:
|
|
143
|
+
* `{tenant}/matchingObjects`
|
|
144
|
+
*/
|
|
145
|
+
tenant?: string;
|
|
146
|
+
children: React__default.ReactNode;
|
|
147
|
+
}
|
|
148
|
+
/**
|
|
149
|
+
* Standardized provider for standalone mode (npm start).
|
|
150
|
+
*
|
|
151
|
+
* Replaces the StandaloneCoreServiceProvider that each remote copies.
|
|
152
|
+
* The remote only needs to provide its createController and addToast.
|
|
153
|
+
*
|
|
154
|
+
* RTDB auto-resolution order (no config required):
|
|
155
|
+
* 1. `REACT_APP_RTDB_EMULATOR_HOST` env var → connects to emulator
|
|
156
|
+
* 2. `firebaseConfig` prop → connects to Firebase cloud
|
|
157
|
+
* 3. Auto-probe `localhost:9000` → uses emulator if alive
|
|
158
|
+
* 4. None found → shows configuration popup (dev only)
|
|
159
|
+
*
|
|
160
|
+
* USAGE IN REMOTES:
|
|
161
|
+
* ```
|
|
162
|
+
* import { StandaloneProvider } from 'teraprox-core-sdk/federation'
|
|
163
|
+
* import { basicController } from '../Http/basicController'
|
|
164
|
+
* import { useToasts } from 'react-toast-notifications'
|
|
165
|
+
*
|
|
166
|
+
* function App() {
|
|
167
|
+
* const { addToast } = useToasts()
|
|
168
|
+
* const tenant = useSelector(s => s.global.companyId)
|
|
169
|
+
* return (
|
|
170
|
+
* <StandaloneProvider
|
|
171
|
+
* createController={(ctx, ep) => basicController(ctx, ep)}
|
|
172
|
+
* addToast={addToast}
|
|
173
|
+
* tenant={tenant}
|
|
174
|
+
* >
|
|
175
|
+
* <Routes />
|
|
176
|
+
* </StandaloneProvider>
|
|
177
|
+
* )
|
|
178
|
+
* }
|
|
179
|
+
* ```
|
|
180
|
+
*/
|
|
181
|
+
declare function StandaloneProvider({ createController, addToast, firebaseConfig, tenant, children }: StandaloneConfig): react_jsx_runtime.JSX.Element;
|
|
182
|
+
|
|
183
|
+
interface DevUser {
|
|
184
|
+
firstName: string;
|
|
185
|
+
lastName: string;
|
|
186
|
+
token: string;
|
|
187
|
+
email: string;
|
|
188
|
+
id: string;
|
|
189
|
+
role: string;
|
|
190
|
+
user: string;
|
|
191
|
+
userName: string;
|
|
192
|
+
setor: string;
|
|
193
|
+
userSetor: {
|
|
194
|
+
setorId: string;
|
|
195
|
+
};
|
|
196
|
+
companyName: string;
|
|
197
|
+
companyId: string;
|
|
198
|
+
filters: any[];
|
|
199
|
+
}
|
|
200
|
+
interface DevAutoLoginProps {
|
|
201
|
+
/** Redux actions from the remote's globalConfigReducer */
|
|
202
|
+
actions: {
|
|
203
|
+
logIn: (user: any) => any;
|
|
204
|
+
setCompany: (company: string) => any;
|
|
205
|
+
};
|
|
206
|
+
/** Mock data for dev (optional, has defaults) */
|
|
207
|
+
devUser?: Partial<DevUser>;
|
|
208
|
+
children: React__default.ReactNode;
|
|
209
|
+
}
|
|
210
|
+
/**
|
|
211
|
+
* Auto-login for standalone dev mode.
|
|
212
|
+
*
|
|
213
|
+
* USAGE:
|
|
214
|
+
* ```
|
|
215
|
+
* import { DevAutoLogin } from 'teraprox-core-sdk/federation'
|
|
216
|
+
* import { logIn, setCompany } from '../Reducers/globalConfigReducer'
|
|
217
|
+
*
|
|
218
|
+
* <DevAutoLogin actions={{ logIn, setCompany }}>
|
|
219
|
+
* <App />
|
|
220
|
+
* </DevAutoLogin>
|
|
221
|
+
* ```
|
|
222
|
+
*/
|
|
223
|
+
declare function DevAutoLogin({ actions, devUser, children }: DevAutoLoginProps): react_jsx_runtime.JSX.Element;
|
|
224
|
+
|
|
225
|
+
/**
|
|
226
|
+
* Manifesto que cada remote exporta para o Core
|
|
227
|
+
* montar menu e rotas dinamicamente.
|
|
228
|
+
*/
|
|
229
|
+
interface RemoteMenuItem {
|
|
230
|
+
/** Label exibido no menu */
|
|
231
|
+
label: string;
|
|
232
|
+
/** Rota no react-router (ex: '/manutencao/ordens-de-servico') */
|
|
233
|
+
path: string;
|
|
234
|
+
/** Nome do módulo no exposes do webpack (ex: './OrdensDeServico') */
|
|
235
|
+
module: string;
|
|
236
|
+
/** Contexto para ReducersBundle (ex: 'ordemDeServico') */
|
|
237
|
+
context: string;
|
|
238
|
+
/** ID do componente para withPermission */
|
|
239
|
+
componentId?: string;
|
|
240
|
+
/** Ícone react-icons (ex: 'FaTools') */
|
|
241
|
+
icon?: string;
|
|
242
|
+
}
|
|
243
|
+
interface RemoteMenuSection {
|
|
244
|
+
/** Nome da seção no menu (ex: 'Manutenção') */
|
|
245
|
+
label: string;
|
|
246
|
+
/** Ícone da seção */
|
|
247
|
+
icon?: string;
|
|
248
|
+
items: RemoteMenuItem[];
|
|
249
|
+
}
|
|
250
|
+
interface RemoteManifest {
|
|
251
|
+
/** Nome do remote (deve corresponder ao name do ModuleFederationPlugin) */
|
|
252
|
+
name: string;
|
|
253
|
+
/** Versão semântica */
|
|
254
|
+
version: string;
|
|
255
|
+
/** Seções de menu que este remote contribui */
|
|
256
|
+
menuSections: RemoteMenuSection[];
|
|
257
|
+
}
|
|
258
|
+
|
|
259
|
+
export { type CoreService as C, DevAutoLogin as D, FederatedBridge as F, type HttpController as H, type MatchingObjectSubscription as M, type ReducersBundle as R, StandaloneProvider as S, type ToastService as T, type ReducersBundleConfig as a, type RemoteManifest as b, type RemoteMenuItem as c, type RemoteMenuSection as d, type ToastOptions as e, createReducersBundle as f };
|
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
export { D as DevAutoLogin, F as FederatedBridge, R as ReducersBundle, a as ReducersBundleConfig, b as RemoteManifest, c as RemoteMenuItem, d as RemoteMenuSection, S as StandaloneProvider, f as createReducersBundle } from './federation-B4ShfmDd.mjs';
|
|
2
|
+
import 'react/jsx-runtime';
|
|
3
|
+
import 'react';
|
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
export { D as DevAutoLogin, F as FederatedBridge, R as ReducersBundle, a as ReducersBundleConfig, b as RemoteManifest, c as RemoteMenuItem, d as RemoteMenuSection, S as StandaloneProvider, f as createReducersBundle } from './federation-B4ShfmDd.js';
|
|
2
|
+
import 'react/jsx-runtime';
|
|
3
|
+
import 'react';
|
|
@@ -0,0 +1,358 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __create = Object.create;
|
|
3
|
+
var __defProp = Object.defineProperty;
|
|
4
|
+
var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
|
|
5
|
+
var __getOwnPropNames = Object.getOwnPropertyNames;
|
|
6
|
+
var __getProtoOf = Object.getPrototypeOf;
|
|
7
|
+
var __hasOwnProp = Object.prototype.hasOwnProperty;
|
|
8
|
+
var __export = (target, all) => {
|
|
9
|
+
for (var name in all)
|
|
10
|
+
__defProp(target, name, { get: all[name], enumerable: true });
|
|
11
|
+
};
|
|
12
|
+
var __copyProps = (to, from, except, desc) => {
|
|
13
|
+
if (from && typeof from === "object" || typeof from === "function") {
|
|
14
|
+
for (let key of __getOwnPropNames(from))
|
|
15
|
+
if (!__hasOwnProp.call(to, key) && key !== except)
|
|
16
|
+
__defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
|
|
17
|
+
}
|
|
18
|
+
return to;
|
|
19
|
+
};
|
|
20
|
+
var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(
|
|
21
|
+
// If the importer is in node compatibility mode or this is not an ESM
|
|
22
|
+
// file that has been converted to a CommonJS file using a Babel-
|
|
23
|
+
// compatible transform (i.e. "__esModule" has not been set), then set
|
|
24
|
+
// "default" to the CommonJS "module.exports" for node compatibility.
|
|
25
|
+
isNodeMode || !mod || !mod.__esModule ? __defProp(target, "default", { value: mod, enumerable: true }) : target,
|
|
26
|
+
mod
|
|
27
|
+
));
|
|
28
|
+
var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
|
|
29
|
+
|
|
30
|
+
// src/federation.ts
|
|
31
|
+
var federation_exports = {};
|
|
32
|
+
__export(federation_exports, {
|
|
33
|
+
DevAutoLogin: () => DevAutoLogin,
|
|
34
|
+
FederatedBridge: () => FederatedBridge,
|
|
35
|
+
StandaloneProvider: () => StandaloneProvider,
|
|
36
|
+
createReducersBundle: () => createReducersBundle
|
|
37
|
+
});
|
|
38
|
+
module.exports = __toCommonJS(federation_exports);
|
|
39
|
+
|
|
40
|
+
// src/federation/FederatedBridge.tsx
|
|
41
|
+
var import_react2 = require("react");
|
|
42
|
+
|
|
43
|
+
// src/context/CoreServiceContext.ts
|
|
44
|
+
var import_react = require("react");
|
|
45
|
+
var CoreServiceContext = (0, import_react.createContext)(null);
|
|
46
|
+
|
|
47
|
+
// src/federation/FederatedBridge.tsx
|
|
48
|
+
var import_jsx_runtime = require("react/jsx-runtime");
|
|
49
|
+
function FederatedBridge({ coreService, children }) {
|
|
50
|
+
(0, import_react2.useEffect)(() => {
|
|
51
|
+
if (typeof window === "undefined") return;
|
|
52
|
+
window.__TERAPROX_HOSTED_BY_CORE__ = true;
|
|
53
|
+
return () => {
|
|
54
|
+
;
|
|
55
|
+
window.__TERAPROX_HOSTED_BY_CORE__ = false;
|
|
56
|
+
};
|
|
57
|
+
}, []);
|
|
58
|
+
return /* @__PURE__ */ (0, import_jsx_runtime.jsx)(CoreServiceContext.Provider, { value: coreService, children });
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
// src/federation/createReducersBundle.ts
|
|
62
|
+
function createReducersBundle(config) {
|
|
63
|
+
const { reducers, contextMap, defaults = [] } = config;
|
|
64
|
+
const allKeys = Object.keys(reducers);
|
|
65
|
+
const getReducerKeysByContext = (context) => {
|
|
66
|
+
const contextKeys = contextMap[context];
|
|
67
|
+
if (!contextKeys) return allKeys;
|
|
68
|
+
return [.../* @__PURE__ */ new Set([...defaults, ...contextKeys])];
|
|
69
|
+
};
|
|
70
|
+
const getReducersForKeys = async (keys = []) => {
|
|
71
|
+
const uniqueKeys = [...new Set(keys)].filter((key) => !!reducers[key]);
|
|
72
|
+
const loaded = await Promise.all(
|
|
73
|
+
uniqueKeys.map(async (key) => {
|
|
74
|
+
const module2 = await reducers[key]();
|
|
75
|
+
return [key, module2.default || module2];
|
|
76
|
+
})
|
|
77
|
+
);
|
|
78
|
+
return Object.fromEntries(loaded);
|
|
79
|
+
};
|
|
80
|
+
const getReducersForModule = async ({
|
|
81
|
+
context
|
|
82
|
+
} = {}) => {
|
|
83
|
+
const keys = getReducerKeysByContext(context || "");
|
|
84
|
+
return getReducersForKeys(keys);
|
|
85
|
+
};
|
|
86
|
+
const loadAllReducers = () => getReducersForKeys(allKeys);
|
|
87
|
+
return {
|
|
88
|
+
getReducerKeysByContext,
|
|
89
|
+
getReducersForKeys,
|
|
90
|
+
getReducersForModule,
|
|
91
|
+
loadAllReducers,
|
|
92
|
+
baseReducers: {}
|
|
93
|
+
};
|
|
94
|
+
}
|
|
95
|
+
|
|
96
|
+
// src/federation/StandaloneProvider.tsx
|
|
97
|
+
var import_react3 = require("react");
|
|
98
|
+
var import_jsx_runtime2 = require("react/jsx-runtime");
|
|
99
|
+
async function probeEmulator(host, port) {
|
|
100
|
+
try {
|
|
101
|
+
const res = await fetch(`http://${host}:${port}/.json`, {
|
|
102
|
+
signal: AbortSignal.timeout(1500)
|
|
103
|
+
});
|
|
104
|
+
return res.ok || res.status === 404;
|
|
105
|
+
} catch (e) {
|
|
106
|
+
return false;
|
|
107
|
+
}
|
|
108
|
+
}
|
|
109
|
+
async function resolveRtdbStrategy(firebaseConfig) {
|
|
110
|
+
var _a;
|
|
111
|
+
const emulatorHostEnv = typeof process !== "undefined" && process.env.REACT_APP_RTDB_EMULATOR_HOST || void 0;
|
|
112
|
+
if (emulatorHostEnv) {
|
|
113
|
+
const [host, portStr] = emulatorHostEnv.split(":");
|
|
114
|
+
const port = parseInt(portStr != null ? portStr : "9000", 10);
|
|
115
|
+
const namespace = (_a = process.env.REACT_APP_RTDB_EMULATOR_NS) != null ? _a : "demo-local";
|
|
116
|
+
return { type: "emulator", host, port, namespace };
|
|
117
|
+
}
|
|
118
|
+
if (firebaseConfig && Object.keys(firebaseConfig).length > 0) {
|
|
119
|
+
return { type: "cloud", config: firebaseConfig };
|
|
120
|
+
}
|
|
121
|
+
const alive = await probeEmulator("localhost", 9e3);
|
|
122
|
+
if (alive) {
|
|
123
|
+
return { type: "emulator", host: "localhost", port: 9e3, namespace: "demo-local" };
|
|
124
|
+
}
|
|
125
|
+
return { type: "none" };
|
|
126
|
+
}
|
|
127
|
+
var _emulatorConnected = /* @__PURE__ */ new Set();
|
|
128
|
+
function RtdbConfigWarning({ onDismiss }) {
|
|
129
|
+
return /* @__PURE__ */ (0, import_jsx_runtime2.jsxs)(
|
|
130
|
+
"div",
|
|
131
|
+
{
|
|
132
|
+
style: {
|
|
133
|
+
position: "fixed",
|
|
134
|
+
bottom: 24,
|
|
135
|
+
right: 24,
|
|
136
|
+
zIndex: 99999,
|
|
137
|
+
background: "#1a1a2e",
|
|
138
|
+
color: "#fff",
|
|
139
|
+
borderRadius: 8,
|
|
140
|
+
padding: "16px 20px",
|
|
141
|
+
maxWidth: 420,
|
|
142
|
+
boxShadow: "0 4px 24px rgba(0,0,0,0.5)",
|
|
143
|
+
borderLeft: "4px solid #f59e0b",
|
|
144
|
+
fontFamily: "monospace",
|
|
145
|
+
fontSize: 13,
|
|
146
|
+
lineHeight: 1.6
|
|
147
|
+
},
|
|
148
|
+
children: [
|
|
149
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)("div", { style: { fontWeight: "bold", marginBottom: 8, color: "#f59e0b", fontSize: 14 }, children: "\u26A0 RTDB n\xE3o configurado" }),
|
|
150
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsxs)("div", { children: [
|
|
151
|
+
"Matching Objects em tempo real desativados.",
|
|
152
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)("br", {}),
|
|
153
|
+
"Configure no ",
|
|
154
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)("code", { children: ".env.dev" }),
|
|
155
|
+
":",
|
|
156
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)("br", {}),
|
|
157
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)("code", { style: { color: "#86efac" }, children: "REACT_APP_RTDB_EMULATOR_HOST=localhost:9000" }),
|
|
158
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)("br", {}),
|
|
159
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsxs)("span", { style: { color: "#94a3b8", fontSize: 11 }, children: [
|
|
160
|
+
"ou inicie o backend com ",
|
|
161
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)("code", { children: "RtdbEmulatorPlugin" }),
|
|
162
|
+
" do @onroad/core"
|
|
163
|
+
] }),
|
|
164
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)("br", {}),
|
|
165
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsxs)("span", { style: { color: "#94a3b8", fontSize: 11 }, children: [
|
|
166
|
+
"e rode o emulator com ",
|
|
167
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)("code", { children: "firebase emulators:start --only database" })
|
|
168
|
+
] })
|
|
169
|
+
] }),
|
|
170
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)(
|
|
171
|
+
"button",
|
|
172
|
+
{
|
|
173
|
+
onClick: onDismiss,
|
|
174
|
+
style: {
|
|
175
|
+
marginTop: 12,
|
|
176
|
+
padding: "4px 14px",
|
|
177
|
+
background: "#374151",
|
|
178
|
+
color: "#fff",
|
|
179
|
+
border: "none",
|
|
180
|
+
borderRadius: 4,
|
|
181
|
+
cursor: "pointer",
|
|
182
|
+
fontSize: 12
|
|
183
|
+
},
|
|
184
|
+
children: "Fechar"
|
|
185
|
+
}
|
|
186
|
+
)
|
|
187
|
+
]
|
|
188
|
+
}
|
|
189
|
+
);
|
|
190
|
+
}
|
|
191
|
+
function StandaloneProvider({ createController, addToast, firebaseConfig, tenant, children }) {
|
|
192
|
+
const [subscriptions] = (0, import_react3.useState)([]);
|
|
193
|
+
const subscriptionsRef = (0, import_react3.useRef)(subscriptions);
|
|
194
|
+
subscriptionsRef.current = subscriptions;
|
|
195
|
+
const [rtdbWarning, setRtdbWarning] = (0, import_react3.useState)(false);
|
|
196
|
+
const toast = (0, import_react3.useMemo)(
|
|
197
|
+
() => ({
|
|
198
|
+
success: (msg, opts) => addToast(msg, { appearance: "success", autoDismiss: true, ...opts }),
|
|
199
|
+
warning: (msg, opts) => addToast(msg, { appearance: "warning", autoDismiss: true, ...opts }),
|
|
200
|
+
error: (msg, opts) => addToast(msg, { appearance: "error", autoDismiss: true, ...opts }),
|
|
201
|
+
info: (msg, opts) => addToast(msg, { appearance: "info", autoDismiss: true, ...opts })
|
|
202
|
+
}),
|
|
203
|
+
[addToast]
|
|
204
|
+
);
|
|
205
|
+
const subscribe = (0, import_react3.useCallback)(
|
|
206
|
+
(mo) => {
|
|
207
|
+
subscriptions.push(mo);
|
|
208
|
+
},
|
|
209
|
+
[subscriptions]
|
|
210
|
+
);
|
|
211
|
+
const unsubscribe = (0, import_react3.useCallback)(
|
|
212
|
+
(mo) => {
|
|
213
|
+
const idx = subscriptions.findIndex(
|
|
214
|
+
(s) => s.context === mo.context && s.location === mo.location
|
|
215
|
+
);
|
|
216
|
+
if (idx >= 0) subscriptions.splice(idx, 1);
|
|
217
|
+
},
|
|
218
|
+
[subscriptions]
|
|
219
|
+
);
|
|
220
|
+
(0, import_react3.useEffect)(() => {
|
|
221
|
+
if (!tenant) return;
|
|
222
|
+
let cleanup;
|
|
223
|
+
let cancelled = false;
|
|
224
|
+
(async () => {
|
|
225
|
+
var _a;
|
|
226
|
+
const strategy = await resolveRtdbStrategy(firebaseConfig);
|
|
227
|
+
if (cancelled) return;
|
|
228
|
+
if (strategy.type === "none") {
|
|
229
|
+
if (process.env.NODE_ENV !== "production") setRtdbWarning(true);
|
|
230
|
+
return;
|
|
231
|
+
}
|
|
232
|
+
try {
|
|
233
|
+
const { initializeApp, getApps } = await import("firebase/app");
|
|
234
|
+
const { getDatabase, ref, onChildAdded } = await import("firebase/database");
|
|
235
|
+
let db;
|
|
236
|
+
if (strategy.type === "emulator") {
|
|
237
|
+
const appName = `onroad-rtdb-emulator-${strategy.port}`;
|
|
238
|
+
const existingApp = getApps().find((a) => a.name === appName);
|
|
239
|
+
const emulatorApp = existingApp != null ? existingApp : initializeApp(
|
|
240
|
+
{
|
|
241
|
+
projectId: strategy.namespace,
|
|
242
|
+
databaseURL: `http://${strategy.host}:${strategy.port}?ns=${strategy.namespace}`
|
|
243
|
+
},
|
|
244
|
+
appName
|
|
245
|
+
);
|
|
246
|
+
db = getDatabase(emulatorApp);
|
|
247
|
+
if (!_emulatorConnected.has(appName)) {
|
|
248
|
+
const { connectDatabaseEmulator } = await import("firebase/database");
|
|
249
|
+
try {
|
|
250
|
+
connectDatabaseEmulator(db, strategy.host, strategy.port);
|
|
251
|
+
_emulatorConnected.add(appName);
|
|
252
|
+
} catch (e) {
|
|
253
|
+
_emulatorConnected.add(appName);
|
|
254
|
+
}
|
|
255
|
+
}
|
|
256
|
+
console.info(
|
|
257
|
+
`[StandaloneProvider] RTDB emulator at ${strategy.host}:${strategy.port} (ns=${strategy.namespace})`
|
|
258
|
+
);
|
|
259
|
+
} else {
|
|
260
|
+
const existingApp = (_a = getApps().find((a) => a.name === "[DEFAULT]")) != null ? _a : getApps()[0];
|
|
261
|
+
const cloudApp = existingApp != null ? existingApp : initializeApp(strategy.config);
|
|
262
|
+
db = getDatabase(cloudApp);
|
|
263
|
+
}
|
|
264
|
+
const moRef = ref(db, `${tenant}/matchingObjects`);
|
|
265
|
+
const unsub = onChildAdded(moRef, (snapshot) => {
|
|
266
|
+
const data = snapshot.val();
|
|
267
|
+
if (!data) return;
|
|
268
|
+
const items = Array.isArray(data) ? data : [data];
|
|
269
|
+
for (const mo of items) {
|
|
270
|
+
if (typeof mo !== "object") continue;
|
|
271
|
+
const subs = subscriptionsRef.current || [];
|
|
272
|
+
for (const sub of subs) {
|
|
273
|
+
const sameContext = sub.context === mo.context;
|
|
274
|
+
const sameLocation = sub.location === mo.location || sub.location === "*" || mo.location === "*" || !sub.location || !mo.location;
|
|
275
|
+
if (sameContext && sameLocation && sub.refresher) {
|
|
276
|
+
try {
|
|
277
|
+
sub.refresher(mo.payload, () => {
|
|
278
|
+
});
|
|
279
|
+
} catch (e) {
|
|
280
|
+
}
|
|
281
|
+
}
|
|
282
|
+
}
|
|
283
|
+
}
|
|
284
|
+
});
|
|
285
|
+
cleanup = () => unsub();
|
|
286
|
+
} catch (err) {
|
|
287
|
+
console.warn("[StandaloneProvider] Firebase RTDB listener failed:", err);
|
|
288
|
+
}
|
|
289
|
+
})();
|
|
290
|
+
return () => {
|
|
291
|
+
cancelled = true;
|
|
292
|
+
cleanup == null ? void 0 : cleanup();
|
|
293
|
+
};
|
|
294
|
+
}, [firebaseConfig, tenant]);
|
|
295
|
+
const value = (0, import_react3.useMemo)(
|
|
296
|
+
() => ({
|
|
297
|
+
createController,
|
|
298
|
+
toast,
|
|
299
|
+
subscribe,
|
|
300
|
+
unsubscribe,
|
|
301
|
+
subscribeEvent: () => {
|
|
302
|
+
},
|
|
303
|
+
unsubscribeEvent: () => {
|
|
304
|
+
},
|
|
305
|
+
handleLogout: () => {
|
|
306
|
+
},
|
|
307
|
+
hostedByCore: false
|
|
308
|
+
}),
|
|
309
|
+
[createController, toast, subscribe, unsubscribe]
|
|
310
|
+
);
|
|
311
|
+
return /* @__PURE__ */ (0, import_jsx_runtime2.jsxs)(CoreServiceContext.Provider, { value, children: [
|
|
312
|
+
children,
|
|
313
|
+
rtdbWarning && /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(RtdbConfigWarning, { onDismiss: () => setRtdbWarning(false) })
|
|
314
|
+
] });
|
|
315
|
+
}
|
|
316
|
+
|
|
317
|
+
// src/federation/DevAutoLogin.tsx
|
|
318
|
+
var import_react4 = require("react");
|
|
319
|
+
var import_react_redux = require("react-redux");
|
|
320
|
+
var import_jsx_runtime3 = require("react/jsx-runtime");
|
|
321
|
+
var DEFAULT_DEV_USER = {
|
|
322
|
+
firstName: "Dev",
|
|
323
|
+
lastName: "User",
|
|
324
|
+
token: "dev-standalone-token",
|
|
325
|
+
email: "dev@teraprox.local",
|
|
326
|
+
id: "dev-user-id",
|
|
327
|
+
role: "admin",
|
|
328
|
+
user: "devuser",
|
|
329
|
+
userName: "devuser",
|
|
330
|
+
setor: "Desenvolvimento",
|
|
331
|
+
userSetor: { setorId: "dev-setor-id" },
|
|
332
|
+
companyName: "Dev Company",
|
|
333
|
+
companyId: "dev-company-id",
|
|
334
|
+
filters: []
|
|
335
|
+
};
|
|
336
|
+
function DevAutoLogin({ actions, devUser, children }) {
|
|
337
|
+
const dispatch = (0, import_react_redux.useDispatch)();
|
|
338
|
+
const token = (0, import_react_redux.useSelector)((state) => {
|
|
339
|
+
var _a;
|
|
340
|
+
return (_a = state.global) == null ? void 0 : _a.token;
|
|
341
|
+
});
|
|
342
|
+
const hostedByCore = typeof window !== "undefined" && window.__TERAPROX_HOSTED_BY_CORE__ === true;
|
|
343
|
+
(0, import_react4.useEffect)(() => {
|
|
344
|
+
if (process.env.NODE_ENV === "development" && !hostedByCore && !token) {
|
|
345
|
+
const user = { ...DEFAULT_DEV_USER, ...devUser };
|
|
346
|
+
dispatch(actions.setCompany(user.companyId));
|
|
347
|
+
dispatch(actions.logIn(user));
|
|
348
|
+
}
|
|
349
|
+
}, [dispatch, hostedByCore, token, actions, devUser]);
|
|
350
|
+
return /* @__PURE__ */ (0, import_jsx_runtime3.jsx)(import_jsx_runtime3.Fragment, { children });
|
|
351
|
+
}
|
|
352
|
+
// Annotate the CommonJS export names for ESM import in node:
|
|
353
|
+
0 && (module.exports = {
|
|
354
|
+
DevAutoLogin,
|
|
355
|
+
FederatedBridge,
|
|
356
|
+
StandaloneProvider,
|
|
357
|
+
createReducersBundle
|
|
358
|
+
});
|