Ejemplo n.º 1
0
    def setUpClass(cls):
        super(SharedAuthTest, cls).setUpClass()
        settings.SHARED_APPS = (
            'django_tenants',
            'django.contrib.auth',
            'django.contrib.contenttypes',
        )
        settings.TENANT_APPS = ('dts_test_app', )
        settings.INSTALLED_APPS = settings.SHARED_APPS + settings.TENANT_APPS
        cls.sync_shared()
        Tenant(domain_urls=['test.com'],
               schema_name=get_public_schema_name()).save()

        # Create a tenant
        cls.tenant = Tenant(domain_urls=['tenant.test.com'],
                            schema_name='tenant')
        cls.tenant.save()

        # Create some users
        with schema_context(get_public_schema_name(
        )):  # this could actually also be executed inside a tenant
            cls.user1 = User(username='******', email="*****@*****.**")
            cls.user1.save()
            cls.user2 = User(username='******', email="*****@*****.**")
            cls.user2.save()

        # Create instances on the tenant that point to the users on public
        with tenant_context(cls.tenant):
            cls.d1 = ModelWithFkToPublicUser(user=cls.user1)
            cls.d1.save()
            cls.d2 = ModelWithFkToPublicUser(user=cls.user2)
            cls.d2.save()
Ejemplo n.º 2
0
    def test_tenant_apps_and_shared_apps_can_have_the_same_apps(self):
        """
        Tests that both SHARED_APPS and TENANT_APPS can have apps in common.
        In this case they should get synced to both tenant and public schemas.
        """
        settings.SHARED_APPS = (
            'django_tenants',  # 2 tables
            'django.contrib.auth',  # 6 tables
            'django.contrib.contenttypes',  # 1 table
            'django.contrib.sessions',
        )  # 1 table
        settings.TENANT_APPS = ('django.contrib.sessions', )  # 1 table
        settings.INSTALLED_APPS = settings.SHARED_APPS + settings.TENANT_APPS
        self.sync_shared()
        tenant = Tenant(domain_urls=['arbitrary.test.com'], schema_name='test')
        tenant.save()

        shared_tables = self.get_tables_list_in_schema(
            get_public_schema_name())
        tenant_tables = self.get_tables_list_in_schema(tenant.schema_name)
        self.assertEqual(2 + 6 + 1 + 1 + self.MIGRATION_TABLE_SIZE,
                         len(shared_tables))
        self.assertIn('django_session', shared_tables)
        self.assertEqual(1 + self.MIGRATION_TABLE_SIZE, len(tenant_tables))
        self.assertIn('django_session', tenant_tables)
Ejemplo n.º 3
0
    def test_tenant_schema_is_created(self):
        """
        When saving a tenant, it's schema should be created.
        """
        tenant = Tenant(domain_urls=['something.test.com'], schema_name='test')
        tenant.save()

        self.assertTrue(schema_exists(tenant.schema_name))
Ejemplo n.º 4
0
    def test_tenant_schema_is_created(self):
        """
        When saving a tenant, it's schema should be created.
        """
        tenant = Tenant(domain_urls=['something.test.com'], schema_name='test')
        tenant.save()

        self.assertTrue(schema_exists(tenant.schema_name))
Ejemplo n.º 5
0
    def setUp(self):
        super(RoutesTestCase, self).setUp()
        self.factory = RequestFactory()
        self.tm = TenantMiddleware()

        self.tenant_domain = 'tenant.test.com'
        self.tenant = Tenant(domain_urls=[self.tenant_domain], schema_name='test')
        self.tenant.save()
Ejemplo n.º 6
0
    def test_switching_tenant_without_previous_tenant(self):
        tenant = Tenant(domain_urls=['something.test.com'], schema_name='test')
        tenant.save()

        connection.tenant = None
        with tenant_context(tenant):
            DummyModel(name="No exception please").save()

        connection.tenant = None
        with schema_context(tenant.schema_name):
            DummyModel(name="Survived it!").save()
Ejemplo n.º 7
0
    def test_switching_tenant_without_previous_tenant(self):
        tenant = Tenant(domain_urls=['something.test.com'], schema_name='test')
        tenant.save()

        connection.tenant = None
        with tenant_context(tenant):
            DummyModel(name="No exception please").save()

        connection.tenant = None
        with schema_context(tenant.schema_name):
            DummyModel(name="Survived it!").save()
Ejemplo n.º 8
0
    def test_switching_search_path(self):
        tenant1 = Tenant(domain_urls=['something.test.com'],
                         schema_name='tenant1')
        tenant1.save()

        connection.set_schema_to_public()
        tenant2 = Tenant(domain_urls=['example.com'], schema_name='tenant2')
        tenant2.save()

        # go to tenant1's path
        connection.set_tenant(tenant1)

        # add some data, 2 DummyModels for tenant1
        DummyModel(name="Schemas are").save()
        DummyModel(name="awesome!").save()

        # switch temporarily to tenant2's path
        with tenant_context(tenant2):
            # add some data, 3 DummyModels for tenant2
            DummyModel(name="Man,").save()
            DummyModel(name="testing").save()
            DummyModel(name="is great!").save()

        # we should be back to tenant1's path, test what we have
        self.assertEqual(2, DummyModel.objects.count())

        # switch back to tenant2's path
        with tenant_context(tenant2):
            self.assertEqual(3, DummyModel.objects.count())
Ejemplo n.º 9
0
class RoutesTestCase(BaseTestCase):
    @classmethod
    def setUpClass(cls):
        super(RoutesTestCase, cls).setUpClass()
        settings.SHARED_APPS = ('django_tenants', )
        settings.TENANT_APPS = ('dts_test_app',
                                'django.contrib.contenttypes',
                                'django.contrib.auth', )
        settings.INSTALLED_APPS = settings.SHARED_APPS + settings.TENANT_APPS
        cls.sync_shared()
        cls.public_tenant = Tenant(domain_urls=['test.com'], schema_name=get_public_schema_name())
        cls.public_tenant.save()

    def setUp(self):
        super(RoutesTestCase, self).setUp()
        self.factory = RequestFactory()
        self.tm = TenantMiddleware()

        self.tenant_domain = 'tenant.test.com'
        self.tenant = Tenant(domain_urls=[self.tenant_domain], schema_name='test')
        self.tenant.save()

    def test_tenant_routing(self):
        """
        Request path should not be altered.
        """
        request_url = '/any/request/'
        request = self.factory.get('/any/request/',
                                   HTTP_HOST=self.tenant_domain)
        self.tm.process_request(request)

        self.assertEquals(request.path_info, request_url)

        # request.tenant should also have been set
        self.assertEquals(request.tenant, self.tenant)

    def test_public_schema_routing(self):
        """
        Request path should not be altered.
        """
        request_url = '/any/request/'
        request = self.factory.get('/any/request/',
                                   HTTP_HOST=self.public_tenant.domain_urls[0])
        self.tm.process_request(request)

        self.assertEquals(request.path_info, request_url)

        # request.tenant should also have been set
        self.assertEquals(request.tenant, self.public_tenant)
Ejemplo n.º 10
0
    def setUp(self):
        super(CeleryTasksTests, self).setUp()
        self.tenant1 = Tenant(domain_url='test1', schema_name='test1')
        self.tenant1.save()

        self.tenant2 = Tenant(domain_url='test2', schema_name='test2')
        self.tenant2.save()

        connection.set_tenant(self.tenant1)
        self.dummy1 = DummyModel.objects.create(name='test1')

        connection.set_tenant(self.tenant2)
        self.dummy2 = DummyModel.objects.create(name='test2')

        connection.set_schema_to_public()
Ejemplo n.º 11
0
    def test_tenant_apps_does_not_sync_shared_apps(self):
        """
        Tests that if an app is in TENANT_APPS, it does not get synced to
        the public schema.
        """
        settings.SHARED_APPS = ('django_tenants',
                                'django.contrib.auth',
                                'django.contrib.contenttypes', )
        settings.TENANT_APPS = ('django.contrib.sessions', )  # 1 table
        settings.INSTALLED_APPS = settings.SHARED_APPS + settings.TENANT_APPS
        self.sync_shared()
        tenant = Tenant(domain_urls=['arbitrary.test.com'], schema_name='test')
        tenant.save()

        tenant_tables = self.get_tables_list_in_schema(tenant.schema_name)
        self.assertEqual(1+self.MIGRATION_TABLE_SIZE, len(tenant_tables))
        self.assertIn('django_session', tenant_tables)
Ejemplo n.º 12
0
    def test_content_types_is_not_mandatory(self):
        """
        Tests that even if content types is in SHARED_APPS, it's
        not required in TENANT_APPS.
        """
        settings.SHARED_APPS = ('django_tenants',  # 2 tables
                                'django.contrib.contenttypes', )  # 1 table
        settings.TENANT_APPS = ('django.contrib.sessions', )  # 1 table
        settings.INSTALLED_APPS = settings.SHARED_APPS + settings.TENANT_APPS
        self.sync_shared()
        tenant = Tenant(domain_urls=['something.test.com'], schema_name='test')
        tenant.save()

        shared_tables = self.get_tables_list_in_schema(get_public_schema_name())
        tenant_tables = self.get_tables_list_in_schema(tenant.schema_name)
        self.assertEqual(2+1 + self.MIGRATION_TABLE_SIZE, len(shared_tables))
        self.assertIn('django_session', tenant_tables)
        self.assertEqual(1+self.MIGRATION_TABLE_SIZE, len(tenant_tables))
        self.assertIn('django_session', tenant_tables)
Ejemplo n.º 13
0
    def test_tenant_apps_does_not_sync_shared_apps(self):
        """
        Tests that if an app is in TENANT_APPS, it does not get synced to
        the public schema.
        """
        settings.SHARED_APPS = (
            'django_tenants',
            'django.contrib.auth',
            'django.contrib.contenttypes',
        )
        settings.TENANT_APPS = ('django.contrib.sessions', )  # 1 table
        settings.INSTALLED_APPS = settings.SHARED_APPS + settings.TENANT_APPS
        self.sync_shared()
        tenant = Tenant(domain_urls=['arbitrary.test.com'], schema_name='test')
        tenant.save()

        tenant_tables = self.get_tables_list_in_schema(tenant.schema_name)
        self.assertEqual(1 + self.MIGRATION_TABLE_SIZE, len(tenant_tables))
        self.assertIn('django_session', tenant_tables)
Ejemplo n.º 14
0
 def setUpClass(cls):
     super(RoutesTestCase, cls).setUpClass()
     settings.SHARED_APPS = ('django_tenants', )
     settings.TENANT_APPS = ('dts_test_app',
                             'django.contrib.contenttypes',
                             'django.contrib.auth', )
     settings.INSTALLED_APPS = settings.SHARED_APPS + settings.TENANT_APPS
     cls.sync_shared()
     cls.public_tenant = Tenant(domain_urls=['test.com'], schema_name=get_public_schema_name())
     cls.public_tenant.save()
Ejemplo n.º 15
0
    def test_tenant_apps_and_shared_apps_can_have_the_same_apps(self):
        """
        Tests that both SHARED_APPS and TENANT_APPS can have apps in common.
        In this case they should get synced to both tenant and public schemas.
        """
        settings.SHARED_APPS = ('django_tenants',  # 2 tables
                                'django.contrib.auth',  # 6 tables
                                'django.contrib.contenttypes',  # 1 table
                                'django.contrib.sessions', )  # 1 table
        settings.TENANT_APPS = ('django.contrib.sessions', )  # 1 table
        settings.INSTALLED_APPS = settings.SHARED_APPS + settings.TENANT_APPS
        self.sync_shared()
        tenant = Tenant(domain_urls=['arbitrary.test.com'], schema_name='test')
        tenant.save()

        shared_tables = self.get_tables_list_in_schema(get_public_schema_name())
        tenant_tables = self.get_tables_list_in_schema(tenant.schema_name)
        self.assertEqual(2+6+1+1+self.MIGRATION_TABLE_SIZE, len(shared_tables))
        self.assertIn('django_session', shared_tables)
        self.assertEqual(1+self.MIGRATION_TABLE_SIZE, len(tenant_tables))
        self.assertIn('django_session', tenant_tables)
Ejemplo n.º 16
0
    def test_switching_search_path(self):
        tenant1 = Tenant(domain_urls=['something.test.com'],
                         schema_name='tenant1')
        tenant1.save()

        connection.set_schema_to_public()
        tenant2 = Tenant(domain_urls=['example.com'], schema_name='tenant2')
        tenant2.save()

        # go to tenant1's path
        connection.set_tenant(tenant1)

        # add some data, 2 DummyModels for tenant1
        DummyModel(name="Schemas are").save()
        DummyModel(name="awesome!").save()

        # switch temporarily to tenant2's path
        with tenant_context(tenant2):
            # add some data, 3 DummyModels for tenant2
            DummyModel(name="Man,").save()
            DummyModel(name="testing").save()
            DummyModel(name="is great!").save()

        # we should be back to tenant1's path, test what we have
        self.assertEqual(2, DummyModel.objects.count())

        # switch back to tenant2's path
        with tenant_context(tenant2):
            self.assertEqual(3, DummyModel.objects.count())
Ejemplo n.º 17
0
    def test_content_types_is_not_mandatory(self):
        """
        Tests that even if content types is in SHARED_APPS, it's
        not required in TENANT_APPS.
        """
        settings.SHARED_APPS = (
            'django_tenants',  # 2 tables
            'django.contrib.contenttypes',
        )  # 1 table
        settings.TENANT_APPS = ('django.contrib.sessions', )  # 1 table
        settings.INSTALLED_APPS = settings.SHARED_APPS + settings.TENANT_APPS
        self.sync_shared()
        tenant = Tenant(domain_urls=['something.test.com'], schema_name='test')
        tenant.save()

        shared_tables = self.get_tables_list_in_schema(
            get_public_schema_name())
        tenant_tables = self.get_tables_list_in_schema(tenant.schema_name)
        self.assertEqual(2 + 1 + self.MIGRATION_TABLE_SIZE, len(shared_tables))
        self.assertIn('django_session', tenant_tables)
        self.assertEqual(1 + self.MIGRATION_TABLE_SIZE, len(tenant_tables))
        self.assertIn('django_session', tenant_tables)
Ejemplo n.º 18
0
    def test_sync_tenant(self):
        """
        When editing an existing tenant, all data should be kept.
        """
        tenant = Tenant(domain_urls=['something.test.com'], schema_name='test')
        tenant.save()

        # go to tenant's path
        connection.set_tenant(tenant)

        # add some data
        DummyModel(name="Schemas are").save()
        DummyModel(name="awesome!").save()

        # edit tenant
        connection.set_schema_to_public()
        tenant.domain_urls = ['example.com']
        tenant.save()

        connection.set_tenant(tenant)

        # test if data is still there
        self.assertEquals(DummyModel.objects.count(), 2)
Ejemplo n.º 19
0
    def test_sync_tenant(self):
        """
        When editing an existing tenant, all data should be kept.
        """
        tenant = Tenant(domain_urls=['something.test.com'], schema_name='test')
        tenant.save()

        # go to tenant's path
        connection.set_tenant(tenant)

        # add some data
        DummyModel(name="Schemas are").save()
        DummyModel(name="awesome!").save()

        # edit tenant
        connection.set_schema_to_public()
        tenant.domain_urls = ['example.com']
        tenant.save()

        connection.set_tenant(tenant)

        # test if data is still there
        self.assertEquals(DummyModel.objects.count(), 2)
Ejemplo n.º 20
0
class CeleryTasksTests(BaseTestCase):
    def setUp(self):
        super(CeleryTasksTests, self).setUp()
        self.tenant1 = Tenant(domain_url='test1', schema_name='test1')
        self.tenant1.save()

        self.tenant2 = Tenant(domain_url='test2', schema_name='test2')
        self.tenant2.save()

        connection.set_tenant(self.tenant1)
        self.dummy1 = DummyModel.objects.create(name='test1')

        connection.set_tenant(self.tenant2)
        self.dummy2 = DummyModel.objects.create(name='test2')

        connection.set_schema_to_public()

    def test_basic_model_update(self):
        # We should be in public schema where dummies don't exist.
        for dummy in self.dummy1, self.dummy2:
            # Test both async and local versions.
            with self.assertRaises(DummyModel.DoesNotExist):
                update_task.apply_async(args=(dummy.pk, 'updated-name'))

            with self.assertRaises(DummyModel.DoesNotExist):
                update_task.apply(args=(dummy.pk, 'updated-name'))

        connection.set_tenant(self.tenant1)
        update_task.apply_async(args=(self.dummy1.pk, 'updated-name'))
        self.assertEqual(connection.schema_name, self.tenant1.schema_name)

        # The task restores the schema from before running the task, so we are
        # using the `tenant1` tenant now.
        model_count = DummyModel.objects.filter(name='updated-name').count()
        self.assertEqual(model_count, 1)

        connection.set_tenant(self.tenant2)
        model_count = DummyModel.objects.filter(name='updated-name').count()
        self.assertEqual(model_count, 0)

    def test_task_retry(self):
        # Schema name should persist through retry attempts.
        connection.set_tenant(self.tenant1)
        update_retry_task.apply_async(args=(self.dummy1.pk, 'updated-name'))

        model_count = DummyModel.objects.filter(name='updated-name').count()
        self.assertEqual(model_count, 1)

    def test_restoring_schema_name(self):
        update_task.apply_async(
            args=(self.dummy1.pk, 'updated-name'),
            kwargs={'_schema_name': self.tenant1.schema_name}
        )
        self.assertEqual(connection.schema_name, get_public_schema_name())

        connection.set_tenant(self.tenant1)
        update_task.apply_async(
            args=(self.dummy2.pk, 'updated-name'),
            kwargs={'_schema_name': self.tenant2.schema_name}
        )
        self.assertEqual(connection.schema_name, self.tenant1.schema_name)

        connection.set_tenant(self.tenant2)
        # The model does not exist in the public schema.
        with self.assertRaises(DummyModel.DoesNotExist):
            update_task.apply_async(
                args=(self.dummy2.pk, 'updated-name'),
                kwargs={'_schema_name': get_public_schema_name()}
            )

        self.assertEqual(connection.schema_name, self.tenant2.schema_name)