Skip to content

Instantly share code, notes, and snippets.

@zyga
Created September 3, 2014 17:43
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save zyga/6b548b1f52e49342d3f0 to your computer and use it in GitHub Desktop.
Save zyga/6b548b1f52e49342d3f0 to your computer and use it in GitHub Desktop.
type() bug?
class NS:
PASSTHRU = frozenset(('__name__', '__qualname__', '__doc__', '__module__'))
def __init__(self, data=None):
if data is None:
data = {}
self.data = data
def __setitem__(self, name, value):
if name in self.PASSTHRU:
self.data[name] = value
elif isinstance(value, str):
self.data[name] = value
else:
raise TypeError
def __getitem__(self, name):
if name in self.PASSTHRU:
return self.data[name]
elif name in self.data:
return self.data[name]
else:
self.data[name] = name
return self.data[name]
class Meta(type):
@classmethod
def __prepare__(mcls, name, bases):
return NS()
def __new__(mcls, name, bases, ns):
classdict = ns.data
return type.__new__(mcls, name, bases, classdict)
class Def(metaclass=Meta):
pass
class Example(Def):
a = 'a'
b = 'b'
c = 'c'
assert Example.a == 'a'
assert Example.b == 'b'
assert Example.c == 'c'
BrokenExample1 = type('BrokenExample1', (Def, ), NS({'x': 'x'}))
# Traceback (most recent call last):
# File "example.py", line 53, in <module>
# BrokenExample1 = type('BrokenExample1', (Def, ), NS({'x': 'x'}))
# TypeError: type() argument 3 must be dict, not NS
BrokenExample2 = type('BrokenExample2', (Def, ), {'x': 'x'})
# Traceback (most recent call last):
# File "example.py", line 58, in <module>
# BrokenExample2 = type('BrokenExample2', (Def, ), {'x': 'x'})
# File "example.py", line 35, in __new__
# classdict = ns.data
# AttributeError: 'dict' object has no attribute 'data'
@zyga
Copy link
Author

zyga commented Sep 3, 2014

Yes I've figured it out... on line 52 I should have used Meta...

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment