From 1db9634d8b2d574563b968c82de811139d0efe66 Mon Sep 17 00:00:00 2001 From: Pasin Suriyentrakorn Date: Fri, 7 Aug 2026 16:23:31 -0700 Subject: [PATCH 1/3] CBL-8722: Generate the Swift private module maps from header list templates Problem: - The CouchbaseLiteSwift_Private module maps are hand-maintained per edition in two repos, so the editions can drift apart if we forget to update both, and the CE repo's CI cannot verify the EE copy. Solution: - Generate both editions' module maps in the CE repo from header list templates, following the Objective-C/Exports pattern. Changes: - Add Swift/ModuleMap/ header list templates and generate_private_modulemap.sh; the EE module map is the CE header list plus the EE additions. - Point CBL_Swift / CBL_EE_Swift xcconfigs at the generated module maps; the EE repo no longer hosts a module map. - Verify the generated files are up to date in pull_request_build_test.sh. - Enable MemberImportVisibility so a Swift file using a type it does not import itself fails to build (catches missing private module imports). - Strip the private module map from the framework in Release builds only. --- AGENTS.md | 5 +- CouchbaseLite.xcodeproj/project.pbxproj | 30 +++- Scripts/pull_request_build_test.sh | 4 + Scripts/remove_private_module.sh | 13 ++ .../CouchbaseLiteSwift-EE.private.txt | 46 +++++ .../ModuleMap/CouchbaseLiteSwift.private.txt | 99 +++++++++++ .../CouchbaseLiteSwift-EE.private.modulemap | 161 ++++++++++++++++++ .../CouchbaseLiteSwift-EE.private.txt | 46 +++++ .../CouchbaseLiteSwift.private.modulemap | 5 +- Swift/ModuleMap/generate_private_modulemap.sh | 97 +++++++++++ xcconfigs/CBL_EE_Swift.xcconfig | 2 +- xcconfigs/CBL_Swift.xcconfig | 2 +- xcconfigs/Project.xcconfig | 4 + 13 files changed, 505 insertions(+), 9 deletions(-) create mode 100644 Swift/ModuleMap/CouchbaseLiteSwift-EE.private.txt create mode 100644 Swift/ModuleMap/CouchbaseLiteSwift.private.txt create mode 100644 Swift/ModuleMap/Generated/CouchbaseLiteSwift-EE.private.modulemap create mode 100644 Swift/ModuleMap/Generated/CouchbaseLiteSwift-EE.private.txt rename Swift/{ => ModuleMap/Generated}/CouchbaseLiteSwift.private.modulemap (94%) create mode 100755 Swift/ModuleMap/generate_private_modulemap.sh diff --git a/AGENTS.md b/AGENTS.md index 4f96c6b8f..f3e8cd964 100644 --- a/AGENTS.md +++ b/AGENTS.md @@ -44,8 +44,8 @@ iOS app-hosted test schemes: - Community Edition code must not depend on Enterprise Edition code. - Enterprise Edition code may extend Community Edition behavior through EE sources or `COUCHBASE_ENTERPRISE` guards. - Swift APIs mirror Obj-C APIs; public API changes usually require updates in both layers. -- Swift-to-Obj-C bridging is controlled by `Swift/CouchbaseLiteSwift.private.modulemap` and `../couchbase-lite-ios-ee/Sources/Swift/CouchbaseLiteSwift.private.modulemap`. -- If a new Obj-C header must be visible to Swift, update the appropriate private module map. +- Swift-to-Obj-C bridging is controlled by the generated private module maps in `Swift/ModuleMap/Generated/` (both editions; generated from the header list templates in `Swift/ModuleMap/`). +- To make a new Obj-C header visible to Swift: add a CE header to `Swift/ModuleMap/CouchbaseLiteSwift.private.txt`, or an EE header to `Swift/ModuleMap/CouchbaseLiteSwift-EE.private.txt`, then run `Swift/ModuleMap/generate_private_modulemap.sh` and commit the regenerated module maps. - Public Obj-C exported symbols are defined by `Objective-C/Exports/CBL.txt` and `Objective-C/Exports/CBL_EE.txt`. ## Guardrails @@ -53,6 +53,7 @@ iOS app-hosted test schemes: - Do not hand-edit `CouchbaseLite.xcodeproj/project.pbxproj`. - If a task requires new files or project membership changes, ask the developer to make them in Xcode. - Do not edit generated export files in `Objective-C/Exports/Generated/` directly. Update the templates and run `Objective-C/Exports/generate_exports.sh` instead. +- Do not edit the generated private module maps in `ModuleMap/Generated/` directly. Update the header list templates and run `Swift/ModuleMap/generate_private_modulemap.sh` instead (see Architecture Notes). ## Build and Test diff --git a/CouchbaseLite.xcodeproj/project.pbxproj b/CouchbaseLite.xcodeproj/project.pbxproj index a6e6a4bc0..c6d3739cf 100644 --- a/CouchbaseLite.xcodeproj/project.pbxproj +++ b/CouchbaseLite.xcodeproj/project.pbxproj @@ -2461,6 +2461,9 @@ 40AA72972C28B1A3007FB1E0 /* VectorSearchTest+Lazy.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = "VectorSearchTest+Lazy.m"; sourceTree = ""; }; 40AA72A12C28B1F2007FB1E0 /* VectorSearchTest.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = VectorSearchTest.h; sourceTree = ""; }; 40C5FD5A2B9946E6004BFD3B /* CBLVectorIndexTypes.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = CBLVectorIndexTypes.h; sourceTree = ""; }; + 40CC4B76302BE6D30002386D /* CouchbaseLiteSwift-EE.private.txt */ = {isa = PBXFileReference; lastKnownFileType = text; path = "CouchbaseLiteSwift-EE.private.txt"; sourceTree = ""; }; + 40CC4B77302BE6E40002386D /* CouchbaseLiteSwift.private.txt */ = {isa = PBXFileReference; lastKnownFileType = text; path = CouchbaseLiteSwift.private.txt; sourceTree = ""; }; + 40CC4B78302BE6EF0002386D /* CouchbaseLiteSwift-EE.private.txt */ = {isa = PBXFileReference; lastKnownFileType = text; path = "CouchbaseLiteSwift-EE.private.txt"; sourceTree = ""; }; 40D6BCBF2DDD183000F209D7 /* MultipeerReplicatorConfiguration.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MultipeerReplicatorConfiguration.swift; sourceTree = ""; }; 40D6BCC12DDD191C00F209D7 /* MultipeerCertificateAuthenticator.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MultipeerCertificateAuthenticator.swift; sourceTree = ""; }; 40D6BCC32DDD19D900F209D7 /* PeerID.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = PeerID.swift; sourceTree = ""; }; @@ -2496,12 +2499,13 @@ 40E46B122DD6A7B5007E495D /* CBLReplicatorStatus+Internal.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = "CBLReplicatorStatus+Internal.h"; sourceTree = ""; }; 40E46B172DD6A808007E495D /* CBLConflictResolverService.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = CBLConflictResolverService.h; sourceTree = ""; }; 40E46B182DD6A808007E495D /* CBLConflictResolverService.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = CBLConflictResolverService.m; sourceTree = ""; }; - 40E905462B5B6D9D00EDF483 /* CouchbaseLiteSwift.private.modulemap */ = {isa = PBXFileReference; lastKnownFileType = "sourcecode.module-map"; path = CouchbaseLiteSwift.private.modulemap; sourceTree = ""; }; 40ECAE852E0E08CC00C109A6 /* Precondition.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Precondition.swift; sourceTree = ""; }; 40ECAE882E0E0B0F00C109A6 /* CBLPrecondition.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = CBLPrecondition.h; sourceTree = ""; }; 40ECAE892E0E0B0F00C109A6 /* CBLPrecondition.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = CBLPrecondition.m; sourceTree = ""; }; 40EF68102B71891A00F0CB50 /* remove_private_module.sh */ = {isa = PBXFileReference; lastKnownFileType = text.script.sh; path = remove_private_module.sh; sourceTree = ""; }; 40EF690A2B77564000F0CB50 /* PrivacyInfo.xcprivacy */ = {isa = PBXFileReference; lastKnownFileType = text.xml; path = PrivacyInfo.xcprivacy; sourceTree = ""; }; + 40F52B1D3026ED0F009C5F9E /* CouchbaseLiteSwift.private.modulemap */ = {isa = PBXFileReference; lastKnownFileType = "sourcecode.module-map"; path = CouchbaseLiteSwift.private.modulemap; sourceTree = ""; }; + 40F52B203026ED0F009C5F9E /* generate_private_modulemap.sh */ = {isa = PBXFileReference; lastKnownFileType = text.script.sh; path = generate_private_modulemap.sh; sourceTree = ""; }; 40FC1AA32B9286E700394276 /* CBLEncryptionKey.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = CBLEncryptionKey.m; sourceTree = ""; }; 40FC1AA42B9286E700394276 /* CBLDatabase+Encryption.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = "CBLDatabase+Encryption.h"; sourceTree = ""; }; 40FC1AA52B9286E700394276 /* CBLDatabaseConfiguration+Encryption.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = "CBLDatabaseConfiguration+Encryption.h"; sourceTree = ""; }; @@ -2587,7 +2591,6 @@ 40FC1C402B928C1600394276 /* ListenerCertificateAuthenticator.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = ListenerCertificateAuthenticator.swift; sourceTree = ""; }; 40FC1C412B928C1600394276 /* ListenerPasswordAuthenticator.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = ListenerPasswordAuthenticator.swift; sourceTree = ""; }; 40FC1C422B928C1600394276 /* ListenerAuthenticator.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = ListenerAuthenticator.swift; sourceTree = ""; }; - 40FC1C432B928C1600394276 /* CouchbaseLiteSwift.private.modulemap */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = "sourcecode.module-map"; path = CouchbaseLiteSwift.private.modulemap; sourceTree = ""; }; 40FC1C452B928C1600394276 /* MessageEndpointConnection.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = MessageEndpointConnection.swift; sourceTree = ""; }; 40FC1C462B928C1600394276 /* ClientCertificateAuthenticator.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = ClientCertificateAuthenticator.swift; sourceTree = ""; }; 40FC1C472B928C1600394276 /* Message.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = Message.swift; sourceTree = ""; }; @@ -3243,8 +3246,8 @@ 409389E72D4AB7DE00691393 /* LogSink */, 40D6BCC62DDD2C2D00F209D7 /* Support */, 27BE3B491E4E45CB0012B74A /* Tests */, + 40F52B213026ED0F009C5F9E /* ModuleMap */, 275F92761E4D30A4007FD5A2 /* CouchbaseLiteSwift.h */, - 40E905462B5B6D9D00EDF483 /* CouchbaseLiteSwift.private.modulemap */, 275F92771E4D30A4007FD5A2 /* Info.plist */, ); path = Swift; @@ -3447,6 +3450,26 @@ path = Resources; sourceTree = ""; }; + 40F52B1E3026ED0F009C5F9E /* Generated */ = { + isa = PBXGroup; + children = ( + 40F52B1D3026ED0F009C5F9E /* CouchbaseLiteSwift.private.modulemap */, + 40CC4B78302BE6EF0002386D /* CouchbaseLiteSwift-EE.private.txt */, + ); + path = Generated; + sourceTree = ""; + }; + 40F52B213026ED0F009C5F9E /* ModuleMap */ = { + isa = PBXGroup; + children = ( + 40F52B1E3026ED0F009C5F9E /* Generated */, + 40CC4B77302BE6E40002386D /* CouchbaseLiteSwift.private.txt */, + 40CC4B76302BE6D30002386D /* CouchbaseLiteSwift-EE.private.txt */, + 40F52B203026ED0F009C5F9E /* generate_private_modulemap.sh */, + ); + path = ModuleMap; + sourceTree = ""; + }; 40FC1AA02B9286E700394276 /* Objective-C */ = { isa = PBXGroup; children = ( @@ -3677,7 +3700,6 @@ 40D6BCBE2DDD17FF00F209D7 /* Multipeer */, 40FC1C4C2B928C1600394276 /* Query */, 40FC1C442B928C1600394276 /* Replicator */, - 40FC1C432B928C1600394276 /* CouchbaseLiteSwift.private.modulemap */, ); name = Swift; path = "../couchbase-lite-ios-ee/Sources/Swift"; diff --git a/Scripts/pull_request_build_test.sh b/Scripts/pull_request_build_test.sh index e57bb7b2d..91b7efce4 100755 --- a/Scripts/pull_request_build_test.sh +++ b/Scripts/pull_request_build_test.sh @@ -81,6 +81,10 @@ else cd couchbase-lite-ios fi +# Verify that the generated private module maps are in sync with their header +# list templates (see Swift/ModuleMap/generate_private_modulemap.sh). +sh Swift/ModuleMap/generate_private_modulemap.sh --check + # Minimum Matrix: # - Run swift tests on iOS platform # - Run objective-C tests on macOS platform diff --git a/Scripts/remove_private_module.sh b/Scripts/remove_private_module.sh index c5e96a178..541151efd 100755 --- a/Scripts/remove_private_module.sh +++ b/Scripts/remove_private_module.sh @@ -2,6 +2,19 @@ set -e +# Only strip the private module from Release builds used for packaging. +# Development (Debug) builds must keep the full private modulemap in the built +# framework; the Xcode indexer resolves CouchbaseLiteSwift_Private from the +# built products, and stripping it there makes all private Obj-C classes +# unresolvable in the editor. +case "${CONFIGURATION}" in + Release*) ;; + *) + echo "Skipping private module removal for configuration '${CONFIGURATION}'" + exit 0 + ;; +esac + FRAMEWORK_DIR=${TARGET_BUILD_DIR}/${PRODUCT_NAME}${WRAPPER_SUFFIX} # Remove private headers from module.private.modulemap: diff --git a/Swift/ModuleMap/CouchbaseLiteSwift-EE.private.txt b/Swift/ModuleMap/CouchbaseLiteSwift-EE.private.txt new file mode 100644 index 000000000..4fcd7fbbd --- /dev/null +++ b/Swift/ModuleMap/CouchbaseLiteSwift-EE.private.txt @@ -0,0 +1,46 @@ +# EE-only header list, appended to the CE header list in the generated EE +# module map. Lines starting with '#' are template comments and are not copied +# to the output. +# + // Enterprise Edition: + header "CBLClientCertificateAuthenticator.h" + header "CBLCoreMLPredictiveModel.h" + header "CBLDatabase+Encryption.h" + header "CBLDatabase+Prediction.h" + header "CBLDatabaseConfiguration+Encryption.h" + header "CBLDatabaseEndpoint.h" + header "CBLEncryptionKey.h" + header "CBLExtension.h" + header "CBLIndexBuilder+Prediction.h" + header "CBLIndexUpdater.h" + header "CBLListenerAuthenticator.h" + header "CBLListenerCertificateAuthenticator.h" + header "CBLListenerPasswordAuthenticator.h" + header "CBLMessage.h" + header "CBLMessageEndpoint.h" + header "CBLMessageEndpointConnection.h" + header "CBLMessageEndpointListener.h" + header "CBLMessagingError.h" + header "CBLMultipeerCertificateAuthenticator.h" + header "CBLMultipeerCollectionConfiguration.h" + header "CBLMultipeerEventTypes.h" + header "CBLMultipeerReplicator.h" + header "CBLMultipeerReplicatorConfiguration.h" + header "CBLMultipeerTransportTypes.h" + header "CBLPeerID.h" + header "CBLPeerInfo.h" + header "CBLPrediction.h" + header "CBLPrediction+Swift.h" + header "CBLPredictiveIndex.h" + header "CBLProtocolType.h" + header "CBLQueryFunction+Prediction.h" + header "CBLQueryFunction+Vector.h" + header "CBLReplicatorConfiguration+ServerCert.h" + header "CBLTLSIdentity.h" + header "CBLTLSIdentity+Swift.h" + header "CBLURLEndpointListener.h" + header "CBLURLEndpointListener+Swift.h" + header "CBLURLEndpointListenerConfiguration.h" + header "CBLVectorEncoding.h" + header "CBLVectorIndexConfiguration.h" + header "CBLVectorIndexTypes.h" diff --git a/Swift/ModuleMap/CouchbaseLiteSwift.private.txt b/Swift/ModuleMap/CouchbaseLiteSwift.private.txt new file mode 100644 index 000000000..c7fbe6cc0 --- /dev/null +++ b/Swift/ModuleMap/CouchbaseLiteSwift.private.txt @@ -0,0 +1,99 @@ +# Header list for the CouchbaseLiteSwift_Private module (CE). +# Lines starting with '#' are template comments and are not copied to the output. +# Everything else is inserted verbatim into the generated module maps by +# generate_private_modulemap.sh in this directory. +# + header "CBLArray.h" + header "CBLArrayFragment.h" + header "CBLArrayIndexConfiguration.h" + header "CBLAuthenticator.h" + header "CBLBasicAuthenticator.h" + header "CBLBlob.h" + header "CBLCollection.h" + header "CBLCollectionChange.h" + header "CBLCollectionChangeObservable.h" + header "CBLCollectionConfiguration.h" + header "CBLConflict.h" + header "CBLConflictResolver.h" + header "CBLConsoleLogSink.h" + header "CBLCustomLogSink.h" + header "CBLDatabase.h" + header "CBLDatabaseConfiguration.h" + header "CBLDictionary.h" + header "CBLDictionaryFragment.h" + header "CBLDocument.h" + header "CBLDocumentChange.h" + header "CBLDocumentFlags.h" + header "CBLDocumentFragment.h" + header "CBLDocumentReplication.h" + header "CBLEdition.h" + header "CBLEncoder.h" + header "CBLEndpoint.h" + header "CBLErrors.h" + header "CBLFileLogSink.h" + header "CBLFragment.h" + header "CBLFullTextIndex.h" + header "CBLFullTextIndexConfiguration.h" + header "CBLIndex.h" + header "CBLIndexable.h" + header "CBLIndexBuilder.h" + header "CBLIndexConfiguration.h" + header "CBLListenerToken.h" + header "CBLLogSinks.h" + header "CBLLogTypes.h" + header "CBLQueryChange.h" + header "CBLMutableArray.h" + header "CBLMutableArrayFragment.h" + header "CBLMutableDictionary.h" + header "CBLMutableDictionaryFragment.h" + header "CBLMutableDocument.h" + header "CBLMutableFragment.h" + header "CBLNewDictionary.h" + header "CBLQuery.h" + header "CBLQuery+JSON.h" + header "CBLQueryArrayExpression.h" + header "CBLQueryArrayFunction.h" + header "CBLQueryBuilder.h" + header "CBLQueryCollation.h" + header "CBLQueryDataSource.h" + header "CBLQueryExpression.h" + header "CBLQueryFactory.h" + header "CBLQueryFunction.h" + header "CBLQueryFullTextFunction.h" + header "CBLQueryIndex.h" + header "CBLQueryJoin.h" + header "CBLQueryLimit.h" + header "CBLQueryMeta.h" + header "CBLQueryOrdering.h" + header "CBLQueryParameters.h" + header "CBLQueryResult.h" + header "CBLQueryResultSet.h" + header "CBLQuerySelectResult.h" + header "CBLQueryVariableExpression.h" + header "CBLReplicator.h" + header "CBLReplicatorChange.h" + header "CBLReplicatorConfiguration.h" + header "CBLReplicatorStatus.h" + header "CBLReplicatorTypes.h" + header "CBLScope.h" + header "CBLSessionAuthenticator.h" + header "CBLURLEndpoint.h" + header "CBLValueIndex.h" + header "CBLValueIndexConfiguration.h" + header "CBLCollectionTypes.h" + header "CBLDefaults.h" + header "CBLQueryFullTextIndexExpressionProtocol.h" + + // Internal + header "CBLQueryFullTextIndexExpression.h" + header "CBLPrecondition.h" + + // Swift Extensions: + header "CBLArray+Swift.h" + header "CBLBlob+Swift.h" + header "CBLCollection+Swift.h" + header "CBLDatabase+Swift.h" + header "CBLDictionary+Swift.h" + header "CBLConflictResolverBridge.h" + header "CBLCollectionConfiguration+Swift.h" + header "CBLLog+Swift.h" diff --git a/Swift/ModuleMap/Generated/CouchbaseLiteSwift-EE.private.modulemap b/Swift/ModuleMap/Generated/CouchbaseLiteSwift-EE.private.modulemap new file mode 100644 index 000000000..102956bed --- /dev/null +++ b/Swift/ModuleMap/Generated/CouchbaseLiteSwift-EE.private.modulemap @@ -0,0 +1,161 @@ +// +// CouchbaseLiteSwift-EE.private.modulemap +// CouchbaseLite +// +// Copyright (c) 2026 Couchbase, Inc All rights reserved. +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// GENERATED BY Swift/ModuleMap/generate_private_modulemap.sh -- DO NOT EDIT DIRECTLY. +// Edit the header list templates and regenerate. +// + +framework module CouchbaseLiteSwift_Private { + header "CBLArray.h" + header "CBLArrayFragment.h" + header "CBLArrayIndexConfiguration.h" + header "CBLAuthenticator.h" + header "CBLBasicAuthenticator.h" + header "CBLBlob.h" + header "CBLCollection.h" + header "CBLCollectionChange.h" + header "CBLCollectionChangeObservable.h" + header "CBLCollectionConfiguration.h" + header "CBLConflict.h" + header "CBLConflictResolver.h" + header "CBLConsoleLogSink.h" + header "CBLCustomLogSink.h" + header "CBLDatabase.h" + header "CBLDatabaseConfiguration.h" + header "CBLDictionary.h" + header "CBLDictionaryFragment.h" + header "CBLDocument.h" + header "CBLDocumentChange.h" + header "CBLDocumentFlags.h" + header "CBLDocumentFragment.h" + header "CBLDocumentReplication.h" + header "CBLEdition.h" + header "CBLEncoder.h" + header "CBLEndpoint.h" + header "CBLErrors.h" + header "CBLFileLogSink.h" + header "CBLFragment.h" + header "CBLFullTextIndex.h" + header "CBLFullTextIndexConfiguration.h" + header "CBLIndex.h" + header "CBLIndexable.h" + header "CBLIndexBuilder.h" + header "CBLIndexConfiguration.h" + header "CBLListenerToken.h" + header "CBLLogSinks.h" + header "CBLLogTypes.h" + header "CBLQueryChange.h" + header "CBLMutableArray.h" + header "CBLMutableArrayFragment.h" + header "CBLMutableDictionary.h" + header "CBLMutableDictionaryFragment.h" + header "CBLMutableDocument.h" + header "CBLMutableFragment.h" + header "CBLNewDictionary.h" + header "CBLQuery.h" + header "CBLQuery+JSON.h" + header "CBLQueryArrayExpression.h" + header "CBLQueryArrayFunction.h" + header "CBLQueryBuilder.h" + header "CBLQueryCollation.h" + header "CBLQueryDataSource.h" + header "CBLQueryExpression.h" + header "CBLQueryFactory.h" + header "CBLQueryFunction.h" + header "CBLQueryFullTextFunction.h" + header "CBLQueryIndex.h" + header "CBLQueryJoin.h" + header "CBLQueryLimit.h" + header "CBLQueryMeta.h" + header "CBLQueryOrdering.h" + header "CBLQueryParameters.h" + header "CBLQueryResult.h" + header "CBLQueryResultSet.h" + header "CBLQuerySelectResult.h" + header "CBLQueryVariableExpression.h" + header "CBLReplicator.h" + header "CBLReplicatorChange.h" + header "CBLReplicatorConfiguration.h" + header "CBLReplicatorStatus.h" + header "CBLReplicatorTypes.h" + header "CBLScope.h" + header "CBLSessionAuthenticator.h" + header "CBLURLEndpoint.h" + header "CBLValueIndex.h" + header "CBLValueIndexConfiguration.h" + header "CBLCollectionTypes.h" + header "CBLDefaults.h" + header "CBLQueryFullTextIndexExpressionProtocol.h" + + // Internal + header "CBLQueryFullTextIndexExpression.h" + header "CBLPrecondition.h" + + // Swift Extensions: + header "CBLArray+Swift.h" + header "CBLBlob+Swift.h" + header "CBLCollection+Swift.h" + header "CBLDatabase+Swift.h" + header "CBLDictionary+Swift.h" + header "CBLConflictResolverBridge.h" + header "CBLCollectionConfiguration+Swift.h" + header "CBLLog+Swift.h" + + // Enterprise Edition: + header "CBLClientCertificateAuthenticator.h" + header "CBLCoreMLPredictiveModel.h" + header "CBLDatabase+Encryption.h" + header "CBLDatabase+Prediction.h" + header "CBLDatabaseConfiguration+Encryption.h" + header "CBLDatabaseEndpoint.h" + header "CBLEncryptionKey.h" + header "CBLExtension.h" + header "CBLIndexBuilder+Prediction.h" + header "CBLIndexUpdater.h" + header "CBLListenerAuthenticator.h" + header "CBLListenerCertificateAuthenticator.h" + header "CBLListenerPasswordAuthenticator.h" + header "CBLMessage.h" + header "CBLMessageEndpoint.h" + header "CBLMessageEndpointConnection.h" + header "CBLMessageEndpointListener.h" + header "CBLMessagingError.h" + header "CBLMultipeerCertificateAuthenticator.h" + header "CBLMultipeerCollectionConfiguration.h" + header "CBLMultipeerEventTypes.h" + header "CBLMultipeerReplicator.h" + header "CBLMultipeerReplicatorConfiguration.h" + header "CBLMultipeerTransportTypes.h" + header "CBLPeerID.h" + header "CBLPeerInfo.h" + header "CBLPrediction.h" + header "CBLPrediction+Swift.h" + header "CBLPredictiveIndex.h" + header "CBLProtocolType.h" + header "CBLQueryFunction+Prediction.h" + header "CBLQueryFunction+Vector.h" + header "CBLReplicatorConfiguration+ServerCert.h" + header "CBLTLSIdentity.h" + header "CBLTLSIdentity+Swift.h" + header "CBLURLEndpointListener.h" + header "CBLURLEndpointListener+Swift.h" + header "CBLURLEndpointListenerConfiguration.h" + header "CBLVectorEncoding.h" + header "CBLVectorIndexConfiguration.h" + header "CBLVectorIndexTypes.h" +} diff --git a/Swift/ModuleMap/Generated/CouchbaseLiteSwift-EE.private.txt b/Swift/ModuleMap/Generated/CouchbaseLiteSwift-EE.private.txt new file mode 100644 index 000000000..4fcd7fbbd --- /dev/null +++ b/Swift/ModuleMap/Generated/CouchbaseLiteSwift-EE.private.txt @@ -0,0 +1,46 @@ +# EE-only header list, appended to the CE header list in the generated EE +# module map. Lines starting with '#' are template comments and are not copied +# to the output. +# + // Enterprise Edition: + header "CBLClientCertificateAuthenticator.h" + header "CBLCoreMLPredictiveModel.h" + header "CBLDatabase+Encryption.h" + header "CBLDatabase+Prediction.h" + header "CBLDatabaseConfiguration+Encryption.h" + header "CBLDatabaseEndpoint.h" + header "CBLEncryptionKey.h" + header "CBLExtension.h" + header "CBLIndexBuilder+Prediction.h" + header "CBLIndexUpdater.h" + header "CBLListenerAuthenticator.h" + header "CBLListenerCertificateAuthenticator.h" + header "CBLListenerPasswordAuthenticator.h" + header "CBLMessage.h" + header "CBLMessageEndpoint.h" + header "CBLMessageEndpointConnection.h" + header "CBLMessageEndpointListener.h" + header "CBLMessagingError.h" + header "CBLMultipeerCertificateAuthenticator.h" + header "CBLMultipeerCollectionConfiguration.h" + header "CBLMultipeerEventTypes.h" + header "CBLMultipeerReplicator.h" + header "CBLMultipeerReplicatorConfiguration.h" + header "CBLMultipeerTransportTypes.h" + header "CBLPeerID.h" + header "CBLPeerInfo.h" + header "CBLPrediction.h" + header "CBLPrediction+Swift.h" + header "CBLPredictiveIndex.h" + header "CBLProtocolType.h" + header "CBLQueryFunction+Prediction.h" + header "CBLQueryFunction+Vector.h" + header "CBLReplicatorConfiguration+ServerCert.h" + header "CBLTLSIdentity.h" + header "CBLTLSIdentity+Swift.h" + header "CBLURLEndpointListener.h" + header "CBLURLEndpointListener+Swift.h" + header "CBLURLEndpointListenerConfiguration.h" + header "CBLVectorEncoding.h" + header "CBLVectorIndexConfiguration.h" + header "CBLVectorIndexTypes.h" diff --git a/Swift/CouchbaseLiteSwift.private.modulemap b/Swift/ModuleMap/Generated/CouchbaseLiteSwift.private.modulemap similarity index 94% rename from Swift/CouchbaseLiteSwift.private.modulemap rename to Swift/ModuleMap/Generated/CouchbaseLiteSwift.private.modulemap index cd546f86c..448ddc4de 100644 --- a/Swift/CouchbaseLiteSwift.private.modulemap +++ b/Swift/ModuleMap/Generated/CouchbaseLiteSwift.private.modulemap @@ -2,7 +2,7 @@ // CouchbaseLiteSwift.private.modulemap // CouchbaseLite // -// Copyright (c) 2024 Couchbase, Inc All rights reserved. +// Copyright (c) 2026 Couchbase, Inc All rights reserved. // // Licensed under the Apache License, Version 2.0 (the "License"); // you may not use this file except in compliance with the License. @@ -16,6 +16,9 @@ // See the License for the specific language governing permissions and // limitations under the License. // +// GENERATED BY Swift/ModuleMap/generate_private_modulemap.sh -- DO NOT EDIT DIRECTLY. +// Edit the header list templates and regenerate. +// framework module CouchbaseLiteSwift_Private { header "CBLArray.h" diff --git a/Swift/ModuleMap/generate_private_modulemap.sh b/Swift/ModuleMap/generate_private_modulemap.sh new file mode 100755 index 000000000..b0e5a8c9f --- /dev/null +++ b/Swift/ModuleMap/generate_private_modulemap.sh @@ -0,0 +1,97 @@ +#! /bin/bash -e + +# Generates the CE and EE private module maps from the header list templates +# (same pattern as Objective-C/Exports/generate_exports.sh): +# CouchbaseLiteSwift.private.txt -> Generated/CouchbaseLiteSwift.private.modulemap (CE) +# + CouchbaseLiteSwift-EE.private.txt -> Generated/CouchbaseLiteSwift-EE.private.modulemap (EE) +# +# Template lines starting with '#' are not copied; all other lines are inserted +# verbatim inside the module declaration. The EE module map is the CE header +# list plus the EE-only headers. +# +# Usage: +# generate_private_modulemap.sh Regenerate; commit the results. +# generate_private_modulemap.sh --check Verify outputs are up to date (CI). + +CHECK="" +if [ "$1" == "--check" ]; then + CHECK=YES +elif [ -n "$1" ]; then + echo "Usage: $0 [--check]" >&2 + exit 2 +fi + +SCRIPT_DIR=$(cd "$(dirname "$0")" && pwd) + +CE_TEMPLATE="$SCRIPT_DIR/CouchbaseLiteSwift.private.txt" +EE_TEMPLATE="$SCRIPT_DIR/CouchbaseLiteSwift-EE.private.txt" +CE_MODULEMAP="$SCRIPT_DIR/Generated/CouchbaseLiteSwift.private.modulemap" +EE_MODULEMAP="$SCRIPT_DIR/Generated/CouchbaseLiteSwift-EE.private.modulemap" + +for t in "$CE_TEMPLATE" "$EE_TEMPLATE"; do + if [ ! -f "$t" ]; then + echo "Template not found: $t" >&2 + exit 1 + fi +done + +emit_header() { + echo "//" + echo "// $1" + echo "// CouchbaseLite" + echo "//" + echo "// Copyright (c) $(date +%Y) Couchbase, Inc All rights reserved." + echo "//" + echo "// Licensed under the Apache License, Version 2.0 (the \"License\");" + echo "// you may not use this file except in compliance with the License." + echo "// You may obtain a copy of the License at" + echo "//" + echo "// http://www.apache.org/licenses/LICENSE-2.0" + echo "//" + echo "// Unless required by applicable law or agreed to in writing, software" + echo "// distributed under the License is distributed on an \"AS IS\" BASIS," + echo "// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied." + echo "// See the License for the specific language governing permissions and" + echo "// limitations under the License." + echo "//" + echo "// GENERATED BY Swift/ModuleMap/generate_private_modulemap.sh -- DO NOT EDIT DIRECTLY." + echo "// Edit the header list templates and regenerate." + echo "//" + echo "" +} + +generate_ce() { + emit_header "CouchbaseLiteSwift.private.modulemap" + echo "framework module CouchbaseLiteSwift_Private {" + grep -v '^#' "$CE_TEMPLATE" + echo "}" +} + +generate_ee() { + emit_header "CouchbaseLiteSwift-EE.private.modulemap" + echo "framework module CouchbaseLiteSwift_Private {" + grep -v '^#' "$CE_TEMPLATE" + echo "" + grep -v '^#' "$EE_TEMPLATE" + echo "}" +} + +verify_or_write() { + local generate_fn="$1" output="$2" name="$3" + if [ -n "$CHECK" ]; then + if "$generate_fn" | diff -q "$output" - > /dev/null 2>&1; then + echo "OK: $name private module map is up to date." + else + echo "ERROR: $name private module map is out of date." >&2 + echo "Run '$0' and commit the results." >&2 + exit 1 + fi + else + mkdir -p "$(dirname "$output")" + "$generate_fn" > "$output" + echo "Generated: $output" + fi +} + +verify_or_write generate_ce "$CE_MODULEMAP" "CE" +verify_or_write generate_ee "$EE_MODULEMAP" "EE" diff --git a/xcconfigs/CBL_EE_Swift.xcconfig b/xcconfigs/CBL_EE_Swift.xcconfig index 8b4c4a13b..00a50caff 100644 --- a/xcconfigs/CBL_EE_Swift.xcconfig +++ b/xcconfigs/CBL_EE_Swift.xcconfig @@ -21,5 +21,5 @@ #include "CBL_Swift.xcconfig" CBL_EXPORTED_SYMBOLS_FILE = // None -MODULEMAP_PRIVATE_FILE = ../couchbase-lite-ios-ee/Sources/Swift/CouchbaseLiteSwift.private.modulemap +MODULEMAP_PRIVATE_FILE = Swift/ModuleMap/Generated/CouchbaseLiteSwift-EE.private.modulemap HEADER_SEARCH_PATHS = $(inherited) $(SRCROOT)/vendor/couchbase-lite-core-EE/P2P/include diff --git a/xcconfigs/CBL_Swift.xcconfig b/xcconfigs/CBL_Swift.xcconfig index 3fd68ccc6..84db64916 100644 --- a/xcconfigs/CBL_Swift.xcconfig +++ b/xcconfigs/CBL_Swift.xcconfig @@ -20,7 +20,7 @@ #include "CBL_ObjC.xcconfig" CBL_EXPORTED_SYMBOLS_FILE = // None -MODULEMAP_PRIVATE_FILE = Swift/CouchbaseLiteSwift.private.modulemap +MODULEMAP_PRIVATE_FILE = Swift/ModuleMap/Generated/CouchbaseLiteSwift.private.modulemap INFOPLIST_FILE = Swift/Info.plist PRODUCT_BUNDLE_IDENTIFIER = com.couchbase.CouchbaseLiteSwift PRODUCT_NAME = CouchbaseLiteSwift diff --git a/xcconfigs/Project.xcconfig b/xcconfigs/Project.xcconfig index b080e8717..cd35a331e 100644 --- a/xcconfigs/Project.xcconfig +++ b/xcconfigs/Project.xcconfig @@ -53,6 +53,10 @@ GCC_NO_COMMON_BLOCKS = YES SWIFT_VERSION = 5.0 +// Allow to detect files using members of modules they do not import (e.g. Obj-C EE components). +// A released Swift 6.1+ feature (SE-0444) provides an early access. Will be ON by default in an up coming release. +SWIFT_UPCOMING_FEATURE_MEMBER_IMPORT_VISIBILITY = YES + // Support Swift library evolution and generation of a module interface file for both DEBUG and RELEASE. BUILD_LIBRARY_FOR_DISTRIBUTION = YES From 14de261a034763a415aa4e22a480a7fade4a07be Mon Sep 17 00:00:00 2001 From: Pasin Suriyentrakorn Date: Tue, 11 Aug 2026 19:25:09 -0700 Subject: [PATCH 2/3] Fix per copilot code review --- AGENTS.md | 2 +- CouchbaseLite.xcodeproj/project.pbxproj | 4 +- Scripts/pull_request_build_test.sh | 2 +- .../CouchbaseLiteSwift-EE.private.txt | 46 ------------------- Swift/ModuleMap/generate_private_modulemap.sh | 4 +- xcconfigs/Project.xcconfig | 4 +- 6 files changed, 9 insertions(+), 53 deletions(-) delete mode 100644 Swift/ModuleMap/Generated/CouchbaseLiteSwift-EE.private.txt diff --git a/AGENTS.md b/AGENTS.md index f3e8cd964..cd6dfbb7a 100644 --- a/AGENTS.md +++ b/AGENTS.md @@ -53,7 +53,7 @@ iOS app-hosted test schemes: - Do not hand-edit `CouchbaseLite.xcodeproj/project.pbxproj`. - If a task requires new files or project membership changes, ask the developer to make them in Xcode. - Do not edit generated export files in `Objective-C/Exports/Generated/` directly. Update the templates and run `Objective-C/Exports/generate_exports.sh` instead. -- Do not edit the generated private module maps in `ModuleMap/Generated/` directly. Update the header list templates and run `Swift/ModuleMap/generate_private_modulemap.sh` instead (see Architecture Notes). +- Do not edit the generated private module maps in `Swift/ModuleMap/Generated/` directly. Update the header list templates and run `Swift/ModuleMap/generate_private_modulemap.sh` instead (see Architecture Notes). ## Build and Test diff --git a/CouchbaseLite.xcodeproj/project.pbxproj b/CouchbaseLite.xcodeproj/project.pbxproj index c6d3739cf..b0cee97cd 100644 --- a/CouchbaseLite.xcodeproj/project.pbxproj +++ b/CouchbaseLite.xcodeproj/project.pbxproj @@ -2463,7 +2463,7 @@ 40C5FD5A2B9946E6004BFD3B /* CBLVectorIndexTypes.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = CBLVectorIndexTypes.h; sourceTree = ""; }; 40CC4B76302BE6D30002386D /* CouchbaseLiteSwift-EE.private.txt */ = {isa = PBXFileReference; lastKnownFileType = text; path = "CouchbaseLiteSwift-EE.private.txt"; sourceTree = ""; }; 40CC4B77302BE6E40002386D /* CouchbaseLiteSwift.private.txt */ = {isa = PBXFileReference; lastKnownFileType = text; path = CouchbaseLiteSwift.private.txt; sourceTree = ""; }; - 40CC4B78302BE6EF0002386D /* CouchbaseLiteSwift-EE.private.txt */ = {isa = PBXFileReference; lastKnownFileType = text; path = "CouchbaseLiteSwift-EE.private.txt"; sourceTree = ""; }; + 40CC4B79302BF1620002386D /* CouchbaseLiteSwift-EE.private.modulemap */ = {isa = PBXFileReference; lastKnownFileType = "sourcecode.module-map"; path = "CouchbaseLiteSwift-EE.private.modulemap"; sourceTree = ""; }; 40D6BCBF2DDD183000F209D7 /* MultipeerReplicatorConfiguration.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MultipeerReplicatorConfiguration.swift; sourceTree = ""; }; 40D6BCC12DDD191C00F209D7 /* MultipeerCertificateAuthenticator.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MultipeerCertificateAuthenticator.swift; sourceTree = ""; }; 40D6BCC32DDD19D900F209D7 /* PeerID.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = PeerID.swift; sourceTree = ""; }; @@ -3454,7 +3454,7 @@ isa = PBXGroup; children = ( 40F52B1D3026ED0F009C5F9E /* CouchbaseLiteSwift.private.modulemap */, - 40CC4B78302BE6EF0002386D /* CouchbaseLiteSwift-EE.private.txt */, + 40CC4B79302BF1620002386D /* CouchbaseLiteSwift-EE.private.modulemap */, ); path = Generated; sourceTree = ""; diff --git a/Scripts/pull_request_build_test.sh b/Scripts/pull_request_build_test.sh index 91b7efce4..829ea473b 100755 --- a/Scripts/pull_request_build_test.sh +++ b/Scripts/pull_request_build_test.sh @@ -83,7 +83,7 @@ fi # Verify that the generated private module maps are in sync with their header # list templates (see Swift/ModuleMap/generate_private_modulemap.sh). -sh Swift/ModuleMap/generate_private_modulemap.sh --check +./Swift/ModuleMap/generate_private_modulemap.sh --check # Minimum Matrix: # - Run swift tests on iOS platform diff --git a/Swift/ModuleMap/Generated/CouchbaseLiteSwift-EE.private.txt b/Swift/ModuleMap/Generated/CouchbaseLiteSwift-EE.private.txt deleted file mode 100644 index 4fcd7fbbd..000000000 --- a/Swift/ModuleMap/Generated/CouchbaseLiteSwift-EE.private.txt +++ /dev/null @@ -1,46 +0,0 @@ -# EE-only header list, appended to the CE header list in the generated EE -# module map. Lines starting with '#' are template comments and are not copied -# to the output. -# - // Enterprise Edition: - header "CBLClientCertificateAuthenticator.h" - header "CBLCoreMLPredictiveModel.h" - header "CBLDatabase+Encryption.h" - header "CBLDatabase+Prediction.h" - header "CBLDatabaseConfiguration+Encryption.h" - header "CBLDatabaseEndpoint.h" - header "CBLEncryptionKey.h" - header "CBLExtension.h" - header "CBLIndexBuilder+Prediction.h" - header "CBLIndexUpdater.h" - header "CBLListenerAuthenticator.h" - header "CBLListenerCertificateAuthenticator.h" - header "CBLListenerPasswordAuthenticator.h" - header "CBLMessage.h" - header "CBLMessageEndpoint.h" - header "CBLMessageEndpointConnection.h" - header "CBLMessageEndpointListener.h" - header "CBLMessagingError.h" - header "CBLMultipeerCertificateAuthenticator.h" - header "CBLMultipeerCollectionConfiguration.h" - header "CBLMultipeerEventTypes.h" - header "CBLMultipeerReplicator.h" - header "CBLMultipeerReplicatorConfiguration.h" - header "CBLMultipeerTransportTypes.h" - header "CBLPeerID.h" - header "CBLPeerInfo.h" - header "CBLPrediction.h" - header "CBLPrediction+Swift.h" - header "CBLPredictiveIndex.h" - header "CBLProtocolType.h" - header "CBLQueryFunction+Prediction.h" - header "CBLQueryFunction+Vector.h" - header "CBLReplicatorConfiguration+ServerCert.h" - header "CBLTLSIdentity.h" - header "CBLTLSIdentity+Swift.h" - header "CBLURLEndpointListener.h" - header "CBLURLEndpointListener+Swift.h" - header "CBLURLEndpointListenerConfiguration.h" - header "CBLVectorEncoding.h" - header "CBLVectorIndexConfiguration.h" - header "CBLVectorIndexTypes.h" diff --git a/Swift/ModuleMap/generate_private_modulemap.sh b/Swift/ModuleMap/generate_private_modulemap.sh index b0e5a8c9f..c7223b6aa 100755 --- a/Swift/ModuleMap/generate_private_modulemap.sh +++ b/Swift/ModuleMap/generate_private_modulemap.sh @@ -79,7 +79,9 @@ generate_ee() { verify_or_write() { local generate_fn="$1" output="$2" name="$3" if [ -n "$CHECK" ]; then - if "$generate_fn" | diff -q "$output" - > /dev/null 2>&1; then + # Compare the module content only, skipping '//' comment lines, so that the + # year in the generated license header does not affect the verification. + if diff -q <(grep -v '^//' "$output" 2>/dev/null) <("$generate_fn" | grep -v '^//') > /dev/null 2>&1; then echo "OK: $name private module map is up to date." else echo "ERROR: $name private module map is out of date." >&2 diff --git a/xcconfigs/Project.xcconfig b/xcconfigs/Project.xcconfig index cd35a331e..4b20e4b55 100644 --- a/xcconfigs/Project.xcconfig +++ b/xcconfigs/Project.xcconfig @@ -53,8 +53,8 @@ GCC_NO_COMMON_BLOCKS = YES SWIFT_VERSION = 5.0 -// Allow to detect files using members of modules they do not import (e.g. Obj-C EE components). -// A released Swift 6.1+ feature (SE-0444) provides an early access. Will be ON by default in an up coming release. +// Allow detecting files that use members of modules they do not import (e.g. Obj-C EE components). +// Released in Swift 6.1 as an upcoming feature (SE-0444); will be ON by default in a future release. SWIFT_UPCOMING_FEATURE_MEMBER_IMPORT_VISIBILITY = YES // Support Swift library evolution and generation of a module interface file for both DEBUG and RELEASE. From 5e7d2adda6954928e00ae6cbfa29a02000ed6b5f Mon Sep 17 00:00:00 2001 From: Pasin Suriyentrakorn Date: Tue, 11 Aug 2026 20:24:58 -0700 Subject: [PATCH 3/3] Move module map check from PR build script to GitHub workflow - Add check_modulemaps.yml workflow running generate_private_modulemap.sh --check on PRs - Remove the check from pull_request_build_test.sh --- .github/workflows/check_modulemaps.yml | 14 ++++++++++++++ Scripts/pull_request_build_test.sh | 3 --- 2 files changed, 14 insertions(+), 3 deletions(-) create mode 100644 .github/workflows/check_modulemaps.yml diff --git a/.github/workflows/check_modulemaps.yml b/.github/workflows/check_modulemaps.yml new file mode 100644 index 000000000..5b9e208eb --- /dev/null +++ b/.github/workflows/check_modulemaps.yml @@ -0,0 +1,14 @@ +name: Check Module Map Files + +on: + pull_request: + branches: + - '**' + +jobs: + verify: + runs-on: macos-latest + steps: + - uses: actions/checkout@v4 + - name: Verify generated private module maps + run: ./Swift/ModuleMap/generate_private_modulemap.sh --check diff --git a/Scripts/pull_request_build_test.sh b/Scripts/pull_request_build_test.sh index 829ea473b..beb688c8f 100755 --- a/Scripts/pull_request_build_test.sh +++ b/Scripts/pull_request_build_test.sh @@ -81,9 +81,6 @@ else cd couchbase-lite-ios fi -# Verify that the generated private module maps are in sync with their header -# list templates (see Swift/ModuleMap/generate_private_modulemap.sh). -./Swift/ModuleMap/generate_private_modulemap.sh --check # Minimum Matrix: # - Run swift tests on iOS platform