silgi 0.0.14 → 0.1.0-beta.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (186) hide show
  1. package/README.md +102 -1
  2. package/dist/_virtual/_rolldown/runtime.mjs +5 -0
  3. package/dist/adapters/astro.d.mts +17 -0
  4. package/dist/adapters/astro.mjs +24 -0
  5. package/dist/adapters/aws-lambda.d.mts +31 -0
  6. package/dist/adapters/aws-lambda.mjs +85 -0
  7. package/dist/adapters/elysia.d.mts +17 -0
  8. package/dist/adapters/elysia.mjs +76 -0
  9. package/dist/adapters/express.d.mts +16 -0
  10. package/dist/adapters/express.mjs +78 -0
  11. package/dist/adapters/fastify.d.mts +15 -0
  12. package/dist/adapters/fastify.mjs +78 -0
  13. package/dist/adapters/message-port.d.mts +37 -0
  14. package/dist/adapters/message-port.mjs +129 -0
  15. package/dist/adapters/nestjs.d.mts +25 -0
  16. package/dist/adapters/nestjs.mjs +91 -0
  17. package/dist/adapters/nextjs.d.mts +21 -0
  18. package/dist/adapters/nextjs.mjs +30 -0
  19. package/dist/adapters/peer.d.mts +27 -0
  20. package/dist/adapters/peer.mjs +36 -0
  21. package/dist/adapters/remix.d.mts +17 -0
  22. package/dist/adapters/remix.mjs +24 -0
  23. package/dist/adapters/solidstart.d.mts +14 -0
  24. package/dist/adapters/solidstart.mjs +30 -0
  25. package/dist/adapters/sveltekit.d.mts +18 -0
  26. package/dist/adapters/sveltekit.mjs +33 -0
  27. package/dist/analyze.mjs +26 -0
  28. package/dist/broker/index.d.mts +62 -0
  29. package/dist/broker/index.mjs +153 -0
  30. package/dist/broker/nats.d.mts +33 -0
  31. package/dist/broker/nats.mjs +31 -0
  32. package/dist/broker/redis.d.mts +51 -0
  33. package/dist/broker/redis.mjs +92 -0
  34. package/dist/builder.d.mts +36 -0
  35. package/dist/builder.mjs +51 -0
  36. package/dist/callable.d.mts +17 -0
  37. package/dist/callable.mjs +42 -0
  38. package/dist/client/adapters/fetch/index.d.mts +17 -0
  39. package/dist/client/adapters/fetch/index.mjs +61 -0
  40. package/dist/client/adapters/ofetch/index.d.mts +41 -0
  41. package/dist/client/adapters/ofetch/index.mjs +92 -0
  42. package/dist/client/client.d.mts +29 -0
  43. package/dist/client/client.mjs +54 -0
  44. package/dist/client/dynamic-link.d.mts +15 -0
  45. package/dist/client/dynamic-link.mjs +16 -0
  46. package/dist/client/index.d.mts +7 -0
  47. package/dist/client/index.mjs +6 -0
  48. package/dist/client/interceptor.d.mts +31 -0
  49. package/dist/client/interceptor.mjs +34 -0
  50. package/dist/client/merge.d.mts +28 -0
  51. package/dist/client/merge.mjs +30 -0
  52. package/dist/client/openapi.d.mts +29 -0
  53. package/dist/client/openapi.mjs +89 -0
  54. package/dist/client/plugins/batch.d.mts +20 -0
  55. package/dist/client/plugins/batch.mjs +64 -0
  56. package/dist/client/plugins/csrf.d.mts +13 -0
  57. package/dist/client/plugins/csrf.mjs +20 -0
  58. package/dist/client/plugins/dedupe.d.mts +10 -0
  59. package/dist/client/plugins/dedupe.mjs +28 -0
  60. package/dist/client/plugins/index.d.mts +5 -0
  61. package/dist/client/plugins/index.mjs +5 -0
  62. package/dist/client/plugins/retry.d.mts +11 -0
  63. package/dist/client/plugins/retry.mjs +21 -0
  64. package/dist/client/server.d.mts +16 -0
  65. package/dist/client/server.mjs +60 -0
  66. package/dist/client/types.d.mts +29 -0
  67. package/dist/codec/devalue.d.mts +21 -0
  68. package/dist/codec/devalue.mjs +32 -0
  69. package/dist/codec/msgpack.d.mts +21 -0
  70. package/dist/codec/msgpack.mjs +59 -0
  71. package/dist/compile.d.mts +54 -0
  72. package/dist/compile.mjs +305 -0
  73. package/dist/contract.d.mts +36 -0
  74. package/dist/contract.mjs +40 -0
  75. package/dist/core/error.d.mts +104 -0
  76. package/dist/core/error.mjs +139 -0
  77. package/dist/core/handler.mjs +546 -0
  78. package/dist/core/iterator.d.mts +17 -0
  79. package/dist/core/iterator.mjs +79 -0
  80. package/dist/core/router-utils.mjs +16 -0
  81. package/dist/core/schema.d.mts +19 -0
  82. package/dist/core/schema.mjs +26 -0
  83. package/dist/core/serve.mjs +38 -0
  84. package/dist/core/sse.d.mts +16 -0
  85. package/dist/core/sse.mjs +95 -0
  86. package/dist/core/storage.d.mts +21 -0
  87. package/dist/core/storage.mjs +63 -0
  88. package/dist/core/utils.mjs +21 -0
  89. package/dist/fast-stringify.mjs +125 -0
  90. package/dist/index.d.mts +15 -37
  91. package/dist/index.mjs +13 -7
  92. package/dist/integrations/ai/index.d.mts +25 -0
  93. package/dist/integrations/ai/index.mjs +116 -0
  94. package/dist/integrations/react/index.d.mts +83 -0
  95. package/dist/integrations/react/index.mjs +197 -0
  96. package/dist/integrations/tanstack-query/index.d.mts +120 -0
  97. package/dist/integrations/tanstack-query/index.mjs +100 -0
  98. package/dist/integrations/tanstack-query/ssr.d.mts +51 -0
  99. package/dist/integrations/tanstack-query/ssr.mjs +89 -0
  100. package/dist/integrations/zod/converter.d.mts +75 -0
  101. package/dist/integrations/zod/converter.mjs +345 -0
  102. package/dist/integrations/zod/index.d.mts +2 -0
  103. package/dist/integrations/zod/index.mjs +2 -0
  104. package/dist/lazy.d.mts +24 -0
  105. package/dist/lazy.mjs +27 -0
  106. package/dist/lifecycle.d.mts +36 -0
  107. package/dist/lifecycle.mjs +46 -0
  108. package/dist/map-input.d.mts +17 -0
  109. package/dist/map-input.mjs +24 -0
  110. package/dist/plugins/analytics.d.mts +168 -0
  111. package/dist/plugins/analytics.mjs +459 -0
  112. package/dist/plugins/batch-server.d.mts +20 -0
  113. package/dist/plugins/batch-server.mjs +86 -0
  114. package/dist/plugins/body-limit.d.mts +16 -0
  115. package/dist/plugins/body-limit.mjs +44 -0
  116. package/dist/plugins/cache.d.mts +170 -0
  117. package/dist/plugins/cache.mjs +200 -0
  118. package/dist/plugins/coerce.d.mts +21 -0
  119. package/dist/plugins/coerce.mjs +46 -0
  120. package/dist/plugins/compression.d.mts +19 -0
  121. package/dist/plugins/compression.mjs +23 -0
  122. package/dist/plugins/cookies.d.mts +44 -0
  123. package/dist/plugins/cookies.mjs +67 -0
  124. package/dist/plugins/cors.d.mts +39 -0
  125. package/dist/plugins/cors.mjs +56 -0
  126. package/dist/plugins/custom-serializer.d.mts +57 -0
  127. package/dist/plugins/custom-serializer.mjs +40 -0
  128. package/dist/plugins/file-upload.d.mts +38 -0
  129. package/dist/plugins/file-upload.mjs +100 -0
  130. package/dist/plugins/index.d.mts +16 -0
  131. package/dist/plugins/index.mjs +16 -0
  132. package/dist/plugins/otel.d.mts +35 -0
  133. package/dist/plugins/otel.mjs +40 -0
  134. package/dist/plugins/pino.d.mts +60 -0
  135. package/dist/plugins/pino.mjs +42 -0
  136. package/dist/plugins/pubsub.d.mts +50 -0
  137. package/dist/plugins/pubsub.mjs +53 -0
  138. package/dist/plugins/ratelimit.d.mts +51 -0
  139. package/dist/plugins/ratelimit.mjs +81 -0
  140. package/dist/plugins/signing.d.mts +41 -0
  141. package/dist/plugins/signing.mjs +115 -0
  142. package/dist/plugins/strict-get.d.mts +10 -0
  143. package/dist/plugins/strict-get.mjs +33 -0
  144. package/dist/route/add.mjs +240 -0
  145. package/dist/route/compiler.mjs +373 -0
  146. package/dist/route/context.mjs +12 -0
  147. package/dist/route/types.d.mts +11 -0
  148. package/dist/route/utils.mjs +17 -0
  149. package/dist/scalar.d.mts +53 -0
  150. package/dist/scalar.mjs +330 -0
  151. package/dist/silgi.d.mts +139 -0
  152. package/dist/silgi.mjs +113 -0
  153. package/dist/trpc-interop.d.mts +22 -0
  154. package/dist/trpc-interop.mjs +68 -0
  155. package/dist/types.d.mts +82 -0
  156. package/dist/ws.d.mts +42 -0
  157. package/dist/ws.mjs +137 -0
  158. package/lib/dashboard/index.html +123 -0
  159. package/lib/ocache.d.mts +1 -0
  160. package/lib/ocache.mjs +1 -0
  161. package/lib/ofetch.d.mts +1 -0
  162. package/lib/ofetch.mjs +1 -0
  163. package/lib/srvx.d.mts +1 -0
  164. package/lib/srvx.mjs +1 -0
  165. package/lib/unstorage.d.mts +1 -0
  166. package/lib/unstorage.mjs +1 -0
  167. package/package.json +291 -65
  168. package/bin/silgi.mjs +0 -3
  169. package/dist/chunks/generate.mjs +0 -933
  170. package/dist/chunks/init.mjs +0 -21
  171. package/dist/cli/config.d.mts +0 -19
  172. package/dist/cli/config.d.ts +0 -19
  173. package/dist/cli/config.mjs +0 -5
  174. package/dist/cli/index.d.mts +0 -2
  175. package/dist/cli/index.d.ts +0 -2
  176. package/dist/cli/index.mjs +0 -119
  177. package/dist/index.d.ts +0 -37
  178. package/dist/plugins/openapi.d.mts +0 -138
  179. package/dist/plugins/openapi.d.ts +0 -138
  180. package/dist/plugins/openapi.mjs +0 -204
  181. package/dist/plugins/scalar.d.mts +0 -14
  182. package/dist/plugins/scalar.d.ts +0 -14
  183. package/dist/plugins/scalar.mjs +0 -66
  184. package/dist/shared/silgi.BMCYk2cR.mjs +0 -841
  185. package/dist/shared/silgi.D5qK9QOm.d.mts +0 -301
  186. package/dist/shared/silgi.D5qK9QOm.d.ts +0 -301
@@ -1,933 +0,0 @@
1
- import { loadConfig } from 'c12';
2
- import { defineCommand } from 'citty';
3
- import { writeFileSync, promises } from 'node:fs';
4
- import { dirname, relative, join } from 'node:path';
5
- import antfu from '@antfu/eslint-config';
6
- import consola from 'consola';
7
- import defu from 'defu';
8
- import { ESLint } from 'eslint';
9
- import { createJiti } from 'jiti';
10
- import { resolve } from 'pathe';
11
- import { camelCase, pascalCase } from 'scule';
12
- import { parseSync } from '@oxc-parser/wasm';
13
- import { writeFile } from 'node:fs/promises';
14
-
15
- async function generateClientGenTS(storage, outputDir) {
16
- const services = Object.keys(storage);
17
- let clientGenContent = `
18
- `;
19
- const imports = [];
20
- for (const service of services) {
21
- const clientStore = storage[service];
22
- let clientStoreContent = `
23
- `;
24
- if (Array.isArray(clientStore?.graphql?.query) && clientStore.graphql.query.length > 0) {
25
- const queryContent = `
26
- query: {
27
- ${clientStore.graphql.query.map((query) => {
28
- imports.push(`import {${query.key}} from '${query.path}'`);
29
- return `${query.newKey}: {
30
- input: VariablesOf<typeof ${query.key}>
31
- output: ResultOf<typeof ${query.key}>
32
- }`;
33
- }).join("\n")}
34
- }
35
- `;
36
- clientStoreContent += queryContent;
37
- }
38
- if (Array.isArray(clientStore?.graphql?.mutation) && clientStore.graphql.mutation.length > 0) {
39
- const mutationContent = `
40
- mutation: {
41
- ${clientStore.graphql.mutation.map((mutation) => {
42
- imports.push(`import {${mutation.key}} from '${mutation.path}'`);
43
- return `${mutation.newKey}: {
44
- input: VariablesOf<typeof ${mutation.key}>
45
- output: ResultOf<typeof ${mutation.key}>
46
- }`;
47
- }).join("\n")}
48
- }
49
- `;
50
- clientStoreContent += mutationContent;
51
- }
52
- if (Array.isArray(clientStore?.zod) && clientStore.zod.length > 0) {
53
- const zodContent = `
54
- zod: {
55
- ${clientStore.zod.map((zod) => {
56
- imports.push(`import {${zod.key}} from '${zod.path}'`);
57
- return `${zod.newKey}: {
58
- input: Zod.infer<typeof ${zod.key}>
59
- }`;
60
- }).join("\n")}
61
- }
62
- `;
63
- clientStoreContent += zodContent;
64
- }
65
- clientGenContent += `
66
- ${service}: {
67
- ${clientStoreContent}
68
- }
69
- `;
70
- }
71
- const content = `// THIS FILE IS GENERATED, DO NOT EDIT!
72
- /* tslint:disable */
73
- /* eslint-disable */
74
- /* prettier-ignore */
75
- /* silgi - productdevbook.com */
76
- import type { ResultOf, VariablesOf } from 'gql.tada'
77
- import type { z as Zod } from 'zod'
78
- ${imports.join("\n")}
79
-
80
- export interface SilgiClientStore {
81
- ${clientGenContent}
82
- }
83
- `;
84
- writeFileSync(outputDir, content, "utf-8");
85
- }
86
-
87
- class SchemaParser {
88
- parseExports(content, filePath) {
89
- const ast = parseSync(content, { sourceType: "module", sourceFilename: filePath });
90
- return {
91
- exportTS: this.parseTypeExports(ast),
92
- exportVariables: this.parseVariableExports(ast)
93
- };
94
- }
95
- parseTypeExports(ast) {
96
- return ast.program.body.filter((i) => i.type === "ExportNamedDeclaration").filter(
97
- (i) => i.declaration?.type === "TSInterfaceDeclaration" || i.declaration?.type === "TSTypeAliasDeclaration"
98
- ).flatMap((node) => node.declaration?.id.name);
99
- }
100
- parseVariableExports(ast) {
101
- return ast.program.body.filter((i) => i.type === "ExportNamedDeclaration").filter((i) => i.declaration?.type === "VariableDeclaration").flatMap((node) => node.declaration?.declarations.map((decl) => decl.id.name));
102
- }
103
- }
104
-
105
- class TypescriptGenerator {
106
- storage;
107
- outputDir;
108
- constructor(storage, outputDir) {
109
- this.storage = storage;
110
- this.outputDir = outputDir;
111
- }
112
- async generate() {
113
- try {
114
- const { scopes, modules } = this.extractScopesAndModules();
115
- const processedData = this.processStorageData(scopes, modules);
116
- const content = this.generateInterfaceContent(processedData);
117
- await this.writeOutputFile(content);
118
- consola.success(`Server interface in ${this.outputDir}`);
119
- } catch (error) {
120
- consola.error("Error generating Silgi interface:", error);
121
- throw error;
122
- }
123
- }
124
- extractScopesAndModules() {
125
- const scopes = new Set(
126
- Object.keys(this.storage.schemaObjects || {}).filter((scope) => scope !== "modules")
127
- );
128
- const modules = new Set(
129
- Object.keys(this.storage.modules || {})
130
- );
131
- return { scopes, modules };
132
- }
133
- processStorageData(scopes, modules) {
134
- const zodInterfacesImports = [];
135
- const importsString = [];
136
- const scopeDatas = [];
137
- const modulesData = [];
138
- for (const scope of scopes) {
139
- if (!this.storage.schemaObjects)
140
- throw new Error("No schemaObjects found in storage");
141
- const scopeData = this.storage.schemaObjects[scope];
142
- const processed = this.processScopeData(scope, scopeData, zodInterfacesImports, importsString);
143
- scopeDatas.push(processed);
144
- }
145
- for (const module of modules) {
146
- if (this.storage.modules && this.storage.modules[module]) {
147
- const moduleData = this.storage.modules[module];
148
- const processed = this.processModuleData(module, moduleData, importsString);
149
- modulesData.push(processed);
150
- }
151
- }
152
- return { scopeDatas, modulesData, importsString, zodInterfacesImports };
153
- }
154
- processScopeData(scope, scopeData, zodInterfacesImports, importsString) {
155
- const shareds = [];
156
- const services = [];
157
- const context = [];
158
- if (scopeData.zod) {
159
- if (scopeData.zod.silgiZodSchema && scopeData.zod.silgiZodSchema?.length > 0) {
160
- scopeData.zod.silgiZodSchema?.forEach((schema) => {
161
- const name = camelCase(`${scope}_${schema.serviceName}silgiZodSchema`);
162
- zodInterfacesImports.push(`import { silgiZodSchema as ${name} } from '${schema.path}'`);
163
- shareds.push({
164
- type: "const",
165
- from: "zod",
166
- scope: "true",
167
- key: schema.serviceName,
168
- value: name
169
- });
170
- });
171
- }
172
- if (scopeData.zod.SilgiZodSchema && scopeData.zod.SilgiZodSchema?.length > 0) {
173
- scopeData.zod.SilgiZodSchema.forEach((schema) => {
174
- const name = pascalCase(`${scope}_${schema.serviceName}SilgiZodSchemaType`);
175
- zodInterfacesImports.push(`import type { SilgiZodSchema as ${name} } from '${schema.path}'`);
176
- shareds.push({
177
- type: "interface",
178
- from: "zod",
179
- key: schema.serviceName,
180
- value: name
181
- });
182
- });
183
- }
184
- }
185
- if (scopeData.service && scopeData.service.silgiService) {
186
- if (scopeData.service.silgiService?.length > 0) {
187
- scopeData.service.silgiService.forEach((schema) => {
188
- const name = camelCase(`${scope}_${schema.serviceName}silgiService`);
189
- importsString.push(`import { silgiService as ${name} } from '${schema.path}'`);
190
- services.push({
191
- type: "const",
192
- from: "service",
193
- key: schema.serviceName,
194
- value: name
195
- });
196
- });
197
- }
198
- if (scopeData.service.SilgiService && scopeData.service.SilgiService.length > 0) {
199
- scopeData.service.SilgiService.forEach((schema) => {
200
- const name = pascalCase(`${scope}_${schema.serviceName}SilgiServiceType`);
201
- importsString.push(`import type { SilgiService as ${name} } from '${schema.path}'`);
202
- services.push({
203
- type: "interface",
204
- from: "service",
205
- key: schema.serviceName,
206
- value: name
207
- });
208
- });
209
- }
210
- }
211
- if (scopeData.context) {
212
- const processedPaths = /* @__PURE__ */ new Set();
213
- if (scopeData.context?.SilgiContext && scopeData.context.SilgiContext.length > 0) {
214
- scopeData.context.SilgiContext.forEach((schema) => {
215
- if (processedPaths.has(schema.path))
216
- return;
217
- processedPaths.add(schema.path);
218
- const pathSegments = schema.path.split("/");
219
- const uniqueIdentifier = pathSegments.slice(-2).filter((segment) => segment !== "index").join("");
220
- const name = pascalCase(`${scope}_${uniqueIdentifier}SilgiContextType`);
221
- importsString.push(`import type { SilgiContext as ${name} } from '${schema.path}'`);
222
- context.push({
223
- type: "interface",
224
- from: "context",
225
- key: scope,
226
- value: name,
227
- path: schema.path
228
- // Store path for debugging
229
- });
230
- });
231
- }
232
- }
233
- if (scopeData.shared) {
234
- if (scopeData.shared.silgiGlobalShared && scopeData.shared.silgiGlobalShared?.length > 0) {
235
- scopeData.shared.silgiGlobalShared.forEach((schema) => {
236
- const name = camelCase(`${scope}_${schema.serviceName}silgiGlobalShared`);
237
- importsString.push(`import { silgiGlobalShared as ${name} } from '${schema.path}'`);
238
- shareds.push({
239
- type: "const",
240
- from: "shared",
241
- key: schema.serviceName,
242
- value: name,
243
- global: schema.global
244
- });
245
- });
246
- }
247
- if (scopeData.shared.SilgiGlobalShared && scopeData.shared.SilgiGlobalShared?.length > 0) {
248
- scopeData.shared.SilgiGlobalShared.forEach((schema) => {
249
- const name = pascalCase(`${scope}_${schema.serviceName}SilgiGlobalSharedType`);
250
- importsString.push(`import type { SilgiGlobalShared as ${name} } from '${schema.path}'`);
251
- shareds.push({
252
- type: "interface",
253
- from: "shared",
254
- key: schema.serviceName,
255
- value: name,
256
- global: schema.global
257
- });
258
- });
259
- }
260
- }
261
- return {
262
- scope,
263
- shareds,
264
- services,
265
- context
266
- };
267
- }
268
- processModuleData(module, moduleData, importsString) {
269
- const methodsConfig = [];
270
- const context = [];
271
- const services = [];
272
- const modules = [];
273
- const moduleConfig = [];
274
- if (moduleData.methodsConfig) {
275
- if (moduleData.methodsConfig.silgiMethodConfig && moduleData.methodsConfig.silgiMethodConfig?.length > 0) {
276
- moduleData.methodsConfig.silgiMethodConfig.forEach((schema) => {
277
- const name = camelCase(`${module}_${schema.serviceName}silgiMethodConfig`);
278
- importsString.push(`import { silgiMethodConfig as ${name} } from '${schema.path}'`);
279
- methodsConfig.push({
280
- type: "const",
281
- from: "methodsConfig",
282
- key: schema.serviceName,
283
- value: name
284
- });
285
- });
286
- }
287
- if (moduleData.methodsConfig.SilgiMethodConfig && moduleData.methodsConfig.SilgiMethodConfig?.length > 0) {
288
- moduleData.methodsConfig.SilgiMethodConfig.forEach((schema) => {
289
- const name = pascalCase(`${module}_${schema.serviceName}SilgiMethodConfigType`);
290
- importsString.push(`import type { SilgiMethodConfig as ${name} } from '${schema.path}'`);
291
- methodsConfig.push({
292
- type: "interface",
293
- from: "methodsConfig",
294
- key: schema.serviceName,
295
- value: name
296
- });
297
- });
298
- }
299
- }
300
- if (moduleData.context) {
301
- const processedPaths = /* @__PURE__ */ new Set();
302
- if (moduleData.context.SilgiContext && moduleData.context.SilgiContext?.length > 0) {
303
- moduleData.context.SilgiContext.forEach(
304
- (schema) => {
305
- if (processedPaths.has(schema.path))
306
- return;
307
- processedPaths.add(schema.path);
308
- const pathSegments = schema.path.split("/");
309
- const uniqueIdentifier = pathSegments.slice(-2).filter((segment) => segment !== "index").join("");
310
- const name = pascalCase(`${module}_${uniqueIdentifier}SilgiContextType`);
311
- importsString.push(`import type { SilgiContext as ${name} } from '${schema.path}'`);
312
- context.push({
313
- type: "interface",
314
- from: "context",
315
- key: module,
316
- value: name
317
- });
318
- }
319
- );
320
- }
321
- }
322
- if (moduleData.service) {
323
- if (moduleData.service.silgiService && moduleData.service.silgiService?.length > 0) {
324
- moduleData.service.silgiService.forEach((schema) => {
325
- if (schema.type === "module") {
326
- const name = camelCase(`${schema.serviceName}silgiModule`);
327
- importsString.push(`import ${name} from '${schema.path}'`);
328
- modules.push({
329
- type: "module",
330
- from: "service",
331
- key: schema.serviceName,
332
- value: name
333
- });
334
- } else {
335
- const name = camelCase(`${module}_${schema.serviceName}silgiService`);
336
- importsString.push(`import { silgiService as ${name} } from '${schema.path}'`);
337
- services.push({
338
- type: "const",
339
- from: "service",
340
- key: schema.serviceName,
341
- value: name
342
- });
343
- }
344
- });
345
- }
346
- if (moduleData.service.SilgiService && moduleData.service.SilgiService?.length > 0) {
347
- moduleData.service.SilgiService.forEach((schema) => {
348
- const name = pascalCase(`${module}_${schema.serviceName}SilgiServiceType`);
349
- importsString.push(`import type { SilgiService as ${name} } from '${schema.path}'`);
350
- services.push({
351
- type: "interface",
352
- from: "service",
353
- key: schema.serviceName,
354
- value: name
355
- });
356
- });
357
- }
358
- }
359
- if (moduleData.moduleConfig) {
360
- if (moduleData.moduleConfig.SilgiModuleConfig && moduleData.moduleConfig.SilgiModuleConfig?.length > 0) {
361
- moduleData.moduleConfig.SilgiModuleConfig.forEach((schema) => {
362
- if (schema.type === "empty") {
363
- moduleConfig.push({
364
- type: "empty",
365
- from: "moduleConfig",
366
- key: schema.serviceName,
367
- value: schema.serviceName
368
- });
369
- } else {
370
- const name = pascalCase(`${module}_${schema.serviceName}SilgiModuleConfigType`);
371
- importsString.push(`import type { SilgiModuleConfig as ${name} } from '${schema.path}'`);
372
- moduleConfig.push({
373
- type: "interface",
374
- from: "moduleConfig",
375
- key: schema.serviceName,
376
- value: name
377
- });
378
- }
379
- });
380
- }
381
- }
382
- return {
383
- module,
384
- methodsConfig,
385
- context,
386
- modules,
387
- moduleConfig
388
- };
389
- }
390
- generateInterfaceContent({ scopeDatas, modulesData, zodInterfacesImports, importsString }) {
391
- return (
392
- /* TS */
393
- `// This file is auto-generated. Do not edit manually.
394
- import { createSilgi } from 'silgi'
395
- import type { OmitSilgiOptions } from 'silgi'
396
- import type { InitSilgi, DefaultContext, DefaultInterface } from 'silgi'
397
-
398
- ${zodInterfacesImports.join("\n")}
399
- ${importsString.join("\n")}
400
-
401
- declare module 'silgi' {
402
- type SharedGlobalMerge = ${scopeDatas.some((scope) => scope.context.length > 0) ? `${scopeDatas.filter((scope) => scope.shareds.length > 0).map((scopeData) => {
403
- return scopeData.shareds.map((shared) => {
404
- if (shared.global) {
405
- return shared.value;
406
- }
407
- }).filter(Boolean).join(" & ");
408
- }).filter(Boolean).join(" & ")}` : ""}
409
-
410
- interface DefaultInterface {
411
- ${scopeDatas.some((scope) => scope.services.length > 0) ? `scopes: {
412
- ${scopeDatas.filter((scope) => scope.services.length > 0).map((scopeData) => {
413
- const services = scopeData.services.map((shared) => {
414
- if (shared.type === "interface") {
415
- return `${shared.key}: ${shared.value}`;
416
- }
417
- }).filter(Boolean).join("\n");
418
- return services ? `${scopeData.scope}: {
419
- ${services}
420
- }` : "";
421
- }).filter(Boolean).join("\n")}
422
- }` : ""}
423
-
424
- ${scopeDatas.some((scope) => scope.shareds.length > 0) ? `shared: {
425
- ${scopeDatas.map((scopeData) => {
426
- const zodShared = scopeData.shareds.filter((shared) => shared.from === "zod").map((shared) => {
427
- if (shared.type === "interface") {
428
- return `${shared.key}: ${shared.value}`;
429
- }
430
- }).filter(Boolean).join("\n");
431
- return `
432
- ${scopeData.scope}: {
433
- ${zodShared ? `zod: {
434
- ${zodShared}
435
- }
436
- }` : ""}`;
437
- }).filter(Boolean).join("\n")}
438
- } & SharedGlobalMerge` : ""}
439
-
440
- ${modulesData.some((module) => module.methodsConfig.length > 0) ? `plugins: {
441
- ${modulesData.map((moduleData) => {
442
- const methodsConfig = moduleData.methodsConfig.map((shared) => {
443
- if (shared.type === "interface") {
444
- return `${shared.value}`;
445
- }
446
- }).filter(Boolean).join("\n");
447
- return methodsConfig ? `${moduleData.module}: ${methodsConfig}` : "";
448
- }).filter(Boolean).join("\n")}
449
- }` : ""}
450
- }
451
-
452
- type ExtendDefaultContext = ${[...scopeDatas, ...modulesData].some((item) => item.context?.length > 0) ? [...scopeDatas, ...modulesData].filter((item) => item.context?.length > 0).map((item) => {
453
- return item.context.map((shared) => {
454
- if (shared.type === "interface") {
455
- return shared.value;
456
- }
457
- }).filter(Boolean).join(" & ");
458
- }).filter(Boolean).reduce((acc, curr) => acc ? `${acc} & ${curr}` : curr, "") : ""}
459
-
460
- interface DefaultContext extends ExtendDefaultContext {}
461
- }
462
-
463
- export const silgiServices = [
464
- ${scopeDatas.flatMap(
465
- (scopeData) => scopeData.services.filter((service) => service.type === "const").map((service) => service.value)
466
- ).filter(Boolean).join(",\n ")}
467
- ]
468
-
469
- export const silgiShared = {
470
- ${scopeDatas.filter((scopeData) => scopeData.shareds.length > 0).map((scopeData) => {
471
- const nonZodShared = scopeData.shareds.filter((shared) => shared.from !== "zod").filter((shared) => shared.type === "const").map((shared) => `...${shared.value}`).filter(Boolean).join(",\n ");
472
- const zodShared = scopeData.shareds.filter((shared) => shared.from === "zod").filter((shared) => shared.type === "const").map((shared) => `${shared.key}: ${shared.value}`).filter(Boolean).join(",\n ");
473
- return `
474
- ${nonZodShared ? `${nonZodShared},` : ""}
475
- ${scopeData.scope}: {
476
- ${zodShared ? `zod: {
477
- ${zodShared}
478
- }` : ""}
479
- }`;
480
- }).join(",\n ")}
481
- }
482
-
483
- let _silgi: InitSilgi<DefaultContext, DefaultInterface>
484
-
485
- interface SilgiCreateOptions {
486
- version: 'v1'
487
- silgi?: Omit<OmitSilgiOptions<DefaultContext, DefaultInterface>, 'services' | 'shared' | 'plugins'>
488
- ${modulesData.flatMap(
489
- (moduleData) => moduleData.moduleConfig.map((module) => {
490
- if (module.key === module.value) {
491
- return `${module.key}: object`;
492
- }
493
- return `${module.key}: ${module.value}`;
494
- })
495
- ).filter(Boolean).join("\n ")}
496
- }
497
-
498
- export function silgi(options: SilgiCreateOptions) {
499
-
500
- if (!_silgi) {
501
- _silgi = createSilgi({
502
- ...options.silgi,
503
- services: silgiServices,
504
- shared: silgiShared,
505
- plugins: [
506
- ${modulesData.flatMap(
507
- (moduleData) => moduleData.modules.filter((module) => module.type === "module").map((module) => {
508
- const plugin = module.value;
509
- return `${plugin}(options.${module.key})`;
510
- })
511
- ).filter(Boolean).join(",\n ")}
512
- ],
513
- })
514
- return _silgi
515
- }
516
- return _silgi
517
- }
518
- `
519
- );
520
- }
521
- async writeOutputFile(content) {
522
- await writeFile(this.outputDir, content, "utf-8");
523
- }
524
- }
525
- async function generateSilgiInterface(storage, outputDir) {
526
- const generator = new TypescriptGenerator(storage, outputDir);
527
- await generator.generate();
528
- }
529
-
530
- function extractNamesFromPath(filePath) {
531
- const parts = dirname(filePath).split("/");
532
- return {
533
- serviceName: parts[parts.length - 1] || "",
534
- scopeName: parts[parts.length - 3] || ""
535
- };
536
- }
537
- function makeRelativePath(from, to) {
538
- const relativePath = relative(dirname(from), to);
539
- return relativePath.startsWith(".") ? relativePath : `./${relativePath}`;
540
- }
541
- function cleanPath(path, removeExtensions = true) {
542
- return removeExtensions ? path.replace(/\.ts$/, "") : path;
543
- }
544
-
545
- class SchemaManager {
546
- constructor(config) {
547
- this.config = config;
548
- this.parser = new SchemaParser();
549
- this.storage = {
550
- schemaObjects: {},
551
- path: "",
552
- files: [],
553
- modules: {}
554
- };
555
- this.clientSchemas ??= {};
556
- this.schemas ??= {};
557
- }
558
- parser;
559
- storage;
560
- schemas;
561
- modulesSchema;
562
- clientSchemas;
563
- async serverScan(filePath, scope) {
564
- try {
565
- const content = await promises.readFile(filePath, "utf-8");
566
- const { exportTS, exportVariables } = this.parser.parseExports(content, filePath);
567
- const { serviceName } = extractNamesFromPath(filePath);
568
- const scopeName = scope.name;
569
- const absoluteFilePath = resolve(this.config.rootDir, filePath);
570
- let relativePath = makeRelativePath(this.config._silgi.outputDirTS, absoluteFilePath);
571
- relativePath = cleanPath(relativePath, this.config.removeExtensions);
572
- this.schemas ??= {};
573
- this.schemas[scopeName] ??= {};
574
- for (const item of exportTS) {
575
- if (item.includes("SilgiContext")) {
576
- this.schemas[scopeName].context ??= {};
577
- this.schemas[scopeName].context.SilgiContext ??= [];
578
- this.schemas[scopeName].context.SilgiContext.push({
579
- type: "interface",
580
- path: relativePath,
581
- serviceName
582
- });
583
- } else if (item.includes("SilgiZodSchema")) {
584
- this.schemas[scopeName].zod ??= {};
585
- this.schemas[scopeName].zod.SilgiZodSchema ??= [];
586
- this.schemas[scopeName].zod.SilgiZodSchema?.push({
587
- type: "interface",
588
- path: relativePath,
589
- serviceName
590
- });
591
- } else if (item.includes("SilgiService")) {
592
- this.schemas[scopeName].service ??= {};
593
- this.schemas[scopeName].service.SilgiService ??= [];
594
- this.schemas[scopeName].service.SilgiService.push({
595
- type: "interface",
596
- path: relativePath,
597
- serviceName
598
- });
599
- } else if (item.includes("SilgiGlobalShared")) {
600
- this.schemas[scopeName].shared ??= {};
601
- this.schemas[scopeName].shared.SilgiGlobalShared ??= [];
602
- this.schemas[scopeName].shared.SilgiGlobalShared.push({
603
- type: "interface",
604
- global: true,
605
- path: relativePath,
606
- serviceName
607
- });
608
- }
609
- }
610
- for (const item of exportVariables) {
611
- if (item.includes("silgiContext")) {
612
- this.schemas[scopeName].context ??= {};
613
- this.schemas[scopeName].context.SilgiContext ??= [];
614
- this.schemas[scopeName].context.SilgiContext.push({
615
- type: "const",
616
- path: relativePath,
617
- serviceName
618
- });
619
- } else if (item.includes("silgiZodSchema")) {
620
- this.schemas[scopeName].zod ??= {};
621
- this.schemas[scopeName].zod.silgiZodSchema ??= [];
622
- this.schemas[scopeName].zod.silgiZodSchema.push({
623
- type: "const",
624
- path: relativePath,
625
- serviceName
626
- });
627
- } else if (item.includes("silgiService")) {
628
- this.schemas[scopeName].service ??= {};
629
- this.schemas[scopeName].service.silgiService ??= [];
630
- this.schemas[scopeName].service.silgiService.push({
631
- type: "const",
632
- path: relativePath,
633
- serviceName
634
- });
635
- } else if (item.includes("silgiGlobalShared")) {
636
- this.schemas[scopeName].shared ??= {};
637
- this.schemas[scopeName].shared.silgiGlobalShared ??= [];
638
- this.schemas[scopeName].shared.silgiGlobalShared.push({
639
- type: "const",
640
- path: relativePath,
641
- serviceName
642
- });
643
- }
644
- }
645
- return Object.keys(this.schemas).length > 0;
646
- } catch (error) {
647
- consola.error(`Error processing file ${filePath}:`, error);
648
- return false;
649
- }
650
- }
651
- async clientScan(filePath, _scope) {
652
- try {
653
- const content = await promises.readFile(filePath, "utf-8");
654
- const { exportVariables } = this.parser.parseExports(content, filePath);
655
- const { serviceName } = extractNamesFromPath(filePath);
656
- const absoluteFilePath = resolve(this.config.rootDir, filePath);
657
- let relativePath = makeRelativePath(this.config._silgi.outputDirClientTS, absoluteFilePath);
658
- relativePath = cleanPath(relativePath, this.config.removeExtensions);
659
- if (!this.clientSchemas[serviceName]) {
660
- this.clientSchemas[serviceName] = {
661
- graphql: {
662
- mutation: [],
663
- query: []
664
- },
665
- zod: []
666
- };
667
- }
668
- for (const item of exportVariables) {
669
- if (typeof item === "string" && item.toLocaleLowerCase().startsWith("zod")) {
670
- this.clientSchemas[serviceName].zod.push({
671
- type: "const",
672
- path: relativePath,
673
- serviceName,
674
- key: item,
675
- newKey: camelCase(item.replace("zod", ""))
676
- });
677
- }
678
- if (typeof item === "string" && item.toLocaleLowerCase().startsWith("mutation")) {
679
- this.clientSchemas[serviceName].graphql.mutation.push({
680
- type: "const",
681
- path: relativePath,
682
- serviceName,
683
- key: item,
684
- newKey: camelCase(item.replace("mutation", ""))
685
- });
686
- }
687
- if (typeof item === "string" && item.toLocaleLowerCase().startsWith("query")) {
688
- this.clientSchemas[serviceName].graphql.query.push({
689
- type: "const",
690
- path: relativePath,
691
- serviceName,
692
- key: item,
693
- newKey: camelCase(item.replace("query", ""))
694
- });
695
- }
696
- }
697
- return true;
698
- } catch (error) {
699
- consola.error(`Error processing file ${filePath}:`, error);
700
- return false;
701
- }
702
- }
703
- async scanDirectory(dir, scope) {
704
- const scan = async (currentDir) => {
705
- const files = await promises.readdir(currentDir);
706
- await Promise.all(files.map(async (file) => {
707
- const filePath = join(currentDir, file);
708
- const stats = await promises.stat(filePath);
709
- if (stats.isDirectory()) {
710
- await scan(filePath);
711
- } else if (file.endsWith(".ts")) {
712
- if (scope.type === "client") {
713
- await this.clientScan(filePath, scope);
714
- } else {
715
- const hasSchemas = await this.serverScan(filePath, scope);
716
- if (hasSchemas) {
717
- this.storage ??= {};
718
- this.storage.files ??= [];
719
- this.storage.schemaObjects = this.schemas;
720
- this.storage.modules = this.modulesSchema;
721
- this.storage.files.push(filePath);
722
- }
723
- }
724
- }
725
- }));
726
- };
727
- await scan(dir);
728
- return this.storage;
729
- }
730
- async scanModules(config) {
731
- const scan = async (currentDir) => {
732
- const files = await promises.readdir(currentDir);
733
- const jiti = createJiti(config.rootDir);
734
- await Promise.all(files.map(async (file) => {
735
- const filePath = join(currentDir, file);
736
- const stats = await promises.stat(filePath);
737
- const absoluteFilePath = resolve(config.rootDir, filePath);
738
- let relativePath = makeRelativePath(config._silgi.outputDirTS, absoluteFilePath);
739
- relativePath = cleanPath(relativePath, config.removeExtensions);
740
- consola.log("\u{1F4C1} Scanning module:", relativePath);
741
- if (stats.isDirectory()) {
742
- await scan(filePath);
743
- } else if (file.endsWith(".ts")) {
744
- try {
745
- const modDefault = await jiti.import(filePath, { default: true });
746
- if (typeof modDefault === "function") {
747
- const result = modDefault();
748
- const name = result.name;
749
- this.modulesSchema ??= {};
750
- this.modulesSchema[name] ??= {};
751
- if (name) {
752
- this.modulesSchema[name].service ??= {};
753
- this.modulesSchema[name].service.silgiService ??= [];
754
- this.modulesSchema[name].service.silgiService.push({
755
- type: "module",
756
- path: relativePath,
757
- serviceName: name
758
- });
759
- if (result.system) {
760
- if (result.system.context) {
761
- this.modulesSchema[name].context ??= {};
762
- this.modulesSchema[name].context.SilgiContext ??= [];
763
- this.modulesSchema[name].context.SilgiContext.push({
764
- type: "interface",
765
- path: relativePath,
766
- serviceName: "empty"
767
- });
768
- }
769
- if (result.system.shared) {
770
- this.modulesSchema[name].shared ??= {};
771
- this.modulesSchema[name].shared.SilgiGlobalShared ??= [];
772
- this.modulesSchema[name].shared.SilgiGlobalShared.push({
773
- type: "interface",
774
- global: true,
775
- path: relativePath,
776
- serviceName: "empty"
777
- });
778
- }
779
- if (result.system.services) {
780
- this.modulesSchema[name].service ??= {};
781
- this.modulesSchema[name].service.SilgiService ??= [];
782
- this.modulesSchema[name].service.SilgiService.push({
783
- type: "interface",
784
- path: relativePath,
785
- serviceName: "empty"
786
- });
787
- }
788
- if (result.system.methodConfig) {
789
- this.modulesSchema[name].methodsConfig ??= {};
790
- this.modulesSchema[name].methodsConfig.SilgiMethodConfig ??= [];
791
- this.modulesSchema[name].methodsConfig.SilgiMethodConfig.push({
792
- type: "interface",
793
- path: relativePath,
794
- serviceName: "empty",
795
- global: true
796
- });
797
- }
798
- if (result.system.moduleConfig) {
799
- this.modulesSchema[name].moduleConfig ??= {};
800
- this.modulesSchema[name].moduleConfig.SilgiModuleConfig ??= [];
801
- this.modulesSchema[name].moduleConfig.SilgiModuleConfig.push({
802
- type: "interface",
803
- path: relativePath,
804
- serviceName: name,
805
- global: true
806
- });
807
- } else {
808
- this.modulesSchema[name].moduleConfig ??= {};
809
- this.modulesSchema[name].moduleConfig.SilgiModuleConfig ??= [];
810
- this.modulesSchema[name].moduleConfig.SilgiModuleConfig.push({
811
- type: "empty",
812
- path: relativePath,
813
- serviceName: name,
814
- global: true
815
- });
816
- }
817
- }
818
- consola.log("\u{1F4C1} Scanning module:", Object.keys(this.modulesSchema).length);
819
- }
820
- }
821
- } catch (error) {
822
- consola.error(`Error processing file ${filePath}:`, error);
823
- }
824
- }
825
- }));
826
- };
827
- if (config.moduleDir) {
828
- for (const module of config.moduleDir) {
829
- const resolvedPath = resolve(config.rootDir, module);
830
- if (module) {
831
- await scan(resolvedPath);
832
- }
833
- }
834
- }
835
- }
836
- async initialize() {
837
- if (this.config.output.server) {
838
- const outputFileTS = resolve(this.config.rootDir, this.config.output.server, "silgi.generated.ts");
839
- this.config._silgi.outputDirTS = outputFileTS;
840
- await promises.mkdir(this.config.output.server, { recursive: true });
841
- }
842
- if (this.config.output.client) {
843
- this.config._silgi.outputDirClientTS = resolve(this.config.rootDir, this.config.output.client, "silgi.generated.ts");
844
- await promises.mkdir(this.config.output.client, { recursive: true });
845
- }
846
- }
847
- async generateOutput() {
848
- if (!this.storage || !this.storage.schemaObjects) {
849
- return;
850
- }
851
- if (this.config.output.server) {
852
- const resolvedPath = resolve(this.config.rootDir, this.config.output.server, "silgi.generated.ts");
853
- await generateSilgiInterface(this.storage, resolvedPath);
854
- }
855
- if (this.storage?.schemaObjects && this.storage.files) {
856
- const schemaCount = Object.keys(this.storage.schemaObjects).length;
857
- consola.log(`Found ${schemaCount} schema objects in ${this.storage.files.length} files`);
858
- }
859
- }
860
- async generateClientOutput() {
861
- if (!this.clientSchemas) {
862
- return;
863
- }
864
- if (this.config.output.client && this.storage.schemaObjects && this.storage.files) {
865
- const resolvedPath = resolve(this.config.rootDir, this.config.output.client, "silgi.generated.ts");
866
- await generateClientGenTS(this.clientSchemas, resolvedPath);
867
- const schemaCount = Object.keys(this.storage.schemaObjects).length;
868
- consola.log(`Found ${schemaCount} schema objects in ${this.storage.files.length} files`);
869
- consola.success(`Generated client schema files in ${resolvedPath}`);
870
- }
871
- }
872
- }
873
- async function generate$1(config) {
874
- const mergeConfig = defu(config, {
875
- removeExtensions: true,
876
- _silgi: {
877
- outputDirTS: "",
878
- outputDirClientTS: ""
879
- }
880
- });
881
- mergeConfig.rootDir = resolve(mergeConfig.rootDir || config.rootDir || ".");
882
- const schemaManager = new SchemaManager(mergeConfig);
883
- try {
884
- await schemaManager.initialize();
885
- await schemaManager.scanModules(mergeConfig);
886
- for (const scope of mergeConfig.scopes) {
887
- const resolvedPath = resolve(mergeConfig.rootDir, scope.path);
888
- consola.log(`\u{1F4C1} Scanning directory: ${resolvedPath}`);
889
- await schemaManager.scanDirectory(resolvedPath, scope);
890
- }
891
- await schemaManager.generateOutput();
892
- await schemaManager.generateClientOutput();
893
- consola.success("Schema generation completed successfully");
894
- try {
895
- const eslint = new ESLint({
896
- fix: true,
897
- cwd: mergeConfig.rootDir,
898
- baseConfig: await antfu({ typescript: true })
899
- });
900
- const results = await eslint.lintFiles([
901
- mergeConfig._silgi.outputDirTS,
902
- mergeConfig._silgi.outputDirClientTS
903
- ]);
904
- await ESLint.outputFixes(results);
905
- const formatter = await eslint.loadFormatter("stylish");
906
- formatter.format(results);
907
- } catch {
908
- }
909
- } catch (error) {
910
- consola.error("Schema generation failed:", error);
911
- process.exit(1);
912
- }
913
- }
914
-
915
- const generate = defineCommand({
916
- meta: {
917
- name: "Silgi Generate",
918
- description: "Generate code",
919
- version: "0.1.0"
920
- },
921
- args: {},
922
- async run() {
923
- const result = await loadConfig({
924
- name: "silgi",
925
- configFile: "silgi.config",
926
- rcFile: ".silgirc"
927
- });
928
- const silgiConfig = result.config;
929
- await generate$1(silgiConfig);
930
- }
931
- });
932
-
933
- export { generate as default };