Skip to main content

Dynamodb model maker.

Project description

Dynamizer

A supportive set of defaults for dynamodb. Dynamizer doesn't aim to abstract away the nuances of dynamodb, but rather to provide effective defaults for the repetitive tasks of (de)serializing models to and from dynamodb.

It provides:

  • Automatic deserialization from dynamo's format. This is helpful when processing a change stream from dynamo.
  • Overwrite detection. If a model is changed between reading it and writing it back to dynamodb an error will be raised, preventing the unintentional overwriting of existing data.
  • Supportive base delete, save, and load function to make a programmers life easier.

Usage

Dynamizer models are built on top of immutable data classes.

import dataclasses
import dynamizer


@dataclasses.dataclass(frozen=True)
class DemoClass(dynamizer.DynamiteModel):
    """A demo class."""

    foobar: str
    fizbuzz: typing.Optional[str] = None

    @property
    def hash_key(self) -> str:
        """
        Get the hash key.

        Dynamizer can't tell you what the right hash/range key scheme is
        write for your use case and access patterns so you must define
        how to translate the model's data into a hash and range key.
        """
        return f"hash-key/{self.foobar}"

    @property
    def range_key(self) -> str:
        """Get the range key."""
        return "/range-key"

    def _gs1(self) -> str:
        """
        Get the gs1 value.

        Dynamizer will also support you in instantiating any global secondary
        indices. It expects these to be defined matching the pattern
        `^_?gs\d+$`. Dynamizer searches the class for any functions matching
        this pattern and automatically manages their lifecycle within dynamodb,
        creating them dynamically as the model is saved, and deleting them
        if they are null in some part of the models life. Note that The index
        itself still needs to be created within dynamodb.
        """
        return f"{self.foobar}/hash-key"

    @classmethod
    def load(cls, my_identifier: typing.Any) -> "DemoClass":
        """
        Load a model from dynamodb.

        Dynamizer does not provide a default load function, since it doesn't
        know all of your specific access patterns and how incoming arguments
        are to be translated into a hash key, range key pair, but it does
        provide helpful secondary methods to make writing a load function
        easier.
        """
        hash_key = _hash_key(my_identifier)
        range_key = _hash_key(my_identifier)
        client = boto3.client("dynamodb")
        result = cls._base_load(client, "my-table-name", hash_key, range_key)
        if result is None:
            raise NotFoundError(f"Could not find {my_identifier}")
        return result

    @classmethod
    def list_group(cls, my_group: typing.Any) -> typing.List["DemoClass"]:
        """
        List a model under the specified group.

        Dynamizer provides methods for easily converting a dynamodb response
        into a python model making it easier to write functions defining a
        variety of access patterns.
        """
        ...
        response = client.query("Something fancy")
        return [cls.inflate(item) for item in response.get("Items", [])]


    def save(self) -> "DemoClass":
        """
        Save a model.

        Dynamizer keeps a count of changes to a model and checks when saving
        to ensure that no changes have come in since the model was initially
        read. This prevents data from being overwritten both during initial
        creation and during updates.
        """
        ...
        return self._base_save(client, "table_to_save_to")

    def delete(self):
        """
        Delete a model.

        Like during saves, Dynamizer keeps a count of changes and will prevent
        a delete from taking place if an update has taken place since the last
        read.
        """
        ...
        self._base_delete(client, "table_to_delete_from")

Mocking

Dynamizer provides a mechanism for mocking out dynamodb calls for testing. The initial state of dynamodb can be set via yaml files.

import dynamizer.mock

data = yaml.safe_load("/path/to/data.yaml")

with dynamizer.mock.from_yaml(data):
    # Within this context dynamodb will have the state defined in data.yaml

The expected format of the yaml file is:

- table_name: my-table-name
  region: us-east-1 # Optional
  secondary_indexes: # Optional
    - name: gs1-gs2
      hash_key: gs1
      range_key: gs2
  objects:
    MyDynamizerSubCls:
      - foo: {S: bar}
        fiz: {S: buzz}
    AnotherDynamizerSubCls:
      - mock: {S: data}

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

dynamizer-0.2.14.tar.gz (8.0 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

dynamizer-0.2.14-py3-none-any.whl (9.8 kB view details)

Uploaded Python 3

File details

Details for the file dynamizer-0.2.14.tar.gz.

File metadata

  • Download URL: dynamizer-0.2.14.tar.gz
  • Upload date:
  • Size: 8.0 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: poetry/2.1.2 CPython/3.13.3 Linux/6.14.4-300.fc42.x86_64

File hashes

Hashes for dynamizer-0.2.14.tar.gz
Algorithm Hash digest
SHA256 5e96267dbfac6e16950d33dec29dc9e80042ea4dcaeccb93adafc393bf337e94
MD5 63e5297c7d3816bd841c0e1921954467
BLAKE2b-256 6d1429d154ca8db4d9dcdf347a1720a8d7b8b1fdf80d1803c8f16de9be9c9516

See more details on using hashes here.

File details

Details for the file dynamizer-0.2.14-py3-none-any.whl.

File metadata

  • Download URL: dynamizer-0.2.14-py3-none-any.whl
  • Upload date:
  • Size: 9.8 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: poetry/2.1.2 CPython/3.13.3 Linux/6.14.4-300.fc42.x86_64

File hashes

Hashes for dynamizer-0.2.14-py3-none-any.whl
Algorithm Hash digest
SHA256 38d787359c44d3e78e0fa49d86bd82e95db7159db806e3a9ce266ce0bdd113fd
MD5 b7e8f56489a540db70e282c9b616b941
BLAKE2b-256 49b212b27f3abd4238de6dfe3b506493bc76e8b58a28ab0c41af11b53e70cda0

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page