nitro-graphql 2.0.0-beta.72 → 2.0.0-beta.73
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +1 -1
- package/dist/cli/adapter.d.mts +0 -3
- package/dist/cli/adapter.mjs +6 -29
- package/dist/cli/commands/generate.mjs +2 -2
- package/dist/cli/config.d.mts +4 -5
- package/dist/cli/config.mjs +3 -1
- package/dist/cli/index.d.mts +3 -6
- package/dist/cli/index.mjs +1 -1
- package/dist/cli/server/graphql-handler.mjs +2 -1
- package/dist/cli/server/watcher.mjs +1 -1
- package/dist/core/codegen/client.d.mts +4 -27
- package/dist/core/codegen/client.mjs +26 -445
- package/dist/core/codegen/file-header.d.mts +7 -0
- package/dist/core/codegen/file-header.mjs +12 -0
- package/dist/core/codegen/index.d.mts +7 -5
- package/dist/core/codegen/index.mjs +7 -5
- package/dist/core/codegen/{runtime.d.mts → runtime-generator.d.mts} +1 -1
- package/dist/core/codegen/{runtime.mjs → runtime-generator.mjs} +1 -1
- package/dist/core/codegen/schema-loader.d.mts +2 -7
- package/dist/core/codegen/schema-loader.mjs +65 -70
- package/dist/core/codegen/server-type-helpers.d.mts +14 -0
- package/dist/core/codegen/server-type-helpers.mjs +76 -0
- package/dist/core/codegen/server.d.mts +1 -15
- package/dist/core/codegen/server.mjs +15 -105
- package/dist/core/codegen/subscription-extractor.d.mts +20 -0
- package/dist/core/codegen/subscription-extractor.mjs +30 -0
- package/dist/core/codegen/vue-subscription-builder.d.mts +10 -0
- package/dist/core/codegen/vue-subscription-builder.mjs +351 -0
- package/dist/core/constants.d.mts +5 -53
- package/dist/core/constants.mjs +13 -54
- package/dist/core/create-config.d.mts +31 -0
- package/dist/core/create-config.mjs +42 -0
- package/dist/core/debug/index.d.mts +2 -2
- package/dist/core/debug/index.mjs +2 -2
- package/dist/core/debug/template.d.mts +1 -5
- package/dist/core/debug/template.mjs +1 -1
- package/dist/core/extend/loader.d.mts +0 -1
- package/dist/core/extend/loader.mjs +59 -89
- package/dist/core/index.d.mts +22 -17
- package/dist/core/index.mjs +19 -15
- package/dist/core/manifest.mjs +3 -1
- package/dist/core/pubsub/index.d.mts +2 -109
- package/dist/core/pubsub/index.mjs +1 -145
- package/dist/core/pubsub/memory-pubsub.d.mts +109 -0
- package/dist/core/pubsub/memory-pubsub.mjs +146 -0
- package/dist/core/scanning/ast-scanner.mjs +4 -2
- package/dist/core/scanning/directives.mjs +2 -3
- package/dist/core/scanning/documents.d.mts +4 -3
- package/dist/core/scanning/documents.mjs +1 -1
- package/dist/core/scanning/{common.d.mts → file-scanner.d.mts} +1 -1
- package/dist/core/scanning/{common.mjs → file-scanner.mjs} +2 -10
- package/dist/core/scanning/index.d.mts +3 -3
- package/dist/core/scanning/index.mjs +3 -3
- package/dist/core/scanning/resolvers.mjs +8 -9
- package/dist/core/scanning/schemas.d.mts +1 -5
- package/dist/core/scanning/schemas.mjs +2 -24
- package/dist/core/schema/builder.d.mts +4 -2
- package/dist/core/schema/builder.mjs +4 -2
- package/dist/core/schema/index.d.mts +2 -2
- package/dist/core/schema/index.mjs +2 -2
- package/dist/core/server/apollo.d.mts +20 -0
- package/dist/core/server/apollo.mjs +54 -0
- package/dist/core/server/index.d.mts +4 -2
- package/dist/core/server/index.mjs +3 -2
- package/dist/core/server/types.d.mts +7 -14
- package/dist/core/server/types.mjs +15 -1
- package/dist/core/server/yoga.d.mts +1 -7
- package/dist/core/server/yoga.mjs +4 -13
- package/dist/core/types/adapter.d.mts +4 -39
- package/dist/core/types/codegen.d.mts +22 -45
- package/dist/core/types/config.d.mts +33 -121
- package/dist/core/types/define.d.mts +8 -5
- package/dist/core/types/index.d.mts +5 -4
- package/dist/core/types/scanning.d.mts +4 -1
- package/dist/core/types/standard-schema.d.mts +64 -0
- package/dist/core/utils/directive-parser.d.mts +8 -63
- package/dist/core/utils/directive-parser.mjs +114 -166
- package/dist/core/utils/file-io.d.mts +1 -5
- package/dist/core/utils/file-io.mjs +1 -11
- package/dist/core/utils/index.d.mts +5 -4
- package/dist/core/utils/index.mjs +6 -5
- package/dist/core/utils/logger.d.mts +1 -10
- package/dist/core/utils/logger.mjs +1 -19
- package/dist/core/utils/ofetch-templates.mjs +3 -4
- package/dist/core/utils/runtime.d.mts +1 -30
- package/dist/core/utils/runtime.mjs +2 -44
- package/dist/core/utils/string.d.mts +10 -0
- package/dist/core/utils/string.mjs +12 -0
- package/dist/core/watcher/create-watcher.d.mts +103 -0
- package/dist/core/watcher/create-watcher.mjs +143 -0
- package/dist/core/watcher/index.d.mts +2 -107
- package/dist/core/watcher/index.mjs +1 -139
- package/dist/define.d.mts +4 -2
- package/dist/define.mjs +7 -6
- package/dist/index.d.mts +4 -3
- package/dist/index.mjs +1 -1
- package/dist/nitro/adapter.d.mts +6 -10
- package/dist/nitro/adapter.mjs +12 -42
- package/dist/nitro/codegen/client-types.d.mts +12 -0
- package/dist/nitro/codegen/client-types.mjs +73 -0
- package/dist/nitro/codegen/external-types.d.mts +8 -0
- package/dist/nitro/codegen/external-types.mjs +47 -0
- package/dist/nitro/codegen/index.d.mts +4 -0
- package/dist/nitro/codegen/index.mjs +4 -0
- package/dist/nitro/codegen/server-types.d.mts +12 -0
- package/dist/nitro/codegen/server-types.mjs +81 -0
- package/dist/nitro/defaults.d.mts +28 -0
- package/dist/nitro/defaults.mjs +34 -0
- package/dist/nitro/index.d.mts +11 -3
- package/dist/nitro/index.mjs +1 -1
- package/dist/nitro/paths.d.mts +3 -2
- package/dist/nitro/paths.mjs +13 -9
- package/dist/nitro/rollup.mjs +4 -3
- package/dist/nitro/routes/_ws-handler.d.mts +6 -0
- package/dist/nitro/routes/_ws-handler.mjs +49 -0
- package/dist/nitro/routes/apollo-server-ws.d.mts +1 -1
- package/dist/nitro/routes/apollo-server-ws.mjs +9 -44
- package/dist/nitro/routes/apollo-server.d.mts +1 -1
- package/dist/nitro/routes/apollo-server.mjs +16 -55
- package/dist/nitro/routes/debug.d.mts +1 -1
- package/dist/nitro/routes/debug.mjs +1 -0
- package/dist/nitro/routes/graphql-yoga-ws.d.mts +1 -1
- package/dist/nitro/routes/graphql-yoga-ws.mjs +6 -44
- package/dist/nitro/routes/graphql-yoga.mjs +7 -5
- package/dist/nitro/routes/health.mjs +22 -24
- package/dist/nitro/setup/extend-loader.d.mts +6 -5
- package/dist/nitro/setup/extend-loader.mjs +30 -58
- package/dist/nitro/setup/file-watcher.mjs +6 -4
- package/dist/nitro/setup/logging.d.mts +1 -8
- package/dist/nitro/setup/logging.mjs +7 -22
- package/dist/nitro/setup/rollup-integration.mjs +32 -1
- package/dist/nitro/setup/scanner.d.mts +8 -43
- package/dist/nitro/setup/scanner.mjs +56 -58
- package/dist/nitro/setup/security.d.mts +10 -0
- package/dist/nitro/setup/security.mjs +17 -0
- package/dist/nitro/setup/type-generation.d.mts +13 -0
- package/dist/nitro/setup/type-generation.mjs +16 -0
- package/dist/nitro/setup.d.mts +4 -3
- package/dist/nitro/setup.mjs +87 -74
- package/dist/nitro/state.d.mts +32 -0
- package/dist/nitro/state.mjs +58 -0
- package/dist/nitro/types/augmentation.d.mts +59 -0
- package/dist/nitro/types/augmentation.mjs +1 -0
- package/dist/nitro/types/config.d.mts +327 -0
- package/dist/nitro/types/config.mjs +1 -0
- package/dist/nitro/types/define.d.mts +13 -0
- package/dist/nitro/types/define.mjs +1 -0
- package/dist/nitro/types/index.d.mts +10 -0
- package/dist/nitro/types/index.mjs +1 -0
- package/dist/nitro/virtual/debug-info.d.mts +9 -0
- package/dist/nitro/virtual/debug-info.mjs +35 -0
- package/dist/nitro/virtual/graphql-config.d.mts +9 -0
- package/dist/nitro/virtual/graphql-config.mjs +33 -0
- package/dist/nitro/virtual/index.d.mts +25 -0
- package/dist/nitro/virtual/index.mjs +45 -0
- package/dist/nitro/virtual/module-config.d.mts +9 -0
- package/dist/nitro/virtual/module-config.mjs +10 -0
- package/dist/nitro/virtual/pubsub.d.mts +9 -0
- package/dist/nitro/virtual/pubsub.mjs +17 -0
- package/dist/nitro/virtual/server-directives.d.mts +9 -0
- package/dist/nitro/virtual/server-directives.mjs +12 -0
- package/dist/nitro/virtual/server-resolvers.d.mts +9 -0
- package/dist/nitro/virtual/server-resolvers.mjs +17 -0
- package/dist/nitro/virtual/server-schemas.d.mts +9 -0
- package/dist/nitro/virtual/server-schemas.mjs +31 -0
- package/dist/nitro/virtual/stubs.d.mts +42 -10
- package/dist/nitro/virtual/stubs.mjs +0 -5
- package/dist/nitro/virtual/utils.d.mts +15 -0
- package/dist/nitro/virtual/utils.mjs +26 -0
- package/dist/nitro/virtual/validation-schemas.d.mts +9 -0
- package/dist/nitro/virtual/validation-schemas.mjs +33 -0
- package/native/index.js +52 -52
- package/package.json +15 -15
- package/dist/cli/commands/index.d.mts +0 -5
- package/dist/cli/commands/index.mjs +0 -5
- package/dist/core/codegen/plugin.d.mts +0 -19
- package/dist/core/codegen/plugin.mjs +0 -29
- package/dist/core/config.d.mts +0 -45
- package/dist/core/config.mjs +0 -76
- package/dist/nitro/codegen.d.mts +0 -18
- package/dist/nitro/codegen.mjs +0 -171
- package/dist/nitro/config.d.mts +0 -50
- package/dist/nitro/config.mjs +0 -55
- package/dist/nitro/types.d.mts +0 -549
- package/dist/nitro/virtual/generators.d.mts +0 -38
- package/dist/nitro/virtual/generators.mjs +0 -190
- /package/dist/{nitro/types.mjs → core/types/standard-schema.mjs} +0 -0
|
@@ -7,19 +7,46 @@ import { createHash } from "node:crypto";
|
|
|
7
7
|
import { existsSync, readFileSync, statSync } from "node:fs";
|
|
8
8
|
import { UrlLoader } from "@graphql-tools/url-loader";
|
|
9
9
|
//#region src/core/codegen/schema-loader.ts
|
|
10
|
-
/**
|
|
11
|
-
* Check if a path is a URL
|
|
12
|
-
*/
|
|
13
10
|
function isUrl(path) {
|
|
14
11
|
return path.startsWith("http://") || path.startsWith("https://");
|
|
15
12
|
}
|
|
13
|
+
/** Resolve schema sources and headers from service config */
|
|
14
|
+
function resolveServiceSources(service) {
|
|
15
|
+
const headers = typeof service.headers === "function" ? service.headers() : service.headers || {};
|
|
16
|
+
const schemaSource = service.schema ?? service.endpoint;
|
|
17
|
+
return {
|
|
18
|
+
headers,
|
|
19
|
+
schemas: Array.isArray(schemaSource) ? schemaSource : [schemaSource]
|
|
20
|
+
};
|
|
21
|
+
}
|
|
22
|
+
/** Build loaders array based on schema source types */
|
|
23
|
+
function buildLoaders(schemas) {
|
|
24
|
+
const loaders = [];
|
|
25
|
+
if (schemas.some((s) => !isUrl(s))) loaders.push(new GraphQLFileLoader());
|
|
26
|
+
if (schemas.some(isUrl)) loaders.push(new UrlLoader());
|
|
27
|
+
return loaders;
|
|
28
|
+
}
|
|
29
|
+
/** Load schema with auto-detected loaders and optional headers */
|
|
30
|
+
function loadWithLoaders(schemas, headers = {}) {
|
|
31
|
+
const loaders = buildLoaders(schemas);
|
|
32
|
+
if (loaders.length === 0) throw new Error("No appropriate loaders found for schema sources");
|
|
33
|
+
return loadSchemaSync(schemas, {
|
|
34
|
+
loaders,
|
|
35
|
+
...Object.keys(headers).length > 0 && { headers }
|
|
36
|
+
});
|
|
37
|
+
}
|
|
38
|
+
/** Resolve the cache file path for a service schema */
|
|
39
|
+
function resolveSchemaFilePath(service, buildDir) {
|
|
40
|
+
const defaultPath = resolve(buildDir, "graphql", "schemas", `${service.name}.graphql`);
|
|
41
|
+
return service.downloadPath ? resolve(service.downloadPath) : defaultPath;
|
|
42
|
+
}
|
|
16
43
|
/**
|
|
17
|
-
* Load GraphQL schema synchronously
|
|
44
|
+
* Load GraphQL schema synchronously from pointers
|
|
18
45
|
*/
|
|
19
46
|
function graphQLLoadSchemaSync(schemaPointers, data = {}) {
|
|
20
|
-
const
|
|
47
|
+
const pointers = Array.isArray(schemaPointers) ? schemaPointers : [schemaPointers];
|
|
21
48
|
try {
|
|
22
|
-
return loadSchemaSync(
|
|
49
|
+
return loadSchemaSync([...pointers, "!**/vfs/**"], {
|
|
23
50
|
...data,
|
|
24
51
|
loaders: [
|
|
25
52
|
new GraphQLFileLoader(),
|
|
@@ -28,7 +55,7 @@ function graphQLLoadSchemaSync(schemaPointers, data = {}) {
|
|
|
28
55
|
]
|
|
29
56
|
});
|
|
30
57
|
} catch (e) {
|
|
31
|
-
if (
|
|
58
|
+
if (e.message?.includes("Unable to find any GraphQL type definitions for the following pointers:")) return;
|
|
32
59
|
throw e;
|
|
33
60
|
}
|
|
34
61
|
}
|
|
@@ -37,90 +64,58 @@ function graphQLLoadSchemaSync(schemaPointers, data = {}) {
|
|
|
37
64
|
*/
|
|
38
65
|
async function loadExternalSchema(service, buildDir) {
|
|
39
66
|
try {
|
|
40
|
-
const
|
|
41
|
-
const schemaSource = service.schema ?? service.endpoint;
|
|
42
|
-
const schemas = Array.isArray(schemaSource) ? schemaSource : [schemaSource];
|
|
67
|
+
const { headers, schemas } = resolveServiceSources(service);
|
|
43
68
|
if (service.downloadSchema && buildDir) {
|
|
44
|
-
const
|
|
45
|
-
const schemaFilePath = service.downloadPath ? resolve(service.downloadPath) : defaultPath;
|
|
69
|
+
const schemaFilePath = resolveSchemaFilePath(service, buildDir);
|
|
46
70
|
if (existsSync(schemaFilePath)) try {
|
|
47
71
|
return loadSchemaSync([schemaFilePath], { loaders: [new GraphQLFileLoader()] });
|
|
48
72
|
} catch {}
|
|
49
73
|
}
|
|
50
|
-
|
|
51
|
-
const hasLocalFiles = schemas.some((schema) => !isUrl(schema));
|
|
52
|
-
const loaders = [];
|
|
53
|
-
if (hasLocalFiles) loaders.push(new GraphQLFileLoader());
|
|
54
|
-
if (hasUrls) loaders.push(new UrlLoader());
|
|
55
|
-
if (loaders.length === 0) throw new Error("No appropriate loaders found for schema sources");
|
|
56
|
-
return loadSchemaSync(schemas, {
|
|
57
|
-
loaders,
|
|
58
|
-
...Object.keys(headers).length > 0 && { headers }
|
|
59
|
-
});
|
|
74
|
+
return loadWithLoaders(schemas, headers);
|
|
60
75
|
} catch {
|
|
61
76
|
return;
|
|
62
77
|
}
|
|
63
78
|
}
|
|
64
79
|
/**
|
|
65
80
|
* Download and save schema from external service
|
|
81
|
+
* Supports modes: true/'once' (download if missing), 'always' (check for updates), 'manual' (skip)
|
|
66
82
|
*/
|
|
67
83
|
async function downloadAndSaveSchema(service, buildDir) {
|
|
68
84
|
const downloadMode = service.downloadSchema;
|
|
69
85
|
if (!downloadMode || downloadMode === "manual") return;
|
|
70
|
-
const
|
|
71
|
-
const schemaFilePath = service.downloadPath ? resolve(service.downloadPath) : defaultPath;
|
|
86
|
+
const schemaFilePath = resolveSchemaFilePath(service, buildDir);
|
|
72
87
|
try {
|
|
73
|
-
const
|
|
74
|
-
const schemaSource = service.schema ?? service.endpoint;
|
|
75
|
-
const schemas = Array.isArray(schemaSource) ? schemaSource : [schemaSource];
|
|
76
|
-
const hasUrlSchemas = schemas.some((schema) => isUrl(schema));
|
|
77
|
-
const hasLocalSchemas = schemas.some((schema) => !isUrl(schema));
|
|
78
|
-
let shouldDownload = false;
|
|
88
|
+
const { headers, schemas } = resolveServiceSources(service);
|
|
79
89
|
const fileExists = existsSync(schemaFilePath);
|
|
80
|
-
if (downloadMode === "always")
|
|
81
|
-
shouldDownload = true;
|
|
82
|
-
if (fileExists && hasUrlSchemas) try {
|
|
83
|
-
const remoteSchemaString = printSchemaWithDirectives(loadSchemaSync(schemas.filter(isUrl), {
|
|
84
|
-
loaders: [new UrlLoader()],
|
|
85
|
-
...Object.keys(headers).length > 0 && { headers }
|
|
86
|
-
}));
|
|
87
|
-
const remoteHash = createHash("md5").update(remoteSchemaString).digest("hex");
|
|
88
|
-
const localSchemaString = readFileSync(schemaFilePath, "utf-8");
|
|
89
|
-
if (remoteHash === createHash("md5").update(localSchemaString).digest("hex")) shouldDownload = false;
|
|
90
|
-
} catch {
|
|
91
|
-
shouldDownload = true;
|
|
92
|
-
}
|
|
93
|
-
else if (fileExists && hasLocalSchemas) {
|
|
94
|
-
const localFiles = schemas.filter((schema) => !isUrl(schema));
|
|
95
|
-
let sourceIsNewer = false;
|
|
96
|
-
for (const localFile of localFiles) if (existsSync(localFile)) {
|
|
97
|
-
const sourceStats = statSync(localFile);
|
|
98
|
-
const cachedStats = statSync(schemaFilePath);
|
|
99
|
-
if (sourceStats.mtime > cachedStats.mtime) {
|
|
100
|
-
sourceIsNewer = true;
|
|
101
|
-
break;
|
|
102
|
-
}
|
|
103
|
-
}
|
|
104
|
-
if (!sourceIsNewer) shouldDownload = false;
|
|
105
|
-
}
|
|
106
|
-
} else if (downloadMode === true || downloadMode === "once") shouldDownload = !fileExists;
|
|
107
|
-
if (shouldDownload) {
|
|
108
|
-
let schema;
|
|
109
|
-
if (hasUrlSchemas && hasLocalSchemas) schema = loadSchemaSync(schemas, {
|
|
110
|
-
loaders: [new GraphQLFileLoader(), new UrlLoader()],
|
|
111
|
-
...Object.keys(headers).length > 0 && { headers }
|
|
112
|
-
});
|
|
113
|
-
else if (hasUrlSchemas) schema = loadSchemaSync(schemas, {
|
|
114
|
-
loaders: [new UrlLoader()],
|
|
115
|
-
...Object.keys(headers).length > 0 && { headers }
|
|
116
|
-
});
|
|
117
|
-
else schema = loadSchemaSync(schemas, { loaders: [new GraphQLFileLoader()] });
|
|
118
|
-
writeFileIfChanged(schemaFilePath, printSchemaWithDirectives(schema));
|
|
119
|
-
}
|
|
90
|
+
if (downloadMode === "always" ? !fileExists || needsUpdate(schemas, headers, schemaFilePath) : !fileExists) writeFileIfChanged(schemaFilePath, printSchemaWithDirectives(loadWithLoaders(schemas, headers)));
|
|
120
91
|
return schemaFilePath;
|
|
121
92
|
} catch {
|
|
122
93
|
return;
|
|
123
94
|
}
|
|
124
95
|
}
|
|
96
|
+
/**
|
|
97
|
+
* Check if a cached schema needs to be updated
|
|
98
|
+
* For URL sources: compare MD5 hashes. For local files: compare mtime.
|
|
99
|
+
*/
|
|
100
|
+
function needsUpdate(schemas, headers, cachedPath) {
|
|
101
|
+
const hasUrls = schemas.some(isUrl);
|
|
102
|
+
const hasLocal = schemas.some((s) => !isUrl(s));
|
|
103
|
+
if (hasUrls) try {
|
|
104
|
+
const remoteSchema = loadSchemaSync(schemas.filter(isUrl), {
|
|
105
|
+
loaders: [new UrlLoader()],
|
|
106
|
+
...Object.keys(headers).length > 0 && { headers }
|
|
107
|
+
});
|
|
108
|
+
return createHash("md5").update(printSchemaWithDirectives(remoteSchema)).digest("hex") !== createHash("md5").update(readFileSync(cachedPath, "utf-8")).digest("hex");
|
|
109
|
+
} catch {
|
|
110
|
+
return true;
|
|
111
|
+
}
|
|
112
|
+
if (hasLocal) {
|
|
113
|
+
const cachedStats = statSync(cachedPath);
|
|
114
|
+
return schemas.filter((s) => !isUrl(s)).some((localFile) => {
|
|
115
|
+
return existsSync(localFile) && statSync(localFile).mtime > cachedStats.mtime;
|
|
116
|
+
});
|
|
117
|
+
}
|
|
118
|
+
return true;
|
|
119
|
+
}
|
|
125
120
|
//#endregion
|
|
126
121
|
export { downloadAndSaveSchema, graphQLLoadSchemaSync, loadExternalSchema };
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
//#region src/core/codegen/server-type-helpers.d.ts
|
|
2
|
+
/**
|
|
3
|
+
* Server type helpers prepended to generated resolver types
|
|
4
|
+
*
|
|
5
|
+
* These TypeScript types power the ResolverReturnType<T> mapped type
|
|
6
|
+
* that integrates Standard Schema (Zod, Valibot, etc.) validation
|
|
7
|
+
* output types into resolvers.
|
|
8
|
+
*/
|
|
9
|
+
/**
|
|
10
|
+
* Generate the imports + type helpers prepended to server type output
|
|
11
|
+
*/
|
|
12
|
+
declare function generateServerPrepend(framework: string): string;
|
|
13
|
+
//#endregion
|
|
14
|
+
export { generateServerPrepend };
|
|
@@ -0,0 +1,76 @@
|
|
|
1
|
+
//#region src/core/codegen/server-type-helpers.ts
|
|
2
|
+
/**
|
|
3
|
+
* Server type helpers prepended to generated resolver types
|
|
4
|
+
*
|
|
5
|
+
* These TypeScript types power the ResolverReturnType<T> mapped type
|
|
6
|
+
* that integrates Standard Schema (Zod, Valibot, etc.) validation
|
|
7
|
+
* output types into resolvers.
|
|
8
|
+
*/
|
|
9
|
+
/**
|
|
10
|
+
* Generate the imports + type helpers prepended to server type output
|
|
11
|
+
*/
|
|
12
|
+
function generateServerPrepend(framework) {
|
|
13
|
+
return `import schemas from '#nitro-graphql/validation-schemas'
|
|
14
|
+
import type { StandardSchemaV1 } from 'nitro-graphql/types'
|
|
15
|
+
|
|
16
|
+
export interface NPMConfig {
|
|
17
|
+
framework: '${framework || "graphql-yoga"}';
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
export type SchemaType = Partial<Record<Partial<keyof ResolversTypes>, StandardSchemaV1>>
|
|
21
|
+
|
|
22
|
+
// Resolve schema keys safely — returns never for empty schema objects
|
|
23
|
+
type SafeSchemaKeys<T> = T extends Record<PropertyKey, never>
|
|
24
|
+
? never
|
|
25
|
+
: keyof T extends string | number | symbol
|
|
26
|
+
? keyof T extends never
|
|
27
|
+
? never
|
|
28
|
+
: keyof T
|
|
29
|
+
: never;
|
|
30
|
+
|
|
31
|
+
type SchemaKeys = SafeSchemaKeys<typeof schemas>;
|
|
32
|
+
|
|
33
|
+
type InferInput<T> = T extends StandardSchemaV1 ? StandardSchemaV1.InferInput<T> : unknown;
|
|
34
|
+
type InferOutput<T> = T extends StandardSchemaV1 ? StandardSchemaV1.InferOutput<T> : unknown;
|
|
35
|
+
|
|
36
|
+
type InferInputFromSchema<T extends SchemaKeys> = InferInput<(typeof schemas)[T]>;
|
|
37
|
+
type InferOutputFromSchema<T extends SchemaKeys> = InferOutput<(typeof schemas)[T]>;
|
|
38
|
+
|
|
39
|
+
type Primitive =
|
|
40
|
+
| null
|
|
41
|
+
| undefined
|
|
42
|
+
| string
|
|
43
|
+
| number
|
|
44
|
+
| boolean
|
|
45
|
+
| symbol
|
|
46
|
+
| bigint;
|
|
47
|
+
|
|
48
|
+
type BuiltIns = Primitive | void | Date | RegExp;
|
|
49
|
+
|
|
50
|
+
/**
|
|
51
|
+
* Maps resolver return types through Standard Schema validation.
|
|
52
|
+
* When a type's __typename matches a schema key, its output type
|
|
53
|
+
* is inferred from the schema's validation output instead.
|
|
54
|
+
*/
|
|
55
|
+
type ResolverReturnType<T> = T extends BuiltIns
|
|
56
|
+
? T
|
|
57
|
+
: T extends (...args: any[]) => unknown
|
|
58
|
+
? T | undefined
|
|
59
|
+
: T extends object
|
|
60
|
+
? T extends Array<infer ItemType>
|
|
61
|
+
? ItemType[] extends T
|
|
62
|
+
? Array<ResolverReturnType<ItemType>>
|
|
63
|
+
: ResolverReturnTypeObject<T>
|
|
64
|
+
: ResolverReturnTypeObject<T>
|
|
65
|
+
: unknown;
|
|
66
|
+
|
|
67
|
+
type ResolverReturnTypeObject<T extends object> =
|
|
68
|
+
T extends { __typename?: infer TTypename }
|
|
69
|
+
? TTypename extends SchemaKeys
|
|
70
|
+
? InferOutputFromSchema<TTypename>
|
|
71
|
+
: { [K in keyof T]: ResolverReturnType<T[K]> }
|
|
72
|
+
: { [K in keyof T]: ResolverReturnType<T[K]> };
|
|
73
|
+
`;
|
|
74
|
+
}
|
|
75
|
+
//#endregion
|
|
76
|
+
export { generateServerPrepend };
|
|
@@ -1,5 +1,4 @@
|
|
|
1
1
|
import { ServerCodegenConfig, ServerCodegenInput, ServerCodegenResult } from "../types/codegen.mjs";
|
|
2
|
-
import { GraphQLSchema } from "graphql";
|
|
3
2
|
|
|
4
3
|
//#region src/core/codegen/server.d.ts
|
|
5
4
|
/**
|
|
@@ -8,20 +7,7 @@ import { GraphQLSchema } from "graphql";
|
|
|
8
7
|
declare const DEFAULT_SERVER_CODEGEN_CONFIG: ServerCodegenConfig;
|
|
9
8
|
/**
|
|
10
9
|
* Generate server-side GraphQL types
|
|
11
|
-
* Pure function that generates TypeScript types from a GraphQL schema
|
|
12
10
|
*/
|
|
13
11
|
declare function generateServerTypesCore(input: ServerCodegenInput): Promise<ServerCodegenResult>;
|
|
14
|
-
/**
|
|
15
|
-
* Generate types from schema (simplified version for direct use)
|
|
16
|
-
* @deprecated Use generateServerTypesCore instead
|
|
17
|
-
*/
|
|
18
|
-
declare function generateTypes(framework: string, schema: GraphQLSchema, config?: {
|
|
19
|
-
codegen?: {
|
|
20
|
-
server?: ServerCodegenConfig;
|
|
21
|
-
};
|
|
22
|
-
federation?: {
|
|
23
|
-
enabled?: boolean;
|
|
24
|
-
};
|
|
25
|
-
}, outputPath?: string): Promise<string>;
|
|
26
12
|
//#endregion
|
|
27
|
-
export { DEFAULT_SERVER_CODEGEN_CONFIG, generateServerTypesCore
|
|
13
|
+
export { DEFAULT_SERVER_CODEGEN_CONFIG, generateServerTypesCore };
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { DEFAULT_GRAPHQL_SCALARS } from "../constants.mjs";
|
|
2
|
-
import {
|
|
2
|
+
import { GENERATED_FILE_HEADER } from "./file-header.mjs";
|
|
3
|
+
import { generateServerPrepend } from "./server-type-helpers.mjs";
|
|
3
4
|
import { defu as defu$1 } from "defu";
|
|
4
5
|
import { codegen } from "@graphql-codegen/core";
|
|
5
6
|
import * as typescriptPlugin from "@graphql-codegen/typescript";
|
|
@@ -22,7 +23,6 @@ const DEFAULT_SERVER_CODEGEN_CONFIG = {
|
|
|
22
23
|
};
|
|
23
24
|
/**
|
|
24
25
|
* Generate server-side GraphQL types
|
|
25
|
-
* Pure function that generates TypeScript types from a GraphQL schema
|
|
26
26
|
*/
|
|
27
27
|
async function generateServerTypesCore(input) {
|
|
28
28
|
const { framework, schema, schemaString: inputSchemaString, config = {}, federationEnabled = false, outputPath } = input;
|
|
@@ -32,111 +32,21 @@ async function generateServerTypesCore(input) {
|
|
|
32
32
|
}, config);
|
|
33
33
|
const schemaString = inputSchemaString || (schema ? printSchemaWithDirectives(schema) : null);
|
|
34
34
|
if (!schemaString) throw new Error("[generateServerTypesCore] No schema or schemaString provided");
|
|
35
|
+
const generated = await codegen({
|
|
36
|
+
filename: outputPath || "types.generated.ts",
|
|
37
|
+
schema: parse(schemaString),
|
|
38
|
+
documents: [],
|
|
39
|
+
config: mergedConfig,
|
|
40
|
+
plugins: [{ typescript: {} }, { typescriptResolvers: {} }],
|
|
41
|
+
pluginMap: {
|
|
42
|
+
typescript: typescriptPlugin,
|
|
43
|
+
typescriptResolvers: typescriptResolversPlugin
|
|
44
|
+
}
|
|
45
|
+
});
|
|
35
46
|
return {
|
|
36
|
-
types:
|
|
37
|
-
filename: outputPath || "types.generated.ts",
|
|
38
|
-
schema: parse(schemaString),
|
|
39
|
-
documents: [],
|
|
40
|
-
config: mergedConfig,
|
|
41
|
-
plugins: [
|
|
42
|
-
{ imports: {} },
|
|
43
|
-
{ pluginContent: {} },
|
|
44
|
-
{ typescript: {} },
|
|
45
|
-
{ typescriptResolvers: {} }
|
|
46
|
-
],
|
|
47
|
-
pluginMap: {
|
|
48
|
-
pluginContent: { plugin: pluginContent },
|
|
49
|
-
imports: { plugin: () => {
|
|
50
|
-
return {
|
|
51
|
-
prepend: [
|
|
52
|
-
`import schemas from '#nitro-graphql/validation-schemas'`,
|
|
53
|
-
`import type { StandardSchemaV1 } from 'nitro-graphql/types'`,
|
|
54
|
-
generateServerTypeHelpers(framework),
|
|
55
|
-
""
|
|
56
|
-
],
|
|
57
|
-
content: ""
|
|
58
|
-
};
|
|
59
|
-
} },
|
|
60
|
-
typescript: typescriptPlugin,
|
|
61
|
-
typescriptResolvers: typescriptResolversPlugin
|
|
62
|
-
}
|
|
63
|
-
}),
|
|
47
|
+
types: GENERATED_FILE_HEADER + generateServerPrepend(framework) + generated,
|
|
64
48
|
schemaString
|
|
65
49
|
};
|
|
66
50
|
}
|
|
67
|
-
/**
|
|
68
|
-
* Generate server type helper code
|
|
69
|
-
*/
|
|
70
|
-
function generateServerTypeHelpers(framework) {
|
|
71
|
-
return `
|
|
72
|
-
export interface NPMConfig {
|
|
73
|
-
framework: '${framework || "graphql-yoga"}';
|
|
74
|
-
}
|
|
75
|
-
|
|
76
|
-
export type SchemaType = Partial<Record<Partial<keyof ResolversTypes>, StandardSchemaV1>>
|
|
77
|
-
|
|
78
|
-
// Check if schemas is empty object, return never if so
|
|
79
|
-
type SafeSchemaKeys<T> = T extends Record<PropertyKey, never>
|
|
80
|
-
? never
|
|
81
|
-
: keyof T extends string | number | symbol
|
|
82
|
-
? keyof T extends never
|
|
83
|
-
? never
|
|
84
|
-
: keyof T
|
|
85
|
-
: never;
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
type SchemaKeys = SafeSchemaKeys<typeof schemas>;
|
|
89
|
-
|
|
90
|
-
type InferInput<T> = T extends StandardSchemaV1 ? StandardSchemaV1.InferInput<T> : unknown;
|
|
91
|
-
type InferOutput<T> = T extends StandardSchemaV1 ? StandardSchemaV1.InferOutput<T> : unknown;
|
|
92
|
-
|
|
93
|
-
type InferInputFromSchema<T extends SchemaKeys> = InferInput<(typeof schemas)[T]>;
|
|
94
|
-
type InferOutputFromSchema<T extends SchemaKeys> = InferOutput<(typeof schemas)[T]>;
|
|
95
|
-
|
|
96
|
-
type Primitive =
|
|
97
|
-
| null
|
|
98
|
-
| undefined
|
|
99
|
-
| string
|
|
100
|
-
| number
|
|
101
|
-
| boolean
|
|
102
|
-
| symbol
|
|
103
|
-
| bigint;
|
|
104
|
-
|
|
105
|
-
type BuiltIns = Primitive | void | Date | RegExp;
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
type ResolverReturnType<T> = T extends BuiltIns
|
|
109
|
-
? T
|
|
110
|
-
: T extends (...args: any[]) => unknown
|
|
111
|
-
? T | undefined
|
|
112
|
-
: T extends object
|
|
113
|
-
? T extends Array<infer ItemType> // Test for arrays/tuples, per https://github.com/microsoft/TypeScript/issues/35156
|
|
114
|
-
? ItemType[] extends T // Test for arrays (non-tuples) specifically
|
|
115
|
-
? Array<ResolverReturnType<ItemType>>
|
|
116
|
-
: ResolverReturnTypeObject<T> // Tuples behave properly
|
|
117
|
-
: ResolverReturnTypeObject<T>
|
|
118
|
-
: unknown;
|
|
119
|
-
|
|
120
|
-
type ResolverReturnTypeObject<T extends object> =
|
|
121
|
-
T extends { __typename?: infer TTypename }
|
|
122
|
-
? TTypename extends SchemaKeys
|
|
123
|
-
? InferOutputFromSchema<TTypename>
|
|
124
|
-
: { [K in keyof T]: ResolverReturnType<T[K]> }
|
|
125
|
-
: { [K in keyof T]: ResolverReturnType<T[K]> };
|
|
126
|
-
`;
|
|
127
|
-
}
|
|
128
|
-
/**
|
|
129
|
-
* Generate types from schema (simplified version for direct use)
|
|
130
|
-
* @deprecated Use generateServerTypesCore instead
|
|
131
|
-
*/
|
|
132
|
-
async function generateTypes(framework, schema, config = {}, outputPath) {
|
|
133
|
-
return (await generateServerTypesCore({
|
|
134
|
-
framework,
|
|
135
|
-
schema,
|
|
136
|
-
config: config.codegen?.server,
|
|
137
|
-
federationEnabled: config.federation?.enabled,
|
|
138
|
-
outputPath
|
|
139
|
-
})).types;
|
|
140
|
-
}
|
|
141
51
|
//#endregion
|
|
142
|
-
export { DEFAULT_SERVER_CODEGEN_CONFIG, generateServerTypesCore
|
|
52
|
+
export { DEFAULT_SERVER_CODEGEN_CONFIG, generateServerTypesCore };
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
import { Source } from "@graphql-tools/utils";
|
|
2
|
+
|
|
3
|
+
//#region src/core/codegen/subscription-extractor.d.ts
|
|
4
|
+
/**
|
|
5
|
+
* Subscription info extracted from GraphQL documents
|
|
6
|
+
*/
|
|
7
|
+
interface SubscriptionInfo {
|
|
8
|
+
/** Original operation name from GraphQL document (used for method names) */
|
|
9
|
+
name: string;
|
|
10
|
+
/** PascalCase version for type references (matches GraphQL codegen output) */
|
|
11
|
+
typeName: string;
|
|
12
|
+
fieldName: string;
|
|
13
|
+
hasVariables: boolean;
|
|
14
|
+
}
|
|
15
|
+
/**
|
|
16
|
+
* Extract subscription operations from GraphQL documents
|
|
17
|
+
*/
|
|
18
|
+
declare function extractSubscriptions(docs: Source[]): SubscriptionInfo[];
|
|
19
|
+
//#endregion
|
|
20
|
+
export { SubscriptionInfo, extractSubscriptions };
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
import { capitalize } from "../utils/string.mjs";
|
|
2
|
+
import { Kind } from "graphql";
|
|
3
|
+
//#region src/core/codegen/subscription-extractor.ts
|
|
4
|
+
/**
|
|
5
|
+
* Extract subscription operations from GraphQL documents
|
|
6
|
+
*/
|
|
7
|
+
function extractSubscriptions(docs) {
|
|
8
|
+
const subscriptions = [];
|
|
9
|
+
for (const doc of docs) {
|
|
10
|
+
if (!doc.document) continue;
|
|
11
|
+
for (const def of doc.document.definitions) if (def.kind === Kind.OPERATION_DEFINITION && def.operation === "subscription") {
|
|
12
|
+
const operationDef = def;
|
|
13
|
+
const name = operationDef.name?.value;
|
|
14
|
+
if (!name) continue;
|
|
15
|
+
const firstSelection = operationDef.selectionSet.selections[0];
|
|
16
|
+
if (firstSelection.kind !== Kind.FIELD) continue;
|
|
17
|
+
const fieldName = firstSelection.name.value;
|
|
18
|
+
const hasVariables = (operationDef.variableDefinitions?.length || 0) > 0;
|
|
19
|
+
subscriptions.push({
|
|
20
|
+
name,
|
|
21
|
+
typeName: capitalize(name),
|
|
22
|
+
fieldName,
|
|
23
|
+
hasVariables
|
|
24
|
+
});
|
|
25
|
+
}
|
|
26
|
+
}
|
|
27
|
+
return subscriptions;
|
|
28
|
+
}
|
|
29
|
+
//#endregion
|
|
30
|
+
export { extractSubscriptions };
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import { Source } from "@graphql-tools/utils";
|
|
2
|
+
|
|
3
|
+
//#region src/core/codegen/vue-subscription-builder.d.ts
|
|
4
|
+
/**
|
|
5
|
+
* Generate subscription builder code (Drizzle-style API) + Vue Composables
|
|
6
|
+
* Returns empty string if subscriptions are not enabled or no subscription operations found
|
|
7
|
+
*/
|
|
8
|
+
declare function generateSubscriptionBuilder(docs: Source[], subscriptionsEnabled: boolean): string;
|
|
9
|
+
//#endregion
|
|
10
|
+
export { generateSubscriptionBuilder };
|