예제 #1
0
 def _inner_resolve_link_rule_ref(cls, obj_name):
     """
     Depth-first resolving of link rule reference.
     """
     if cls._tx_type is RULE_ABSTRACT:
         for inherited in cls._tx_inh_by:
             result = _inner_resolve_link_rule_ref(inherited,
                                                   obj_name)
             if result:
                 return result
     elif cls._tx_type == RULE_COMMON:
         # TODO make this code exchangable
         # allow to know the current attribute (model location for
         # namespace) and to navigate through the whole model...
         # OR (with another scope provider) to make custom lookups in
         # the model
         #
         # Scopeprovider
         # - needs: .current reference (in the model)
         #          .the model (?)
         # - provides: the resolved object or None
         if id(cls) in get_parser(obj)._instances:
             objs = get_parser(obj)._instances[id(cls)]
             if obj_name in objs:
                 return objs[obj_name]
예제 #2
0
 def __call__(self, obj, attr, obj_ref):
     from textx.scoping.tools import get_referenced_object, \
         get_list_of_concatenated_objects
     from textx.scoping import Postponed
     from textx import get_model
     try:
         # print("DEBUG: ExtRelativeName.__call__(...{})".
         #      format(obj_ref.obj_name))
         one_def_obj = get_referenced_object(None, obj,
                                             self.path_to_definition_object)
         def_obj_list = get_list_of_concatenated_objects(
             one_def_obj, self.path_to_extension, [])
         # print("DEBUG: {}".format(def_obj_list))
         for def_obj in def_obj_list:
             if type(def_obj) is Postponed:
                 self.postponed_counter += 1
                 return def_obj
             res = get_referenced_object(
                 None, def_obj,
                 self.path_to_target + "." + obj_ref.obj_name, obj_ref.cls)
             if res:
                 return res  # may be Postponed
         return None
     except TypeError as e:
         from textx.scoping.tools import get_parser
         line, col = get_parser(obj).pos_to_linecol(obj_ref.position)
         raise TextXSemanticError('ExtRelativeName: {}'.format(str(e)),
                                  line=line,
                                  col=col,
                                  filename=get_model(obj)._tx_filename)
예제 #3
0
 def _inner_resolve_link_rule_ref(cls, obj_name):
     """
     Depth-first resolving of link rule reference.
     """
     if cls._tx_type is RULE_ABSTRACT:
         for inherited in cls._tx_inh_by:
             result = _inner_resolve_link_rule_ref(inherited,
                                                   obj_name)
             if result:
                 return result
     elif cls._tx_type == RULE_COMMON:
         # TODO make this code exchangable
         # allow to know the current attribute (model location for
         # namespace) and to navigate through the whole model...
         # OR (with another scope provider) to make custom lookups in
         # the model
         #
         # Scopeprovider
         # - needs: .current reference (in the model)
         #          .the model (?)
         # - provides: the resolved object or None
         if id(cls) in get_parser(obj)._instances:
             objs = get_parser(obj)._instances[id(cls)]
             return objs.get(obj_name)
예제 #4
0
 def __call__(self, obj, attr, obj_ref):
     from textx.scoping.tools import get_referenced_object
     from textx.scoping import Postponed
     from textx import get_model
     try:
         res = get_referenced_object(
             None, obj,
             self.path_to_container_object + "." + obj_ref.obj_name,
             obj_ref.cls)
         if type(res) is Postponed:
             self.postponed_counter += 1
         return res
     except TypeError as e:
         from textx.scoping.tools import get_parser
         line, col = get_parser(obj).pos_to_linecol(obj_ref.position)
         raise TextXSemanticError('{}'.format(str(e)), line=line, col=col,
                                  filename=get_model(obj)._tx_filename)
예제 #5
0
    def __call__(self, obj, attr, obj_ref):
        """
        the default scope provider

        Args:
            obj: unused (used for multi_metamodel_support)
            attr: unused
            obj_ref: the cross reference to be resolved

        Returns:
            the resolved reference or None
        """
        from textx.const import RULE_COMMON, RULE_ABSTRACT
        from textx.model import ObjCrossRef
        from textx.scoping.tools import get_parser

        if obj_ref is None:
            return None  # an error! (see model.py: resolve_refs (TODO check)

        assert type(obj_ref) is ObjCrossRef, type(obj_ref)

        if get_parser(obj).debug:
            get_parser(obj).dprint("Resolving obj crossref: {}:{}"
                                   .format(obj_ref.cls, obj_ref.obj_name))

        def _inner_resolve_link_rule_ref(cls, obj_name):
            """
            Depth-first resolving of link rule reference.
            """
            if cls._tx_type is RULE_ABSTRACT:
                for inherited in cls._tx_inh_by:
                    result = _inner_resolve_link_rule_ref(inherited,
                                                          obj_name)
                    if result:
                        return result
            elif cls._tx_type == RULE_COMMON:
                # TODO make this code exchangable
                # allow to know the current attribute (model location for
                # namespace) and to navigate through the whole model...
                # OR (with another scope provider) to make custom lookups in
                # the model
                #
                # Scopeprovider
                # - needs: .current reference (in the model)
                #          .the model (?)
                # - provides: the resolved object or None
                if id(cls) in get_parser(obj)._instances:
                    objs = get_parser(obj)._instances[id(cls)]
                    return objs.get(obj_name)

        if self.multi_metamodel_support:
            from textx import get_model, get_children
            from textx import textx_isinstance
            result_lst = get_children(
                lambda x:
                _hasattr(x, "name") and _getattr(x, "name") == obj_ref.obj_name
                and textx_isinstance(x, obj_ref.cls), get_model(obj))
            if len(result_lst) == 1:
                result = result_lst[0]
            elif len(result_lst) > 1:
                line, col = get_parser(obj).pos_to_linecol(obj_ref.position)
                raise TextXSemanticError(
                    "name {} is not unique.".format(obj_ref.obj_name),
                    line=line, col=col, filename=get_model(obj)._tx_filename)
            else:
                result = None
        else:
            result = _inner_resolve_link_rule_ref(obj_ref.cls,
                                                  obj_ref.obj_name)
        if result:
            return result

        return None  # error handled outside
예제 #6
0
    def __call__(self, obj, attr, obj_ref):
        """
        the default scope provider

        Args:
            obj: unused (used for multi_metamodel_support)
            attr: unused
            obj_ref: the cross reference to be resolved

        Returns:
            the resolved reference or None
        """
        from textx.const import RULE_COMMON, RULE_ABSTRACT
        from textx.model import ObjCrossRef
        from textx.scoping.tools import get_parser

        if obj_ref is None:
            return None  # an error! (see model.py: resolve_refs (TODO check)

        assert type(obj_ref) is ObjCrossRef, type(obj_ref)

        if get_parser(obj).debug:
            get_parser(obj).dprint("Resolving obj crossref: {}:{}"
                                   .format(obj_ref.cls, obj_ref.obj_name))

        def _inner_resolve_link_rule_ref(cls, obj_name):
            """
            Depth-first resolving of link rule reference.
            """
            if cls._tx_type is RULE_ABSTRACT:
                for inherited in cls._tx_inh_by:
                    result = _inner_resolve_link_rule_ref(inherited,
                                                          obj_name)
                    if result:
                        return result
            elif cls._tx_type == RULE_COMMON:
                # TODO make this code exchangable
                # allow to know the current attribute (model location for
                # namespace) and to navigate through the whole model...
                # OR (with another scope provider) to make custom lookups in
                # the model
                #
                # Scopeprovider
                # - needs: .current reference (in the model)
                #          .the model (?)
                # - provides: the resolved object or None
                if id(cls) in get_parser(obj)._instances:
                    objs = get_parser(obj)._instances[id(cls)]
                    return objs.get(obj_name)

        if self.multi_metamodel_support:
            from textx import get_model, get_children
            from textx import textx_isinstance
            result_lst = get_children(
                lambda x:
                hasattr(x, "name") and x.name == obj_ref.obj_name
                and textx_isinstance(x, obj_ref.cls), get_model(obj))
            if len(result_lst) == 1:
                result = result_lst[0]
            elif len(result_lst) > 1:
                line, col = get_parser(obj).pos_to_linecol(obj_ref.position)
                raise TextXSemanticError(
                    "name {} is not unique.".format(obj_ref.obj_name),
                    line=line, col=col, filename=get_model(obj)._tx_filename)
            else:
                result = None
        else:
            result = _inner_resolve_link_rule_ref(obj_ref.cls,
                                                  obj_ref.obj_name)
        if result:
            return result

        return None  # error handled outside