def test_valid_all_functions_called(self, mock_parsing_handler, mock_api_handler, mock_progress): """ Makes sure that all functions are called when a valid directory in given :return: """ my_directory = path.join(path_to_module, "fake_ngs_data") class StubValidationResult: @staticmethod def is_valid(): return True class StubDirectoryStatus: directory = my_directory status = DirectoryStatus.NEW @staticmethod def status_equals(status): return status == DirectoryStatus.NEW # add mock data to the function calls that are essential stub_directory_status = StubDirectoryStatus() mock_parsing_handler.get_run_status.side_effect = [ stub_directory_status ] mock_parsing_handler.parse_and_validate.side_effect = [ "Fake Sequencing Run" ] mock_api_handler.initialize_api_from_config.side_effect = [None] mock_api_handler.prepare_and_validate_for_upload.side_effect = [ StubValidationResult ] mock_api_handler.upload_sequencing_run.side_effect = [None] mock_api_handler.get_default_upload_mode.side_effect = [MODE_DEFAULT] mock_api_handler.get_upload_modes.side_effect = [UPLOAD_MODES] mock_progress.write_directory_status.side_effect = [None, None] cli_entry.upload_run_single_entry(my_directory, force_upload=False) # Make sure directory status is init mock_progress.write_directory_status.assert_called_with( stub_directory_status, None) # Make sure parsing and validation is done mock_parsing_handler.parse_and_validate.assert_called_with( my_directory) # api must be initialized mock_api_handler.initialize_api_from_config.assert_called_with() # api must prep for upload mock_api_handler.prepare_and_validate_for_upload.assert_called_with( "Fake Sequencing Run") # api should check upload modes mock_api_handler.get_default_upload_mode.assert_called_with() mock_api_handler.get_upload_modes.assert_called_with() # api should try to upload mock_api_handler.upload_sequencing_run.assert_called_with( sequencing_run="Fake Sequencing Run", upload_mode=MODE_DEFAULT)
def test_invalid_at_api_sequencing_run(self, mock_parsing_handler, mock_api_handler, mock_progress): """ Makes sure that all functions are called when a invalid directory in given Invalidity comes from api module, When parsing, it should be valid :return: """ directory = path.join(path_to_module, "fake_ngs_data") class StubValidationResult: @staticmethod def is_valid(): return False @staticmethod def error_count(): return 0 @property def error_list(self): return [] class StubDirectoryStatus: directory = path.join(path_to_module, "fake_ngs_data") status = DirectoryStatus.NEW @staticmethod def status_equals(status): return status == DirectoryStatus.NEW # add mock data to the function calls that are essential stub_directory_status = StubDirectoryStatus() mock_parsing_handler.get_run_status.side_effect = [ stub_directory_status ] mock_parsing_handler.parse_and_validate.side_effect = [ "Fake Sequencing Run" ] mock_api_handler.initialize_api_from_config.side_effect = [None] mock_api_handler.prepare_and_validate_for_upload.side_effect = [ StubValidationResult ] mock_api_handler.upload_sequencing_run.side_effect = [None] mock_api_handler.get_default_upload_mode.side_effect = [MODE_DEFAULT] mock_api_handler.get_upload_modes.side_effect = [UPLOAD_MODES] cli_entry.upload_run_single_entry(directory) # Make sure the validation is tried mock_api_handler.prepare_and_validate_for_upload.assert_called_with( "Fake Sequencing Run") # make sure the upload is NOT done, as validation is invalid mock_api_handler.upload_sequencing_run.assert_not_called()
def test_valid_force_upload(self, mock_parsing_handler, mock_api_handler, mock_progress): """ Makes sure that all functions are called when a valid directory in given In this case, we are forcing an upload, so no run is new check should happen :return: """ directory = path.join(path_to_module, "fake_ngs_data") class StubValidationResult: @staticmethod def is_valid(): return True class StubDirectoryStatus: directory = path.join(path_to_module, "fake_ngs_data") status = DirectoryStatus.NEW # add mock data to the function calls that are essential mock_stub_directory_status = StubDirectoryStatus() mock_stub_directory_status.status_equals = MagicMock( return_value=False) mock_parsing_handler.get_run_status.side_effect = [ mock_stub_directory_status ] mock_parsing_handler.parse_and_validate.side_effect = [ "Fake Sequencing Run" ] # mock_parsing_handler.run_is_new.side_effect = [None] mock_api_handler.initialize_api_from_config.side_effect = [None] mock_api_handler.prepare_and_validate_for_upload.side_effect = [ StubValidationResult ] mock_api_handler.upload_sequencing_run.side_effect = [None] mock_api_handler.get_default_upload_mode.side_effect = [MODE_DEFAULT] mock_api_handler.get_upload_modes.side_effect = [UPLOAD_MODES] cli_entry.upload_run_single_entry(directory, True) # Check that run status was found mock_parsing_handler.get_run_status.assert_called_with(directory) # Make sure run is new check is not done (Only invalid check is done) mock_stub_directory_status.status_equals.assert_called_once_with( DirectoryStatus.INVALID) # Make sure parsing and validation is done mock_parsing_handler.parse_and_validate.assert_called_with(directory) # api must be initialized mock_api_handler.initialize_api_from_config.assert_called_with() # api must prep for upload mock_api_handler.prepare_and_validate_for_upload.assert_called_with( "Fake Sequencing Run") # api should try to upload mock_api_handler.upload_sequencing_run.assert_called_with( sequencing_run="Fake Sequencing Run", upload_mode=MODE_DEFAULT)
def test_valid_new_status_file_upload(self, mock_parsing_handler, mock_api_handler, mock_progress): """ Makes sure that all functions are called when a valid directory in given In this case, the run is new check should happen :return: """ directory = path.join(path_to_module, "fake_ngs_data") class StubValidationResult: @staticmethod def is_valid(): return True class StubDirectoryStatus: directory = path.join(path_to_module, "fake_ngs_data") status = DirectoryStatus.NEW # add mock data to the function calls that are essential mock_stub_directory_status = StubDirectoryStatus() mock_stub_directory_status.status_equals = Mock() mock_stub_directory_status.status_equals.side_effect = [False, True] mock_parsing_handler.get_run_status.side_effect = [ mock_stub_directory_status ] mock_parsing_handler.parse_and_validate.side_effect = [ "Fake Sequencing Run" ] mock_api_handler.initialize_api_from_config.side_effect = [None] mock_api_handler.prepare_and_validate_for_upload.side_effect = [ StubValidationResult ] mock_api_handler.upload_sequencing_run.side_effect = [None] cli_entry.upload_run_single_entry(directory, False) # Check that run status was found mock_parsing_handler.get_run_status.assert_called_with(directory) # Make sure run is new check is done mock_stub_directory_status.status_equals.assert_called_with( DirectoryStatus.NEW) # Make sure parsing and validation is done mock_parsing_handler.parse_and_validate.assert_called_with(directory) # api must be initialized mock_api_handler.initialize_api_from_config.assert_called_with() # api must prep for upload mock_api_handler.prepare_and_validate_for_upload.assert_called_with( "Fake Sequencing Run") # api should try to upload mock_api_handler.upload_sequencing_run.assert_called_with( "Fake Sequencing Run")
def test_valid_already_uploaded(self, mock_parsing_handler, mock_api_handler, mock_progress): """ Makes sure that all functions are called when a valid directory in given In this case, the run is new check should occur, and the run should not be uploaded, and not be parsed :return: """ directory = path.join(path_to_module, "fake_ngs_data") class StubValidationResult: @staticmethod def is_valid(): return True # add mock data to the function calls that are essential class StubDirectoryStatus: directory = path.join(path_to_module, "fake_ngs_data") status = DirectoryStatus.COMPLETE # add mock data to the function calls that are essential mock_stub_directory_status = StubDirectoryStatus() mock_stub_directory_status.status_equals = Mock() mock_stub_directory_status.status_equals.side_effect = [False, False] mock_parsing_handler.get_run_status.side_effect = [ mock_stub_directory_status ] mock_parsing_handler.parse_and_validate.side_effect = [ "Fake Sequencing Run" ] mock_api_handler.initialize_api_from_config.side_effect = [None] mock_api_handler.prepare_and_validate_for_upload.side_effect = [ StubValidationResult ] mock_api_handler.upload_sequencing_run.side_effect = [None] mock_api_handler.get_default_upload_mode.side_effect = [MODE_DEFAULT] mock_api_handler.get_upload_modes.side_effect = [UPLOAD_MODES] cli_entry.upload_run_single_entry(directory, False) # Check that run status was found mock_parsing_handler.get_run_status.assert_called_with(directory) # Make sure run is new check is not done mock_stub_directory_status.status_equals.assert_called_with( DirectoryStatus.NEW) # Make sure parsing and validation is NOT done mock_parsing_handler.parse_and_validate.assert_not_called() # make sure the upload is NOT done, as validation is invalid mock_api_handler.upload_sequencing_run.assert_not_called()
def test_valid_miseq_with_status_file_already_uploaded(self): """ Test a valid miseq directory for upload from end to end We create a status file that indicates the files have already been uploaded, Then make sure it does not upload :return: """ # Set our sample config file to use miseq parser and the correct irida credentials self.write_to_config_file( client_id=tests_integration.client_id, client_secret=tests_integration.client_secret, username=tests_integration.username, password=tests_integration.password, base_url=tests_integration.base_url, parser="miseq") # Write a status file to the upload directory directory_status = model.DirectoryStatus( directory=path.join(path_to_module, "fake_ngs_data")) directory_status.status = model.DirectoryStatus.COMPLETE progress.write_directory_status(directory_status) # Do the upload, without force option upload_result = upload_run_single_entry( path.join(path_to_module, "fake_ngs_data"), False) # Make sure the upload was a failure self.assertEqual(upload_result.exit_code, 1)
def test_valid_resourse_error_during_upload(self, mock_parsing_handler, mock_api_handler, mock_progress): """ Makes sure no crash occurs and program exits with error when IridaResourceError occurs during upload :return: """ my_directory = path.join(path_to_module, "fake_ngs_data") class StubValidationResult: @staticmethod def is_valid(): return True class StubDirectoryStatus: directory = my_directory status = DirectoryStatus.NEW @staticmethod def status_equals(status): return status == DirectoryStatus.NEW # add mock data to the function calls that are essential stub_directory_status = StubDirectoryStatus() mock_parsing_handler.get_run_status.side_effect = [ stub_directory_status ] mock_parsing_handler.parse_and_validate.side_effect = [ "Fake Sequencing Run" ] mock_api_handler.initialize_api_from_config.side_effect = [None] mock_api_handler.prepare_and_validate_for_upload.side_effect = [ StubValidationResult ] mock_api_handler.upload_sequencing_run.side_effect = [None] mock_api_handler.upload_sequencing_run.side_effect = [ IridaResourceError("") ] mock_progress.write_directory_status.side_effect = [None, None] result = cli_entry.upload_run_single_entry(my_directory, force_upload=False) # Check that the run failed to upload self.assertEqual(result.exit_code, exit_return.EXIT_CODE_ERROR) # Make sure directory status is init mock_progress.write_directory_status.assert_called_with( stub_directory_status) # Make sure parsing and validation is done mock_parsing_handler.parse_and_validate.assert_called_with( my_directory) # api must be initialized mock_api_handler.initialize_api_from_config.assert_called_with() # api must prep for upload mock_api_handler.prepare_and_validate_for_upload.assert_called_with( "Fake Sequencing Run") # api should try to upload mock_api_handler.upload_sequencing_run.assert_called_with( "Fake Sequencing Run")
def run(self): """ This runs when the threads start call is done :return: """ self._exit_return = cli_entry.upload_run_single_entry( self._run_dir, self._force_state, self._upload_mode) pass
def test_invalid_at_parsing_sequencing_run(self, mock_parsing_handler, mock_api_handler, mock_progress): """ Makes sure that all functions are called when a invalid directory in given Invalidity comes from parsing module :return: """ directory = path.join(path_to_module, "fake_ngs_data") class StubDirectoryStatus: directory = path.join(path_to_module, "fake_ngs_data") status = DirectoryStatus.NEW @staticmethod def status_equals(status): return status == DirectoryStatus.NEW # add mock data to the function calls that are essential mock_parsing_handler.get_run_status.side_effect = [StubDirectoryStatus] mock_parsing_handler.parse_and_validate.side_effect = [ DirectoryError("", "") ] mock_api_handler.initialize_api_from_config.side_effect = [None] mock_api_handler.prepare_and_validate_for_upload.side_effect = [None] mock_api_handler.upload_sequencing_run.side_effect = [None] mock_api_handler.get_default_upload_mode.side_effect = [MODE_DEFAULT] mock_api_handler.get_upload_modes.side_effect = [UPLOAD_MODES] cli_entry.upload_run_single_entry(directory) # Check that run status was found mock_parsing_handler.get_run_status.assert_called_with(directory) # Make sure the error throwing function is called mock_parsing_handler.parse_and_validate.assert_called_with(directory) # Make sure the later functions are not called mock_api_handler.initialize_api_from_config.assert_not_called() mock_api_handler.prepare_and_validate_for_upload.assert_not_called() mock_api_handler.upload_sequencing_run.assert_not_called()
def test_invalid_before_parsing_sequencing_run(self, mock_parsing_handler, mock_api_handler, mock_progress): """ Makes sure that all functions are called when a invalid directory in given Invalidity comes from checking if the run is valid, but before parsing :return: """ class StubDirectoryStatus: directory = path.join(path_to_module, "fake_ngs_data") status = DirectoryStatus.INVALID message = "" @staticmethod def status_equals(status): return status == DirectoryStatus.INVALID # add mock data to the function calls that are essential mock_parsing_handler.get_run_status.side_effect = [StubDirectoryStatus] mock_parsing_handler.parse_and_validate.side_effect = [ "Fake Sequencing Run" ] mock_api_handler.initialize_api_from_config.side_effect = [None] mock_api_handler.prepare_and_validate_for_upload.side_effect = [None] mock_api_handler.upload_sequencing_run.side_effect = [None] directory = path.join(path_to_module, "fake_ngs_data") cli_entry.upload_run_single_entry(directory) # Check that run status was found mock_parsing_handler.get_run_status.assert_called_with(directory) # Make sure the later functions are not called mock_parsing_handler.parse_and_validate.assert_not_called() mock_api_handler.initialize_api_from_config.assert_not_called() mock_api_handler.prepare_and_validate_for_upload.assert_not_called() mock_api_handler.upload_sequencing_run.assert_not_called()
def test_valid_assemblies_directory_upload(self): """ Test a valid directory of assemblies for upload end to end :return: """ # Set our sample config file to use miseq parser and the correct irida credentials self.write_to_config_file( client_id=tests_integration.client_id, client_secret=tests_integration.client_secret, username=tests_integration.username, password=tests_integration.password, base_url=tests_integration.base_url, parser="directory") # instance an api test_api = api.ApiCalls(client_id=tests_integration.client_id, client_secret=tests_integration.client_secret, base_url=tests_integration.base_url, username=tests_integration.username, password=tests_integration.password) # Create a test project, the uploader does not make new projects on its own # so one must exist to upload samples into # This may not be the project that the files get uploaded to, # but one will be made in the case this is the only test being run project_name = "test_project_assemblies" project_description = "test_project_description_assemblies" project = model.Project(name=project_name, description=project_description) test_api.send_project(project) # We always upload to project "1" so that tests will be consistent no matter how many / which tests are run project_id = "1" # Do the upload upload_result = upload_run_single_entry(directory=path.join( path_to_module, "fake_assemblies_data"), upload_assemblies=True) # Make sure the upload was a success self.assertEqual(upload_result.exit_code, 0) # Verify the files were uploaded sample_list = test_api.get_samples(project_id) test_sample = sample_list[0] sequence_files = test_api.get_assemblies_files(project_id, test_sample.sample_name) self.assertEqual(len(sequence_files), 1) self.assertEqual(sequence_files[0]['fileName'], 'file_1.fasta')
def test_upload_to_nonexistent_project(self): """ Everything is correct except the sample sheet file specifies an invalid project Samples should not be uploaded :return: """ # try to upload to a non existent project # Set our sample config file to use miseq parser and the correct irida credentials self.write_to_config_file( client_id=tests_integration.client_id, client_secret=tests_integration.client_secret, username=tests_integration.username, password=tests_integration.password, base_url=tests_integration.base_url, parser="miseq", readonly=False) # instance an api test_api = api.ApiCalls(client_id=tests_integration.client_id, client_secret=tests_integration.client_secret, base_url=tests_integration.base_url, username=tests_integration.username, password=tests_integration.password) # Create a test project, the uploader does not make new projects on its own # so one must exist to upload samples into # This may not be the project that the files get uploaded to, # but one will be made in the case this is the only test being run project_name = "test_project" project_description = "test_project_description" project = model.Project(name=project_name, description=project_description) test_api.send_project(project) # Do the upload upload_result = upload_run_single_entry( path.join(path_to_module, "fake_ngs_data_nonexistent_project")) # Make sure the upload was a failure self.assertEqual(upload_result.exit_code, 1) # Verify that the project does not exist project_id = "1000" with self.assertRaises(api.exceptions.IridaKeyError): test_api.get_samples(project_id)
def test_invalid_read_only_miseq_upload(self): """ Test failing to upload a readonly miseq directory because readonly is turned off :return: """ # Set our sample config file to use miseq parser and the correct irida credentials self.write_to_config_file( client_id=tests_integration.client_id, client_secret=tests_integration.client_secret, username=tests_integration.username, password=tests_integration.password, base_url=tests_integration.base_url, parser="miseq", readonly=False) # instance an api test_api = api.ApiCalls(client_id=tests_integration.client_id, client_secret=tests_integration.client_secret, base_url=tests_integration.base_url, username=tests_integration.username, password=tests_integration.password) # Create a test project, the uploader does not make new projects on its own # so one must exist to upload samples into # This may not be the project that the files get uploaded to, # but one will be made in the case this is the only test being run project_name = "test_read_only_project_fail" project_description = "test_project_description" project = model.Project(name=project_name, description=project_description) test_api.send_project(project) # try the upload upload_result = upload_run_single_entry(path.join( path_to_module, "fake_ngs_data_read_only"), force_upload=False, upload_mode=api.MODE_DEFAULT) # Make sure the upload was a failure self.assertEqual(upload_result.exit_code, 1)
def test_upload_parse_fail(self): """ Given an invalid sample sheet, make sure that the upload does not happen :return: """ # try to upload to a non existent project # Set our sample config file to use miseq parser and the correct irida credentials self.write_to_config_file( client_id=tests_integration.client_id, client_secret=tests_integration.client_secret, username=tests_integration.username, password=tests_integration.password, base_url=tests_integration.base_url, parser="miseq") # instance an api test_api = api.ApiCalls(client_id=tests_integration.client_id, client_secret=tests_integration.client_secret, base_url=tests_integration.base_url, username=tests_integration.username, password=tests_integration.password) # Create a test project, the uploader does not make new projects on its own # so one must exist to upload samples into # This may not be the project that the files get uploaded to, # but one will be made in the case this is the only test being run project_name = "test_project" project_description = "test_project_description" project = model.Project(name=project_name, description=project_description) test_api.send_project(project) # Do the upload upload_result = upload_run_single_entry( path.join(path_to_module, "fake_ngs_data_parse_fail")) # Make sure the upload was a failure self.assertEqual(upload_result.exit_code, 1)
def test_valid_miseq_upload(self): """ Test a valid miseq directory for upload from end to end :return: """ # Set our sample config file to use miseq parser and the correct irida credentials self.write_to_config_file( client_id=tests_integration.client_id, client_secret=tests_integration.client_secret, username=tests_integration.username, password=tests_integration.password, base_url=tests_integration.base_url, parser="miseq") # instance an api test_api = api.ApiCalls(client_id=tests_integration.client_id, client_secret=tests_integration.client_secret, base_url=tests_integration.base_url, username=tests_integration.username, password=tests_integration.password) # Create a test project, the uploader does not make new projects on its own # so one must exist to upload samples into # This may not be the project that the files get uploaded to, # but one will be made in the case this is the only test being run project_name = "test_project" project_description = "test_project_description" project = model.Project(name=project_name, description=project_description) test_api.send_project(project) # We always upload to project "1" so that tests will be consistent no matter how many / which tests are run project_id = "1" # Do the upload upload_result = upload_run_single_entry( path.join(path_to_module, "fake_ngs_data")) # Make sure the upload was a success self.assertEqual(upload_result.exit_code, 0) # Verify the files were uploaded sample_list = test_api.get_samples(project_id) sample_1_found = False sample_2_found = False sample_3_found = False for sample in sample_list: if sample.sample_name in ["01-1111", "02-2222", "03-3333"]: if sample.sample_name == "01-1111": sample_1_found = True sequence_files = test_api.get_sequence_files( project_id, sample.sample_name) self.assertEqual(len(sequence_files), 2) res_sequence_file_names = [ sequence_files[0]['fileName'], sequence_files[1]['fileName'] ] expected_sequence_file_names = [ '01-1111_S1_L001_R1_001.fastq.gz', '01-1111_S1_L001_R2_001.fastq.gz' ] self.assertEqual(res_sequence_file_names.sort(), expected_sequence_file_names.sort()) elif sample.sample_name == "02-2222": sample_2_found = True sequence_files = test_api.get_sequence_files( project_id, sample.sample_name) self.assertEqual(len(sequence_files), 2) res_sequence_file_names = [ sequence_files[0]['fileName'], sequence_files[1]['fileName'] ] expected_sequence_file_names = [ '02-2222_S1_L001_R1_001.fastq.gz', '02-2222_S1_L001_R2_001.fastq.gz' ] self.assertEqual(res_sequence_file_names.sort(), expected_sequence_file_names.sort()) elif sample.sample_name == "03-3333": sample_3_found = True sequence_files = test_api.get_sequence_files( project_id, sample.sample_name) self.assertEqual(len(sequence_files), 2) res_sequence_file_names = [ sequence_files[0]['fileName'], sequence_files[1]['fileName'] ] expected_sequence_file_names = [ '03-3333_S1_L001_R1_001.fastq.gz', '03-3333_S1_L001_R2_001.fastq.gz' ] self.assertEqual(res_sequence_file_names.sort(), expected_sequence_file_names.sort()) self.assertEqual(sample_1_found, True) self.assertEqual(sample_2_found, True) self.assertEqual(sample_3_found, True)
def test_valid_directory_upload(self): """ Test a valid directory for upload end to end :return: """ # Set our sample config file to use miseq parser and the correct irida credentials self.write_to_config_file( client_id=tests_integration.client_id, client_secret=tests_integration.client_secret, username=tests_integration.username, password=tests_integration.password, base_url=tests_integration.base_url, parser="directory", readonly=False) # instance an api test_api = api.ApiCalls(client_id=tests_integration.client_id, client_secret=tests_integration.client_secret, base_url=tests_integration.base_url, username=tests_integration.username, password=tests_integration.password) # Create a test project, the uploader does not make new projects on its own # so one must exist to upload samples into # This may not be the project that the files get uploaded to, # but one will be made in the case this is the only test being run project_name = "test_project_2" project_description = "test_project_description_2" project = model.Project(name=project_name, description=project_description) test_api.send_project(project) # We always upload to project "1" so that tests will be consistent no matter how many / which tests are run project_id = "1" # Do the upload upload_result = upload_run_single_entry( path.join(path_to_module, "fake_dir_data")) # Make sure the upload was a success self.assertEqual(upload_result.exit_code, 0) # Verify the files were uploaded sample_list = test_api.get_samples(project_id) sample_1_found = False sample_2_found = False sample_3_found = False for sample in sample_list: if sample.sample_name in [ "my-sample-1", "my-sample-2", "my-sample-3" ]: if sample.sample_name == "my-sample-1": sample_1_found = True sequence_files = test_api.get_sequence_files( project_id, sample.sample_name) self.assertEqual(len(sequence_files), 2) self.assertEqual(sequence_files[0]['fileName'], 'file_1.fastq.gz') self.assertEqual(sequence_files[1]['fileName'], 'file_2.fastq.gz') elif sample.sample_name == "my-sample-2": sample_2_found = True sequence_files = test_api.get_sequence_files( project_id, sample.sample_name) self.assertEqual(len(sequence_files), 2) self.assertEqual(sequence_files[0]['fileName'], 'samp_F.fastq.gz') self.assertEqual(sequence_files[1]['fileName'], 'samp_R.fastq.gz') elif sample.sample_name == "my-sample-3": sample_3_found = True sequence_files = test_api.get_sequence_files( project_id, sample.sample_name) self.assertEqual(len(sequence_files), 2) self.assertEqual(sequence_files[0]['fileName'], 'germ_f.fastq.gz') self.assertEqual(sequence_files[1]['fileName'], 'germ_r.fastq.gz') self.assertEqual(sample_1_found, True) self.assertEqual(sample_2_found, True) self.assertEqual(sample_3_found, True)