feat(#357): Paket 6 — Contact-Model ins ContactsPlugin (physischer Move + PEP-562-Lazy-Re-Export-Bruecke, ALEMBIC_OWNED_TABLES gegen Schema-Dual-Ownership, outbox-Vorbestands-Fix in models/__init__)
Check Cross-Plugin Imports / check (push) Has been cancelled
Check Cross-Plugin Imports / check (push) Has been cancelled
This commit is contained in:
@@ -0,0 +1,93 @@
|
||||
"""Contact model ownership tests - Paket 6 (#357).
|
||||
|
||||
Beweist: Contact/ContactPerson leben physisch im ContactsPlugin (models.py),
|
||||
app/models/contact.py ist nur noch eine Re-Export-Bruecke (Kompatibilitaet fuer
|
||||
Alembic env.py, Core-Services, Tests) und die contacts/contactpersons-Tabellen
|
||||
bleiben Alembic-owned (kein Plugin-Schema-Sync-Dual-Ownership).
|
||||
"""
|
||||
|
||||
from __future__ import annotations
|
||||
|
||||
|
||||
class TestContactModelOwnership:
|
||||
"""Contact/ContactPerson sind physisch im ContactsPlugin beheimatet."""
|
||||
|
||||
def test_contact_class_owned_by_contacts_plugin(self):
|
||||
"""Contact.__module__ zeigt auf das Plugin, nicht auf app.models."""
|
||||
from app.models.contact import Contact
|
||||
|
||||
assert Contact.__module__ == "app.plugins.builtins.contacts.models"
|
||||
|
||||
def test_contact_person_class_owned_by_contacts_plugin(self):
|
||||
"""ContactPerson.__module__ zeigt auf das Plugin."""
|
||||
from app.models.contact import ContactPerson
|
||||
|
||||
assert ContactPerson.__module__ == "app.plugins.builtins.contacts.models"
|
||||
|
||||
def test_plugin_models_module_importable_directly(self):
|
||||
"""Das Plugin-Modul ist direkt importierbar (Vorbild: mail.models)."""
|
||||
from app.plugins.builtins.contacts.models import Contact, ContactPerson
|
||||
|
||||
assert Contact.__tablename__ == "contacts"
|
||||
assert ContactPerson.__tablename__ == "contactpersons"
|
||||
|
||||
def test_shim_identity_same_class_objects(self):
|
||||
"""Shim-Import und Plugin-Import liefern dieselbe Klasse (kein Duplikat)."""
|
||||
from app.models.contact import Contact as ViaShim
|
||||
from app.plugins.builtins.contacts.models import Contact as ViaPlugin
|
||||
|
||||
assert ViaShim is ViaPlugin
|
||||
|
||||
|
||||
class TestAlembicMetadataIntegrity:
|
||||
"""Base.metadata bleibt nach dem Move vollstaendig (Alembic-Sicherheit)."""
|
||||
|
||||
def test_contacts_table_in_base_metadata(self):
|
||||
"""contacts/contactpersons sind in Base.metadata registriert.
|
||||
|
||||
env.py laedt from app.models import * - ohne funktionierenden Re-Export
|
||||
wuerde Alembic-Autogenerate die Tabellen als entfernt betrachten (DROP).
|
||||
"""
|
||||
from app.core.db import Base
|
||||
|
||||
assert "contacts" in Base.metadata.tables
|
||||
assert "contactpersons" in Base.metadata.tables
|
||||
|
||||
def test_models_package_export_unchanged(self):
|
||||
"""from app.models import Contact funktioniert weiter (env.py-Signal)."""
|
||||
import app.models
|
||||
|
||||
assert app.models.Contact is not None
|
||||
assert app.models.ContactPerson is not None
|
||||
|
||||
|
||||
class TestSyncPluginSchemaExclude:
|
||||
"""contacts/contactpersons bleiben Alembic-owned, kein Plugin-Sync."""
|
||||
|
||||
def test_alembic_owned_tables_constant_declares_contacts(self):
|
||||
"""sync_plugin_schema deklariert contacts/contactpersons als Alembic-owned.
|
||||
|
||||
Der __module__-Filter des Scripts wuerde nach dem Move sonst die
|
||||
Alembic-verwalteten Tabellen in den Plugin-Schema-Sync-Kanal ziehen
|
||||
(Dual-Ownership -> Schema-Drift gegen 142 Migrationen).
|
||||
"""
|
||||
from scripts.sync_plugin_schema import ALEMBIC_OWNED_TABLES
|
||||
|
||||
assert "contacts" in ALEMBIC_OWNED_TABLES
|
||||
assert "contactpersons" in ALEMBIC_OWNED_TABLES
|
||||
|
||||
|
||||
class TestCoreImportCompatibility:
|
||||
"""Bestehende Core-Import-Stellen funktionieren ueber den Shim weiter."""
|
||||
|
||||
def test_core_worker_imports_contact(self):
|
||||
"""app.core.worker (dokumentierter P16-Fall) importiert Contact weiter."""
|
||||
from app.models.contact import Contact # noqa: F401
|
||||
|
||||
def test_contact_merge_fk_resolves(self):
|
||||
"""FK-Kette contact_merge_history -> contacts loest sich weiter auf."""
|
||||
from app.core.db import Base
|
||||
|
||||
merge = Base.metadata.tables["contact_merge_history"]
|
||||
fk_targets = {fk.target_fullname for fk in merge.foreign_keys}
|
||||
assert "contacts.id" in fk_targets
|
||||
Reference in New Issue
Block a user