Skip to main content

Extra check using pydandic in flask application

Project description

Publish to PyPI

PyPI version License Swagger UI

FlaskNova

A modern and lightweight extension for Flask that brings FastAPI-style features like automatic OpenAPI schema, Swagger UI, request validation, typed routing, and structured responses.


🚀 Features

  • ✅ Automatic OpenAPI 3.0 schema generation
  • ✅ Built-in Swagger UI at /docs (configurable)
  • ✅ Request validation using Pydantic models
  • ✅ Response model serialization (Pydantic, dataclass, or custom class with to_dict)
  • ✅ Docstring-based or keyword-based summary and description for endpoints
  • ✅ Typed URL parameters (<int:id>, <uuid:id>, etc.)
  • ✅ Customizable Swagger UI route path and OpenAPI metadata
  • ✅ Configurable via FLASKNOVA_SWAGGER_ENABLED and FLASKNOVA_SWAGGER_ROUTE
  • ✅ Clean modular routing with NovaBlueprint
  • ✅ Built-in HTTP status codes (flasknova.status)
  • ✅ Optional JWT auth and dependency injection helpers
  • ✅ Minimal boilerplate and highly extensible

Table of Contents


Why FlaskNova?

FlaskNova brings modern API development to Flask with:

  • Automatic OpenAPI/Swagger UI: Instantly document and test your API.
  • Flexible serialization: Use Pydantic, dataclasses, or custom classes (with type hints) for both requests and responses.
  • Dependency injection: Cleaner, more testable route logic.
  • Unified error handling and status codes: Consistent, readable, and robust.
  • Production-ready logging: Built-in, unified logger for your whole app.
  • Minimal boilerplate: Focus on your business logic, not plumbing.

FlaskNova is ideal for teams and solo developers who want the power of modern Python API frameworks—without leaving Flask.


Features

  • Swagger UI: FlaskNova includes automatic Swagger UI documentation for your API. Once your app is running, visit flasknova/docs in your browser to explore and test your endpoints interactively.

  • Flexible Serialization: Validate incoming request data and serialize responses using Pydantic models. For responses, you can return Pydantic models, dataclasses, dictionaries, or objects with a to_dict()/dict()/dump() method. Marshmallow schemas and custom classes with a serialization method are also supported for response serialization. If you use a custom class, you must implement a to_dict, dict, or dump method—otherwise, FlaskNova will not be able to serialize your object.

  • Dependency Injection: Use the Depend helper to inject dependencies into your route handlers.

  • Status Codes: Use the status module for readable HTTP status codes (e.g., status.OK, status.UNPROCESSABLE_ENTITY).

  • Custom HTTP Exceptions: Raise HTTPException or ResponseValidationError for consistent error responses.

  • Blueprint Support: Use NovaBlueprint for modular route organization.


Installation

pip install flask-nova 

Quick Example

from flasknova import FlaskNova, NovaBlueprint, status
from pydantic import BaseModel

app = FlaskNova(__name__)
api = NovaBlueprint("api", __name__)

class User(BaseModel):
    username: str
    email: str

@api.route("/users", methods=["POST"], response_model=User, summary="Create a new user", description="Accepts user data and returns the created user.")
def create_user(data: User):
    return data, status.CREATED

app.register_blueprint(api)

if __name__ == "__main__":
    app.setup_swagger()
    app.run(debug=True)

Go to http://localhost:5000/docs to try it out in Swagger UI.


📝 Route Documentation Options

You can describe endpoints in two ways:

✅ Using summary and description keyword arguments:

@api.route("/hello", summary="Say hello", description="Returns a greeting message.")
def hello():
    return {"msg": "Hello!"}

✅ Or using a docstring:

@api.route("/hello")
def hello():
    """Say hello.

    Returns a greeting message to the user.
    """
    return {"msg": "Hello!"}

If both are provided, FlaskNova prefers summary and description, falling back to the docstring if missing.


🔀 Typed URL Parameters

Use Flask-style parameters with automatic OpenAPI type mapping:

@api.route("/users/<int:user_id>", methods=["GET"])
def get_user(user_id: int):
    ...

Supported converters: int, float, uuid, path, string (default).


🧪 Enabling Swagger UI

FlaskNova automatically mounts Swagger UI when app.setup_swagger() is called:

if __name__ == "__main__":
    app.setup_swagger()
    app.run(debug=True)

🔧 Environment Configuration

You can control Swagger UI using environment variables:

Variable Default Description
FLASKNOVA_SWAGGER_ENABLED True Disable Swagger UI entirely if set to False
FLASKNOVA_SWAGGER_ROUTE /docs Change the Swagger UI mount path

Example using a .env file:

FLASKNOVA_SWAGGER_ENABLED=True
FLASKNOVA_SWAGGER_ROUTE=/api/docs

🛠️ Customizing OpenAPI Metadata

You can also pass metadata via setup_swagger():

app.setup_swagger(
    mount_path="/docs",
    openapi_url="/openapi.json",
    info={
        "title": "My API",
        "version": "2.0.1",
        "description": "Modern Flask API.",
        "contact": {"name": "Dev Team", "email": "hello@example.com"},
        "license": {"name": "MIT", "url": "https://opensource.org/licenses/MIT"}
    }
)

🔁 Response Models

Supported response types:

  • ✅ Pydantic models
  • ✅ Dataclasses
  • ✅ Custom classes (must implement to_dict() or dict())
@dataclasses.dataclass
class User:
    id: int
    name: str

@api.route("/me", response_model=User)
def get_profile():
    return {"id"=1, "name"="nova"}

from typing import List
@api.route('/pyduser', methods=['GET'], response_model=List[UserSchema], tags=["Pydantic"])
def list_pydusers():
    return users.values()

app.register_blueprint(api)

Custom Class Example (with Type Hints)

from flasknova import FlaskNova, NovaBlueprint, status, HTTPException

app = FlaskNova(__name__)
api = NovaBlueprint('api', __name__)

# IMPORTANT: You must add class-level type hints for OpenAPI/Swagger UI to show fields!
class CustomUser:
    id: int
    name: str
    email: str

    def to_dict(self):
        return {"id": self.id, "name": self.name, "email": self.email}

users = {}

@api.route('/customuser', methods=['POST'])
def create_customuser(data: CustomUser):
    users[data.id] = data
    return data, status.CREATED

@api.route('/customuser/<int:user_id>', methods=['GET'])
def get_customuser(user_id: int):
    user = users.get(user_id)
    if not user:
        raise HTTPException(status_code=status.NOT_FOUND, detail="User not found", title="Not Found")
    return user
from typing import List
@api.route('/customuser', methods=['GET'], response_model=List[CustomUser], tags=["Custom"])
def list_customusers():
    return users.values()

app.register_blueprint(api)

Dataclass Example

from flasknova import FlaskNova, NovaBlueprint, status, HTTPException
import dataclasses

app = FlaskNova(__name__)
api = NovaBlueprint('api', __name__)

@dataclasses.dataclass
class DCUser:
    id: int
    name: str
    email: str

users = {}

@api.route('/dcuser', methods=['POST'])
def create_dcuser(data: DCUser):
    users[data.id] = data
    return data, status.CREATED

@api.route('/dcuser/<int:user_id>', methods=['GET'])
def get_dcuser(user_id: int):
    user = users.get(user_id)
    if not user:
        raise HTTPException(status_code=status.NOT_FOUND, detail="User not found", title="Not Found")
    return user
from typing import List
@api.route('/dcuser', methods=['GET'], response_model=List[DCUser], tags=["Dataclass"])
def list_dcusers():
    return users.values()

app.register_blueprint(api)

Status Codes

Use the status module for readable status codes:

from flasknova import status

print(status.OK)  # 200
print(status.UNPROCESSABLE_ENTITY)  # 422

Error Handling

Raise HTTPException or ResponseValidationError for custom error responses:

from flasknova import HTTPException, status

raise HTTPException(
    status_code=status.NOT_FOUND,
    detail="User not found",
    title="Not Found"
)

Supported request/response types:

  • Pydantic models: Full request validation and schema generation.
  • Dataclasses: Fields and types are shown in Swagger UI (converted to Pydantic models under the hood).
  • Custom classes: Fields are shown in Swagger UI if you add class-level type hints (see above). Type hints in __init__ are not enough!
  • Marshmallow schemas: Supported for response serialization only (not for request validation or OpenAPI schema generation).
  • Dictionaries and objects with a to_dict(), dict(), or dump() method: Supported for response serialization.

Type Hints are Required for OpenAPI!

If you want your custom class or dataclass fields to appear in Swagger UI, you must add class-level type hints:

class MyCustom:
    id: int
    name: str
    # ...

If you only add type hints in __init__, they will NOT be detected for OpenAPI schema generation.

Example:

class Bad:
    def __init__(self, id: int):
        self.id = id  # <-- This will NOT show up in Swagger UI!

Response Serialization & Custom Responses

FlaskNova automatically serializes your route responses using Pydantic models. For responses, you may also return dataclasses, dictionaries, or objects with a to_dict()/dict()/dump() method, or Marshmallow schemas—these will be serialized to JSON.

You can still return Flask make_response objects directly from your route handlers, giving you full control over headers, cookies, and advanced response customization when needed.

Examples:

from flask import make_response, jsonify

@api.route('/custom', methods=["GET"])
def custom():
    data = {"message": "Custom response"}
    response = make_response(jsonify(data), 201)
    response.headers['X-Custom-Header'] = 'Value'
    return response

If you return a Flask Response (such as from make_response), FlaskNova will pass it through untouched. Otherwise, it will serialize your data and wrap it in a proper JSON response with the correct status code.


Logging

Access the unified logger:

from flasknova import logger
logger.info("FlaskNova app started!")

FAQ

Why don't my custom class fields appear in Swagger UI?

You must add class-level type hints . Example:

class MyCustom:
    id: int
    name: str
Why does my dataclass or custom class not validate requests?

Only Pydantic models are used for request validation. Dataclasses and custom classes are supported for schema generation and response serialization, but not for request validation.

Can I use Marshmallow schemas for request validation?

No, Marshmallow schemas are only supported for response serialization, not for request validation or OpenAPI schema generation.

How do I customize the Swagger UI or OpenAPI output?

You can extend FlaskNova or open an issue/feature request on GitHub for advanced customization needs.

My schema is empty or missing fields!

Make sure your class is fully imported and all fields have type hints at the class level. If you still have issues, check the logs for warnings.

How do I contribute a new feature or fix a bug?
  1. Fork the repository and create a new branch from main for your feature or fix.
  2. Write clear, well-tested code that follows the existing style. Add or update tests and documentation as needed.
  3. Commit your changes with descriptive messages.
  4. Push your branch to your fork and open a pull request (PR) against the main repository.
  5. In your PR, describe your changes, reference any related issues, and explain any design decisions.
  6. Participate in code review and update your PR as needed.

For questions or suggestions, open an issue on GitHub.

Showcase: Real-world usage or integrations

FlaskNova is designed to be flexible and production-ready. Here are some ways you can use it in real projects:

  • Internal APIs: Build robust internal tools or microservices with automatic docs and validation.
  • Public APIs: Ship developer-friendly APIs with interactive Swagger UI and clear error handling.
  • Integrations: Use FlaskNova with Flask extensions (e.g., Flask-JWT-Extended for auth, Flask-CORS for cross-origin support).
  • Recipes:
    • Authentication: Use dependency injection to inject user/session objects into your routes.
    • Custom serialization: Return dataclasses, custom classes, or Pydantic models for flexible responses.
    • Advanced OpenAPI: Add tags, descriptions, and examples to your endpoints for richer docs.

If you use FlaskNova in your project, consider sharing your experience or opening a PR to add your project to this showcase!

📖 Learn More


📚 License

MIT License


🤝 Contributing

Contributions are welcome!

  • Fork the repo, create your branch from main
  • Write tests and keep code clean
  • Open a PR with a clear explanation

Open issues or feature requests on GitHub.


📦 PyPI Release

The latest version is available here:

🔗 FlaskNova on PyPI
🔗 GitHub Release Notes

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

flask_nova-0.1.0.tar.gz (18.3 kB view details)

Uploaded Source

Built Distribution

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

flask_nova-0.1.0-py3-none-any.whl (16.2 kB view details)

Uploaded Python 3

File details

Details for the file flask_nova-0.1.0.tar.gz.

File metadata

  • Download URL: flask_nova-0.1.0.tar.gz
  • Upload date:
  • Size: 18.3 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: poetry/2.1.3 CPython/3.13.5 Windows/10

File hashes

Hashes for flask_nova-0.1.0.tar.gz
Algorithm Hash digest
SHA256 0c2f34015e2a3b57c407d32911fe130b9c8c954b78749253956dd9ae8e990bd6
MD5 03ae72ef914c940cf176062d1cccd864
BLAKE2b-256 f1484f63101932e3ba195bcd4cbf3e21be244195b72403d75cfe028a02444264

See more details on using hashes here.

File details

Details for the file flask_nova-0.1.0-py3-none-any.whl.

File metadata

  • Download URL: flask_nova-0.1.0-py3-none-any.whl
  • Upload date:
  • Size: 16.2 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: poetry/2.1.3 CPython/3.13.5 Windows/10

File hashes

Hashes for flask_nova-0.1.0-py3-none-any.whl
Algorithm Hash digest
SHA256 8bdb666519074b06420b01ca33abf7df3d0cd915e916e77e4ec58d0e65b4b95b
MD5 ccacccdbf15c28d2c012e4d8e73c6a95
BLAKE2b-256 5f09d25b99949dd645601c7af3a046f5778ac5b55eb5ce6d387c0c5a8fcb18c1

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