[Python-es] Chequear código python

Chema Cortes pych3m4 en gmail.com
Mar Nov 20 04:04:54 CET 2012


El día 17 de noviembre de 2012 15:09, Benito Rodríguez Arcos
<brarcos en gmail.com> escribió:

> Supongo que esto valdría, pero tendría que ejecutar el código que suben los
> usuarios a la web....

Es casi imposible saber qué será un objeto hasta que no ejecutas el
código.  Por ejemplo,

from MegaClase import MegaClase

X=MegaClase

class MyClase(X):
  pass


Es difícil saber que X es equivalente a MegaClase sin ejecutar el código.


Por otra parte, puedes aprovechar el analizador sintáctico del python
(AST) y crear unos "visitadores" sin tener que ejecutar código (aunque
sigue estando el mismo problema que he comentado antes). Te pongo un
ejemplo que podría servirte. A partir de este ejemplo sería fácil
filtrar todo ćodigo que no tuviera participación en la derivación de
la clase abstracta y proceder a una compilación "segura":


import ast

class CKV_functiondef(ast.NodeVisitor):

    def __init__(self):
        self.funcs=[]

    def visit_FunctionDef(self, node):
        self.funcs.append(node.name)

class CKV_class(ast.NodeVisitor):

    def __init__(self):
        self.class_found=[]

    def visit_ClassDef(self, node):
        name = node.name
        base = node.bases[0].id if len(node.bases)>0 else ""

        ckv_meths=CKV_functiondef()
        ckv_meths.visit(node.body[0])
        meths=ckv_meths.funcs

        self.class_found.append( (name,base,meths) )


#baroque test

code="""
import sys

print sys.path

class A:
    pass

class B(P):
    def __init__(self):
        pass

C=A

class D(C):
    class M(object):
        pass

def f():
    class X(object):
        pass

"""

parse=ast.parse(code)

c=CKV_class()

c.visit(parse)

for name, base, meths in c.class_found:
    print "Class: %s(%s)"%(name,base)
    for m in meths:
        print "    Method: %s"%m





-- 
Hyperreals *R: http://ch3m4.org/blog
Quarks, bits y otras criaturas infinitesimales


Más información sobre la lista de distribución Python-es