-
Notifications
You must be signed in to change notification settings - Fork 486
Description
Hi,
So I worked on a script to automatically generate a subproject and add it to an existing project and set up target dependency, link binary, and embedded frameworks. However, I noticed after running the script, the Xcode crashes when adding a new file to the project. When I tried to reproduce it in a simpler situation, I noticed that it's now crashing by adding any new phase under "Build phase". Following is the code sample for reproducing it and I have attached a zip file that has the script and sample code in it. For ease of use, I added the lines to clear and re-copy sample project.
By spending some time, I found the root cause of it is this line that's using the same product group as the main project instead of creating a new one, which seems to be what Xcode does. I tried the new theory with add_subproject_reference method and that fixes the issue with Xcode crash.
I was wondering if there's any specific reason the subproject is getting added to main project's product list instead of creating a new one? Or it might be something I'm doing wrong in code below for adding a subproject.
Thanks!
require("Xcodeproj")
require("pathname")
# def add_subproject_reference(main_project, subproject)
# # We call into the private function `FileReferencesFactory.new_file_reference` instead of `FileReferencesFactory.new_reference`
# # because it delegates into `FileReferencesFactory.new_subproject` which has the extra behavior of opening the Project which
# # is an expensive operation for large projects.
# #
# ref = Xcodeproj::Project::FileReferencesFactory.send(:new_file_reference, main_project.main_group, subproject.path, :built_products)
# basename = Pathname(subproject.path).basename
# subproject_name = File.basename(basename, ".*")
# ref.name = basename.to_s
# ref.include_in_index = nil
# product_group_ref = main_project.new(Xcodeproj::Project::PBXGroup)
# product_group_ref.name = "Products"
# subproject.products_group.files.each do |product_reference|
# container_proxy = main_project.new(Xcodeproj::Project::PBXContainerItemProxy)
# container_proxy.container_portal = ref.uuid
# container_proxy.proxy_type = Xcodeproj::Constants::PROXY_TYPES[:reference]
# container_proxy.remote_global_id_string = product_reference.uuid
# container_proxy.remote_info = subproject_name.to_s
# reference_proxy = main_project.new(Xcodeproj::Project::PBXReferenceProxy)
# extension = File.extname(product_reference.path)[1..-1]
# reference_proxy.file_type = Xcodeproj::Constants::FILE_TYPES_BY_EXTENSION[extension]
# reference_proxy.path = product_reference.path
# reference_proxy.remote_ref = container_proxy
# reference_proxy.source_tree = "BUILT_PRODUCTS_DIR"
# product_group_ref << reference_proxy
# end
#
# attribute = Xcodeproj::Project::PBXProject.references_by_keys_attributes.find { |attrb| attrb.name == :project_references }
# project_reference = Xcodeproj::Project::ObjectDictionary.new(attribute, product_group_ref)
# project_reference[:project_ref] = ref
# project_reference[:product_group] = product_group_ref
# main_project.root_object.project_references << project_reference
# ref
# end
require("fileutils")
FileUtils.rm_rf("./Subproj")
FileUtils.cp_r("./Mainproj copy/.", ".")
subproj_target_name = "Subproj"
worksace_path = "./Mainproj.xcworkspace"
workspace = Xcodeproj::Workspace.new_from_xcworkspace(worksace_path)
mainproj = Xcodeproj::Project.open("./Mainproj/Mainproj.xcodeproj")
subproj = Xcodeproj::Project.new("./#{subproj_target_name}/#{subproj_target_name}.xcodeproj")
subproj.new_target(:framework, subproj_target_name, :ios, "11.0", nil, :swift)
subproj.main_group.new_group(subproj_target_name)
workspace_ref_subproj = Xcodeproj::Workspace::FileReference.new("./Subproj/Subproj.xcodeproj")
workspace << workspace_ref_subproj
workspace.save_as(worksace_path)
subproj.save
# mainproj_ref_subproj = add_subproject_reference(mainproj, subproj)
mainproj_ref_subproj = Xcodeproj::Project::FileReferencesFactory.new_reference(mainproj.main_group, subproj.path, :built_products)
mainproj.targets[0].add_dependency(subproj.targets[0])
mainproj.targets[0].frameworks_build_phase.add_file_reference(
mainproj_ref_subproj.file_reference_proxies.first,
true
)
mainproj.save