"""Tests for sync module.""" import json from i18n_key_sync.sync import SyncChange, Syncer, SyncResult class TestSyncChange: """Tests for SyncChange class.""" def test_sync_change_creation(self): """Test creating a SyncChange.""" change = SyncChange( locale="en", key="new_key", old_value=None, new_value="New Value", action="add", ) assert change.locale == "en" assert change.key == "new_key" assert change.old_value is None assert change.new_value == "New Value" assert change.action == "add" class TestSyncResult: """Tests for SyncResult class.""" def test_sync_result_total_changes(self): """Test SyncResult total_changes property.""" result = SyncResult( changes=[ SyncChange("en", "key1", None, "value1", "add"), SyncChange("es", "key2", None, "value2", "add"), ], locales_updated=["en", "es"], ) assert result.total_changes == 2 class TestSyncer: """Tests for Syncer class.""" def test_sync_keys_adds_missing(self, locale_parser, tmp_path): """Test syncing adds missing keys to locale files.""" locale_dir = tmp_path / "locales" locale_dir.mkdir() locale_file = locale_dir / "en.json" locale_file.write_text(json.dumps({"existing": "value"})) syncer = Syncer(locale_parser) keys = {"existing", "new_key1", "new_key2"} changes = syncer.sync_keys( keys=keys, locale_dir=str(locale_dir), placeholder_value="TODO", dry_run=False, ) assert len(changes) == 2 assert changes[0].action == "add" assert changes[0].key in ["new_key1", "new_key2"] data = json.loads(locale_file.read_text()) assert "new_key1" in data assert "new_key2" in data def test_sync_keys_dry_run(self, locale_parser, tmp_path): """Test dry run doesn't modify files.""" locale_dir = tmp_path / "locales" locale_dir.mkdir() locale_file = locale_dir / "en.json" locale_file.write_text(json.dumps({"existing": "value"})) syncer = Syncer(locale_parser) keys = {"existing", "new_key"} changes = syncer.sync_keys( keys=keys, locale_dir=str(locale_dir), placeholder_value="TODO", dry_run=True, ) assert len(changes) == 1 data = json.loads(locale_file.read_text()) assert "new_key" not in data assert data == {"existing": "value"} def test_sync_keys_specific_locales(self, locale_parser, tmp_path): """Test syncing only specific locales.""" locale_dir = tmp_path / "locales" locale_dir.mkdir() en_file = locale_dir / "en.json" en_file.write_text(json.dumps({})) es_file = locale_dir / "es.json" es_file.write_text(json.dumps({})) syncer = Syncer(locale_parser) keys = {"key1", "key2"} changes = syncer.sync_keys( keys=keys, locale_dir=str(locale_dir), target_locales=["en"], placeholder_value="TODO", dry_run=False, ) assert len(changes) == 2 en_data = json.loads(en_file.read_text()) assert "key1" in en_data assert "key2" in en_data es_data = json.loads(es_file.read_text()) assert "key1" not in es_data def test_sync_keys_fill_from_locale(self, locale_parser, tmp_path): """Test syncing with fill from source locale.""" locale_dir = tmp_path / "locales" locale_dir.mkdir() en_file = locale_dir / "en.json" en_file.write_text(json.dumps({"key1": "Hello", "key2": "World"})) es_file = locale_dir / "es.json" es_file.write_text(json.dumps({"key1": "Hola"})) syncer = Syncer(locale_parser) keys = {"key1", "key2", "key3"} changes = syncer.sync_keys( keys=keys, locale_dir=str(locale_dir), target_locales=["es"], placeholder_value="TODO", fill_from_locale="en", dry_run=False, ) assert len(changes) == 2 es_data = json.loads(es_file.read_text()) assert es_data["key1"] == "Hola" assert es_data["key2"] == "World" assert es_data["key3"] == "TODO" def test_sync_to_new_locale(self, locale_parser, tmp_path): """Test creating a new locale file.""" locale_dir = tmp_path / "locales" locale_dir.mkdir() en_file = locale_dir / "en.json" en_file.write_text(json.dumps({"key1": "Hello", "key2": "World"})) syncer = Syncer(locale_parser) keys = {"key1", "key2", "key3"} changes = syncer.sync_to_new_locale( keys=keys, locale_dir=str(locale_dir), new_locale="fr", source_locale="en", placeholder_value="TODO", dry_run=False, ) assert len(changes) == 3 fr_file = locale_dir / "fr.json" assert fr_file.exists() fr_data = json.loads(fr_file.read_text()) assert fr_data["key1"] == "Hello" assert fr_data["key2"] == "World" assert fr_data["key3"] == "TODO" def test_sync_to_new_locale_dry_run(self, locale_parser, tmp_path): """Test creating new locale with dry run.""" locale_dir = tmp_path / "locales" locale_dir.mkdir() en_file = locale_dir / "en.json" en_file.write_text(json.dumps({"key1": "Hello"})) syncer = Syncer(locale_parser) keys = {"key1", "key2"} changes = syncer.sync_to_new_locale( keys=keys, locale_dir=str(locale_dir), new_locale="fr", source_locale="en", placeholder_value="TODO", dry_run=True, ) assert len(changes) == 2 fr_file = locale_dir / "fr.json" assert not fr_file.exists() def test_sync_keys_nested(self, locale_parser, tmp_path): """Test syncing nested keys.""" locale_dir = tmp_path / "locales" locale_dir.mkdir() locale_file = locale_dir / "en.json" locale_file.write_text(json.dumps({})) syncer = Syncer(locale_parser) keys = {"user.profile.name", "user.profile.email", "common.save"} changes = syncer.sync_keys( keys=keys, locale_dir=str(locale_dir), placeholder_value="TODO", dry_run=False, ) assert len(changes) == 3 data = json.loads(locale_file.read_text()) assert data["user"]["profile"]["name"] == "TODO" assert data["user"]["profile"]["email"] == "TODO" assert data["common"]["save"] == "TODO"