@fivem-nui/svelte 0.0.0-stage → 1.0.0
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/README.md +284 -2
- package/dist/actions/clickOutside/clickOutside.d.ts +24 -0
- package/dist/actions/clickOutside/clickOutside.d.ts.map +1 -0
- package/dist/actions/clickOutside/clickOutside.js +62 -0
- package/dist/actions/clickOutside/clickOutside.js.map +1 -0
- package/dist/actions/clickOutside/handler.d.ts +11 -0
- package/dist/actions/clickOutside/handler.d.ts.map +1 -0
- package/dist/actions/clickOutside/handler.js +45 -0
- package/dist/actions/clickOutside/handler.js.map +1 -0
- package/dist/actions/clickOutside/index.d.ts +4 -0
- package/dist/actions/clickOutside/index.d.ts.map +1 -0
- package/dist/actions/clickOutside/index.js +4 -0
- package/dist/actions/clickOutside/index.js.map +1 -0
- package/dist/actions/clickOutside/types.d.ts +36 -0
- package/dist/actions/clickOutside/types.d.ts.map +1 -0
- package/dist/actions/clickOutside/types.js +6 -0
- package/dist/actions/clickOutside/types.js.map +1 -0
- package/dist/actions/clickOutside.d.ts +63 -0
- package/dist/actions/clickOutside.d.ts.map +1 -0
- package/dist/actions/clickOutside.js +106 -0
- package/dist/actions/clickOutside.js.map +1 -0
- package/dist/actions/escape/escape.d.ts +26 -0
- package/dist/actions/escape/escape.d.ts.map +1 -0
- package/dist/actions/escape/escape.js +74 -0
- package/dist/actions/escape/escape.js.map +1 -0
- package/dist/actions/escape/handler.d.ts +11 -0
- package/dist/actions/escape/handler.d.ts.map +1 -0
- package/dist/actions/escape/handler.js +50 -0
- package/dist/actions/escape/handler.js.map +1 -0
- package/dist/actions/escape/index.d.ts +4 -0
- package/dist/actions/escape/index.d.ts.map +1 -0
- package/dist/actions/escape/index.js +4 -0
- package/dist/actions/escape/index.js.map +1 -0
- package/dist/actions/escape/types.d.ts +70 -0
- package/dist/actions/escape/types.d.ts.map +1 -0
- package/dist/actions/escape/types.js +12 -0
- package/dist/actions/escape/types.js.map +1 -0
- package/dist/actions/escape.d.ts +99 -0
- package/dist/actions/escape.d.ts.map +1 -0
- package/dist/actions/escape.js +128 -0
- package/dist/actions/escape.js.map +1 -0
- package/dist/actions/focusTrap/focusTrap.d.ts +19 -0
- package/dist/actions/focusTrap/focusTrap.d.ts.map +1 -0
- package/dist/actions/focusTrap/focusTrap.js +198 -0
- package/dist/actions/focusTrap/focusTrap.js.map +1 -0
- package/dist/actions/focusTrap/focusables.d.ts +39 -0
- package/dist/actions/focusTrap/focusables.d.ts.map +1 -0
- package/dist/actions/focusTrap/focusables.js +142 -0
- package/dist/actions/focusTrap/focusables.js.map +1 -0
- package/dist/actions/focusTrap/index.d.ts +5 -0
- package/dist/actions/focusTrap/index.d.ts.map +1 -0
- package/dist/actions/focusTrap/index.js +5 -0
- package/dist/actions/focusTrap/index.js.map +1 -0
- package/dist/actions/focusTrap/trapStack.d.ts +33 -0
- package/dist/actions/focusTrap/trapStack.d.ts.map +1 -0
- package/dist/actions/focusTrap/trapStack.js +84 -0
- package/dist/actions/focusTrap/trapStack.js.map +1 -0
- package/dist/actions/focusTrap/types.d.ts +50 -0
- package/dist/actions/focusTrap/types.d.ts.map +1 -0
- package/dist/actions/focusTrap/types.js +10 -0
- package/dist/actions/focusTrap/types.js.map +1 -0
- package/dist/actions/focusTrap.d.ts +24 -0
- package/dist/actions/focusTrap.d.ts.map +1 -0
- package/dist/actions/focusTrap.js +201 -0
- package/dist/actions/focusTrap.js.map +1 -0
- package/dist/actions/focusTrap.types.d.ts +50 -0
- package/dist/actions/focusTrap.types.d.ts.map +1 -0
- package/dist/actions/focusTrap.types.js +10 -0
- package/dist/actions/focusTrap.types.js.map +1 -0
- package/dist/actions/focusables.d.ts +39 -0
- package/dist/actions/focusables.d.ts.map +1 -0
- package/dist/actions/focusables.js +142 -0
- package/dist/actions/focusables.js.map +1 -0
- package/dist/actions/index.d.ts +5 -0
- package/dist/actions/index.d.ts.map +1 -0
- package/dist/actions/index.js +5 -0
- package/dist/actions/index.js.map +1 -0
- package/dist/actions/layer/index.d.ts +4 -0
- package/dist/actions/layer/index.d.ts.map +1 -0
- package/dist/actions/layer/index.js +4 -0
- package/dist/actions/layer/index.js.map +1 -0
- package/dist/actions/layer/layer.d.ts +28 -0
- package/dist/actions/layer/layer.d.ts.map +1 -0
- package/dist/actions/layer/layer.js +118 -0
- package/dist/actions/layer/layer.js.map +1 -0
- package/dist/actions/layer/layerStack.d.ts +10 -0
- package/dist/actions/layer/layerStack.d.ts.map +1 -0
- package/dist/actions/layer/layerStack.js +153 -0
- package/dist/actions/layer/layerStack.js.map +1 -0
- package/dist/actions/layer/types.d.ts +105 -0
- package/dist/actions/layer/types.d.ts.map +1 -0
- package/dist/actions/layer/types.js +14 -0
- package/dist/actions/layer/types.js.map +1 -0
- package/dist/actions/layer.d.ts +133 -0
- package/dist/actions/layer.d.ts.map +1 -0
- package/dist/actions/layer.js +269 -0
- package/dist/actions/layer.js.map +1 -0
- package/dist/actions/trapStack.d.ts +33 -0
- package/dist/actions/trapStack.d.ts.map +1 -0
- package/dist/actions/trapStack.js +84 -0
- package/dist/actions/trapStack.js.map +1 -0
- package/dist/client.d.ts +179 -0
- package/dist/client.d.ts.map +1 -0
- package/dist/client.js +176 -0
- package/dist/client.js.map +1 -0
- package/dist/context/index.d.ts +68 -0
- package/dist/context/index.d.ts.map +1 -0
- package/dist/context/index.js +112 -0
- package/dist/context/index.js.map +1 -0
- package/dist/index.d.ts +22 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +30 -0
- package/dist/index.js.map +1 -0
- package/dist/mock/index.d.ts +27 -0
- package/dist/mock/index.d.ts.map +1 -0
- package/dist/mock/index.js +137 -0
- package/dist/mock/index.js.map +1 -0
- package/dist/mock/interceptor.d.ts +19 -0
- package/dist/mock/interceptor.d.ts.map +1 -0
- package/dist/mock/interceptor.js +128 -0
- package/dist/mock/interceptor.js.map +1 -0
- package/dist/mock/types.d.ts +100 -0
- package/dist/mock/types.d.ts.map +1 -0
- package/dist/mock/types.js +27 -0
- package/dist/mock/types.js.map +1 -0
- package/dist/mock/url.d.ts +14 -0
- package/dist/mock/url.d.ts.map +1 -0
- package/dist/mock/url.js +38 -0
- package/dist/mock/url.js.map +1 -0
- package/dist/runes/clickOutside.svelte.d.ts +29 -0
- package/dist/runes/clickOutside.svelte.d.ts.map +1 -0
- package/dist/runes/clickOutside.svelte.js +42 -0
- package/dist/runes/clickOutside.svelte.js.map +1 -0
- package/dist/runes/escape.svelte.d.ts +34 -0
- package/dist/runes/escape.svelte.d.ts.map +1 -0
- package/dist/runes/escape.svelte.js +44 -0
- package/dist/runes/escape.svelte.js.map +1 -0
- package/dist/runes/focusTrap.svelte.d.ts +21 -0
- package/dist/runes/focusTrap.svelte.d.ts.map +1 -0
- package/dist/runes/focusTrap.svelte.js +37 -0
- package/dist/runes/focusTrap.svelte.js.map +1 -0
- package/dist/runes/index.svelte.d.ts +8 -0
- package/dist/runes/index.svelte.d.ts.map +1 -0
- package/dist/runes/index.svelte.js +8 -0
- package/dist/runes/index.svelte.js.map +1 -0
- package/dist/runes/layer.svelte.d.ts +36 -0
- package/dist/runes/layer.svelte.d.ts.map +1 -0
- package/dist/runes/layer.svelte.js +48 -0
- package/dist/runes/layer.svelte.js.map +1 -0
- package/dist/runes/query.svelte.d.ts +104 -0
- package/dist/runes/query.svelte.d.ts.map +1 -0
- package/dist/runes/query.svelte.js +179 -0
- package/dist/runes/query.svelte.js.map +1 -0
- package/dist/runes/state.svelte.d.ts +72 -0
- package/dist/runes/state.svelte.d.ts.map +1 -0
- package/dist/runes/state.svelte.js +98 -0
- package/dist/runes/state.svelte.js.map +1 -0
- package/dist/runes/window.svelte.d.ts +120 -0
- package/dist/runes/window.svelte.d.ts.map +1 -0
- package/dist/runes/window.svelte.js +196 -0
- package/dist/runes/window.svelte.js.map +1 -0
- package/dist/types/index.d.ts +2 -0
- package/dist/types/index.d.ts.map +1 -0
- package/dist/types/index.js +3 -0
- package/dist/types/index.js.map +1 -0
- package/dist/types/nui.d.ts +34 -0
- package/dist/types/nui.d.ts.map +1 -0
- package/dist/types/nui.js +17 -0
- package/dist/types/nui.js.map +1 -0
- package/dist/utils/env.d.ts +21 -0
- package/dist/utils/env.d.ts.map +1 -0
- package/dist/utils/env.js +36 -0
- package/dist/utils/env.js.map +1 -0
- package/dist/utils/error.d.ts +11 -0
- package/dist/utils/error.d.ts.map +1 -0
- package/dist/utils/error.js +30 -0
- package/dist/utils/error.js.map +1 -0
- package/dist/utils/index.d.ts +3 -0
- package/dist/utils/index.d.ts.map +1 -0
- package/dist/utils/index.js +3 -0
- package/dist/utils/index.js.map +1 -0
- package/dist/utils/keyboard.d.ts +127 -0
- package/dist/utils/keyboard.d.ts.map +1 -0
- package/dist/utils/keyboard.js +152 -0
- package/dist/utils/keyboard.js.map +1 -0
- package/package.json +76 -4
- package/src/actions/clickOutside/clickOutside.ts +78 -0
- package/src/actions/clickOutside/handler.ts +49 -0
- package/src/actions/clickOutside/index.ts +11 -0
- package/src/actions/clickOutside/types.ts +54 -0
- package/src/actions/escape/escape.ts +90 -0
- package/src/actions/escape/handler.ts +52 -0
- package/src/actions/escape/index.ts +11 -0
- package/src/actions/escape/types.ts +88 -0
- package/src/actions/focusTrap/focusTrap.ts +228 -0
- package/src/actions/focusTrap/focusables.ts +155 -0
- package/src/actions/focusTrap/index.ts +22 -0
- package/src/actions/focusTrap/trapStack.ts +109 -0
- package/src/actions/focusTrap/types.ts +64 -0
- package/src/actions/index.ts +35 -0
- package/src/actions/layer/index.ts +13 -0
- package/src/actions/layer/layer.ts +140 -0
- package/src/actions/layer/layerStack.ts +169 -0
- package/src/actions/layer/types.ts +132 -0
- package/src/client.ts +323 -0
- package/src/context/index.ts +127 -0
- package/src/index.ts +53 -0
- package/src/mock/index.ts +176 -0
- package/src/mock/interceptor.ts +177 -0
- package/src/mock/types.ts +125 -0
- package/src/mock/url.ts +37 -0
- package/src/runes/clickOutside.svelte.ts +53 -0
- package/src/runes/escape.svelte.ts +71 -0
- package/src/runes/focusTrap.svelte.ts +56 -0
- package/src/runes/index.svelte.ts +38 -0
- package/src/runes/layer.svelte.ts +74 -0
- package/src/runes/query.svelte.ts +313 -0
- package/src/runes/state.svelte.ts +175 -0
- package/src/runes/window.svelte.ts +308 -0
- package/src/utils/env.ts +36 -0
- package/src/utils/index.ts +2 -0
- package/src/utils/keyboard.ts +244 -0
package/dist/client.js
ADDED
|
@@ -0,0 +1,176 @@
|
|
|
1
|
+
import { NuiClient as CoreNuiClient } from '@fivem-nui/core';
|
|
2
|
+
import { installGlobalErrorHandlers } from '@fivem-nui/error';
|
|
3
|
+
/**
|
|
4
|
+
* Svelte NUI Client adapter.
|
|
5
|
+
*
|
|
6
|
+
* Wraps `@fivem-nui/core`'s transport layer with type-safe overloads for contract maps,
|
|
7
|
+
* event listeners, RPC requests, and lifecycle tracking.
|
|
8
|
+
*/
|
|
9
|
+
export class SvelteNuiClient {
|
|
10
|
+
_typedClient;
|
|
11
|
+
_client;
|
|
12
|
+
_listeners = new Set();
|
|
13
|
+
_listening = false;
|
|
14
|
+
/**
|
|
15
|
+
* Creates a new SvelteNuiClient instance.
|
|
16
|
+
*
|
|
17
|
+
* @param options - Configuration options for the client adapter and underlying transport.
|
|
18
|
+
*/
|
|
19
|
+
constructor(options = {}) {
|
|
20
|
+
this._typedClient = options.client ?? new CoreNuiClient(options);
|
|
21
|
+
this._client = this._typedClient;
|
|
22
|
+
if (options.autoInitialize !== false) {
|
|
23
|
+
this.listen();
|
|
24
|
+
}
|
|
25
|
+
if (options.captureGlobalErrors) {
|
|
26
|
+
const errorOpts = typeof options.captureGlobalErrors === 'object' ? options.captureGlobalErrors : {};
|
|
27
|
+
const unsubErrors = installGlobalErrorHandlers(errorOpts);
|
|
28
|
+
this._listeners.add(unsubErrors);
|
|
29
|
+
}
|
|
30
|
+
}
|
|
31
|
+
_ensureListening() {
|
|
32
|
+
if (!this._listening) {
|
|
33
|
+
const unsub = this._client.listen();
|
|
34
|
+
this._listeners.add(unsub);
|
|
35
|
+
this._listening = true;
|
|
36
|
+
}
|
|
37
|
+
}
|
|
38
|
+
on(eventName, handler) {
|
|
39
|
+
this._ensureListening();
|
|
40
|
+
const unsub = this._client.on(eventName, handler);
|
|
41
|
+
this._listeners.add(unsub);
|
|
42
|
+
return () => {
|
|
43
|
+
this._listeners.delete(unsub);
|
|
44
|
+
unsub();
|
|
45
|
+
};
|
|
46
|
+
}
|
|
47
|
+
once(eventName, handler) {
|
|
48
|
+
this._ensureListening();
|
|
49
|
+
let unsub;
|
|
50
|
+
const wrappedHandler = (data) => {
|
|
51
|
+
this._listeners.delete(unsub);
|
|
52
|
+
handler(data);
|
|
53
|
+
};
|
|
54
|
+
unsub = this._client.once(eventName, wrappedHandler);
|
|
55
|
+
this._listeners.add(unsub);
|
|
56
|
+
return () => {
|
|
57
|
+
this._listeners.delete(unsub);
|
|
58
|
+
unsub();
|
|
59
|
+
};
|
|
60
|
+
}
|
|
61
|
+
/**
|
|
62
|
+
* Removes an event listener.
|
|
63
|
+
*
|
|
64
|
+
* @param eventName - Name of the event to stop listening for.
|
|
65
|
+
* @param handler - Specific handler callback to remove. If omitted, removes all handlers for this event.
|
|
66
|
+
*/
|
|
67
|
+
off(eventName, handler) {
|
|
68
|
+
this._client.off(eventName, handler);
|
|
69
|
+
}
|
|
70
|
+
send(eventName, payload) {
|
|
71
|
+
this._ensureListening();
|
|
72
|
+
this._client.send(eventName, payload);
|
|
73
|
+
}
|
|
74
|
+
async sendAndWait(eventName, payload) {
|
|
75
|
+
this._ensureListening();
|
|
76
|
+
await this._client.sendAndWait(eventName, payload);
|
|
77
|
+
}
|
|
78
|
+
async request(eventName, request, timeout, signal) {
|
|
79
|
+
this._ensureListening();
|
|
80
|
+
return this._client.request(eventName, request, timeout, signal);
|
|
81
|
+
}
|
|
82
|
+
// --- Lifecycle Callbacks ---
|
|
83
|
+
/**
|
|
84
|
+
* Sends a notification to a specific native callback endpoint (e.g. `'ready'`, `'close'`).
|
|
85
|
+
*
|
|
86
|
+
* @param callbackName - Name of the native callback endpoint.
|
|
87
|
+
* @param payload - Optional data to send with the notification.
|
|
88
|
+
*/
|
|
89
|
+
notify(callbackName, payload) {
|
|
90
|
+
this._client.notify(callbackName, payload);
|
|
91
|
+
}
|
|
92
|
+
/**
|
|
93
|
+
* Sends a notification and awaits HTTP transmission confirmation.
|
|
94
|
+
*
|
|
95
|
+
* @param callbackName - Name of the native callback endpoint.
|
|
96
|
+
* @param payload - Optional data to send with the notification.
|
|
97
|
+
* @returns Promise that resolves once the HTTP notification is acknowledged.
|
|
98
|
+
*/
|
|
99
|
+
async notifyAndWait(callbackName, payload) {
|
|
100
|
+
await this._client.notifyAndWait(callbackName, payload);
|
|
101
|
+
}
|
|
102
|
+
/**
|
|
103
|
+
* Registers a handler for requests initiated from C# to the UI.
|
|
104
|
+
*
|
|
105
|
+
* @param eventName - Name of the incoming RPC endpoint from C#.
|
|
106
|
+
* @param handler - Handler function returning a promise with response envelope.
|
|
107
|
+
*/
|
|
108
|
+
callback(eventName, handler) {
|
|
109
|
+
this._ensureListening();
|
|
110
|
+
this._client.callback(eventName, handler);
|
|
111
|
+
}
|
|
112
|
+
/**
|
|
113
|
+
* Unregisters an incoming RPC callback handler previously registered with {@link callback}.
|
|
114
|
+
*
|
|
115
|
+
* @param eventName - Name of the RPC endpoint to unregister.
|
|
116
|
+
* @returns True if a handler was registered and removed, false otherwise.
|
|
117
|
+
*/
|
|
118
|
+
unregisterCallback(eventName) {
|
|
119
|
+
return this._client.unregisterCallback(eventName);
|
|
120
|
+
}
|
|
121
|
+
// --- Window Lifecycle ---
|
|
122
|
+
/**
|
|
123
|
+
* Listens for window lifecycle actions from C# (`'open'`, `'close'`, `'focus'`, `'blur'`).
|
|
124
|
+
*
|
|
125
|
+
* @param handler - Callback invoked with the lifecycle action and target window identifier.
|
|
126
|
+
* @returns Unsubscribe function to remove the window action listener.
|
|
127
|
+
*/
|
|
128
|
+
onWindow(handler) {
|
|
129
|
+
this._ensureListening();
|
|
130
|
+
const unsub = this._client.onWindow((action, win) => handler(action, win));
|
|
131
|
+
this._listeners.add(unsub);
|
|
132
|
+
return () => {
|
|
133
|
+
this._listeners.delete(unsub);
|
|
134
|
+
unsub();
|
|
135
|
+
};
|
|
136
|
+
}
|
|
137
|
+
/**
|
|
138
|
+
* Starts listening for NUI message events dispatched to the window.
|
|
139
|
+
*
|
|
140
|
+
* @returns Unsubscribe function to stop listening to window messages.
|
|
141
|
+
*/
|
|
142
|
+
listen() {
|
|
143
|
+
const unsub = this._client.listen();
|
|
144
|
+
this._listeners.add(unsub);
|
|
145
|
+
this._listening = true;
|
|
146
|
+
return unsub;
|
|
147
|
+
}
|
|
148
|
+
/**
|
|
149
|
+
* Returns an untyped view of the underlying transport client.
|
|
150
|
+
*
|
|
151
|
+
* @returns Untyped transport client reference.
|
|
152
|
+
*/
|
|
153
|
+
getClient() {
|
|
154
|
+
return this._client;
|
|
155
|
+
}
|
|
156
|
+
/**
|
|
157
|
+
* Returns the underlying strongly typed `@fivem-nui/core` client instance.
|
|
158
|
+
*
|
|
159
|
+
* @returns The underlying `NuiClient` instance.
|
|
160
|
+
*/
|
|
161
|
+
getTypedClient() {
|
|
162
|
+
return this._typedClient;
|
|
163
|
+
}
|
|
164
|
+
/**
|
|
165
|
+
* Cleans up all active listeners, stops listening, and disposes the underlying transport client.
|
|
166
|
+
*/
|
|
167
|
+
destroy() {
|
|
168
|
+
for (const unsub of this._listeners) {
|
|
169
|
+
unsub();
|
|
170
|
+
}
|
|
171
|
+
this._listeners.clear();
|
|
172
|
+
this._listening = false;
|
|
173
|
+
this._typedClient.dispose();
|
|
174
|
+
}
|
|
175
|
+
}
|
|
176
|
+
//# sourceMappingURL=client.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"client.js","sourceRoot":"","sources":["../src/client.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
import type { SvelteNuiClient } from '../client';
|
|
2
|
+
/**
|
|
3
|
+
* Global Symbol key used for Svelte Context API registration.
|
|
4
|
+
* Scoped with package prefix to prevent realm collisions with other libraries.
|
|
5
|
+
*/
|
|
6
|
+
export declare const NUI_CONTEXT_KEY: unique symbol;
|
|
7
|
+
/**
|
|
8
|
+
* Registers the global default `SvelteNuiClient` instance used when no scoped context is found.
|
|
9
|
+
*
|
|
10
|
+
* @remarks
|
|
11
|
+
* **SSR & CEF Environment**:
|
|
12
|
+
* The default client is a singleton stored on `globalThis` intended for client-side FiveM CEF
|
|
13
|
+
* and SPA environments. In server-side rendering (SSR) environments, avoid relying on global
|
|
14
|
+
* singletons and prefer component-scoped context via `setNuiClient()`.
|
|
15
|
+
*
|
|
16
|
+
* @param client - The client instance to register as the default.
|
|
17
|
+
* @returns The registered client instance for convenient chaining.
|
|
18
|
+
*/
|
|
19
|
+
export declare function setDefaultNuiClient(client: SvelteNuiClient): SvelteNuiClient;
|
|
20
|
+
/**
|
|
21
|
+
* Directly retrieves the global default `SvelteNuiClient` instance without checking Svelte context.
|
|
22
|
+
* Useful in standalone stores, utility files, or outside component initialization.
|
|
23
|
+
*
|
|
24
|
+
* @returns The registered global default client, or `null` if none has been registered.
|
|
25
|
+
*/
|
|
26
|
+
export declare function getDefaultNuiClient(): SvelteNuiClient | null;
|
|
27
|
+
/**
|
|
28
|
+
* Resets the default global client instance to null.
|
|
29
|
+
* Intended for test isolation and teardown.
|
|
30
|
+
*/
|
|
31
|
+
export declare function resetDefaultNuiClient(): void;
|
|
32
|
+
/**
|
|
33
|
+
* Provides a `SvelteNuiClient` instance to the component hierarchy via Svelte's Context API.
|
|
34
|
+
*
|
|
35
|
+
* @param client - The client instance to provide to child components.
|
|
36
|
+
* @returns The provided client instance for convenient inline assignment.
|
|
37
|
+
*
|
|
38
|
+
* @example
|
|
39
|
+
* ```svelte
|
|
40
|
+
* <script>
|
|
41
|
+
* import { setNuiClient, SvelteNuiClient } from '@fivem-nui/svelte';
|
|
42
|
+
* const client = setNuiClient(new SvelteNuiClient());
|
|
43
|
+
* </script>
|
|
44
|
+
* ```
|
|
45
|
+
*/
|
|
46
|
+
export declare function setNuiClient(client: SvelteNuiClient): SvelteNuiClient;
|
|
47
|
+
/**
|
|
48
|
+
* Retrieves the currently active `SvelteNuiClient`.
|
|
49
|
+
*
|
|
50
|
+
* Resolution priority order:
|
|
51
|
+
* 1. **Component Context**: Scoped client provided via `setNuiClient()` in an ancestor component
|
|
52
|
+
* (checked safely; outside component lifecycle, this step is skipped).
|
|
53
|
+
* 2. **Explicit Override**: `fallbackClient` argument passed directly to `useNuiClient(fallbackClient)`.
|
|
54
|
+
* 3. **Global Default**: Singleton client registered via `setDefaultNuiClient()` or the default `nui` instance
|
|
55
|
+
* registered upon importing the root package entrypoint (`src/index.ts`).
|
|
56
|
+
*
|
|
57
|
+
* @remarks
|
|
58
|
+
* **Lifecycle Safety**:
|
|
59
|
+
* Svelte's `hasContext()` / `getContext()` throw a `lifecycle_outside_component` runtime error
|
|
60
|
+
* when invoked outside component initialization (e.g. in async handlers, stores, or outside component trees).
|
|
61
|
+
* This function safely catches that error to allow graceful fallback to the explicit or global client.
|
|
62
|
+
*
|
|
63
|
+
* @param fallbackClient - Optional client to use if no scoped context is found.
|
|
64
|
+
* @returns The resolved `SvelteNuiClient`.
|
|
65
|
+
* @throws Error if no client is found in context, fallback, or default singleton.
|
|
66
|
+
*/
|
|
67
|
+
export declare function useNuiClient(fallbackClient?: SvelteNuiClient): SvelteNuiClient;
|
|
68
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/context/index.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,WAAW,CAAC;AAEjD;;;GAGG;AACH,eAAO,MAAM,eAAe,eAAyC,CAAC;AAmBtE;;;;;;;;;;;GAWG;AACH,wBAAgB,mBAAmB,CAAC,MAAM,EAAE,eAAe,GAAG,eAAe,CAW5E;AAED;;;;;GAKG;AACH,wBAAgB,mBAAmB,IAAI,eAAe,GAAG,IAAI,CAE5D;AAED;;;GAGG;AACH,wBAAgB,qBAAqB,IAAI,IAAI,CAE5C;AAED;;;;;;;;;;;;;GAaG;AACH,wBAAgB,YAAY,CAAC,MAAM,EAAE,eAAe,GAAG,eAAe,CAGrE;AAED;;;;;;;;;;;;;;;;;;;GAmBG;AACH,wBAAgB,YAAY,CAAC,cAAc,CAAC,EAAE,eAAe,GAAG,eAAe,CAkB9E"}
|
|
@@ -0,0 +1,112 @@
|
|
|
1
|
+
import { getContext, setContext, hasContext } from 'svelte';
|
|
2
|
+
/**
|
|
3
|
+
* Global Symbol key used for Svelte Context API registration.
|
|
4
|
+
* Scoped with package prefix to prevent realm collisions with other libraries.
|
|
5
|
+
*/
|
|
6
|
+
export const NUI_CONTEXT_KEY = Symbol.for('@fivem-nui/svelte:client');
|
|
7
|
+
/**
|
|
8
|
+
* Global Symbol key used to store the default client singleton on `globalThis`.
|
|
9
|
+
* Ensures duplicate package copies (e.g. nested node_modules or micro-frontends)
|
|
10
|
+
* share the same default client instance.
|
|
11
|
+
*/
|
|
12
|
+
const GLOBAL_DEFAULT_KEY = Symbol.for('@fivem-nui/svelte:default-client');
|
|
13
|
+
function getDefaultClient() {
|
|
14
|
+
const g = globalThis;
|
|
15
|
+
return g[GLOBAL_DEFAULT_KEY] ?? null;
|
|
16
|
+
}
|
|
17
|
+
function setDefaultClient(client) {
|
|
18
|
+
const g = globalThis;
|
|
19
|
+
g[GLOBAL_DEFAULT_KEY] = client;
|
|
20
|
+
}
|
|
21
|
+
/**
|
|
22
|
+
* Registers the global default `SvelteNuiClient` instance used when no scoped context is found.
|
|
23
|
+
*
|
|
24
|
+
* @remarks
|
|
25
|
+
* **SSR & CEF Environment**:
|
|
26
|
+
* The default client is a singleton stored on `globalThis` intended for client-side FiveM CEF
|
|
27
|
+
* and SPA environments. In server-side rendering (SSR) environments, avoid relying on global
|
|
28
|
+
* singletons and prefer component-scoped context via `setNuiClient()`.
|
|
29
|
+
*
|
|
30
|
+
* @param client - The client instance to register as the default.
|
|
31
|
+
* @returns The registered client instance for convenient chaining.
|
|
32
|
+
*/
|
|
33
|
+
export function setDefaultNuiClient(client) {
|
|
34
|
+
const current = getDefaultClient();
|
|
35
|
+
const isHmr = typeof import.meta !== 'undefined' && Boolean(import.meta?.hot);
|
|
36
|
+
if (!isHmr && current !== null && current !== client) {
|
|
37
|
+
console.warn('[fivem-nui-svelte] setDefaultNuiClient called with a new client instance while a default client was already registered. Overwriting default client.');
|
|
38
|
+
}
|
|
39
|
+
setDefaultClient(client);
|
|
40
|
+
return client;
|
|
41
|
+
}
|
|
42
|
+
/**
|
|
43
|
+
* Directly retrieves the global default `SvelteNuiClient` instance without checking Svelte context.
|
|
44
|
+
* Useful in standalone stores, utility files, or outside component initialization.
|
|
45
|
+
*
|
|
46
|
+
* @returns The registered global default client, or `null` if none has been registered.
|
|
47
|
+
*/
|
|
48
|
+
export function getDefaultNuiClient() {
|
|
49
|
+
return getDefaultClient();
|
|
50
|
+
}
|
|
51
|
+
/**
|
|
52
|
+
* Resets the default global client instance to null.
|
|
53
|
+
* Intended for test isolation and teardown.
|
|
54
|
+
*/
|
|
55
|
+
export function resetDefaultNuiClient() {
|
|
56
|
+
setDefaultClient(null);
|
|
57
|
+
}
|
|
58
|
+
/**
|
|
59
|
+
* Provides a `SvelteNuiClient` instance to the component hierarchy via Svelte's Context API.
|
|
60
|
+
*
|
|
61
|
+
* @param client - The client instance to provide to child components.
|
|
62
|
+
* @returns The provided client instance for convenient inline assignment.
|
|
63
|
+
*
|
|
64
|
+
* @example
|
|
65
|
+
* ```svelte
|
|
66
|
+
* <script>
|
|
67
|
+
* import { setNuiClient, SvelteNuiClient } from '@fivem-nui/svelte';
|
|
68
|
+
* const client = setNuiClient(new SvelteNuiClient());
|
|
69
|
+
* </script>
|
|
70
|
+
* ```
|
|
71
|
+
*/
|
|
72
|
+
export function setNuiClient(client) {
|
|
73
|
+
setContext(NUI_CONTEXT_KEY, client);
|
|
74
|
+
return client;
|
|
75
|
+
}
|
|
76
|
+
/**
|
|
77
|
+
* Retrieves the currently active `SvelteNuiClient`.
|
|
78
|
+
*
|
|
79
|
+
* Resolution priority order:
|
|
80
|
+
* 1. **Component Context**: Scoped client provided via `setNuiClient()` in an ancestor component
|
|
81
|
+
* (checked safely; outside component lifecycle, this step is skipped).
|
|
82
|
+
* 2. **Explicit Override**: `fallbackClient` argument passed directly to `useNuiClient(fallbackClient)`.
|
|
83
|
+
* 3. **Global Default**: Singleton client registered via `setDefaultNuiClient()` or the default `nui` instance
|
|
84
|
+
* registered upon importing the root package entrypoint (`src/index.ts`).
|
|
85
|
+
*
|
|
86
|
+
* @remarks
|
|
87
|
+
* **Lifecycle Safety**:
|
|
88
|
+
* Svelte's `hasContext()` / `getContext()` throw a `lifecycle_outside_component` runtime error
|
|
89
|
+
* when invoked outside component initialization (e.g. in async handlers, stores, or outside component trees).
|
|
90
|
+
* This function safely catches that error to allow graceful fallback to the explicit or global client.
|
|
91
|
+
*
|
|
92
|
+
* @param fallbackClient - Optional client to use if no scoped context is found.
|
|
93
|
+
* @returns The resolved `SvelteNuiClient`.
|
|
94
|
+
* @throws Error if no client is found in context, fallback, or default singleton.
|
|
95
|
+
*/
|
|
96
|
+
export function useNuiClient(fallbackClient) {
|
|
97
|
+
try {
|
|
98
|
+
if (hasContext(NUI_CONTEXT_KEY)) {
|
|
99
|
+
return getContext(NUI_CONTEXT_KEY);
|
|
100
|
+
}
|
|
101
|
+
}
|
|
102
|
+
catch {
|
|
103
|
+
// Outside component initialization lifecycle (e.g. async handler, store, or external helper).
|
|
104
|
+
// Safely proceed to explicit fallback or global default client.
|
|
105
|
+
}
|
|
106
|
+
const client = fallbackClient ?? getDefaultClient();
|
|
107
|
+
if (!client) {
|
|
108
|
+
throw new Error('[fivem-nui-svelte] No NuiClient available. Call setNuiClient(client) in a parent component, provide an explicit client argument to useNuiClient(fallback), or register a default client via setDefaultNuiClient(client) at startup.');
|
|
109
|
+
}
|
|
110
|
+
return client;
|
|
111
|
+
}
|
|
112
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/context/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,EAAE,UAAU,EAAE,UAAU,EAAE,MAAM,QAAQ,CAAC;AAG5D;;;GAGG;AACH,MAAM,CAAC,MAAM,eAAe,GAAG,MAAM,CAAC,GAAG,CAAC,0BAA0B,CAAC,CAAC;AAEtE;;;;GAIG;AACH,MAAM,kBAAkB,GAAG,MAAM,CAAC,GAAG,CAAC,kCAAkC,CAAC,CAAC;AAE1E,SAAS,gBAAgB;IACvB,MAAM,CAAC,GAAG,UAA0E,CAAC;IACrF,OAAO,CAAC,CAAC,kBAAkB,CAAC,IAAI,IAAI,CAAC;AACvC,CAAC;AAED,SAAS,gBAAgB,CAAC,MAA8B;IACtD,MAAM,CAAC,GAAG,UAA0E,CAAC;IACrF,CAAC,CAAC,kBAAkB,CAAC,GAAG,MAAM,CAAC;AACjC,CAAC;AAED;;;;;;;;;;;GAWG;AACH,MAAM,UAAU,mBAAmB,CAAC,MAAuB;IACzD,MAAM,OAAO,GAAG,gBAAgB,EAAE,CAAC;IACnC,MAAM,KAAK,GAAG,OAAO,OAAO,IAAI,KAAK,WAAW,IAAI,OAAO,CAAE,OAAO,IAAY,EAAE,GAAG,CAAC,CAAC;IAEvF,IAAI,CAAC,KAAK,IAAI,OAAO,KAAK,IAAI,IAAI,OAAO,KAAK,MAAM,EAAE,CAAC;QACrD,OAAO,CAAC,IAAI,CACV,qJAAqJ,CACtJ,CAAC;IACJ,CAAC;IACD,gBAAgB,CAAC,MAAM,CAAC,CAAC;IACzB,OAAO,MAAM,CAAC;AAChB,CAAC;AAED;;;;;GAKG;AACH,MAAM,UAAU,mBAAmB;IACjC,OAAO,gBAAgB,EAAE,CAAC;AAC5B,CAAC;AAED;;;GAGG;AACH,MAAM,UAAU,qBAAqB;IACnC,gBAAgB,CAAC,IAAI,CAAC,CAAC;AACzB,CAAC;AAED;;;;;;;;;;;;;GAaG;AACH,MAAM,UAAU,YAAY,CAAC,MAAuB;IAClD,UAAU,CAAC,eAAe,EAAE,MAAM,CAAC,CAAC;IACpC,OAAO,MAAM,CAAC;AAChB,CAAC;AAED;;;;;;;;;;;;;;;;;;;GAmBG;AACH,MAAM,UAAU,YAAY,CAAC,cAAgC;IAC3D,IAAI,CAAC;QACH,IAAI,UAAU,CAAC,eAAe,CAAC,EAAE,CAAC;YAChC,OAAO,UAAU,CAAkB,eAAe,CAAC,CAAC;QACtD,CAAC;IACH,CAAC;IAAC,MAAM,CAAC;QACP,8FAA8F;QAC9F,gEAAgE;IAClE,CAAC;IAED,MAAM,MAAM,GAAG,cAAc,IAAI,gBAAgB,EAAE,CAAC;IACpD,IAAI,CAAC,MAAM,EAAE,CAAC;QACZ,MAAM,IAAI,KAAK,CACb,qOAAqO,CACtO,CAAC;IACJ,CAAC;IAED,OAAO,MAAM,CAAC;AAChB,CAAC"}
|
package/dist/index.d.ts
ADDED
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
import { SvelteNuiClient, type SvelteNuiClientOptions } from './client';
|
|
2
|
+
/**
|
|
3
|
+
* Default global `SvelteNuiClient` singleton instance.
|
|
4
|
+
* Automatically registered with {@link setDefaultNuiClient}.
|
|
5
|
+
*/
|
|
6
|
+
export declare const nui: SvelteNuiClient;
|
|
7
|
+
/**
|
|
8
|
+
* Creates a new custom `SvelteNuiClient` instance.
|
|
9
|
+
*
|
|
10
|
+
* @param options - Configuration options for the client.
|
|
11
|
+
* @returns A new `SvelteNuiClient` instance.
|
|
12
|
+
*/
|
|
13
|
+
export declare function createNui(options?: SvelteNuiClientOptions): SvelteNuiClient;
|
|
14
|
+
export { SvelteNuiClient, type SvelteNuiClientOptions };
|
|
15
|
+
export * from './context';
|
|
16
|
+
export * from './runes/index.svelte';
|
|
17
|
+
export * from './actions';
|
|
18
|
+
export * from './utils';
|
|
19
|
+
export * from './mock';
|
|
20
|
+
export * from '@fivem-nui/error';
|
|
21
|
+
export type { NuiEventMap, NuiEventKey, NuiEventRequest, NuiEventResponse, NuiEventPayload, SendPayload, RequestPayload, RequestResponse, NuiWindowAction, NuiMessage, NuiError } from '@fivem-nui/core';
|
|
22
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAGA,OAAO,EAAE,eAAe,EAAE,KAAK,sBAAsB,EAAE,MAAM,UAAU,CAAC;AAKxE;;;GAGG;AACH,eAAO,MAAM,GAAG,iBAAwB,CAAC;AAGzC;;;;;GAKG;AACH,wBAAgB,SAAS,CAAC,OAAO,CAAC,EAAE,sBAAsB,GAAG,eAAe,CAE3E;AAID,OAAO,EAAE,eAAe,EAAE,KAAK,sBAAsB,EAAE,CAAC;AAIxD,cAAc,WAAW,CAAC;AAC1B,cAAc,sBAAsB,CAAC;AACrC,cAAc,WAAW,CAAC;AAC1B,cAAc,SAAS,CAAC;AACxB,cAAc,QAAQ,CAAC;AACvB,cAAc,kBAAkB,CAAC;AAIjC,YAAY,EACV,WAAW,EACX,WAAW,EACX,eAAe,EACf,gBAAgB,EAChB,eAAe,EACf,WAAW,EACX,cAAc,EACd,eAAe,EACf,eAAe,EACf,UAAU,EACV,QAAQ,EACT,MAAM,iBAAiB,CAAC"}
|
package/dist/index.js
ADDED
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
// Main entrypoint for @fivem-nui/svelte
|
|
2
|
+
// High-performance Svelte SDK for FiveM NUI
|
|
3
|
+
import { SvelteNuiClient } from './client';
|
|
4
|
+
import { setDefaultNuiClient } from './context';
|
|
5
|
+
// ===== GLOBAL CLIENT SINGLETON & FACTORY =====
|
|
6
|
+
/**
|
|
7
|
+
* Default global `SvelteNuiClient` singleton instance.
|
|
8
|
+
* Automatically registered with {@link setDefaultNuiClient}.
|
|
9
|
+
*/
|
|
10
|
+
export const nui = new SvelteNuiClient();
|
|
11
|
+
setDefaultNuiClient(nui);
|
|
12
|
+
/**
|
|
13
|
+
* Creates a new custom `SvelteNuiClient` instance.
|
|
14
|
+
*
|
|
15
|
+
* @param options - Configuration options for the client.
|
|
16
|
+
* @returns A new `SvelteNuiClient` instance.
|
|
17
|
+
*/
|
|
18
|
+
export function createNui(options) {
|
|
19
|
+
return new SvelteNuiClient(options);
|
|
20
|
+
}
|
|
21
|
+
// ===== CLIENT CLASS & TYPES =====
|
|
22
|
+
export { SvelteNuiClient };
|
|
23
|
+
// ===== DOMAINS RE-EXPORTS =====
|
|
24
|
+
export * from './context';
|
|
25
|
+
export * from './runes/index.svelte';
|
|
26
|
+
export * from './actions';
|
|
27
|
+
export * from './utils';
|
|
28
|
+
export * from './mock';
|
|
29
|
+
export * from '@fivem-nui/error';
|
|
30
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,wCAAwC;AACxC,4CAA4C;AAE5C,OAAO,EAAE,eAAe,EAA+B,MAAM,UAAU,CAAC;AACxE,OAAO,EAAE,mBAAmB,EAAE,MAAM,WAAW,CAAC;AAEhD,gDAAgD;AAEhD;;;GAGG;AACH,MAAM,CAAC,MAAM,GAAG,GAAG,IAAI,eAAe,EAAE,CAAC;AACzC,mBAAmB,CAAC,GAAG,CAAC,CAAC;AAEzB;;;;;GAKG;AACH,MAAM,UAAU,SAAS,CAAC,OAAgC;IACxD,OAAO,IAAI,eAAe,CAAC,OAAO,CAAC,CAAC;AACtC,CAAC;AAED,mCAAmC;AAEnC,OAAO,EAAE,eAAe,EAA+B,CAAC;AAExD,iCAAiC;AAEjC,cAAc,WAAW,CAAC;AAC1B,cAAc,sBAAsB,CAAC;AACrC,cAAc,WAAW,CAAC;AAC1B,cAAc,SAAS,CAAC;AACxB,cAAc,QAAQ,CAAC;AACvB,cAAc,kBAAkB,CAAC"}
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
import { type NuiMockOptions, type NuiMockController, NuiMessageType } from './types';
|
|
2
|
+
export { NuiMessageType };
|
|
3
|
+
export type { NuiMockOptions, NuiMockController };
|
|
4
|
+
export { isNuiUrl, parseNuiUrl } from './url';
|
|
5
|
+
export { createFetchInterceptor, extractRequestBody } from './interceptor';
|
|
6
|
+
/**
|
|
7
|
+
* Sets up a browser mock environment for FiveM NUI.
|
|
8
|
+
*
|
|
9
|
+
* Intercepts POST requests sent to `https://<resource>/<callback>` and
|
|
10
|
+
* responds with mock data when running outside FiveM CEF.
|
|
11
|
+
*
|
|
12
|
+
* @param options - Configuration options for the mock environment.
|
|
13
|
+
* @returns Controller for emitting simulated events and registering dynamic mocks.
|
|
14
|
+
*
|
|
15
|
+
* @example
|
|
16
|
+
* ```ts
|
|
17
|
+
* import { setupNuiMock } from '@fivem-nui/svelte';
|
|
18
|
+
*
|
|
19
|
+
* const mock = setupNuiMock({
|
|
20
|
+
* requests: {
|
|
21
|
+
* getPlayerData: () => ({ id: 1, name: 'John Doe' })
|
|
22
|
+
* }
|
|
23
|
+
* });
|
|
24
|
+
* ```
|
|
25
|
+
*/
|
|
26
|
+
export declare function setupNuiMock(options?: NuiMockOptions): NuiMockController;
|
|
27
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/mock/index.ts"],"names":[],"mappings":"AAEA,OAAO,EACL,KAAK,cAAc,EACnB,KAAK,iBAAiB,EACtB,cAAc,EAEf,MAAM,SAAS,CAAC;AAGjB,OAAO,EAAE,cAAc,EAAE,CAAC;AAC1B,YAAY,EAAE,cAAc,EAAE,iBAAiB,EAAE,CAAC;AAClD,OAAO,EAAE,QAAQ,EAAE,WAAW,EAAE,MAAM,OAAO,CAAC;AAC9C,OAAO,EAAE,sBAAsB,EAAE,kBAAkB,EAAE,MAAM,eAAe,CAAC;AAE3E;;;;;;;;;;;;;;;;;;;GAmBG;AACH,wBAAgB,YAAY,CAAC,OAAO,GAAE,cAAmB,GAAG,iBAAiB,CA4I5E"}
|
|
@@ -0,0 +1,137 @@
|
|
|
1
|
+
import { isNui, getResourceName } from '../utils/env';
|
|
2
|
+
import { NuiMessageType, NOOP_CONTROLLER } from './types';
|
|
3
|
+
import { createFetchInterceptor } from './interceptor';
|
|
4
|
+
export { NuiMessageType };
|
|
5
|
+
export { isNuiUrl, parseNuiUrl } from './url';
|
|
6
|
+
export { createFetchInterceptor, extractRequestBody } from './interceptor';
|
|
7
|
+
/**
|
|
8
|
+
* Sets up a browser mock environment for FiveM NUI.
|
|
9
|
+
*
|
|
10
|
+
* Intercepts POST requests sent to `https://<resource>/<callback>` and
|
|
11
|
+
* responds with mock data when running outside FiveM CEF.
|
|
12
|
+
*
|
|
13
|
+
* @param options - Configuration options for the mock environment.
|
|
14
|
+
* @returns Controller for emitting simulated events and registering dynamic mocks.
|
|
15
|
+
*
|
|
16
|
+
* @example
|
|
17
|
+
* ```ts
|
|
18
|
+
* import { setupNuiMock } from '@fivem-nui/svelte';
|
|
19
|
+
*
|
|
20
|
+
* const mock = setupNuiMock({
|
|
21
|
+
* requests: {
|
|
22
|
+
* getPlayerData: () => ({ id: 1, name: 'John Doe' })
|
|
23
|
+
* }
|
|
24
|
+
* });
|
|
25
|
+
* ```
|
|
26
|
+
*/
|
|
27
|
+
export function setupNuiMock(options = {}) {
|
|
28
|
+
const { requests = {}, callbacks = {}, onSend: sendHandlers = {}, latencyMs = 50, log = true, resourceName: customResource } = options;
|
|
29
|
+
// 1. SSR check first to avoid referencing window when unavailable
|
|
30
|
+
if (typeof window === 'undefined') {
|
|
31
|
+
return NOOP_CONTROLLER;
|
|
32
|
+
}
|
|
33
|
+
// 2. In CEF FiveM, the mock interceptor must remain disabled
|
|
34
|
+
if (isNui()) {
|
|
35
|
+
if (log) {
|
|
36
|
+
console.info('[fivem-nui-svelte] Running inside FiveM CEF - mock interceptor disabled.');
|
|
37
|
+
}
|
|
38
|
+
return NOOP_CONTROLLER;
|
|
39
|
+
}
|
|
40
|
+
// 3. Clean up any previously active mock instance (e.g. on Vite HMR reload)
|
|
41
|
+
if (window.__nuiMock && typeof window.__nuiMock.destroy === 'function') {
|
|
42
|
+
window.__nuiMock.destroy();
|
|
43
|
+
}
|
|
44
|
+
const targetResource = customResource || getResourceName('') || 'nui';
|
|
45
|
+
const activeRequests = { ...requests };
|
|
46
|
+
const activeCallbacks = { ...callbacks };
|
|
47
|
+
const activeSendHandlers = { ...sendHandlers };
|
|
48
|
+
const originalFetch = window.fetch;
|
|
49
|
+
function emitEvent(eventName, payload, delayMs) {
|
|
50
|
+
const dispatch = () => {
|
|
51
|
+
if (log) {
|
|
52
|
+
console.debug(`[NUI Mock] <- EVENT '${eventName}'`, payload);
|
|
53
|
+
}
|
|
54
|
+
window.postMessage({
|
|
55
|
+
type: NuiMessageType.Event,
|
|
56
|
+
event: eventName,
|
|
57
|
+
payload,
|
|
58
|
+
// 'data' preserved alongside 'payload' for backward compatibility with legacy scripts
|
|
59
|
+
data: payload
|
|
60
|
+
}, '*');
|
|
61
|
+
};
|
|
62
|
+
if (delayMs && delayMs > 0) {
|
|
63
|
+
setTimeout(dispatch, delayMs);
|
|
64
|
+
}
|
|
65
|
+
else {
|
|
66
|
+
dispatch();
|
|
67
|
+
}
|
|
68
|
+
}
|
|
69
|
+
function emitWindow(action, windowName, delayMs) {
|
|
70
|
+
const dispatch = () => {
|
|
71
|
+
if (log) {
|
|
72
|
+
console.debug(`[NUI Mock] <- WINDOW action='${action}' window='${windowName ?? '*'}'`);
|
|
73
|
+
}
|
|
74
|
+
window.postMessage({
|
|
75
|
+
type: action,
|
|
76
|
+
event: windowName,
|
|
77
|
+
action,
|
|
78
|
+
window: windowName
|
|
79
|
+
}, '*');
|
|
80
|
+
};
|
|
81
|
+
if (delayMs && delayMs > 0) {
|
|
82
|
+
setTimeout(dispatch, delayMs);
|
|
83
|
+
}
|
|
84
|
+
else {
|
|
85
|
+
dispatch();
|
|
86
|
+
}
|
|
87
|
+
}
|
|
88
|
+
const interceptedFetch = createFetchInterceptor({
|
|
89
|
+
targetResource,
|
|
90
|
+
latencyMs,
|
|
91
|
+
log,
|
|
92
|
+
activeRequests,
|
|
93
|
+
activeCallbacks,
|
|
94
|
+
activeSendHandlers,
|
|
95
|
+
originalFetch
|
|
96
|
+
});
|
|
97
|
+
window.fetch = interceptedFetch;
|
|
98
|
+
const controller = {
|
|
99
|
+
emitEvent,
|
|
100
|
+
emitWindow,
|
|
101
|
+
mockRequest(eventName, handler) {
|
|
102
|
+
activeRequests[eventName] = handler;
|
|
103
|
+
return () => {
|
|
104
|
+
if (activeRequests[eventName] === handler) {
|
|
105
|
+
delete activeRequests[eventName];
|
|
106
|
+
}
|
|
107
|
+
};
|
|
108
|
+
},
|
|
109
|
+
removeRequest(eventName) {
|
|
110
|
+
delete activeRequests[eventName];
|
|
111
|
+
},
|
|
112
|
+
onSend(eventName, handler) {
|
|
113
|
+
activeSendHandlers[eventName] = handler;
|
|
114
|
+
return () => {
|
|
115
|
+
if (activeSendHandlers[eventName] === handler) {
|
|
116
|
+
delete activeSendHandlers[eventName];
|
|
117
|
+
}
|
|
118
|
+
};
|
|
119
|
+
},
|
|
120
|
+
destroy() {
|
|
121
|
+
if (typeof window !== 'undefined') {
|
|
122
|
+
if (window.fetch === interceptedFetch) {
|
|
123
|
+
window.fetch = originalFetch;
|
|
124
|
+
}
|
|
125
|
+
if (window.__nuiMock === controller) {
|
|
126
|
+
delete window.__nuiMock;
|
|
127
|
+
}
|
|
128
|
+
}
|
|
129
|
+
}
|
|
130
|
+
};
|
|
131
|
+
window.__nuiMock = controller;
|
|
132
|
+
if (log) {
|
|
133
|
+
console.info(`[fivem-nui-svelte] Mock interceptor active for resource '${targetResource}'. window.__nuiMock ready.`);
|
|
134
|
+
}
|
|
135
|
+
return controller;
|
|
136
|
+
}
|
|
137
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/mock/index.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
export interface InterceptorContext {
|
|
2
|
+
targetResource: string;
|
|
3
|
+
latencyMs: number;
|
|
4
|
+
log: boolean;
|
|
5
|
+
activeRequests: Record<string, (payload: any) => Promise<any> | any>;
|
|
6
|
+
activeCallbacks: Record<string, (payload: any) => void>;
|
|
7
|
+
activeSendHandlers: Record<string, (payload: any) => void>;
|
|
8
|
+
originalFetch: typeof window.fetch;
|
|
9
|
+
}
|
|
10
|
+
/**
|
|
11
|
+
* Extracts the body payload from a `fetch` invocation, supporting both `init.body`
|
|
12
|
+
* and body text inside a `Request` instance.
|
|
13
|
+
*/
|
|
14
|
+
export declare function extractRequestBody(input: RequestInfo | URL, init?: RequestInit): Promise<any>;
|
|
15
|
+
/**
|
|
16
|
+
* Creates the `window.fetch` interceptor function that simulates FiveM CEF transport.
|
|
17
|
+
*/
|
|
18
|
+
export declare function createFetchInterceptor(ctx: InterceptorContext): typeof window.fetch;
|
|
19
|
+
//# sourceMappingURL=interceptor.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"interceptor.d.ts","sourceRoot":"","sources":["../../src/mock/interceptor.ts"],"names":[],"mappings":"AAEA,MAAM,WAAW,kBAAkB;IACjC,cAAc,EAAE,MAAM,CAAC;IACvB,SAAS,EAAE,MAAM,CAAC;IAClB,GAAG,EAAE,OAAO,CAAC;IACb,cAAc,EAAE,MAAM,CAAC,MAAM,EAAE,CAAC,OAAO,EAAE,GAAG,KAAK,OAAO,CAAC,GAAG,CAAC,GAAG,GAAG,CAAC,CAAC;IACrE,eAAe,EAAE,MAAM,CAAC,MAAM,EAAE,CAAC,OAAO,EAAE,GAAG,KAAK,IAAI,CAAC,CAAC;IACxD,kBAAkB,EAAE,MAAM,CAAC,MAAM,EAAE,CAAC,OAAO,EAAE,GAAG,KAAK,IAAI,CAAC,CAAC;IAC3D,aAAa,EAAE,OAAO,MAAM,CAAC,KAAK,CAAC;CACpC;AAED;;;GAGG;AACH,wBAAsB,kBAAkB,CACtC,KAAK,EAAE,WAAW,GAAG,GAAG,EACxB,IAAI,CAAC,EAAE,WAAW,GACjB,OAAO,CAAC,GAAG,CAAC,CAkBd;AAED;;GAEG;AACH,wBAAgB,sBAAsB,CAAC,GAAG,EAAE,kBAAkB,GAAG,OAAO,MAAM,CAAC,KAAK,CAsInF"}
|