klasik 2.0.8 โ†’ 2.2.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.
Files changed (47) hide show
  1. package/README.md +710 -3
  2. package/dist/bin/go-schema-gen +0 -0
  3. package/dist/builders/class-builder.d.ts +1 -0
  4. package/dist/builders/class-builder.d.ts.map +1 -1
  5. package/dist/builders/class-builder.js.map +1 -1
  6. package/dist/cli/commands/generate-crd.d.ts +1 -0
  7. package/dist/cli/commands/generate-crd.d.ts.map +1 -1
  8. package/dist/cli/commands/generate-crd.js +2 -0
  9. package/dist/cli/commands/generate-crd.js.map +1 -1
  10. package/dist/cli/commands/generate-go.d.ts +22 -0
  11. package/dist/cli/commands/generate-go.d.ts.map +1 -0
  12. package/dist/cli/commands/generate-go.js +130 -0
  13. package/dist/cli/commands/generate-go.js.map +1 -0
  14. package/dist/cli/commands/generate-jsonschema.d.ts +1 -0
  15. package/dist/cli/commands/generate-jsonschema.d.ts.map +1 -1
  16. package/dist/cli/commands/generate-jsonschema.js +2 -0
  17. package/dist/cli/commands/generate-jsonschema.js.map +1 -1
  18. package/dist/cli/commands/generate.d.ts +1 -0
  19. package/dist/cli/commands/generate.d.ts.map +1 -1
  20. package/dist/cli/commands/generate.js +2 -0
  21. package/dist/cli/commands/generate.js.map +1 -1
  22. package/dist/cli/index.js +3 -1
  23. package/dist/cli/index.js.map +1 -1
  24. package/dist/cli/utils/options.d.ts +4 -0
  25. package/dist/cli/utils/options.d.ts.map +1 -1
  26. package/dist/cli/utils/options.js +7 -0
  27. package/dist/cli/utils/options.js.map +1 -1
  28. package/dist/generator/generator.d.ts.map +1 -1
  29. package/dist/generator/generator.js +4 -0
  30. package/dist/generator/generator.js.map +1 -1
  31. package/dist/loaders/go-schema-loader.d.ts +60 -0
  32. package/dist/loaders/go-schema-loader.d.ts.map +1 -0
  33. package/dist/loaders/go-schema-loader.js +221 -0
  34. package/dist/loaders/go-schema-loader.js.map +1 -0
  35. package/dist/plugins/ajv-validator-plugin.d.ts +45 -0
  36. package/dist/plugins/ajv-validator-plugin.d.ts.map +1 -0
  37. package/dist/plugins/ajv-validator-plugin.js +320 -0
  38. package/dist/plugins/ajv-validator-plugin.js.map +1 -0
  39. package/package.json +5 -3
  40. package/tools/go-schema-gen/README.md +147 -0
  41. package/tools/go-schema-gen/build.sh +24 -0
  42. package/tools/go-schema-gen/comment_extractor.go +128 -0
  43. package/tools/go-schema-gen/go-schema-gen +0 -0
  44. package/tools/go-schema-gen/go.mod +36 -0
  45. package/tools/go-schema-gen/go.sum +112 -0
  46. package/tools/go-schema-gen/main.go +155 -0
  47. package/tools/go-schema-gen/registry.go +35 -0
package/README.md CHANGED
@@ -1,12 +1,13 @@
1
1
  # Klasik
2
2
 
3
- Generate TypeScript clients from OpenAPI specifications, Kubernetes CRDs, and JSON Schema with full type safety and class-transformer support.
3
+ Generate TypeScript clients from OpenAPI specifications, Kubernetes CRDs, JSON Schema, and Go structs with full type safety and class-transformer support.
4
4
 
5
5
  Perfect for:
6
6
  - ๐Ÿš€ Kubernetes operators and controllers
7
7
  - ๐Ÿ”ง REST API clients with type safety
8
8
  - ๐Ÿ“ฆ NestJS backend services
9
9
  - ๐ŸŽฏ Type-safe microservice communication
10
+ - ๐Ÿ”„ Go-to-TypeScript code sharing
10
11
 
11
12
  ## Features
12
13
 
@@ -14,13 +15,14 @@ Perfect for:
14
15
  ๐ŸŽฏ **Type-Safe** - Full TypeScript support with strict typing
15
16
  ๐Ÿ”„ **class-transformer** - Automatic serialization/deserialization
16
17
  โœ… **class-validator** - Built-in validation decorators
18
+ ๐Ÿ“‹ **Ajv JSON Schema** - Draft 2020-12 validation with deep nesting support
17
19
  ๐ŸŽจ **NestJS Ready** - @ApiProperty decorators out of the box
18
- ๐Ÿ“ฆ **Multiple Formats** - OpenAPI, Kubernetes CRDs, JSON Schema
20
+ ๐Ÿ“ฆ **Multiple Formats** - OpenAPI, Kubernetes CRDs, JSON Schema, Go structs
19
21
  ๐ŸŒ **ESM Support** - Modern JavaScript modules with .js extensions
20
22
  ๐Ÿ”— **External $refs** - Automatic resolution of external schemas
21
23
  ๐ŸŽญ **Custom Templates** - Mustache-based customization
22
24
  โš™๏ธ **Flexible Output** - Multiple export styles (namespace, direct, both)
23
- ๐Ÿงช **Well Tested** - Comprehensive test coverage (748 passing tests)
25
+ ๐Ÿงช **Well Tested** - Comprehensive test coverage (797 passing tests)
24
26
  ๐Ÿš€ **Production Ready** - Used in real-world projects
25
27
  ๐Ÿ“ **Full CLI** - Rich command-line interface with 4 commands
26
28
  ๐Ÿ” **Authentication** - Custom headers including Bearer tokens
@@ -62,6 +64,17 @@ klasik generate-jsonschema \
62
64
  --output ./src/generated
63
65
  ```
64
66
 
67
+ Generate from Go structs (requires Go installed, auto-setup on first use):
68
+
69
+ ```bash
70
+ klasik generate-go \
71
+ --type "helm.sh/helm/v3/pkg/chart.Metadata" \
72
+ --type "helm.sh/helm/v3/pkg/chart.Chart" \
73
+ --output ./src/generated \
74
+ --class-validator \
75
+ --nestjs-swagger
76
+ ```
77
+
65
78
  #### Bare Mode
66
79
 
67
80
  Generate models directly in the output directory without wrapper structure:
@@ -238,6 +251,416 @@ const tasks = await api.listTasks();
238
251
 
239
252
  For more details, see the [Validation Guide](./docs/validation.md).
240
253
 
254
+ ## Ajv JSON Schema Validation
255
+
256
+ Klasik can generate Ajv-based JSON Schema validation alongside or instead of class-validator decorators. This provides comprehensive JSON Schema Draft 2020-12 validation with deep nested object support and optimized performance.
257
+
258
+ ### Why Ajv Validation?
259
+
260
+ **Advantages over class-validator:**
261
+ - โœ… **Full JSON Schema compliance** - Supports all Draft 2020-12 features
262
+ - โœ… **Deep nested validation** - Automatically validates nested objects at all levels
263
+ - โœ… **Performance optimized** - Schema compilation is cached per class
264
+ - โœ… **Standards-based** - Uses industry-standard JSON Schema format
265
+ - โœ… **Independent** - Works alongside or without class-validator
266
+
267
+ **When to use:**
268
+ - Complex nested object structures (User โ†’ Address โ†’ Coordinates)
269
+ - JSON Schema-first development workflows
270
+ - Need for format validation (email, uuid, date-time, etc.)
271
+ - Projects requiring JSON Schema compliance
272
+ - High-performance validation scenarios
273
+
274
+ ### Basic Usage
275
+
276
+ Enable with the `--use-ajv` flag:
277
+
278
+ ```bash
279
+ klasik generate \
280
+ --url https://api.example.com/openapi.json \
281
+ --output ./generated \
282
+ --use-ajv
283
+ ```
284
+
285
+ ### Generated Code Structure
286
+
287
+ Each generated class includes:
288
+
289
+ 1. **`static getSchema()`** - Returns the JSON Schema
290
+ 2. **`static validateWithJsonSchema(data)`** - Validates data against the schema
291
+ 3. **Private cached validator** - Optimized for performance
292
+
293
+ **Example generated class:**
294
+
295
+ ```typescript
296
+ import { Ajv } from "ajv";
297
+ import { addFormats } from "ajv-formats";
298
+ import { Expose } from "class-transformer";
299
+
300
+ export class User {
301
+ /**
302
+ * Get JSON Schema for User
303
+ * @returns JSON Schema Draft 2020-12
304
+ */
305
+ static getSchema(): object {
306
+ return {
307
+ "$schema": "https://json-schema.org/draft/2020-12/schema",
308
+ "type": "object",
309
+ "properties": {
310
+ "name": {
311
+ "type": "string",
312
+ "minLength": 1
313
+ },
314
+ "email": {
315
+ "type": "string",
316
+ "format": "email"
317
+ },
318
+ "address": {
319
+ "type": "object"
320
+ }
321
+ },
322
+ "additionalProperties": false,
323
+ "required": ["name", "email"]
324
+ };
325
+ }
326
+
327
+ private static _ajvInstance: Ajv | null = null;
328
+ private static _compiledValidator: any = null;
329
+
330
+ /** Get or create Ajv instance for User */
331
+ private static getAjvInstance(): Ajv {
332
+ if (!this._ajvInstance) {
333
+ this._ajvInstance = new Ajv({ allErrors: true, strict: false });
334
+ addFormats(this._ajvInstance);
335
+ }
336
+ return this._ajvInstance;
337
+ }
338
+
339
+ /** Get or create compiled validator for User (cached for performance) */
340
+ private static getCompiledValidator(): any {
341
+ if (!this._compiledValidator) {
342
+ const ajv = this.getAjvInstance();
343
+ const schema = this.getSchema();
344
+ this._compiledValidator = ajv.compile(schema);
345
+ }
346
+ return this._compiledValidator;
347
+ }
348
+
349
+ /**
350
+ * Validate data against JSON Schema with recursive nested validation
351
+ * @param data - Data to validate
352
+ * @returns Validation result with errors if any
353
+ */
354
+ static validateWithJsonSchema(data: unknown): { valid: boolean; errors: any[] } {
355
+ const validate = this.getCompiledValidator();
356
+ const valid = validate(data);
357
+
358
+ // Collect errors
359
+ const allErrors: any[] = validate.errors || [];
360
+
361
+ // Recursively validate nested objects that have validateWithJsonSchema method
362
+ if (valid && typeof data === "object" && data !== null) {
363
+ for (const [key, value] of Object.entries(data)) {
364
+ if (value && typeof value === "object") {
365
+ const constructor = (value as any).constructor;
366
+ if (constructor && typeof constructor.validateWithJsonSchema === "function") {
367
+ const nestedResult = constructor.validateWithJsonSchema(value);
368
+ if (!nestedResult.valid) {
369
+ allErrors.push(...nestedResult.errors.map((e: any) => ({
370
+ ...e,
371
+ instancePath: `/${key}${e.instancePath || ""}`
372
+ })));
373
+ }
374
+ }
375
+ }
376
+ }
377
+ }
378
+
379
+ return { valid: allErrors.length === 0, errors: allErrors };
380
+ }
381
+
382
+ @Expose()
383
+ name: string;
384
+
385
+ @Expose()
386
+ email: string;
387
+
388
+ @Expose()
389
+ address?: Address;
390
+ }
391
+ ```
392
+
393
+ ### Using Validation Methods
394
+
395
+ **Valid data:**
396
+
397
+ ```typescript
398
+ import { User } from './generated/models';
399
+
400
+ const userData = {
401
+ name: 'John Doe',
402
+ email: 'john@example.com'
403
+ };
404
+
405
+ const result = User.validateWithJsonSchema(userData);
406
+
407
+ if (result.valid) {
408
+ console.log('โœ… Data is valid!');
409
+ } else {
410
+ console.error('โŒ Validation failed:', result.errors);
411
+ }
412
+ ```
413
+
414
+ **Invalid data:**
415
+
416
+ ```typescript
417
+ const invalidData = {
418
+ name: '', // minLength: 1 violation
419
+ email: 'not-an-email' // format: email violation
420
+ };
421
+
422
+ const result = User.validateWithJsonSchema(invalidData);
423
+
424
+ console.log(result);
425
+ // {
426
+ // valid: false,
427
+ // errors: [
428
+ // {
429
+ // instancePath: '/name',
430
+ // schemaPath: '#/properties/name/minLength',
431
+ // keyword: 'minLength',
432
+ // params: { limit: 1 },
433
+ // message: 'must NOT have fewer than 1 characters'
434
+ // },
435
+ // {
436
+ // instancePath: '/email',
437
+ // schemaPath: '#/properties/email/format',
438
+ // keyword: 'format',
439
+ // params: { format: 'email' },
440
+ // message: 'must match format "email"'
441
+ // }
442
+ // ]
443
+ // }
444
+ ```
445
+
446
+ ### Deep Nested Validation
447
+
448
+ The validator automatically validates nested objects recursively:
449
+
450
+ ```typescript
451
+ import { User, Address } from './generated/models';
452
+
453
+ // Create nested structure
454
+ const address = new Address();
455
+ address.street = ''; // Invalid: minLength violation
456
+ address.city = 'Springfield';
457
+ address.zipCode = 'INVALID'; // Invalid: pattern violation
458
+
459
+ const user = {
460
+ name: 'John Doe',
461
+ email: 'john@example.com',
462
+ address // Nested object
463
+ };
464
+
465
+ const result = User.validateWithJsonSchema(user);
466
+
467
+ console.log(result);
468
+ // {
469
+ // valid: false,
470
+ // errors: [
471
+ // {
472
+ // instancePath: '/address/street',
473
+ // keyword: 'minLength',
474
+ // message: 'must NOT have fewer than 1 characters'
475
+ // },
476
+ // {
477
+ // instancePath: '/address/zipCode',
478
+ // keyword: 'pattern',
479
+ // message: 'must match pattern "^[0-9]{5}$"'
480
+ // }
481
+ // ]
482
+ // }
483
+ ```
484
+
485
+ **Note:** Error paths include the full nested path (`/address/street`), making it easy to identify exactly where validation failed.
486
+
487
+ ### Supported Validations
488
+
489
+ All JSON Schema Draft 2020-12 validation keywords are supported:
490
+
491
+ **String constraints:**
492
+ - `minLength`, `maxLength`
493
+ - `pattern` (regex)
494
+ - `format` (email, uuid, date-time, uri, etc.)
495
+
496
+ **Numeric constraints:**
497
+ - `minimum`, `maximum`
498
+ - `exclusiveMinimum`, `exclusiveMaximum`
499
+ - `multipleOf`
500
+
501
+ **Array constraints:**
502
+ - `minItems`, `maxItems`
503
+ - `uniqueItems`
504
+
505
+ **Object constraints:**
506
+ - `required` properties
507
+ - `additionalProperties`
508
+
509
+ **Other:**
510
+ - `enum` values
511
+ - `nullable` types
512
+ - Union types with `anyOf`
513
+
514
+ ### Performance Optimization
515
+
516
+ The generated code includes **compilation caching** for optimal performance:
517
+
518
+ ```typescript
519
+ // First validation: Schema is compiled and cached
520
+ User.validateWithJsonSchema(data1); // Compile + Validate
521
+
522
+ // Subsequent validations: Uses cached compiled validator
523
+ User.validateWithJsonSchema(data2); // Validate only (fast!)
524
+ User.validateWithJsonSchema(data3); // Validate only (fast!)
525
+ ```
526
+
527
+ **Benefits:**
528
+ - Schema compiled once per class, not per validation
529
+ - Significant performance improvement for repeated validations
530
+ - Singleton Ajv instance shared across validations
531
+
532
+ ### Combining with class-validator
533
+
534
+ You can use both validation approaches together:
535
+
536
+ ```bash
537
+ klasik generate \
538
+ --url https://api.example.com/openapi.json \
539
+ --output ./generated \
540
+ --class-validator \
541
+ --use-ajv
542
+ ```
543
+
544
+ **Generated class has both:**
545
+
546
+ ```typescript
547
+ export class User {
548
+ // class-validator decorators
549
+ @IsString()
550
+ @MinLength(1)
551
+ @Expose()
552
+ name: string;
553
+
554
+ @IsEmail()
555
+ @Expose()
556
+ email: string;
557
+
558
+ // PLUS Ajv validation methods
559
+ static getSchema(): object { /* ... */ }
560
+ static validateWithJsonSchema(data: unknown) { /* ... */ }
561
+ }
562
+ ```
563
+
564
+ **Use case:** Runtime validation with class-validator in NestJS controllers, plus JSON Schema validation for external integrations.
565
+
566
+ ### Dependencies
567
+
568
+ When using `--use-ajv`, the following dependencies are automatically added to `package.json`:
569
+
570
+ ```json
571
+ {
572
+ "dependencies": {
573
+ "ajv": "^8.12.0",
574
+ "ajv-formats": "^2.1.1"
575
+ }
576
+ }
577
+ ```
578
+
579
+ Install them in your project:
580
+
581
+ ```bash
582
+ cd generated
583
+ npm install
584
+ ```
585
+
586
+ ### Complete Example
587
+
588
+ ```bash
589
+ # Generate models with Ajv validation
590
+ klasik generate-jsonschema \
591
+ --url ./schemas/user.json \
592
+ --output ./src/models \
593
+ --use-ajv
594
+
595
+ # Use in your code
596
+ cat > example.ts << 'EOF'
597
+ import { User } from './src/models';
598
+
599
+ // Valid user
600
+ const validUser = {
601
+ name: 'Alice Smith',
602
+ email: 'alice@example.com',
603
+ age: 30
604
+ };
605
+
606
+ const result1 = User.validateWithJsonSchema(validUser);
607
+ console.log('Valid:', result1.valid); // true
608
+
609
+ // Invalid user
610
+ const invalidUser = {
611
+ name: '', // Too short
612
+ email: 'invalid-email',
613
+ age: -5 // Negative age
614
+ };
615
+
616
+ const result2 = User.validateWithJsonSchema(invalidUser);
617
+ console.log('Valid:', result2.valid); // false
618
+ console.log('Errors:', result2.errors);
619
+ // [
620
+ // { instancePath: '/name', message: 'must NOT have fewer than 1 characters' },
621
+ // { instancePath: '/email', message: 'must match format "email"' },
622
+ // { instancePath: '/age', message: 'must be >= 0' }
623
+ // ]
624
+ EOF
625
+
626
+ npx ts-node example.ts
627
+ ```
628
+
629
+ ### Advanced: Accessing the JSON Schema
630
+
631
+ You can access the generated JSON Schema directly:
632
+
633
+ ```typescript
634
+ import { User } from './generated/models';
635
+
636
+ // Get the schema
637
+ const schema = User.getSchema();
638
+
639
+ console.log(JSON.stringify(schema, null, 2));
640
+ // {
641
+ // "$schema": "https://json-schema.org/draft/2020-12/schema",
642
+ // "type": "object",
643
+ // "properties": {
644
+ // "name": { "type": "string", "minLength": 1 },
645
+ // "email": { "type": "string", "format": "email" }
646
+ // },
647
+ // "required": ["name", "email"],
648
+ // "additionalProperties": false
649
+ // }
650
+
651
+ // Use with external JSON Schema validators
652
+ import Ajv from 'ajv';
653
+ const ajv = new Ajv();
654
+ const validate = ajv.compile(User.getSchema());
655
+ validate(data);
656
+ ```
657
+
658
+ **Use cases:**
659
+ - Generating OpenAPI documentation
660
+ - Sharing schemas with other systems
661
+ - Custom validation workflows
662
+ - Schema introspection
663
+
241
664
  ## CLI Commands
242
665
 
243
666
  ### `klasik generate`
@@ -262,6 +685,7 @@ klasik generate [options]
262
685
  | `--skip-js-extensions` | Skip .js extensions (for bundlers) | `false` |
263
686
  | `--nestjs-swagger` | Add @ApiProperty decorators | `false` |
264
687
  | `--class-validator` | Add class-validator decorators | `false` |
688
+ | `--use-ajv` | Add Ajv JSON Schema validation methods | `false` |
265
689
  | `--header <header>` | Custom header (repeatable) | - |
266
690
  | `--timeout <ms>` | Request timeout | `30000` |
267
691
  | `--template <dir>` | Custom template directory | - |
@@ -292,6 +716,19 @@ klasik generate \
292
716
  --nestjs-swagger \
293
717
  --class-validator
294
718
 
719
+ # With Ajv JSON Schema validation
720
+ klasik generate \
721
+ --url https://api.example.com/spec.json \
722
+ --output ./src/api \
723
+ --use-ajv
724
+
725
+ # With both class-validator and Ajv
726
+ klasik generate \
727
+ --url https://api.example.com/spec.json \
728
+ --output ./src/api \
729
+ --class-validator \
730
+ --use-ajv
731
+
295
732
  # With external refs and authentication
296
733
  klasik generate \
297
734
  --url https://api.example.com/spec.json \
@@ -373,6 +810,7 @@ klasik generate-crd [options]
373
810
  | `--crd-kind-case <format>` | Folder naming: `pascal`, `snake`, `kebab` | `pascal` |
374
811
  | `--nestjs-swagger` | Add @ApiProperty decorators | `false` |
375
812
  | `--class-validator` | Add class-validator decorators | `false` |
813
+ | `--use-ajv` | Add Ajv JSON Schema validation methods | `false` |
376
814
  | `--esm` | Add .js extensions for ESM | `false` |
377
815
  | `--header <header>` | Custom header (repeatable) | - |
378
816
  | `--resolve-refs` | Resolve external $ref files | `false` |
@@ -428,6 +866,7 @@ klasik generate-jsonschema [options]
428
866
  | `-o, --output <dir>` | Output directory (required) | - |
429
867
  | `--nestjs-swagger` | Add @ApiProperty decorators | `false` |
430
868
  | `--class-validator` | Add class-validator decorators | `false` |
869
+ | `--use-ajv` | Add Ajv JSON Schema validation methods | `false` |
431
870
  | `--esm` | Add .js extensions for ESM | `false` |
432
871
  | `--header <header>` | Custom header (repeatable) | - |
433
872
  | `--resolve-refs` | Resolve external $ref files | `false` |
@@ -455,8 +894,87 @@ klasik generate-jsonschema \
455
894
  --output ./src/types \
456
895
  --nestjs-swagger \
457
896
  --class-validator
897
+
898
+ # With Ajv JSON Schema validation
899
+ klasik generate-jsonschema \
900
+ --url ./schemas/user.json \
901
+ --output ./src/types \
902
+ --use-ajv
903
+ ```
904
+
905
+ ### `klasik generate-go`
906
+
907
+ Generate TypeScript models from Go structs using runtime reflection.
908
+
909
+ **Usage:**
910
+
911
+ ```bash
912
+ klasik generate-go [options]
458
913
  ```
459
914
 
915
+ **Options:**
916
+
917
+ | Option | Description | Default |
918
+ |--------|-------------|---------|
919
+ | `-t, --type <type>` | Go type path (package.Type) (repeatable, required) | - |
920
+ | `-o, --output <dir>` | Output directory (required) | - |
921
+ | `--nestjs-swagger` | Add @ApiProperty decorators | `false` |
922
+ | `--class-validator` | Add class-validator decorators | `false` |
923
+ | `--use-ajv` | Add Ajv JSON Schema validation methods | `false` |
924
+ | `--esm` | Add .js extensions for ESM | `false` |
925
+ | `--template <dir>` | Custom template directory | - |
926
+ | `--export-style <style>` | Export style: `namespace`, `direct`, `both`, `none` | `namespace` |
927
+ | `--bare` | Generate models directly in output dir | `false` |
928
+ | `--go-tool-path <path>` | Path to go-schema-gen binary | auto-detected |
929
+ | `--allow-additional-properties` | Allow additional properties in JSON Schema | `false` |
930
+
931
+ **Prerequisites:**
932
+ - Go 1.21+ must be installed (first-time setup is automatic)
933
+ - Types must be registered in `tools/go-schema-gen/registry.go`
934
+
935
+ **Examples:**
936
+
937
+ ```bash
938
+ # Generate from Helm chart types
939
+ klasik generate-go \
940
+ --type "helm.sh/helm/v3/pkg/chart.Metadata" \
941
+ --type "helm.sh/helm/v3/pkg/chart.Chart" \
942
+ --output ./src/helm-types \
943
+ --nestjs-swagger \
944
+ --class-validator
945
+
946
+ # Generate with Ajv validation
947
+ klasik generate-go \
948
+ --type "helm.sh/helm/v3/pkg/chart.Metadata" \
949
+ --output ./src/types \
950
+ --use-ajv
951
+
952
+ # Generate for ESM
953
+ klasik generate-go \
954
+ --type "helm.sh/helm/v3/pkg/chart.Chart" \
955
+ --output ./src/types \
956
+ --esm
957
+ ```
958
+
959
+ **How it works:**
960
+ 1. Uses Go reflection via `invopop/jsonschema` library
961
+ 2. Generates JSON Schema from Go structs
962
+ 3. Feeds to existing JsonSchemaParser
963
+ 4. Generates TypeScript with full type safety
964
+
965
+ **Adding new types:**
966
+
967
+ Edit `tools/go-schema-gen/registry.go`:
968
+ ```go
969
+ import mypackage "github.com/org/package"
970
+
971
+ var typeRegistry = map[string]interface{}{
972
+ "github.com/org/package.MyStruct": mypackage.MyStruct{},
973
+ }
974
+ ```
975
+
976
+ Then rebuild: `cd tools/go-schema-gen && ./build.sh`
977
+
460
978
  ## Kubernetes CRD Support
461
979
 
462
980
  Klasik can generate TypeScript models directly from Kubernetes CustomResourceDefinitions (CRDs). Perfect for working with custom Kubernetes resources like ArgoCD Applications, Cert-Manager Certificates, or your own custom resources.
@@ -573,6 +1091,193 @@ const pkg: Package = {
573
1091
  // Full TypeScript intellisense and type checking!
574
1092
  ```
575
1093
 
1094
+ ## Go Struct Support
1095
+
1096
+ Klasik can generate TypeScript models from Go structs using runtime reflection. Perfect for sharing types between Go backends and TypeScript frontends, or for generating types from existing Go packages like Helm, Kubernetes, or your own custom packages.
1097
+
1098
+ ### Features
1099
+
1100
+ - โœ… **Runtime reflection** - Uses Go's reflection API with `invopop/jsonschema`
1101
+ - โœ… **Struct tag support** - Respects `json`, `yaml`, `jsonschema` tags
1102
+ - โœ… **Multiple types** - Generate from multiple structs in one command
1103
+ - โœ… **Automatic references** - Nested types resolved with $ref
1104
+ - โœ… **Full decorator support** - NestJS, class-validator, class-transformer, Ajv
1105
+ - โœ… **Production-ready** - Tested with Helm chart types
1106
+
1107
+ ### Prerequisites
1108
+
1109
+ - **Go 1.21+** must be installed (download from [go.dev](https://go.dev/dl/))
1110
+ - Types must be registered in `tools/go-schema-gen/registry.go`
1111
+
1112
+ **Note:** The first time you use `generate-go`, Klasik will automatically:
1113
+ 1. Check if Go is installed
1114
+ 2. Download Go dependencies (`go mod tidy`)
1115
+ 3. Build the Go schema generator tool
1116
+
1117
+ This only happens once - subsequent runs use the cached binary.
1118
+
1119
+ ### How It Works
1120
+
1121
+ 1. Go tool uses reflection to inspect struct at runtime
1122
+ 2. Generates JSON Schema Draft 2020-12
1123
+ 3. Feeds to existing JsonSchemaParser
1124
+ 4. Generates TypeScript with full type safety
1125
+
1126
+ **Architecture:**
1127
+ ```
1128
+ Go Struct โ†’ Reflection โ†’ JSON Schema โ†’ JsonSchemaParser โ†’ IR โ†’ TypeScript
1129
+ ```
1130
+
1131
+ ### Quick Start
1132
+
1133
+ First-time users: Just run the command! Klasik will automatically set up everything:
1134
+
1135
+ ```bash
1136
+ klasik generate-go \
1137
+ --type "helm.sh/helm/v3/pkg/chart.Metadata" \
1138
+ --output ./src/helm-types
1139
+
1140
+ # Output:
1141
+ # Building Go schema generator (first time only)...
1142
+ # Installing Go dependencies...
1143
+ # Compiling Go tool...
1144
+ # โœ“ Go tool built successfully
1145
+ # โœ” Generation complete!
1146
+ ```
1147
+
1148
+ Subsequent runs are instant (no rebuild needed):
1149
+
1150
+ ```bash
1151
+ klasik generate-go \
1152
+ --type "helm.sh/helm/v3/pkg/chart.Chart" \
1153
+ --output ./src/helm-types \
1154
+ --nestjs-swagger \
1155
+ --class-validator
1156
+ ```
1157
+
1158
+ ### Struct Tag Mapping
1159
+
1160
+ Go struct tags are automatically converted to JSON Schema:
1161
+
1162
+ | Go Tag | Effect | JSON Schema |
1163
+ |--------|--------|-------------|
1164
+ | `json:"fieldName"` | Property name | `"properties": {"fieldName": {...}}` |
1165
+ | `json:",omitempty"` | Optional field | Not in `"required"` array |
1166
+ | `jsonschema:"required"` | Force required | Added to `"required"` array |
1167
+ | `jsonschema:"minLength=5"` | Validation | `"minLength": 5` |
1168
+ | `jsonschema:"pattern=^[A-Z]"` | Regex | `"pattern": "^[A-Z]"` |
1169
+ | `jsonschema_description:"..."` | Documentation | `"description": "..."` |
1170
+
1171
+ **Example Go Struct:**
1172
+ ```go
1173
+ type Metadata struct {
1174
+ Name string `json:"name" jsonschema:"required,minLength=1"`
1175
+ Version string `json:"version" jsonschema:"required"`
1176
+ Description string `json:"description,omitempty"`
1177
+ }
1178
+ ```
1179
+
1180
+ **Generated TypeScript:**
1181
+ ```typescript
1182
+ export class Metadata {
1183
+ @ApiProperty()
1184
+ @IsString()
1185
+ name: string;
1186
+
1187
+ @ApiProperty()
1188
+ @IsString()
1189
+ version: string;
1190
+
1191
+ @ApiProperty({ required: false })
1192
+ @IsOptional()
1193
+ @IsString()
1194
+ description?: string;
1195
+ }
1196
+ ```
1197
+
1198
+ ### Adding New Types
1199
+
1200
+ To add new Go packages/types:
1201
+
1202
+ 1. Edit `tools/go-schema-gen/registry.go`:
1203
+ ```go
1204
+ import (
1205
+ chart "helm.sh/helm/v3/pkg/chart"
1206
+ mypackage "github.com/org/package"
1207
+ )
1208
+
1209
+ var typeRegistry = map[string]interface{}{
1210
+ // Existing types
1211
+ "helm.sh/helm/v3/pkg/chart.Metadata": chart.Metadata{},
1212
+
1213
+ // Add your types
1214
+ "github.com/org/package.MyStruct": mypackage.MyStruct{},
1215
+ }
1216
+ ```
1217
+
1218
+ 2. Update dependencies:
1219
+ ```bash
1220
+ cd tools/go-schema-gen
1221
+ go mod tidy
1222
+ ```
1223
+
1224
+ 3. Rebuild the tool:
1225
+ ```bash
1226
+ ./build.sh
1227
+ ```
1228
+
1229
+ 4. Use your new type:
1230
+ ```bash
1231
+ klasik generate-go \
1232
+ --type "github.com/org/package.MyStruct" \
1233
+ --output ./src/types
1234
+ ```
1235
+
1236
+ ### Limitations
1237
+
1238
+ - **Type Registry Required** - Types must be pre-registered (no dynamic loading)
1239
+ - **Requires Recompilation** - Adding new packages requires rebuilding the Go tool
1240
+ - **Go Installation** - Go must be installed on the system
1241
+
1242
+ ### Troubleshooting
1243
+
1244
+ **"Go is not installed" error:**
1245
+ ```bash
1246
+ # Install Go from https://go.dev/dl/
1247
+ # On macOS with Homebrew:
1248
+ brew install go
1249
+
1250
+ # Verify installation:
1251
+ go version
1252
+ ```
1253
+
1254
+ **"Failed to build Go tool" error:**
1255
+ ```bash
1256
+ # Try manual build:
1257
+ cd tools/go-schema-gen
1258
+ ./build.sh
1259
+
1260
+ # Or rebuild from scratch:
1261
+ rm -rf ../../dist/bin/go-schema-gen
1262
+ klasik generate-go --type "..." --output ...
1263
+ ```
1264
+
1265
+ **Rebuild the Go tool manually:**
1266
+ ```bash
1267
+ cd tools/go-schema-gen
1268
+ go mod tidy
1269
+ ./build.sh
1270
+ ```
1271
+
1272
+ ### Future Enhancements
1273
+
1274
+ Planned features for future releases:
1275
+ - Go Plugin support for dynamic loading
1276
+ - Auto-discovery of types in packages
1277
+ - `validate` tag support
1278
+ - Custom type mappings
1279
+ - Multi-platform pre-built binaries
1280
+
576
1281
  ## NestJS Integration
577
1282
 
578
1283
  Klasik integrates seamlessly with NestJS, generating models with `@ApiProperty` decorators for automatic Swagger/OpenAPI documentation and `class-validator` decorators for runtime validation.
@@ -890,6 +1595,8 @@ Built with:
890
1595
  - [ts-morph](https://github.com/dsherret/ts-morph) - TypeScript Compiler API wrapper
891
1596
  - [class-transformer](https://github.com/typestack/class-transformer) - Object transformation
892
1597
  - [class-validator](https://github.com/typestack/class-validator) - Runtime validation
1598
+ - [ajv](https://github.com/ajv-validator/ajv) - JSON Schema validator
1599
+ - [ajv-formats](https://github.com/ajv-validator/ajv-formats) - Format validation for Ajv
893
1600
  - [mustache](https://github.com/janl/mustache.js) - Template engine
894
1601
  - [commander](https://github.com/tj/commander.js) - CLI framework
895
1602