Git Product home page Git Product logo

ormar-postgres-extensions's Introduction

ormar-postgres-extensions

All Contributors

Maturity badge - level 1 Stage Discord

Pypi Wheel PyPI - Python Version PyPI - Downloads PyPI - License

Build Status codecov

Overview

ormar-postgres-extensions is a an extension to theOrmar ORM. It enables developers to write models that map to native PostgreSQL types.

Motivation

Ormar is an amazing async ORM that works with FastAPI. However, it is agnostic to the underlying database used meaning that we cannot use native PostgreSQL types such as UUID or JSONB columns. The aim of this library is to provide Ormar fields that can be used to generate database columns with native PG types.

Installation

python -m pip install ormar-postgres-extensions

Usage

Fields

Three native PG fields are provided. The JSONB and UUID types map to native JSONB and UUID data types respectively. The Array type can be used to create an array column. Using these in an Ormar model is as simple as importing the fields and using them in the model.

UUID

from uuid import UUID

import ormar
import ormar_postgres_extensions as ormar_pg_ext


class MyModel(ormar.Model):
    uuid: UUID = ormar_pg_ext.UUID(unique=True, nullable=False)

JSONB

import ormar
import ormar_postgres_extensions as ormar_pg_ext

class JSONBTestModel(ormar.Model):
    id: int = ormar.Integer(primary_key=True)
    data: dict = ormar_pg_ext.JSONB()
jsonb_contained_by

The maps to the contains operator in Postgres.

await JSONBTestModel.objects.filter(data__jsonb_contained_by=dict(key="value")).all()
jsonb_contains

The maps to the contains operator in Postgres.

await JSONBTestModel.objects.filter(data__jsonb_contains=dict(key="value")).all()
jsonb_has_all

The maps to the has_all operator in Postgres.

from sqlalchemy.dialects.postgresql import array

await JSONBTestModel.objects.filter(data__jsonb_has_all=array(["key1", "key2"])).all()
jsonb_has_any

The maps to the has_any operator in Postgres.

from sqlalchemy.dialects.postgresql import array

await JSONBTestModel.objects.filter(data__jsonb_has_any=array(["key1", "key2"])).all()
jsonb_has_key

The maps to the has_key operator in Postgres.

await JSONBTestModel.objects.filter(data__jsonb_has_key="key1").all()

Array

Array field requires a bit more setup to pass the type of the array into the field

import ormar
import sqlalchemy
import ormar_postgres_extensions as ormar_pg_ext

class ModelWithArray(ormar.Model):
    class Meta:
        database = database
        metadata = metadata

    id: int = ormar.Integer(primary_key=True)
    data: list = ormar_pg_ext.ARRAY(item_type=sqlalchemy.String())

Arrays have access to three special methods that map to specific PostgreSQL array functions

array_contained_by

The maps to the contained_by operator in Postgres.

await ModelWithArray.objects.filter(data__array_contained_by=["a"]).all()
array_contains

The maps to the contains operator in Postgres.

await ModelWithArray.objects.filter(data__array_contains=["a"]).all()
array_overlap

The maps to the overlap operator in Postgres.

await ModelWithArray.objects.filter(data__array_overlap=["a"]).all()

INET / CIDR

from ipaddress import IPv4Address, IPv6Address, IPv4Interface, IPv6Interface
from typing import Union

import ormar
import ormar_postgres_extensions as ormar_pg_ext

IPAddress = Union[
    IPv4Address,
    IPv4Interface,
    IPv6Address,
    IPv6Interface,
]

class INETTestModel(ormar.Model):
    id: int = ormar.Integer(primary_key=True)
    inet: IPAddress = ormar_pg_ext.INET()
    cidr: IPAddress = ormar_pg_ext.CIDR()
contained_by

This maps to the << operator

from ipaddress import ip_interface
await INETTestModel.objects.filter(inet__contained_by=ip_interface("192.168.1.0/24")).all()
contained_by_eq

This maps to the <<= operator

from ipaddress import ip_interface
await INETTestModel.objects.filter(inet__contained_by_eq=ip_interface("192.168.1.0/24")).all()
contains_subnet

This maps to the >> operator

from ipaddress import ip_interface
await INETTestModel.objects.filter(inet__contains_subnet=ip_interface("192.168.1.0/24")).all()
contains_subnet_eq

This maps to the >>= operator

from ipaddress import ip_interface
await INETTestModel.objects.filter(inet__contains_subnet_eq=ip_interface("192.168.1.0/24")).all()
contains_or_eq

This maps to the && operator

from ipaddress import ip_interface
await INETTestModel.objects.filter(inet__contains_or_eq=ip_interface("192.168.1.0/24")).all()

MACADDR

from ipaddress import IPv4Address, IPv6Address, IPv4Interface, IPv6Interface
from typing import Union

import ormar
import ormar_postgres_extensions as ormar_pg_ext

class MacAddrTestModel(ormar.Model):
    id: int = ormar.Integer(primary_key=True)
    addr: str = ormar_pg_ext.MACADDR()

Uninstalling

pip uninstall ormar-postgres-extensions

Contributing

Feel free to open a PR or GitHub issue. Contributions welcome!

To develop locally, clone this repository and run . script/bootstrap to install test dependencies. You can then use invoke --list to see available commands. To run the tests locally, PostgreSQL needs to be running. This can be easily started via inv database.

See contributing guide

Contributors

You don't really have to add this section yourself! Simply use all-contributors by adding comments in your PRs like so:


Evert Timberg

๐Ÿค” ๐Ÿš‡ ๐Ÿšง ๐Ÿ“– โš ๏ธ
@all-contributors please add <username> for <contribution type>

Find out more about All-Contributors on their website!

License

ormar-postgres-extensions is licensed under Apache License Version 2.0.

ormar-postgres-extensions's People

Contributors

allcontributors[bot] avatar etimberg avatar rajaiswal avatar semantic-release-bot avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar

ormar-postgres-extensions's Issues

Implement Monetary PG types

Is your feature request related to a problem? Please describe.

Postgres has a monetary datatype that we should support

Describe the solution you'd like

Ormar field for monetary types

Describe alternatives you've considered

No response

Additional context

No response

Consider supporting Pydantic 2.0?

Is your feature request related to a problem? Please describe.

Hi, there. I'm using this extension, thanks a lot.
The package is not compatible with Pydantic 2.0 when I try to update pydantic to 2.0 with Poetry.
Would you consider supporting Pydantic 2.0?

Describe the solution you'd like

No response

Describe alternatives you've considered

No response

Additional context

No response

Support Geometric Types

Is your feature request related to a problem? Please describe.

Postgres has geometric types. This library should support those.

Describe the solution you'd like

  1. Ormar fields for the different geometric types
  2. Implementations for geometric operators that are supported by SQLALchemy

Describe alternatives you've considered

No response

Additional context

No response

Array Field Aesthetic Suggestion (Not a Bug)

Describe the bug

The current Array field examples have:

await ModelWithArray.objects.filter(
  ModelWithArray.data.array_contained_by(["a"])
).all()

but as per my test this also works as is:

await ModelWithArray.objects.filter(data__array_contained_by=["a"]).all()

The latter seems like a better representation consistent with ormar. Need to change tests and Readme.

To reproduce

Run tests by replacing current format with this one:

await ModelWithArray.objects.filter(data__array_contained_by=["a"]).all()

Expected behaviour

After replacing with suggested format the tests pass and functionality is maintained.

Ormar PostgreSQL Extensions Version

v2.1.0

Ormar Version

v0.10.24

PostgreSQL Version

13

Additional Context

No response

Support network address types

Is your feature request related to a problem? Please describe.

Postgres has network address types that should be supported by this library

Describe the solution you'd like

  1. Fields for different network address types
  2. Implementation of network address operators

Describe alternatives you've considered

No response

Additional context

No response

Add tests covering other UUID types

Is your feature request related to a problem? Please describe.

There are new UUID versions that have been proposed. We should add tests covering them to ensure that everything still works

Describe the solution you'd like

Add tests covering UUID v6, v7, and v8

Describe alternatives you've considered

No response

Additional context

No response

Import Issue

What is your question?

from sqlalchemy.dialects.postgres import array

How do I actually install this?

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.