Metadata-Version: 2.1
Name: petisco
Version: 0.29.7
Summary: Petisco is a framework for helping Python developers to build clean Applications
Home-page: https://github.com/alice-biometrics/petisco
Author: ALiCE Biometrics
Author-email: support@alicebiometrics.com
License: MIT
Description: # petisco :cookie:  [![version](https://img.shields.io/github/release/alice-biometrics/petisco/all.svg)](https://github.com/alice-biometrics/petisco/releases) [![ci](https://github.com/alice-biometrics/petisco/workflows/ci/badge.svg)](https://github.com/alice-biometrics/petisco/actions) [![pypi](https://img.shields.io/pypi/dm/petisco)](https://pypi.org/project/petisco/)
        
        <img src="https://github.com/alice-biometrics/custom-emojis/blob/master/images/alice_header.png" width=auto>
        
        Petisco is a framework for helping Python developers to build clean Applications in Python.
        
        :warning: disclaimer: not stable yet
        
        
        ## Table of Contents
        - [Installation :computer:](#installation-computer)
        - [Getting Started :chart_with_upwards_trend:](#getting-started-chart_with_upwards_trend)
            * [Flask Application (by petisco :cookie:)](#flask-application-by-petisco-cookie)
            * [Configure your Application :rocket:](#configure-your-application-rocket)
            * [Handlers](#handlers)
              - [Controller Handler](#controller-handler)
            * [Model your Domain](#model-your-domain)
              - [Value Objects](#value-objects)
              - [Events](#events)
              - [Aggregate Root](#aggregate-root)
        - [Testing :white_check_mark:](#testing-white_check_mark)
        - [Extras](#extras)
        - [Contact :mailbox_with_mail:](#contact-mailbox_with_mail)
        
        
        ## Installation :computer:
        
        ```console
        pip install petisco
        ```
        
        Installation with Extras 
        
        ```console
        pip install petisco[flask]
        pip install petisco[sqlalchemy]
        pip install petisco[redis]
        pip install petisco[rabbitmq]
        pip install petisco[fixtures]
        pip install petisco[flask,sqlalchemy,redis,rabbitmq,fixtures]
        ```
        
        ## Getting Started :chart_with_upwards_trend:	
        
        ### Flask Application (by Petisco :cookie:)
        
        Check the following repo to learn how to use petisco with flask: [petisco-task-manager](https://github.com/alice-biometrics/petisco-task-manager)
        
        ### Configure your Application :rocket:
        
        Configure your app using the `petisco.yml`
        
        ```yaml
        app:
          name: taskmanager
          version:
            from_file: VERSION
        tasks:
          recurring-task:
            run_in: 5 # seconds
            interval: 10 # seconds
            handler: taskmanager.tasks.recurring_task
          scheduled-task:
            run_in: 10 # seconds
            handler: taskmanager.tasks.scheduled_task
          instant-task:
            handler: taskmanager.tasks.instant_task
        framework:
            selected_framework: flask
            config_file: swagger.yaml
            port: 8080
            port_env: PETISCO_PORT
        logger:
            selected_logger: logging
            name: petisco
            format: "%(name)s - %(levelname)s - %(message)s"
            config: taskmanager.src.config.logging.logging_config
        persistence:
          config: taskmanager.src.config.persistence.config_persistence
          models:
            task: taskmanager.src.modules.tasks.infrastructure.persistence.models.task_model.TaskModel
            event: taskmanager.src.modules.events.infrastructure.persistence.models.event_model.EventModel
        providers:
           services_provider: taskmanager.src.config.services.services_provider
           repositories_provider: taskmanager.src.config.repositories.repositories_provider
        events:
          publish_deploy_event: True
          publisher:
            provider: taskmanager.src.config.events.publisher_provider
          subscriber:
            provider: taskmanager.src.config.events.subscriber_provider
            subscribers:
              store-event:
                organization: acme
                service: taskmanager
                topic: taskmanager-events
                dead_letter: True
                handler: taskmanager.src.modules.events.application.store.event_store.event_store
        ```
        
        For instance, if your app don't need cron dispatchers, events persistence and repositories, you can remove it from the `petisco.yml`:
        
        ```yaml
        app:
          name: taskmanager-nopersistence
          version:
            from_file: VERSION
        framework:
            selected_framework: flask
            config_file: swagger.yaml
            port: 8080
            port_env: PETISCO_PORT
        logger:
            selected_logger: logging
            name: petisco
            format: "%(name)s - %(levelname)s - %(message)s"
            config: taskmanager.src.config.logging.logging_config
        providers:
           services_provider: taskmanager.src.config.services.services_provider
        ```
        
        ### Handlers
        
        **petisco** implement a sort of decorator to handle common behaviour of application elements.
        
        #### Controller Handler
        
        Add it to your entry point controller and manage the behaviour:
        
        ```python
            from petisco import controller_handler
            from meiga import Success
        
            @controller_handler()
            def my_controller(headers=None):
                return Success("Hello Petisco")
        ```
        *controller_handler parameters:*
        
            Parameters
            ----------
            app_name
                Application Name. If not specified it will get it from Petisco.get_app_version().
            app_version
                Application Version. If not specified it will get it from Petisco.get_app_version().
            logger
                A ILogger implementation. If not specified it will get it from Petisco.get_logger(). You can also use NotImplementedLogger
            token_manager
                TokenManager object. Here, you can define how to deal with JWT Tokens
            success_handler
                Handler to deal with Success Results
            error_handler
                Handler to deal with Failure Results
            headers_provider
                Injectable function to provide headers. By default is used headers_provider
            logging_types_blacklist
                Logging Blacklist. Object of defined Type will not be logged. By default ( [bytes] ) bytes object won't be logged.
            publisher
                A IEventPublisher implementation. If not specified it will get it from Petisco.get_event_publisher().
            send_request_responded_event
                Boolean to select if RequestResponded event is send. It will use provided publisher
            """
            
        ### Model your Domain
        
        
        #### Value Objects
        
        Extend `ValueObject` to model your Value Objects.
        
        Find some examples in [petisco/domain/value_objects](petisco/domain/value_objects)
        
        #### Events
        
        Extend `Event` to model your domain events.
        
        ```python
        from petisco import Event, UserId, Name
        
        class UserCreated(Event):
            user_id: UserId
            name: Name
        
            def __init__(self, user_id: UserId, name: Name):
                self.user_id = user_id
                self.name = name
                super().__init__()
        ```
        
        To prevent the propagation of Id parameters throughout your domain, you can compose your Event with a [`InfoId`](petisco/domain/aggregate_roots/info_id.py)
        
        ```python
        user_created = UserCreated(user_id, name).add_info_id(info_id)
        ```
        
        #### Aggregate Root
        
        Extend `AggregateRoot` to model your Aggregate Roots
         
        ```python
        from petisco import AggregateRoot, UserId, Name
        from my_code import UserCreated
        
        class User(AggregateRoot):
        
            def __init__(self, name: Name, user_id: UserId):
                self.name = name
                self.user_id = user_id
                super().__init__()
        
            @staticmethod
            def create(name: Name):
                user = User(name, UserId.generate())
                user.record(UserCreated(user.user_id, user.name))
                return user
        ```
        
        Use semantic constructors and `record` domain `Event`s very easy.
        
        ```python 
        user = User.create(Name("Petisco"))
        events = user.pull_domain_events() # Events ready to be published
        ```
        ### Testing :white_check_mark:
        
        ###### Petisco Fixtures
        
        Import useful petisco fixtures with :
        
        ```python
        from petisco.fixtures import *
        ```
        
        We can use [petisco_client](petisco/fixtures/client.py) to simulate our client in acceptance tests
        
        ```python
        import pytest
        
        @pytest.mark.acceptance
        def test_should_return_200_when_call_healthcheck(
            petisco_client
        ):
            response = petisco_client.get("/petisco/environment")
            assert response.status_code == 200
        ```
        
        Included in *petisco_client* we can find [petisco_sql_database](petisco/fixtures/persistence.py).
        This fixture will create and connect a database and after the test this will be deleted.
        
        
        #### Extras
        
        ###### RabbitMQ <img src="https://github.com/alice-biometrics/custom-emojis/blob/master/images/rabbitmq.png" width="16">
        
        To test RabbitEventManager you need to run locally a RabbitMQ application, otherwise related test will be skipped.
        Please, check the official doc here: https://www.rabbitmq.com/download.html
        
        Run RabbitMQ with docker
        
        ```console
        docker run -it --rm --name rabbitmq -p 5672:5672 -p 15672:15672 rabbitmq:3-management
        ```
        
        Please, check examples in [examples/pubsub](examples/pubsub)
        
        Run a Subscriber
        
        ```console
        python examples/pubsub/sub.py
        ```
        
        Run a Publisher:
        
        ```console
        python examples/pubsub/pub.py
        ```
        
        Run a Subscriber linked to a dead letter queues.
        
        ```console
        python examples/pubsub/dl_sub.py
        ```
        
        This can be used to requeue nack events.
        
        
        ##### Configurations
        
        * `RABBITMQ_HEARTBEAT`: (default: 60 s)
        * `RABBITMQ_USER`: (default: guest)
        * `RABBITMQ_PASSWORD`: (default: guest)
        * `RABBITMQ_HOST`: (default: localhost)
        * `RABBITMQ_HOST`: (default: 5672)
        * `RABBITMQ_CONNECTION_NUM_MAX_RETRIES`: (default: 15)
        * `RABBITMQ_CONNECTION_WAIT_SECONDS_RETRY`: (default: 1)
        * `RABBITMQ_MESSAGE_TTL`: (default 1000 ms) If a queue is already created it will generate a precodition failure.
        
        
        ## Development
        
        ### Using lume
        
        ```console
        pip install lume
        ```
        
        Then:
        
        ```console 
        lume -install -all
        ```
        
        
        ## Contact :mailbox_with_mail:
        
        support@alicebiometrics.com
        
Keywords: DDD,Use Case,Clean Architecture,REST,Applications
Platform: UNKNOWN
Classifier: License :: OSI Approved :: MIT License
Classifier: Programming Language :: Python
Classifier: Programming Language :: Python :: 3
Description-Content-Type: text/markdown
Provides-Extra: redis
Provides-Extra: sqlalchemy
Provides-Extra: gunicorn
Provides-Extra: slack
Provides-Extra: fixtures
Provides-Extra: rabbitmq
Provides-Extra: flask
