xcode-archive-cache 0.0.8.pre.2 → 0.0.10
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/lib/artifact_cache/archiver.rb +2 -1
- data/lib/artifact_cache/local_storage.rb +2 -1
- data/lib/build/performer.rb +1 -1
- data/lib/build/product_extractor.rb +88 -5
- data/lib/build_graph/builder.rb +5 -1
- data/lib/build_graph/native_target_finder.rb +46 -11
- data/lib/build_graph/node.rb +50 -2
- data/lib/build_graph/rebuild_evaluator.rb +30 -4
- data/lib/build_graph/sha_calculator.rb +22 -1
- data/lib/build_settings/extractor.rb +21 -1
- data/lib/build_settings/filter.rb +7 -3
- data/lib/build_settings/loader.rb +8 -1
- data/lib/build_settings/parser.rb +1 -1
- data/lib/injection/build_flags_changer.rb +173 -4
- data/lib/injection/dependency_remover.rb +22 -1
- data/lib/injection/headers_mover.rb +27 -3
- data/lib/injection/injector.rb +69 -20
- data/lib/injection/storage.rb +47 -6
- data/lib/modulemap/file_handler.rb +20 -0
- data/lib/modulemap/header_path_extractor.rb +67 -0
- data/lib/modulemap/header_path_fixer.rb +65 -0
- data/lib/runner/runner.rb +31 -24
- data/lib/shell/executor.rb +2 -2
- data/lib/xcode-archive-cache.rb +4 -0
- data/lib/xcodebuild/executor.rb +4 -0
- metadata +32 -17
@@ -13,7 +13,7 @@ module XcodeArchiveCache
|
|
13
13
|
# @return [Hash{String => Container}]
|
14
14
|
# Target build settings keyed by target name
|
15
15
|
#
|
16
|
-
def extract_per_target(build_settings)
|
16
|
+
def extract_per_target(build_settings, fix_simulator)
|
17
17
|
per_target_settings = build_settings.split("Build settings for action")
|
18
18
|
result = Hash.new
|
19
19
|
|
@@ -22,6 +22,7 @@ module XcodeArchiveCache
|
|
22
22
|
target_name = get_target_name(parsed_settings)
|
23
23
|
next unless target_name
|
24
24
|
|
25
|
+
replace_platform_with_simulator(parsed_settings) if fix_simulator
|
25
26
|
filtered_settings = filter.filter(parsed_settings)
|
26
27
|
result[target_name] = Container.new(parsed_settings, filtered_settings)
|
27
28
|
end
|
@@ -65,6 +66,25 @@ module XcodeArchiveCache
|
|
65
66
|
result
|
66
67
|
end
|
67
68
|
|
69
|
+
|
70
|
+
# @param [Hash{String => String}] settings
|
71
|
+
#
|
72
|
+
def replace_platform_with_simulator(settings)
|
73
|
+
original_platform = settings[EFFECTIVE_PLATFORM_NAME_KEY]
|
74
|
+
simulator_platform = settings[CORRESPONDING_SIMULATOR_PLATFORM_NAME_KEY]
|
75
|
+
settings[EFFECTIVE_PLATFORM_NAME_KEY] = "-#{simulator_platform}"
|
76
|
+
|
77
|
+
configuration = settings[CONFIGURATION_KEY]
|
78
|
+
path_regexp = Regexp.new("#{configuration}#{original_platform}")
|
79
|
+
simulator_path = "#{configuration}-#{simulator_platform}"
|
80
|
+
settings.each do |key, value|
|
81
|
+
settings[key] = value.gsub(path_regexp, simulator_path)
|
82
|
+
end
|
83
|
+
end
|
84
|
+
|
85
|
+
EFFECTIVE_PLATFORM_NAME_KEY = "EFFECTIVE_PLATFORM_NAME".freeze
|
86
|
+
CORRESPONDING_SIMULATOR_PLATFORM_NAME_KEY = "CORRESPONDING_SIMULATOR_PLATFORM_NAME".freeze
|
87
|
+
CONFIGURATION_KEY = "CONFIGURATION".freeze
|
68
88
|
TARGET_NAME_KEY = "TARGETNAME".freeze
|
69
89
|
|
70
90
|
# @param [Hash{String => String}] parsed_settings
|
@@ -10,7 +10,7 @@ module XcodeArchiveCache
|
|
10
10
|
# Machine-dependent settings i.e. paths, user names, group names are rejected
|
11
11
|
#
|
12
12
|
def filter(settings, settings_to_keep = SETTINGS_TO_KEEP)
|
13
|
-
filtered_settings = settings.select {|name, _| settings_to_keep.include?(name)}
|
13
|
+
filtered_settings = settings.select { |name, _| settings_to_keep.include?(name) }
|
14
14
|
SETTINGS_TO_STRIP.each do |name|
|
15
15
|
value = filtered_settings[name]
|
16
16
|
next if value == nil
|
@@ -44,7 +44,9 @@ module XcodeArchiveCache
|
|
44
44
|
# splitting will be broken, but probability of
|
45
45
|
# someone using such path is quite low (or it isn't ?)
|
46
46
|
#
|
47
|
-
value_components = value_without_quotes
|
47
|
+
value_components = value_without_quotes
|
48
|
+
.split(/^-|\s-/)
|
49
|
+
.select { |component| component.length > 0 }
|
48
50
|
|
49
51
|
index = 0
|
50
52
|
indices_to_remove = []
|
@@ -66,7 +68,8 @@ module XcodeArchiveCache
|
|
66
68
|
kept_components.push(component) unless indices_to_remove.include?(component_index)
|
67
69
|
end
|
68
70
|
|
69
|
-
kept_components.join(" -")
|
71
|
+
result = kept_components.join(" -")
|
72
|
+
result.length > 0 ? "-#{result}" : ""
|
70
73
|
end
|
71
74
|
|
72
75
|
# TODO: extend
|
@@ -283,6 +286,7 @@ module XcodeArchiveCache
|
|
283
286
|
output-file-map
|
284
287
|
save-optimization-record-path
|
285
288
|
working-directory
|
289
|
+
fmodule-map-file
|
286
290
|
)
|
287
291
|
end
|
288
292
|
end
|
@@ -3,6 +3,11 @@ module XcodeArchiveCache
|
|
3
3
|
|
4
4
|
FULL_PRODUCT_NAME_KEY = "FULL_PRODUCT_NAME".freeze
|
5
5
|
DWARF_DSYM_FILE_NAME_KEY = "DWARF_DSYM_FILE_NAME".freeze
|
6
|
+
MODULEMAP_FILE_KEY = "MODULEMAP_FILE".freeze
|
7
|
+
SWIFT_OBJC_INTERFACE_HEADER_NAME_KEY = "SWIFT_OBJC_INTERFACE_HEADER_NAME".freeze
|
8
|
+
SWIFT_MODULE_NAME_KEY = "SWIFT_MODULE_NAME".freeze
|
9
|
+
PRODUCT_MODULE_NAME_KEY = "PRODUCT_MODULE_NAME".freeze
|
10
|
+
DERIVED_SOURCES_DIR_KEY = "DERIVED_SOURCES_DIR".freeze
|
6
11
|
|
7
12
|
class Container
|
8
13
|
|
@@ -58,9 +63,11 @@ module XcodeArchiveCache
|
|
58
63
|
end
|
59
64
|
end
|
60
65
|
|
66
|
+
should_fix_settings = executor.set_up_for_simulator?
|
67
|
+
|
61
68
|
threads.each do |thread|
|
62
69
|
project_path, all_targets_settings = thread.value
|
63
|
-
per_target_settings = extractor.extract_per_target(all_targets_settings)
|
70
|
+
per_target_settings = extractor.extract_per_target(all_targets_settings, should_fix_settings)
|
64
71
|
set_project_settings(project_path, per_target_settings)
|
65
72
|
end
|
66
73
|
end
|
@@ -7,9 +7,9 @@ module XcodeArchiveCache
|
|
7
7
|
# @param [Xcodeproj::Project::Object::XCBuildConfiguration] build_configuration
|
8
8
|
# @param [String] path
|
9
9
|
#
|
10
|
-
def
|
10
|
+
def replace_or_add_framework_search_path(build_configuration, target_name, path)
|
11
11
|
debug("using framework search path #{path}")
|
12
|
-
|
12
|
+
replace_or_add_flag(build_configuration, [FRAMEWORK_SEARCH_PATHS_KEY], nil, [target_name], path_to_search_path(path), true)
|
13
13
|
end
|
14
14
|
|
15
15
|
# @param [Xcodeproj::Project::Object::XCBuildConfiguration] build_configuration
|
@@ -26,6 +26,37 @@ module XcodeArchiveCache
|
|
26
26
|
# @param [Xcodeproj::Project::Object::XCBuildConfiguration] build_configuration
|
27
27
|
# @param [XcodeArchiveCache::BuildGraph::Node] node
|
28
28
|
#
|
29
|
+
def add_static_lib_linker_flag(build_configuration, node)
|
30
|
+
flag = get_linker_flag(node)
|
31
|
+
if flag
|
32
|
+
debug("using ld flag #{flag}")
|
33
|
+
add_linker_flag(build_configuration, flag)
|
34
|
+
end
|
35
|
+
end
|
36
|
+
|
37
|
+
# @param [Xcodeproj::Project::Object::XCBuildConfiguration] build_configuration
|
38
|
+
# @param [XcodeArchiveCache::BuildGraph::Node] node
|
39
|
+
#
|
40
|
+
def add_static_lib_libtool_flag(build_configuration, node)
|
41
|
+
flag = get_linker_flag(node)
|
42
|
+
if flag
|
43
|
+
debug("using libtool flag #{flag}")
|
44
|
+
add_libtool_flag(build_configuration, flag)
|
45
|
+
end
|
46
|
+
end
|
47
|
+
|
48
|
+
# @param [Xcodeproj::Project::Object::XCBuildConfiguration] build_configuration
|
49
|
+
# @param [String] path
|
50
|
+
#
|
51
|
+
def add_swift_include_path(build_configuration, path)
|
52
|
+
debug("adding #{path} to SWIFT_INCLUDE_PATHS")
|
53
|
+
add_flag_to_configuration(build_configuration, SWIFT_INCLUDE_PATHS_KEY, path_to_search_path(path))
|
54
|
+
end
|
55
|
+
|
56
|
+
# @param [Xcodeproj::Project::Object::XCBuildConfiguration] build_configuration
|
57
|
+
# @param [String] artifact_location
|
58
|
+
# @param [XcodeArchiveCache::BuildGraph::Node] node
|
59
|
+
#
|
29
60
|
def add_framework_headers_iquote(build_configuration, artifact_location, node)
|
30
61
|
headers_search_path = get_framework_headers_iquote(artifact_location, node)
|
31
62
|
debug("using -iquote path #{headers_search_path}")
|
@@ -35,9 +66,9 @@ module XcodeArchiveCache
|
|
35
66
|
# @param [Xcodeproj::Project::Object::XCBuildConfiguration] build_configuration
|
36
67
|
# @param [String] path
|
37
68
|
#
|
38
|
-
def
|
69
|
+
def replace_or_add_library_search_path(build_configuration, target_name, path)
|
39
70
|
debug("using library search path #{path}")
|
40
|
-
|
71
|
+
replace_or_add_flag(build_configuration, [LIBRARY_SEARCH_PATHS_KEY], nil, [target_name], path_to_search_path(path), true)
|
41
72
|
end
|
42
73
|
|
43
74
|
# @param [Xcodeproj::Project::Object::XCBuildConfiguration] build_configuration
|
@@ -64,15 +95,32 @@ module XcodeArchiveCache
|
|
64
95
|
add_cflag(build_configuration, path_to_capital_i(path))
|
65
96
|
end
|
66
97
|
|
98
|
+
# @param [Xcodeproj::Project::Object::XCBuildConfiguration] build_configuration
|
99
|
+
# @param [Array<String>] old_modulemap_names
|
100
|
+
# @param [String] path
|
101
|
+
#
|
102
|
+
def fix_module_map_path(build_configuration, old_modulemap_names, path)
|
103
|
+
debug("using #{path}")
|
104
|
+
|
105
|
+
settings_with_modulemaps = [OTHER_CFLAGS_KEY, OTHER_CPLUSPLUSFLAGS_KEY, OTHER_SWIFT_FLAGS_KEY]
|
106
|
+
replace_or_add_flag(build_configuration, settings_with_modulemaps, MODULE_MAP_FLAG, old_modulemap_names, path_to_search_path(path), false)
|
107
|
+
end
|
108
|
+
|
67
109
|
private
|
68
110
|
|
69
111
|
FRAMEWORK_SEARCH_PATHS_KEY = "FRAMEWORK_SEARCH_PATHS"
|
70
112
|
LIBRARY_SEARCH_PATHS_KEY = "LIBRARY_SEARCH_PATHS"
|
71
113
|
HEADER_SEARCH_PATHS_KEY = "HEADER_SEARCH_PATHS"
|
72
114
|
OTHER_CFLAGS_KEY = "OTHER_CFLAGS"
|
115
|
+
OTHER_CPLUSPLUSFLAGS_KEY = "OTHER_CPLUSPLUSFLAGS"
|
73
116
|
OTHER_LDFLAGS_KEY = "OTHER_LDFLAGS"
|
117
|
+
OTHER_LIBTOOLFLAGS_KEY = "OTHER_LIBTOOLFLAGS"
|
118
|
+
OTHER_SWIFT_FLAGS_KEY = "OTHER_SWIFT_FLAGS"
|
119
|
+
SWIFT_INCLUDE_PATHS_KEY = "SWIFT_INCLUDE_PATHS"
|
74
120
|
INHERITED_SETTINGS_VALUE = "$(inherited)"
|
75
121
|
|
122
|
+
MODULE_MAP_FLAG = "-fmodule-map-file="
|
123
|
+
|
76
124
|
# @param [Xcodeproj::Project::Object::XCBuildConfiguration] build_configuration
|
77
125
|
# @param [String] flag
|
78
126
|
#
|
@@ -80,6 +128,13 @@ module XcodeArchiveCache
|
|
80
128
|
add_flag_to_configuration(build_configuration, OTHER_LDFLAGS_KEY, flag)
|
81
129
|
end
|
82
130
|
|
131
|
+
# @param [Xcodeproj::Project::Object::XCBuildConfiguration] build_configuration
|
132
|
+
# @param [String] flag
|
133
|
+
#
|
134
|
+
def add_libtool_flag(build_configuration, flag)
|
135
|
+
add_flag_to_configuration(build_configuration, OTHER_LIBTOOLFLAGS_KEY, flag)
|
136
|
+
end
|
137
|
+
|
83
138
|
# @param [Xcodeproj::Project::Object::XCBuildConfiguration] build_configuration
|
84
139
|
# @param [String] flag
|
85
140
|
#
|
@@ -167,6 +222,120 @@ module XcodeArchiveCache
|
|
167
222
|
|
168
223
|
"-framework \"#{framework_name}\""
|
169
224
|
end
|
225
|
+
|
226
|
+
# @param [XcodeArchiveCache::BuildGraph::Node] node
|
227
|
+
#
|
228
|
+
# @return [String]
|
229
|
+
#
|
230
|
+
# libSomething.a -> -lSomething
|
231
|
+
#
|
232
|
+
def get_linker_flag(node)
|
233
|
+
return unless node.product_file_name
|
234
|
+
|
235
|
+
node.product_file_name.gsub(/^lib/, "-l").gsub(/\.a$/, "")
|
236
|
+
end
|
237
|
+
|
238
|
+
# @param [Xcodeproj::Project::Object::XCBuildConfiguration] build_configuration
|
239
|
+
# @param [Array<String>] setting_keys
|
240
|
+
# @param [String] flag_name
|
241
|
+
# @param [Array<String>] possible_old_values
|
242
|
+
# @param [String] new_value
|
243
|
+
#
|
244
|
+
def replace_or_add_flag(build_configuration, setting_keys, flag_name, possible_old_values, new_value, add_if_missing)
|
245
|
+
replaced = false
|
246
|
+
|
247
|
+
setting_keys.each do |setting|
|
248
|
+
replaced = replace_flag_value(build_configuration.build_settings, setting, flag_name, possible_old_values, new_value) || replaced
|
249
|
+
end
|
250
|
+
|
251
|
+
if build_configuration.base_configuration_reference
|
252
|
+
xcconfig_path = build_configuration.base_configuration_reference.real_path
|
253
|
+
project_dir = File.dirname(build_configuration.project.path)
|
254
|
+
|
255
|
+
replaced = replace_flag_value_in_xcconfig_recursively(xcconfig_path, project_dir, setting_keys, flag_name, possible_old_values, new_value) || replaced
|
256
|
+
end
|
257
|
+
|
258
|
+
if !replaced && add_if_missing
|
259
|
+
full_value = get_full_flag_value(flag_name, new_value)
|
260
|
+
|
261
|
+
setting_keys.each do |setting|
|
262
|
+
add_flag_to_configuration(build_configuration, setting, full_value)
|
263
|
+
end
|
264
|
+
end
|
265
|
+
end
|
266
|
+
|
267
|
+
# @param [String] xcconfig_path
|
268
|
+
# @param [String] project_dir
|
269
|
+
# @param [Array<String>] setting_keys
|
270
|
+
# @param [String] flag_name
|
271
|
+
# @param [Array<String>] possible_old_values
|
272
|
+
# @param [String] new_value
|
273
|
+
#
|
274
|
+
def replace_flag_value_in_xcconfig_recursively(xcconfig_path, project_dir, setting_keys, flag_name, possible_old_values, new_value)
|
275
|
+
debug("changing #{possible_old_values} to #{new_value} in #{File.basename(xcconfig_path)}")
|
276
|
+
return unless File.exist?(xcconfig_path)
|
277
|
+
|
278
|
+
replaced = false
|
279
|
+
xcconfig = Xcodeproj::Config.new(xcconfig_path)
|
280
|
+
|
281
|
+
setting_keys.each do |key|
|
282
|
+
replaced = replace_flag_value(xcconfig.attributes, key, flag_name, possible_old_values, new_value) || replaced
|
283
|
+
end
|
284
|
+
|
285
|
+
xcconfig.save_as(Pathname.new(xcconfig_path))
|
286
|
+
|
287
|
+
xcconfig.includes.each do |included_xcconfig|
|
288
|
+
included_xcconfig_path = File.join(project_dir, included_xcconfig)
|
289
|
+
replaced = replace_flag_value_in_xcconfig_recursively(included_xcconfig_path, project_dir, setting_keys, flag_name, possible_old_values, new_value) || replaced
|
290
|
+
end
|
291
|
+
|
292
|
+
replaced
|
293
|
+
end
|
294
|
+
|
295
|
+
# @param [Hash] attributes
|
296
|
+
# @param [String] setting_key
|
297
|
+
# @param [String] flag_name
|
298
|
+
# @param [Array<String>] possible_old_values
|
299
|
+
# @param [String] new_value
|
300
|
+
#
|
301
|
+
def replace_flag_value(attributes, setting_key, flag_name, possible_old_values, new_value)
|
302
|
+
build_settings = attributes[setting_key]
|
303
|
+
return unless build_settings
|
304
|
+
|
305
|
+
replaced = false
|
306
|
+
is_string = build_settings.is_a?(String)
|
307
|
+
build_settings = build_settings.split(" ") if is_string
|
308
|
+
full_value = get_full_flag_value(flag_name, new_value)
|
309
|
+
old_value_regexps = possible_old_values.map { |value| Regexp.new("#{value}\"*$") }
|
310
|
+
|
311
|
+
updated_settings = build_settings
|
312
|
+
.map { |line| line.split(" ") }
|
313
|
+
.flatten
|
314
|
+
.map do |line|
|
315
|
+
if flag_name
|
316
|
+
next line unless line.include?(flag_name)
|
317
|
+
end
|
318
|
+
|
319
|
+
updated_line = line
|
320
|
+
|
321
|
+
old_value_regexps.each do |regexp|
|
322
|
+
if regexp.match?(line)
|
323
|
+
replaced = true
|
324
|
+
updated_line = full_value
|
325
|
+
break
|
326
|
+
end
|
327
|
+
end
|
328
|
+
|
329
|
+
updated_line
|
330
|
+
end
|
331
|
+
|
332
|
+
attributes[setting_key] = is_string ? updated_settings.join(" ") : updated_settings
|
333
|
+
replaced
|
334
|
+
end
|
335
|
+
|
336
|
+
def get_full_flag_value(flag_name, value)
|
337
|
+
"#{flag_name}#{value}"
|
338
|
+
end
|
170
339
|
end
|
171
340
|
end
|
172
341
|
end
|
@@ -12,11 +12,21 @@ module XcodeArchiveCache
|
|
12
12
|
debug("removing #{prebuilt_target.name} from #{dependent_target.display_name}")
|
13
13
|
|
14
14
|
remove_from_dependencies(prebuilt_target, dependent_target)
|
15
|
+
remove_from_linking(prebuilt_node, dependent_target)
|
15
16
|
remove_from_schemes(prebuilt_target, dependent_target)
|
16
17
|
|
17
18
|
debug("finished removing #{prebuilt_target.name} from #{dependent_target.display_name}")
|
18
19
|
end
|
19
20
|
|
21
|
+
# @param [XcodeArchiveCache::BuildGraph::Node] prebuilt_node
|
22
|
+
# @param [Xcodeproj::Project::Object::PBXNativeTarget] dependent_target
|
23
|
+
#
|
24
|
+
# @return [Boolean]
|
25
|
+
#
|
26
|
+
def is_linked(prebuilt_node, dependent_target)
|
27
|
+
!find_linked(prebuilt_node, dependent_target).empty?
|
28
|
+
end
|
29
|
+
|
20
30
|
private
|
21
31
|
|
22
32
|
# @param [Xcodeproj::Project::Object::PBXNativeTarget] prebuilt_target
|
@@ -46,7 +56,7 @@ module XcodeArchiveCache
|
|
46
56
|
#
|
47
57
|
def remove_from_linking(prebuilt_node, dependent_target)
|
48
58
|
debug("product name is #{prebuilt_node.product_file_name}")
|
49
|
-
frameworks = dependent_target
|
59
|
+
frameworks = find_linked(prebuilt_node, dependent_target)
|
50
60
|
debug("found #{frameworks.length} linked products")
|
51
61
|
|
52
62
|
frameworks.each do |framework|
|
@@ -67,6 +77,17 @@ module XcodeArchiveCache
|
|
67
77
|
end
|
68
78
|
end
|
69
79
|
|
80
|
+
# @param [Xcodeproj::Project::Object::PBXNativeTarget] dependent_target
|
81
|
+
# @param [XcodeArchiveCache::BuildGraph::Node] prebuilt_node
|
82
|
+
#
|
83
|
+
# @return [Array<PBXBuildFile>]
|
84
|
+
#
|
85
|
+
def find_linked(prebuilt_node, dependent_target)
|
86
|
+
return [] unless dependent_target.frameworks_build_phase
|
87
|
+
|
88
|
+
dependent_target.frameworks_build_phase.files.select {|file| file.display_name == prebuilt_node.product_file_name}
|
89
|
+
end
|
90
|
+
|
70
91
|
# @param [Xcodeproj::Project::Object::PBXNativeTarget] target
|
71
92
|
#
|
72
93
|
# @return [Array<Xcodeproj::XCScheme>]
|
@@ -9,6 +9,7 @@ module XcodeArchiveCache
|
|
9
9
|
def initialize(storage)
|
10
10
|
@storage = storage
|
11
11
|
@build_settings_interpolator = XcodeArchiveCache::BuildSettings::StringInterpolator.new
|
12
|
+
@modulemap_header_path_extractor = XcodeArchiveCache::Modulemap::HeaderPathExtractor.new
|
12
13
|
end
|
13
14
|
|
14
15
|
# @param [XcodeArchiveCache::BuildGraph::Node] node
|
@@ -19,17 +20,36 @@ module XcodeArchiveCache
|
|
19
20
|
|
20
21
|
node.native_target.copy_files_build_phases.each do |build_phase|
|
21
22
|
file_paths = build_phase.files
|
22
|
-
.map {|build_file| get_real_path(build_file)}
|
23
|
+
.map { |build_file| get_real_path(build_file) }
|
23
24
|
.compact
|
24
25
|
.uniq
|
25
|
-
.select {|path| File.extname(path) == ".h"}
|
26
|
+
.select { |path| File.extname(path) == ".h" }
|
26
27
|
destination_path = get_destination_dir_path(node, build_phase)
|
27
28
|
storage.store_headers(node, destination_path, file_paths)
|
28
29
|
|
29
30
|
header_count += file_paths.length
|
30
31
|
end
|
31
32
|
|
32
|
-
|
33
|
+
if node.has_static_library_product?
|
34
|
+
headers_file_paths = node.native_target
|
35
|
+
.headers_build_phase
|
36
|
+
.files
|
37
|
+
.select { |file| file.settings && file.settings["ATTRIBUTES"].include?("Public") }
|
38
|
+
.map { |header| get_real_path(header) }
|
39
|
+
.uniq
|
40
|
+
storage.store_default_headers(node, headers_file_paths)
|
41
|
+
|
42
|
+
header_count += headers_file_paths.length
|
43
|
+
end
|
44
|
+
|
45
|
+
modulemap_file_path = node.original_modulemap_file_path
|
46
|
+
if modulemap_file_path && File.exist?(modulemap_file_path)
|
47
|
+
header_file_paths = modulemap_header_path_extractor.extract_all_paths(modulemap_file_path)
|
48
|
+
storage.store_modulemap_headers(node, header_file_paths)
|
49
|
+
header_count += header_file_paths.length
|
50
|
+
end
|
51
|
+
|
52
|
+
debug("found #{header_count} header(s)")
|
33
53
|
end
|
34
54
|
|
35
55
|
private
|
@@ -42,6 +62,10 @@ module XcodeArchiveCache
|
|
42
62
|
#
|
43
63
|
attr_reader :build_settings_interpolator
|
44
64
|
|
65
|
+
# @return [XcodeArchiveCache::Modulemap::HeaderPathExtractor]
|
66
|
+
#
|
67
|
+
attr_reader :modulemap_header_path_extractor
|
68
|
+
|
45
69
|
# @param [Xcodeproj::Project::Object::PBXBuildFile] build_file
|
46
70
|
#
|
47
71
|
# @return [String]
|
data/lib/injection/injector.rb
CHANGED
@@ -14,13 +14,14 @@ module XcodeArchiveCache
|
|
14
14
|
@dependency_remover = DependencyRemover.new
|
15
15
|
@build_flags_changer = BuildFlagsChanger.new
|
16
16
|
@pods_fixer = PodsScriptFixer.new
|
17
|
+
@modulemap_fixer = XcodeArchiveCache::Modulemap::HeaderPathFixer.new(storage)
|
17
18
|
@framework_embedder = FrameworkEmbedder.new
|
18
19
|
end
|
19
20
|
|
20
21
|
# @param [XcodeArchiveCache::BuildGraph::Graph] graph
|
21
22
|
#
|
22
23
|
def perform_internal_injection(graph)
|
23
|
-
|
24
|
+
inject_unpacked_and_rebuilt(graph.nodes)
|
24
25
|
add_header_paths(graph.nodes)
|
25
26
|
save_graph_projects(graph)
|
26
27
|
end
|
@@ -34,9 +35,15 @@ module XcodeArchiveCache
|
|
34
35
|
return
|
35
36
|
end
|
36
37
|
|
38
|
+
no_rebuild_performed = root_node.state == :unpacked
|
39
|
+
|
37
40
|
graph.nodes.each do |node|
|
38
|
-
|
39
|
-
|
41
|
+
if no_rebuild_performed || node.state == :rebuilt_and_cached
|
42
|
+
headers_mover.prepare_headers_for_injection(node)
|
43
|
+
modulemap_fixer.fix_modulemap(node)
|
44
|
+
end
|
45
|
+
|
46
|
+
add_as_prebuilt_dependency(node, target)
|
40
47
|
remove_native_target_from_project(node)
|
41
48
|
end
|
42
49
|
|
@@ -51,8 +58,8 @@ module XcodeArchiveCache
|
|
51
58
|
pods_fixer.fix_embed_frameworks_script(target, graph, storage.container_dir_path)
|
52
59
|
pods_fixer.fix_copy_resources_script(target, graph, storage.container_dir_path)
|
53
60
|
else
|
54
|
-
framework_nodes = graph.nodes.select {|node| node.has_framework_product?}
|
55
|
-
framework_file_paths = framework_nodes.map {|node| File.join(storage.get_storage_path(node), node.product_file_name)}
|
61
|
+
framework_nodes = graph.nodes.select { |node| node.has_framework_product? }
|
62
|
+
framework_file_paths = framework_nodes.map { |node| File.join(storage.get_storage_path(node), node.product_file_name) }
|
56
63
|
framework_embedder.embed(framework_file_paths, target)
|
57
64
|
end
|
58
65
|
|
@@ -86,16 +93,26 @@ module XcodeArchiveCache
|
|
86
93
|
#
|
87
94
|
attr_reader :pods_fixer
|
88
95
|
|
96
|
+
# @return [ModulemapFixer]
|
97
|
+
#
|
98
|
+
attr_reader :modulemap_fixer
|
99
|
+
|
89
100
|
# @return [FrameworkEmbedder]
|
90
101
|
#
|
91
102
|
attr_reader :framework_embedder
|
92
103
|
|
93
104
|
# @param [Array<XcodeArchiveCache::BuildGraph::Node>] nodes
|
94
105
|
#
|
95
|
-
def
|
96
|
-
cached_nodes = nodes.select {|node| node.state == :unpacked}
|
106
|
+
def inject_unpacked_and_rebuilt(nodes)
|
107
|
+
cached_nodes = nodes.select { |node| node.state == :unpacked }
|
97
108
|
cached_nodes.each do |node|
|
98
109
|
headers_mover.prepare_headers_for_injection(node)
|
110
|
+
modulemap_fixer.fix_modulemap(node)
|
111
|
+
add_as_prebuilt_to_dependents(node)
|
112
|
+
end
|
113
|
+
|
114
|
+
built_nodes = nodes.select { |node| node.state == :rebuilt_and_cached }
|
115
|
+
built_nodes.each do |node|
|
99
116
|
add_as_prebuilt_to_dependents(node)
|
100
117
|
end
|
101
118
|
end
|
@@ -104,10 +121,11 @@ module XcodeArchiveCache
|
|
104
121
|
#
|
105
122
|
def add_header_paths(nodes)
|
106
123
|
header_storage_paths = storage.get_all_headers_storage_paths
|
124
|
+
return if header_storage_paths.length == 0
|
107
125
|
|
108
126
|
nodes
|
109
127
|
.select(&:waiting_for_rebuild)
|
110
|
-
.each {|node| add_header_paths_to_target(node.native_target, header_storage_paths)}
|
128
|
+
.each { |node| add_header_paths_to_target(node.native_target, header_storage_paths) }
|
111
129
|
end
|
112
130
|
|
113
131
|
# @param [Xcodeproj::Project::Object::PBXNativeTarget] target
|
@@ -133,8 +151,7 @@ module XcodeArchiveCache
|
|
133
151
|
.all_dependent_nodes
|
134
152
|
.select(&:waiting_for_rebuild)
|
135
153
|
dependent_to_rebuild.each do |dependent_node|
|
136
|
-
|
137
|
-
add_as_prebuilt_dependency(prebuilt_node, dependent_node.native_target, should_link)
|
154
|
+
add_as_prebuilt_dependency(prebuilt_node, dependent_node.native_target)
|
138
155
|
end
|
139
156
|
|
140
157
|
remove_native_target_from_project(prebuilt_node)
|
@@ -145,13 +162,16 @@ module XcodeArchiveCache
|
|
145
162
|
def save_graph_projects(graph)
|
146
163
|
projects = graph.nodes.map(&:native_target).map(&:project).uniq
|
147
164
|
debug("updating #{projects.length} projects")
|
148
|
-
projects.each {|project| project.save}
|
165
|
+
projects.each { |project| project.save }
|
149
166
|
end
|
150
167
|
|
151
168
|
# @param [XcodeArchiveCache::BuildGraph::Node] prebuilt_node
|
152
169
|
# @param [Xcodeproj::Project::Object::PBXNativeTarget] dependent_target
|
153
170
|
#
|
154
|
-
def add_as_prebuilt_dependency(prebuilt_node, dependent_target
|
171
|
+
def add_as_prebuilt_dependency(prebuilt_node, dependent_target)
|
172
|
+
target_identifier = get_target_identifier(dependent_target)
|
173
|
+
return if prebuilt_node.targets_injected_to.include?(target_identifier)
|
174
|
+
|
155
175
|
debug("adding #{prebuilt_node.name} as prebuilt to #{dependent_target.display_name}")
|
156
176
|
|
157
177
|
unless prebuilt_node.has_acceptable_product?
|
@@ -161,9 +181,11 @@ module XcodeArchiveCache
|
|
161
181
|
if prebuilt_node.has_framework_product?
|
162
182
|
add_as_prebuilt_framework(prebuilt_node, dependent_target)
|
163
183
|
elsif prebuilt_node.has_static_library_product?
|
164
|
-
add_as_prebuilt_static_lib(prebuilt_node, dependent_target
|
184
|
+
add_as_prebuilt_static_lib(prebuilt_node, dependent_target)
|
165
185
|
end
|
166
186
|
|
187
|
+
prebuilt_node.targets_injected_to.push(target_identifier)
|
188
|
+
|
167
189
|
debug("done with #{prebuilt_node.name} for #{dependent_target.display_name}")
|
168
190
|
end
|
169
191
|
|
@@ -174,22 +196,41 @@ module XcodeArchiveCache
|
|
174
196
|
build_configuration = find_build_configuration(dependent_target)
|
175
197
|
|
176
198
|
artifact_location = storage.get_storage_path(prebuilt_node)
|
177
|
-
build_flags_changer.
|
199
|
+
build_flags_changer.replace_or_add_framework_search_path(build_configuration, prebuilt_node.native_target.name, artifact_location)
|
178
200
|
build_flags_changer.add_framework_headers_iquote(build_configuration, artifact_location, prebuilt_node)
|
179
201
|
|
202
|
+
if dependency_remover.is_linked(prebuilt_node, dependent_target)
|
203
|
+
build_flags_changer.add_framework_linker_flag(build_configuration, prebuilt_node)
|
204
|
+
end
|
205
|
+
|
180
206
|
dependency_remover.remove_dependency(prebuilt_node, dependent_target)
|
181
207
|
end
|
182
208
|
|
183
209
|
# @param [XcodeArchiveCache::BuildGraph::Node] prebuilt_node
|
184
210
|
# @param [Xcodeproj::Project::Object::PBXNativeTarget] dependent_target
|
185
|
-
# @param [Boolean] should_link
|
186
211
|
#
|
187
|
-
def add_as_prebuilt_static_lib(prebuilt_node, dependent_target
|
212
|
+
def add_as_prebuilt_static_lib(prebuilt_node, dependent_target)
|
188
213
|
build_configuration = find_build_configuration(dependent_target)
|
189
214
|
|
190
|
-
|
191
|
-
|
192
|
-
|
215
|
+
injected_modulemap_file_path = storage.get_modulemap_path(prebuilt_node)
|
216
|
+
if injected_modulemap_file_path
|
217
|
+
modulemap_file_names = [prebuilt_node.resulting_modulemap_file_name]
|
218
|
+
build_flags_changer.fix_module_map_path(build_configuration, modulemap_file_names, injected_modulemap_file_path)
|
219
|
+
|
220
|
+
original_modulemap_path = prebuilt_node.original_modulemap_file_path
|
221
|
+
add_header_paths_to_target(dependent_target, [File.dirname(original_modulemap_path)])
|
222
|
+
end
|
223
|
+
|
224
|
+
artifact_location = storage.get_storage_path(prebuilt_node)
|
225
|
+
build_flags_changer.replace_or_add_library_search_path(build_configuration, prebuilt_node.native_target.name, artifact_location)
|
226
|
+
build_flags_changer.add_swift_include_path(build_configuration, artifact_location)
|
227
|
+
|
228
|
+
if dependency_remover.is_linked(prebuilt_node, dependent_target)
|
229
|
+
if dependent_target.product_type == Xcodeproj::Constants::PRODUCT_TYPE_UTI[:static_library]
|
230
|
+
build_flags_changer.add_static_lib_libtool_flag(build_configuration, prebuilt_node)
|
231
|
+
else
|
232
|
+
build_flags_changer.add_static_lib_linker_flag(build_configuration, prebuilt_node)
|
233
|
+
end
|
193
234
|
end
|
194
235
|
|
195
236
|
dependency_remover.remove_dependency(prebuilt_node, dependent_target)
|
@@ -198,7 +239,7 @@ module XcodeArchiveCache
|
|
198
239
|
# @param [Xcodeproj::Project::Object::PBXNativeTarget] target
|
199
240
|
#
|
200
241
|
def find_build_configuration(target)
|
201
|
-
build_configuration = target.build_configurations.select {|configuration| configuration.name == configuration_name}.first
|
242
|
+
build_configuration = target.build_configurations.select { |configuration| configuration.name == configuration_name }.first
|
202
243
|
unless build_configuration
|
203
244
|
raise Informative, "#{configuration_name} build configuration not found on target #{node.name}"
|
204
245
|
end
|
@@ -223,6 +264,14 @@ module XcodeArchiveCache
|
|
223
264
|
debug("deleting #{node.name} target")
|
224
265
|
node.native_target.project.targets.delete(node.native_target)
|
225
266
|
end
|
267
|
+
|
268
|
+
# @param [Xcodeproj::Project::Object::PBXNativeTarget] target
|
269
|
+
#
|
270
|
+
# @return [String]
|
271
|
+
#
|
272
|
+
def get_target_identifier(target)
|
273
|
+
target.uuid + target.project.path.realpath.to_s
|
274
|
+
end
|
226
275
|
end
|
227
276
|
end
|
228
277
|
end
|