Exemplo n.º 1
0
    def handle_interest_from_lower(self, face_id: int, interest: Interest, to_lower: multiprocessing.Queue):
        self.logger.info("Incoming interest: " + interest.name.to_string())
        # incoming interest is nfn expression
        if interest.name.string_components[-1] == "NFN":
            try:
                parser = DefaultNFNParser()
                nfn_str, prepended_name = parser.network_name_to_nfn_str(interest.name)
                ast = parser.parse(nfn_str)
                # assert that valid publish expression
                if is_publish_expression(ast):
                    # store to database
                    data_name = ast.params[0]._element
                    payload = ast.params[1]._element
                    try:
                        payload = base64.b64decode(payload[7:])
                        self.logger.info("Payload is base64 encoded. Decoded.")
                    except:
                        self.logger.info("Invalid publish expression. The payload could not be decoded.")
                        nack = Nack(interest.name, reason=NackReason.COMP_NOT_PARSED, interest=interest)
                        self.queue_to_lower.put([face_id, nack])

                    self.cs.add_content_object(Content(data_name, payload))
                    self.logger.info("Add to database: " + data_name)
                    # reply confirmation
                    confirmation = Content(interest.name, "ok")
                    to_lower.put([face_id, confirmation])

                else:
                    self.logger.info("Invalid publish expression. Wrong format.")
                    nack = Nack(interest.name, reason=NackReason.COMP_NOT_PARSED, interest=interest)
                    self.queue_to_lower.put([face_id, nack])

            except:
                self.logger.info("Invalid publish expression.")
                nack = Nack(interest.name, reason=NackReason.COMP_NOT_PARSED, interest=interest)
                self.queue_to_lower.put([face_id, nack])

        # incoming interest is data request
        else:
            db_entry = self.cs.find_content_object(interest.name)
            if db_entry is not None:
                self.logger.info("Found in database")
                to_lower.put([face_id, db_entry.content])
                return
            else:
                self.logger.info("Not found in database")
                nack = Nack(interest.name, NackReason.NO_CONTENT, interest)
                to_lower.put([face_id, nack])
                return
Exemplo n.º 2
0
class test_DefaultNFNParser(unittest.TestCase):
    """Test the default Parser"""

    def setUp(self):
        self.parser = DefaultNFNParser()
        pass

    def tearDown(self):
        pass

    def test_parser_parsing_name(self):
        """Test the parser, parse a simple name"""
        string = "/test/data"
        ast = AST_Name("/test/data")

        res = self.parser.parse(string)
        self.assertTrue(isinstance(res, AST_Name))
        self.assertEqual(ast._element, res._element)

    def test_parser_parsing_simple_call(self):
        """Test the parser, parsing a simple call"""
        string = "/call/func(/test/data)"
        fc1 = AST_FuncCall("/call/func")
        param1 = AST_Name("/test/data")

        res: AST = self.parser.parse(string)
        self.assertTrue(isinstance(res, AST_FuncCall))
        self.assertEqual(fc1._element, res._element)
        self.assertEqual(len(res.params), 1)
        self.assertTrue(isinstance(res.params[0], AST_Name))
        self.assertEqual(param1._element, res.params[0]._element)

    def test_parser_parsing_simple_call_multiple_parameter(self):
        """Test the parser, parsing a simple call with multiple parameter"""
        string = "/call/func(/test/data,2,X)"
        fc1 = AST_FuncCall("/call/func")
        param1 = AST_Name("/test/data")
        param2 = AST_Int("2")
        param3 = AST_Var("X")

        res: AST = self.parser.parse(string)
        self.assertTrue(isinstance(res, AST_FuncCall))
        self.assertEqual(fc1._element, res._element)
        self.assertEqual(len(res.params), 3)
        self.assertTrue(isinstance(res.params[0], AST_Name))
        self.assertEqual(param1._element, res.params[0]._element)
        self.assertTrue(isinstance(res.params[1], AST_Int))
        self.assertEqual(param2._element, res.params[1]._element)
        self.assertTrue(isinstance(res.params[2], AST_Var))
        self.assertEqual(param3._element, res.params[2]._element)

    def test_parser_parsing_multiple_calls(self):
        """Test the parser, parsing multiple calls"""
        string = '/call/func(/lib/wcount("HelloWorld"))'
        fc1 = AST_FuncCall("/call/func")
        fc2 = AST_FuncCall("/lib/wcount")
        param1 = AST_String('"HelloWorld"')

        res: AST = self.parser.parse(string)
        self.assertTrue(isinstance(res, AST_FuncCall))
        self.assertEqual(fc1._element, res._element)
        self.assertEqual(len(res.params), 1)
        self.assertTrue(isinstance(res.params[0], AST_FuncCall))
        self.assertEqual(fc2._element, res.params[0]._element)
        self.assertEqual(len(res.params[0].params), 1)
        self.assertTrue(isinstance(res.params[0].params[0], AST_String))
        self.assertEqual(param1._element, res.params[0].params[0]._element)

    def test_parser_parsing_multiple_calls_multiple_parameter(self):
        """Test the parser, parsing multiple calls with multiple parameters"""
        string = '/call/func(3,/lib/wcount(/call/libfun(/test/data),"HelloWorld"))'
        fc1 = AST_FuncCall("/call/func")
        fc2 = AST_FuncCall("/lib/wcount")
        fc3 = AST_FuncCall("/call/libfun")
        param1 = AST_Int("3")
        param2 = AST_Int("/test/data")
        param3 = AST_String('"HelloWorld"')

        res: AST = self.parser.parse(string)
        self.assertTrue(isinstance(res, AST_FuncCall))
        self.assertEqual(fc1._element, res._element)
        self.assertEqual(len(res.params), 2)
        self.assertTrue(isinstance(res.params[0], AST_Int))
        self.assertEqual(param1._element, res.params[0]._element)
        self.assertTrue(isinstance(res.params[1], AST_FuncCall))
        self.assertEqual(fc2._element, res.params[1]._element)
        self.assertEqual(len(res.params[1].params), 2)
        self.assertTrue(isinstance(res.params[1].params[0], AST_FuncCall))
        self.assertEqual(fc3._element, res.params[1].params[0]._element)
        self.assertEqual(len(res.params[1].params[0].params), 1)
        self.assertTrue(isinstance(res.params[1].params[0].params[0], AST_Name))
        self.assertEqual(param2._element, res.params[1].params[0].params[0]._element)
        self.assertTrue(isinstance(res.params[1].params[1], AST_String))
        self.assertEqual(param3._element, res.params[1].params[1]._element)

    def test_parser_parsing_error1(self):
        """Test the parser, parsing call with syntax error 1"""
        string = "/call/func(/test/data"
        res: AST = self.parser.parse(string)
        self.assertEqual(res, None)

    def test_parser_parsing_error2(self):
        """Test the parser, parsing call with syntax error 2"""
        string = "/call/func(/test/data,/lib/call(X)"
        res: AST = self.parser.parse(string)
        self.assertEqual(res, None)

    def test_parser_parsing_error3(self):
        """Test the parser, parsing call with syntax error 3"""
        string = "call/func(/test/data)"
        res: AST = self.parser.parse(string)
        self.assertEqual(res, None)

    def test_ast_to_string(self):
        """Test converting the ast back to a string"""
        string = '/call/func(3,/lib/wcount(/call/libfun(/test/data),"HelloWorld"))'
        ast: AST = self.parser.parse(string)
        res = str(ast)
        self.assertEqual(string, res)

    def test_sub_ast_to_string(self):
        """Test converting the ast back to a string"""
        string = '/call/func(3,/lib/wcount(/call/libfun(/test/data),"HelloWorld"))'
        part_str = '/lib/wcount(/call/libfun(/test/data),"HelloWorld")'
        ast: AST = self.parser.parse(string)
        part_ast = ast.params[1]
        res = str(part_ast)
        self.assertEqual(part_str, res)

    def test_ast_to_string_nfn_marker(self):
        """Test converting the ast back to a string using nfn marker"""
        string = '/call/func(3,/lib/wcount(/call/libfun(/test/data),"HelloWorld"))'
        marked_str = '/call/func(3,%/lib/wcount%(/call/libfun(/test/data),"HelloWorld"))'
        ast: AST = self.parser.parse(string)
        ast.params[1]._prepend = True
        res = str(ast)
        self.assertEqual(marked_str, res)

    def test_network_name_to_nfn_str(self):
        """Test transforming network name to nfn str"""
        n = Name("/test/data")
        function_str = '/call/func(3,/lib/wcount(/call/libfun(_),"HelloWorld"))'
        cmp_str = '/call/func(3,/lib/wcount(/call/libfun(/test/data),"HelloWorld"))'
        n += function_str
        n += "NFN"
        res, prepended = self.parser.network_name_to_nfn_str(n)
        self.assertEqual(res, cmp_str)
        self.assertEqual(prepended, Name("/test/data"))

    def test_nfn_str_to_network_name(self):
        "Test transforming nfn str to network name"
        nfn_str = '/call/func(3,/lib/wcount(/call/libfun(%/test/data%),"HelloWorld"))'
        compname = Name("/test/data")
        function_str = '/call/func(3,/lib/wcount(/call/libfun(_),"HelloWorld"))'
        compname += function_str
        compname += "NFN"
        res = self.parser.nfn_str_to_network_name(nfn_str)
        self.assertEqual(res, compname)