require 'xcodeproj' module IOS class ProjectManipulator attr_reader :configurator, :keep_demo, :module_type, :module_root_path, :module_path, :has_swiftgen, :has_interface, :has_test def self.perform(options) new(options).perform end def initialize(options) @configurator = options.fetch(:configurator) @keep_demo = options.fetch(:keep_demo) @module_type = options.fetch(:module_type) @has_swiftgen = options.fetch(:has_swiftgen) @has_interface = options.fetch(:has_interface) @has_test = options.fetch(:has_test) @module_root_path = "" end def run createModulePath createModuleImplFolder createModuleDummies createPodspec if @has_interface == :yes createModuleInterfaceFolder createModuleInterfaceDummies createPodspecInterface end if @has_test == :yes createTests end createSwiftgen if @has_swiftgen == :yes createExampleProject if @keep_demo == :yes end def project_folder $basePath = `git rev-parse --show-toplevel`.chomp raise "Para rodar a rotina, você deve estar na raiz do projeto" if $basePath == "." return $basePath end def module_folder return "FeatureModules" if @module_type == :feature "CoreModules" end def createModulePath @configurator.printMessage("Criando estrutura do módulo") @module_root_path = File.join(project_folder, [module_folder, @configurator.pod_name]) @module_path = File.join(@module_root_path, @configurator.pod_name) # Create a new folder with pod name FileUtils.mkdir_p @module_path # Create a new folder with pod name interface if @has_interface == :yes FileUtils.mkdir_p @module_path + "Interface" end # Create a new folder with pod name test if @has_test == :yes FileUtils.mkdir_p @module_path + "Tests" end Dir.chdir @module_root_path @configurator.printDone end def createExampleProject @configurator.printMessage("Criando projeto Exemplo") projectFileName = File.join(@module_root_path, "Example") FileUtils.cp_r(File.join(@configurator.template_path, "/Example/Example"), @module_root_path) podDevInjection = "pod '${POD_NAME}', path: '../'" if @has_test == :yes podDevInjection = "pod '${POD_NAME}', path: '../', :testspecs => ['Tests']" end if @has_interface == :yes podDevInjection += "\n pod '${POD_NAME}Interface', path: '../'" end text = File.read projectFileName + "/Podfile" text.gsub!("${DEV_PODS}", podDevInjection) text.gsub!("${POD_NAME}", @configurator.pod_name) File.open(projectFileName + "/Podfile", "w") { |file| file.puts text} @configurator.printDone end def createModuleImplFolder @configurator.printMessage("Gerando pastas base") FileUtils.mkdir_p File.join(@module_path, "Sources") if @module_type == :feature FileUtils.mkdir_p File.join(@module_path, "Sources", "Features") end if @has_swiftgen == :yes FileUtils.mkdir_p File.join(@module_path, "Sources", "ModuleConfiguration") end FileUtils.mkdir_p File.join(@module_path, "Resources") @configurator.printDone end def createModuleInterfaceFolder @configurator.printMessage("Gerando pastas de interface") FileUtils.mkdir_p File.join(@module_path + "Interface" , "Sources") FileUtils.mkdir_p File.join(@module_path + "Interface", "Resources") @configurator.printDone end def createModuleDummies @configurator.printMessage("Gerando arquivos de exemplo") if @module_type == :feature FileUtils.touch File.join(@module_path, "Sources", "Features", "Dummy.swift") else FileUtils.touch File.join(@module_path, "Sources", "DummySource.swift") end # Header.h headerFilename = File.join(@module_path, "Resources", @configurator.pod_name + ".h") FileUtils.cp( File.join(@configurator.template_path, "Feature", "Header_template"), headerFilename ) text = File.read(headerFilename) text.gsub!("${POD_NAME}", @configurator.pod_name) File.open(headerFilename, "w") { |file| file.puts text} # Info.plist FileUtils.cp( File.join(@configurator.template_path, "Feature", "Info_template"), File.join(@module_path, "Resources", "Info.plist") ) if @has_swiftgen == :yes # Bundle bundleFilename = File.join(@module_path, "Sources", "ModuleConfiguration", "Bundle.swift") FileUtils.cp( File.join(@configurator.template_path, "Feature", "bundle_template"), bundleFilename ) text = File.read(bundleFilename) text.gsub!("${POD_NAME}", @configurator.pod_name) File.open(bundleFilename, "w") { |file| file.puts text} # Strings FileUtils.touch File.join(@module_path, "Resources", "Localizable.strings") File.open(File.join(@module_path, "Resources", "Localizable.strings"), "w") { |file| file.puts "\"example.title.text\" = \"EXAMPLE\";" } # Assets FileUtils.mkdir_p(File.join(@module_path, "Resources", "Assets.xcassets")) end @configurator.printDone end def createModuleInterfaceDummies @configurator.printMessage("Gerando arquivos de exemplo na Interface") FileUtils.touch File.join(@module_path + "Interface", "Sources", "DummyInterface.swift") # Info.plist FileUtils.cp( File.join(@configurator.template_path, "Feature", "Info_template"), File.join(@module_path + "Interface", "Resources", "Info.plist") ) # Header.h headerFilename = File.join(@module_path + "Interface", "Resources", @configurator.pod_name + ".h") FileUtils.cp( File.join(@configurator.template_path, "Feature", "Header_template"), headerFilename ) text = File.read(headerFilename) text.gsub!("${POD_NAME}", @configurator.pod_name) File.open(headerFilename, "w") { |file| file.puts text} @configurator.printDone end def createSwiftgen @configurator.printMessage("Criando arquivo swiftgen") fileName = File.join(@module_root_path, "swiftgen.yml") FileUtils.cp( File.join(@configurator.template_path, "swiftgen.yml"), fileName ) text = File.read(fileName) text.gsub!("${POD_NAME}", @configurator.pod_name) File.open(fileName, "w") { |file| file.puts text} @configurator.printDone end def createPodspec @configurator.printMessage("Configurando arquivo Podspec") podspecFilename = "#{module_root_path}/#{@configurator.pod_name}.podspec" FileUtils.cp(File.join(@configurator.template_path, "NAME.podspec"), podspecFilename) text = File.read podspecFilename podTests = "" if @has_test == :yes podTests = "# TESTS" podTests += "\n s.test_spec 'Tests' do |test_spec|" podTests += "\n test_spec.source_files = '${POD_NAME}Tests/**/*'" podTests += "\n test_spec.exclude_files = '${POD_NAME}Tests/Resources/*.plist'" podTests += "\n end" end podInternal = "" if @has_interface == :yes podInternal = "s.dependency '${POD_NAME}Interface'" end text.gsub!("${FEATURE_INTERNAL}", podInternal) text.gsub!("${FEATURE_TEST}", podTests) text.gsub!("${POD_NAME}", @configurator.pod_name) text.gsub!("${USER_NAME}", @configurator.user_name) text.gsub!("${USER_EMAIL}", @configurator.user_email) File.open(podspecFilename, "w") { |file| file.puts text} @configurator.printDone end def createPodspecInterface @configurator.printMessage("Configurando arquivo Podspec Interface") podspecFilename = "#{module_root_path}/#{@configurator.pod_name}Interface.podspec" FileUtils.cp(File.join(@configurator.template_path, "NAMEInterface.podspec"), podspecFilename) text = File.read podspecFilename text.gsub!("${POD_NAME}", @configurator.pod_name) text.gsub!("${USER_NAME}", @configurator.user_name) text.gsub!("${USER_EMAIL}", @configurator.user_email) File.open(podspecFilename, "w") { |file| file.puts text} @configurator.printDone end def createTests @configurator.printMessage("Gerando pastas de testes") # Folders FileUtils.mkdir_p File.join(@module_path + "Tests" , "Resources") FileUtils.mkdir_p File.join(@module_path + "Tests" , "Sources") FileUtils.mkdir_p File.join(@module_path + "Tests" , "Tests") # Dummies FileUtils.touch File.join(@module_path + "Tests", "Sources", "DummyModel.swift") FileUtils.touch File.join(@module_path + "Tests", "Tests", "DummyTest.swift") # Info.plist FileUtils.cp( File.join(@configurator.template_path, "Feature", "Info_template"), File.join(@module_path + "Tests", "Resources", "Info.plist") ) @configurator.printDone end end end