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,312 @@
1
+ module Pod
2
+ class Installer
3
+ class Xcode
4
+ class PodsProjectGenerator
5
+ # This class is responsible for integrating a pod target. This includes integrating
6
+ # the test targets included by each pod target.
7
+ #
8
+ class PodTargetIntegrator
9
+ # @return [TargetInstallationResult] the installation result of the target that should be integrated.
10
+ #
11
+ attr_reader :target_installation_result
12
+
13
+ # @return [Boolean] whether to use input/output paths for build phase scripts
14
+ #
15
+ attr_reader :use_input_output_paths
16
+ alias use_input_output_paths? use_input_output_paths
17
+
18
+ # Initialize a new instance
19
+ #
20
+ # @param [TargetInstallationResult] target_installation_result @see #target_installation_result
21
+ # @param [Boolean] use_input_output_paths @see #use_input_output_paths
22
+ #
23
+ def initialize(target_installation_result, use_input_output_paths: true)
24
+ @target_installation_result = target_installation_result
25
+ @use_input_output_paths = use_input_output_paths
26
+ end
27
+
28
+ # Integrates the pod target.
29
+ #
30
+ # @return [void]
31
+ #
32
+ def integrate!
33
+ UI.section(integration_message) do
34
+ target_installation_result.non_library_specs_by_native_target.each do |native_target, spec|
35
+ add_embed_frameworks_script_phase(native_target, spec)
36
+ add_copy_resources_script_phase(native_target, spec)
37
+ add_on_demand_resources(native_target, spec) if spec.app_specification?
38
+ UserProjectIntegrator::TargetIntegrator.create_or_update_user_script_phases(script_phases_for_specs(spec), native_target)
39
+ end
40
+ add_copy_dsyms_script_phase(target_installation_result.native_target)
41
+ add_copy_xcframeworks_script_phase(target_installation_result.native_target)
42
+ UserProjectIntegrator::TargetIntegrator.create_or_update_user_script_phases(script_phases_for_specs(target.library_specs), target_installation_result.native_target)
43
+ end
44
+ end
45
+
46
+ # @return [String] a string representation suitable for debugging.
47
+ #
48
+ def inspect
49
+ "#<#{self.class} for target `#{target.label}'>"
50
+ end
51
+
52
+ private
53
+
54
+ # @!group Integration steps
55
+ #---------------------------------------------------------------------#
56
+
57
+ # Find or create a 'Copy Pods Resources' build phase
58
+ #
59
+ # @param [PBXNativeTarget] native_target
60
+ # the native target for which to add the copy resources script
61
+ #
62
+ # @param [Pod::Specification] spec
63
+ # the specification to integrate
64
+ #
65
+ # @return [void]
66
+ #
67
+ def add_copy_resources_script_phase(native_target, spec)
68
+ script_path = "${PODS_ROOT}/#{target.copy_resources_script_path_for_spec(spec).relative_path_from(target.sandbox.root)}"
69
+
70
+ input_paths_by_config = {}
71
+ output_paths_by_config = {}
72
+
73
+ dependent_targets = if spec.test_specification?
74
+ target.dependent_targets_for_test_spec(spec)
75
+ else
76
+ target.dependent_targets_for_app_spec(spec)
77
+ end
78
+ host_target_spec_names = target.app_host_dependent_targets_for_spec(spec).flat_map do |pt|
79
+ pt.specs.map(&:name)
80
+ end.uniq
81
+ resource_paths = dependent_targets.flat_map do |dependent_target|
82
+ spec_paths_to_include = dependent_target.library_specs.map(&:name)
83
+ spec_paths_to_include -= host_target_spec_names
84
+ spec_paths_to_include << spec.name if dependent_target == target
85
+ dependent_target.resource_paths.values_at(*spec_paths_to_include).flatten.compact
86
+ end.uniq
87
+
88
+ if use_input_output_paths? && !resource_paths.empty?
89
+ input_file_list_path = target.copy_resources_script_input_files_path_for_spec(spec)
90
+ input_file_list_relative_path = "${PODS_ROOT}/#{input_file_list_path.relative_path_from(target.sandbox.root)}"
91
+ input_paths_key = UserProjectIntegrator::TargetIntegrator::XCFileListConfigKey.new(input_file_list_path, input_file_list_relative_path)
92
+ input_paths_by_config[input_paths_key] = [script_path] + resource_paths
93
+
94
+ output_file_list_path = target.copy_resources_script_output_files_path_for_spec(spec)
95
+ output_file_list_relative_path = "${PODS_ROOT}/#{output_file_list_path.relative_path_from(target.sandbox.root)}"
96
+ output_paths_key = UserProjectIntegrator::TargetIntegrator::XCFileListConfigKey.new(output_file_list_path, output_file_list_relative_path)
97
+ output_paths_by_config[output_paths_key] = UserProjectIntegrator::TargetIntegrator.resource_output_paths(resource_paths)
98
+ end
99
+
100
+ if resource_paths.empty?
101
+ UserProjectIntegrator::TargetIntegrator.remove_copy_resources_script_phase_from_target(native_target)
102
+ else
103
+ UserProjectIntegrator::TargetIntegrator.create_or_update_copy_resources_script_phase_to_target(
104
+ native_target, script_path, input_paths_by_config, output_paths_by_config)
105
+ end
106
+ end
107
+
108
+ # Find or create a 'Embed Pods Frameworks' Run Script Build Phase
109
+ #
110
+ # @param [PBXNativeTarget] native_target
111
+ # the native target for which to add the embed frameworks script
112
+ #
113
+ # @param [Pod::Specification] spec
114
+ # the specification to integrate
115
+ #
116
+ # @return [void]
117
+ #
118
+ def add_embed_frameworks_script_phase(native_target, spec)
119
+ script_path = "${PODS_ROOT}/#{target.embed_frameworks_script_path_for_spec(spec).relative_path_from(target.sandbox.root)}"
120
+
121
+ input_paths_by_config = {}
122
+ output_paths_by_config = {}
123
+
124
+ dependent_targets = if spec.test_specification?
125
+ target.dependent_targets_for_test_spec(spec)
126
+ else
127
+ target.dependent_targets_for_app_spec(spec)
128
+ end
129
+ host_target_spec_names = target.app_host_dependent_targets_for_spec(spec).flat_map do |pt|
130
+ pt.specs.map(&:name)
131
+ end.uniq
132
+ framework_paths = dependent_targets.flat_map do |dependent_target|
133
+ spec_paths_to_include = dependent_target.library_specs.map(&:name)
134
+ spec_paths_to_include -= host_target_spec_names
135
+ spec_paths_to_include << spec.name if dependent_target == target
136
+ dependent_target.framework_paths.values_at(*spec_paths_to_include).flatten.compact
137
+ end.uniq
138
+ xcframework_paths = dependent_targets.flat_map do |dependent_target|
139
+ spec_paths_to_include = dependent_target.library_specs.map(&:name)
140
+ spec_paths_to_include -= host_target_spec_names
141
+ spec_paths_to_include << spec.name if dependent_target == target
142
+ dependent_target.xcframeworks.values_at(*spec_paths_to_include).flatten.compact
143
+ end.uniq
144
+
145
+ if use_input_output_paths? && !framework_paths.empty? || !xcframework_paths.empty?
146
+ input_file_list_path = target.embed_frameworks_script_input_files_path_for_spec(spec)
147
+ input_file_list_relative_path = "${PODS_ROOT}/#{input_file_list_path.relative_path_from(target.sandbox.root)}"
148
+ input_paths_key = UserProjectIntegrator::TargetIntegrator::XCFileListConfigKey.new(input_file_list_path, input_file_list_relative_path)
149
+ input_paths_by_config[input_paths_key] = [script_path] + UserProjectIntegrator::TargetIntegrator.embed_frameworks_input_paths(framework_paths, xcframework_paths)
150
+
151
+ output_file_list_path = target.embed_frameworks_script_output_files_path_for_spec(spec)
152
+ output_file_list_relative_path = "${PODS_ROOT}/#{output_file_list_path.relative_path_from(target.sandbox.root)}"
153
+ output_paths_key = UserProjectIntegrator::TargetIntegrator::XCFileListConfigKey.new(output_file_list_path, output_file_list_relative_path)
154
+ output_paths_by_config[output_paths_key] = UserProjectIntegrator::TargetIntegrator.embed_frameworks_output_paths(framework_paths, xcframework_paths)
155
+ end
156
+
157
+ if framework_paths.empty? && xcframework_paths.empty?
158
+ UserProjectIntegrator::TargetIntegrator.remove_embed_frameworks_script_phase_from_target(native_target)
159
+ else
160
+ UserProjectIntegrator::TargetIntegrator.create_or_update_embed_frameworks_script_phase_to_target(
161
+ native_target, script_path, input_paths_by_config, output_paths_by_config)
162
+ end
163
+ end
164
+
165
+ # Find or create a 'Prepare Artifacts' Run Script Build Phase
166
+ #
167
+ # @param [PBXNativeTarget] native_target
168
+ # the native target for which to add the prepare artifacts script
169
+ #
170
+ # @return [void]
171
+ #
172
+ def add_copy_xcframeworks_script_phase(native_target)
173
+ script_path = "${PODS_ROOT}/#{target.copy_xcframeworks_script_path.relative_path_from(target.sandbox.root)}"
174
+
175
+ input_paths_by_config = {}
176
+ output_paths_by_config = {}
177
+
178
+ xcframeworks = target.xcframeworks.values.flatten
179
+
180
+ if use_input_output_paths? && !xcframeworks.empty?
181
+ input_file_list_path = target.copy_xcframeworks_script_input_files_path
182
+ input_file_list_relative_path = "${PODS_ROOT}/#{input_file_list_path.relative_path_from(target.sandbox.root)}"
183
+ input_paths_key = UserProjectIntegrator::TargetIntegrator::XCFileListConfigKey.new(input_file_list_path, input_file_list_relative_path)
184
+ input_paths = input_paths_by_config[input_paths_key] = [script_path]
185
+
186
+ framework_paths = xcframeworks.map { |xcf| "${PODS_ROOT}/#{xcf.path.relative_path_from(target.sandbox.root)}" }
187
+ input_paths.concat framework_paths
188
+
189
+ output_file_list_path = target.copy_xcframeworks_script_output_files_path
190
+ output_file_list_relative_path = "${PODS_ROOT}/#{output_file_list_path.relative_path_from(target.sandbox.root)}"
191
+ output_paths_key = UserProjectIntegrator::TargetIntegrator::XCFileListConfigKey.new(output_file_list_path, output_file_list_relative_path)
192
+ output_paths_by_config[output_paths_key] = xcframeworks.map do |xcf|
193
+ "#{Target::BuildSettings::XCFRAMEWORKS_BUILD_DIR_VARIABLE}/#{xcf.target_name}/#{xcf.name}.framework"
194
+ end
195
+ end
196
+
197
+ if xcframeworks.empty?
198
+ UserProjectIntegrator::TargetIntegrator.remove_copy_xcframeworks_script_phase_from_target(native_target)
199
+ else
200
+ UserProjectIntegrator::TargetIntegrator.create_or_update_copy_xcframeworks_script_phase_to_target(
201
+ native_target, script_path, input_paths_by_config, output_paths_by_config)
202
+ end
203
+ end
204
+
205
+ # Adds a script phase that copies and strips dSYMs that are part of this target. Note this only deals with
206
+ # vendored dSYMs.
207
+ #
208
+ # @param [PBXNativeTarget] native_target
209
+ # the native target for which to add the copy dSYM files build phase.
210
+ #
211
+ # @return [void]
212
+ #
213
+ def add_copy_dsyms_script_phase(native_target)
214
+ script_path = "${PODS_ROOT}/#{target.copy_dsyms_script_path.relative_path_from(target.sandbox.root)}"
215
+ dsym_paths = PodTargetInstaller.dsym_paths(target)
216
+ bcsymbolmap_paths = PodTargetInstaller.bcsymbolmap_paths(target)
217
+
218
+ if dsym_paths.empty? && bcsymbolmap_paths.empty?
219
+ script_phase = native_target.shell_script_build_phases.find do |bp|
220
+ bp.name && bp.name.end_with?(UserProjectIntegrator::TargetIntegrator::COPY_DSYM_FILES_PHASE_NAME)
221
+ end
222
+ native_target.build_phases.delete(script_phase) if script_phase.present?
223
+ return
224
+ end
225
+
226
+ phase_name = UserProjectIntegrator::TargetIntegrator::BUILD_PHASE_PREFIX + UserProjectIntegrator::TargetIntegrator::COPY_DSYM_FILES_PHASE_NAME
227
+ phase = UserProjectIntegrator::TargetIntegrator.create_or_update_shell_script_build_phase(native_target, phase_name)
228
+ phase.shell_script = %("#{script_path}"\n)
229
+
230
+ input_paths_by_config = {}
231
+ output_paths_by_config = {}
232
+ if use_input_output_paths?
233
+ input_file_list_path = target.copy_dsyms_script_input_files_path
234
+ input_file_list_relative_path = "${PODS_ROOT}/#{input_file_list_path.relative_path_from(target.sandbox.root)}"
235
+ input_paths_key = UserProjectIntegrator::TargetIntegrator::XCFileListConfigKey.new(input_file_list_path, input_file_list_relative_path)
236
+ input_paths = input_paths_by_config[input_paths_key] = []
237
+ input_paths.concat([dsym_paths, *bcsymbolmap_paths].flatten.compact)
238
+
239
+ output_file_list_path = target.copy_dsyms_script_output_files_path
240
+ output_file_list_relative_path = "${PODS_ROOT}/#{output_file_list_path.relative_path_from(target.sandbox.root)}"
241
+ output_paths_key = UserProjectIntegrator::TargetIntegrator::XCFileListConfigKey.new(output_file_list_path, output_file_list_relative_path)
242
+ output_paths = output_paths_by_config[output_paths_key] = []
243
+
244
+ dsym_output_paths = dsym_paths.map { |dsym_path| "${DWARF_DSYM_FOLDER_PATH}/#{File.basename(dsym_path)}" }
245
+ bcsymbolmap_output_paths = bcsymbolmap_paths.map { |bcsymbolmap_path| "${DWARF_DSYM_FOLDER_PATH}/#{File.basename(bcsymbolmap_path)}" }
246
+ output_paths.concat([dsym_output_paths, *bcsymbolmap_output_paths].flatten.compact)
247
+ end
248
+
249
+ UserProjectIntegrator::TargetIntegrator.set_input_output_paths(phase, input_paths_by_config, output_paths_by_config)
250
+ end
251
+
252
+ # Adds the ODRs that are related to this app spec. This includes the app spec dependencies as well as the ODRs
253
+ # coming from the app spec itself.
254
+ #
255
+ # @param [Xcodeproj::PBXNativeTarget] native_target
256
+ # the native target for which to add the ODR file references into.
257
+ #
258
+ # @param [Specification] app_spec
259
+ # the app spec to integrate ODRs for.
260
+ #
261
+ # @return [void]
262
+ #
263
+ def add_on_demand_resources(native_target, app_spec)
264
+ dependent_targets = target.dependent_targets_for_app_spec(app_spec)
265
+ parent_odr_group = native_target.project.group_for_spec(app_spec.name)
266
+
267
+ # Add ODRs of the app spec dependencies first.
268
+ dependent_targets.each do |pod_target|
269
+ file_accessors = pod_target.file_accessors.select do |fa|
270
+ fa.spec.library_specification? ||
271
+ fa.spec.test_specification? && pod_target.test_app_hosts_by_spec[fa.spec]&.first == app_spec
272
+ end
273
+ target_odr_group_name = "#{pod_target.label}-OnDemandResources"
274
+ UserProjectIntegrator::TargetIntegrator.update_on_demand_resources(target.sandbox, native_target.project,
275
+ native_target, file_accessors,
276
+ parent_odr_group, target_odr_group_name)
277
+ end
278
+
279
+ # Now add the ODRs of our own app spec declaration.
280
+ file_accessor = target.file_accessors.find { |fa| fa.spec == app_spec }
281
+ target_odr_group_name = "#{target.subspec_label(app_spec)}-OnDemandResources"
282
+ UserProjectIntegrator::TargetIntegrator.update_on_demand_resources(target.sandbox, native_target.project,
283
+ native_target, file_accessor,
284
+ parent_odr_group, target_odr_group_name)
285
+ end
286
+
287
+ # @return [String] the message that should be displayed for the target
288
+ # integration.
289
+ #
290
+ def integration_message
291
+ "Integrating target `#{target.name}`"
292
+ end
293
+
294
+ # @return [PodTarget] the target part of the installation result.
295
+ #
296
+ def target
297
+ target_installation_result.target
298
+ end
299
+
300
+ # @param [Specification, Array<Specification>] specs
301
+ # the specs to return script phrases from.
302
+ #
303
+ # @return [Array<Hash<Symbol=>String>] an array of all combined script phases from the specs.
304
+ #
305
+ def script_phases_for_specs(specs)
306
+ Array(specs).flat_map { |spec| spec.consumer(target.platform).script_phases }
307
+ end
308
+ end
309
+ end
310
+ end
311
+ end
312
+ end
@@ -0,0 +1,90 @@
1
+ module Pod
2
+ class Installer
3
+ class Xcode
4
+ class PodsProjectWriter
5
+ # @return [Sandbox] sandbox
6
+ # The Pods sandbox instance.
7
+ #
8
+ attr_reader :sandbox
9
+
10
+ # @return [Array<Project>] projects
11
+ # The list project to write.
12
+ #
13
+ attr_reader :projects
14
+
15
+ # @return [Hash<String, TargetInstallationResult>] pod_target_installation_results
16
+ # Hash of pod target name to installation results.
17
+ #
18
+ attr_reader :pod_target_installation_results
19
+
20
+ # @return [InstallationOptions] installation_options
21
+ #
22
+ attr_reader :installation_options
23
+
24
+ # Initialize a new instance
25
+ #
26
+ # @param [Sandbox] sandbox @see #sandbox
27
+ # @param [Project] projects @see #project
28
+ # @param [Hash<String, TargetInstallationResult>] pod_target_installation_results @see #pod_target_installation_results
29
+ # @param [InstallationOptions] installation_options @see #installation_options
30
+ #
31
+ def initialize(sandbox, projects, pod_target_installation_results, installation_options)
32
+ @sandbox = sandbox
33
+ @projects = projects
34
+ @pod_target_installation_results = pod_target_installation_results
35
+ @installation_options = installation_options
36
+ end
37
+
38
+ # Writes projects to disk.
39
+ #
40
+ # @yield If provided, this block will execute right before writing the projects to disk.
41
+ #
42
+ def write!
43
+ cleanup_projects(projects)
44
+
45
+ projects.each do |project|
46
+ library_product_types = [:framework, :dynamic_library, :static_library]
47
+ results_by_native_target = Hash[pod_target_installation_results.map do |_, result|
48
+ [result.native_target, result]
49
+ end]
50
+ project.recreate_user_schemes(false) do |scheme, target|
51
+ next unless target.respond_to?(:symbol_type)
52
+ next unless library_product_types.include? target.symbol_type
53
+ installation_result = results_by_native_target[target]
54
+ next unless installation_result
55
+ installation_result.test_native_targets.each do |test_native_target|
56
+ scheme.add_test_target(test_native_target)
57
+ end
58
+ end
59
+ end
60
+
61
+ yield if block_given?
62
+
63
+ save_projects(projects)
64
+ end
65
+
66
+ private
67
+
68
+ # Cleans up projects before writing.
69
+ #
70
+ def cleanup_projects(projects)
71
+ projects.each do |project|
72
+ [project.pods, project.support_files_group,
73
+ project.development_pods, project.dependencies_group].each { |group| group.remove_from_project if group.empty? }
74
+ end
75
+ end
76
+
77
+ # Sorts and then saves projects which writes them to disk.
78
+ #
79
+ def save_projects(projects)
80
+ projects.each do |project|
81
+ project.sort(:groups_position => :below)
82
+ UI.message "- Writing Xcode project file to #{UI.path project.path}" do
83
+ project.save
84
+ end
85
+ end
86
+ end
87
+ end
88
+ end
89
+ end
90
+ end
@@ -0,0 +1,120 @@
1
+ module Pod
2
+ class Installer
3
+ class Xcode
4
+ # Responsible for creating and preparing a Pod::Project instance
5
+ #
6
+ class ProjectGenerator
7
+ # @return [Sandbox] sandbox
8
+ # The Pods sandbox instance.
9
+ #
10
+ attr_reader :sandbox
11
+
12
+ # @return [String] path
13
+ # Path of the project.
14
+ #
15
+ attr_reader :path
16
+
17
+ # @return [Array<PodTarget>] pod_targets
18
+ # Array of pod targets this project includes.
19
+ #
20
+ attr_reader :pod_targets
21
+
22
+ # @return [Hash{String=>Symbol}] A hash representing all the user build
23
+ # configurations across all integration targets. Each key
24
+ # corresponds to the name of a configuration and its value to
25
+ # its type (`:debug` or `:release`).
26
+ #
27
+ attr_reader :build_configurations
28
+
29
+ # @return [Array<Platform>] The list of all platforms this project supports.
30
+ #
31
+ attr_reader :platforms
32
+
33
+ # @return [Integer] Object version for the Xcode project.
34
+ #
35
+ attr_reader :object_version
36
+
37
+ # @return [String] Path to the Podfile included in the project.
38
+ #
39
+ attr_reader :podfile_path
40
+
41
+ # @return [Bool] Bool indicating if this project is a pod target subproject.
42
+ # Used by `generate_multiple_pod_projects` installation option.
43
+ #
44
+ attr_reader :pod_target_subproject
45
+
46
+ # Initialize a new instance
47
+ #
48
+ # @param [Sandbox] sandbox @see #sandbox
49
+ # @param [String] path @see #path
50
+ # @param [Array<PodTarget>] pod_targets @see #pod_targets
51
+ # @param [Hash{String=>Symbol}] build_configurations @see #build_configurations
52
+ # @param [Array<Platform>] platforms @see #platforms
53
+ # @param [Integer] object_version @see #object_version
54
+ # @param [String] podfile_path @see #podfile_path
55
+ #
56
+ def initialize(sandbox, path, pod_targets, build_configurations, platforms,
57
+ object_version, podfile_path = nil, pod_target_subproject: false)
58
+ @sandbox = sandbox
59
+ @path = path
60
+ @pod_targets = pod_targets
61
+ @build_configurations = build_configurations
62
+ @platforms = platforms
63
+ @object_version = object_version
64
+ @podfile_path = podfile_path
65
+ @pod_target_subproject = pod_target_subproject
66
+ end
67
+
68
+ public
69
+
70
+ # @return [Project] Generated and prepared project.
71
+ #
72
+ def generate!
73
+ project = create_project(path, object_version, pod_target_subproject)
74
+ prepare(sandbox, project, pod_targets, build_configurations, platforms, podfile_path)
75
+ project
76
+ end
77
+
78
+ private
79
+
80
+ def create_project(path, object_version, pod_target_subproject)
81
+ object_version ||= Xcodeproj::Constants::DEFAULT_OBJECT_VERSION
82
+ Pod::Project.new(path, false, object_version, :pod_target_subproject => pod_target_subproject)
83
+ end
84
+
85
+ def prepare(sandbox, project, pod_targets, build_configurations, platforms, podfile_path)
86
+ UI.message "- Creating #{project.project_name} project" do
87
+ build_configurations.each do |name, type|
88
+ project.add_build_configuration(name, type)
89
+ end
90
+ # Reset symroot just in case the user has added a new build configuration other than 'Debug' or 'Release'.
91
+ project.symroot = Pod::Project::LEGACY_BUILD_ROOT
92
+ pod_names = pod_targets.map(&:pod_name).uniq
93
+ pod_names.each do |pod_name|
94
+ local = sandbox.local?(pod_name)
95
+ path = sandbox.pod_dir(pod_name)
96
+ was_absolute = sandbox.local_path_was_absolute?(pod_name)
97
+ project.add_pod_group(pod_name, path, local, was_absolute)
98
+ end
99
+ if podfile_path
100
+ project.add_podfile(podfile_path)
101
+ end
102
+ osx_deployment_target = platforms.select { |p| p.name == :osx }.map(&:deployment_target).min
103
+ ios_deployment_target = platforms.select { |p| p.name == :ios }.map(&:deployment_target).min
104
+ watchos_deployment_target = platforms.select { |p| p.name == :watchos }.map(&:deployment_target).min
105
+ tvos_deployment_target = platforms.select { |p| p.name == :tvos }.map(&:deployment_target).min
106
+ project.build_configurations.each do |build_configuration|
107
+ build_configuration.build_settings['MACOSX_DEPLOYMENT_TARGET'] = osx_deployment_target.to_s if osx_deployment_target
108
+ build_configuration.build_settings['IPHONEOS_DEPLOYMENT_TARGET'] = ios_deployment_target.to_s if ios_deployment_target
109
+ build_configuration.build_settings['WATCHOS_DEPLOYMENT_TARGET'] = watchos_deployment_target.to_s if watchos_deployment_target
110
+ build_configuration.build_settings['TVOS_DEPLOYMENT_TARGET'] = tvos_deployment_target.to_s if tvos_deployment_target
111
+ build_configuration.build_settings['STRIP_INSTALLED_PRODUCT'] = 'NO'
112
+ build_configuration.build_settings['CLANG_ENABLE_OBJC_ARC'] = 'YES'
113
+ build_configuration.build_settings['CLANG_ANALYZER_LOCALIZABILITY_NONLOCALIZED'] = 'YES'
114
+ end
115
+ end
116
+ end
117
+ end
118
+ end
119
+ end
120
+ end
@@ -0,0 +1,140 @@
1
+ module Pod
2
+ class Installer
3
+ class Xcode
4
+ class PodsProjectGenerator
5
+ # A simple container produced after a target installation is completed.
6
+ #
7
+ class TargetInstallationResult
8
+ # @return [Target] target
9
+ # The target this installation result is for.
10
+ #
11
+ attr_reader :target
12
+
13
+ # @return [PBXNativeTarget] native_target
14
+ # The native target that was produced for this target.
15
+ #
16
+ attr_reader :native_target
17
+
18
+ # @return [Array<PBXNativeTarget>] resource_bundle_targets
19
+ # The resource bundle targets that were produced for this target. Can be empty if the target had
20
+ # no resource bundles.
21
+ #
22
+ attr_reader :resource_bundle_targets
23
+
24
+ # @return [Array<PBXNativeTarget>] test_native_targets
25
+ # The test native targets that were produced for this target. Can be empty if there were no test
26
+ # native targets created (e.g. no test specs present).
27
+ #
28
+ attr_reader :test_native_targets
29
+
30
+ # @return [Hash{String=>Array<PBXNativeTarget>}] test_resource_bundle_targets
31
+ # The test resource bundle targets that were produced for this target keyed by test spec name.
32
+ # Can be empty if the target had no resource bundles for any tests.
33
+ #
34
+ attr_reader :test_resource_bundle_targets
35
+
36
+ # @return [Array<PBXNativeTarget>] test_app_host_targets
37
+ # The test app host native targets that were produced for this target. Can be empty.
38
+ #
39
+ attr_reader :test_app_host_targets
40
+
41
+ # @return [Hash{Specification => PBXNativeTarget}] app_native_targets
42
+ # The app native targets that were produced for this target. Can be empty if there were no app
43
+ # native targets created (e.g. no app specs present).
44
+ #
45
+ attr_reader :app_native_targets
46
+
47
+ # @return [Hash{String=>Array<PBXNativeTarget>}] app_resource_bundle_targets
48
+ # The app resource bundle targets that were produced for this target keyed by app spec name.
49
+ # Can be empty if the target had no resource bundles for any apps.
50
+ #
51
+ attr_reader :app_resource_bundle_targets
52
+
53
+ # Initialize a new instance
54
+ #
55
+ # @param [Target] target @see #target
56
+ # @param [PBXNativeTarget] native_target @see #native_target
57
+ # @param [Array<PBXNativeTarget>] resource_bundle_targets @see #resource_bundle_targets
58
+ # @param [Array<PBXNativeTarget>] test_native_targets @see #test_native_targets
59
+ # @param [Hash{String=>Array<PBXNativeTarget>}] test_resource_bundle_targets @see #test_resource_bundle_targets
60
+ # @param [Array<PBXNativeTarget>] test_app_host_targets @see #test_app_host_targets
61
+ # @param [Hash{Specification => PBXNativeTarget}] app_native_targets @see #app_native_targets
62
+ # @param [Hash{String=>Array<PBXNativeTarget>}] app_resource_bundle_targets @see #app_resource_bundle_targets
63
+ #
64
+ def initialize(target, native_target, resource_bundle_targets = [], test_native_targets = [],
65
+ test_resource_bundle_targets = {}, test_app_host_targets = [],
66
+ app_native_targets = {}, app_resource_bundle_targets = {})
67
+ @target = target
68
+ @native_target = native_target
69
+ @resource_bundle_targets = resource_bundle_targets
70
+ @test_native_targets = test_native_targets
71
+ @test_resource_bundle_targets = test_resource_bundle_targets
72
+ @test_app_host_targets = test_app_host_targets
73
+ @app_native_targets = app_native_targets
74
+ @app_resource_bundle_targets = app_resource_bundle_targets
75
+ end
76
+
77
+ # Returns the corresponding native target to use based on the provided specification.
78
+ #
79
+ # @param [Specification] spec
80
+ # The specification to base from in order to find the native target.
81
+ #
82
+ # @return [PBXNativeTarget, Nil] the native target to use or `nil` if none is found.
83
+ #
84
+ def native_target_for_spec(spec)
85
+ return native_target if spec.library_specification?
86
+ return test_native_target_from_spec(spec) if spec.test_specification?
87
+ app_native_target_from_spec(spec) if spec.app_specification?
88
+ end
89
+
90
+ # @return [Hash{PBXNativeTarget => Specification}] a hash where the keys are the test native targets and the value
91
+ # is the test spec associated with this native target.
92
+ #
93
+ def test_specs_by_native_target
94
+ test_specs_by_native_target = Hash[target.test_specs.map { |spec| [test_native_target_from_spec(spec), spec] }]
95
+ test_specs_by_native_target.delete_if { |k, _| k.nil? }
96
+ end
97
+
98
+ # @return [Hash{PBXNativeTarget => Specification}] a hash where the keys are the app native targets and the value
99
+ # is the app spec associated with this native target.
100
+ #
101
+ def app_specs_by_native_target
102
+ app_specs_by_native_target = Hash[target.app_specs.map { |spec| [app_native_target_from_spec(spec), spec] }]
103
+ app_specs_by_native_target.delete_if { |k, _| k.nil? }
104
+ end
105
+
106
+ # @return [Hash{PBXNativeTarget => Specification}] a hash where the keys are the native targets and the value
107
+ # is the non-library spec associated with this native target.
108
+ #
109
+ def non_library_specs_by_native_target
110
+ test_specs_by_native_target.merge(app_specs_by_native_target)
111
+ end
112
+
113
+ # @param label [String] the label of the app host target.
114
+ #
115
+ # @return [PBXNativeTarget] the app host target with the given target label.
116
+ #
117
+ def app_host_target_labelled(label)
118
+ app_native_targets.values.find do |app_native_target|
119
+ app_native_target.name == label
120
+ end || test_app_host_targets.find do |app_native_target|
121
+ app_native_target.name == label
122
+ end
123
+ end
124
+
125
+ private
126
+
127
+ def test_native_target_from_spec(spec)
128
+ test_native_targets.find do |test_native_target|
129
+ test_native_target.name == target.test_target_label(spec)
130
+ end
131
+ end
132
+
133
+ def app_native_target_from_spec(spec)
134
+ app_native_targets[spec]
135
+ end
136
+ end
137
+ end
138
+ end
139
+ end
140
+ end