From 0c1dcdbb6db54eb64786d624a5bd0fd006c08d3d Mon Sep 17 00:00:00 2001 From: Anthony Miller Date: Wed, 24 Apr 2024 12:27:58 -0700 Subject: [PATCH] Add validation for fieldmerging w/selection set init --- .../MockApolloCodegenConfiguration.swift | 4 +- .../ApolloCodegenTests.swift | 40 +++++++++++++++++++ .../ApolloCodegen+Errors.swift | 8 ++++ .../ConfigurationValidation.swift | 6 +++ 4 files changed, 57 insertions(+), 1 deletion(-) diff --git a/Tests/ApolloCodegenInternalTestHelpers/MockApolloCodegenConfiguration.swift b/Tests/ApolloCodegenInternalTestHelpers/MockApolloCodegenConfiguration.swift index 393a7d60e..37e38ca84 100644 --- a/Tests/ApolloCodegenInternalTestHelpers/MockApolloCodegenConfiguration.swift +++ b/Tests/ApolloCodegenInternalTestHelpers/MockApolloCodegenConfiguration.swift @@ -30,6 +30,7 @@ extension ApolloCodegenConfiguration { public static func mock( _ moduleType: ApolloCodegenConfiguration.SchemaTypesFileOutput.ModuleType, options: ApolloCodegenConfiguration.OutputOptions = .init(), + experimentalFeatures: ExperimentalFeatures = .init(), schemaNamespace: String = "TestSchema", to path: String = "MockModulePath" ) -> Self { @@ -42,7 +43,8 @@ extension ApolloCodegenConfiguration { output: .init( schemaTypes: .init(path: path, moduleType: moduleType) ), - options: options + options: options, + experimentalFeatures: experimentalFeatures ) } } diff --git a/Tests/ApolloCodegenTests/ApolloCodegenTests.swift b/Tests/ApolloCodegenTests/ApolloCodegenTests.swift index 431c90005..3475527d4 100644 --- a/Tests/ApolloCodegenTests/ApolloCodegenTests.swift +++ b/Tests/ApolloCodegenTests/ApolloCodegenTests.swift @@ -2374,6 +2374,46 @@ class ApolloCodegenTests: XCTestCase { }) } + func test__validation__givenFieldMerging_notAll_andSelectionSetInitializers_enabled_shouldThrowError() throws { + // given + let fieldMergingOptions: [ApolloCodegenConfiguration.FieldMerging] = [ + .none, + .ancestors, + .namedFragments, + .siblings, + [.ancestors, .namedFragments], + [.siblings, .ancestors], + [.siblings, .namedFragments] + ] + let initializerOptions: [ApolloCodegenConfiguration.SelectionSetInitializers] = [ + .all, + .localCacheMutations, + .operations, + .namedFragments, + .fragment(named: "TestFragment"), + [.operations, .localCacheMutations] + ] + + for fieldMergingOption in fieldMergingOptions { + for initializerOption in initializerOptions { + + let config = ApolloCodegenConfiguration.mock( + .other, + options: .init( + selectionSetInitializers: initializerOption + ), + experimentalFeatures: .init( + fieldMerging: fieldMergingOption + ) + ) + + // then + expect(try ApolloCodegen._validate(config: config)) + .to(throwError(ApolloCodegen.Error.fieldMergingIncompatibility)) + } + } + } + // MARK: Path Match Exclusion Tests func test__match__givenFilesInSpecialExcludedPaths_shouldNotReturnExcludedPaths() throws { diff --git a/apollo-ios-codegen/Sources/ApolloCodegenLib/ApolloCodegen+Errors.swift b/apollo-ios-codegen/Sources/ApolloCodegenLib/ApolloCodegen+Errors.swift index 0c6b0ce79..ed20dd488 100644 --- a/apollo-ios-codegen/Sources/ApolloCodegenLib/ApolloCodegen+Errors.swift +++ b/apollo-ios-codegen/Sources/ApolloCodegenLib/ApolloCodegen+Errors.swift @@ -17,6 +17,7 @@ extension ApolloCodegen { case invalidConfiguration(message: String) case invalidSchemaName(_ name: String, message: String) case targetNameConflict(name: String) + case fieldMergingIncompatibility public var errorDescription: String? { switch self { @@ -52,6 +53,13 @@ extension ApolloCodegen { Target name '\(name)' conflicts with a reserved library name. Please choose a different \ target name. """ + case .fieldMergingIncompatibility: + return """ + Options for disabling 'fieldMerging' and enabling 'selectionSetInitializers' are + incompatible. + + Please set either 'fieldMerging' to 'all' or 'selectionSetInitializers' to be empty. + """ } } } diff --git a/apollo-ios-codegen/Sources/ApolloCodegenLib/ConfigurationValidation.swift b/apollo-ios-codegen/Sources/ApolloCodegenLib/ConfigurationValidation.swift index 00281f825..dc35746a0 100644 --- a/apollo-ios-codegen/Sources/ApolloCodegenLib/ConfigurationValidation.swift +++ b/apollo-ios-codegen/Sources/ApolloCodegenLib/ConfigurationValidation.swift @@ -21,6 +21,12 @@ extension ApolloCodegen.ConfigurationContext { """) } + guard self.experimentalFeatures.fieldMerging == .all || + self.options.selectionSetInitializers == [] + else { + throw ApolloCodegen.Error.fieldMergingIncompatibility + } + guard !SwiftKeywords.DisallowedSchemaNamespaceNames.contains(self.schemaNamespace.lowercased()) else {