jsgui3-server 0.0.138 → 0.0.140
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/AGENTS.md +87 -0
- package/README.md +12 -0
- package/docs/GUIDE_TO_AGENTIC_WORKFLOWS_BY_GROK.md +19 -0
- package/docs/advanced-usage-examples.md +1360 -0
- package/docs/agent-development-guide.md +386 -0
- package/docs/api-reference.md +916 -0
- package/docs/broken-functionality-tracker.md +285 -0
- package/docs/bundling-system-deep-dive.md +525 -0
- package/docs/cli-reference.md +393 -0
- package/docs/comprehensive-documentation.md +1403 -0
- package/docs/configuration-reference.md +808 -0
- package/docs/controls-development.md +859 -0
- package/docs/documentation-review/CURRENT_REVIEW.md +95 -0
- package/docs/function-publishers-json-apis.md +847 -0
- package/docs/getting-started-with-json.md +518 -0
- package/docs/minification-compression-sourcemaps-status.md +482 -0
- package/docs/minification-compression-sourcemaps-test-results.md +205 -0
- package/docs/publishers-guide.md +313 -0
- package/docs/resources-guide.md +615 -0
- package/docs/serve-helpers.md +406 -0
- package/docs/simple-server-api-design.md +13 -0
- package/docs/system-architecture.md +275 -0
- package/docs/troubleshooting.md +698 -0
- package/examples/json/README.md +115 -0
- package/examples/json/basic-api/README.md +345 -0
- package/examples/json/basic-api/server.js +199 -0
- package/examples/json/simple-api/README.md +125 -0
- package/examples/json/simple-api/diagnostic-report.json +73 -0
- package/examples/json/simple-api/diagnostic-test.js +433 -0
- package/examples/json/simple-api/server-debug.md +58 -0
- package/examples/json/simple-api/server.js +91 -0
- package/examples/json/simple-api/test.js +215 -0
- package/http/responders/static/Static_Route_HTTP_Responder.js +1 -2
- package/package.json +19 -8
- package/publishers/helpers/assigners/static-compressed-response-buffers/Single_Control_Webpage_Server_Static_Compressed_Response_Buffers_Assigner.js +65 -12
- package/publishers/helpers/preparers/static/bundle/Static_Routes_Responses_Webpage_Bundle_Preparer.js +6 -1
- package/publishers/http-function-publisher.js +59 -38
- package/publishers/http-webpage-publisher.js +48 -1
- package/resources/processors/bundlers/js/esbuild/Advanced_JS_Bundler_Using_ESBuild.js +38 -146
- package/resources/processors/bundlers/js/esbuild/Core_JS_Non_Minifying_Bundler_Using_ESBuild.js +54 -5
- package/resources/processors/bundlers/js/esbuild/Core_JS_Single_File_Minifying_Bundler_Using_ESBuild.js +36 -4
- package/serve-factory.js +36 -9
- package/server.js +10 -4
- package/test-report.json +0 -0
- package/tests/README.md +250 -0
- package/tests/assigners.test.js +316 -0
- package/tests/bundlers.test.js +329 -0
- package/tests/configuration-validation.test.js +530 -0
- package/tests/content-analysis.test.js +641 -0
- package/tests/end-to-end.test.js +496 -0
- package/tests/error-handling.test.js +746 -0
- package/tests/performance.test.js +653 -0
- package/tests/publishers.test.js +395 -0
- package/tests/temp_invalid.js +7 -0
- package/tests/temp_invalid_utf8.js +1 -0
- package/tests/temp_malformed.js +10 -0
- package/tests/test-runner.js +261 -0
|
@@ -0,0 +1,406 @@
|
|
|
1
|
+
# Serve Helpers Reference
|
|
2
|
+
|
|
3
|
+
## When to Read
|
|
4
|
+
|
|
5
|
+
This document explains the internal helper utilities used by the Server.serve() API. Read this when:
|
|
6
|
+
- You need to understand how JSGUI3 Server automatically discovers and loads client files
|
|
7
|
+
- You're extending the server with custom client discovery logic
|
|
8
|
+
- You want to understand the configuration resolution process
|
|
9
|
+
- You're debugging issues with automatic client file detection
|
|
10
|
+
- You need to implement similar auto-discovery patterns in your own code
|
|
11
|
+
|
|
12
|
+
**Note:** This is an internal API reference. For end-user documentation, see [README.md](../README.md). For CLI usage, see [docs/cli-reference.md](docs/cli-reference.md).
|
|
13
|
+
|
|
14
|
+
## Overview
|
|
15
|
+
|
|
16
|
+
The serve helpers provide automatic client file discovery, configuration resolution, and utility functions that make the `Server.serve()` API work seamlessly. These utilities handle the complex logic of finding client files, resolving configuration, and preparing server options.
|
|
17
|
+
|
|
18
|
+
## Core Functions
|
|
19
|
+
|
|
20
|
+
### truthy(value)
|
|
21
|
+
|
|
22
|
+
Converts various value types to boolean with flexible truthiness rules.
|
|
23
|
+
|
|
24
|
+
```javascript
|
|
25
|
+
truthy(true) // true
|
|
26
|
+
truthy(false) // false
|
|
27
|
+
truthy(1) // true
|
|
28
|
+
truthy(0) // false
|
|
29
|
+
truthy("yes") // true
|
|
30
|
+
truthy("false") // false (string "false")
|
|
31
|
+
truthy("") // false (empty string)
|
|
32
|
+
truthy("0") // false (string "0")
|
|
33
|
+
truthy(null) // false
|
|
34
|
+
truthy({}) // true (truthy object)
|
|
35
|
+
```
|
|
36
|
+
|
|
37
|
+
**Used for:** Environment variable parsing, configuration option validation.
|
|
38
|
+
|
|
39
|
+
### guess_caller_file()
|
|
40
|
+
|
|
41
|
+
Attempts to determine the file that called the current function by walking the call stack.
|
|
42
|
+
|
|
43
|
+
```javascript
|
|
44
|
+
// In a file called /app/server.js
|
|
45
|
+
const caller = guess_caller_file();
|
|
46
|
+
// Returns: "/app/server.js"
|
|
47
|
+
```
|
|
48
|
+
|
|
49
|
+
**Algorithm:**
|
|
50
|
+
1. Captures current stack trace
|
|
51
|
+
2. Filters out internal Node.js and library files
|
|
52
|
+
3. Returns the first non-internal file path
|
|
53
|
+
4. Returns null if no suitable file found
|
|
54
|
+
|
|
55
|
+
**Used for:** Automatic project root detection, relative path resolution.
|
|
56
|
+
|
|
57
|
+
### resolve_from_base(base_dir, relative_path)
|
|
58
|
+
|
|
59
|
+
Resolves a path relative to a base directory, or returns absolute paths as-is.
|
|
60
|
+
|
|
61
|
+
```javascript
|
|
62
|
+
resolve_from_base("/app", "client.js") // "/app/client.js"
|
|
63
|
+
resolve_from_base("/app", "./src/main.js") // "/app/src/main.js"
|
|
64
|
+
resolve_from_base("/app", "/tmp/file.js") // "/tmp/file.js" (absolute)
|
|
65
|
+
```
|
|
66
|
+
|
|
67
|
+
**Used for:** Configuration path resolution, client file path handling.
|
|
68
|
+
|
|
69
|
+
### find_default_client_path(preferred, caller_dir)
|
|
70
|
+
|
|
71
|
+
Automatically discovers client files using a prioritized search strategy.
|
|
72
|
+
|
|
73
|
+
```javascript
|
|
74
|
+
// Search order:
|
|
75
|
+
find_default_client_path(null, "/app")
|
|
76
|
+
// 1. /app/client.js
|
|
77
|
+
// 2. /app/src/client.js
|
|
78
|
+
// 3. /app/app/client.js
|
|
79
|
+
// 4. /app/../client.js (process.cwd())
|
|
80
|
+
```
|
|
81
|
+
|
|
82
|
+
**Search Priority:**
|
|
83
|
+
1. **Preferred path**: If explicitly provided and exists
|
|
84
|
+
2. **Caller directory**: `client.js`, `src/client.js`, `app/client.js`
|
|
85
|
+
3. **Working directory**: Same patterns in `process.cwd()`
|
|
86
|
+
|
|
87
|
+
**Returns:** Absolute path to found client file, or null if none found.
|
|
88
|
+
|
|
89
|
+
**Used for:** Automatic client file discovery in `Server.serve()`.
|
|
90
|
+
|
|
91
|
+
### load_default_control_from_client(client_path)
|
|
92
|
+
|
|
93
|
+
Loads and extracts control constructors from client files.
|
|
94
|
+
|
|
95
|
+
```javascript
|
|
96
|
+
// client.js exports jsgui object with controls
|
|
97
|
+
const control = load_default_control_from_client("/app/client.js");
|
|
98
|
+
// Returns: Function (control constructor) or null
|
|
99
|
+
```
|
|
100
|
+
|
|
101
|
+
**Loading Strategy:**
|
|
102
|
+
1. **Direct function export**: `module.exports = MyControl`
|
|
103
|
+
2. **Default export**: `module.exports.default`
|
|
104
|
+
3. **Controls object**: `module.exports.controls.MyControl`
|
|
105
|
+
4. **Named exports**: `module.exports.control`, `module.exports.Ctrl`
|
|
106
|
+
|
|
107
|
+
**Returns:** First valid control constructor found, or null.
|
|
108
|
+
|
|
109
|
+
**Used for:** Automatic control loading when no explicit control provided.
|
|
110
|
+
|
|
111
|
+
### ensure_route_leading_slash(route)
|
|
112
|
+
|
|
113
|
+
Ensures route strings start with a forward slash.
|
|
114
|
+
|
|
115
|
+
```javascript
|
|
116
|
+
ensure_route_leading_slash("api/users") // "/api/users"
|
|
117
|
+
ensure_route_leading_slash("/dashboard") // "/dashboard"
|
|
118
|
+
ensure_route_leading_slash("") // "/"
|
|
119
|
+
ensure_route_leading_slash(null) // "/"
|
|
120
|
+
```
|
|
121
|
+
|
|
122
|
+
**Used for:** Route normalization in multi-page configurations.
|
|
123
|
+
|
|
124
|
+
## Usage Patterns
|
|
125
|
+
|
|
126
|
+
### Automatic Client Discovery
|
|
127
|
+
|
|
128
|
+
```javascript
|
|
129
|
+
// Server.serve() uses these helpers internally:
|
|
130
|
+
|
|
131
|
+
// 1. Determine caller file
|
|
132
|
+
const caller_file = guess_caller_file();
|
|
133
|
+
|
|
134
|
+
// 2. Get caller directory
|
|
135
|
+
const caller_dir = caller_file ? path.dirname(caller_file) : process.cwd();
|
|
136
|
+
|
|
137
|
+
// 3. Find client file
|
|
138
|
+
const client_path = find_default_client_path(explicit_path, caller_dir);
|
|
139
|
+
|
|
140
|
+
// 4. Load control
|
|
141
|
+
const control = load_default_control_from_client(client_path);
|
|
142
|
+
```
|
|
143
|
+
|
|
144
|
+
### Configuration Resolution
|
|
145
|
+
|
|
146
|
+
```javascript
|
|
147
|
+
// Environment variable parsing
|
|
148
|
+
const debug_enabled = truthy(process.env.JSGUI_DEBUG);
|
|
149
|
+
const port = Number.isFinite(+process.env.PORT) ? +process.env.PORT : 8080;
|
|
150
|
+
const host = process.env.HOST || null;
|
|
151
|
+
```
|
|
152
|
+
|
|
153
|
+
### Path Resolution
|
|
154
|
+
|
|
155
|
+
```javascript
|
|
156
|
+
// Relative path handling
|
|
157
|
+
const config_path = resolve_from_base(project_root, "./config/app.js");
|
|
158
|
+
const static_path = resolve_from_base(caller_dir, "./public");
|
|
159
|
+
```
|
|
160
|
+
|
|
161
|
+
## Error Handling
|
|
162
|
+
|
|
163
|
+
### File Not Found
|
|
164
|
+
|
|
165
|
+
```javascript
|
|
166
|
+
const client_path = find_default_client_path(null, "/app");
|
|
167
|
+
if (!client_path) {
|
|
168
|
+
throw new Error(
|
|
169
|
+
`No client file found. Searched in:\n` +
|
|
170
|
+
` /app/client.js\n` +
|
|
171
|
+
` /app/src/client.js\n` +
|
|
172
|
+
` /app/app/client.js\n` +
|
|
173
|
+
` ${process.cwd()}/client.js\n` +
|
|
174
|
+
` ${process.cwd()}/src/client.js\n` +
|
|
175
|
+
` ${process.cwd()}/app/client.js`
|
|
176
|
+
);
|
|
177
|
+
}
|
|
178
|
+
```
|
|
179
|
+
|
|
180
|
+
### Invalid Control
|
|
181
|
+
|
|
182
|
+
```javascript
|
|
183
|
+
const control = load_default_control_from_client(client_path);
|
|
184
|
+
if (!control) {
|
|
185
|
+
throw new Error(
|
|
186
|
+
`No control found in ${client_path}. Ensure your client file exports a control constructor.`
|
|
187
|
+
);
|
|
188
|
+
}
|
|
189
|
+
```
|
|
190
|
+
|
|
191
|
+
## Integration Examples
|
|
192
|
+
|
|
193
|
+
### Custom Client Discovery
|
|
194
|
+
|
|
195
|
+
```javascript
|
|
196
|
+
const { find_default_client_path, load_default_control_from_client } = require('./serve-helpers');
|
|
197
|
+
|
|
198
|
+
function findAndLoadClient(base_dir) {
|
|
199
|
+
const client_path = find_default_client_path(null, base_dir);
|
|
200
|
+
if (!client_path) return null;
|
|
201
|
+
|
|
202
|
+
const control = load_default_control_from_client(client_path);
|
|
203
|
+
return { path: client_path, control };
|
|
204
|
+
}
|
|
205
|
+
```
|
|
206
|
+
|
|
207
|
+
### Configuration Builder
|
|
208
|
+
|
|
209
|
+
```javascript
|
|
210
|
+
const { truthy, resolve_from_base } = require('./serve-helpers');
|
|
211
|
+
|
|
212
|
+
function buildServerConfig(options) {
|
|
213
|
+
return {
|
|
214
|
+
port: options.port || +process.env.PORT || 8080,
|
|
215
|
+
host: options.host || process.env.HOST || null,
|
|
216
|
+
debug: truthy(options.debug || process.env.JSGUI_DEBUG),
|
|
217
|
+
root: resolve_from_base(process.cwd(), options.root || '.')
|
|
218
|
+
};
|
|
219
|
+
}
|
|
220
|
+
```
|
|
221
|
+
|
|
222
|
+
## Testing Helpers
|
|
223
|
+
|
|
224
|
+
### Mocking File System
|
|
225
|
+
|
|
226
|
+
```javascript
|
|
227
|
+
// For testing client discovery
|
|
228
|
+
const mock_fs = {
|
|
229
|
+
existsSync: (path) => mock_files.has(path)
|
|
230
|
+
};
|
|
231
|
+
|
|
232
|
+
// Override in tests
|
|
233
|
+
const original_existsSync = require('fs').existsSync;
|
|
234
|
+
require('fs').existsSync = mock_fs.existsSync;
|
|
235
|
+
```
|
|
236
|
+
|
|
237
|
+
### Testing Control Loading
|
|
238
|
+
|
|
239
|
+
```javascript
|
|
240
|
+
// Mock require for testing
|
|
241
|
+
const mock_client_module = {
|
|
242
|
+
controls: { MyControl: class MyControl {} }
|
|
243
|
+
};
|
|
244
|
+
|
|
245
|
+
const original_require = require;
|
|
246
|
+
require = (path) => {
|
|
247
|
+
if (path === '/mock/client.js') return mock_client_module;
|
|
248
|
+
return original_require(path);
|
|
249
|
+
};
|
|
250
|
+
```
|
|
251
|
+
|
|
252
|
+
## Performance Considerations
|
|
253
|
+
|
|
254
|
+
### Caching
|
|
255
|
+
|
|
256
|
+
```javascript
|
|
257
|
+
// Cache resolved paths
|
|
258
|
+
const path_cache = new Map();
|
|
259
|
+
|
|
260
|
+
function cached_resolve_from_base(base_dir, relative_path) {
|
|
261
|
+
const key = `${base_dir}:${relative_path}`;
|
|
262
|
+
if (path_cache.has(key)) return path_cache.get(key);
|
|
263
|
+
|
|
264
|
+
const resolved = resolve_from_base(base_dir, relative_path);
|
|
265
|
+
path_cache.set(key, resolved);
|
|
266
|
+
return resolved;
|
|
267
|
+
}
|
|
268
|
+
```
|
|
269
|
+
|
|
270
|
+
### Lazy Loading
|
|
271
|
+
|
|
272
|
+
```javascript
|
|
273
|
+
// Only load when needed
|
|
274
|
+
let _client_cache = null;
|
|
275
|
+
|
|
276
|
+
function get_client_info() {
|
|
277
|
+
if (_client_cache) return _client_cache;
|
|
278
|
+
|
|
279
|
+
const caller_file = guess_caller_file();
|
|
280
|
+
const caller_dir = caller_file ? path.dirname(caller_file) : process.cwd();
|
|
281
|
+
const client_path = find_default_client_path(null, caller_dir);
|
|
282
|
+
|
|
283
|
+
_client_cache = { caller_dir, client_path };
|
|
284
|
+
return _client_cache;
|
|
285
|
+
}
|
|
286
|
+
```
|
|
287
|
+
|
|
288
|
+
## Debugging
|
|
289
|
+
|
|
290
|
+
### Verbose Logging
|
|
291
|
+
|
|
292
|
+
```javascript
|
|
293
|
+
function debug_client_discovery(caller_dir) {
|
|
294
|
+
console.log('Client discovery:');
|
|
295
|
+
console.log(' Caller directory:', caller_dir);
|
|
296
|
+
|
|
297
|
+
const candidates = [
|
|
298
|
+
path.join(caller_dir, 'client.js'),
|
|
299
|
+
path.join(caller_dir, 'src', 'client.js'),
|
|
300
|
+
path.join(caller_dir, 'app', 'client.js')
|
|
301
|
+
];
|
|
302
|
+
|
|
303
|
+
candidates.forEach(candidate => {
|
|
304
|
+
const exists = fs.existsSync(candidate);
|
|
305
|
+
console.log(` ${exists ? '✓' : '✗'} ${candidate}`);
|
|
306
|
+
});
|
|
307
|
+
}
|
|
308
|
+
```
|
|
309
|
+
|
|
310
|
+
### Stack Trace Analysis
|
|
311
|
+
|
|
312
|
+
```javascript
|
|
313
|
+
function debug_caller_detection() {
|
|
314
|
+
const orig = Error.prepareStackTrace;
|
|
315
|
+
try {
|
|
316
|
+
Error.prepareStackTrace = (_, stack) => stack;
|
|
317
|
+
const err = new Error();
|
|
318
|
+
const stack = err.stack;
|
|
319
|
+
|
|
320
|
+
console.log('Call stack:');
|
|
321
|
+
stack.forEach((frame, i) => {
|
|
322
|
+
console.log(` ${i}: ${frame.getFileName()}:${frame.getLineNumber()}`);
|
|
323
|
+
});
|
|
324
|
+
} finally {
|
|
325
|
+
Error.prepareStackTrace = orig;
|
|
326
|
+
}
|
|
327
|
+
}
|
|
328
|
+
```
|
|
329
|
+
|
|
330
|
+
## Extension Points
|
|
331
|
+
|
|
332
|
+
### Custom Client Discovery
|
|
333
|
+
|
|
334
|
+
```javascript
|
|
335
|
+
function custom_find_client_path(caller_dir) {
|
|
336
|
+
// Custom search logic
|
|
337
|
+
const custom_candidates = [
|
|
338
|
+
'lib/client.js',
|
|
339
|
+
'dist/client.js',
|
|
340
|
+
'build/client.js'
|
|
341
|
+
];
|
|
342
|
+
|
|
343
|
+
for (const candidate of custom_candidates) {
|
|
344
|
+
const full_path = path.join(caller_dir, candidate);
|
|
345
|
+
if (fs.existsSync(full_path)) return full_path;
|
|
346
|
+
}
|
|
347
|
+
|
|
348
|
+
// Fall back to default
|
|
349
|
+
return find_default_client_path(null, caller_dir);
|
|
350
|
+
}
|
|
351
|
+
```
|
|
352
|
+
|
|
353
|
+
### Custom Control Loading
|
|
354
|
+
|
|
355
|
+
```javascript
|
|
356
|
+
function custom_load_control(client_path) {
|
|
357
|
+
const mod = require(client_path);
|
|
358
|
+
|
|
359
|
+
// Custom loading logic
|
|
360
|
+
if (mod.MyApp) return mod.MyApp;
|
|
361
|
+
if (mod.default && mod.default.MainControl) return mod.default.MainControl;
|
|
362
|
+
|
|
363
|
+
// Fall back to default
|
|
364
|
+
return load_default_control_from_client(client_path);
|
|
365
|
+
}
|
|
366
|
+
```
|
|
367
|
+
|
|
368
|
+
## Common Issues and Solutions
|
|
369
|
+
|
|
370
|
+
### Stack Trace Issues
|
|
371
|
+
|
|
372
|
+
**Problem:** `guess_caller_file()` returns wrong file
|
|
373
|
+
**Solution:** Ensure function is called directly from target file, not through multiple layers of abstraction
|
|
374
|
+
|
|
375
|
+
### Path Resolution Issues
|
|
376
|
+
|
|
377
|
+
**Problem:** Relative paths resolve incorrectly
|
|
378
|
+
**Solution:** Always use absolute paths when possible, or ensure base directory is correct
|
|
379
|
+
|
|
380
|
+
### Module Loading Issues
|
|
381
|
+
|
|
382
|
+
**Problem:** Control not found in client file
|
|
383
|
+
**Solution:** Check export structure matches expected patterns (controls object, default export, etc.)
|
|
384
|
+
|
|
385
|
+
### Caching Issues
|
|
386
|
+
|
|
387
|
+
**Problem:** Changes to client files not detected
|
|
388
|
+
**Solution:** Clear require cache in development: `delete require.cache[client_path]`
|
|
389
|
+
|
|
390
|
+
## Future Enhancements
|
|
391
|
+
|
|
392
|
+
### Planned Features
|
|
393
|
+
|
|
394
|
+
- **TypeScript Support**: Automatic `.ts` file discovery
|
|
395
|
+
- **Multiple Client Files**: Support for multiple entry points
|
|
396
|
+
- **Plugin System**: Extensible discovery and loading
|
|
397
|
+
- **Configuration Files**: JSON/YAML config file support
|
|
398
|
+
- **Hot Reloading**: Automatic file watching and reloading
|
|
399
|
+
|
|
400
|
+
### API Stability
|
|
401
|
+
|
|
402
|
+
These helpers are internal utilities but follow semantic versioning. Breaking changes will be clearly documented and migration guides provided.
|
|
403
|
+
|
|
404
|
+
---
|
|
405
|
+
|
|
406
|
+
This reference documents the internal utilities that power JSGUI3 Server's automatic discovery and configuration features. Understanding these helpers is essential for extending or debugging the server framework.
|
|
@@ -1,5 +1,18 @@
|
|
|
1
1
|
# Simple Server API Design
|
|
2
2
|
|
|
3
|
+
## When to Read
|
|
4
|
+
|
|
5
|
+
This document explains the design principles and implementation of the simplified JSGUI3 Server API. Read this when:
|
|
6
|
+
- You want to understand the evolution from complex to simple server APIs
|
|
7
|
+
- You're designing new server frameworks or APIs
|
|
8
|
+
- You need to implement the Server.serve() method or similar simplified interfaces
|
|
9
|
+
- You're interested in progressive disclosure and API design patterns
|
|
10
|
+
- You want to see examples of reducing boilerplate code in framework development
|
|
11
|
+
|
|
12
|
+
**Note:** For actual usage of the JSGUI3 Server API, see [README.md](../README.md). For comprehensive technical documentation, see [docs/comprehensive-documentation.md](docs/comprehensive-documentation.md).
|
|
13
|
+
|
|
14
|
+
# Simple Server API Design
|
|
15
|
+
|
|
3
16
|
**Goal:** Make jsgui3-server trivially easy to use for simple cases while preserving full power for complex scenarios.
|
|
4
17
|
|
|
5
18
|
## Design Philosophy
|
|
@@ -0,0 +1,275 @@
|
|
|
1
|
+
# JSGUI3 Server System Architecture
|
|
2
|
+
|
|
3
|
+
## When to Read
|
|
4
|
+
|
|
5
|
+
This document provides a comprehensive overview of the JSGUI3 Server system architecture. Read this when:
|
|
6
|
+
- You need to understand how all the major components fit together
|
|
7
|
+
- You're planning to extend or modify the system architecture
|
|
8
|
+
- You want to understand the data flow and integration points
|
|
9
|
+
- You're debugging complex system-level issues
|
|
10
|
+
- You're contributing to the core framework development
|
|
11
|
+
|
|
12
|
+
**Note:** For API usage, see [README.md](../README.md). For detailed component documentation, see [docs/comprehensive-documentation.md](docs/comprehensive-documentation.md).
|
|
13
|
+
|
|
14
|
+
## System Overview
|
|
15
|
+
|
|
16
|
+
JSGUI3 Server is a Node.js-based web framework that serves modern JavaScript GUI applications. The system follows a modular architecture with clear separation of concerns, built around the core principle of **component-based web serving**.
|
|
17
|
+
|
|
18
|
+
## Core Architecture Layers
|
|
19
|
+
|
|
20
|
+
### 1. Entry Point Layer
|
|
21
|
+
**Files:** `server.js`, `serve-factory.js`, `cli.js`
|
|
22
|
+
|
|
23
|
+
**Purpose:** Provides the main server interfaces and command-line tools.
|
|
24
|
+
|
|
25
|
+
**Key Components:**
|
|
26
|
+
- `JSGUI_Single_Process_Server`: Main server class handling HTTP requests
|
|
27
|
+
- `Server.serve()`: Simplified API for quick application setup
|
|
28
|
+
- CLI tools for development and deployment
|
|
29
|
+
|
|
30
|
+
### 2. Publishing Layer
|
|
31
|
+
**Directory:** `publishers/`
|
|
32
|
+
|
|
33
|
+
**Purpose:** Handles conversion of various content types to HTTP responses.
|
|
34
|
+
|
|
35
|
+
**Key Publishers:**
|
|
36
|
+
- `HTTP_Webpage_Publisher`: Serves bundled JSGUI3 controls as complete web pages
|
|
37
|
+
- `HTTP_Website_Publisher`: Manages multi-page websites
|
|
38
|
+
- `HTTP_Function_Publisher`: Exposes JavaScript functions as REST API endpoints
|
|
39
|
+
- `HTTP_CSS_Publisher`: Serves CSS stylesheets
|
|
40
|
+
- `HTTP_JS_Publisher`: Serves JavaScript bundles
|
|
41
|
+
- `HTTP_Image_Publisher`: Handles image file serving
|
|
42
|
+
|
|
43
|
+
### 3. Resource Management Layer
|
|
44
|
+
**Directory:** `resources/`
|
|
45
|
+
|
|
46
|
+
**Purpose:** Provides abstractions for accessing different types of data and functionality.
|
|
47
|
+
|
|
48
|
+
**Key Resources:**
|
|
49
|
+
- `Server_Resource_Pool`: Manages collections of resources with lifecycle management
|
|
50
|
+
- `Website_Resource`: Wraps website objects for server integration
|
|
51
|
+
- `File_System_Resource`: Provides file system access
|
|
52
|
+
- `Data_Resource`: Handles data storage and retrieval
|
|
53
|
+
- `Local_Server_Info_Resource`: Provides server environment information
|
|
54
|
+
|
|
55
|
+
### 4. Processing Layer
|
|
56
|
+
**Directory:** `resources/processors/`
|
|
57
|
+
|
|
58
|
+
**Purpose:** Handles transformation and optimization of client-side assets.
|
|
59
|
+
|
|
60
|
+
**Key Processors:**
|
|
61
|
+
- **Bundlers** (`bundlers/`): Combine and optimize JavaScript, CSS, and other assets
|
|
62
|
+
- `JS_Bundler`: JavaScript bundling with ESBuild integration
|
|
63
|
+
- `CSS_Bundler`: CSS processing and optimization
|
|
64
|
+
- `Webpage_Bundler`: Complete webpage assembly
|
|
65
|
+
- **Extractors** (`extractors/`): Extract metadata and assets from components
|
|
66
|
+
|
|
67
|
+
### 5. Control Layer
|
|
68
|
+
**Directory:** `controls/`
|
|
69
|
+
|
|
70
|
+
**Purpose:** Defines reusable UI components that can be served to browsers.
|
|
71
|
+
|
|
72
|
+
**Key Components:**
|
|
73
|
+
- `Active_HTML_Document`: Base class for all UI controls
|
|
74
|
+
- Page controls (`page/`): Full-page layouts
|
|
75
|
+
- Panel controls (`panel/`): Container components
|
|
76
|
+
|
|
77
|
+
### 6. HTTP Handling Layer
|
|
78
|
+
**Directory:** `http/`
|
|
79
|
+
|
|
80
|
+
**Purpose:** Manages low-level HTTP request/response handling.
|
|
81
|
+
|
|
82
|
+
**Key Components:**
|
|
83
|
+
- `HTTP_Responder`: Base class for HTTP response handling
|
|
84
|
+
- `Static_Route_HTTP_Responder`: Serves pre-generated static content
|
|
85
|
+
|
|
86
|
+
### 7. Website Abstraction Layer
|
|
87
|
+
**Directory:** `website/`
|
|
88
|
+
|
|
89
|
+
**Purpose:** Provides high-level abstractions for website structure and content.
|
|
90
|
+
|
|
91
|
+
**Key Components:**
|
|
92
|
+
- `Website`: Represents a complete website with multiple pages
|
|
93
|
+
- `Webpage`: Represents individual pages within a website
|
|
94
|
+
|
|
95
|
+
## Data Flow Architecture
|
|
96
|
+
|
|
97
|
+
### Request Processing Flow
|
|
98
|
+
|
|
99
|
+
```
|
|
100
|
+
Client Request
|
|
101
|
+
↓
|
|
102
|
+
HTTP Server (Node.js http/https)
|
|
103
|
+
↓
|
|
104
|
+
Server Router
|
|
105
|
+
↓
|
|
106
|
+
Resource Pool
|
|
107
|
+
↓
|
|
108
|
+
Appropriate Publisher
|
|
109
|
+
↓
|
|
110
|
+
Resource Access
|
|
111
|
+
↓
|
|
112
|
+
Content Processing/Bundling
|
|
113
|
+
↓
|
|
114
|
+
HTTP Response
|
|
115
|
+
```
|
|
116
|
+
|
|
117
|
+
### Component Serving Flow
|
|
118
|
+
|
|
119
|
+
```
|
|
120
|
+
Control Class (e.g., MyCustomControl)
|
|
121
|
+
↓
|
|
122
|
+
HTTP_Webpage_Publisher
|
|
123
|
+
↓
|
|
124
|
+
JS/CSS Extraction & Bundling
|
|
125
|
+
↓
|
|
126
|
+
Static_Route_HTTP_Responder
|
|
127
|
+
↓
|
|
128
|
+
Client Browser
|
|
129
|
+
```
|
|
130
|
+
|
|
131
|
+
### API Serving Flow
|
|
132
|
+
|
|
133
|
+
```
|
|
134
|
+
Function Definition
|
|
135
|
+
↓
|
|
136
|
+
HTTP_Function_Publisher
|
|
137
|
+
↓
|
|
138
|
+
Server Router (/api/functionName)
|
|
139
|
+
↓
|
|
140
|
+
HTTP Response (JSON/Text)
|
|
141
|
+
```
|
|
142
|
+
|
|
143
|
+
## Integration Points
|
|
144
|
+
|
|
145
|
+
### External Dependencies
|
|
146
|
+
|
|
147
|
+
**Core Dependencies:**
|
|
148
|
+
- `jsgui3-html`: Base framework providing core classes
|
|
149
|
+
- `obext`: Object extension utilities for reactive properties
|
|
150
|
+
- `Node.js`: Runtime environment and HTTP server
|
|
151
|
+
|
|
152
|
+
**Optional Dependencies:**
|
|
153
|
+
- ESBuild: JavaScript bundling and minification
|
|
154
|
+
- Various resource-specific libraries
|
|
155
|
+
|
|
156
|
+
### Internal Module Integration
|
|
157
|
+
|
|
158
|
+
**Router ↔ Publishers:**
|
|
159
|
+
- Router receives HTTP requests and routes to appropriate publishers
|
|
160
|
+
- Publishers handle content-type specific processing
|
|
161
|
+
|
|
162
|
+
**Publishers ↔ Resources:**
|
|
163
|
+
- Publishers access data through resource abstractions
|
|
164
|
+
- Resources provide unified interface to different data sources
|
|
165
|
+
|
|
166
|
+
**Resources ↔ Processors:**
|
|
167
|
+
- Processors transform raw resources into optimized output
|
|
168
|
+
- Resources manage processor lifecycle and configuration
|
|
169
|
+
|
|
170
|
+
## Configuration and Environment
|
|
171
|
+
|
|
172
|
+
### Environment Variables
|
|
173
|
+
- `PORT`: Server port (default: 8080)
|
|
174
|
+
- `HOST`: Server host binding
|
|
175
|
+
- `JSGUI_DEBUG`: Enable debug mode
|
|
176
|
+
|
|
177
|
+
### Configuration Files
|
|
178
|
+
- `jsgui.config.js`: Optional configuration file
|
|
179
|
+
- Inline configuration through `Server.serve()` options
|
|
180
|
+
|
|
181
|
+
## Performance and Scalability
|
|
182
|
+
|
|
183
|
+
### Resource Pooling
|
|
184
|
+
- Connection pooling for database and external service access
|
|
185
|
+
- Thread/worker pools for background processing
|
|
186
|
+
- Cache pools for compiled assets and frequently accessed data
|
|
187
|
+
|
|
188
|
+
### Bundling Optimization
|
|
189
|
+
- ESBuild integration for fast JavaScript processing
|
|
190
|
+
- CSS extraction and deduplication
|
|
191
|
+
- Asset caching and compression
|
|
192
|
+
|
|
193
|
+
### Memory Management
|
|
194
|
+
- Control lifecycle management through context registration
|
|
195
|
+
- Resource cleanup and garbage collection
|
|
196
|
+
- Shared data models to reduce memory duplication
|
|
197
|
+
|
|
198
|
+
## Error Handling and Resilience
|
|
199
|
+
|
|
200
|
+
### Error Propagation
|
|
201
|
+
- Structured error handling throughout the pipeline
|
|
202
|
+
- Graceful degradation when components fail
|
|
203
|
+
- Comprehensive logging for debugging
|
|
204
|
+
|
|
205
|
+
### Recovery Mechanisms
|
|
206
|
+
- Automatic restart capabilities
|
|
207
|
+
- Fallback resource access patterns
|
|
208
|
+
- Error boundary components for UI stability
|
|
209
|
+
|
|
210
|
+
## Development and Testing
|
|
211
|
+
|
|
212
|
+
### Development Mode Features
|
|
213
|
+
- Hot reloading for control changes
|
|
214
|
+
- Enhanced debugging output
|
|
215
|
+
- Source map generation
|
|
216
|
+
|
|
217
|
+
### Testing Infrastructure
|
|
218
|
+
- Unit tests for individual components
|
|
219
|
+
- Integration tests for system interactions
|
|
220
|
+
- End-to-end tests for complete workflows
|
|
221
|
+
|
|
222
|
+
## Deployment Patterns
|
|
223
|
+
|
|
224
|
+
### Single Process Deployment
|
|
225
|
+
- Simple single-server deployment
|
|
226
|
+
- Resource pooling for efficiency
|
|
227
|
+
- Built-in load balancing across network interfaces
|
|
228
|
+
|
|
229
|
+
### Development vs Production
|
|
230
|
+
- Debug mode for development
|
|
231
|
+
- Optimized bundling for production
|
|
232
|
+
- Environment-specific configuration
|
|
233
|
+
|
|
234
|
+
## Extension Points
|
|
235
|
+
|
|
236
|
+
### Custom Publishers
|
|
237
|
+
Extend the `Publisher` base class to handle new content types.
|
|
238
|
+
|
|
239
|
+
### Custom Resources
|
|
240
|
+
Implement the `Resource` interface for new data sources.
|
|
241
|
+
|
|
242
|
+
### Custom Controls
|
|
243
|
+
Extend `Active_HTML_Document` for new UI components.
|
|
244
|
+
|
|
245
|
+
### Custom Processors
|
|
246
|
+
Add new processing pipelines for assets and data.
|
|
247
|
+
|
|
248
|
+
## Security Considerations
|
|
249
|
+
|
|
250
|
+
### Access Control
|
|
251
|
+
- Resource-level access control through resource pools
|
|
252
|
+
- Publisher-level security through HTTP handling
|
|
253
|
+
- Environment-based security configurations
|
|
254
|
+
|
|
255
|
+
### Data Protection
|
|
256
|
+
- Secure handling of sensitive configuration
|
|
257
|
+
- Safe external resource access patterns
|
|
258
|
+
- Input validation and sanitization
|
|
259
|
+
|
|
260
|
+
## Future Evolution
|
|
261
|
+
|
|
262
|
+
### Planned Enhancements
|
|
263
|
+
- Multi-process server architecture
|
|
264
|
+
- Advanced caching strategies
|
|
265
|
+
- Enhanced real-time capabilities
|
|
266
|
+
- Improved development tooling
|
|
267
|
+
|
|
268
|
+
### Backward Compatibility
|
|
269
|
+
- API stability commitments
|
|
270
|
+
- Migration paths for breaking changes
|
|
271
|
+
- Deprecation warnings and timelines
|
|
272
|
+
|
|
273
|
+
---
|
|
274
|
+
|
|
275
|
+
This architecture document provides the foundation for understanding how JSGUI3 Server components work together. For detailed implementation of specific components, refer to their individual documentation files.
|