Implementing Contradiction Detection in MemPalace: A Complete Technical Guide
MemPalace performs offline contradiction detection by comparing user-supplied text against a local Entity Registry and temporal Knowledge Graph, identifying similar-name confusion and relationship mismatches without requiring external API calls.
MemPalace is a privacy-first knowledge management system that maintains a personal "palace" of facts and relationships. Implementing contradiction detection in MemPalace allows the system to catch factual errors, outdated information, and potential confusions before they pollute your knowledge base. The entire detection pipeline operates locally using SQLite and JSON files, ensuring no sensitive data leaves your machine.
How Contradiction Detection Works in MemPalace
The detection system in mempalace/fact_checker.py operates as an offline validation layer. When you submit text for checking, the system cross-references two internal data structures to identify potential issues.
The Two Data Sources
MemPalace maintains two distinct knowledge stores for validation:
- Entity Registry – A JSON dictionary containing known people, projects, and concepts loaded via
mempalace/entity_registry.py(specifically the_load_known_entities_rawfunction) - Knowledge Graph (KG) – A temporal SQLite database stored at
palace_path/knowledge_graph.sqlite3that records relationships between entities with validity windows (e.g., "Bob is Alice's brother" valid from 2020-01-01 to null)
The Detection Pipeline
The main entry point check_text(text, palace_path) in mempalace/fact_checker.py orchestrates the validation process. It returns a list of detected issues, running two primary checks sequentially:
_check_entity_confusion– Identifies potential typos or similar names_check_kg_contradictions– Validates relationship claims against stored facts
Core Detection Logic in fact_checker.py
The fact_checker.py module contains the primary contradiction detection engine, implementing two distinct validation strategies.
Similar-Name Confusion Detection
The _check_entity_confusion method (lines 96-149) prevents subtle data entry errors by detecting names that appear in input text but differ by ≤2 edit distance from a different registered name. This catches typical typos that might create duplicate or confused entities.
The implementation uses a fast edit-distance helper _edit_distance (lines 89-108) to compare extracted names against the Entity Registry without requiring fuzzy database queries.
Knowledge Graph Contradiction Detection
The _check_kg_contradictions method (lines 82-127) handles semantic validation by parsing relationship claims and querying the temporal Knowledge Graph. It detects two specific contradiction types:
- Relationship mismatch – When the text claims "Bob is Alice's brother" but the KG records Bob as Alice's husband
- Stale fact – When the claim matches a KG entry that has expired (its
valid_todate precedes today)
Parsing Claims from Text
Before the Knowledge Graph can validate relationships, the system must extract structured semantic triples from unstructured text.
Regex Pattern Matching
The _extract_claims function (lines 55-79) uses compiled patterns stored in _RELATIONSHIP_PATTERNS to identify relationship statements. The default patterns recognize:
- "X is Y's Z" (e.g., "Bob is Alice's brother")
- "X's Z is Y" (e.g., "Alice's brother is Bob")
Each match yields a triple tuple of (subject, predicate, object) that represents the semantic claim for KG validation.
Extracting Semantic Triples
Once extracted, claims are validated against the Knowledge Graph instance created at line 104 in fact_checker.py, which points to palace_path/knowledge_graph.sqlite3. The KnowledgeGraph class defined in mempalace/knowledge_graph.py provides the query interface.
Querying the Temporal Knowledge Graph
The Knowledge Graph implementation in mempalace/knowledge_graph.py supports temporal validity, allowing facts to have finite lifespans.
Relationship Mismatch Detection
For each extracted claim, the system queries outgoing facts for the subject using query_entity(name, as_of=None, direction="outgoing"). If the KG contains a fact sharing the same object but a different predicate, the system generates a relationship_mismatch issue (lines 27-50 in fact_checker.py).
The temporal filtering uses _temporal_filter_sql to ensure only currently valid facts participate in the contradiction check unless a specific as_of date is provided.
Stale Fact Detection
When a claim exactly matches a KG entry but the entry's valid_to date (validated via sanitize_iso_temporal from mempalace/config.py) precedes the current date, the system flags a stale_fact issue (lines 52-65). This prevents users from asserting relationships that have explicitly expired.
Practical Implementation Examples
Basic Python API Usage
Import the check_text function to validate strings programmatically:
from mempalace.fact_checker import check_text
# Detect contradictions in a user message
issues = check_text(
"Bob is Alice's brother",
palace_path="/home/user/.mempalace/palace"
)
for issue in issues:
print(issue["type"], "→", issue["detail"])
CLI Invocation
Run contradiction detection from the command line:
$ python -m mempalace.fact_checker "Bob is Alice's brother" \
--palace /home/user/.mempalace/palace
When a mismatch is detected, the CLI outputs structured JSON:
[
{
"type": "relationship_mismatch",
"detail": "Text says 'Bob is Alice's brother' but KG records Bob husband Alice",
"entity": "Bob",
"claim": {"predicate": "brother", "object": "Alice"},
"kg_fact": {"predicate": "husband", "object": "Alice"}
}
]
Extending Detection with Custom Patterns
Add new relationship types by appending compiled regex patterns to _RELATIONSHIP_PATTERNS in mempalace/fact_checker.py:
import re
# Add support for "works with" relationships
_RELATIONSHIP_PATTERNS.append(
re.compile(r"\b([A-Z][\w-]+)\s+works\s+with\s+([A-Z][\w-]+)\b")
)
Now statements like "Bob works with Alice" will be parsed and validated against the Knowledge Graph.
Summary
- MemPalace contradiction detection operates entirely offline in
mempalace/fact_checker.py, comparing text against local JSON and SQLite data stores. - Entity confusion detection uses edit-distance calculations in
_check_entity_confusionto catch typos and similar names. - Knowledge Graph validation extracts semantic triples via
_extract_claimsand checks them against temporal facts inknowledge_graph.sqlite3. - Two contradiction types are identified:
relationship_mismatch(conflicting predicates) andstale_fact(expired validity windows). - Zero external dependencies preserve the privacy-first architecture—no API calls are required for fact validation.
- Extensible architecture allows custom regex patterns and additional check functions to be integrated into the
check_textpipeline.
Frequently Asked Questions
How does MemPalace handle temporal facts that change over time?
The Knowledge Graph in mempalace/knowledge_graph.py stores each relationship with optional valid_from and valid_to timestamps. When query_entity is called, the _temporal_filter_sql helper applies the as_of parameter (defaulting to the current date) to return only facts valid at that specific time. This allows the system to detect stale_fact contradictions when users assert relationships that have expired, while still maintaining historical accuracy in the database.
Can I use contradiction detection without the full MemPalace application?
Yes, the fact_checker.py module is self-contained. You can import check_text into any Python script, provided you supply a valid palace_path containing the knowledge_graph.sqlite3 file and entity registry JSON. The CLI interface also allows standalone operation via python -m mempalace.fact_checker, making it suitable for integration with external scripts or git hooks.
What edit distance threshold does MemPalace use for entity confusion detection?
The _check_entity_confusion function flags names that differ by ≤2 edit distance from a registered entity name, provided they are not identical matches. This threshold is implemented in lines 96-149 of fact_checker.py using the internal _edit_distance helper (lines 89-108), which performs a fast dynamic programming calculation optimized for short strings typical of personal knowledge bases.
How can I add support for non-English relationship patterns?
Extend the _RELATIONSHIP_PATTERNS list in mempalace/fact_checker.py with compiled regex patterns matching your target language's relationship syntax. Ensure your patterns capture named groups or return tuples matching the (subject, predicate, object) format expected by _check_kg_contradictions. Since the KG stores raw strings, non-English entities and predicates are fully supported without modification to the KnowledgeGraph class in mempalace/knowledge_graph.py.
Have a question about this repo?
These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:
curl -s "https://instagit.com/install.md" Maintain an open-source project? Get it listed too →