Added first version of DebugManager. Implemented draft of the rule engine
This commit is contained in:
@@ -2,19 +2,20 @@ import ast
|
||||
|
||||
import pytest
|
||||
from core.builtin_concepts import ReturnValueConcept, ParserResultConcept, BuiltinConcepts
|
||||
from core.concept import Concept, CB, NotInit
|
||||
from core.concept import Concept, CB
|
||||
from core.sheerka.services.SheerkaExecute import ParserInput
|
||||
from core.tokenizer import Tokenizer
|
||||
from evaluators.PythonEvaluator import PythonEvaluator, PythonEvalError
|
||||
from evaluators.PythonEvaluator import PythonEvaluator, PythonEvalError, NamesWithAttributesVisitor
|
||||
from parsers.BaseNodeParser import SourceCodeNode, SourceCodeWithConceptNode
|
||||
from parsers.FunctionParser import FunctionParser
|
||||
from parsers.PythonParser import PythonNode, PythonParser
|
||||
from parsers.PythonWithConceptsParser import PythonWithConceptsParser
|
||||
|
||||
from tests.TestUsingMemoryBasedSheerka import TestUsingMemoryBasedSheerka
|
||||
|
||||
|
||||
def get_concept_name(concept):
|
||||
return concept.name
|
||||
def get_obj_name(obj):
|
||||
return obj.name
|
||||
|
||||
|
||||
def get_source_code_node(source_code, concepts=None):
|
||||
@@ -36,7 +37,7 @@ def get_source_code_node(source_code, concepts=None):
|
||||
tokens = list(Tokenizer(source_code, yield_eof=False))
|
||||
return SourceCodeNode(0, len(tokens), tokens, python_node=python_node)
|
||||
else:
|
||||
python_node.concepts = concepts
|
||||
python_node.objects = concepts
|
||||
scwcn = SourceCodeWithConceptNode(None, None)
|
||||
scwcn.python_node = python_node
|
||||
return scwcn
|
||||
@@ -62,10 +63,13 @@ class TestPythonEvaluator(TestUsingMemoryBasedSheerka):
|
||||
assert PythonEvaluator().matches(context, ret_val) == expected
|
||||
|
||||
@pytest.mark.parametrize("text, expected", [
|
||||
("1 + 1", 2),
|
||||
("test()", "I have access to Sheerka !"),
|
||||
# ("1 + 1", 2),
|
||||
# ("test()", "I have access to Sheerka !"),
|
||||
("sheerka.test()", "I have access to Sheerka !"),
|
||||
("a=10\na", 10),
|
||||
("Concept('foo')", Concept('foo')),
|
||||
("BuiltinConcepts.NOP", BuiltinConcepts.NOP),
|
||||
("in_context(BuiltinConcepts.EVAL_QUESTION_REQUESTED)", False),
|
||||
])
|
||||
def test_i_can_eval(self, text, expected):
|
||||
context = self.get_context()
|
||||
@@ -76,6 +80,29 @@ class TestPythonEvaluator(TestUsingMemoryBasedSheerka):
|
||||
assert evaluated.status
|
||||
assert evaluated.value == expected
|
||||
|
||||
def test_i_can_eval_isinstance(self):
|
||||
sheerka, context, foo = self.init_concepts("foo")
|
||||
parsed = PythonParser().parse(context, ParserInput("isinstance('foo', str)"))
|
||||
evaluated = PythonEvaluator().eval(context, parsed)
|
||||
assert evaluated.status
|
||||
assert evaluated.value
|
||||
|
||||
parsed = PythonParser().parse(context, ParserInput("isinstance(foo, 'foo')"))
|
||||
evaluated = PythonEvaluator().eval(context, parsed)
|
||||
assert evaluated.status
|
||||
assert evaluated.value
|
||||
|
||||
def test_i_can_eval_context_obj_properties(self):
|
||||
sheerka, context, foo = self.init_concepts(Concept("foo").def_var("a", "hello world!").auto_init())
|
||||
context = self.get_context()
|
||||
parsed = PythonParser().parse(context, ParserInput("a"))
|
||||
|
||||
context.obj = foo
|
||||
evaluated = PythonEvaluator().eval(context, parsed)
|
||||
|
||||
assert evaluated.status
|
||||
assert evaluated.value == "hello world!"
|
||||
|
||||
@pytest.mark.parametrize("source_code_node, expected", [
|
||||
(get_source_code_node("1 + 1"), 2),
|
||||
(get_source_code_node("one + one", {"one": Concept("one", body="1")}), 2)
|
||||
@@ -89,14 +116,14 @@ class TestPythonEvaluator(TestUsingMemoryBasedSheerka):
|
||||
assert evaluated.status
|
||||
assert evaluated.value == expected
|
||||
|
||||
def test_i_can_eval_using_context(self):
|
||||
def test_i_can_eval_a_method_that_requires_the_context(self):
|
||||
context = self.get_context()
|
||||
parsed = PythonParser().parse(context, ParserInput("test_using_context('value for param1', 10)"))
|
||||
parsed = PythonParser().parse(context, ParserInput("test_using_context('value for param')"))
|
||||
|
||||
evaluated = PythonEvaluator().eval(context, parsed)
|
||||
|
||||
assert evaluated.status
|
||||
assert evaluated.value.startswith("I have access to Sheerka ! param1='value for param1', param2=10, event=")
|
||||
assert evaluated.value == "I have access to Sheerka ! param='value for param', event='xxx'."
|
||||
|
||||
def test_i_can_eval_using_context_when_self_is_not_sheerka(self):
|
||||
sheerka, context = self.init_concepts()
|
||||
@@ -107,21 +134,6 @@ class TestPythonEvaluator(TestUsingMemoryBasedSheerka):
|
||||
assert evaluated.status
|
||||
assert sheerka.has_key("foo")
|
||||
|
||||
@pytest.mark.parametrize("concept", [
|
||||
Concept("foo"),
|
||||
Concept("foo", body="2"),
|
||||
Concept("foo").def_var("prop", "'a'"),
|
||||
Concept("foo", body="bar")
|
||||
])
|
||||
def test_simple_concepts_are_not_for_me(self, concept):
|
||||
context = self.get_context()
|
||||
context.sheerka.add_in_cache(Concept("foo"))
|
||||
|
||||
parsed = PythonParser().parse(context, ParserInput("foo"))
|
||||
evaluated = PythonEvaluator().eval(context, parsed)
|
||||
|
||||
assert not evaluated.status
|
||||
assert context.sheerka.isinstance(evaluated.value, BuiltinConcepts.NOT_FOR_ME)
|
||||
|
||||
def test_i_can_eval_ast_expression_that_references_concepts(self):
|
||||
"""
|
||||
@@ -167,10 +179,10 @@ class TestPythonEvaluator(TestUsingMemoryBasedSheerka):
|
||||
def test_i_can_eval_concept_token(self):
|
||||
context = self.get_context()
|
||||
context.sheerka.add_in_cache(Concept("foo", body="2"))
|
||||
context.add_to_short_term_memory("get_obj_name", get_obj_name)
|
||||
|
||||
parsed = PythonParser().parse(context, ParserInput("get_concept_name(c:foo:)"))
|
||||
parsed = PythonParser().parse(context, ParserInput("get_obj_name(c:foo:)"))
|
||||
python_evaluator = PythonEvaluator()
|
||||
python_evaluator.globals["get_concept_name"] = get_concept_name
|
||||
evaluated = python_evaluator.eval(context, parsed)
|
||||
|
||||
assert evaluated.status
|
||||
@@ -210,7 +222,8 @@ class TestPythonEvaluator(TestUsingMemoryBasedSheerka):
|
||||
evaluated = python_evaluator.eval(context, parsed)
|
||||
|
||||
assert evaluated.status
|
||||
assert sheerka.get_concepts_weights(BuiltinConcepts.PRECEDENCE) == {'1001': 1, '1002': 2}
|
||||
assert sheerka.get_concepts_weights(BuiltinConcepts.PRECEDENCE) == {'c:__var__0 plus __var__1|1001:': 1,
|
||||
'c:__var__0 mult __var__1|1002:': 2}
|
||||
|
||||
def test_i_can_define_variables(self):
|
||||
sheerka, context = self.init_concepts()
|
||||
@@ -261,7 +274,7 @@ class TestPythonEvaluator(TestUsingMemoryBasedSheerka):
|
||||
evaluated = PythonEvaluator().eval(context, parsed)
|
||||
|
||||
assert not evaluated.status
|
||||
assert context.sheerka.isinstance(evaluated.value, BuiltinConcepts.TOO_MANY_ERRORS)
|
||||
assert context.sheerka.isinstance(evaluated.value, BuiltinConcepts.ERROR)
|
||||
|
||||
error0 = evaluated.body.body[0]
|
||||
assert isinstance(error0, PythonEvalError)
|
||||
@@ -275,21 +288,6 @@ class TestPythonEvaluator(TestUsingMemoryBasedSheerka):
|
||||
assert error1.error.args[0] == 'can only concatenate str (not "int") to str'
|
||||
assert error1.concepts == {'foo': 'string'}
|
||||
|
||||
def test_i_do_not_include_not_initialized_variables_when_evaluating(self):
|
||||
sheerka, context, foo = self.init_concepts(
|
||||
Concept("foo a", pre="a == 'True'").def_var("a", "'True'").def_var("b"))
|
||||
|
||||
foo.set_value("b", "'Initialized!'")
|
||||
context.obj = foo
|
||||
|
||||
assert foo.get_value("a") == NotInit
|
||||
assert foo.get_value("b") == "'Initialized!'"
|
||||
|
||||
my_globals = {}
|
||||
PythonEvaluator().update_globals_with_context(my_globals, context)
|
||||
|
||||
assert my_globals == {"self": foo, "b": "'Initialized!'"}
|
||||
|
||||
def test_i_can_use_sheerka_locals(self):
|
||||
sheerka, context = self.init_concepts()
|
||||
|
||||
@@ -307,11 +305,47 @@ class TestPythonEvaluator(TestUsingMemoryBasedSheerka):
|
||||
|
||||
def test_i_can_eval_concept_with_ret(self):
|
||||
sheerka, context, one, the = self.init_concepts("one", Concept("the a", ret="a").def_var("a"))
|
||||
ret_val = get_ret_val_from_source_code(context, "test_using_context(one, the one)", {
|
||||
"the one": self.get_concept_instance(sheerka, the, a="one"),
|
||||
"one": self.get_concept_instance(sheerka, "one")
|
||||
ret_val = get_ret_val_from_source_code(context, "test_using_context(the one)", {
|
||||
"the one": self.get_concept_instance(sheerka, the, a="one")
|
||||
})
|
||||
|
||||
evaluated = PythonEvaluator().eval(context, ret_val)
|
||||
assert evaluated.status
|
||||
assert evaluated.value.startswith("I have access to Sheerka ! param1=(1001)one, param2=(1001)one, event=")
|
||||
assert evaluated.value == "I have access to Sheerka ! param=(1001)one, event='xxx'."
|
||||
|
||||
def test_i_can_eval_rules_from_python_parser(self):
|
||||
sheerka, context = self.init_concepts()
|
||||
parsed_ret_val = PythonParser().parse(context, ParserInput("r:|1:.id"))
|
||||
|
||||
assert parsed_ret_val.status
|
||||
|
||||
evaluated = PythonEvaluator().eval(context, parsed_ret_val)
|
||||
assert evaluated.status
|
||||
assert evaluated.value == "1"
|
||||
|
||||
def test_i_can_eval_rules_from_function_parser(self):
|
||||
context = self.get_context()
|
||||
context.add_to_short_term_memory("get_obj_name", get_obj_name)
|
||||
|
||||
parsed = FunctionParser().parse(context, ParserInput("get_obj_name(r:|1:)"))
|
||||
python_evaluator = PythonEvaluator()
|
||||
evaluated = python_evaluator.eval(context, parsed)
|
||||
|
||||
assert evaluated.status
|
||||
assert evaluated.value == "Print return values"
|
||||
|
||||
@pytest.mark.parametrize("text, expected", [
|
||||
("foo.bar.baz", [["foo", "bar", "baz"]]),
|
||||
("foo.bar.baz; one.two.three", [["foo", "bar", "baz"]]),
|
||||
("foo.bar.baz; one.two.three; foo.bar", [["foo", "bar", "baz"], ["foo", "bar"]]),
|
||||
("one.two.three", []),
|
||||
("foo", [["foo"]]),
|
||||
("foo.bar[1].baz", [["foo", "bar", "baz"]]),
|
||||
("foo[1].bar.baz", [["foo", "bar", "baz"]]),
|
||||
])
|
||||
def test_names_with_attributes_visitor(self, text, expected):
|
||||
ast_ = ast.parse(text, "<src>", mode="exec")
|
||||
visitor = NamesWithAttributesVisitor()
|
||||
|
||||
sequence = visitor.get_sequences(ast_, "foo")
|
||||
assert sequence == expected
|
||||
|
||||
Reference in New Issue
Block a user