diff --git a/osf/management/commands/migrate_funder_ids_to_ror.py b/osf/management/commands/migrate_funder_ids_to_ror.py index 7d4d46563af..6680fa367cf 100644 --- a/osf/management/commands/migrate_funder_ids_to_ror.py +++ b/osf/management/commands/migrate_funder_ids_to_ror.py @@ -97,7 +97,7 @@ def handle(self, *args, **options): self.stdout.write(f" Records updated: {stats['updated']}") self.stdout.write(f" Records re-indexed: {stats['reindexed']}") self.stdout.write(f" Funders migrated: {stats['funders_migrated']}") - self.stdout.write(f" Funders not in mapping: {stats['not_in_mapping']}") + self.stdout.write(f" Unmapped funders removed: {stats['not_in_mapping']}") if stats['errors']: self.stdout.write(self.style.ERROR(f" Errors: {stats['errors']}")) @@ -307,14 +307,15 @@ def migrate_record(self, record, mapping, dry_run, update_funder_name): f'{funder_identifier} -> {ror_info["ror_id"]}' ) else: - # No mapping found, keep original - updated_funding_info.append(funder) + # No mapping found, remove unmapped Crossref funder + record_modified = True funder_stats['not_found'] += 1 funder_stats['unmapped_ids'].add(funder_identifier) logger.warning( - f'No ROR mapping found for Crossref Funder ID: {funder_identifier} ' - f'in record {record.guid._id}' + f'{"[DRY RUN] " if dry_run else ""}' + f'Removing unmapped Crossref Funder ID: {funder_identifier} ' + f'from record {record.guid._id}' ) # Warn about duplicate ROR IDs that would result from migration diff --git a/osf_tests/management_commands/test_migrate_funder_ids_to_ror.py b/osf_tests/management_commands/test_migrate_funder_ids_to_ror.py index e003f6ffc64..a7bec602e5f 100644 --- a/osf_tests/management_commands/test_migrate_funder_ids_to_ror.py +++ b/osf_tests/management_commands/test_migrate_funder_ids_to_ror.py @@ -201,8 +201,8 @@ def test_migrate_multiple_funders(self, record_with_multiple_funders, csv_mappin assert funders[2]['funder_identifier'] == 'https://ror.org/021nxhr62' assert funders[2]['funder_identifier_type'] == 'ROR' - def test_unmapped_funder_preserved(self, record_with_unmapped_funder, csv_mapping_file): - """Test that funders not in mapping are preserved unchanged.""" + def test_unmapped_funder_removed(self, record_with_unmapped_funder, csv_mapping_file): + """Test that funders not in mapping are removed.""" command = Command() command.stdout = type('MockStdout', (), {'write': lambda self, x: None})() @@ -214,17 +214,13 @@ def test_unmapped_funder_preserved(self, record_with_unmapped_funder, csv_mappin update_funder_name=False ) - assert updated is False + assert updated is True assert stats['migrated'] == 0 assert stats['not_found'] == 1 assert 'http://dx.doi.org/10.13039/999999999' in stats['unmapped_ids'] record_with_unmapped_funder.refresh_from_db() - funder = record_with_unmapped_funder.funding_info[0] - - # Should be unchanged - assert funder['funder_identifier'] == 'http://dx.doi.org/10.13039/999999999' - assert funder['funder_identifier_type'] == 'Crossref Funder ID' + assert record_with_unmapped_funder.funding_info == [] def test_load_mapping_various_id_formats(self, csv_mapping_file): """Test that mapping handles various ID formats.""" @@ -347,8 +343,8 @@ def test_reindex_not_triggered_with_skip_flag(self, record_with_crossref_funder, assert funder['funder_identifier'] == 'https://ror.org/01cwqze88' assert funder['funder_identifier_type'] == 'ROR' - def test_reindex_not_triggered_for_unmapped_records(self, record_with_unmapped_funder, csv_mapping_file, mock_reindex): - """Test that re-indexing is NOT triggered for records that weren't updated.""" + def test_reindex_triggered_for_unmapped_records(self, record_with_unmapped_funder, csv_mapping_file, mock_reindex): + """Test that re-indexing IS triggered when unmapped funders are removed.""" mock_update_search, mock_request_identifier_update = mock_reindex call_command( @@ -356,8 +352,8 @@ def test_reindex_not_triggered_for_unmapped_records(self, record_with_unmapped_f '--csv-file', csv_mapping_file, ) - mock_update_search.assert_not_called() - mock_request_identifier_update.assert_not_called() + mock_update_search.assert_called() + mock_request_identifier_update.assert_called_with('doi') def test_end_to_end_call_command(self, record_with_crossref_funder, record_with_multiple_funders, csv_mapping_file, mock_reindex): """Test the full management command end-to-end via call_command."""