xcode-archive-cache 0.0.10.pre.1 → 0.0.12

Sign up to get free protection for your applications and to get access to all the features.
@@ -4,36 +4,41 @@ module XcodeArchiveCache
4
4
 
5
5
  include XcodeArchiveCache::Logs
6
6
 
7
- def initialize
7
+ # @param [XcodeArchiveCache::Injection::Storage] storage
8
+ #
9
+ def initialize(storage)
10
+ @storage = storage
8
11
  @build_settings_interpolator = XcodeArchiveCache::BuildSettings::StringInterpolator.new
9
12
  end
10
13
 
11
14
  # @param [Xcodeproj::Project::Object::PBXNativeTarget] target
12
15
  # @param [XcodeArchiveCache::BuildGraph::Graph] graph
13
- # @param [String] products_dir
14
16
  #
15
- def fix_embed_frameworks_script(target, graph, products_dir)
17
+ def fix_embed_frameworks_script(target, graph)
16
18
  build_settings = graph.dependent_build_settings
17
19
  file_path = find_embed_frameworks_script(target, build_settings)
18
20
  return unless file_path
19
21
 
20
- fix_script(file_path, graph, products_dir)
22
+ fix_script(file_path, graph)
21
23
  end
22
24
 
23
25
  # @param [Xcodeproj::Project::Object::PBXNativeTarget] target
24
26
  # @param [XcodeArchiveCache::BuildGraph::Graph] graph
25
- # @param [String] products_dir
26
27
  #
27
- def fix_copy_resources_script(target, graph, products_dir)
28
+ def fix_copy_resources_script(target, graph)
28
29
  build_settings = graph.dependent_build_settings
29
30
  file_path = find_copy_resources_script(target, build_settings)
30
31
  return unless file_path
31
32
 
32
- fix_script(file_path, graph, products_dir)
33
+ fix_script(file_path, graph)
33
34
  end
34
35
 
35
36
  private
36
37
 
38
+ # @return [XcodeArchiveCache::Injection::Storage]
39
+ #
40
+ attr_reader :storage
41
+
37
42
  # @return [XcodeArchiveCache::BuildSettings::StringInterpolator]
38
43
  #
39
44
  attr_reader :build_settings_interpolator
@@ -44,7 +49,7 @@ module XcodeArchiveCache
44
49
  # @return [String]
45
50
  #
46
51
  def find_embed_frameworks_script(target, build_settings)
47
- find_script(target, build_settings, "[CP] Embed Pods Frameworks")
52
+ target.find_script(build_settings_interpolator, build_settings, "[CP] Embed Pods Frameworks")
48
53
  end
49
54
 
50
55
  # @param [Xcodeproj::Project::Object::PBXNativeTarget] target
@@ -53,38 +58,18 @@ module XcodeArchiveCache
53
58
  # @return [String]
54
59
  #
55
60
  def find_copy_resources_script(target, build_settings)
56
- find_script(target, build_settings, "[CP] Copy Pods Resources")
57
- end
58
-
59
- # @param [Xcodeproj::Project::Object::PBXNativeTarget] target
60
- # @param [XcodeArchiveCache::BuildSettings::Container] build_settings
61
- # @param [String] script_name
62
- #
63
- # @return [String]
64
- #
65
- def find_script(target, build_settings, script_name)
66
- target.shell_script_build_phases.each do |phase|
67
- if phase.display_name == script_name
68
- return build_settings_interpolator.interpolate(phase.shell_script, build_settings)
69
- .gsub(/^"|"$/, "")
70
- .strip
71
- end
72
- end
73
-
74
- nil
61
+ target.find_script(build_settings_interpolator, build_settings, "[CP] Copy Pods Resources")
75
62
  end
76
63
 
77
64
  # @param [String] file_path
78
- # @param [XcodeArchiveCache::BuildGraph::Node] graph
79
- # @param [String] products_dir
65
+ # @param [XcodeArchiveCache::BuildGraph::Graph] graph
80
66
  #
81
- def fix_script(file_path, graph, products_dir)
67
+ def fix_script(file_path, graph)
82
68
  info("fixing #{file_path}")
83
69
  script = File.read(file_path)
84
70
  graph.nodes.each do |node|
85
- relative_product_path = "#{node.native_target.display_name}/#{node.product_file_name}"
86
- absolute_product_path = File.join(products_dir, relative_product_path)
87
- script = script.gsub(Regexp.new("\"[^\"]+\/#{node.product_file_name}\""), "\"#{absolute_product_path}\"")
71
+ product_path = File.join(storage.get_storage_path(node), node.product_file_name)
72
+ script = script.gsub(Regexp.new("\"[^\"]+\/#{node.product_file_name}\""), "\"#{product_path}\"")
88
73
  end
89
74
 
90
75
  File.open(file_path, "w") {|file| file.puts(script)}
@@ -0,0 +1,126 @@
1
+ module XcodeArchiveCache
2
+ module Injection
3
+ class PodsXCFrameworkFixer
4
+
5
+ include XcodeArchiveCache::Logs
6
+
7
+ # @param [XcodeArchiveCache::Injection::Storage] storage
8
+ # @param [XcodeArchive::BuildGraph::NativeTargetFinder] native_target_finder
9
+ # @param [String] configuration_name
10
+ #
11
+ def initialize(storage, native_target_finder, configuration_name)
12
+ @storage = storage
13
+ @native_target_finder = native_target_finder
14
+ @configuration_name = configuration_name
15
+ @shell_executor = XcodeArchiveCache::Shell::Executor.new
16
+ @build_settings_interpolator = XcodeArchiveCache::BuildSettings::StringInterpolator.new
17
+ @checked_targets = []
18
+ end
19
+
20
+ # @param [Xcodeproj::Project::Object::PBXAbstractTarget] target
21
+ # @param [XcodeArchiveCache::BuildSettings::Loader] build_settings_loader
22
+ #
23
+ def fix(target, build_settings_loader)
24
+ checked_targets.push(target.equatable_identifier)
25
+ build_settings = build_settings_loader.get_settings(target.project.path, target.display_name)
26
+
27
+ debug("fixing #{target.display_name}")
28
+ script_path = find_copy_xcframeworks_script(target, build_settings)
29
+ if script_path != nil
30
+ fix_file(script_path)
31
+
32
+ unless shell_executor.execute_with_env(script_path, build_settings.all)
33
+ raise XcodeArchiveCache::Informative, "Failed to execute Pods XCFramework script #{script_path}"
34
+ end
35
+ end
36
+
37
+ embed_frameworks_script_path = find_embed_frameworks_script(target, build_settings)
38
+ if embed_frameworks_script_path != nil
39
+ fix_file(embed_frameworks_script_path)
40
+ end
41
+
42
+ build_configuration = target.find_build_configuration(configuration_name)
43
+ if build_configuration.has_xcconfig?
44
+ fix_xcconfig_recursively(build_configuration.get_xcconfig_path, build_configuration.get_project_dir)
45
+ end
46
+
47
+ dependencies = native_target_finder.find_all_dependencies(target)
48
+ dependencies.each do |dependency_target|
49
+ if checked_targets.include?(dependency_target.equatable_identifier)
50
+ next
51
+ end
52
+
53
+ fix(dependency_target, build_settings_loader)
54
+ end
55
+ end
56
+
57
+ private
58
+
59
+ # @return [XcodeArchive::Injection::InjectionStorage]
60
+ #
61
+ attr_reader :storage
62
+
63
+ # @return [XcodeArchive::BuildGraph::NativeTargetFinder]
64
+ #
65
+ attr_reader :native_target_finder
66
+
67
+ # @return [String]
68
+ #
69
+ attr_reader :configuration_name
70
+
71
+ # @return [XcodeArchiveCache::Shell::Executor]
72
+ #
73
+ attr_reader :shell_executor
74
+
75
+ # @return [XcodeArchiveCache::BuildSettings::StringInterpolator]
76
+ #
77
+ attr_reader :build_settings_interpolator
78
+
79
+ # @return [Array<String>]
80
+ #
81
+ attr_accessor :checked_targets
82
+
83
+ # @param [String] path
84
+ # @param [String] project_dir
85
+ #
86
+ def fix_xcconfig_recursively(path, project_dir)
87
+ fix_file(path)
88
+ xcconfig = Xcodeproj::Config.new(path)
89
+
90
+ xcconfig.includes.each do |included_xcconfig|
91
+ included_xcconfig_path = File.join(project_dir, included_xcconfig)
92
+ fix_xcconfig_recursively(included_xcconfig_path, project_dir)
93
+ end
94
+ end
95
+
96
+ # @param [Xcodeproj::Project::Object::PBXAbstractTarget] target
97
+ # @param [XcodeArchiveCache::BuildSettings::Container] build_settings
98
+ #
99
+ # @return [String]
100
+ #
101
+ def find_copy_xcframeworks_script(target, build_settings)
102
+ target.find_script(build_settings_interpolator, build_settings, "[CP] Copy XCFrameworks")
103
+ end
104
+
105
+ # @param [Xcodeproj::Project::Object::PBXAbstractTarget] target
106
+ # @param [XcodeArchiveCache::BuildSettings::Container] build_settings
107
+ #
108
+ # @return [String]
109
+ #
110
+ def find_embed_frameworks_script(target, build_settings)
111
+ target.find_script(build_settings_interpolator, build_settings, "[CP] Embed Pods Frameworks")
112
+ end
113
+
114
+ # @param [String] file_path
115
+ #
116
+ def fix_file(file_path)
117
+ debug("fixing #{file_path}")
118
+ contents = File
119
+ .read(file_path)
120
+ .gsub("${PODS_XCFRAMEWORKS_BUILD_DIR}", storage.container_dir_path)
121
+
122
+ File.open(file_path, "w") {|file| file.puts(contents)}
123
+ end
124
+ end
125
+ end
126
+ end
@@ -23,8 +23,8 @@ module XcodeArchiveCache
23
23
  # @param [String] path
24
24
  # @param [Array<String>] file_paths
25
25
  #
26
- def store_headers(node, path, file_paths)
27
- storage_path = get_full_header_storage_path(path)
26
+ def store_headers(node, path, file_paths, save_path = true)
27
+ storage_path = Pathname.new(path).absolute? ? path : get_full_header_storage_path(path)
28
28
 
29
29
  unless File.exist?(storage_path)
30
30
  FileUtils.mkdir_p(storage_path)
@@ -34,7 +34,7 @@ module XcodeArchiveCache
34
34
  FileUtils.cp(file_path, get_stored_file_path(storage_path, file_path))
35
35
  end
36
36
 
37
- save_header_storage_path(storage_path, node)
37
+ save_header_storage_path(storage_path, node) if save_path
38
38
  end
39
39
 
40
40
  # @param [XcodeArchiveCache::BuildGraph::Node] node
@@ -44,13 +44,8 @@ module XcodeArchiveCache
44
44
  store_headers(node, get_default_headers_storage_path(node), file_paths)
45
45
  end
46
46
 
47
- # @param [XcodeArchiveCache::BuildGraph::Node] node
48
- #
49
- def store_modulemap(node)
50
- modulemap_file_path = node.modulemap_file_path
51
- if modulemap_file_path && File.exist?(modulemap_file_path)
52
- store_headers(node, get_default_headers_storage_path(node), [modulemap_file_path])
53
- end
47
+ def store_modulemap_headers(node, file_paths)
48
+ store_headers(node, get_storage_path(node), file_paths, false)
54
49
  end
55
50
 
56
51
  # @param [XcodeArchiveCache::BuildGraph::Node] node
@@ -58,11 +53,11 @@ module XcodeArchiveCache
58
53
  # @return [String]
59
54
  #
60
55
  def get_modulemap_path(node)
61
- modulemap_file_path = node.modulemap_file_path
62
- return if modulemap_file_path == nil
56
+ modulemap_file_name = node.resulting_modulemap_file_name
57
+ return if modulemap_file_name == nil
63
58
 
64
- storage_path = get_full_header_storage_path(get_default_headers_storage_path(node))
65
- stored_modulemap_file_path = get_stored_file_path(storage_path, modulemap_file_path)
59
+ storage_path = get_storage_path(node)
60
+ stored_modulemap_file_path = get_stored_file_path(storage_path, modulemap_file_name)
66
61
  File.exist?(stored_modulemap_file_path) ? stored_modulemap_file_path : nil
67
62
  end
68
63
 
@@ -82,7 +77,7 @@ module XcodeArchiveCache
82
77
  def prepare_storage(node)
83
78
  path = get_storage_path(node)
84
79
  if File.exist?(path)
85
- raise StandardError.new, "Injection storage path is already busy"
80
+ raise StandardError.new, "Injection storage path is already busy: #{path}"
86
81
  end
87
82
 
88
83
  FileUtils.mkdir_p(path)
@@ -94,7 +89,12 @@ module XcodeArchiveCache
94
89
  # @return [String]
95
90
  #
96
91
  def get_storage_path(node)
97
- File.join(container_dir_path, node.name)
92
+ path = File.join(container_dir_path, node.name)
93
+ if node.native_target
94
+ path += "-#{node.native_target.uuid}"
95
+ end
96
+
97
+ path
98
98
  end
99
99
 
100
100
  # @param [XcodeArchiveCache::BuildGraph::Node] node
@@ -0,0 +1,20 @@
1
+ module XcodeArchiveCache
2
+ module Modulemap
3
+ class FileHandler
4
+ # @param [String] modulemap_path
5
+ #
6
+ # @return [Array<String>]
7
+ #
8
+ def read_modulemap_lines(modulemap_path)
9
+ File.read(modulemap_path).split("\n")
10
+ end
11
+
12
+ # @param [Array<String>] lines
13
+ # @param [String] modulemap_path
14
+ #
15
+ def write_modulemap_lines(lines, modulemap_path)
16
+ File.open(modulemap_path, "w") { |file| file.puts lines.join("\n") }
17
+ end
18
+ end
19
+ end
20
+ end
@@ -0,0 +1,67 @@
1
+ module XcodeArchiveCache
2
+ module Modulemap
3
+ class HeaderPathDeclaration
4
+ # @return [String]
5
+ #
6
+ attr_reader :type
7
+
8
+ # @return [String]
9
+ #
10
+ attr_reader :path
11
+
12
+ # @param [String] type
13
+ # @param [String] path
14
+ #
15
+ def initialize(type, path)
16
+ @type = type
17
+ @path = path
18
+ end
19
+ end
20
+
21
+ class HeaderPathExtractor
22
+
23
+ include XcodeArchiveCache::Logs
24
+
25
+ # @param [String] modulemap_path
26
+ #
27
+ # @return [Array<String>]
28
+ #
29
+ def extract_all_paths(modulemap_path)
30
+ modulemap_dir = File.dirname(modulemap_path)
31
+ modulemap_lines = FileHandler.new.read_modulemap_lines(modulemap_path)
32
+ header_paths = []
33
+
34
+ modulemap_lines.each do |line|
35
+ header_declaration = extract_header_declaration(line)
36
+ if header_declaration
37
+ header_paths << get_full_header_path(modulemap_dir, header_declaration.path)
38
+ end
39
+ end
40
+
41
+ debug("modulemap header paths: #{header_paths}")
42
+
43
+ header_paths
44
+ end
45
+
46
+ # @param [String] modulemap_dir
47
+ # @param [String] path
48
+ #
49
+ # @return [String]
50
+ #
51
+ def get_full_header_path(modulemap_dir, path)
52
+ Pathname.new(path).absolute? ? path : File.join(modulemap_dir, path)
53
+ end
54
+
55
+ # @param [String] line
56
+ #
57
+ # @return [XcodeArchiveCache::Modulemap::HeaderPathDeclaration]
58
+ #
59
+ def extract_header_declaration(line)
60
+ if line.include?("header") && !line.include?("exclude")
61
+ components = line.split("\"")
62
+ HeaderPathDeclaration.new(components[0], components[1])
63
+ end
64
+ end
65
+ end
66
+ end
67
+ end
@@ -0,0 +1,65 @@
1
+ module XcodeArchiveCache
2
+ module Modulemap
3
+ class HeaderPathFixer
4
+
5
+ include XcodeArchiveCache::Logs
6
+
7
+ # @param [Storage] storage
8
+ #
9
+ def initialize(storage)
10
+ @storage = storage
11
+ @header_path_extractor = HeaderPathExtractor.new
12
+ end
13
+
14
+ # @param [XcodeArchiveCache::BuildGraph::Node] node
15
+ #
16
+ def fix_modulemap(node)
17
+ return unless node.has_static_library_product?
18
+
19
+ injected_modulemap_file_path = storage.get_modulemap_path(node)
20
+ return if injected_modulemap_file_path == nil
21
+
22
+ file_handler = FileHandler.new
23
+
24
+ modulemap_dir = File.dirname(injected_modulemap_file_path)
25
+ modulemap_lines = file_handler.read_modulemap_lines(injected_modulemap_file_path)
26
+
27
+ updated_lines = modulemap_lines.map do |line|
28
+ declaration = header_path_extractor.extract_header_declaration(line)
29
+ next line unless declaration
30
+
31
+ # absolute paths depend on machine and derived data dir
32
+ #
33
+ full_header_path = header_path_extractor.get_full_header_path(modulemap_dir, declaration.path)
34
+ should_replace = Pathname.new(declaration.path).absolute? || !File.exist?(full_header_path)
35
+ next line unless should_replace
36
+
37
+ header_file_name = File.basename(declaration.path)
38
+ injected_header_path = File.join(modulemap_dir, header_file_name)
39
+ next line if injected_header_path == declaration.path
40
+
41
+ if File.exist?(injected_header_path)
42
+ debug("substituting #{declaration.path} with #{injected_header_path} in #{File.basename(injected_modulemap_file_path)}")
43
+ "#{declaration.type}\"#{injected_header_path}\""
44
+ else
45
+ error("failed to substitute missing header #{declaration.path} with another missing header in #{File.basename(injected_modulemap_file_path)}")
46
+ error("leaving the path as it is")
47
+ line
48
+ end
49
+ end
50
+
51
+ file_handler.write_modulemap_lines(updated_lines, injected_modulemap_file_path)
52
+ end
53
+
54
+ private
55
+
56
+ # @return [Storage]
57
+ #
58
+ attr_accessor :storage
59
+
60
+ # @return [XcodeArchiveCache::Modulemap::HeaderPathExtractor]
61
+ #
62
+ attr_accessor :header_path_extractor
63
+ end
64
+ end
65
+ end
data/lib/runner/runner.rb CHANGED
@@ -9,7 +9,7 @@ module XcodeArchiveCache
9
9
  @config = config
10
10
 
11
11
  projects = list_projects
12
- @native_target_finder = XcodeArchiveCache::BuildGraph::NativeTargetFinder.new(projects)
12
+ @native_target_finder = XcodeArchiveCache::BuildGraph::NativeTargetFinder.new(projects, config.active_configuration.build_configuration)
13
13
 
14
14
  storage_path = File.absolute_path(config.storage.path)
15
15
  @cache_storage = XcodeArchiveCache::ArtifactCache::LocalStorage.new(storage_path)
@@ -37,7 +37,7 @@ module XcodeArchiveCache
37
37
  return workspace.file_references.map {|file_reference| Xcodeproj::Project.open(file_reference.absolute_path(workspace_dir))}
38
38
  end
39
39
 
40
- raise Informative, "Configuration misses entry point -- must have either a project or a workspace"
40
+ raise XcodeArchiveCache::Informative, "Configuration misses entry point -- must have either a project or a workspace"
41
41
  end
42
42
 
43
43
  def run
@@ -65,37 +65,56 @@ module XcodeArchiveCache
65
65
  def handle_target(target_config)
66
66
  target = @native_target_finder.find_for_product_name(target_config.name)
67
67
  unless target
68
- raise Informative, "Target not found for #{target_config.name}"
68
+ raise XcodeArchiveCache::Informative, "Target not found for #{target_config.name}"
69
69
  end
70
70
 
71
+ xcodebuild_executor = XcodeArchiveCache::Xcodebuild::Executor.new(config.active_configuration.build_configuration,
72
+ target.platform_name,
73
+ config.settings.destination,
74
+ config.active_configuration.action,
75
+ config.active_configuration.xcodebuild_args)
76
+ build_settings_loader = XcodeArchiveCache::BuildSettings::Loader.new(xcodebuild_executor)
77
+ graph_builder = XcodeArchiveCache::BuildGraph::Builder.new(@native_target_finder, build_settings_loader)
78
+
79
+ dependency_targets = Hash.new
80
+ build_graphs = Hash.new
81
+
82
+ target_config.dependencies.each do |dependency_name|
83
+ info("creating build graph for #{dependency_name}")
84
+
85
+ dependency_target = find_dependency_target(target, dependency_name)
86
+ dependency_targets[dependency_name] = dependency_target
87
+ build_graphs[dependency_name] = graph_builder.build_graph(target, dependency_target)
88
+ end
89
+
90
+ pods_xcframeworks_fixer = XcodeArchiveCache::Injection::PodsXCFrameworkFixer.new(@injection_storage, @native_target_finder, config.active_configuration.build_configuration)
91
+ pods_xcframeworks_fixer.fix(target, build_settings_loader)
92
+
71
93
  target_config.dependencies.each do |dependency_name|
72
- handle_dependency(target, dependency_name)
94
+ info("processing #{dependency_name}")
95
+
96
+ dependency_target = dependency_targets[dependency_name]
97
+ build_graph = build_graphs[dependency_name]
98
+
99
+ @rebuild_evaluator.evaluate_build_graph(build_graph)
100
+ unpack_cached_artifacts(build_graph)
101
+ rebuild_if_needed(xcodebuild_executor, dependency_target, build_graph)
102
+ @injector.perform_outgoing_injection(build_graph, target)
73
103
  end
74
104
  end
75
105
 
76
106
  # @param [Xcodeproj::Project::Object::PBXNativeTarget] target
77
107
  # @param [String] dependency_name
78
108
  #
79
- def handle_dependency(target, dependency_name)
80
- info("checking #{dependency_name}")
81
-
109
+ # @return [Xcodeproj::Project::Object::PBXNativeTarget]
110
+ #
111
+ def find_dependency_target(target, dependency_name)
82
112
  dependency_target = @native_target_finder.find_for_product_name(dependency_name)
83
113
  unless dependency_target
84
- raise Informative, "Target not found for #{dependency_name} of #{target.display_name}"
114
+ raise XcodeArchiveCache::Informative, "Target not found for #{dependency_name} of #{target.display_name}"
85
115
  end
86
116
 
87
- xcodebuild_executor = XcodeArchiveCache::Xcodebuild::Executor.new(config.active_configuration.build_configuration,
88
- dependency_target.platform_name,
89
- config.settings.destination,
90
- config.active_configuration.action,
91
- config.active_configuration.xcodebuild_args)
92
- graph_builder = XcodeArchiveCache::BuildGraph::Builder.new(@native_target_finder, xcodebuild_executor)
93
- graph = graph_builder.build_graph(target, dependency_target)
94
-
95
- @rebuild_evaluator.evaluate_build_graph(graph)
96
- unpack_cached_artifacts(graph)
97
- rebuild_if_needed(xcodebuild_executor, dependency_target, graph)
98
- @injector.perform_outgoing_injection(graph, target)
117
+ dependency_target
99
118
  end
100
119
 
101
120
  # @param [XcodeArchiveCache::BuildGraph::Graph] graph
@@ -12,7 +12,7 @@ module XcodeArchiveCache
12
12
  output, status = Open3.capture2e(actual_command)
13
13
 
14
14
  if status.exitstatus != 0
15
- raise Informative, "#{command}\nexecution failed\n#{output}"
15
+ raise XcodeArchiveCache::Informative, "#{command}\nexecution failed\n#{output}"
16
16
  end
17
17
 
18
18
  output
@@ -31,6 +31,18 @@ module XcodeArchiveCache
31
31
  result
32
32
  end
33
33
 
34
+ # @param [String] command
35
+ # @param [Hash] env
36
+ #
37
+ # @return [Boolean] true if command succeeded and returned 0, false otherwise
38
+ #
39
+ def execute_with_env(command, env)
40
+ result = system(env, "set -x && '#{command}'")
41
+
42
+ return false if result == nil
43
+ result
44
+ end
45
+
34
46
  private
35
47
 
36
48
  # @param [String] command
@@ -40,12 +40,16 @@ require 'build_settings/parser'
40
40
 
41
41
  require 'injection/injector'
42
42
  require 'injection/pods_script_fixer'
43
- require 'injection/modulemap_fixer'
44
43
  require 'injection/build_flags_changer'
45
44
  require 'injection/dependency_remover'
46
45
  require 'injection/headers_mover'
47
46
  require 'injection/storage'
48
47
  require 'injection/framework_embedder'
48
+ require 'injection/pods_xcframework_fixer'
49
+
50
+ require 'modulemap/file_handler'
51
+ require 'modulemap/header_path_extractor'
52
+ require 'modulemap/header_path_fixer'
49
53
 
50
54
  require 'runner/runner'
51
55
 
@@ -53,6 +57,9 @@ require 'shell/executor'
53
57
 
54
58
  require 'xcodebuild/executor'
55
59
 
60
+ require 'extensions/target'
61
+ require 'extensions/build_configuration'
62
+
56
63
  module XcodeArchiveCache
57
64
  class Informative < StandardError
58
65
  include CLAide::InformativeError
@@ -117,7 +117,7 @@ module XcodeArchiveCache
117
117
  #
118
118
  inferred_destination = action == ARCHIVE_ACTION ? GENERIC_DESTINATION : destination_by_platform
119
119
  if inferred_destination == nil
120
- raise Informative, "Destination not set for #{platform} platform"
120
+ raise XcodeArchiveCache::Informative, "Destination not set for #{platform} platform"
121
121
  end
122
122
 
123
123
  destination_specifier = inferred_destination == GENERIC_DESTINATION ? "generic/platform=#{platform}" : inferred_destination