You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
Classes without __namespace__ cannot be used for reflection #1774
My software does lots of reflection on "plugin" types. Simply inheriting from a specific type is enough in C#, but when I use python.net I also have to define __namespace__. Since my users generally have the namespace being ., there is no logic reason for them to have to do this.
I can see which part of the code causes this:
// from MetaType.cs:133 (git: 7247da55c174be1b733e5f9fc4e1c356f6c42dc4)if(clsDict.HasKey("__assembly__")||clsDict.HasKey("__namespace__")){returnTypeManager.CreateSubType(name,base_type,clsDict);}
I am wonder if we could broaden the cases where TypeManager.CreateSubType is used. For example in cases where the super class is a type created with CreateSubType, or just any .NET class in general. Maybe it could also be if the super class implements a specific interface.
_TODO_
Add a way to not have to specify namespace in the class in order for reflection to work.
The logic reason is that classes with __namespace__ are .NET classes as well as Python classes, and classes without it are just Python classes. This is by design.
@lostmsu The point is that it could be enough that the base class is a .NET class. Since we control the __new__ in this case anyhow, this wouldn't be a huge change (a breaking one, yes, but I think the new behaviour might be less surprising).
Maybe I can add that if the base class is abstract, inheriting from it without namespace causes a an exception during construction: "Python.Runtime.PythonException: cannot instantiate abstract class". A similar issue happens with interfaces.
Also the python object seems to loose all memory of its type once it gets converted back into an C# object, casting it to its base type.
@rmadsen-ks Hi can I ask if you find any workaround for the problem? I’m having the exact same problem of inheriting from an abstract base class then converting back into C# loses all info. GetType.GetFields() won’t work at all and I’m honestly stuck right now. I wonder if #433 can help.
Hi @phuongdtvd, this sounded like a design decision to me, so I made a fork which does some of these things a bit differently. I don't think #433 makes a huge difference here.
@rmadsen-ks Could you create a PR from your branch? I personally don't see (right now) a problem with always making classes derived from .NET classes also .NET classes themselves (with a way to shut that off). We could make this behaviour configurable (something like Runtime.Configure("<feature-name>", true)), to keep it compatible without bumping the major version.
Hi @filmor, sure, but I have a bunch of features on that fork, some more or less experimental. In total, it is not that many changes. I'll clean it up a bit and setup a PR.
Turning previously non-.NET types defined in Python as derived from .NET types into .NET types would be a breaking change. As 3.0 is released, this is problematic.
Activity
lostmsu commentedon Apr 27, 2022
The logic reason is that classes with
__namespace__are .NET classes as well as Python classes, and classes without it are just Python classes. This is by design.filmor commentedon Apr 27, 2022
@lostmsu The point is that it could be enough that the base class is a .NET class. Since we control the
__new__in this case anyhow, this wouldn't be a huge change (a breaking one, yes, but I think the new behaviour might be less surprising).lostmsu commentedon Apr 27, 2022
@filmor are you suggesting all new derived classes to be .NET classes by default? What would be the way to turn that off?
rmadsen-ks commentedon Apr 29, 2022
Maybe I can add that if the base class is abstract, inheriting from it without namespace causes a an exception during construction: "Python.Runtime.PythonException: cannot instantiate abstract class". A similar issue happens with interfaces.
Also the python object seems to loose all memory of its type once it gets converted back into an C# object, casting it to its base type.
Both these issues could be fixed by this change.
phuongdtvd commentedon Nov 17, 2022
@rmadsen-ks Hi can I ask if you find any workaround for the problem? I’m having the exact same problem of inheriting from an abstract base class then converting back into C# loses all info. GetType.GetFields() won’t work at all and I’m honestly stuck right now. I wonder if #433 can help.
rmadsen-ks commentedon Nov 18, 2022
Hi @phuongdtvd, this sounded like a design decision to me, so I made a fork which does some of these things a bit differently. I don't think #433 makes a huge difference here.
filmor commentedon Nov 18, 2022
@rmadsen-ks Could you create a PR from your branch? I personally don't see (right now) a problem with always making classes derived from .NET classes also .NET classes themselves (with a way to shut that off). We could make this behaviour configurable (something like
Runtime.Configure("<feature-name>", true)), to keep it compatible without bumping the major version.rmadsen-ks commentedon Nov 18, 2022
Hi @filmor, sure, but I have a bunch of features on that fork, some more or less experimental. In total, it is not that many changes. I'll clean it up a bit and setup a PR.
rmadsen-ks commentedon Nov 18, 2022
@filmor, I have added PR #2019. Those are the majority of changes in my fork.
lostmsu commentedon Nov 29, 2022
Turning previously non-.NET types defined in Python as derived from .NET types into .NET types would be a breaking change. As 3.0 is released, this is problematic.
filmor commentedon Nov 29, 2022
@lostmsu I lined out how we could do it anyhow, via a runtime/startup feature flag mechanism. No magic required.