@openapi-qraft/tanstack-query-react-plugin 2.4.1 → 2.5.0-beta.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 (75) hide show
  1. package/CHANGELOG.md +10 -0
  2. package/dist/generateCode.d.ts +2 -2
  3. package/dist/generateCode.d.ts.map +1 -1
  4. package/dist/generateCode.js.map +1 -1
  5. package/dist/plugin.d.ts.map +1 -1
  6. package/dist/plugin.js +6 -3
  7. package/dist/plugin.js.map +1 -1
  8. package/dist/ts-factory/getIndexFactory.d.ts +2 -2
  9. package/dist/ts-factory/getIndexFactory.d.ts.map +1 -1
  10. package/dist/ts-factory/getIndexFactory.js.map +1 -1
  11. package/dist/ts-factory/getServiceFactory.d.ts +3 -2
  12. package/dist/ts-factory/getServiceFactory.d.ts.map +1 -1
  13. package/dist/ts-factory/getServiceFactory.js +113 -42
  14. package/dist/ts-factory/getServiceFactory.js.map +1 -1
  15. package/dist/ts-factory/service-operation.generated/ServiceOperationCancelQueries.js +3 -3
  16. package/dist/ts-factory/service-operation.generated/ServiceOperationCancelQueries.js.map +1 -1
  17. package/dist/ts-factory/service-operation.generated/ServiceOperationFetchInfiniteQuery.js +12 -12
  18. package/dist/ts-factory/service-operation.generated/ServiceOperationFetchInfiniteQuery.js.map +1 -1
  19. package/dist/ts-factory/service-operation.generated/ServiceOperationFetchQuery.js +10 -10
  20. package/dist/ts-factory/service-operation.generated/ServiceOperationFetchQuery.js.map +1 -1
  21. package/dist/ts-factory/service-operation.generated/ServiceOperationGetInfiniteQueryData.js +6 -6
  22. package/dist/ts-factory/service-operation.generated/ServiceOperationGetInfiniteQueryData.js.map +1 -1
  23. package/dist/ts-factory/service-operation.generated/ServiceOperationGetQueriesData.js +6 -6
  24. package/dist/ts-factory/service-operation.generated/ServiceOperationGetQueriesData.js.map +1 -1
  25. package/dist/ts-factory/service-operation.generated/ServiceOperationGetQueryData.js +5 -5
  26. package/dist/ts-factory/service-operation.generated/ServiceOperationGetQueryData.js.map +1 -1
  27. package/dist/ts-factory/service-operation.generated/ServiceOperationGetQueryState.js +11 -11
  28. package/dist/ts-factory/service-operation.generated/ServiceOperationGetQueryState.js.map +1 -1
  29. package/dist/ts-factory/service-operation.generated/ServiceOperationInvalidateQueries.js +2 -2
  30. package/dist/ts-factory/service-operation.generated/ServiceOperationInvalidateQueries.js.map +1 -1
  31. package/dist/ts-factory/service-operation.generated/ServiceOperationIsFetchingQueries.js +3 -3
  32. package/dist/ts-factory/service-operation.generated/ServiceOperationIsFetchingQueries.js.map +1 -1
  33. package/dist/ts-factory/service-operation.generated/ServiceOperationIsMutatingQueries.js +3 -3
  34. package/dist/ts-factory/service-operation.generated/ServiceOperationIsMutatingQueries.js.map +1 -1
  35. package/dist/ts-factory/service-operation.generated/ServiceOperationMutationFn.js +3 -3
  36. package/dist/ts-factory/service-operation.generated/ServiceOperationMutationFn.js.map +1 -1
  37. package/dist/ts-factory/service-operation.generated/ServiceOperationQueryFn.js +6 -6
  38. package/dist/ts-factory/service-operation.generated/ServiceOperationQueryFn.js.map +1 -1
  39. package/dist/ts-factory/service-operation.generated/ServiceOperationRefetchQueries.js +3 -3
  40. package/dist/ts-factory/service-operation.generated/ServiceOperationRefetchQueries.js.map +1 -1
  41. package/dist/ts-factory/service-operation.generated/ServiceOperationRemoveQueries.js +3 -3
  42. package/dist/ts-factory/service-operation.generated/ServiceOperationRemoveQueries.js.map +1 -1
  43. package/dist/ts-factory/service-operation.generated/ServiceOperationResetQueries.js +3 -3
  44. package/dist/ts-factory/service-operation.generated/ServiceOperationResetQueries.js.map +1 -1
  45. package/dist/ts-factory/service-operation.generated/ServiceOperationSetInfiniteQueryData.js +8 -8
  46. package/dist/ts-factory/service-operation.generated/ServiceOperationSetInfiniteQueryData.js.map +1 -1
  47. package/dist/ts-factory/service-operation.generated/ServiceOperationSetQueriesData.js +3 -3
  48. package/dist/ts-factory/service-operation.generated/ServiceOperationSetQueriesData.js.map +1 -1
  49. package/dist/ts-factory/service-operation.generated/ServiceOperationSetQueryData.js +5 -5
  50. package/dist/ts-factory/service-operation.generated/ServiceOperationSetQueryData.js.map +1 -1
  51. package/dist/ts-factory/service-operation.generated/ServiceOperationUseInfiniteQuery.js +19 -19
  52. package/dist/ts-factory/service-operation.generated/ServiceOperationUseInfiniteQuery.js.map +1 -1
  53. package/dist/ts-factory/service-operation.generated/ServiceOperationUseIsFetchingQueries.js +3 -3
  54. package/dist/ts-factory/service-operation.generated/ServiceOperationUseIsFetchingQueries.js.map +1 -1
  55. package/dist/ts-factory/service-operation.generated/ServiceOperationUseIsMutating.js +3 -3
  56. package/dist/ts-factory/service-operation.generated/ServiceOperationUseIsMutating.js.map +1 -1
  57. package/dist/ts-factory/service-operation.generated/ServiceOperationUseMutation.js +7 -7
  58. package/dist/ts-factory/service-operation.generated/ServiceOperationUseMutation.js.map +1 -1
  59. package/dist/ts-factory/service-operation.generated/ServiceOperationUseMutationState.js +5 -5
  60. package/dist/ts-factory/service-operation.generated/ServiceOperationUseMutationState.js.map +1 -1
  61. package/dist/ts-factory/service-operation.generated/ServiceOperationUseQueries.js +2 -2
  62. package/dist/ts-factory/service-operation.generated/ServiceOperationUseQueries.js.map +1 -1
  63. package/dist/ts-factory/service-operation.generated/ServiceOperationUseQuery.js +15 -15
  64. package/dist/ts-factory/service-operation.generated/ServiceOperationUseQuery.js.map +1 -1
  65. package/dist/ts-factory/service-operation.generated/ServiceOperationUseSuspenseInfiniteQuery.js +9 -9
  66. package/dist/ts-factory/service-operation.generated/ServiceOperationUseSuspenseInfiniteQuery.js.map +1 -1
  67. package/dist/ts-factory/service-operation.generated/ServiceOperationUseSuspenseQueries.js +2 -2
  68. package/dist/ts-factory/service-operation.generated/ServiceOperationUseSuspenseQueries.js.map +1 -1
  69. package/dist/ts-factory/service-operation.generated/ServiceOperationUseSuspenseQuery.js +6 -6
  70. package/dist/ts-factory/service-operation.generated/ServiceOperationUseSuspenseQuery.js.map +1 -1
  71. package/package.json +3 -3
  72. package/src/generateCode.ts +5 -5
  73. package/src/plugin.ts +11 -3
  74. package/src/ts-factory/getIndexFactory.ts +2 -2
  75. package/src/ts-factory/getServiceFactory.ts +241 -80
@@ -1,3 +1,4 @@
1
+ import { isReadOnlyOperation } from '@openapi-qraft/plugin/lib/isReadOnlyOperation';
1
2
  import { ServiceOperation } from '@openapi-qraft/plugin/lib/open-api/OpenAPIService';
2
3
  import camelCase from 'camelcase';
3
4
  import ts from 'typescript';
@@ -35,8 +36,9 @@ import { createOperationMethodTSDocExample } from './tsdoc/createOperationMethod
35
36
 
36
37
  const factory = ts.factory;
37
38
 
38
- export type ServiceImportsFactoryOptions = {
39
+ export type ServiceFactoryOptions = {
39
40
  openapiTypesImportPath: string;
41
+ queryableWriteOperations: boolean;
40
42
  };
41
43
 
42
44
  type Service = { typeName: string; variableName: string };
@@ -44,18 +46,18 @@ type Service = { typeName: string; variableName: string };
44
46
  export const getServiceFactory = (
45
47
  service: Service,
46
48
  operations: ServiceOperation[],
47
- { openapiTypesImportPath }: ServiceImportsFactoryOptions
49
+ options: ServiceFactoryOptions
48
50
  ) => {
49
51
  const mainNodes = [
50
- getServiceInterfaceFactory(service, operations),
52
+ getServiceInterfaceFactory(service, operations, options),
51
53
  getServiceVariableFactory(service, operations),
52
- ...getOperationsTypes(operations),
54
+ ...getOperationsTypes(operations, options),
53
55
  ];
54
56
 
55
57
  const importNodes = [
56
- getOpenAPISchemaImportsFactory(openapiTypesImportPath),
58
+ getOpenAPISchemaImportsFactory(options.openapiTypesImportPath),
57
59
  ...getServiceOperationImportsFactory(
58
- filterUnusedTypes(getModuleTypeImports(operations), mainNodes)
60
+ filterUnusedTypes(getModuleTypeImports(operations, options), mainNodes)
59
61
  ),
60
62
  ];
61
63
 
@@ -112,7 +114,8 @@ const getServiceOperationImportsFactory = (
112
114
 
113
115
  const getServiceInterfaceFactory = (
114
116
  service: Service,
115
- operations: ServiceOperation[]
117
+ operations: ServiceOperation[],
118
+ options: Pick<ServiceFactoryOptions, 'queryableWriteOperations'>
116
119
  ) => {
117
120
  return factory.createInterfaceDeclaration(
118
121
  [factory.createToken(ts.SyntaxKind.ExportKeyword)],
@@ -120,19 +123,25 @@ const getServiceInterfaceFactory = (
120
123
  undefined,
121
124
  undefined,
122
125
  operations.map((operation) =>
123
- getServiceInterfaceOperationFactory(operation, service)
126
+ getServiceInterfaceOperationFactory(operation, service, options)
124
127
  )
125
128
  );
126
129
  };
127
130
 
128
131
  const getServiceInterfaceOperationFactory = (
129
132
  operation: ServiceOperation,
130
- service: Service
133
+ service: Service,
134
+ options: Pick<ServiceFactoryOptions, 'queryableWriteOperations'>
131
135
  ) => {
132
136
  const operationMethodNodes = getMethodSignatureNodes(
133
- operation.method === 'get'
137
+ isReadOnlyOperation(operation)
134
138
  ? createServicesQueryOperationNodes()
135
- : createServicesMutationOperationNodes()
139
+ : options.queryableWriteOperations
140
+ ? [
141
+ ...createServicesMutationOperationNodes(),
142
+ ...createServicesQueryOperationNodes(),
143
+ ]
144
+ : createServicesMutationOperationNodes()
136
145
  );
137
146
 
138
147
  operationMethodNodes.forEach((node) => {
@@ -176,11 +185,16 @@ const getServiceInterfaceOperationFactory = (
176
185
  undefined,
177
186
  factory.createTypeLiteralNode([
178
187
  ...replaceGenericTypesWithOperationTypes(
179
- reduceAreAllOptionalConditionalTParamsType(
180
- operationMethodNodes,
188
+ reduceAreAllOptionalConditionalTVariablesType(
189
+ reduceAreAllOptionalConditionalTParamsType(
190
+ operationMethodNodes,
191
+ operation,
192
+ options
193
+ ),
181
194
  operation
182
195
  ),
183
- operation
196
+ operation,
197
+ options
184
198
  ),
185
199
  factory.createPropertySignature(
186
200
  undefined,
@@ -202,7 +216,11 @@ const getServiceInterfaceOperationFactory = (
202
216
  factory.createIdentifier('parameters'),
203
217
  undefined,
204
218
  factory.createTypeReferenceNode(
205
- getOperationParametersTypeName(operation),
219
+ getOperationParametersTypeName(
220
+ operation,
221
+ options,
222
+ isReadOnlyOperation(operation) ? 'query' : 'mutation'
223
+ ),
206
224
  undefined
207
225
  )
208
226
  ),
@@ -224,7 +242,7 @@ const getServiceInterfaceOperationFactory = (
224
242
  undefined
225
243
  )
226
244
  ),
227
- operation.method !== 'get'
245
+ !isReadOnlyOperation(operation) || operation.requestBody
228
246
  ? factory.createPropertySignature(
229
247
  undefined,
230
248
  factory.createIdentifier('body'),
@@ -362,31 +380,36 @@ const getOperationBodyFactory = (operation: ServiceOperation) => {
362
380
  ...mediaTypes.map((mediaType) =>
363
381
  factory.createIndexedAccessTypeNode(
364
382
  factory.createIndexedAccessTypeNode(
365
- factory.createTypeReferenceNode(
366
- factory.createIdentifier('NonNullable'),
367
- [
383
+ (() => {
384
+ const requestBodyNode = factory.createIndexedAccessTypeNode(
368
385
  factory.createIndexedAccessTypeNode(
369
386
  factory.createIndexedAccessTypeNode(
370
- factory.createIndexedAccessTypeNode(
371
- factory.createTypeReferenceNode(
372
- factory.createIdentifier('paths'),
373
- undefined
374
- ),
375
- factory.createLiteralTypeNode(
376
- factory.createStringLiteral(operation.path)
377
- )
387
+ factory.createTypeReferenceNode(
388
+ factory.createIdentifier('paths'),
389
+ undefined
378
390
  ),
379
391
  factory.createLiteralTypeNode(
380
- factory.createStringLiteral(operation.method)
392
+ factory.createStringLiteral(operation.path)
381
393
  )
382
394
  ),
383
395
  factory.createLiteralTypeNode(
384
- factory.createStringLiteral('requestBody')
396
+ factory.createStringLiteral(operation.method)
385
397
  )
386
398
  ),
387
- ]
388
- ),
389
- // todo::Add optional NonNullable inference, see `POST /entities/{entity_id}/documents`
399
+ factory.createLiteralTypeNode(
400
+ factory.createStringLiteral('requestBody')
401
+ )
402
+ );
403
+
404
+ if (!operation.requestBody?.required) {
405
+ return factory.createTypeReferenceNode(
406
+ factory.createIdentifier('NonNullable'),
407
+ [requestBodyNode]
408
+ );
409
+ }
410
+
411
+ return requestBodyNode;
412
+ })(),
390
413
  factory.createLiteralTypeNode(factory.createStringLiteral('content'))
391
414
  ),
392
415
  factory.createLiteralTypeNode(factory.createStringLiteral(mediaType))
@@ -398,39 +421,63 @@ const getOperationBodyFactory = (operation: ServiceOperation) => {
398
421
  ]);
399
422
  };
400
423
 
401
- const createOperationParametersFactory = (operation: ServiceOperation) => {
402
- if (!operation.parameters?.length)
403
- return operation.method === 'get'
404
- ? factory.createKeywordTypeNode(ts.SyntaxKind.UndefinedKeyword)
405
- : // mutation with predefined parameters fallback to an empty object
406
- factory.createTypeLiteralNode(
407
- ['query', 'header', 'path'].map((name) =>
408
- factory.createPropertySignature(
409
- undefined,
410
- factory.createIdentifier(name),
411
- factory.createToken(ts.SyntaxKind.QuestionToken),
412
- factory.createKeywordTypeNode(ts.SyntaxKind.NeverKeyword)
424
+ const createOperationParametersFactory = (
425
+ operation: ServiceOperation,
426
+ withRequestBody: boolean
427
+ ) => {
428
+ if (isReadOnlyOperation(operation) && !operation.parameters?.length) {
429
+ return factory.createKeywordTypeNode(ts.SyntaxKind.UndefinedKeyword);
430
+ }
431
+
432
+ const parametersNodes = operation.parameters?.length
433
+ ? factory.createIndexedAccessTypeNode(
434
+ factory.createIndexedAccessTypeNode(
435
+ factory.createIndexedAccessTypeNode(
436
+ factory.createTypeReferenceNode(
437
+ factory.createIdentifier('paths'),
438
+ undefined
439
+ ),
440
+ factory.createLiteralTypeNode(
441
+ factory.createStringLiteral(operation.path)
413
442
  )
443
+ ),
444
+ factory.createLiteralTypeNode(
445
+ factory.createStringLiteral(operation.method)
414
446
  )
415
- );
447
+ ),
448
+ factory.createLiteralTypeNode(factory.createStringLiteral('parameters'))
449
+ )
450
+ : factory.createTypeLiteralNode(
451
+ ['query', 'header', 'path'].map((name) =>
452
+ factory.createPropertySignature(
453
+ undefined,
454
+ factory.createIdentifier(name),
455
+ factory.createToken(ts.SyntaxKind.QuestionToken),
456
+ factory.createKeywordTypeNode(ts.SyntaxKind.NeverKeyword)
457
+ )
458
+ )
459
+ );
416
460
 
417
- return factory.createIndexedAccessTypeNode(
418
- factory.createIndexedAccessTypeNode(
419
- factory.createIndexedAccessTypeNode(
461
+ if (!withRequestBody || !operation.requestBody) {
462
+ return parametersNodes;
463
+ }
464
+
465
+ return factory.createIntersectionTypeNode([
466
+ parametersNodes,
467
+ factory.createTypeLiteralNode([
468
+ factory.createPropertySignature(
469
+ undefined,
470
+ factory.createIdentifier('body'),
471
+ operation.requestBody.required
472
+ ? undefined
473
+ : factory.createToken(ts.SyntaxKind.QuestionToken),
420
474
  factory.createTypeReferenceNode(
421
- factory.createIdentifier('paths'),
475
+ factory.createIdentifier(getOperationBodyTypeName(operation)),
422
476
  undefined
423
- ),
424
- factory.createLiteralTypeNode(
425
- factory.createStringLiteral(operation.path)
426
477
  )
427
478
  ),
428
- factory.createLiteralTypeNode(
429
- factory.createStringLiteral(operation.method)
430
- )
431
- ),
432
- factory.createLiteralTypeNode(factory.createStringLiteral('parameters'))
433
- );
479
+ ]),
480
+ ]);
434
481
  };
435
482
 
436
483
  const getServiceVariableFactory = (
@@ -460,7 +507,10 @@ const getServiceVariableFactory = (
460
507
  );
461
508
  };
462
509
 
463
- const getOperationsTypes = (operations: ServiceOperation[]) => {
510
+ const getOperationsTypes = (
511
+ operations: ServiceOperation[],
512
+ options: Pick<ServiceFactoryOptions, 'queryableWriteOperations'>
513
+ ) => {
464
514
  return operations.flatMap((operation) => {
465
515
  const nodes = [
466
516
  factory.createTypeAliasDeclaration(
@@ -469,12 +519,39 @@ const getOperationsTypes = (operations: ServiceOperation[]) => {
469
519
  undefined,
470
520
  getOperationSchemaFactory(operation)
471
521
  ),
472
- factory.createTypeAliasDeclaration(
473
- undefined,
474
- factory.createIdentifier(getOperationParametersTypeName(operation)),
475
- undefined,
476
- createOperationParametersFactory(operation)
477
- ),
522
+ ...(isSeparateParametersOperation(operation, options)
523
+ ? [
524
+ factory.createTypeAliasDeclaration(
525
+ undefined,
526
+ factory.createIdentifier(
527
+ getOperationParametersTypeName(operation, options, 'query')
528
+ ),
529
+ undefined,
530
+ createOperationParametersFactory(operation, true)
531
+ ),
532
+ factory.createTypeAliasDeclaration(
533
+ undefined,
534
+ factory.createIdentifier(
535
+ getOperationParametersTypeName(operation, options, 'mutation')
536
+ ),
537
+ undefined,
538
+ createOperationParametersFactory(operation, false)
539
+ ),
540
+ ]
541
+ : [
542
+ factory.createTypeAliasDeclaration(
543
+ undefined,
544
+ factory.createIdentifier(
545
+ getOperationParametersTypeName(
546
+ operation,
547
+ options,
548
+ isReadOnlyOperation(operation) ? 'query' : 'mutation'
549
+ )
550
+ ),
551
+ undefined,
552
+ createOperationParametersFactory(operation, false)
553
+ ),
554
+ ]),
478
555
  factory.createTypeAliasDeclaration(
479
556
  undefined,
480
557
  factory.createIdentifier(getOperationDataTypeName(operation)),
@@ -489,7 +566,7 @@ const getOperationsTypes = (operations: ServiceOperation[]) => {
489
566
  ),
490
567
  ];
491
568
 
492
- if (operation.method !== 'get') {
569
+ if (!isReadOnlyOperation(operation) || operation.requestBody) {
493
570
  nodes.push(
494
571
  factory.createTypeAliasDeclaration(
495
572
  undefined,
@@ -507,8 +584,29 @@ const getOperationsTypes = (operations: ServiceOperation[]) => {
507
584
  const getOperationSchemaTypeName = (operation: ServiceOperation) =>
508
585
  camelCase(`${operation.name}-Schema`, { pascalCase: true });
509
586
 
510
- const getOperationParametersTypeName = (operation: ServiceOperation) =>
511
- camelCase(`${operation.name}-Parameters`, { pascalCase: true });
587
+ const getOperationParametersTypeName = (
588
+ operation: ServiceOperation,
589
+ options: Pick<ServiceFactoryOptions, 'queryableWriteOperations'>,
590
+ desiredPrefix: 'query' | 'mutation'
591
+ ) => {
592
+ const operationPurpose = isSeparateParametersOperation(operation, options)
593
+ ? `-${desiredPrefix}`
594
+ : '';
595
+
596
+ return camelCase(`${operation.name}${operationPurpose}-Parameters`, {
597
+ pascalCase: true,
598
+ });
599
+ };
600
+
601
+ const isSeparateParametersOperation = (
602
+ operation: ServiceOperation,
603
+ options: Pick<ServiceFactoryOptions, 'queryableWriteOperations'>
604
+ ) =>
605
+ Boolean(
606
+ options.queryableWriteOperations &&
607
+ operation.requestBody &&
608
+ !isReadOnlyOperation(operation)
609
+ );
512
610
 
513
611
  const getOperationDataTypeName = (operation: ServiceOperation) =>
514
612
  camelCase(`${operation.name}-Data`, { pascalCase: true });
@@ -674,15 +772,22 @@ const getMethodSignatureNodes = (
674
772
 
675
773
  /**
676
774
  * Returns a list of all the modules that are imported by the operations.
677
- * @param operations
775
+ * @param operations The list of service operations to analyze
776
+ * @param options Options for controlling module imports generation.Options for controlling module imports generation.
678
777
  * @returns Record<moduleName, importSpecifierNames[]>
679
778
  */
680
- const getModuleTypeImports = (operations: ServiceOperation[]) => {
779
+ const getModuleTypeImports = (
780
+ operations: ServiceOperation[],
781
+ options: Pick<ServiceFactoryOptions, 'queryableWriteOperations'>
782
+ ) => {
681
783
  const nodes = [
682
- ...(operations.some((operation) => operation.method === 'get')
784
+ ...(operations.some(
785
+ (operation) =>
786
+ isReadOnlyOperation(operation) || options.queryableWriteOperations
787
+ )
683
788
  ? createServicesQueryOperationNodes()
684
789
  : []),
685
- ...(operations.some((operation) => operation.method !== 'get')
790
+ ...(operations.some((operation) => !isReadOnlyOperation(operation))
686
791
  ? createServicesMutationOperationNodes()
687
792
  : []),
688
793
  ];
@@ -720,12 +825,13 @@ const getModuleTypeImports = (operations: ServiceOperation[]) => {
720
825
  /**
721
826
  * Replaces generic types with operation types with named types.
722
827
  *
723
- * For example, replaces `TParams` and `TQueryFnData` will be
828
+ * For example, replaces `TQueryParams` and `TQueryFnData` will be
724
829
  * replaced with `GetEntitiesSchemaParameters` and `GetEntitiesSchemaData`.
725
830
  */
726
831
  function replaceGenericTypesWithOperationTypes<T extends ts.Node>(
727
832
  node: T[],
728
- operation: ServiceOperation
833
+ operation: ServiceOperation,
834
+ options: Pick<ServiceFactoryOptions, 'queryableWriteOperations'>
729
835
  ): T[] {
730
836
  const transformer =
731
837
  (context: ts.TransformationContext) => (rootNode: ts.Node) => {
@@ -735,8 +841,18 @@ function replaceGenericTypesWithOperationTypes<T extends ts.Node>(
735
841
 
736
842
  if (node.typeName.text === 'TSchema')
737
843
  newTypeName = getOperationSchemaTypeName(operation);
738
- else if (node.typeName.text === 'TParams')
739
- newTypeName = getOperationParametersTypeName(operation);
844
+ else if (node.typeName.text === 'TQueryParams')
845
+ newTypeName = getOperationParametersTypeName(
846
+ operation,
847
+ options,
848
+ 'query'
849
+ );
850
+ else if (node.typeName.text === 'TMutationParams')
851
+ newTypeName = getOperationParametersTypeName(
852
+ operation,
853
+ options,
854
+ 'mutation'
855
+ );
740
856
  else if (
741
857
  node.typeName.text === 'TOperationQueryFnData' ||
742
858
  node.typeName.text === 'TMutationData'
@@ -765,10 +881,55 @@ function replaceGenericTypesWithOperationTypes<T extends ts.Node>(
765
881
  }
766
882
 
767
883
  /**
768
- * Replaces `AreAllOptional<TParams>` with `TParams | void` if `TParams` is optional,
769
- * and with `TParams` when at least one parameter is required.
884
+ * Replaces `AreAllOptional<TQueryParams>` with `TQueryParams | void` if `TQueryParams` is optional,
885
+ * and with `TQueryParams` when at least one parameter or `body` (when --queryable-write-operations enabled) is required.
770
886
  */
771
887
  function reduceAreAllOptionalConditionalTParamsType<T extends ts.Node>(
888
+ node: T[],
889
+ operation: ServiceOperation,
890
+ options: Pick<ServiceFactoryOptions, 'queryableWriteOperations'>
891
+ ): T[] {
892
+ const transformer =
893
+ (context: ts.TransformationContext) => (rootNode: ts.Node) => {
894
+ function visit(node: ts.Node): ts.Node {
895
+ if (
896
+ ts.isConditionalTypeNode(node) &&
897
+ ts.isTypeReferenceNode(node.checkType) &&
898
+ ts.isIdentifier(node.checkType.typeName) &&
899
+ node.checkType.typeName.text === 'AreAllOptional' &&
900
+ node.checkType.typeArguments?.every((node) => {
901
+ return (
902
+ ts.isTypeReferenceNode(node) &&
903
+ ts.isIdentifier(node.typeName) &&
904
+ node.typeName.text === 'TQueryParams'
905
+ );
906
+ })
907
+ ) {
908
+ if (
909
+ operation.parameters?.some((parameter) => parameter.required) ||
910
+ (options.queryableWriteOperations &&
911
+ operation.requestBody?.required)
912
+ ) {
913
+ return node.falseType;
914
+ } else {
915
+ return node.trueType;
916
+ }
917
+ }
918
+ return ts.visitEachChild(node, visit, context);
919
+ }
920
+ return ts.visitNode(rootNode, visit);
921
+ };
922
+
923
+ const result = ts.transform(node, [transformer]);
924
+
925
+ return result.transformed as T[];
926
+ }
927
+
928
+ /**
929
+ * Replaces `AreAllOptional<TVariables>` with `TVariables | void` if `TVariables` is optional,
930
+ * and with `TVariables` when `body` is required.
931
+ */
932
+ function reduceAreAllOptionalConditionalTVariablesType<T extends ts.Node>(
772
933
  node: T[],
773
934
  operation: ServiceOperation
774
935
  ): T[] {
@@ -784,11 +945,11 @@ function reduceAreAllOptionalConditionalTParamsType<T extends ts.Node>(
784
945
  return (
785
946
  ts.isTypeReferenceNode(node) &&
786
947
  ts.isIdentifier(node.typeName) &&
787
- node.typeName.text === 'TParams'
948
+ node.typeName.text === 'TVariables'
788
949
  );
789
950
  })
790
951
  ) {
791
- if (operation.parameters?.some((parameter) => parameter.required)) {
952
+ if (operation.requestBody?.required) {
792
953
  return node.falseType;
793
954
  } else {
794
955
  return node.trueType;