Commit 82f47ffc authored by Fabio Pelosin's avatar Fabio Pelosin

[UserProjectIntegrator] Improve handling of the workspace

parent c048d1cb
......@@ -66,10 +66,10 @@ module Pod
#-----------------------------------------------------------------------#
# @!group Integration steps
private
# @!group Integration steps
# Creates and saved the workspace containing the Pods project and the
# user projects, if needed.
#
......@@ -80,19 +80,21 @@ module Pod
# @return [void]
#
def create_workspace
projpaths = (user_project_paths.dup.push(sandbox.project_path)).map do |path|
all_projects = user_project_paths.sort.push(sandbox.project_path).uniq
projpaths = all_projects.map do |path|
path.relative_path_from(workspace_path.dirname).to_s
end.uniq
end
if workspace_path.exist?
current_workspace = Xcodeproj::Workspace.new_from_xcworkspace(workspace_path)
if current_workspace.projpaths != projpaths
workspace = Xcodeproj::Workspace.new(*projpaths)
workspace = Xcodeproj::Workspace.new_from_xcworkspace(workspace_path)
new_projpaths = projpaths - workspace.projpaths
unless new_projpaths.empty?
workspace.projpaths.concat(new_projpaths)
workspace.save_as(workspace_path)
end
else
UI.notice "From now on use `#{workspace_path.basename}'."
UI.notice "From now on use `#{workspace_path.basename}`."
workspace = Xcodeproj::Workspace.new(*projpaths)
workspace.save_as(workspace_path)
end
......@@ -108,8 +110,7 @@ module Pod
# @return [void]
#
def integrate_user_targets
libraries.each do |lib|
next if lib.target_definition.empty?
libraries_to_integrate.each do |lib|
TargetIntegrator.new(lib).integrate!
end
end
......@@ -133,9 +134,9 @@ module Pod
#-----------------------------------------------------------------------#
# @!group Helpers.
private
public
# @!group Helpers.
# @return [Pathname] the path where the workspace containing the Pods
# project and the user projects should be saved.
......@@ -164,6 +165,11 @@ module Pod
end.compact.uniq
end
def libraries_to_integrate
libraries.reject { |lib| lib.target_definition.empty? }
end
#-----------------------------------------------------------------------#
end
......
......@@ -41,7 +41,14 @@ module Pod
def targets
unless @targets
target_uuids = library.user_target_uuids
targets = target_uuids.map { |uuid| user_project.targets.find { |target| target.uuid == uuid } }
targets = target_uuids.map do |uuid|
target = user_project.objects_by_uuid[uuid]
unless target
raise Informative, "[Bug] Unable to find the target with " \
"the `#{uuid}` UUID for the `#{library}` library"
end
target
end
non_integrated = targets.reject do |target|
target.frameworks_build_phase.files.any? do |build_file|
file_ref = build_file.file_ref
......
<?xml version='1.0' encoding='UTF-8'?><Workspace version='1.0'><FileRef location='group:SampleApp.xcodeproj'/><FileRef location='group:Pods/Pods.xcodeproj'/></Workspace>
\ No newline at end of file
<?xml version='1.0' encoding='UTF-8'?><Workspace version='1.0'><FileRef location='group:Pods/Pods.xcodeproj'/><FileRef location='group:SampleApp.xcodeproj'/></Workspace>
\ No newline at end of file
......@@ -37,10 +37,10 @@ Generating Pods Project
- Running pre install hooks
- Adding source files to Pods project
- Adding resources to Pods project
- Linking headers
- Installing targets
- Installing target `Pods` iOS 6.0
- Adding Build files
- Linking headers
- Generating xcconfig file at `Pods/Pods.xcconfig`
- Generating target header at `Pods/Pods-header.h`
- Generating prefix header at `Pods/Pods-prefix.pch`
......
......@@ -23,10 +23,10 @@ Generating Pods Project
- Running pre install hooks
- Adding source files to Pods project
- Adding resources to Pods project
- Linking headers
- Installing targets
- Installing target `Pods` iOS 4.3
- Adding Build files
- Linking headers
- Generating xcconfig file at `Pods/Pods.xcconfig`
- Generating target header at `Pods/Pods-header.h`
- Generating prefix header at `Pods/Pods-prefix.pch`
......@@ -41,6 +41,6 @@ Generating Pods Project
Integrating client projects
[!] From now on use `SampleApp.xcworkspace'.
[!] From now on use `SampleApp.xcworkspace`.
Integrating `libPods.a` into target `iOS App` of project `SampleApp.xcodeproj`.
......@@ -34,6 +34,6 @@ Generating Pods Project
Integrating client projects
[!] From now on use `SampleApp.xcworkspace'.
[!] From now on use `SampleApp.xcworkspace`.
Integrating `libPods.a` into target `iOS App` of project `SampleApp.xcodeproj`.
......@@ -57,10 +57,10 @@ Generating Pods Project
- Running pre install hooks
- Adding source files to Pods project
- Adding resources to Pods project
- Linking headers
- Installing targets
- Installing target `Pods` iOS 6.0
- Adding Build files
- Linking headers
- Generating xcconfig file at `Pods/Pods.xcconfig`
- Generating target header at `Pods/Pods-header.h`
- Generating prefix header at `Pods/Pods-prefix.pch`
......@@ -70,7 +70,6 @@ Generating Pods Project
- Generating dummy source file at `Pods/Pods-dummy.m`
- Installing target `Pods-test` iOS 6.0
- Adding Build files
- Linking headers
- Generating xcconfig file at `Pods/Pods-test.xcconfig`
- Generating target header at `Pods/Pods-test-header.h`
- Generating prefix header at `Pods/Pods-test-prefix.pch`
......@@ -80,7 +79,6 @@ Generating Pods Project
- Generating dummy source file at `Pods/Pods-test-dummy.m`
- Installing target `Pods-SampleApp_2` iOS 6.0
- Adding Build files
- Linking headers
- Generating xcconfig file at `Pods/Pods-SampleApp_2.xcconfig`
- Generating target header at `Pods/Pods-SampleApp_2-header.h`
- Generating prefix header at `Pods/Pods-SampleApp_2-prefix.pch`
......@@ -95,10 +93,10 @@ Generating Pods Project
Integrating client projects
[!] From now on use `SampleApp.xcworkspace'.
[!] From now on use `SampleApp.xcworkspace`.
Integrating `libPods.a` into target `SampleApp` of project `SampleApp.xcodeproj`.
Integrating `libPods-test.a` into target `SampleAppTests` of project `SampleApp.xcodeproj`.
Integrating `libPods-SampleApp_2.a` into target `SampleAppTests` of project `SampleApp.xcodeproj`.
Integrating `libPods-SampleApp_2.a` into target `SampleApp_2` of project `SampleApp.xcodeproj`.
......@@ -34,10 +34,10 @@ Generating Pods Project
- Running pre install hooks
- Adding source files to Pods project
- Adding resources to Pods project
- Linking headers
- Installing targets
- Installing target `Pods` iOS 6.0
- Adding Build files
- Linking headers
- Generating xcconfig file at `Pods/Pods.xcconfig`
- Generating target header at `Pods/Pods-header.h`
- Generating prefix header at `Pods/Pods-prefix.pch`
......@@ -52,6 +52,6 @@ Generating Pods Project
Integrating client projects
[!] From now on use `SampleApp.xcworkspace'.
[!] From now on use `SampleApp.xcworkspace`.
Integrating `libPods.a` into target `SampleApp` of project `SampleApp.xcodeproj`.
......@@ -35,10 +35,10 @@ Generating Pods Project
- Podfile
- Adding source files to Pods project
- Adding resources to Pods project
- Linking headers
- Installing targets
- Installing target `Pods` iOS 6.0
- Adding Build files
- Linking headers
- Generating xcconfig file at `Pods/Pods.xcconfig`
- Generating target header at `Pods/Pods-header.h`
- Generating prefix header at `Pods/Pods-prefix.pch`
......@@ -54,6 +54,6 @@ Generating Pods Project
Integrating client projects
[!] From now on use `SampleApp.xcworkspace'.
[!] From now on use `SampleApp.xcworkspace`.
Integrating `libPods.a` into target `SampleApp` of project `SampleApp.xcodeproj`.
......@@ -35,10 +35,10 @@ Generating Pods Project
- Running pre install hooks
- Adding source files to Pods project
- Adding resources to Pods project
- Linking headers
- Installing targets
- Installing target `Pods` iOS 6.0
- Adding Build files
- Linking headers
- Generating xcconfig file at `Pods/Pods.xcconfig`
- Generating target header at `Pods/Pods-header.h`
- Generating prefix header at `Pods/Pods-prefix.pch`
......@@ -53,6 +53,6 @@ Generating Pods Project
Integrating client projects
[!] From now on use `SampleApp.xcworkspace'.
[!] From now on use `SampleApp.xcworkspace`.
Integrating `libPods.a` into target `SampleApp` of project `SampleApp.xcodeproj`.
<?xml version='1.0' encoding='UTF-8'?><Workspace version='1.0'><FileRef location='group:SampleApp.xcodeproj'/><FileRef location='group:Pods/Pods.xcodeproj'/></Workspace>
\ No newline at end of file
<?xml version='1.0' encoding='UTF-8'?><Workspace version='1.0'><FileRef location='group:Pods/Pods.xcodeproj'/><FileRef location='group:SampleApp.xcodeproj'/></Workspace>
\ No newline at end of file
......@@ -25,10 +25,10 @@ Generating Pods Project
- Running pre install hooks
- Adding source files to Pods project
- Adding resources to Pods project
- Linking headers
- Installing targets
- Installing target `Pods` iOS 6.0
- Adding Build files
- Linking headers
- Generating xcconfig file at `Pods/Pods.xcconfig`
- Generating target header at `Pods/Pods-header.h`
- Generating prefix header at `Pods/Pods-prefix.pch`
......
......@@ -55,6 +55,6 @@ Generating Pods Project
Integrating client projects
[!] From now on use `SampleApp.xcworkspace'.
[!] From now on use `SampleApp.xcworkspace`.
Integrating `libPods.a` into target `SampleApp` of project `SampleApp.xcodeproj`.
......@@ -26,10 +26,10 @@ Generating Pods Project
- Running pre install hooks
- Adding source files to Pods project
- Adding resources to Pods project
- Linking headers
- Installing targets
- Installing target `Pods-iOS App` iOS 4.3
- Adding Build files
- Linking headers
- Generating xcconfig file at `Pods/Pods-iOS App.xcconfig`
- Generating target header at `Pods/Pods-iOS App-header.h`
- Generating prefix header at `Pods/Pods-iOS App-prefix.pch`
......@@ -39,7 +39,6 @@ Generating Pods Project
- Generating dummy source file at `Pods/Pods-iOS App-dummy.m`
- Installing target `Pods-OS X App` OS X 10.6
- Adding Build files
- Linking headers
- Generating xcconfig file at `Pods/Pods-OS X App.xcconfig`
- Generating target header at `Pods/Pods-OS X App-header.h`
- Generating prefix header at `Pods/Pods-OS X App-prefix.pch`
......@@ -54,7 +53,7 @@ Generating Pods Project
Integrating client projects
[!] From now on use `SampleApp.xcworkspace'.
[!] From now on use `SampleApp.xcworkspace`.
Integrating `libPods-iOS App.a` into target `iOS App` of project `SampleApp.xcodeproj`.
......
......@@ -27,7 +27,7 @@ module Pod
it 'returns the targets that need to be integrated' do
pods_library = @sample_project.frameworks_group.new_static_library('Pods')
@target.frameworks_build_phase.add_file_reference(pods_library)
Xcodeproj::Project.any_instance.stubs(:targets).returns([@target])
Xcodeproj::Project.any_instance.stubs(:objects_by_uuid).returns(@target.uuid => @target)
@target_integrator.targets.map(&:name).should.be.empty?
end
......
......@@ -8,76 +8,150 @@ module Pod
before do
@sample_project_path = SpecHelper.create_sample_app_copy_from_fixture('SampleProject')
sample_project_path = @sample_project_path
sample_project = Xcodeproj::Project.new sample_project_path
@podfile = Podfile.new do
platform :ios
xcodeproj sample_project_path
pod 'JSONKit'
target :test_runner, :exclusive => true do
link_with 'TestRunner'
pod 'Kiwi'
target :empty do
end
end
config.sandbox.project = Project.new()
@library = Library.new(@podfile.target_definitions[:default])
@library.user_project_path = sample_project_path
@library.user_target_uuids = ['A346496C14F9BE9A0080D870']
@library.support_files_root = config.sandbox.root
empty_library = Library.new(@podfile.target_definitions[:empty])
@integrator = Installer::UserProjectIntegrator.new(@podfile, config.sandbox, temporary_directory, [@library, empty_library])
end
#-----------------------------------------------------------------------#
describe "In general" do
@installation_root = @sample_project_path.dirname
@pods_project = Project.new()
config.sandbox.project = @pods_project
@libraries = @podfile.target_definitions.values.map do |target_definition|
lib = Library.new(target_definition)
lib.user_project_path = sample_project_path
lib.target = @pods_project.new_target(:static_library, target_definition.label, target_definition.platform.name)
lib.user_target_uuids = sample_project.targets.reject do |target|
target.is_a? Xcodeproj::Project::Object::PBXAggregateTarget
end.map(&:uuid)
lib.support_files_root = config.sandbox.root
lib.user_project_path = sample_project_path
lib
it "adds the Pods project to the workspace" do
@integrator.integrate!
workspace_path = @integrator.send(:workspace_path)
workspace = Xcodeproj::Workspace.new_from_xcworkspace(workspace_path)
workspace.projpaths.find { |path| path =~ /Pods.xcodeproj/ }.should.not.be.nil
end
@integrator = Installer::UserProjectIntegrator.new(@podfile, config.sandbox, @installation_root, @libraries)
end
it "uses the path of the workspace defined in the podfile" do
path = "a_path"
@podfile.workspace path
@integrator.workspace_path.should == path + ".xcworkspace"
end
it "integrates the user targets" do
@integrator.integrate!
user_project = Xcodeproj::Project.new(@sample_project_path)
target = user_project.objects_by_uuid[@library.user_target_uuids.first]
target.frameworks_build_phase.files.map(&:display_name).should.include('libPods.a')
end
it "names the workspace after the user project if needed" do
@integrator.workspace_path.should == @sample_project_path.dirname + 'SampleProject.xcworkspace'
end
it "warns if the podfile does not contain any dependency" do
Podfile::TargetDefinition.any_instance.stubs(:empty?).returns(true)
@integrator.integrate!
UI.warnings.should.include?('The Podfile does not contain any dependency')
end
it "raises if no workspace could be selected" do
@integrator.expects(:user_project_paths).returns(%w[ project1 project2 ])
lambda { @integrator.workspace_path }.should.raise Informative
end
it "returns the paths of the user projects" do
@integrator.user_project_paths.should == [ @sample_project_path ]
end
#-----------------------------------------------------------------------#
it "adds the project being integrated to the workspace" do
@integrator.integrate!
workspace = Xcodeproj::Workspace.new_from_xcworkspace(@integrator.workspace_path)
workspace.projpaths.sort.should == %w{ ../Pods/Pods.xcodeproj SampleProject.xcodeproj }
end
describe "Workspace creation" do
it "adds the Pods project to the workspace" do
@integrator.integrate!
workspace = Xcodeproj::Workspace.new_from_xcworkspace(@integrator.workspace_path)
workspace.projpaths.find { |path| path =~ /Pods.xcodeproj/ }.should.not.be.nil
end
it "creates a new workspace if needed" do
@integrator.send(:create_workspace)
workspace_path = @integrator.send(:workspace_path)
saved = Xcodeproj::Workspace.new_from_xcworkspace(workspace_path)
saved.projpaths.should == [
"SampleProject/SampleProject.xcodeproj",
"Pods/Pods.xcodeproj"
]
end
it "updates an existing workspace if needed" do
workspace_path = @integrator.send(:workspace_path)
workspace = Xcodeproj::Workspace.new('SampleProject/SampleProject.xcodeproj')
workspace.save_as(workspace_path)
@integrator.send(:create_workspace)
saved = Xcodeproj::Workspace.new_from_xcworkspace(workspace_path)
saved.projpaths.should == [
"SampleProject/SampleProject.xcodeproj",
"Pods/Pods.xcodeproj"
]
end
it "doesn't write the workspace if not needed" do
projpaths = [
"SampleProject/SampleProject.xcodeproj",
"Pods/Pods.xcodeproj"
]
workspace = Xcodeproj::Workspace.new(projpaths)
workspace_path = @integrator.send(:workspace_path)
workspace.save_as(workspace_path)
Xcodeproj::Workspace.expects(:save_as).never
@integrator.send(:create_workspace)
end
it "only appends projects to the workspace and never deletes one" do
workspace = Xcodeproj::Workspace.new('user_added_project.xcodeproj')
workspace_path = @integrator.send(:workspace_path)
workspace.save_as(workspace_path)
@integrator.send(:create_workspace)
saved = Xcodeproj::Workspace.new_from_xcworkspace(workspace_path)
saved.projpaths.should == [
'user_added_project.xcodeproj',
"SampleProject/SampleProject.xcodeproj",
"Pods/Pods.xcodeproj"
]
end
it "preserves the order of the projects in the workspace" do
projpaths = [
"Pods/Pods.xcodeproj",
"SampleProject/SampleProject.xcodeproj",
]
workspace = Xcodeproj::Workspace.new(projpaths)
workspace_path = @integrator.send(:workspace_path)
workspace.save_as(workspace_path)
@integrator.send(:create_workspace)
saved = Xcodeproj::Workspace.new_from_xcworkspace(workspace_path)
saved.projpaths.should == [
"Pods/Pods.xcodeproj",
"SampleProject/SampleProject.xcodeproj",
]
end
it "warns if the podfile does not contain any dependency" do
Podfile::TargetDefinition.any_instance.stubs(:empty?).returns(true)
@integrator.integrate!
UI.warnings.should.include?('The Podfile does not contain any dependency')
end
xit "It writes the workspace only if needed" do
#-----------------------------------------------------------------------#
describe "Helpers" do
it "uses the path of the workspace defined in the podfile" do
path = "a_path"
@podfile.workspace(path)
@integrator.send(:workspace_path).should == path + ".xcworkspace"
end
it "names the workspace after the user project if needed" do
@integrator.send(:workspace_path).should == temporary_directory + 'SampleProject.xcworkspace'
end
it "raises if no workspace could be selected" do
@integrator.expects(:user_project_paths).returns(%w[ project1 project2 ])
e = lambda { @integrator.send(:workspace_path) }.should.raise Informative
end
it "returns the paths of the user projects" do
@integrator.send(:user_project_paths).should == [ @sample_project_path ]
end
it "skips libraries with empty target definitions" do
@integrator.libraries.map(&:name).should == ["Pods", "Pods-empty"]
@integrator.send(:libraries_to_integrate).map(&:name).should == ['Pods']
end
end
#-----------------------------------------------------------------------#
end
end
end
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment