buz 2.14.1__tar.gz → 2.14.3__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {buz-2.14.1 → buz-2.14.3}/PKG-INFO +2 -1
- {buz-2.14.1 → buz-2.14.3}/pyproject.toml +2 -1
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/buz_kafka/base_buz_aiokafka_async_consumer.py +31 -1
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/buz_kafka/buz_aiokafka_async_consumer.py +6 -3
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/buz_kafka/buz_aiokafka_multi_threaded_consumer.py +6 -1
- buz-2.14.3/src/buz/event/infrastructure/buz_kafka/exceptions/retry_exception.py +12 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/buz_kafka/kafka_event_async_subscriber_executor.py +22 -6
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/buz_kafka/kafka_event_sync_subscriber_executor.py +20 -3
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/meta_subscriber.py +6 -1
- buz-2.14.3/src/buz/kafka/domain/exceptions/not_all_partition_assigned_exception.py +13 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/infrastructure/kafka_python/kafka_python_admin_client.py +4 -1
- buz-2.14.1/src/buz/kafka/domain/exceptions/not_all_partition_assigned_exception.py +0 -8
- {buz-2.14.1 → buz-2.14.3}/LICENSE +0 -0
- {buz-2.14.1 → buz-2.14.3}/README.md +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/command/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/command/asynchronous/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/command/asynchronous/base_command_handler.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/command/asynchronous/command_bus.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/command/asynchronous/command_handler.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/command/asynchronous/middleware/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/command/asynchronous/middleware/base_handle_middleware.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/command/asynchronous/middleware/handle_middleware.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/command/asynchronous/middleware/handle_middleware_chain_resolver.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/command/asynchronous/self_process/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/command/asynchronous/self_process/self_process_command_bus.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/command/command.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/command/more_than_one_command_handler_related_exception.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/command/synchronous/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/command/synchronous/base_command_handler.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/command/synchronous/command_bus.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/command/synchronous/command_handler.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/command/synchronous/middleware/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/command/synchronous/middleware/base_handle_middleware.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/command/synchronous/middleware/handle_middleware.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/command/synchronous/middleware/handle_middleware_chain_resolver.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/command/synchronous/self_process/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/command/synchronous/self_process/self_process_command_bus.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/command/synchronous/synced_async/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/command/synchronous/synced_async/synced_async_command_bus.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/async_consumer.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/async_event_bus.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/async_subscriber.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/async_worker.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/base_async_subscriber.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/base_subscriber.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/consumer.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/dead_letter_queue/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/dead_letter_queue/dlq_criteria.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/dead_letter_queue/dlq_record.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/dead_letter_queue/dlq_repository.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/event.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/event_bus.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/exceptions/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/exceptions/event_not_published_exception.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/exceptions/event_restore_exception.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/exceptions/subscribers_not_found_exception.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/exceptions/term_signal_interruption_exception.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/exceptions/worker_execution_exception.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/buz_kafka/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/buz_kafka/async_buz_kafka_event_bus.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/buz_kafka/buz_kafka_event_bus.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/buz_kafka/consume_strategy/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/buz_kafka/consume_strategy/consume_strategy.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/buz_kafka/consume_strategy/kafka_on_fail_strategy.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/buz_kafka/consume_strategy/topic_and_subscription_group_per_subscriber_kafka_consumer_strategy.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/buz_kafka/exceptions/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/buz_kafka/exceptions/kafka_event_bus_config_not_valid_exception.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/buz_kafka/kafka_event_subscriber_executor.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/buz_kafka/publish_strategy/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/buz_kafka/publish_strategy/publish_strategy.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/buz_kafka/publish_strategy/topic_per_event_kafka_publish_strategy.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/kombu/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/kombu/allowed_kombu_serializer.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/kombu/consume_strategy/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/kombu/consume_strategy/consume_strategy.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/kombu/consume_strategy/queue_per_subscriber_consume_strategy.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/kombu/kombu_consumer.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/kombu/kombu_event_bus.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/kombu/publish_strategy/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/kombu/publish_strategy/fanout_exchange_per_event_publish_strategy.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/kombu/publish_strategy/publish_strategy.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/kombu/retry_strategy/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/kombu/retry_strategy/publish_retry_policy.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/kombu/retry_strategy/simple_publish_retry_policy.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/models/consuming_task.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/queue/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/meta_base_subscriber.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/middleware/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/middleware/async_consume_middleware.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/middleware/async_consume_middleware_chain_resolver.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/middleware/async_publish_middleware.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/middleware/async_publish_middleware_chain_resolver.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/middleware/base_consume_middleware.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/middleware/base_publish_middleware.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/middleware/consume_middleware.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/middleware/consume_middleware_chain_resolver.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/middleware/exceptions/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/middleware/exceptions/event_already_in_progress_exception.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/middleware/publish_middleware.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/middleware/publish_middleware_chain_resolver.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/strategies/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/strategies/execution_strategy/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/strategies/execution_strategy/async_execution_strategy.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/strategies/execution_strategy/async_self_process_execution_strategy.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/strategies/execution_strategy/cyclic_iterator_execution_strategy.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/strategies/execution_strategy/execution_strategy.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/strategies/execution_strategy/self_process_execution_strategy.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/strategies/retry/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/strategies/retry/consume_retrier.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/strategies/retry/consumed_event_retry.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/strategies/retry/consumed_event_retry_repository.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/strategies/retry/max_retries_consume_retrier.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/strategies/retry/max_retries_negative_exception.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/strategies/retry/reject_callback.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/subscriber.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/sync/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/sync/sync_event_bus.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/transactional_outbox/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/transactional_outbox/event_to_outbox_record_translator.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/transactional_outbox/fqn_to_event_mapper.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/transactional_outbox/outbox_criteria/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/transactional_outbox/outbox_criteria/deliverable_records_outbox_criteria_factory.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/transactional_outbox/outbox_criteria/outbox_criteria.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/transactional_outbox/outbox_criteria/outbox_criteria_factory.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/transactional_outbox/outbox_criteria/outbox_sorting_criteria.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/transactional_outbox/outbox_record.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/transactional_outbox/outbox_record_finder/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/transactional_outbox/outbox_record_finder/outbox_record_stream_finder.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/transactional_outbox/outbox_record_finder/polling_outbox_record_stream_finder.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/transactional_outbox/outbox_record_to_event_translator.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/transactional_outbox/outbox_record_validation/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/transactional_outbox/outbox_record_validation/abstract_outbox_record_validator.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/transactional_outbox/outbox_record_validation/outbox_record_size_not_allowed_exception.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/transactional_outbox/outbox_record_validation/outbox_record_validation_exception.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/transactional_outbox/outbox_record_validation/outbox_record_validator.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/transactional_outbox/outbox_record_validation/size_outbox_record_validator.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/transactional_outbox/outbox_repository.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/transactional_outbox/transactional_outbox_event_bus.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/transactional_outbox/transactional_outbox_worker.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/event/worker.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/handler.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/domain/exceptions/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/domain/exceptions/not_valid_kafka_message_exception.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/domain/exceptions/not_valid_partition_number_exception.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/domain/exceptions/topic_already_created_exception.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/domain/exceptions/topic_not_found_exception.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/domain/models/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/domain/models/auto_create_topic_configuration.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/domain/models/consumer_initial_offset_position.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/domain/models/create_kafka_topic.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/domain/models/kafka_connection_config.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/domain/models/kafka_connection_credentials.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/domain/models/kafka_connection_plain_text_credentials.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/domain/models/kafka_connection_sasl_credentials.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/domain/models/kafka_consumer_record.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/domain/models/kafka_poll_record.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/domain/models/kafka_supported_compression_type.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/domain/models/kafka_supported_sasl_mechanisms.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/domain/models/kafka_supported_security_protocols.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/domain/services/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/domain/services/async_kafka_producer.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/domain/services/kafka_admin_client.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/domain/services/kafka_admin_test_client.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/domain/services/kafka_producer.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/infrastructure/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/infrastructure/aiokafka/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/infrastructure/aiokafka/aiokafka_consumer.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/infrastructure/aiokafka/aiokafka_producer.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/infrastructure/aiokafka/rebalance/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/infrastructure/aiokafka/rebalance/kafka_callback_rebalancer.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/infrastructure/aiokafka/translators/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/infrastructure/aiokafka/translators/consumer_initial_offset_position_translator.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/infrastructure/cdc/cdc_message.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/infrastructure/deserializers/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/infrastructure/deserializers/byte_deserializer.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/infrastructure/deserializers/bytes_to_message_deserializer.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/infrastructure/deserializers/implementations/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/infrastructure/deserializers/implementations/cdc/cdc_record_bytes_to_event_deserializer.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/infrastructure/deserializers/implementations/cdc/not_valid_cdc_message_exception.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/infrastructure/deserializers/implementations/json_byte_deserializer.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/infrastructure/deserializers/implementations/json_bytes_to_message_deserializer.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/infrastructure/interfaces/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/infrastructure/interfaces/async_connection_manager.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/infrastructure/interfaces/connection_manager.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/infrastructure/kafka_python/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/infrastructure/kafka_python/exception/consumer_interrupted_exception.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/infrastructure/kafka_python/kafka_python_admin_test_client.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/infrastructure/kafka_python/kafka_python_producer.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/infrastructure/kafka_python/translators/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/infrastructure/kafka_python/translators/consumer_initial_offset_position_translator.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/infrastructure/serializers/byte_serializer.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/infrastructure/serializers/implementations/cdc_record_bytes_to_event_serializer.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/infrastructure/serializers/implementations/json_byte_serializer.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/kafka/infrastructure/serializers/kafka_header_serializer.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/locator/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/locator/handler_fqn_not_found_exception.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/locator/locator.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/locator/message_fqn_not_found_exception.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/locator/pypendency/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/locator/pypendency/container_locator.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/locator/pypendency/container_locator_resolution_configuration.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/locator/pypendency/handler_not_found_exception.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/locator/pypendency/handler_not_registered_exception.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/locator/sync/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/locator/sync/handler_already_registered_exception.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/locator/sync/handler_not_registered_exception.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/locator/sync/instance_locator.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/message.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/middleware/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/middleware/middleware.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/middleware/middleware_chain_builder.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/py.typed +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/query/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/query/asynchronous/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/query/asynchronous/base_query_handler.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/query/asynchronous/middleware/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/query/asynchronous/middleware/base_handle_middleware.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/query/asynchronous/middleware/handle_middleware.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/query/asynchronous/middleware/handle_middleware_chain_resolver.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/query/asynchronous/query_bus.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/query/asynchronous/query_handler.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/query/asynchronous/self_process/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/query/asynchronous/self_process/self_process_query_bus.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/query/more_than_one_query_handler_related_exception.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/query/query.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/query/query_response.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/query/synchronous/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/query/synchronous/base_query_handler.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/query/synchronous/middleware/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/query/synchronous/middleware/base_handle_middleware.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/query/synchronous/middleware/handle_middleware.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/query/synchronous/middleware/handle_middleware_chain_resolver.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/query/synchronous/query_bus.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/query/synchronous/query_handler.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/query/synchronous/self_process/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/query/synchronous/self_process/self_process_query_bus.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/query/synchronous/synced_async/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/query/synchronous/synced_async/synced_async_query_bus.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/queue/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/queue/in_memory/in_memory_multiqueue_repository.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/queue/in_memory/in_memory_queue_repository.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/queue/multiqueue_repository.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/queue/queue_repository.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/serializer/message_to_bytes_serializer.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/serializer/message_to_json_bytes_serializer.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/wrapper/__init__.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/wrapper/async_to_sync.py +0 -0
- {buz-2.14.1 → buz-2.14.3}/src/buz/wrapper/event_loop.py +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.1
|
|
2
2
|
Name: buz
|
|
3
|
-
Version: 2.14.
|
|
3
|
+
Version: 2.14.3
|
|
4
4
|
Summary: Buz is a set of light, simple and extensible implementations of event, command and query buses.
|
|
5
5
|
License: MIT
|
|
6
6
|
Author: Luis Pintado Lozano
|
|
@@ -22,6 +22,7 @@ Classifier: Typing :: Typed
|
|
|
22
22
|
Provides-Extra: aiokafka
|
|
23
23
|
Provides-Extra: kombu
|
|
24
24
|
Provides-Extra: pypendency
|
|
25
|
+
Requires-Dist: aiohttp (>=3.11.13,<4.0.0)
|
|
25
26
|
Requires-Dist: aiokafka[lz4] (==0.12.0) ; extra == "aiokafka"
|
|
26
27
|
Requires-Dist: asgiref (>=3.8.1,<4.0.0) ; extra == "aiokafka"
|
|
27
28
|
Requires-Dist: asyncio (>=3.4.3,<4.0.0) ; extra == "aiokafka"
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
[tool.poetry]
|
|
2
2
|
name = "buz"
|
|
3
|
-
version = "2.14.
|
|
3
|
+
version = "2.14.3"
|
|
4
4
|
description = "Buz is a set of light, simple and extensible implementations of event, command and query buses."
|
|
5
5
|
readme = "README.md"
|
|
6
6
|
authors = ["Luis Pintado Lozano <luis.pintado.lozano@gmail.com>", "Gerardo Parra <gprauxiliar@gmail.com>"]
|
|
@@ -31,6 +31,7 @@ asyncio = { version ="^3.4.3", optional = true }
|
|
|
31
31
|
aiokafka = {version = "==0.12.0", extras = ["lz4"], optional = true}
|
|
32
32
|
asgiref = {version = "^3.8.1", optional = true}
|
|
33
33
|
cachetools = "^5.5.0"
|
|
34
|
+
aiohttp = "^3.11.13"
|
|
34
35
|
|
|
35
36
|
[tool.poetry.dev-dependencies]
|
|
36
37
|
black = "^23.3"
|
{buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/buz_kafka/base_buz_aiokafka_async_consumer.py
RENAMED
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import json
|
|
1
2
|
import traceback
|
|
2
3
|
from abc import abstractmethod
|
|
3
4
|
from asyncio import Lock, Task, create_task, gather, Semaphore, Event as AsyncIOEvent, sleep
|
|
@@ -5,6 +6,7 @@ from datetime import timedelta, datetime
|
|
|
5
6
|
from itertools import cycle
|
|
6
7
|
from logging import Logger
|
|
7
8
|
from typing import AsyncIterator, Optional, Sequence, Type, TypeVar
|
|
9
|
+
from aiohttp import web
|
|
8
10
|
|
|
9
11
|
from aiokafka import TopicPartition
|
|
10
12
|
from aiokafka.coordinator.assignors.abstract import AbstractPartitionAssignor
|
|
@@ -43,6 +45,7 @@ class BaseBuzAIOKafkaAsyncConsumer(AsyncConsumer):
|
|
|
43
45
|
kafka_partition_assignors: tuple[Type[AbstractPartitionAssignor], ...] = (),
|
|
44
46
|
subscribers: Sequence[MetaSubscriber],
|
|
45
47
|
logger: Logger,
|
|
48
|
+
health_check_port: Optional[int],
|
|
46
49
|
consumer_initial_offset_position: ConsumerInitialOffsetPosition,
|
|
47
50
|
auto_create_topic_configuration: Optional[AutoCreateTopicConfiguration] = None,
|
|
48
51
|
seconds_between_executions_if_there_are_no_tasks_in_the_queue: int = 1,
|
|
@@ -55,6 +58,7 @@ class BaseBuzAIOKafkaAsyncConsumer(AsyncConsumer):
|
|
|
55
58
|
self.__kafka_partition_assignors = kafka_partition_assignors
|
|
56
59
|
self.__subscribers = subscribers
|
|
57
60
|
self._logger = logger
|
|
61
|
+
self.__health_check_port = health_check_port
|
|
58
62
|
self.__consumer_initial_offset_position = consumer_initial_offset_position
|
|
59
63
|
self.__max_records_retrieved_per_poll = 1
|
|
60
64
|
self.__executor_per_consumer_mapper: dict[AIOKafkaConsumer, KafkaEventSubscriberExecutor] = {}
|
|
@@ -78,12 +82,26 @@ class BaseBuzAIOKafkaAsyncConsumer(AsyncConsumer):
|
|
|
78
82
|
)
|
|
79
83
|
self.__seconds_between_polls_if_there_are_no_new_tasks = seconds_between_polls_if_there_are_no_new_tasks
|
|
80
84
|
self.__polling_tasks_semaphore = Semaphore(max_number_of_concurrent_polling_tasks)
|
|
81
|
-
|
|
82
85
|
self.__task_execution_mutex = Lock()
|
|
83
86
|
|
|
87
|
+
async def configure_health_check_server(self, health_check_port: int) -> web.TCPSite:
|
|
88
|
+
self._logger.info(f"Starting health check server on port {health_check_port}")
|
|
89
|
+
app = web.Application()
|
|
90
|
+
app.router.add_get("/health", lambda request: self.__health_check())
|
|
91
|
+
runner = web.AppRunner(app)
|
|
92
|
+
await runner.setup()
|
|
93
|
+
site = web.TCPSite(runner, "localhost", health_check_port)
|
|
94
|
+
await site.start()
|
|
95
|
+
return site
|
|
96
|
+
|
|
84
97
|
async def run(self) -> None:
|
|
85
98
|
start_time = datetime.now()
|
|
86
99
|
await self.__generate_kafka_consumers()
|
|
100
|
+
health_check_server: Optional[web.TCPSite] = None
|
|
101
|
+
|
|
102
|
+
if self.__health_check_port is not None:
|
|
103
|
+
health_check_server = await self.configure_health_check_server(self.__health_check_port)
|
|
104
|
+
|
|
87
105
|
self.__initial_coroutines_created_elapsed_time = datetime.now() - start_time
|
|
88
106
|
|
|
89
107
|
if len(self.__executor_per_consumer_mapper) == 0:
|
|
@@ -94,6 +112,9 @@ class BaseBuzAIOKafkaAsyncConsumer(AsyncConsumer):
|
|
|
94
112
|
worker_errors = await self.__run_worker()
|
|
95
113
|
self.__events_processed_elapsed_time = datetime.now() - start_consumption_time
|
|
96
114
|
|
|
115
|
+
if health_check_server is not None:
|
|
116
|
+
await health_check_server.stop()
|
|
117
|
+
|
|
97
118
|
await self.__handle_graceful_stop(worker_errors)
|
|
98
119
|
|
|
99
120
|
async def __handle_graceful_stop(self, worker_errors: tuple[Optional[Exception], Optional[Exception]]) -> None:
|
|
@@ -270,6 +291,15 @@ class BaseBuzAIOKafkaAsyncConsumer(AsyncConsumer):
|
|
|
270
291
|
for kafka_consumer in self.__queue_per_consumer_mapper.keys():
|
|
271
292
|
await kafka_consumer.stop()
|
|
272
293
|
|
|
294
|
+
async def __health_check(self) -> web.Response:
|
|
295
|
+
health_information = {
|
|
296
|
+
"subscribers": [subscriber.fqn() for subscriber in self.__subscribers],
|
|
297
|
+
"number_of_subscribers": len(self.__subscribers),
|
|
298
|
+
"event_processed": self.__events_processed,
|
|
299
|
+
}
|
|
300
|
+
|
|
301
|
+
return web.Response(text=json.dumps(health_information), content_type="application/json")
|
|
302
|
+
|
|
273
303
|
def __print_statistics(self) -> None:
|
|
274
304
|
self._logger.info("Number of subscribers: %d", len(self.__subscribers))
|
|
275
305
|
self._logger.info(f"Start kafka consumers elapsed time: {self.__start_kafka_consumers_elapsed_time}")
|
{buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/buz_kafka/buz_aiokafka_async_consumer.py
RENAMED
|
@@ -4,7 +4,6 @@ from typing import Optional, Sequence, Type, TypeVar
|
|
|
4
4
|
from aiokafka.coordinator.assignors.abstract import AbstractPartitionAssignor
|
|
5
5
|
|
|
6
6
|
from buz.event import Event
|
|
7
|
-
|
|
8
7
|
from buz.event.async_subscriber import AsyncSubscriber
|
|
9
8
|
from buz.event.infrastructure.buz_kafka.base_buz_aiokafka_async_consumer import BaseBuzAIOKafkaAsyncConsumer
|
|
10
9
|
from buz.event.infrastructure.buz_kafka.consume_strategy.consume_strategy import KafkaConsumeStrategy
|
|
@@ -15,11 +14,11 @@ from buz.event.meta_subscriber import MetaSubscriber
|
|
|
15
14
|
from buz.event.middleware.async_consume_middleware import AsyncConsumeMiddleware
|
|
16
15
|
from buz.event.strategies.retry.consume_retrier import ConsumeRetrier
|
|
17
16
|
from buz.event.strategies.retry.reject_callback import RejectCallback
|
|
18
|
-
|
|
19
17
|
from buz.kafka.domain.models.auto_create_topic_configuration import AutoCreateTopicConfiguration
|
|
20
18
|
from buz.kafka.domain.models.consumer_initial_offset_position import ConsumerInitialOffsetPosition
|
|
21
19
|
from buz.kafka.domain.models.kafka_connection_config import KafkaConnectionConfig
|
|
22
20
|
from buz.kafka.domain.services.kafka_admin_client import KafkaAdminClient
|
|
21
|
+
from buz.kafka.infrastructure.deserializers.byte_deserializer import ByteDeserializer
|
|
23
22
|
from buz.kafka.infrastructure.deserializers.bytes_to_message_deserializer import BytesToMessageDeserializer
|
|
24
23
|
from buz.kafka.infrastructure.deserializers.implementations.json_bytes_to_message_deserializer import (
|
|
25
24
|
JSONBytesToMessageDeserializer,
|
|
@@ -52,6 +51,7 @@ class BuzAIOKafkaAsyncConsumer(BaseBuzAIOKafkaAsyncConsumer):
|
|
|
52
51
|
seconds_between_polls_if_there_are_tasks_in_the_queue: int = 1,
|
|
53
52
|
seconds_between_polls_if_there_are_no_new_tasks: int = 1,
|
|
54
53
|
max_number_of_concurrent_polling_tasks: int = 20,
|
|
54
|
+
health_check_port: Optional[int] = None,
|
|
55
55
|
):
|
|
56
56
|
super().__init__(
|
|
57
57
|
connection_config=connection_config,
|
|
@@ -68,6 +68,7 @@ class BuzAIOKafkaAsyncConsumer(BaseBuzAIOKafkaAsyncConsumer):
|
|
|
68
68
|
seconds_between_polls_if_there_are_tasks_in_the_queue=seconds_between_polls_if_there_are_tasks_in_the_queue,
|
|
69
69
|
seconds_between_polls_if_there_are_no_new_tasks=seconds_between_polls_if_there_are_no_new_tasks,
|
|
70
70
|
max_number_of_concurrent_polling_tasks=max_number_of_concurrent_polling_tasks,
|
|
71
|
+
health_check_port=health_check_port,
|
|
71
72
|
)
|
|
72
73
|
self.__on_fail_strategy = on_fail_strategy
|
|
73
74
|
self.__consume_middlewares = consume_middlewares
|
|
@@ -84,7 +85,9 @@ class BuzAIOKafkaAsyncConsumer(BaseBuzAIOKafkaAsyncConsumer):
|
|
|
84
85
|
f"Subscriber {subscriber.__class__.__name__} is not a subclass of Subscriber, probably you are trying to use a synchronous subscriber"
|
|
85
86
|
)
|
|
86
87
|
|
|
87
|
-
byte_deserializer = self._deserializers_per_subscriber.get(
|
|
88
|
+
byte_deserializer: ByteDeserializer[Event] = self._deserializers_per_subscriber.get(
|
|
89
|
+
subscriber
|
|
90
|
+
) or JSONBytesToMessageDeserializer(
|
|
88
91
|
# todo: it looks like in next python versions the inference engine is powerful enough to ensure this type, so we can remove it when we upgrade the python version of the library
|
|
89
92
|
event_class=subscriber.handles() # type: ignore
|
|
90
93
|
)
|
|
@@ -19,6 +19,7 @@ from buz.kafka.domain.models.auto_create_topic_configuration import AutoCreateTo
|
|
|
19
19
|
from buz.kafka.domain.models.consumer_initial_offset_position import ConsumerInitialOffsetPosition
|
|
20
20
|
from buz.kafka.domain.models.kafka_connection_config import KafkaConnectionConfig
|
|
21
21
|
from buz.kafka.domain.services.kafka_admin_client import KafkaAdminClient
|
|
22
|
+
from buz.kafka.infrastructure.deserializers.byte_deserializer import ByteDeserializer
|
|
22
23
|
from buz.kafka.infrastructure.deserializers.bytes_to_message_deserializer import BytesToMessageDeserializer
|
|
23
24
|
from buz.kafka.infrastructure.deserializers.implementations.json_bytes_to_message_deserializer import (
|
|
24
25
|
JSONBytesToMessageDeserializer,
|
|
@@ -51,6 +52,7 @@ class BuzAIOKafkaMultiThreadedConsumer(BaseBuzAIOKafkaAsyncConsumer):
|
|
|
51
52
|
seconds_between_polls_if_there_are_tasks_in_the_queue: int = 1,
|
|
52
53
|
seconds_between_polls_if_there_are_no_new_tasks: int = 1,
|
|
53
54
|
max_number_of_concurrent_polling_tasks: int = 20,
|
|
55
|
+
health_check_port: Optional[int] = 3123,
|
|
54
56
|
):
|
|
55
57
|
super().__init__(
|
|
56
58
|
connection_config=connection_config,
|
|
@@ -67,6 +69,7 @@ class BuzAIOKafkaMultiThreadedConsumer(BaseBuzAIOKafkaAsyncConsumer):
|
|
|
67
69
|
seconds_between_polls_if_there_are_tasks_in_the_queue=seconds_between_polls_if_there_are_tasks_in_the_queue,
|
|
68
70
|
seconds_between_polls_if_there_are_no_new_tasks=seconds_between_polls_if_there_are_no_new_tasks,
|
|
69
71
|
max_number_of_concurrent_polling_tasks=max_number_of_concurrent_polling_tasks,
|
|
72
|
+
health_check_port=health_check_port,
|
|
70
73
|
)
|
|
71
74
|
self.__on_fail_strategy = on_fail_strategy
|
|
72
75
|
self.__consume_middlewares = consume_middlewares
|
|
@@ -83,7 +86,9 @@ class BuzAIOKafkaMultiThreadedConsumer(BaseBuzAIOKafkaAsyncConsumer):
|
|
|
83
86
|
f"Subscriber {subscriber.__class__.__name__} is not a subclass of Subscriber, probably you are trying to use an asynchronous subscriber"
|
|
84
87
|
)
|
|
85
88
|
|
|
86
|
-
byte_deserializer = self._deserializers_per_subscriber.get(
|
|
89
|
+
byte_deserializer: ByteDeserializer[Event] = self._deserializers_per_subscriber.get(
|
|
90
|
+
subscriber
|
|
91
|
+
) or JSONBytesToMessageDeserializer(
|
|
87
92
|
# todo: it looks like in next python versions the inference engine is powerful enough to ensure this type, so we can remove it when we upgrade the python version of the library
|
|
88
93
|
event_class=subscriber.handles() # type: ignore
|
|
89
94
|
)
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
class ConsumerRetryException(Exception):
|
|
2
|
+
def __init__(
|
|
3
|
+
self,
|
|
4
|
+
*,
|
|
5
|
+
event_id: str,
|
|
6
|
+
subscriber_fqn: str,
|
|
7
|
+
number_of_executions: int,
|
|
8
|
+
) -> None:
|
|
9
|
+
super().__init__(
|
|
10
|
+
f"An exception happened during the consumption of the event '{event_id}' by the subscriber '{subscriber_fqn}' "
|
|
11
|
+
+ f"during execution number '{number_of_executions}'. Retrying the consumption..."
|
|
12
|
+
)
|
|
@@ -6,6 +6,7 @@ from typing import Optional, Sequence, cast
|
|
|
6
6
|
from buz.event import Event
|
|
7
7
|
from buz.event.async_subscriber import AsyncSubscriber
|
|
8
8
|
from buz.event.infrastructure.buz_kafka.consume_strategy.kafka_on_fail_strategy import KafkaOnFailStrategy
|
|
9
|
+
from buz.event.infrastructure.buz_kafka.exceptions.retry_exception import ConsumerRetryException
|
|
9
10
|
from buz.event.infrastructure.buz_kafka.kafka_event_subscriber_executor import KafkaEventSubscriberExecutor
|
|
10
11
|
from buz.event.middleware.async_consume_middleware import AsyncConsumeMiddleware
|
|
11
12
|
from buz.event.middleware.async_consume_middleware_chain_resolver import AsyncConsumeMiddlewareChainResolver
|
|
@@ -26,7 +27,7 @@ class KafkaEventAsyncSubscriberExecutor(KafkaEventSubscriberExecutor):
|
|
|
26
27
|
logger: Logger,
|
|
27
28
|
consume_middlewares: Optional[Sequence[AsyncConsumeMiddleware]] = None,
|
|
28
29
|
seconds_between_retries: float = 5,
|
|
29
|
-
byte_deserializer: ByteDeserializer,
|
|
30
|
+
byte_deserializer: ByteDeserializer[Event],
|
|
30
31
|
header_deserializer: KafkaHeaderSerializer,
|
|
31
32
|
on_fail_strategy: KafkaOnFailStrategy,
|
|
32
33
|
consume_retrier: Optional[ConsumeRetrier] = None,
|
|
@@ -53,10 +54,17 @@ class KafkaEventAsyncSubscriberExecutor(KafkaEventSubscriberExecutor):
|
|
|
53
54
|
|
|
54
55
|
kafka_record_value = cast(bytes, kafka_poll_record.value)
|
|
55
56
|
|
|
57
|
+
deserialized_value = self.__byte_deserializer.deserialize(kafka_record_value)
|
|
58
|
+
|
|
59
|
+
self.__logger.info(
|
|
60
|
+
f"consuming the event '{deserialized_value.id}' by the subscriber '{self.__subscriber.fqn()}', "
|
|
61
|
+
+ f"topic: '{kafka_poll_record.topic}', partition: '{kafka_poll_record.partition}', offset: '{kafka_poll_record.offset}'"
|
|
62
|
+
)
|
|
63
|
+
|
|
56
64
|
await self.__consumption_callback(
|
|
57
65
|
self.__subscriber,
|
|
58
66
|
KafkaConsumerRecord(
|
|
59
|
-
value=
|
|
67
|
+
value=deserialized_value,
|
|
60
68
|
headers=self.__header_deserializer.deserialize(kafka_poll_record.headers),
|
|
61
69
|
),
|
|
62
70
|
)
|
|
@@ -78,20 +86,28 @@ class KafkaEventAsyncSubscriberExecutor(KafkaEventSubscriberExecutor):
|
|
|
78
86
|
|
|
79
87
|
async def __perform_consume(self, event: Event, subscriber: AsyncSubscriber) -> None:
|
|
80
88
|
should_retry = True
|
|
89
|
+
number_of_executions = 0
|
|
81
90
|
while should_retry is True:
|
|
82
91
|
try:
|
|
92
|
+
number_of_executions += 1
|
|
83
93
|
await subscriber.consume(event)
|
|
84
94
|
return
|
|
85
95
|
except Exception as exception:
|
|
86
|
-
self.__logger.exception(
|
|
87
|
-
f"Event {event.id} could not be consumed by the subscriber, error: {traceback.format_exc()}"
|
|
88
|
-
)
|
|
89
|
-
|
|
90
96
|
if self.__should_retry(event, subscriber) is True:
|
|
97
|
+
self.__logger.warning(
|
|
98
|
+
ConsumerRetryException(
|
|
99
|
+
number_of_executions=number_of_executions,
|
|
100
|
+
event_id=event.id,
|
|
101
|
+
subscriber_fqn=subscriber.fqn(),
|
|
102
|
+
),
|
|
103
|
+
exc_info=exception,
|
|
104
|
+
)
|
|
91
105
|
self.__register_retry(event, subscriber)
|
|
92
106
|
await sleep(self.__seconds_between_retires)
|
|
93
107
|
continue
|
|
94
108
|
|
|
109
|
+
self.__logger.exception(exception)
|
|
110
|
+
|
|
95
111
|
if self.__reject_callback:
|
|
96
112
|
self.__reject_callback.on_reject(event=event, subscribers=[subscriber], exception=exception)
|
|
97
113
|
|
|
@@ -4,6 +4,7 @@ import time
|
|
|
4
4
|
from typing import Optional, Sequence, cast
|
|
5
5
|
from buz.event import Event
|
|
6
6
|
from buz.event.infrastructure.buz_kafka.consume_strategy.kafka_on_fail_strategy import KafkaOnFailStrategy
|
|
7
|
+
from buz.event.infrastructure.buz_kafka.exceptions.retry_exception import ConsumerRetryException
|
|
7
8
|
from buz.event.infrastructure.buz_kafka.kafka_event_subscriber_executor import KafkaEventSubscriberExecutor
|
|
8
9
|
from buz.event.middleware.consume_middleware import ConsumeMiddleware
|
|
9
10
|
from buz.event.middleware.consume_middleware_chain_resolver import ConsumeMiddlewareChainResolver
|
|
@@ -25,7 +26,7 @@ class KafkaEventSyncSubscriberExecutor(KafkaEventSubscriberExecutor):
|
|
|
25
26
|
logger: Logger,
|
|
26
27
|
consume_middlewares: Optional[Sequence[ConsumeMiddleware]] = None,
|
|
27
28
|
seconds_between_retries: float = 5,
|
|
28
|
-
byte_deserializer: ByteDeserializer,
|
|
29
|
+
byte_deserializer: ByteDeserializer[Event],
|
|
29
30
|
header_deserializer: KafkaHeaderSerializer,
|
|
30
31
|
on_fail_strategy: KafkaOnFailStrategy,
|
|
31
32
|
consume_retrier: Optional[ConsumeRetrier] = None,
|
|
@@ -52,12 +53,19 @@ class KafkaEventSyncSubscriberExecutor(KafkaEventSubscriberExecutor):
|
|
|
52
53
|
|
|
53
54
|
kafka_record_value = cast(bytes, kafka_poll_record.value)
|
|
54
55
|
|
|
56
|
+
deserialized_value = self.__byte_deserializer.deserialize(kafka_record_value)
|
|
57
|
+
|
|
58
|
+
self.__logger.info(
|
|
59
|
+
f"consuming the event '{deserialized_value.id}' by the subscriber '{self.__subscriber.fqn()}', "
|
|
60
|
+
+ f"topic: '{kafka_poll_record.topic}', partition: '{kafka_poll_record.partition}', offset: '{kafka_poll_record.offset}'"
|
|
61
|
+
)
|
|
62
|
+
|
|
55
63
|
await get_running_loop().run_in_executor(
|
|
56
64
|
None,
|
|
57
65
|
lambda: self.__execution_callback(
|
|
58
66
|
self.__subscriber,
|
|
59
67
|
KafkaConsumerRecord(
|
|
60
|
-
value=
|
|
68
|
+
value=deserialized_value,
|
|
61
69
|
headers=self.__header_deserializer.deserialize(kafka_poll_record.headers),
|
|
62
70
|
),
|
|
63
71
|
),
|
|
@@ -75,13 +83,22 @@ class KafkaEventSyncSubscriberExecutor(KafkaEventSubscriberExecutor):
|
|
|
75
83
|
|
|
76
84
|
def __perform_consume(self, event: Event, subscriber: Subscriber) -> None:
|
|
77
85
|
should_retry = True
|
|
86
|
+
execution_number = 0
|
|
78
87
|
while should_retry is True:
|
|
79
88
|
try:
|
|
89
|
+
execution_number += 1
|
|
80
90
|
subscriber.consume(event)
|
|
81
91
|
return
|
|
82
92
|
except Exception as exception:
|
|
83
|
-
self.__logger.warning(f"Event {event.id} could not be consumed by the subscriber {subscriber.fqn}")
|
|
84
93
|
if self.__should_retry(event, subscriber) is True:
|
|
94
|
+
self.__logger.warning(
|
|
95
|
+
ConsumerRetryException(
|
|
96
|
+
number_of_executions=execution_number,
|
|
97
|
+
event_id=event.id,
|
|
98
|
+
subscriber_fqn=subscriber.fqn(),
|
|
99
|
+
),
|
|
100
|
+
exc_info=exception,
|
|
101
|
+
)
|
|
85
102
|
self.__register_retry(event, subscriber)
|
|
86
103
|
time.sleep(self.__seconds_between_retires)
|
|
87
104
|
continue
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
from abc import ABC, abstractmethod
|
|
2
|
-
from typing import Awaitable, Union
|
|
2
|
+
from typing import Awaitable, Type, Union
|
|
3
3
|
|
|
4
4
|
from buz import Handler
|
|
5
5
|
from buz.event import Event
|
|
@@ -9,3 +9,8 @@ class MetaSubscriber(Handler, ABC):
|
|
|
9
9
|
@abstractmethod
|
|
10
10
|
def consume(self, event: Event) -> Union[None, Awaitable[None]]:
|
|
11
11
|
pass
|
|
12
|
+
|
|
13
|
+
@classmethod
|
|
14
|
+
@abstractmethod
|
|
15
|
+
def handles(cls) -> Type[Event]:
|
|
16
|
+
pass
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
from __future__ import annotations
|
|
2
|
+
|
|
3
|
+
|
|
4
|
+
class NotAllPartitionAssignedException(Exception):
|
|
5
|
+
def __init__(
|
|
6
|
+
self,
|
|
7
|
+
*,
|
|
8
|
+
topic_name: str,
|
|
9
|
+
consumer_group: str,
|
|
10
|
+
) -> None:
|
|
11
|
+
super().__init__(
|
|
12
|
+
f'Not all the partitions in the consumer group "{consumer_group}" were assigned in the topic "{topic_name}". Please disconnect the rest of subscribers'
|
|
13
|
+
)
|
{buz-2.14.1 → buz-2.14.3}/src/buz/kafka/infrastructure/kafka_python/kafka_python_admin_client.py
RENAMED
|
@@ -228,7 +228,10 @@ class KafkaPythonAdminClient(KafkaAdminClient):
|
|
|
228
228
|
|
|
229
229
|
# We need all the partitions in order to update the offsets
|
|
230
230
|
if len(consumer.assignment()) != len(topic_partitions):
|
|
231
|
-
raise NotAllPartitionAssignedException(
|
|
231
|
+
raise NotAllPartitionAssignedException(
|
|
232
|
+
topic_name=topic,
|
|
233
|
+
consumer_group=consumer_group,
|
|
234
|
+
)
|
|
232
235
|
|
|
233
236
|
# This could produce a race condition, but it is a limitation of kafka admin (we are not able to check if all the partition are assigned using the manual assignment)
|
|
234
237
|
# https://github.com/dpkp/kafka-python/blob/master/kafka/consumer/group.py#L430
|
|
@@ -1,8 +0,0 @@
|
|
|
1
|
-
from __future__ import annotations
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
class NotAllPartitionAssignedException(Exception):
|
|
5
|
-
def __init__(self, topic_name: str) -> None:
|
|
6
|
-
super().__init__(
|
|
7
|
-
f'Not all the partition were assigned for the topic "{topic_name}", please disconnect the rest of subscribers'
|
|
8
|
-
)
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{buz-2.14.1 → buz-2.14.3}/src/buz/command/asynchronous/self_process/self_process_command_bus.py
RENAMED
|
File without changes
|
|
File without changes
|
{buz-2.14.1 → buz-2.14.3}/src/buz/command/more_than_one_command_handler_related_exception.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{buz-2.14.1 → buz-2.14.3}/src/buz/command/synchronous/middleware/handle_middleware_chain_resolver.py
RENAMED
|
File without changes
|
|
File without changes
|
{buz-2.14.1 → buz-2.14.3}/src/buz/command/synchronous/self_process/self_process_command_bus.py
RENAMED
|
File without changes
|
|
File without changes
|
{buz-2.14.1 → buz-2.14.3}/src/buz/command/synchronous/synced_async/synced_async_command_bus.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/buz_kafka/async_buz_kafka_event_bus.py
RENAMED
|
File without changes
|
|
File without changes
|
{buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/buz_kafka/consume_strategy/__init__.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/buz_kafka/kafka_event_subscriber_executor.py
RENAMED
|
File without changes
|
{buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/buz_kafka/publish_strategy/__init__.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/kombu/consume_strategy/consume_strategy.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/kombu/publish_strategy/publish_strategy.py
RENAMED
|
File without changes
|
|
File without changes
|
{buz-2.14.1 → buz-2.14.3}/src/buz/event/infrastructure/kombu/retry_strategy/publish_retry_policy.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{buz-2.14.1 → buz-2.14.3}/src/buz/event/middleware/async_consume_middleware_chain_resolver.py
RENAMED
|
File without changes
|
|
File without changes
|
{buz-2.14.1 → buz-2.14.3}/src/buz/event/middleware/async_publish_middleware_chain_resolver.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{buz-2.14.1 → buz-2.14.3}/src/buz/event/middleware/exceptions/event_already_in_progress_exception.py
RENAMED
|
File without changes
|