def __new__(mcl, classname, bases, classdict):


        newcls = super(autoparsed, mcl).__new__(mcl, classname, bases, classdict)
        module = __import__( newcls.__module__, globals(), locals(), [''] )
        #print "autoparsed", newcls

        if issubclass(newcls, Parsed):
            # find the attribute _parser, which holds the parser class for this Parsed type
            parsercls = classdict.get('_parser',None)


            if isParserClass(parsercls) or ( parsercls is None and '_rules' in classdict):

                rules = classdict.get('_rules',None)
                if rules is not None:
                    # there's no parser, but there is a set of rules. use this to create a default parser
                    if not isIterable(rules):
                        raise TypeError, "_rules attribute must be an iterable list of string rules"

                    # first add the rules to the parserdict as attributes, these will be converted to methods, below
                    parserdict = {}
                    for i, rule in enumerate(rules):
                        attrname = 'p_%s_%02d' % ( classname, i+1)
                        parserdict[ attrname ] = rule
                else:
                    # parser already exists. use it, but use __dict__, not inherited info
                    parserdict = parsercls.__dict__

                # a dictionary of updates to be made to the parser
                updatedict = {}

                # automatically set the start attribute to the name of this class
                if 'start' not in parserdict:
                    updatedict['start'] = classname

                # gather up all the tokens and rules and store them separately
                tokensDict = {}
                rulesDict = {}
                reservedDict = {}
                accepts_set= set(classdict.get('_accepts', []) )

                classNameReg = re.compile('[a-zA-Z][a-zA-Z0-9]*')
                for name, obj in parserdict.items() :
                    # print "class %s has attribute %s" % (parsercls.__name__, m)

                    # RULES
                    if name.startswith('p_') :
                        shortname = name[2:]
                        # shorthand syntax: needs to be converted to a function
                        if isinstance(obj, basestring) :
                            v = obj
                            needsWrapping = True
                        # regular syntax: already a function
                        elif inspect.isfunction(obj) or inspect.ismethod(obj) :
                            v = inspect.getdoc(obj)
                            needsWrapping = False
                        else :
                            raise SyntaxError, "Token definition %s defines neither a string nor a function, unable to parse" % name

                        # process the docstring
                        accepts = []
                        colonSplit = [ x.strip() for x in v.split(':')]
                        if len(colonSplit) == 1:
                            v = classname + ' : ' + v
                            colonSplit = [classname, colonSplit[0] ]

                        if len(colonSplit) ==2 and colonSplit[0] != '':
                            pipeSplit = [ x.strip() for x in colonSplit[1].split('|') ]
                            for grp in pipeSplit:
                                # be sure to filter out ourselves
                                accepts += [ x for x in grp.split() if classNameReg.match(x) and x!=classname ]

                        # add the classes involved in the rules
                        accepts_set.update( accepts )

                        # create the function
                        if needsWrapping:
                            def p_func(self, p):
                                p[0] = newcls( *p[1:len(p)] )
                            p_func.__name__ = name
                            p_func.__doc__ = v
                            if verbose():
                                print "overwriting %s._parser.%s with yacc function: %r" % ( classname, name, v)
                            updatedict[name] = p_func
                            rulesDict[name] = p_func
    #                        k = m[0][2:]
    #                        if k in tokensDict :
    #                            warnings.warn("Token %s redefined in Parser %s" % (k, parser), UserWarning)
    #                        tokensDict[k] = v
                        else:
                            rulesDict[name] = obj

                    # TOKENS
                    elif name.startswith('t_') and name != 't_error' :
                        shortname = name[2:]
                        if isinstance(obj, basestring) :
                            v = obj
                        elif inspect.isfunction(obj) or inspect.ismethod(obj) :
                            v = obj.__doc__
                        else :
                            raise SyntaxError, "Token definition %s defines neither a string nor a function, unable to parse" % name
                        tokensDict[name] = obj

                if verbose():
                    print "%s accepts: %s" % (newcls.__name__, list(accepts_set) )

                # find bases
                bases = []
                for parsedname in accepts_set:
                    try:
                        parsedcls = getattr( module, parsedname )
                    except AttributeError:
                        warnings.warn("Could not find a Parsed class %s in module %s.  Assuming that it is an custom token." % (parsedname, module), UserWarning)
                        continue

                    try:
                        parser = parsedcls._parser
                    except AttributeError:
                        try:
                            parser = getattr( module, parsedname + 'Parser' )
                        except AttributeError:
                            raise SyntaxError, "Cannot find parser class for parsed class %s. It should be explicitly or automatically created as %s._parser or be named %sParser" % (parsedname, parsedname, parsedname )

                    assert isinstance(parser, Parser) or (inspect.isclass(parser) and issubclass(parser, Parser)), '%s._parser is not a subclass of Parser, it is %r' % ( parsedname, parser )

                    bases.append( parser )

                # some of our bases might be subclasses of other bases.  we want the smallest list of superclasses, so weed out
                # other classes that are directly dependent on other bases
                newbases = []
                for i in bases:
                    issuperclass = False
                    #parents = inspect.getmro(i)
                    for j in bases:
                        if i in inspect.getmro(j)[1:]:
                            issuperclass = True
                            break
                    if not issuperclass:
                        newbases.append(i)

                newbases = sorted( newbases, key=lambda x: len(inspect.getmro(x)), reverse=True)

                #print "%s bases" % newcls.__name__

                for base in newbases:
                    #print base
                    #print '\t', base.tokensDict
                    #print '\t', base.rulesDict
                    tokensDict.update( base.tokensDict )
                    rulesDict.update( base.rulesDict )
#                    if hasattr(base, '_reserved'):
#                        reservedDict.update( base._reserved )

                updatedict.update( tokensDict )
                updatedict.update( rulesDict )

                    #for i, parent in enumerate(inspect.getmro(base)):
                    #    print '\t'*i, parent
                #print inspect.getclasstree(bases)
#                    for base in newbases:
#                        _printClassTree( base )

                if rules is not None:
                    #time to make the parser
                    # we use the Rules in the 'accepts' list to determine the bases of this parser class

                    # TODO : filter out bases that are superclasses of other bases: we only need one set

                    parserName = classname + 'Parser'
                    #newbases = sorted( newbases, key = lambda x: x.__name__)


                    updatedict['tokensDict'] = tokensDict
                    updatedict['rulesDict'] = rulesDict
#                    updatedict['_reserved'] = reservedDict

                    parserdict.update( updatedict )

                    # create parser class
                    parsercls = type( parserName, (Parser,), parserdict )
                    parsercls.__module__ = module.__name__
                    setattr( newcls, '_parser', parsercls)
                else:
                    # update the existing parser
                    for k, v in updatedict.iteritems():
                        setattr( parsercls, k, v )

                setattr(newcls, '_accepts', tuple(accepts_set) )

            elif issubclass( newcls, Token ):
                # a token subclass defines its regex on the '_token' attr.
                # if this attr is defined, it causes a Parser class to be created for this token, along with
                # a rule, which is named after the class
                token = classdict.get('_token',None)
                if token is None:
                    raise TypeError, "Token classes that use the autoparsed metaclass must define a _token attribute"

                #print "automatically setting up token class for %s" % newcls.__name__

                tokenBasename = classname + '_Token'
                tokenName = 't_' + tokenBasename
                ruleName = 'p_' + tokenBasename
                parserName = classname + 'Parser'

                if hasattr(token, '__name__'):
                    #print "setting token name to %s" % tokenName
                    token.__name__ = tokenName

                parserdict = {}
                parserdict[tokenName] = token

                tokensDict = {tokenName:token}

#                if hasattr(newcls, '_reserved'):
#                    print "adding _reserved to %s" % parserName
#                    parserdict['_reserved'] = newcls._reserved

                parserdict['tokensDict'] = tokensDict


                # the rule is named after the class
                doc = '''%s : %s ''' % ( classname, tokenBasename )
                #class _parser( Parser ): pass

                def rule(self, p):
                    p[0] = newcls( p[1], pos=p.lexpos(1))
                rule.__name__ = ruleName
                rule.__doc__ = doc
                parserdict[ruleName] = rule
                parserdict['rulesDict'] = {ruleName:rule}

                # create the Parser class
                print "creating parser %s" % parserName
                parsercls = type( parserName, (Parser,), parserdict )
                parsercls.__module__ = module.__name__
                #setattr( _parser, tokenName, token )
                #setattr( _parser, ruleName, rule )
                setattr( newcls, '_parser', parsercls )


        return newcls
dataset/ETHPy150Open CountZer0/PipelineConstructionSet/python/maya/site-packages/pymel-1.0.5/pymel/util/objectParser.py/autoparsed.__new__/original