@objectstack/runtime 3.0.10 → 3.1.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/.turbo/turbo-build.log +9 -9
- package/CHANGELOG.md +20 -0
- package/dist/index.cjs +75 -16
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +2 -0
- package/dist/index.d.ts +2 -0
- package/dist/index.js +75 -16
- package/dist/index.js.map +1 -1
- package/package.json +5 -5
- package/src/dispatcher-plugin.ts +18 -0
- package/src/http-dispatcher.test.ts +385 -0
- package/src/http-dispatcher.ts +68 -16
package/dist/index.d.cts
CHANGED
|
@@ -491,6 +491,8 @@ declare class HttpDispatcher {
|
|
|
491
491
|
* - DELETE /packages/:id → uninstall a package
|
|
492
492
|
* - PATCH /packages/:id/enable → enable a package
|
|
493
493
|
* - PATCH /packages/:id/disable → disable a package
|
|
494
|
+
* - POST /packages/:id/publish → publish a package (metadata snapshot)
|
|
495
|
+
* - POST /packages/:id/revert → revert a package to last published state
|
|
494
496
|
*
|
|
495
497
|
* Uses ObjectQL SchemaRegistry directly (via the 'objectql' service)
|
|
496
498
|
* with broker fallback for backward compatibility.
|
package/dist/index.d.ts
CHANGED
|
@@ -491,6 +491,8 @@ declare class HttpDispatcher {
|
|
|
491
491
|
* - DELETE /packages/:id → uninstall a package
|
|
492
492
|
* - PATCH /packages/:id/enable → enable a package
|
|
493
493
|
* - PATCH /packages/:id/disable → disable a package
|
|
494
|
+
* - POST /packages/:id/publish → publish a package (metadata snapshot)
|
|
495
|
+
* - POST /packages/:id/revert → revert a package to last published state
|
|
494
496
|
*
|
|
495
497
|
* Uses ObjectQL SchemaRegistry directly (via the 'objectql' service)
|
|
496
498
|
* with broker fallback for backward compatibility.
|
package/dist/index.js
CHANGED
|
@@ -306,7 +306,7 @@ var HttpDispatcher = class {
|
|
|
306
306
|
* path: sub-path after /auth/
|
|
307
307
|
*/
|
|
308
308
|
async handleAuth(path, method, body, context) {
|
|
309
|
-
const authService = this.getService(CoreServiceName.enum.auth);
|
|
309
|
+
const authService = await this.getService(CoreServiceName.enum.auth);
|
|
310
310
|
if (authService && typeof authService.handler === "function") {
|
|
311
311
|
const response = await authService.handler(context.request, context.response);
|
|
312
312
|
return { handled: true, result: response };
|
|
@@ -328,7 +328,7 @@ var HttpDispatcher = class {
|
|
|
328
328
|
const broker = this.ensureBroker();
|
|
329
329
|
const parts = path.replace(/^\/+/, "").split("/").filter(Boolean);
|
|
330
330
|
if (parts[0] === "types") {
|
|
331
|
-
const protocol = this.kernel?.context?.getService ? this.kernel.context.getService("protocol") : null;
|
|
331
|
+
const protocol = this.kernel?.context?.getService ? await this.kernel.context.getService("protocol") : null;
|
|
332
332
|
if (protocol && typeof protocol.getMetaTypes === "function") {
|
|
333
333
|
const result = await protocol.getMetaTypes({});
|
|
334
334
|
return { handled: true, response: this.success(result) };
|
|
@@ -340,10 +340,25 @@ var HttpDispatcher = class {
|
|
|
340
340
|
return { handled: true, response: this.success({ types: ["object", "app", "plugin"] }) };
|
|
341
341
|
}
|
|
342
342
|
}
|
|
343
|
+
if (parts.length === 3 && parts[2] === "published" && (!method || method === "GET")) {
|
|
344
|
+
const [type, name] = parts;
|
|
345
|
+
const metadataService = await this.getService(CoreServiceName.enum.metadata);
|
|
346
|
+
if (metadataService && typeof metadataService.getPublished === "function") {
|
|
347
|
+
const data = await metadataService.getPublished(type, name);
|
|
348
|
+
if (data === void 0) return { handled: true, response: this.error("Not found", 404) };
|
|
349
|
+
return { handled: true, response: this.success(data) };
|
|
350
|
+
}
|
|
351
|
+
try {
|
|
352
|
+
const data = await broker.call("metadata.getPublished", { type, name }, { request: context.request });
|
|
353
|
+
return { handled: true, response: this.success(data) };
|
|
354
|
+
} catch (e) {
|
|
355
|
+
return { handled: true, response: this.error(e.message, 404) };
|
|
356
|
+
}
|
|
357
|
+
}
|
|
343
358
|
if (parts.length === 2) {
|
|
344
359
|
const [type, name] = parts;
|
|
345
360
|
if (method === "PUT" && body) {
|
|
346
|
-
const protocol = this.kernel?.context?.getService ? this.kernel.context.getService("protocol") : null;
|
|
361
|
+
const protocol = this.kernel?.context?.getService ? await this.kernel.context.getService("protocol") : null;
|
|
347
362
|
if (protocol && typeof protocol.saveMetaItem === "function") {
|
|
348
363
|
try {
|
|
349
364
|
const result = await protocol.saveMetaItem({ type, name, item: body });
|
|
@@ -365,7 +380,7 @@ var HttpDispatcher = class {
|
|
|
365
380
|
return { handled: true, response: this.success(data2) };
|
|
366
381
|
}
|
|
367
382
|
const singularType = type.endsWith("s") ? type.slice(0, -1) : type;
|
|
368
|
-
const protocol = this.kernel?.context?.getService ? this.kernel.context.getService("protocol") : null;
|
|
383
|
+
const protocol = this.kernel?.context?.getService ? await this.kernel.context.getService("protocol") : null;
|
|
369
384
|
if (protocol && typeof protocol.getMetaItem === "function") {
|
|
370
385
|
try {
|
|
371
386
|
const data2 = await protocol.getMetaItem({ type: singularType, name });
|
|
@@ -383,7 +398,7 @@ var HttpDispatcher = class {
|
|
|
383
398
|
if (parts.length === 1) {
|
|
384
399
|
const typeOrName = parts[0];
|
|
385
400
|
const packageId = query?.package || void 0;
|
|
386
|
-
const protocol = this.kernel?.context?.getService ? this.kernel.context.getService("protocol") : null;
|
|
401
|
+
const protocol = this.kernel?.context?.getService ? await this.kernel.context.getService("protocol") : null;
|
|
387
402
|
if (protocol && typeof protocol.getMetaItems === "function") {
|
|
388
403
|
try {
|
|
389
404
|
const data = await protocol.getMetaItems({ type: typeOrName, packageId });
|
|
@@ -412,7 +427,7 @@ var HttpDispatcher = class {
|
|
|
412
427
|
}
|
|
413
428
|
}
|
|
414
429
|
if (parts.length === 0) {
|
|
415
|
-
const protocol = this.kernel?.context?.getService ? this.kernel.context.getService("protocol") : null;
|
|
430
|
+
const protocol = this.kernel?.context?.getService ? await this.kernel.context.getService("protocol") : null;
|
|
416
431
|
if (protocol && typeof protocol.getMetaTypes === "function") {
|
|
417
432
|
const result = await protocol.getMetaTypes({});
|
|
418
433
|
return { handled: true, response: this.success(result) };
|
|
@@ -486,7 +501,7 @@ var HttpDispatcher = class {
|
|
|
486
501
|
* path: sub-path after /analytics/
|
|
487
502
|
*/
|
|
488
503
|
async handleAnalytics(path, method, body, context) {
|
|
489
|
-
const analyticsService = this.getService(CoreServiceName.enum.analytics);
|
|
504
|
+
const analyticsService = await this.getService(CoreServiceName.enum.analytics);
|
|
490
505
|
if (!analyticsService) return { handled: false };
|
|
491
506
|
const m = method.toUpperCase();
|
|
492
507
|
const subPath = path.replace(/^\/+/, "");
|
|
@@ -514,6 +529,8 @@ var HttpDispatcher = class {
|
|
|
514
529
|
* - DELETE /packages/:id → uninstall a package
|
|
515
530
|
* - PATCH /packages/:id/enable → enable a package
|
|
516
531
|
* - PATCH /packages/:id/disable → disable a package
|
|
532
|
+
* - POST /packages/:id/publish → publish a package (metadata snapshot)
|
|
533
|
+
* - POST /packages/:id/revert → revert a package to last published state
|
|
517
534
|
*
|
|
518
535
|
* Uses ObjectQL SchemaRegistry directly (via the 'objectql' service)
|
|
519
536
|
* with broker fallback for backward compatibility.
|
|
@@ -521,7 +538,7 @@ var HttpDispatcher = class {
|
|
|
521
538
|
async handlePackages(path, method, body, query, context) {
|
|
522
539
|
const m = method.toUpperCase();
|
|
523
540
|
const parts = path.replace(/^\/+/, "").split("/").filter(Boolean);
|
|
524
|
-
const qlService = this.getObjectQLService();
|
|
541
|
+
const qlService = await this.getObjectQLService();
|
|
525
542
|
const registry = qlService?.registry;
|
|
526
543
|
if (!registry) {
|
|
527
544
|
if (this.kernel.broker) {
|
|
@@ -558,6 +575,32 @@ var HttpDispatcher = class {
|
|
|
558
575
|
if (!pkg) return { handled: true, response: this.error(`Package '${id}' not found`, 404) };
|
|
559
576
|
return { handled: true, response: this.success(pkg) };
|
|
560
577
|
}
|
|
578
|
+
if (parts.length === 2 && parts[1] === "publish" && m === "POST") {
|
|
579
|
+
const id = decodeURIComponent(parts[0]);
|
|
580
|
+
const metadataService = await this.getService(CoreServiceName.enum.metadata);
|
|
581
|
+
if (metadataService && typeof metadataService.publishPackage === "function") {
|
|
582
|
+
const result = await metadataService.publishPackage(id, body || {});
|
|
583
|
+
return { handled: true, response: this.success(result) };
|
|
584
|
+
}
|
|
585
|
+
if (this.kernel.broker) {
|
|
586
|
+
const result = await this.kernel.broker.call("metadata.publishPackage", { packageId: id, ...body }, { request: context.request });
|
|
587
|
+
return { handled: true, response: this.success(result) };
|
|
588
|
+
}
|
|
589
|
+
return { handled: true, response: this.error("Metadata service not available", 503) };
|
|
590
|
+
}
|
|
591
|
+
if (parts.length === 2 && parts[1] === "revert" && m === "POST") {
|
|
592
|
+
const id = decodeURIComponent(parts[0]);
|
|
593
|
+
const metadataService = await this.getService(CoreServiceName.enum.metadata);
|
|
594
|
+
if (metadataService && typeof metadataService.revertPackage === "function") {
|
|
595
|
+
await metadataService.revertPackage(id);
|
|
596
|
+
return { handled: true, response: this.success({ success: true }) };
|
|
597
|
+
}
|
|
598
|
+
if (this.kernel.broker) {
|
|
599
|
+
await this.kernel.broker.call("metadata.revertPackage", { packageId: id }, { request: context.request });
|
|
600
|
+
return { handled: true, response: this.success({ success: true }) };
|
|
601
|
+
}
|
|
602
|
+
return { handled: true, response: this.error("Metadata service not available", 503) };
|
|
603
|
+
}
|
|
561
604
|
if (parts.length === 1 && m === "GET") {
|
|
562
605
|
const id = decodeURIComponent(parts[0]);
|
|
563
606
|
const pkg = registry.getPackage(id);
|
|
@@ -621,7 +664,7 @@ var HttpDispatcher = class {
|
|
|
621
664
|
* path: sub-path after /storage/
|
|
622
665
|
*/
|
|
623
666
|
async handleStorage(path, method, file, context) {
|
|
624
|
-
const storageService = this.getService(CoreServiceName.enum["file-storage"]) || this.kernel.services?.["file-storage"];
|
|
667
|
+
const storageService = await this.getService(CoreServiceName.enum["file-storage"]) || this.kernel.services?.["file-storage"];
|
|
625
668
|
if (!storageService) {
|
|
626
669
|
return { handled: true, response: this.error("File storage not configured", 501) };
|
|
627
670
|
}
|
|
@@ -666,7 +709,7 @@ var HttpDispatcher = class {
|
|
|
666
709
|
if (parts[0] === "view" && parts[1]) {
|
|
667
710
|
const objectName = parts[1];
|
|
668
711
|
const type = parts[2] || query?.type || "list";
|
|
669
|
-
const protocol = this.kernel?.context?.getService ? this.kernel.context.getService("protocol") : null;
|
|
712
|
+
const protocol = this.kernel?.context?.getService ? await this.kernel.context.getService("protocol") : null;
|
|
670
713
|
if (protocol && typeof protocol.getUiView === "function") {
|
|
671
714
|
try {
|
|
672
715
|
const result = await protocol.getUiView({ object: objectName, type });
|
|
@@ -696,7 +739,7 @@ var HttpDispatcher = class {
|
|
|
696
739
|
* GET /:name/runs/:runId → getRun
|
|
697
740
|
*/
|
|
698
741
|
async handleAutomation(path, method, body, context, query) {
|
|
699
|
-
const automationService = this.getService(CoreServiceName.enum.automation);
|
|
742
|
+
const automationService = await this.getService(CoreServiceName.enum.automation);
|
|
700
743
|
if (!automationService) return { handled: false };
|
|
701
744
|
const m = method.toUpperCase();
|
|
702
745
|
const parts = path.replace(/^\/+/, "").split("/").filter(Boolean);
|
|
@@ -779,9 +822,9 @@ var HttpDispatcher = class {
|
|
|
779
822
|
}
|
|
780
823
|
return this.kernel.services || {};
|
|
781
824
|
}
|
|
782
|
-
getService(name) {
|
|
825
|
+
async getService(name) {
|
|
783
826
|
if (typeof this.kernel.getService === "function") {
|
|
784
|
-
return this.kernel.getService(name);
|
|
827
|
+
return await this.kernel.getService(name);
|
|
785
828
|
}
|
|
786
829
|
const services = this.getServicesMap();
|
|
787
830
|
return services[name];
|
|
@@ -790,17 +833,17 @@ var HttpDispatcher = class {
|
|
|
790
833
|
* Get the ObjectQL service which provides access to SchemaRegistry.
|
|
791
834
|
* Tries multiple access patterns since kernel structure varies.
|
|
792
835
|
*/
|
|
793
|
-
getObjectQLService() {
|
|
836
|
+
async getObjectQLService() {
|
|
794
837
|
if (typeof this.kernel.getService === "function") {
|
|
795
838
|
try {
|
|
796
|
-
const svc = this.kernel.getService("objectql");
|
|
839
|
+
const svc = await this.kernel.getService("objectql");
|
|
797
840
|
if (svc?.registry) return svc;
|
|
798
841
|
} catch {
|
|
799
842
|
}
|
|
800
843
|
}
|
|
801
844
|
if (this.kernel?.context?.getService) {
|
|
802
845
|
try {
|
|
803
|
-
const svc = this.kernel.context.getService("objectql");
|
|
846
|
+
const svc = await this.kernel.context.getService("objectql");
|
|
804
847
|
if (svc?.registry) return svc;
|
|
805
848
|
} catch {
|
|
806
849
|
}
|
|
@@ -1057,6 +1100,22 @@ function createDispatcherPlugin(config = {}) {
|
|
|
1057
1100
|
errorResponse(err, res);
|
|
1058
1101
|
}
|
|
1059
1102
|
});
|
|
1103
|
+
server.post(`${prefix}/packages/:id/publish`, async (req, res) => {
|
|
1104
|
+
try {
|
|
1105
|
+
const result = await dispatcher.handlePackages(`/${req.params.id}/publish`, "POST", req.body, {}, { request: req });
|
|
1106
|
+
sendResult(result, res);
|
|
1107
|
+
} catch (err) {
|
|
1108
|
+
errorResponse(err, res);
|
|
1109
|
+
}
|
|
1110
|
+
});
|
|
1111
|
+
server.post(`${prefix}/packages/:id/revert`, async (req, res) => {
|
|
1112
|
+
try {
|
|
1113
|
+
const result = await dispatcher.handlePackages(`/${req.params.id}/revert`, "POST", req.body, {}, { request: req });
|
|
1114
|
+
sendResult(result, res);
|
|
1115
|
+
} catch (err) {
|
|
1116
|
+
errorResponse(err, res);
|
|
1117
|
+
}
|
|
1118
|
+
});
|
|
1060
1119
|
server.post(`${prefix}/storage/upload`, async (req, res) => {
|
|
1061
1120
|
try {
|
|
1062
1121
|
const result = await dispatcher.handleStorage("upload", "POST", req.body, { request: req });
|