Compare commits

...
Author SHA1 Message Date
Nicolò Boschi f515b8207b chore: run generate scripts after dead code removal 2026-03-06 14:25:16 +01:00
Nicolò Boschi 0e3ccd038b refactor: remove dead code and clarify observations vs mental models
- Delete engine/mental_models/ module (stale Pydantic models with wrong
  schema, describing an old design where mental models were directives;
  had no importers outside itself)
- Remove unused imports in api/http.py (acquire_with_retry, Observation)
- Remove unused Pydantic models in api/http.py (BanksResponse,
  ObservationEvidenceResponse)
- Add clarifying NOTE to consolidation/consolidator.py distinguishing
  observations (auto-generated bottom-up) from mental models (user-defined
  pinned reflections refreshed via reflect)
2026-03-06 14:00:26 +01:00
4 changed files with 4 additions and 86 deletions
-19
View File
@@ -71,9 +71,7 @@ def FieldWithDefault(default_factory: Callable, **kwargs) -> Any:
from hindsight_api.config import get_config
from hindsight_api.engine.db_utils import acquire_with_retry
from hindsight_api.engine.memory_engine import Budget, _current_schema, _get_tiktoken_encoding, fq_table
from hindsight_api.engine.reflect.observations import Observation
from hindsight_api.engine.response_models import VALID_RECALL_FACT_TYPES, MemoryFact, TokenUsage
from hindsight_api.engine.search.tags import TagsMatch
from hindsight_api.extensions import HttpExtension, OperationValidationError, load_extension
@@ -759,14 +757,6 @@ class ReflectResponse(BaseModel):
)
class BanksResponse(BaseModel):
"""Response model for banks list endpoint."""
model_config = ConfigDict(json_schema_extra={"example": {"banks": ["user123", "bank_alice", "bank_bob"]}})
banks: list[str]
class DispositionTraits(BaseModel):
"""Disposition traits that influence how memories are formed and interpreted."""
@@ -1305,15 +1295,6 @@ class BankStatsResponse(BaseModel):
# Mental Model models
class ObservationEvidenceResponse(BaseModel):
"""A single piece of evidence supporting an observation."""
memory_id: str = Field(description="ID of the memory unit this evidence comes from")
quote: str = Field(description="Exact quote from the memory supporting the observation")
relevance: str = Field(description="Brief explanation of how this quote supports the observation")
timestamp: str = Field(description="When the source memory was created (ISO format)")
# =========================================================================
# Directive Models
# =========================================================================
@@ -9,6 +9,10 @@ Observations are stored in memory_units with fact_type='observation' and include
- proof_count: Number of supporting memories
- source_memory_ids: Array of memory UUIDs that contribute to this observation
- history: JSONB tracking changes over time
NOTE: Observations are distinct from mental models (pinned reflections).
- Observations: auto-generated bottom-up by this engine from raw facts (memory_units table, fact_type='observation')
- Mental models: user-defined queries stored in the mental_models table, refreshed on demand via reflect
"""
import json
@@ -1,14 +0,0 @@
"""
Mental models module for Hindsight.
Mental models contain directives - hard rules that are injected into reflect prompts.
Directives are user-defined and their observations are user-provided (not LLM-generated).
Other types of consolidated knowledge are handled by:
- Learnings: Automatic bottom-up consolidation from facts
- Pinned Reflections: User-curated living documents
"""
from .models import MentalModel, MentalModelSubtype
__all__ = ["MentalModel", "MentalModelSubtype"]
@@ -1,53 +0,0 @@
"""
Pydantic models for mental models.
"""
from datetime import datetime, timezone
from enum import Enum
from pydantic import BaseModel, Field
class MentalModelSubtype(str, Enum):
"""Subtype of mental model.
Currently only DIRECTIVE is supported. Other types of consolidated knowledge
are handled by:
- Learnings: Automatic bottom-up consolidation from facts
- Pinned Reflections: User-curated living documents
"""
DIRECTIVE = "directive" # User-defined hard rules, observations user-provided
class MentalModel(BaseModel):
"""
A mental model representing synthesized understanding.
Mental models are the agent's consolidated knowledge. Unlike raw facts,
mental models provide:
- A one-liner description for quick scanning/retrieval
- A full summary for deep understanding
- Links to related mental models
"""
id: str = Field(description="Unique identifier within the bank")
bank_id: str = Field(description="Bank this mental model belongs to")
subtype: MentalModelSubtype = Field(description="How this model was created")
name: str = Field(description="Human-readable name")
description: str = Field(description="One-liner for quick scanning and retrieval matching")
summary: str | None = Field(default=None, description="Full synthesized understanding")
# References
entity_id: str | None = Field(default=None, description="Reference to entities table when type=entity")
source_facts: list[str] = Field(default_factory=list, description="Fact IDs used to generate summary")
links: list[str] = Field(default_factory=list, description="Related mental model IDs")
# Tags for scoped visibility (similar to document tags)
tags: list[str] = Field(default_factory=list, description="Tags for scoped visibility filtering")
# Timestamps
last_updated: datetime | None = Field(default=None, description="When summary was last regenerated")
created_at: datetime = Field(
default_factory=lambda: datetime.now(timezone.utc), description="When this model was created"
)