Added first implementation of concepts ambiguity resolution + Jenkins file test
This commit is contained in:
@@ -19,7 +19,7 @@ class TestAddConceptEvaluator(TestUsingMemoryBasedSheerka):
|
||||
@staticmethod
|
||||
def get_concept_part(part):
|
||||
if isinstance(part, str):
|
||||
node = PythonNode(part, ast.parse(part, mode="eval"))
|
||||
node = PythonNode(part, ast.parse(part, mode="exec"))
|
||||
return ReturnValueConcept(
|
||||
who="parsers.Default",
|
||||
status=True,
|
||||
@@ -169,11 +169,16 @@ class TestAddConceptEvaluator(TestUsingMemoryBasedSheerka):
|
||||
|
||||
assert from_db.compiled == {} # ast is not saved in db
|
||||
|
||||
def test_i_can_get_variables_from_python_node_when_long_name(self):
|
||||
ret_val = self.get_concept_part("isinstance(a, str)")
|
||||
@pytest.mark.parametrize("expression, name, expected", [
|
||||
("isinstance(a, str)", "a b", {"a"}),
|
||||
("a.location=b", "a is in b", {"a", "b"}),
|
||||
("a.location=b", "'a' is in b", {"b"}),
|
||||
])
|
||||
def test_i_can_get_variables_from_python_node_when_long_name(self, expression, name, expected):
|
||||
ret_val = self.get_concept_part(expression)
|
||||
context = self.get_context()
|
||||
|
||||
assert AddConceptEvaluator.get_variables(context.sheerka, ret_val, ["a", "b"]) == ["a"]
|
||||
assert AddConceptEvaluator.get_variables(context.sheerka, ret_val, name.split()) == expected
|
||||
|
||||
def test_i_can_get_variables_when_keywords(self):
|
||||
sheerka, context = self.init_concepts()
|
||||
@@ -182,7 +187,7 @@ class TestAddConceptEvaluator(TestUsingMemoryBasedSheerka):
|
||||
name_to_use = AddConceptEvaluator.get_name_to_use(def_concept)
|
||||
concept_part = self.get_concept_part("pre")
|
||||
|
||||
assert AddConceptEvaluator.get_variables(context.sheerka, concept_part, name_to_use) == ["pre"]
|
||||
assert AddConceptEvaluator.get_variables(context.sheerka, concept_part, name_to_use) == {"pre"}
|
||||
|
||||
def test_i_cannot_get_variables_from_python_node_when_name_has_only_one_token(self):
|
||||
ret_val = self.get_concept_part("isinstance(a, str)")
|
||||
@@ -196,14 +201,14 @@ class TestAddConceptEvaluator(TestUsingMemoryBasedSheerka):
|
||||
status=True,
|
||||
value=ParserResultConcept(value=concept))
|
||||
|
||||
assert AddConceptEvaluator.get_variables(self.get_sheerka(), ret_val, []) == ["a", "b"]
|
||||
assert AddConceptEvaluator.get_variables(self.get_sheerka(), ret_val, []) == {"a", "b"}
|
||||
|
||||
def test_i_can_get_variables_from_definition(self):
|
||||
parsing_expression = Sequence(ConceptExpression('mult'),
|
||||
ZeroOrMore(Sequence(StrMatch("+"), ConceptExpression("add"))))
|
||||
ret_val = self.get_return_value("mult (('+'|'-') add)?", parsing_expression)
|
||||
|
||||
assert AddConceptEvaluator.get_variables(self.get_sheerka(), ret_val, []) == ["add", "mult"]
|
||||
assert AddConceptEvaluator.get_variables(self.get_sheerka(), ret_val, []) == {"add", "mult"}
|
||||
|
||||
def test_concept_that_references_itself_is_correctly_created(self):
|
||||
context = self.get_context()
|
||||
|
||||
@@ -1,8 +1,8 @@
|
||||
import pytest
|
||||
|
||||
from core.builtin_concepts import ReturnValueConcept, ParserResultConcept, BuiltinConcepts
|
||||
from core.concept import Concept, ConceptParts
|
||||
from evaluators.ConceptEvaluator import ConceptEvaluator
|
||||
|
||||
from tests.TestUsingMemoryBasedSheerka import TestUsingMemoryBasedSheerka
|
||||
|
||||
|
||||
@@ -20,11 +20,12 @@ class TestAddConceptEvaluator(TestUsingMemoryBasedSheerka):
|
||||
|
||||
def test_i_can_evaluate_concept(self):
|
||||
context = self.get_context()
|
||||
context.local_hints.add(BuiltinConcepts.EVAL_BODY_REQUESTED)
|
||||
context.local_hints.update({BuiltinConcepts.EVAL_BODY_REQUESTED, BuiltinConcepts.EVAL_WHERE_REQUESTED})
|
||||
concept = Concept(name="foo",
|
||||
where="True",
|
||||
pre="2",
|
||||
post="3").def_var("a", "4").def_var("b", "5")
|
||||
pre="2 > 1",
|
||||
ret="3",
|
||||
post="4").def_var("a", "5").def_var("b", "6")
|
||||
|
||||
evaluator = ConceptEvaluator()
|
||||
item = self.pretval(concept)
|
||||
@@ -34,10 +35,11 @@ class TestAddConceptEvaluator(TestUsingMemoryBasedSheerka):
|
||||
assert result.status
|
||||
assert result.value.name == "foo"
|
||||
assert result.value.get_value(ConceptParts.WHERE) == True
|
||||
assert result.value.get_value(ConceptParts.PRE) == 2
|
||||
assert result.value.get_value(ConceptParts.POST) == 3
|
||||
assert result.value.get_value("a") == 4
|
||||
assert result.value.get_value("b") == 5
|
||||
assert result.value.get_value(ConceptParts.PRE) == True
|
||||
assert result.value.get_value(ConceptParts.RET) == 3
|
||||
assert result.value.get_value(ConceptParts.POST) == 4
|
||||
assert result.value.get_value("a") == 5
|
||||
assert result.value.get_value("b") == 6
|
||||
assert result.value.key == "foo"
|
||||
assert result.parents == [item]
|
||||
|
||||
@@ -118,4 +120,3 @@ class TestAddConceptEvaluator(TestUsingMemoryBasedSheerka):
|
||||
assert not context.sheerka.is_success(error_concept) # it's indeed an error
|
||||
assert result.status
|
||||
assert result.value == error_concept
|
||||
|
||||
|
||||
@@ -15,7 +15,7 @@ def retval(obj, who="who", status=True):
|
||||
class TestEvalEvaluator(TestUsingMemoryBasedSheerka):
|
||||
def test_i_can_match_and_eval(self):
|
||||
context = self.get_context()
|
||||
context.global_hints.add(BuiltinConcepts.CONCEPT_VALUE_REQUESTED)
|
||||
context.global_hints.add(BuiltinConcepts.RETURN_VALUE_REQUESTED)
|
||||
|
||||
to_eval1 = ReturnValueConcept("some_name", True, Concept(name="2", body="to eval").auto_init())
|
||||
to_eval2 = ReturnValueConcept("some_name", True, Concept(name="3", body="also to eval").auto_init())
|
||||
@@ -49,12 +49,12 @@ class TestEvalEvaluator(TestUsingMemoryBasedSheerka):
|
||||
context = self.get_context()
|
||||
assert not EvalEvaluator().matches(context, [return_value])
|
||||
|
||||
context.global_hints.add(BuiltinConcepts.CONCEPT_VALUE_REQUESTED)
|
||||
context.global_hints.add(BuiltinConcepts.RETURN_VALUE_REQUESTED)
|
||||
assert EvalEvaluator().matches(context, [return_value])
|
||||
|
||||
def test_i_can_match_depending_on_builtin_concept_processing(self):
|
||||
context = self.get_context()
|
||||
context.global_hints.add(BuiltinConcepts.CONCEPT_VALUE_REQUESTED)
|
||||
context.global_hints.add(BuiltinConcepts.RETURN_VALUE_REQUESTED)
|
||||
return_values = [ReturnValueConcept("some_name", True, Concept(name="2", body="to eval").auto_init())]
|
||||
evaluator = EvalEvaluator()
|
||||
|
||||
|
||||
@@ -45,4 +45,4 @@ class TestPrepareEvalEvaluator(TestUsingMemoryBasedSheerka):
|
||||
assert res.body.body == expected
|
||||
|
||||
assert BuiltinConcepts.EVAL_BODY_REQUESTED in context.global_hints
|
||||
assert BuiltinConcepts.CONCEPT_VALUE_REQUESTED in context.global_hints
|
||||
assert BuiltinConcepts.RETURN_VALUE_REQUESTED in context.global_hints
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
import pytest
|
||||
from core.builtin_concepts import ReturnValueConcept, ParserResultConcept, BuiltinConcepts
|
||||
from core.concept import Concept, CB
|
||||
from core.concept import Concept, CB, NotInit
|
||||
from core.sheerka.services.SheerkaExecute import ParserInput
|
||||
from evaluators.PythonEvaluator import PythonEvaluator, PythonEvalError
|
||||
from parsers.PythonParser import PythonNode, PythonParser
|
||||
@@ -137,7 +137,7 @@ class TestPythonEvaluator(TestUsingMemoryBasedSheerka):
|
||||
assert evaluated.status
|
||||
assert not evaluated.value # the first test is between Concept(foo) and int(2)
|
||||
|
||||
context.local_hints.add(BuiltinConcepts.EVAL_SUCCESS_REQUESTED)
|
||||
context.local_hints.add(BuiltinConcepts.EVAL_UNTIL_SUCCESS_REQUESTED)
|
||||
evaluated = python_evaluator.eval(context, parsed)
|
||||
assert evaluated.status
|
||||
assert evaluated.value # we test until we compare foo.body and 2
|
||||
@@ -224,3 +224,18 @@ class TestPythonEvaluator(TestUsingMemoryBasedSheerka):
|
||||
assert isinstance(error1.error, TypeError)
|
||||
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!'"}
|
||||
|
||||
@@ -0,0 +1,74 @@
|
||||
import pytest
|
||||
from core.concept import Concept
|
||||
from evaluators.ResolveAmbiguityEvaluator import ResolveAmbiguityEvaluator
|
||||
|
||||
from tests.BaseTest import BaseTest
|
||||
from tests.TestUsingMemoryBasedSheerka import TestUsingMemoryBasedSheerka
|
||||
|
||||
|
||||
pretval = BaseTest.pretval
|
||||
|
||||
|
||||
class TestResolveAmbiguityEvaluator(TestUsingMemoryBasedSheerka):
|
||||
|
||||
@pytest.mark.parametrize("return_values, expected", [
|
||||
([pretval(Concept("foo"), source="source"), pretval(Concept("bar"), source="source")], True),
|
||||
([pretval(Concept("foo"), source="source"), pretval(Concept("bar"), source="source", status=False)], False),
|
||||
([pretval(Concept("foo"), source="source1"), pretval(Concept("bar"), source="source2")], False),
|
||||
])
|
||||
def test_i_can_match(self, return_values, expected):
|
||||
context = self.get_context()
|
||||
assert ResolveAmbiguityEvaluator().matches(context, return_values) == expected
|
||||
|
||||
def test_i_can_manage_when_no_source(self):
|
||||
context = self.get_context()
|
||||
return_values = [BaseTest.retval(Concept("foo"))]
|
||||
|
||||
assert not ResolveAmbiguityEvaluator().matches(context, return_values)
|
||||
|
||||
def test_i_can_eval(self):
|
||||
context = self.get_context()
|
||||
return_values = [
|
||||
self.pretval(Concept("hello a").def_var("a", "world"), "hello word"),
|
||||
self.pretval(Concept("hello world"), "hello word"),
|
||||
self.pretval(Concept("hello world", pre="False"), "hello word"),
|
||||
self.retval(Concept("not a parser result")),
|
||||
self.retval(Concept("status is false"), status=False),
|
||||
self.pretval(Concept("false parser result"), status=False),
|
||||
]
|
||||
|
||||
evaluator = ResolveAmbiguityEvaluator()
|
||||
evaluator.matches(context, return_values)
|
||||
res = evaluator.eval(context, return_values)
|
||||
|
||||
assert len(res) == 1
|
||||
resolved = res[0]
|
||||
|
||||
assert resolved.who == evaluator.name
|
||||
assert resolved.body == return_values[1].body
|
||||
assert resolved.parents == [
|
||||
return_values[0],
|
||||
return_values[1],
|
||||
return_values[2],
|
||||
]
|
||||
|
||||
def test_i_can_eval_all_fail(self):
|
||||
context = self.get_context()
|
||||
return_values = [
|
||||
self.pretval(Concept("hello world", pre="2 < 1"), "hello word"),
|
||||
self.pretval(Concept("hello world", pre="False"), "hello word"),
|
||||
]
|
||||
|
||||
evaluator = ResolveAmbiguityEvaluator()
|
||||
evaluator.matches(context, return_values)
|
||||
res = evaluator.eval(context, return_values)
|
||||
|
||||
assert len(res) == 1
|
||||
resolved = res[0]
|
||||
|
||||
assert resolved.who == evaluator.name
|
||||
assert resolved.body == []
|
||||
assert resolved.parents == [
|
||||
return_values[0],
|
||||
return_values[1],
|
||||
]
|
||||
Reference in New Issue
Block a user