Skip to content

Instantly share code, notes, and snippets.

Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save johnpauljanecek/1e767022198dcc7e45d7 to your computer and use it in GitHub Desktop.
Save johnpauljanecek/1e767022198dcc7e45d7 to your computer and use it in GitHub Desktop.
Blog notebooks
Display the source blob
Display the rendered blob
Raw
{
"cells": [
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Code for blog post on Save time creating classmethods using a metaclass\n",
"http://johnpauljanecek.work/blog/creating-classmethods-using-a-metaclass/"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"# Verify that classes are in fact just fancy dictionaries"
]
},
{
"cell_type": "code",
"execution_count": 6,
"metadata": {
"collapsed": false
},
"outputs": [],
"source": [
"from pprint import pprint as pp"
]
},
{
"cell_type": "code",
"execution_count": 21,
"metadata": {
"collapsed": false
},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"'Foo.__dict__'\n",
"mappingproxy({'__doc__': None, '__weakref__': <attribute '__weakref__' of 'Foo' objects>, 'a_class_variable': 'a', 'a_function': <function Foo.a_function at 0x7fb358f79488>, '__dict__': <attribute '__dict__' of 'Foo' objects>, '__module__': '__main__'})\n",
"'pretty Foo'\n",
"'Pretty Foo.__dict__'\n",
"{'__dict__': <attribute '__dict__' of 'Foo' objects>,\n",
" '__doc__': None,\n",
" '__module__': '__main__',\n",
" '__weakref__': <attribute '__weakref__' of 'Foo' objects>,\n",
" 'a_class_variable': 'a',\n",
" 'a_function': <function Foo.a_function at 0x7fb358f79488>}\n"
]
}
],
"source": [
"class Foo(object):\n",
" a_class_variable = \"a\"\n",
" def a_function(self):\n",
" print(a_function)\n",
" \n",
"pp(\"Foo.__dict__\")\n",
"pp(Foo.__dict__)\n",
"pp(\"pretty Foo\")\n",
"pp(\"Pretty Foo.__dict__\")\n",
"pp(dict(Foo.__dict__)) #convert it to a dictionary so pp dumps it out nice"
]
},
{
"cell_type": "code",
"execution_count": 38,
"metadata": {
"collapsed": false,
"scrolled": true
},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"('__new__ \\n'\n",
" \" cls => <class '__main__.BarMetaClass'> \\n\"\n",
" \" name => 'Bar' \\n\"\n",
" \" bases => (<class 'object'>,) \\n\"\n",
" \" dct => {'__qualname__': 'Bar', 'a_class_variable': 'a', '__module__': \"\n",
" \"'__main__', 'a_function': <function Bar.a_function at 0x7fb358f43598>}\")\n",
"('__init__ \\n'\n",
" \" cls => <class '__main__.Bar'> \\n\"\n",
" \" name => 'Bar' \\n\"\n",
" \" bases => (<class 'object'>,) \\n\"\n",
" \" dct => {'__qualname__': 'Bar', 'a_class_variable': 'a', '__module__': \"\n",
" \"'__main__', 'a_function': <function Bar.a_function at 0x7fb358f43598>}\")\n"
]
}
],
"source": [
"class BarMetaClass(type):\n",
" def __new__(cls, name,bases, dct):\n",
" #this is called before the class has been created\n",
" pp(\"__new__ \\n cls => %r \\n name => %r \\n bases => %r \\n dct => %r\" % (cls,name,bases,dct))\n",
" #the parent __new__ metaclass has to be returned\n",
" return type.__new__(cls,name, bases, dct)\n",
" \n",
" def __init__(cls, name,bases, dct):\n",
" #the parent __init__ metaclass method has to be called\n",
" type.__init__(cls,name, bases, dct)\n",
" #this is called after the class has been created\n",
" pp(\"__init__ \\n cls => %r \\n name => %r \\n bases => %r \\n dct => %r\" % (cls,name,bases,dct))\n",
" \n",
"\n",
"class Bar(object,metaclass = BarMetaClass):\n",
" a_class_variable = \"a\"\n",
" def a_function(self):\n",
" print(a_function)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"# adding a method and variable to class Foo using FooMetaClass"
]
},
{
"cell_type": "code",
"execution_count": 44,
"metadata": {
"collapsed": false
},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"'testing out foo'\n",
"\"Foo.my_variable => 'my_variable'\"\n",
"\"foo.my_function() => 'from my function'\"\n"
]
}
],
"source": [
"def my_function(self):\n",
" return \"from my function\"\n",
"\n",
"class FooMetaClass(type):\n",
" def __new__(cls, name,bases, dct):\n",
" dct[\"my_function\"] = my_function\n",
" dct[\"my_variable\"] = \"my_variable\"\n",
" #the parent __new__ metaclass has to be returned\n",
" return type.__new__(cls,name, bases, dct) \n",
"\n",
"class Foo(object,metaclass = FooMetaClass):\n",
" a_class_variable = \"a\"\n",
" def a_function(self):\n",
" print(a_function)\n",
" \n",
"pp(\"testing out foo\")\n",
"pp(\"Foo.my_variable => %r\" % Foo.my_variable)\n",
"foo = Foo()\n",
"pp(\"foo.my_function() => %r\" % foo.my_function())"
]
},
{
"cell_type": "code",
"execution_count": 11,
"metadata": {
"collapsed": false
},
"outputs": [],
"source": [
"def CreateRpcFunction(name):\n",
" def wrappedFunction(self,*args,**kwArgs):\n",
" self.call(name,*args,**kwArgs)\n",
" return name\n",
" return wrappedFunction"
]
},
{
"cell_type": "code",
"execution_count": 19,
"metadata": {
"collapsed": false,
"scrolled": true
},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"'dump rpc functions'\n",
"['rpc_get_user', 'rpc_list_users', 'rpc_set_user']\n",
"\"called name 'rpc_get_user' args () kwArgs {}\"\n",
"\"rpcClient.rpc_get_user() => 'rpc_get_user'\"\n",
"\"called name 'rpc_list_users' args () kwArgs {'startsWith': 'Fred'}\"\n",
"\"rpcClient.rpc_list_user() => 'rpc_list_users'\"\n"
]
}
],
"source": [
"wrapFunctionNames = [\"rpc_list_users\",\"rpc_get_user\",\"rpc_set_user\"]\n",
"\n",
"class RpcClientMeta(type):\n",
" def __new__(cls,name,bases, dct):\n",
" for name in wrapFunctionNames :\n",
" dct[name] = CreateRpcFunction(name)\n",
" return type.__new__(cls,name,bases, dct)\n",
" \n",
"\n",
"class RpcClient(object,metaclass = RpcClientMeta):\n",
" \n",
" def call(self,name,*args,**kwArgs):\n",
" \"\"\"\n",
" simulates calling the rpc on the server.\n",
" \"\"\"\n",
" pp(\"called name %r args %r kwArgs %r\" % (name,args,kwArgs))\n",
" return name\n",
" \n",
"rpcClient = RpcClient()\n",
"pp(\"dump rpc functions\")\n",
"pp([name for name in dir(rpcClient) if name.startswith(\"rpc_\")])\n",
"\n",
"pp(\"rpcClient.rpc_get_user() => %r\" % rpcClient.rpc_get_user())\n",
"pp(\"rpcClient.rpc_list_user() => %r\" % rpcClient.rpc_list_users(startsWith = \"Fred\"))"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {
"collapsed": true
},
"outputs": [],
"source": []
}
],
"metadata": {
"kernelspec": {
"display_name": "Python 3",
"language": "python",
"name": "python3"
},
"language_info": {
"codemirror_mode": {
"name": "ipython",
"version": 3
},
"file_extension": ".py",
"mimetype": "text/x-python",
"name": "python",
"nbconvert_exporter": "python",
"pygments_lexer": "ipython3",
"version": "3.4.3"
}
},
"nbformat": 4,
"nbformat_minor": 0
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment