Module descriptor

This idea is for module attribute getting and setting:

If the original object’s type has __get__ and (__set__ or __delete__), when get it from module visiting attribute, it will call obj.__get__(module, ModuleType) and when set it from module changing attribute, it will call obj.__set__(module, value).

You can use the name _ to define the module property here:

@property
def unchangeable_data(_):
    return some_value

Then user can only get the attribute unchangeable_data and cannot set it.

NOTE: the objects only have __get__ won’t do it (such as FunctionType).

1 Like

What use cases would this functionality be required for?

I did look for this in the past, but only out of curiosity while about class descriptors (ie “do modules also support this?”). I wasn’t surprised it doesn’t exist, but also couldn’t think of a reason for it to exist. Because it’s possible to use classes that look and feel like a module (‘from package import foo’ where foo is an instance) I didn’t investigate further. There just didn’t seem like a reason to increase the complexity of the interpreter and performance of module lookups.

You should have a look at PEP 726 – Module __setattr__ and __delattr__.

3 Likes

This seems like the job of a types.ModuleType subclass at first glance, but that would be far from trivial. I like the idea, but it would be a breaking change (what if a library exposes a top-level ready-to-use property that users can bind to their classes by an assignment in the class body?)