How to create abstract properties in python abstract classes? – Python

Photo of author
Written By M Ibrahim
abstract-class abstract-methods application.properties arrow-python decorator

Quick Fix: Utilize the @property decorator followed by @abstractmethod to create abstract properties in Python abstract classes. Specify the abstract property method by def my_abstract_property(self): ....

The Problem:

The code is supposed to instantiate Base1 class, where Base1 is a subclass of an abstract class, Base. However, the error is not raised even when Base1 does not provide the abstract property called ‘name’. How can one create abstract properties in Python abstract classes?

The Solutions:

Solution 1: Using @property and @abstractmethod Decorators

In Python 3.3 and later, you can define an abstract property in an abstract class using a combination of the `@property` and `@abstractmethod` decorators. For Python 2, you can use the `@abstractproperty` decorator instead.

Here’s an example in Python 3.3+:

from abc import ABC, abstractmethod

class Base(ABC):
    @property
    @abstractmethod
    def name(self):
        pass


class C(Base):
    @property
    def name(self):
        return "Class C"


if __name__ == "__main__":
    c = C()
    print(c.name)  # Output: Class C

In this example, the `name` property is defined as an abstract property in the `Base` class. The `C` class inherits from `Base` and provides an implementation for the `name` property. When you create an instance of the `C` class and access the `name` property, the value `”Class C”` is returned.

For Python 2, you can use the `@abstractproperty` decorator:

from abc import ABCMeta, abstractproperty

class Base(object):
    __metaclass__ = ABCMeta

    @abstractproperty
    def name(self):
        pass


class C(Base):
    @property
    def name(self):
        return "Class C"


if __name__ == "__main__":
    c = C()
    print(c.name)  # Output: Class C

The `@abstractproperty` decorator works similarly to the `@abstractmethod` decorator, but it is specifically designed for abstract properties.

Solution 3: compatibleabstractproperty decorator

In the following code, we define a decorator function called compatibleabstractproperty. This decorator function is meant to be used with Python versions 2 and 3, and it checks the Python version to determine which decorator to use. For Python 3.3 and above, it uses abstractmethod, while for earlier versions of Python, it uses abstractproperty.

To use this decorator, simply apply it to the property method in the abstract class, as shown in the following example:

from abc import ABCMeta, abstractmethod
import sys

def compatibleabstractproperty(func):

    if sys.version_info > (3, 3):             
        return property(abstractmethod(func))
    else:
        return abstractproperty(func)

class Base(object):
    __metaclass__ = ABCMeta

    @compatibleabstractproperty
    def name(self):
        raise NotImplementedError()


class C(Base):
    @property
    def name(self):
        return "class C"


if __name__ == "__main__":
    b1 = C()
    print(b1.name)

This code will output “class C”, demonstrating that the abstract property is working as expected.