Refactored Caching, Refactored BnfNodeParser, Introduced Sphinx
This commit is contained in:
@@ -1,15 +1,15 @@
|
||||
import pytest
|
||||
from core.builtin_concepts import BuiltinConcepts
|
||||
from core.concept import Concept, PROPERTIES_TO_SERIALIZE, Property, simplec
|
||||
from core.concept import Concept, PROPERTIES_TO_SERIALIZE, simplec
|
||||
from evaluators.MutipleSameSuccessEvaluator import MultipleSameSuccessEvaluator
|
||||
from parsers.BaseNodeParser import SyaAssociativity
|
||||
from parsers.BnfNodeParser import Sequence, StrMatch, OrderedChoice, Optional, ConceptExpression
|
||||
from sdp.sheerkaDataProvider import SheerkaDataProvider
|
||||
|
||||
from tests.TestUsingFileBasedSheerka import TestUsingFileBasedSheerka
|
||||
from tests.TestUsingMemoryBasedSheerka import TestUsingMemoryBasedSheerka
|
||||
|
||||
|
||||
class TestSheerkaNonReg(TestUsingFileBasedSheerka):
|
||||
class TestSheerkaNonRegMemory(TestUsingMemoryBasedSheerka):
|
||||
|
||||
def init_scenario(self, init_expressions):
|
||||
sheerka = self.get_sheerka()
|
||||
@@ -105,10 +105,10 @@ as:
|
||||
expected = self.get_default_concept()
|
||||
expected.metadata.id = "1001"
|
||||
expected.metadata.desc = None
|
||||
expected.metadata.props = [("a", None), ("b", None)]
|
||||
expected.metadata.variables = [("a", None), ("b", None)]
|
||||
expected.init_key()
|
||||
|
||||
sheerka = self.get_sheerka()
|
||||
sheerka = self.get_sheerka(cache_only=False)
|
||||
res = sheerka.evaluate_user_input(text)
|
||||
|
||||
assert len(res) == 1
|
||||
@@ -120,21 +120,15 @@ as:
|
||||
for prop in PROPERTIES_TO_SERIALIZE:
|
||||
assert getattr(concept_saved.metadata, prop) == getattr(expected.metadata, prop)
|
||||
|
||||
assert concept_saved.key in sheerka.cache_by_key
|
||||
assert concept_saved.id in sheerka.cache_by_id
|
||||
assert sheerka.sdp.io.exists(
|
||||
sheerka.sdp.io.get_obj_path(SheerkaDataProvider.ObjectsFolder, concept_saved.get_origin()))
|
||||
# cache is up to date
|
||||
assert sheerka.has_key(concept_saved.key)
|
||||
assert sheerka.has_id(concept_saved.id)
|
||||
assert sheerka.has_name(concept_saved.name)
|
||||
assert sheerka.has_hash(concept_saved.get_definition_hash())
|
||||
assert sheerka.cache_manager.copy(sheerka.CONCEPTS_BY_FIRST_KEYWORD_ENTRY) == {'+': ['1001']}
|
||||
|
||||
def test_i_can_def_several_concepts(self):
|
||||
sheerka = self.get_sheerka(use_dict=False)
|
||||
sheerka.evaluate_user_input("def concept foo")
|
||||
|
||||
sheerka = self.get_sheerka(use_dict=False)
|
||||
res = sheerka.evaluate_user_input("def concept bar")
|
||||
|
||||
assert len(res) == 1
|
||||
assert res[0].status
|
||||
assert res[0].body.body.id == "1002"
|
||||
# sdp is up to date
|
||||
assert sheerka.sdp.exists(sheerka.CONCEPTS_BY_KEY_ENTRY, expected.key)
|
||||
|
||||
def test_i_can_evaluate_def_concept_part_when_one_part_is_a_ref_of_another_concept(self):
|
||||
"""
|
||||
@@ -145,11 +139,11 @@ as:
|
||||
sheerka = self.get_sheerka()
|
||||
|
||||
# concept 'a plus b' is known
|
||||
concept_a_plus_b = Concept(name="a plus b").def_prop("a").def_prop("b")
|
||||
concept_a_plus_b = Concept(name="a plus b").def_var("a").def_var("b").init_key()
|
||||
sheerka.add_in_cache(concept_a_plus_b)
|
||||
|
||||
res = sheerka.evaluate_user_input("def concept a xx b as a plus b")
|
||||
expected = Concept(name="a xx b", body="a plus b").def_prop("a").def_prop("b").init_key()
|
||||
expected = Concept(name="a xx b", body="a plus b").def_var("a").def_var("b").init_key()
|
||||
expected.metadata.id = "1001"
|
||||
|
||||
assert len(res) == 1
|
||||
@@ -161,10 +155,7 @@ as:
|
||||
for prop in PROPERTIES_TO_SERIALIZE:
|
||||
assert getattr(concept_saved.metadata, prop) == getattr(expected.metadata, prop)
|
||||
|
||||
assert concept_saved.key in sheerka.cache_by_key
|
||||
assert concept_saved.id in sheerka.cache_by_id
|
||||
assert sheerka.sdp.io.exists(
|
||||
sheerka.sdp.io.get_obj_path(SheerkaDataProvider.ObjectsFolder, concept_saved.get_origin()))
|
||||
assert sheerka.has_key(concept_saved.key)
|
||||
|
||||
def test_i_cannot_evaluate_the_same_def_concept_twice(self):
|
||||
text = """
|
||||
@@ -202,7 +193,7 @@ as:
|
||||
|
||||
def test_i_can_recognize_concept_with_variable(self):
|
||||
sheerka = self.get_sheerka()
|
||||
concept_hello = Concept(name="hello a").def_prop("a")
|
||||
concept_hello = Concept(name="hello a").def_var("a")
|
||||
concept_foo = Concept(name="foo")
|
||||
sheerka.add_in_cache(concept_hello)
|
||||
sheerka.add_in_cache(concept_foo)
|
||||
@@ -212,15 +203,15 @@ as:
|
||||
assert len(res) == 1
|
||||
assert res[0].status
|
||||
assert sheerka.isinstance(return_value, concept_hello)
|
||||
assert return_value.metadata.props[0] == ('a', "foo")
|
||||
assert return_value.metadata.variables[0] == ('a', "foo")
|
||||
|
||||
# sanity check
|
||||
evaluated = sheerka.evaluate_concept(self.get_context(eval_body=True), return_value)
|
||||
assert evaluated.props["a"].value == concept_foo
|
||||
assert evaluated.get_value("a") == concept_foo
|
||||
|
||||
def test_i_can_recognize_concept_with_variable_and_python_as_body(self):
|
||||
sheerka = self.get_sheerka()
|
||||
hello_a = sheerka.add_in_cache(Concept(name="hello a", body="'hello ' + a").def_prop("a"))
|
||||
hello_a = sheerka.add_in_cache(Concept(name="hello a", body="'hello ' + a").def_var("a"))
|
||||
sheerka.add_in_cache(Concept(name="foo", body="'foo'"))
|
||||
|
||||
res = sheerka.evaluate_user_input("hello foo")
|
||||
@@ -232,15 +223,14 @@ as:
|
||||
evaluated = sheerka.evaluate_concept(self.get_context(eval_body=True), res[0].value)
|
||||
assert evaluated.body == "hello foo"
|
||||
assert evaluated.metadata.is_evaluated
|
||||
assert evaluated.props["a"].value == simplec("foo", "foo")
|
||||
assert evaluated.props["a"].value.metadata.is_evaluated
|
||||
assert evaluated.get_value("a") == simplec("foo", "foo")
|
||||
assert evaluated.get_value("a").metadata.is_evaluated
|
||||
|
||||
def test_i_can_recognize_duplicate_concepts_with_same_value(self):
|
||||
sheerka = self.get_sheerka()
|
||||
|
||||
sheerka.add_in_cache(Concept(name="hello a", body="'hello ' + a").def_prop("a"))
|
||||
sheerka.add_in_cache(Concept(name="hello foo", body="'hello foo'"))
|
||||
sheerka.add_in_cache(Concept(name="foo", body="'foo'"))
|
||||
self.create_concept_lite(sheerka, Concept(name="hello a", body="'hello ' + a"), variables=["a"])
|
||||
self.create_concept_lite(sheerka, Concept(name="hello foo", body="'hello foo'"))
|
||||
self.create_concept_lite(sheerka, Concept(name="foo", body="'foo'"))
|
||||
|
||||
res = sheerka.evaluate_user_input("hello foo")
|
||||
assert len(res) == 1
|
||||
@@ -250,10 +240,9 @@ as:
|
||||
|
||||
def test_i_cannot_manage_duplicate_concepts_when_the_values_are_different(self):
|
||||
sheerka = self.get_sheerka()
|
||||
|
||||
sheerka.add_in_cache(Concept(name="hello a", body="'hello ' + a").def_prop("a"))
|
||||
sheerka.add_in_cache(Concept(name="hello foo", body="'hello foo'"))
|
||||
sheerka.add_in_cache(Concept(name="foo", body="'another value'"))
|
||||
self.create_concept_lite(sheerka, Concept(name="hello a", body="'hello ' + a"), variables=["a"])
|
||||
self.create_concept_lite(sheerka, Concept(name="hello foo", body="'hello foo'"))
|
||||
self.create_concept_lite(sheerka, Concept(name="foo", body="'another value'"))
|
||||
|
||||
res = sheerka.evaluate_user_input("hello foo")
|
||||
assert len(res) == 1
|
||||
@@ -270,8 +259,8 @@ as:
|
||||
sheerka = self.get_sheerka()
|
||||
context = self.get_context(sheerka)
|
||||
|
||||
sheerka.create_new_concept(context, Concept(name="hello a", body="'hello ' + a").def_prop("a"))
|
||||
sheerka.create_new_concept(context, Concept(name="hello b", body="'hello ' + b").def_prop("b"))
|
||||
sheerka.create_new_concept(context, Concept(name="hello a", body="'hello ' + a").def_var("a"))
|
||||
sheerka.create_new_concept(context, Concept(name="hello b", body="'hello ' + b").def_var("b"))
|
||||
|
||||
res = sheerka.evaluate_user_input("hello 'foo'")
|
||||
assert len(res) == 1
|
||||
@@ -283,42 +272,12 @@ as:
|
||||
sheerka = self.get_sheerka()
|
||||
context = self.get_context(sheerka)
|
||||
|
||||
sheerka.create_new_concept(context, Concept(name="concepts", body="sheerka.concepts()"))
|
||||
sheerka.create_new_concept(context, Concept(name="concepts", body="sheerka.test()"))
|
||||
res = sheerka.evaluate_user_input("eval concepts")
|
||||
|
||||
assert len(res) == 1
|
||||
assert res[0].status
|
||||
assert isinstance(res[0].value, list)
|
||||
|
||||
def test_i_can_create_concept_with_bnf_definition(self):
|
||||
sheerka = self.get_sheerka(use_dict=False, skip_builtins_in_db=False)
|
||||
a = Concept("a")
|
||||
sheerka.add_in_cache(a)
|
||||
sheerka.concepts_definition_cache = {a: OrderedChoice("one", "two")}
|
||||
|
||||
res = sheerka.evaluate_user_input("def concept plus from bnf a ('plus' plus)?")
|
||||
assert len(res) == 1
|
||||
assert res[0].status
|
||||
assert sheerka.isinstance(res[0].value, BuiltinConcepts.NEW_CONCEPT)
|
||||
|
||||
saved_concept = sheerka.sdp.get_safe(sheerka.CONCEPTS_ENTRY, "plus")
|
||||
assert saved_concept.key == "plus"
|
||||
assert saved_concept.metadata.definition == "a ('plus' plus)?"
|
||||
assert "a" in saved_concept.props
|
||||
assert "plus" in saved_concept.props
|
||||
|
||||
saved_definitions = sheerka.sdp.get_safe(sheerka.CONCEPTS_DEFINITIONS_ENTRY)
|
||||
expected_bnf = Sequence(
|
||||
ConceptExpression(a, rule_name="a"),
|
||||
Optional(Sequence(StrMatch("plus"), ConceptExpression(saved_concept, rule_name="plus"))))
|
||||
assert saved_definitions["c:plus|1001:"] == "(c:a:=a ('plus' c:plus|1001:=plus)?)"
|
||||
|
||||
new_concept = res[0].value.body
|
||||
assert new_concept.metadata.name == "plus"
|
||||
assert new_concept.metadata.definition == "a ('plus' plus)?"
|
||||
assert new_concept.bnf == expected_bnf
|
||||
assert "a" in new_concept.props
|
||||
assert "plus" in new_concept.props
|
||||
assert res[0].value == sheerka.test()
|
||||
|
||||
def test_i_can_recognize_bnf_definitions(self):
|
||||
sheerka = self.get_sheerka()
|
||||
@@ -344,41 +303,11 @@ as:
|
||||
assert sheerka.isinstance(return_value, concept_b)
|
||||
|
||||
# sanity check
|
||||
evaluated = sheerka.evaluate_concept(self.get_context(eval_body=True), return_value)
|
||||
evaluated = sheerka.evaluate_concept(self.get_context(sheerka=sheerka, eval_body=True), return_value)
|
||||
assert evaluated.body == "one three"
|
||||
assert evaluated.metadata.is_evaluated
|
||||
assert evaluated.props["a"] == Property("a", sheerka.new(concept_a.key, body="one").init_key())
|
||||
assert evaluated.props["a"].value.metadata.is_evaluated
|
||||
|
||||
def test_i_can_recognize_bnf_definitions_from_separate_instances(self):
|
||||
"""
|
||||
Same test then before,
|
||||
but make sure that the BNF are correctly persisted and loaded
|
||||
"""
|
||||
sheerka = self.get_sheerka(use_dict=False)
|
||||
concept_a = sheerka.evaluate_user_input("def concept a from bnf 'one' 'two'")[0].body.body
|
||||
|
||||
res = self.get_sheerka(use_dict=False).evaluate_user_input("one two")
|
||||
assert len(res) == 1
|
||||
assert res[0].status
|
||||
assert sheerka.isinstance(res[0].value, concept_a)
|
||||
|
||||
# add another bnf definition
|
||||
concept_b = sheerka.evaluate_user_input("def concept b from bnf a 'three'")[0].body.body
|
||||
|
||||
res = self.get_sheerka(use_dict=False).evaluate_user_input("one two") # previous one still works
|
||||
assert len(res) == 1
|
||||
assert res[0].status
|
||||
assert sheerka.isinstance(res[0].value, concept_a)
|
||||
|
||||
res = self.get_sheerka(use_dict=False).evaluate_user_input("one two three") # new one works
|
||||
assert len(res) == 1
|
||||
assert res[0].status
|
||||
assert sheerka.isinstance(res[0].value, concept_b)
|
||||
|
||||
evaluated = sheerka.evaluate_concept(self.get_context(eval_body=True), res[0].value)
|
||||
assert evaluated.body == "one two three"
|
||||
assert evaluated.props["a"] == Property("a", sheerka.new(concept_a.key, body="one two").init_key())
|
||||
assert evaluated.get_value("a") == sheerka.new(concept_a.key, body="one").init_key()
|
||||
assert evaluated.get_value("a").metadata.is_evaluated
|
||||
|
||||
@pytest.mark.parametrize("user_input", [
|
||||
"def concept greetings from def hello a where a",
|
||||
@@ -393,7 +322,7 @@ as:
|
||||
assert res[0].status
|
||||
concept_found = res[0].value
|
||||
assert sheerka.isinstance(concept_found, greetings)
|
||||
assert concept_found.get_prop("a") == "foo"
|
||||
assert concept_found.get_value("a") == "foo"
|
||||
assert concept_found.metadata.need_validation
|
||||
|
||||
res = sheerka.evaluate_user_input("greetings")
|
||||
@@ -401,10 +330,9 @@ as:
|
||||
assert res[0].status
|
||||
concept_found = res[0].value
|
||||
assert sheerka.isinstance(concept_found, greetings)
|
||||
assert concept_found.get_prop("a") is None
|
||||
assert concept_found.get_value("a") is None
|
||||
assert not concept_found.metadata.need_validation
|
||||
|
||||
# @pytest.mark.xfail
|
||||
@pytest.mark.parametrize("desc, definitions", [
|
||||
("Simple form", [
|
||||
"def concept one as 1",
|
||||
@@ -452,7 +380,7 @@ as:
|
||||
assert len(res) == 1
|
||||
assert res[0].status
|
||||
assert sheerka.isinstance(res[0].body, "twenties")
|
||||
assert sheerka.evaluate_concept(self.get_context(eval_body=True), res[0].body).body == 21
|
||||
assert sheerka.evaluate_concept(self.get_context(sheerka=sheerka, eval_body=True), res[0].body).body == 21
|
||||
|
||||
res = sheerka.evaluate_user_input("twenty one + 1")
|
||||
assert len(res) == 1
|
||||
@@ -479,7 +407,6 @@ as:
|
||||
assert res[0].status
|
||||
assert res[0].body == 23
|
||||
|
||||
# @pytest.mark.xfail
|
||||
def test_i_can_mix_bnf_and_isa(self):
|
||||
"""
|
||||
if 'one' isa 'number, twenty number should be recognized
|
||||
@@ -497,7 +424,7 @@ as:
|
||||
assert len(res) == 1
|
||||
assert res[0].status
|
||||
assert sheerka.isinstance(res[0].body, "twenties")
|
||||
assert sheerka.evaluate_concept(self.get_context(eval_body=True), res[0].value).body == 21
|
||||
assert sheerka.evaluate_concept(self.get_context(sheerka=sheerka, eval_body=True), res[0].value).body == 21
|
||||
|
||||
res = sheerka.evaluate_user_input("twenty one + 1")
|
||||
assert len(res) == 1
|
||||
@@ -524,7 +451,7 @@ as:
|
||||
assert res[0].status
|
||||
assert res[0].body == 23
|
||||
|
||||
def test_i_can_mix_bnf_and_isa_when_concept_other_case(self):
|
||||
def test_i_can_mix_bnf_and_isa_2(self):
|
||||
sheerka = self.get_sheerka()
|
||||
|
||||
init = [
|
||||
@@ -544,7 +471,6 @@ as:
|
||||
assert res[0].status
|
||||
assert res[0].body == 21
|
||||
|
||||
# @pytest.mark.xfail
|
||||
def test_i_can_use_concepts_defined_with_from(self):
|
||||
sheerka = self.get_sheerka()
|
||||
|
||||
@@ -656,31 +582,6 @@ as:
|
||||
assert res[0].status
|
||||
assert res[0].body == 3
|
||||
|
||||
@pytest.mark.xfail
|
||||
def test_i_can_recognize_composition_of_concept(self):
|
||||
sheerka = self.get_sheerka()
|
||||
|
||||
definitions = [
|
||||
"def concept little a where a",
|
||||
"def concept blue a where a",
|
||||
"def concept house"
|
||||
]
|
||||
|
||||
for definition in definitions:
|
||||
sheerka.evaluate_user_input(definition)
|
||||
|
||||
### CAUTION ####
|
||||
# this test cannot work !!
|
||||
# it is just to hint the result that I would like to achieve
|
||||
|
||||
res = sheerka.evaluate_user_input("little blue house")
|
||||
assert len(res) == 2
|
||||
assert res[0].status
|
||||
assert res[0].body == "little(blue(house))"
|
||||
|
||||
assert res[1].status
|
||||
assert res[1].body == "little blue(house)"
|
||||
|
||||
def test_i_can_say_that_a_concept_isa_another_concept(self):
|
||||
sheerka = self.get_sheerka()
|
||||
sheerka.evaluate_user_input("def concept foo")
|
||||
@@ -779,36 +680,35 @@ as:
|
||||
sheerka.evaluate_user_input(exp)
|
||||
|
||||
res = sheerka.evaluate_user_input("twenty one")
|
||||
assert len(res) == 1 and res[0].status and sheerka.isinstance(res[0].body, "twenties")
|
||||
assert len(res) == 1
|
||||
assert res[0].status
|
||||
assert sheerka.isinstance(res[0].body, "twenties")
|
||||
|
||||
res = sheerka.evaluate_user_input("eval twenty one")
|
||||
assert len(res) == 1 and res[0].status and res[0].body == 21
|
||||
assert len(res) == 1
|
||||
assert res[0].status
|
||||
assert res[0].body == 21
|
||||
|
||||
res = sheerka.evaluate_user_input("twenty two")
|
||||
assert len(res) == 1 and res[0].status and sheerka.isinstance(res[0].body, "twenties")
|
||||
assert len(res) == 1
|
||||
assert res[0].status
|
||||
assert sheerka.isinstance(res[0].body, "twenties")
|
||||
|
||||
res = sheerka.evaluate_user_input("eval twenty two")
|
||||
assert len(res) == 1 and res[0].status and res[0].body == 22
|
||||
assert len(res) == 1
|
||||
assert res[0].status
|
||||
assert res[0].body == 22
|
||||
|
||||
res = sheerka.evaluate_user_input("twenty three")
|
||||
assert len(res) == 1
|
||||
assert not res[0].status
|
||||
assert sheerka.isinstance(res[0].body, BuiltinConcepts.WHERE_CLAUSE_FAILED)
|
||||
assert sheerka.isinstance(res[0].body, BuiltinConcepts.MULTIPLE_ERRORS)
|
||||
assert str(BuiltinConcepts.WHERE_CLAUSE_FAILED) in [error.key for error in sheerka.get_error(res[0].body.body)]
|
||||
|
||||
res = sheerka.evaluate_user_input("eval twenty three")
|
||||
assert len(res) == 1
|
||||
assert not res[0].status
|
||||
assert sheerka.isinstance(res[0].body, BuiltinConcepts.WHERE_CLAUSE_FAILED)
|
||||
|
||||
|
||||
# def test_i_can_detect_when_only_one_evaluator_is_in_error(self):
|
||||
# sheerka = self.get_sheerka()
|
||||
#
|
||||
# sheerka.evaluate_user_input("def concept 1 as one")
|
||||
# res = sheerka.evaluate_user_input("eval 1")
|
||||
# assert len(res) == 1
|
||||
# assert not res[0].status
|
||||
# assert sheerka.isinstance(res[0].body, BuiltinConcepts.CONCEPT_EVAL_ERROR)
|
||||
assert str(BuiltinConcepts.WHERE_CLAUSE_FAILED) in [error.key for error in sheerka.get_error(res[0].body.body)]
|
||||
|
||||
def test_i_can_manage_some_type_of_infinite_recursion(self):
|
||||
sheerka = self.get_sheerka()
|
||||
@@ -862,7 +762,7 @@ as:
|
||||
assert not res[0].status
|
||||
assert sheerka.isinstance(res[0].body, BuiltinConcepts.WHERE_CLAUSE_FAILED)
|
||||
|
||||
@pytest.mark.xfail
|
||||
@pytest.mark.skip("Not ready for that")
|
||||
def test_i_can_manage_missing_variables_from_bnf_parsing(self):
|
||||
definitions = [
|
||||
"def concept one as 1",
|
||||
@@ -894,8 +794,8 @@ as:
|
||||
assert len(res) == 1
|
||||
assert res[0].status
|
||||
|
||||
twenties = sheerka.get("twenties")
|
||||
number = sheerka.get("number")
|
||||
twenties = sheerka.get_by_key("twenties")
|
||||
number = sheerka.get_by_key("number")
|
||||
assert sheerka.isa(twenties, number)
|
||||
|
||||
def test_i_can_mix_sya_concepts_and_bnf_concept(self):
|
||||
@@ -910,9 +810,9 @@ as:
|
||||
|
||||
sheerka = self.init_scenario(definitions)
|
||||
context = self.get_context(sheerka)
|
||||
sheerka.set_sya_def(context, [
|
||||
(sheerka.get("mult").id, 20, SyaAssociativity.Right),
|
||||
(sheerka.get("plus").id, 10, SyaAssociativity.Right),
|
||||
sheerka.force_sya_def(context, [
|
||||
(sheerka.get_by_name("mult").id, 20, SyaAssociativity.Right),
|
||||
(sheerka.get_by_name("plus").id, 10, SyaAssociativity.Right),
|
||||
])
|
||||
|
||||
res = sheerka.evaluate_user_input("eval one plus two mult three")
|
||||
@@ -954,3 +854,71 @@ as:
|
||||
assert len(res) == 1
|
||||
assert res[0].status
|
||||
assert res[0].body == 64
|
||||
|
||||
|
||||
class TestSheerkaNonRegFile(TestUsingFileBasedSheerka):
|
||||
def test_i_can_def_several_concepts(self):
|
||||
sheerka = self.get_sheerka()
|
||||
sheerka.evaluate_user_input("def concept foo")
|
||||
|
||||
sheerka = self.get_sheerka()
|
||||
res = sheerka.evaluate_user_input("def concept bar")
|
||||
|
||||
assert len(res) == 1
|
||||
assert res[0].status
|
||||
assert res[0].body.body.id == "1002"
|
||||
|
||||
def test_i_can_create_concept_with_bnf_definition(self):
|
||||
sheerka = self.get_sheerka()
|
||||
concept_a = self.bnf_concept("a", expression=OrderedChoice(StrMatch("one"), StrMatch("two")))
|
||||
sheerka.create_new_concept(self.get_context(sheerka), concept_a)
|
||||
|
||||
res = sheerka.evaluate_user_input("def concept plus from bnf a ('plus' plus)?")
|
||||
assert len(res) == 1
|
||||
assert res[0].status
|
||||
assert sheerka.isinstance(res[0].value, BuiltinConcepts.NEW_CONCEPT)
|
||||
|
||||
saved_concept = sheerka.sdp.get(sheerka.CONCEPTS_BY_KEY_ENTRY, "plus")
|
||||
assert saved_concept.key == "plus"
|
||||
assert saved_concept.metadata.definition == "a ('plus' plus)?"
|
||||
assert "a" in saved_concept.values
|
||||
assert "plus" in saved_concept.values
|
||||
|
||||
expected_bnf = Sequence(
|
||||
ConceptExpression(concept_a, rule_name="a"),
|
||||
Optional(Sequence(StrMatch("plus"), ConceptExpression("plus"))))
|
||||
|
||||
new_concept = res[0].value.body
|
||||
assert new_concept.metadata.name == "plus"
|
||||
assert new_concept.metadata.definition == "a ('plus' plus)?"
|
||||
assert new_concept.bnf == expected_bnf
|
||||
assert "a" in new_concept.values
|
||||
assert "plus" in new_concept.values
|
||||
|
||||
def test_i_can_recognize_bnf_definitions_from_separate_instances(self):
|
||||
sheerka = self.get_sheerka()
|
||||
concept_a = sheerka.evaluate_user_input("def concept a from bnf 'one' 'two'")[0].body.body
|
||||
|
||||
sheerka = self.get_sheerka()
|
||||
res = sheerka.evaluate_user_input("one two")
|
||||
assert len(res) == 1
|
||||
assert res[0].status
|
||||
assert sheerka.isinstance(res[0].value, concept_a)
|
||||
|
||||
# add another bnf definition
|
||||
concept_b = sheerka.evaluate_user_input("def concept b from bnf a 'three'")[0].body.body
|
||||
|
||||
sheerka = self.get_sheerka()
|
||||
res = sheerka.evaluate_user_input("one two") # previous one still works
|
||||
assert len(res) == 1
|
||||
assert res[0].status
|
||||
assert sheerka.isinstance(res[0].value, concept_a)
|
||||
|
||||
res = self.get_sheerka().evaluate_user_input("one two three") # new one works
|
||||
assert len(res) == 1
|
||||
assert res[0].status
|
||||
assert sheerka.isinstance(res[0].value, concept_b)
|
||||
|
||||
evaluated = sheerka.evaluate_concept(self.get_context(eval_body=True), res[0].value)
|
||||
assert evaluated.body == "one two three"
|
||||
assert evaluated.get_value("a") == sheerka.new(concept_a.key, body="one two").init_key()
|
||||
|
||||
Reference in New Issue
Block a user