Added basic implentation for where

This commit is contained in:
2020-02-05 18:47:20 +01:00
parent a5a721094b
commit afc1e22949
35 changed files with 864 additions and 320 deletions
+134 -1
View File
@@ -1,10 +1,13 @@
from ast import Str
import pytest
from core.builtin_concepts import BuiltinConcepts
from core.concept import Concept, ConceptParts, DoNotResolve
from core.tokenizer import Tokenizer, TokenKind, Token
from parsers.BnfParser import BnfParser
from parsers.ConceptLexerParser import ConceptLexerParser, ConceptNode, Sequence, StrMatch, OrderedChoice, Optional, \
ParsingExpressionVisitor, TerminalNode, NonTerminalNode, ZeroOrMore, OneOrMore, \
UnrecognizedTokensNode, cnode, short_cnode
UnrecognizedTokensNode, cnode, short_cnode, ConceptExpression, ConceptGroupExpression
from tests.TestUsingMemoryBasedSheerka import TestUsingMemoryBasedSheerka
@@ -75,6 +78,7 @@ class TestConceptLexerParser(TestUsingMemoryBasedSheerka):
context = self.get_context()
for c in concepts:
context.sheerka.add_in_cache(c)
context.sheerka.set_id_if_needed(c, False)
parser = ConceptLexerParser()
parser.initialize(context, grammar)
@@ -586,6 +590,32 @@ class TestConceptLexerParser(TestUsingMemoryBasedSheerka):
assert res.status
assert res.value.body == [cnode("foo", 0, 2, "twenty one")]
def test_i_can_initialize_when_cyclic_reference(self):
foo = Concept(name="foo")
grammar = {foo: Optional("one", ConceptExpression("foo"))}
context, parser = self.init([foo], grammar)
assert parser.concepts_grammars[foo] == Optional("one", ConceptExpression(foo, rule_name="foo"))
def test_i_cannot_initialize_when_cyclic_reference_when_concept_is_under_construction_and_not_known(self):
foo = Concept(name="foo").init_key()
grammar = {foo: Optional("one", ConceptExpression("foo"))}
context = self.get_context()
parser = ConceptLexerParser()
parser.initialize(context, grammar)
assert parser.concepts_grammars[foo] == Optional("one", ConceptExpression("foo", rule_name="foo"))
def test_i_can_initialize_when_cyclic_reference_when_concept_is_under_construction_and_known(self):
foo = Concept(name="foo").init_key()
grammar = {foo: Optional("one", ConceptExpression("foo"))}
context = self.get_context()
context.concepts["foo"] = foo
parser = ConceptLexerParser()
parser.initialize(context, grammar)
assert parser.concepts_grammars[foo] == Optional("one", ConceptExpression(foo, rule_name="foo"))
def test_i_can_parse_concept_reference_that_is_group(self):
"""
if one is number, then number is a 'group'
@@ -1092,6 +1122,109 @@ class TestConceptLexerParser(TestUsingMemoryBasedSheerka):
assert cprop(concept_found, "seq")[1] == DoNotResolve("un ok")
assert cprop(concept_found, "seq")[2] == DoNotResolve("uno ok")
@pytest.mark.parametrize("rule, expected", [
(StrMatch("string"), "'string'"),
(StrMatch("string", rule_name="rule_name"), "'string'=rule_name"),
(Sequence(StrMatch("foo"), StrMatch("bar")), "('foo' 'bar')"),
(Sequence(StrMatch("foo"), StrMatch("bar"), rule_name="rule_name"), "('foo' 'bar')=rule_name"),
(OrderedChoice(StrMatch("foo"), StrMatch("bar")), "('foo'|'bar')"),
(OrderedChoice(StrMatch("foo"), StrMatch("bar"), rule_name="rule_name"), "('foo'|'bar')=rule_name"),
(Optional(StrMatch("foo")), "'foo'?"),
(Optional(StrMatch("foo"), rule_name="rule_name"), "'foo'?=rule_name"),
(ZeroOrMore(StrMatch("foo")), "'foo'*"),
(ZeroOrMore(StrMatch("foo"), rule_name="rule_name"), "'foo'*=rule_name"),
(OneOrMore(StrMatch("foo")), "'foo'+"),
(OneOrMore(StrMatch("foo"), rule_name="rule_name"), "'foo'+=rule_name"),
(Sequence(
Optional(StrMatch("foo"), rule_name="a"),
ZeroOrMore(StrMatch("bar"), rule_name="b"),
OneOrMore(StrMatch("baz"), rule_name="c"),
rule_name="d"), "('foo'?=a 'bar'*=b 'baz'+=c)=d"),
(OrderedChoice(
Optional(StrMatch("foo"), rule_name="a"),
ZeroOrMore(StrMatch("bar"), rule_name="b"),
OneOrMore(StrMatch("baz"), rule_name="c"),
rule_name="d"), "('foo'?=a|'bar'*=b|'baz'+=c)=d"),
(Sequence(
OrderedChoice(StrMatch("foo"), StrMatch("bar"), rule_name="a"),
OrderedChoice(StrMatch("x"), StrMatch("y"), rule_name="b"),
rule_name="c"), "(('foo'|'bar')=a ('x'|'y')=b)=c")
])
def test_i_can_encode_grammar(self, rule, expected):
foo = Concept(name="foo")
grammar = {foo: rule}
context, parser = self.init([foo], grammar)
encoded = parser.encode_grammar(parser.concepts_grammars)
assert encoded["c:foo|1001:"] == expected
bnf_parser = BnfParser()
parse_res = bnf_parser.parse(context, encoded["c:foo|1001:"])
assert parse_res.status
assert parse_res.value.value == rule
def test_i_can_encode_grammar_when_concept_simple(self):
foo = Concept(name="foo")
bar = Concept(name="bar")
grammar = {foo: ConceptExpression(bar)}
context, parser = self.init([foo, bar], grammar)
encoded = parser.encode_grammar(parser.concepts_grammars)
assert encoded["c:foo|1001:"] == "c:bar|1002:=bar"
bnf_parser = BnfParser()
parse_res = bnf_parser.parse(context, encoded["c:foo|1001:"])
assert parse_res.status
assert parse_res.value.value == grammar[foo]
def test_i_can_encode_grammar_when_concepts(self):
foo = Concept(name="foo")
bar = Concept(name="bar")
baz = Concept(name="baz")
grammar = {foo: Sequence(
StrMatch("a"),
OrderedChoice(ConceptExpression(bar),
OneOrMore(ConceptExpression(baz)), rule_name="oc"), rule_name="s")}
context, parser = self.init([foo, bar, baz], grammar)
encoded = parser.encode_grammar(parser.concepts_grammars)
assert encoded["c:foo|1001:"] == "('a' (c:bar|1002:=bar|c:baz|1003:=baz+)=oc)=s"
bnf_parser = BnfParser()
parse_res = bnf_parser.parse(context, encoded["c:foo|1001:"])
assert parse_res.status
assert parse_res.value.value == grammar[foo]
def test_i_can_encode_grammar_when_set_concepts(self):
foo = Concept(name="foo")
bar = Concept(name="bar")
baz = Concept(name="baz")
grammar = {foo: Sequence(
StrMatch("a"),
OrderedChoice(bar,
OneOrMore(ConceptExpression(baz)), rule_name="oc"), rule_name="s")}
context = self.get_context()
for c in [foo, bar, baz]:
context.sheerka.add_in_cache(c)
context.sheerka.set_id_if_needed(c, False)
context.sheerka.add_concept_to_set(context, baz, bar)
parser = ConceptLexerParser()
parser.initialize(context, grammar)
encoded = parser.encode_grammar(parser.concepts_grammars)
assert encoded["c:foo|1001:"] == "('a' (c:bar|1002:=bar|c:baz|1003:=baz+)=oc)=s"
bnf_parser = BnfParser()
parse_res = bnf_parser.parse(context, encoded["c:foo|1001:"])
assert parse_res.status
expected = Sequence(
StrMatch("a"),
OrderedChoice(ConceptGroupExpression(bar, rule_name="bar"),
OneOrMore(ConceptExpression(baz, rule_name="baz")), rule_name="oc"), rule_name="s")
assert parse_res.value.value == expected
#
# def test_i_can_parse_basic_arithmetic_operations_and_resolve_properties(self):
# context = self.get_context()