def __getattr__(self, attr: str) -> TokenAction: """ Shortcut to get a TokenAction stored in self.tokens. """ name = Name.from_camel(attr) try: return self.tokens.name_to_token[name] except KeyError: raise AttributeError(f"No such token: {attr}")
def __new__(mcs, name, bases, dct): assert len(bases) == 1, ( "Multiple inheritance for LexerToken subclasses is not supported" ) fields = [] for fld_name, fld_value in dct.items(): if isinstance(fld_value, TokenAction): fld_value.name = Name.from_camel(fld_name) fields.append(fld_value) dct['fields'] = getattr(bases[0], 'fields', []) + fields return type.__new__(mcs, name, bases, dct)
def add_tokens(self, cls): for fld_name, fld_value in cls.__dict__.items(): if isinstance(fld_value, TokenAction): dest_list = self.tokens elif isinstance(fld_value, TokenFamily): dest_list = self.token_families else: continue # Several items here are shared: for example, the # LexerToken.LexingFailure instance can be used in two different # lexers, so we can't assume its name is always None. Just accept # when it has already the expected name. name = Name.from_camel(fld_name) assert fld_value.name in (None, name) fld_value.name = name dest_list.append(fld_value)
def add_tokens(self, klass): for fld_name, fld_value in klass.__dict__.items(): if isinstance(fld_value, TokenAction): fld_value.name = Name.from_camel(fld_name) self.fields.append(fld_value)