Skip to content

Commit

Permalink
Remove self.facts reset in from_cypher (#33)
Browse files Browse the repository at this point in the history
* Remove self.facts reset in from_cypher

* Add unit tests
  • Loading branch information
acazau authored Aug 13, 2024
1 parent ab3c2cd commit 82b4671
Show file tree
Hide file tree
Showing 3 changed files with 79 additions and 1 deletion.
1 change: 0 additions & 1 deletion hybridagi/core/datatypes.py
Original file line number Diff line number Diff line change
Expand Up @@ -160,7 +160,6 @@ def to_cypher(self) -> str:

def from_cypher(self, cypher_facts: str, metadata: Dict[str, Any] = {}):
triplets = re.findall(CYPHER_FACT_REGEX, cypher_facts)
self.facts = []
for triplet in triplets:
subject_label, subject_name, predicate, object_label, object_name = triplet
self.facts.append(Fact(
Expand Down
23 changes: 23 additions & 0 deletions tests/core/test_datatypes.py
Original file line number Diff line number Diff line change
Expand Up @@ -124,3 +124,26 @@ def test_interaction_session_with_chat():
session.chat.msgs.append(dt.Message(role=dt.Role.User, content="Can you tell me what is the capital of France?"))
assert session.chat.msgs[0].content == "Hello, I'm an AI assistant what can I do to help you?"
assert session.chat.msgs[1].content == "Can you tell me what is the capital of France?"

def test_fact_list_from_cypher():
cypher_facts = """
(:Person {name:"John"})-[:KNOWS]->(:Person {name:"Jane"}),
(:City {name:"New York"})-[:LOCATED_IN]->(:Country {name:"USA"})
"""
fact_list = dt.FactList().from_cypher(cypher_facts)

assert len(fact_list.facts) == 2

# Test first fact
assert fact_list.facts[0].subj.label == "Person"
assert fact_list.facts[0].subj.name == "John"
assert fact_list.facts[0].rel.name == "KNOWS"
assert fact_list.facts[0].obj.label == "Person"
assert fact_list.facts[0].obj.name == "Jane"

# Test second fact
assert fact_list.facts[1].subj.label == "City"
assert fact_list.facts[1].subj.name == "New York"
assert fact_list.facts[1].rel.name == "LOCATED_IN"
assert fact_list.facts[1].obj.label == "Country"
assert fact_list.facts[1].obj.name == "USA"
56 changes: 56 additions & 0 deletions tests/modules/extractors/test_llm_fact_extractor.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,56 @@
import dspy
from hybridagi.modules.extractors.llm_fact_extractor import LLMFactExtractor
from hybridagi.core.datatypes import Document, DocumentList, FactList

from dspy.utils.dummies import DummyLM

def test_llm_fact_extractor_with_document():
answers = ['(:Person {name:"Bob"})-[:KNOWS]->(:Person {name:"Alice"})']
dspy.settings.configure(lm=DummyLM(answers=answers))

extractor = LLMFactExtractor()

doc = Document(text="Bob knows Alice.")
result = extractor.forward(doc)

assert isinstance(result, FactList)
assert len(result.facts) == 1
assert result.facts[0].subj.label == "Person"
assert result.facts[0].subj.name == "Bob"
assert result.facts[0].rel.name == "KNOWS"
assert result.facts[0].obj.label == "Person"
assert result.facts[0].obj.name == "Alice"

def test_llm_fact_extractor_with_document_list():
answers = [
'(:Person {name:"John"})-[:LIKES]->(:Fruit {name:"apples"})',
'(:Person {name:"Mary"})-[:HATES]->(:Fruit {name:"bananas"})'
]
dspy.settings.configure(lm=DummyLM(answers=answers))

extractor = LLMFactExtractor()

docs = DocumentList(docs=[
Document(text="John likes apples."),
Document(text="Mary hates bananas.")
])
result = extractor.forward(docs)

assert isinstance(result, FactList)
assert len(result.facts) == 2
assert result.facts[0].subj.name == "John"
assert result.facts[0].rel.name == "LIKES"
assert result.facts[0].obj.name == "apples"
assert result.facts[1].subj.name == "Mary"
assert result.facts[1].rel.name == "HATES"
assert result.facts[1].obj.name == "bananas"

def test_llm_fact_extractor_with_invalid_input():
extractor = LLMFactExtractor()

try:
extractor.forward("Invalid input")
except ValueError as e:
assert str(e) == "LLMFactExtractor input must be a Document or DocumentList"
else:
assert False, "ValueError was not raised"

0 comments on commit 82b4671

Please sign in to comment.