@specverse/engines 4.1.5 → 4.1.6

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.
Files changed (120) hide show
  1. package/dist/libs/instance-factories/applications/templates/generic/backend-env-generator.js +22 -0
  2. package/dist/libs/instance-factories/applications/templates/generic/backend-package-json-generator.js +66 -0
  3. package/dist/libs/instance-factories/applications/templates/generic/backend-tsconfig-generator.js +54 -0
  4. package/dist/libs/instance-factories/applications/templates/generic/main-generator.js +290 -0
  5. package/dist/libs/instance-factories/applications/templates/react/_view-components-source.js +530 -0
  6. package/dist/libs/instance-factories/applications/templates/react/api-client-generator.js +437 -0
  7. package/dist/libs/instance-factories/applications/templates/react/api-types-generator.js +146 -0
  8. package/dist/libs/instance-factories/applications/templates/react/app-tsx-generator.js +73 -0
  9. package/dist/libs/instance-factories/applications/templates/react/env-example-generator.js +18 -0
  10. package/dist/libs/instance-factories/applications/templates/react/field-helpers-generator.js +99 -0
  11. package/dist/libs/instance-factories/applications/templates/react/gitignore-generator.js +35 -0
  12. package/dist/libs/instance-factories/applications/templates/react/index-css-generator.js +9 -0
  13. package/dist/libs/instance-factories/applications/templates/react/index-html-generator.js +23 -0
  14. package/dist/libs/instance-factories/applications/templates/react/main-tsx-generator.js +29 -0
  15. package/dist/libs/instance-factories/applications/templates/react/package-json-generator.js +49 -0
  16. package/dist/libs/instance-factories/applications/templates/react/pattern-adapter-generator.js +156 -0
  17. package/dist/libs/instance-factories/applications/templates/react/react-pattern-adapter.js +935 -0
  18. package/dist/libs/instance-factories/applications/templates/react/relationship-field-generator.js +143 -0
  19. package/dist/libs/instance-factories/applications/templates/react/runtime-app-tsx-generator.js +101 -0
  20. package/dist/libs/instance-factories/applications/templates/react/runtime-package-json-generator.js +50 -0
  21. package/dist/libs/instance-factories/applications/templates/react/tailwind-adapter-generator.js +646 -0
  22. package/dist/libs/instance-factories/applications/templates/react/tailwind-adapter-wrapper-generator.js +65 -0
  23. package/dist/libs/instance-factories/applications/templates/react/tsconfig-generator.js +28 -0
  24. package/dist/libs/instance-factories/applications/templates/react/use-api-hooks-generator.js +132 -0
  25. package/dist/libs/instance-factories/applications/templates/react/view-dashboard-generator.js +143 -0
  26. package/dist/libs/instance-factories/applications/templates/react/view-detail-generator.js +143 -0
  27. package/dist/libs/instance-factories/applications/templates/react/view-form-generator.js +355 -0
  28. package/dist/libs/instance-factories/applications/templates/react/view-list-generator.js +91 -0
  29. package/dist/libs/instance-factories/applications/templates/react/view-router-generator.js +79 -0
  30. package/dist/libs/instance-factories/applications/templates/react/vite-config-generator.js +42 -0
  31. package/dist/libs/instance-factories/cli/templates/commander/cli-bin-wrapper-generator.js +11 -0
  32. package/dist/libs/instance-factories/cli/templates/commander/cli-entry-generator.js +111 -0
  33. package/dist/libs/instance-factories/cli/templates/commander/command-generator.js +928 -0
  34. package/dist/libs/instance-factories/communication/templates/eventemitter/bus-generator.js +83 -0
  35. package/dist/libs/instance-factories/communication/templates/eventemitter/publisher-generator.js +91 -0
  36. package/dist/libs/instance-factories/communication/templates/eventemitter/subscriber-generator.js +86 -0
  37. package/dist/libs/instance-factories/controllers/templates/fastify/meta-routes-generator.js +93 -0
  38. package/dist/libs/instance-factories/controllers/templates/fastify/routes-generator.js +280 -0
  39. package/dist/libs/instance-factories/controllers/templates/fastify/server-generator.js +125 -0
  40. package/dist/libs/instance-factories/infrastructure/templates/docker-k8s/infrastructure-generator.js +25 -0
  41. package/dist/libs/instance-factories/orms/templates/prisma/schema-generator.js +371 -0
  42. package/dist/libs/instance-factories/orms/templates/prisma/services-generator.js +266 -0
  43. package/dist/libs/instance-factories/scaffolding/templates/generic/env-example-generator.js +51 -0
  44. package/dist/libs/instance-factories/scaffolding/templates/generic/env-generator.js +61 -0
  45. package/dist/libs/instance-factories/scaffolding/templates/generic/gitignore-generator.js +59 -0
  46. package/dist/libs/instance-factories/scaffolding/templates/generic/package-json-generator.js +126 -0
  47. package/dist/libs/instance-factories/scaffolding/templates/generic/readme-generator.js +159 -0
  48. package/dist/libs/instance-factories/scaffolding/templates/generic/tsconfig-generator.js +56 -0
  49. package/dist/libs/instance-factories/scaffolding/templates/generic/tsconfig-react-generator.js +37 -0
  50. package/dist/libs/instance-factories/sdks/templates/python/sdk-generator.js +29 -0
  51. package/dist/libs/instance-factories/sdks/templates/typescript/sdk-generator.js +28 -0
  52. package/dist/libs/instance-factories/services/templates/memory/generate-interpreter.js +14 -0
  53. package/dist/libs/instance-factories/services/templates/memory/step-conventions-memory.js +415 -0
  54. package/dist/libs/instance-factories/services/templates/prisma/behavior-generator.js +177 -0
  55. package/dist/libs/instance-factories/services/templates/prisma/controller-generator.js +413 -0
  56. package/dist/libs/instance-factories/services/templates/prisma/service-generator.js +243 -0
  57. package/dist/libs/instance-factories/services/templates/prisma/step-conventions.js +264 -0
  58. package/dist/libs/instance-factories/services/templates/shared-patterns.js +24 -0
  59. package/dist/libs/instance-factories/shared/path-resolver.js +59 -0
  60. package/dist/libs/instance-factories/storage/templates/mongodb/config-generator.js +13 -0
  61. package/dist/libs/instance-factories/storage/templates/mongodb/docker-generator.js +16 -0
  62. package/dist/libs/instance-factories/storage/templates/postgresql/config-generator.js +45 -0
  63. package/dist/libs/instance-factories/storage/templates/postgresql/docker-generator.js +46 -0
  64. package/dist/libs/instance-factories/storage/templates/redis/config-generator.js +14 -0
  65. package/dist/libs/instance-factories/storage/templates/redis/docker-generator.js +16 -0
  66. package/dist/libs/instance-factories/test-generation.js +145 -0
  67. package/dist/libs/instance-factories/testing/templates/vitest/tests-generator.js +30 -0
  68. package/dist/libs/instance-factories/tools/templates/mcp/mcp-server-generator.js +149 -0
  69. package/dist/libs/instance-factories/tools/templates/mcp/static/src/controllers/MCPServerController.js +232 -0
  70. package/dist/libs/instance-factories/tools/templates/mcp/static/src/events/EventEmitter.js +49 -0
  71. package/dist/libs/instance-factories/tools/templates/mcp/static/src/index.js +18 -0
  72. package/dist/libs/instance-factories/tools/templates/mcp/static/src/interfaces/ResourceProvider.js +0 -0
  73. package/dist/libs/instance-factories/tools/templates/mcp/static/src/models/LibrarySuggestion.js +97 -0
  74. package/dist/libs/instance-factories/tools/templates/mcp/static/src/models/SpecVerseResource.js +64 -0
  75. package/dist/libs/instance-factories/tools/templates/mcp/static/src/server/mcp-server.js +182 -0
  76. package/dist/libs/instance-factories/tools/templates/mcp/static/src/services/CLIProxyService.js +1210 -0
  77. package/dist/libs/instance-factories/tools/templates/mcp/static/src/services/EmbeddedResourcesAdapter.js +172 -0
  78. package/dist/libs/instance-factories/tools/templates/mcp/static/src/services/EntityModuleService.js +240 -0
  79. package/dist/libs/instance-factories/tools/templates/mcp/static/src/services/HybridResourcesProvider.js +147 -0
  80. package/dist/libs/instance-factories/tools/templates/mcp/static/src/services/LibraryToolsService.js +281 -0
  81. package/dist/libs/instance-factories/tools/templates/mcp/static/src/services/OrchestratorBridge.js +409 -0
  82. package/dist/libs/instance-factories/tools/templates/mcp/static/src/services/OrchestratorToolsService.js +414 -0
  83. package/dist/libs/instance-factories/tools/templates/mcp/static/src/services/PromptToolsService.js +467 -0
  84. package/dist/libs/instance-factories/tools/templates/mcp/static/src/services/ResourcesProviderService.js +135 -0
  85. package/dist/libs/instance-factories/tools/templates/mcp/static/src/types/index.js +0 -0
  86. package/dist/libs/instance-factories/tools/templates/vscode/static/extension.js +965 -0
  87. package/dist/libs/instance-factories/tools/templates/vscode/vscode-extension-generator.js +238 -0
  88. package/dist/libs/instance-factories/validation/templates/zod/validation-generator.js +25 -0
  89. package/dist/libs/instance-factories/views/index.js +48 -0
  90. package/dist/libs/instance-factories/views/templates/react/adapters/antd-adapter.js +742 -0
  91. package/dist/libs/instance-factories/views/templates/react/adapters/mui-adapter.js +824 -0
  92. package/dist/libs/instance-factories/views/templates/react/adapters/shadcn-adapter.js +719 -0
  93. package/dist/libs/instance-factories/views/templates/react/app-generator.js +45 -0
  94. package/dist/libs/instance-factories/views/templates/react/components-generator.js +779 -0
  95. package/dist/libs/instance-factories/views/templates/react/forms-generator.js +285 -0
  96. package/dist/libs/instance-factories/views/templates/react/frontend-package-json-generator.js +46 -0
  97. package/dist/libs/instance-factories/views/templates/react/hooks-generator.js +111 -0
  98. package/dist/libs/instance-factories/views/templates/react/index-css-generator.js +9 -0
  99. package/dist/libs/instance-factories/views/templates/react/index-html-generator.js +23 -0
  100. package/dist/libs/instance-factories/views/templates/react/main-tsx-generator.js +21 -0
  101. package/dist/libs/instance-factories/views/templates/react/react-component-generator.js +299 -0
  102. package/dist/libs/instance-factories/views/templates/react/router-generator.js +136 -0
  103. package/dist/libs/instance-factories/views/templates/react/router-generic-generator.js +107 -0
  104. package/dist/libs/instance-factories/views/templates/react/shared-utils-generator.js +179 -0
  105. package/dist/libs/instance-factories/views/templates/react/spec-json-generator.js +7 -0
  106. package/dist/libs/instance-factories/views/templates/react/types-generator.js +56 -0
  107. package/dist/libs/instance-factories/views/templates/react/views-metadata-generator.js +27 -0
  108. package/dist/libs/instance-factories/views/templates/react/vite-config-generator.js +29 -0
  109. package/dist/libs/instance-factories/views/templates/runtime/runtime-view-renderer.js +261 -0
  110. package/dist/libs/instance-factories/views/templates/shared/adapter-types.js +34 -0
  111. package/dist/libs/instance-factories/views/templates/shared/atomic-components-registry.js +800 -0
  112. package/dist/libs/instance-factories/views/templates/shared/base-generator.js +305 -0
  113. package/dist/libs/instance-factories/views/templates/shared/component-metadata.js +517 -0
  114. package/dist/libs/instance-factories/views/templates/shared/composite-pattern-types.js +0 -0
  115. package/dist/libs/instance-factories/views/templates/shared/composite-patterns.js +445 -0
  116. package/dist/libs/instance-factories/views/templates/shared/index.js +80 -0
  117. package/dist/libs/instance-factories/views/templates/shared/pattern-validator.js +210 -0
  118. package/dist/libs/instance-factories/views/templates/shared/property-mapper.js +492 -0
  119. package/dist/libs/instance-factories/views/templates/shared/syntax-mapper.js +321 -0
  120. package/package.json +3 -2
@@ -0,0 +1,172 @@
1
+ import { SpecVerseResourceModel } from "../models/SpecVerseResource.js";
2
+ class EmbeddedResourcesAdapter {
3
+ resourceCatalog = /* @__PURE__ */ new Map();
4
+ embeddedResources;
5
+ isInitialized = false;
6
+ constructor(embeddedResources) {
7
+ this.embeddedResources = embeddedResources;
8
+ }
9
+ async initializeResources() {
10
+ if (this.isInitialized) {
11
+ return;
12
+ }
13
+ const resources = [
14
+ {
15
+ uri: "specverse://schema/json",
16
+ name: "SpecVerse v3.1 JSON Schema",
17
+ description: "Complete JSON schema for SpecVerse v3.1 specifications",
18
+ mimeType: "application/json"
19
+ },
20
+ {
21
+ uri: "specverse://schema/ai-yaml",
22
+ name: "SpecVerse v3.1 AI-Optimized Schema",
23
+ description: "AI-friendly YAML schema with guidance and examples",
24
+ mimeType: "application/x-yaml"
25
+ },
26
+ {
27
+ uri: "specverse://prompts/create",
28
+ name: "Create Prompt Template",
29
+ description: "Template for generating SpecVerse specifications from requirements",
30
+ mimeType: "application/x-yaml"
31
+ },
32
+ {
33
+ uri: "specverse://prompts/analyse",
34
+ name: "Analysis Prompt Template",
35
+ description: "Template for extracting specifications from existing code",
36
+ mimeType: "application/x-yaml"
37
+ },
38
+ {
39
+ uri: "specverse://prompts/materialise",
40
+ name: "Implementation Planning Template",
41
+ description: "Template for creating implementation plans from specifications",
42
+ mimeType: "application/x-yaml"
43
+ },
44
+ {
45
+ uri: "specverse://prompts/realize",
46
+ name: "Code Generation Template",
47
+ description: "Template for generating source code from specifications",
48
+ mimeType: "application/x-yaml"
49
+ },
50
+ {
51
+ uri: "specverse://libraries/catalog",
52
+ name: "SpecVerse Library Catalog",
53
+ description: "Complete catalog of available SpecVerse libraries with AI metadata",
54
+ mimeType: "application/x-yaml"
55
+ },
56
+ {
57
+ uri: "specverse://examples/chat-prompts",
58
+ name: "Chat Prompt Examples",
59
+ description: "Example prompts for terminal/chat-based AI interactions",
60
+ mimeType: "text/markdown"
61
+ },
62
+ {
63
+ uri: "specverse://examples/api-calls",
64
+ name: "API Integration Examples",
65
+ description: "Examples for API-based AI integrations",
66
+ mimeType: "application/javascript"
67
+ }
68
+ ];
69
+ for (const resourceData of resources) {
70
+ const resource = SpecVerseResourceModel.create(resourceData);
71
+ this.resourceCatalog.set(resource.uri, resource);
72
+ }
73
+ this.isInitialized = true;
74
+ }
75
+ async listResources() {
76
+ await this.initializeResources();
77
+ return Array.from(this.resourceCatalog.values()).map((resource) => ({
78
+ uri: resource.uri,
79
+ name: resource.name,
80
+ description: resource.description,
81
+ mimeType: resource.mimeType,
82
+ content: resource.content,
83
+ metadata: resource.metadata
84
+ }));
85
+ }
86
+ async getResourceContent(uri) {
87
+ await this.initializeResources();
88
+ const resource = this.resourceCatalog.get(uri);
89
+ if (!resource) {
90
+ throw new Error(`Resource not found: ${uri}`);
91
+ }
92
+ if (resource.isLoaded()) {
93
+ return resource.content;
94
+ }
95
+ const resourcePath = this.resolveResourcePath(uri);
96
+ const embeddedResource = this.embeddedResources[resourcePath];
97
+ if (!embeddedResource) {
98
+ throw new Error(`Embedded resource not found: ${resourcePath} for URI: ${uri}`);
99
+ }
100
+ const updatedResource = resource.withContent(embeddedResource.content);
101
+ this.resourceCatalog.set(uri, updatedResource);
102
+ return embeddedResource.content;
103
+ }
104
+ async readResource(uri) {
105
+ try {
106
+ const content = await this.getResourceContent(uri);
107
+ const resource = this.resourceCatalog.get(uri);
108
+ return {
109
+ content: [{
110
+ type: "resource",
111
+ resource: {
112
+ uri: resource.uri,
113
+ name: resource.name,
114
+ description: resource.description,
115
+ mimeType: resource.mimeType,
116
+ content
117
+ }
118
+ }]
119
+ };
120
+ } catch (error) {
121
+ return {
122
+ content: [{
123
+ type: "text",
124
+ text: `Error reading resource: ${error instanceof Error ? error.message : String(error)}`
125
+ }],
126
+ isError: true
127
+ };
128
+ }
129
+ }
130
+ resolveResourcePath(uri) {
131
+ switch (uri) {
132
+ case "specverse://schema/json":
133
+ return "schemas/SPECVERSE-SCHEMA.json";
134
+ case "specverse://schema/ai-yaml":
135
+ return "schemas/specverse-ai.yaml";
136
+ case "specverse://prompts/create":
137
+ return "prompts/create.prompt.yaml";
138
+ case "specverse://prompts/analyse":
139
+ return "prompts/analyse.prompt.yaml";
140
+ case "specverse://prompts/materialise":
141
+ return "prompts/materialise.prompt.yaml";
142
+ case "specverse://prompts/realize":
143
+ return "prompts/realize.prompt.yaml";
144
+ case "specverse://libraries/catalog":
145
+ return "libraries/catalog/library-catalog.yaml";
146
+ case "specverse://examples/chat-prompts":
147
+ return "examples/chat-prompts/ecommerce-store-example.md";
148
+ case "specverse://examples/api-calls":
149
+ return "examples/api-calls/orchestrator-workflow-example.js";
150
+ default:
151
+ throw new Error(`Unknown resource URI: ${uri}`);
152
+ }
153
+ }
154
+ isResourceAvailable(uri) {
155
+ return this.resourceCatalog.has(uri);
156
+ }
157
+ getCachedResourceCount() {
158
+ return Array.from(this.resourceCatalog.values()).filter((r) => r.isLoaded()).length;
159
+ }
160
+ getEmbeddedResourcesInfo() {
161
+ const paths = Object.keys(this.embeddedResources);
162
+ const totalSize = Object.values(this.embeddedResources).reduce((sum, res) => sum + res.size, 0);
163
+ return {
164
+ count: paths.length,
165
+ totalSize,
166
+ paths
167
+ };
168
+ }
169
+ }
170
+ export {
171
+ EmbeddedResourcesAdapter
172
+ };
@@ -0,0 +1,240 @@
1
+ class EntityModuleService {
2
+ registry = null;
3
+ behaviouralProcessor = null;
4
+ loaded = false;
5
+ /**
6
+ * Attempt to load the entity registry from @specverse/engine-entities.
7
+ * Fails gracefully if not available.
8
+ */
9
+ async initialize() {
10
+ try {
11
+ const { resolve, dirname } = await import("path");
12
+ const { fileURLToPath } = await import("url");
13
+ const baseDir = resolve(dirname(fileURLToPath(import.meta.url)), "..", "..", "..");
14
+ const entitiesPath = resolve(baseDir, "dist", "entities", "index.js");
15
+ const conventionPath = resolve(baseDir, "dist", "entities", "_shared", "behaviour", "convention-processor.js");
16
+ const entitiesModule = await import(entitiesPath);
17
+ entitiesModule.bootstrapEntityModules();
18
+ this.registry = entitiesModule.getEntityRegistry();
19
+ const { BehaviouralConventionProcessor } = await import(conventionPath);
20
+ this.behaviouralProcessor = new BehaviouralConventionProcessor();
21
+ const entitiesDir = resolve(baseDir, "src", "entities");
22
+ this.behaviouralProcessor.loadGrammarsFromEntities(entitiesDir);
23
+ this.loaded = true;
24
+ return true;
25
+ } catch (error) {
26
+ this.loaded = false;
27
+ return false;
28
+ }
29
+ }
30
+ isAvailable() {
31
+ return this.loaded;
32
+ }
33
+ /**
34
+ * Get entity module metadata for all registered modules.
35
+ */
36
+ getEntityModules() {
37
+ if (!this.registry) return [];
38
+ const modules = this.registry.getInDependencyOrder();
39
+ return modules.map((mod) => ({
40
+ name: mod.name,
41
+ type: mod.type,
42
+ version: mod.version,
43
+ dependsOn: mod.dependsOn || [],
44
+ hasConventionProcessor: !!mod.conventionProcessor,
45
+ inferenceRuleCount: mod.inferenceRules?.length || 0,
46
+ inferenceRules: (mod.inferenceRules || []).map((r) => ({
47
+ id: r.id,
48
+ description: r.description,
49
+ triggeredBy: r.triggeredBy,
50
+ generates: r.generates
51
+ })),
52
+ diagramPlugins: mod.diagramPlugins || [],
53
+ generatorCount: mod.generators?.length || 0
54
+ }));
55
+ }
56
+ /**
57
+ * Get behavioural convention grammars for all entities.
58
+ */
59
+ getConventionGrammars() {
60
+ if (!this.behaviouralProcessor) return [];
61
+ return this.behaviouralProcessor.getGrammars().map((g) => ({
62
+ entity: g.entity,
63
+ domain: g.domain,
64
+ conventions: Object.values(g.conventions).map((c) => ({
65
+ name: c.name,
66
+ pattern: c.pattern,
67
+ description: c.description,
68
+ expandsTo: c.expandsTo
69
+ }))
70
+ }));
71
+ }
72
+ /**
73
+ * Expand a behavioural constraint string.
74
+ */
75
+ expandConstraint(input) {
76
+ if (!this.behaviouralProcessor) {
77
+ return { success: false, error: "Behavioural convention processor not available" };
78
+ }
79
+ const result = this.behaviouralProcessor.expand(input);
80
+ if (result) {
81
+ return { success: true, result };
82
+ }
83
+ return { success: false, error: `No matching convention pattern for: "${input}"` };
84
+ }
85
+ /**
86
+ * Generate MCP resources from entity module metadata.
87
+ */
88
+ generateResources() {
89
+ if (!this.loaded) return [];
90
+ const resources = [];
91
+ const modules = this.getEntityModules();
92
+ resources.push({
93
+ uri: "specverse://entities/registry",
94
+ name: "Entity Module Registry",
95
+ description: `All ${modules.length} registered entity modules with their facets, dependencies, and capabilities`,
96
+ mimeType: "application/json",
97
+ content: JSON.stringify({ entityModules: modules }, null, 2)
98
+ });
99
+ const grammars = this.getConventionGrammars();
100
+ const totalConventions = grammars.reduce((sum, g) => sum + g.conventions.length, 0);
101
+ resources.push({
102
+ uri: "specverse://entities/conventions",
103
+ name: "Behavioural Conventions Catalog",
104
+ description: `${totalConventions} behavioural conventions across ${grammars.length} entities. Use in constraints: section of .specly files.`,
105
+ mimeType: "application/json",
106
+ content: JSON.stringify({ grammars }, null, 2)
107
+ });
108
+ const allRules = modules.flatMap((m) => m.inferenceRules);
109
+ resources.push({
110
+ uri: "specverse://entities/inference-rules",
111
+ name: "Inference Rules Summary",
112
+ description: `${allRules.length} inference rules that generate architecture from specifications`,
113
+ mimeType: "application/json",
114
+ content: JSON.stringify({ rules: allRules }, null, 2)
115
+ });
116
+ const allPlugins = modules.flatMap(
117
+ (m) => m.diagramPlugins.map((p) => ({ ...p, entity: m.name }))
118
+ );
119
+ resources.push({
120
+ uri: "specverse://entities/diagram-plugins",
121
+ name: "Diagram Plugins",
122
+ description: `${allPlugins.length} diagram types available for visualization`,
123
+ mimeType: "application/json",
124
+ content: JSON.stringify({ plugins: allPlugins }, null, 2)
125
+ });
126
+ return resources;
127
+ }
128
+ /**
129
+ * Generate MCP tools for entity module interaction.
130
+ */
131
+ generateTools() {
132
+ if (!this.loaded) return [];
133
+ return [
134
+ {
135
+ name: "specverse_expand_constraint",
136
+ description: 'Expand a behavioural constraint string into a Quint invariant. Example: "models must have attributes"',
137
+ inputSchema: {
138
+ type: "object",
139
+ properties: {
140
+ constraint: {
141
+ type: "string",
142
+ description: 'Human-readable constraint to expand (e.g., "models must have attributes")'
143
+ }
144
+ },
145
+ required: ["constraint"]
146
+ }
147
+ },
148
+ {
149
+ name: "specverse_list_conventions",
150
+ description: "List available behavioural conventions for a specific entity type",
151
+ inputSchema: {
152
+ type: "object",
153
+ properties: {
154
+ entity: {
155
+ type: "string",
156
+ description: 'Entity type (e.g., "models", "controllers", "services")'
157
+ }
158
+ },
159
+ required: ["entity"]
160
+ }
161
+ },
162
+ {
163
+ name: "specverse_entity_info",
164
+ description: "Get detailed metadata about an entity module (conventions, inference rules, diagram plugins)",
165
+ inputSchema: {
166
+ type: "object",
167
+ properties: {
168
+ entity: {
169
+ type: "string",
170
+ description: 'Entity name (e.g., "models", "controllers", "deployments")'
171
+ }
172
+ },
173
+ required: ["entity"]
174
+ }
175
+ }
176
+ ];
177
+ }
178
+ /**
179
+ * Execute an entity module tool.
180
+ */
181
+ async executeTool(name, args) {
182
+ switch (name) {
183
+ case "specverse_expand_constraint": {
184
+ const result = this.expandConstraint(args.constraint);
185
+ return {
186
+ content: [{
187
+ type: "text",
188
+ text: JSON.stringify(result, null, 2)
189
+ }]
190
+ };
191
+ }
192
+ case "specverse_list_conventions": {
193
+ const grammars = this.getConventionGrammars();
194
+ const grammar = grammars.find((g) => g.entity === args.entity);
195
+ if (!grammar) {
196
+ return {
197
+ content: [{
198
+ type: "text",
199
+ text: `No conventions found for entity "${args.entity}". Available: ${grammars.map((g) => g.entity).join(", ")}`
200
+ }]
201
+ };
202
+ }
203
+ return {
204
+ content: [{
205
+ type: "text",
206
+ text: JSON.stringify(grammar, null, 2)
207
+ }]
208
+ };
209
+ }
210
+ case "specverse_entity_info": {
211
+ const modules = this.getEntityModules();
212
+ const mod = modules.find((m) => m.name === args.entity);
213
+ if (!mod) {
214
+ return {
215
+ content: [{
216
+ type: "text",
217
+ text: `Entity "${args.entity}" not found. Available: ${modules.map((m) => m.name).join(", ")}`
218
+ }]
219
+ };
220
+ }
221
+ return {
222
+ content: [{
223
+ type: "text",
224
+ text: JSON.stringify(mod, null, 2)
225
+ }]
226
+ };
227
+ }
228
+ default:
229
+ return {
230
+ content: [{
231
+ type: "text",
232
+ text: `Unknown entity module tool: ${name}`
233
+ }]
234
+ };
235
+ }
236
+ }
237
+ }
238
+ export {
239
+ EntityModuleService
240
+ };
@@ -0,0 +1,147 @@
1
+ import { existsSync, readFileSync } from "fs";
2
+ import { join, dirname } from "path";
3
+ import { fileURLToPath } from "url";
4
+ import { ResourcesProviderService } from "./ResourcesProviderService.js";
5
+ import { EmbeddedResourcesAdapter } from "./EmbeddedResourcesAdapter.js";
6
+ const __filename = fileURLToPath(import.meta.url);
7
+ const __dirname = dirname(__filename);
8
+ class HybridResourcesProvider {
9
+ provider;
10
+ mode;
11
+ constructor(config) {
12
+ this.mode = this.detectMode(config);
13
+ if (this.mode === "embedded") {
14
+ if (!config.embeddedResources) {
15
+ this.provider = new EmbeddedResourcesAdapter({});
16
+ } else {
17
+ this.provider = new EmbeddedResourcesAdapter(config.embeddedResources);
18
+ }
19
+ } else {
20
+ this.provider = new ResourcesProviderService(config.resourcesPath);
21
+ }
22
+ }
23
+ detectMode(config) {
24
+ if (config.mode === "filesystem") return "filesystem";
25
+ if (config.mode === "embedded") return "embedded";
26
+ if (config.embeddedResources) {
27
+ return "embedded";
28
+ }
29
+ if (this.hasEmbeddedResourcesFile()) {
30
+ return "embedded";
31
+ }
32
+ if (this.isWebEnvironment()) {
33
+ return "embedded";
34
+ }
35
+ const resourcesPath = config.resourcesPath || join(__dirname, "../../resources");
36
+ if (existsSync(resourcesPath)) {
37
+ return "filesystem";
38
+ }
39
+ if (this.tryImportEmbeddedResources()) {
40
+ return "embedded";
41
+ }
42
+ return "filesystem";
43
+ }
44
+ hasEmbeddedResourcesFile() {
45
+ try {
46
+ const embeddedPath2 = join(dirname(__dirname), "embedded-resources.js");
47
+ return existsSync(embeddedPath2);
48
+ } catch {
49
+ return false;
50
+ }
51
+ }
52
+ isWebEnvironment() {
53
+ try {
54
+ if (typeof window !== "undefined") return true;
55
+ return this.hasEmbeddedResourcesFile();
56
+ } catch {
57
+ return false;
58
+ }
59
+ }
60
+ loadEmbeddedResources() {
61
+ try {
62
+ const embeddedPath = join(dirname(__dirname), "embedded-resources.js");
63
+ if (existsSync(embeddedPath)) {
64
+ const content = readFileSync(embeddedPath, "utf-8");
65
+ const match = content.match(/export const EMBEDDED_RESOURCES = ({[\s\S]*?});/);
66
+ if (match) {
67
+ const embeddedResources = eval("(" + match[1] + ")");
68
+ return embeddedResources;
69
+ }
70
+ }
71
+ return null;
72
+ } catch (error) {
73
+ console.warn("Failed to load embedded resources:", error);
74
+ return null;
75
+ }
76
+ }
77
+ async loadEmbeddedResourcesAsync() {
78
+ try {
79
+ const embeddedPath2 = join(dirname(__dirname), "embedded-resources.js");
80
+ if (existsSync(embeddedPath2)) {
81
+ const embeddedModule = await import(embeddedPath2);
82
+ return embeddedModule.EMBEDDED_RESOURCES || null;
83
+ }
84
+ return null;
85
+ } catch (error) {
86
+ console.warn("Dynamic import of embedded resources failed:", error);
87
+ return null;
88
+ }
89
+ }
90
+ tryImportEmbeddedResources() {
91
+ return this.loadEmbeddedResources();
92
+ }
93
+ async initializeResources() {
94
+ if (this.mode === "embedded" && this.provider instanceof EmbeddedResourcesAdapter) {
95
+ const providerInfo = this.provider.getEmbeddedResourcesInfo();
96
+ if (providerInfo.count === 0) {
97
+ try {
98
+ const embeddedResources2 = await this.loadEmbeddedResourcesAsync();
99
+ if (embeddedResources2) {
100
+ this.provider = new EmbeddedResourcesAdapter(embeddedResources2);
101
+ }
102
+ } catch (error) {
103
+ console.warn("Failed to load embedded resources, falling back to filesystem:", error);
104
+ this.mode = "filesystem";
105
+ this.provider = new ResourcesProviderService();
106
+ }
107
+ }
108
+ }
109
+ return this.provider.initializeResources();
110
+ }
111
+ async listResources() {
112
+ return this.provider.listResources();
113
+ }
114
+ async getResourceContent(uri) {
115
+ return this.provider.getResourceContent(uri);
116
+ }
117
+ async readResource(uri) {
118
+ return this.provider.readResource(uri);
119
+ }
120
+ isResourceAvailable(uri) {
121
+ return this.provider.isResourceAvailable(uri);
122
+ }
123
+ getCachedResourceCount() {
124
+ return this.provider.getCachedResourceCount();
125
+ }
126
+ getMode() {
127
+ return this.mode;
128
+ }
129
+ getProviderInfo() {
130
+ const info = {
131
+ mode: this.mode,
132
+ type: this.provider.constructor.name,
133
+ resourcesInfo: void 0
134
+ };
135
+ if (this.provider instanceof EmbeddedResourcesAdapter) {
136
+ info.resourcesInfo = this.provider.getEmbeddedResourcesInfo();
137
+ } else if (this.provider instanceof ResourcesProviderService) {
138
+ info.resourcesInfo = {
139
+ cached: this.provider.getCachedResourceCount()
140
+ };
141
+ }
142
+ return info;
143
+ }
144
+ }
145
+ export {
146
+ HybridResourcesProvider
147
+ };