示例#1
0
    def decodeCriteria(self, typeCriteria, getterCriteria):
        '''
        Exploit that provides the decoder for the criteria.
        
        @param typeCriteria: TypeCriteria
            The criteria type to decode.
        @param getterCriteria: callable(object) -> object
            The getter used to get the criteria from the target object.
        @return: callable(**data) -> boolean
            The exploit that provides the criteria decoding.
        '''
        assert isinstance(
            typeCriteria,
            TypeCriteria), 'Invalid criteria type %s' % typeCriteria
        assert callable(getterCriteria), 'Invalid getter %s' % getterCriteria
        criteria = typeCriteria.container
        assert isinstance(criteria, Criteria)

        if issubclass(typeCriteria.clazz, AsOrdered):
            exclude = ('ascending', 'priority')
        else:
            exclude = ()

        children = {}
        for prop, typeProp in criteria.properties.items():
            if prop in exclude: continue

            if isinstance(typeProp, Iter):
                assert isinstance(typeProp, Iter)

                setter = setterWithGetter(obtainOnObj(prop, list), list.append)
                propDecode = self.decodePrimitiveList(setter,
                                                      typeProp.itemType)
            else:
                propDecode = self.decodePrimitive(setterOnObj(prop), typeProp)
            children[prop] = propDecode

        exploitPath = self.decodePath(children)

        def exploit(path, target, **data):
            assert isinstance(path, deque), 'Invalid path %s' % path

            if path:
                return exploitPath(path=path,
                                   target=getterCriteria(target),
                                   **data)
            if not criteria.main: return False

            data.update(path=path, target=getterCriteria(target))
            for prop in criteria.main:
                if not children[prop](**data): return False
            return True

        return exploit
示例#2
0
    def decodeCriteria(self, typeCriteria, getterCriteria):
        """
        Exploit that provides the decoder for the criteria.
        
        @param typeCriteria: TypeCriteria
            The criteria type to decode.
        @param getterCriteria: callable(object) -> object
            The getter used to get the criteria from the target object.
        @return: callable(**data) -> boolean
            The exploit that provides the criteria decoding.
        """
        assert isinstance(typeCriteria, TypeCriteria), "Invalid criteria type %s" % typeCriteria
        assert callable(getterCriteria), "Invalid getter %s" % getterCriteria
        criteria = typeCriteria.container
        assert isinstance(criteria, Criteria)

        if issubclass(typeCriteria.clazz, AsOrdered):
            exclude = ("ascending", "priority")
        else:
            exclude = ()

        children = {}
        for prop, typeProp in criteria.properties.items():
            if prop in exclude:
                continue

            if isinstance(typeProp, Iter):
                assert isinstance(typeProp, Iter)

                setter = setterWithGetter(obtainOnObj(prop, list), list.append)
                propDecode = self.decodePrimitiveList(setter, typeProp.itemType)
            else:
                propDecode = self.decodePrimitive(setterOnObj(prop), typeProp)
            children[prop] = propDecode

        exploitPath = self.decodePath(children)

        def exploit(path, target, **data):
            assert isinstance(path, deque), "Invalid path %s" % path

            if path:
                return exploitPath(path=path, target=getterCriteria(target), **data)
            if not criteria.main:
                return False

            data.update(path=path, target=getterCriteria(target))
            for prop in criteria.main:
                if not children[prop](**data):
                    return False
            return True

        return exploit
示例#3
0
    def decodeInvoker(self, invoker):
        """
        Create a decode exploit for the invoker.
        
        @param invoker: Invoker
            The invoker to create a parameters decoder for.
        @return: callable(**data) -> boolean
            The exploit that provides the invoker decoding.
        """
        assert isinstance(invoker, Invoker), "Invalid invoker %s" % invoker

        children, ordered = {}, {}
        for inp in invoker.inputs:
            assert isinstance(inp, Input)
            typeInp = inp.type
            assert isinstance(typeInp, Type)

            if typeInp.isPrimitive:
                if isinstance(typeInp, Iter):
                    assert isinstance(typeInp, Iter)

                    setter = setterWithGetter(obtainOnDict(inp.name, list), list.append)
                    inpDecode = self.decodePrimitiveList(setter, typeInp.itemType)
                else:
                    inpDecode = self.decodePrimitive(setterOnDict(inp.name), typeInp)
                children[inp.name] = inpDecode

            elif isinstance(typeInp, TypeQuery):
                assert isinstance(typeInp, TypeQuery)
                assert isinstance(typeInp.query, Query)

                childrenQuery, orderedQuery, getterQuery = {}, {}, obtainOnDict(inp.name, inp.type.clazz)
                for nameEntry, classCriteria in typeInp.query.criterias.items():

                    getter = getterChain(getterQuery, getterOnObj(nameEntry))
                    childrenQuery[nameEntry] = self.decodeCriteria(typeFor(classCriteria), getter)

                    if issubclass(classCriteria, AsOrdered):
                        orderedQuery[nameEntry] = self.decodeSetOrder(
                            typeInp.criteriaEntryTypeFor(nameEntry), getterQuery
                        )

                isUpdated = False
                if invoker.output.isOf(typeInp.owner):
                    # If the query is a main query and also there is no name conflict then add the query children to
                    # the main children
                    if set(childrenQuery.keys()).isdisjoint(children.keys()) and set(orderedQuery).isdisjoint(ordered):
                        isUpdated = True
                        children.update(childrenQuery)
                        ordered.update(orderedQuery)

                if not isUpdated:
                    children[inp.name] = self.decodePath(childrenQuery)
                    ordered[inp.name] = self.decodePath(orderedQuery)

        if self.nameOrderAsc in children:
            log.error("Name conflict for '%s' in %s", self.nameOrderAsc, invoker)
        elif self.nameOrderDesc in children:
            log.error("Name conflict for '%s' in %s", self.nameOrderDesc, invoker)
        else:
            exploitOrder = self.decodePath(ordered)
            children[self.nameOrderAsc] = self.decodeOrder(True, exploitOrder)
            children[self.nameOrderDesc] = self.decodeOrder(False, exploitOrder)

        exploitPath = self.decodePath(children)

        def exploit(path, **data):
            assert isinstance(path, str), "Invalid path %s" % path

            path = deque(path.split(self.separatorName))
            return exploitPath(path=path, **data)

        return exploit
示例#4
0
    def decodeInvoker(self, invoker):
        '''
        Create a decode exploit for the invoker.
        
        @param invoker: Invoker
            The invoker to create a parameters decoder for.
        @return: callable(**data) -> boolean
            The exploit that provides the invoker decoding.
        '''
        assert isinstance(invoker, Invoker), 'Invalid invoker %s' % invoker

        children, ordered = {}, {}
        for inp in invoker.inputs:
            assert isinstance(inp, Input)
            typeInp = inp.type
            assert isinstance(typeInp, Type)

            if typeInp.isPrimitive:
                if isinstance(typeInp, Iter):
                    assert isinstance(typeInp, Iter)

                    setter = setterWithGetter(obtainOnDict(inp.name, list),
                                              list.append)
                    inpDecode = self.decodePrimitiveList(
                        setter, typeInp.itemType)
                else:
                    inpDecode = self.decodePrimitive(setterOnDict(inp.name),
                                                     typeInp)
                children[inp.name] = inpDecode

            elif isinstance(typeInp, TypeQuery):
                assert isinstance(typeInp, TypeQuery)
                assert isinstance(typeInp.query, Query)

                childrenQuery, orderedQuery, getterQuery = {}, {}, obtainOnDict(
                    inp.name, inp.type.clazz)
                for nameEntry, classCriteria in typeInp.query.criterias.items(
                ):

                    getter = getterChain(getterQuery, getterOnObj(nameEntry))
                    childrenQuery[nameEntry] = self.decodeCriteria(
                        typeFor(classCriteria), getter)

                    if issubclass(classCriteria, AsOrdered):
                        orderedQuery[nameEntry] = self.decodeSetOrder(
                            typeInp.criteriaEntryTypeFor(nameEntry),
                            getterQuery)

                isUpdated = False
                if invoker.output.isOf(typeInp.owner):
                    # If the query is a main query and also there is no name conflict then add the query children to
                    # the main children
                    if set(childrenQuery.keys()).isdisjoint(children.keys(
                    )) and set(orderedQuery).isdisjoint(ordered):
                        isUpdated = True
                        children.update(childrenQuery)
                        ordered.update(orderedQuery)

                if not isUpdated:
                    children[inp.name] = self.decodePath(childrenQuery)
                    ordered[inp.name] = self.decodePath(orderedQuery)

        if self.nameOrderAsc in children:
            log.error('Name conflict for \'%s\' in %s', self.nameOrderAsc,
                      invoker)
        elif self.nameOrderDesc in children:
            log.error('Name conflict for \'%s\' in %s', self.nameOrderDesc,
                      invoker)
        else:
            exploitOrder = self.decodePath(ordered)
            children[self.nameOrderAsc] = self.decodeOrder(True, exploitOrder)
            children[self.nameOrderDesc] = self.decodeOrder(
                False, exploitOrder)

        exploitPath = self.decodePath(children)

        def exploit(path, **data):
            assert isinstance(path, str), 'Invalid path %s' % path

            path = deque(path.split(self.separatorName))
            return exploitPath(path=path, **data)

        return exploit