Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Cross database join #442

Closed
RealJTG opened this issue Oct 6, 2014 · 3 comments
Closed

Cross database join #442

RealJTG opened this issue Oct 6, 2014 · 3 comments

Comments

@RealJTG
Copy link

RealJTG commented Oct 6, 2014

Is it possible to perform cross database join somehow on the same MySQL instance? For example:

SELECT A.value, B.value
FROM db1.foo A 
JOIN db2.bar B ON A.id = B.id
@coleifer
Copy link
Owner

coleifer commented Oct 6, 2014

Interesting. Peewee does not support this out of the box, so your best option right now is to probably use the RawQuery helper (docs).

Another option is to take a look at how the PostgresqlDatabase supports a "schema" argument. The schema is only used to prefix table and column names, so maybe it could be repurposed to prefix with the database name instead?

@RealJTG
Copy link
Author

RealJTG commented Oct 7, 2014

schema seems to work fine. I'm using flask-peewee and my DB class now looks like this (with delayed initialization coleifer/flask-peewee#154 and multiple configurations support)

class SchemaProxy(object):
    __slots__ = ['obj']

    def __init__(self):
        self.initialize(None)

    def initialize(self, obj):
        self.obj = obj

    def __str__(self):
        return self.obj or None


class ConfigurableDatabase(Database):

    def __init__(self, app=None, config_key='DATABASE'):
        self.config_key = config_key
        self.schema = SchemaProxy()
        super(ConfigurableDatabase, self).__init__(app)

    def load_database(self):
        self.database_config = dict(self.app.config[self.config_key])
        try:
            self.database_name = self.database_config.pop('name')
            self.database_engine = self.database_config.pop('engine')
            self.schema.initialize(self.database_name)
        except KeyError:
            raise ImproperlyConfigured('Please specify a "name" and "engine" for your database')

        try:
            self.database_class = load_class(self.database_engine)
            assert issubclass(self.database_class, PeeweeDatabase)
        except ImportError:
            raise ImproperlyConfigured('Unable to import: "%s"' % self.database_engine)
        except AttributeError:
            raise ImproperlyConfigured('Database engine not found: "%s"' % self.database_engine)
        except AssertionError:
            raise ImproperlyConfigured('Database engine not a subclass of peewee.Database: "%s"' % self.database_engine)

        self.database = self.database_class(self.database_name, **self.database_config)

    def get_model_class(self):
        class BaseModel(Model):
            class Meta:
                database = self.proxy
                schema = self.schema

        return BaseModel

With werkzeug.local.LocalProxy even cleaner, but not sure about side effects

class ConfigurableDatabase(Database):

    def get_model_class(self):
        class BaseModel(Model):
            class Meta:
                database = self.proxy
                schema = LocalProxy(lambda: self.database_name)

        return BaseModel

@coleifer
Copy link
Owner

coleifer commented Oct 7, 2014

Neat. I'm going to close as it sounds like your immediate issue is resolved. Please comment if this is not the case.

@coleifer coleifer closed this as completed Oct 7, 2014
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants