cocoapods-tt 0.0.1

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 (124) hide show
  1. checksums.yaml +7 -0
  2. data/lib/cocoapods-tt/command/native/install.rb +56 -0
  3. data/lib/cocoapods-tt/command/native/update.rb +157 -0
  4. data/lib/cocoapods-tt/command/tt/make.rb +92 -0
  5. data/lib/cocoapods-tt/command/tt.rb +115 -0
  6. data/lib/cocoapods-tt/command.rb +1 -0
  7. data/lib/cocoapods-tt/gem_version.rb +3 -0
  8. data/lib/cocoapods-tt/native/command.rb +185 -0
  9. data/lib/cocoapods-tt/native/config.rb +366 -0
  10. data/lib/cocoapods-tt/native/core_overrides.rb +1 -0
  11. data/lib/cocoapods-tt/native/downloader/cache.rb +322 -0
  12. data/lib/cocoapods-tt/native/downloader/request.rb +86 -0
  13. data/lib/cocoapods-tt/native/downloader/response.rb +16 -0
  14. data/lib/cocoapods-tt/native/downloader.rb +192 -0
  15. data/lib/cocoapods-tt/native/executable.rb +247 -0
  16. data/lib/cocoapods-tt/native/external_sources/abstract_external_source.rb +205 -0
  17. data/lib/cocoapods-tt/native/external_sources/downloader_source.rb +30 -0
  18. data/lib/cocoapods-tt/native/external_sources/path_source.rb +55 -0
  19. data/lib/cocoapods-tt/native/external_sources/podspec_source.rb +54 -0
  20. data/lib/cocoapods-tt/native/external_sources.rb +57 -0
  21. data/lib/cocoapods-tt/native/gem_version.rb +5 -0
  22. data/lib/cocoapods-tt/native/generator/acknowledgements/markdown.rb +44 -0
  23. data/lib/cocoapods-tt/native/generator/acknowledgements/plist.rb +94 -0
  24. data/lib/cocoapods-tt/native/generator/acknowledgements.rb +107 -0
  25. data/lib/cocoapods-tt/native/generator/app_target_helper.rb +363 -0
  26. data/lib/cocoapods-tt/native/generator/bridge_support.rb +22 -0
  27. data/lib/cocoapods-tt/native/generator/constant.rb +19 -0
  28. data/lib/cocoapods-tt/native/generator/copy_dsyms_script.rb +56 -0
  29. data/lib/cocoapods-tt/native/generator/copy_resources_script.rb +223 -0
  30. data/lib/cocoapods-tt/native/generator/copy_xcframework_script.rb +227 -0
  31. data/lib/cocoapods-tt/native/generator/dummy_source.rb +31 -0
  32. data/lib/cocoapods-tt/native/generator/embed_frameworks_script.rb +196 -0
  33. data/lib/cocoapods-tt/native/generator/file_list.rb +39 -0
  34. data/lib/cocoapods-tt/native/generator/header.rb +103 -0
  35. data/lib/cocoapods-tt/native/generator/info_plist_file.rb +128 -0
  36. data/lib/cocoapods-tt/native/generator/module_map.rb +99 -0
  37. data/lib/cocoapods-tt/native/generator/prefix_header.rb +60 -0
  38. data/lib/cocoapods-tt/native/generator/script_phase_constants.rb +100 -0
  39. data/lib/cocoapods-tt/native/generator/umbrella_header.rb +46 -0
  40. data/lib/cocoapods-tt/native/hooks_manager.rb +132 -0
  41. data/lib/cocoapods-tt/native/installer/analyzer/analysis_result.rb +87 -0
  42. data/lib/cocoapods-tt/native/installer/analyzer/locking_dependency_analyzer.rb +103 -0
  43. data/lib/cocoapods-tt/native/installer/analyzer/pod_variant.rb +87 -0
  44. data/lib/cocoapods-tt/native/installer/analyzer/pod_variant_set.rb +175 -0
  45. data/lib/cocoapods-tt/native/installer/analyzer/podfile_dependency_cache.rb +55 -0
  46. data/lib/cocoapods-tt/native/installer/analyzer/sandbox_analyzer.rb +268 -0
  47. data/lib/cocoapods-tt/native/installer/analyzer/specs_state.rb +108 -0
  48. data/lib/cocoapods-tt/native/installer/analyzer/target_inspection_result.rb +58 -0
  49. data/lib/cocoapods-tt/native/installer/analyzer/target_inspector.rb +258 -0
  50. data/lib/cocoapods-tt/native/installer/analyzer.rb +1204 -0
  51. data/lib/cocoapods-tt/native/installer/base_install_hooks_context.rb +135 -0
  52. data/lib/cocoapods-tt/native/installer/installation_options.rb +195 -0
  53. data/lib/cocoapods-tt/native/installer/pod_source_installer.rb +224 -0
  54. data/lib/cocoapods-tt/native/installer/pod_source_preparer.rb +77 -0
  55. data/lib/cocoapods-tt/native/installer/podfile_validator.rb +168 -0
  56. data/lib/cocoapods-tt/native/installer/post_install_hooks_context.rb +9 -0
  57. data/lib/cocoapods-tt/native/installer/post_integrate_hooks_context.rb +9 -0
  58. data/lib/cocoapods-tt/native/installer/pre_install_hooks_context.rb +51 -0
  59. data/lib/cocoapods-tt/native/installer/pre_integrate_hooks_context.rb +9 -0
  60. data/lib/cocoapods-tt/native/installer/project_cache/project_cache.rb +11 -0
  61. data/lib/cocoapods-tt/native/installer/project_cache/project_cache_analysis_result.rb +53 -0
  62. data/lib/cocoapods-tt/native/installer/project_cache/project_cache_analyzer.rb +200 -0
  63. data/lib/cocoapods-tt/native/installer/project_cache/project_cache_version.rb +43 -0
  64. data/lib/cocoapods-tt/native/installer/project_cache/project_installation_cache.rb +103 -0
  65. data/lib/cocoapods-tt/native/installer/project_cache/project_metadata_cache.rb +73 -0
  66. data/lib/cocoapods-tt/native/installer/project_cache/target_cache_key.rb +176 -0
  67. data/lib/cocoapods-tt/native/installer/project_cache/target_metadata.rb +74 -0
  68. data/lib/cocoapods-tt/native/installer/sandbox_dir_cleaner.rb +105 -0
  69. data/lib/cocoapods-tt/native/installer/sandbox_header_paths_installer.rb +45 -0
  70. data/lib/cocoapods-tt/native/installer/source_provider_hooks_context.rb +34 -0
  71. data/lib/cocoapods-tt/native/installer/target_uuid_generator.rb +34 -0
  72. data/lib/cocoapods-tt/native/installer/user_project_integrator/target_integrator/xcconfig_integrator.rb +179 -0
  73. data/lib/cocoapods-tt/native/installer/user_project_integrator/target_integrator.rb +815 -0
  74. data/lib/cocoapods-tt/native/installer/user_project_integrator.rb +280 -0
  75. data/lib/cocoapods-tt/native/installer/xcode/multi_pods_project_generator.rb +82 -0
  76. data/lib/cocoapods-tt/native/installer/xcode/pods_project_generator/aggregate_target_dependency_installer.rb +66 -0
  77. data/lib/cocoapods-tt/native/installer/xcode/pods_project_generator/aggregate_target_installer.rb +192 -0
  78. data/lib/cocoapods-tt/native/installer/xcode/pods_project_generator/app_host_installer.rb +154 -0
  79. data/lib/cocoapods-tt/native/installer/xcode/pods_project_generator/file_references_installer.rb +329 -0
  80. data/lib/cocoapods-tt/native/installer/xcode/pods_project_generator/pod_target_dependency_installer.rb +195 -0
  81. data/lib/cocoapods-tt/native/installer/xcode/pods_project_generator/pod_target_installer.rb +1239 -0
  82. data/lib/cocoapods-tt/native/installer/xcode/pods_project_generator/pod_target_integrator.rb +312 -0
  83. data/lib/cocoapods-tt/native/installer/xcode/pods_project_generator/pods_project_writer.rb +90 -0
  84. data/lib/cocoapods-tt/native/installer/xcode/pods_project_generator/project_generator.rb +120 -0
  85. data/lib/cocoapods-tt/native/installer/xcode/pods_project_generator/target_installation_result.rb +140 -0
  86. data/lib/cocoapods-tt/native/installer/xcode/pods_project_generator/target_installer.rb +257 -0
  87. data/lib/cocoapods-tt/native/installer/xcode/pods_project_generator/target_installer_helper.rb +110 -0
  88. data/lib/cocoapods-tt/native/installer/xcode/pods_project_generator.rb +291 -0
  89. data/lib/cocoapods-tt/native/installer/xcode/pods_project_generator_result.rb +54 -0
  90. data/lib/cocoapods-tt/native/installer/xcode/single_pods_project_generator.rb +38 -0
  91. data/lib/cocoapods-tt/native/installer/xcode/target_validator.rb +170 -0
  92. data/lib/cocoapods-tt/native/installer/xcode.rb +11 -0
  93. data/lib/cocoapods-tt/native/installer.rb +1044 -0
  94. data/lib/cocoapods-tt/native/native_target_extension.rb +60 -0
  95. data/lib/cocoapods-tt/native/open-uri.rb +33 -0
  96. data/lib/cocoapods-tt/native/podfile.rb +13 -0
  97. data/lib/cocoapods-tt/native/project.rb +544 -0
  98. data/lib/cocoapods-tt/native/resolver/lazy_specification.rb +88 -0
  99. data/lib/cocoapods-tt/native/resolver/resolver_specification.rb +41 -0
  100. data/lib/cocoapods-tt/native/resolver.rb +600 -0
  101. data/lib/cocoapods-tt/native/sandbox/file_accessor.rb +532 -0
  102. data/lib/cocoapods-tt/native/sandbox/headers_store.rb +163 -0
  103. data/lib/cocoapods-tt/native/sandbox/path_list.rb +242 -0
  104. data/lib/cocoapods-tt/native/sandbox/pod_dir_cleaner.rb +71 -0
  105. data/lib/cocoapods-tt/native/sandbox/podspec_finder.rb +23 -0
  106. data/lib/cocoapods-tt/native/sandbox.rb +470 -0
  107. data/lib/cocoapods-tt/native/sources_manager.rb +221 -0
  108. data/lib/cocoapods-tt/native/target/aggregate_target.rb +558 -0
  109. data/lib/cocoapods-tt/native/target/build_settings.rb +1385 -0
  110. data/lib/cocoapods-tt/native/target/pod_target.rb +1168 -0
  111. data/lib/cocoapods-tt/native/target.rb +378 -0
  112. data/lib/cocoapods-tt/native/user_interface/error_report.rb +204 -0
  113. data/lib/cocoapods-tt/native/user_interface/inspector_reporter.rb +102 -0
  114. data/lib/cocoapods-tt/native/user_interface.rb +463 -0
  115. data/lib/cocoapods-tt/native/validator.rb +1170 -0
  116. data/lib/cocoapods-tt/native/version_metadata.rb +26 -0
  117. data/lib/cocoapods-tt/native/xcode/framework_paths.rb +54 -0
  118. data/lib/cocoapods-tt/native/xcode/linkage_analyzer.rb +22 -0
  119. data/lib/cocoapods-tt/native/xcode/xcframework/xcframework_slice.rb +138 -0
  120. data/lib/cocoapods-tt/native/xcode/xcframework.rb +99 -0
  121. data/lib/cocoapods-tt/native/xcode.rb +7 -0
  122. data/lib/cocoapods-tt.rb +1 -0
  123. data/lib/cocoapods_plugin.rb +17 -0
  124. metadata +193 -0
@@ -0,0 +1,1385 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Pod
4
+ class Target
5
+ # @since 1.5.0
6
+ class BuildSettings
7
+ #-------------------------------------------------------------------------#
8
+
9
+ # @!group Constants
10
+
11
+ # @return [Set<String>]
12
+ # The build settings that should be treated as arrays, rather than strings.
13
+ #
14
+ PLURAL_SETTINGS = %w(
15
+ ALTERNATE_PERMISSIONS_FILES
16
+ ARCHS
17
+ BUILD_VARIANTS
18
+ EXCLUDED_SOURCE_FILE_NAMES
19
+ FRAMEWORK_SEARCH_PATHS
20
+ GCC_PREPROCESSOR_DEFINITIONS
21
+ GCC_PREPROCESSOR_DEFINITIONS_NOT_USED_IN_PRECOMPS
22
+ HEADER_SEARCH_PATHS
23
+ INCLUDED_SOURCE_FILE_NAMES
24
+ INFOPLIST_PREPROCESSOR_DEFINITIONS
25
+ LD_RUNPATH_SEARCH_PATHS
26
+ LIBRARY_SEARCH_PATHS
27
+ LOCALIZED_STRING_MACRO_NAMES
28
+ OTHER_CFLAGS
29
+ OTHER_CPLUSPLUSFLAGS
30
+ OTHER_LDFLAGS
31
+ OTHER_SWIFT_FLAGS
32
+ REZ_SEARCH_PATHS
33
+ SECTORDER_FLAGS
34
+ SWIFT_ACTIVE_COMPILATION_CONDITIONS
35
+ SWIFT_INCLUDE_PATHS
36
+ SYSTEM_FRAMEWORK_SEARCH_PATHS
37
+ SYSTEM_HEADER_SEARCH_PATHS
38
+ USER_HEADER_SEARCH_PATHS
39
+ WARNING_CFLAGS
40
+ WARNING_LDFLAGS
41
+ ).to_set.freeze
42
+
43
+ # @return [String]
44
+ # The variable for the configuration build directory used when building pod targets.
45
+ #
46
+ CONFIGURATION_BUILD_DIR_VARIABLE = '${PODS_CONFIGURATION_BUILD_DIR}'
47
+
48
+ # @return [String]
49
+ # The variable for the configuration intermediate frameworks directory used for building pod targets
50
+ # that contain vendored xcframeworks.
51
+ #
52
+ XCFRAMEWORKS_BUILD_DIR_VARIABLE = '${PODS_XCFRAMEWORKS_BUILD_DIR}'
53
+
54
+ #-------------------------------------------------------------------------#
55
+
56
+ # @!group DSL
57
+
58
+ # Creates a method that calculates a part of the build settings for the {#target}.
59
+ #
60
+ # @!visibility private
61
+ #
62
+ # @param [Symbol,String] method_name
63
+ # The name of the method to define
64
+ #
65
+ # @param [Boolean] build_setting
66
+ # Whether the method name should be added (upcased) to {.build_setting_names}
67
+ #
68
+ # @param [Boolean] memoized
69
+ # Whether the method should be memoized
70
+ #
71
+ # @param [Boolean] sorted
72
+ # Whether the return value should be sorted
73
+ #
74
+ # @param [Boolean] uniqued
75
+ # Whether the return value should be uniqued
76
+ #
77
+ # @param [Boolean] compacted
78
+ # Whether the return value should be compacted
79
+ #
80
+ # @param [Boolean] frozen
81
+ # Whether the return value should be frozen
82
+ #
83
+ # @param [Boolean, Symbol] from_search_paths_aggregate_targets
84
+ # If truthy, the method from {Aggregate} that should be used to concatenate build settings from
85
+ # {::Pod::AggregateTarget#search_paths_aggregate_target}
86
+ #
87
+ # @param [Symbol] from_pod_targets_to_link
88
+ # If truthy, the `_to_import` values from `BuildSettings#pod_targets_to_link` will be concatenated
89
+ #
90
+ # @param [Block] implementation
91
+ #
92
+ # @macro [attach] define_build_settings_method
93
+ # @!method $1
94
+ #
95
+ # The `$1` build setting for the {#target}.
96
+ #
97
+ # The return value from this method will be: `${1--1}`.
98
+ #
99
+ def self.define_build_settings_method(method_name, build_setting: false,
100
+ memoized: false, sorted: false, uniqued: false, compacted: false, frozen: true,
101
+ from_search_paths_aggregate_targets: false, from_pod_targets_to_link: false,
102
+ &implementation)
103
+
104
+ memoized_key = "#{self}##{method_name}"
105
+
106
+ (@build_settings_names ||= Set.new) << method_name.to_s.upcase if build_setting
107
+
108
+ raw_method_name = :"_raw_#{method_name}"
109
+ define_method(raw_method_name, &implementation)
110
+ private(raw_method_name)
111
+
112
+ dup_before_freeze = frozen && (from_pod_targets_to_link || from_search_paths_aggregate_targets || uniqued || sorted)
113
+
114
+ define_method(method_name) do
115
+ if memoized
116
+ retval = @__memoized.fetch(memoized_key, :not_found)
117
+ return retval if :not_found != retval
118
+ end
119
+
120
+ retval = send(raw_method_name)
121
+ if retval.nil?
122
+ @__memoized[memoized_key] = retval if memoized
123
+ return
124
+ end
125
+
126
+ retval = retval.dup if dup_before_freeze && retval.frozen?
127
+
128
+ retval.concat(pod_targets_to_link.flat_map { |pod_target| pod_target.build_settings_for_spec(pod_target.root_spec, :configuration => configuration_name).public_send("#{method_name}_to_import") }) if from_pod_targets_to_link
129
+ retval.concat(search_paths_aggregate_target_pod_target_build_settings.flat_map(&from_search_paths_aggregate_targets)) if from_search_paths_aggregate_targets
130
+
131
+ retval.compact! if compacted
132
+ retval.uniq! if uniqued
133
+ retval.sort! if sorted
134
+ retval.freeze if frozen
135
+
136
+ @__memoized[memoized_key] = retval if memoized
137
+
138
+ retval
139
+ end
140
+ end
141
+ private_class_method :define_build_settings_method
142
+
143
+ # @param [XCFramework] xcframework the xcframework slice that will be copied to the intermediates dir
144
+ #
145
+ # @return [String] the path to the directory containing the xcframework slice
146
+ #
147
+ def self.xcframework_intermediate_dir(xcframework)
148
+ "#{XCFRAMEWORKS_BUILD_DIR_VARIABLE}/#{xcframework.target_name}"
149
+ end
150
+
151
+ class << self
152
+ #-------------------------------------------------------------------------#
153
+
154
+ # @!group Public API
155
+
156
+ # @return [Set<String>] a set of all the build settings names that will
157
+ # be present in the #xcconfig
158
+ #
159
+ attr_reader :build_settings_names
160
+ end
161
+
162
+ #-------------------------------------------------------------------------#
163
+
164
+ # @!group Public API
165
+
166
+ # @return [Target]
167
+ # The target this build settings object is generating build settings for
168
+ #
169
+ attr_reader :target
170
+
171
+ # Initialize a new instance
172
+ #
173
+ # @param [Target] target
174
+ # see {#target}
175
+ #
176
+ def initialize(target)
177
+ @target = target
178
+ @__memoized = {}
179
+ end
180
+
181
+ def initialize_copy(other)
182
+ super
183
+ @__memoized = {}
184
+ end
185
+
186
+ # @return [Xcodeproj::Config]
187
+ define_build_settings_method :xcconfig, :memoized => true do
188
+ settings = add_inherited_to_plural(to_h)
189
+ Xcodeproj::Config.new(settings)
190
+ end
191
+
192
+ alias generate xcconfig
193
+
194
+ # Saves the generated xcconfig to the given path
195
+ #
196
+ # @return [Xcodeproj::Config]
197
+ #
198
+ # @see #xcconfig
199
+ #
200
+ # @param [String,Pathname] path
201
+ # The path the xcconfig will be saved to
202
+ #
203
+ def save_as(path)
204
+ xcconfig.save_as(path)
205
+ end
206
+
207
+ #-------------------------------------------------------------------------#
208
+
209
+ # @!group Build System
210
+
211
+ # @return [String]
212
+ define_build_settings_method :pods_build_dir, :build_setting => true do
213
+ '${BUILD_DIR}'
214
+ end
215
+
216
+ # @return [String]
217
+ define_build_settings_method :pods_configuration_build_dir, :build_setting => true do
218
+ '${PODS_BUILD_DIR}/$(CONFIGURATION)$(EFFECTIVE_PLATFORM_NAME)'
219
+ end
220
+
221
+ define_build_settings_method :pods_xcframeworks_build_dir, :build_setting => true do
222
+ '$(PODS_CONFIGURATION_BUILD_DIR)/XCFrameworkIntermediates'
223
+ end
224
+
225
+ # @return [String]
226
+ define_build_settings_method :use_recursive_script_inputs_in_script_phases, :build_setting => true do
227
+ 'YES'
228
+ end
229
+
230
+ #-------------------------------------------------------------------------#
231
+
232
+ # @!group Code Signing
233
+
234
+ # @return [String]
235
+ define_build_settings_method :code_sign_identity, :build_setting => true do
236
+ return unless target.build_as_dynamic?
237
+ return unless target.platform.to_sym == :osx
238
+ ''
239
+ end
240
+
241
+ #-------------------------------------------------------------------------#
242
+
243
+ # @!group Frameworks
244
+
245
+ # @return [Array<String>]
246
+ define_build_settings_method :frameworks do
247
+ []
248
+ end
249
+
250
+ # @return [Array<String>]
251
+ define_build_settings_method :weak_frameworks do
252
+ []
253
+ end
254
+
255
+ # @return [Array<String>]
256
+ define_build_settings_method :framework_search_paths, :build_setting => true, :memoized => true do
257
+ framework_search_paths_to_import_developer_frameworks(frameworks + weak_frameworks)
258
+ end
259
+
260
+ # @param [Array<String>] frameworks
261
+ # The list of framework names
262
+ #
263
+ # @return [Array<String>]
264
+ # the `FRAMEWORK_SEARCH_PATHS` needed to import developer frameworks
265
+ def framework_search_paths_to_import_developer_frameworks(frameworks)
266
+ if frameworks.include?('XCTest') || frameworks.include?('SenTestingKit')
267
+ %w[ $(PLATFORM_DIR)/Developer/Library/Frameworks ]
268
+ else
269
+ []
270
+ end
271
+ end
272
+
273
+ #-------------------------------------------------------------------------#
274
+
275
+ # @!group Libraries
276
+
277
+ # @return [Array<String>]
278
+ define_build_settings_method :libraries do
279
+ []
280
+ end
281
+
282
+ #-------------------------------------------------------------------------#
283
+
284
+ # @!group Clang
285
+
286
+ # @return [Array<String>]
287
+ define_build_settings_method :gcc_preprocessor_definitions, :build_setting => true do
288
+ %w( COCOAPODS=1 )
289
+ end
290
+
291
+ # @return [Array<String>]
292
+ define_build_settings_method :other_cflags, :build_setting => true, :memoized => true do
293
+ module_map_files.map { |f| "-fmodule-map-file=#{f}" }
294
+ end
295
+
296
+ # @return [Array<String>]
297
+ define_build_settings_method :module_map_files do
298
+ []
299
+ end
300
+
301
+ #-------------------------------------------------------------------------#
302
+
303
+ # @!group Swift
304
+
305
+ # @return [Boolean]
306
+ # Whether `OTHER_SWIFT_FLAGS` should be generated when the target
307
+ # does not use swift.
308
+ #
309
+ def other_swift_flags_without_swift?
310
+ false
311
+ end
312
+
313
+ # @return [Array<String>]
314
+ define_build_settings_method :other_swift_flags, :build_setting => true, :memoized => true do
315
+ return unless target.uses_swift? || other_swift_flags_without_swift?
316
+ flags = %w(-D COCOAPODS)
317
+ flags.concat module_map_files.flat_map { |f| ['-Xcc', "-fmodule-map-file=#{f}"] }
318
+ flags
319
+ end
320
+
321
+ #-------------------------------------------------------------------------#
322
+
323
+ # @!group Linking
324
+
325
+ # @return [Boolean]
326
+ define_build_settings_method :requires_objc_linker_flag? do
327
+ false
328
+ end
329
+
330
+ # @return [Boolean]
331
+ define_build_settings_method :requires_fobjc_arc? do
332
+ false
333
+ end
334
+
335
+ # Xcode 12 turns on this warning by default which is problematic for CocoaPods-generated
336
+ # imports which use double-quoted paths.
337
+ # @return [Boolean]
338
+ define_build_settings_method :clang_warn_quoted_include_in_framework_header, :build_setting => true do
339
+ 'NO'
340
+ end
341
+
342
+ # @return [Array<String>]
343
+ # the `LD_RUNPATH_SEARCH_PATHS` needed for dynamically linking the {#target}
344
+ #
345
+ # @param [Boolean] requires_host_target
346
+ #
347
+ # @param [Boolean] test_bundle
348
+ #
349
+ def _ld_runpath_search_paths(requires_host_target: false, test_bundle: false, uses_swift: false)
350
+ paths = []
351
+ if uses_swift
352
+ paths << '/usr/lib/swift'
353
+ paths << '$(PLATFORM_DIR)/Developer/Library/Frameworks' if test_bundle
354
+ end
355
+ if target.platform.symbolic_name == :osx
356
+ paths << "'@executable_path/../Frameworks'"
357
+ paths << if test_bundle
358
+ "'@loader_path/../Frameworks'"
359
+ else
360
+ "'@loader_path/Frameworks'"
361
+ end
362
+ paths << '${DT_TOOLCHAIN_DIR}/usr/lib/swift/${PLATFORM_NAME}' if uses_swift
363
+ else
364
+ paths << "'@executable_path/Frameworks'"
365
+ paths << "'@loader_path/Frameworks'"
366
+ paths << "'@executable_path/../../Frameworks'" if requires_host_target
367
+ end
368
+ paths
369
+ end
370
+ private :_ld_runpath_search_paths
371
+
372
+ # @return [Array<String>]
373
+ define_build_settings_method :other_ldflags, :build_setting => true, :memoized => true do
374
+ ld_flags = []
375
+ ld_flags << '-ObjC' if requires_objc_linker_flag?
376
+ if requires_fobjc_arc?
377
+ ld_flags << '-fobjc-arc'
378
+ end
379
+ libraries.each { |l| ld_flags << %(-l"#{l}") }
380
+ frameworks.each { |f| ld_flags << '-framework' << %("#{f}") }
381
+ weak_frameworks.each { |f| ld_flags << '-weak_framework' << %("#{f}") }
382
+ ld_flags
383
+ end
384
+
385
+ #-------------------------------------------------------------------------#
386
+
387
+ # @!group Private Methods
388
+
389
+ private
390
+
391
+ # @return [Hash<String => String|Array<String>>]
392
+ def to_h
393
+ hash = {}
394
+ self.class.build_settings_names.sort.each do |setting|
395
+ hash[setting] = public_send(setting.downcase)
396
+ end
397
+ hash
398
+ end
399
+
400
+ # @return [Hash<String => String>]
401
+ def add_inherited_to_plural(hash)
402
+ Hash[hash.map do |key, value|
403
+ next [key, '$(inherited)'] if value.nil?
404
+ if PLURAL_SETTINGS.include?(key)
405
+ raise ArgumentError, "#{key} is a plural setting, cannot have #{value.inspect} as its value" unless value.is_a? Array
406
+
407
+ value = "$(inherited) #{quote_array(value)}"
408
+ else
409
+ raise ArgumentError, "#{key} is not a plural setting, cannot have #{value.inspect} as its value" unless value.is_a? String
410
+ end
411
+
412
+ [key, value]
413
+ end]
414
+ end
415
+
416
+ # @return [Array<String>]
417
+ #
418
+ # @param [Array<String>] array
419
+ #
420
+ def quote_array(array)
421
+ array.map do |element|
422
+ case element
423
+ when /\A([\w-]+?)=(.+)\z/
424
+ key = Regexp.last_match(1)
425
+ value = Regexp.last_match(2)
426
+ value = %("#{value}") if value =~ /[^\w\d]/
427
+ %(#{key}=#{value})
428
+ when /[\$\[\]\ ]/
429
+ %("#{element}")
430
+ else
431
+ element
432
+ end
433
+ end.join(' ')
434
+ end
435
+
436
+ # @param [Hash] xcconfig_values_by_consumer_by_key
437
+ #
438
+ # @param [#to_s] attribute
439
+ # The name of the attribute being merged
440
+ #
441
+ # @return [Hash<String, String>]
442
+ #
443
+ def merged_xcconfigs(xcconfig_values_by_consumer_by_key, attribute, overriding: {})
444
+ xcconfig_values_by_consumer_by_key.each_with_object(overriding.dup) do |(key, values_by_consumer), xcconfig|
445
+ uniq_values = values_by_consumer.values.uniq
446
+ values_are_bools = uniq_values.all? { |v| v =~ /\A(yes|no)\z/i }
447
+ if values_are_bools
448
+ # Boolean build settings
449
+ if uniq_values.count > 1
450
+ UI.warn "Can't merge #{attribute} for pod targets: " \
451
+ "#{values_by_consumer.keys.map(&:name)}. Boolean build " \
452
+ "setting #{key} has different values."
453
+ else
454
+ xcconfig[key] = uniq_values.first
455
+ end
456
+ elsif PLURAL_SETTINGS.include? key
457
+ # Plural build settings
458
+ if xcconfig.key?(key)
459
+ overridden = xcconfig[key]
460
+ uniq_values.prepend(overridden)
461
+ end
462
+ xcconfig[key] = uniq_values.uniq.join(' ')
463
+ elsif uniq_values.count > 1
464
+ # Singular build settings
465
+ UI.warn "Can't merge #{attribute} for pod targets: " \
466
+ "#{values_by_consumer.keys.map(&:name)}. Singular build " \
467
+ "setting #{key} has different values."
468
+ else
469
+ xcconfig[key] = uniq_values.first
470
+ end
471
+ end
472
+ end
473
+
474
+ # Merges the spec-defined xcconfig into the derived xcconfig,
475
+ # overriding any singular settings and merging plural settings.
476
+ #
477
+ # @param [Hash<String,String>] spec_xcconfig_hash the merged xcconfig defined in the spec.
478
+ #
479
+ # @param [Xcodeproj::Config] xcconfig the config to merge into.
480
+ #
481
+ # @return [Xcodeproj::Config] the merged config.
482
+ #
483
+ def merge_spec_xcconfig_into_xcconfig(spec_xcconfig_hash, xcconfig)
484
+ plural_configs, singlular_configs = spec_xcconfig_hash.partition { |k, _v| PLURAL_SETTINGS.include?(k) }.map { |a| Hash[a] }
485
+ xcconfig.attributes.merge!(singlular_configs)
486
+ xcconfig.merge!(plural_configs)
487
+ xcconfig
488
+ end
489
+
490
+ # Filters out pod targets whose `specs` are a subset of
491
+ # another target's.
492
+ #
493
+ # @param [Array<PodTarget>] pod_targets
494
+ #
495
+ # @return [Array<PodTarget>]
496
+ #
497
+ def select_maximal_pod_targets(pod_targets)
498
+ subset_targets = []
499
+ pod_targets.uniq.group_by(&:pod_name).each do |_pod_name, targets|
500
+ targets.combination(2) do |a, b|
501
+ if (a.specs - b.specs).empty?
502
+ subset_targets << a
503
+ elsif (b.specs - a.specs).empty?
504
+ subset_targets << b
505
+ end
506
+ end
507
+ end
508
+ pod_targets - subset_targets
509
+ end
510
+
511
+ # @param [String] target_name the name of the target this xcframework belongs to
512
+ #
513
+ # @param [Pathname,String] path the path to the xcframework bundle
514
+ #
515
+ # @return [Xcode::XCFramework] the xcframework at the given path
516
+ #
517
+ def load_xcframework(target_name, path)
518
+ Xcode::XCFramework.new(target_name, path)
519
+ end
520
+
521
+ # A subclass that generates build settings for a {PodTarget}
522
+ class PodTargetSettings < BuildSettings
523
+ #-------------------------------------------------------------------------#
524
+
525
+ # @!group Public API
526
+
527
+ # @see BuildSettings.build_settings_names
528
+ def self.build_settings_names
529
+ @build_settings_names | BuildSettings.build_settings_names
530
+ end
531
+
532
+ # @return [Boolean]
533
+ # whether settings are being generated for a test bundle
534
+ #
535
+ attr_reader :test_xcconfig
536
+ alias test_xcconfig? test_xcconfig
537
+
538
+ # @return [Boolean]
539
+ # whether settings are being generated for an application bundle
540
+ #
541
+ attr_reader :app_xcconfig
542
+ alias app_xcconfig? app_xcconfig
543
+
544
+ # @return [Boolean]
545
+ # whether settings are being generated for an library bundle
546
+ #
547
+ attr_reader :library_xcconfig
548
+ alias library_xcconfig? library_xcconfig
549
+
550
+ def non_library_xcconfig?
551
+ !library_xcconfig?
552
+ end
553
+
554
+ # @return [Specification]
555
+ # The non-library specification these build settings are for or `nil`.
556
+ #
557
+ attr_reader :non_library_spec
558
+
559
+ # Initializes a new instance
560
+ #
561
+ # @param [PodTarget] target
562
+ # see {#target}
563
+ #
564
+ # @param [Specification] non_library_spec
565
+ # see {#non_library_spec}
566
+ #
567
+ # @param [Symbol] configuration
568
+ # see {#configuration}
569
+ #
570
+ def initialize(target, non_library_spec = nil, configuration: nil)
571
+ super(target)
572
+ if @non_library_spec = non_library_spec
573
+ @test_xcconfig = non_library_spec.test_specification?
574
+ @app_xcconfig = non_library_spec.app_specification?
575
+ @xcconfig_spec_type = non_library_spec.spec_type
576
+ @library_xcconfig = false
577
+ else
578
+ @test_xcconfig = @app_xcconfig = false
579
+ @xcconfig_spec_type = :library
580
+ @library_xcconfig = true
581
+ end
582
+ (@configuration = configuration) || raise("No configuration for #{self}.")
583
+ end
584
+
585
+ # @return [Xcodeproj::Xconfig]
586
+ define_build_settings_method :xcconfig, :memoized => true do
587
+ xcconfig = super()
588
+ merge_spec_xcconfig_into_xcconfig(merged_pod_target_xcconfigs, xcconfig)
589
+ end
590
+
591
+ #-------------------------------------------------------------------------#
592
+
593
+ # @!group Paths
594
+
595
+ # @return [String]
596
+ define_build_settings_method :pods_root, :build_setting => true do
597
+ '${SRCROOT}'
598
+ end
599
+
600
+ # @return [String]
601
+ define_build_settings_method :pods_target_srcroot, :build_setting => true do
602
+ target.pod_target_srcroot
603
+ end
604
+
605
+ #-------------------------------------------------------------------------#
606
+
607
+ # @!group Frameworks
608
+
609
+ # @return [Array<String>]
610
+ define_build_settings_method :consumer_frameworks, :memoized => true do
611
+ spec_consumers.flat_map(&:frameworks)
612
+ end
613
+
614
+ # @return [Array<String>]
615
+ define_build_settings_method :frameworks, :memoized => true, :sorted => true, :uniqued => true do
616
+ return [] if target.build_as_static? && library_xcconfig?
617
+
618
+ frameworks = []
619
+ frameworks.concat consumer_frameworks
620
+ if library_xcconfig?
621
+ # We know that this library target is being built dynamically based
622
+ # on the guard above, so include any vendored static frameworks and vendored xcframeworks.
623
+ if target.should_build?
624
+ frameworks.concat vendored_static_frameworks.map { |l| File.basename(l, '.framework') }
625
+ frameworks.concat vendored_xcframeworks.
626
+ select { |xcf| xcf.build_type.static_framework? }.
627
+ map(&:name).
628
+ uniq
629
+
630
+ # Include direct dynamic dependencies to the linker flags. We used to add those in the 'Link Binary With Libraries'
631
+ # phase but we no longer do since we cannot differentiate between debug or release configurations within
632
+ # that phase.
633
+ frameworks.concat target.dependent_targets_by_config[@configuration].flat_map { |pt| pt.build_settings[@configuration].dynamic_frameworks_to_import }
634
+ else
635
+ # Also include any vendored dynamic frameworks of dependencies.
636
+ frameworks.concat dependent_targets.reject(&:should_build?).flat_map { |pt| pt.build_settings[@configuration].dynamic_frameworks_to_import }
637
+ end
638
+ else
639
+ frameworks.concat dependent_targets_to_link.flat_map { |pt| pt.build_settings[@configuration].frameworks_to_import }
640
+ end
641
+
642
+ frameworks
643
+ end
644
+
645
+ # @return [Array<String>]
646
+ define_build_settings_method :static_frameworks_to_import, :memoized => true do
647
+ static_frameworks_to_import = []
648
+ static_frameworks_to_import.concat vendored_static_frameworks.map { |f| File.basename(f, '.framework') } unless target.should_build? && target.build_as_dynamic?
649
+ unless target.should_build? && target.build_as_dynamic?
650
+ static_frameworks_to_import.concat vendored_xcframeworks.
651
+ select { |xcf| xcf.build_type.static_framework? }.
652
+ map(&:name).
653
+ uniq
654
+ end
655
+ static_frameworks_to_import << target.product_basename if target.should_build? && target.build_as_static_framework?
656
+ static_frameworks_to_import
657
+ end
658
+
659
+ # @return [Array<String>]
660
+ define_build_settings_method :dynamic_frameworks_to_import, :memoized => true do
661
+ dynamic_frameworks_to_import = vendored_dynamic_frameworks.map { |f| File.basename(f, '.framework') }
662
+ dynamic_frameworks_to_import.concat vendored_xcframeworks.
663
+ select { |xcf| xcf.build_type.dynamic_framework? }.
664
+ map(&:name).
665
+ uniq
666
+ dynamic_frameworks_to_import << target.product_basename if target.should_build? && target.build_as_dynamic_framework?
667
+ dynamic_frameworks_to_import.concat consumer_frameworks
668
+ dynamic_frameworks_to_import
669
+ end
670
+
671
+ # @return [Array<String>]
672
+ define_build_settings_method :weak_frameworks, :memoized => true do
673
+ return [] if target.build_as_static? && library_xcconfig?
674
+
675
+ weak_frameworks = spec_consumers.flat_map(&:weak_frameworks)
676
+ weak_frameworks.concat dependent_targets.flat_map { |pt| pt.build_settings[@configuration].weak_frameworks_to_import }
677
+ weak_frameworks
678
+ end
679
+
680
+ # @return [Array<String>]
681
+ define_build_settings_method :frameworks_to_import, :memoized => true, :sorted => true, :uniqued => true do
682
+ static_frameworks_to_import + dynamic_frameworks_to_import
683
+ end
684
+
685
+ # @return [Array<String>]
686
+ define_build_settings_method :weak_frameworks_to_import, :memoized => true, :sorted => true, :uniqued => true do
687
+ spec_consumers.flat_map(&:weak_frameworks)
688
+ end
689
+
690
+ # @return [Array<String>]
691
+ define_build_settings_method :framework_search_paths, :build_setting => true, :memoized => true, :sorted => true, :uniqued => true do
692
+ paths = super().dup
693
+ paths.concat dependent_targets.flat_map { |pt| pt.build_settings[@configuration].framework_search_paths_to_import }
694
+ paths.concat framework_search_paths_to_import
695
+ paths.delete(target.configuration_build_dir(CONFIGURATION_BUILD_DIR_VARIABLE)) if library_xcconfig?
696
+ paths
697
+ end
698
+
699
+ # @return [String]
700
+ define_build_settings_method :framework_header_search_path, :memoized => true do
701
+ return unless target.build_as_framework?
702
+ "#{target.build_product_path}/Headers"
703
+ end
704
+
705
+ # @return [Array<String>]
706
+ define_build_settings_method :vendored_framework_search_paths, :memoized => true do
707
+ search_paths = []
708
+ search_paths.concat file_accessors.
709
+ flat_map(&:vendored_frameworks).
710
+ map { |f| File.join '${PODS_ROOT}', f.dirname.relative_path_from(target.sandbox.root) }
711
+ xcframework_intermediates = vendored_xcframeworks.
712
+ select { |xcf| xcf.build_type.framework? }.
713
+ map { |xcf| BuildSettings.xcframework_intermediate_dir(xcf) }.
714
+ uniq
715
+ search_paths.concat xcframework_intermediates
716
+ search_paths
717
+ end
718
+
719
+ # @return [Array<String>]
720
+ define_build_settings_method :framework_search_paths_to_import, :memoized => true do
721
+ paths = framework_search_paths_to_import_developer_frameworks(consumer_frameworks)
722
+ paths.concat vendored_framework_search_paths
723
+ return paths unless target.build_as_framework? && target.should_build?
724
+
725
+ paths + [target.configuration_build_dir(CONFIGURATION_BUILD_DIR_VARIABLE)]
726
+ end
727
+
728
+ # @return [Array<String>]
729
+ define_build_settings_method :vendored_static_frameworks, :memoized => true do
730
+ file_accessors.flat_map(&:vendored_static_frameworks)
731
+ end
732
+
733
+ # @return [Array<String>]
734
+ define_build_settings_method :vendored_dynamic_frameworks, :memoized => true do
735
+ file_accessors.flat_map(&:vendored_dynamic_frameworks)
736
+ end
737
+
738
+ # @return [Array<Xcode::XCFramework>]
739
+ define_build_settings_method :vendored_xcframeworks, :memoized => true do
740
+ file_accessors.flat_map do |file_accessor|
741
+ file_accessor.vendored_xcframeworks.map { |path| load_xcframework(file_accessor.spec.name, path) }
742
+ end
743
+ end
744
+
745
+ # @return [Array<String>]
746
+ define_build_settings_method :system_framework_search_paths, :build_setting => true, :memoized => true, :sorted => true, :uniqued => true do
747
+ return ['$(PLATFORM_DIR)/Developer/Library/Frameworks'] if should_apply_xctunwrap_fix?
748
+ []
749
+ end
750
+
751
+ #-------------------------------------------------------------------------#
752
+
753
+ # @!group Libraries
754
+
755
+ # Converts array of library path references to just the names to use
756
+ # link each library, e.g. from '/path/to/libSomething.a' to 'Something'
757
+ #
758
+ # @param [Array<String>] libraries
759
+ #
760
+ # @return [Array<String>]
761
+ #
762
+ def linker_names_from_libraries(libraries)
763
+ libraries.map { |l| File.basename(l, File.extname(l)).sub(/\Alib/, '') }
764
+ end
765
+
766
+ # @return [Array<String>]
767
+ define_build_settings_method :libraries, :memoized => true, :sorted => true, :uniqued => true do
768
+ return [] if library_xcconfig? && target.build_as_static?
769
+
770
+ libraries = []
771
+ if non_library_xcconfig? || target.build_as_dynamic?
772
+ libraries.concat linker_names_from_libraries(vendored_static_libraries)
773
+ libraries.concat libraries_to_import
774
+ xcframework_libraries = vendored_xcframeworks.
775
+ select { |xcf| xcf.build_type.static_library? }.
776
+ flat_map { |xcf| linker_names_from_libraries([xcf.slices.first.binary_path]) }.
777
+ uniq
778
+ libraries.concat xcframework_libraries
779
+ end
780
+ if non_library_xcconfig?
781
+ libraries.concat dependent_targets.flat_map { |pt| pt.build_settings[@configuration].dynamic_libraries_to_import }
782
+ libraries.concat dependent_targets_to_link.flat_map { |pt| pt.build_settings[@configuration].static_libraries_to_import }
783
+ end
784
+ libraries
785
+ end
786
+
787
+ # @return [Array<String>]
788
+ define_build_settings_method :static_libraries_to_import, :memoized => true do
789
+ static_libraries_to_import = []
790
+ unless target.should_build? && target.build_as_dynamic?
791
+ static_libraries_to_import.concat linker_names_from_libraries(vendored_static_libraries)
792
+ xcframework_libraries = vendored_xcframeworks.
793
+ select { |xcf| xcf.build_type.static_library? }.
794
+ flat_map { |xcf| linker_names_from_libraries([xcf.slices.first.binary_path]) }.
795
+ uniq
796
+ static_libraries_to_import.concat linker_names_from_libraries(xcframework_libraries)
797
+ end
798
+ static_libraries_to_import << target.product_basename if target.should_build? && target.build_as_static_library?
799
+ static_libraries_to_import
800
+ end
801
+
802
+ # @return [Array<String>]
803
+ define_build_settings_method :dynamic_libraries_to_import, :memoized => true do
804
+ dynamic_libraries_to_import = linker_names_from_libraries(vendored_dynamic_libraries)
805
+ dynamic_libraries_to_import.concat spec_consumers.flat_map(&:libraries)
806
+ dynamic_libraries_to_import << target.product_basename if target.should_build? && target.build_as_dynamic_library?
807
+ dynamic_libraries_to_import
808
+ end
809
+
810
+ # @return [Array<String>]
811
+ define_build_settings_method :libraries_to_import, :memoized => true, :sorted => true, :uniqued => true do
812
+ static_libraries_to_import + dynamic_libraries_to_import
813
+ end
814
+
815
+ # @return [Array<String>]
816
+ define_build_settings_method :library_search_paths, :build_setting => true, :memoized => true, :sorted => true, :uniqued => true do
817
+ library_search_paths = should_apply_xctunwrap_fix? ? ['$(PLATFORM_DIR)/Developer/usr/lib'] : []
818
+ return library_search_paths if library_xcconfig? && target.build_as_static?
819
+
820
+ library_search_paths.concat library_search_paths_to_import.dup
821
+ library_search_paths.concat dependent_targets.flat_map { |pt| pt.build_settings[@configuration].vendored_dynamic_library_search_paths }
822
+ if library_xcconfig?
823
+ library_search_paths.delete(target.configuration_build_dir(CONFIGURATION_BUILD_DIR_VARIABLE))
824
+ else
825
+ library_search_paths.concat(dependent_targets.flat_map { |pt| pt.build_settings[@configuration].library_search_paths_to_import })
826
+ end
827
+
828
+ library_search_paths
829
+ end
830
+
831
+ # @return [Array<String>]
832
+ define_build_settings_method :vendored_static_libraries, :memoized => true do
833
+ file_accessors.flat_map(&:vendored_static_libraries)
834
+ end
835
+
836
+ # @return [Array<String>]
837
+ define_build_settings_method :vendored_dynamic_libraries, :memoized => true do
838
+ file_accessors.flat_map(&:vendored_dynamic_libraries)
839
+ end
840
+
841
+ # @return [Array<String>]
842
+ define_build_settings_method :vendored_static_library_search_paths, :memoized => true do
843
+ paths = vendored_static_libraries.map { |f| File.join '${PODS_ROOT}', f.dirname.relative_path_from(target.sandbox.root) }
844
+ paths.concat vendored_xcframeworks.
845
+ select { |xcf| xcf.build_type.static_library? }.
846
+ map { |xcf| BuildSettings.xcframework_intermediate_dir(xcf) }
847
+ paths
848
+ end
849
+
850
+ # @return [Array<String>]
851
+ define_build_settings_method :vendored_dynamic_library_search_paths, :memoized => true do
852
+ paths = vendored_dynamic_libraries.map { |f| File.join '${PODS_ROOT}', f.dirname.relative_path_from(target.sandbox.root) }
853
+ paths.concat vendored_xcframeworks.
854
+ select { |xcf| xcf.build_type.dynamic_library? }.
855
+ map { |xcf| BuildSettings.xcframework_intermediate_dir(xcf) }
856
+ paths
857
+ end
858
+
859
+ # @return [Array<String>]
860
+ define_build_settings_method :library_search_paths_to_import, :memoized => true do
861
+ search_paths = vendored_static_library_search_paths + vendored_dynamic_library_search_paths
862
+ if target.uses_swift? || other_swift_flags_without_swift?
863
+ search_paths << '/usr/lib/swift'
864
+ search_paths << '${DT_TOOLCHAIN_DIR}/usr/lib/swift/${PLATFORM_NAME}'
865
+ search_paths << '$(PLATFORM_DIR)/Developer/Library/Frameworks' if test_xcconfig?
866
+ end
867
+ return search_paths if target.build_as_framework? || !target.should_build?
868
+
869
+ search_paths << target.configuration_build_dir(CONFIGURATION_BUILD_DIR_VARIABLE)
870
+ end
871
+
872
+ #-------------------------------------------------------------------------#
873
+
874
+ # @!group Clang
875
+
876
+ # @return [Array<String>]
877
+ define_build_settings_method :module_map_files, :memoized => true do
878
+ dependent_targets.map { |pt| pt.build_settings[@configuration].module_map_file_to_import }.compact.sort
879
+ end
880
+
881
+ # @return [Array<String>]
882
+ define_build_settings_method :module_map_file_to_import, :memoized => true do
883
+ return unless target.should_build?
884
+ return if target.build_as_framework? # framework module maps are automatically discovered
885
+ return unless target.defines_module?
886
+
887
+ if target.uses_swift?
888
+ # for swift, we have a custom build phase that copies in the module map, appending the .Swift module
889
+ "${PODS_CONFIGURATION_BUILD_DIR}/#{target.label}/#{target.product_module_name}.modulemap"
890
+ else
891
+ "${PODS_ROOT}/#{target.module_map_path.relative_path_from(target.sandbox.root)}"
892
+ end
893
+ end
894
+
895
+ # @return [Array<String>]
896
+ define_build_settings_method :header_search_paths, :build_setting => true, :memoized => true, :sorted => true do
897
+ paths = target.header_search_paths(:include_dependent_targets_for_test_spec => test_xcconfig? && non_library_spec, :include_dependent_targets_for_app_spec => app_xcconfig? && non_library_spec, :configuration => @configuration)
898
+
899
+ dependent_vendored_xcframeworks = []
900
+ dependent_vendored_xcframeworks.concat vendored_xcframeworks
901
+ dependent_vendored_xcframeworks.concat dependent_targets.flat_map { |pt| pt.build_settings[@configuration].vendored_xcframeworks }
902
+ paths.concat dependent_vendored_xcframeworks.
903
+ select { |xcf| xcf.build_type.static_library? }.
904
+ map { |xcf| "#{BuildSettings.xcframework_intermediate_dir(xcf)}/Headers" }.
905
+ compact
906
+ paths
907
+ end
908
+
909
+ # @return [Array<String>]
910
+ define_build_settings_method :public_header_search_paths, :memoized => true, :sorted => true do
911
+ target.header_search_paths(:include_dependent_targets_for_test_spec => test_xcconfig? && non_library_spec, :include_dependent_targets_for_app_spec => app_xcconfig? && non_library_spec, :include_private_headers => false, :configuration => @configuration)
912
+ end
913
+
914
+ #-------------------------------------------------------------------------#
915
+
916
+ # @!group Swift
917
+
918
+ # @see BuildSettings#other_swift_flags_without_swift?
919
+ def other_swift_flags_without_swift?
920
+ return false if library_xcconfig?
921
+
922
+ target.uses_swift_for_spec?(non_library_spec)
923
+ end
924
+
925
+ # @return [Array<String>]
926
+ define_build_settings_method :other_swift_flags, :build_setting => true, :memoized => true do
927
+ return unless target.uses_swift? || other_swift_flags_without_swift?
928
+
929
+ flags = super()
930
+ flags << '-suppress-warnings' if target.inhibit_warnings? && library_xcconfig?
931
+ if !target.build_as_framework? && target.defines_module? && library_xcconfig?
932
+ flags.concat %w( -import-underlying-module -Xcc -fmodule-map-file=${SRCROOT}/${MODULEMAP_FILE} )
933
+ end
934
+ flags
935
+ end
936
+
937
+ # @return [Array<String>]
938
+ define_build_settings_method :swift_include_paths, :build_setting => true, :memoized => true, :sorted => true, :uniqued => true do
939
+ paths = dependent_targets.flat_map { |pt| pt.build_settings[@configuration].swift_include_paths_to_import }
940
+ paths.concat swift_include_paths_to_import if non_library_xcconfig?
941
+ vendored_static_library_search_paths = dependent_targets.flat_map { |pt| pt.build_settings[@configuration].vendored_static_library_search_paths }
942
+ paths.concat vendored_static_library_search_paths
943
+ paths.concat ['$(PLATFORM_DIR)/Developer/usr/lib'] if should_apply_xctunwrap_fix?
944
+ paths
945
+ end
946
+
947
+ # @return [Array<String>]
948
+ define_build_settings_method :swift_include_paths_to_import, :memoized => true do
949
+ return [] unless target.uses_swift? && !target.build_as_framework?
950
+
951
+ [target.configuration_build_dir(CONFIGURATION_BUILD_DIR_VARIABLE)]
952
+ end
953
+
954
+ #-------------------------------------------------------------------------#
955
+
956
+ # @!group Linking
957
+
958
+ # @return [Boolean] whether the `-ObjC` linker flag is required.
959
+ #
960
+ # @note this is only true when generating build settings for a test bundle
961
+ #
962
+ def requires_objc_linker_flag?
963
+ test_xcconfig? || app_xcconfig?
964
+ end
965
+
966
+ # @return [Boolean] whether the `-fobjc-arc` linker flag is required.
967
+ #
968
+ define_build_settings_method :requires_fobjc_arc?, :memoized => true do
969
+ target.podfile.set_arc_compatibility_flag? &&
970
+ file_accessors.any? { |fa| fa.spec_consumer.requires_arc? }
971
+ end
972
+
973
+ # @return [Array<String>]
974
+ define_build_settings_method :ld_runpath_search_paths, :build_setting => true, :memoized => true do
975
+ return if library_xcconfig?
976
+ _ld_runpath_search_paths(:test_bundle => test_xcconfig?,
977
+ :uses_swift => other_swift_flags_without_swift? || dependent_targets.any?(&:uses_swift?))
978
+ end
979
+
980
+ #-------------------------------------------------------------------------#
981
+
982
+ # @!group Packaging
983
+
984
+ # @return [String]
985
+ define_build_settings_method :skip_install, :build_setting => true do
986
+ 'YES'
987
+ end
988
+
989
+ # @return [String]
990
+ define_build_settings_method :product_bundle_identifier, :build_setting => true do
991
+ 'org.cocoapods.${PRODUCT_NAME:rfc1034identifier}'
992
+ end
993
+
994
+ # @return [String]
995
+ define_build_settings_method :configuration_build_dir, :build_setting => true, :memoized => true do
996
+ return if non_library_xcconfig?
997
+ target.configuration_build_dir(CONFIGURATION_BUILD_DIR_VARIABLE)
998
+ end
999
+
1000
+ # @return [String]
1001
+ define_build_settings_method :application_extension_api_only, :build_setting => true, :memoized => true do
1002
+ target.application_extension_api_only ? 'YES' : nil
1003
+ end
1004
+
1005
+ # @return [String]
1006
+ define_build_settings_method :build_library_for_distribution, :build_setting => true, :memoized => true do
1007
+ target.build_library_for_distribution ? 'YES' : nil
1008
+ end
1009
+
1010
+ #-------------------------------------------------------------------------#
1011
+
1012
+ # @!group Target Properties
1013
+
1014
+ # @return [Array<PodTarget>]
1015
+ define_build_settings_method :dependent_targets, :memoized => true do
1016
+ select_maximal_pod_targets(
1017
+ if test_xcconfig?
1018
+ target.dependent_targets_for_test_spec(non_library_spec, :configuration => @configuration)
1019
+ elsif app_xcconfig?
1020
+ target.dependent_targets_for_app_spec(non_library_spec, :configuration => @configuration)
1021
+ else
1022
+ target.recursive_dependent_targets(:configuration => @configuration)
1023
+ end,
1024
+ )
1025
+ end
1026
+
1027
+ # @return [Array<PodTarget>]
1028
+ define_build_settings_method :dependent_targets_to_link, :memoized => true do
1029
+ if test_xcconfig?
1030
+ # we're embedding into an app defined by an app spec
1031
+ host_targets = target.app_host_dependent_targets_for_spec(non_library_spec, :configuration => @configuration)
1032
+ dependent_targets - host_targets
1033
+ else
1034
+ dependent_targets
1035
+ end
1036
+ end
1037
+
1038
+ # Returns the +pod_target_xcconfig+ for the pod target and its spec
1039
+ # consumers grouped by keys
1040
+ #
1041
+ # @return [Hash{String,Hash{Target,String}]
1042
+ #
1043
+ def pod_target_xcconfig_values_by_consumer_by_key
1044
+ spec_consumers.each_with_object({}) do |spec_consumer, hash|
1045
+ spec_consumer.pod_target_xcconfig.each do |k, v|
1046
+ (hash[k] ||= {})[spec_consumer] = v
1047
+ end
1048
+ end
1049
+ end
1050
+
1051
+ # Merges the +pod_target_xcconfig+ for all pod targets into a
1052
+ # single hash and warns on conflicting definitions.
1053
+ #
1054
+ # @return [Hash{String, String}]
1055
+ #
1056
+ define_build_settings_method :merged_pod_target_xcconfigs, :memoized => true do
1057
+ merged_xcconfigs(pod_target_xcconfig_values_by_consumer_by_key, :pod_target_xcconfig,
1058
+ :overriding => non_library_xcconfig? ? target.build_settings[@configuration].merged_pod_target_xcconfigs : {})
1059
+ end
1060
+
1061
+ # @return [Array<Sandbox::FileAccessor>]
1062
+ define_build_settings_method :file_accessors, :memoized => true do
1063
+ if non_library_xcconfig?
1064
+ target.file_accessors.select { |fa| non_library_spec == fa.spec }
1065
+ else
1066
+ target.file_accessors.select { |fa| fa.spec.spec_type == @xcconfig_spec_type }
1067
+ end
1068
+ end
1069
+
1070
+ # @return [Array<Specification::Consumer>]
1071
+ define_build_settings_method :spec_consumers, :memoized => true do
1072
+ if non_library_xcconfig?
1073
+ target.spec_consumers.select { |sc| non_library_spec == sc.spec }
1074
+ else
1075
+ target.spec_consumers.select { |sc| sc.spec.spec_type == @xcconfig_spec_type }
1076
+ end
1077
+ end
1078
+
1079
+ # Xcode 11 causes an issue with frameworks or libraries before 12.2 deployment target that link or are part of
1080
+ # test bundles that use XCTUnwrap. Apple has provided an official work around for this.
1081
+ #
1082
+ # @see https://developer.apple.com/documentation/xcode_release_notes/xcode_11_release_notes
1083
+ #
1084
+ # @return [Boolean] Whether to apply the fix or not.
1085
+ #
1086
+ define_build_settings_method :should_apply_xctunwrap_fix?, :memoized => true do
1087
+ library_xcconfig? &&
1088
+ target.platform.name == :ios &&
1089
+ Version.new(target.platform.deployment_target) < Version.new('12.2') &&
1090
+ (frameworks_to_import + weak_frameworks_to_import).uniq.include?('XCTest')
1091
+ end
1092
+
1093
+ #-------------------------------------------------------------------------#
1094
+ end
1095
+
1096
+ # A subclass that generates build settings for a `PodTarget`
1097
+ class AggregateTargetSettings < BuildSettings
1098
+ #-------------------------------------------------------------------------#
1099
+
1100
+ # @!group Public API
1101
+
1102
+ # @see BuildSettings.build_settings_names
1103
+ def self.build_settings_names
1104
+ @build_settings_names | BuildSettings.build_settings_names
1105
+ end
1106
+
1107
+ # @return [Symbol]
1108
+ # The build configuration these settings will be used for
1109
+ attr_reader :configuration_name
1110
+
1111
+ # Initializes a new instance
1112
+ #
1113
+ # @param [AggregateTarget] target
1114
+ # see {#target}
1115
+ #
1116
+ # @param [Symbol] configuration_name
1117
+ # see {#configuration_name}
1118
+ #
1119
+ def initialize(target, configuration_name, configuration: nil)
1120
+ super(target)
1121
+ @configuration_name = configuration_name
1122
+ (@configuration = configuration) || raise("No configuration for #{self}.")
1123
+ end
1124
+
1125
+ # @return [Xcodeproj::Config] xcconfig
1126
+ define_build_settings_method :xcconfig, :memoized => true do
1127
+ xcconfig = super()
1128
+ merge_spec_xcconfig_into_xcconfig(merged_user_target_xcconfigs, xcconfig)
1129
+ end
1130
+
1131
+ #-------------------------------------------------------------------------#
1132
+
1133
+ # @!group Paths
1134
+
1135
+ # @return [String]
1136
+ define_build_settings_method :pods_podfile_dir_path, :build_setting => true, :memoized => true do
1137
+ target.podfile_dir_relative_path
1138
+ end
1139
+
1140
+ # @return [String]
1141
+ define_build_settings_method :pods_root, :build_setting => true, :memoized => true do
1142
+ target.relative_pods_root
1143
+ end
1144
+
1145
+ #-------------------------------------------------------------------------#
1146
+
1147
+ # @!group Frameworks
1148
+
1149
+ # @return [Array<String>]
1150
+ define_build_settings_method :frameworks, :memoized => true, :sorted => true, :uniqued => true, :from_pod_targets_to_link => true, :from_search_paths_aggregate_targets => :dynamic_frameworks_to_import do
1151
+ []
1152
+ end
1153
+
1154
+ # @return [Array<String>]
1155
+ define_build_settings_method :weak_frameworks, :memoized => true, :sorted => true, :uniqued => true, :from_pod_targets_to_link => true, :from_search_paths_aggregate_targets => :weak_frameworks do
1156
+ []
1157
+ end
1158
+
1159
+ # @return [Array<String>]
1160
+ define_build_settings_method :framework_search_paths, :build_setting => true, :memoized => true, :sorted => true, :uniqued => true, :from_pod_targets_to_link => true, :from_search_paths_aggregate_targets => :framework_search_paths_to_import do
1161
+ []
1162
+ end
1163
+
1164
+ #-------------------------------------------------------------------------#
1165
+
1166
+ # @!group Libraries
1167
+
1168
+ # @return [Array<String>]
1169
+ define_build_settings_method :libraries, :memoized => true, :sorted => true, :uniqued => true, :from_pod_targets_to_link => true, :from_search_paths_aggregate_targets => :dynamic_libraries_to_import do
1170
+ []
1171
+ end
1172
+
1173
+ # @return [Array<String>]
1174
+ define_build_settings_method :library_search_paths, :build_setting => true, :memoized => true, :sorted => true, :uniqued => true, :from_pod_targets_to_link => true, :from_search_paths_aggregate_targets => :vendored_dynamic_library_search_paths do
1175
+ []
1176
+ end
1177
+
1178
+ #-------------------------------------------------------------------------#
1179
+
1180
+ # @!group Clang
1181
+
1182
+ # @return [Array<String>]
1183
+ define_build_settings_method :header_search_paths, :build_setting => true, :memoized => true, :sorted => true, :uniqued => true do
1184
+ paths = []
1185
+
1186
+ if !target.build_as_framework? || !pod_targets.all?(&:should_build?)
1187
+ paths.concat target.sandbox.public_headers.search_paths(target.platform)
1188
+ end
1189
+
1190
+ # Make frameworks headers discoverable with any syntax (quotes,
1191
+ # brackets, @import, etc.)
1192
+ paths.concat pod_targets.
1193
+ select { |pt| pt.build_as_framework? && pt.should_build? }.
1194
+ map { |pt| pt.build_settings[@configuration].framework_header_search_path }
1195
+
1196
+ xcframework_library_headers = pod_targets.flat_map { |pt| pt.build_settings[@configuration].vendored_xcframeworks }.
1197
+ select { |xcf| xcf.build_type.static_library? }.
1198
+ map { |xcf| "#{BuildSettings.xcframework_intermediate_dir(xcf)}/Headers" }.
1199
+ compact
1200
+
1201
+ paths.concat xcframework_library_headers
1202
+
1203
+ paths.concat target.search_paths_aggregate_targets.flat_map { |at| at.build_settings(configuration_name).header_search_paths }
1204
+
1205
+ paths
1206
+ end
1207
+
1208
+ # @return [Array<String>]
1209
+ define_build_settings_method :other_cflags, :build_setting => true, :memoized => true do
1210
+ flags = super()
1211
+
1212
+ pod_targets_inhibiting_warnings = pod_targets.select(&:inhibit_warnings?)
1213
+
1214
+ silenced_headers = []
1215
+ silenced_frameworks = []
1216
+ pod_targets_inhibiting_warnings.each do |pt|
1217
+ if pt.build_as_framework? && pt.should_build?
1218
+ silenced_headers.append pt.build_settings[@configuration].framework_header_search_path
1219
+ else
1220
+ silenced_headers.concat pt.build_settings[@configuration].public_header_search_paths
1221
+ end
1222
+ silenced_frameworks.concat pt.build_settings[@configuration].framework_search_paths_to_import
1223
+ end
1224
+
1225
+ flags += silenced_headers.uniq.flat_map { |p| ['-isystem', p] }
1226
+ flags += silenced_frameworks.uniq.flat_map { |p| ['-iframework', p] }
1227
+
1228
+ flags
1229
+ end
1230
+
1231
+ # @return [Array<String>]
1232
+ define_build_settings_method :module_map_files, :memoized => true, :sorted => true, :uniqued => true, :compacted => true, :from_search_paths_aggregate_targets => :module_map_file_to_import do
1233
+ pod_targets.map { |pt| pt.build_settings[@configuration].module_map_file_to_import }
1234
+ end
1235
+
1236
+ #-------------------------------------------------------------------------#
1237
+
1238
+ # @!group Swift
1239
+
1240
+ # @see BuildSettings#other_swift_flags_without_swift?
1241
+ def other_swift_flags_without_swift?
1242
+ module_map_files.any?
1243
+ end
1244
+
1245
+ # @return [Array<String>]
1246
+ define_build_settings_method :swift_include_paths, :build_setting => true, :memoized => true, :sorted => true, :uniqued => true, :from_pod_targets_to_link => true, :from_search_paths_aggregate_targets => :swift_include_paths_to_import do
1247
+ []
1248
+ end
1249
+
1250
+ # @return [String]
1251
+ define_build_settings_method :always_embed_swift_standard_libraries, :build_setting => true, :memoized => true do
1252
+ return unless must_embed_swift?
1253
+ return if target_swift_version < EMBED_STANDARD_LIBRARIES_MINIMUM_VERSION
1254
+
1255
+ 'YES'
1256
+ end
1257
+
1258
+ # @return [String]
1259
+ define_build_settings_method :embedded_content_contains_swift, :build_setting => true, :memoized => true do
1260
+ return unless must_embed_swift?
1261
+ return if target_swift_version >= EMBED_STANDARD_LIBRARIES_MINIMUM_VERSION
1262
+
1263
+ 'YES'
1264
+ end
1265
+
1266
+ # @return [Boolean]
1267
+ define_build_settings_method :must_embed_swift?, :memoized => true do
1268
+ !target.requires_host_target? && pod_targets.any?(&:uses_swift?)
1269
+ end
1270
+
1271
+ #-------------------------------------------------------------------------#
1272
+
1273
+ # @!group Linking
1274
+
1275
+ # @return [Array<String>]
1276
+ define_build_settings_method :ld_runpath_search_paths, :build_setting => true, :memoized => true, :uniqued => true do
1277
+ return unless pod_targets.any?(&:build_as_dynamic?) || any_vendored_dynamic_artifacts?
1278
+ symbol_type = target.user_targets.map(&:symbol_type).uniq.first
1279
+ test_bundle = symbol_type == :octest_bundle || symbol_type == :unit_test_bundle || symbol_type == :ui_test_bundle
1280
+ _ld_runpath_search_paths(:requires_host_target => target.requires_host_target?, :test_bundle => test_bundle,
1281
+ :uses_swift => pod_targets.any?(&:uses_swift?))
1282
+ end
1283
+
1284
+ # @return [Boolean]
1285
+ define_build_settings_method :any_vendored_dynamic_artifacts?, :memoized => true do
1286
+ pod_targets.any? do |pt|
1287
+ pt.file_accessors.any? do |fa|
1288
+ !fa.vendored_dynamic_artifacts.empty? || !fa.vendored_dynamic_xcframeworks.empty?
1289
+ end
1290
+ end
1291
+ end
1292
+
1293
+ # @return [Boolean]
1294
+ define_build_settings_method :any_vendored_static_artifacts?, :memoized => true do
1295
+ pod_targets.any? do |pt|
1296
+ pt.file_accessors.any? do |fa|
1297
+ !fa.vendored_static_artifacts.empty?
1298
+ end
1299
+ end
1300
+ end
1301
+
1302
+ # @return [Boolean]
1303
+ define_build_settings_method :requires_objc_linker_flag?, :memoized => true do
1304
+ pod_targets.any?(&:build_as_static?) ||
1305
+ any_vendored_static_artifacts?
1306
+ end
1307
+
1308
+ # @return [Boolean]
1309
+ define_build_settings_method :requires_fobjc_arc?, :memoized => true do
1310
+ target.podfile.set_arc_compatibility_flag? &&
1311
+ target.spec_consumers.any?(&:requires_arc?)
1312
+ end
1313
+
1314
+ #-------------------------------------------------------------------------#
1315
+
1316
+ # @!group Target Properties
1317
+
1318
+ # @return [Version] the SWIFT_VERSION of the target being integrated
1319
+ #
1320
+ define_build_settings_method :target_swift_version, :memoized => true, :frozen => false do
1321
+ swift_version = target.target_definition.swift_version
1322
+ swift_version = nil if swift_version.blank?
1323
+ Version.new(swift_version)
1324
+ end
1325
+
1326
+ EMBED_STANDARD_LIBRARIES_MINIMUM_VERSION = Version.new('2.3')
1327
+ private_constant :EMBED_STANDARD_LIBRARIES_MINIMUM_VERSION
1328
+
1329
+ # Returns the {PodTarget}s which are active for the current
1330
+ # configuration name.
1331
+ #
1332
+ # @return [Array<PodTarget>]
1333
+ #
1334
+ define_build_settings_method :pod_targets, :memoized => true do
1335
+ target.pod_targets_for_build_configuration(configuration_name)
1336
+ end
1337
+
1338
+ # @return [Array<PodTarget>]
1339
+ define_build_settings_method :pod_targets_to_link, :memoized => true do
1340
+ pod_targets -
1341
+ target.search_paths_aggregate_targets.flat_map { |at| at.build_settings(configuration_name).pod_targets_to_link }
1342
+ end
1343
+
1344
+ # @return [Array<PodTarget>]
1345
+ define_build_settings_method :search_paths_aggregate_target_pod_target_build_settings, :memoized => true, :uniqued => true do
1346
+ pod_targets = target.search_paths_aggregate_targets.flat_map { |at| at.build_settings(configuration_name).pod_targets }
1347
+ pod_targets = select_maximal_pod_targets(pod_targets)
1348
+ pod_targets.map { |pt| pt.build_settings[@configuration] }
1349
+ end
1350
+
1351
+ # Returns the +user_target_xcconfig+ for all pod targets and their spec
1352
+ # consumers grouped by keys
1353
+ #
1354
+ # @return [Hash{String,Hash{Target,String}]
1355
+ #
1356
+ def user_target_xcconfig_values_by_consumer_by_key
1357
+ targets = (pod_targets + target.search_paths_aggregate_targets.flat_map(&:pod_targets)).uniq
1358
+ targets.each_with_object({}) do |target, hash|
1359
+ target.spec_consumers.each do |spec_consumer|
1360
+ spec_consumer.user_target_xcconfig.each do |k, v|
1361
+ # TODO: Need to decide how we are going to ensure settings like these
1362
+ # are always excluded from the user's project.
1363
+ #
1364
+ # See https://github.com/CocoaPods/CocoaPods/issues/1216
1365
+ next if k == 'USE_HEADERMAP'
1366
+ (hash[k] ||= {})[spec_consumer] = v
1367
+ end
1368
+ end
1369
+ end
1370
+ end
1371
+
1372
+ # Merges the +user_target_xcconfig+ for all pod targets into a
1373
+ # single hash and warns on conflicting definitions.
1374
+ #
1375
+ # @return [Hash{String, String}]
1376
+ #
1377
+ define_build_settings_method :merged_user_target_xcconfigs, :memoized => true do
1378
+ merged_xcconfigs(user_target_xcconfig_values_by_consumer_by_key, :user_target_xcconfig)
1379
+ end
1380
+
1381
+ #-------------------------------------------------------------------------#
1382
+ end
1383
+ end
1384
+ end
1385
+ end