Skip to main content

A Python SDK for backend systems development @midil.io

Project description

Midil Kit

A comprehensive Python SDK for backend systems development at midil.io. This library provides a rich set of tools for building modern, scalable backend applications with support for authentication, event handling, HTTP clients, and JSON:API compliance.

✨ Features

🔐 Authentication & Authorization

  • JWT Authorization: Comprehensive JWT token verification and validation
  • AWS Cognito Integration: Ready-to-use Cognito client credentials flow and JWT authorizer
  • Pluggable Auth Providers: Abstract interfaces for custom authentication implementations
  • FastAPI Middleware: Built-in authentication middleware for FastAPI applications

📡 Event System

  • Event Dispatching: Abstract event dispatcher with polling and AWS integrations
  • SQS Consumer: AWS SQS message consumption with automatic retry and context handling
  • Event Scheduling: AWS EventBridge integration and periodic task scheduling
  • Event Context: Distributed tracing and context management for events

🌐 HTTP Client

  • Enhanced HTTP Client: HTTPX-based client with authentication integration
  • Retry Logic: Configurable retry strategies with exponential backoff and jitter
  • Transport Layer: Custom transport with comprehensive error handling
  • Auth Integration: Seamless integration with authentication providers

📋 JSON:API Compliance

  • Document Creation: Full JSON:API compliant document creation and validation
  • Resource Management: Type-safe resource objects with relationships
  • Query Parameters: Parsing and validation of JSON:API query parameters (sort, include, pagination)
  • Error Handling: Standardized JSON:API error document creation

🚀 Framework Extensions

  • FastAPI Integration: Authentication middleware and JSON:API dependencies
  • Type Safety: Full type hints throughout with Pydantic models
  • Async Support: Native async/await support across all components

📦 Installation

Using Poetry (Recommended)

poetry add midil-kit

Using pip

pip install midil-kit

Optional Dependencies

The library supports optional feature sets through extras:

# Web framework extensions (FastAPI)
poetry add midil-kit[fastapi]

# Authentication providers (JWT, Cognito)
poetry add midil-kit[auth]

# AWS event services (SQS, EventBridge)
poetry add midil-kit[event]

# AWS infrastructure (auth + event)
poetry add midil-kit[aws]

# All optional dependencies
poetry add midil-kit[all]

🚀 Quick Start

Authentication with Cognito

from midil.auth.cognito import CognitoClientCredentialsAuthClient, CognitoJWTAuthorizer

# Authentication client for outbound requests
auth_client = CognitoClientCredentialsAuthClient(
    client_id="your-client-id",
    client_secret="your-client-secret",
    cognito_domain="your-domain.auth.region.amazoncognito.com"
)

# Get access token
token = await auth_client.get_token()
headers = await auth_client.get_headers()

# JWT authorizer for inbound requests
authorizer = CognitoJWTAuthorizer(
    user_pool_id="your-user-pool-id",
    region="us-east-1"
)

# Verify incoming token
claims = await authorizer.verify("jwt-token")

Event System

from midil.event.dispatchers.polling import PollingEventDispatcher
from midil.event.consumers.sqs import run_sqs_consumer
from midil.event.context import event_context

# Event dispatcher
dispatcher = PollingEventDispatcher()

# Register event handlers
@dispatcher.on("user.created")
async def handle_user_created(event: str, body: dict):
    print(f"User created: {body['user_id']}")

# Start event processing
await dispatcher.start_event_processor()

# Send events
await dispatcher.notify("user.created", {"user_id": "123"})

# SQS consumer
await run_sqs_consumer(
    queue_url="https://sqs.region.amazonaws.com/account/queue-name",
    region_name="us-east-1"
)

HTTP Client with Authentication

from midil.http import HttpClient
from midil.auth.cognito import CognitoClientCredentialsAuthClient
from httpx import URL

# Create authenticated HTTP client
auth_client = CognitoClientCredentialsAuthClient(...)
http_client = HttpClient(
    auth_client=auth_client,
    base_url=URL("https://api.example.com")
)

# Make authenticated requests
response = await http_client.send_request(
    method="POST",
    url="/users",
    data={"name": "John Doe"}
)

JSON:API Documents

from midil.jsonapi import JSONAPIDocument, ResourceObject, ErrorObject

# Create a resource document
resource = ResourceObject(
    id="1",
    type="articles",
    attributes={"title": "JSON:API with Midil Kit", "content": "..."}
)

document = JSONAPIDocument(data=resource)

# Create error documents
error = ErrorObject(
    status="422",
    title="Validation Error",
    detail="Title is required"
)

error_document = JSONAPIDocument(errors=[error])

FastAPI Integration

from fastapi import FastAPI, Depends
from midil.extensions.fastapi.middleware.auth_middleware import CognitoAuthMiddleware
from midil.extensions.fastapi.dependencies.jsonapi import parse_sort, parse_include

app = FastAPI()

# Add authentication middleware
app.add_middleware(CognitoAuthMiddleware)

# JSON:API query parameter parsing
@app.get("/articles")
async def list_articles(
    sort=Depends(parse_sort),
    include=Depends(parse_include)
):
    return {"data": [], "meta": {"sort": sort, "include": include}}

# Access authenticated user
def get_auth(request):
    return request.state.auth

@app.get("/me")
async def get_current_user(auth=Depends(get_auth)):
    return {"user_id": auth.claims.sub}

📚 API Reference

Authentication Module (midil.auth)

Core Interfaces

  • AuthNProvider: Abstract authentication provider for outbound requests
  • AuthZProvider: Abstract authorization provider for inbound token verification
  • AuthNToken: Token model with expiration handling
  • AuthZTokenClaims: Token claims model

Cognito Implementation

  • CognitoClientCredentialsAuthClient: OAuth2 client credentials flow
  • CognitoJWTAuthorizer: JWT token verification for Cognito

Event Module (midil.event)

Dispatchers

  • AbstractEventDispatcher: Base event dispatcher with memory queue
  • PollingEventDispatcher: In-memory event dispatcher with observer pattern

Consumers

  • SQSEventConsumer: AWS SQS message consumer with retry logic

Schedulers

  • AWSEventBridgeClient: EventBridge integration for scheduled events
  • PeriodicTask: Periodic task execution with customizable strategies

Context Management

  • EventContext: Event tracing and context management
  • event_context(): Async context manager for event scoping

HTTP Module (midil.http)

Client

  • HttpClient: Enhanced HTTP client with auth integration
  • MidilAsyncClient: Custom HTTPX client with retry transport

Retry System

  • RetryTransport: Configurable retry transport layer
  • DefaultRetryStrategy: Standard retry strategy implementation
  • ExponentialBackoffWithJitter: Backoff strategy with jitter

JSON:API Module (midil.jsonapi)

Document Models

  • JSONAPIDocument: Main document container
  • ResourceObject: Resource representation with attributes and relationships
  • ErrorObject: Error representation
  • QueryParams: Query parameter parsing and validation

Utilities

  • Sort, Include, PaginationParams: Query parameter models

Extensions Module (midil.extensions)

FastAPI Integration

  • BaseAuthMiddleware: Base authentication middleware
  • CognitoAuthMiddleware: Cognito-specific middleware
  • AuthContext: Request authentication context
  • parse_sort(), parse_include(): JSON:API query parameter dependencies

🛠️ Development

Prerequisites

  • Python 3.12+
  • Poetry for dependency management

Setup

  1. Clone the repository:
git clone <repository-url>
cd midil-kit
  1. Install dependencies:
make install
  1. Install pre-commit hooks:
make pre-commit-install

Development Commands

# Run tests
make test

# Run tests with coverage
make test-cov

# Lint code
make lint

# Format code
make format

# Type checking
make type-check

# Run all checks
make check

# Clean build artifacts
make clean

# Build package
make build

Changelog Management

The project uses towncrier for changelog management:

# Create a changelog entry
make changelog-draft

# Preview changelog changes
make changelog-preview

# Update changelog
make changelog

# Prepare a new release
make release

Testing

# Run all tests
poetry run pytest

# Run with coverage
poetry run pytest --cov=midil --cov-report=html

# Run specific test file
poetry run pytest tests/auth/test_cognito.py

Code Quality

The project enforces code quality through:

  • Black: Code formatting
  • Ruff: Fast Python linter
  • MyPy: Static type checking
  • Pre-commit hooks: Automated quality checks

🏗️ Architecture

Modular Design

Midil Kit follows a modular architecture:

midil/
├── auth/           # Authentication & authorization
├── event/          # Event system & messaging
├── http/           # HTTP client & retry logic
├── jsonapi/        # JSON:API compliance
└── extensions/     # Framework integrations
    └── fastapi/    # FastAPI-specific extensions

Design Principles

  • Type Safety: Comprehensive type hints using Pydantic models
  • Async First: Native async/await support throughout
  • Pluggable: Abstract interfaces for custom implementations
  • Framework Agnostic: Core functionality independent of web frameworks
  • AWS Native: First-class support for AWS services

🤝 Contributing

  1. Fork the repository
  2. Create a feature branch (git checkout -b feature/amazing-feature)
  3. Make your changes
  4. Add tests for new functionality
  5. Ensure all tests pass (make check)
  6. Create a changelog entry (make changelog-draft)
  7. Commit your changes (git commit -m 'feat: add amazing feature')
  8. Push to the branch (git push origin feature/amazing-feature)
  9. Open a Pull Request

Commit Message Format

This project follows Conventional Commits:

<type>(<scope>): <description>

[optional body]

[optional footer(s)]

Types:

  • feat: A new feature
  • fix: A bug fix
  • docs: Documentation only changes
  • style: Changes that do not affect the meaning of the code
  • refactor: A code change that neither fixes a bug nor adds a feature
  • test: Adding missing tests or correcting existing tests
  • chore: Changes to the build process or auxiliary tools

Scopes:

  • auth: Authentication & authorization
  • event: Event system
  • http: HTTP client
  • jsonapi: JSON:API functionality
  • extensions: Framework extensions
  • docs: Documentation
  • ci: Continuous integration

Examples:

feat(auth): add support for refresh tokens
fix(event): resolve memory leak in event dispatcher
docs: update installation instructions
test(jsonapi): add tests for error document creation

📄 License

This project is licensed under the Apache License 2.0 - see the LICENSE file for details.

🔄 Changelog

See CHANGELOG.md for a detailed history of changes.

Recent Releases

  • v3.0.0 - Breaking changes with improved naming conventions and PATCH/POST resource compliance
  • v2.1.0 - Infrastructure packages, FastAPI extensions, and improved interfaces
  • v2.0.0 - Major architectural improvements with auth, http, and event modules

🆘 Support


Built with ❤️ by the Midil.io team for the Python backend development community.

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

midil_kit-3.0.0.tar.gz (32.6 kB view details)

Uploaded Source

Built Distribution

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

midil_kit-3.0.0-py3-none-any.whl (39.7 kB view details)

Uploaded Python 3

File details

Details for the file midil_kit-3.0.0.tar.gz.

File metadata

  • Download URL: midil_kit-3.0.0.tar.gz
  • Upload date:
  • Size: 32.6 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: poetry/2.0.1 CPython/3.13.2 Darwin/24.3.0

File hashes

Hashes for midil_kit-3.0.0.tar.gz
Algorithm Hash digest
SHA256 cbc07b0cc567adeffb51c3876b253e1f8bb9c71410859fefea2f337be1c69be2
MD5 a89ae20bc90013fcbbf2f589939939cb
BLAKE2b-256 6cb7ba57cf43dbafc6d8234e6a64b677c48c4c64332c51d542582cb033eb8d4f

See more details on using hashes here.

File details

Details for the file midil_kit-3.0.0-py3-none-any.whl.

File metadata

  • Download URL: midil_kit-3.0.0-py3-none-any.whl
  • Upload date:
  • Size: 39.7 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: poetry/2.0.1 CPython/3.13.2 Darwin/24.3.0

File hashes

Hashes for midil_kit-3.0.0-py3-none-any.whl
Algorithm Hash digest
SHA256 53e15c464436d2e4ead4a774cf521125ed5d9297317d515160a90cf3f6749759
MD5 2b0eb82342a3c8f3e3dcdc29387d1694
BLAKE2b-256 8f0eafff4149891877d45b6d0f9661bd0efdf8e940595cf5c3713fe7af621549

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