__post_init__() for multiple inherited dataclasses

Viewed 1695

Trying to evaluate if dataclasses are suitable for an upcoming project, but right now I'm stuck with this code:

from dataclasses import dataclass

@dataclass
class MixinA:
    attrA: int
    def __post_init__(self):
        print('MixinA post_init')
        self.attrA = [self.attrA]

@dataclass
class MixinB:
    attrB: str
    def __post_init__(self):
        print('MixinB post_init')
        self.attrB = [self.attrB]

@dataclass
class MixinC:
    attrC: bool
    def __post_init__(self):
        print('MixinC post_init')
        self.attrC = [self.attrC]

@dataclass
class Inherited(MixinC, MixinB, MixinA):
    pass

obj = Inherited(4, 'Hello', False)
print(obj.attrA, obj.attrB, obj.attrC)
print(obj.__class__.mro())

It is a surprise to me that only __post_init__() in the first base class is called, when I expect all three are invoked:

MixinC post_init
4 Hello [False]
[<class '__main__.Inherited'>, <class '__main__.MixinC'>, <class '__main__.MixinB'>, <class '__main__.MixinA'>, <class 'object'>]

Besides, changing inheritance doesn't do me any good. Following inheritance generates the exact same output as above:

class MixinA:
class MixinB(MixinA):
class MixinC(MixinB):
class Inherited(MixinC):

Did I write the testing code in a wrong way, or is current behavior done by oversight or intention?

The core issue for me is, I want to transform each attribute before generating the final dataclass instances. The actual inheritance is of larger scale, and doing it within each and every class would be very redundant.

If __post_init__() is a no-go, is there any alternative approach (such as InitVar or custom __init__())?

0 Answers
Related