@gqlkit-ts/cli 0.1.0 → 0.3.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/auto-type-generator/auto-type-generator.d.ts +26 -4
- package/dist/auto-type-generator/auto-type-generator.d.ts.map +1 -1
- package/dist/auto-type-generator/auto-type-generator.js +846 -152
- package/dist/auto-type-generator/auto-type-generator.js.map +1 -1
- package/dist/auto-type-generator/index.d.ts +9 -2
- package/dist/auto-type-generator/index.d.ts.map +1 -1
- package/dist/auto-type-generator/index.js +3 -0
- package/dist/auto-type-generator/index.js.map +1 -1
- package/dist/auto-type-generator/inline-enum-collector.d.ts +39 -0
- package/dist/auto-type-generator/inline-enum-collector.d.ts.map +1 -0
- package/dist/auto-type-generator/inline-enum-collector.js +193 -0
- package/dist/auto-type-generator/inline-enum-collector.js.map +1 -0
- package/dist/auto-type-generator/inline-object-traverser.d.ts +20 -0
- package/dist/auto-type-generator/inline-object-traverser.d.ts.map +1 -0
- package/dist/auto-type-generator/inline-object-traverser.js +22 -0
- package/dist/auto-type-generator/inline-object-traverser.js.map +1 -0
- package/dist/auto-type-generator/inline-union-collector.d.ts +29 -0
- package/dist/auto-type-generator/inline-union-collector.d.ts.map +1 -0
- package/dist/auto-type-generator/inline-union-collector.js +216 -0
- package/dist/auto-type-generator/inline-union-collector.js.map +1 -0
- package/dist/auto-type-generator/inline-union-types.d.ts +29 -0
- package/dist/auto-type-generator/inline-union-types.d.ts.map +1 -0
- package/dist/auto-type-generator/inline-union-types.js +2 -0
- package/dist/auto-type-generator/inline-union-types.js.map +1 -0
- package/dist/auto-type-generator/inline-union-validator.d.ts +76 -0
- package/dist/auto-type-generator/inline-union-validator.d.ts.map +1 -0
- package/dist/auto-type-generator/inline-union-validator.js +329 -0
- package/dist/auto-type-generator/inline-union-validator.js.map +1 -0
- package/dist/auto-type-generator/naming-convention.d.ts +22 -1
- package/dist/auto-type-generator/naming-convention.d.ts.map +1 -1
- package/dist/auto-type-generator/naming-convention.js +24 -0
- package/dist/auto-type-generator/naming-convention.js.map +1 -1
- package/dist/auto-type-generator/resolve-type-generator.d.ts +20 -0
- package/dist/auto-type-generator/resolve-type-generator.d.ts.map +1 -0
- package/dist/auto-type-generator/resolve-type-generator.js +2 -0
- package/dist/auto-type-generator/resolve-type-generator.js.map +1 -0
- package/dist/auto-type-generator/resolver-field-iterator.d.ts +13 -0
- package/dist/auto-type-generator/resolver-field-iterator.d.ts.map +1 -0
- package/dist/auto-type-generator/resolver-field-iterator.js +22 -0
- package/dist/auto-type-generator/resolver-field-iterator.js.map +1 -0
- package/dist/auto-type-generator/typename-extractor.d.ts +26 -0
- package/dist/auto-type-generator/typename-extractor.d.ts.map +1 -0
- package/dist/auto-type-generator/typename-extractor.js +142 -0
- package/dist/auto-type-generator/typename-extractor.js.map +1 -0
- package/dist/auto-type-generator/typename-resolve-type-generator.d.ts +35 -0
- package/dist/auto-type-generator/typename-resolve-type-generator.d.ts.map +1 -0
- package/dist/auto-type-generator/typename-resolve-type-generator.js +177 -0
- package/dist/auto-type-generator/typename-resolve-type-generator.js.map +1 -0
- package/dist/auto-type-generator/typename-types.d.ts +43 -0
- package/dist/auto-type-generator/typename-types.d.ts.map +1 -0
- package/dist/auto-type-generator/typename-types.js +37 -0
- package/dist/auto-type-generator/typename-types.js.map +1 -0
- package/dist/auto-type-generator/typename-validator.d.ts +37 -0
- package/dist/auto-type-generator/typename-validator.d.ts.map +1 -0
- package/dist/auto-type-generator/typename-validator.js +206 -0
- package/dist/auto-type-generator/typename-validator.js.map +1 -0
- package/dist/cli.js +2 -0
- package/dist/cli.js.map +1 -1
- package/dist/commands/docs.d.ts +51 -0
- package/dist/commands/docs.d.ts.map +1 -0
- package/dist/commands/docs.js +154 -0
- package/dist/commands/docs.js.map +1 -0
- package/dist/gen-orchestrator/orchestrator.d.ts.map +1 -1
- package/dist/gen-orchestrator/orchestrator.js +119 -14
- package/dist/gen-orchestrator/orchestrator.js.map +1 -1
- package/dist/resolver-extractor/extract-resolvers.d.ts +28 -1
- package/dist/resolver-extractor/extract-resolvers.d.ts.map +1 -1
- package/dist/resolver-extractor/extractor/define-api-extractor.d.ts +16 -1
- package/dist/resolver-extractor/extractor/define-api-extractor.d.ts.map +1 -1
- package/dist/resolver-extractor/extractor/define-api-extractor.js +86 -309
- package/dist/resolver-extractor/extractor/define-api-extractor.js.map +1 -1
- package/dist/resolver-extractor/index.d.ts +0 -1
- package/dist/resolver-extractor/index.d.ts.map +1 -1
- package/dist/resolver-extractor/validator/abstract-resolver-validator.d.ts +1 -0
- package/dist/resolver-extractor/validator/abstract-resolver-validator.d.ts.map +1 -1
- package/dist/resolver-extractor/validator/abstract-resolver-validator.js +9 -5
- package/dist/resolver-extractor/validator/abstract-resolver-validator.js.map +1 -1
- package/dist/schema-generator/emitter/code-emitter.d.ts +10 -2
- package/dist/schema-generator/emitter/code-emitter.d.ts.map +1 -1
- package/dist/schema-generator/emitter/code-emitter.js +39 -4
- package/dist/schema-generator/emitter/code-emitter.js.map +1 -1
- package/dist/schema-generator/generate-schema.d.ts +1 -0
- package/dist/schema-generator/generate-schema.d.ts.map +1 -1
- package/dist/schema-generator/generate-schema.js +90 -4
- package/dist/schema-generator/generate-schema.js.map +1 -1
- package/dist/schema-generator/integrator/result-integrator.d.ts +34 -2
- package/dist/schema-generator/integrator/result-integrator.d.ts.map +1 -1
- package/dist/schema-generator/integrator/result-integrator.js +96 -1
- package/dist/schema-generator/integrator/result-integrator.js.map +1 -1
- package/dist/schema-generator/resolver-collector/resolver-collector.d.ts +2 -0
- package/dist/schema-generator/resolver-collector/resolver-collector.d.ts.map +1 -1
- package/dist/schema-generator/resolver-collector/resolver-collector.js +22 -0
- package/dist/schema-generator/resolver-collector/resolver-collector.js.map +1 -1
- package/dist/shared/constants.d.ts +0 -16
- package/dist/shared/constants.d.ts.map +1 -1
- package/dist/shared/constants.js +0 -19
- package/dist/shared/constants.js.map +1 -1
- package/dist/shared/directive-detector.d.ts.map +1 -1
- package/dist/shared/directive-detector.js +8 -15
- package/dist/shared/directive-detector.js.map +1 -1
- package/dist/shared/enum-prefix-detector.d.ts +63 -0
- package/dist/shared/enum-prefix-detector.d.ts.map +1 -0
- package/dist/shared/enum-prefix-detector.js +80 -0
- package/dist/shared/enum-prefix-detector.js.map +1 -0
- package/dist/shared/file-scanner.d.ts.map +1 -1
- package/dist/shared/file-scanner.js +5 -3
- package/dist/shared/file-scanner.js.map +1 -1
- package/dist/shared/ignore-fields-detector.d.ts +26 -0
- package/dist/shared/ignore-fields-detector.d.ts.map +1 -0
- package/dist/shared/ignore-fields-detector.js +83 -0
- package/dist/shared/ignore-fields-detector.js.map +1 -0
- package/dist/shared/ignore-fields-validator.d.ts +29 -0
- package/dist/shared/ignore-fields-validator.d.ts.map +1 -0
- package/dist/shared/ignore-fields-validator.js +43 -0
- package/dist/shared/ignore-fields-validator.js.map +1 -0
- package/dist/shared/index.d.ts +3 -1
- package/dist/shared/index.d.ts.map +1 -1
- package/dist/shared/index.js +1 -3
- package/dist/shared/index.js.map +1 -1
- package/dist/shared/interface-detector.d.ts +3 -2
- package/dist/shared/interface-detector.d.ts.map +1 -1
- package/dist/shared/interface-detector.js +54 -11
- package/dist/shared/interface-detector.js.map +1 -1
- package/dist/shared/path-utils.d.ts +2 -0
- package/dist/shared/path-utils.d.ts.map +1 -0
- package/dist/shared/path-utils.js +4 -0
- package/dist/shared/path-utils.js.map +1 -0
- package/dist/shared/source-location.d.ts +5 -0
- package/dist/shared/source-location.d.ts.map +1 -1
- package/dist/shared/source-location.js +7 -0
- package/dist/shared/source-location.js.map +1 -1
- package/dist/shared/type-converter.d.ts.map +1 -1
- package/dist/shared/type-converter.js +11 -0
- package/dist/shared/type-converter.js.map +1 -1
- package/dist/shared/typescript-utils.d.ts +34 -7
- package/dist/shared/typescript-utils.d.ts.map +1 -1
- package/dist/shared/typescript-utils.js +72 -24
- package/dist/shared/typescript-utils.js.map +1 -1
- package/dist/type-extractor/collector/scalar-collector.d.ts.map +1 -1
- package/dist/type-extractor/collector/scalar-collector.js +4 -14
- package/dist/type-extractor/collector/scalar-collector.js.map +1 -1
- package/dist/type-extractor/converter/graphql-converter.d.ts.map +1 -1
- package/dist/type-extractor/converter/graphql-converter.js +57 -4
- package/dist/type-extractor/converter/graphql-converter.js.map +1 -1
- package/dist/type-extractor/extractor/field-type-resolver.d.ts +28 -0
- package/dist/type-extractor/extractor/field-type-resolver.d.ts.map +1 -0
- package/dist/type-extractor/extractor/field-type-resolver.js +433 -0
- package/dist/type-extractor/extractor/field-type-resolver.js.map +1 -0
- package/dist/type-extractor/extractor/type-extractor.d.ts +12 -3
- package/dist/type-extractor/extractor/type-extractor.d.ts.map +1 -1
- package/dist/type-extractor/extractor/type-extractor.js +260 -229
- package/dist/type-extractor/extractor/type-extractor.js.map +1 -1
- package/dist/type-extractor/extractor/type-name-collector.d.ts +24 -0
- package/dist/type-extractor/extractor/type-name-collector.d.ts.map +1 -0
- package/dist/type-extractor/extractor/type-name-collector.js +102 -0
- package/dist/type-extractor/extractor/type-name-collector.js.map +1 -0
- package/dist/type-extractor/mapper/scalar-base-type-mapper.d.ts +89 -0
- package/dist/type-extractor/mapper/scalar-base-type-mapper.d.ts.map +1 -0
- package/dist/type-extractor/mapper/scalar-base-type-mapper.js +158 -0
- package/dist/type-extractor/mapper/scalar-base-type-mapper.js.map +1 -0
- package/dist/type-extractor/types/diagnostics.d.ts +1 -1
- package/dist/type-extractor/types/diagnostics.d.ts.map +1 -1
- package/dist/type-extractor/types/graphql.d.ts +2 -0
- package/dist/type-extractor/types/graphql.d.ts.map +1 -1
- package/dist/type-extractor/types/index.d.ts +2 -1
- package/dist/type-extractor/types/index.d.ts.map +1 -1
- package/dist/type-extractor/types/index.js +1 -1
- package/dist/type-extractor/types/index.js.map +1 -1
- package/dist/type-extractor/types/ts-type-reference-factory.d.ts +47 -0
- package/dist/type-extractor/types/ts-type-reference-factory.d.ts.map +1 -0
- package/dist/type-extractor/types/ts-type-reference-factory.js +75 -0
- package/dist/type-extractor/types/ts-type-reference-factory.js.map +1 -0
- package/dist/type-extractor/types/typescript.d.ts +25 -1
- package/dist/type-extractor/types/typescript.d.ts.map +1 -1
- package/dist/type-extractor/validator/type-validator.js +1 -1
- package/dist/type-extractor/validator/type-validator.js.map +1 -1
- package/docs/coding-agents.md +64 -0
- package/docs/configuration.md +6 -20
- package/docs/getting-started.md +15 -12
- package/docs/index.md +36 -21
- package/docs/integration/apollo.md +8 -40
- package/docs/integration/drizzle.md +187 -0
- package/docs/integration/prisma.md +196 -0
- package/docs/integration/yoga.md +8 -40
- package/docs/schema/abstract-resolvers.md +117 -0
- package/docs/schema/directives.md +5 -0
- package/docs/schema/documentation.md +5 -0
- package/docs/schema/enums.md +307 -0
- package/docs/schema/fields.md +66 -0
- package/docs/schema/index.md +21 -0
- package/docs/schema/inputs.md +117 -15
- package/docs/schema/interfaces.md +31 -1
- package/docs/schema/objects.md +42 -0
- package/docs/schema/queries-mutations.md +138 -22
- package/docs/schema/scalars.md +5 -0
- package/docs/schema/unions.md +208 -1
- package/docs/what-is-gqlkit.md +13 -8
- package/package.json +14 -5
- package/src/auto-type-generator/auto-type-generator.ts +1670 -0
- package/src/auto-type-generator/index.ts +63 -0
- package/src/auto-type-generator/inline-enum-collector.ts +338 -0
- package/src/auto-type-generator/inline-object-traverser.ts +49 -0
- package/src/auto-type-generator/inline-union-collector.ts +402 -0
- package/src/auto-type-generator/inline-union-types.ts +33 -0
- package/src/auto-type-generator/inline-union-validator.ts +482 -0
- package/src/auto-type-generator/name-collision-validator.ts +119 -0
- package/src/auto-type-generator/naming-convention.ts +163 -0
- package/src/auto-type-generator/resolve-type-generator.ts +21 -0
- package/src/auto-type-generator/resolver-field-iterator.ts +39 -0
- package/src/auto-type-generator/typename-extractor.ts +230 -0
- package/src/auto-type-generator/typename-resolve-type-generator.ts +281 -0
- package/src/auto-type-generator/typename-types.ts +66 -0
- package/src/auto-type-generator/typename-validator.ts +326 -0
- package/src/cli.ts +13 -0
- package/src/commands/docs.ts +211 -0
- package/src/commands/gen.ts +141 -0
- package/src/commands/main.ts +5 -0
- package/src/config/define-config.ts +28 -0
- package/src/config/index.ts +7 -0
- package/src/config/types.ts +144 -0
- package/src/config-loader/index.ts +14 -0
- package/src/config-loader/loader.ts +143 -0
- package/src/config-loader/validator.ts +672 -0
- package/src/gen-orchestrator/hook-executor/hook-executor.ts +117 -0
- package/src/gen-orchestrator/orchestrator.ts +798 -0
- package/src/gen-orchestrator/reporter/diagnostic-reporter.ts +44 -0
- package/src/gen-orchestrator/reporter/progress-reporter.ts +61 -0
- package/src/gen-orchestrator/writer/file-writer.ts +38 -0
- package/src/index.ts +2 -0
- package/src/resolver-extractor/extract-resolvers.ts +82 -0
- package/src/resolver-extractor/extractor/define-api-extractor.ts +740 -0
- package/src/resolver-extractor/index.ts +13 -0
- package/src/resolver-extractor/validator/abstract-resolver-validator.ts +259 -0
- package/src/schema-generator/builder/ast-builder.ts +706 -0
- package/src/schema-generator/emitter/code-emitter.ts +385 -0
- package/src/schema-generator/emitter/sdl-emitter.ts +13 -0
- package/src/schema-generator/generate-schema.ts +267 -0
- package/src/schema-generator/index.ts +19 -0
- package/src/schema-generator/integrator/result-integrator.ts +759 -0
- package/src/schema-generator/pruner/schema-pruner.ts +112 -0
- package/src/schema-generator/resolver-collector/resolver-collector.ts +157 -0
- package/src/shared/constants.ts +122 -0
- package/src/shared/default-value-detector.ts +172 -0
- package/src/shared/diagnostics.ts +35 -0
- package/src/shared/directive-definition-extractor.ts +564 -0
- package/src/shared/directive-detector.ts +556 -0
- package/src/shared/enum-prefix-detector.ts +99 -0
- package/src/shared/file-scanner.ts +170 -0
- package/src/shared/ignore-fields-detector.ts +109 -0
- package/src/shared/ignore-fields-validator.ts +66 -0
- package/src/shared/index.ts +34 -0
- package/src/shared/inline-object-extractor.ts +102 -0
- package/src/shared/inline-object-utils.ts +23 -0
- package/src/shared/interface-detector.ts +176 -0
- package/src/shared/interface-validator.ts +211 -0
- package/src/shared/metadata-detector.ts +443 -0
- package/src/shared/path-utils.ts +3 -0
- package/src/shared/program-factory.ts +51 -0
- package/src/shared/source-location.ts +38 -0
- package/src/shared/tsconfig-loader.ts +126 -0
- package/src/shared/tsdoc-parser.ts +155 -0
- package/src/shared/type-converter.ts +99 -0
- package/src/shared/typescript-utils.ts +246 -0
- package/src/type-extractor/collector/result-collector.ts +57 -0
- package/src/type-extractor/collector/scalar-collector.ts +254 -0
- package/src/type-extractor/converter/field-eligibility.ts +112 -0
- package/src/type-extractor/converter/graphql-converter.ts +483 -0
- package/src/type-extractor/extract-types.ts +1 -0
- package/src/type-extractor/extractor/field-type-resolver.ts +614 -0
- package/src/type-extractor/extractor/type-extractor.ts +1644 -0
- package/src/type-extractor/extractor/type-name-collector.ts +130 -0
- package/src/type-extractor/index.ts +20 -0
- package/src/type-extractor/mapper/scalar-base-type-mapper.ts +265 -0
- package/src/type-extractor/types/diagnostics.ts +109 -0
- package/src/type-extractor/types/graphql.ts +55 -0
- package/src/type-extractor/types/index.ts +37 -0
- package/src/type-extractor/types/ts-type-reference-factory.ts +150 -0
- package/src/type-extractor/types/typescript.ts +137 -0
- package/src/type-extractor/validator/type-validator.ts +77 -0
- package/dist/auto-type-generator/auto-type-generator.test.d.ts +0 -2
- package/dist/auto-type-generator/auto-type-generator.test.d.ts.map +0 -1
- package/dist/auto-type-generator/auto-type-generator.test.js +0 -613
- package/dist/auto-type-generator/auto-type-generator.test.js.map +0 -1
- package/dist/auto-type-generator/name-collision-validator.test.d.ts +0 -2
- package/dist/auto-type-generator/name-collision-validator.test.d.ts.map +0 -1
- package/dist/auto-type-generator/name-collision-validator.test.js +0 -358
- package/dist/auto-type-generator/name-collision-validator.test.js.map +0 -1
- package/dist/auto-type-generator/naming-convention.test.d.ts +0 -2
- package/dist/auto-type-generator/naming-convention.test.d.ts.map +0 -1
- package/dist/auto-type-generator/naming-convention.test.js +0 -132
- package/dist/auto-type-generator/naming-convention.test.js.map +0 -1
- package/dist/commands/gen.test.d.ts +0 -2
- package/dist/commands/gen.test.d.ts.map +0 -1
- package/dist/commands/gen.test.js +0 -226
- package/dist/commands/gen.test.js.map +0 -1
- package/dist/config-loader/loader.test.d.ts +0 -2
- package/dist/config-loader/loader.test.d.ts.map +0 -1
- package/dist/config-loader/loader.test.js +0 -123
- package/dist/config-loader/loader.test.js.map +0 -1
- package/dist/config-loader/validator.test.d.ts +0 -2
- package/dist/config-loader/validator.test.d.ts.map +0 -1
- package/dist/config-loader/validator.test.js +0 -846
- package/dist/config-loader/validator.test.js.map +0 -1
- package/dist/gen-orchestrator/golden.test.d.ts +0 -2
- package/dist/gen-orchestrator/golden.test.d.ts.map +0 -1
- package/dist/gen-orchestrator/golden.test.js +0 -102
- package/dist/gen-orchestrator/golden.test.js.map +0 -1
- package/dist/gen-orchestrator/hook-executor/hook-executor.test.d.ts +0 -2
- package/dist/gen-orchestrator/hook-executor/hook-executor.test.d.ts.map +0 -1
- package/dist/gen-orchestrator/hook-executor/hook-executor.test.js +0 -167
- package/dist/gen-orchestrator/hook-executor/hook-executor.test.js.map +0 -1
- package/dist/gen-orchestrator/reporter/progress-reporter.test.d.ts +0 -2
- package/dist/gen-orchestrator/reporter/progress-reporter.test.d.ts.map +0 -1
- package/dist/gen-orchestrator/reporter/progress-reporter.test.js +0 -74
- package/dist/gen-orchestrator/reporter/progress-reporter.test.js.map +0 -1
- package/dist/resolver-extractor/validator/only-validator.d.ts +0 -61
- package/dist/resolver-extractor/validator/only-validator.d.ts.map +0 -1
- package/dist/resolver-extractor/validator/only-validator.js +0 -76
- package/dist/resolver-extractor/validator/only-validator.js.map +0 -1
- package/dist/resolver-extractor/validator/only-validator.test.d.ts +0 -8
- package/dist/resolver-extractor/validator/only-validator.test.d.ts.map +0 -1
- package/dist/resolver-extractor/validator/only-validator.test.js +0 -352
- package/dist/resolver-extractor/validator/only-validator.test.js.map +0 -1
- package/dist/schema-generator/builder/ast-builder.test.d.ts +0 -2
- package/dist/schema-generator/builder/ast-builder.test.d.ts.map +0 -1
- package/dist/schema-generator/builder/ast-builder.test.js +0 -469
- package/dist/schema-generator/builder/ast-builder.test.js.map +0 -1
- package/dist/shared/file-scanner.test.d.ts +0 -2
- package/dist/shared/file-scanner.test.d.ts.map +0 -1
- package/dist/shared/file-scanner.test.js +0 -138
- package/dist/shared/file-scanner.test.js.map +0 -1
- package/dist/shared/interface-validator.test.d.ts +0 -2
- package/dist/shared/interface-validator.test.d.ts.map +0 -1
- package/dist/shared/interface-validator.test.js +0 -145
- package/dist/shared/interface-validator.test.js.map +0 -1
- package/dist/type-extractor/types/typescript.test.d.ts +0 -2
- package/dist/type-extractor/types/typescript.test.d.ts.map +0 -1
- package/dist/type-extractor/types/typescript.test.js +0 -287
- package/dist/type-extractor/types/typescript.test.js.map +0 -1
|
@@ -0,0 +1,211 @@
|
|
|
1
|
+
import { access, mkdir, readFile, symlink, writeFile } from "node:fs/promises";
|
|
2
|
+
import { dirname, join, relative } from "node:path";
|
|
3
|
+
import { fileURLToPath } from "node:url";
|
|
4
|
+
import { define } from "gunshi";
|
|
5
|
+
|
|
6
|
+
const __dirname = dirname(fileURLToPath(import.meta.url));
|
|
7
|
+
const CLI_DOCS_DIR = join(__dirname, "../../docs");
|
|
8
|
+
const SKILL_NAME = "gqlkit-guide";
|
|
9
|
+
|
|
10
|
+
export interface RunDocsCommandOptions {
|
|
11
|
+
readonly output: string;
|
|
12
|
+
readonly claude: boolean;
|
|
13
|
+
readonly codex: boolean;
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
export interface RunDocsCommandResult {
|
|
17
|
+
readonly exitCode: number;
|
|
18
|
+
readonly filesWritten: string[];
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
async function exists(path: string): Promise<boolean> {
|
|
22
|
+
try {
|
|
23
|
+
await access(path);
|
|
24
|
+
return true;
|
|
25
|
+
} catch {
|
|
26
|
+
return false;
|
|
27
|
+
}
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
async function detectClaudeEnvironment(dir: string): Promise<boolean> {
|
|
31
|
+
const claudeMdExists = await exists(join(dir, "CLAUDE.md"));
|
|
32
|
+
const claudeDirExists = await exists(join(dir, ".claude"));
|
|
33
|
+
return claudeMdExists || claudeDirExists;
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
async function detectCodexEnvironment(dir: string): Promise<boolean> {
|
|
37
|
+
const agentsMdExists = await exists(join(dir, "AGENTS.md"));
|
|
38
|
+
const codexDirExists = await exists(join(dir, ".codex"));
|
|
39
|
+
return agentsMdExists || codexDirExists;
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
function generateSkillMd(): string {
|
|
43
|
+
return `---
|
|
44
|
+
name: ${SKILL_NAME}
|
|
45
|
+
description: Use when the user asks about "gqlkit", "gqlkit usage", "gqlkit schema definition", "gqlkit configuration", "gqlkit resolvers", "GraphQL code generation with gqlkit", or needs guidance on gqlkit conventions, type definitions, or integration with GraphQL servers or ORMs.
|
|
46
|
+
---
|
|
47
|
+
|
|
48
|
+
# gqlkit Guide
|
|
49
|
+
|
|
50
|
+
gqlkit generates GraphQL schema and resolver maps from TypeScript types and functions.
|
|
51
|
+
|
|
52
|
+
## How it works
|
|
53
|
+
|
|
54
|
+
1. Write TypeScript types in \`src/gqlkit/schema/\` → become GraphQL types
|
|
55
|
+
2. Write resolver functions using \`defineQuery\`, \`defineMutation\`, \`defineField\` → become GraphQL resolvers
|
|
56
|
+
3. Run \`gqlkit gen\` → outputs \`typeDefs\` and \`resolvers\` to \`src/gqlkit/__generated__/\`
|
|
57
|
+
|
|
58
|
+
## Design principles
|
|
59
|
+
|
|
60
|
+
- **Implement first**: Write types and resolvers, generate schema when ready. No edit-regenerate-implement loops.
|
|
61
|
+
- **Just types and functions**: Plain TypeScript with a thin API. No decorators, no complex generics.
|
|
62
|
+
- **Type-safe**: TypeScript types become GraphQL types. Resolver signatures checked at compile time.
|
|
63
|
+
|
|
64
|
+
## How to Use This Skill
|
|
65
|
+
|
|
66
|
+
Read [references/index.md](references/index.md) first. It contains the complete documentation index with all available topics.
|
|
67
|
+
|
|
68
|
+
Navigate to specific documentation files based on user needs as indicated in the index.
|
|
69
|
+
`;
|
|
70
|
+
}
|
|
71
|
+
|
|
72
|
+
function generateRules(): string {
|
|
73
|
+
return `## gqlkit
|
|
74
|
+
|
|
75
|
+
When working with GraphQL schema, types, or resolvers using gqlkit, use the \`${SKILL_NAME}\` skill.
|
|
76
|
+
`;
|
|
77
|
+
}
|
|
78
|
+
|
|
79
|
+
async function createSymlinkIfNotExists(
|
|
80
|
+
linkPath: string,
|
|
81
|
+
target: string,
|
|
82
|
+
): Promise<void> {
|
|
83
|
+
try {
|
|
84
|
+
await symlink(target, linkPath, "dir");
|
|
85
|
+
} catch (error) {
|
|
86
|
+
if ((error as NodeJS.ErrnoException).code !== "EEXIST") {
|
|
87
|
+
throw error;
|
|
88
|
+
}
|
|
89
|
+
}
|
|
90
|
+
}
|
|
91
|
+
|
|
92
|
+
async function appendOrCreateFile(
|
|
93
|
+
filePath: string,
|
|
94
|
+
content: string,
|
|
95
|
+
): Promise<void> {
|
|
96
|
+
try {
|
|
97
|
+
const existing = await readFile(filePath, "utf-8");
|
|
98
|
+
if (!existing.includes("## gqlkit")) {
|
|
99
|
+
await writeFile(filePath, `${existing}\n${content}`);
|
|
100
|
+
}
|
|
101
|
+
} catch (error) {
|
|
102
|
+
if ((error as NodeJS.ErrnoException).code === "ENOENT") {
|
|
103
|
+
await writeFile(filePath, content);
|
|
104
|
+
} else {
|
|
105
|
+
throw error;
|
|
106
|
+
}
|
|
107
|
+
}
|
|
108
|
+
}
|
|
109
|
+
|
|
110
|
+
interface AiToolConfig {
|
|
111
|
+
readonly configDir: string;
|
|
112
|
+
readonly rulesFile: string;
|
|
113
|
+
}
|
|
114
|
+
|
|
115
|
+
async function generateToolFiles(
|
|
116
|
+
outputDir: string,
|
|
117
|
+
config: AiToolConfig,
|
|
118
|
+
filesWritten: string[],
|
|
119
|
+
): Promise<void> {
|
|
120
|
+
const skillDir = join(outputDir, `${config.configDir}/skills/${SKILL_NAME}`);
|
|
121
|
+
await mkdir(skillDir, { recursive: true });
|
|
122
|
+
|
|
123
|
+
const skillMdPath = join(skillDir, "SKILL.md");
|
|
124
|
+
await writeFile(skillMdPath, generateSkillMd());
|
|
125
|
+
filesWritten.push(skillMdPath);
|
|
126
|
+
|
|
127
|
+
const referencesPath = join(skillDir, "references");
|
|
128
|
+
const relativePath = relative(skillDir, CLI_DOCS_DIR);
|
|
129
|
+
await createSymlinkIfNotExists(referencesPath, relativePath);
|
|
130
|
+
filesWritten.push(referencesPath);
|
|
131
|
+
|
|
132
|
+
const rulesPath = join(outputDir, config.rulesFile);
|
|
133
|
+
await appendOrCreateFile(rulesPath, generateRules());
|
|
134
|
+
filesWritten.push(rulesPath);
|
|
135
|
+
}
|
|
136
|
+
|
|
137
|
+
export async function runDocsCommand(
|
|
138
|
+
options: RunDocsCommandOptions,
|
|
139
|
+
): Promise<RunDocsCommandResult> {
|
|
140
|
+
if (!(await exists(CLI_DOCS_DIR))) {
|
|
141
|
+
console.error(
|
|
142
|
+
`Documentation directory not found: ${CLI_DOCS_DIR}\nRun "pnpm build" to generate documentation files.`,
|
|
143
|
+
);
|
|
144
|
+
return { exitCode: 1, filesWritten: [] };
|
|
145
|
+
}
|
|
146
|
+
|
|
147
|
+
const filesWritten: string[] = [];
|
|
148
|
+
|
|
149
|
+
const autoDetect = !options.claude && !options.codex;
|
|
150
|
+
const generateClaude =
|
|
151
|
+
options.claude ||
|
|
152
|
+
(autoDetect && (await detectClaudeEnvironment(options.output)));
|
|
153
|
+
const generateCodex =
|
|
154
|
+
options.codex ||
|
|
155
|
+
(autoDetect && (await detectCodexEnvironment(options.output)));
|
|
156
|
+
|
|
157
|
+
if (!generateClaude && !generateCodex) {
|
|
158
|
+
console.log(
|
|
159
|
+
"No AI tool environment detected. Use --claude or --codex to generate explicitly.",
|
|
160
|
+
);
|
|
161
|
+
return { exitCode: 0, filesWritten: [] };
|
|
162
|
+
}
|
|
163
|
+
|
|
164
|
+
if (generateClaude) {
|
|
165
|
+
await generateToolFiles(
|
|
166
|
+
options.output,
|
|
167
|
+
{ configDir: ".claude", rulesFile: "CLAUDE.md" },
|
|
168
|
+
filesWritten,
|
|
169
|
+
);
|
|
170
|
+
}
|
|
171
|
+
|
|
172
|
+
if (generateCodex) {
|
|
173
|
+
await generateToolFiles(
|
|
174
|
+
options.output,
|
|
175
|
+
{ configDir: ".codex", rulesFile: "AGENTS.md" },
|
|
176
|
+
filesWritten,
|
|
177
|
+
);
|
|
178
|
+
}
|
|
179
|
+
|
|
180
|
+
return { exitCode: 0, filesWritten };
|
|
181
|
+
}
|
|
182
|
+
|
|
183
|
+
export const docsCommand = define({
|
|
184
|
+
name: "docs",
|
|
185
|
+
args: {
|
|
186
|
+
output: {
|
|
187
|
+
type: "string",
|
|
188
|
+
description: "Output directory for generated files",
|
|
189
|
+
},
|
|
190
|
+
claude: {
|
|
191
|
+
type: "boolean",
|
|
192
|
+
description: `Generate Claude Code files (.claude/skills/${SKILL_NAME}/, CLAUDE.md)`,
|
|
193
|
+
},
|
|
194
|
+
codex: {
|
|
195
|
+
type: "boolean",
|
|
196
|
+
description: `Generate Codex files (.codex/skills/${SKILL_NAME}/, AGENTS.md)`,
|
|
197
|
+
},
|
|
198
|
+
},
|
|
199
|
+
run: async (ctx) => {
|
|
200
|
+
const output = ctx.values.output ?? process.cwd();
|
|
201
|
+
const claude = ctx.values.claude ?? false;
|
|
202
|
+
const codex = ctx.values.codex ?? false;
|
|
203
|
+
const result = await runDocsCommand({ output, claude, codex });
|
|
204
|
+
for (const file of result.filesWritten) {
|
|
205
|
+
console.log(`Generated: ${file}`);
|
|
206
|
+
}
|
|
207
|
+
if (result.exitCode !== 0) {
|
|
208
|
+
process.exitCode = result.exitCode;
|
|
209
|
+
}
|
|
210
|
+
},
|
|
211
|
+
});
|
|
@@ -0,0 +1,141 @@
|
|
|
1
|
+
import { dirname } from "node:path";
|
|
2
|
+
import { define } from "gunshi";
|
|
3
|
+
import { loadConfig } from "../config-loader/index.js";
|
|
4
|
+
import { executeHooks } from "../gen-orchestrator/hook-executor/hook-executor.js";
|
|
5
|
+
import {
|
|
6
|
+
executeGeneration,
|
|
7
|
+
type GenerationConfig,
|
|
8
|
+
writeGeneratedFiles,
|
|
9
|
+
} from "../gen-orchestrator/orchestrator.js";
|
|
10
|
+
import { createDiagnosticReporter } from "../gen-orchestrator/reporter/diagnostic-reporter.js";
|
|
11
|
+
import { createProgressReporter } from "../gen-orchestrator/reporter/progress-reporter.js";
|
|
12
|
+
|
|
13
|
+
export interface RunGenCommandOptions {
|
|
14
|
+
readonly cwd: string;
|
|
15
|
+
}
|
|
16
|
+
|
|
17
|
+
export interface RunGenCommandResult {
|
|
18
|
+
readonly exitCode: number;
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
export async function runGenCommand(
|
|
22
|
+
options: RunGenCommandOptions,
|
|
23
|
+
): Promise<RunGenCommandResult> {
|
|
24
|
+
const writer = {
|
|
25
|
+
stdout: (msg: string) => console.log(msg),
|
|
26
|
+
stderr: (msg: string) => console.error(msg),
|
|
27
|
+
};
|
|
28
|
+
|
|
29
|
+
const progressReporter = createProgressReporter(writer);
|
|
30
|
+
const diagnosticReporter = createDiagnosticReporter(writer);
|
|
31
|
+
|
|
32
|
+
const configResult = await loadConfig({ cwd: options.cwd });
|
|
33
|
+
|
|
34
|
+
if (configResult.diagnostics.length > 0) {
|
|
35
|
+
diagnosticReporter.reportDiagnostics(configResult.diagnostics);
|
|
36
|
+
diagnosticReporter.reportError("Config load failed");
|
|
37
|
+
return { exitCode: 1 };
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
const configDir = configResult.configPath
|
|
41
|
+
? dirname(configResult.configPath)
|
|
42
|
+
: options.cwd;
|
|
43
|
+
|
|
44
|
+
const { sourceDir, sourceIgnoreGlobs, output, scalars, tsconfigPath } =
|
|
45
|
+
configResult.config;
|
|
46
|
+
|
|
47
|
+
const config: GenerationConfig = {
|
|
48
|
+
cwd: options.cwd,
|
|
49
|
+
sourceDir,
|
|
50
|
+
sourceIgnoreGlobs,
|
|
51
|
+
output,
|
|
52
|
+
configDir,
|
|
53
|
+
customScalars: scalars,
|
|
54
|
+
tsconfigPath,
|
|
55
|
+
};
|
|
56
|
+
|
|
57
|
+
progressReporter.startPhase("Extracting types");
|
|
58
|
+
progressReporter.startPhase("Extracting resolvers");
|
|
59
|
+
progressReporter.startPhase("Generating schema");
|
|
60
|
+
|
|
61
|
+
const result = await executeGeneration(config);
|
|
62
|
+
|
|
63
|
+
if (result.diagnostics.length > 0) {
|
|
64
|
+
diagnosticReporter.reportDiagnostics(result.diagnostics);
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
if (!result.success) {
|
|
68
|
+
diagnosticReporter.reportError("Generation failed");
|
|
69
|
+
return { exitCode: 1 };
|
|
70
|
+
}
|
|
71
|
+
|
|
72
|
+
const writeResult = await writeGeneratedFiles({
|
|
73
|
+
files: result.files,
|
|
74
|
+
});
|
|
75
|
+
|
|
76
|
+
if (!writeResult.success) {
|
|
77
|
+
diagnosticReporter.reportError("Failed to write output files");
|
|
78
|
+
return { exitCode: 1 };
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
for (const filePath of writeResult.filesWritten) {
|
|
82
|
+
progressReporter.fileWritten(filePath);
|
|
83
|
+
}
|
|
84
|
+
progressReporter.complete();
|
|
85
|
+
|
|
86
|
+
const { hooks } = configResult.config;
|
|
87
|
+
let hookFailed = false;
|
|
88
|
+
|
|
89
|
+
if (
|
|
90
|
+
writeResult.filesWritten.length > 0 &&
|
|
91
|
+
hooks.afterAllFileWrite.length > 0
|
|
92
|
+
) {
|
|
93
|
+
progressReporter.startHookPhase();
|
|
94
|
+
|
|
95
|
+
const hookResult = await executeHooks({
|
|
96
|
+
commands: hooks.afterAllFileWrite,
|
|
97
|
+
filePaths: writeResult.filesWritten,
|
|
98
|
+
cwd: options.cwd,
|
|
99
|
+
onHookComplete: (result) => {
|
|
100
|
+
if (result.success) {
|
|
101
|
+
progressReporter.hookCompleted(result.command);
|
|
102
|
+
} else {
|
|
103
|
+
progressReporter.hookFailed(
|
|
104
|
+
result.command,
|
|
105
|
+
result.exitCode,
|
|
106
|
+
result.stderr,
|
|
107
|
+
);
|
|
108
|
+
}
|
|
109
|
+
},
|
|
110
|
+
});
|
|
111
|
+
|
|
112
|
+
hookFailed = !hookResult.success;
|
|
113
|
+
const failedCount = hookResult.results.filter((r) => !r.success).length;
|
|
114
|
+
progressReporter.hookPhaseSummary(hookResult.results.length, failedCount);
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
if (hookFailed) {
|
|
118
|
+
diagnosticReporter.reportError("Hook execution failed");
|
|
119
|
+
return { exitCode: 1 };
|
|
120
|
+
}
|
|
121
|
+
|
|
122
|
+
diagnosticReporter.reportSuccess("Generation complete!");
|
|
123
|
+
return { exitCode: 0 };
|
|
124
|
+
}
|
|
125
|
+
|
|
126
|
+
export const genCommand = define({
|
|
127
|
+
name: "gen",
|
|
128
|
+
args: {
|
|
129
|
+
cwd: {
|
|
130
|
+
type: "string",
|
|
131
|
+
description: "Working directory for code generation",
|
|
132
|
+
},
|
|
133
|
+
},
|
|
134
|
+
run: async (ctx) => {
|
|
135
|
+
const cwd = ctx.values.cwd ?? process.cwd();
|
|
136
|
+
const result = await runGenCommand({ cwd });
|
|
137
|
+
if (result.exitCode !== 0) {
|
|
138
|
+
process.exitCode = result.exitCode;
|
|
139
|
+
}
|
|
140
|
+
},
|
|
141
|
+
});
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
import type { GqlkitConfig } from "./types.js";
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
* 型安全な設定オブジェクトを作成するヘルパー関数。
|
|
5
|
+
* IDE での型補完とコンパイル時の型チェックを提供する。
|
|
6
|
+
*
|
|
7
|
+
* @example
|
|
8
|
+
* ```typescript
|
|
9
|
+
* // gqlkit.config.ts
|
|
10
|
+
* import { defineConfig } from "@gqlkit-ts/cli";
|
|
11
|
+
*
|
|
12
|
+
* export default defineConfig({
|
|
13
|
+
* scalars: [
|
|
14
|
+
* {
|
|
15
|
+
* graphqlName: "DateTime",
|
|
16
|
+
* type: { from: "./src/types/scalars", name: "DateTime" },
|
|
17
|
+
* },
|
|
18
|
+
* {
|
|
19
|
+
* graphqlName: "UUID",
|
|
20
|
+
* type: { from: "./src/types/scalars", name: "UUID" },
|
|
21
|
+
* },
|
|
22
|
+
* ],
|
|
23
|
+
* });
|
|
24
|
+
* ```
|
|
25
|
+
*/
|
|
26
|
+
export function defineConfig(config: GqlkitConfig): GqlkitConfig {
|
|
27
|
+
return config;
|
|
28
|
+
}
|
|
@@ -0,0 +1,144 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Output configuration for generated files.
|
|
3
|
+
* All paths are relative to project root.
|
|
4
|
+
*/
|
|
5
|
+
export interface OutputConfig {
|
|
6
|
+
/**
|
|
7
|
+
* Output path for resolver map file.
|
|
8
|
+
* - If relative, resolved from project root
|
|
9
|
+
* - If null, suppresses resolvers output
|
|
10
|
+
* - If undefined, uses default path
|
|
11
|
+
* @default "src/gqlkit/__generated__/resolvers.ts"
|
|
12
|
+
*/
|
|
13
|
+
readonly resolversPath?: string | null;
|
|
14
|
+
|
|
15
|
+
/**
|
|
16
|
+
* Output path for GraphQL schema AST (DocumentNode).
|
|
17
|
+
* - If relative, resolved from project root
|
|
18
|
+
* - If null, suppresses AST output
|
|
19
|
+
* - If undefined, uses default path
|
|
20
|
+
* @default "src/gqlkit/__generated__/typeDefs.ts"
|
|
21
|
+
*/
|
|
22
|
+
readonly typeDefsPath?: string | null;
|
|
23
|
+
|
|
24
|
+
/**
|
|
25
|
+
* Output path for GraphQL schema SDL.
|
|
26
|
+
* - If relative, resolved from project root
|
|
27
|
+
* - If null, suppresses SDL output
|
|
28
|
+
* - If undefined, uses default path
|
|
29
|
+
* @default "src/gqlkit/__generated__/schema.graphql"
|
|
30
|
+
*/
|
|
31
|
+
readonly schemaPath?: string | null;
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
/**
|
|
35
|
+
* Hook configuration for lifecycle events.
|
|
36
|
+
*/
|
|
37
|
+
export interface HooksConfig {
|
|
38
|
+
/**
|
|
39
|
+
* Commands to execute after all files are written.
|
|
40
|
+
* Each command receives all written file paths as arguments.
|
|
41
|
+
* Commands are executed sequentially in order.
|
|
42
|
+
*/
|
|
43
|
+
readonly afterAllFileWrite?: string | ReadonlyArray<string>;
|
|
44
|
+
}
|
|
45
|
+
|
|
46
|
+
/**
|
|
47
|
+
* Type definition for gqlkit configuration file.
|
|
48
|
+
* Used in `gqlkit.config.ts`.
|
|
49
|
+
*/
|
|
50
|
+
export interface GqlkitConfig {
|
|
51
|
+
/**
|
|
52
|
+
* Source directory to scan for types and resolvers.
|
|
53
|
+
* All TypeScript files (.ts, .cts, .mts) under this directory will be scanned.
|
|
54
|
+
* @default "src/gqlkit/schema"
|
|
55
|
+
*/
|
|
56
|
+
readonly sourceDir?: string;
|
|
57
|
+
|
|
58
|
+
/**
|
|
59
|
+
* Glob patterns to exclude from source scanning.
|
|
60
|
+
* Patterns are matched against file paths relative to sourceDir.
|
|
61
|
+
* @default []
|
|
62
|
+
*/
|
|
63
|
+
readonly sourceIgnoreGlobs?: ReadonlyArray<string>;
|
|
64
|
+
|
|
65
|
+
/**
|
|
66
|
+
* Output configuration for generated files.
|
|
67
|
+
*/
|
|
68
|
+
readonly output?: OutputConfig;
|
|
69
|
+
|
|
70
|
+
/**
|
|
71
|
+
* Custom scalar mapping definitions.
|
|
72
|
+
* Configures the mapping between TypeScript types and GraphQL scalars.
|
|
73
|
+
*/
|
|
74
|
+
readonly scalars?: ReadonlyArray<ScalarMappingConfig>;
|
|
75
|
+
|
|
76
|
+
/**
|
|
77
|
+
* Path to TypeScript configuration file.
|
|
78
|
+
* - If relative, resolved from config file
|
|
79
|
+
* - Absolute paths are also supported
|
|
80
|
+
* - If unspecified, automatically searches for tsconfig.json in project root
|
|
81
|
+
*/
|
|
82
|
+
readonly tsconfigPath?: string;
|
|
83
|
+
|
|
84
|
+
/**
|
|
85
|
+
* Hook configuration for lifecycle events.
|
|
86
|
+
*/
|
|
87
|
+
readonly hooks?: HooksConfig;
|
|
88
|
+
}
|
|
89
|
+
|
|
90
|
+
/**
|
|
91
|
+
* Custom scalar mapping configuration.
|
|
92
|
+
* Maps TypeScript types to GraphQL scalar types.
|
|
93
|
+
*
|
|
94
|
+
* @example
|
|
95
|
+
* // Global type (e.g., Date)
|
|
96
|
+
* { name: "DateTime", tsType: { name: "Date" } }
|
|
97
|
+
*
|
|
98
|
+
* // Module type
|
|
99
|
+
* { name: "DateTime", tsType: { name: "DateTimeString", from: "./src/types" } }
|
|
100
|
+
*
|
|
101
|
+
* // With usage constraint
|
|
102
|
+
* { name: "DateTime", tsType: { name: "Date" }, only: "input" }
|
|
103
|
+
*
|
|
104
|
+
* // With description
|
|
105
|
+
* { name: "DateTime", tsType: { name: "Date" }, description: "ISO 8601 format" }
|
|
106
|
+
*/
|
|
107
|
+
export interface ScalarMappingConfig {
|
|
108
|
+
/**
|
|
109
|
+
* GraphQL scalar name.
|
|
110
|
+
* Example: "DateTime", "UUID", "URL"
|
|
111
|
+
*/
|
|
112
|
+
readonly name: string;
|
|
113
|
+
|
|
114
|
+
/**
|
|
115
|
+
* TypeScript type information to map.
|
|
116
|
+
*/
|
|
117
|
+
readonly tsType: {
|
|
118
|
+
/**
|
|
119
|
+
* TypeScript type name.
|
|
120
|
+
* Example: "Date", "DateTime", "UUID"
|
|
121
|
+
*/
|
|
122
|
+
readonly name: string;
|
|
123
|
+
|
|
124
|
+
/**
|
|
125
|
+
* Import path for the type. If omitted, treated as a global type.
|
|
126
|
+
* Example: "./src/types/scalars", "@my-lib/scalars"
|
|
127
|
+
*/
|
|
128
|
+
readonly from?: string;
|
|
129
|
+
};
|
|
130
|
+
|
|
131
|
+
/**
|
|
132
|
+
* Usage constraint for the scalar type.
|
|
133
|
+
* - "input": Only use this type for input positions (arguments, input type fields)
|
|
134
|
+
* - "output": Only use this type for output positions (return types, object type fields)
|
|
135
|
+
* - undefined: Use for both input and output positions
|
|
136
|
+
*/
|
|
137
|
+
readonly only?: "input" | "output";
|
|
138
|
+
|
|
139
|
+
/**
|
|
140
|
+
* Description for the scalar type.
|
|
141
|
+
* Will be included in the generated GraphQL schema.
|
|
142
|
+
*/
|
|
143
|
+
readonly description?: string;
|
|
144
|
+
}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
export {
|
|
2
|
+
type LoadConfigOptions,
|
|
3
|
+
type LoadConfigResult,
|
|
4
|
+
loadConfig,
|
|
5
|
+
type ResolvedConfig,
|
|
6
|
+
type ResolvedHooksConfig,
|
|
7
|
+
type ResolvedOutputConfig,
|
|
8
|
+
type ResolvedScalarMapping,
|
|
9
|
+
} from "./loader.js";
|
|
10
|
+
|
|
11
|
+
export type {
|
|
12
|
+
ValidateConfigOptions,
|
|
13
|
+
ValidateConfigResult,
|
|
14
|
+
} from "./validator.js";
|
|
@@ -0,0 +1,143 @@
|
|
|
1
|
+
import { existsSync } from "node:fs";
|
|
2
|
+
import { join } from "node:path";
|
|
3
|
+
import { createJiti } from "jiti";
|
|
4
|
+
import type { Diagnostic } from "../type-extractor/types/index.js";
|
|
5
|
+
import { validateConfig } from "./validator.js";
|
|
6
|
+
|
|
7
|
+
export interface LoadConfigOptions {
|
|
8
|
+
readonly cwd: string;
|
|
9
|
+
}
|
|
10
|
+
|
|
11
|
+
export interface ResolvedScalarMapping {
|
|
12
|
+
readonly graphqlName: string;
|
|
13
|
+
readonly typeName: string;
|
|
14
|
+
readonly importPath: string | null;
|
|
15
|
+
readonly only: "input" | "output" | null;
|
|
16
|
+
readonly description: string | null;
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
/**
|
|
20
|
+
* Resolved output configuration.
|
|
21
|
+
* Undefined values are resolved to defaults.
|
|
22
|
+
*/
|
|
23
|
+
export interface ResolvedOutputConfig {
|
|
24
|
+
/** Resolver map output path. Null suppresses output */
|
|
25
|
+
readonly resolversPath: string | null;
|
|
26
|
+
/** Schema AST (typeDefs) output path. Null suppresses output */
|
|
27
|
+
readonly typeDefsPath: string | null;
|
|
28
|
+
/** Schema SDL output path. Null suppresses output */
|
|
29
|
+
readonly schemaPath: string | null;
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
/**
|
|
33
|
+
* Resolved hook configuration.
|
|
34
|
+
* Commands are normalized to array format.
|
|
35
|
+
*/
|
|
36
|
+
export interface ResolvedHooksConfig {
|
|
37
|
+
/** Normalized to array (empty if not configured) */
|
|
38
|
+
readonly afterAllFileWrite: ReadonlyArray<string>;
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
export interface ResolvedConfig {
|
|
42
|
+
readonly sourceDir: string;
|
|
43
|
+
readonly sourceIgnoreGlobs: ReadonlyArray<string>;
|
|
44
|
+
readonly output: ResolvedOutputConfig;
|
|
45
|
+
readonly scalars: ReadonlyArray<ResolvedScalarMapping>;
|
|
46
|
+
readonly tsconfigPath: string | null;
|
|
47
|
+
readonly hooks: ResolvedHooksConfig;
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
export interface LoadConfigResult {
|
|
51
|
+
readonly config: ResolvedConfig;
|
|
52
|
+
readonly configPath: string | undefined;
|
|
53
|
+
readonly diagnostics: ReadonlyArray<Diagnostic>;
|
|
54
|
+
}
|
|
55
|
+
|
|
56
|
+
const CONFIG_FILE_NAME = "gqlkit.config.ts";
|
|
57
|
+
|
|
58
|
+
export const DEFAULT_SOURCE_DIR = "src/gqlkit/schema";
|
|
59
|
+
export const DEFAULT_RESOLVERS_PATH = "src/gqlkit/__generated__/resolvers.ts";
|
|
60
|
+
export const DEFAULT_TYPEDEFS_PATH = "src/gqlkit/__generated__/typeDefs.ts";
|
|
61
|
+
export const DEFAULT_SCHEMA_PATH = "src/gqlkit/__generated__/schema.graphql";
|
|
62
|
+
|
|
63
|
+
const DEFAULT_OUTPUT_CONFIG: ResolvedOutputConfig = {
|
|
64
|
+
resolversPath: DEFAULT_RESOLVERS_PATH,
|
|
65
|
+
typeDefsPath: DEFAULT_TYPEDEFS_PATH,
|
|
66
|
+
schemaPath: DEFAULT_SCHEMA_PATH,
|
|
67
|
+
};
|
|
68
|
+
|
|
69
|
+
const DEFAULT_HOOKS_CONFIG: ResolvedHooksConfig = {
|
|
70
|
+
afterAllFileWrite: [],
|
|
71
|
+
};
|
|
72
|
+
|
|
73
|
+
const DEFAULT_RESOLVED_CONFIG: ResolvedConfig = {
|
|
74
|
+
sourceDir: DEFAULT_SOURCE_DIR,
|
|
75
|
+
sourceIgnoreGlobs: [],
|
|
76
|
+
output: DEFAULT_OUTPUT_CONFIG,
|
|
77
|
+
scalars: [],
|
|
78
|
+
tsconfigPath: null,
|
|
79
|
+
hooks: DEFAULT_HOOKS_CONFIG,
|
|
80
|
+
};
|
|
81
|
+
|
|
82
|
+
export async function loadConfig(
|
|
83
|
+
options: LoadConfigOptions,
|
|
84
|
+
): Promise<LoadConfigResult> {
|
|
85
|
+
const configPath = join(options.cwd, CONFIG_FILE_NAME);
|
|
86
|
+
|
|
87
|
+
if (!existsSync(configPath)) {
|
|
88
|
+
return {
|
|
89
|
+
config: DEFAULT_RESOLVED_CONFIG,
|
|
90
|
+
configPath: undefined,
|
|
91
|
+
diagnostics: [],
|
|
92
|
+
};
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
const jiti = createJiti(options.cwd, {
|
|
96
|
+
interopDefault: true,
|
|
97
|
+
});
|
|
98
|
+
|
|
99
|
+
try {
|
|
100
|
+
const loadedModule = await jiti.import(configPath);
|
|
101
|
+
const rawConfig =
|
|
102
|
+
(loadedModule as { default?: unknown }).default ?? loadedModule;
|
|
103
|
+
|
|
104
|
+
const validationResult = validateConfig({
|
|
105
|
+
config: rawConfig,
|
|
106
|
+
configPath,
|
|
107
|
+
});
|
|
108
|
+
|
|
109
|
+
if (!validationResult.valid || !validationResult.resolvedConfig) {
|
|
110
|
+
return {
|
|
111
|
+
config: DEFAULT_RESOLVED_CONFIG,
|
|
112
|
+
configPath,
|
|
113
|
+
diagnostics: validationResult.diagnostics,
|
|
114
|
+
};
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
return {
|
|
118
|
+
config: validationResult.resolvedConfig,
|
|
119
|
+
configPath,
|
|
120
|
+
diagnostics: [],
|
|
121
|
+
};
|
|
122
|
+
} catch (error) {
|
|
123
|
+
const message =
|
|
124
|
+
error instanceof Error ? error.message : "Unknown error occurred";
|
|
125
|
+
|
|
126
|
+
return {
|
|
127
|
+
config: DEFAULT_RESOLVED_CONFIG,
|
|
128
|
+
configPath,
|
|
129
|
+
diagnostics: [
|
|
130
|
+
{
|
|
131
|
+
code: "CONFIG_SYNTAX_ERROR",
|
|
132
|
+
message: `Failed to load config file: ${message}`,
|
|
133
|
+
severity: "error",
|
|
134
|
+
location: {
|
|
135
|
+
file: configPath,
|
|
136
|
+
line: 1,
|
|
137
|
+
column: 1,
|
|
138
|
+
},
|
|
139
|
+
},
|
|
140
|
+
],
|
|
141
|
+
};
|
|
142
|
+
}
|
|
143
|
+
}
|