# Copyright (c) Meta Platforms, Inc. and affiliates. # # This source code is licensed under the MIT license found in the # LICENSE file in the root directory of this source tree. require "test/unit" require_relative "../codegen.rb" require_relative "./test_utils/PodMock.rb" require_relative "./test_utils/PathnameMock.rb" require_relative "./test_utils/FileMock.rb" require_relative "./test_utils/DirMock.rb" require_relative "./test_utils/systemUtils.rb" require_relative "./test_utils/CodegenUtilsMock.rb" class CodegenTests < Test::Unit::TestCase :third_party_provider_header :third_party_provider_implementation :base_path :prefix :tmp_schema_list_file def setup Pod::Config.reset() @prefix = "../.." @third_party_provider_header = "RCTThirdPartyFabricComponentsProvider.h" @third_party_provider_implementation = "RCTThirdPartyFabricComponentsProvider.mm" @base_path = "~/app/ios" @tmp_schema_list_file = "tmpSchemaList.txt" Pathname.pwd!(@base_path) Pod::Config.instance.installation_root.relative_path_from = @base_path end def teardown system_reset_commands() Pod::UI.reset() Pod::Executable.reset() Pathname.reset() FileMock.reset() DirMock.reset() end # ============================================== # # Test - setup_fabric # # ============================================== # def testCheckAndGenerateEmptyThirdPartyProvider_whenFileAlreadyExists_doNothing() # Arrange FileMock.mocked_existing_files([ @prefix + "/React/Fabric/" + @third_party_provider_header, @prefix + "/React/Fabric/" + @third_party_provider_implementation, ]) # Act checkAndGenerateEmptyThirdPartyProvider!(@prefix, false, dir_manager: DirMock, file_manager: FileMock) # Assert assert_equal(Pathname.pwd_invocation_count, 1) assert_equal(Pod::Config.instance.installation_root.relative_path_from_invocation_count, 1) assert_equal(FileMock.exist_invocation_params, [ @prefix + "/React/Fabric/" + @third_party_provider_header, @prefix + "/React/Fabric/" + @third_party_provider_implementation, ]) assert_equal(DirMock.exist_invocation_params, []) assert_equal(Pod::UI.collected_messages, []) assert_equal($collected_commands, []) assert_equal(FileMock.open_files.length, 0) assert_equal(Pod::Executable.executed_commands.length, 0) end def testCheckAndGenerateEmptyThirdPartyProvider_whenHeaderMissingAndCodegenMissing_raiseError() # Arrange FileMock.mocked_existing_files([ @base_path + "/build/" + @third_party_provider_implementation, ]) # Act assert_raise { checkAndGenerateEmptyThirdPartyProvider!(@prefix, false, dir_manager: DirMock, file_manager: FileMock) } # Assert assert_equal(Pathname.pwd_invocation_count, 1) assert_equal(Pod::Config.instance.installation_root.relative_path_from_invocation_count, 1) assert_equal(FileMock.exist_invocation_params, [ @prefix + "/React/Fabric/" + @third_party_provider_header ]) assert_equal(DirMock.exist_invocation_params, [ @base_path + "/"+ @prefix + "/../react-native-codegen", @base_path + "/"+ @prefix + "/../@react-native/codegen", ]) assert_equal(Pod::UI.collected_messages, []) assert_equal($collected_commands, []) assert_equal(FileMock.open_files.length, 0) assert_equal(Pod::Executable.executed_commands.length, 0) end def testCheckAndGenerateEmptyThirdPartyProvider_whenImplementationMissingAndCodegenrepoExists_dontBuildCodegen() # Arrange FileMock.mocked_existing_files([ @prefix + "/React/Fabric/" + @third_party_provider_header, @prefix + "/React/Fabric/tmpSchemaList.txt" ]) DirMock.mocked_existing_dirs([ @base_path + "/"+ @prefix + "/../react-native-codegen", @base_path + "/"+ @prefix + "/../react-native-codegen/lib" ]) # Act checkAndGenerateEmptyThirdPartyProvider!(@prefix, false, dir_manager: DirMock, file_manager: FileMock) # Assert assert_equal(Pathname.pwd_invocation_count, 1) assert_equal(Pod::Config.instance.installation_root.relative_path_from_invocation_count, 1) assert_equal(FileMock.exist_invocation_params, [ @prefix + "/React/Fabric/" + @third_party_provider_header, @prefix + "/React/Fabric/" + @third_party_provider_implementation, @prefix + "/React/Fabric/tmpSchemaList.txt", ]) assert_equal(DirMock.exist_invocation_params, [ @base_path + "/"+ @prefix + "/../react-native-codegen", @base_path + "/"+ @prefix + "/../react-native-codegen/lib", ]) assert_equal(Pod::UI.collected_messages, ["[Codegen] generating an empty RCTThirdPartyFabricComponentsProvider"]) assert_equal($collected_commands, []) assert_equal(FileMock.open_invocation_count, 1) assert_equal(FileMock.open_files_with_mode[@prefix + "/React/Fabric/tmpSchemaList.txt"], 'w') assert_equal(FileMock.open_files[0].collected_write, ["[]"]) assert_equal(FileMock.open_files[0].fsync_invocation_count, 1) assert_equal(Pod::Executable.executed_commands[0], { "command" => "node", "arguments" => [ @base_path + "/" + @prefix + "/scripts/generate-provider-cli.js", "--platform", 'ios', "--schemaListPath", @prefix + "/React/Fabric/tmpSchemaList.txt", "--outputDir", @prefix + "/React/Fabric" ] }) assert_equal(FileMock.delete_invocation_count, 1) assert_equal(FileMock.deleted_files, [ @prefix + "/React/Fabric/tmpSchemaList.txt"]) end def testCheckAndGenerateEmptyThirdPartyProvider_whenBothMissing_buildCodegen() # Arrange codegen_cli_path = @base_path + "/" + @prefix + "/../@react-native/codegen" DirMock.mocked_existing_dirs([ codegen_cli_path, ]) # Act checkAndGenerateEmptyThirdPartyProvider!(@prefix, false, dir_manager: DirMock, file_manager: FileMock) # Assert assert_equal(Pathname.pwd_invocation_count, 1) assert_equal(Pod::Config.instance.installation_root.relative_path_from_invocation_count, 1) assert_equal(FileMock.exist_invocation_params, [ @prefix + "/React/Fabric/" + @third_party_provider_header, @prefix + "/React/Fabric/" + @tmp_schema_list_file ]) assert_equal(DirMock.exist_invocation_params, [ @base_path + "/" + @prefix + "/../react-native-codegen", codegen_cli_path, codegen_cli_path + "/lib", ]) assert_equal(Pod::UI.collected_messages, [ "[Codegen] building #{codegen_cli_path}.", "[Codegen] generating an empty RCTThirdPartyFabricComponentsProvider" ]) assert_equal($collected_commands, ["~/app/ios/../../../@react-native/codegen/scripts/oss/build.sh"]) assert_equal(FileMock.open_files[0].collected_write, ["[]"]) assert_equal(FileMock.open_files[0].fsync_invocation_count, 1) assert_equal(Pod::Executable.executed_commands[0], { "command" => "node", "arguments" => [ @base_path + "/" + @prefix + "/scripts/generate-provider-cli.js", "--platform", 'ios', "--schemaListPath", @prefix + "/React/Fabric/" + @tmp_schema_list_file, "--outputDir", @prefix + "/React/Fabric" ] }) end # ================= # # Test - RunCodegen # # ================= # def testRunCodegen_whenNewArchEnabled_runsCodegen # Arrange app_path = "~/app" config_file = "" codegen_utils_mock = CodegenUtilsMock.new() # Act run_codegen!(app_path, config_file, :new_arch_enabled => true, :codegen_utils => codegen_utils_mock) # Assert assert_equal(codegen_utils_mock.use_react_native_codegen_discovery_params, [{ :app_path=>"~/app", :codegen_disabled=>false, :codegen_output_dir=>"build/generated/ios", :config_file_dir=>"", :fabric_enabled=>false, :folly_version=>"2021.07.22.00", :react_native_path=>"../node_modules/react-native" }]) assert_equal(codegen_utils_mock.get_react_codegen_spec_params, []) assert_equal(codegen_utils_mock.generate_react_codegen_spec_params, []) end def testRunCodegen_whenNewArchDisabled_runsCodegen # Arrange app_path = "~/app" config_file = "" package_json_file = "~/app/package.json" codegen_specs = { "name" => "React-Codegen" } codegen_utils_mock = CodegenUtilsMock.new(:react_codegen_spec => codegen_specs) # Act run_codegen!( app_path, config_file, :new_arch_enabled => false, :fabric_enabled => true, :package_json_file => package_json_file, :codegen_utils => codegen_utils_mock) # Assert assert_equal(codegen_utils_mock.use_react_native_codegen_discovery_params, []) assert_equal(codegen_utils_mock.get_react_codegen_spec_params, [{ :fabric_enabled => true, :folly_version=>"2021.07.22.00", :package_json_file => "~/app/package.json", :script_phases => nil }]) assert_equal(codegen_utils_mock.generate_react_codegen_spec_params, [{ :codegen_output_dir=>"build/generated/ios", :react_codegen_spec=>{"name"=>"React-Codegen"} }]) end end