[Twisted-Python] what is a non-class class?
From spread/jelly.py in _unjelly_method:
- if type(im_class) is not types.ClassType: raise InsecureJelly("Method found with non-class class.") Same problem in _unjelly_instance What is a non-class class or rather what sort of types is meant to be insecure? Suggestions for a better error message instead of "non-class class"? This should work with both old style and new style classes, right now it works only for old style and fails for new style. Working with Python3 gives bonus points. Current source code does not have test cases for both _unjelly_instance and _unjelly_method using new style classes. My patch for ticket 4935 has a such a test case for _unjelly_method which fails as expected. If only user defined classes are accepted as secure, see also https://stackoverflow.com/questions/14612865/how-to-check-if-object-is-insta... Would it be acceptable to instead exclude an explicit list of basic types as that stackoverflow answer suggests? if im_class in (int, long, float, bool, list, set, frozenset, dict, type(None), str, unicode, tuple, what else?): raise InsecureJelly https://twistedmatrix.com/documents/current/api/twisted.spread.jelly.Insecur... does not cover this. Python 2.7.6:
class A(object): ... pass ... type(A)
type(int)
import types types.ClassType
class B: ... pass ... type(B)
Python 3.3:
class A: ... pass ... type(A)
type(int)
-- Wolfgang
On Sep 1, 2014, at 3:24 PM, Wolfgang Rohdewald
What is a non-class class or rather what sort of types is meant to be insecure?
Jelly is dynamically typed, so any value might show up in any position. In this case, a value shows up in the slot in the serialization of a method object which indicates that method's class might be any object, but it has to be a class.
Suggestions for a better error message instead of "non-class class"?
It's not clear that there needs to be a better error message here; you'll only get this message if you have corrupt data on the wire, since a correct implementation of PB will never put anything other than a class in that slot. (Except I think it might be broken in the face of new-style classes; ClassType is the old-style class type, 'type' is the new one, so, that should probably be fixed, as per your other thread...) -glyph
I still do not like "non-class class" because this is a contradiction in itself. Anyway a non-class class is a class whose objects may not get a method attached. So far so good, but that was obvious. Am Dienstag, 2. September 2014, 16:29:41 schrieb Glyph Lefkowitz:
Except I think it might be broken in the face of new-style classes; ClassType is the old-style class type, 'type' is the new one, so, that should probably be fixed
That is my problem. How do I know if the object is of a non-class class? As you say, current code does not handle new style classes. I cannot check if the object is of type "type" because int is also of type "type". An int certainly should not get a method attached. Then we could just as well remove this check. That is why I proposed to instead exclude a list of basic types int, float, list, dict, set and so on. -- Wolfgang
On Sep 2, 2014, at 11:45 PM, Wolfgang Rohdewald
I still do not like "non-class class" because this is a contradiction in itself.
How about "non-class found in class slot when deserializing method object"?
Anyway a non-class class is a class whose objects may not get a method attached. So far so good, but that was obvious.
Uh... no? A non-class in an object which is not a class. The error is when that object is provided as the class associated with a method.
Am Dienstag, 2. September 2014, 16:29:41 schrieb Glyph Lefkowitz:
Except I think it might be broken in the face of new-style classes; ClassType is the old-style class type, 'type' is the new one, so, that should probably be fixed
That is my problem. How do I know if the object is of a non-class class?
isinstance(something, (types.ClassType, type)).
As you say, current code does not handle new style classes.
Yes, but it could be easily modified to do so.
I cannot check if the object is of type "type" because int is also of type "type". An int certainly should not get a method attached. Then we could just as well remove this check.
isinstance(object, type) True isinstance(object(), type) False
That is why I proposed to instead exclude a list of basic types int, float, list, dict, set and so on.
I'm not sure I understand the proposal. But in any case - it's not necessary. It's clearly possible to determine if a particular value is a type or not. -glyph
Am Mittwoch, 3. September 2014, 00:29:59 schrieb Glyph:
That is my problem. How do I know if the object is of a non-class class?
isinstance(something, (types.ClassType, type)).
but that will make it possible to attach a method even to type "int" Python2:
isinstance(int, type) True
isinstance(object, type) True isinstance(object(), type) False
Sure but the test only gets the class and it should certainly not instantiate it. Meanwhile I believe it is best to simply remove the test since python itself will reject most:
a=int a.x=5 Traceback (most recent call last): File "<stdin>", line 1, in <module> TypeError: can't set attributes of built-in/extension type 'int'
-- Wolfgang
On Sep 3, 2014, at 12:55 AM, Wolfgang Rohdewald
Am Mittwoch, 3. September 2014, 00:29:59 schrieb Glyph:
That is my problem. How do I know if the object is of a non-class class?
isinstance(something, (types.ClassType, type)).
but that will make it possible to attach a method even to type "int"
Yes, that's fine. 'int' has methods, there's no reason that those methods couldn't be serialized by jelly. For example:
(3).conjugate
The bound method object there is the sort of thing that we're talking about. Particularly since we might be talking about a subclass of 'int' with its own overridden conjugate method, and the im_class attribute says which class the method's function actually came from.
Python2:
isinstance(int, type) True
isinstance(object, type) True isinstance(object(), type) False
Sure but the test only gets the class and it should certainly not instantiate it.
Right; the point is that you get a thing, and that thing may be a class object _or_ it might be an instance object, and if it's an instance that's invalid.
Meanwhile I believe it is best to simply remove the test since python itself will reject most:
a=int a.x=5 Traceback (most recent call last): File "<stdin>", line 1, in <module> TypeError: can't set attributes of built-in/extension type 'int'
This is about serializing and deserializing existing methods, not assigning attributes to instances. -glyph
participants (3)
-
Glyph
-
Glyph Lefkowitz
-
Wolfgang Rohdewald