Metadata-Version: 1.2
Name: jardin
Version: 0.13.0
Summary: A dataframe-base ORM
Home-page: https://github.com/instacart/jardin
Author: Emmanuel Turlay
Author-email: emmanuel@instacart.com
License: MIT
Description-Content-Type: UNKNOWN
Description: jardin
        ======
        
        Jardin is a ``pandas.DataFrame``-based ORM for Python applications.
        
        Getting started
        ---------------
        
        In your working directory (the root of your app), create a file named
        ``jardin_conf.py``:
        
        .. code:: python
        
            # jardin_conf.py
        
            DATABASES = {
              'my_first_database': 'https://username:password@database.url:port',
              'my_second_database': 'https://username:password@database.url:port'
            }
        
            LOG_LEVEL = logging.DEBUG
        
            WATERMARK = 'My Great App'
        
        Then, in your app, say you have a table called ``users``:
        
        .. code:: python
        
            # app.py
            import jardin
        
            class Users(jardin.Model):
              db_names = {'read': 'my_first_database', 'write': 'my_second_database'}
        
        In the console:
        
        .. code:: python
        
            >>> from app import Users
            >>> users = Users.last(4)
            # /* My Great App */ SELECT * FROM users ORDER BY u.created_at DESC LIMIT 4;
            >>> users
            id   name    email              ...
            0    John    john@beatl.es      ...
            1    Paul    paul@beatl.es      ...
            2    George  george@beatl.es    ...
            3    Ringo   ringo@beatl.es     ...
        
        The resulting object is a pandas dataframe:
        
        .. code:: python
        
            >>> import pandas
            >>> isinstance(users, pandas.DataFrame)
            True
            >>> isinstance(users, jardin.Model)
            True
        
        Queries
        -------
        
        SELECT queries
        ~~~~~~~~~~~~~~
        
        Here is the basic syntax to select records from the database
        
        .. code:: python
        
            >>> users = Users.select(select = ['id', 'name'], where = {'email': 'paul@beatl.es'},
                                     order = 'id ASC', limit = 1)
            # /* My Great App */ SELECT u.id, u.name FROM users u WHERE u.email = 'paul@beatl.es' ORDER BY u.id ASC LIMIT 1;
            >>> users
            id   name
            1    Paul
        
        Arguments
        ^^^^^^^^^
        
        -  ``select`` – The list of columns to return. If not provided, all
           columns will be returned.
        -  ``where`` – conditions. Many different formats can be used to provide
           conditions. See `docs <#where-argument>`__.
        -  ``inner_join``, ``left_join`` – List of tables to join with their
           join condition. Can also be a list of classes if the appropriate
           associations have been declared. See
           `docs <#inner_join-left_join-arguments>`__.
        -  ``order`` – order clause
        -  ``limit`` – limit clause
        -  ``group`` – grouping clause
        -  ``scopes`` – list of pre-defined scopes. See docs.
        
        ``where`` argument
        ''''''''''''''''''
        
        Here are the different ways to feed a condition clause to a query. \*
        ``where = "name = 'John'"`` \* ``where = {'name': 'John'}`` \*
        ``where = {'id': (0, 3)}`` – selects where ``id`` is between 0 and 3 \*
        ``where = {'id': [0, 1, 2]}`` – selects where ``id`` is in the array \*
        ``where = [{'id': (0, 10), 'instrument': 'drums'}, ["created_at > %(created_at)s", {'created_at': '1963-03-22'}]]``
        
        ``inner_join``, ``left_join`` arguments
        '''''''''''''''''''''''''''''''''''''''
        
        The simplest way to join another table is as follows
        
        .. code:: python
        
            >>> Users.select(inner_join = ["instruments i ON i.id = u.instrument_id"])
        
        If you have configured your models associations, see
        `here <#associations>`__, you can simply pass the class as argument:
        
        .. code:: python
        
            >>> Users.select(inner_join = [Instruments])
        
        Individual record selection
        ^^^^^^^^^^^^^^^^^^^^^^^^^^^
        
        You can also look-up a single record by id:
        
        .. code:: python
        
            >>> Users.find(1)
            # /* My Great App */ SELECT * FROM users u WHERE u.id = 1;
            {'id': 1, 'name': 'Paul', 'email': 'paul@beatl.es', ...}
        
        Note that the returned object is a ``Record`` object which allows you to
        access attributes in those way:
        
        .. code:: python
        
            >>> user['name']
            Paul
            >>> user.name
            Paul
        
        INSERT queries
        ~~~~~~~~~~~~~~
        
        .. code:: python
        
            >>> user = Users.insert(name = 'Pete', email = 'pete@beatl.es')
            # /* My Great App */ INSERT INTO users (name, email) VALUES ('Pete', 'pete@beatl.es') RETURNING id;
            # /* My Great App */ SELECT u.* FROM users WHERE u.id = 4;
            >>> user
            id   name    email
            4    Pete    pete@beatl.es
        
        UPDATE queries
        ~~~~~~~~~~~~~~
        
        .. code:: python
        
            >>> users = Users.update(values = {'hair': 'long'}, where = {'name': 'John'})
            # /* My Great App */ UPDATE users u SET (u.hair) = ('long') WHERE u.name = 'John' RETURNING id;
            # /* My Great App */ SELECT * FROM users u WHERE u.name = 'John';
        
        DELETE queries
        ~~~~~~~~~~~~~~
        
        .. code:: python
        
            >>> Users.delete(where = {'id': 1})
            # /* My Great App */ DELETE FROM users u WHERE u.id = 1;
        
        Associations
        ------------
        
        It is possible to define associations between models. For example, if
        each user has multiple instruments:
        
        .. code:: python
        
            # app.py
        
            import jardin
        
            class MyModel(jardin.Model):
              db_names = {'read': 'my_first_database', 'write': 'my_second_database'}
        
            class Instruments(MyModel):
              belongs_to = {'users': 'user_id'}
        
            class Users(MyModel):
              has_many = [Instruments]
        
        and then you can query the associated records:
        
        .. code:: python
        
            >>> users = Users.select()
            # /* My Great App */ SELECT * FROM users u;
            >>> instruments = users.instruments()
            # /* My Great App */ SELECT * FROM instruments i WHERE i.id IN (0, 1, ...);
        
        Or you can declare joins more easily
        
        .. code:: python
        
            >>> users = Users.select(inner_join = [Instruments])
        
        Scopes
        ------
        
        Queries conditions can be generalized across your app:
        
        .. code:: python
        
            # app.py
        
            class Users(jardin.Model):
              scopes = {
                'alive': {'name': ['Paul', 'Ringo']},
                'guitarists': {'name': ['John', 'George']}
              }
        
        The key is the name of the scope, and the value is the conditions to be
        applied. Anything that can be fed to the ``where`` argument of
        ``Model#select`` can be used to define a scope.
        
        Use them as such:
        
        .. code:: python
        
            >>> users = Users.select(scopes = ['alive'], ...)
            # /* My Great App */ SELECT * FROM users u WHERE u.name IN ('Paul', 'Ringo') AND ...;
        
        Misc
        ----
        
        Watermark and trace
        ~~~~~~~~~~~~~~~~~~~
        
        Multiple databases
        ~~~~~~~~~~~~~~~~~~
        
Keywords: postgres database ORM
Platform: UNKNOWN
Classifier: Intended Audience :: Developers
Classifier: License :: OSI Approved :: MIT License
Classifier: Programming Language :: Python :: 2.7
Requires-Python: >=2.7, <3
