A package to define interface in Python
Project description
interface-py
interface-py is a lightweight Python package for defining interfaces and concrete implementations with enforced contracts.
It ensures that concrete classes implement all required methods, properties, and fields, including validation for empty or invalid property getters.
Features
- Define interfaces using the
@interfacedecorator. - Enforce that concrete classes implement all interface methods, fields, and properties.
- Detects and enforces rules for empty, explicit, and invalid getters/setters.
- Support for fields with four declaration styles:
- With annotation only →
x: int - With annotation +
...→y: float = ... - Without annotation +
...→z = ... - With direct type assignment →
DataModel = dictor any other type/class
- With annotation only →
- Ensures that property getters defined explicitly in interfaces always raise an error.
- Allows defining properties in interfaces with empty bodies (
...,pass, or docstring-only`). - Enforce getter, setter, and deleter implementation rules for properties.
- Supports multi-level interface hierarchies with automatic contract aggregation.
- Prevents runtime errors from missing implementations.
- Works alongside Python's built-in ABCs.
Installation
pip install interface-py
Usage
Defining an Interface
from interface_py import interface
@interface
class HumanInterface:
# field definitions
name: str
age: int = ...
nickname = ...
DataModel = dict # direct type assignment
def speak(self): ...
@property
def rank(self): ...
@rank.setter
def rank(self, value): ...
- Property definitions in interfaces may have an empty body (
...,pass, or docstring-only`). - However, explicit getters (e.g.
@rank.getter) are not allowed in interfaces, even if their body is empty.
Multi-level Interface Example
from interface_py import interface, concrete
@interface
class MilitaryHumanInterface(HumanInterface):
def march(self): ...
@concrete
class Soldier(MilitaryHumanInterface):
name: str = "John"
age: int = 25
nickname = "Eagle"
def speak(self):
print("Reporting for duty!")
def march(self):
print("Marching!")
@property
def rank(self):
return self._rank
@rank.setter
def rank(self, value):
self._rank = value
MilitaryHumanInterfaceextendsHumanInterface.Soldierimplements all required methods, fields, and properties from both interfaces automatically.- Multi-level inheritance automatically merges all parent interface contracts.
Field Enforcement Examples
from interface_py import interface, concrete
@interface
class ExampleInterface:
x: int # only annotation
y: float = ... # annotation with ellipsis
z = ... # plain ellipsis
DataModel = dict # direct type assignment
# ✅ Correct implementation
@concrete
class GoodImpl(ExampleInterface):
x: int = 10
y: float = 3.14
z = "hello"
DataModel = dict
# ❌ Incorrect implementation
@concrete
class BadImpl(ExampleInterface):
x: str = "oops" # wrong type (expected int)
# y missing → TypeError
z = ... # not allowed to keep ellipsis
DataModel = list # wrong type assignment
Method Enforcement Rules
In interfaces, all methods must have an empty body.
Empty bodies are recognized as:
pass...- docstring-only functions (for example, a function that only contains a string literal as its body)
In concrete classes, all methods must have a non-empty body.
Methods defined with only pass, ..., or docstring-only are considered unimplemented and raise a TypeError.
Property Enforcement Rules
-
A property can be declared in an interface as:
@property def data(self): ...
-
The above is valid and treated as a contract placeholder.
-
However, the following is invalid and raises an error:
@property def data(self): pass @data.getter def data(self): ...
-
Concrete classes must implement the getter, and if defined in the interface, also the setter and deleter.
Validation
- Instantiating a concrete class that does not implement all interface methods/fields/properties raises a
TypeError. - Ensures consistent interface contracts across your project.
- The decorator
@interfaceautomatically enforces the interface behavior without requiring any base class. - The decorator
@concreteensures that at least one parent of the concrete class is an interface.
Why Use interface-py?
- Provides contract enforcement in dynamically typed Python.
- Detects incomplete or empty implementations early.
- Helps structure large codebases with clear interface and implementation separation.
- Avoids runtime errors from missing or placeholder methods.
- Enforces correctness while remaining Pythonic.
License
MIT License
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file interface_py-1.3.8.tar.gz.
File metadata
- Download URL: interface_py-1.3.8.tar.gz
- Upload date:
- Size: 9.2 kB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.12.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
bcd63306fa6262525c47680042a3fb30ceaeae72c4e026422d299e19d763a5fa
|
|
| MD5 |
de5ebeb7e5ac1b6f8339de3e60634bd8
|
|
| BLAKE2b-256 |
fc4e319fe3e7a3cb3f9c7da46826388d5c72ecbd1ccc1aeae95eb171e69a3c9e
|
File details
Details for the file interface_py-1.3.8-py3-none-any.whl.
File metadata
- Download URL: interface_py-1.3.8-py3-none-any.whl
- Upload date:
- Size: 8.0 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.12.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
61f78dc841a4e77e1caf559eca0e6c2725f06e280c89fe19c7e05f7d5fca4d66
|
|
| MD5 |
9c97360b34b46061a282ea69a9687970
|
|
| BLAKE2b-256 |
8062b07859fa132525c5b3d0525fc23055b19a688d20359be85d2640a02bd31d
|